setup-bus.c (14c8530dbc1b7cd5020c44b391e34bdb731fd098) | setup-bus.c (5b28541552ef5eeffc41d6936105f38c2508e566) |
---|---|
1/* 2 * drivers/pci/setup-bus.c 3 * 4 * Extruded from code written by 5 * Dave Rusling (david.rusling@reo.mts.dec.com) 6 * David Mosberger (davidm@cs.arizona.edu) 7 * David Miller (davem@redhat.com) 8 * --- 699 unchanged lines hidden (view full) --- 708 mem_base_hi); 709 } 710} 711 712/* Helper function for sizing routines: find first available 713 bus resource of a given type. Note: we intentionally skip 714 the bus resources which have already been assigned (that is, 715 have non-NULL parent resource). */ | 1/* 2 * drivers/pci/setup-bus.c 3 * 4 * Extruded from code written by 5 * Dave Rusling (david.rusling@reo.mts.dec.com) 6 * David Mosberger (davidm@cs.arizona.edu) 7 * David Miller (davem@redhat.com) 8 * --- 699 unchanged lines hidden (view full) --- 708 mem_base_hi); 709 } 710} 711 712/* Helper function for sizing routines: find first available 713 bus resource of a given type. Note: we intentionally skip 714 the bus resources which have already been assigned (that is, 715 have non-NULL parent resource). */ |
716static struct resource *find_free_bus_resource(struct pci_bus *bus, unsigned long type) | 716static struct resource *find_free_bus_resource(struct pci_bus *bus, 717 unsigned long type_mask, unsigned long type) |
717{ 718 int i; 719 struct resource *r; | 718{ 719 int i; 720 struct resource *r; |
720 unsigned long type_mask = IORESOURCE_IO | IORESOURCE_MEM | 721 IORESOURCE_PREFETCH; | |
722 723 pci_bus_for_each_resource(bus, r, i) { 724 if (r == &ioport_resource || r == &iomem_resource) 725 continue; 726 if (r && (r->flags & type_mask) == type && !r->parent) 727 return r; 728 } 729 return NULL; --- 80 unchanged lines hidden (view full) --- 810 * since these windows have 1K or 4K granularity and the IO ranges 811 * of non-bridge PCI devices are limited to 256 bytes. 812 * We must be careful with the ISA aliasing though. 813 */ 814static void pbus_size_io(struct pci_bus *bus, resource_size_t min_size, 815 resource_size_t add_size, struct list_head *realloc_head) 816{ 817 struct pci_dev *dev; | 721 722 pci_bus_for_each_resource(bus, r, i) { 723 if (r == &ioport_resource || r == &iomem_resource) 724 continue; 725 if (r && (r->flags & type_mask) == type && !r->parent) 726 return r; 727 } 728 return NULL; --- 80 unchanged lines hidden (view full) --- 809 * since these windows have 1K or 4K granularity and the IO ranges 810 * of non-bridge PCI devices are limited to 256 bytes. 811 * We must be careful with the ISA aliasing though. 812 */ 813static void pbus_size_io(struct pci_bus *bus, resource_size_t min_size, 814 resource_size_t add_size, struct list_head *realloc_head) 815{ 816 struct pci_dev *dev; |
818 struct resource *b_res = find_free_bus_resource(bus, IORESOURCE_IO); | 817 struct resource *b_res = find_free_bus_resource(bus, IORESOURCE_IO, 818 IORESOURCE_IO); |
819 resource_size_t size = 0, size0 = 0, size1 = 0; 820 resource_size_t children_add_size = 0; 821 resource_size_t min_align, align; 822 823 if (!b_res) 824 return; 825 826 min_align = window_alignment(bus, IORESOURCE_IO); --- 75 unchanged lines hidden (view full) --- 902} 903 904/** 905 * pbus_size_mem() - size the memory window of a given bus 906 * 907 * @bus : the bus 908 * @mask: mask the resource flag, then compare it with type 909 * @type: the type of free resource from bridge | 819 resource_size_t size = 0, size0 = 0, size1 = 0; 820 resource_size_t children_add_size = 0; 821 resource_size_t min_align, align; 822 823 if (!b_res) 824 return; 825 826 min_align = window_alignment(bus, IORESOURCE_IO); --- 75 unchanged lines hidden (view full) --- 902} 903 904/** 905 * pbus_size_mem() - size the memory window of a given bus 906 * 907 * @bus : the bus 908 * @mask: mask the resource flag, then compare it with type 909 * @type: the type of free resource from bridge |
910 * @type2: second match type 911 * @type3: third match type |
|
910 * @min_size : the minimum memory window that must to be allocated 911 * @add_size : additional optional memory window 912 * @realloc_head : track the additional memory window on this list 913 * 914 * Calculate the size of the bus and minimal alignment which 915 * guarantees that all child resources fit in this size. 916 */ 917static int pbus_size_mem(struct pci_bus *bus, unsigned long mask, | 912 * @min_size : the minimum memory window that must to be allocated 913 * @add_size : additional optional memory window 914 * @realloc_head : track the additional memory window on this list 915 * 916 * Calculate the size of the bus and minimal alignment which 917 * guarantees that all child resources fit in this size. 918 */ 919static int pbus_size_mem(struct pci_bus *bus, unsigned long mask, |
918 unsigned long type, resource_size_t min_size, 919 resource_size_t add_size, 920 struct list_head *realloc_head) | 920 unsigned long type, unsigned long type2, 921 unsigned long type3, 922 resource_size_t min_size, resource_size_t add_size, 923 struct list_head *realloc_head) |
921{ 922 struct pci_dev *dev; 923 resource_size_t min_align, align, size, size0, size1; 924 resource_size_t aligns[14]; /* Alignments from 1Mb to 8Gb */ 925 int order, max_order; | 924{ 925 struct pci_dev *dev; 926 resource_size_t min_align, align, size, size0, size1; 927 resource_size_t aligns[14]; /* Alignments from 1Mb to 8Gb */ 928 int order, max_order; |
926 struct resource *b_res = find_free_bus_resource(bus, type); 927 unsigned int mem64_mask = 0; | 929 struct resource *b_res = find_free_bus_resource(bus, 930 mask | IORESOURCE_PREFETCH, type); |
928 resource_size_t children_add_size = 0; 929 930 if (!b_res) 931 return 0; 932 933 memset(aligns, 0, sizeof(aligns)); 934 max_order = 0; 935 size = 0; 936 | 931 resource_size_t children_add_size = 0; 932 933 if (!b_res) 934 return 0; 935 936 memset(aligns, 0, sizeof(aligns)); 937 max_order = 0; 938 size = 0; 939 |
937 mem64_mask = b_res->flags & IORESOURCE_MEM_64; 938 b_res->flags &= ~IORESOURCE_MEM_64; 939 | |
940 list_for_each_entry(dev, &bus->devices, bus_list) { 941 int i; 942 943 for (i = 0; i < PCI_NUM_RESOURCES; i++) { 944 struct resource *r = &dev->resource[i]; 945 resource_size_t r_size; 946 | 940 list_for_each_entry(dev, &bus->devices, bus_list) { 941 int i; 942 943 for (i = 0; i < PCI_NUM_RESOURCES; i++) { 944 struct resource *r = &dev->resource[i]; 945 resource_size_t r_size; 946 |
947 if (r->parent || (r->flags & mask) != type) | 947 if (r->parent || ((r->flags & mask) != type && 948 (r->flags & mask) != type2 && 949 (r->flags & mask) != type3)) |
948 continue; 949 r_size = resource_size(r); 950#ifdef CONFIG_PCI_IOV 951 /* put SRIOV requested res to the optional list */ 952 if (realloc_head && i >= PCI_IOV_RESOURCES && 953 i <= PCI_IOV_RESOURCE_END) { 954 r->end = r->start - 1; 955 add_to_list(realloc_head, dev, r, r_size, 0/* don't care */); --- 20 unchanged lines hidden (view full) --- 976 } 977 size += r_size; 978 /* Exclude ranges with size > align from 979 calculation of the alignment. */ 980 if (r_size == align) 981 aligns[order] += align; 982 if (order > max_order) 983 max_order = order; | 950 continue; 951 r_size = resource_size(r); 952#ifdef CONFIG_PCI_IOV 953 /* put SRIOV requested res to the optional list */ 954 if (realloc_head && i >= PCI_IOV_RESOURCES && 955 i <= PCI_IOV_RESOURCE_END) { 956 r->end = r->start - 1; 957 add_to_list(realloc_head, dev, r, r_size, 0/* don't care */); --- 20 unchanged lines hidden (view full) --- 978 } 979 size += r_size; 980 /* Exclude ranges with size > align from 981 calculation of the alignment. */ 982 if (r_size == align) 983 aligns[order] += align; 984 if (order > max_order) 985 max_order = order; |
984 mem64_mask &= r->flags & IORESOURCE_MEM_64; | |
985 986 if (realloc_head) 987 children_add_size += get_res_add_size(realloc_head, r); 988 } 989 } 990 991 min_align = calculate_mem_align(aligns, max_order); 992 min_align = max(min_align, window_alignment(bus, b_res->flags)); --- 8 unchanged lines hidden (view full) --- 1001 dev_info(&bus->self->dev, "disabling bridge window " 1002 "%pR to %pR (unused)\n", b_res, 1003 &bus->busn_res); 1004 b_res->flags = 0; 1005 return 1; 1006 } 1007 b_res->start = min_align; 1008 b_res->end = size0 + min_align - 1; | 986 987 if (realloc_head) 988 children_add_size += get_res_add_size(realloc_head, r); 989 } 990 } 991 992 min_align = calculate_mem_align(aligns, max_order); 993 min_align = max(min_align, window_alignment(bus, b_res->flags)); --- 8 unchanged lines hidden (view full) --- 1002 dev_info(&bus->self->dev, "disabling bridge window " 1003 "%pR to %pR (unused)\n", b_res, 1004 &bus->busn_res); 1005 b_res->flags = 0; 1006 return 1; 1007 } 1008 b_res->start = min_align; 1009 b_res->end = size0 + min_align - 1; |
1009 b_res->flags |= IORESOURCE_STARTALIGN | mem64_mask; | 1010 b_res->flags |= IORESOURCE_STARTALIGN; |
1010 if (size1 > size0 && realloc_head) { 1011 add_to_list(realloc_head, bus->self, b_res, size1-size0, min_align); 1012 dev_printk(KERN_DEBUG, &bus->self->dev, "bridge window " 1013 "%pR to %pR add_size %llx\n", b_res, 1014 &bus->busn_res, (unsigned long long)size1-size0); 1015 } 1016 return 1; 1017} --- 99 unchanged lines hidden (view full) --- 1117handle_done: 1118 ; 1119} 1120 1121void __ref __pci_bus_size_bridges(struct pci_bus *bus, 1122 struct list_head *realloc_head) 1123{ 1124 struct pci_dev *dev; | 1011 if (size1 > size0 && realloc_head) { 1012 add_to_list(realloc_head, bus->self, b_res, size1-size0, min_align); 1013 dev_printk(KERN_DEBUG, &bus->self->dev, "bridge window " 1014 "%pR to %pR add_size %llx\n", b_res, 1015 &bus->busn_res, (unsigned long long)size1-size0); 1016 } 1017 return 1; 1018} --- 99 unchanged lines hidden (view full) --- 1118handle_done: 1119 ; 1120} 1121 1122void __ref __pci_bus_size_bridges(struct pci_bus *bus, 1123 struct list_head *realloc_head) 1124{ 1125 struct pci_dev *dev; |
1125 unsigned long mask, prefmask; | 1126 unsigned long mask, prefmask, type2 = 0, type3 = 0; |
1126 resource_size_t additional_mem_size = 0, additional_io_size = 0; | 1127 resource_size_t additional_mem_size = 0, additional_io_size = 0; |
1128 struct resource *b_res; |
|
1127 1128 list_for_each_entry(dev, &bus->devices, bus_list) { 1129 struct pci_bus *b = dev->subordinate; 1130 if (!b) 1131 continue; 1132 1133 switch (dev->class >> 8) { 1134 case PCI_CLASS_BRIDGE_CARDBUS: --- 28 unchanged lines hidden (view full) --- 1163 default: 1164 pbus_size_io(bus, realloc_head ? 0 : additional_io_size, 1165 additional_io_size, realloc_head); 1166 /* If the bridge supports prefetchable range, size it 1167 separately. If it doesn't, or its prefetchable window 1168 has already been allocated by arch code, try 1169 non-prefetchable range for both types of PCI memory 1170 resources. */ | 1129 1130 list_for_each_entry(dev, &bus->devices, bus_list) { 1131 struct pci_bus *b = dev->subordinate; 1132 if (!b) 1133 continue; 1134 1135 switch (dev->class >> 8) { 1136 case PCI_CLASS_BRIDGE_CARDBUS: --- 28 unchanged lines hidden (view full) --- 1165 default: 1166 pbus_size_io(bus, realloc_head ? 0 : additional_io_size, 1167 additional_io_size, realloc_head); 1168 /* If the bridge supports prefetchable range, size it 1169 separately. If it doesn't, or its prefetchable window 1170 has already been allocated by arch code, try 1171 non-prefetchable range for both types of PCI memory 1172 resources. */ |
1173 b_res = &bus->self->resource[PCI_BRIDGE_RESOURCES]; |
|
1171 mask = IORESOURCE_MEM; 1172 prefmask = IORESOURCE_MEM | IORESOURCE_PREFETCH; | 1174 mask = IORESOURCE_MEM; 1175 prefmask = IORESOURCE_MEM | IORESOURCE_PREFETCH; |
1173 if (pbus_size_mem(bus, prefmask, prefmask, | 1176 if (b_res[2].flags & IORESOURCE_MEM_64) { 1177 prefmask |= IORESOURCE_MEM_64; 1178 if (pbus_size_mem(bus, prefmask, prefmask, 1179 prefmask, prefmask, |
1174 realloc_head ? 0 : additional_mem_size, | 1180 realloc_head ? 0 : additional_mem_size, |
1175 additional_mem_size, realloc_head)) 1176 mask = prefmask; /* Success, size non-prefetch only. */ 1177 else 1178 additional_mem_size += additional_mem_size; 1179 pbus_size_mem(bus, mask, IORESOURCE_MEM, | 1181 additional_mem_size, realloc_head)) { 1182 /* 1183 * Success, with pref mmio64, 1184 * next will size non-pref or 1185 * non-mmio64 */ 1186 mask = prefmask; 1187 type2 = prefmask & ~IORESOURCE_MEM_64; 1188 type3 = prefmask & ~IORESOURCE_PREFETCH; 1189 } 1190 } 1191 if (!type2) { 1192 prefmask &= ~IORESOURCE_MEM_64; 1193 if (pbus_size_mem(bus, prefmask, prefmask, 1194 prefmask, prefmask, 1195 realloc_head ? 0 : additional_mem_size, 1196 additional_mem_size, realloc_head)) { 1197 /* Success, next will size non-prefetch. */ 1198 mask = prefmask; 1199 } else 1200 additional_mem_size += additional_mem_size; 1201 type2 = type3 = IORESOURCE_MEM; 1202 } 1203 pbus_size_mem(bus, mask, IORESOURCE_MEM, type2, type3, |
1180 realloc_head ? 0 : additional_mem_size, 1181 additional_mem_size, realloc_head); 1182 break; 1183 } 1184} 1185 1186void __ref pci_bus_size_bridges(struct pci_bus *bus) 1187{ --- 69 unchanged lines hidden (view full) --- 1257 dev_info(&bridge->dev, "not setting up bridge for bus " 1258 "%04x:%02x\n", pci_domain_nr(b), b->number); 1259 break; 1260 } 1261} 1262static void pci_bridge_release_resources(struct pci_bus *bus, 1263 unsigned long type) 1264{ | 1204 realloc_head ? 0 : additional_mem_size, 1205 additional_mem_size, realloc_head); 1206 break; 1207 } 1208} 1209 1210void __ref pci_bus_size_bridges(struct pci_bus *bus) 1211{ --- 69 unchanged lines hidden (view full) --- 1281 dev_info(&bridge->dev, "not setting up bridge for bus " 1282 "%04x:%02x\n", pci_domain_nr(b), b->number); 1283 break; 1284 } 1285} 1286static void pci_bridge_release_resources(struct pci_bus *bus, 1287 unsigned long type) 1288{ |
1265 int idx; 1266 bool changed = false; 1267 struct pci_dev *dev; | 1289 struct pci_dev *dev = bus->self; |
1268 struct resource *r; 1269 unsigned long type_mask = IORESOURCE_IO | IORESOURCE_MEM | | 1290 struct resource *r; 1291 unsigned long type_mask = IORESOURCE_IO | IORESOURCE_MEM | |
1270 IORESOURCE_PREFETCH; | 1292 IORESOURCE_PREFETCH | IORESOURCE_MEM_64; 1293 unsigned old_flags = 0; 1294 struct resource *b_res; 1295 int idx = 1; |
1271 | 1296 |
1272 dev = bus->self; 1273 for (idx = PCI_BRIDGE_RESOURCES; idx <= PCI_BRIDGE_RESOURCE_END; 1274 idx++) { 1275 r = &dev->resource[idx]; 1276 if ((r->flags & type_mask) != type) 1277 continue; 1278 if (!r->parent) 1279 continue; 1280 /* 1281 * if there are children under that, we should release them 1282 * all 1283 */ 1284 release_child_resources(r); 1285 if (!release_resource(r)) { 1286 dev_printk(KERN_DEBUG, &dev->dev, 1287 "resource %d %pR released\n", idx, r); 1288 /* keep the old size */ 1289 r->end = resource_size(r) - 1; 1290 r->start = 0; 1291 r->flags = 0; 1292 changed = true; 1293 } 1294 } | 1297 b_res = &dev->resource[PCI_BRIDGE_RESOURCES]; |
1295 | 1298 |
1296 if (changed) { | 1299 /* 1300 * 1. if there is io port assign fail, will release bridge 1301 * io port. 1302 * 2. if there is non pref mmio assign fail, release bridge 1303 * nonpref mmio. 1304 * 3. if there is 64bit pref mmio assign fail, and bridge pref 1305 * is 64bit, release bridge pref mmio. 1306 * 4. if there is pref mmio assign fail, and bridge pref is 1307 * 32bit mmio, release bridge pref mmio 1308 * 5. if there is pref mmio assign fail, and bridge pref is not 1309 * assigned, release bridge nonpref mmio. 1310 */ 1311 if (type & IORESOURCE_IO) 1312 idx = 0; 1313 else if (!(type & IORESOURCE_PREFETCH)) 1314 idx = 1; 1315 else if ((type & IORESOURCE_MEM_64) && 1316 (b_res[2].flags & IORESOURCE_MEM_64)) 1317 idx = 2; 1318 else if (!(b_res[2].flags & IORESOURCE_MEM_64) && 1319 (b_res[2].flags & IORESOURCE_PREFETCH)) 1320 idx = 2; 1321 else 1322 idx = 1; 1323 1324 r = &b_res[idx]; 1325 1326 if (!r->parent) 1327 return; 1328 1329 /* 1330 * if there are children under that, we should release them 1331 * all 1332 */ 1333 release_child_resources(r); 1334 if (!release_resource(r)) { 1335 type = old_flags = r->flags & type_mask; 1336 dev_printk(KERN_DEBUG, &dev->dev, "resource %d %pR released\n", 1337 PCI_BRIDGE_RESOURCES + idx, r); 1338 /* keep the old size */ 1339 r->end = resource_size(r) - 1; 1340 r->start = 0; 1341 r->flags = 0; 1342 |
1297 /* avoiding touch the one without PREF */ 1298 if (type & IORESOURCE_PREFETCH) 1299 type = IORESOURCE_PREFETCH; 1300 __pci_setup_bridge(bus, type); | 1343 /* avoiding touch the one without PREF */ 1344 if (type & IORESOURCE_PREFETCH) 1345 type = IORESOURCE_PREFETCH; 1346 __pci_setup_bridge(bus, type); |
1347 /* for next child res under same bridge */ 1348 r->flags = old_flags; |
|
1301 } 1302} 1303 1304enum release_type { 1305 leaf_only, 1306 whole_subtree, 1307}; 1308/* --- 162 unchanged lines hidden (view full) --- 1471 LIST_HEAD(realloc_head); /* list of resources that 1472 want additional resources */ 1473 struct list_head *add_list = NULL; 1474 int tried_times = 0; 1475 enum release_type rel_type = leaf_only; 1476 LIST_HEAD(fail_head); 1477 struct pci_dev_resource *fail_res; 1478 unsigned long type_mask = IORESOURCE_IO | IORESOURCE_MEM | | 1349 } 1350} 1351 1352enum release_type { 1353 leaf_only, 1354 whole_subtree, 1355}; 1356/* --- 162 unchanged lines hidden (view full) --- 1519 LIST_HEAD(realloc_head); /* list of resources that 1520 want additional resources */ 1521 struct list_head *add_list = NULL; 1522 int tried_times = 0; 1523 enum release_type rel_type = leaf_only; 1524 LIST_HEAD(fail_head); 1525 struct pci_dev_resource *fail_res; 1526 unsigned long type_mask = IORESOURCE_IO | IORESOURCE_MEM | |
1479 IORESOURCE_PREFETCH; | 1527 IORESOURCE_PREFETCH | IORESOURCE_MEM_64; |
1480 int pci_try_num = 1; 1481 enum enable_type enable_local; 1482 1483 /* don't realloc if asked to do so */ 1484 enable_local = pci_realloc_detect(bus, pci_realloc_enable); 1485 if (pci_realloc_enabled(enable_local)) { 1486 int max_depth = pci_bus_get_depth(bus); 1487 --- 158 unchanged lines hidden --- | 1528 int pci_try_num = 1; 1529 enum enable_type enable_local; 1530 1531 /* don't realloc if asked to do so */ 1532 enable_local = pci_realloc_detect(bus, pci_realloc_enable); 1533 if (pci_realloc_enabled(enable_local)) { 1534 int max_depth = pci_bus_get_depth(bus); 1535 --- 158 unchanged lines hidden --- |