Использование функций драйвера
На следующем шаге выдается запрос на выделение блока размером в 64 страницы. Если после возврата из драйвера регистр ah очищен, то блок выделен, в противном случае происходит переход на метку emmerr.
В случае успешного выделения блока формируются Curpg и Lastpg и на этом выполнение фрагмента завершено.
В примере Б.5 отсутствуют команды, обработки аварийных ситуаций. Предполагается, что первая из них имеет метку emmerr. Что делать в случае ошибки, решать вам, например, можно вывести на экран текст аварийного сообщения и завершить выполнение задачи. На стадии отладки полезно предусмотреть вывод кода ошибки, который находится в регистре ah.
Напоминаем, что после выполнения команд примера Б.5 блок только закреплен за задачей, но не доступен для записи или чтения. Для работы с его конкретными страницами их надо отобразить на физические страницы сегмента EMS. В этом заключается одно из существенных отличий доступа к блокам расширенной памяти от доступа к блокам обычной памяти.
Отображение страниц
Для отображения логической страницы блока на одну из физических страниц сегмента EMS запрашивается функция 44h. Мы рассмотрим универсальный вариант подпрограммы отображения страниц.
В зависимости от логики выполняемых в задаче действий может потребоваться отображение от одной до четырех страниц. Поэтому подпрограмма, текст которой приведен в примере Б.6, имеет две точки входа.
При вызове call mapseg отображаются четыре подряд расположенные страницы. Предварительно в регистре bx указывается номер первой логической страницы, а в регистре dx – идентификатор блока, которому принадлежат отображаемые страницы. Вариант вызова подпрограммы mapseg показан в примере Б.7.
При вызове call mapip дополнительно (кроме заполнения регистров bx и dx) в регистре ах указывается номер первой физической страницы, а в регистре сх – количество страниц.
Если отображение страниц выполнено успешно, то при возврате из подпрограммы отсутствует признак переполнения (С-разряд очищен), в противном случае он установлен. Следует отметить, что при работе отлаженной задачи аварийные ситуации исключены.
Пример Б.6. Подпрограмма отображения 4-х страниц сегмента EMS.
mapseg: mov ex, 04; количество повторов цикла xor al, al нулевая физическая страница maplp: reov ah, 44h код функции отображения памяти int 67h обращение к драйверу or ah, ah отображение выполнено? jne @F › нет, переход на локальную метку inc ax следующая физическая страница inc bx следующая логическая страница loop maplp управление повторами цикла clc очистка С-разряда ret возврат на основную программу @@: stc установка С-разряда ret возврат на основную программу
При входе в точку mapseg задается 4 повтора цикла отображения начиная с нулевой физической страницы. После этого выполняется цикл отображения, имеющий метку mapip (вторая точка входа).
Если отображение происходит без ошибок, то номера физической и логической страницы увеличиваются на 1 и цикл повторяется до тех пор, пока не будет отображено заданное количество страниц.
При возникновении ошибки ее код возвращается в регистре ah. В этом случае выполнение цикла прекращается и происходит переход на локальную метку, что приведет к возврату из подпрограммы с установленным признаком переполнения.
Освобождение памяти
Для освобождения выделенного задаче блока выполняются следующие действия:
mov dx, Ehndlr; dx = идентификатор блока mov ax, 4500h; ах = код функции освобождения блока int 67h; обращение к драйверу
При исполнении запроса драйвер открепляет пространство блока от задачи, и оно становится общедоступным.
Как уже говорилось, перед завершением задачи освобождение выделенной для нее расширенной памяти обязательно. В противном случае это пространство окажется недоступным для других претендентов и будет освобождено только при выключении или перезагрузке компьютера.
Освобождаются все блоки, затребованные задачей. Для этого описанные команды повторяются, с указанием в регистре dx идентификаторов разных блоков, закрепленных за задачей.