xserver: Branch 'master' - 3 commits

Keith Packard keithp at kemper.freedesktop.org
Wed Jun 1 17:32:02 UTC 2016


 dix/enterleave.c |    1 -
 dix/events.c     |    1 -
 os/inputthread.c |   14 +++++++++++---
 os/osinit.c      |    2 +-
 4 files changed, 12 insertions(+), 6 deletions(-)

New commits:
commit 7c77c42fe87316e5c68611f03b0bda96656c4a4c
Author: Keith Packard <keithp at keithp.com>
Date:   Fri May 27 17:36:57 2016 -0700

    dix: Don't update current time in the middle of input event processing
    
    In patch 137ac094e7ab8c871f3b36e40ad826ac797f0e26, Adam moved an
    expensive call to UpdateCurrentTime out of the main dispatch
    loop. That's a good change as the original fix from Chase was a bit
    expensive. However, it breaks grab processing and so a couple of the
    calls to UpdateCurrenTime need to be removed.
    
    Input event processing can generate a stream of events; a button press
    that activates a grab will send a press followed by a sequence of
    enter/leave events. All of these should have the same time stamp on
    the wire as they occur at the 'same' time.
    
    More importantly, the grab time recorded in the device is pulled from
    currentTime after all of the events are delivered, so if currentTime
    doesn't match the time in the device event, then future grab
    modifications will fail as the time marked in the device will be
    'later' than the grab time known to the client (which is defined as
    the timestamp from the activating input event).
    
    A bit of history here -- it used to be that currentTime was driven
    *entirely* by input events; those timestamps didn't even have to be
    related to the system time in any way. Then we started doing ICCCM
    stuff and people got confused when PropertyNotify events would have
    the same timestamp even when delivered minutes apart because no input
    events were delivered.
    
    We added code in the server to go update the time, but only if no
    input events were pending (so that the clock "wouldn't" go
    backwards). The only places where this is necessary is in request
    processing which may generate an event with a timestamp, and there
    only at the very top of the request processing code so that the whole
    request would be processed at the 'same time', just like events.
    
    cc: Chase Douglas <chase.douglas at canonical.com>
    cc: Peter Hutterer <peter.hutterer at who-t.net>
    cc: Adam Jackson <ajax at redhat.com>
    Signed-off-by: Keith Packard <keithp at keithp.com>
    Tested-by: Michel Dänzer <michel.daenzer at amd.com>
    Acked-by: Peter Hutterer <peter.hutterer at who-t.net>

diff --git a/dix/enterleave.c b/dix/enterleave.c
index 0c6c616..1b341f2 100644
--- a/dix/enterleave.c
+++ b/dix/enterleave.c
@@ -782,7 +782,6 @@ DeviceFocusEvent(DeviceIntPtr dev, int type, int mode, int detail,
     DeviceIntPtr mouse;
     int btlen, len, i;
 
-    UpdateCurrentTimeIf();
     mouse = IsFloating(dev) ? dev : GetMaster(dev, MASTER_POINTER);
 
     /* XI 2 event */
diff --git a/dix/events.c b/dix/events.c
index 0404eba..8efdf18 100644
--- a/dix/events.c
+++ b/dix/events.c
@@ -2242,7 +2242,6 @@ DeliverEventsToWindow(DeviceIntPtr pDev, WindowPtr pWin, xEvent
                                    this mask is the mask of the grab. */
     int type = pEvents->u.u.type;
 
-    UpdateCurrentTimeIf();
     /* Deliver to window owner */
     if ((filter == CantBeFiltered) || core_get_type(pEvents) != 0) {
         enum EventDeliveryState rc;
commit ce6546337487c052b5dd3c04d3d8d4b09d691c3d
Author: Keith Packard <keithp at keithp.com>
Date:   Tue May 31 09:38:17 2016 -0700

    os: Initialize NotifyFds earlier in startup
    
    If the server calls AbortServer during the first-time initialization
    (which can happen if you start the server on an already using
    DISPLAY), then the dbus code will shut down and call the notify fd
    interface. If the notify fd list hasn't been initialized, the server
    will crash.
    
    Signed-off-by: Keith Packard <keithp at keithp.com>
    Reviewed-by: Peter Hutterer <peter.hutterer at who-t.net>

diff --git a/os/osinit.c b/os/osinit.c
index 54b39a0..629fef5 100644
--- a/os/osinit.c
+++ b/os/osinit.c
@@ -195,6 +195,7 @@ OsInit(void)
 #ifdef BUSFAULT
         busfault_init();
 #endif
+        InitNotifyFds();
 
 #ifdef HAVE_BACKTRACE
         /*
@@ -314,7 +315,6 @@ OsInit(void)
         LockServer();
         been_here = TRUE;
     }
-    InitNotifyFds();
     TimerInit();
     OsVendorInit();
     OsResetSignals();
commit f0756793e4c30278164d7a5cc483ce6a311c58dc
Author: Keith Packard <keithp at keithp.com>
Date:   Tue May 31 09:14:17 2016 -0700

    os: Lock input while messing with input device list
    
    The list of input devices may be changed by hotplugging while the
    server is active, and those changes may come from either the main
    thread or the input thread. That means the list of input devices needs
    to be protected by a mutex.
    
    This prevents input drivers from receiving I/O ready callbacks after
    removing a device.
    
    Signed-off-by: Keith Packard <keithp at keithp.com>
    Reviewed-by: Peter Hutterer <peter.hutterer at who-t.net>

diff --git a/os/inputthread.c b/os/inputthread.c
index 390b66b..40a0443 100644
--- a/os/inputthread.c
+++ b/os/inputthread.c
@@ -197,12 +197,14 @@ InputThreadRegisterDev(int fd,
     dev->readInputProc = readInputProc;
     dev->readInputArgs = readInputArgs;
 
+    input_lock();
     xorg_list_add(&dev->node, &inputThreadInfo->devs);
 
     FD_SET(fd, &inputThreadInfo->fds);
 
     InputThreadFillPipe(hotplugPipeWrite);
     DebugF("input-thread: registered device %d\n", fd);
+    input_unlock();
 
     return 1;
 }
@@ -228,6 +230,7 @@ InputThreadUnregisterDev(int fd)
         return 1;
     }
 
+    input_lock();
     xorg_list_for_each_entry(dev, &inputThreadInfo->devs, node)
         if (dev->fd == fd) {
             found_device = TRUE;
@@ -235,12 +238,17 @@ InputThreadUnregisterDev(int fd)
         }
 
     /* fd didn't match any registered device. */
-    if (!found_device)
+    if (!found_device) {
+        input_unlock();
         return 0;
+    }
 
     xorg_list_del(&dev->node);
 
     FD_CLR(fd, &inputThreadInfo->fds);
+
+    input_unlock();
+
     free(dev);
 
     InputThreadFillPipe(hotplugPipeWrite);
@@ -292,14 +300,14 @@ InputThreadDoWork(void *arg)
 
         DebugF("input-thread: %s generating events\n", __func__);
 
+        input_lock();
         /* Call the device drivers to generate input events for us */
         xorg_list_for_each_entry_safe(dev, next, &inputThreadInfo->devs, node) {
             if (FD_ISSET(dev->fd, &readyFds) && dev->readInputProc) {
-                input_lock();
                 dev->readInputProc(dev->fd, X_NOTIFY_READ, dev->readInputArgs);
-                input_unlock();
             }
         }
+        input_unlock();
 
         /* Kick main thread to process the generated input events and drain
          * events from hotplug pipe */


More information about the xorg-commit mailing list