1 /************************************************************
2 Copyright (c) 1993 by Silicon Graphics Computer Systems, Inc.
4 Permission to use, copy, modify, and distribute this
5 software and its documentation for any purpose and without
6 fee is hereby granted, provided that the above copyright
7 notice appear in all copies and that both that copyright
8 notice and this permission notice appear in supporting
9 documentation, and that the name of Silicon Graphics not be
10 used in advertising or publicity pertaining to distribution
11 of the software without specific prior written permission.
12 Silicon Graphics makes no representation about the suitability
13 of this software for any purpose. It is provided "as is"
14 without any express or implied warranty.
16 SILICON GRAPHICS DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS
17 SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
18 AND FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL SILICON
19 GRAPHICS BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
20 DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
21 DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
22 OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH
23 THE USE OR PERFORMANCE OF THIS SOFTWARE.
25 ********************************************************/
33 #include "X11/extensions/XKBcommon.h"
34 #include "XKBcommonint.h"
35 #include <X11/keysym.h>
36 #include <X11/extensions/XKBfilecommon.h>
38 #define mapSize(m) (sizeof(m) / sizeof(XkbKTMapEntryRec))
39 static XkbKTMapEntryRec map2Level[]= {
40 { True, ShiftMask, {1, ShiftMask, 0} }
43 static XkbKTMapEntryRec mapAlpha[]= {
44 { True, ShiftMask, { 1, ShiftMask, 0 } },
45 { True, LockMask, { 0, LockMask, 0 } }
48 static XkbModsRec preAlpha[]= {
50 { LockMask, LockMask, 0 }
53 #define NL_VMOD_MASK 0
54 static XkbKTMapEntryRec mapKeypad[]= {
55 { True, ShiftMask, { 1, ShiftMask, 0 } },
56 { False, 0, { 1, 0, NL_VMOD_MASK } }
59 static XkbKeyTypeRec canonicalTypes[XkbNumRequiredTypes] = {
66 { { ShiftMask, ShiftMask, 0 },
68 mapSize(map2Level), /* map_count */
72 { { ShiftMask|LockMask, ShiftMask|LockMask, 0 },
74 mapSize(mapAlpha), /* map_count */
78 { { ShiftMask, ShiftMask, NL_VMOD_MASK },
80 mapSize(mapKeypad), /* map_count */
87 XkbcInitCanonicalKeyTypes(XkbcDescPtr xkb, unsigned which, int keypadVMod)
90 XkbKeyTypePtr from,to;
96 rtrn= XkbcAllocClientMap(xkb, XkbKeyTypesMask, XkbNumRequiredTypes);
101 if ((which & XkbAllRequiredTypes) == 0)
105 from = canonicalTypes;
108 if (which & XkbOneLevelMask)
109 rtrn = XkbcCopyKeyType(&from[XkbOneLevelIndex], &to[XkbOneLevelIndex]);
111 if ((which & XkbTwoLevelMask) && (rtrn == Success))
112 rtrn = XkbcCopyKeyType(&from[XkbTwoLevelIndex], &to[XkbTwoLevelIndex]);
114 if ((which & XkbAlphabeticMask) && (rtrn == Success))
115 rtrn = XkbcCopyKeyType(&from[XkbAlphabeticIndex],
116 &to[XkbAlphabeticIndex]);
118 if ((which & XkbKeypadMask) && (rtrn == Success)) {
121 rtrn = XkbcCopyKeyType(&from[XkbKeypadIndex], &to[XkbKeypadIndex]);
122 type = &to[XkbKeypadIndex];
124 if ((keypadVMod >= 0) && (keypadVMod < XkbNumVirtualMods) &&
126 type->mods.vmods = (1 << keypadVMod);
127 type->map[0].active = True;
128 type->map[0].mods.mask = ShiftMask;
129 type->map[0].mods.real_mods = ShiftMask;
130 type->map[0].mods.vmods = 0;
131 type->map[0].level = 1;
132 type->map[1].active = False;
133 type->map[1].mods.mask = 0;
134 type->map[1].mods.real_mods = 0;
135 type->map[1].mods.vmods = (1 << keypadVMod);
136 type->map[1].level = 1;
144 XkbcVirtualModsToReal(XkbcDescPtr xkb, unsigned virtual_mask,
152 if (virtual_mask == 0) {
159 for (i = mask = 0, bit = 1; i < XkbNumVirtualMods; i++, bit <<= 1) {
160 if (virtual_mask & bit)
161 mask |= xkb->server->vmods[i];
169 * All latin-1 alphanumerics, plus parens, slash, minus, underscore and
172 static unsigned char componentSpecLegal[] = {
173 0x00, 0x00, 0x00, 0x00, 0x00, 0xa7, 0xff, 0x83,
174 0xfe, 0xff, 0xff, 0x87, 0xfe, 0xff, 0xff, 0x07,
175 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
176 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, 0x7f, 0xff
180 XkbcEnsureSafeMapName(char *name)
185 while (*name!='\0') {
186 if ((componentSpecLegal[(*name) / 8] & (1 << ((*name) % 8))) == 0)
193 _XkbcKSCheckCase(KeySym ks)
195 unsigned set = (ks & (~0xff)) >> 8;
199 case 0: /* latin 1 */
200 if ((ks >= XK_A && ks <= XK_Z) ||
201 (ks >= XK_Agrave && ks <= XK_THORN && ks != XK_multiply))
203 if ((ks >= XK_a && ks <= XK_z) ||
204 (ks >= XK_agrave && ks <= XK_ydiaeresis))
207 case 1: /* latin 2 */
208 if ((ks >= XK_Aogonek && ks <= XK_Zabovedot && ks != XK_breve) ||
209 (ks >= XK_Racute && ks<=XK_Tcedilla))
211 if ((ks >= XK_aogonek && ks <= XK_zabovedot && ks != XK_caron) ||
212 (ks >= XK_racute && ks <= XK_tcedilla))
215 case 2: /* latin 3 */
216 if ((ks >= XK_Hstroke && ks <= XK_Jcircumflex) ||
217 (ks >= XK_Cabovedot && ks <= XK_Scircumflex))
219 if ((ks >= XK_hstroke && ks <= XK_jcircumflex) ||
220 (ks >= XK_cabovedot && ks <= XK_scircumflex))
223 case 3: /* latin 4 */
224 if ((ks >= XK_Rcedilla && ks <= XK_Tslash) ||
226 (ks >= XK_Amacron && ks <= XK_Umacron))
228 if ((ks >= XK_rcedilla && ks <= XK_tslash) ||
230 (ks >= XK_amacron && ks <= XK_umacron))
233 case 18: /* latin 8 */
234 if ((ks == XK_Babovedot) ||
235 (ks >= XK_Dabovedot && ks <= XK_Wacute) ||
236 (ks >= XK_Ygrave && ks <= XK_Fabovedot) ||
237 (ks == XK_Mabovedot) ||
238 (ks == XK_Pabovedot) ||
239 (ks == XK_Sabovedot) ||
240 (ks == XK_Wdiaeresis) ||
241 (ks >= XK_Wcircumflex && ks <= XK_Ycircumflex))
243 if ((ks == XK_babovedot) ||
244 (ks == XK_dabovedot) ||
245 (ks == XK_fabovedot) ||
246 (ks == XK_mabovedot) ||
247 (ks >= XK_wgrave && ks <= XK_wacute) ||
249 (ks >= XK_wdiaeresis && ks <= XK_ycircumflex))
252 case 19: /* latin 9 */
253 if (ks == XK_OE || ks == XK_Ydiaeresis)
263 #define UNMATCHABLE(c) ((c) == '(' || (c) == ')' || (c) == '/')
266 XkbcNameMatchesPattern(char *name, char *ptrn)
268 while (ptrn[0] != '\0') {
269 if (name[0] == '\0') {
270 if (ptrn[0] == '*') {
277 if (ptrn[0] == '?') {
278 if (UNMATCHABLE(name[0]))
281 else if (ptrn[0] == '*') {
282 if (!UNMATCHABLE(name[0]) &&
283 XkbcNameMatchesPattern(name + 1, ptrn))
285 return XkbcNameMatchesPattern(name, ptrn + 1);
287 else if (ptrn[0] != name[0])
294 /* if we get here, the pattern is exhausted (-:just like me:-) */
295 return (name[0] == '\0');