Лабораторная работа № 11-12. «Изучение организации и принципов работы клавиатуры». Краткие теоретические и учебно-методические материалы
Лабораторная работа № 11-12 «Изучение организации и принципов работы клавиатуры» Цель работы: изучение организации и принципов работы клавиатуры и закрепление практических навыков управления ею, а также практических навыков создания собственных программ обработки прерываний. Образовательные результаты, заявленные во ФГОС третьего поколения: Студент должен уметь: - осуществлять разработку кода программного модуля на современных языках программирования; - создавать программу по разработанному алгоритму как отдельный модуль; - выполнять отладку и тестирование программы на уровне модуля знать: - основные этапы разработки программного обеспечения; - основные принципы технологии структурного и объектно-ориентированного программирования; - основные принципы отладки итестирования программных продуктов. Краткие теоретические и учебно-методические материалы по теме лабораторной работы Работа клавиатуры организована на базе собственного микропроцессора. При нажатии или отпускании любой клавиши генерируется код (скан-код), который записывается в собственную память (аппаратный буфер) клавиатуры. При этом в центральный процессор выдается прерывание 9, сигнализирующее о появлении очередного скан-кода. Программа обработки этого прерывания может теперь прочитать код из клавиатуры. Если она этого не сделает, то сканкоды будут накапливаться в аппаратном буфере и могут быть прочитаны позднее. Чтение скан-кода производится из однобайтного порта 0x60. При выполнении только чтения скан-код не удаляется из аппаратного буфера, и при следующем обращении к порту 0x60 будет прочитан тот же скан-код.
Для того, чтобы удалить скан-код из аппаратного буфера, необходимо послать в клавиатуру сигнал подтверждения: на короткое время выставить единицу в старшем разряде однобайтного порта 0 x61 (не разрушая при этом остальных разрядов этого порта). Каждая клавиша имеет собственный уникальный скан-код, в том числе и на 101-клавишной клавиатуре AT, где некоторые клавиши дублируются - например, левая и правая клавиши Shift имеют разные скан-коды. Распределение значений скан-кодов примерно соответствует расположению клавиш на панели клавиатуры. Скан-коды не совпадают с кодировкой внутримашинного представления символов, для которой применяется код ASCII. Преобразование скан-кодов в коды ASCII происходит программными путем.
Пример. Разработать программу обработки прерывания от клавиатуры, которая должна: распознавать нажатие " горячей" комбинации клавиш и реагировать на него звуковым сигналом; при первом нажатии " горячей" комбинации переходить в режим блокировки ввода заданной клавиши, при втором - отменять этот режим; системная обработка всех других клавиш нарушаться не должна. Комбинация клавиш LeftCtrl+RightShift+F3; блокирование ввода клавиши 3. Программа состоит из основной программы и трех функций. void *readvect(int in) - функция читает вектор прерывания с номером in и возвращает его значение. void writevect (int in, void *h) - функция устанавливает новый вектор прерывания in на новый обработчик этого прерывания по адресу h. void interrupt new9() - процедура нового обработчика прерывания 9h. Глобальные переменные программы: old9 - адрес старого обработчика прерывания 9h; F3_code - скан-код клавиши " F3", которая входит в комбинацию " горячих" клавиш; key3_code - скан-код клавиши " 3", которая будет блокироваться/разблокироваться при каждом нажатии " горячей" комбинации клавиш; f - флаг, который при каждом нажатии " горячей" комбинации клавиш переключается из состояния 0 в 1 или из 1 в 0 (состояние 1 означает, что клавиша " 3" заблокирована); rr и sr - переменные, которые используются для задания значений регистров общего назначения и сегментных регистров соответственно при вызове прерывания.
В главной программе использует символьный массив string для проверки работы программы. Переменные процедуры обработки прерывания 9h: c - переменная, которая используется для подтверждения приема из клавиатуры, в случае, если была нажата клавиша " 3", а флаг f показывал, что эта клавиша заблокирована; x, y - переменные, которые используются для сохранения координат курсора на экране в момент вызова процедуры обработки прерывания; byte17 - байт флага состояния клавиатуры в области данных BIOS по адресу 0040: 0017; byte18 - байт флага состояния клавиатуры в области данных BIOS по адресу 0040: 0018; mask - маска, которая используется для определения нажатия клавиши левый Shift (в этом случае бит 1 в byte17 установлен в 1); mask17 - маска, которая используется для определения нажатия клавиши Сtrl (в этом случае бит 2 в byte17 установлен в 1); mask18 - маска, которая используется для определения нажатия клавиши левый Сtrl (в этом случае бит 0 в byte18 установлен в 1); Главная программа выполняет такие действия: Запоминает адрес старого обработчика прерывания 9h, вызывая функцию readvect(in) с параметром in=9. Записывает в таблицу векторов прерываний адрес нового обработчика прерывания с помощью функции writevect(). Вводом строки символов дает возможность проверить работу программы и ее реакцию на нажатие " горячей" комбинации клавиш и блокирование/разблокирование ввода клавиши " 3". В конце работы восстанавливает в таблице векторов прерываний адрес старого обработчика. Для решения задачи процедура обработки прерывания от клавиатуры new9() должна действовать по такому алгоритму: Прочитать флаги состояния клавиатуры (статус клавиш-переключателей), которые находятся в области данных BIOS (два байта по адресам 0040: 0017 и 0040: 0018). Выделить бит 1 в флаге по адресу 0040: 0017 (если он равен 1, то нажата клавиша левый Shift). Выделить бит 2 в этом же флаге (если он равен 1, то нажата левый или правый Ctrl). Выделить бит 0 в флаге состояния клавиатуры по адресу 0040: 0018 (если он равен 1, то нажата клавиша левый Ctrl).
Из порта 60h прочитать скан-код нажатой клавиши. Если нажата комбинация клавиш левый Shift, правый Ctrl (нажата клавиша Ctrl, но это не правый Ctrl)и клавиша F3, то выполнить п. 7. Иначе - перейти к п. 8. Сигнализировать о нажатии " горячей" комбинации клавиш звуковым сигналом, переключить значение флага блокирования ввода клавиши " 3" на обратное и вызвать старый обработчик прерывания от клавиатуры. Прочитав байт из порта 60h, определить, нажата ли клавиша 3" и если, кроме этого, еще и флаг блокирования указывает на то, что она заблокирована (f=1), то выполнить п. п. 9 и 10, иначе - вызвать старый обработчик прерывания. Послать подтверждение приема в клавиатуру. Для этого в порт 61h на короткое время выставить " 1" по шине старшего разряда. Сбросить контроллер прерываний, посылая код 20h в порт 20h. Функция readvect() читает вектор заданного прерывания. Для чтения вектора используется функция 35h DOS (прерывания 21h): Вход: AH = 35h; AL = номер вектора прерывания. Выход: ES: BX = адрес программы обработки прерывания Функция writevect() устанавливает новый вектор прерывания на заданный адрес. Для записи вектора используется функция 25h DOS: Вход: AL = номер вектора прерывания; DS: BX = 4-байтный адрес нового обработчика прерывания. /* Подключение стандартных заголовков */ #include < dos. h>
void interrupt (*old9)(); /* Старый обработчик прерывания 9h */ void interrupt new9(); /* Новый обработчик прерывания 9h */ void *readvect (int in); /* Чтение вектора */ void writevect (int in, void *h); /* Запись вектора */
unsigned char F3_code=61; /* scan-code " F3" */ unsigned char key3_code=4; /* scan-code " 3" */ char f=0; /* Флаг */ union REGS rr; struct SREGS sr; /*--------------------------------------------------------*/ void main() { char string[80]; /* Буфер для ввода текста */ textbackground(0); clrscr(); textattr(0x0a); cprintf(" ---------------" ); cprintf(" Лабораторная работа " ); cprintf(" ---------------" ); cprintf(" ---------------" ); cprintf(" Управление клавиатурой " );
cprintf(" ---------------" ); old9=readvect(9); writevect(9, new9); textattr(0x0c); cprintf(" \n\n\r\" горячая\" комбинация: " ); textattr(0x0a); cprintf(" Left Shift, Right Ctrl, F3\n\r" ); textattr(0x0b); cprintf(" Клавиша, которая блокируется: " ); textattr(0x0f); cprintf(" 3" ); textattr(0x07); cprintf(" \r\nВводите строку символов> " ); scanf(" %s", string); writevect(9, old9); } /*--------------------------------------------------------*/ /* Чтение вектора */ void *readvect(int in) { rr. h. ah=0x35; rr. h. al=in; intdosx(& rr, & rr, & sr); return(MK_FP(sr. es, rr. x. bx)); } /*--------------------------------------------------------*/ /* Запись вектора */ void writevect(int in, void *h) { rr. h. ah=0x25; rr. h. al=in; sr. ds=FP_SEG(h); rr. x. dx=FP_OFF(h); intdosx(& rr, & rr, & sr); } /*--------------------------------------------------------*/ /* Новый обработчик 9-го прерыванмя */ void interrupt new9() { unsigned char c, x, y; unsigned char byte17, byte18; unsigned char mask=0x02; unsigned char mask17=0x04; unsigned char mask18=0x01; byte17=peekb(0x40, 0x17); byte18=peekb(0x40, 0x18); if((inportb(0x60)==F3_code)& & (byte17& mask)& & (byte17& mask17)& & (! (byte18& mask18))) { cputs(" \7" ); x=wherex(); y=wherey(); gotoxy(55, 3); textattr(0x1e); if(f==0) { f=1; cprintf(" Клавиша \" 3\" заблокирована " ); } else { f=0; cprintf(" Клавиша \" 3\" разблокирована" ); } gotoxy(x, y); textattr(0x07); (*old9)(); } if( (f==1) & & (inportb(0x60)==key3_code) ) { c=inportb(0x61); outportb(0x61, c|0x80); outportb(0x61, c); outportb(0x20, 0x20); } else (*old9)(); } Во время программы при первом нажатии комбинации клавиш LeftCtrl+RightShift+F3 программа переходит в режим блокирования вводу клавиши 3, при втором - отменяет этот режим.
Задания для лабораторной работы: Разработать программу обработки прерывания от клавиатуры, которая должна: распознавать нажатие " горячей" комбинации клавиш и реагировать на него звуковым сигналом; при первом нажатии " горячей" комбинации переходить в режим блокировки ввода заданной клавиши, при втором - отменять этот режим; системная обработка всех других клавиш нарушаться не должна. 1. комбинация клавиш LeftCtrl+RightShift+F3; блокирование ввода клавиши 3. 2. комбинация клавиш LeftAlt+RightShift+F1; блокирование ввода клавиши 2. 3. комбинация клавиш LeftCtrl+RightShift+F7; блокирование ввода клавиши 4. 4. комбинация клавиш LeftShift+RightAlt+F9; блокирование ввода клавиши 1. 5. комбинация клавиш LeftAlt+RightShift+F2; блокирование ввода клавиши 5. 6. комбинация клавиш LeftAlt+RightCtrl+F4; блокирование ввода клавиши 7. 7. комбинация клавиш LeftCtrl+RightShift+F7; блокирование ввода клавиши 8. 8. комбинация клавиш LeftAlt+RightShift+F9; блокирование ввода клавиши 9. 9. комбинация клавиш LeftAlt+RightShift+F8; блокирование ввода клавиши 6. 10. комбинация клавиш LeftCtrl+RightAlt+F6; блокирование ввода клавиши 0. 11. комбинация клавиш LeftAlt+RightShift+F1; блокирование ввода клавиши q. 12. комбинация клавиш LeftCtrl+RightShift+F12; блокирование ввода клавиши g
13. комбинация клавиш LeftAlt+Rightv+F11; блокирование ввода клавиши wh 14. комбинация клавиш LeftCtrl+RightShift+F10; блокирование ввода клавиши e 15. комбинация клавиш LeftAlt+RightShift+F12; блокирование ввода клавиши r 16. комбинация клавиш LeftCtrl+RightShift+F2; блокирование ввода клавиши g 17. комбинация клавиш LeftAlt+RightShift+F1; блокирование ввода клавиши t 18. комбинация клавиш LeftAlt+RightCtrl+F3; блокирование ввода клавиши y 19. комбинация клавиш LeftCtrl+RightAlt+F4; блокирование ввода клавиши u 20. комбинация клавиш LeftAlt+RightShift+F5; блокирование ввода клавиши i 21. комбинация клавиш LeftCtrl+RightAlt+F8; блокирование ввода клавиши o 22. комбинация клавиш LeftAlt+RightCtrl+F6; блокирование ввода клавиши p 23. комбинация клавиш LeftAlt+RightShift+F5; блокирование ввода клавиши l 24. комбинация клавиш LeftShift+RightAlt+F9; блокирование ввода клавиши k 25. комбинация клавиш LeftAlt+RightShift+F1; блокирование ввода клавиши j 26. комбинация клавиш LeftAlt+RightCtrl+F3; блокирование ввода клавиши h 27. комбинация клавиш LeftAlt+RightShift+F2; блокирование ввода клавиши d 28. комбинация клавиш LeftCtrl+RightAlt+F12; блокирование ввода клавиши s 29. комбинация клавиш LeftCtrl+RightShift+F11; блокирование ввода клавиши z 30. комбинация клавиш LeftAlt+RightCtrl+F9; блокирование ввода клавиши x 31. комбинация клавиш LeftAlt+RightShift+F10; блокирование ввода клавиши c 32. комбинация клавиш LeftAlt+RightCtrl+F8; блокирование ввода клавиши v 33. комбинация клавиш LeftAlt+RightShift+F5; блокирование ввода клавиши b 34. комбинация клавиш LeftShift+RightAlt+F4; блокирование ввода клавиши n 35. комбинация клавиш LeftAlt+RightShift+F1; блокирование ввода клавиши m.
Контрольные вопросы: 1. Опишите функции стандартного ввода DOS связанные с клавиатурой. 2. Что такое скан-коды? 3. Каким образом происходит чтение скан-кодов? 4. Для чего служат однобайтные ASCII-коды? 5. Для чего служат расширенные ASCII-коды?
Воспользуйтесь поиском по сайту: ©2015 - 2024 megalektsii.ru Все авторские права принадлежат авторам лекционных материалов. Обратная связь с нами...
|