[PATCH] xkbcomp Fix missing support for "affect" and incorrect modifier handling for ISOLock

Andreas Wettstein wettstein509 at solnet.ch
Sat Feb 15 08:34:41 PST 2014


Add missing support for "affect" flag to selectively affect locking or
unlocking for for modifier locking, control locking, and ISOLock.
Fix some incorrect masking and modifier handling for ISOLock.

Signed-off-by: Andreas Wettstein <wettstein509 at solnet.ch>
---
 action.c | 52 +++++++++++++++++++++++++++++++++++++---------------
 1 file changed, 37 insertions(+), 15 deletions(-)

diff --git a/action.c b/action.c
index 4623c0c..dd89a1c 100644
--- a/action.c
+++ b/action.c
@@ -436,6 +436,14 @@ HandleSetLatchMods(XkbDescPtr xkb,
     return ReportIllegal(action->type, field);
 }
 
+static LookupEntry lockWhich[] = {
+    {"both", 0},
+    {"lock", XkbSA_LockNoUnlock},
+    {"neither", (XkbSA_LockNoLock | XkbSA_LockNoUnlock)},
+    {"unlock", XkbSA_LockNoLock},
+    {NULL, 0}
+};
+
 static Bool
 HandleLockMods(XkbDescPtr xkb,
                XkbAnyAction * action,
@@ -443,12 +451,19 @@ HandleLockMods(XkbDescPtr xkb,
 {
     XkbModAction *act;
     unsigned t1, t2;
+    ExprResult rtrn;
 
     act = (XkbModAction *) action;
-    if ((array_ndx != NULL) && (field == F_Modifiers))
+    if ((array_ndx != NULL) && (field == F_Modifiers || field == F_Affect))
         return ReportActionNotArray(action->type, field);
     switch (field)
     {
+    case F_Affect:
+        if (!ExprResolveEnum(value, &rtrn, lockWhich))
+            return ReportMismatch(action->type, field, "lock or unlock");
+        act->flags &= ~(XkbSA_LockNoLock | XkbSA_LockNoUnlock);
+        act->flags |= rtrn.uval;
+        return True;
     case F_Modifiers:
         t1 = act->flags;
         if (CheckModifierField(xkb, action->type, value, &t1, &t2))
@@ -641,14 +656,6 @@ static LookupEntry btnNames[] = {
     {NULL, 0}
 };
 
-static LookupEntry lockWhich[] = {
-    {"both", 0},
-    {"lock", XkbSA_LockNoUnlock},
-    {"neither", (XkbSA_LockNoLock | XkbSA_LockNoUnlock)},
-    {"unlock", XkbSA_LockNoLock},
-    {NULL, 0}
-};
-
 static Bool
 HandlePtrBtn(XkbDescPtr xkb,
              XkbAnyAction * action,
@@ -682,7 +689,7 @@ HandlePtrBtn(XkbDescPtr xkb,
         if (!ExprResolveEnum(value, &rtrn, lockWhich))
             return ReportMismatch(action->type, field, "lock or unlock");
         act->flags &= ~(XkbSA_LockNoLock | XkbSA_LockNoUnlock);
-        act->flags |= rtrn.ival;
+        act->flags |= rtrn.uval;
         return True;
     }
     else if (field == F_Count)
@@ -779,8 +786,12 @@ static LookupEntry isoNames[] = {
     {"pointer", XkbSA_ISONoAffectPtr},
     {"ctrls", XkbSA_ISONoAffectCtrls},
     {"controls", XkbSA_ISONoAffectCtrls},
-    {"all", ~((unsigned) 0)},
+    {"all", XkbSA_ISOAffectMask},
     {"none", 0},
+    {"both", 0},
+    {"lock", XkbSA_LockNoUnlock},
+    {"neither", (XkbSA_LockNoLock | XkbSA_LockNoUnlock)},
+    {"unlock", XkbSA_LockNoLock},
     {NULL, 0},
 };
 
@@ -804,8 +815,8 @@ HandleISOLock(XkbDescPtr xkb,
         if (CheckModifierField(xkb, action->type, value, &flags, &mods))
         {
             act->flags = flags & (~XkbSA_ISODfltIsGroup);
-            act->real_mods = mods & 0xff;
-            mods = (mods >> 8) & 0xff;
+            act->real_mods = act->mask = (mods & 0xff);
+            mods = (mods >> 8) & 0xffff;
             XkbSetModActionVMods(act, mods);
             return True;
         }
@@ -827,6 +838,8 @@ HandleISOLock(XkbDescPtr xkb,
         if (!ExprResolveMask(value, &rtrn, SimpleLookup, (XPointer) isoNames))
             return ReportMismatch(action->type, field, "keyboard component");
         act->affect = (~rtrn.uval) & XkbSA_ISOAffectMask;
+        act->flags &= ~(XkbSA_LockNoLock | XkbSA_LockNoUnlock);
+        act->flags |= rtrn.uval & (XkbSA_LockNoLock | XkbSA_LockNoUnlock);
         return True;
     }
     return ReportIllegal(action->type, field);
@@ -943,6 +956,15 @@ HandleSetLockControls(XkbDescPtr xkb,
         XkbActionSetCtrls(act, rtrn.uval);
         return True;
     }
+    else if (field == F_Affect && action->type == XkbSA_LockControls) {
+        if (array_ndx != NULL)
+            return ReportActionNotArray(action->type, field);
+        if (!ExprResolveEnum(value, &rtrn, lockWhich))
+            return ReportMismatch(action->type, field, "lock or unlock");
+        act->flags &= ~(XkbSA_LockNoLock | XkbSA_LockNoUnlock);
+        act->flags |= rtrn.uval;
+        return True;
+    }
     return ReportIllegal(action->type, field);
 }
 
@@ -1122,7 +1144,7 @@ HandleDeviceBtn(XkbDescPtr xkb,
         if (!ExprResolveEnum(value, &rtrn, lockWhich))
             return ReportMismatch(action->type, field, "lock or unlock");
         act->flags &= ~(XkbSA_LockNoLock | XkbSA_LockNoUnlock);
-        act->flags |= rtrn.ival;
+        act->flags |= rtrn.uval;
         return True;
     }
     else if (field == F_Count)
@@ -1289,7 +1311,7 @@ ApplyActionFactoryDefaults(XkbAction * action)
     }
     else if (action->type == XkbSA_ISOLock)
     {
-        action->iso.real_mods = LockMask;
+        action->iso.real_mods = action->iso.mask = LockMask;
     }
     return;
 }
-- 
1.8.3.1



More information about the xorg-devel mailing list