diff options
author | Huacai Chen <chenhc@lemote.com> | 2020-07-05 05:59:58 -0400 |
---|---|---|
committer | Matt Turner <mattst88@gmail.com> | 2020-08-18 17:20:09 +0000 |
commit | 249a12c54a9316b089bd22683c011519348496df (patch) | |
tree | 457d4c8424d59a84edf2d12f21580daa18b4bd28 | |
parent | 5c96eb5f44e62a4cfe835023cde304eb5795b8fd (diff) |
linux: Fix platform device probe for DT-based PCI
On a DT-base PCI platform, the sysfs path of vga device is like this:
/sys/devices/platform/bus@10000000/1a000000.pci/pci0000:00/0000:00:11.0/0000:04:00.0.
Then the ID_PATH from udev is platform-1a000000.pci-pci-0000:04:00.0 and
the BusID will be pci-0000:04:00.0, which causes Xorg start fail. This
is because config_udev_odev_setup_attribs() use strstr() to search the
first "pci-" in ID_PATH. To fix this, we implement a strrstr() function
and use it to search the last "pci-" in ID_PATH, which can get a correct
BusID.
(backported from commit 9fbd3e43dd9e13700df96b508c3d97f77e2b9f7e)
Reviewed-by: Dave Airlie <airlied@redhat.com>
Signed-off-by: Huacai Chen <chenhc@lemote.com>
-rw-r--r-- | config/udev.c | 27 |
1 files changed, 26 insertions, 1 deletions
diff --git a/config/udev.c b/config/udev.c index 14409549b..b00d90237 100644 --- a/config/udev.c +++ b/config/udev.c @@ -464,6 +464,31 @@ config_udev_fini(void) #ifdef CONFIG_UDEV_KMS +/* Find the last occurrence of the needle in haystack */ +static char *strrstr(const char *haystack, const char *needle) +{ + char *prev, *last, *tmp; + + prev = strstr(haystack, needle); + if (!prev) + return NULL; + + last = prev; + tmp = prev + 1; + + while (tmp) { + last = strstr(tmp, needle); + if (!last) + return prev; + else { + prev = last; + tmp = prev + 1; + } + } + + return last; +} + static void config_udev_odev_setup_attribs(struct udev_device *udev_device, const char *path, const char *syspath, int major, int minor, @@ -478,7 +503,7 @@ config_udev_odev_setup_attribs(struct udev_device *udev_device, const char *path attribs->minor = minor; value = udev_device_get_property_value(udev_device, "ID_PATH"); - if (value && (str = strstr(value, "pci-"))) { + if (value && (str = strrstr(value, "pci-"))) { attribs->busid = XNFstrdup(str); attribs->busid[3] = ':'; } |