$Revision$ ;// mike.dld [ VKEY_LSHIFT = 0000000000000001b VKEY_RSHIFT = 0000000000000010b VKEY_LCONTROL = 0000000000000100b VKEY_RCONTROL = 0000000000001000b VKEY_LALT = 0000000000010000b VKEY_RALT = 0000000000100000b VKEY_CAPSLOCK = 0000000001000000b VKEY_NUMLOCK = 0000000010000000b VKEY_SCRLOCK = 0000000100000000b VKEY_SHIFT = 0000000000000011b VKEY_CONTROL = 0000000000001100b VKEY_ALT = 0000000000110000b uglobal align 4 kb_state dd 0 ext_code db 0 keyboard_mode db 0 keyboard_data db 0 altmouseb db 0 ctrl_alt_del db 0 kb_lights db 0 align 4 hotkey_scancodes rd 256 ; we have 256 scancodes hotkey_list rd 256*4 ; max 256 defined hotkeys hotkey_buffer rd 120*2 ; buffer for 120 hotkeys endg iglobal hotkey_tests dd hotkey_test0 dd hotkey_test1 dd hotkey_test2 dd hotkey_test3 dd hotkey_test4 hotkey_tests_num = 5 endg hotkey_test0: test al, al setz al ret hotkey_test1: test al, al setnp al ret hotkey_test2: cmp al, 3 setz al ret hotkey_test3: cmp al, 1 setz al ret hotkey_test4: cmp al, 2 setz al ret hotkey_do_test: push eax mov edx, [kb_state] shr edx, cl add cl, cl mov eax, [eax+4] shr eax, cl and eax, 15 cmp al, hotkey_tests_num jae .fail xchg eax, edx and al, 3 call [hotkey_tests + edx*4] cmp al, 1 pop eax ret .fail: stc pop eax ret align 4 irq1: ; save_ring3_context ; mov ax, os_data ; mov ds, ax ; mov es, ax movzx eax,word[TASK_COUNT] ; top window process movzx eax,word[WIN_POS+eax*2] shl eax,8 mov al,[SLOT_BASE+eax+APPDATA.keyboard_mode] mov [keyboard_mode],al in al,0x60 mov [keyboard_data],al ; ch = scancode ; cl = ext_code ; bh = 0 - normal key ; bh = 1 - modifier (Shift/Ctrl/Alt) ; bh = 2 - extended code mov ch,al cmp al,0xE0 je @f cmp al,0xE1 jne .normal_code @@: mov bh, 2 mov [ext_code], al jmp .writekey .normal_code: mov cl, 0 xchg cl, [ext_code] and al,0x7F mov bh, 1 @@: cmp al,0x2A jne @f cmp cl,0xE0 je .writekey mov eax,VKEY_LSHIFT jmp .modifier @@: cmp al,0x36 jne @f cmp cl,0xE0 je .writekey mov eax,VKEY_RSHIFT jmp .modifier @@: cmp al,0x38 jne @f mov eax, VKEY_LALT test cl, cl jz .modifier mov al, VKEY_RALT jmp .modifier @@: cmp al,0x1D jne @f mov eax, VKEY_LCONTROL test cl, cl jz .modifier mov al, VKEY_RCONTROL cmp cl, 0xE0 jz .modifier mov [ext_code], cl jmp .writekey @@: cmp al,0x3A jne @f mov bl,4 mov eax,VKEY_CAPSLOCK jmp .no_key.xor @@: cmp al,0x45 jne @f test cl, cl jnz .writekey mov bl,2 mov eax,VKEY_NUMLOCK jmp .no_key.xor @@: cmp al,0x46 jne @f mov bl,1 mov eax,VKEY_SCRLOCK jmp .no_key.xor @@: test ch,ch js .writekey movzx eax,ch ; plain key mov bl,[keymap+eax] mov edx,[kb_state] test dl,VKEY_CONTROL ; ctrl alt del jz .noctrlaltdel test dl,VKEY_ALT jz .noctrlaltdel cmp ch,53h jne .noctrlaltdel mov [ctrl_alt_del],1 .noctrlaltdel: test dl,VKEY_CONTROL ; ctrl on ? jz @f sub bl,0x60 @@: test dl,VKEY_SHIFT ; shift on ? jz @f mov bl,[keymap_shift+eax] @@: test dl,VKEY_ALT ; alt on ? jz @f mov bl,[keymap_alt+eax] @@: mov bh, 0 jmp .writekey .modifier: test ch, ch js .modifier.up or [kb_state], eax jmp .writekey .modifier.up: not eax and [kb_state], eax jmp .writekey .no_key.xor: mov bh, 0 test ch, ch js .writekey xor [kb_state], eax xor [kb_lights], bl call set_lights .writekey: ; test for system hotkeys movzx eax, ch cmp bh, 1 ja .nohotkey jb @f xor eax, eax @@: mov eax, [hotkey_scancodes + eax*4] .hotkey_loop: test eax, eax jz .nohotkey mov cl, 0 call hotkey_do_test jc .hotkey_cont mov cl, 2 call hotkey_do_test jc .hotkey_cont mov cl, 4 call hotkey_do_test jnc .hotkey_found .hotkey_cont: mov eax, [eax] jmp .hotkey_loop .hotkey_found: mov eax, [eax+8] ; put key in buffer for process in slot eax mov edi, hotkey_buffer @@: cmp dword [edi], 0 jz .found_free add edi, 8 cmp edi, hotkey_buffer+120*8 jb @b ; no free space - replace first entry mov edi, hotkey_buffer .found_free: mov [edi], eax movzx eax, ch cmp bh, 1 jnz @f xor eax, eax @@: mov [edi+4], ax mov eax, [kb_state] mov [edi+6], ax jmp .exit.irq1 .nohotkey: cmp [keyboard_mode],0 ; return from keymap jne .scancode test bh, bh jnz .exit.irq1 test bl, bl jz .exit.irq1 jmp .dowrite .scancode: mov bl, ch .dowrite: movzx eax,byte[KEY_COUNT] cmp al,120 jae .exit.irq1 inc eax mov [KEY_COUNT],al mov [KEY_COUNT+eax],bl .exit.irq1: mov [check_idle_semaphore],5 ; mov al,0x20 ; ready for next irq ; out 0x20,al ; restore_ring3_context ; iret ret set_lights: mov al,0xED call kb_write mov al,[kb_lights] call kb_write ret ;// mike.dld ]