Commit | Line | Data |
---|---|---|
7217e0ca ML |
1 | Date: Tue, 20 May 2014 14:32:59 +1000 |
2 | From: Peter Hutterer <peter.hutterer@who-t.net> | |
3 | Subject: [PATCH] mi: don't process events from disabled devices (#77884) | |
4 | ||
5 | Once a device is disabled, it doesn't have a sprite pointer anymore. If an | |
6 | event is still in the queue and processed after DisableDevice finished, a | |
7 | dereference causes a crash. Example backtrace (crash forced by injecting an | |
8 | event at the right time): | |
9 | ||
10 | (EE) 0: /opt/xorg/bin/Xorg (OsSigHandler+0x3c) [0x48d334] | |
11 | (EE) 1: /lib64/libpthread.so.0 (__restore_rt+0x0) [0x37fcc0f74f] | |
12 | (EE) 2: /opt/xorg/bin/Xorg (mieqMoveToNewScreen+0x38) [0x609240] | |
13 | (EE) 3: /opt/xorg/bin/Xorg (mieqProcessDeviceEvent+0xd4) [0x609389] | |
14 | (EE) 4: /opt/xorg/bin/Xorg (mieqProcessInputEvents+0x206) [0x609720] | |
15 | (EE) 5: /opt/xorg/bin/Xorg (ProcessInputEvents+0xd) [0x4aeb58] | |
16 | (EE) 6: /opt/xorg/bin/Xorg (xf86VTSwitch+0x1a6) [0x4af457] | |
17 | (EE) 7: /opt/xorg/bin/Xorg (xf86Wakeup+0x2bf) [0x4af0a7] | |
18 | (EE) 8: /opt/xorg/bin/Xorg (WakeupHandler+0x83) [0x4445cb] | |
19 | (EE) 9: /opt/xorg/bin/Xorg (WaitForSomething+0x3fe) [0x491bf6] | |
20 | (EE) 10: /opt/xorg/bin/Xorg (Dispatch+0x97) [0x435748] | |
21 | (EE) 11: /opt/xorg/bin/Xorg (dix_main+0x61d) [0x4438a9] | |
22 | (EE) 12: /opt/xorg/bin/Xorg (main+0x28) [0x49ba28] | |
23 | (EE) 13: /lib64/libc.so.6 (__libc_start_main+0xf5) [0x37fc821d65] | |
24 | (EE) 14: /opt/xorg/bin/Xorg (_start+0x29) [0x425e69] | |
25 | (EE) 15: ? (?+0x29) [0x29] | |
26 | ||
27 | xf86VTSwitch() calls ProcessInputEvents() before disabling a device, and | |
28 | DisableDevice() calls mieqProcessInputEvents() again when flushing touches and | |
29 | button events. Between that and disabling the device (which causes new events | |
30 | to be refused) there is a window where events may be triggered and enqueued. | |
31 | On the next call to PIE that event is processed on a now defunct device, | |
32 | causing the crash. | |
33 | ||
34 | The simplest fix to this is to discard events from disabled devices. We flush | |
35 | the queue often enough before disabling that when we get here, we really don't | |
36 | care about the events from this device. | |
37 | ||
38 | X.Org Bug 77884 <http://bugs.freedesktop.org/show_bug.cgi?id=77884> | |
39 | --- | |
40 | Modified by Maarten Lankhorst to pass tests. | |
41 | ||
42 | mi/mieq.c | 4 ++++ | |
43 | 1 file changed, 4 insertions(+) | |
44 | ||
45 | diff --git a/mi/mieq.c b/mi/mieq.c | |
46 | index 4c07480..188a0b0 100644 | |
47 | --- a/mi/mieq.c | |
48 | +++ b/mi/mieq.c | |
49 | @@ -515,6 +515,10 @@ mieqProcessDeviceEvent(DeviceIntPtr dev, InternalEvent *event, ScreenPtr screen) | |
50 | ||
51 | verify_internal_event(event); | |
52 | ||
53 | + /* refuse events from disabled devices */ | |
54 | + if (dev && !dev->enabled) | |
55 | + return 0; | |
56 | + | |
57 | /* Custom event handler */ | |
58 | handler = miEventQueue.handlers[event->any.type]; | |
59 | ||
60 | -- | |
61 | 1.9.0 | |
62 |