Fixes a long-standing issue of the numlock being out-of-sync on a hotplugged keyboard.
Signed-off-by: Peter Hutterer <[email protected]> --- dix/devices.c | 7 +++++++ include/xkbsrv.h | 2 ++ xkb/xkbActions.c | 38 ++++++++++++++++++++++++++++++++++++++ 3 files changed, 47 insertions(+) diff --git a/dix/devices.c b/dix/devices.c index 1c86d52..f5a16bf 100644 --- a/dix/devices.c +++ b/dix/devices.c @@ -416,6 +416,7 @@ EnableDevice(DeviceIntPtr dev, BOOL sendevent) XISendDeviceHierarchyEvent(flags); } + XkbUpdateKbdModifiersFromMaster(dev); RecalculateMasterButtons(dev); /* initialise an idle timer for this device*/ @@ -2649,6 +2650,12 @@ AttachDevice(ClientPtr client, DeviceIntPtr dev, DeviceIntPtr master) dev->spriteInfo->paired = master; dev->spriteInfo->spriteOwner = FALSE; + /* AttachDevice is also called during EnableDevice, when the device + fd isn't set yet. Trying to write to the device will fail, but + the internal state is updated so the LEDs won't light up on the + second call at the end of EnableDevice */ + if (dev->public.on) + XkbUpdateKbdModifiersFromMaster(dev); RecalculateMasterButtons(master); } diff --git a/include/xkbsrv.h b/include/xkbsrv.h index 73a7b19..35f7bc4 100644 --- a/include/xkbsrv.h +++ b/include/xkbsrv.h @@ -758,6 +758,8 @@ XkbLatchLockState(ClientPtr client, int modLatches, int latchGroup, int groupLatch); +void +XkbUpdateKbdModifiersFromMaster(DeviceIntPtr dev); extern _X_EXPORT void XkbGetRulesDflts(XkbRMLVOSet * /* rmlvo */ ); diff --git a/xkb/xkbActions.c b/xkb/xkbActions.c index 1443498..c89baaf 100644 --- a/xkb/xkbActions.c +++ b/xkb/xkbActions.c @@ -79,6 +79,44 @@ XkbSetExtension(DeviceIntPtr device, ProcessInputProc proc) WRAP_PROCESS_INPUT_PROC(device, xkbPrivPtr, proc, xkbUnwrapProc); } +/** + * Update keyboard modifiers, and most importantly LEDs from the master + * device. + */ +void +XkbUpdateKbdModifiersFromMaster(DeviceIntPtr dev) +{ + DeviceIntPtr master = GetMaster(dev, MASTER_KEYBOARD); + XkbStateRec *state; + + if (!master) + return; + if (!dev->key) + return; + + BUG_WARN(!master->key); + + /* FIXME: this is potentially buggy. if the modmap of the slave differs + * from the master, we'll update the wrong mods and groups here. We'll + * have to live with that for now. + * Really what we'd need here is get each mod separately, map it to the + * respective mod on the other device, then update that map. + */ + state = &master->key->xkbInfo->state; + XkbLatchLockState(NullClient, dev, + state->locked_mods, + state->locked_mods, + state->locked_group, + state->locked_group, + state->latched_mods, + state->latched_mods, + state->latched_group, + state->latched_group); + +} + + + /***====================================================================***/ static XkbAction -- 1.8.4.2 _______________________________________________ [email protected]: X.Org development Archives: http://lists.x.org/archives/xorg-devel Info: http://lists.x.org/mailman/listinfo/xorg-devel
