summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--config/config-backends.h1
-rw-r--r--config/config.c56
-rw-r--r--config/udev.c69
-rw-r--r--configure.ac20
-rw-r--r--hw/xfree86/common/Makefile.am8
-rw-r--r--hw/xfree86/common/xf86.h5
-rw-r--r--hw/xfree86/common/xf86AutoConfig.c9
-rw-r--r--hw/xfree86/common/xf86Bus.c18
-rw-r--r--hw/xfree86/common/xf86Bus.h1
-rw-r--r--hw/xfree86/common/xf86fbBus.c4
-rw-r--r--hw/xfree86/common/xf86pciBus.c41
-rw-r--r--hw/xfree86/common/xf86pciBus.h10
-rw-r--r--hw/xfree86/common/xf86platformBus.c379
-rw-r--r--hw/xfree86/common/xf86platformBus.h59
-rw-r--r--hw/xfree86/common/xf86str.h11
-rw-r--r--hw/xfree86/os-support/linux/Makefile.am2
-rw-r--r--hw/xfree86/os-support/linux/lnx_platform.c130
-rw-r--r--hw/xfree86/os-support/shared/platform_noop.c23
-rw-r--r--hw/xfree86/os-support/xf86_OSproc.h6
-rw-r--r--include/dix-config.h.in3
-rw-r--r--include/hotplug.h35
-rw-r--r--include/xorg-config.h.in3
-rw-r--r--include/xorg-server.h.in3
23 files changed, 877 insertions, 19 deletions
diff --git a/config/config-backends.h b/config/config-backends.h
index 62abc0a5f..6423701fc 100644
--- a/config/config-backends.h
+++ b/config/config-backends.h
@@ -36,6 +36,7 @@ BOOL device_is_duplicate(const char *config_info);
int config_udev_pre_init(void);
int config_udev_init(void);
void config_udev_fini(void);
+void config_udev_odev_probe(config_odev_probe_proc_ptr probe_callback);
#else
#ifdef CONFIG_NEED_DBUS
diff --git a/config/config.c b/config/config.c
index 24e7ba7a0..d0889a394 100644
--- a/config/config.c
+++ b/config/config.c
@@ -85,6 +85,14 @@ config_fini(void)
#endif
}
+void
+config_odev_probe(config_odev_probe_proc_ptr probe_callback)
+{
+#if defined(CONFIG_UDEV_KMS)
+ config_udev_odev_probe(probe_callback);
+#endif
+}
+
static void
remove_device(const char *backend, DeviceIntPtr dev)
{
@@ -133,3 +141,51 @@ device_is_duplicate(const char *config_info)
return FALSE;
}
+
+struct OdevAttributes *
+config_odev_allocate_attribute_list(void)
+{
+ struct OdevAttributes *attriblist;
+
+ attriblist = malloc(sizeof(struct OdevAttributes));
+ if (!attriblist)
+ return NULL;
+
+ xorg_list_init(&attriblist->list);
+ return attriblist;
+}
+
+void
+config_odev_free_attribute_list(struct OdevAttributes *attribs)
+{
+ config_odev_free_attributes(attribs);
+ free(attribs);
+}
+
+Bool
+config_odev_add_attribute(struct OdevAttributes *attribs, int attrib,
+ const char *attrib_name)
+{
+ struct OdevAttribute *oa;
+
+ oa = malloc(sizeof(struct OdevAttribute));
+ if (!oa)
+ return FALSE;
+
+ oa->attrib_id = attrib;
+ oa->attrib_name = strdup(attrib_name);
+ xorg_list_append(&oa->member, &attribs->list);
+ return TRUE;
+}
+
+void
+config_odev_free_attributes(struct OdevAttributes *attribs)
+{
+ struct OdevAttribute *iter, *safe;
+
+ xorg_list_for_each_entry_safe(iter, safe, &attribs->list, member) {
+ xorg_list_del(&iter->member);
+ free(iter->attrib_name);
+ free(iter);
+ }
+}
diff --git a/config/udev.c b/config/udev.c
index 1995184f3..efa8d3257 100644
--- a/config/udev.c
+++ b/config/udev.c
@@ -366,3 +366,72 @@ config_udev_fini(void)
udev_monitor = NULL;
udev_unref(udev);
}
+
+#ifdef CONFIG_UDEV_KMS
+
+static Bool
+config_udev_odev_setup_attribs(const char *path, const char *syspath,
+ config_odev_probe_proc_ptr probe_callback)
+{
+ struct OdevAttributes *attribs = config_odev_allocate_attribute_list();
+ int ret;
+
+ if (!attribs)
+ return FALSE;
+
+ ret = config_odev_add_attribute(attribs, ODEV_ATTRIB_PATH, path);
+ if (ret == FALSE)
+ goto fail;
+
+ ret = config_odev_add_attribute(attribs, ODEV_ATTRIB_SYSPATH, syspath);
+ if (ret == FALSE)
+ goto fail;
+
+ /* ownership of attribs is passed to probe layer */
+ probe_callback(attribs);
+ return TRUE;
+fail:
+ config_odev_free_attributes(attribs);
+ free(attribs);
+ return FALSE;
+}
+
+void
+config_udev_odev_probe(config_odev_probe_proc_ptr probe_callback)
+{
+ struct udev *udev;
+ struct udev_enumerate *enumerate;
+ struct udev_list_entry *devices, *device;
+
+ udev = udev_monitor_get_udev(udev_monitor);
+ enumerate = udev_enumerate_new(udev);
+ if (!enumerate)
+ return;
+
+ udev_enumerate_add_match_subsystem(enumerate, "drm");
+ udev_enumerate_add_match_sysname(enumerate, "card[0-9]*");
+ udev_enumerate_scan_devices(enumerate);
+ devices = udev_enumerate_get_list_entry(enumerate);
+ udev_list_entry_foreach(device, devices) {
+ const char *syspath = udev_list_entry_get_name(device);
+ struct udev_device *udev_device = udev_device_new_from_syspath(udev, syspath);
+ const char *path = udev_device_get_devnode(udev_device);
+ const char *sysname = udev_device_get_sysname(udev_device);
+
+ if (!path || !syspath)
+ goto no_probe;
+ else if (strcmp(udev_device_get_subsystem(udev_device), "drm") != 0)
+ goto no_probe;
+ else if (strncmp(sysname, "card", 4) != 0)
+ goto no_probe;
+
+ config_udev_odev_setup_attribs(path, syspath, probe_callback);
+
+ no_probe:
+ udev_device_unref(udev_device);
+ }
+ udev_enumerate_unref(enumerate);
+ return;
+}
+#endif
+
diff --git a/configure.ac b/configure.ac
index d5ddf6e10..d1358a224 100644
--- a/configure.ac
+++ b/configure.ac
@@ -615,6 +615,7 @@ AC_ARG_ENABLE(dbe, AS_HELP_STRING([--disable-dbe], [Build DBE extensi
AC_ARG_ENABLE(xf86bigfont, AS_HELP_STRING([--enable-xf86bigfont], [Build XF86 Big Font extension (default: disabled)]), [XF86BIGFONT=$enableval], [XF86BIGFONT=no])
AC_ARG_ENABLE(dpms, AS_HELP_STRING([--disable-dpms], [Build DPMS extension (default: enabled)]), [DPMSExtension=$enableval], [DPMSExtension=yes])
AC_ARG_ENABLE(config-udev, AS_HELP_STRING([--enable-config-udev], [Build udev support (default: auto)]), [CONFIG_UDEV=$enableval], [CONFIG_UDEV=auto])
+AC_ARG_ENABLE(config-udev-kms, AS_HELP_STRING([--enable-config-udev-kms], [Build udev kms support (default: auto)]), [CONFIG_UDEV_KMS=$enableval], [CONFIG_UDEV_KMS=auto])
AC_ARG_ENABLE(config-dbus, AS_HELP_STRING([--enable-config-dbus], [Build D-BUS API support (default: no)]), [CONFIG_DBUS_API=$enableval], [CONFIG_DBUS_API=no])
AC_ARG_ENABLE(config-hal, AS_HELP_STRING([--disable-config-hal], [Build HAL support (default: auto)]), [CONFIG_HAL=$enableval], [CONFIG_HAL=auto])
AC_ARG_ENABLE(config-wscons, AS_HELP_STRING([--enable-config-wscons], [Build wscons config support (default: auto)]), [CONFIG_WSCONS=$enableval], [CONFIG_WSCONS=auto])
@@ -704,6 +705,7 @@ case $host_os in
CONFIG_DBUS_API=no
CONFIG_HAL=no
CONFIG_UDEV=no
+ CONFIG_UDEV_KMS=no
DGA=no
DRI2=no
INT10MODULE=no
@@ -838,11 +840,16 @@ AM_CONDITIONAL(CONFIG_UDEV, [test "x$CONFIG_UDEV" = xyes])
if test "x$CONFIG_UDEV" = xyes; then
CONFIG_DBUS_API=no
CONFIG_HAL=no
+ if test "x$CONFIG_UDEV_KMS" = xauto; then
+ CONFIG_UDEV_KMS="$HAVE_LIBUDEV"
+ fi
if ! test "x$HAVE_LIBUDEV" = xyes; then
AC_MSG_ERROR([udev configuration API requested, but libudev is not installed])
fi
AC_DEFINE(CONFIG_UDEV, 1, [Use libudev for input hotplug])
-
+ if test "x$CONFIG_UDEV_KMS" = xyes; then
+ AC_DEFINE(CONFIG_UDEV_KMS, 1, [Use libudev for kms enumeration])
+ fi
SAVE_LIBS=$LIBS
SAVE_CFLAGS=$CFLAGS
CFLAGS=$UDEV_CFLAGS
@@ -852,6 +859,7 @@ if test "x$CONFIG_UDEV" = xyes; then
LIBS=$SAVE_LIBS
CFLAGS=$SAVE_CFLAGS
fi
+AM_CONDITIONAL(CONFIG_UDEV_KMS, [test "x$CONFIG_UDEV_KMS" = xyes])
dnl HAVE_DBUS is true if we actually have the D-Bus library, whereas
dnl CONFIG_DBUS_API is true if we want to enable the D-Bus config
@@ -1099,7 +1107,7 @@ case "$DRI2,$HAVE_DRI2PROTO" in
esac
AM_CONDITIONAL(DRI2, test "x$DRI2" = xyes)
-if test "x$DRI" = xyes || test "x$DRI2" = xyes; then
+if test "x$DRI" = xyes || test "x$DRI2" = xyes || test "x$CONFIG_UDEV_KMS" = xyes; then
if test "x$DRM" = xyes; then
AC_DEFINE(WITH_LIBDRM, 1, [Building with libdrm support])
PKG_CHECK_MODULES([LIBDRM], $LIBDRM)
@@ -1650,7 +1658,7 @@ if test "x$XORG" = xyes; then
PKG_CHECK_MODULES([PCIACCESS], $LIBPCIACCESS)
SDK_REQUIRED_MODULES="$SDK_REQUIRED_MODULES $LIBPCIACCESS"
- XORG_SYS_LIBS="$XORG_SYS_LIBS $PCIACCESS_LIBS $GLX_SYS_LIBS"
+ XORG_SYS_LIBS="$XORG_SYS_LIBS $PCIACCESS_LIBS $GLX_SYS_LIBS $LIBDRM_LIBS"
XORG_CFLAGS="$XORG_CFLAGS $PCIACCESS_CFLAGS"
AC_DEFINE(XSERVER_LIBPCIACCESS, 1, [Use libpciaccess for all pci manipulation])
@@ -1668,6 +1676,10 @@ if test "x$XORG" = xyes; then
fi
AC_MSG_RESULT([$PCI])
+ if test "x$CONFIG_UDEV_KMS" = xyes; then
+ AC_DEFINE(XSERVER_PLATFORM_BUS, 1, [X server supports platform device enumeration])
+ fi
+ AC_MSG_RESULT([$XSERVER_PLATFORM_BUS])
dnl ===================================================================
dnl ==================== end of PCI configuration =====================
dnl ===================================================================
@@ -1856,7 +1868,7 @@ AM_CONDITIONAL([SOLARIS_ASM_INLINE], [test "x$solaris_asm_inline" = xyes])
AM_CONDITIONAL([SOLARIS_VT], [test "x$solaris_vt" = xyes])
AM_CONDITIONAL([DGA], [test "x$DGA" = xyes])
AM_CONDITIONAL([XF86VIDMODE], [test "x$XF86VIDMODE" = xyes])
-
+AM_CONDITIONAL([XORG_BUS_PLATFORM], [test "x$CONFIG_UDEV_KMS" = xyes])
dnl XWin DDX
AC_MSG_CHECKING([whether to build XWin DDX])
diff --git a/hw/xfree86/common/Makefile.am b/hw/xfree86/common/Makefile.am
index 27921777d..65d98e694 100644
--- a/hw/xfree86/common/Makefile.am
+++ b/hw/xfree86/common/Makefile.am
@@ -22,9 +22,13 @@ if DGA
DGASOURCES = xf86DGA.c
endif
+if XORG_BUS_PLATFORM
+PLATSOURCES = xf86platformBus.c
+endif
+
RANDRSOURCES = xf86RandR.c
-BUSSOURCES = xf86fbBus.c xf86noBus.c $(PCI_SOURCES) $(SBUS_SOURCES)
+BUSSOURCES = xf86fbBus.c xf86noBus.c $(PCI_SOURCES) $(SBUS_SOURCES) $(PLATSOURCES)
MODEDEFSOURCES = $(srcdir)/vesamodes $(srcdir)/extramodes
@@ -56,7 +60,7 @@ sdk_HEADERS = compiler.h fourcc.h xf86.h xf86Module.h xf86Opt.h \
xf86PciInfo.h xf86Priv.h xf86Privstr.h \
xf86cmap.h xf86fbman.h xf86str.h xf86Xinput.h xisb.h \
$(XVSDKINCS) $(XF86VMODE_SDK) xorgVersion.h \
- xf86sbusBus.h xf86VGAarbiter.h xf86Optionstr.h
+ xf86sbusBus.h xf86VGAarbiter.h xf86Optionstr.h xf86platformBus.h
DISTCLEANFILES = xf86Build.h
CLEANFILES = $(BUILT_SOURCES)
diff --git a/hw/xfree86/common/xf86.h b/hw/xfree86/common/xf86.h
index 129660d81..88a219c7f 100644
--- a/hw/xfree86/common/xf86.h
+++ b/hw/xfree86/common/xf86.h
@@ -71,6 +71,11 @@ extern _X_EXPORT Bool fbSlotClaimed;
#if (defined(__sparc__) || defined(__sparc)) && !defined(__OpenBSD__)
extern _X_EXPORT Bool sbusSlotClaimed;
#endif
+
+#if defined(XSERVER_PLATFORM_BUS)
+extern _X_EXPORT int platformSlotClaimed;
+#endif
+
extern _X_EXPORT confDRIRec xf86ConfigDRI;
extern _X_EXPORT Bool xf86DRI2Enabled(void);
diff --git a/hw/xfree86/common/xf86AutoConfig.c b/hw/xfree86/common/xf86AutoConfig.c
index d0eb0affb..271ce86b6 100644
--- a/hw/xfree86/common/xf86AutoConfig.c
+++ b/hw/xfree86/common/xf86AutoConfig.c
@@ -198,10 +198,13 @@ listPossibleVideoDrivers(char *matches[], int nmatches)
}
i = 0;
+#ifdef XSERVER_PLATFORM_BUS
+ i = xf86PlatformMatchDriver(matches, nmatches);
+#endif
#ifdef sun
/* Check for driver type based on /dev/fb type and if valid, use
it instead of PCI bus probe results */
- if (xf86Info.consoleFd >= 0) {
+ if (xf86Info.consoleFd >= 0 && (i < (nmatches - 1))) {
struct vis_identifier visid;
const char *cp;
extern char xf86SolarisFbDev[PATH_MAX];
@@ -251,6 +254,7 @@ listPossibleVideoDrivers(char *matches[], int nmatches)
}
#endif
#ifdef __sparc__
+ if (i < (nmatches - 1))
{
char *sbusDriver = sparcDriverName();
@@ -259,7 +263,8 @@ listPossibleVideoDrivers(char *matches[], int nmatches)
}
#endif
#ifdef XSERVER_LIBPCIACCESS
- i = xf86PciMatchDriver(matches, nmatches);
+ if (i < (nmatches - 1))
+ i = xf86PciMatchDriver(matches, nmatches);
#endif
/* Fallback to platform default hardware */
if (i < (nmatches - 1)) {
diff --git a/hw/xfree86/common/xf86Bus.c b/hw/xfree86/common/xf86Bus.c
index 6c86f5e26..d0cfb2b3e 100644
--- a/hw/xfree86/common/xf86Bus.c
+++ b/hw/xfree86/common/xf86Bus.c
@@ -77,8 +77,14 @@ xf86CallDriverProbe(DriverPtr drv, Bool detect_only)
{
Bool foundScreen = FALSE;
+#ifdef XSERVER_PLATFORM_BUS
+ if (drv->platformProbe != NULL) {
+ foundScreen = xf86platformProbeDev(drv);
+ }
+#endif
+
#ifdef XSERVER_LIBPCIACCESS
- if (drv->PciProbe != NULL) {
+ if (!foundScreen && (drv->PciProbe != NULL)) {
if (xf86DoConfigure && xf86DoConfigurePass1) {
assert(detect_only);
foundScreen = xf86PciAddMatchingDev(drv);
@@ -202,6 +208,9 @@ xf86BusConfig(void)
void
xf86BusProbe(void)
{
+#ifdef XSERVER_PLATFORM_BUS
+ xf86platformProbe();
+#endif
#ifdef XSERVER_LIBPCIACCESS
xf86PciProbe();
#endif
@@ -238,6 +247,8 @@ StringToBusType(const char *busID, const char **retID)
ret = BUS_PCI;
if (!xf86NameCmp(p, "sbus"))
ret = BUS_SBUS;
+ if (!xf86NameCmp(p, "platform"))
+ ret = BUS_PLATFORM;
if (ret != BUS_NONE)
if (retID)
*retID = busID + strlen(p) + 1;
@@ -270,6 +281,8 @@ xf86IsEntityPrimary(int entityIndex)
return pEnt->bus.id.pci == primaryBus.id.pci;
case BUS_SBUS:
return pEnt->bus.id.sbus.fbNum == primaryBus.id.sbus.fbNum;
+ case BUS_PLATFORM:
+ return pEnt->bus.id.plat == primaryBus.id.plat;
default:
return FALSE;
}
@@ -541,6 +554,9 @@ xf86PostProbe(void)
#if (defined(__sparc__) || defined(__sparc)) && !defined(__OpenBSD__)
sbusSlotClaimed ||
#endif
+#ifdef XSERVER_PLATFORM_BUS
+ platformSlotClaimed ||
+#endif
#ifdef XSERVER_LIBPCIACCESS
pciSlotClaimed
#else
diff --git a/hw/xfree86/common/xf86Bus.h b/hw/xfree86/common/xf86Bus.h
index abf2efd1a..e83ba780a 100644
--- a/hw/xfree86/common/xf86Bus.h
+++ b/hw/xfree86/common/xf86Bus.h
@@ -42,6 +42,7 @@
#if defined(__sparc__) || defined(__sparc)
#include "xf86sbusBus.h"
#endif
+#include "xf86platformBus.h"
typedef struct {
DriverPtr driver;
diff --git a/hw/xfree86/common/xf86fbBus.c b/hw/xfree86/common/xf86fbBus.c
index 1e5162332..303b9c2f5 100644
--- a/hw/xfree86/common/xf86fbBus.c
+++ b/hw/xfree86/common/xf86fbBus.c
@@ -54,6 +54,10 @@ xf86ClaimFbSlot(DriverPtr drvp, int chipset, GDevPtr dev, Bool active)
EntityPtr p;
int num;
+#ifdef XSERVER_PLATFORM_BUS
+ if (platformSlotClaimed)
+ return -1;
+#endif
#ifdef XSERVER_LIBPCIACCESS
if (pciSlotClaimed)
return -1;
diff --git a/hw/xfree86/common/xf86pciBus.c b/hw/xfree86/common/xf86pciBus.c
index d758260b6..a2c18ebf2 100644
--- a/hw/xfree86/common/xf86pciBus.c
+++ b/hw/xfree86/common/xf86pciBus.c
@@ -110,7 +110,7 @@ xf86PciProbe(void)
xf86PciVideoInfo[num - 1] = info;
pci_device_probe(info);
- if (pci_device_is_boot_vga(info)) {
+ if (primaryBus.type == BUS_NONE && pci_device_is_boot_vga(info)) {
primaryBus.type = BUS_PCI;
primaryBus.id.pci = info;
}
@@ -352,7 +352,15 @@ xf86ComparePciBusString(const char *busID, int bus, int device, int func)
Bool
xf86IsPrimaryPci(struct pci_device *pPci)
{
- return ((primaryBus.type == BUS_PCI) && (pPci == primaryBus.id.pci));
+ if (primaryBus.type == BUS_PCI)
+ return pPci == primaryBus.id.pci;
+#ifdef XSERVER_PLATFORM_BUS
+ if (primaryBus.type == BUS_PLATFORM)
+ if (primaryBus.id.plat->pdev)
+ if (MATCH_PCI_DEVICES(primaryBus.id.plat->pdev, pPci))
+ return TRUE;
+#endif
+ return FALSE;
}
/*
@@ -367,7 +375,15 @@ xf86GetPciInfoForEntity(int entityIndex)
return NULL;
p = xf86Entities[entityIndex];
- return (p->bus.type == BUS_PCI) ? p->bus.id.pci : NULL;
+ switch (p->bus.type) {
+ case BUS_PCI:
+ return p->bus.id.pci;
+ case BUS_PLATFORM:
+ return p->bus.id.plat->pdev;
+ default:
+ break;
+ }
+ return NULL;
}
/*
@@ -400,6 +416,13 @@ xf86CheckPciSlot(const struct pci_device *d)
if ((p->bus.type == BUS_PCI) && (p->bus.id.pci == d)) {
return FALSE;
}
+#ifdef XSERVER_PLATFORM_BUS
+ if ((p->bus.type == BUS_PLATFORM) && (p->bus.id.plat->pdev)) {
+ struct pci_device *ud = p->bus.id.plat->pdev;
+ if (MATCH_PCI_DEVICES(ud, d))
+ return FALSE;
+ }
+#endif
}
return TRUE;
}
@@ -1065,8 +1088,8 @@ xf86ConfigActivePciEntity(ScrnInfoPtr pScrn, int entityIndex,
return TRUE;
}
-static int
-videoPtrToDriverList(struct pci_device *dev,
+int
+xf86VideoPtrToDriverList(struct pci_device *dev,
char *returnList[], int returnListMax)
{
int i;
@@ -1249,8 +1272,8 @@ xchomp(char *line)
* don't export their PCI ID's properly. If distros don't end up using this
* feature it can and should be removed because the symbol-based resolution
* scheme should be the primary one */
-static void
-matchDriverFromFiles(char **matches, uint16_t match_vendor, uint16_t match_chip)
+void
+xf86MatchDriverFromFiles(char **matches, uint16_t match_vendor, uint16_t match_chip)
{
DIR *idsdir;
FILE *fp;
@@ -1379,7 +1402,7 @@ xf86PciMatchDriver(char *matches[], int nmatches)
pci_iterator_destroy(iter);
#ifdef __linux__
if (info)
- matchDriverFromFiles(matches, info->vendor_id, info->device_id);
+ xf86MatchDriverFromFiles(matches, info->vendor_id, info->device_id);
#endif
for (i = 0; (i < nmatches) && (matches[i]); i++) {
@@ -1387,7 +1410,7 @@ xf86PciMatchDriver(char *matches[], int nmatches)
}
if ((info != NULL) && (i < nmatches)) {
- i += videoPtrToDriverList(info, &(matches[i]), nmatches - i);
+ i += xf86VideoPtrToDriverList(info, &(matches[i]), nmatches - i);
}
return i;
diff --git a/hw/xfree86/common/xf86pciBus.h b/hw/xfree86/common/xf86pciBus.h
index 56ec6e9e7..4972c3688 100644
--- a/hw/xfree86/common/xf86pciBus.h
+++ b/hw/xfree86/common/xf86pciBus.h
@@ -42,4 +42,14 @@ Bool xf86PciConfigure(void *busData, struct pci_device *pDev);
void xf86PciConfigureNewDev(void *busData, struct pci_device *pVideo,
GDevRec * GDev, int *chipset);
+#define MATCH_PCI_DEVICES(x, y) (((x)->domain == (y)->domain) && \
+ ((x)->bus == (y)->bus) && \
+ ((x)->func == (y)->func) && \
+ ((x)->dev == (y)->dev))
+
+void
+xf86MatchDriverFromFiles(char **matches, uint16_t match_vendor, uint16_t match_chip);
+int
+xf86VideoPtrToDriverList(struct pci_device *dev,
+ char *returnList[], int returnListMax);
#endif /* _XF86_PCI_BUS_H */
diff --git a/hw/xfree86/common/xf86platformBus.c b/hw/xfree86/common/xf86platformBus.c
new file mode 100644
index 000000000..50b7636ea
--- /dev/null
+++ b/hw/xfree86/common/xf86platformBus.c
@@ -0,0 +1,379 @@
+/*
+ * Copyright © 2012 Red Hat.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ *
+ * Author: Dave Airlie <airlied@redhat.com>
+ */
+
+/*
+ * This file contains the interfaces to the bus-specific code
+ */
+
+#ifdef HAVE_XORG_CONFIG_H
+#include <xorg-config.h>
+#endif
+
+#ifdef XSERVER_PLATFORM_BUS
+#include <errno.h>
+
+#include <pciaccess.h>
+#include <fcntl.h>
+#include <unistd.h>
+#include "os.h"
+#include "hotplug.h"
+
+#include "xf86.h"
+#include "xf86_OSproc.h"
+#include "xf86Priv.h"
+#include "xf86str.h"
+#include "xf86Bus.h"
+#include "Pci.h"
+#include "xf86platformBus.h"
+
+int platformSlotClaimed;
+
+int xf86_num_platform_devices;
+
+static struct xf86_platform_device *xf86_platform_devices;
+
+int
+xf86_add_platform_device(struct OdevAttributes *attribs)
+{
+ xf86_platform_devices = xnfrealloc(xf86_platform_devices,
+ (sizeof(struct xf86_platform_device)
+ * (xf86_num_platform_devices + 1)));
+
+ xf86_platform_devices[xf86_num_platform_devices].attribs = attribs;
+ xf86_platform_devices[xf86_num_platform_devices].pdev = NULL;
+
+ xf86_num_platform_devices++;
+ return 0;
+}
+
+int
+xf86_remove_platform_device(int dev_index)
+{
+ int j;
+
+ config_odev_free_attribute_list(xf86_platform_devices[dev_index].attribs);
+
+ for (j = dev_index; j < xf86_num_platform_devices - 1; j++)
+ memcpy(&xf86_platform_devices[j], &xf86_platform_devices[j + 1], sizeof(struct xf86_platform_device));
+ xf86_num_platform_devices--;
+ return 0;
+}
+
+Bool
+xf86_add_platform_device_attrib(int index, int attrib_id, char *attrib_name)
+{
+ struct xf86_platform_device *device = &xf86_platform_devices[index];
+
+ return config_odev_add_attribute(device->attribs, attrib_id, attrib_name);
+}
+
+char *
+xf86_get_platform_attrib(int index, int attrib_id)
+{
+ struct xf86_platform_device *device = &xf86_platform_devices[index];
+ struct OdevAttribute *oa;
+
+ xorg_list_for_each_entry(oa, &device->attribs->list, member) {
+ if (oa->attrib_id == attrib_id)
+ return oa->attrib_name;
+ }
+ return NULL;
+}
+
+char *
+xf86_get_platform_device_attrib(struct xf86_platform_device *device, int attrib_id)
+{
+ struct OdevAttribute *oa;
+
+ xorg_list_for_each_entry(oa, &device->attribs->list, member) {
+ if (oa->attrib_id == attrib_id)
+ return oa->attrib_name;
+ }
+ return NULL;
+}
+
+
+/*
+ * xf86IsPrimaryPlatform() -- return TRUE if primary device
+ * is a platform device and it matches this one.
+ */
+
+static Bool
+xf86IsPrimaryPlatform(struct xf86_platform_device *plat)
+{
+ return ((primaryBus.type == BUS_PLATFORM) && (plat == primaryBus.id.plat));
+}
+
+static void
+platform_find_pci_info(struct xf86_platform_device *pd, char *busid)
+{
+ struct pci_slot_match devmatch;
+ struct pci_device *info;
+ struct pci_device_iterator *iter;
+ int ret;
+
+ ret = sscanf(busid, "pci:%04x:%02x:%02x.%u",
+ &devmatch.domain, &devmatch.bus, &devmatch.dev,
+ &devmatch.func);
+ if (ret != 4)
+ return;
+
+ iter = pci_slot_match_iterator_create(&devmatch);
+ info = pci_device_next(iter);
+ if (info) {
+ pd->pdev = info;
+ pci_device_probe(info);
+ if (pci_device_is_boot_vga(info)) {
+ primaryBus.type = BUS_PLATFORM;
+ primaryBus.id.plat = pd;
+ }
+ }
+ pci_iterator_destroy(iter);
+
+}
+
+static Bool
+xf86_check_platform_slot(const struct xf86_platform_device *pd)
+{
+ int i;
+
+ for (i = 0; i < xf86NumEntities; i++) {
+ const EntityPtr u = xf86Entities[i];
+
+ if (pd->pdev && u->bus.type == BUS_PCI)
+ return !MATCH_PCI_DEVICES(pd->pdev, u->bus.id.pci);
+ if ((u->bus.type == BUS_PLATFORM) && (pd == u->bus.id.plat)) {
+ return FALSE;
+ }
+ }
+ return TRUE;
+}
+
+/**
+ * @return The numbers of found devices that match with the current system
+ * drivers.
+ */
+int
+xf86PlatformMatchDriver(char *matches[], int nmatches)
+{
+ int i, j = 0;
+ struct pci_device *info = NULL;
+ int pass = 0;
+
+ for (pass = 0; pass < 2; pass++) {
+ for (i = 0; i < xf86_num_platform_devices; i++) {
+
+ if (xf86IsPrimaryPlatform(&xf86_platform_devices[i]) && (pass == 1))
+ continue;
+ else if (!xf86IsPrimaryPlatform(&xf86_platform_devices[i]) && (pass == 0))
+ continue;
+
+ info = xf86_platform_devices[i].pdev;
+#ifdef __linux__
+ if (info)
+ xf86MatchDriverFromFiles(matches, info->vendor_id, info->device_id);
+#endif
+
+ for (j = 0; (j < nmatches) && (matches[j]); j++) {
+ /* find end of matches list */
+ }
+
+ if ((info != NULL) && (j < nmatches)) {
+ j += xf86VideoPtrToDriverList(info, &(matches[j]), nmatches - j);
+ }
+ }
+ }
+ return j;
+}
+
+int
+xf86platformProbe(void)
+{
+ int i;
+ Bool pci = TRUE;
+
+ if (!xf86scanpci()) {
+ pci = FALSE;
+ }
+
+ config_odev_probe(&xf86PlatformDeviceProbe);
+ for (i = 0; i < xf86_num_platform_devices; i++) {
+ char *busid = xf86_get_platform_attrib(i, ODEV_ATTRIB_BUSID);
+
+ if (pci && (strncmp(busid, "pci:", 4) == 0)) {
+ platform_find_pci_info(&xf86_platform_devices[i], busid);
+ }
+ }
+ return 0;
+}
+
+static int
+xf86ClaimPlatformSlot(struct xf86_platform_device * d, DriverPtr drvp,
+ int chipset, GDevPtr dev, Bool active)
+{
+ EntityPtr p = NULL;
+ int num;
+
+ if (xf86_check_platform_slot(d)) {
+ num = xf86AllocateEntity();
+ p = xf86Entities[num];
+ p->driver = drvp;
+ p->chipset = chipset;
+ p->bus.type = BUS_PLATFORM;
+ p->bus.id.plat = d;
+ p->active = active;
+ p->inUse = FALSE;
+ if (dev)
+ xf86AddDevToEntity(num, dev);
+
+ platformSlotClaimed++;
+ return num;
+ }
+ else
+ return -1;
+}
+
+static int
+xf86UnclaimPlatformSlot(struct xf86_platform_device *d, GDevPtr dev)
+{
+ int i;
+
+ for (i = 0; i < xf86NumEntities; i++) {
+ const EntityPtr p = xf86Entities[i];
+
+ if ((p->bus.type == BUS_PLATFORM) && (p->bus.id.plat == d)) {
+ if (dev)
+ xf86RemoveDevFromEntity(i, dev);
+ platformSlotClaimed--;
+ p->bus.type = BUS_NONE;
+ return 0;
+ }
+ }
+ return 0;
+}
+
+
+#define END_OF_MATCHES(m) \
+ (((m).vendor_id == 0) && ((m).device_id == 0) && ((m).subvendor_id == 0))
+
+static Bool doPlatformProbe(struct xf86_platform_device *dev, DriverPtr drvp,
+ GDevPtr gdev, int flags, intptr_t match_data)
+{
+ Bool foundScreen = FALSE;
+ int entity;
+
+ if (gdev->screen == 0 && !xf86_check_platform_slot(dev))
+ return FALSE;
+
+ entity = xf86ClaimPlatformSlot(dev, drvp, 0,
+ gdev, gdev->active);
+
+ if ((entity == -1) && (gdev->screen > 0)) {
+ unsigned nent;
+
+ for (nent = 0; nent < xf86NumEntities; nent++) {
+ EntityPtr pEnt = xf86Entities[nent];
+
+ if (pEnt->bus.type != BUS_PLATFORM)
+ continue;
+ if (pEnt->bus.id.plat == dev) {
+ entity = nent;
+ xf86AddDevToEntity(nent, gdev);
+ break;
+ }
+ }
+ }
+ if (entity != -1) {
+ if (drvp->platformProbe(drvp, entity, flags, dev, match_data))
+ foundScreen = TRUE;
+ else
+ xf86UnclaimPlatformSlot(dev, gdev);
+ }
+ return foundScreen;
+}
+
+static Bool
+probeSingleDevice(struct xf86_platform_device *dev, DriverPtr drvp, GDevPtr gdev, int flags)
+{
+ int k;
+ Bool foundScreen = FALSE;
+ struct pci_device *pPci;
+ const struct pci_id_match *const devices = drvp->supported_devices;
+
+ if (dev->pdev && devices) {
+ int device_id = dev->pdev->device_id;
+ pPci = dev->pdev;
+ for (k = 0; !END_OF_MATCHES(devices[k]); k++) {
+ if (PCI_ID_COMPARE(devices[k].vendor_id, pPci->vendor_id)
+ && PCI_ID_COMPARE(devices[k].device_id, device_id)
+ && ((devices[k].device_class_mask & pPci->device_class)
+ == devices[k].device_class)) {
+ foundScreen = doPlatformProbe(dev, drvp, gdev, flags, devices[k].match_data);
+ if (foundScreen)
+ break;
+ }
+ }
+ }
+ else if (dev->pdev && !devices)
+ return FALSE;
+ else
+ foundScreen = doPlatformProbe(dev, drvp, gdev, flags, 0);
+ return foundScreen;
+}
+
+int
+xf86platformProbeDev(DriverPtr drvp)
+{
+ Bool foundScreen = FALSE;
+ GDevPtr *devList;
+ const unsigned numDevs = xf86MatchDevice(drvp->driverName, &devList);
+ int i, j;
+
+ /* find the main device or any device specificed in xorg.conf */
+ for (i = 0; i < numDevs; i++) {
+ for (j = 0; j < xf86_num_platform_devices; j++) {
+ if (devList[i]->busID && *devList[i]->busID) {
+ if (xf86PlatformDeviceCheckBusID(&xf86_platform_devices[j], devList[i]->busID))
+ break;
+ }
+ else {
+ if (xf86_platform_devices[j].pdev) {
+ if (xf86IsPrimaryPlatform(&xf86_platform_devices[j]))
+ break;
+ }
+ }
+ }
+
+ if (j == xf86_num_platform_devices)
+ continue;
+
+ foundScreen = probeSingleDevice(&xf86_platform_devices[j], drvp, devList[i], 0);
+ if (!foundScreen)
+ continue;
+ }
+
+ return foundScreen;
+}
+
+#endif
diff --git a/hw/xfree86/common/xf86platformBus.h b/hw/xfree86/common/xf86platformBus.h
new file mode 100644
index 000000000..15a3022ac
--- /dev/null
+++ b/hw/xfree86/common/xf86platformBus.h
@@ -0,0 +1,59 @@
+/*
+ * Copyright © 2012 Red Hat.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ *
+ * Author: Dave Airlie <airlied@redhat.com>
+ */
+#ifndef XF86_PLATFORM_BUS_H
+#define XF86_PLATFORM_BUS_H
+
+#include "hotplug.h"
+
+struct xf86_platform_device {
+ struct OdevAttributes *attribs;
+ /* for PCI devices */
+ struct pci_device *pdev;
+};
+
+#ifdef XSERVER_PLATFORM_BUS
+int xf86platformProbe(void);
+int xf86platformProbeDev(DriverPtr drvp);
+
+extern int xf86_num_platform_devices;
+
+extern char *
+xf86_get_platform_attrib(int index, int attrib_id);
+extern int
+xf86_add_platform_device(struct OdevAttributes *attribs);
+extern int
+xf86_remove_platform_device(int dev_index);
+extern Bool
+xf86_add_platform_device_attrib(int index, int attrib_id, char *attrib_str);
+
+extern _X_EXPORT char *
+xf86_get_platform_device_attrib(struct xf86_platform_device *device, int attrib_id);
+extern _X_EXPORT Bool
+xf86PlatformDeviceCheckBusID(struct xf86_platform_device *device, const char *busid);
+
+extern _X_EXPORT int
+xf86PlatformMatchDriver(char *matches[], int nmatches);
+#endif
+
+#endif
diff --git a/hw/xfree86/common/xf86str.h b/hw/xfree86/common/xf86str.h
index a1404c3aa..e12dcc4ce 100644
--- a/hw/xfree86/common/xf86str.h
+++ b/hw/xfree86/common/xf86str.h
@@ -311,6 +311,7 @@ struct _SymTabRec;
struct _PciChipsets;
struct pci_device;
+struct xf86_platform_device;
typedef struct _DriverRec {
int driverVersion;
@@ -325,9 +326,16 @@ typedef struct _DriverRec {
const struct pci_id_match *supported_devices;
Bool (*PciProbe) (struct _DriverRec * drv, int entity_num,
struct pci_device * dev, intptr_t match_data);
+ Bool (*platformProbe) (struct _DriverRec * drv, int entity_num, int flags,
+ struct xf86_platform_device * dev, intptr_t match_data);
} DriverRec, *DriverPtr;
/*
+ * platform probe flags
+ * no flags are defined yet - but drivers should fail to load if a flag they
+ * don't understand is passed.
+ */
+/*
* AddDriver flags
*/
#define HaveDriverFuncs 1
@@ -343,6 +351,7 @@ typedef struct _DriverRec {
#undef BUS_NONE
#undef BUS_PCI
#undef BUS_SBUS
+#undef BUS_PLATFORM
#undef BUS_last
#endif
@@ -350,6 +359,7 @@ typedef enum {
BUS_NONE,
BUS_PCI,
BUS_SBUS,
+ BUS_PLATFORM,
BUS_last /* Keep last */
} BusType;
@@ -362,6 +372,7 @@ typedef struct _bus {
union {
struct pci_device *pci;
SbusBusId sbus;
+ struct xf86_platform_device *plat;
} id;
} BusRec, *BusPtr;
diff --git a/hw/xfree86/os-support/linux/Makefile.am b/hw/xfree86/os-support/linux/Makefile.am
index 36748df2c..61175b386 100644
--- a/hw/xfree86/os-support/linux/Makefile.am
+++ b/hw/xfree86/os-support/linux/Makefile.am
@@ -22,7 +22,7 @@ XORG_CFLAGS += -DHAVE_APM
endif
liblinux_la_SOURCES = lnx_init.c lnx_video.c \
- lnx_agp.c lnx_kmod.c lnx_bell.c \
+ lnx_agp.c lnx_kmod.c lnx_bell.c lnx_platform.c \
$(srcdir)/../shared/bios_mmap.c \
$(srcdir)/../shared/VTsw_usl.c \
$(srcdir)/../shared/posix_tty.c \
diff --git a/hw/xfree86/os-support/linux/lnx_platform.c b/hw/xfree86/os-support/linux/lnx_platform.c
new file mode 100644
index 000000000..9c63ee543
--- /dev/null
+++ b/hw/xfree86/os-support/linux/lnx_platform.c
@@ -0,0 +1,130 @@
+#ifdef HAVE_XORG_CONFIG_H
+#include <xorg-config.h>
+#endif
+
+#ifdef XSERVER_PLATFORM_BUS
+
+#include <xf86drm.h>
+#include <fcntl.h>
+#include <unistd.h>
+
+/* Linux platform device support */
+#include "xf86_OSproc.h"
+
+#include "xf86.h"
+#include "xf86platformBus.h"
+#include "xf86Bus.h"
+
+static Bool
+get_drm_info(struct OdevAttributes *attribs, char *path)
+{
+ drmSetVersion sv;
+ char *buf;
+ int fd;
+
+ fd = open(path, O_RDWR, O_CLOEXEC);
+ if (fd == -1)
+ return FALSE;
+
+ sv.drm_di_major = 1;
+ sv.drm_di_minor = 4;
+ sv.drm_dd_major = -1; /* Don't care */
+ sv.drm_dd_minor = -1; /* Don't care */
+ if (drmSetInterfaceVersion(fd, &sv)) {
+ ErrorF("setversion 1.4 failed\n");
+ return FALSE;
+ }
+
+ xf86_add_platform_device(attribs);
+
+ buf = drmGetBusid(fd);
+ xf86_add_platform_device_attrib(xf86_num_platform_devices - 1,
+ ODEV_ATTRIB_BUSID, buf);
+ drmFreeBusid(buf);
+ close(fd);
+ return TRUE;
+}
+
+Bool
+xf86PlatformDeviceCheckBusID(struct xf86_platform_device *device, const char *busid)
+{
+ struct OdevAttribute *attrib;
+ const char *syspath = NULL;
+ BusType bustype;
+ const char *id;
+ xorg_list_for_each_entry(attrib, &device->attribs->list, member) {
+ if (attrib->attrib_id == ODEV_ATTRIB_SYSPATH) {
+ syspath = attrib->attrib_name;
+ break;
+ }
+ }
+
+ if (!syspath)
+ return FALSE;
+
+ bustype = StringToBusType(busid, &id);
+ if (bustype == BUS_PCI) {
+ struct pci_device *pPci = device->pdev;
+ if (xf86ComparePciBusString(busid,
+ ((pPci->domain << 8)
+ | pPci->bus),
+ pPci->dev, pPci->func)) {
+ return TRUE;
+ }
+ }
+ else if (bustype == BUS_PLATFORM) {
+ /* match on the minimum string */
+ int len = strlen(id);
+
+ if (strlen(syspath) < strlen(id))
+ len = strlen(syspath);
+
+ if (strncmp(id, syspath, len))
+ return FALSE;
+ return TRUE;
+ }
+ return FALSE;
+}
+
+void
+xf86PlatformDeviceProbe(struct OdevAttributes *attribs)
+{
+ struct OdevAttribute *attrib;
+ int i;
+ char *path = NULL;
+ Bool ret;
+
+ xorg_list_for_each_entry(attrib, &attribs->list, member) {
+ if (attrib->attrib_id == ODEV_ATTRIB_PATH) {
+ path = attrib->attrib_name;
+ break;
+ }
+ }
+ if (!path)
+ goto out_free;
+
+ for (i = 0; i < xf86_num_platform_devices; i++) {
+ char *dpath;
+ dpath = xf86_get_platform_attrib(i, ODEV_ATTRIB_PATH);
+
+ if (!strcmp(path, dpath))
+ break;
+ }
+
+ if (i != xf86_num_platform_devices)
+ goto out_free;
+
+ LogMessage(X_INFO, "config/udev: Adding drm device (%s)\n",
+ path);
+
+ ret = get_drm_info(attribs, path);
+ if (ret == FALSE)
+ goto out_free;
+
+ return;
+
+out_free:
+ config_odev_free_attribute_list(attribs);
+}
+
+#endif
diff --git a/hw/xfree86/os-support/shared/platform_noop.c b/hw/xfree86/os-support/shared/platform_noop.c
new file mode 100644
index 000000000..199ae5e8e
--- /dev/null
+++ b/hw/xfree86/os-support/shared/platform_noop.c
@@ -0,0 +1,23 @@
+
+#ifdef HAVE_XORG_CONFIG_H
+#include <xorg-config.h>
+#endif
+
+#ifdef XSERVER_PLATFORM_BUS
+/* noop platform device support */
+#include "xf86_OSproc.h"
+
+#include "xf86.h"
+#include "xf86platformBus.h"
+
+Bool
+xf86PlatformDeviceCheckBusID(struct xf86_platform_device *device, const char *busid)
+{
+ return FALSE;
+}
+
+void xf86PlatformDeviceProbe(struct OdevAttributes *attribs)
+{
+
+}
+#endif
diff --git a/hw/xfree86/os-support/xf86_OSproc.h b/hw/xfree86/os-support/xf86_OSproc.h
index e171146dd..2f0172e15 100644
--- a/hw/xfree86/os-support/xf86_OSproc.h
+++ b/hw/xfree86/os-support/xf86_OSproc.h
@@ -221,6 +221,12 @@ extern _X_EXPORT void xf86InitVidMem(void);
#endif /* XF86_OS_PRIVS */
+#ifdef XSERVER_PLATFORM_BUS
+#include "hotplug.h"
+void
+xf86PlatformDeviceProbe(struct OdevAttributes *attribs);
+#endif
+
_XFUNCPROTOEND
#endif /* NO_OSLIB_PROTOTYPES */
#endif /* _XF86_OSPROC_H */
diff --git a/include/dix-config.h.in b/include/dix-config.h.in
index 3c9bbafeb..77681a953 100644
--- a/include/dix-config.h.in
+++ b/include/dix-config.h.in
@@ -390,6 +390,9 @@
/* Use libudev for input hotplug */
#undef CONFIG_UDEV
+/* Use libudev for kms enumeration */
+#undef CONFIG_UDEV_KMS
+
/* Use udev_monitor_filter_add_match_tag() */
#undef HAVE_UDEV_MONITOR_FILTER_ADD_MATCH_TAG
diff --git a/include/hotplug.h b/include/hotplug.h
index f3eeea21d..50007624a 100644
--- a/include/hotplug.h
+++ b/include/hotplug.h
@@ -26,8 +26,43 @@
#ifndef HOTPLUG_H
#define HOTPLUG_H
+#include "list.h"
+
extern _X_EXPORT void config_pre_init(void);
extern _X_EXPORT void config_init(void);
extern _X_EXPORT void config_fini(void);
+struct OdevAttribute {
+ struct xorg_list member;
+ int attrib_id;
+ char *attrib_name;
+};
+
+struct OdevAttributes {
+ struct xorg_list list;
+};
+
+struct OdevAttributes *
+config_odev_allocate_attribute_list(void);
+
+void
+config_odev_free_attribute_list(struct OdevAttributes *attribs);
+
+Bool
+config_odev_add_attribute(struct OdevAttributes *attribs, int attrib,
+ const char *attrib_name);
+
+void
+config_odev_free_attributes(struct OdevAttributes *attribs);
+
+/* path to kernel device node - Linux e.g. /dev/dri/card0 */
+#define ODEV_ATTRIB_PATH 1
+/* system device path - Linux e.g. /sys/devices/pci0000:00/0000:00:01.0/0000:01:00.0/drm/card1 */
+#define ODEV_ATTRIB_SYSPATH 2
+/* DRI-style bus id */
+#define ODEV_ATTRIB_BUSID 3
+
+typedef void (*config_odev_probe_proc_ptr)(struct OdevAttributes *attribs);
+void config_odev_probe(config_odev_probe_proc_ptr probe_callback);
+
#endif /* HOTPLUG_H */
diff --git a/include/xorg-config.h.in b/include/xorg-config.h.in
index 2cc416ae7..a71b25d72 100644
--- a/include/xorg-config.h.in
+++ b/include/xorg-config.h.in
@@ -136,4 +136,7 @@
/* Have getresuid */
#undef HAVE_GETRESUID
+/* Have X server platform bus support */
+#undef XSERVER_PLATFORM_BUS
+
#endif /* _XORG_CONFIG_H_ */
diff --git a/include/xorg-server.h.in b/include/xorg-server.h.in
index 8086f32ae..c0761f78a 100644
--- a/include/xorg-server.h.in
+++ b/include/xorg-server.h.in
@@ -205,6 +205,9 @@
/* X Access Control Extension */
#undef XACE
+/* Have X server platform bus support */
+#undef XSERVER_PLATFORM_BUS
+
#ifdef _LP64
#define _XSERVER64 1
#endif