From a81adf16eff7163c1645e5b270ee038860105050 Mon Sep 17 00:00:00 2001 From: Ori Bernstein Date: Sun, 16 Jul 2006 00:29:42 -0500 Subject: [PATCH] Added broken version of mirroring contents of backing server. VERY BROKEN. mainly so I'll have something to sync at DDC/OLS --- hw/xnest/Events.c | 115 ++++++++++++++++++++++++++---------- hw/xnest/Init.c | 139 ++++++++++++++++++++++++-------------------- hw/xnest/Window.c | 123 ++++++++++++++++++++++++++++++++++++--- hw/xnest/XNWindow.h | 9 +++ 4 files changed, 284 insertions(+), 102 deletions(-) diff --git a/hw/xnest/Events.c b/hw/xnest/Events.c index 89e3f0ea3..cf6eebd0a 100644 --- a/hw/xnest/Events.c +++ b/hw/xnest/Events.c @@ -90,14 +90,22 @@ void xnestHandleEvent(XCBGenericEvent *e) XCBExposeEvent *xev; XCBResizeRequestEvent *rev; XCBConfigureNotifyEvent *cev; + XCBButtonPressEvent *bpe; + XCBButtonReleaseEvent *bre; + XCBReparentNotifyEvent *ev_reparent; + XCBCreateNotifyEvent *ev_create; + XCBGetGeometryCookie gcook; + XCBGetGeometryRep *grep; + CARD32 ev_mask; xEvent ev; ScreenPtr pScreen; WindowPtr pWin; WindowPtr pSib; + WindowPtr pParent; RegionRec Rgn; BoxRec Box; lastEventTime = GetTimeInMillis(); - + switch (e->response_type & ~0x80) { case XCBKeyPress: ErrorF("Key Pressed\n"); @@ -119,7 +127,8 @@ void xnestHandleEvent(XCBGenericEvent *e) case XCBButtonPress: xnestUpdateModifierState(((XCBButtonPressEvent *)e)->state); - ((XCBButtonPressEvent *)e)->time.id = lastEventTime = GetTimeInMillis(); + bpe = (XCBButtonPressEvent *)e; + bpe->time.id = lastEventTime = GetTimeInMillis(); memcpy(&ev, e, sizeof(XCBGenericEvent)); mieqEnqueue((xEventPtr) &ev); break; @@ -140,8 +149,7 @@ void xnestHandleEvent(XCBGenericEvent *e) mieqEnqueue(&x); #endif pev = (XCBMotionNotifyEvent *)e; - miPointerAbsoluteCursor (pev->event_x, pev->event_y, - lastEventTime = GetTimeInMillis()); + miPointerAbsoluteCursor (pev->event_x, pev->event_y, lastEventTime = GetTimeInMillis()); break; case XCBFocusIn: @@ -179,8 +187,7 @@ void xnestHandleEvent(XCBGenericEvent *e) ErrorF("Entry Notify\n"); XCBTIMESTAMP t = { XCBCurrentTime }; XCBSetInputFocus(xnestConnection, RevertToNone, eev->child, t); - miPointerAbsoluteCursor (eev->event_x, eev->event_y, - lastEventTime = GetTimeInMillis()); + miPointerAbsoluteCursor (eev->event_x, eev->event_y, lastEventTime = GetTimeInMillis()); xnestDirectInstallColormaps(pScreen); } } @@ -215,46 +222,90 @@ void xnestHandleEvent(XCBGenericEvent *e) miWindowExposures(pWin, &Rgn, NullRegion); } break; - case XCBResizeRequest: - rev = (XCBResizeRequestEvent *)e; - pWin = xnestWindowPtr(rev->window); - rev->window = xnestWindow(xnestWindowPtr(rev->window)); - memcpy(&ev, rev, sizeof(XCBGenericEvent)); - if (pWin) { - DeliverEvents(pWin, &ev, 1, NULL); - //miSlideAndSizeWindow(pWin, pWin->drawable.x, pWin->drawable.y, rev->width, rev->height, NULL); - } - break; case XCBConfigureNotify: cev = (XCBConfigureNotifyEvent *)e; pWin = xnestWindowPtr(cev->window); - cev->event = xnestWindow(xnestWindowPtr(cev->event)); - cev->window = xnestWindow(xnestWindowPtr(cev->window)); - pSib = xnestWindowPtr(cev->above_sibling); - if (pSib) - cev->above_sibling = xnestWindow(pSib); - memcpy(&ev, cev, sizeof(XCBGenericEvent)); - if (pWin) { + if (xnestWindowPriv(pWin)->owner == XSCREEN_OWNED_XSCREEN) { + pScreen = pWin->drawable.pScreen; + pSib = xnestWindowPtr(cev->above_sibling); + cev->event = xnestWindow(xnestWindowPtr(cev->event)); + cev->window = xnestWindow(xnestWindowPtr(cev->window)); + if (pSib) + cev->above_sibling = xnestWindow(pSib); + memcpy(&ev, cev, sizeof(XCBGenericEvent)); DeliverEvents(pWin, &ev, 1, NULL); - //miSlideAndSizeWindow(pWin, cev->x, cev->y, cev->width, cev->height, pSib); + } + pWin->origin.x = pWin->drawable.x + wBorderWidth(pWin) + cev->x; + pWin->origin.y = pWin->drawable.y + wBorderWidth(pWin) + cev->y; + pWin->drawable.height = cev->height; + pWin->drawable.width = cev->width; + ErrorF("drawable->x: %d, drawable->y: %d, origin->x: %d, origin->y: %d\n", + pWin->drawable.x, pWin->drawable.y, pWin->origin.x, pWin->origin.y); + break; + + case XCBReparentNotify: + /*Reparent windows. This is to track non-xscreen managed windows and their + * relationship to xscreen managed windows. It should be harmless to poke at + * the relationships on xscreen managed windows too, I think.. or will it? FIXME and + * test.*/ + ev_reparent = (XCBReparentNotifyEvent *)e; + pParent = xnestWindowPtr(ev_reparent->parent); + pWin = xnestWindowPtr(ev_reparent->window); + ReparentWindow(pWin, pParent, ev_reparent->x, ev_reparent->y, wClient(pWin)); + break; + + case XCBCreateNotify: + ev_create = (XCBCreateNotifyEvent *)e; + pParent = xnestWindowPtr(ev_create->parent); + /*make sure we didn't create this window. If we did, ignore it, we already track it*/ + pWin = xnestWindowPtr(ev_create->window); + if (!pWin) { + gcook = XCBGetGeometry(xnestConnection, (XCBDRAWABLE)ev_create->window); + + pWin = AllocateWindow(pScreen); + + xnestWindowPriv(pWin)->window = ev_create->window; + xnestWindowPriv(pWin)->sibling_above = (XCBWINDOW){0}; + xnestWindowPriv(pWin)->owner = XSCREEN_OWNED_BACKING; + + pWin->parent = pParent; + + grep = XCBGetGeometryReply(xnestConnection, gcook, NULL); + pWin->origin.x = grep->x; + pWin->origin.y = grep->y; + pWin->drawable.width = grep->width; + pWin->drawable.height = grep->height; + wClient(pWin) = serverClient; + pWin->drawable.id = FakeClientID(0); + + pWin->firstChild = NULL; + pWin->lastChild = NULL; + pWin->prevSib = NULL; + pWin->optional = NULL; + pWin->valdata = NULL; + + REGION_NULL(pScreen, &pWin->winSize); + REGION_NULL(pScreen, &pWin->borderSize); + REGION_NULL(pScreen, &pWin->clipList); + REGION_NULL(pScreen, &pWin->borderClip); + + /*set drawable relative to parent. FIXME: is this correct?*/ + pWin->drawable.x = pWin->origin.x - pWin->parent->origin.x + wBorderWidth(pWin); + pWin->drawable.y = pWin->origin.y - pWin->parent->origin.y + wBorderWidth(pWin); + ev_mask = XCBEventMaskSubstructureNotify|XCBEventMaskStructureNotify; + XCBChangeWindowAttributes(xnestConnection, ev_create->window, XCBCWEventMask, &ev_mask); } break; - /* - pWin = xnestWindowPtr(cev->event); - pSib = xnestWindowPtr(cev->above_sibling); - if (pWin) - break; - */ + case XCBNoExposure: case XCBGraphicsExposure: case XCBCirculateNotify: case XCBGravityNotify: case XCBMapNotify: - case XCBReparentNotify: case XCBUnmapNotify: - // break; + // break; default: ErrorF("****xnest warning: unhandled event %d\n", e->response_type & ~0x80); diff --git a/hw/xnest/Init.c b/hw/xnest/Init.c index c2175277a..3a4cbd3cb 100644 --- a/hw/xnest/Init.c +++ b/hw/xnest/Init.c @@ -1,15 +1,15 @@ /* $Xorg: Init.c,v 1.3 2000/08/17 19:53:28 cpqbld Exp $ */ /* -Copyright 1993 by Davor Matic + Copyright 1993 by Davor Matic -Permission to use, copy, modify, distribute, and sell this software -and its documentation for any purpose is hereby granted without fee, -provided that the above copyright notice appear in all copies and that -both that copyright notice and this permission notice appear in -supporting documentation. Davor Matic makes no representations about -the suitability of this software for any purpose. It is provided "as -is" without express or implied warranty. + Permission to use, copy, modify, distribute, and sell this software + and its documentation for any purpose is hereby granted without fee, + provided that the above copyright notice appear in all copies and that + both that copyright notice and this permission notice appear in + supporting documentation. Davor Matic makes no representations about + the suitability of this software for any purpose. It is provided "as + is" without express or implied warranty. */ /* $XFree86: xc/programs/Xserver/hw/xnest/Init.c,v 3.24 2003/01/15 02:34:14 torrey Exp $ */ @@ -48,63 +48,80 @@ is" without express or implied warranty. Bool xnestDoFullGeneration = True; -void -InitOutput(ScreenInfo *screenInfo, int argc, char *argv[]) + +void InitOutput(ScreenInfo *screenInfo, int argc, char *argv[]) { - int i, j; - const XCBSetup *setup; + int i, j; + const XCBSetup *setup; - xnestOpenDisplay(argc, argv); - setup = XCBGetSetup(xnestConnection); - - screenInfo->imageByteOrder = setup->image_byte_order; - screenInfo->bitmapScanlineUnit = setup->bitmap_format_scanline_unit; - screenInfo->bitmapScanlinePad = setup->bitmap_format_scanline_pad; - screenInfo->bitmapBitOrder = setup->bitmap_format_bit_order; - - screenInfo->numPixmapFormats = 0; - for (i = 0; i < xnestNumPixmapFormats; i++) - for (j = 0; j < xnestNumDepth; j++) - if ((xnestPixmapFormats[i].depth == 1) || - (xnestPixmapFormats[i].depth == xnestDepths[j])) { - screenInfo->formats[screenInfo->numPixmapFormats].depth = - xnestPixmapFormats[i].depth; - screenInfo->formats[screenInfo->numPixmapFormats].bitsPerPixel = - xnestPixmapFormats[i].bits_per_pixel; - screenInfo->formats[screenInfo->numPixmapFormats].scanlinePad = - xnestPixmapFormats[i].scanline_pad; - screenInfo->numPixmapFormats++; - break; - } - - xnestWindowPrivateIndex = AllocateWindowPrivateIndex(); - xnestGCPrivateIndex = AllocateGCPrivateIndex(); - xnestFontPrivateIndex = AllocateFontPrivateIndex(); - - if (!xnestNumScreens) xnestNumScreens = 1; + xnestOpenDisplay(argc, argv); + setup = XCBGetSetup(xnestConnection); - for (i = 0; i < xnestNumScreens; i++) - AddScreen(xnestOpenScreen, argc, argv); - xnestNumScreens = screenInfo->numScreens; + screenInfo->imageByteOrder = setup->image_byte_order; + screenInfo->bitmapScanlineUnit = setup->bitmap_format_scanline_unit; + screenInfo->bitmapScanlinePad = setup->bitmap_format_scanline_pad; + screenInfo->bitmapBitOrder = setup->bitmap_format_bit_order; - xnestDoFullGeneration = xnestFullGeneration; + /** + * list the pixmap formats the backing server supports. + * FIXME: how do we get Xscreen to regenerate this properly? + * should this only connect to backing servers with compatible + * pixmap formats? + **/ + screenInfo->numPixmapFormats = 0; + for (i = 0; i < xnestNumPixmapFormats; i++) { + for (j = 0; j < xnestNumDepth; j++) { + if ((xnestPixmapFormats[i].depth == 1) || + (xnestPixmapFormats[i].depth == xnestDepths[j])) { + screenInfo->formats[screenInfo->numPixmapFormats].depth = + xnestPixmapFormats[i].depth; + screenInfo->formats[screenInfo->numPixmapFormats].bitsPerPixel = + xnestPixmapFormats[i].bits_per_pixel; + screenInfo->formats[screenInfo->numPixmapFormats].scanlinePad = + xnestPixmapFormats[i].scanline_pad; + screenInfo->numPixmapFormats++; + break; + } + } + } + + xnestWindowPrivateIndex = AllocateWindowPrivateIndex(); + xnestGCPrivateIndex = AllocateGCPrivateIndex(); + xnestFontPrivateIndex = AllocateFontPrivateIndex(); + + if (!xnestNumScreens) + xnestNumScreens = 1; + + for (i = 0; i < xnestNumScreens; i++) + AddScreen(xnestOpenScreen, argc, argv); + + xnestNumScreens = screenInfo->numScreens; + + xnestDoFullGeneration = xnestFullGeneration; + + /** + * Add a tree representing the windows on the backing server, so that + * we can represent reparenting windows inside windows on other servers. + * don't need to create the root window's WindowPtr, this is handled + * when the DIX tells us to create the root window. + **/ + //xscreenInitBackingWindows(xnestConnection, XCBSetupRootsIter(XCBGetSetup(xnestConnection)).data->root); } -void -InitInput(int argc, char *argv[]) +void InitInput(int argc, char *argv[]) { - xnestPointerDevice = AddInputDevice(xnestPointerProc, TRUE); - xnestKeyboardDevice = AddInputDevice(xnestKeyboardProc, TRUE); + xnestPointerDevice = AddInputDevice(xnestPointerProc, TRUE); + xnestKeyboardDevice = AddInputDevice(xnestKeyboardProc, TRUE); - RegisterPointerDevice(xnestPointerDevice); - RegisterKeyboardDevice(xnestKeyboardDevice); + RegisterPointerDevice(xnestPointerDevice); + RegisterKeyboardDevice(xnestKeyboardDevice); - mieqInit((DevicePtr)xnestKeyboardDevice, (DevicePtr)xnestPointerDevice); + mieqInit((DevicePtr)xnestKeyboardDevice, (DevicePtr)xnestPointerDevice); - AddEnabledDevice(XCBGetFileDescriptor(xnestConnection)); + AddEnabledDevice(XCBGetFileDescriptor(xnestConnection)); - RegisterBlockAndWakeupHandlers(xnestBlockHandler, xnestWakeupHandler, NULL); + RegisterBlockAndWakeupHandlers(xnestBlockHandler, xnestWakeupHandler, NULL); } /* @@ -112,18 +129,18 @@ InitInput(int argc, char *argv[]) */ void AbortDDX() { - xnestDoFullGeneration = True; - xnestCloseDisplay(); + xnestDoFullGeneration = True; + xnestCloseDisplay(); } /* Called by GiveUp(). */ void ddxGiveUp() { - AbortDDX(); + AbortDDX(); } #ifdef __DARWIN__ -void + void DarwinHandleGUI(int argc, char *argv[]) { } @@ -131,15 +148,13 @@ DarwinHandleGUI(int argc, char *argv[]) void GlxExtensionInit(); void GlxWrapInitVisuals(void *procPtr); -void -DarwinGlxExtensionInit() +void DarwinGlxExtensionInit() { GlxExtensionInit(); } -void -DarwinGlxWrapInitVisuals( - void *procPtr) +void DarwinGlxWrapInitVisuals( + void *procPtr) { GlxWrapInitVisuals(procPtr); } diff --git a/hw/xnest/Window.c b/hw/xnest/Window.c index 574ba8db0..09c34dc1b 100644 --- a/hw/xnest/Window.c +++ b/hw/xnest/Window.c @@ -74,6 +74,106 @@ WindowPtr xnestWindowPtr(XCBWINDOW window) return wm.pWin; } +/** + * Walk through all the windows on the backing server and + * add a representation of them to the Xscreen server, so that + * we can let Xscreen tell windows that they've been reparented, + * and other fun stuff. + **/ +static void xscreenInitBackingWindows(XCBConnection *c, WindowPtr pParent) +{ + int i; + XCBWINDOW *child; + XCBQueryTreeCookie qcook; + XCBQueryTreeRep *qrep; + XCBGetGeometryCookie gcook; + XCBGetGeometryRep *grep; + XCBWINDOW w = {0}; + ScreenPtr pScreen; + WindowPtr pWin = NULL; + WindowPtr pPrev = NULL; + CARD32 ev_mask; + + + /*FIXME: THIS IS WRONG! How do I get the screen? + * No issue though, so far, since I only work with one screen. + * pScreen = xnestScreen(w); + */ + w = xnestWindow(pParent); + pScreen = screenInfo.screens[0]; + qcook = XCBQueryTree(c, w); + qrep = XCBQueryTreeReply(c, qcook, NULL); + child = XCBQueryTreeChildren(qrep); + /* Walk through the windows, initializing the privates. + * FIXME: initialize x, y, and pWin contents.. how? */ + for (i=0; i < qrep->children_len; i++){ + /*if we're not already tracking this one*/ + pWin = xnestWindowPtr(child[i]); + if (!pWin) { + gcook = XCBGetGeometry(c, (XCBDRAWABLE)child[i]); + + pWin = AllocateWindow(pScreen); + + pWin->firstChild = NULL; + pWin->lastChild = NULL; + pWin->prevSib = NULL; + pWin->optional = NULL; + pWin->valdata = NULL; + pWin->parent = xnestWindowPtr(w); + wClient(pWin) = serverClient; + pWin->drawable.id = FakeClientID(0); + + REGION_NULL(pScreen, &pWin->winSize); + REGION_NULL(pScreen, &pWin->borderSize); + REGION_NULL(pScreen, &pWin->clipList); + REGION_NULL(pScreen, &pWin->borderClip); + + xnestWindowPriv(pWin)->window = child[i]; + xnestWindowPriv(pWin)->parent = w; + xnestWindowPriv(pWin)->sibling_above = (i>0) ? child[i-1] : (XCBWINDOW){0}; + xnestWindowPriv(pWin)->owner = XSCREEN_OWNED_BACKING; + + + grep = XCBGetGeometryReply(c, gcook, NULL); + pWin->origin.x = grep->x; + pWin->origin.y = grep->y; + pWin->drawable.width = grep->width; + pWin->drawable.height = grep->height; + + if (pWin->parent) { + /*set drawable relative to parent. FIXME: is this correct?*/ + pWin->drawable.x = pWin->origin.x - pWin->parent->origin.x + wBorderWidth(pWin); + pWin->drawable.y = pWin->origin.y - pWin->parent->origin.y + wBorderWidth(pWin); + } else { + /*root window*/ + pWin->drawable.x = pWin->origin.x; + pWin->drawable.y = pWin->origin.y; + } + /*listen to events on the new window*/ + ev_mask = XCBEventMaskSubstructureNotify|XCBEventMaskStructureNotify; + XCBChangeWindowAttributes(xnestConnection, child[i], XCBCWEventMask, &ev_mask); + } + + /** + * append the window into the list. + * NB: This reorders the WindowPtrs for windows we created in Xscreen. + * IS THIS RIGHT?!? + **/ + if (!pParent->firstChild) + pParent->firstChild = pWin; + if (pPrev) + pPrev->nextSib = pWin; + pParent->lastChild = pWin; + pWin->prevSib = pPrev; + /*this is the last sibling in the list*/ + pWin->nextSib = NULL; + pPrev = pWin; + /*and recurse, adding this window's children*/ + xscreenInitBackingWindows(c, pWin); + /*FIXME: insert the window into the stack*/ + } +} + Bool xnestCreateWindow(WindowPtr pWin) { unsigned long mask; @@ -88,6 +188,8 @@ Bool xnestCreateWindow(WindowPtr pWin) screen = XCBSetupRootsIter (XCBGetSetup (xnestConnection)).data; if (xnestIsRoot(pWin)) { xnestWindowPriv(pWin)->window = screen->root; + /*now that we've created the root window, we can do the backing windows*/ + xscreenInitBackingWindows(xnestConnection, pWin); return True; } @@ -104,6 +206,9 @@ Bool xnestCreateWindow(WindowPtr pWin) param.backing_store = XCBBackingStoreNotUseful; if (pWin->parent) { + pWin->origin.x += pWin->parent->origin.x; + pWin->origin.y += pWin->parent->origin.y; + if (pWin->optional && pWin->optional->visual != wVisual(pWin->parent)) { vid.id = wVisual(pWin); visual = xnestVisualFromID(pWin->drawable.pScreen, vid); @@ -169,17 +274,19 @@ Bool xnestDestroyWindow(WindowPtr pWin) if (pWin->nextSib) xnestWindowPriv(pWin->nextSib)->sibling_above = xnestWindowPriv(pWin)->sibling_above; + if (xnestWindowPriv(pWin)->owner == XSCREEN_OWNED_XSCREEN){ #ifdef SHAPE - REGION_DESTROY(pWin->drawable.pScreen, - xnestWindowPriv(pWin)->bounding_shape); - REGION_DESTROY(pWin->drawable.pScreen, - xnestWindowPriv(pWin)->clip_shape); + REGION_DESTROY(pWin->drawable.pScreen, + xnestWindowPriv(pWin)->bounding_shape); + REGION_DESTROY(pWin->drawable.pScreen, + xnestWindowPriv(pWin)->clip_shape); #endif - XCBDestroyWindow(xnestConnection, xnestWindow(pWin)); - xnestWindowPriv(pWin)->window.xid = None; + XCBDestroyWindow(xnestConnection, xnestWindow(pWin)); + xnestWindowPriv(pWin)->window.xid = None; - if (pWin->optional && pWin->optional->colormap && pWin->parent) - xnestSetInstalledColormapWindows(pWin->drawable.pScreen); + if (pWin->optional && pWin->optional->colormap && pWin->parent) + xnestSetInstalledColormapWindows(pWin->drawable.pScreen); + } return True; } diff --git a/hw/xnest/XNWindow.h b/hw/xnest/XNWindow.h index d7adb206a..46fd4f9fe 100644 --- a/hw/xnest/XNWindow.h +++ b/hw/xnest/XNWindow.h @@ -16,6 +16,10 @@ is" without express or implied warranty. #ifndef XNESTWINDOW_H #define XNESTWINDOW_H +typedef enum { + XSCREEN_OWNED_XSCREEN, /*Xscreen owns the window*/ + XSCREEN_OWNED_BACKING, /*The backing server owns the window*/ +} XscreenWindowOwner; typedef struct { XCBWINDOW window; @@ -30,8 +34,13 @@ typedef struct { RegionPtr bounding_shape; RegionPtr clip_shape; #endif /* SHAPE */ + /* is this a window from the backing server, or + * is it a window on Xscreen? true for window on + * backing server.*/ + XscreenWindowOwner owner; } xnestPrivWin; + typedef struct { WindowPtr pWin; XCBWINDOW window;