Hi,

I'm using using the above mentioned patch for more than one year
without any issue, with 2 PCI express GPU Ati R230 and Debian Sid.

Eachtime a new revision of xserver-xorg is published I must recompile
to include the patch, but it the patch fails to fully apply on xserver
1.20.1-5

I took the freedom to update it; you can find it in attachment.



-- 
Cordialement,
Thierry Bugier
diff --git a/config/10-auto-bind-gpu.conf b/config/10-auto-bind-gpu.conf
new file mode 100644
index 0000000..7fbff4b
--- /dev/null
+++ b/config/10-auto-bind-gpu.conf
@@ -0,0 +1,3 @@
+Section "ServerFlags"
+    Option "AutoBindGPU" "true"
+EndSection
diff --git a/config/Makefile.am b/config/Makefile.am
index 51aae47..532e51a 100644
--- a/config/Makefile.am
+++ b/config/Makefile.am
@@ -18,7 +18,7 @@ libconfig_la_LIBADD += $(UDEV_LIBS)
 
 if XORG
 xorgconfddir = $(datadir)/X11/$(XF86CONFIGDIR)
-xorgconfd_DATA = 10-quirks.conf
+xorgconfd_DATA = 10-quirks.conf 10-auto-bind-gpu.conf
 endif
 
 else
@@ -38,4 +38,4 @@ endif # !CONFIG_HAL
 
 endif # !CONFIG_UDEV
 
-EXTRA_DIST = x11-input.fdi fdi2iclass.py 10-quirks.conf
+EXTRA_DIST = x11-input.fdi fdi2iclass.py 10-quirks.conf 10-auto-bind-gpu.conf
diff --git a/hw/xfree86/common/xf86Config.c b/hw/xfree86/common/xf86Config.c
index 2c1d335..b49f25d 100644
--- a/hw/xfree86/common/xf86Config.c
+++ b/hw/xfree86/common/xf86Config.c
@@ -643,6 +643,7 @@ typedef enum {
     FLAG_DRI2,
     FLAG_USE_SIGIO,
     FLAG_AUTO_ADD_GPU,
+    FLAG_AUTO_BIND_GPU,
     FLAG_MAX_CLIENTS,
     FLAG_IGLX,
     FLAG_DEBUG,
@@ -699,6 +700,8 @@ static OptionInfoRec FlagOptions[] = {
      {0}, FALSE},
     {FLAG_AUTO_ADD_GPU, "AutoAddGPU", OPTV_BOOLEAN,
      {0}, FALSE},
+    {FLAG_AUTO_BIND_GPU, "AutoBindGPU", OPTV_BOOLEAN,
+     {0}, FALSE},
     {FLAG_MAX_CLIENTS, "MaxClients", OPTV_INTEGER,
      {0}, FALSE },
     {FLAG_IGLX, "IndirectGLX", OPTV_BOOLEAN,
@@ -779,6 +782,22 @@ configServerFlags(XF86ConfFlagsPtr flagsconf, XF86OptionPtr layoutopts)
     }
     xf86Msg(from, "%sutomatically adding GPU devices\n",
             xf86Info.autoAddGPU ? "A" : "Not a");
+
+    if (xf86AutoBindGPU) {
+        xf86Info.autoBindGPU = TRUE;
+        from = X_CMDLINE;
+    }
+    else if (xf86IsOptionSet(FlagOptions, FLAG_AUTO_BIND_GPU)) {
+        xf86GetOptValBool(FlagOptions, FLAG_AUTO_BIND_GPU,
+                          &xf86Info.autoBindGPU);
+        from = X_CONFIG;
+    }
+    else {
+        from = X_DEFAULT;
+    }
+    xf86Msg(from, "%sutomatically binding GPU devices\n",
+            xf86Info.autoBindGPU ? "A" : "Not a");
+
     /*
      * Set things up based on the config file information.  Some of these
      * settings may be overridden later when the command line options are
diff --git a/hw/xfree86/common/xf86Globals.c b/hw/xfree86/common/xf86Globals.c
index 7cc7401..64694f7 100644
--- a/hw/xfree86/common/xf86Globals.c
+++ b/hw/xfree86/common/xf86Globals.c
@@ -133,6 +133,7 @@ xf86InfoRec xf86Info = {
 #else
     .autoAddGPU = FALSE,
 #endif
+    .autoBindGPU = FALSE,
 };
 
 const char *xf86ConfigFile = NULL;
@@ -193,6 +194,7 @@ Bool xf86FlipPixels = FALSE;
 Gamma xf86Gamma = { 0.0, 0.0, 0.0 };
 
 Bool xf86AllowMouseOpenFail = FALSE;
+Bool xf86AutoBindGPU = FALSE;
 
 #ifdef XF86VIDMODE
 Bool xf86VidModeDisabled = FALSE;
diff --git a/hw/xfree86/common/xf86Init.c b/hw/xfree86/common/xf86Init.c
index 3c5cc70..f654db1 100644
--- a/hw/xfree86/common/xf86Init.c
+++ b/hw/xfree86/common/xf86Init.c
@@ -76,6 +76,7 @@
 #include "xf86DDC.h"
 #include "xf86Xinput.h"
 #include "xf86InPriv.h"
+#include "xf86Crtc.h"
 #include "picturestr.h"
 #include "randrstr.h"
 #include "glxvndabi.h"
@@ -237,6 +238,15 @@ xf86PrivsElevated(void)
     return PrivsElevated();
 }
 
+static void
+xf86AutoConfigOutputDevices(void)
+{
+    int i;
+
+    for (i = 0; i < xf86NumGPUScreens; i++)
+        xf86AutoConfigOutputDevice(xf86GPUScreens[i], xf86Screens[0]);
+}
+
 static void
 TrapSignals(void)
 {
@@ -770,6 +780,8 @@ InitOutput(ScreenInfo * pScreenInfo, int argc, char **argv)
     for (i = 0; i < xf86NumGPUScreens; i++)
         AttachUnboundGPU(xf86Screens[0]->pScreen, xf86GPUScreens[i]->pScreen);
 
+    xf86AutoConfigOutputDevices();
+
     xf86VGAarbiterWrapFunctions();
     if (sigio_blocked)
         input_unlock();
@@ -1278,6 +1290,10 @@ ddxProcessArgument(int argc, char **argv, int i)
         xf86Info.iglxFrom = X_CMDLINE;
         return 0;
     }
+    if (!strcmp(argv[i], "-autoBindGPU")) {
+        xf86AutoBindGPU = TRUE;
+        return 1;
+    }
 
     /* OS-specific processing */
     return xf86ProcessArgument(argc, argv, i);
diff --git a/hw/xfree86/common/xf86Priv.h b/hw/xfree86/common/xf86Priv.h
index 393af39..89ce3a5 100644
--- a/hw/xfree86/common/xf86Priv.h
+++ b/hw/xfree86/common/xf86Priv.h
@@ -46,6 +46,7 @@
 extern _X_EXPORT const char *xf86ConfigFile;
 extern _X_EXPORT const char *xf86ConfigDir;
 extern _X_EXPORT Bool xf86AllowMouseOpenFail;
+extern _X_EXPORT Bool xf86AutoBindGPU;
 
 #ifdef XF86VIDMODE
 extern _X_EXPORT Bool xf86VidModeDisabled;
diff --git a/hw/xfree86/common/xf86Privstr.h b/hw/xfree86/common/xf86Privstr.h
index 21c2e1f..b2d6bf8 100644
--- a/hw/xfree86/common/xf86Privstr.h
+++ b/hw/xfree86/common/xf86Privstr.h
@@ -97,6 +97,7 @@ typedef struct {
     MessageType dri2From;
 
     Bool autoAddGPU;
+    Bool autoBindGPU;
     const char *debug;
 } xf86InfoRec, *xf86InfoPtr;
 
diff --git a/hw/xfree86/common/xf86platformBus.c b/hw/xfree86/common/xf86platformBus.c
index cef47da..bce798d 100644
--- a/hw/xfree86/common/xf86platformBus.c
+++ b/hw/xfree86/common/xf86platformBus.c
@@ -49,6 +49,7 @@
 #include "Pci.h"
 #include "xf86platformBus.h"
 #include "xf86Config.h"
+#include "xf86Crtc.h"
 
 #include "randrstr.h"
 int platformSlotClaimed;
@@ -665,6 +666,7 @@ xf86platformAddDevice(int index)
    }
    /* attach unbound to 0 protocol screen */
    AttachUnboundGPU(xf86Screens[0]->pScreen, xf86GPUScreens[i]->pScreen);
+   xf86AutoConfigOutputDevice(xf86GPUScreens[i], xf86Screens[0]);
 
    RRResourcesChanged(xf86Screens[0]->pScreen);
    RRTellChanged(xf86Screens[0]->pScreen);
diff --git a/hw/xfree86/man/Xorg.man b/hw/xfree86/man/Xorg.man
index 13a9dc3..da0db98 100644
--- a/hw/xfree86/man/Xorg.man
+++ b/hw/xfree86/man/Xorg.man
@@ -154,6 +154,14 @@ option, and is provided for compatibility with the native SCO X server.
 Sets the default color depth.  Legal values are 1, 4, 8, 15, 16, and
 24.  Not all drivers support all values.
 .TP 8
+.B \-autoBindGPU
+Enable automatically setting secondary GPUs up as output sinks and offload
+sources. Making e.g. laptop outputs connected only to the secondary GPU directly
+available for use without needing to run "xrandr --setprovideroutputsource".
+This is equivalent to the
+.B AutoBindGPU
+xorg.conf(__filemansuffix__) file option.
+.TP 8
 .B \-disableVidMode
 Disable the parts of the VidMode extension (used by the xvidtune
 client) that can be used to change the video modes.  This is equivalent
diff --git a/hw/xfree86/man/xorg.conf.man b/hw/xfree86/man/xorg.conf.man
index 9589262..163b6f9 100644
--- a/hw/xfree86/man/xorg.conf.man
+++ b/hw/xfree86/man/xorg.conf.man
@@ -672,6 +672,12 @@ Enabled by default.
 If this option is disabled, then no GPU devices will be added from the udev
 backend. Enabled by default. (May need to be disabled to setup Xinerama).
 .TP 7
+.BI "Option \*qAutoBindGPU\*q  \*q" boolean \*q
+If enabled then secondary GPUs will be automatically set up as output-sinks and
+offload-sources. Making e.g. laptop outputs connected only to the secondary
+GPU directly available for use without needing to run
+"xrandr --setprovideroutputsource". Disabled by default.
+.TP 7
 .BI "Option \*qLog\*q \*q" string \*q
 This option controls whether the log is flushed and/or synced to disk after
 each message.
diff --git a/hw/xfree86/modes/xf86Crtc.c b/hw/xfree86/modes/xf86Crtc.c
index 37a45bb..169f33e 100644
--- a/hw/xfree86/modes/xf86Crtc.c
+++ b/hw/xfree86/modes/xf86Crtc.c
@@ -3515,3 +3515,31 @@ xf86DetachAllCrtc(ScrnInfoPtr scrn)
             crtc->x = crtc->y = 0;
         }
 }
+
+void xf86AutoConfigOutputDevice(ScrnInfoPtr pScrn, ScrnInfoPtr master)
+{
+    RRProviderPtr master_provider;
+    xf86CrtcConfigPtr config = XF86_CRTC_CONFIG_PTR(master);
+    xf86CrtcConfigPtr slave_config = XF86_CRTC_CONFIG_PTR(pScrn);
+
+    if (!xf86Info.autoBindGPU)
+        return;
+
+    if (!config || !slave_config)
+        return;
+
+    master_provider = config->randr_provider;
+
+    if ((master->capabilities & RR_Capability_SinkOffload) &&
+               pScrn->capabilities & RR_Capability_SourceOffload) {
+        /* source offload */
+        AttachOffloadGPU(master->pScreen, pScrn->pScreen);
+        slave_config->randr_provider->offload_sink = master_provider;
+    }
+    if ((master->capabilities & RR_Capability_SourceOutput) &&
+               pScrn->capabilities & RR_Capability_SinkOutput) {
+        /* sink offload */
+        AttachOutputGPU(master->pScreen, pScrn->pScreen);
+        slave_config->randr_provider->output_source = master_provider;
+    }
+}
diff --git a/hw/xfree86/modes/xf86Crtc.h b/hw/xfree86/modes/xf86Crtc.h
index 1d1124a..d701f0a 100644
--- a/hw/xfree86/modes/xf86Crtc.h
+++ b/hw/xfree86/modes/xf86Crtc.h
@@ -1140,4 +1140,7 @@ xf86ProviderSetup(ScrnInfoPtr scrn,
 extern _X_EXPORT void
 xf86DetachAllCrtc(ScrnInfoPtr scrn);
 
+extern _X_EXPORT void
+xf86AutoConfigOutputDevice(ScrnInfoPtr pScrn, ScrnInfoPtr master);
+
 #endif                          /* _XF86CRTC_H_ */

Reply via email to