Update the cursor for each window on receiving an X11 event, don't
wait for the SetCursor call.
Added EnterNotify handler to set the cursor on window map/unmap.

diff --git a/dlls/x11drv/window.c b/dlls/x11drv/window.c
index 0887068..c5f726e 100644
--- a/dlls/x11drv/window.c
+++ b/dlls/x11drv/window.c
@@ -115,7 +115,6 @@
  *              get_window_attributes
  *
  * Fill the window attributes structure for an X window.
- * Returned cursor must be freed by caller.
  */
 static int get_window_attributes( Display *display, WND *win, XSetWindowAttributes *attr )
 {
@@ -128,14 +127,13 @@
     attr->override_redirect = !managed;
     attr->colormap          = X11DRV_PALETTE_PaletteXColormap;
     attr->save_under        = ((win->clsStyle & CS_SAVEBITS) != 0);
-    attr->cursor            = None;
+    attr->cursor            = x11drv_thread_data()->cursor;
     attr->event_mask        = (ExposureMask | KeyPressMask | KeyReleaseMask | PointerMotionMask |
-                               ButtonPressMask | ButtonReleaseMask);
+                               ButtonPressMask | ButtonReleaseMask | EnterWindowMask);
+
     if (is_window_top_level( win ))
-    {
         attr->event_mask |= StructureNotifyMask | FocusChangeMask | KeymapStateMask;
-        attr->cursor = X11DRV_GetCursor( display, GlobalLock16(GetCursor()) );
-    }
+
     return (CWOverrideRedirect | CWSaveUnder | CWEventMask | CWColormap | CWCursor);
 }
 
@@ -153,7 +151,6 @@
     wine_tsx11_lock();
     mask = get_window_attributes( display, win, &attr );
     XChangeWindowAttributes( display, get_whole_window(win), mask, &attr );
-    if (attr.cursor) XFreeCursor( display, attr.cursor );
     wine_tsx11_unlock();
 }
 
@@ -200,7 +197,7 @@
     XSetWindowAttributes attr;
 
     attr.event_mask = (ExposureMask | KeyPressMask | KeyReleaseMask | PointerMotionMask |
-                       ButtonPressMask | ButtonReleaseMask);
+                       ButtonPressMask | ButtonReleaseMask | EnterWindowMask);
     attr.bit_gravity = NorthWestGravity;
     attr.backing_store = NotUseful/*WhenMapped*/;
     attr.colormap      = X11DRV_PALETTE_PaletteXColormap; /* Needed due to our visual */
@@ -230,6 +227,8 @@
     struct x11drv_win_data *data = win->pDriverData;
 
     if (!data->icon_window) return;
+    if (x11drv_thread_data()->cursor_window == data->icon_window)
+        x11drv_thread_data()->cursor_window = None;
     wine_tsx11_lock();
     XDeleteContext( display, data->icon_window, winContext );
     XDestroyWindow( display, data->icon_window );
@@ -695,7 +694,6 @@
     data->whole_window = XCreateWindow( display, parent, rect.left, rect.top, cx, cy,
                                         0, screen_depth, InputOutput, visual,
                                         mask, &attr );
-    if (attr.cursor) XFreeCursor( display, attr.cursor );
 
     if (!data->whole_window)
     {
@@ -734,7 +732,7 @@
     data->client_rect = rect;
 
     attr.event_mask = (ExposureMask | KeyPressMask | KeyReleaseMask | PointerMotionMask |
-                       ButtonPressMask | ButtonReleaseMask);
+                       ButtonPressMask | ButtonReleaseMask | EnterWindowMask);
     attr.bit_gravity = (win->clsStyle & (CS_VREDRAW | CS_HREDRAW)) ?
                        ForgetGravity : NorthWestGravity;
     attr.backing_store = NotUseful/*WhenMapped*/;
@@ -827,7 +825,8 @@
  */
 BOOL X11DRV_DestroyWindow( HWND hwnd )
 {
-    Display *display = thread_display();
+    struct x11drv_thread_data *thread_data = x11drv_thread_data();
+    Display *display = thread_data->display;
     WND *wndPtr = WIN_GetPtr( hwnd );
     X11DRV_WND_DATA *data = wndPtr->pDriverData;
 
@@ -836,6 +835,7 @@
     if (data->whole_window)
     {
         TRACE( "win %x xwin %lx/%lx\n", hwnd, data->whole_window, data->client_window );
+        if (thread_data->cursor_window == data->whole_window) thread_data->cursor_window = None;
         wine_tsx11_lock();
         XSync( gdi_display, False );  /* flush any reference to this drawable in GDI queue */
         XDeleteContext( display, data->whole_window, winContext );