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

ACPI / scan: Prefer devices without _HID for _ADR matching

Commit c2a6bbaf (ACPI / scan: Prefer devices without _HID/_CID
for _ADR matching) added a list_empty(&adev->pnp.ids) check to
find_child_checks() so as to catch situations in which the ACPI
core attempts to decode _ADR for a device having a _HID too which
is strictly against the spec.  However, it overlooked the fact that
the adev->pnp.ids list for the devices taken into account by
find_child_checks() may contain device IDs set internally by the
kernel, like "LNXVIDEO" (thanks to Zhang Rui for that realization),
and it broke the enumeration of those devices as a result.

To unbreak it, replace the overly coarse grained list_empty()
check with a much more precise check against the pnp.type.platform_id
flag which is only set for devices having a _HID (that's how it
should be done from the start, as having both _ADR and _CID is
actually permitted).

Fixes: c2a6bbaf (ACPI / scan: Prefer devices without _HID/_CID for _ADR matching)
Link: https://bugzilla.kernel.org/show_bug.cgi?id=194889Reported-and-tested-by: default avatarMike <mike@mikewilson.me.uk>
Tested-by: default avatarHans de Goede <hdegoede@redhat.com>
Cc: 4.10+ <stable@vger.kernel.org> # 4.10+
Signed-off-by: default avatarRafael J. Wysocki <rafael.j.wysocki@intel.com>
parent c02ed2e7
...@@ -99,13 +99,13 @@ static int find_child_checks(struct acpi_device *adev, bool check_children) ...@@ -99,13 +99,13 @@ static int find_child_checks(struct acpi_device *adev, bool check_children)
return -ENODEV; return -ENODEV;
/* /*
* If the device has a _HID (or _CID) returning a valid ACPI/PNP * If the device has a _HID returning a valid ACPI/PNP device ID, it is
* device ID, it is better to make it look less attractive here, so that * better to make it look less attractive here, so that the other device
* the other device with the same _ADR value (that may not have a valid * with the same _ADR value (that may not have a valid device ID) can be
* device ID) can be matched going forward. [This means a second spec * matched going forward. [This means a second spec violation in a row,
* violation in a row, so whatever we do here is best effort anyway.] * so whatever we do here is best effort anyway.]
*/ */
return sta_present && list_empty(&adev->pnp.ids) ? return sta_present && !adev->pnp.type.platform_id ?
FIND_CHILD_MAX_SCORE : FIND_CHILD_MIN_SCORE; FIND_CHILD_MAX_SCORE : FIND_CHILD_MIN_SCORE;
} }
......
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