Commit ff181e5a authored by Rafael J. Wysocki's avatar Rafael J. Wysocki

ACPI / hotplug / PCI: Clean up bridge_mutex usage

Do not acquire bridge_mutex around the addition of a slot to its
bridge's list of slots and arount the addition of a function to
its slot's list of functions, because that doesn't help anything
right now (those lists are walked without any locking anyway).

However, acquire bridge_mutex around the list walk in
acpiphp_remove_slots() and use list_for_each_entry() there,
because we terminate the walk as soon as we find the first matching
entry.  This prevents that list walk from colliding with bridge
addition and removal.
Signed-off-by: default avatarRafael J. Wysocki <rafael.j.wysocki@intel.com>
Tested-by: default avatarMika Westerberg <mika.westerberg@linux.intel.com>
parent a1d0abce
...@@ -323,9 +323,7 @@ static acpi_status register_slot(acpi_handle handle, u32 lvl, void *data, ...@@ -323,9 +323,7 @@ static acpi_status register_slot(acpi_handle handle, u32 lvl, void *data,
INIT_LIST_HEAD(&slot->funcs); INIT_LIST_HEAD(&slot->funcs);
mutex_init(&slot->crit_sect); mutex_init(&slot->crit_sect);
mutex_lock(&bridge_mutex);
list_add_tail(&slot->node, &bridge->slots); list_add_tail(&slot->node, &bridge->slots);
mutex_unlock(&bridge_mutex);
/* Register slots for ejectable funtions only. */ /* Register slots for ejectable funtions only. */
if (acpi_pci_check_ejectable(pbus, handle) || is_dock_device(handle)) { if (acpi_pci_check_ejectable(pbus, handle) || is_dock_device(handle)) {
...@@ -355,9 +353,7 @@ static acpi_status register_slot(acpi_handle handle, u32 lvl, void *data, ...@@ -355,9 +353,7 @@ static acpi_status register_slot(acpi_handle handle, u32 lvl, void *data,
slot_found: slot_found:
newfunc->slot = slot; newfunc->slot = slot;
mutex_lock(&bridge_mutex);
list_add_tail(&newfunc->sibling, &slot->funcs); list_add_tail(&newfunc->sibling, &slot->funcs);
mutex_unlock(&bridge_mutex);
if (pci_bus_read_dev_vendor_id(pbus, PCI_DEVFN(device, function), if (pci_bus_read_dev_vendor_id(pbus, PCI_DEVFN(device, function),
&val, 60*1000)) &val, 60*1000))
...@@ -1025,17 +1021,21 @@ void acpiphp_enumerate_slots(struct pci_bus *bus) ...@@ -1025,17 +1021,21 @@ void acpiphp_enumerate_slots(struct pci_bus *bus)
/* Destroy hotplug slots associated with the PCI bus */ /* Destroy hotplug slots associated with the PCI bus */
void acpiphp_remove_slots(struct pci_bus *bus) void acpiphp_remove_slots(struct pci_bus *bus)
{ {
struct acpiphp_bridge *bridge, *tmp; struct acpiphp_bridge *bridge;
if (acpiphp_disabled) if (acpiphp_disabled)
return; return;
list_for_each_entry_safe(bridge, tmp, &bridge_list, list) mutex_lock(&bridge_mutex);
list_for_each_entry(bridge, &bridge_list, list)
if (bridge->pci_bus == bus) { if (bridge->pci_bus == bus) {
mutex_unlock(&bridge_mutex);
cleanup_bridge(bridge); cleanup_bridge(bridge);
put_bridge(bridge); put_bridge(bridge);
break; return;
} }
mutex_unlock(&bridge_mutex);
} }
/** /**
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment