Thursday, June 21, 2012

_XkbErrCode2 macro explanation

While debugging some keyboard layout issues, I got this error:
X Error of failed request:  BadValue (integer parameter out of range for operation)
  Major opcode of failed request:  145 (XKEYBOARD)
  Minor opcode of failed request:  9 (XkbSetMap)
  Value in failed request:  0x163f0005
  Serial number of failed request:  116
  Current serial number in output stream:  122
X Errors are supposed to be useful to the client, usually denoting some error code (e.g. BadValue) and, if possible, the value that triggered it. After reading the code, I found the _XkbErrCode2 family of macros that expand to fill in the error code.
#define _XkbErrCode2(a,b) \
   ((XID)((((unsigned int)(a))<<24)|((b)&0xffffff)))
#define _XkbErrCode3(a,b,c) \
   _XkbErrCode2(a,(((unsigned int)(b))<<16)|(c))
#define _XkbErrCode4(a,b,c,d) \
   _XkbErrCode3(a,b,((((unsigned int)(c))<<8)|(d)))
Easy enough to decompose on the client though there's no indication of which decomposed representation is the correct one.
xkb/xkb.c:1742 _XkbErrCode3(0x16, i + req->firstKeySym, wire->width);
xkb/xkb.c:1749 _XkbErrCode4(0x16, i + req->firstKeySym, wire->nSyms, w);
That's when I started wondering what the 0x16 could mean - could it possibly be _XkbErrBadValue (from xkbfile.h) Bit generic, but possible. But why isn't it using the define? Looking at other _XkbErrCode calls, some were somewhat close but others were miles out. XkbBell returning _XkbErrMissingVMods? That didn't make sense.

And that's when it struck me: they didn't have any meaning. 0x16 is literally 0x16, the 22nd error code statement in this function. And, in this case also the 23rd since it is used twice. Of course, if one ever de-duplicate some of the XKB code the numbering is out. And I couldn't find a place where this is documented, so who knows how much damage we did to that approach without noticing.

Anyway, if you ever have to google for _XkbErrCode2, I'm hoping this post now comes up and explains the despair you're about to encounter.

No comments: