1. Средства BIOS

Так же как и для вывода на экран, BIOS предоставляет больше возможностей по сравнению с DOS для считывания данных и управления клавиатурой. Например, функциями DOS нельзя определить нажатие комбинаций клавиш типа Ctrl-Alt-Enter или нажатие двух клавиш Shift одновременно, DOS не может определить момент отпускания нажатой клавиши, и наконец, в DOS нет аналога функции С ungetch (), помещающей символ в буфер клавиатуры, как если бы его ввел пользователь. Все это можно осуществить, используя различные функции прерывания 16h и операции с байтами состояния клавиатуры.

INT 16h, АН = 0, 10h, 20h - Чтение символа с ожиданием

 

Ввод: АН = 00h (83/84-key), 10h (101/102-key), 20h (122-key)
Вывод:

AL = ASCII-код символа, 0 или префикс скан-кода

АН = скан-код нажатой клавиши или расширенный ASCII-код

 

Каждой клавише на клавиатуре соответствует так называемый скан-код (см. приложение 1), соответствующий только этой клавише. Этот код посылается клавиатурой при каждом нажатии и отпускании клавиши и обрабатывается BIOS (обработчиком прерывания INT 9). Прерывание 16h дает возможность получить код нажатия, не перехватывая, этот обработчик. Если нажатой клавише соответствует ASCII-символ, то в АН возвращается код этого символа, а в AL - скан-код клавиши. Если нажатой клавише соответствует расширенный ASCII-код, в AL возвращается префикс скан-кода (например, Е0 для серых клавиш) или 0, если префикса нет, а в АН - расширенный ASCII-код. Функция 00Н обрабатывает только комбинации, использующие клавиши 84-клавишной клавиатуры, l0h обрабатывает все 101 - 105-клавишные комбинации, 20h - 122-клавишные. Тип клавиатуры можно определить с помощью функции 09h прерывания 16h, если она поддерживается BIOS (поддерживается ли эта функция, можно узнать с помощью функции C0h прерывания 15h).

INT 16h, АН = 1, 11h, 21h - Проверка символа

 

Ввод: АН = 01h (83/84-key), 11h (101/102-key), 21h (122-key)
Вывод:

ZF = 1, если буфер пуст

ZF = 0, если в буфере присутствует символ, в этом случае

AL = ASCII-код символа, 0 или префикс скан-кода

АН = скан-код нажатой клавиши или расширенный ASCII-код

 

Символ остается в буфере клавиатуры, хотя некоторые BIOS удаляют символ из буфера при обработке функции 01h, если он соответствует расширенному ASCII-коду, отсутствующему на 84-клавишных клавиатурах.

INT 16h, АН = 05h - Поместить символ в буфер клавиатуры

 

Ввод:

АН = 05h

СН = скан-код

CL = ASCII-код

Вывод:

AL = 00, если операция выполнена успешно

AL = 01h, если буфер клавиатуры переполнен

АН модифицируется многими BIOS

 

Обычно можно поместить 0 вместо скан-кода в СН, если функция, которая будет выполнять чтение из буфера, будет использовать именно ASCII-код.

Например, следующая программа при запуске из DOS вызывает команду DIR (но при запуске из некоторых оболочек, например FAR, этого не произойдет).


Пример №1.1

. model tiny ; модель памяти, в которой сегменты кода, данных и стека объединены.
. code ; сегмент кода, который содержит данные.
org 100h ; начало СОМ-файла
begin: ; метка начала кода программы
mov cl,'d' ; заносим в регистр cl - ASCII-код буквы "d"
call ungetch ; переходим на метку ungetch: (вызов подпрограммы)
mov cl,'i' ; заносим в регистр cl - ASCII-код буквы "i"
call ungetch ; вызываем подпрограмму
mov cl,'r' ; заносим в регистр cl - ASCII-код буквы "r"
call ungetch ; вызываем подпрограмму
mov cl,0Dh ; перевод строки
Ungetch proc ; метка начала подпрограммы
mov ah,05h ; AH = номер функции
mov ch,0 ; CH = 0 (скан-код неважен)
int 16h ; вызов DOS (прерывание)
ret ; функция DOS "завершить работу процедуры"
Ungetch endp ; окончание подпрограммы
end begin ; метка окончания кода программы

 

Оформление процедур (подпрограмм).

______________

Call ungetch

Ungetch proc

Ungetch endp

______________

Ungetch - название процедуры

Call - вызов подпрограммы

Proc - procedure - процедура

endp - end procedure - конец процедуры

Стоит еще отметить, что из одной подпрограммы можно вызывать другие. Из других - третьи. Чаще всего с целью упрощения программы и, тем самым, уменьшения ее размера программисты используют простую связку команд:

Call метка

метка:

Любой вызов подпрограмм заканчивается возращение в блок кода командой ret (ret - return - возврат).

INT 16h, AH = 02h, 12h, 22h - Считать состояние клавиатуры

 

Ввод: АН = 02h (83/84-key), 12h (101/102-key), 22h (122-key)
Вывод:

AL = байт состояния клавиатуры 1

АН = байт состояния клавиатуры 2 (только для функций 12h и 22h)

 

Байт состояния клавиатуры 1 (этот байт всегда расположен в памяти по адресу 0000h: 0417h или 0040h: 0017h):

Бит 7: Ins включена

Бит 6: CapsLock включена

Бит 5: NumLock включена

Бит 4: ScrollLock включена

Бит 3: Alt нажата (любая Alt для функции 02h, часто только левая Alt для 12h/22h)

Бит 2: Ctrl нажата (любая Ctrl)

Бит 1: Левая Shift нажата

Бит 0: Правая Shift нажата

Байт состояния клавиатуры 2 (этот байт всегда расположен в памяти по адресу 0000h: 0418h или 0040h: 0018h):

Бит 7: SysRq нажата

Бит 6: CapsLock нажата

Бит 5: NumLock нажата

Бит 4: ScrollLock нажата

Бит 3: Правая Alt нажата

Бит 2: Правая Ctrl нажата

Бит 1: Левая Alt нажата

Бит 0: Левая Ctrl нажата

Оба этих байта постоянно располагаются в памяти, так что вместо вызова прерывания часто удобнее просто считывать значения напрямую. Более того, в эти байты можно записывать новые значения, и BIOS изменит состояние клавиатуры соответственно:

Помимо этих двух байт BIOS хранит в своей области данных и весь клавиатурный буфер, к которому также можно обращаться напрямую. Буфер занимает 16 слов с 0h: 041Eh no 0h: 043Dh включительно, причем по адресу 0h: 041Ah лежит адрес (ближний) начала буфера, то есть адрес, по которому располагается следующий введенный символ, а по адресу 0h: 041Ch лежит адрес конца буфера, так что если эти два адреса равны, буфер пуст. Буфер действует как кольцо: если начало буфера - 043Ch, а конец - 0420h, то в буфере находятся три символа по адресам 043Ch, 041Eh и 0420h. Каждый символ хранится в виде слова - того же самого, которое возвращает функция 10h прерывания INT 16h. В некоторых случаях (если) буфер размещается по другим адресам, тогда адрес его начала хранится в области данных BIOS по адресу 0480h, а конца - по адресу 0482h. Прямой доступ к буферу клавиатуры лишь немногим быстрее, чем вызов соответствующих функций BIOS, и для приложений, требующих максимальной скорости, таких как игры или демо-программы, используют управление клавиатурой на уровне портов ввода-вывода.


Информация о работе «Разработка виртуальных лабораторных работ средствами эмулятора Emu8086»
Раздел: Информатика, программирование
Количество знаков с пробелами: 193894
Количество таблиц: 73
Количество изображений: 12

0 комментариев


Наверх