Subversion Repositories Kolibri OS

Rev

Rev 2434 | Rev 3555 | Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | Download | RSS feed

  1. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  2. ;;                                                              ;;
  3. ;; Copyright (C) KolibriOS team 2004-2011. All rights reserved. ;;
  4. ;; Copyright (C) MenuetOS 2000-2004 Ville Mikael Turjanmaa      ;;
  5. ;; Distributed under terms of the GNU General Public License    ;;
  6. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  7.  
  8. $Revision: 2987 $
  9.  
  10.  
  11. VKEY_LSHIFT   = 0000000000000001b
  12. VKEY_RSHIFT   = 0000000000000010b
  13. VKEY_LCONTROL = 0000000000000100b
  14. VKEY_RCONTROL = 0000000000001000b
  15. VKEY_LALT     = 0000000000010000b
  16. VKEY_RALT     = 0000000000100000b
  17. VKEY_CAPSLOCK = 0000000001000000b
  18. VKEY_NUMLOCK  = 0000000010000000b
  19. VKEY_SCRLOCK  = 0000000100000000b
  20.  
  21. VKEY_SHIFT    = 0000000000000011b
  22. VKEY_CONTROL  = 0000000000001100b
  23. VKEY_ALT      = 0000000000110000b
  24.  
  25. uglobal
  26.   align 4
  27.   kb_state      dd 0
  28.   ext_code      db 0
  29.  
  30.   keyboard_mode db 0
  31.   keyboard_data db 0
  32.  
  33.   altmouseb     db 0
  34.   ctrl_alt_del  db 0
  35.  
  36.   kb_lights     db 0
  37.   old_kb_lights db 0
  38.  
  39. align 4
  40.         hotkey_scancodes        rd      256     ; we have 256 scancodes
  41.         hotkey_list             rd      256*4   ; max 256 defined hotkeys
  42.         hotkey_buffer           rd      120*2   ; buffer for 120 hotkeys
  43. endg
  44.  
  45. iglobal
  46. hotkey_tests    dd      hotkey_test0
  47.                 dd      hotkey_test1
  48.                 dd      hotkey_test2
  49.                 dd      hotkey_test3
  50.                 dd      hotkey_test4
  51. hotkey_tests_num = 5
  52. endg
  53. ;---------------------------------------------------------------------
  54. hotkey_test0:
  55.         test    al, al
  56.         setz    al
  57.         ret
  58. ;---------------------------------------------------------------------
  59. hotkey_test1:
  60.         test    al, al
  61.         setnp   al
  62.         ret
  63. ;---------------------------------------------------------------------
  64. hotkey_test2:
  65.         cmp     al, 3
  66.         setz    al
  67.         ret
  68. ;---------------------------------------------------------------------
  69. hotkey_test3:
  70.         cmp     al, 1
  71.         setz    al
  72.         ret
  73. ;---------------------------------------------------------------------
  74. hotkey_test4:
  75.         cmp     al, 2
  76.         setz    al
  77.         ret
  78. ;---------------------------------------------------------------------
  79. hotkey_do_test:
  80.         push    eax
  81.         mov     edx, [kb_state]
  82.         shr     edx, cl
  83.         add     cl, cl
  84.         mov     eax, [eax+4]
  85.         shr     eax, cl
  86.         and     eax, 15
  87.         cmp     al, hotkey_tests_num
  88.         jae     .fail
  89.        
  90.         xchg    eax, edx
  91.         and     al, 3
  92.         call    [hotkey_tests + edx*4]
  93.         cmp     al, 1
  94.         pop     eax
  95.         ret
  96. ;--------------------------------------
  97. .fail:
  98.         stc
  99.         pop     eax
  100.         ret
  101. ;---------------------------------------------------------------------
  102. align 4
  103. set_keyboard_data:
  104.         movzx   eax, word[TASK_COUNT]; top window process
  105.         movzx   eax, word[WIN_POS+eax*2]
  106.         shl     eax, 8
  107.         mov     al, [SLOT_BASE+eax+APPDATA.keyboard_mode]
  108.         mov     [keyboard_mode], al
  109.        
  110.         mov     eax, ecx
  111.        
  112.         push    ebx esi edi ebp
  113.         call    send_scancode
  114.         pop     ebp edi esi ebx
  115.         ret
  116. ;---------------------------------------------------------------------
  117. struct KEYBOARD
  118. next           dd      ?
  119. prev           dd      ?
  120. functions      dd      ?
  121. userdata       dd      ?
  122. ends
  123. struct KBDFUNC
  124. strucsize      dd      ?
  125. close          dd      ?
  126. setlights      dd      ?
  127. ends
  128.  
  129. iglobal
  130. keyboards:
  131.         dd      keyboards
  132.         dd      keyboards
  133. endg
  134. uglobal
  135. keyboard_list_mutex     MUTEX
  136. endg
  137.  
  138. register_keyboard:
  139.         push    ebx
  140.         push    sizeof.KEYBOARD
  141.         pop     eax
  142.         call    malloc
  143.         test    eax, eax
  144.         jz      .nothing
  145.         mov     ecx, [esp+4+4]
  146.         mov     [eax+KEYBOARD.functions], ecx
  147.         mov     ecx, [esp+8+4]
  148.         mov     [eax+KEYBOARD.userdata], ecx
  149.         xchg    eax, ebx
  150.         mov     ecx, keyboard_list_mutex
  151.         call    mutex_lock
  152.         mov     ecx, keyboards
  153.         mov     edx, [ecx+KEYBOARD.prev]
  154.         mov     [ebx+KEYBOARD.next], ecx
  155.         mov     [ebx+KEYBOARD.prev], edx
  156.         mov     [edx+KEYBOARD.next], ebx
  157.         mov     [ecx+KEYBOARD.prev], ebx
  158.         mov     ecx, [ebx+KEYBOARD.functions]
  159.         cmp     [ecx+KBDFUNC.strucsize], KBDFUNC.setlights
  160.         jbe     .unlock
  161.         mov     ecx, [ecx+KBDFUNC.setlights]
  162.         test    ecx, ecx
  163.         jz      .unlock
  164.         stdcall ecx, [ebx+KEYBOARD.userdata], dword [kb_lights]
  165. .unlock:
  166.         mov     ecx, keyboard_list_mutex
  167.         call    mutex_unlock
  168.         xchg    eax, ebx
  169. .nothing:
  170.         pop     ebx
  171.         ret     8
  172.  
  173. delete_keyboard:
  174.         push    ebx
  175.         mov     ebx, [esp+4+4]
  176.         mov     ecx, keyboard_list_mutex
  177.         call    mutex_lock
  178.         mov     eax, [ebx+KEYBOARD.next]
  179.         mov     edx, [ebx+KEYBOARD.prev]
  180.         mov     [eax+KEYBOARD.prev], edx
  181.         mov     [edx+KEYBOARD.next], eax
  182.         call    mutex_unlock
  183.         mov     ecx, [ebx+KEYBOARD.functions]
  184.         cmp     [ecx+KBDFUNC.strucsize], KBDFUNC.close
  185.         jbe     .nothing
  186.         mov     ecx, [ecx+KBDFUNC.close]
  187.         test    ecx, ecx
  188.         jz      .nothing
  189.         stdcall ecx, [ebx+KEYBOARD.userdata]
  190. .nothing:
  191.         pop     ebx
  192.         ret     4
  193. ;---------------------------------------------------------------------
  194. align 4
  195. irq1:
  196.         movzx   eax, word[TASK_COUNT]; top window process
  197.         movzx   eax, word[WIN_POS+eax*2]
  198.         shl     eax, 8
  199.         mov     al, [SLOT_BASE+eax+APPDATA.keyboard_mode]
  200.         mov     [keyboard_mode], al
  201.        
  202.         in      al, 0x60
  203. ;--------------------------------------
  204. send_scancode:
  205.         mov     [keyboard_data], al
  206. ; ch = scancode
  207. ; cl = ext_code
  208. ; bh = 0 - normal key
  209. ; bh = 1 - modifier (Shift/Ctrl/Alt)
  210. ; bh = 2 - extended code
  211.         mov     ch, al
  212.         cmp     al, 0xE0
  213.         je      @f
  214.        
  215.         cmp     al, 0xE1
  216.         jne     .normal_code
  217. @@:
  218.         mov     bh, 2
  219.         mov     [ext_code], al
  220.         jmp     .writekey
  221. ;--------------------------------------
  222. .normal_code:
  223.         mov     cl, 0
  224.         xchg    cl, [ext_code]
  225.         and     al, 0x7F
  226.         mov     bh, 1
  227. @@:
  228.         cmp     al, 0x2A
  229.         jne     @f
  230.        
  231.         cmp     cl, 0xE0
  232.         je      .writekey
  233.        
  234.         mov     eax, VKEY_LSHIFT
  235.         jmp     .modifier
  236. ;--------------------------------------
  237. @@:
  238.         cmp     al, 0x36
  239.         jne     @f
  240.        
  241.         cmp     cl, 0xE0
  242.         je      .writekey
  243.        
  244.         mov     eax, VKEY_RSHIFT
  245.         jmp     .modifier
  246. ;--------------------------------------
  247. @@:
  248.         cmp     al, 0x38
  249.         jne     @f
  250.        
  251.         mov     eax, VKEY_LALT
  252.         test    cl, cl
  253.         jz      .modifier
  254.        
  255.         mov     al, VKEY_RALT
  256.         jmp     .modifier
  257. ;--------------------------------------
  258. @@:
  259.         cmp     al, 0x1D
  260.         jne     @f
  261.        
  262.         mov     eax, VKEY_LCONTROL
  263.         test    cl, cl
  264.         jz      .modifier
  265.        
  266.         mov     al, VKEY_RCONTROL
  267.         cmp     cl, 0xE0
  268.         jz      .modifier
  269.        
  270.         mov     [ext_code], cl
  271.         jmp     .writekey
  272. ;--------------------------------------
  273. @@:
  274.         cmp     al, 0x3A
  275.         jne     @f
  276.        
  277.         mov     bl, 4
  278.         mov     eax, VKEY_CAPSLOCK
  279.         jmp     .no_key.xor
  280. ;--------------------------------------
  281. @@:
  282.         cmp     al, 0x45
  283.         jne     @f
  284.         test    cl, cl
  285.         jnz     .writekey
  286.        
  287.         mov     bl, 2
  288.         mov     eax, VKEY_NUMLOCK
  289.         jmp     .no_key.xor
  290. ;--------------------------------------
  291. @@:
  292.         cmp     al, 0x46
  293.         jne     @f
  294.        
  295.         mov     bl, 1
  296.         mov     eax, VKEY_SCRLOCK
  297.         jmp     .no_key.xor
  298. ;--------------------------------------
  299. @@:
  300.         xor     ebx, ebx
  301.         test    ch, ch
  302.         js      .writekey
  303.        
  304.         movzx   eax, ch          ; plain key
  305.         mov     bl, [keymap+eax]
  306.         mov     edx, [kb_state]
  307.         test    dl, VKEY_CONTROL ; ctrl alt del
  308.         jz      .noctrlaltdel
  309.        
  310.         test    dl, VKEY_ALT
  311.         jz      .noctrlaltdel
  312.        
  313.         cmp     ch, 53h
  314.         jne     .noctrlaltdel
  315.        
  316.         mov     [ctrl_alt_del], 1
  317. .noctrlaltdel:
  318.         test    dl, VKEY_CONTROL ; ctrl on ?
  319.         jz      @f
  320.        
  321.         sub     bl, 0x60
  322. @@:
  323.         test    dl, VKEY_CAPSLOCK        ; caps lock on ?
  324.         jz      .no_caps_lock
  325.        
  326.         test    dl, VKEY_SHIFT   ; shift on ?
  327.         jz      .keymap_shif
  328.        
  329.         jmp     @f
  330. ;--------------------------------------
  331. .no_caps_lock:
  332.         test    dl, VKEY_SHIFT   ; shift on ?
  333.         jz      @f
  334. .keymap_shif:  
  335.         mov     bl, [keymap_shift+eax]
  336. @@:
  337.         test    dl, VKEY_ALT     ; alt on ?
  338.         jz      @f
  339.        
  340.         mov     bl, [keymap_alt+eax]
  341. @@:
  342.         jmp     .writekey
  343. ;--------------------------------------
  344. .modifier:
  345.         test    ch, ch
  346.         js      .modifier.up
  347.         or      [kb_state], eax
  348.         jmp     .writekey
  349. ;--------------------------------------
  350. .modifier.up:
  351.         not     eax
  352.         and     [kb_state], eax
  353.         jmp     .writekey
  354. ;--------------------------------------
  355. .no_key.xor:
  356.         mov     bh, 0
  357.         test    ch, ch
  358.         js      .writekey
  359.        
  360.         xor     [kb_state], eax
  361.         xor     [kb_lights], bl
  362.         push    ecx
  363.         call    set_lights
  364.         pop     ecx
  365. .writekey:
  366.         pushad
  367. ; test for system hotkeys
  368.         movzx   eax, ch
  369.         cmp     bh, 1
  370.         ja      .nohotkey
  371.         jb      @f
  372.        
  373.         xor     eax, eax
  374. @@:
  375.         mov     eax, [hotkey_scancodes + eax*4]
  376. .hotkey_loop:
  377.         test    eax, eax
  378.         jz      .nohotkey
  379.        
  380.         mov     cl, 0
  381.         call    hotkey_do_test
  382.         jc      .hotkey_cont
  383.        
  384.         mov     cl, 2
  385.         call    hotkey_do_test
  386.         jc      .hotkey_cont
  387.        
  388.         mov     cl, 4
  389.         call    hotkey_do_test
  390.         jnc     .hotkey_found
  391. .hotkey_cont:
  392.         mov     eax, [eax]
  393.         jmp     .hotkey_loop
  394. ;--------------------------------------
  395. .hotkey_found:
  396.         mov     eax, [eax+8]
  397. ; put key in buffer for process in slot eax
  398.         mov     edi, hotkey_buffer
  399. @@:
  400.         cmp     dword [edi], 0
  401.         jz      .found_free
  402.        
  403.         add     edi, 8
  404.         cmp     edi, hotkey_buffer+120*8
  405.         jb      @b
  406. ; no free space - replace first entry
  407.         mov     edi, hotkey_buffer
  408. .found_free:
  409.         mov     [edi], eax
  410.         movzx   eax, ch
  411.         cmp     bh, 1
  412.         jnz     @f
  413.        
  414.         xor     eax, eax
  415. @@:
  416.         mov     [edi+4], ax
  417.         mov     eax, [kb_state]
  418.         mov     [edi+6], ax
  419.  
  420.         cmp     [PID_lock_input], dword 0
  421.         je      .nohotkey
  422.  
  423.         popad
  424.         jmp     .exit.irq1
  425. ;--------------------------------------
  426. .nohotkey:
  427.         popad
  428.  
  429.         cmp     [keyboard_mode], 0; return from keymap
  430.         jne     .scancode
  431.        
  432.         test    bh, bh
  433.         jnz     .exit.irq1
  434.        
  435.         test    bl, bl
  436.         jz      .exit.irq1
  437.  
  438.         test    [kb_state], VKEY_NUMLOCK
  439.         jz      .dowrite
  440.        
  441.         cmp     cl, 0xE0
  442.         jz      .dowrite
  443.        
  444.         cmp     ch, 55
  445.         jnz     @f
  446.        
  447.         mov     bl, 0x2A        ;*
  448.         jmp     .dowrite
  449. ;--------------------------------------
  450. @@:
  451.         cmp     ch, 71
  452.         jb      .dowrite
  453.        
  454.         cmp     ch, 83
  455.         ja      .dowrite
  456.        
  457.         movzx   eax, ch
  458.         mov     bl, [numlock_map + eax - 71]
  459.         jmp     .dowrite
  460. ;--------------------------------------
  461. .scancode:
  462.         mov     bl, ch
  463. .dowrite:
  464.         movzx   eax, byte[KEY_COUNT]
  465.         cmp     al, 120
  466.         jae     .exit.irq1
  467.         inc     eax
  468.         mov     [KEY_COUNT], al
  469.         mov     [KEY_COUNT+eax], bl
  470. .exit.irq1:
  471.         mov     [check_idle_semaphore], 5
  472.         ret
  473. ;---------------------------------------------------------------------
  474. set_lights:
  475.         push    ebx esi
  476.         mov     ecx, keyboard_list_mutex
  477.         call    mutex_lock
  478.         mov     esi, keyboards
  479. .loop:
  480.         mov     esi, [esi+KEYBOARD.next]
  481.         cmp     esi, keyboards
  482.         jz      .done
  483.         mov     eax, [esi+KEYBOARD.functions]
  484.         cmp     dword [eax], KBDFUNC.setlights
  485.         jbe     .loop
  486.         mov     eax, [eax+KBDFUNC.setlights]
  487.         test    eax, eax
  488.         jz      .loop
  489.         stdcall eax, [esi+KEYBOARD.userdata], dword [kb_lights]
  490.         jmp     .loop
  491. .done:
  492.         mov     ecx, keyboard_list_mutex
  493.         call    mutex_unlock
  494.         pop     esi ebx
  495.         ret
  496.  
  497. ps2_set_lights:
  498.         mov     al, 0xED
  499.         call    kb_write
  500.         mov     al, [esp+8]
  501.         call    kb_write
  502.         ret     8
  503.  
  504. ;// mike.dld ]
  505. check_lights_state:
  506.         mov     al, [kb_lights]
  507.         cmp     al, [old_kb_lights]
  508.         jz      .nothing
  509.         mov     [old_kb_lights], al
  510.         call    set_lights
  511. .nothing:
  512.         ret
  513. ;---------------------------------------------------------------------
  514. numlock_map:
  515.     db   0x37   ;Num 7
  516.     db   0x38   ;Num 8
  517.     db   0x39   ;Num 9
  518.     db   0x2D   ;Num -
  519.     db   0x34   ;Num 4
  520.     db   0x35   ;Num 5
  521.     db   0x36   ;Num 6
  522.     db   0x2B   ;Num +
  523.     db   0x31   ;Num 1
  524.     db   0x32   ;Num 2
  525.     db   0x33   ;Num 3
  526.     db   0x30   ;Num 0
  527.     db   0x2E   ;Num .
  528. ;---------------------------------------------------------------------
  529.