From: Dave Airlie airl...@redhat.com
This patch introduces gpu screens into screenInfo. It adds interfaces
for adding and removing gpu screens, along with adding private fixup,
block handler support, and scratch pixmap init.
GPU screens have a myNum that is offset by GPU_SCREEN_OFFSET (256),
this is used for logging etc.
v2: no glyph pictures for GPU screens for now.
v3: introduce MAXGPUSCREENS, fix return value check
Signed-off-by: Dave Airlie airl...@redhat.com
---
dix/dispatch.c | 75 --
dix/dixutils.c |6
dix/main.c | 15 ++
dix/privates.c |5
include/misc.h |4 +++
include/screenint.h |9 ++
include/scrnintstr.h |4 +++
render/glyph.c |2 ++
8 files changed, 118 insertions(+), 2 deletions(-)
diff --git a/dix/dispatch.c b/dix/dispatch.c
index 34d82f4..b0fc531 100644
--- a/dix/dispatch.c
+++ b/dix/dispatch.c
@@ -3724,7 +3724,7 @@ with its screen number, a pointer to its ScreenRec, argc,
and argv.
*/
-static int init_screen(ScreenPtr pScreen, int i)
+static int init_screen(ScreenPtr pScreen, int i, Bool gpu)
{
int scanlinepad, format, depth, bitsPerPixel, j, k;
@@ -3732,6 +3732,10 @@ static int init_screen(ScreenPtr pScreen, int i)
return -1;
}
pScreen-myNum = i;
+if (gpu) {
+pScreen-myNum += GPU_SCREEN_OFFSET;
+pScreen-isGPU = TRUE;
+}
pScreen-totalPixmapSize = 0; /* computed in
CreateScratchPixmapForScreen */
pScreen-ClipNotify = 0;/* for R4 ddx compatibility */
pScreen-CreateScreenResources = 0;
@@ -3788,7 +3792,7 @@ AddScreen(Bool (*pfnInit) (ScreenPtr /*pScreen */ ,
if (!pScreen)
return -1;
-ret = init_screen(pScreen, i);
+ret = init_screen(pScreen, i, FALSE);
if (ret != 0) {
free(pScreen);
return ret;
@@ -3817,3 +3821,70 @@ AddScreen(Bool (*pfnInit) (ScreenPtr /*pScreen */ ,
return i;
}
+
+int
+AddGPUScreen(Bool (*pfnInit) (ScreenPtr /*pScreen */ ,
+ int /*argc */ ,
+ char ** /*argv */
+ ),
+ int argc, char **argv)
+{
+int i;
+ScreenPtr pScreen;
+Bool ret;
+
+i = screenInfo.numGPUScreens;
+if (i == MAXGPUSCREENS)
+return -1;
+
+pScreen = (ScreenPtr) calloc(1, sizeof(ScreenRec));
+if (!pScreen)
+return -1;
+
+ret = init_screen(pScreen, i, TRUE);
+if (ret != 0) {
+free(pScreen);
+return ret;
+}
+
+/* This is where screen specific stuff gets initialized. Load the
+ screen structure, call the hardware, whatever.
+ This is also where the default colormap should be allocated and
+ also pixel values for blackPixel, whitePixel, and the cursor
+ Note that InitScreen is NOT allowed to modify argc, argv, or
+ any of the strings pointed to by argv. They may be passed to
+ multiple screens.
+ */
+screenInfo.gpuscreens[i] = pScreen;
+screenInfo.numGPUScreens++;
+if (!(*pfnInit) (pScreen, argc, argv)) {
+dixFreePrivates(pScreen-devPrivates, PRIVATE_SCREEN);
+free(pScreen);
+screenInfo.numGPUScreens--;
+return -1;
+}
+
+update_desktop_dimensions();
+
+dixRegisterScreenPrivateKey(cursorScreenDevPriv, pScreen, PRIVATE_CURSOR,
+0);
+
+return i;
+}
+
+void
+RemoveGPUScreen(ScreenPtr pScreen)
+{
+int idx, j;
+if (!pScreen-isGPU)
+return;
+
+idx = pScreen-myNum - GPU_SCREEN_OFFSET;
+for (j = idx; j screenInfo.numGPUScreens - 1; j++) {
+screenInfo.gpuscreens[j] = screenInfo.gpuscreens[j + 1];
+}
+screenInfo.numGPUScreens--;
+
+free(pScreen);
+
+}
diff --git a/dix/dixutils.c b/dix/dixutils.c
index b249a81..3f24629 100644
--- a/dix/dixutils.c
+++ b/dix/dixutils.c
@@ -386,6 +386,9 @@ BlockHandler(pointer pTimeout, pointer pReadmask)
for (i = 0; i screenInfo.numScreens; i++)
(*screenInfo.screens[i]-BlockHandler) (screenInfo.screens[i],
pTimeout, pReadmask);
+for (i = 0; i screenInfo.numGPUScreens; i++)
+(*screenInfo.gpuscreens[i]-BlockHandler) (screenInfo.gpuscreens[i],
+ pTimeout, pReadmask);
for (i = 0; i numHandlers; i++)
if (!handlers[i].deleted)
(*handlers[i].BlockHandler) (handlers[i].blockData,
@@ -422,6 +425,9 @@ WakeupHandler(int result, pointer pReadmask)
for (i = 0; i screenInfo.numScreens; i++)
(*screenInfo.screens[i]-WakeupHandler) (screenInfo.screens[i],
result, pReadmask);
+for (i = 0; i screenInfo.numGPUScreens; i++)
+(*screenInfo.gpuscreens[i]-WakeupHandler) (screenInfo.gpuscreens[i],
+result,