Re: [PATCH v4 xserver] xkb: fix releasing overlay while keydown

2016-11-07 Thread Mariusz Mazur
Applied to my work env. If something starts acting funny I'll let you know.

2016-11-06 23:42 GMT+01:00 Mihail Konev <k@ya.ru>:
> Testcase:
>
> In ~/.xbindkeysrc:
>
>   "xterm &"
>XF86LaunchA
>
> In ~/ov.xkb:
>
>   xkb_keymap {
>   xkb_keycodes { include "evdev" };
>   xkb_types{ include "complete" };
>
>   xkb_compat   { include "complete"
>interpret Overlay1_Enable+AnyOfOrNone(all) {
>   action= SetControls(controls=Overlay1);
>};
>   };
>
>   xkb_symbols  { include "pc+inet(evdev)+us"
>   key  { [ Overlay1_Enable ] };
>   key  { overlay1 =  }; // Insert+1 => 2
>   key  { overlay1 =  }; // Insert+~ => XF86LaunchA
>   };
>
>   xkb_geometry { include "pc(pc104)" };
>   };
>
> Apply this layout: 'xkbcomp ~/ov.xkb $DISPLAY'.
> Run "xbindkeys -n -v"
> In the exact order:
> - press Insert
> - press Tilde
> - release Insert
> - wait
> - release Tilde
> Keyboard input in the new terminal window(s) would be locked
> until another Insert+Tilde .
>
> Reported-by: Mariusz Mazur <mariusz.g.ma...@gmail.com>
> Signed-off-by: Mihail Konev <k@ya.ru>
> ---
> v3 was still incorrect and did not done what it was supposed to.
> This version is specifically tested to properly enable and disable
> overlay, i.e. allow "`"-s to be sent both before and after Insert being
> down.
> Debugging version attached.
>
> Without (keywas_overlaid - 1) trickery it does not address the issue
> (i.e. input stays locked until Insert+Tilde)
> (but does not happen without open-new-window being triggered by xbindkeys,
> i.e. when the latter is not running).
> Maybe overlay_perkey_state description comment should better reflect this.
>
> Also commit description missed Reported-by.
>
> The "where-overlay1,2-is-in-xkb" is resolved in this patch.
>
> As for "applicability of overlays", they are per-keycode, and 
> layout-independent.
> This differs from RedirectKey that are per-keysym, and, therefore,
> also per-shift-level and per-layout (per-group).
>
> There should be no need to use overlays instead of RedirectKey,
> especially given that overlay is a "behavior", which
> could be only one per keycode.
>
>  xkb/xkbPrKeyEv.c | 36 +++-
>  1 file changed, 31 insertions(+), 5 deletions(-)
>
> diff --git a/xkb/xkbPrKeyEv.c b/xkb/xkbPrKeyEv.c
> index f7a6b4b14306..35bb1e9f405a 100644
> --- a/xkb/xkbPrKeyEv.c
> +++ b/xkb/xkbPrKeyEv.c
> @@ -43,6 +43,14 @@ THE USE OR PERFORMANCE OF THIS SOFTWARE.
>
>  /******/
>
> +/* Keeps track of overlay in effect for a given key,
> + * so that if an overlay is released while key is down,
> + * the key retains overlaid until its release.
> + * Cannot be a bitmask, as needs at least three values
> + * (as overlaid keys need to generate two releases).
> + * */
> +static unsigned char overlay_perkey_state[256];
> +
>  void
>  XkbProcessKeyboardEvent(DeviceEvent *event, DeviceIntPtr keybd)
>  {
> @@ -121,20 +129,38 @@ XkbProcessKeyboardEvent(DeviceEvent *event, 
> DeviceIntPtr keybd)
>  case XkbKB_Overlay2:
>  {
>  unsigned which;
> +unsigned overlay_active_now;
> +unsigned is_keyrelease = (event->type == ET_KeyRelease) ? 1 : 0;
> +unsigned key_was_overlaid = 0;
>
>  if (behavior.type == XkbKB_Overlay1)
>  which = XkbOverlay1Mask;
>  else
>  which = XkbOverlay2Mask;
> -if ((xkbi->desc->ctrls->enabled_ctrls & which) == 0)
> +overlay_active_now = (xkbi->desc->ctrls->enabled_ctrls & which) 
> ? 1 : 0;
> +
> +if ((unsigned char)key == key) {
> +key_was_overlaid = overlay_perkey_state[key];
> +if (overlay_active_now && !is_keyrelease)
> +overlay_perkey_state[key] = 2;
> +else if (is_keyrelease && (overlay_active_now || 
> key_was_overlaid))
> +overlay_perkey_state[key] = key_was_overlaid - 1;
> +else if (key_was_overlaid && !overlay_active_now && 
> !is_keyrelease) {
> +/* ignore key presses after overlay is released,
> + * as their release would have been overridden in prev 
> branch,
> + * and key wou

Re: Debugging keyboard overlay+xbindkeys

2016-11-04 Thread Mariusz Mazur
Question is, was it there for 22 years cause it's unfixable or because
nobody uses overlay? :)

2016-11-04 19:33 GMT+01:00  :
>> - press caps
>> - press f
>> - release caps
>> - wait
>> - release f
>
> In xserver/xkb/xkbPrKeyEv.c, there is a bug that prevents key
> press/release to be tracked properly for keys with overlays, in case
> such a key is down while the overlay state changes.  There is even a
> comment (from 9/11/94) that mentions the problem.
>
> Andreas
> ___
> xorg-devel@lists.x.org: X.Org development
> Archives: http://lists.x.org/archives/xorg-devel
> Info: https://lists.x.org/mailman/listinfo/xorg-devel
___
xorg-devel@lists.x.org: X.Org development
Archives: http://lists.x.org/archives/xorg-devel
Info: https://lists.x.org/mailman/listinfo/xorg-devel

Re: [PATCH v4 xserver] xkb: fix releasing overlay while keydown

2016-11-15 Thread Mariusz Mazur
A week has passed and everything's working fine (and I'm using the
overlay keycombos very very heavily). Seems the patch does not have
any unforeseen side effects.

2016-11-07 22:25 GMT+01:00 Mariusz Mazur <mariusz.g.ma...@gmail.com>:
> Applied to my work env. If something starts acting funny I'll let you know.
>
> 2016-11-06 23:42 GMT+01:00 Mihail Konev <k@ya.ru>:
>> Testcase:
>>
>> In ~/.xbindkeysrc:
>>
>>   "xterm &"
>>XF86LaunchA
>>
>> In ~/ov.xkb:
>>
>>   xkb_keymap {
>>   xkb_keycodes { include "evdev" };
>>   xkb_types{ include "complete" };
>>
>>   xkb_compat   { include "complete"
>>interpret Overlay1_Enable+AnyOfOrNone(all) {
>>   action= SetControls(controls=Overlay1);
>>};
>>   };
>>
>>   xkb_symbols  { include "pc+inet(evdev)+us"
>>   key  { [ Overlay1_Enable ] };
>>   key  { overlay1 =  }; // Insert+1 => 2
>>   key  { overlay1 =  }; // Insert+~ => 
>> XF86LaunchA
>>   };
>>
>>   xkb_geometry { include "pc(pc104)" };
>>   };
>>
>> Apply this layout: 'xkbcomp ~/ov.xkb $DISPLAY'.
>> Run "xbindkeys -n -v"
>> In the exact order:
>> - press Insert
>> - press Tilde
>> - release Insert
>> - wait
>> - release Tilde
>> Keyboard input in the new terminal window(s) would be locked
>> until another Insert+Tilde .
>>
>> Reported-by: Mariusz Mazur <mariusz.g.ma...@gmail.com>
>> Signed-off-by: Mihail Konev <k@ya.ru>
>> ---
>> v3 was still incorrect and did not done what it was supposed to.
>> This version is specifically tested to properly enable and disable
>> overlay, i.e. allow "`"-s to be sent both before and after Insert being
>> down.
>> Debugging version attached.
>>
>> Without (keywas_overlaid - 1) trickery it does not address the issue
>> (i.e. input stays locked until Insert+Tilde)
>> (but does not happen without open-new-window being triggered by xbindkeys,
>> i.e. when the latter is not running).
>> Maybe overlay_perkey_state description comment should better reflect this.
>>
>> Also commit description missed Reported-by.
>>
>> The "where-overlay1,2-is-in-xkb" is resolved in this patch.
>>
>> As for "applicability of overlays", they are per-keycode, and 
>> layout-independent.
>> This differs from RedirectKey that are per-keysym, and, therefore,
>> also per-shift-level and per-layout (per-group).
>>
>> There should be no need to use overlays instead of RedirectKey,
>> especially given that overlay is a "behavior", which
>> could be only one per keycode.
>>
>>  xkb/xkbPrKeyEv.c | 36 +++-
>>  1 file changed, 31 insertions(+), 5 deletions(-)
>>
>> diff --git a/xkb/xkbPrKeyEv.c b/xkb/xkbPrKeyEv.c
>> index f7a6b4b14306..35bb1e9f405a 100644
>> --- a/xkb/xkbPrKeyEv.c
>> +++ b/xkb/xkbPrKeyEv.c
>> @@ -43,6 +43,14 @@ THE USE OR PERFORMANCE OF THIS SOFTWARE.
>>
>>  /******/
>>
>> +/* Keeps track of overlay in effect for a given key,
>> + * so that if an overlay is released while key is down,
>> + * the key retains overlaid until its release.
>> + * Cannot be a bitmask, as needs at least three values
>> + * (as overlaid keys need to generate two releases).
>> + * */
>> +static unsigned char overlay_perkey_state[256];
>> +
>>  void
>>  XkbProcessKeyboardEvent(DeviceEvent *event, DeviceIntPtr keybd)
>>  {
>> @@ -121,20 +129,38 @@ XkbProcessKeyboardEvent(DeviceEvent *event, 
>> DeviceIntPtr keybd)
>>  case XkbKB_Overlay2:
>>  {
>>  unsigned which;
>> +unsigned overlay_active_now;
>> +unsigned is_keyrelease = (event->type == ET_KeyRelease) ? 1 : 0;
>> +unsigned key_was_overlaid = 0;
>>
>>  if (behavior.type == XkbKB_Overlay1)
>>  which = XkbOverlay1Mask;
>>  else
>>  which = XkbOverlay2Mask;
>> -if ((xkbi->desc->ctrls->enabled_ctrls & which) == 0)
>> +overlay_active_now = (xkbi->desc->ctrls->enabled_ctrls & which) 
>> ? 1 : 0;
>> +
>> +if ((unsigned char)key == ke

Debugging keyboard overlay+xbindkeys

2016-11-03 Thread Mariusz Mazur
Short version: using keyboard overlay to send e.g. XF86LaunchA, then
intercepting that with something like xbindkeys and launching an app
often triggers a bug which messes up the 'keycombo intercept'
mechanism in xorg.


Long version: inspired by fully programmable keyboards like the
ergodox or UHK, I've attempted to get the same functionality from
xorg. And almost succeeded.

What I did:
1. Switched the overlay key to act as a modifier.
 interpret Overlay1_Enable+AnyOfOrNone(all) {
-action= LockControls(controls=Overlay1);
+action= SetControls(controls=Overlay1);

2. Bound it to caps lock.
3. Defined caps+hjkl to act as arrow keys.
4. Defined caps+f to send XF86LaunchA to start a new terminal window
(among other similar shortcuts, like ones for switching virtual
desktops, but caps+f is the worst offender, so I'll focus on that).

The arrow keys thing works fine. The "launch app X" part doesn't. I've
tried various combinations of : kde4+konsole+xbindkeys and
lxde+lxterminal and it just doesn't work properly. The issues I've
seen:
- caps+f doesn't register some times; I need to mash it twice or
thrice for it to actually start a terminal
- xev says that sometimes the XF86LaunchA is not intercepted by
xbindkeys/lxde and actually arrives in xev; I'm guessing that might
have something to do with the previous issue
- sometimes a terminal starts in a weird zombie state, in which it
does not respond to keyboard and seems 'unfocused' (the cmd prompt
rectangle is not filled, even though the window is focused)
- The worst offender is my old kde4+xbindkeys combination (with up to
date xorg and kernel mind you) which very often (not always though)
blocks all keyboard input to all windows (xev shows nothing when I
press keys) until I either enter the exact key combination that caused
the issue (so usually caps+f) once or twice at which point it unlocks
the keyboard or I switch to some other tty and back again, which also
resets the problem (along with my xkb_keymap, which I then need to
reload). Ah, just figured it out. When in this 'locked' state *all* of
the keys I press end up intercepted by xbindkeys, which is why they
don't arrive in any apps.

It would seem using the overlay mechanism the way I do messes with
whatever mechanism xbindkeys/lxde use for intercepting keyboard
shortcuts. Does anybody have any suggestions on any tools/approaches I
could use to try to debug this further? Or is this mechanism something
so ancient that there's hope of getting it to work correctly?
___
xorg-devel@lists.x.org: X.Org development
Archives: http://lists.x.org/archives/xorg-devel
Info: https://lists.x.org/mailman/listinfo/xorg-devel

Re: Debugging keyboard overlay+xbindkeys

2016-11-04 Thread Mariusz Mazur
2016-11-03 22:20 GMT+01:00 Ran Benita :
>> 4. Defined caps+f to send XF86LaunchA to start a new terminal window
>> (among other similar shortcuts, like ones for switching virtual
>> desktops, but caps+f is the worst offender, so I'll focus on that).
>
> Nice hack.

Some ground work, a gui and such multi-layer keyboard rebindings could
become standard in many a linux distro.

> Just a guess, but maybe you are hitting this?
> https://cgit.freedesktop.org/xorg/xserver/tree/xkb/xkbPrKeyEv.c?id=xorg-server-1.18.99.902#n134
>
> Try running `xbindkeys --verbose` and see its output on key
> press/relase? The problem is in one of xserver, libX11 or xbindkeys,
> this would help narrow it down.

I know the issue isn't xbindkeys-specific, since I can also trigger a
form of it both on lxde and kde4.

Ha, bingo! While writing a reply I've been poking around it again and
found a fully reliable trigger in xbindkeys. It might just well be the
code you've linked to. Here's how to do it:

Relevant changes to keymap:

 interpret Overlay1_Enable+AnyOfOrNone(all) {
-action= LockControls(controls=Overlay1);
+action= SetControls(controls=Overlay1);
 };

 key  {
 type= "ALPHABETIC",
+overlay1= ,
 symbols[Group1]= [   f,   F ]
 };

-key  { [   Caps_Lock ] };
+key  { [   Overlay1_Enable ] };

-modifier_map Lock {  };



Contents of .xbindkeysrc:

"echo hi"
XF86LaunchA


Now run "xbindkeys -n -v" and in the exact order:
- press caps
- press f
- release caps
- wait
- release f

Voila. (Tested on two separate systems.)

Now, is there any chance of this getting a fix?
___
xorg-devel@lists.x.org: X.Org development
Archives: http://lists.x.org/archives/xorg-devel
Info: https://lists.x.org/mailman/listinfo/xorg-devel

Re: [PATCH v4 xserver] xkb: fix releasing overlay while keydown

2017-01-04 Thread Mariusz Mazur
I've been using this heavily (at least a few hundred overlay1
keystrokes per day) for the past almost two months and had zero
issues. Any chance this could get merged?

2016-11-15 10:31 GMT+01:00 Mariusz Mazur <mariusz.g.ma...@gmail.com>:
> A week has passed and everything's working fine (and I'm using the
> overlay keycombos very very heavily). Seems the patch does not have
> any unforeseen side effects.
>
> 2016-11-07 22:25 GMT+01:00 Mariusz Mazur <mariusz.g.ma...@gmail.com>:
>> Applied to my work env. If something starts acting funny I'll let you know.
>>
>> 2016-11-06 23:42 GMT+01:00 Mihail Konev <k@ya.ru>:
>>> Testcase:
>>>
>>> In ~/.xbindkeysrc:
>>>
>>>   "xterm &"
>>>XF86LaunchA
>>>
>>> In ~/ov.xkb:
>>>
>>>   xkb_keymap {
>>>   xkb_keycodes { include "evdev" };
>>>   xkb_types{ include "complete" };
>>>
>>>   xkb_compat   { include "complete"
>>>interpret Overlay1_Enable+AnyOfOrNone(all) {
>>>   action= SetControls(controls=Overlay1);
>>>};
>>>   };
>>>
>>>   xkb_symbols  { include "pc+inet(evdev)+us"
>>>   key  { [ Overlay1_Enable ] };
>>>   key  { overlay1 =  }; // Insert+1 => 2
>>>   key  { overlay1 =  }; // Insert+~ => 
>>> XF86LaunchA
>>>   };
>>>
>>>   xkb_geometry { include "pc(pc104)" };
>>>   };
>>>
>>> Apply this layout: 'xkbcomp ~/ov.xkb $DISPLAY'.
>>> Run "xbindkeys -n -v"
>>> In the exact order:
>>> - press Insert
>>> - press Tilde
>>> - release Insert
>>> - wait
>>> - release Tilde
>>> Keyboard input in the new terminal window(s) would be locked
>>> until another Insert+Tilde .
>>>
>>> Reported-by: Mariusz Mazur <mariusz.g.ma...@gmail.com>
>>> Signed-off-by: Mihail Konev <k@ya.ru>
>>> ---
>>> v3 was still incorrect and did not done what it was supposed to.
>>> This version is specifically tested to properly enable and disable
>>> overlay, i.e. allow "`"-s to be sent both before and after Insert being
>>> down.
>>> Debugging version attached.
>>>
>>> Without (keywas_overlaid - 1) trickery it does not address the issue
>>> (i.e. input stays locked until Insert+Tilde)
>>> (but does not happen without open-new-window being triggered by xbindkeys,
>>> i.e. when the latter is not running).
>>> Maybe overlay_perkey_state description comment should better reflect this.
>>>
>>> Also commit description missed Reported-by.
>>>
>>> The "where-overlay1,2-is-in-xkb" is resolved in this patch.
>>>
>>> As for "applicability of overlays", they are per-keycode, and 
>>> layout-independent.
>>> This differs from RedirectKey that are per-keysym, and, therefore,
>>> also per-shift-level and per-layout (per-group).
>>>
>>> There should be no need to use overlays instead of RedirectKey,
>>> especially given that overlay is a "behavior", which
>>> could be only one per keycode.
>>>
>>>  xkb/xkbPrKeyEv.c | 36 +++-
>>>  1 file changed, 31 insertions(+), 5 deletions(-)
>>>
>>> diff --git a/xkb/xkbPrKeyEv.c b/xkb/xkbPrKeyEv.c
>>> index f7a6b4b14306..35bb1e9f405a 100644
>>> --- a/xkb/xkbPrKeyEv.c
>>> +++ b/xkb/xkbPrKeyEv.c
>>> @@ -43,6 +43,14 @@ THE USE OR PERFORMANCE OF THIS SOFTWARE.
>>>
>>>  
>>> /******/
>>>
>>> +/* Keeps track of overlay in effect for a given key,
>>> + * so that if an overlay is released while key is down,
>>> + * the key retains overlaid until its release.
>>> + * Cannot be a bitmask, as needs at least three values
>>> + * (as overlaid keys need to generate two releases).
>>> + * */
>>> +static unsigned char overlay_perkey_state[256];
>>> +
>>>  void
>>>  XkbProcessKeyboardEvent(DeviceEvent *event, DeviceIntPtr keybd)
>>>  {
>>> @@ -121,20 +129,38 @@ XkbProcessKeyboardEvent(DeviceEvent *event, 
>>> DeviceIntPtr keybd)
>>>  case XkbKB_Overlay2:
>>>  {
>>>