diff options
Diffstat (limited to 'drivers/char/keyboard.c')
-rw-r--r-- | drivers/char/keyboard.c | 19 |
1 files changed, 14 insertions, 5 deletions
diff --git a/drivers/char/keyboard.c b/drivers/char/keyboard.c index 3ef7bf1a6..c25f24bc4 100644 --- a/drivers/char/keyboard.c +++ b/drivers/char/keyboard.c @@ -64,7 +64,7 @@ EXPORT_SYMBOL(handle_scancode); extern void ctrl_alt_del(void); -struct wait_queue * keypress_wait = NULL; +DECLARE_WAIT_QUEUE_HEAD(keypress_wait); struct console; int keyboard_wait_for_keypress(struct console *co) @@ -247,9 +247,10 @@ void handle_scancode(unsigned char scancode, int down) sysrq_pressed = !up_flag; return; } else if (sysrq_pressed) { - if (!up_flag) + if (!up_flag) { handle_sysrq(kbd_sysrq_xlate[keycode], kbd_pt_regs, kbd, tty); - return; + return; + } } #endif @@ -279,7 +280,8 @@ void handle_scancode(unsigned char scancode, int down) u_char type; /* the XOR below used to be an OR */ - int shift_final = shift_state ^ kbd->lockstate ^ kbd->slockstate; + int shift_final = (shift_state | kbd->slockstate) ^ + kbd->lockstate; ushort *key_map = key_maps[shift_final]; if (key_map != NULL) { @@ -311,6 +313,7 @@ void handle_scancode(unsigned char scancode, int down) /* we have at least to update shift_state */ #if 1 /* how? two almost equivalent choices follow */ compute_shiftstate(); + kbd->slockstate = 0; /* play it safe */ #else keysym = U(plain_map[keycode]); type = KTYP(keysym); @@ -757,7 +760,7 @@ void compute_shiftstate(void) for(j=0; j<BITS_PER_LONG; j++,k++) if(test_bit(k, key_down)) { sym = U(plain_map[k]); - if(KTYP(sym) == KT_SHIFT) { + if(KTYP(sym) == KT_SHIFT || KTYP(sym) == KT_SLOCK) { val = KVAL(sym); if (val == KVAL(K_CAPSSHIFT)) val = KVAL(K_SHIFT); @@ -809,9 +812,15 @@ static void do_lock(unsigned char value, char up_flag) static void do_slock(unsigned char value, char up_flag) { + do_shift(value,up_flag); if (up_flag || rep) return; chg_vc_kbd_slock(kbd, value); + /* try to make Alt, oops, AltGr and such work */ + if (!key_maps[kbd->lockstate ^ kbd->slockstate]) { + kbd->slockstate = 0; + chg_vc_kbd_slock(kbd, value); + } } /* |