]> git.sesse.net Git - rdpsrv/blob - Xserver/programs/Xserver/hw/vnc/kbdptr.c
Support RDP5 logon packets.
[rdpsrv] / Xserver / programs / Xserver / hw / vnc / kbdptr.c
1 /*
2  * kbdptr.c - deal with keyboard and pointer device over TCP & UDP.
3  *
4  *
5  */
6
7 /*
8  *  Copyright (C) 2002-2003 RealVNC Ltd.
9  *  Copyright (C) 1999 AT&T Laboratories Cambridge.  All Rights Reserved.
10  *
11  *  This is free software; you can redistribute it and/or modify
12  *  it under the terms of the GNU General Public License as published by
13  *  the Free Software Foundation; either version 2 of the License, or
14  *  (at your option) any later version.
15  *
16  *  This software is distributed in the hope that it will be useful,
17  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
18  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19  *  GNU General Public License for more details.
20  *
21  *  You should have received a copy of the GNU General Public License
22  *  along with this software; if not, write to the Free Software
23  *  Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307,
24  *  USA.
25  */
26
27 #include <stdio.h>
28
29 #include "X11/X.h"
30 #define NEED_EVENTS
31 #include "X11/Xproto.h"
32 #include "inputstr.h"
33 #define XK_CYRILLIC
34 #include <X11/keysym.h>
35 #include <mi.h>
36 #include <mipointer.h>
37 #include <property.h>
38 #include <Xatom.h>
39 #include "rfb.h"
40
41 extern WindowPtr *WindowTable; /* Why isn't this in a header file? */
42
43 #define KEY_IS_PRESSED(keycode) \
44     (kbdDevice->key->down[(keycode) >> 3] & (1 << ((keycode) & 7)))
45
46
47 static void XConvertCase(KeySym sym, KeySym *lower, KeySym *upper);
48
49 static DeviceIntPtr kbdDevice;
50
51 #define MIN_KEY_CODE            8
52 #define MAX_KEY_CODE            255
53 #define NO_OF_KEYS              (MAX_KEY_CODE - MIN_KEY_CODE + 1)
54 #define GLYPHS_PER_KEY          2
55
56 static KeySym kbdMap[] = {
57
58     /* Modifiers */
59
60     XK_Control_L,       NoSymbol,
61 #define CONTROL_L_KEY_CODE      MIN_KEY_CODE
62
63     XK_Control_R,       NoSymbol,
64 #define CONTROL_R_KEY_CODE      (MIN_KEY_CODE + 1)
65
66     XK_Shift_L,         NoSymbol,
67 #define SHIFT_L_KEY_CODE        (MIN_KEY_CODE + 2)
68
69     XK_Shift_R,         NoSymbol,
70 #define SHIFT_R_KEY_CODE        (MIN_KEY_CODE + 3)
71
72     XK_Meta_L,          NoSymbol,
73 #define META_L_KEY_CODE         (MIN_KEY_CODE + 4)
74
75     XK_Meta_R,          NoSymbol,
76 #define META_R_KEY_CODE         (MIN_KEY_CODE + 5)
77
78     XK_Alt_L,           NoSymbol,
79 #define ALT_L_KEY_CODE          (MIN_KEY_CODE + 6)
80
81     XK_Alt_R,           NoSymbol,
82 #define ALT_R_KEY_CODE          (MIN_KEY_CODE + 7)
83
84     /* Standard US keyboard */
85
86     XK_space,           NoSymbol,
87     XK_0,               XK_parenright,
88     XK_1,               XK_exclam,
89     XK_2,               XK_at,
90     XK_3,               XK_numbersign,
91     XK_4,               XK_dollar,
92     XK_5,               XK_percent,
93     XK_6,               XK_asciicircum,
94     XK_7,               XK_ampersand,
95     XK_8,               XK_asterisk,
96     XK_9,               XK_parenleft,
97
98     XK_minus,           XK_underscore,
99     XK_equal,           XK_plus,
100     XK_bracketleft,     XK_braceleft,
101     XK_bracketright,    XK_braceright,
102     XK_semicolon,       XK_colon,
103     XK_apostrophe,      XK_quotedbl,
104     XK_grave,           XK_asciitilde,
105     XK_comma,           XK_less,
106     XK_period,          XK_greater,
107     XK_slash,           XK_question,
108     XK_backslash,       XK_bar,
109
110     XK_a,               XK_A,
111     XK_b,               XK_B,
112     XK_c,               XK_C,
113     XK_d,               XK_D,
114     XK_e,               XK_E,
115     XK_f,               XK_F,
116     XK_g,               XK_G,
117     XK_h,               XK_H,
118     XK_i,               XK_I,
119     XK_j,               XK_J,
120     XK_k,               XK_K,
121     XK_l,               XK_L,
122     XK_m,               XK_M,
123     XK_n,               XK_N,
124     XK_o,               XK_O,
125     XK_p,               XK_P,
126     XK_q,               XK_Q,
127     XK_r,               XK_R,
128     XK_s,               XK_S,
129     XK_t,               XK_T,
130     XK_u,               XK_U,
131     XK_v,               XK_V,
132     XK_w,               XK_W,
133     XK_x,               XK_X,
134     XK_y,               XK_Y,
135     XK_z,               XK_Z,
136
137     /* Other useful keys */
138
139     XK_BackSpace,       NoSymbol,
140     XK_Return,          NoSymbol,
141     XK_Tab,             NoSymbol,
142     XK_Escape,          NoSymbol,
143     XK_Delete,          NoSymbol,
144
145     XK_Home,            NoSymbol,
146     XK_End,             NoSymbol,
147     XK_Page_Up,         NoSymbol,
148     XK_Page_Down,       NoSymbol,
149     XK_Up,              NoSymbol,
150     XK_Down,            NoSymbol,
151     XK_Left,            NoSymbol,
152     XK_Right,           NoSymbol,
153
154     XK_F1,              NoSymbol,
155     XK_F2,              NoSymbol,
156     XK_F3,              NoSymbol,
157     XK_F4,              NoSymbol,
158     XK_F5,              NoSymbol,
159     XK_F6,              NoSymbol,
160     XK_F7,              NoSymbol,
161     XK_F8,              NoSymbol,
162     XK_F9,              NoSymbol,
163     XK_F10,             NoSymbol,
164     XK_F11,             NoSymbol,
165     XK_F12,             NoSymbol,
166
167     /* Plus blank ones which can be filled in using xmodmap */
168
169 };
170
171 #define N_PREDEFINED_KEYS (sizeof(kbdMap) / (sizeof(KeySym) * GLYPHS_PER_KEY))
172
173
174 void
175 PtrDeviceInit()
176 {
177 }
178
179
180 void
181 KbdDeviceInit(pDevice, pKeySyms, pModMap)
182     DeviceIntPtr pDevice;
183     KeySymsPtr pKeySyms;
184     CARD8 *pModMap;
185 {
186     int i;
187
188     kbdDevice = pDevice;
189
190     for (i = 0; i < MAP_LENGTH; i++)
191         pModMap[i] = NoSymbol;
192
193     pModMap[CONTROL_L_KEY_CODE] = ControlMask;
194     pModMap[CONTROL_R_KEY_CODE] = ControlMask;
195     pModMap[SHIFT_L_KEY_CODE] = ShiftMask;
196     pModMap[SHIFT_R_KEY_CODE] = ShiftMask;
197     pModMap[META_L_KEY_CODE] = Mod1Mask;
198     pModMap[META_R_KEY_CODE] = Mod1Mask;
199     pModMap[ALT_L_KEY_CODE] = Mod1Mask;
200     pModMap[ALT_R_KEY_CODE] = Mod1Mask;
201
202     pKeySyms->minKeyCode = MIN_KEY_CODE;
203     pKeySyms->maxKeyCode = MAX_KEY_CODE;
204     pKeySyms->mapWidth = GLYPHS_PER_KEY;
205
206     pKeySyms->map = (KeySym *)xalloc(sizeof(KeySym)
207                                      * MAP_LENGTH * GLYPHS_PER_KEY);
208
209     if (!pKeySyms->map) {
210         rfbLog("xalloc failed\n");
211         exit(1);
212     }
213
214     for (i = 0; i < MAP_LENGTH * GLYPHS_PER_KEY; i++)
215         pKeySyms->map[i] = NoSymbol;
216
217     for (i = 0; i < N_PREDEFINED_KEYS * GLYPHS_PER_KEY; i++) {
218         pKeySyms->map[i] = kbdMap[i];
219     }
220 }
221
222
223
224 void
225 KbdDeviceOn()
226 {
227 }
228
229
230 void
231 KbdDeviceOff()
232 {
233 }
234
235
236 void
237 PtrDeviceOn(pDev)
238     DeviceIntPtr pDev;
239 {
240 }
241
242
243 void
244 PtrDeviceOff()
245 {
246 }
247
248
249 void
250 PtrDeviceControl(dev, ctrl)
251     DevicePtr dev;
252     PtrCtrl *ctrl;
253 {
254 }
255
256
257 void
258 KbdAddEvent(down, keySym, cl)
259     Bool down;
260     KeySym keySym;
261     rfbClientPtr cl;
262 {
263     xEvent ev, fake;
264     KeySymsPtr keySyms = &kbdDevice->key->curKeySyms;
265     int i;
266     int keyCode = 0;
267     int freeIndex = -1;
268     unsigned long time;
269     Bool fakeShiftPress = FALSE;
270     Bool fakeShiftLRelease = FALSE;
271     Bool fakeShiftRRelease = FALSE;
272     Bool shiftMustBeReleased = FALSE;
273     Bool shiftMustBePressed = FALSE;
274
275     if (cl) {
276         CARD32 clientId = cl->sock;
277         ChangeWindowProperty(WindowTable[0], VNC_LAST_CLIENT_ID, XA_INTEGER,
278                              32, PropModeReplace, 1, (pointer)&clientId, TRUE);
279     }
280
281     if (down) {
282         if (rfbTrace) rfbLog("KeyPress: 0x%x\n",keySym);
283         ev.u.u.type = KeyPress;
284     } else {
285         ev.u.u.type = KeyRelease;
286     }
287
288     /* First check if it's one of our predefined keys.  If so then we can make
289        some attempt at allowing an xmodmap inside a VNC desktop behave
290        something like you'd expect - e.g. if keys A & B are swapped over and
291        the VNC client sends an A, then map it to a B when generating the X
292        event.  We don't attempt to do this for keycodes which we make up on the
293        fly because it's too hard... */
294
295     for (i = 0; i < N_PREDEFINED_KEYS * GLYPHS_PER_KEY; i++) {
296         if (keySym == kbdMap[i]) {
297             keyCode = MIN_KEY_CODE + i / GLYPHS_PER_KEY;
298
299             if (kbdMap[(i/GLYPHS_PER_KEY) * GLYPHS_PER_KEY + 1] != NoSymbol) {
300
301                 /* this keycode has more than one symbol associated with it,
302                    so shift state is important */
303
304                 if ((i % GLYPHS_PER_KEY) == 0)
305                     shiftMustBeReleased = TRUE;
306                 else
307                     shiftMustBePressed = TRUE;
308             }
309             break;
310         }
311     }
312
313     if (!keyCode) {
314
315         /* not one of our predefined keys - see if it's in the current keyboard
316            mapping (i.e. we've already allocated an extra keycode for it) */
317
318         if (keySyms->mapWidth < 2) {
319             rfbLog("KbdAddEvent: Sanity check failed - Keyboard mapping has "
320                    "less than 2 keysyms per keycode (KeySym 0x%x)\n", keySym);
321             return;
322         }
323
324         for (i = 0; i < NO_OF_KEYS * keySyms->mapWidth; i++) {
325             if (keySym == keySyms->map[i]) {
326                 keyCode = MIN_KEY_CODE + i / keySyms->mapWidth;
327
328                 if (keySyms->map[(i / keySyms->mapWidth)
329                                         * keySyms->mapWidth + 1] != NoSymbol) {
330
331                     /* this keycode has more than one symbol associated with
332                        it, so shift state is important */
333
334                     if ((i % keySyms->mapWidth) == 0)
335                         shiftMustBeReleased = TRUE;
336                     else
337                         shiftMustBePressed = TRUE;
338                 }
339                 break;
340             }
341             if ((freeIndex == -1) && (keySyms->map[i] == NoSymbol)
342                 && (i % keySyms->mapWidth) == 0)
343             {
344                 freeIndex = i;
345             }
346         }
347     }
348
349     if (!keyCode) {
350         KeySym lower, upper;
351
352         /* we don't have an existing keycode - make one up on the fly and add
353            it to the keyboard mapping.  Thanks to Vlad Harchev for pointing
354            out problems with non-ascii capitalisation. */
355
356         if (freeIndex == -1) {
357             rfbLog("KbdAddEvent: ignoring KeySym 0x%x - no free KeyCodes\n",
358                    keySym);
359             return;
360         }
361
362         keyCode = MIN_KEY_CODE + freeIndex / keySyms->mapWidth;
363
364         XConvertCase(keySym, &lower, &upper);
365
366         if (lower == upper) {
367             keySyms->map[freeIndex] = keySym;
368
369         } else {
370             keySyms->map[freeIndex] = lower;
371             keySyms->map[freeIndex+1] = upper;
372
373             if (keySym == lower)
374                 shiftMustBeReleased = TRUE;
375             else
376                 shiftMustBePressed = TRUE;
377         }
378
379         SendMappingNotify(MappingKeyboard, keyCode, 1, serverClient);
380
381         rfbLog("KbdAddEvent: unknown KeySym 0x%x - allocating KeyCode %d\n",
382                keySym, keyCode);
383     }
384
385     time = GetTimeInMillis();
386
387     if (down) {
388         if (shiftMustBePressed && !(kbdDevice->key->state & ShiftMask)) {
389             fakeShiftPress = TRUE;
390             fake.u.u.type = KeyPress;
391             fake.u.u.detail = SHIFT_L_KEY_CODE;
392             fake.u.keyButtonPointer.time = time;
393             mieqEnqueue(&fake);
394         }
395         if (shiftMustBeReleased && (kbdDevice->key->state & ShiftMask)) {
396             if (KEY_IS_PRESSED(SHIFT_L_KEY_CODE)) {
397                 fakeShiftLRelease = TRUE;
398                 fake.u.u.type = KeyRelease;
399                 fake.u.u.detail = SHIFT_L_KEY_CODE;
400                 fake.u.keyButtonPointer.time = time;
401                 mieqEnqueue(&fake);
402             }
403             if (KEY_IS_PRESSED(SHIFT_R_KEY_CODE)) {
404                 fakeShiftRRelease = TRUE;
405                 fake.u.u.type = KeyRelease;
406                 fake.u.u.detail = SHIFT_R_KEY_CODE;
407                 fake.u.keyButtonPointer.time = time;
408                 mieqEnqueue(&fake);
409             }
410         }
411     }
412
413     ev.u.u.detail = keyCode;
414     ev.u.keyButtonPointer.time = time;
415     mieqEnqueue(&ev);
416
417     if (fakeShiftPress) {
418         fake.u.u.type = KeyRelease;
419         fake.u.u.detail = SHIFT_L_KEY_CODE;
420         fake.u.keyButtonPointer.time = time;
421         mieqEnqueue(&fake);
422     }
423     if (fakeShiftLRelease) {
424         fake.u.u.type = KeyPress;
425         fake.u.u.detail = SHIFT_L_KEY_CODE;
426         fake.u.keyButtonPointer.time = time;
427         mieqEnqueue(&fake);
428     }
429     if (fakeShiftRRelease) {
430         fake.u.u.type = KeyPress;
431         fake.u.u.detail = SHIFT_R_KEY_CODE;
432         fake.u.keyButtonPointer.time = time;
433         mieqEnqueue(&fake);
434     }
435 }
436
437 void
438 PtrAddEvent(buttonMask, x, y, cl)
439     int buttonMask;
440     int x;
441     int y;
442     rfbClientPtr cl;
443 {
444     xEvent ev;
445     int i;
446     unsigned long time;
447     static int oldButtonMask = 0;
448
449     if (cl) {
450         CARD32 clientId = cl->sock;
451         ChangeWindowProperty(WindowTable[0], VNC_LAST_CLIENT_ID, XA_INTEGER,
452                              32, PropModeReplace, 1, (pointer)&clientId, TRUE);
453     }
454
455     time = GetTimeInMillis();
456
457     miPointerAbsoluteCursor(x, y, time);
458
459     for (i = 0; i < 5; i++) {
460         if ((buttonMask ^ oldButtonMask) & (1<<i)) {
461             if (buttonMask & (1<<i)) {
462                 ev.u.u.type = ButtonPress;
463                 ev.u.u.detail = i + 1;
464                 ev.u.keyButtonPointer.time = time;
465                 mieqEnqueue(&ev);
466             } else {
467                 ev.u.u.type = ButtonRelease;
468                 ev.u.u.detail = i + 1;
469                 ev.u.keyButtonPointer.time = time;
470                 mieqEnqueue(&ev);
471             }
472         }
473     }
474
475     oldButtonMask = buttonMask;
476 }
477
478 void
479 KbdReleaseAllKeys()
480 {
481     int i, j;
482     xEvent ev;
483     unsigned long time = GetTimeInMillis();
484
485     for (i = 0; i < DOWN_LENGTH; i++) {
486         if (kbdDevice->key->down[i] != 0) {
487             for (j = 0; j < 8; j++) {
488                 if (kbdDevice->key->down[i] & (1 << j)) {
489                     ev.u.u.type = KeyRelease;
490                     ev.u.u.detail = (i << 3) | j;
491                     ev.u.keyButtonPointer.time = time;
492                     mieqEnqueue(&ev);
493                 }
494             }
495         }
496     }
497 }
498
499
500 /* copied from Xlib source */
501
502 static void XConvertCase(KeySym sym, KeySym *lower, KeySym *upper)
503 {
504     *lower = sym;
505     *upper = sym;
506     switch(sym >> 8) {
507     case 0: /* Latin 1 */
508         if ((sym >= XK_A) && (sym <= XK_Z))
509             *lower += (XK_a - XK_A);
510         else if ((sym >= XK_a) && (sym <= XK_z))
511             *upper -= (XK_a - XK_A);
512         else if ((sym >= XK_Agrave) && (sym <= XK_Odiaeresis))
513             *lower += (XK_agrave - XK_Agrave);
514         else if ((sym >= XK_agrave) && (sym <= XK_odiaeresis))
515             *upper -= (XK_agrave - XK_Agrave);
516         else if ((sym >= XK_Ooblique) && (sym <= XK_Thorn))
517             *lower += (XK_oslash - XK_Ooblique);
518         else if ((sym >= XK_oslash) && (sym <= XK_thorn))
519             *upper -= (XK_oslash - XK_Ooblique);
520         break;
521     case 1: /* Latin 2 */
522         /* Assume the KeySym is a legal value (ignore discontinuities) */
523         if (sym == XK_Aogonek)
524             *lower = XK_aogonek;
525         else if (sym >= XK_Lstroke && sym <= XK_Sacute)
526             *lower += (XK_lstroke - XK_Lstroke);
527         else if (sym >= XK_Scaron && sym <= XK_Zacute)
528             *lower += (XK_scaron - XK_Scaron);
529         else if (sym >= XK_Zcaron && sym <= XK_Zabovedot)
530             *lower += (XK_zcaron - XK_Zcaron);
531         else if (sym == XK_aogonek)
532             *upper = XK_Aogonek;
533         else if (sym >= XK_lstroke && sym <= XK_sacute)
534             *upper -= (XK_lstroke - XK_Lstroke);
535         else if (sym >= XK_scaron && sym <= XK_zacute)
536             *upper -= (XK_scaron - XK_Scaron);
537         else if (sym >= XK_zcaron && sym <= XK_zabovedot)
538             *upper -= (XK_zcaron - XK_Zcaron);
539         else if (sym >= XK_Racute && sym <= XK_Tcedilla)
540             *lower += (XK_racute - XK_Racute);
541         else if (sym >= XK_racute && sym <= XK_tcedilla)
542             *upper -= (XK_racute - XK_Racute);
543         break;
544     case 2: /* Latin 3 */
545         /* Assume the KeySym is a legal value (ignore discontinuities) */
546         if (sym >= XK_Hstroke && sym <= XK_Hcircumflex)
547             *lower += (XK_hstroke - XK_Hstroke);
548         else if (sym >= XK_Gbreve && sym <= XK_Jcircumflex)
549             *lower += (XK_gbreve - XK_Gbreve);
550         else if (sym >= XK_hstroke && sym <= XK_hcircumflex)
551             *upper -= (XK_hstroke - XK_Hstroke);
552         else if (sym >= XK_gbreve && sym <= XK_jcircumflex)
553             *upper -= (XK_gbreve - XK_Gbreve);
554         else if (sym >= XK_Cabovedot && sym <= XK_Scircumflex)
555             *lower += (XK_cabovedot - XK_Cabovedot);
556         else if (sym >= XK_cabovedot && sym <= XK_scircumflex)
557             *upper -= (XK_cabovedot - XK_Cabovedot);
558         break;
559     case 3: /* Latin 4 */
560         /* Assume the KeySym is a legal value (ignore discontinuities) */
561         if (sym >= XK_Rcedilla && sym <= XK_Tslash)
562             *lower += (XK_rcedilla - XK_Rcedilla);
563         else if (sym >= XK_rcedilla && sym <= XK_tslash)
564             *upper -= (XK_rcedilla - XK_Rcedilla);
565         else if (sym == XK_ENG)
566             *lower = XK_eng;
567         else if (sym == XK_eng)
568             *upper = XK_ENG;
569         else if (sym >= XK_Amacron && sym <= XK_Umacron)
570             *lower += (XK_amacron - XK_Amacron);
571         else if (sym >= XK_amacron && sym <= XK_umacron)
572             *upper -= (XK_amacron - XK_Amacron);
573         break;
574     case 6: /* Cyrillic */
575         /* Assume the KeySym is a legal value (ignore discontinuities) */
576         if (sym >= XK_Serbian_DJE && sym <= XK_Serbian_DZE)
577             *lower -= (XK_Serbian_DJE - XK_Serbian_dje);
578         else if (sym >= XK_Serbian_dje && sym <= XK_Serbian_dze)
579             *upper += (XK_Serbian_DJE - XK_Serbian_dje);
580         else if (sym >= XK_Cyrillic_YU && sym <= XK_Cyrillic_HARDSIGN)
581             *lower -= (XK_Cyrillic_YU - XK_Cyrillic_yu);
582         else if (sym >= XK_Cyrillic_yu && sym <= XK_Cyrillic_hardsign)
583             *upper += (XK_Cyrillic_YU - XK_Cyrillic_yu);
584         break;
585     case 7: /* Greek */
586         /* Assume the KeySym is a legal value (ignore discontinuities) */
587         if (sym >= XK_Greek_ALPHAaccent && sym <= XK_Greek_OMEGAaccent)
588             *lower += (XK_Greek_alphaaccent - XK_Greek_ALPHAaccent);
589         else if (sym >= XK_Greek_alphaaccent && sym <= XK_Greek_omegaaccent &&
590                  sym != XK_Greek_iotaaccentdieresis &&
591                  sym != XK_Greek_upsilonaccentdieresis)
592             *upper -= (XK_Greek_alphaaccent - XK_Greek_ALPHAaccent);
593         else if (sym >= XK_Greek_ALPHA && sym <= XK_Greek_OMEGA)
594             *lower += (XK_Greek_alpha - XK_Greek_ALPHA);
595         else if (sym >= XK_Greek_alpha && sym <= XK_Greek_omega &&
596                  sym != XK_Greek_finalsmallsigma)
597             *upper -= (XK_Greek_alpha - XK_Greek_ALPHA);
598         break;
599     }
600 }