Bug 40756 - There are fake KeyRelease events on listening "foreign" window.
Summary: There are fake KeyRelease events on listening "foreign" window.
Status: RESOLVED INVALID
Alias: None
Product: xorg
Classification: Unclassified
Component: Server/General (show other bugs)
Version: 7.6 (2010.12)
Hardware: All All
: medium normal
Assignee: Xorg Project Team
QA Contact: Xorg Project Team
URL:
Whiteboard:
Keywords:
Depends on:
Blocks:
 
Reported: 2011-09-10 10:14 UTC by Vadim Ushakov
Modified: 2018-06-12 18:43 UTC (History)
2 users (show)

See Also:
i915 platform:
i915 features:


Attachments

Description Vadim Ushakov 2011-09-10 10:14:18 UTC
When a client is listening for events of "foreign" windows, it receives fake KeyRelease before each KeyPress.

How to reproduce:

1. Run xev with its own window and press some keys. It works as expected:

KeyPress event, serial 41, synthetic NO, window 0x1e00001,
    root 0x199, subw 0x0, time 7167984, (838,-77), root:(953,658),
    state 0x0, keycode 65 (keysym 0x20, space), same_screen YES,
    XLookupString gives 1 bytes: (20) " "
    XmbLookupString gives 1 bytes: (20) " "
    XFilterEvent returns: False

KeyRelease event, serial 41, synthetic NO, window 0x1e00001,
    root 0x199, subw 0x0, time 7168102, (838,-77), root:(953,658),
    state 0x0, keycode 65 (keysym 0x20, space), same_screen YES,
    XLookupString gives 1 bytes: (20) " "
    XFilterEvent returns: False

KeyPress event, serial 41, synthetic NO, window 0x1e00001,
    root 0x199, subw 0x0, time 7174348, (838,-77), root:(953,658),
    state 0x0, keycode 50 (keysym 0xffe1, Shift_L), same_screen YES,
    XLookupString gives 0 bytes: 
    XmbLookupString gives 0 bytes: 
    XFilterEvent returns: False

KeyRelease event, serial 41, synthetic NO, window 0x1e00001,
    root 0x199, subw 0x0, time 7174453, (838,-77), root:(953,658),
    state 0x1, keycode 50 (keysym 0xffe1, Shift_L), same_screen YES,
    XLookupString gives 0 bytes: 
    XFilterEvent returns: False

KeyPress event, serial 41, synthetic NO, window 0x1e00001,
    root 0x199, subw 0x0, time 7176414, (838,-77), root:(953,658),
    state 0x0, keycode 24 (keysym 0x71, q), same_screen YES,
    XLookupString gives 1 bytes: (71) "q"
    XmbLookupString gives 1 bytes: (71) "q"
    XFilterEvent returns: False

KeyRelease event, serial 41, synthetic NO, window 0x1e00001,
    root 0x199, subw 0x0, time 7176494, (838,-77), root:(953,658),
    state 0x0, keycode 24 (keysym 0x71, q), same_screen YES,
    XLookupString gives 1 bytes: (71) "q"
    XFilterEvent returns: False

2. Now run another xev for the same window and press some keys.  The output contains fake KeyRelease events:

KeyRelease event, serial 17, synthetic NO, window 0x1e00001,
    root 0x199, subw 0x0, time 7167984, (838,-77), root:(953,658),
    state 0x0, keycode 65 (keysym 0x20, space), same_screen YES,
    XLookupString gives 1 bytes: (20) " "
    XFilterEvent returns: False

KeyPress event, serial 17, synthetic NO, window 0x1e00001,
    root 0x199, subw 0x0, time 7167984, (838,-77), root:(953,658),
    state 0x0, keycode 65 (keysym 0x20, space), same_screen YES,
    XLookupString gives 1 bytes: (20) " "
    XmbLookupString gives 1 bytes: (20) " "
    XFilterEvent returns: False

KeyRelease event, serial 17, synthetic NO, window 0x1e00001,
    root 0x199, subw 0x0, time 7168102, (838,-77), root:(953,658),
    state 0x0, keycode 65 (keysym 0x20, space), same_screen YES,
    XLookupString gives 1 bytes: (20) " "
    XFilterEvent returns: False

KeyRelease event, serial 17, synthetic NO, window 0x1e00001,
    root 0x199, subw 0x0, time 7174348, (838,-77), root:(953,658),
    state 0x0, keycode 50 (keysym 0xffe1, Shift_L), same_screen YES,
    XLookupString gives 0 bytes: 
    XFilterEvent returns: False

KeyPress event, serial 17, synthetic NO, window 0x1e00001,
    root 0x199, subw 0x0, time 7174348, (838,-77), root:(953,658),
    state 0x0, keycode 50 (keysym 0xffe1, Shift_L), same_screen YES,
    XLookupString gives 0 bytes: 
    XmbLookupString gives 0 bytes: 
    XFilterEvent returns: False

KeyRelease event, serial 17, synthetic NO, window 0x1e00001,
    root 0x199, subw 0x0, time 7174453, (838,-77), root:(953,658),
    state 0x1, keycode 50 (keysym 0xffe1, Shift_L), same_screen YES,
    XLookupString gives 0 bytes: 
    XFilterEvent returns: False

KeyRelease event, serial 17, synthetic NO, window 0x1e00001,
    root 0x199, subw 0x0, time 7176414, (838,-77), root:(953,658),
    state 0x0, keycode 24 (keysym 0x71, q), same_screen YES,
    XLookupString gives 1 bytes: (71) "q"
    XFilterEvent returns: False

KeyPress event, serial 17, synthetic NO, window 0x1e00001,
    root 0x199, subw 0x0, time 7176414, (838,-77), root:(953,658),
    state 0x0, keycode 24 (keysym 0x71, q), same_screen YES,
    XLookupString gives 1 bytes: (71) "q"
    XmbLookupString gives 1 bytes: (71) "q"
    XFilterEvent returns: False

KeyRelease event, serial 17, synthetic NO, window 0x1e00001,
    root 0x199, subw 0x0, time 7176494, (838,-77), root:(953,658),
    state 0x0, keycode 24 (keysym 0x71, q), same_screen YES,
    XLookupString gives 1 bytes: (71) "q"
    XFilterEvent returns: False


The bug is reproduced on X Server 1.10.3.901 and 1.11.0.


It seems that the bug is in keypress autorepeat code. The current implementation uses sequenceNumber field to store autorepeat flag:

------------------------------

/**
 * Hack to allow detectable autorepeat for core and XI1 events.
 * The sequence number is unused until we send to the client and can be
 * misused to store data. More or less, anyway.
 *
 * Do not use this. It may change any time without warning, eat your babies
 * and piss on your cat.
 */
static void
EventSetKeyRepeatFlag(xEvent *event, BOOL on)
{
    event->u.u.sequenceNumber = on;
}

/**
 * Check if the event was marked as a repeat event before.
 * NOTE: This is a nasty hack and should NOT be used by anyone else but
 * TryClientEvents.
 */
BOOL
EventIsKeyRepeat(xEvent *event)
{
    return !!event->u.u.sequenceNumber;
}

------------------------------

The function DeliverEventsToWindow() at first sends the event to the window owner and then to all other clients listening for the window events. 
When the event is sent to the window owner, event sequenceNumber is overwritten with real client sequence number. Next, the event is sent to other clients. And since result of the EventIsKeyRepeat() is no more valid and always equal to true, fake KeyRelease is generated in TryClientEvents().

Sorry for poor English. :-)
Comment 1 Adam Jackson 2018-06-12 18:43:28 UTC
Mass closure: This bug has been untouched for more than six years, and is not obviously still valid. Please file a new report if you continue to experience issues with a current server.


Use of freedesktop.org services, including Bugzilla, is subject to our Code of Conduct. How we collect and use information is described in our Privacy Policy.