xserver: Branch 'master' - 13 commits

Jeremy Huddleston jeremyhu at kemper.freedesktop.org
Wed Nov 21 23:29:10 PST 2007


 hw/darwin/darwin.c               |   22 +++++
 hw/darwin/darwin.h               |   10 ++
 hw/darwin/darwinEvents.c         |   16 ++++
 hw/darwin/darwinKeyboard.c       |    2 
 hw/darwin/quartz/quartz.c        |   96 ++++++++++++++++++++++++-
 hw/darwin/quartz/quartzCocoa.m   |    2 
 hw/darwin/quartz/xpr/xprScreen.c |   64 +++++++++-------
 miext/rootless/rootless.h        |    1 
 miext/rootless/rootlessCommon.c  |   81 ++++++++++++++++++++-
 miext/rootless/rootlessCommon.h  |   19 +++++
 miext/rootless/rootlessScreen.c  |   70 ++++++++++++++++++
 miext/rootless/rootlessWindow.c  |  147 +++++++++++++++++++++++++++++++++++----
 12 files changed, 477 insertions(+), 53 deletions(-)

New commits:
commit 602de4f70b6f4aab93b514f3a01917bd5d4ad640
Author: Jeremy Huddleston <jeremy at tifa.local>
Date:   Wed Nov 21 16:53:10 2007 -0800

    Darwin: Use UTF8String since lossyCString is deprecated
    (cherry picked from commit 1786f9464af51ff606a612aec6fe420fa9688a28)

diff --git a/hw/darwin/quartz/quartzCocoa.m b/hw/darwin/quartz/quartzCocoa.m
index 46a9828..48cadc6 100644
--- a/hw/darwin/quartz/quartzCocoa.m
+++ b/hw/darwin/quartz/quartzCocoa.m
@@ -94,7 +94,7 @@ char *QuartzReadCocoaPasteboard(void)
         char *buffer;
 
         if (! string) return NULL;
-        buffer = (char *) [string lossyCString];
+        buffer = (char *) [string UTF8String];
         text = (char *) malloc(strlen(buffer)+1);
         if (text)
             strcpy(text, buffer);
commit 13666e287c347aab2a5e9d8ee5f6bb29b9b85171
Author: Ben Byer <bbyer at bbyer.local>
Date:   Sun Nov 18 17:44:12 2007 -0800

    Darwin: Added some DEBUG_LOG sauce to the XP_EVENT handling code
    (cherry picked from commit ec84a4cef66a2b46ed71f9758c434ea629d2f270)

diff --git a/hw/darwin/quartz/xpr/xprScreen.c b/hw/darwin/quartz/xpr/xprScreen.c
index 2db249f..57a60a2 100644
--- a/hw/darwin/quartz/xpr/xprScreen.c
+++ b/hw/darwin/quartz/xpr/xprScreen.c
@@ -63,26 +63,24 @@ static void
 eventHandler(unsigned int type, const void *arg,
              unsigned int arg_size, void *data)
 {
-    switch (type)
-    {
+    switch (type) {
     case XP_EVENT_DISPLAY_CHANGED:
-      //      ErrorF("XP_EVENT_DISPLAY_MOVED\n");
-        QuartzMessageServerThread(kXDarwinDisplayChanged, 0);
-        break;
+      DEBUG_LOG("XP_EVENT_DISPLAY_CHANGED\n");
+      QuartzMessageServerThread(kXDarwinDisplayChanged, 0);
+      break;
 
     case XP_EVENT_WINDOW_STATE_CHANGED:
-      //      ErrorF("XP_EVENT_WINDOW_STATE_CHANGED\n");
-        if (arg_size >= sizeof(xp_window_state_event))
-        {
-            const xp_window_state_event *ws_arg = arg;
-
-            QuartzMessageServerThread(kXDarwinWindowState, 2,
-                                      ws_arg->id, ws_arg->state);
-        }
-        break;
+      DEBUG_LOG("XP_EVENT_WINDOW_STATE_CHANGED\n");
+      if (arg_size >= sizeof(xp_window_state_event)) {
+	const xp_window_state_event *ws_arg = arg;
+	
+	QuartzMessageServerThread(kXDarwinWindowState, 2,
+				  ws_arg->id, ws_arg->state);
+      }
+      break;
 
     case XP_EVENT_WINDOW_MOVED:
-      //      ErrorF("XP_EVENT_WINDOW_MOVED\n");
+     	DEBUG_LOG("XP_EVENT_WINDOW_MOVED\n");
         if (arg_size == sizeof(xp_window_id))
         {
             xp_window_id id = * (xp_window_id *) arg;
@@ -98,20 +96,23 @@ eventHandler(unsigned int type, const void *arg,
         break;
 
     case XP_EVENT_SURFACE_DESTROYED:
+      DEBUG_LOG("XP_EVENT_SURFACE_DESTROYED\n");
     case XP_EVENT_SURFACE_CHANGED:
-      //      ErrorF("XP_EVENT_SURFACE_MOVED\n");
-        if (arg_size == sizeof(xp_surface_id))
-        {
-            int kind;
-
-            if (type == XP_EVENT_SURFACE_DESTROYED)
-                kind = AppleDRISurfaceNotifyDestroyed;
-            else
-                kind = AppleDRISurfaceNotifyChanged;
-
-            DRISurfaceNotify(*(xp_surface_id *) arg, kind);
+      DEBUG_LOG("XP_EVENT_SURFACE_CHANGED\n");
+        if (arg_size == sizeof(xp_surface_id)) {
+	  int kind;
+	  
+	  if (type == XP_EVENT_SURFACE_DESTROYED)
+	    kind = AppleDRISurfaceNotifyDestroyed;
+	  else
+	    kind = AppleDRISurfaceNotifyChanged;
+	  
+	  DRISurfaceNotify(*(xp_surface_id *) arg, kind);
         }
         break;
+    default:
+      ErrorF("Unknown XP_EVENT type (%d) in xprScreen:eventHandler\n",
+	     type);
     }
 }
 
commit 829b6641bd64c352e1e8a7c619f84dedbdb07a09
Author: Ben Byer <bbyer at bbyer.local>
Date:   Sun Nov 18 17:43:40 2007 -0800

    Darwin: Disabled ALT_IS_MODE_SWITCH
    (cherry picked from commit fd181254f85543558190140787dc7b41f6cf90db)

diff --git a/hw/darwin/darwinKeyboard.c b/hw/darwin/darwinKeyboard.c
index 4e7a136..932cdd5 100644
--- a/hw/darwin/darwinKeyboard.c
+++ b/hw/darwin/darwinKeyboard.c
@@ -61,7 +61,7 @@
 #undef DUMP_DARWIN_KEYMAP
 
 /* Define this to use Alt for Mode_switch. */
-#define ALT_IS_MODE_SWITCH 1
+//#define ALT_IS_MODE_SWITCH 1
 
 #include <stdio.h>
 #include <stdlib.h>
commit 8486f8af91b477c7bcb8438a0e9a72d0c11d1d63
Author: Ben Byer <bbyer at bbyer.local>
Date:   Thu Nov 15 02:25:50 2007 -0800

    Darwin: Added a lightweight debugging facility to support troubleshooting
    (for example) the stuck modifier key issue
    (cherry picked from commit 0e0b452d10c0af55497c3299b5f3db45d5b381cb)

diff --git a/hw/darwin/darwin.c b/hw/darwin/darwin.c
index a4ec002..a772218 100644
--- a/hw/darwin/darwin.c
+++ b/hw/darwin/darwin.c
@@ -75,6 +75,10 @@
 #include "darwin.h"
 #include "darwinClut8.h"
 
+#ifdef ENABLE_DEBUG_LOG
+FILE *debug_log_fp = NULL;
+#endif
+
 /*
  * X server shared global variables
  */
@@ -652,6 +656,20 @@ void OsVendorInit(void)
 {
     if (serverGeneration == 1) {
         DarwinPrintBanner();
+#ifdef ENABLE_DEBUG_LOG
+	{
+	  char *home_dir=NULL, *log_file_path=NULL;
+	  home_dir = getenv("HOME");
+	  if (home_dir) asprintf(&log_file_path, "%s/%s", home_dir, DEBUG_LOG_NAME);
+	  if (log_file_path) {
+	    if (!access(log_file_path, F_OK)) {
+	      debug_log_fp = fopen(log_file_path, "a");
+	      if (debug_log_fp) ErrorF("Debug logging enabled to %s\n", log_file_path);
+	    }
+	    free(log_file_path);
+	  }
+	}
+#endif
     }
 
     // Find the full path to the keymapping file.
diff --git a/hw/darwin/darwin.h b/hw/darwin/darwin.h
index 587ba1c..646bb24 100644
--- a/hw/darwin/darwin.h
+++ b/hw/darwin/darwin.h
@@ -157,4 +157,14 @@ enum {
     kXDarwinWindowMoved       // window has moved on screen
 };
 
+#define ENABLE_DEBUG_LOG 1
+
+#ifdef ENABLE_DEBUG_LOG
+extern FILE *debug_log_fp;
+#define DEBUG_LOG_NAME "x11-debug.txt"
+#define DEBUG_LOG(msg, args...) if (debug_log_fp) fprintf(debug_log_fp, "%s:%d: " msg, __FUNCTION__, __LINE__, ##args )
+#else
+#define DEBUG_LOG(msg, args...) 
+#endif
+
 #endif  /* _DARWIN_H */
commit 74214a9f42b931f99d83ddb4efb3720881a2de16
Author: Ben Byer <bbyer at bbyer.local>
Date:   Thu Nov 15 00:56:54 2007 -0800

    Darwin: Patch to avert (some) damage / rootless crashes, courtesy of Ken Thomases
    (cherry picked from commit 148a87ff20aa5e7a6d839610aa14fa1a31505c4a)

diff --git a/miext/rootless/rootless.h b/miext/rootless/rootless.h
index b4a5b2a..5224dca 100644
--- a/miext/rootless/rootless.h
+++ b/miext/rootless/rootless.h
@@ -66,7 +66,6 @@ typedef struct _RootlessWindowRec {
     int bytesPerRow;
 
     PixmapPtr pixmap;
-    PixmapPtr oldPixmap;
 
 #ifdef ROOTLESS_TRACK_DAMAGE
     RegionRec damage;
diff --git a/miext/rootless/rootlessCommon.c b/miext/rootless/rootlessCommon.c
index 03842e4..562f655 100644
--- a/miext/rootless/rootlessCommon.c
+++ b/miext/rootless/rootlessCommon.c
@@ -172,8 +172,24 @@ void RootlessStartDrawing(WindowPtr pWindow)
         winRec->is_drawing = TRUE;
     }
 
-    winRec->oldPixmap = pScreen->GetWindowPixmap(pWindow);
-    pScreen->SetWindowPixmap(pWindow, winRec->pixmap);
+    PixmapPtr curPixmap = pScreen->GetWindowPixmap(pWindow);
+    if (curPixmap == winRec->pixmap)
+    {
+        RL_DEBUG_MSG("Window %p already has winRec->pixmap %p; not pushing\n", pWindow, winRec->pixmap);
+    }
+    else
+    {
+        PixmapPtr oldPixmap = pWindow->devPrivates[rootlessWindowOldPixmapPrivateIndex].ptr;
+        if (oldPixmap != NULL)
+        {
+            if (oldPixmap == curPixmap)
+                RL_DEBUG_MSG("Window %p's curPixmap %p is the same as its oldPixmap; strange\n", pWindow, curPixmap);
+            else
+                RL_DEBUG_MSG("Window %p's existing oldPixmap %p being lost!\n", pWindow, oldPixmap);
+        }
+        pWindow->devPrivates[rootlessWindowOldPixmapPrivateIndex].ptr = curPixmap;
+        pScreen->SetWindowPixmap(pWindow, winRec->pixmap);
+    }
 }
 
 
@@ -182,6 +198,29 @@ void RootlessStartDrawing(WindowPtr pWindow)
  *  Stop drawing to a window's backing buffer. If flush is true,
  *  damaged regions are flushed to the screen.
  */
+static int RestorePreDrawingPixmapVisitor(WindowPtr pWindow, pointer data)
+{
+    RootlessWindowRec *winRec = (RootlessWindowRec*)data;
+    ScreenPtr pScreen = pWindow->drawable.pScreen;
+    PixmapPtr exPixmap = pScreen->GetWindowPixmap(pWindow);
+    PixmapPtr oldPixmap = pWindow->devPrivates[rootlessWindowOldPixmapPrivateIndex].ptr;
+    if (oldPixmap == NULL)
+    {
+        if (exPixmap == winRec->pixmap)
+            RL_DEBUG_MSG("Window %p appears to be in drawing mode (ex-pixmap %p equals winRec->pixmap, which is being freed) but has no oldPixmap!\n", pWindow, exPixmap);
+    }
+    else
+    {
+        if (exPixmap != winRec->pixmap)
+            RL_DEBUG_MSG("Window %p appears to be in drawing mode (oldPixmap %p) but ex-pixmap %p not winRec->pixmap %p!\n", pWindow, oldPixmap, exPixmap, winRec->pixmap);
+        if (oldPixmap == winRec->pixmap)
+            RL_DEBUG_MSG("Window %p's oldPixmap %p is winRec->pixmap, which has just been freed!\n", pWindow, oldPixmap);
+        pScreen->SetWindowPixmap(pWindow, oldPixmap);
+        pWindow->devPrivates[rootlessWindowOldPixmapPrivateIndex].ptr = NULL;
+    }
+    return WT_WALKCHILDREN;
+}
+
 void RootlessStopDrawing(WindowPtr pWindow, Bool flush)
 {
     ScreenPtr pScreen = pWindow->drawable.pScreen;
@@ -198,7 +237,7 @@ void RootlessStopDrawing(WindowPtr pWindow, Bool flush)
         SCREENREC(pScreen)->imp->StopDrawing(winRec->wid, flush);
 
         FreeScratchPixmapHeader(winRec->pixmap);
-        pScreen->SetWindowPixmap(pWindow, winRec->oldPixmap);
+        TraverseTree(top, RestorePreDrawingPixmapVisitor, (pointer)winRec);
         winRec->pixmap = NULL;
 
         winRec->is_drawing = FALSE;
diff --git a/miext/rootless/rootlessCommon.h b/miext/rootless/rootlessCommon.h
index d6a0161..fd8725a 100644
--- a/miext/rootless/rootlessCommon.h
+++ b/miext/rootless/rootlessCommon.h
@@ -60,6 +60,7 @@
 extern int rootlessGCPrivateIndex;
 extern int rootlessScreenPrivateIndex;
 extern int rootlessWindowPrivateIndex;
+extern int rootlessWindowOldPixmapPrivateIndex;
 
 
 // RootlessGCRec: private per-gc data
diff --git a/miext/rootless/rootlessScreen.c b/miext/rootless/rootlessScreen.c
index 6b54042..538b698 100644
--- a/miext/rootless/rootlessScreen.c
+++ b/miext/rootless/rootlessScreen.c
@@ -65,6 +65,7 @@ extern Bool RootlessCreateGC(GCPtr pGC);
 int rootlessGCPrivateIndex = -1;
 int rootlessScreenPrivateIndex = -1;
 int rootlessWindowPrivateIndex = -1;
+int rootlessWindowOldPixmapPrivateIndex = -1;
 
 
 /*
@@ -618,6 +619,8 @@ RootlessAllocatePrivates(ScreenPtr pScreen)
         if (rootlessGCPrivateIndex == -1) return FALSE;
         rootlessWindowPrivateIndex = AllocateWindowPrivateIndex();
         if (rootlessWindowPrivateIndex == -1) return FALSE;
+        rootlessWindowOldPixmapPrivateIndex = AllocateWindowPrivateIndex();
+        if (rootlessWindowOldPixmapPrivateIndex == -1) return FALSE;
         rootlessGeneration = serverGeneration;
     }
 
@@ -627,6 +630,8 @@ RootlessAllocatePrivates(ScreenPtr pScreen)
         return FALSE;
     if (!AllocateWindowPrivate(pScreen, rootlessWindowPrivateIndex, 0))
         return FALSE;
+    if (!AllocateWindowPrivate(pScreen, rootlessWindowOldPixmapPrivateIndex, 0))
+        return FALSE;
 
     s = xalloc(sizeof(RootlessScreenRec));
     if (! s) return FALSE;
diff --git a/miext/rootless/rootlessWindow.c b/miext/rootless/rootlessWindow.c
index 3074a3f..14bc674 100644
--- a/miext/rootless/rootlessWindow.c
+++ b/miext/rootless/rootlessWindow.c
@@ -198,6 +198,7 @@ RootlessCreateWindow(WindowPtr pWin)
     RegionRec saveRoot;
 
     WINREC(pWin) = NULL;
+    pWin->devPrivates[rootlessWindowOldPixmapPrivateIndex].ptr = NULL;
 
     SCREEN_UNWRAP(pWin->drawable.pScreen, CreateWindow);
 
commit f5f833b80609f1f98c93113183bd2b1bab3bfec9
Author: Ben Byer <bbyer at bbyer.local>
Date:   Sun Nov 11 04:30:34 2007 -0800

    Darwin: These changes are necessary, yet not sufficient, to get 8-bit indexed
    color mode working in Xquartz.
    (cherry picked from commit a415f62f5289fae99ea9b0038d21fad7695b1336)

diff --git a/miext/rootless/rootlessCommon.c b/miext/rootless/rootlessCommon.c
index 9cbb7fa..03842e4 100644
--- a/miext/rootless/rootlessCommon.c
+++ b/miext/rootless/rootlessCommon.c
@@ -37,6 +37,7 @@
 #include <limits.h> /* For CHAR_BIT */
 
 #include "rootlessCommon.h"
+#include "colormapst.h"
 
 unsigned int rootless_CopyBytes_threshold = 0;
 unsigned int rootless_FillBytes_threshold = 0;
@@ -98,6 +99,41 @@ IsFramedWindow(WindowPtr pWin)
     return (top && WINREC(top));
 }
 
+Bool
+RootlessResolveColormap (ScreenPtr pScreen, int first_color,
+                         int n_colors, uint32_t *colors)
+{
+  int last, i;
+  ColormapPtr map;
+
+  map = RootlessGetColormap (pScreen);
+  if (map == NULL || map->class != PseudoColor) return FALSE;
+
+  last = MIN (map->pVisual->ColormapEntries, first_color + n_colors);
+  for (i = MAX (0, first_color); i < last; i++) {
+    Entry *ent = map->red + i;
+    uint16_t red, green, blue;
+
+      if (!ent->refcnt)	continue;
+      if (ent->fShared) {
+	red = ent->co.shco.red->color;
+	green = ent->co.shco.green->color;
+	blue = ent->co.shco.blue->color;
+      } else {
+	red = ent->co.local.red;
+	green = ent->co.local.green;
+	blue = ent->co.local.blue;
+      }
+
+      colors[i - first_color] = (0xFF000000UL
+				 | ((uint32_t) red & 0xff00) << 8
+				 | (green & 0xff00)
+				 | (blue >> 8));
+    }
+
+  return TRUE;
+}
+
 
 /*
  * RootlessStartDrawing
diff --git a/miext/rootless/rootlessCommon.h b/miext/rootless/rootlessCommon.h
index b7f11bd..d6a0161 100644
--- a/miext/rootless/rootlessCommon.h
+++ b/miext/rootless/rootlessCommon.h
@@ -32,6 +32,7 @@
 #include <dix-config.h>
 #endif
 
+#include <stdint.h>
 #ifndef _ROOTLESSCOMMON_H
 #define _ROOTLESSCOMMON_H
 
@@ -106,13 +107,20 @@ typedef struct _RootlessScreenRec {
     GlyphsProcPtr Glyphs;
 #endif
 
+    InstallColormapProcPtr InstallColormap;
+    UninstallColormapProcPtr UninstallColormap;
+    StoreColorsProcPtr StoreColors;
+
     void *pixmap_data;
     unsigned int pixmap_data_size;
 
+    ColormapPtr colormap;
+
     void *redisplay_timer;
     unsigned int redisplay_timer_set :1;
     unsigned int redisplay_queued :1;
     unsigned int redisplay_expired :1;
+    unsigned int colormap_changed :1;
 } RootlessScreenRec, *RootlessScreenPtr;
 
 
@@ -253,6 +261,16 @@ void RootlessRedisplayScreen(ScreenPtr pScreen);
 
 void RootlessQueueRedisplay(ScreenPtr pScreen);
 
+/* Return the colormap currently installed on the given screen. */
+ColormapPtr RootlessGetColormap (ScreenPtr pScreen);
+
+/* Convert colormap to ARGB. */
+Bool RootlessResolveColormap (ScreenPtr pScreen, int first_color,
+			      int n_colors, uint32_t *colors);
+
+void RootlessFlushWindowColormap (WindowPtr pWin);
+void RootlessFlushScreenColormaps (ScreenPtr pScreen);
+
 // Move a window to its proper location on the screen.
 void RootlessRepositionWindow(WindowPtr pWin);
 
diff --git a/miext/rootless/rootlessScreen.c b/miext/rootless/rootlessScreen.c
index 489d3fb..6b54042 100644
--- a/miext/rootless/rootlessScreen.c
+++ b/miext/rootless/rootlessScreen.c
@@ -42,6 +42,7 @@
 #include "propertyst.h"
 #include "mivalidate.h"
 #include "picturestr.h"
+#include "colormapst.h"
 
 #include <sys/types.h>
 #include <sys/stat.h>
@@ -469,6 +470,67 @@ RootlessMarkOverlappedWindows(WindowPtr pWin, WindowPtr pFirst,
     return result;
 }
 
+ColormapPtr
+RootlessGetColormap (ScreenPtr pScreen)
+{
+  RootlessScreenRec *s = SCREENREC (pScreen);
+
+  return s->colormap;
+}
+
+static void
+RootlessInstallColormap (ColormapPtr pMap)
+{
+  ScreenPtr pScreen = pMap->pScreen;
+  RootlessScreenRec *s = SCREENREC (pScreen);
+
+  SCREEN_UNWRAP(pScreen, InstallColormap);
+
+  if (s->colormap != pMap) {
+    s->colormap = pMap;
+    s->colormap_changed = TRUE;
+    RootlessQueueRedisplay (pScreen);
+  }
+
+  pScreen->InstallColormap (pMap);
+
+  SCREEN_WRAP (pScreen, InstallColormap);
+}
+
+static void
+RootlessUninstallColormap (ColormapPtr pMap)
+{
+  ScreenPtr pScreen = pMap->pScreen;
+  RootlessScreenRec *s = SCREENREC (pScreen);
+
+  SCREEN_UNWRAP(pScreen, UninstallColormap);
+
+  if (s->colormap == pMap)
+    s->colormap = NULL;
+
+  pScreen->UninstallColormap (pMap);
+
+  SCREEN_WRAP(pScreen, UninstallColormap);
+}
+
+static void
+RootlessStoreColors (ColormapPtr pMap, int ndef, xColorItem *pdef)
+{
+  ScreenPtr pScreen = pMap->pScreen;
+  RootlessScreenRec *s = SCREENREC (pScreen);
+
+  SCREEN_UNWRAP(pScreen, StoreColors);
+
+  if (s->colormap == pMap && ndef > 0) {
+    s->colormap_changed = TRUE;
+    RootlessQueueRedisplay (pScreen);
+  }
+
+  pScreen->StoreColors (pMap, ndef, pdef);
+
+  SCREEN_WRAP(pScreen, StoreColors);
+}
+
 
 static CARD32
 RootlessRedisplayCallback(OsTimerPtr timer, CARD32 time, void *arg)
@@ -614,6 +676,9 @@ RootlessWrap(ScreenPtr pScreen)
     WRAP(MarkOverlappedWindows);
     WRAP(ValidateTree);
     WRAP(ChangeWindowAttributes);
+    WRAP(InstallColormap);
+    WRAP(UninstallColormap);
+    WRAP(StoreColors);
 
 #ifdef SHAPE
     WRAP(SetShape);
diff --git a/miext/rootless/rootlessWindow.c b/miext/rootless/rootlessWindow.c
index 89c02f8..3074a3f 100644
--- a/miext/rootless/rootlessWindow.c
+++ b/miext/rootless/rootlessWindow.c
@@ -445,6 +445,12 @@ RootlessInitializeFrame(WindowPtr pWin, RootlessWindowRec *winRec)
 }
 
 
+Bool
+RootlessColormapCallback (void *data, int first_color, int n_colors, uint32_t *colors)
+{
+  return RootlessResolveColormap (data, first_color, n_colors, colors);
+}
+
 /*
  * RootlessEnsureFrame
  *  Make sure the given window is framed. If the window doesn't have a
@@ -503,6 +509,9 @@ RootlessEnsureFrame(WindowPtr pWin)
         return NULL;
     }
 
+    if (pWin->drawable.depth == 8)
+      RootlessFlushWindowColormap(pWin);
+
 #ifdef SHAPE
     if (pShape != NULL)
         REGION_UNINIT(pScreen, &shape);
@@ -1455,6 +1464,115 @@ out:
     }
 }
 
+
+void
+RootlessFlushWindowColormap (WindowPtr pWin)
+{
+  RootlessWindowRec *winRec = WINREC (pWin);
+  xp_window_changes wc;
+
+  if (winRec == NULL)
+    return;
+
+  RootlessStopDrawing (pWin, FALSE);
+
+  /* This is how we tell xp that the colormap may have changed. */
+
+  wc.colormap = RootlessColormapCallback;
+  wc.colormap_data = pWin->drawable.pScreen;
+
+  configure_window (winRec->wid, XP_COLORMAP, &wc);
+}
+
+/*
+ * SetPixmapOfAncestors
+ *  Set the Pixmaps on all ParentRelative windows up the ancestor chain.
+ */
+static void
+SetPixmapOfAncestors(WindowPtr pWin)
+{
+    ScreenPtr pScreen = pWin->drawable.pScreen;
+    WindowPtr topWin = TopLevelParent(pWin);
+    RootlessWindowRec *topWinRec = WINREC(topWin);
+
+    while (pWin->backgroundState == ParentRelative) {
+        if (pWin == topWin) {
+            // disallow ParentRelative background state on top level
+            XID pixel = 0;
+            ChangeWindowAttributes(pWin, CWBackPixel, &pixel, serverClient);
+            RL_DEBUG_MSG("Cleared ParentRelative on 0x%x.\n", pWin);
+            break;
+        }
+
+        pWin = pWin->parent;
+        pScreen->SetWindowPixmap(pWin, topWinRec->pixmap);
+    }
+}
+
+
+/*
+ * RootlessPaintWindowBackground
+ */
+void
+RootlessPaintWindowBackground(WindowPtr pWin, RegionPtr pRegion, int what)
+{
+    ScreenPtr pScreen = pWin->drawable.pScreen;
+ 
+    if (IsRoot(pWin))
+        return;
+
+    RL_DEBUG_MSG("paintwindowbackground start (win 0x%x, framed %i) ",
+                 pWin, IsFramedWindow(pWin));
+
+    if (IsFramedWindow(pWin)) {
+        RootlessStartDrawing(pWin);
+        RootlessDamageRegion(pWin, pRegion);
+
+        // For ParentRelative windows, we have to make sure the window
+        // pixmap is set correctly all the way up the ancestor chain.
+        if (pWin->backgroundState == ParentRelative) {
+            SetPixmapOfAncestors(pWin);
+        }
+    }
+
+    SCREEN_UNWRAP(pScreen, PaintWindowBackground);
+    pScreen->PaintWindowBackground(pWin, pRegion, what);
+    SCREEN_WRAP(pScreen, PaintWindowBackground);
+
+    RL_DEBUG_MSG("paintwindowbackground end\n");
+}
+
+
+/*
+ * RootlessPaintWindowBorder
+ */
+void
+RootlessPaintWindowBorder(WindowPtr pWin, RegionPtr pRegion, int what)
+{
+    RL_DEBUG_MSG("paintwindowborder start (win 0x%x) ", pWin);
+
+    if (IsFramedWindow(pWin)) {
+        RootlessStartDrawing(pWin);
+        RootlessDamageRegion(pWin, pRegion);
+
+        // For ParentRelative windows with tiled borders, we have to make
+        // sure the window pixmap is set correctly all the way up the
+        // ancestor chain.
+        if (!pWin->borderIsPixel &&
+            pWin->backgroundState == ParentRelative)
+        {
+            SetPixmapOfAncestors(pWin);
+        }
+    }
+
+    SCREEN_UNWRAP(pWin->drawable.pScreen, PaintWindowBorder);
+    pWin->drawable.pScreen->PaintWindowBorder(pWin, pRegion, what);
+    SCREEN_WRAP(pWin->drawable.pScreen, PaintWindowBorder);
+
+    RL_DEBUG_MSG("paintwindowborder end\n");
+}
+
+
 /*
  * RootlessChangeBorderWidth
  *  FIXME: untested!
@@ -1516,20 +1634,20 @@ RootlessChangeBorderWidth(WindowPtr pWin, unsigned int width)
 void
 RootlessOrderAllWindows (void)
 {
-  int i;
-  WindowPtr pWin;
-  
-  RL_DEBUG_MSG("RootlessOrderAllWindows() ");
-  for (i = 0; i < screenInfo.numScreens; i++) {
-    if (screenInfo.screens[i] == NULL) continue;
-    pWin = WindowTable[i];
-    if (pWin == NULL) continue;
+    int i;
+    WindowPtr pWin;
+    
+    RL_DEBUG_MSG("RootlessOrderAllWindows() ");
+    for (i = 0; i < screenInfo.numScreens; i++) {
+      if (screenInfo.screens[i] == NULL) continue;
+      pWin = WindowTable[i];
+      if (pWin == NULL) continue;
       
-    for (pWin = pWin->firstChild; pWin != NULL; pWin = pWin->nextSib) {
-      if (!pWin->realized) continue;
-      if (RootlessEnsureFrame(pWin) == NULL) continue;
-      RootlessReorderWindow (pWin);
+      for (pWin = pWin->firstChild; pWin != NULL; pWin = pWin->nextSib) {
+	if (!pWin->realized) continue;
+	if (RootlessEnsureFrame(pWin) == NULL) continue;
+	RootlessReorderWindow (pWin);
+      }
     }
-  }
-  RL_DEBUG_MSG("RootlessOrderAllWindows() done");
+    RL_DEBUG_MSG("RootlessOrderAllWindows() done");
 }
commit 8358334180a4f8c1e73fc5647a62bcd3539dee45
Author: Ben Byer <bbyer at bbyer.local>
Date:   Sun Nov 11 04:30:00 2007 -0800

    Darwin: Fixed the call to xp_init so that we now receive Motion notifications even
    if X is not the active application.
    fixes <rdar://problem/5167664> xeyes dead until window activation
    (cherry picked from commit c7573379a85a1480cc51650075078e41dafe56af)

diff --git a/hw/darwin/quartz/xpr/xprScreen.c b/hw/darwin/quartz/xpr/xprScreen.c
index 674a268..2db249f 100644
--- a/hw/darwin/quartz/xpr/xprScreen.c
+++ b/hw/darwin/quartz/xpr/xprScreen.c
@@ -231,7 +231,8 @@ xprDisplayInit(void)
     else
         darwinScreensFound =  1;
 
-    if (xp_init(XP_IN_BACKGROUND | XP_NO_DEFERRED_UPDATES) != Success)
+    if (xp_init(XP_BACKGROUND_EVENTS | XP_NO_DEFERRED_UPDATES) != Success)
+    {
         FatalError("Could not initialize the Xplugin library.");
 
     xp_select_events(XP_EVENT_DISPLAY_CHANGED
commit 512dee90878e552ad1b2bb5b27366707f6464f28
Author: Ben Byer <bbyer at bbyer.apple.com>
Date:   Thu Nov 8 22:17:38 2007 -0800

    Darwin: fix for spurious "Are you sure you want to quit?" message
    (cherry picked from commit 30cbfc786e4fedda3fe070bacceabe1d9212d00b)

diff --git a/hw/darwin/quartz/quartz.c b/hw/darwin/quartz/quartz.c
index ac1c347..8565e34 100644
--- a/hw/darwin/quartz/quartz.c
+++ b/hw/darwin/quartz/quartz.c
@@ -189,6 +189,7 @@ void DarwinModeInitInput(
     int argc,
     char **argv )
 {
+    X11ApplicationSetCanQuit(1);
     X11ApplicationServerReady();
     // Do final display mode specific initialization before handling events
     if (quartzProcs->InitInput)
commit 28e73e99a9a59223963312c5dd43ce5566d1db9d
Author: Ben Byer <bbyer at bbyer.apple.com>
Date:   Thu Nov 8 22:12:41 2007 -0800

    Darwin: Adding "fake RandR" support from old X11.app
    (cherry picked from commit 633490c4e8dab30af7ecbe1bef076c22ad5f5da9)

diff --git a/hw/darwin/quartz/quartz.c b/hw/darwin/quartz/quartz.c
index 0bbbada..ac1c347 100644
--- a/hw/darwin/quartz/quartz.c
+++ b/hw/darwin/quartz/quartz.c
@@ -54,6 +54,8 @@
 #include <fcntl.h>
 #include <IOKit/pwr_mgt/IOPMLib.h>
 
+#define FAKE_RANDR 1
+
 // Shared global variables for Quartz modes
 int                     quartzEventWriteFD = -1;
 int                     quartzStartClients = 1;
@@ -69,6 +71,30 @@ int                     noPseudoramiXExtension = FALSE;
 QuartzModeProcsPtr      quartzProcs = NULL;
 const char             *quartzOpenGLBundle = NULL;
 
+#if defined(RANDR) && !defined(FAKE_RANDR)
+Bool DarwinModeRandRGetInfo (ScreenPtr pScreen, Rotation *rotations) {
+  return FALSE;
+}
+
+Bool DarwinModeRandRSetConfig (ScreenPtr           pScreen,
+			       Rotation            randr,
+			       int                 rate,
+			       RRScreenSizePtr     pSize) {
+  return FALSE;
+}
+
+Bool DarwinModeRandRInit (ScreenPtr pScreen) {
+  rrScrPrivPtr    pScrPriv;
+    
+  if (!RRScreenInit (pScreen)) return FALSE;
+
+  pScrPriv = rrGetScrPriv(pScreen);
+  pScrPriv->rrGetInfo = DarwinModeRandRGetInfo;
+  pScrPriv->rrSetConfig = DarwinModeRandRSetConfig;
+  return TRUE;
+}
+#endif
+
 /*
 ===========================================================================
 
@@ -170,6 +196,51 @@ void DarwinModeInitInput(
 }
 
 
+#ifdef FAKE_RANDR
+extern char	*ConnectionInfo;
+
+static int padlength[4] = {0, 3, 2, 1};
+
+static void
+RREditConnectionInfo (ScreenPtr pScreen)
+{
+    xConnSetup	    *connSetup;
+    char	    *vendor;
+    xPixmapFormat   *formats;
+    xWindowRoot	    *root;
+    xDepth	    *depth;
+    xVisualType	    *visual;
+    int		    screen = 0;
+    int		    d;
+
+    connSetup = (xConnSetup *) ConnectionInfo;
+    vendor = (char *) connSetup + sizeof (xConnSetup);
+    formats = (xPixmapFormat *) ((char *) vendor +
+				 connSetup->nbytesVendor +
+				 padlength[connSetup->nbytesVendor & 3]);
+    root = (xWindowRoot *) ((char *) formats +
+			    sizeof (xPixmapFormat) * screenInfo.numPixmapFormats);
+    while (screen != pScreen->myNum)
+    {
+	depth = (xDepth *) ((char *) root + 
+			    sizeof (xWindowRoot));
+	for (d = 0; d < root->nDepths; d++)
+	{
+	    visual = (xVisualType *) ((char *) depth +
+				      sizeof (xDepth));
+	    depth = (xDepth *) ((char *) visual +
+				depth->nVisuals * sizeof (xVisualType));
+	}
+	root = (xWindowRoot *) ((char *) depth);
+	screen++;
+    }
+    root->pixWidth = pScreen->width;
+    root->pixHeight = pScreen->height;
+    root->mmWidth = pScreen->mmWidth;
+    root->mmHeight = pScreen->mmHeight;
+}
+#endif
+
 /*
  * QuartzUpdateScreens
  *  Adjust for screen arrangement changes.
@@ -181,6 +252,7 @@ static void QuartzUpdateScreens(void)
     int x, y, width, height, sx, sy;
     xEvent e;
 
+    ErrorF("QuartzUpdateScreens()\n");
     if (noPseudoramiXExtension || screenInfo.numScreens != 1)
     {
         /* FIXME: if not using Xinerama, we have multiple screens, and
@@ -202,8 +274,11 @@ static void QuartzUpdateScreens(void)
     pScreen->mmHeight = pScreen->mmHeight * ((double) height / pScreen->height);
     pScreen->width = width;
     pScreen->height = height;
-
-    /* FIXME: should probably do something with RandR here. */
+    
+#ifndef FAKE_RANDR
+    if(!DarwinModeRandRInit(pScreen))
+      FatalError("Failed to init RandR extension.\n");
+#endif
 
     DarwinAdjustScreenOrigins(&screenInfo);
     quartzProcs->UpdateScreen(pScreen);
@@ -231,7 +306,9 @@ static void QuartzUpdateScreens(void)
     e.u.configureNotify.override = pRoot->overrideRedirect;
     DeliverEvents(pRoot, &e, 1, NullWindow);
 
-    /* FIXME: Should we use RREditConnectionInfo(pScreen)? */
+#ifdef FAKE_RANDR
+    RREditConnectionInfo(pScreen);
+#endif
 }
 
 
commit 01b70afaac0990b41d1fb6fadbfd64df1486b669
Author: Ben Byer <bbyer at bbyer.local>
Date:   Sat Nov 3 05:34:19 2007 -0700

    Darwin: Initial support for Spaces -- if you use Expose to drag an X11
    window to another Space, it will work correctly (as opposed
    to just leaving a ghost window).  We accomplish this by listening
    for the notification from Xplugin that our window has been moved,
    and then we ask X11 to move the window to the new location.
    (cherry picked from commit 2d50ea8013e7c1639d570e227b53b037fb567565)

diff --git a/hw/darwin/quartz/quartz.c b/hw/darwin/quartz/quartz.c
index 3374baa..0bbbada 100644
--- a/hw/darwin/quartz/quartz.c
+++ b/hw/darwin/quartz/quartz.c
@@ -426,6 +426,18 @@ void DarwinModeProcessEvent(
 	    RootlessOrderAllWindows();
             break;
 
+        case kXDarwinWindowState:
+	  ErrorF("kXDarwinWindowState\n");
+	  break;
+    case kXDarwinWindowMoved: {
+	  WindowPtr pWin = (WindowPtr)xe->u.clientMessage.u.l.longs0;
+	  short x = xe->u.clientMessage.u.l.longs1,
+	        y = xe->u.clientMessage.u.l.longs2;
+	  ErrorF("kXDarwinWindowMoved(%p, %hd, %hd)\n", pWin, x, y);
+	  RootlessMoveWindow(pWin, x, y, pWin->nextSib, VTMove);
+    }
+	  break;
+
         default:
             ErrorF("Unknown application defined event type %d.\n", xe->u.u.type);
     }
diff --git a/hw/darwin/quartz/xpr/xprScreen.c b/hw/darwin/quartz/xpr/xprScreen.c
index a625e62..674a268 100644
--- a/hw/darwin/quartz/xpr/xprScreen.c
+++ b/hw/darwin/quartz/xpr/xprScreen.c
@@ -87,7 +87,13 @@ eventHandler(unsigned int type, const void *arg,
         {
             xp_window_id id = * (xp_window_id *) arg;
 	    WindowPtr pWin = xprGetXWindow(id);
-            QuartzMessageServerThread(kXDarwinWindowMoved, 1, pWin);
+	    BoxRec box;
+	    xp_error retval  = xp_get_window_bounds(id, &box);
+	    if (retval != Success) {
+	      ErrorF("Unable to find new bounds for window\n");
+	      break;
+	    }
+            QuartzMessageServerThread(kXDarwinWindowMoved, 3, pWin, box.x1, box.y1);
         }
         break;
 
commit b39edc01a6588697b65f831e8ab1dbb24cbe7b24
Author: Ben Byer <bbyer at bbyer.local>
Date:   Wed Oct 31 23:46:50 2007 -0700

    Darwin: Swap modifier keys for buttons 2 and 3 -- now Option-click is the middle click
    (cherry picked from commit 0aa61293b62aeb69a93b2035d0aef8644343eed3)

diff --git a/hw/darwin/darwin.c b/hw/darwin/darwin.c
index 22e1338..a4ec002 100644
--- a/hw/darwin/darwin.c
+++ b/hw/darwin/darwin.c
@@ -99,8 +99,8 @@ int                     darwinSyncKeymap = FALSE;
 int                     darwinSwapAltMeta = FALSE;
 
 // modifier masks for faking mouse buttons
-int                     darwinFakeMouse2Mask = NX_COMMANDMASK;
-int                     darwinFakeMouse3Mask = NX_ALTERNATEMASK;
+int                     darwinFakeMouse2Mask = NX_ALTERNATEMASK;
+int                     darwinFakeMouse3Mask = NX_COMMANDMASK;
 
 // devices
 DeviceIntPtr            darwinPointer = NULL;
commit 606a8dc73d91a198d72d249934dc027a23f4c338
Author: Ben Byer <bbyer at bbyer.local>
Date:   Wed Oct 31 03:39:47 2007 -0700

    Darwin: Trap Deactivate messages and release modifiers to avoid "stuck shift lock" (etc) bugs
    (cherry picked from commit 2b189a99330eb465fa0d17020fb1db1e38829151)

diff --git a/hw/darwin/darwinEvents.c b/hw/darwin/darwinEvents.c
index bc3a041..06c4cc7 100644
--- a/hw/darwin/darwinEvents.c
+++ b/hw/darwin/darwinEvents.c
@@ -147,6 +147,16 @@ static void DarwinUpdateModifiers(
     }
 }
 
+/*
+ * DarwinReleaseModifiers
+ * This hacky function releases all modifier keys.  It should be called when X11.app
+ * is deactivated (kXDarwinDeactivate) to prevent modifiers from getting stuck if they
+ * are held down during a "context" switch -- otherwise, we would miss the KeyUp.
+ */
+static void DarwinReleaseModifiers(void) {
+	xEvent e;
+	DarwinUpdateModifiers(&e, KeyRelease, COMMAND_MASK(-1) | CONTROL_MASK(-1) | ALTERNATE_MASK(-1) | SHIFT_MASK(-1));
+}
 
 /*
  * DarwinSimulateMouseClick
@@ -347,6 +357,9 @@ void ProcessInputEvents(void) {
 	      ErrorF("Unexpected XDarwinScrollWheel event in DarwinProcessInputEvents\n");
 	      break;
 
+			case kXDarwinDeactivate:
+				DarwinReleaseModifiers();
+				// fall through
             default:
                 // Check for mode specific event
                 DarwinModeProcessEvent(&xe);
commit 4c18ef4331aaee268431a3ba50991f0312b82870
Author: Ben Byer <bbyer at bbyer.local>
Date:   Wed Oct 31 03:22:18 2007 -0700

    Darwin: Workaround for a bug where the holding down Command to make a "fake"
    button 2 click would actually result in a Command-2 chord.
    (I.e. it wasn't releasing Command before clicking the fake button.)
    (cherry picked from commit 0d5dd5dffa4c5ce3f54dfe53720a39d524dc8e37)

diff --git a/hw/darwin/darwinEvents.c b/hw/darwin/darwinEvents.c
index 3d7f268..bc3a041 100644
--- a/hw/darwin/darwinEvents.c
+++ b/hw/darwin/darwinEvents.c
@@ -166,6 +166,9 @@ static void DarwinSimulateMouseClick(
     int modifierMask)   // modifiers used for the fake click
 {
     // first fool X into forgetting about the keys
+	// for some reason, it's not enough to tell X we released the Command key -- 
+	// it has to be the *left* Command key.
+	if (modifierMask & NX_COMMANDMASK) modifierMask |=NX_DEVICELCMDKEYMASK ;
     DarwinUpdateModifiers(KeyRelease, modifierMask);
 
     // push the mouse button


More information about the xorg-commit mailing list