КЛАВИАТУРА

Практически ни одна программа не обходится без обращения к клавиатуре.

Программа может использовать клавиатуру по-разному. Она может задержать свое выполнение до тех пор, пока оператор не введет какое-нибудь число или пока не нажмет какую-нибудь клавишу. Выполняя некоторую работу, программа может периодически проверять, не нажал ли оператор на клавишу, изменяющую режим работы программы. Резидентные программы могут контролировать все нажатия на клавиши, активизируясь при нажатии определенной заранее комбинации. Можно использовать прерывание, вырабатываемое клавиатурой, например, для завершения работы программы.

1. Принципы работы клавиатуры

2. Клавишные переключатели

3. Интерфейс клавиатуры. Разъемы

4.Формат передачи данных

5. Контроллер клавиатуры

6. Порты для работы с клавиатурой

7. Аппаратное прерывание клавиатуры

8. Средства BIOS для работы с клавиатурой

9. Средства MS-DOS для работы с клавиатурой

10. Клавиатурные функции библиотеки Microsoft C


BIOS
8. Средства BIOS для работы с клавиатурой

Набор функций для работы с клавиатурой, предоставляемый в распоряжение программиста прерыванием BIOS INT 16h, включает в себя функции для выборки кода нажатого символа из буфера с ожиданием нажатия, функции для проверки содержимого буфера и для управления содержимым буфера, функции для изменения скоростных характеристик клавиатуры.

8.1. Чтение символа с ожиданием

8.2. Проверка буфера на наличие в нем символов

8.3. Получение состояния переключающих клавиш

8.4. Установка временных характеристик клавиатуры

8.5. Запись символов в буфер клавиатуры

8.6 Чтение символа с ожиданием для 101-клавишной клавиатуры

8.7. Проверка буфера на наличие в нем символов для 101-клавишной клавиатуры

8.8. Получение состояния переключающих клавиш для 101-клавишной клавиатуры


MS-DOS
9. Средства MS-DOS для работы с клавиатурой

К сожалению, MS-DOS не предоставляет программам каких-либо существенных дополнительных возможностей по сравнению с функциями прерывания BIOS INT 16h. Поэтому многие программы работают с клавиатурой через BIOS.

Однако, если программа пользуется клавиатурными функциями MS-DOS, то ей доступно средство переназначения ввода операционной системы. Это возможно благодаря тому, что клавиатурные функции MS-DOS являются функциями, работающими со стандартным вводом MS-DOS, а стандартный ввод может быть переназначен.

Кроме того, некоторые клавиатурные функции автоматически посылают введенные символы на устройство стандартного вывода. По умолчанию это дисплей, но устройство стандартного вывода может быть переназначено для вывода в файл, на принтер или другое устройство.

Клавиатурные функции MS-DOS больше всего подходят для тех программ, которые ведут с оператором "построчный" диалог. Для таких программ при использовании средств переназначения ввода/вывода возможна организация автоматического "пакетного" выполнения, когда все сообщения выводятся в файл, а все данные, которые обычно вводятся с клавиатуры, считываются из заранее подготовленного файла "ответов".

Некоторые клавиатурные функции MS-DOS отслеживают комбинации клавиш Ctrl-C и Ctrl-Break. Если оператор ввел такую комбинацию клавиш, вызывается прерывание INT 23h, завершающее работу текущей программы. Если ваша программа не должна завершаться при нажатии этих комбинаций клавиш, можно либо создать и подключить собственный обработчик для INT 23h, либо использовать те клавиатурные функции MS-DOS, которые не выполняют проверку указанных выше комбинаций клавиш.

Далее приведено подробное описание клавиатурных функций прерывания MS-DOS INT 21h.

9.1. Буферизованный ввод с эхо-выводом

9.2. Буферизованный ввод без эхо-вывода

9.3. Нефильтрованный ввод без эхо-вывода

9.4. Ввод/вывод на консоль

9.5. Ввод строки символов

9.6. Проверка состояния стандартного ввода

9.7. Сброс буфера клавиатуры


Принципы
1. Принципы работы клавиатуры

Клавиатура выполнена, как правило, в виде отдельного устройства, подключаемого к компьютеру тонким кабелем. Малогабаритные компьютеры Lap-Top используют встроенную клавиатуру.

Внутри клавиатуры находится компьютер. Только этот компьютер состоит из одной микросхемы и выполняет специализированные функции. Он отслеживает нажатия на клавиши и посылает номер нажатой клавиши в центральный компьютер.

Если рассмотреть сильно упрощенную принципиальную схему клавиатуры, представленную на рисунке, можно заметить, что все клавиши находятся в узлах матрицы:

Рис.1. Упрощенная схема клавиатуры

Все горизонтальные линии матрицы подключены через резисторы к источнику питания +5 В. Клавиатурный компьютер имеет два порта - выходной и входной. Входной порт подключен к горизонтальным линиям матрицы (X0-X4), а выходной - к вертикальным (Y0-Y5).

Устанавливая по очереди на каждой из вертикальных линий уровень напряжения, соответствующий логическому 0, клавиатурный компьютер опрашивает состояние горизонтальных линий. Если ни одна клавиша не нажата, уровень напряжения на всех горизонтальных линиях соответствует логической 1 (т.к. все эти линии подключены к источнику питания +5 В через резисторы).

При нажатии на какую-либо клавишу, соответствующая вертикальная и горизонтальная линии окажутся замкнутыми. Когда на этой вертикальной линии процессор установит значение логического 0, то уровень напряжения на горизонтальной линии также будет соответствовать логическому 0.

Как только на одной из горизонтальных линий появится уровень логического 0, клавиатурный процессор фиксирует нажатие на клавишу. Он посылает в центральный компьютер запрос на прерывание и номер клавиши в матрице. Аналогичные действия выполняются и тогда, когда отпускается нажатая ранее клавиша.

Номер клавиши, посылаемый клавиатурным процессором, однозначно связан с распайкой клавиатурной матрицы и не зависит напрямую от обозначений, нанесенных на поверхность клавиш. Этот номер называется скан-кодом (Scan Code).

Слово scan ("сканирование"), подчеркивает тот факт, что клавиатурный компьютер сканирует клавиатуру для поиска нажатой клавиши.

Но программе нужен не порядковый номер нажатой клавиши, а соответствующий обозначению на этой клавише ASCII-код. Этот код не зависит однозначно от скан-кода, т.к. одной и той же клавише могут соответствовать несколько значений ASCII-кода. Это зависит от состояния других клавиш. Например, клавиша с обозначением '1' используется еще и для ввода символа '!' (если она нажата вместе с клавишей SHIFT).

Поэтому все преобразования скан-кода в ASCII-код выполняются программным обеспечением. Как правило, эти преобразования выполняют модули BIOS. Для использования символов кириллицы эти модули расширяются клавиатурными драйверами.

Если нажать на клавишу и не отпускать ее, клавиатура перейдет в режим автоповтора. В этом режиме в центральный компьютер автоматически через некоторый период времени, называемый периодом автоповтора, посылается код нажатой клавиши. Режим автоповтора облегчает ввод с клавиатуры большого количества одинаковых символов.

Следует отметить, что клавиатура содержит внутренний 16-байтовый буфер, через который она осуществляет обмен данными с компьютером.

В настоящее время существует три различных типа клавиатуры. Это клавиатура для компьютеров IBM PC/XT, 84-клавишная клавиатура для IBM AT и 101-клавишная (расширенная) клавиатура для IBM AT. Некоторые клавиатуры имеют переключатель режима работы (XT/AT), расположенный на нижней крышке. Он должен быть установлен в правильное положение.

Типичная упрощенная структурная схема электронной части клавиатуры показана на рис. 2.

Рис. 2. Структурная схема электронной части клавиатуры


Клавишные переключатели
2. Клавишные переключатели.

Технические и эргономические характеристики клавиатур ПЭВМ — удобство пользования, максимальная скорость набора, показатели надежности (например, количество переключении) и ряд других — во многом определяются техническими характеристиками клавишных переключателей. Важны форма и размер клавиш, шаг их расположения, величина хода, усилия нажатия, окраска, надписи и прочие характеристики.

В зависимости от требований, предъявляемых к клавиатурам, в них используются клавишные переключатели различных типов. По способу управления клавишные переключатели делятся на клавиши нажатия (тактильные) и прикосновения (сенсорные). Применяются как контактные (с электрическим контактом), так и бесконтактные переключатели.

Контактные переключатели, в которых электрическое замыкание и размыкание цепи электромеханического контакта происходит после нажатия клавиши, просты в конструкции, обеспечивают низкое омическое сопротивление контакта, дешевы. Однако такие переключатели не могут обеспечить в цепи четкого фронта сигнала замыкания (размыкания). В момент нажатия клавиши, стоящей в электрической цепи, происходит нерегулярное замыкание этой цепи («дребезг» контакта) до тех пор, пока не установится надежный сигнал. Влияние «дребезга» устраняют схемным либо программным путем. К недостаткам контактных переключателей можно отнести сравнительно малый срок службы (число переключений до отказа), непостоянство переходного сопротивления контакта вследствие окисления покрытий контактирующих поверхностей под воздействием окружающей среды или электроэрозии.

Рис. 3. Устройство герконового контактного клавишного переключателя: 1 — геркон; 2 — миниатюрный постоянный магнит; 3 — клавишный стержень

Лучшие показатели по долговечности дают герконовые переключатели (рис. 3), в них коммутация герметизированных контактов осуществляется под воздействием миниатюрного постоянного магнита, приводимого в движение клавишным стержнем.

В последние годы при изготовлении клавиатур ПЭВМ широко используются контактные переключатели на основе токопроводящей резины, в которых ряд элементов клавиши изготавливается из силиконовой резины. На нижней поверхности колпачка клавиши из непроводящей резины помещается прокладка из токопроводящей резины. Клавиши закрепляются на плате, на которой печатным способом выполнены необходимые электрические контакты и схемы их соединения. В момент нажатия клавиши токопроводящая резиновая прокладка прижимается к плате и замыкает необходимые контакты. Конструкции переключателей на основе токопроводящей резины обеспечивают, как правило, малый ход клавиш.

Рис 4. Устройство контактного клавишного переключателя мембранного типа:

1 — головка клавиши; 2 — возвратная пружина; 3 — элемент корпуса; 4 — гибкие печатные платы с контактами; 5 — металлическое основание; б — лавсановая изоляционная прокладка; 7 — контактная пружина

Мембранные клавиатуры (рис. 4) отличаются хорошей герметичностью, малыми размерами и массой, помехозащищенностью, малым «дребезгом», незначительным расходом драгоценных металлов. Они просты по конструкции, содержат минимальное число деталей, обладают высокой степенью автоматизации и возможностью крупносерийного производства. Мембранная клавиатура состоит из соединенных в пакет пластмассового корпуса и мембранной панели, состоящей из двух гибких лавсановых контактных пластин (печатных плат) с металлизированными токопроводящими головками, являющимися контактирующими и токоведущими частями переключателя. Гибкие печатные платы изолированы друг от друга диэлектрической пластиной и находятся на металлическом основании. При нажатии на клавишу усилие через демпфирующую пружину, расположенную в корпусе, передается на гибкие печатные платы, замыкая их контакты между собой. С помощью пружины клавиша возвращается в исходное положение. Несмотря на высокую технологичность и другие достоинства, мембранные клавиатуры до сих пор находят ограниченное применение в профессиональных ПЭВМ. Это связано прежде всего с трудностями размещения в корпусе клавиатуры электронной части, а также ее низкой ремонтопригодностью.

В случае, когда требуется обеспечить высокую надежность работы, бесшумную эксплуатацию, а также устойчивость против влаги, коррозии, пыли, а стоимость не играет определяющей роли, в конструкциях клавиатур применяются бесконтактные клавишные переключатели.

Рис. 5. Устройство бесконтактного клавишного переключателя емкостного типа:

1 — клавиша; 2 — металлическая пластина; 3 — изолятор; 4 — обкладки печатного конденсатора; G — высокочастотный генератор; VT — транзистор.

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

Рис. 6. Устройство бесконтактного клавишного переключателя индуктивного типа:1 — направляющая; 2 • — подвижный шток; 3 — клавиша; 4 — подвижная металлическая пластина; 5 — пружина;6 — печатная индуктивность; 7 — защитная пленка.

В клавишном переключателе, использующем изменение емкости при нажатии и включении его в схему (рис. 5.) на печатной плате нанесены в виде прямоугольных пластинок обкладки конденсатора, сверху на обкладки нанесен слой изолятора, например лавсановая пленка. На одну из обкладок от генератора подается специальный сигнал, например частотой 200 кГц и амплитудой до 100 В. При нажатии на клавишу соединенная с ней металлическая пластина опускается на обкладки конденсатора, в результате его емкостное сопротивление уменьшается и на второй обкладке появляется сигнал, поступающий на электронную схему.

Клавишный переключатель индуктивного типа (рис.6) состоит из неподвижной части (направляющей) и подвижной (штока, на одном конце которого находится подвижная часть датчика — металлическая пластина, которая прижимается к штоку за счет пружины).

На другом конце на шток насажена клавиша. Неподвижная часть датчика электрически представляет собой индуктивность и выполнена печатным способом. Для предотвращения механического износа эта часть защищается склеивающей лентой. При нажатии на клавишу металлическая пластина приближается к индуктивности, вызывая уменьшение значения последней. При изменении индуктивности формируется сигнал о срабатывании датчика. Клавиша возвращается в исходное состояние за счет пружины, прижимающей металлическую пластину к штоку.

В бесконтактных переключателях, управляемых магнитным полем, эффект включения может достигаться изменением сопротивления магниторезистивного элемента под действием постоянного магнита, укрепляемого на подвижном стержне клавиши. Вместо магниторезистивных элементов могут быть применены также датчики Холла.

В оптоэлектронных клавишных переключателях нажатие клавиши приводит к вводу заслонки между источником излучения (обычно светодиодом) и приемником излучения (фотодиодом). Характеристики оптоэлектронных переключателей близки к характеристикам переключателей, управляемых магнитным полем.

В ряде клавиатур ПЭВМ используются сенсорные переключатели, которые не имеют подвижных механических частей (отсутствует ход клавиши). Прикосновение руки пользователя к клавише сразу вызывает переключение. Работа с такой клавиатурой требует от пользователя определенных навыков и обязательно звуковой и световой обратной связи.


Интерфейс клавиатуры. Разъемы
3. Интерфейс клавиатуры. Разъемы

Для подключения клавиатуры предназначен последовательный интерфейс, состоящий из двух обязательных сигналов DATA (данные) и CLK (синхроимпульсы). Необязательный сигнал RESET сбрасывает клавиатуру низким уровнем сигнала.

При разрешении передачи данных они передаются в ПЭВМ по шине данных последовательно побайтно начиная с младшего бита. При отсутствии разрешения передачи в ПЭВМ код клавиши запоминается в буфере. Выдача кодов осуществляется в той же последовательности, что и запись. Каждый передаваемый бит информации сопровождается синхроимпульсом.

Микроконтроллер 8042 обеспечивает двунаправленный интерфейс с клавиатурой. Передача информации к клавиатуре используется для управления индикаторами ее состояния и, программирования параметров (автоповтор, набор скан-кодов).

Хотя электрический интерфейс клавиатур XT и AT совпадает (за исключением возможности двунаправленного обмена в AT), логические форматы посылок существенно отличаются. POST способен производить диагностику клавиатуры, причем подключение клавиатуры неподходящего типа или не подключенную клавиатуру он воспримет как ошибку. Если проверка клавиатуры разрешена в BIOS Setup, то по этой ошибке POST будет сколь угодно долго дожидаться получения кода нажатия клавиши F1.

Большинство IBM-совместимых моделей ПЭВМ используют стандартные пятиконтактные разъемные соединители типа DIN (отечественный аналог ОНЦ-ВГ-4А-5/16-В по ГОСТ 12368—89) для подключения клавиатуры к системному блоку: контакт 1 — синхроимпульсы, такт (CLK); 2 — данные (DATA); 3 — резерв; 4 — земля (GND); 5 — «+5 В» (VCC). В оригинальных моделях семейства PS/2 и более новых фирма IBM использует шестиконтактные DIN-разъемные соединители (mini-DIN): 1 — данные; 2, 6 — резерв; 3 — земля;4 — «+5 В»; 5 — синхроимпульсы, такт.

Рис. 7. Разъемы подключения клавиатур XT, AT, PS/2 (вид со стороны контактов):а-Din; б-mini-Din.

Электрически и логически интерфейс клавиатуры PS/2 повторяет интерфейс клавиатуры AT, поэтому для согласования типа разъема применяют специальные переходники. Предпочтительнее использовать переходники, выполненные в виде мягкого кабеля с разъемами. Монолитный переходник, особенно с АТ-клавиатуры на PS/2-разъем системной платы, хуже тем, что малейшее движение кабеля вызывает большой момент силы, выламывающей переходник из маленького гнезда PS/2.

Вид разъемов клавиатур (со стороны задней панели) и назначение контактов приведены на рис. 7.

Питание от разъема клавиатуры часто используется такими устройствами, как внешние накопители или адаптеры локальных сетей, подключаемыми к параллельному порту. Плавкий предохранитель, установленный на системной плате, может и не выдерживать броска тока, потребляемого этими внешними устройствами, При этом, естественно, откажется работать и клавиатура — ее индикаторы и не мигнут при включении, как это происходит при ее инициализации, Находится эта неисправность при наличии тестера (и знания возможной причины) достаточно легко.


Формат передачи данных
4.Формат передачи данных

Обмен данными между клавиатурой и ПЭВМ может осуществляться с помощью 9- или 11-разрядных кодовых комбинаций.

При 9-разрядном обмене (XT-клавиатура) 1 бит стартовый, последующие — данные; при 11-разрядном обмене дополнительно добавляются бит паритета и стоповый бит. От клавиатуры в ПЭВМ передается информация: об изменении состояния клавиши и клавиатуры, о сбоях в работе клавиатуры и результатах самотестирования. Прием данных от клавиатуры должен осуществляться в диапазоне между положительным и отрицательным фронтами синхроимпульса. Период следования импульсов тактовой частоты — от 50 мкс до 1 мс.

Клавиатура PC AT передает и принимает данные в 11-разрядном формате. Контроллер 8042 автоматически определяет тип клавиатуры по формату данных. Первый разряд - стартовый, за ним следуют восемь информационных разрядов, разряд паритета и стоповый разряд. Посылка данных синхронизируется клавиатурой. В конце передачи контроллер клавиатуры блокирует интерфейс до тех пор, пока система не примет полученный байт. Если байт данных получен с ошибкой паритета, в клавиатуру автоматически отсылается команда RESEND.

На рис. 8 показаны 11-разрядный формат и примеры передачи данных.

Примечание: клавиатура сбрасывает стоповый разряд линии данных в конце их посылки для
подтверждения передачи.

Рис. 8. 11-разрядные форматы данных


Контроллер клавиатуры
5. Контроллер клавиатуры

В архитектуре PC AT новое качество в сравнении с PC XT приобрел контроллер клавиатуры- однокристальный микрокомпьютер типа 8042, который представляет собой контроллер универсального периферийного интерфейса (UPI) и обеспечивает выполнение следующих функций:

управление определенными системными функциями и интерфейсом клавиатуры;

чтение информации о конфигурации системы для процедур BIOS.

В контроллере 8042 имеется внутренняя ROM, которая программируется с учетом кодов сканирования клавиатуры и рабочих команд. Контроллер 8042 взаимодействует с клавиатурой в двунаправленном последовательном формате с синхронизацией данных. Контроллер 8042 последовательно принимает данные, проверяет их паритет, преобразует скан-коды в системные коды и прерывает МП для передачи данных системе.

Кроме управления клавиатурой, через программно-управляемые и программно-читаемые линии внешних портов контроллера формируются сигналы управления вентилем Gate A20, аппаратного системного сброса и считываются сигналы от конфигурационных джамперов системной платы.

На рис. 9 приведена блок-схема контроллера клавиатуры.

Рис. 9. Блок-схема контроллера клавиатуры

Контроллер 8042 подключается к системе через шину периферийных устройств XD при помощи программно-доступных входного и выходного буферов, которые представляют собой два буфера шины данных: один для ввода и один для вывода. На рис. 10 изображена схема подключения контроллера 8042 к шине ХD.

Рис. 10. Схема подключения контроллера 8042 к шине XD

Выходной буфер представляет собой 8-разрядный регистр, который доступен системе только как читаемый порт с адресом 60h. Контроллер 8042 использует выходной буфер для передачи системе кодов сканирования, полученных от клавиатуры, и байтов данных, прочитанных по команде системы. Выходной буфер должен быть прочитан только после того, как установлен признак " буфер полон" (разряд 0 регистра состояния - 8-разрядного регистра, который доступен системе как читаемый порт 64h).

Входной буфер представляет собой 8-разрядный регистр, который доступен системе только как записываемый порт с адресом 60h или 64h. Операция записи по адресу 60h устанавливает флажок, который указывает на последующую запись данных. Запись по адресу 64h устанавливает флажок, который указывает на последующую запись команды. Данные, записанные по адресу 60h, отсылаются клавиатуре, если не являются командой для контроллера. Данные должны быть записаны во входной буфер только после того, как сброшен признак " буфер полон" (разряд 1 регистра состояния).

Контроллер 8042 и клавиатура связаны четырехпроводным экранированным кабелем, включающим линию питания (+5 В), линию заземления, линии сигнала данных и сигнала синхронизации.

Контроллер 8042 и клавиатура взаимодействуют с помощью механизма квитирования, используя линии данных и синхронизации для синхронного последовательного интерфейса.

Клавиатура обеспечивает синхронизирующий сигнал для передачи данных в каждом из направлений.


Порты
6 Порты для работы с клавиатурой

Для работы с клавиатурой типа PC/XT используются порты с адресами 60h и 61h.

Порт 60h при чтении содержит скан-код последней нажатой клавиши.

Порт 61h управляет не только клавиатурой, но и другими устройствами компьютера, например, работой встроенного динамика. Этот порт доступен как для чтения, так и для записи. Для нас важен самый старший бит этого порта. Если в старший бит порта 61h записать значение 1, клавиатура будет заблокирована, если 0 - разблокирована.

Так как порт 61h управляет не только клавиатурой, при изменении содержимого старшего бита необходимо сохранить состояние остальных битов этого порта. Для этого можно сначала выполнить чтение содержимого порта в регистр, изменить состояние старшего бита, затем выполнить запись нового значения в порт:

          .........

        in      al, 61h

        or      al, 80h

        out     61h, al

          .........

Компьютер типа IBM AT позволяет управлять скоростными характеристиками клавиатуры, а также зажигать или гасить светодиоды на лицевой панели клавиатуры - Scroll Lock, Num Lock, Caps Lock.

Для расширенного управления клавиатурой используется порт 60h в режиме записи. Этот порт используются для управления подчиненным процессором Intel 8042, ответственным за обмен данными с клавиатурным компьютером.

При использовании порта 60h на запись программа дополнительно получает следующие возможности:

•	 установка времени ожидания перед переходом клавиатуры в режим автоповтора;

•	 установка периода генерации скан-кода в режиме автоповтора;

•	 управление светодиодами, расположенными на лицевой панели клавиатуры - Scroll Lock, Num Lock, Caps Lock.

Процессор 8042 обслуживает не только клавиатуру, но и другие системы компьютера. Через порт 64h, например, выполняется сброс (отключение) процессора 80286 для возврата из защищенного режима работы в реальный.

Для посылки команды процессору 8042 вначале необходимо убедиться в том, что его внутренняя очередь команд пуста. Это можно сделать, прочитав слово состояния 8042 из порта с адресом 64h. Бит с номером 1 должен быть равен нулю.

Далее приведен фрагмент программы, составленной на языке ассемблера, проверяющий состояние очереди команд процессора 8042:

                ..........

        mov     cx,0               ; счетчик для ограничения времени

                                                ; ожидания готовности 8042

wait_loop:

; читаем порт состояния процессора 8042

        in      al,64h

        and     al,00000010b  ; флаг готовности

; ожидаем готовность процессора 8042

        loopnz  wait_loop

                                                ; к приему команды

                ..........

После того, как программа дождется готовности процессора 8042, она может послать ему команду, записав ее в порт с адресом 60h:

                ..........

        mov     al,cmd             ; команда для 8042

        out     60h ,al            ; вывод команды в 8042

                ..........

Некоторые команды состоят более чем из одного байта. Остальные байты команды необходимо записать в порт 60h, предварительно убедившись в готовности процессора 8042 с помощью последовательности команд, приведенной выше. В большинстве случаев можно также использовать простую временную задержку:

                ..........

        mov     al, cmd_byte1

        out     60h, al

        mov     cx, 2000h

wait_loop: loop wait_loop

        mov     al, cmd_byte2

        out     60h, al

                ..........

Ниже приведен формат двух команд процессора 8042, имеющих отношение к работе с клавиатурой - команду установки задержки и периода автоповтора и команду управления светодиодами, расположенными на клавиатуре.

Для установки характеристик режима автоповтора в порт 60h необходимо записать код команды 0F3h, затем байт, определяющий характеристики режима:

Биты    Значение

0-4     Период автоповтора:

           0 - 30.0;       0Ah - 10.0;

           1 - 26.7;       0Dh -  9.2;

           2 - 24.0;       10h -  7.5;

           4 - 20.0; 14h -  5.0;

           8 - 15.0;       1Fh -  2.0.

        Период автоповтора определяет количество

        посылок скан-кода, генерируемых процессором

        клавиатуры в одну секунду. Можно использовать не

        только те значения, которые приведены выше,

        но и промежуточные, например, 9 или 15h.

5-6     Задержка включения режима автоповтора:

            00 - 250 мс;

            01 - 500 мс;

            10 - 750 мс;

            11 - 1000 мс.

7       Зарезервировано, должно быть равно 0.

Первоначально при инициализации системы период задержки для включения режима автоповтора устанавливается модулями BIOS равным 500 мс при периоде автоповтора, равном 10 повторам в секунду. Если это слишком медленно для вас, вы можете установить другие значения. Некоторые прикладные программы, например, текстовый процессор Microsoft Word, содержат средства для управления временными характеристиками клавиатуры.

Для управления светодиодами, расположенными на лицевой панели клавиатуры, используется команда 0EDh. Вслед за этой командой в порт 60h необходимо записать байт, имеющий следующий формат:

Биты    Значение

0       1 - включить светодиод Scroll Lock;

1       1 - включить светодиод Num Lock;

2       1 - включить светодиод Caps Lock;

3-7     не используются.


Аппаратное прерывание клавиатуры
7 Аппаратное прерывание клавиатуры

Клавиатура подключена к линии прерывания IRQ1. Этой линии соответствует прерывание INT 09h.

Клавиатурное прерывание обслуживается модулями BIOS. Драйверы клавиатуры и резидентные программы могут организовывать дополнительную обработку прерывания INT 09h. Для этого может быть использована цепочка обработчиков прерывания.

Как работает стандартный обработчик клавиатурного прерывания, входящий в состав BIOS?

Этот обработчик выполняет следующие действия:

•	читает из порта 60h скан-код нажатой клавиши;

•	записывает вычисленное по скан-коду значение ASCII-кода нажатой клавиши в специальный буфер клавиатуры, расположенный в области данных BIOS;

•	устанавливает в 1 бит 7 порта 61h, разрешая дальнейшую работу клавиатуры;

•	возвращает этот бит в исходное состояние;

•	записывает в порт 20h значение 20h для правильного завершения обработки аппаратного прерывания.

Обработчик прерывания INT 09h не просто записывает значение ASCII-кода в буфер клавиатуры. Дополнительно отслеживаются нажатия таких комбинаций клавиш, как Ctrl-Alt-Del, обрабатываются специальные клавиши PrtSc и SysReq. При вычислении кода ASCII нажатой клавиши учитывается состояние клавиш Shift и CapsLock.

Буфер клавиатуры имеет длину 32 байта и расположен по адресу 0000h:041Eh для машин IBM PC/XT.

В IBM AT и PS/2 расположение клавиатурного буфера задается содержимым двух слов памяти с адресами 0000h:0480h (компонента смещения адреса начала буфера) и 0000h:0482h (смещение конца буфера). Обычно в IBM AT эти ячейки памяти содержат значения, соответственно, 001Eh и 003Eh. Так как смещения заданы относительно сегментного адреса 0040h, то видно, что обычное расположение клавиатурного буфера в IBM AT и PS/2 соответствует его расположению в IBM PC/XT.

Клавиатурный буфер организован циклически. Это означает, что при его переполнении самые старые значения будут потеряны. Две ячейки памяти, находящиеся в области данных BIOS с адресами 0000h:041Ah и 0000h:041Ch содержат, соответственно, указатели на начало и конец буфера. Если значения этих указателей равны друг другу, буфер пуст. (Можно удалить все символы из буфера клавиатуры, установив оба указателя на начало буфера. Однако есть более предпочтительный способ с использованием прерывания BIOS INT 16h).

Указателями на начало и конец клавиатурного буфера обычно управляют обработчики прерываний INT 09h и INT 16h.

Программа извлекает из буфера коды нажатых клавиш, используя различные функции прерывания INT 16h.

Помимо управления содержимым буфера клавиатуры, обработчик прерывания INT 09h отслеживает нажатия на так называемые переключающие клавиши - NumLock, ScrollLock, CapsLock, Ins. Состояние этих клавиш записывается в область данных BIOS в два байта с адресами 0000h:0417h и 0000h:0418h.

Формат байта 0000h:0417h:

Биты    Значение

0       Нажата правая клавиша Shift.

1       Нажата левая клавиша Shift.

2       Нажата комбинация клавиш Ctrl-Shift с любой

        стороны.

3       Нажата комбинация клавиш Alt-Shift с любой

        стороны.

4       Состояние клавиши ScrollLock.

5       Состояние клавиши NumLock.

6       Состояние клавиши CapsLock.

7       Состояние клавиши Insert.

Формат байта 0000h:0418h:

Биты    Значение

0       Нажата левая клавиша Shift вместе с клавишей

        Ctrl.

1       Нажата левая клавиша Shift вместе с клавишей

        Alt.

2       Нажата клавиша SysReq.

3       Состояние клавиши Pause.

4       Нажата клавиша ScrollLock.

5       Нажата клавиша NumLock.

6       Нажата клавиша CapsLock.

7       Нажата клавиша Insert.

Программой обработки прерывания INT 09h отслеживаются некоторые комбинации клавиш. В таблице приведены эти комбинации и действия, выполняемые обработчиком прерывания при их обнаружении:

Комбинация клавиш   Выполняемые действия

Ctrl-Alt-Del        Сброс и перезагрузка системы.

Ctrl-NumLock,       Перевод машины в состояние ожидания

Pause               до нажатия любой клавиши.

Shift-PrtSc         Распечатка на принтере содержимого

                    видеопамяти.

Ctrl-Break          Выполнение прерывания INT 1Bh,

                    завершающего работу программы.

Многие типы клавиатур имеют отдельную альтернативную цифровую панель, напоминающую клавиатуру калькулятора. Если одновременно с нажатием на клавишу Alt набрать число на этой панели (не большее, чем 255 и не равное 0), то это число будет помещено в буфер клавиатуры, как будто бы оно было введено нажатием на одну клавишу. Это число будет также записано в слове по адресу 0000h:0419h в области данных BIOS.

При переполнении внутреннего буфера клавиатуры или буфера, расположенного в области данных BIOS, программа-обработчик прерывания INT 09h генерирует звуковой сигнал.

При составлении программ для MS-DOS у вас едва ли появится необходимость непосредственного манипулирования содержимым буфера клавиатуры - вы можете использовать прерывание BIOS INT 16h для выполнения практически всех клавиатурных операций.

В следующем разделе будут изучены непосредственно средства работы с клавиатурой, предоставляемые в распоряжение прерыванием BIOS INT 16h.


Чтение символа с ожиданием
8.1. Чтение символа с ожиданием

Функция 00h выполняет чтение кода символа из буфера клавиатуры, если он там есть. Если буфер клавиатуры пуст, программа переводится в состояние ожидания до тех пор, пока не будет нажата какая-нибудь клавиша. Скан-код и ASCII-код нажатой клавиши передаются программе.

Формат вызова функции:

На входе:       AH = 00h

На выходе:      AL = ASCII-код символа или 0, если AH содержит

                расширенный ASCII-код символа;

                AH = скан-код или расширенный ASCII-код

                символа, если AL=0;

Таблица скан-кодов для клавиатуры IBM PC/XT:

----------T----------T------------T-------------T---------------¬

¦01   Esc ¦12   E    ¦23   H      ¦34   . >     ¦45   NumLock   ¦

¦02   1 ! ¦13   R    ¦24   J      ¦35   / ?     ¦46   ScrollLock¦

¦03   2 @ ¦14   T    ¦25   K      ¦36 Shft(прав)¦47   Home [7]  ¦

¦04   3 # ¦15   Y    ¦26   L      ¦37   * PrtSc ¦48   Up   [8]  ¦

¦05   4 $ ¦16   U    ¦27   ; :    ¦38   Alt     ¦49   PgUp [9]  ¦

¦06   5 % ¦17   I    ¦28   " '    ¦39   Пробел  ¦4a   K -       ¦

¦07   6 ^ ¦18   O    ¦29   ` ~    ¦3a   CapsLock¦4b   <-   [4]  ¦

¦08   7 & ¦19   P    ¦2a Shft(лев)¦3b   F1      ¦4c        [5]  ¦

¦09   8 * ¦1a   [ {  ¦2b   \ |    ¦3c   F2      ¦4d   ->   [6]  ¦

¦0a   9 ( ¦1b   ] }  ¦2c   Z      ¦3d   F3      ¦4e   K +       ¦

¦0b   0 ) ¦1c   Enter¦2d   X      ¦3e   F4      ¦4f   End  [1]  ¦

¦0c   - _ ¦1d   Ctrl ¦2e   C      ¦3f   F5      ¦50   Dn   [2]  ¦

¦0d   + = ¦1e   A    ¦2f   V      ¦40   F6      ¦51   PgDn [3]  ¦

¦0e   Bksp¦1f   S    ¦30   B      ¦41   F7      ¦52   Ins  [0]  ¦

¦0f   Tab ¦20   D    ¦31   N      ¦42   F8      ¦53   Del  [.]  ¦

¦10   Q   ¦21   F    ¦32   M      ¦43   F9      ¦               ¦

¦11   W   ¦22   G    ¦33   , <    ¦44   F10     ¦               ¦

L---------¦----------¦------------¦-------------¦----------------

Для остальных клавиш функция 00h прерывания INT 16h возвращает расширенный ASCII-код:

г--------T--------------T--------------T-------------¬

¦ F1   3b¦ Shift-F1   54¦ Ctrl-F1   5e ¦ Alt-F1   68 ¦

¦ F2   3c¦ Shift-F2   55¦ Ctrl-F2   5f ¦ Alt-F2   69 ¦

¦ F3   3d¦ Shift-F3   56¦ Ctrl-F3   60 ¦ Alt-F3   6a ¦

¦ F4   3e¦ Shift-F4   57¦ Ctrl-F4   61 ¦ Alt-F4   6b ¦

¦ F5   3f¦ Shift-F5   58¦ Ctrl-F5   62 ¦ Alt-F5   6c ¦

¦ F6   40¦ Shift-F6   59¦ Ctrl-F6   63 ¦ Alt-F6   6d ¦

¦ F7   41¦ Shift-F7   5a¦ Ctrl-F7   64 ¦ Alt-F7   6e ¦

¦ F8   42¦ Shift-F8   5b¦ Ctrl-F8   65 ¦ Alt-F8   6f ¦

¦ F9   43¦ Shift-F9   5c¦ Ctrl-F9   66 ¦ Alt-F9   70 ¦

¦ F10  44¦ Shift-F10  5d¦ Ctrl-F10  67 ¦ Alt-F10  71 ¦

L--------¦--------------¦--------------¦--------------

г----------T----------T-------------T-------------¬

¦ Alt-A  1e¦ Alt-P  19¦ Alt-3     7a¦ Down  Dn  50¦

¦ Alt-B  30¦ Alt-Q  10¦ Alt-4     7b¦ Left  <-  4b¦

¦ Alt-C  2e¦ Alt-R  13¦ Alt-5     7c¦ Right ->  4d¦

¦ Alt-D  20¦ Alt-S  1f¦ Alt-6     7d¦ Up    Up  48¦

¦ Alt-E  12¦ Alt-T  14¦ Alt-7     7e¦ End       4f¦

¦ Alt-F  21¦ Alt-U  16¦ Alt-8     7f¦ Home      47¦

¦ Alt-G  22¦ Alt-V  2f¦ Alt-9     80¦ PgDn      51¦

¦ Alt-H  23¦ Alt-W  11¦ Alt--     82¦ PgUp      49¦

¦ Alt-I  17¦ Alt-X  2d¦ Alt-=     83¦             ¦

¦ Alt-J  24¦ Alt-Y  15¦             ¦ ^Left     73¦

¦ Alt-K  25¦ Alt-Z  2c¦             ¦ ^Right    74¦

¦ Alt-L  26¦          ¦ Shift-Tab 0f¦ ^End      75¦

¦ Alt-M  32¦ Alt-0  81¦ Ins       52¦ ^Home     77¦

¦ Alt-N  31¦ Alt-1  78¦ Del       53¦ ^PgDn     76¦

¦ Alt-O  18¦ Alt-2  79¦ ^PrtSc    72¦ ^PgUp     84¦

L----------¦----------¦-------------¦--------------

Скан-коды клавиш, имеющихся только на 101-клавишной клавиатуре:

г-------------T------------------T------------------¬

¦ F11       85¦ Alt-Bksp      0e ¦  Alt- Д /      a4¦

¦ F12       86¦ Alt-Enter     1c ¦  Alt- Д *      37¦

¦ Shft-F11  87¦ Alt-Esc       01 ¦  Alt- Д -      4a¦

¦ Shft-F12  88¦ Alt-Tab       a5 ¦  Alt- Д +      4e¦

¦ Ctrl-F11  89¦ Ctrl-Tab      94 ¦  Alt- Д Enter  a6¦

¦ Ctrl-F12  8a¦                  ¦                  ¦

¦ Alt-F11   8b¦ Alt-up     Up 98 ¦ Ctrl- Д /      95¦

¦ Alt-F12   8c¦ Alt-down   Dn a0 ¦ Ctrl- Д *      96¦

¦ Alt-[     1a¦ Alt-left   <- 9b ¦ Ctrl- Д -      8e¦

¦ Alt-]     1b¦ Alt-right  -> 9d ¦ Ctrl- Д +      90¦

¦ Alt-;     27¦                  ¦                  ¦

¦ Alt-'     28¦ Alt-Delete    a3 ¦ Ctrl- Д Up [8] 8d¦

¦ Alt-`     29¦ Alt-End       9f ¦ Ctrl- Д 5  [5] 8f¦

¦ Alt-\     2b¦ Alt-Home      97 ¦ Ctrl- Д Dn [2] 91¦

¦ Alt-,     33¦ Alt-Insert    a2 ¦ Ctrl- Д Ins[0] 92¦

¦ Alt-.     34¦ Alt-PageUp    99 ¦ Ctrl- Д Del[.] 93¦

L-------------¦------------------¦-------------------

Буква "Д" в последней таблице обозначает дополнительную ("калькуляторную") клавиатуру.


Проверка буфера на наличие в нем символов
8.2. Проверка буфера на наличие в нем символов

На входе:       AH = 01h.

На выходе:      ZF = 0, если в буфере имеется код нажатой

                        на клавиатуре клавиши;

                ZF = 1, если буфер клавиатуры пуст;

                AL = ASCII-код символа или 0, если AH содержит

                      расширенный ASCII-код символа;

                AH = скан-код или расширенный ASCII-код

                      символа, если AL=0.

Функция 01h поможет вам проверить состояние буфера клавиатуры - есть там коды нажатых клавиш или нет. При этом программа не переводится в состояние ожидания, даже если буфер клавиатуры пуст. В этом случае в регистре флагов устанавливается в единицу флаг ZF и управление возвращается программе.

Эту функцию удобно использовать во время выполнения какого-либо длительного процесса (например, форматирования диска или передачи данных по линии связи) для прерывания этого процесса по запросу оператора.

Кроме того, функцию можно использовать вместе с функцией 00h для сброса содержимого клавиатурного буфера. Для этого в цикле повторяют вызов функции 01h, вслед за которым идет вызов функции 00h при условии, что буфер клавиатуры не пуст. Сброс клавиатурного буфера полезно выполнять перед вводом ответственной информации, так как из-за случайного двойного или тройного нажатия на клавишу в буфере клавиатуры могут оказаться лишние символы.


Получение состояния переключающих клавиш
8.3. Получение состояния переключающих клавиш

На входе:       AH = 02h

На выходе:      AL = Байт состояния переключающих клавиш

Функция возвращает в регистре AL состояние переключающих клавиш (Shift, Ctrl, Alt, ScrollLock, NumLock, CapsLock, Ins). Формат байта состояния соответствует формату байта, находящегося в области данных BIOS по адресу 0000h:0417h:

Биты    Значение

0       Нажата правая клавиша Shift.

1       Нажата левая клавиша Shift.

2       Нажата комбинация клавиш Ctrl-Shift с любой

        стороны.

3       Нажата комбинация клавиш Alt-Shift с любой

        стороны.

4       Состояние клавиши ScrollLock.

5       Состояние клавиши NumLock.

6       Состояние клавиши CapsLock.

7       Состояние клавиши Insert.

Функция может быть использована для анализа текущего состояния переключающих клавиш.


Установка временных характеристик клавиатуры
8.4. Установка временных характеристик клавиатуры

На входе:       AH = 03h;

                AL = 05h;

                BL = Период автоповтора (количество повторов

                     за одну секунду):

                        0 - 30.0;       0Ah - 10.0;

                        1 - 26.7;       0Dh -  9.2;

                        2 - 24.0;       10h -  7.5;

                        4 - 20.0; 14h -  5.0;

                        8 - 15.0;       1Fh -  2.0.

                BH =    Задержка включения режима автоповтора:

                        0 - 250 мс;

                        1 - 500 мс;

                        2 - 750 мс;

                        3 - 1000 мс.

На выходе:      Не используются.

Мы уже рассказывали о возможности изменения временных характеристик клавиатуры. Если BIOS, установленная в вашей машине, изготовлена после 15 декабря 1985 года, вы можете воспользоваться этой функцией для ускорения (или замедления) работы клавиатуры.


Запись символов в буфер клавиатуры
8.5. Запись символов в буфер клавиатуры

На входе:       AH = 05h;

                CL = ASCII-код записываемого символа;

                CH = скан-код записываемого символа, или 0.

На выходе:      AL = 0  - запись выполнена успешно;

                1       - буфер клавиатуры переполнен.


Чтение символа с ожиданием для 101-клавишной клавиатуры
8.6 Чтение символа с ожиданием для 101-клавишной клавиатуры

Функция 10h полностью аналогична функции 00h, но она предназначена для работы с клавиатурой, имеющей 101 клавишу.

Формат вызова функции:

На входе:       AH = 10h.

На выходе:      AL = ASCII-код символа или 0, если AH содержит

                расширенный ASCII-код символа;

                AH = скан-код или расширенный ASCII-код

                символа, если AL=0.

Функция определена для BIOS, изготовленной не раньше 15 декабря 1985 года.


Проверка буфера на наличие в нем символов для 101-клавишной клавиатуры
8.7. Проверка буфера на наличие в нем символов для 101-клавишной клавиатуры

На входе:       AH = 11h.

На выходе:      ZF = 0, если в буфере имеется код нажатой

                        на клавиатуре клавиши;

                ZF = 1, если буфер клавиатуры пуст;

                AL = ASCII-код символа или 0, если AH содержит

                        расширенный ASCII-код символа;

                AH = скан-код или расширенный ASCII-код

                        символа, если AL=0.

Функция 11h полностью аналогична функции 01h, но она предназначена для работы с клавиатурой, имеющей 101 клавишу.

Эта функция определена для BIOS, изготовленной не раньше 15 декабря 1985 года.


Получение состояния переключающих клавиш для 101-клавишной клавиатуры
8.8. Получение состояния переключающих клавиш для 101-клавишной клавиатуры

На входе:       AH = 12h.

На выходе:      AL = Байт состояния переключающих клавиш.

Функция возвращает в регистре AL состояние переключающих клавиш (Shift, Ctrl, Alt, ScrollLock, NumLock, CapsLock, Ins):

Биты    Значение

0       Нажата левая клавиша Shift вместе с Ctrl.

1       Нажата левая клавиша Shift вместе с Alt.

2       Нажата правая клавиша Shift вместе с Ctrl.

3       Нажата правая клавиша Shift вместе с Alt.

4       Нажата клавиша ScrollLock.

5       Нажата клавиша NumLock.

6       Нажата клавиша CapsLock.

7       Нажата клавиша SysReq.

Функция 12h аналогична функции 02h, но она предназначена для работы с клавиатурой, имеющей 101 клавишу и имеет другой формат байта состояния.

Эта функция определена для BIOS, изготовленной не раньше 15 декабря 1985 года.


Буферизованный ввод с эхо-выводом
9.1. Буферизованный ввод с эхо-выводом

На входе:       AH = 01h.

На выходе:      AL = ASCII-код символа или 0. Если регистр

                содержит 0, то следующий вызов этой же

                функции возвратит в регистре AL

                расширенный ASCII-код символа.

                Функция проверяет комбинации клавиш

                Ctrl-C и Ctrl-Break.

Функция читает символы со стандартного устройства ввода. Если стандартным устройством ввода является клавиатура, и буфер клавиатуры пуст, выполнение программы задерживается до нажатия на любую клавишу.

Введенный символ выводится на стандартное устройство вывода.

Если программа в качестве ASCII-кода получила 0, она должна вызвать эту функцию еще один раз. Во второй раз регистр AL будет содержать расширенный ASCII-код нажатой клавиши.


Буферизованный ввод без эхо-вывода
9.2. Буферизованный ввод без эхо-вывода

На входе:       AH = 08h.

На выходе:      AL = ASCII-код символа или 0. Если регистр

                содержит 0, то следующий вызов этой же

                функции возвратит в регистре AL

                расширенный ASCII-код символа.

                Функция проверяет комбинации клавиш

                Ctrl-C и Ctrl-Break.

Функция аналогична предыдущей. Она читает символы со стандартного устройства ввода. Если стандартным устройством ввода является клавиатура, и буфер клавиатуры пуст, выполнение программы задерживается до нажатия на любую клавишу.

Эту функцию необходимо использовать в тех случаях, когда не требуется автоматически дублировать на экране вводимые с клавиатуры символы. Например, с ее помощью можно организовать ввод паролей.


Нефильтрованный ввод без эхо-вывода
9.3. Нефильтрованный ввод без эхо-вывода

На входе:       AH = 07h.

На выходе:      AL = ASCII-код символа или 0. Если регистр

                содержит 0, то следующий вызов этой же

                функции возвратит в регистре AL

                расширенный ASCII-код символа.

                Функция не проверяет комбинации клавиш

                Ctrl-C и Ctrl-Break.

Если буфер клавиатуры пуст, выполнение программы задерживается до нажатия на любую клавишу.

Эту функцию удобно использовать в тех случаях, когда завершение программы по нажатию комбинаций клавиш Ctrl-C или Ctrl-Break по тем или иным причинам нежелательно. Например, программа держит в оперативной памяти буфера для данных, которые перед завершением работы обязательно должны быть записаны на диск. Если оператор в неподходящий момент времени нажал Ctrl-C и программа аварийно завершила работу, содержимое буферов будет потеряно.


Ввод/вывод на консоль
9.4. Ввод/вывод на консоль

На входе:       AH = 06h;

                DL = 0FFh - для ввода символа с консоли;

                  или:

                DL = код символа, не равный 0FFh - для

                  вывода символа на консоль.

На выходе:      ZF = 0, если в буфере имеется код нажатой

                        на клавиатуре клавиши;

                ZF = 1, если буфер клавиатуры пуст;

                AL = ASCII-код символа или 0, если AH содержит

                   расширенный ASCII-код символа.

                Функция проверяет комбинации клавиш

                Ctrl-C и Ctrl-Break.

Функция 06h может использоваться как для ввода с консоли, так и для вывода символов на консоль. Режим работы функции зависит от содержимого регистра DL при вызове функции. Если этот регистр содержит значение 0FFh, функция выполняет ввод с консоли, в противном случае символ, код которого записан в этот регистр, выводится на консоль.

Очевидно, что с помощью этой функции нельзя вывести на консоль символ с кодом 0FFh.

Основное отличие функции 06h от всех описанных ранее заключается в том, что эта функция не ожидает, пока оператор нажмет на клавишу. Если буфер клавиатуры пуст, функция просто устанавливает флаг процессора ZF в 1.

Если в буфере клавиатуры имеются символы, флаг ZF сбрасывается и в регистр AL функция записывает ASCII-код символа.


Ввод строки символов
9.5. Ввод строки символов

На входе:       AH    = 0Ah;

                DS:DX = адрес буфера для ввода строки;

На выходе:      Буфер содержит введенную строку.

                Функция проверяет комбинации клавиш

                Ctrl-C и Ctrl-Break.

Функция предназначена для ввода с клавиатуры строки символов. Перед вызовом функции необходимо специальным образом подготовить буфер, адрес которого передается в регистрах DS:DX - в первый байт буфера следует записать максимальную длину вводимой строки (в диапазоне от 1 до 244):

----T---T---T---T---T---T- - -

¦max¦ ? ¦ ?   ?   ?   ?   ?

L-T-+---+---+---+---+---+ -  -

  ¦

  L----> максимальная длина вводимой строки

После возврата из функции буфер будет иметь следующий формат:

----T---T---T---T---T---T- - -

¦max¦len¦ T   E   X   T   0Dh

L-T-+-T-+---+---+---+---+ -  -

  ¦   ¦

  ¦   L------- длина введенной строки (без учета

  ¦                      завершающего символа CR)

  L----------- остается без изменений

Ввод осуществляется до тех пор, пока либо количество введенных символов не достигнет max-1, либо пока не будет нажата клавиша Enter (код 0Dh). Если оператор уже ввел max-1 символ и продолжает вводить символы дальше, функция выдает звуковой сигнал на каждое нажатие и игнорирует вводимые символы до тех пор, пока не будет нажата клавиша Enter.

При вводе строки можно использовать стандартные средства редактирования MS-DOS, используемые при вводе команд в режиме командной строки.


Проверка состояния стандартного ввода
9.6. Проверка состояния стандартного ввода

На входе:       AH = 0Bh.

На выходе:      AL = 0FFh, если в буфере имеется код нажатой

                           на клавиатуре клавиши;

                AL = 0,    если буфер клавиатуры пуст;

                Функция проверяет комбинации клавиш

                Ctrl-C и Ctrl-Break.

Эта функция проверяет состояние клавиатурного буфера. Вы можете вызывать ее перед функциями 01h, 07h, 08h для того, чтобы избежать ожидания нажатия на клавишу.

Если ваша программа выполняет какую-либо длительную обработку (копирование файлов, форматирование дисков и т.п.), вы можете вызывать эту функцию в процессе обработки для проверки нажатия комбинации клавиш, прерывающих работу программы.


Сброс буфера клавиатуры
9.7. Сброс буфера клавиатуры

На входе:       AH = 0Ch;

                AL = 1, 6, 7, 8 или 0Ah.

На выходе:      не опеределены.

Функция очищает клавиатурный буфер, затем вызывает клавиатурную функцию MS-DOS, номер которой определяется содержимым регистра AL. Если же регистр AL содержит другое значение, кроме приведенных выше, функция просто сбрасывает содержимое буфера и не выполняет никаких других действий.

Эту функцию удобно использовать тогда, когда перед вводом символа необходимо убедиться в том, что буфер клавиатуры пуст.


Клавиатурные функции библиотеки Microsoft C
10. Клавиатурные функции библиотеки Microsoft C

Стандартные библиотеки трансляторов Microsoft QuickC и C 6.0 содержат набор функций, предназначенных для работы с клавиатурой. Эти функции повторяют и немного дополняют возможности функций MS-DOS и BIOS, обслуживающих клавиатуру.

Самые простые из них - getch() и getche(). Они описаны в файле conio.h.

Функция getch() имеет следующий прототип:

int getch(void);

Эта функция возвращает ASCII-код прочитанного из клавиатурного буфера символа, причем прочитанный символ не отображается на экране. Если была нажата функциональная клавиша или клавиша перемещения курсора, функция возвращает 0. В этом случае функцию надо вызвать еще раз для получения расширенного ASCII-кода нажатой клавиши.

Функция обрабатывает клавиши Ctrl-С и Ctrl-Break - при вводе этих комбинаций клавиш работа программы завершается.

Если клавиатурный буфер пуст, программа переводится в состояние ожидания.

Функция getche() полностью аналогична функции getch(), за исключением того, что прочитанный символ отображается на экране. Прототип функции getche():

int getche(void);

Для проверки буфера клавиатуры на наличие символов можно использовать функцию kbhit(). Она также описана в файле conio.h:

int kbhit(void);

Если буфер клавиатуры не пуст, функция возвращает ненулевое значение. В этом случае программа может прочитать символы из буфера клавиатуры при помощи фукнкций getch() и getche(). Если буфер клавиатуры пуст, функция возвращает нулевое значение.

Для ввода с клавиатуры строки символов можно использовать функцию cgets(), работающую аналогично функции 0Ah прерывания MS-DOS INT 21h:

char *cgets(char *buffer);

Функция описана в файле conio.h.

Перед вызовом аргумент функции buffer должен указывать на массив, размер которого должен быть достаточным для хранения вводимой строки, завершающего строку нулевого байта и двух дополнительных байтов. Первый элемент массива buffer[0] должен содержать максимальную длину вводимой строки - как и для функции 0Ah прерывания MS-DOS INT 21h.

После завершения ввода второй элемент массива buffer[1] будет содержать длину введенной строки, сама строка будет завершаться символами новой строки NL, перевода строки LF и нулем.

Функция cgets() возвращает указатель на начало введенной строки в буфере, т.е. на третий элемент массива buffer[2].

Существует и более удобная для использования функция, позволяющая вводить строку с клавиатуры, а точнее, из стандартного потока ввода. Это функция gets():

char *gets(char *buffer);

Функция gets() описана в файле stdio.h.

Эта функция читает строку из стандартного потока ввода stdin и запоминает ее в буфере buffer. Символ новой строки \n в конце введенной строки функция заменяет на ноль.

После завершения ввода функция возвращает указатель на заполненный буфер или NULL в случае ошибки или условия "Конец файла".

Обратим ваше внимание на отличия между функциями cgets() и gets():

•	Функция cgets() позволяет редактировать вводимую строку символов, функция gets() просто записывает в буфер все символы подряд (в том числе и коды клавиш редактирования).

•	Программе, использующей для ввода с клавиатуры функцию cgets(), недоступны средства переназначения ввода операционной системы. Если же программа использует функцию gets(), которая читает строку из стандартного потока ввода, можно использовать средства переназначения.

•	Перед вызовом функции cgets() необходимо специальным образом подготовить буфер для вводимой строки (записать в первый байт буфера длину вводимой строки). Функция gets() не требует никакой подготовки буфера.

Еще одна полезная функция, которую можно использовать для ввода с клавиатуры - scanf(). Эта функция подробно описана во всех книгах по языку программирования Си. Отметим только, что с помощью этой функции можно организовать ввод чисел в заданном формате. Однако можно сначала ввести строку при помощи функций cgets() или gets(), а уже потом выполнять все необходимые проверки и преобразования этой строки.