Pregunta
Me quedé atrapado en esta cosa, quiero ver si el botón de desplazamiento a la derecha se ha presionado, así que tengo este código assambler:
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
¿Por qué no funciona?, Creo que el problema es que int 16,2 no está funcionando correctamente, si es así ¿por qué es esto? esto es lo que se supone 16,2 INT hacer:
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
Nunca veo el mensaje, he mirado en el registro AL en depurar y no parece cambiar después de que llamo INT 16,2.I'm que ejecuta Windows 7 en un Arhitecture x 86, y estoy trabajar con TASM
Solución
¿Cómo estás probando esto?
Por curiosidad, hice un programa simple (código de abajo). Cuando se ejecuta en la consola de Windows, que detecta desviación a la izquierda (Result: 2
) pero nunca detecta desplazamiento a la derecha (Result: 1
se esperaba, pero sólo consiguió Result: 0
).
cuando se ejecuta en DOS puro (en VMWare), se muestra correctamente todas las combinaciones de (0 a 3).
Por lo que parece ser un artefacto de NTVDM (emulación de DOS de Windows), aunque no tengo ninguna fuente para citar.
Mi código:
.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
Otros consejos
que debe ser capaz de limpiar su cheque haciendo:
test al,1
jnz rshift
No puedo explicar por qué su código no está funcionando, pero se puede sustituir
mov ah,10000000b
shl al,7
and al,10000000b
cmp al,ah ;check if first bit is 1
por
test al, 1
que hace lo mismo y es más idiomático, si hay una cosa tal como un idioma en el montaje.
EDIT:
Como Michael señala en el comentario anterior, es necesario invertir el salto condicional si se utiliza la instrucción test
. test al, C
establece ZF si y sólo el bit a bit y de al
Y C
es cero.