Alexandre Julliard : winex11: Add infrastructure for managing the extra data of generic extension events .

Alexandre Julliard julliard at winehq.org
Wed Apr 13 10:49:25 CDT 2011


Module: wine
Branch: master
Commit: a8575a8b4dc6f3678654dd3b72ece6d6f58632fa
URL:    http://source.winehq.org/git/wine.git/?a=commit;h=a8575a8b4dc6f3678654dd3b72ece6d6f58632fa

Author: Alexandre Julliard <julliard at winehq.org>
Date:   Tue Apr 12 21:16:15 2011 +0200

winex11: Add infrastructure for managing the extra data of generic extension events.

---

 configure                      |   12 ++++++++++++
 configure.ac                   |    2 +-
 dlls/winex11.drv/event.c       |   32 ++++++++++++++++++++++++++------
 dlls/winex11.drv/x11drv.h      |    3 +++
 dlls/winex11.drv/x11drv_main.c |   13 +++++++++++++
 dlls/winex11.drv/xrandr.c      |    4 +---
 dlls/winex11.drv/xrender.c     |    2 --
 include/config.h.in            |    3 +++
 8 files changed, 59 insertions(+), 12 deletions(-)

diff --git a/configure b/configure
index 76ecd55..8e8d044 100755
--- a/configure
+++ b/configure
@@ -8733,6 +8733,18 @@ _ACEOF
 
 
 fi
+ac_fn_c_check_member "$LINENO" "XEvent" "xcookie" "ac_cv_member_XEvent_xcookie" "#ifdef HAVE_X11_XLIB_H
+#include <X11/Xlib.h>
+#endif
+"
+if test "x$ac_cv_member_XEvent_xcookie" = x""yes; then :
+
+cat >>confdefs.h <<_ACEOF
+#define HAVE_XEVENT_XCOOKIE 1
+_ACEOF
+
+
+fi
 
 
 
diff --git a/configure.ac b/configure.ac
index 21c8d85..e82d193 100644
--- a/configure.ac
+++ b/configure.ac
@@ -1045,7 +1045,7 @@ then
                          [libxcomposite ${notice_platform}development files not found, Xcomposite won't be supported.])
 
         dnl *** Check for XICCallback struct
-        AC_CHECK_MEMBERS([XICCallback.callback],,,
+        AC_CHECK_MEMBERS([XICCallback.callback, XEvent.xcookie],,,
 [#ifdef HAVE_X11_XLIB_H
 #include <X11/Xlib.h>
 #endif])
diff --git a/dlls/winex11.drv/event.c b/dlls/winex11.drv/event.c
index 474e288..a05e906 100644
--- a/dlls/winex11.drv/event.c
+++ b/dlls/winex11.drv/event.c
@@ -86,6 +86,9 @@ extern BOOL ximInComposeMode;
 #define XEMBED_UNREGISTER_ACCELERATOR 13
 #define XEMBED_ACTIVATE_ACCELERATOR   14
 
+Bool (*pXGetEventData)( Display *display, XEvent /*XGenericEventCookie*/ *event ) = NULL;
+void (*pXFreeEventData)( Display *display, XEvent /*XGenericEventCookie*/ *event ) = NULL;
+
   /* Event handlers */
 static void X11DRV_FocusIn( HWND hwnd, XEvent *event );
 static void X11DRV_FocusOut( HWND hwnd, XEvent *event );
@@ -140,8 +143,6 @@ static x11drv_event_handler handlers[MAX_EVENT_HANDLERS] =
     NULL                      /* 35 GenericEvent */
 };
 
-
-
 static const char * event_names[MAX_EVENT_HANDLERS] =
 {
     NULL, NULL, "KeyPress", "KeyRelease", "ButtonPress", "ButtonRelease",
@@ -152,13 +153,29 @@ static const char * event_names[MAX_EVENT_HANDLERS] =
     "CirculateNotify", "CirculateRequest", "PropertyNotify", "SelectionClear", "SelectionRequest",
     "SelectionNotify", "ColormapNotify", "ClientMessage", "MappingNotify", "GenericEvent"
 };
+
 /* return the name of an X event */
 static const char *dbgstr_event( int type )
 {
-    if (type < MAX_EVENT_HANDLERS && event_names[type]) return event_names[type - KeyPress];
+    if (type < MAX_EVENT_HANDLERS && event_names[type]) return event_names[type];
     return wine_dbg_sprintf( "Unknown event %d", type );
 }
 
+static inline void get_event_data( XEvent *event )
+{
+#if defined(GenericEvent) && defined(HAVE_XEVENT_XCOOKIE)
+    if (event->xany.type != GenericEvent) return;
+    if (!pXGetEventData || !pXGetEventData( event->xany.display, event )) event->xcookie.data = NULL;
+#endif
+}
+
+static inline void free_event_data( XEvent *event )
+{
+#if defined(GenericEvent) && defined(HAVE_XEVENT_XCOOKIE)
+    if (event->xany.type != GenericEvent) return;
+    if (event->xcookie.data) pXFreeEventData( event->xany.display, event );
+#endif
+}
 
 /***********************************************************************
  *           X11DRV_register_event_handler
@@ -333,22 +350,25 @@ static int process_events( Display *display, Bool (*filter)(Display*, XEvent*,XP
             else
                 continue;  /* filtered, ignore it */
         }
+        get_event_data( &event );
         if (prev_event.type) action = merge_events( &prev_event, &event );
         switch( action )
         {
-        case MERGE_DISCARD:  /* discard prev, keep new */
-            prev_event = event;
-            break;
         case MERGE_HANDLE:  /* handle prev, keep new */
             call_event_handler( display, &prev_event );
+            /* fall through */
+        case MERGE_DISCARD:  /* discard prev, keep new */
+            free_event_data( &prev_event );
             prev_event = event;
             break;
         case MERGE_KEEP:  /* handle new, keep prev for future merging */
             call_event_handler( display, &event );
+            free_event_data( &event );
             break;
         }
     }
     if (prev_event.type) call_event_handler( display, &prev_event );
+    free_event_data( &prev_event );
     XFlush( gdi_display );
     wine_tsx11_unlock();
     if (count) TRACE( "processed %d events\n", count );
diff --git a/dlls/winex11.drv/x11drv.h b/dlls/winex11.drv/x11drv.h
index a06de4f..5f6c5cf 100644
--- a/dlls/winex11.drv/x11drv.h
+++ b/dlls/winex11.drv/x11drv.h
@@ -729,6 +729,9 @@ extern void X11DRV_SelectionRequest( HWND hWnd, XEvent *event );
 extern void X11DRV_SelectionClear( HWND hWnd, XEvent *event );
 extern void X11DRV_MappingNotify( HWND hWnd, XEvent *event );
 
+extern Bool (*pXGetEventData)( Display *display, XEvent /*XGenericEventCookie*/ *event );
+extern void (*pXFreeEventData)( Display *display, XEvent /*XGenericEventCookie*/ *event );
+
 extern DWORD EVENT_x11_time_to_win32_time(Time time);
 
 /* X11 driver private messages, must be in the range 0x80001000..0x80001fff */
diff --git a/dlls/winex11.drv/x11drv_main.c b/dlls/winex11.drv/x11drv_main.c
index 473b61f..9ac20c3 100644
--- a/dlls/winex11.drv/x11drv_main.c
+++ b/dlls/winex11.drv/x11drv_main.c
@@ -529,7 +529,20 @@ sym_not_found:
  */
 static BOOL process_attach(void)
 {
+    char error[1024];
     Display *display;
+    void *libx11 = wine_dlopen( SONAME_LIBX11, RTLD_NOW|RTLD_GLOBAL, error, sizeof(error) );
+
+    if (!libx11)
+    {
+        ERR( "failed to load %s: %s\n", SONAME_LIBX11, error );
+        return FALSE;
+    }
+    pXGetEventData = wine_dlsym( libx11, "XGetEventData", NULL, 0 );
+    pXFreeEventData = wine_dlsym( libx11, "XFreeEventData", NULL, 0 );
+#ifdef SONAME_LIBXEXT
+    wine_dlopen( SONAME_LIBXEXT, RTLD_NOW|RTLD_GLOBAL, NULL, 0 );
+#endif
 
     setup_options();
 
diff --git a/dlls/winex11.drv/xrandr.c b/dlls/winex11.drv/xrandr.c
index c313bab..0aea463 100644
--- a/dlls/winex11.drv/xrandr.c
+++ b/dlls/winex11.drv/xrandr.c
@@ -71,9 +71,7 @@ static int load_xrandr(void)
 {
     int r = 0;
 
-    if (wine_dlopen(SONAME_LIBX11, RTLD_NOW|RTLD_GLOBAL, NULL, 0) &&
-        wine_dlopen(SONAME_LIBXEXT, RTLD_NOW|RTLD_GLOBAL, NULL, 0) &&
-        wine_dlopen(SONAME_LIBXRENDER, RTLD_NOW|RTLD_GLOBAL, NULL, 0) &&
+    if (wine_dlopen(SONAME_LIBXRENDER, RTLD_NOW|RTLD_GLOBAL, NULL, 0) &&
         (xrandr_handle = wine_dlopen(SONAME_LIBXRANDR, RTLD_NOW, NULL, 0)))
     {
 
diff --git a/dlls/winex11.drv/xrender.c b/dlls/winex11.drv/xrender.c
index 33e420a..52e7f25 100644
--- a/dlls/winex11.drv/xrender.c
+++ b/dlls/winex11.drv/xrender.c
@@ -346,8 +346,6 @@ void X11DRV_XRender_Init(void)
     int event_base, i;
 
     if (client_side_with_render &&
-	wine_dlopen(SONAME_LIBX11, RTLD_NOW|RTLD_GLOBAL, NULL, 0) &&
-	wine_dlopen(SONAME_LIBXEXT, RTLD_NOW|RTLD_GLOBAL, NULL, 0) && 
 	(xrender_handle = wine_dlopen(SONAME_LIBXRENDER, RTLD_NOW, NULL, 0)))
     {
 
diff --git a/include/config.h.in b/include/config.h.in
index b7460cc..19a6b48 100644
--- a/include/config.h.in
+++ b/include/config.h.in
@@ -1118,6 +1118,9 @@
 /* Define to 1 if you have the <X11/Xutil.h> header file. */
 #undef HAVE_X11_XUTIL_H
 
+/* Define to 1 if `xcookie' is a member of `XEvent'. */
+#undef HAVE_XEVENT_XCOOKIE
+
 /* Define to 1 if `callback' is a member of `XICCallback'. */
 #undef HAVE_XICCALLBACK_CALLBACK
 




More information about the wine-cvs mailing list