diff options
Diffstat (limited to 'drivers/pci/probe.c')
-rw-r--r-- | drivers/pci/probe.c | 185 |
1 files changed, 48 insertions, 137 deletions
diff --git a/drivers/pci/probe.c b/drivers/pci/probe.c index 36698e57b97f..aaaf0a1fed22 100644 --- a/drivers/pci/probe.c +++ b/drivers/pci/probe.c | |||
@@ -14,8 +14,6 @@ | |||
14 | 14 | ||
15 | #define CARDBUS_LATENCY_TIMER 176 /* secondary latency timer */ | 15 | #define CARDBUS_LATENCY_TIMER 176 /* secondary latency timer */ |
16 | #define CARDBUS_RESERVE_BUSNR 3 | 16 | #define CARDBUS_RESERVE_BUSNR 3 |
17 | #define PCI_CFG_SPACE_SIZE 256 | ||
18 | #define PCI_CFG_SPACE_EXP_SIZE 4096 | ||
19 | 17 | ||
20 | /* Ugh. Need to stop exporting this to modules. */ | 18 | /* Ugh. Need to stop exporting this to modules. */ |
21 | LIST_HEAD(pci_root_buses); | 19 | LIST_HEAD(pci_root_buses); |
@@ -44,72 +42,6 @@ int no_pci_devices(void) | |||
44 | } | 42 | } |
45 | EXPORT_SYMBOL(no_pci_devices); | 43 | EXPORT_SYMBOL(no_pci_devices); |
46 | 44 | ||
47 | #ifdef HAVE_PCI_LEGACY | ||
48 | /** | ||
49 | * pci_create_legacy_files - create legacy I/O port and memory files | ||
50 | * @b: bus to create files under | ||
51 | * | ||
52 | * Some platforms allow access to legacy I/O port and ISA memory space on | ||
53 | * a per-bus basis. This routine creates the files and ties them into | ||
54 | * their associated read, write and mmap files from pci-sysfs.c | ||
55 | * | ||
56 | * On error unwind, but don't propogate the error to the caller | ||
57 | * as it is ok to set up the PCI bus without these files. | ||
58 | */ | ||
59 | static void pci_create_legacy_files(struct pci_bus *b) | ||
60 | { | ||
61 | int error; | ||
62 | |||
63 | b->legacy_io = kzalloc(sizeof(struct bin_attribute) * 2, | ||
64 | GFP_ATOMIC); | ||
65 | if (!b->legacy_io) | ||
66 | goto kzalloc_err; | ||
67 | |||
68 | b->legacy_io->attr.name = "legacy_io"; | ||
69 | b->legacy_io->size = 0xffff; | ||
70 | b->legacy_io->attr.mode = S_IRUSR | S_IWUSR; | ||
71 | b->legacy_io->read = pci_read_legacy_io; | ||
72 | b->legacy_io->write = pci_write_legacy_io; | ||
73 | error = device_create_bin_file(&b->dev, b->legacy_io); | ||
74 | if (error) | ||
75 | goto legacy_io_err; | ||
76 | |||
77 | /* Allocated above after the legacy_io struct */ | ||
78 | b->legacy_mem = b->legacy_io + 1; | ||
79 | b->legacy_mem->attr.name = "legacy_mem"; | ||
80 | b->legacy_mem->size = 1024*1024; | ||
81 | b->legacy_mem->attr.mode = S_IRUSR | S_IWUSR; | ||
82 | b->legacy_mem->mmap = pci_mmap_legacy_mem; | ||
83 | error = device_create_bin_file(&b->dev, b->legacy_mem); | ||
84 | if (error) | ||
85 | goto legacy_mem_err; | ||
86 | |||
87 | return; | ||
88 | |||
89 | legacy_mem_err: | ||
90 | device_remove_bin_file(&b->dev, b->legacy_io); | ||
91 | legacy_io_err: | ||
92 | kfree(b->legacy_io); | ||
93 | b->legacy_io = NULL; | ||
94 | kzalloc_err: | ||
95 | printk(KERN_WARNING "pci: warning: could not create legacy I/O port " | ||
96 | "and ISA memory resources to sysfs\n"); | ||
97 | return; | ||
98 | } | ||
99 | |||
100 | void pci_remove_legacy_files(struct pci_bus *b) | ||
101 | { | ||
102 | if (b->legacy_io) { | ||
103 | device_remove_bin_file(&b->dev, b->legacy_io); | ||
104 | device_remove_bin_file(&b->dev, b->legacy_mem); | ||
105 | kfree(b->legacy_io); /* both are allocated here */ | ||
106 | } | ||
107 | } | ||
108 | #else /* !HAVE_PCI_LEGACY */ | ||
109 | static inline void pci_create_legacy_files(struct pci_bus *bus) { return; } | ||
110 | void pci_remove_legacy_files(struct pci_bus *bus) { return; } | ||
111 | #endif /* HAVE_PCI_LEGACY */ | ||
112 | |||
113 | /* | 45 | /* |
114 | * PCI Bus Class Devices | 46 | * PCI Bus Class Devices |
115 | */ | 47 | */ |
@@ -219,7 +151,7 @@ static inline enum pci_bar_type decode_bar(struct resource *res, u32 bar) | |||
219 | 151 | ||
220 | res->flags = bar & ~PCI_BASE_ADDRESS_MEM_MASK; | 152 | res->flags = bar & ~PCI_BASE_ADDRESS_MEM_MASK; |
221 | 153 | ||
222 | if (res->flags == PCI_BASE_ADDRESS_MEM_TYPE_64) | 154 | if (res->flags & PCI_BASE_ADDRESS_MEM_TYPE_64) |
223 | return pci_bar_mem64; | 155 | return pci_bar_mem64; |
224 | return pci_bar_mem32; | 156 | return pci_bar_mem32; |
225 | } | 157 | } |
@@ -304,9 +236,8 @@ static int __pci_read_base(struct pci_dev *dev, enum pci_bar_type type, | |||
304 | } else { | 236 | } else { |
305 | res->start = l64; | 237 | res->start = l64; |
306 | res->end = l64 + sz64; | 238 | res->end = l64 + sz64; |
307 | printk(KERN_DEBUG "PCI: %s reg %x 64bit mmio: [%llx, %llx]\n", | 239 | dev_printk(KERN_DEBUG, &dev->dev, |
308 | pci_name(dev), pos, (unsigned long long)res->start, | 240 | "reg %x 64bit mmio: %pR\n", pos, res); |
309 | (unsigned long long)res->end); | ||
310 | } | 241 | } |
311 | } else { | 242 | } else { |
312 | sz = pci_size(l, sz, mask); | 243 | sz = pci_size(l, sz, mask); |
@@ -316,9 +247,10 @@ static int __pci_read_base(struct pci_dev *dev, enum pci_bar_type type, | |||
316 | 247 | ||
317 | res->start = l; | 248 | res->start = l; |
318 | res->end = l + sz; | 249 | res->end = l + sz; |
319 | printk(KERN_DEBUG "PCI: %s reg %x %s: [%llx, %llx]\n", pci_name(dev), | 250 | |
320 | pos, (res->flags & IORESOURCE_IO) ? "io port":"32bit mmio", | 251 | dev_printk(KERN_DEBUG, &dev->dev, "reg %x %s: %pR\n", pos, |
321 | (unsigned long long)res->start, (unsigned long long)res->end); | 252 | (res->flags & IORESOURCE_IO) ? "io port" : "32bit mmio", |
253 | res); | ||
322 | } | 254 | } |
323 | 255 | ||
324 | out: | 256 | out: |
@@ -389,9 +321,7 @@ void __devinit pci_read_bridge_bases(struct pci_bus *child) | |||
389 | res->start = base; | 321 | res->start = base; |
390 | if (!res->end) | 322 | if (!res->end) |
391 | res->end = limit + 0xfff; | 323 | res->end = limit + 0xfff; |
392 | printk(KERN_DEBUG "PCI: bridge %s io port: [%llx, %llx]\n", | 324 | dev_printk(KERN_DEBUG, &dev->dev, "bridge io port: %pR\n", res); |
393 | pci_name(dev), (unsigned long long) res->start, | ||
394 | (unsigned long long) res->end); | ||
395 | } | 325 | } |
396 | 326 | ||
397 | res = child->resource[1]; | 327 | res = child->resource[1]; |
@@ -403,9 +333,8 @@ void __devinit pci_read_bridge_bases(struct pci_bus *child) | |||
403 | res->flags = (mem_base_lo & PCI_MEMORY_RANGE_TYPE_MASK) | IORESOURCE_MEM; | 333 | res->flags = (mem_base_lo & PCI_MEMORY_RANGE_TYPE_MASK) | IORESOURCE_MEM; |
404 | res->start = base; | 334 | res->start = base; |
405 | res->end = limit + 0xfffff; | 335 | res->end = limit + 0xfffff; |
406 | printk(KERN_DEBUG "PCI: bridge %s 32bit mmio: [%llx, %llx]\n", | 336 | dev_printk(KERN_DEBUG, &dev->dev, "bridge 32bit mmio: %pR\n", |
407 | pci_name(dev), (unsigned long long) res->start, | 337 | res); |
408 | (unsigned long long) res->end); | ||
409 | } | 338 | } |
410 | 339 | ||
411 | res = child->resource[2]; | 340 | res = child->resource[2]; |
@@ -441,9 +370,9 @@ void __devinit pci_read_bridge_bases(struct pci_bus *child) | |||
441 | res->flags = (mem_base_lo & PCI_MEMORY_RANGE_TYPE_MASK) | IORESOURCE_MEM | IORESOURCE_PREFETCH; | 370 | res->flags = (mem_base_lo & PCI_MEMORY_RANGE_TYPE_MASK) | IORESOURCE_MEM | IORESOURCE_PREFETCH; |
442 | res->start = base; | 371 | res->start = base; |
443 | res->end = limit + 0xfffff; | 372 | res->end = limit + 0xfffff; |
444 | printk(KERN_DEBUG "PCI: bridge %s %sbit mmio pref: [%llx, %llx]\n", | 373 | dev_printk(KERN_DEBUG, &dev->dev, "bridge %sbit mmio pref: %pR\n", |
445 | pci_name(dev), (res->flags & PCI_PREF_RANGE_TYPE_64) ? "64" : "32", | 374 | (res->flags & PCI_PREF_RANGE_TYPE_64) ? "64" : "32", |
446 | (unsigned long long) res->start, (unsigned long long) res->end); | 375 | res); |
447 | } | 376 | } |
448 | } | 377 | } |
449 | 378 | ||
@@ -764,7 +693,7 @@ static int pci_setup_device(struct pci_dev * dev) | |||
764 | dev->class = class; | 693 | dev->class = class; |
765 | class >>= 8; | 694 | class >>= 8; |
766 | 695 | ||
767 | dev_dbg(&dev->dev, "found [%04x/%04x] class %06x header type %02x\n", | 696 | dev_dbg(&dev->dev, "found [%04x:%04x] class %06x header type %02x\n", |
768 | dev->vendor, dev->device, class, dev->hdr_type); | 697 | dev->vendor, dev->device, class, dev->hdr_type); |
769 | 698 | ||
770 | /* "Unknown power state" */ | 699 | /* "Unknown power state" */ |
@@ -846,6 +775,11 @@ static int pci_setup_device(struct pci_dev * dev) | |||
846 | return 0; | 775 | return 0; |
847 | } | 776 | } |
848 | 777 | ||
778 | static void pci_release_capabilities(struct pci_dev *dev) | ||
779 | { | ||
780 | pci_vpd_release(dev); | ||
781 | } | ||
782 | |||
849 | /** | 783 | /** |
850 | * pci_release_dev - free a pci device structure when all users of it are finished. | 784 | * pci_release_dev - free a pci device structure when all users of it are finished. |
851 | * @dev: device that's been disconnected | 785 | * @dev: device that's been disconnected |
@@ -858,7 +792,7 @@ static void pci_release_dev(struct device *dev) | |||
858 | struct pci_dev *pci_dev; | 792 | struct pci_dev *pci_dev; |
859 | 793 | ||
860 | pci_dev = to_pci_dev(dev); | 794 | pci_dev = to_pci_dev(dev); |
861 | pci_vpd_release(pci_dev); | 795 | pci_release_capabilities(pci_dev); |
862 | kfree(pci_dev); | 796 | kfree(pci_dev); |
863 | } | 797 | } |
864 | 798 | ||
@@ -889,8 +823,9 @@ static void set_pcie_port_type(struct pci_dev *pdev) | |||
889 | int pci_cfg_space_size_ext(struct pci_dev *dev) | 823 | int pci_cfg_space_size_ext(struct pci_dev *dev) |
890 | { | 824 | { |
891 | u32 status; | 825 | u32 status; |
826 | int pos = PCI_CFG_SPACE_SIZE; | ||
892 | 827 | ||
893 | if (pci_read_config_dword(dev, 256, &status) != PCIBIOS_SUCCESSFUL) | 828 | if (pci_read_config_dword(dev, pos, &status) != PCIBIOS_SUCCESSFUL) |
894 | goto fail; | 829 | goto fail; |
895 | if (status == 0xffffffff) | 830 | if (status == 0xffffffff) |
896 | goto fail; | 831 | goto fail; |
@@ -938,8 +873,6 @@ struct pci_dev *alloc_pci_dev(void) | |||
938 | 873 | ||
939 | INIT_LIST_HEAD(&dev->bus_list); | 874 | INIT_LIST_HEAD(&dev->bus_list); |
940 | 875 | ||
941 | pci_msi_init_pci_dev(dev); | ||
942 | |||
943 | return dev; | 876 | return dev; |
944 | } | 877 | } |
945 | EXPORT_SYMBOL(alloc_pci_dev); | 878 | EXPORT_SYMBOL(alloc_pci_dev); |
@@ -951,6 +884,7 @@ EXPORT_SYMBOL(alloc_pci_dev); | |||
951 | static struct pci_dev *pci_scan_device(struct pci_bus *bus, int devfn) | 884 | static struct pci_dev *pci_scan_device(struct pci_bus *bus, int devfn) |
952 | { | 885 | { |
953 | struct pci_dev *dev; | 886 | struct pci_dev *dev; |
887 | struct pci_slot *slot; | ||
954 | u32 l; | 888 | u32 l; |
955 | u8 hdr_type; | 889 | u8 hdr_type; |
956 | int delay = 1; | 890 | int delay = 1; |
@@ -999,6 +933,10 @@ static struct pci_dev *pci_scan_device(struct pci_bus *bus, int devfn) | |||
999 | dev->error_state = pci_channel_io_normal; | 933 | dev->error_state = pci_channel_io_normal; |
1000 | set_pcie_port_type(dev); | 934 | set_pcie_port_type(dev); |
1001 | 935 | ||
936 | list_for_each_entry(slot, &bus->slots, list) | ||
937 | if (PCI_SLOT(devfn) == slot->number) | ||
938 | dev->slot = slot; | ||
939 | |||
1002 | /* Assume 32-bit PCI; let 64-bit PCI cards (which are far rarer) | 940 | /* Assume 32-bit PCI; let 64-bit PCI cards (which are far rarer) |
1003 | set this higher, assuming the system even supports it. */ | 941 | set this higher, assuming the system even supports it. */ |
1004 | dev->dma_mask = 0xffffffff; | 942 | dev->dma_mask = 0xffffffff; |
@@ -1007,9 +945,22 @@ static struct pci_dev *pci_scan_device(struct pci_bus *bus, int devfn) | |||
1007 | return NULL; | 945 | return NULL; |
1008 | } | 946 | } |
1009 | 947 | ||
948 | return dev; | ||
949 | } | ||
950 | |||
951 | static void pci_init_capabilities(struct pci_dev *dev) | ||
952 | { | ||
953 | /* MSI/MSI-X list */ | ||
954 | pci_msi_init_pci_dev(dev); | ||
955 | |||
956 | /* Power Management */ | ||
957 | pci_pm_init(dev); | ||
958 | |||
959 | /* Vital Product Data */ | ||
1010 | pci_vpd_pci22_init(dev); | 960 | pci_vpd_pci22_init(dev); |
1011 | 961 | ||
1012 | return dev; | 962 | /* Alternative Routing-ID Forwarding */ |
963 | pci_enable_ari(dev); | ||
1013 | } | 964 | } |
1014 | 965 | ||
1015 | void pci_device_add(struct pci_dev *dev, struct pci_bus *bus) | 966 | void pci_device_add(struct pci_dev *dev, struct pci_bus *bus) |
@@ -1028,8 +979,8 @@ void pci_device_add(struct pci_dev *dev, struct pci_bus *bus) | |||
1028 | /* Fix up broken headers */ | 979 | /* Fix up broken headers */ |
1029 | pci_fixup_device(pci_fixup_header, dev); | 980 | pci_fixup_device(pci_fixup_header, dev); |
1030 | 981 | ||
1031 | /* Initialize power management of the device */ | 982 | /* Initialize various capabilities */ |
1032 | pci_pm_init(dev); | 983 | pci_init_capabilities(dev); |
1033 | 984 | ||
1034 | /* | 985 | /* |
1035 | * Add the device to our list of discovered devices | 986 | * Add the device to our list of discovered devices |
@@ -1237,8 +1188,11 @@ EXPORT_SYMBOL(pci_scan_bridge); | |||
1237 | EXPORT_SYMBOL_GPL(pci_scan_child_bus); | 1188 | EXPORT_SYMBOL_GPL(pci_scan_child_bus); |
1238 | #endif | 1189 | #endif |
1239 | 1190 | ||
1240 | static int __init pci_sort_bf_cmp(const struct pci_dev *a, const struct pci_dev *b) | 1191 | static int __init pci_sort_bf_cmp(const struct device *d_a, const struct device *d_b) |
1241 | { | 1192 | { |
1193 | const struct pci_dev *a = to_pci_dev(d_a); | ||
1194 | const struct pci_dev *b = to_pci_dev(d_b); | ||
1195 | |||
1242 | if (pci_domain_nr(a->bus) < pci_domain_nr(b->bus)) return -1; | 1196 | if (pci_domain_nr(a->bus) < pci_domain_nr(b->bus)) return -1; |
1243 | else if (pci_domain_nr(a->bus) > pci_domain_nr(b->bus)) return 1; | 1197 | else if (pci_domain_nr(a->bus) > pci_domain_nr(b->bus)) return 1; |
1244 | 1198 | ||
@@ -1251,50 +1205,7 @@ static int __init pci_sort_bf_cmp(const struct pci_dev *a, const struct pci_dev | |||
1251 | return 0; | 1205 | return 0; |
1252 | } | 1206 | } |
1253 | 1207 | ||
1254 | /* | ||
1255 | * Yes, this forcably breaks the klist abstraction temporarily. It | ||
1256 | * just wants to sort the klist, not change reference counts and | ||
1257 | * take/drop locks rapidly in the process. It does all this while | ||
1258 | * holding the lock for the list, so objects can't otherwise be | ||
1259 | * added/removed while we're swizzling. | ||
1260 | */ | ||
1261 | static void __init pci_insertion_sort_klist(struct pci_dev *a, struct list_head *list) | ||
1262 | { | ||
1263 | struct list_head *pos; | ||
1264 | struct klist_node *n; | ||
1265 | struct device *dev; | ||
1266 | struct pci_dev *b; | ||
1267 | |||
1268 | list_for_each(pos, list) { | ||
1269 | n = container_of(pos, struct klist_node, n_node); | ||
1270 | dev = container_of(n, struct device, knode_bus); | ||
1271 | b = to_pci_dev(dev); | ||
1272 | if (pci_sort_bf_cmp(a, b) <= 0) { | ||
1273 | list_move_tail(&a->dev.knode_bus.n_node, &b->dev.knode_bus.n_node); | ||
1274 | return; | ||
1275 | } | ||
1276 | } | ||
1277 | list_move_tail(&a->dev.knode_bus.n_node, list); | ||
1278 | } | ||
1279 | |||
1280 | void __init pci_sort_breadthfirst(void) | 1208 | void __init pci_sort_breadthfirst(void) |
1281 | { | 1209 | { |
1282 | LIST_HEAD(sorted_devices); | 1210 | bus_sort_breadthfirst(&pci_bus_type, &pci_sort_bf_cmp); |
1283 | struct list_head *pos, *tmp; | ||
1284 | struct klist_node *n; | ||
1285 | struct device *dev; | ||
1286 | struct pci_dev *pdev; | ||
1287 | struct klist *device_klist; | ||
1288 | |||
1289 | device_klist = bus_get_device_klist(&pci_bus_type); | ||
1290 | |||
1291 | spin_lock(&device_klist->k_lock); | ||
1292 | list_for_each_safe(pos, tmp, &device_klist->k_list) { | ||
1293 | n = container_of(pos, struct klist_node, n_node); | ||
1294 | dev = container_of(n, struct device, knode_bus); | ||
1295 | pdev = to_pci_dev(dev); | ||
1296 | pci_insertion_sort_klist(pdev, &sorted_devices); | ||
1297 | } | ||
1298 | list_splice(&sorted_devices, &device_klist->k_list); | ||
1299 | spin_unlock(&device_klist->k_lock); | ||
1300 | } | 1211 | } |