English 中文(简体)
8086 assembler,INT 16,2
原标题:

I got stuck at this thing,I want to see if right shift button has been pressed,so I have this assambler code:

mov ah,2
int 16h           ;calling INT 16,2 - Read Keyboard Flags interrupt      
mov ah,10000000b
shl al,7 
and al,10000000b
cmp al,ah         ;check if first bit is 1
je rshift 
jmp final


rshift:
mov ah,9
lea dx,rsh  ;rsh is a string that says that "right shift button has been pressed"
int 21h
jmp final  

final:             ; quit program
mov ax,4c00h
int 21h

why is it not working ?,I think the problem is that int 16,2 is not working properly,if so why is that? here is what INT 16,2 is supposed to do:

AH = 02
on return:
AL = BIOS keyboard flags (located in BIOS Data Area 40:17)

|7|6|5|4|3|2|1|0|  AL or BIOS Data Area 40:17
| | | | | | | `---- right shift key depressed
| | | | | | `----- left shift key depressed
| | | | | `------ CTRL key depressed
| | | | `------- ALT key depressed
| | | `-------- scroll-lock is active
| | `--------- num-lock is active
| `---------- caps-lock is active
`----------- insert is active

I never see the message,I ve looked at the AL register in debug and it doesn t seem to change after I call INT 16,2.I m running Win 7 on a x86 arhitecture,and I m working with tasm

最佳回答

How are you testing this?

Out of curiosity, i made a simple program (code below). When run under Windows console, it detects left shift (Result: 2) but never detects right shift (expected Result: 1, but only got Result: 0).

When run under pure DOS (in VMWare), it correctly displays all combinations (0 to 3).

So it seems to be an artifact of NTVDM (Windows DOS emulation), though I don t have any sources to cite.

My code:

.model small

.code

start:
    mov ax, seg msg
    mov ds, ax

    mov ah, 2
    int 16h

    and al,3        ; get two lower bits - both SHIFTs
    add digit, al   ; convert to decimal

    lea dx, msg
    mov ah, 9
    int 21h

    mov ax, 4c00h
    int 21h

.data

msg     db   Result:  
digit   db   0 
        db  13,10, $ ,0

.stack
        db  16384 dup(?)

end start
问题回答

you should be able to clean up your check by doing :

test al,1
jnz rshift

I cannot explain why your code isn t working, but you can replace

mov ah,10000000b
shl al,7 
and al,10000000b
cmp al,ah         ;check if first bit is 1

by

test al, 1

which does the same thing and is more idiomatic, if there is such a thing as an idiom in assembly.

EDIT: As Michael points out in the comment below, you need to reverse the conditional jump if you use the test instruction. test al, C sets ZF if and only the bitwise and of al AND C is zero.





相关问题
List of suspected Malicious patterns

I am doing an anti-virus project by disassembling its code and analyzing it. So I want a list of the Suspected Malicious pattern codes, so I can observe which is suspected and which is not? So I want ...

Prefetch for Intel Core 2 Duo

Has anyone had experience using prefetch instructions for the Core 2 Duo processor? I ve been using the (standard?) prefetch set (prefetchnta, prefetcht1, etc) with success for a series of P4 ...

How are mutex and lock structures implemented?

I understand the concept of locks, mutex and other synchronization structures, but how are they implemented? Are they provided by the OS, or are these structures dependent on special CPU instructions ...

Installing GNU Assembler in OSX

No matter how hard I google, I can t seem to find a (relatively) easy-to-follow instruction on how to install the GNU Assembler on a mac. I know I can use gcc -c (Apple Clang on a Mac) to assemble .s ...

8086 assembler,INT 16,2

I got stuck at this thing,I want to see if right shift button has been pressed,so I have this assambler code: mov ah,2 int 16h ;calling INT 16,2 - Read Keyboard Flags interrupt mov ah,...

Translate a FOR to assembler

I need to translate what is commented within the method, to assembler. I have a roughly idea, but can t. Anyone can help me please? Is for an Intel x32 architecture: int secuencia ( int n, ...

热门标签