提交 705b1aaa 编写于 作者: A Alex Chiang 提交者: Jesse Barnes

PCI: Introduce /sys/bus/pci/rescan

This interface allows the user to force a rescan of all PCI buses
in system, and rediscover devices that have been removed earlier.

pci_bus_attrs implementation from Trent Piepho.

Thanks to Vegard Nossum for discovering locking issues with the
sysfs interface.

Cc: Trent Piepho <xyzzy@speakeasy.org>
Signed-off-by: NAlex Chiang <achiang@hp.com>
Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
上级 3ed4fd96
...@@ -57,6 +57,15 @@ Description: ...@@ -57,6 +57,15 @@ Description:
match the driver to the device. For example: match the driver to the device. For example:
# echo "8086 10f5" > /sys/bus/pci/drivers/foo/remove_id # echo "8086 10f5" > /sys/bus/pci/drivers/foo/remove_id
What: /sys/bus/pci/rescan
Date: January 2009
Contact: Linux PCI developers <linux-pci@vger.kernel.org>
Description:
Writing a non-zero value to this attribute will
force a rescan of all PCI buses in the system, and
re-discover previously removed devices.
Depends on CONFIG_HOTPLUG.
What: /sys/bus/pci/devices/.../vpd What: /sys/bus/pci/devices/.../vpd
Date: February 2008 Date: February 2008
Contact: Ben Hutchings <bhutchings@solarflare.com> Contact: Ben Hutchings <bhutchings@solarflare.com>
......
...@@ -1049,6 +1049,7 @@ struct bus_type pci_bus_type = { ...@@ -1049,6 +1049,7 @@ struct bus_type pci_bus_type = {
.remove = pci_device_remove, .remove = pci_device_remove,
.shutdown = pci_device_shutdown, .shutdown = pci_device_shutdown,
.dev_attrs = pci_dev_attrs, .dev_attrs = pci_dev_attrs,
.bus_attrs = pci_bus_attrs,
.pm = PCI_PM_OPS_PTR, .pm = PCI_PM_OPS_PTR,
}; };
......
...@@ -219,6 +219,32 @@ msi_bus_store(struct device *dev, struct device_attribute *attr, ...@@ -219,6 +219,32 @@ msi_bus_store(struct device *dev, struct device_attribute *attr,
return count; return count;
} }
#ifdef CONFIG_HOTPLUG
static DEFINE_MUTEX(pci_remove_rescan_mutex);
static ssize_t bus_rescan_store(struct bus_type *bus, const char *buf,
size_t count)
{
unsigned long val;
struct pci_bus *b = NULL;
if (strict_strtoul(buf, 0, &val) < 0)
return -EINVAL;
if (val) {
mutex_lock(&pci_remove_rescan_mutex);
while ((b = pci_find_next_bus(b)) != NULL)
pci_rescan_bus(b);
mutex_unlock(&pci_remove_rescan_mutex);
}
return count;
}
struct bus_attribute pci_bus_attrs[] = {
__ATTR(rescan, (S_IWUSR|S_IWGRP), NULL, bus_rescan_store),
__ATTR_NULL
};
#endif
struct device_attribute pci_dev_attrs[] = { struct device_attribute pci_dev_attrs[] = {
__ATTR_RO(resource), __ATTR_RO(resource),
__ATTR_RO(vendor), __ATTR_RO(vendor),
......
...@@ -138,6 +138,12 @@ extern int pcie_mch_quirk; ...@@ -138,6 +138,12 @@ extern int pcie_mch_quirk;
extern struct device_attribute pci_dev_attrs[]; extern struct device_attribute pci_dev_attrs[];
extern struct device_attribute dev_attr_cpuaffinity; extern struct device_attribute dev_attr_cpuaffinity;
extern struct device_attribute dev_attr_cpulistaffinity; extern struct device_attribute dev_attr_cpulistaffinity;
#ifdef CONFIG_HOTPLUG
extern struct bus_attribute pci_bus_attrs[];
#else
#define pci_bus_attrs NULL
#endif
/** /**
* pci_match_one_device - Tell if a PCI device structure has a matching * pci_match_one_device - Tell if a PCI device structure has a matching
......
...@@ -1228,13 +1228,13 @@ unsigned int __devinit pci_rescan_bus(struct pci_bus *bus) ...@@ -1228,13 +1228,13 @@ unsigned int __devinit pci_rescan_bus(struct pci_bus *bus)
max = pci_scan_child_bus(bus); max = pci_scan_child_bus(bus);
up_read(&pci_bus_sem); down_read(&pci_bus_sem);
list_for_each_entry(dev, &bus->devices, bus_list) list_for_each_entry(dev, &bus->devices, bus_list)
if (dev->hdr_type == PCI_HEADER_TYPE_BRIDGE || if (dev->hdr_type == PCI_HEADER_TYPE_BRIDGE ||
dev->hdr_type == PCI_HEADER_TYPE_CARDBUS) dev->hdr_type == PCI_HEADER_TYPE_CARDBUS)
if (dev->subordinate) if (dev->subordinate)
pci_bus_size_bridges(dev->subordinate); pci_bus_size_bridges(dev->subordinate);
down_read(&pci_bus_sem); up_read(&pci_bus_sem);
pci_bus_assign_resources(bus); pci_bus_assign_resources(bus);
pci_enable_bridges(bus); pci_enable_bridges(bus);
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册