Программирование видеоадаптеров CGA, EGA и VGA© Александр Фролов, Григорий ФроловТом 3, М.: Диалог-МИФИ, 1992, 287 стр. 7.1. Краткий обзорВидеоадаптеры EGA и VGA содержат большое количество регистров. EGA имеет около шестидесяти регистров, а VGA и Super VGA еще больше. Большая часть регистров EGA доступна только для записи, что создает определенные проблемы, особенно для мультизадачных систем. Из-за этого некоторые фирмы-изготовители видеоадаптеров выпускают совместимые с EGA платы видеоадаптеров, для регистров которых разрешена также и операция чтения. В новых адаптерах VGA и Super VGA практически все регистры доступны как для записи так и для чтения. Условимся, что в тех случаях, когда VGA имеет отличия от EGA, мы будем на это специально указывать. Доступ к большинству регистров видеоадаптеров осуществляется в два этапа: через один порт ввода/вывода выбирается номер интересующего вас регистра, а затем через другой порт ввода/вывода осуществляется обмен данными. Это позволяет сэкономить большое число портов процессора. Заметим, что в различных режимах работы
видеоадаптера, его регистры могут иметь
различные адреса. В таблицах 8.1 и 8.2 приведен
список адресов регистров в монохромных и цветных
режимах.
Таблица 8.1 Карта портов ввода/вывода (монохромный режим).
Таблица 8.2 Карта портов ввода/вывода (цветной режим). Адресное пространство видеопамяти также
различается в разных режимах работы
видеоадаптера. В таблице 8.3 приведены адреса
памяти в зависимости от режима работы.
Таблица 8.3 Распределение видеопамяти в различных режимах. Функция Get_Seg_Vmem, приведенная ниже, при помощи функции 0Fh прерывания INT 10h определяет текущий режим работы видеоадаптера и возвращает сегмент начала видеопамяти. Если видеоадаптер работает в нестандартном режиме, функция возвращает ноль.
#include "sysp.h"
unsigned Get_Seg_Vmem(void) {
unsigned char mode;
unsigned seg_address;
// определяем текущий режим видеоадаптера
_asm {
mov ah,0Fh
int 10h
mov mode,al
}
// если видеоадаптер находится в режимах 0, 1, 2, 3,
// 4, 5, 6 то видеопамять начинается с сегмента B800h
if((mode >= 0) && (mode <= 6))
seg_address = 0xB800;
// если видеоадаптер находится в режиме 7,
// то видеопамять начинается с сегмента B000h
else if(mode == 7)
seg_address = 0xB000;
// если видеоадаптер находится в режимах 0Dh - 13h,
// то видеопамять начинается с сегмента A000h
else if((mode >= 0x0D) && (mode <= 0x13))
seg_address = 0xA000;
// если видеоадаптер не находится в стандартном режиме
// возвращаем ноль
else seg_address = 0x0;
return(seg_address);
}
Ниже подробно рассмотрены регистры видеоадаптеров EGA и VGA. Регистры сгруппированы по признаку выполняемых ими функций. Мы выделили следующие группы регистров:
|

