diff options
Diffstat (limited to 'drivers/pci/bus.c')
-rw-r--r-- | drivers/pci/bus.c | 78 |
1 files changed, 12 insertions, 66 deletions
diff --git a/drivers/pci/bus.c b/drivers/pci/bus.c index c8709c6fdb7c..8647dc6f52d0 100644 --- a/drivers/pci/bus.c +++ b/drivers/pci/bus.c | |||
@@ -161,73 +161,35 @@ pci_bus_alloc_resource(struct pci_bus *bus, struct resource *res, | |||
161 | void __weak pcibios_resource_survey_bus(struct pci_bus *bus) { } | 161 | void __weak pcibios_resource_survey_bus(struct pci_bus *bus) { } |
162 | 162 | ||
163 | /** | 163 | /** |
164 | * pci_bus_add_device - add a single device | 164 | * pci_bus_add_device - start driver for a single device |
165 | * @dev: device to add | 165 | * @dev: device to add |
166 | * | 166 | * |
167 | * This adds a single pci device to the global | 167 | * This adds add sysfs entries and start device drivers |
168 | * device list and adds sysfs and procfs entries | ||
169 | */ | 168 | */ |
170 | int pci_bus_add_device(struct pci_dev *dev) | 169 | int pci_bus_add_device(struct pci_dev *dev) |
171 | { | 170 | { |
172 | int retval; | 171 | int retval; |
173 | 172 | ||
174 | pci_fixup_device(pci_fixup_final, dev); | 173 | /* |
175 | 174 | * Can not put in pci_device_add yet because resources | |
176 | retval = pcibios_add_device(dev); | 175 | * are not assigned yet for some devices. |
177 | if (retval) | 176 | */ |
178 | return retval; | 177 | pci_create_sysfs_dev_files(dev); |
179 | |||
180 | dev->match_driver = false; | ||
181 | retval = device_add(&dev->dev); | ||
182 | if (retval) | ||
183 | return retval; | ||
184 | 178 | ||
185 | dev->match_driver = true; | 179 | dev->match_driver = true; |
186 | retval = device_attach(&dev->dev); | 180 | retval = device_attach(&dev->dev); |
187 | WARN_ON(retval < 0); | 181 | WARN_ON(retval < 0); |
188 | 182 | ||
189 | dev->is_added = 1; | 183 | dev->is_added = 1; |
190 | pci_proc_attach_device(dev); | ||
191 | pci_create_sysfs_dev_files(dev); | ||
192 | return 0; | ||
193 | } | ||
194 | |||
195 | /** | ||
196 | * pci_bus_add_child - add a child bus | ||
197 | * @bus: bus to add | ||
198 | * | ||
199 | * This adds sysfs entries for a single bus | ||
200 | */ | ||
201 | int pci_bus_add_child(struct pci_bus *bus) | ||
202 | { | ||
203 | int retval; | ||
204 | |||
205 | if (bus->bridge) | ||
206 | bus->dev.parent = bus->bridge; | ||
207 | |||
208 | retval = device_register(&bus->dev); | ||
209 | if (retval) | ||
210 | return retval; | ||
211 | 184 | ||
212 | bus->is_added = 1; | 185 | return 0; |
213 | |||
214 | /* Create legacy_io and legacy_mem files for this bus */ | ||
215 | pci_create_legacy_files(bus); | ||
216 | |||
217 | return retval; | ||
218 | } | 186 | } |
219 | 187 | ||
220 | /** | 188 | /** |
221 | * pci_bus_add_devices - insert newly discovered PCI devices | 189 | * pci_bus_add_devices - start driver for PCI devices |
222 | * @bus: bus to check for new devices | 190 | * @bus: bus to check for new devices |
223 | * | 191 | * |
224 | * Add newly discovered PCI devices (which are on the bus->devices | 192 | * Start driver for PCI devices and add some sysfs entries. |
225 | * list) to the global PCI device list, add the sysfs and procfs | ||
226 | * entries. Where a bridge is found, add the discovered bus to | ||
227 | * the parents list of child buses, and recurse (breadth-first | ||
228 | * to be compatible with 2.4) | ||
229 | * | ||
230 | * Call hotplug for each new devices. | ||
231 | */ | 193 | */ |
232 | void pci_bus_add_devices(const struct pci_bus *bus) | 194 | void pci_bus_add_devices(const struct pci_bus *bus) |
233 | { | 195 | { |
@@ -240,36 +202,20 @@ void pci_bus_add_devices(const struct pci_bus *bus) | |||
240 | if (dev->is_added) | 202 | if (dev->is_added) |
241 | continue; | 203 | continue; |
242 | retval = pci_bus_add_device(dev); | 204 | retval = pci_bus_add_device(dev); |
243 | if (retval) | ||
244 | dev_err(&dev->dev, "Error adding device, continuing\n"); | ||
245 | } | 205 | } |
246 | 206 | ||
247 | list_for_each_entry(dev, &bus->devices, bus_list) { | 207 | list_for_each_entry(dev, &bus->devices, bus_list) { |
248 | BUG_ON(!dev->is_added); | 208 | BUG_ON(!dev->is_added); |
249 | 209 | ||
250 | child = dev->subordinate; | 210 | child = dev->subordinate; |
251 | /* | 211 | |
252 | * If there is an unattached subordinate bus, attach | ||
253 | * it and then scan for unattached PCI devices. | ||
254 | */ | ||
255 | if (!child) | 212 | if (!child) |
256 | continue; | 213 | continue; |
257 | if (list_empty(&child->node)) { | ||
258 | down_write(&pci_bus_sem); | ||
259 | list_add_tail(&child->node, &dev->bus->children); | ||
260 | up_write(&pci_bus_sem); | ||
261 | } | ||
262 | pci_bus_add_devices(child); | 214 | pci_bus_add_devices(child); |
263 | 215 | ||
264 | /* | ||
265 | * register the bus with sysfs as the parent is now | ||
266 | * properly registered. | ||
267 | */ | ||
268 | if (child->is_added) | 216 | if (child->is_added) |
269 | continue; | 217 | continue; |
270 | retval = pci_bus_add_child(child); | 218 | child->is_added = 1; |
271 | if (retval) | ||
272 | dev_err(&dev->dev, "Error adding bus, continuing\n"); | ||
273 | } | 219 | } |
274 | } | 220 | } |
275 | 221 | ||