3 # Patch managed by http://www.holgerschurig.de/patcher.html
6 --- qt-2.3.10-snapshot-20050131/src/kernel/qkeyboard_qws.cpp~kernel-keymap
7 +++ qt-2.3.10-snapshot-20050131/src/kernel/qkeyboard_qws.cpp
10 **********************************************************************/
12 +/****************************************************************************
14 +** Keyboard Handling Redesign
15 +** Copyright 2003, Chris Larson <kergoth@handhelds.org>
16 +** Copyright 2004,2005 Holger Hans Peter Frether <freyther@handhelds.org>
18 +** TODO: (key: . = in progress, x = completed)
20 +** [.] Tty driver should load its initial keymap from the kernel,
21 +** thereby ensuring keymap consistency between X, console, and qt/e
22 +** [x] Read kernel keymappings.
23 +** [x] Read kernel keycode -> unicode map.
24 +** [x] Use them, along with the existing keyM, to push events up.
25 +** [x] Create a new table, from transformed keycode -> qt keycode, rather
26 +** than the existing raw keycode -> qt keycode.
27 +** [ ] Adapt handleKey to deal with keys that have no unicode value, such as
28 +** keypresses that are mapped to strings in the string table. (e.g. F keys)
29 +** [x] Cursor orientation change based on display rotation should not
30 +** be bound to Ipaq or 5xxx, but instead as a runtime choice based
31 +** on whether or not we're using a Transformed display driver.
32 +** [.] Double check that VT handling, particularly with regard to switching,
33 +** is handled properly.
34 +** [ ] Add a generic means of dealing with additional (outside the realm of
35 +** ctrl, alt, shift, altgr) modifiers. Also ensure a means of binding
36 +** a keypress/combination to a 'lock' of said additional modifiers.
40 +** [ ] Fix NumLock handling
41 +** [ ] Fix Keypad handling
42 +** [ ] Fix LED handling (LED_NUM and LED_CAP) don't seem to work
43 +** [ ] Fix CTRL+ALT+H (somehow takes the function of CTRL+ALT+BACKSPACE)
45 +**********************************************************************/
48 #include "qwindowsystem_qws.h"
49 #include "qwsutils_qws.h"
56 -#include <linux/kd.h>
58 +#include <sys/wait.h>
59 #include <sys/ioctl.h>
60 #include <sys/types.h>
67 +#include <linux/kd.h>
68 +#include <linux/keyboard.h>
72 #include <qcopchannel_qws.h>
78 -#include <asm/sharp_char.h>
81 -#if defined(QT_QWS_IPAQ) || defined(QT_QWS_SL5XXX)
82 -#define QT_QWS_AUTOREPEAT_MANUALLY
87 -#if defined(QT_QWS_IPAQ) || defined(QT_QWS_SL5XXX)
88 static int dir_keyrot = -1;
90 static int xform_dirkey(int key)
92 int xf = qt_screen->transformOrientation() + dir_keyrot;
93 return (key-Qt::Key_Left+xf)%4+Qt::Key_Left;
97 #define VTSWITCHSIG SIGUSR2
100 { Qt::Key_F35, 0xffff , 0xffff , 0xffff }, // 21 light
101 { Qt::Key_Escape, 0xffff , 0xffff , 0xffff }, // 22
103 +#ifdef QT_QWS_SL6000
104 // Direction key code are for *UNROTATED* display.
105 - { Qt::Key_Up, 0xffff , 0xffff , 0xffff }, // 23
106 - { Qt::Key_Right, 0xffff , 0xffff , 0xffff }, // 24
107 - { Qt::Key_Left, 0xffff , 0xffff , 0xffff }, // 25
108 - { Qt::Key_Down, 0xffff , 0xffff , 0xffff }, // 26
109 + { Qt::Key_Left, 0xffff , 0xffff , 0xffff }, // 23
110 + { Qt::Key_Up, 0xffff , 0xffff , 0xffff }, // 24
111 + { Qt::Key_Down, 0xffff , 0xffff , 0xffff }, // 25
112 + { Qt::Key_Right, 0xffff , 0xffff , 0xffff }, // 26
114 + // Direction key code are for *UNROTATED* display.
115 + { Qt::Key_Up, 0xffff , 0xffff , 0xffff }, // 23
116 + { Qt::Key_Right, 0xffff , 0xffff , 0xffff }, // 24
117 + { Qt::Key_Left, 0xffff , 0xffff , 0xffff }, // 25
118 + { Qt::Key_Down, 0xffff , 0xffff , 0xffff }, // 26
121 { Qt::Key_F33, 0xffff , 0xffff , 0xffff }, // 27 OK
122 { Qt::Key_F12, 0xffff , 0xffff , 0xffff }, // 28 40 home
124 { Qt::Key_unknown, 0xffff , 0xffff , 0xffff }, // 63
125 { Qt::Key_unknown, 0xffff , 0xffff , 0xffff }, // 64
126 { Qt::Key_unknown, 0xffff , 0xffff , 0xffff }, // 65
127 - { Qt::Key_unknown, 0xffff , 0xffff , 0xffff }, // 66
128 + { Qt::Key_F14, 0xffff , 0xffff , 0xffff }, // 66
129 { Qt::Key_Meta, 0xffff , 0xffff , 0xffff }, // 67
130 { Qt::Key_unknown, 0xffff , 0xffff , 0xffff }, // 68
131 { Qt::Key_unknown, 0xffff , 0xffff , 0xffff }, // 69
132 @@ -649,12 +684,61 @@
134 QWSTtyKeyboardHandler(const QString&);
135 virtual ~QWSTtyKeyboardHandler();
136 + void readKeyboardMap();
137 + void readUnicodeMap();
138 + void handleKey(unsigned char code);
141 void readKeyboardData();
144 + void modifyModifier( int map, int modify, bool release );
145 + void modifyLock( unsigned int lock, bool release );
146 + void handleExtra( unsigned int key, bool release );
147 + static void restoreLeds();
148 + static void toggleLed(unsigned int);
149 + int map_to_modif ();
152 struct termios origTermData;
153 + unsigned short acm[E_TABSZ];
156 + Key_AltGr = 0x01ffff,
157 + Key_Console1 = 0x02ffff,
158 + Key_Console2 = 0x03ffff,
159 + Key_Console3 = 0x04ffff,
160 + Key_Console4 = 0x05ffff,
161 + Key_Console5 = 0x06ffff,
162 + Key_Console6 = 0x07ffff,
163 + Key_Console7 = 0x08ffff,
164 + Key_Console8 = 0x09ffff,
165 + Key_Console9 = 0x0affff,
166 + Key_Console10 = 0x0bffff,
167 + Key_Console11 = 0x0cffff,
168 + Key_Console12 = 0x0dffff,
169 + Key_NumLock = 0x0effff,
170 + Key_ShiftLock = 0x0fffff,
171 + Key_CtrlLock = 0x10ffff,
172 + Key_AltLock = 0x11ffff,
173 + Key_AltGrLock = 0x12ffff
176 + KeyMap( Qt::Key _key = Qt::Key_unknown, unsigned short _code = 0 )
177 + : key( _key ), code( _code )
179 + KeyMap( ExtraKey _key, unsigned short _code )
180 + : key( _key ), code( _code )
182 + unsigned int key; // 16 Bit
183 + unsigned short code;
186 + KeyMap kernel_map[(1<<KG_CAPSSHIFT)][NR_KEYS];
199 sharp_kbdctl_modifstat st;
200 int dev = ::open("/dev/sharp_kbdctl", O_RDWR);
207 #if defined(QT_QWS_IPAQ)
208 // iPAQ Action Key has ScanCode 0x60: 0x60|0x80 = 0xe0 == extended mode 1 !
209 ipaq_return_pressed = FALSE;
212 } else if ( extended == 2 ) {
218 keyCode = Qt::Key_Pause;
219 @@ -1199,7 +1285,7 @@
226 unicode = currentKey->ctrl_unicode;
228 @@ -1244,9 +1330,12 @@
232 +#include "keyboard_linux_to_qt.h"
234 QWSTtyKeyboardHandler::QWSTtyKeyboardHandler(const QString& device)
235 + : current_map(0), modifier( 0 ), numlock( false ), capslock( false )
238 kbdFD=open(device.isEmpty() ? "/dev/tty0" : device.latin1(), O_RDWR | O_NDELAY, 0);
241 @@ -1262,11 +1351,7 @@
242 tcgetattr( kbdFD, &termdata );
244 #if !defined(_OS_FREEBSD_) && !defined(_OS_SOLARIS_)
245 -# ifdef QT_QWS_USE_KEYCODES
246 - ioctl(kbdFD, KDSKBMODE, K_MEDIUMRAW);
248 - ioctl(kbdFD, KDSKBMODE, K_RAW);
250 + ioctl(kbdFD, KDSKBMODE, K_MEDIUMRAW);
253 termdata.c_iflag = (IGNPAR | IGNBRK) & (~PARMRK) & (~ISTRIP);
254 @@ -1279,6 +1364,9 @@
255 cfsetospeed(&termdata, 9600);
256 tcsetattr(kbdFD, TCSANOW, &termdata);
261 signal(VTSWITCHSIG, vtSwitchHandler);
263 #if !defined(_OS_FREEBSD_) && !defined(_OS_SOLARIS_)
264 @@ -1300,6 +1388,7 @@
266 QWSTtyKeyboardHandler::~QWSTtyKeyboardHandler()
272 @@ -1328,13 +1417,451 @@
276 +void QWSTtyKeyboardHandler::readUnicodeMap()
280 + if (ioctl(kbdFD,GIO_UNISCRNMAP,acm) != 0)
285 +void QWSTtyKeyboardHandler::readKeyboardMap()
287 + struct kbentry kbe;
291 + for (int map = 0; map < (1<<KG_CAPSSHIFT); ++map) {
292 + unsigned short kval;
293 + kbe.kb_table = map;
295 + for (int key = 0; key < NR_KEYS; ++key) {
296 + kbe.kb_index = key;
298 + if (ioctl(kbdFD, KDGKBENT, &kbe) != 0)
301 + if ((kbe.kb_value == K_HOLE) || (kbe.kb_value == K_NOSUCHMAP))
304 + kval = KVAL(kbe.kb_value);
305 + switch (KTYP(kbe.kb_value)) {
307 + * Map asciis and letters to Qt KeyCodes
308 + * via the map (0-255)
312 + kernel_map[map][key] = KeyMap( linux_to_qt[kval], kval );
316 + * Handle the F Keys and map them
321 + kernel_map[map][key] = KeyMap( static_cast<Qt::Key>( Qt::Key_F1 + kval ), kval );
322 + else if ( kval >= 31 && kval <= 33)
323 + kernel_map[map][key] = KeyMap( static_cast<Qt::Key>( Qt::Key_F21 + kval ), kval );
324 + else if ( kval >= 34 && kval <= 45 ) {
326 + kernel_map[map][key] = KeyMap(static_cast<KeyMap::ExtraKey>( KeyMap::Key_Console1+off ), kval );
328 + switch(kbe.kb_value ) {
330 + kernel_map[map][key] = KeyMap( Qt::Key_Insert, kval );
333 + kernel_map[map][key] = KeyMap( Qt::Key_Delete, kval ); // right?
336 + kernel_map[map][key] = KeyMap( Qt::Key_End , kval );
339 + kernel_map[map][key] = KeyMap( Qt::Key_Prior, kval );
342 + kernel_map[map][key] = KeyMap( Qt::Key_Next, kval );
345 + kernel_map[map][key] = KeyMap( Qt::Key_Menu, kval );
348 + kernel_map[map][key] = KeyMap( Qt::Key_Help, kval );
351 + kernel_map[map][key] = KeyMap( Qt::Key_Pause, kval );
356 + kernel_map[map][key] = KeyMap( Qt::Key_unknown, kval );
362 + switch ( kbe.kb_value ) {
364 + kernel_map[map][key] = KeyMap( Qt::Key_Enter, kval );
367 + kernel_map[map][key] = KeyMap( Qt::Key_CapsLock, kval );
370 + kernel_map[map][key] = KeyMap( Qt::Key_NumLock, kval );
373 + kernel_map[map][key] = KeyMap( Qt::Key_ScrollLock, kval );
387 + case K_DECRCONSOLE:
388 + case K_INCRCONSOLE:
389 + case K_SPAWNCONSOLE:
390 + case K_BARENUMLOCK:
392 + kernel_map[map][key] = KeyMap( Qt::Key_unknown, kval );
398 + * Number Values might be wrong
400 + switch(kbe.kb_value ) {
402 + kernel_map[map][key] = KeyMap( Qt::Key_0, kval );
405 + kernel_map[map][key] = KeyMap( Qt::Key_1, kval );
408 + kernel_map[map][key] = KeyMap( Qt::Key_2, kval );
411 + kernel_map[map][key] = KeyMap( Qt::Key_3, kval );
414 + kernel_map[map][key] = KeyMap( Qt::Key_4, kval );
417 + kernel_map[map][key] = KeyMap( Qt::Key_5, kval );
420 + kernel_map[map][key] = KeyMap( Qt::Key_6, kval );
423 + kernel_map[map][key] = KeyMap( Qt::Key_7, kval );
426 + kernel_map[map][key] = KeyMap( Qt::Key_8, kval );
429 + kernel_map[map][key] = KeyMap( Qt::Key_9, kval );
432 + kernel_map[map][key] = KeyMap( Qt::Key_Plus, kval );
435 + kernel_map[map][key] = KeyMap( Qt::Key_Minus, kval );
438 + kernel_map[map][key] = KeyMap( Qt::Key_multiply, kval );
441 + kernel_map[map][key] = KeyMap( Qt::Key_division, kval );
444 + kernel_map[map][key] = KeyMap( Qt::Key_Enter, kval );
447 + kernel_map[map][key] = KeyMap( Qt::Key_Comma, kval ) ;
450 + kernel_map[map][key] = KeyMap( Qt::Key_plusminus, kval );
454 + kernel_map[map][key] = KeyMap( Qt::Key_ParenLeft, kval );
457 + kernel_map[map][key] = KeyMap( Qt::Key_ParenRight, kval );
460 + kernel_map[map][key] = KeyMap( Qt::Key_unknown, kval );
465 + switch(kbe.kb_value ) {
473 + kernel_map[map][key] = KeyMap( Qt::Key_unknown, kval );
479 + kernel_map[map][key] = KeyMap( Qt::Key_unknown, kval );
483 + switch(kbe.kb_value ) {
485 + kernel_map[map][key] = KeyMap( Qt::Key_Down, kval );
488 + kernel_map[map][key] = KeyMap( Qt::Key_Left, kval );
491 + kernel_map[map][key] = KeyMap( Qt::Key_Right, kval );
494 + kernel_map[map][key] = KeyMap( Qt::Key_Up, kval );
500 + switch( kbe.kb_value ) {
502 + kernel_map[map][key] = KeyMap( Qt::Key_Shift, kval );
505 + kernel_map[map][key] = KeyMap( Qt::Key_Alt, kval );
508 + kernel_map[map][key] = KeyMap( Qt::Key_Control, kval );
511 + kernel_map[map][key] = KeyMap( KeyMap::Key_AltGr, kval );
519 + kernel_map[map][key] = KeyMap( Qt::Key_unknown, kval );
524 + * What is this for?
530 + kernel_map[map][key] = KeyMap( Qt::Key_unknown, kval );
531 + //qWarning("keycode %d, map %d, type %d, val %d, acm %c\n", key, map, KTYP(kbe.kb_value), kval, acm[kval]);
537 +int QWSTtyKeyboardHandler::map_to_modif()
541 + if (current_map & (1<<KG_ALT))
542 + modifiers |= Qt::AltButton;
543 + else if (current_map & (1<<KG_CTRL))
544 + modifiers |= Qt::ControlButton;
545 + else if (current_map & (1<<KG_SHIFT))
546 + modifiers |= Qt::ShiftButton;
552 + * Handle Extra Keys for VT switching and Quitting
554 +void QWSTtyKeyboardHandler::handleExtra( unsigned int key, bool release ) {
557 + if ( (modifier & (1<<KG_ALT)) && (modifier & (1<<KG_CTRL)) ) {
558 + if ( key == Qt::Key_Left )
559 + term = QMAX(vtQws -1, 1 );
560 + else if ( key == Qt::Key_Right )
561 + term = QMIN(vtQws +1, 12 );
564 + if ( key >= KeyMap::Key_Console1 && key <= KeyMap::Key_Console12 )
565 + term = key - KeyMap::Key_Console1 + 1;
568 + current_map = modifier = 0;
569 + numlock = capslock = false;
570 + ioctl(kbdFD, VT_ACTIVATE, term );
575 + if ( (modifier & (1<<KG_ALT)) && (modifier & (1<<KG_CTRL) ) )
576 + if ( key == Qt::Key_Delete || key == Qt::Key_Backspace ) {
577 + qWarning( "Instructed to quit on %d", key );
585 +void QWSTtyKeyboardHandler::modifyModifier( int map, int modify, bool release ) {
588 + current_map &= ~map;
590 + current_map |= map;
593 + if ( modify != -1 ) {
595 + modifier &= ~modify;
597 + modifier |= modify;
601 +void QWSTtyKeyboardHandler::handleKey(unsigned char code)
603 + int old_modifier = modifier;
604 + bool release = false;
605 + bool mod_key = true;
613 + KeyMap key_map = kernel_map[current_map][code];
614 + unsigned short unicode = acm[key_map.code];
615 + unsigned int qtKeyCode = key_map.key;
618 + qWarning( "KeyCode: %d KVAL: %d", qtKeyCode, key_map.code );
619 +// qWarning( "Alt:%d Ctrl:%d Shift:%d Key = %d", modifier & (1<<KG_ALT),
620 +// modifier & (1<<KG_CTRL),
621 +// modifier & (1<<KG_SHIFT), key_map.key );
622 +// qDebug("code %d, mCode %d, uni '%c', qtKeyCode %d", code, map.code,
623 +// QChar(unicode ).isPrint() ?
624 +// unicode : '?' , qtKeyCode);
626 + // Handle map changes based on press/release of modifiers
627 + // hardcoded for now
635 + modif = (1<<KG_ALT);
637 + case Qt::Key_Control:
638 + modif = (1<<KG_CTRL);
641 + case Qt::Key_Shift:
642 + modif = (1<<KG_SHIFT);
645 + case KeyMap::Key_AltGr:
646 + map = (1<<KG_ALTGR );
649 + case Qt::Key_Right:
653 + if (qt_screen->isTransformed())
654 + qtKeyCode = static_cast<Qt::Key>( xform_dirkey(static_cast<int>( qtKeyCode ) ) );
657 + * handle lock, we don't handle scroll lock!
659 + case Qt::Key_CapsLock:
660 + case Qt::Key_NumLock:
669 + * Change the Map. We handle locks a bit different
672 + modifyLock( qtKeyCode, release );
674 + modifyModifier( map, modif, release );
676 + handleExtra( qtKeyCode, release );
679 + * do not repeat modifier keys
681 + if ( modifier == old_modifier && mod_key )
684 + processKeyEvent(unicode & 0xff, qtKeyCode, map_to_modif(), !release, 0);
687 void QWSTtyKeyboardHandler::readKeyboardData()
689 unsigned char buf[81];
690 int n = ::read(kbdFD, buf, 80 );
691 for ( int loop = 0; loop < n; loop++ )
693 + handleKey(buf[loop]);
696 +void QWSTtyKeyboardHandler::modifyLock( unsigned int lock, bool release ) {
700 + if ( lock == Qt::Key_CapsLock ) {
701 + toggleLed( LED_CAP );
702 + capslock = !capslock;
703 + }else if ( lock == Qt::Key_NumLock ) {
704 + toggleLed( LED_NUM );
705 + numlock = !numlock;
709 +void QWSTtyKeyboardHandler::restoreLeds() {
711 + ioctl(kbdFD, KDGETLED, &leds );
714 + ioctl(kbdFD, KDSETLED, &leds );
717 +void QWSTtyKeyboardHandler::toggleLed(unsigned int led) {
719 + int ret = ioctl(kbdFD, KDGETLED, &leds );
720 + leds = leds & led ? (leds & ~led) : (leds | led);
721 + ret = ioctl(kbdFD, KDSETLED, &leds );
725 @@ -1439,13 +1966,13 @@
728 // custom scan codes - translate them and create a key event immediately
729 - if( overrideMap && event.value == 0 || overrideMap->find( event.value ) )
730 + if( overrideMap && event.value == 0 || overrideMap->find( event.value ) )
735 QWSServer::KeyMap *km = overrideMap->find( event.value );
736 - switch( km->unicode )
737 + switch( km->unicode )
741 @@ -1473,14 +2000,14 @@
746 - else if( lastPress )
748 + else if( lastPress )
750 - processKeyEvent( lastPress->unicode, lastPress->key_code, 0,
751 + processKeyEvent( lastPress->unicode, lastPress->key_code, 0,
760 @@ -1845,10 +2372,10 @@
761 handler = new QWSUsbKeyboardHandler(device);
762 } else if ( type == "TTY" ) {
763 handler = new QWSTtyKeyboardHandler(device);
766 else if( type == "Samsung" ) {
767 handler = new QWSSamsungKeypadHandler(device);
771 qWarning( "Keyboard type %s:%s unsupported", spec.latin1(), device.latin1() );
774 +++ qt-2.3.10-snapshot-20050131/src/kernel/keyboard_linux_to_qt.h
777 + * Generated with a small python utility found at
778 + * http://handhelds.org/~zecke/downloads/python_keytable_creator.py
781 +static const Qt::Key linux_to_qt[] = {
792 +Qt::Key_unknown, // LineFeed
796 +Qt::Key_unknown, // No Symbol
803 +Qt::Key_unknown, // No Symbol
811 +Qt::Key_unknown, // No symbol
873 +Qt::Key_BracketLeft,
875 +Qt::Key_BracketRight,
876 +Qt::Key_AsciiCircum,
878 +Qt::Key_QuoteLeft, // grave
942 +Qt::Key_nobreakspace,
952 +Qt::Key_ordfeminine,
953 +Qt::Key_guillemotleft,
960 +Qt::Key_twosuperior,
961 +Qt::Key_threesuperior,
965 +Qt::Key_periodcentered,
967 +Qt::Key_onesuperior,
969 +Qt::Key_guillemotright,
972 +Qt::Key_threequarters,
973 +Qt::Key_questiondown,
976 +Qt::Key_Acircumflex,
984 +Qt::Key_Ecircumflex,
988 +Qt::Key_Icircumflex,
994 +Qt::Key_Ocircumflex,
1001 +Qt::Key_Ucircumflex,
1002 +Qt::Key_Udiaeresis,
1008 +Qt::Key_acircumflex,
1010 +Qt::Key_adiaeresis,
1016 +Qt::Key_ecircumflex,
1017 +Qt::Key_ediaeresis,
1020 +Qt::Key_icircumflex,
1021 +Qt::Key_idiaeresis,
1026 +Qt::Key_ocircumflex,
1028 +Qt::Key_odiaeresis,
1033 +Qt::Key_ucircumflex,
1034 +Qt::Key_udiaeresis,