From 478f4f6bf900517b4185d0fb948813af33a00bdf Mon Sep 17 00:00:00 2001 From: matt335672 <30179339+matt335672@users.noreply.github.com> Date: Wed, 12 Jun 2024 16:26:27 +0100 Subject: [PATCH] Move to evdev keycodes Uses the evdev X11 keycodes passed over from xrdp, so that these do not have to be mapped within xorgxrdp as well. --- xrdpkeyb/rdpKeyboard.c | 209 ++++++++++------------------------------- 1 file changed, 50 insertions(+), 159 deletions(-) diff --git a/xrdpkeyb/rdpKeyboard.c b/xrdpkeyb/rdpKeyboard.c index 4061b535..5c2ad9c2 100644 --- a/xrdpkeyb/rdpKeyboard.c +++ b/xrdpkeyb/rdpKeyboard.c @@ -79,10 +79,13 @@ xrdp keyboard module /* num lock */ #define NUM_LOCK_KEY_CODE 77 +// From /usr/share/X11/xkb/keycodes/evdev +#define EVDEV_PAUS_KEY_CODE 127 + #define N_PREDEFINED_KEYS \ (sizeof(g_kbdMap) / (sizeof(KeySym) * GLYPHS_PER_KEY)) -static char g_base_str[] = "base"; +static char g_rules_str[] = "evdev"; static char g_pc104_str[] = "pc104"; static char g_us_str[] = "us"; static char g_empty_str[] = ""; @@ -267,209 +270,97 @@ check_keysa(rdpKeyboard *keyboard) /** * @param down - true for KeyDown events, false otherwise - * @param param1 - ASCII code of pressed key + * @param param1 - X11 keycode of pressed key * @param param2 - * @param param3 - scancode of pressed key - * @param param4 - + * @param param4 - device flags ******************************************************************************/ static void KbdAddEvent(rdpKeyboard *keyboard, int down, int param1, int param2, int param3, int param4) { - int rdp_scancode; - int x_scancode; - int is_ext; - int is_spe; - int type; - - type = down ? KeyPress : KeyRelease; - rdp_scancode = param3; - is_ext = param4 & 256; /* 0x100 */ - is_spe = param4 & 512; /* 0x200 */ - x_scancode = 0; - - switch (rdp_scancode) + int x_keycode = param1; + int rdp_scancode = param3; + int is_spe = param4 & 512; /* 0x200 */ + int type = down ? KeyPress : KeyRelease; + + // Create an extended scancode where if the extended bit is set, + // the scancode is >= 0x100 + int ext_rdp_scancode = (param4 & 0x100) | rdp_scancode; + LLOGLN(0, ("KbdAddEvent: down=%d scancode=%09x keycode=%d flags%08x", down, ext_rdp_scancode, x_keycode, param4)); + switch (ext_rdp_scancode) { - case 58: /* caps lock */ - case 42: /* left shift */ - case 54: /* right shift */ - case 70: /* scroll lock */ - x_scancode = rdp_scancode + MIN_KEY_CODE; - - if (x_scancode > 0) - { - rdpEnqueueKey(keyboard->device, type, x_scancode); - } - - break; - - case 56: /* left - right alt button */ - - if (is_ext) - { - x_scancode = 113; /* right alt button */ - } - else - { - x_scancode = 64; /* left alt button */ - } - - rdpEnqueueKey(keyboard->device, type, x_scancode); - break; - - case 15: /* tab */ - + /* Non-repeating keys (except ctrl - see below) */ + case 0x02a: /* left shift */ + case 0x036: /* right shift */ + case 0x03a: /* caps lock */ + case 0x038: /* left alt */ + case 0x046: /* scroll lock */ + case 0x059: /* left meta */ + case 0x05a: /* right meta */ + case 0x138: /* right alt */ + case 0x15b: /* left win key */ + case 0x15c: /* right win key */ + case 0x15d: /* menu key */ + rdpEnqueueKey(keyboard->device, type, x_keycode); + break; + + case 0x00f: /* tab */ if (!down && !keyboard->tab_down) { - /* leave x_scancode 0 here, we don't want the tab key up */ + /* leave x_keycode 0 here, we don't want the tab key up */ check_keysa(keyboard); } else { - sendDownUpKeyEvent(keyboard->device, type, 23); + sendDownUpKeyEvent(keyboard->device, type, x_keycode); } keyboard->tab_down = down; break; - case 29: /* left or right ctrl */ + case 0x01d: /* left ctrl */ + case 0x11d: /* right ctrl */ - /* this is to handle special case with pause key sending control first */ + /* The pause key (0xE1 0x1D from the keyboard controller) + * is mapped to a combination of ctrl and numlock events - + * see [MS-RDPBCGR] 2.2.8.1.1.3.1.1.1 for details */ if (is_spe) { if (down) { keyboard->pause_spe = 1; - /* leave x_scancode 0 here, we don't want the control key down */ + /* leave x_keycode 0 here, we don't want the control key down */ } } else { - x_scancode = is_ext ? 109 : 37; - keyboard->ctrl_down = down ? x_scancode : 0; - rdpEnqueueKey(keyboard->device, type, x_scancode); + keyboard->ctrl_down = down ? x_keycode : 0; + rdpEnqueueKey(keyboard->device, type, x_keycode); } break; - case 69: /* Pause or Num Lock */ + + case 0x045: /* Pause or Num Lock */ if (keyboard->pause_spe) { - x_scancode = 110; + x_keycode = EVDEV_PAUS_KEY_CODE; if (!down) { keyboard->pause_spe = 0; } } - else - { - x_scancode = keyboard->ctrl_down ? 110 : 77; - } - - sendDownUpKeyEvent(keyboard->device, type, x_scancode); - break; - - case 28: /* Enter or Return */ - x_scancode = is_ext ? 108 : 36; - sendDownUpKeyEvent(keyboard->device, type, x_scancode); - break; - - case 53: /* / */ - x_scancode = is_ext ? 112 : 61; - sendDownUpKeyEvent(keyboard->device, type, x_scancode); - break; - - case 55: /* * on KP or Print Screen */ - x_scancode = is_ext ? 111 : 63; - sendDownUpKeyEvent(keyboard->device, type, x_scancode); - break; - - case 71: /* 7 or Home */ - x_scancode = is_ext ? 97 : 79; - sendDownUpKeyEvent(keyboard->device, type, x_scancode); - break; - case 72: /* 8 or Up */ - x_scancode = is_ext ? 98 : 80; - sendDownUpKeyEvent(keyboard->device, type, x_scancode); - break; - - case 73: /* 9 or PgUp */ - x_scancode = is_ext ? 99 : 81; - sendDownUpKeyEvent(keyboard->device, type, x_scancode); - break; - - case 75: /* 4 or Left */ - x_scancode = is_ext ? 100 : 83; - sendDownUpKeyEvent(keyboard->device, type, x_scancode); - break; - - case 77: /* 6 or Right */ - x_scancode = is_ext ? 102 : 85; - sendDownUpKeyEvent(keyboard->device, type, x_scancode); - break; - - case 79: /* 1 or End */ - x_scancode = is_ext ? 103 : 87; - sendDownUpKeyEvent(keyboard->device, type, x_scancode); - break; - - case 80: /* 2 or Down */ - x_scancode = is_ext ? 104 : 88; - sendDownUpKeyEvent(keyboard->device, type, x_scancode); - break; - - case 81: /* 3 or PgDn */ - x_scancode = is_ext ? 105 : 89; - sendDownUpKeyEvent(keyboard->device, type, x_scancode); - break; - - case 82: /* 0 or Insert */ - x_scancode = is_ext ? 106 : 90; - sendDownUpKeyEvent(keyboard->device, type, x_scancode); - break; - - case 83: /* . or Delete */ - x_scancode = is_ext ? 107 : 91; - sendDownUpKeyEvent(keyboard->device, type, x_scancode); - break; - - case 91: /* left win key */ - rdpEnqueueKey(keyboard->device, type, 115); - break; - - case 92: /* right win key */ - rdpEnqueueKey(keyboard->device, type, 116); - break; - - case 93: /* menu key */ - rdpEnqueueKey(keyboard->device, type, 117); - break; - - case 89: /* left meta */ - rdpEnqueueKey(keyboard->device, type, 156); - break; - - case 90: /* right meta */ - rdpEnqueueKey(keyboard->device, type, 156); - break; - - case 115: /* "/ ?" on br keyboard */ - sendDownUpKeyEvent(keyboard->device, type, 211); - break; - - case 126: /* . on br keypad */ - sendDownUpKeyEvent(keyboard->device, type, 134); + sendDownUpKeyEvent(keyboard->device, type, x_keycode); break; default: - x_scancode = rdp_scancode + MIN_KEY_CODE; - - if (x_scancode > 0) + if (x_keycode > 0) { - sendDownUpKeyEvent(keyboard->device, type, x_scancode); + sendDownUpKeyEvent(keyboard->device, type, x_keycode); } break; @@ -689,7 +580,7 @@ rdpkeybControl(DeviceIntPtr device, int what) case DEVICE_INIT: rdpkeybDeviceInit(device, &keySyms, modMap); memset(&set, 0, sizeof(set)); - set.rules = g_base_str; + set.rules = g_rules_str; set.model = g_pc104_str; set.layout = g_us_str; set.variant = g_empty_str; @@ -866,7 +757,7 @@ rdpLoadLayout(rdpKeyboard *keyboard, struct xrdp_client_info *client_info) LLOGLN(0, ("rdpLoadLayout: keylayout 0x%8.8x variant %s display %s", keylayout, client_info->variant, display)); memset(&set, 0, sizeof(set)); - set.rules = g_base_str; + set.rules = g_rules_str; set.model = g_pc104_str; set.layout = g_us_str;