Примеры:
mov SI, offset string | ; В SI загружается относительный адрес ячейки string |
mov AX, [SI] | ; Содержимое ячейки string загружается в AX |
inc [SI] | ; Увеличиваться содержимое ячейки string |
mov BX, [SI] | ; Новое содержимое ячейки string загружается в BX |
mov DI, SI | ; Относительный адрес ячейки string копируется в DI |
1.5 Регистровый косвенный режим со смещением (базовый и индексный).
Адресуется память (байт или слово). Относительный адрес операнда определяется, как сумма содержимого регистра BX, BP, SI или DI и указанной в команде константы, иногда называемой смещением. Смещение может быть числом или адресом. Так же, как и в случае базовой адресации, при использовании регистров BX, SI и DI подразумевается сегмент, адресуемый через DS, а при использовании ВР подразумевается сегмент стека и, соответственно, регистр SS.
смещение = {SP, BP, DI, SI, BX} + смещение из команды
Иногда можно встретиться с альтернативными обозначениями того же способа адресации, которые допускает ассемблер. Вместо, например, 4 [ВХ] можно с таким же успехом написать [ВХ+4], 4+ [ВХ] или [ВХ] +4. Такая неоднозначность языка ничего, кроме путаницы, не приносит, однако ее надо иметь в виду, так как с этими обозначениями можно столкнуться, например, рассматривая текст деассемблированной программы.
Рассмотрим теперь пример использования базовой адресации со смещением при обращении к стеку:
смещение = {SP, BP, DI, SI, BX} + смещение из команды
Здесь квадратные скобки [] - это тоже оператор. Он вычисляет адрес как сумму того, что находится внутри скобок с тем, что находится снаружи.
array db 0, 10, 20, 30, 40, 50, 60; Пусть в сегменте данных определен массив:
Последовательность команд:
mov BX,5
mov AL,array [5] ; загрузит в AL элемент массива с индексом 5, то есть 50.
Тот же результат будет получен и в таких последовательностях команд:
mov BX,offset array
mov AL,5 [BX]
или
mov AL, [BX] +5
mov AL, [BX+5]
1.6 Базово-индексный режим
Адресуется память (байт или слово). Относительный адрес операнда определяется, как сумма содержимого следующих пар регистров:
смещение [BX] [SI] | (подразумевается DS: смещение [BX] [SI]) |
смещение [BX] [DI] | (подразумевается DS: смещение [BX] [DI]) |
смещение [BP] [SI] | (подразумевается SS: смещение [BP] [SI]) |
смещение [BP] [DI] | (подразумевается SS: смещение [BP] [DI]) |
Во всех этих случаях можно также писать:
смещение [BX+SI] |
[смещение +BX+SI] |
[BX+SI] +смещение |
Это чрезвычайно распространенный способ адресации, особенно, при работе с массивами. В нем используются два регистра, при этом одним из них должен быть базовый (ВХ или ВР), а другим - индексный (SI или DI). Как правило, в одном из регистров находится адрес массива, а в другом - индекс в нем, при этом совершенно безразлично, в каком что.
1.7 Базово-индексная адресация со смещением.
Адресуется память (байт или слово). Относительный адрес операнда определяется как сумма содержимого двух регистров и смещения.
Это способ адресации является развитием предыдущего. В нем используются те же пары регистров, но полученный с их помощью результирующий адрес можно еще сместить на значение указанной в команде константы. Как и в случае базово-индексной адресации, константа может представлять собой индекс (и тогда в одном из регистров должен содержаться базовый адрес памяти), но может быть и базовым адресом. В последнем случае регистры могут использоваться для хранения составляющих индекса.
Приведем формальный пример рассматриваемого режима адресации.
Пусть в сегменте данных определен массив из 24 байт
syms db 'ЙЦУКЕНГШЩЗХЪ'
db 'йцукенгшщзхъ'
Последовательность команд
mov BX,12mov SI,6
mov DL,syms [BX] [SI] ; загрузит в регистр DL элемент с индексом 6 из второго ряда, то есть код ASCII буквы г
Тот же результат будет получен и в таком варианте:
mov BX,offset syms
mov SI,6
mov DL,12 [BX] [SI]
2. Порядок выполнения работы:
1. С помощью редактора эмулятора EMU 8086 напишите программу, исходный текст которой приводится в листинге №1:
2. Создайте исполняемый файл типа MZ.
3. Изучите структуру программы, также изучите структуру сегмента данных программы: найдите в нем все переменные, определенные в тексте программы.
4. Переделайте программу с использованием упрощенных директив сегментации так, чтобы получить исполняемый файл типа.com и сравните размеры программ.
5. Выполните первые 5 шагов программы, анализируя и записывая состояние регистров на каждом шаге.
6. Занесите в СХ 00FFh. Определите по способу адресации ячейку памяти в сегменте, где произойдут изменения, записать ее адрес.
7. Выполните дальнейшие шаги программы, анализируя возможные способы адресации.
8. Подготовьте отчет, который должен содержать тексты программ, адреса сегментных регистров и записи адресов ячеек памяти против соответствующих команд, а также запись содержимого этих ячеек.
9. В отчете должны содержаться ответы на следующие вопросы.
3. Контрольные вопросы
Как переслать содержимое X в Y?
Чем отличаются команды
MOV [si], cx
и
MOV si, cx?
К какому способу адресации относится команда MOV dx, offset message?
Какие сегменты используются при следующих вариантах адресации: [BX] [SI], [BX] [DI], [BP] [SI], [BP] [DI] ?
5. Что произойдет при выполнении инструкции
MOV AL, DS: 17h?
Чем эта команда отличается от следующей:
MOV AL, DS: [17h] ?
6. Пусть в сегменте данных определен массив
Array db 0,15,22,31,44,45,62,67,76,99
Что окажется в регистре AL после выполнения команд:
MOV BX, 5
MOV AL, array [BX] ?
7. Какой это способ адресации (пример вопроса 6)?
8. Укажите, какие инструкции в программе (листинг №1), созданной в данной лабораторной работе, относятся к инструкциям:
с непосредственным;
косвенным режимом адресации?
9. Укажите способ записи обращения напрямую к ячейке памяти по известному абсолютному адресу?
10. Префиксы, Виды префиксов. Префиксы замены сегмента?
11. Перечислите регистры косвенной и базовой адресации. Опишите отличия?
12. Сущность эффективности базовой адресации в сравнении с прямой?
Листинг №1.
TITLE MOVE2 MOVE2 SEGMENT 'CODE' ASSUME CS: MOVE2, DS: DATA MYPROC PROC OUTPROC:
MOV AX,DATA MOV DS,AX MOV AH,BH MOV AH,X MOV CH,3 MOV AX,3 MOV AX,Y MOV [SI],CX MOV [BP],CX MOV [SI],258 MOV [BP+516],1027 MOV BYTE PTR X,255 MOV BYTE PTR [DI+515],4 MOV WORD PTR [DI+515],4 MOV [DI+BP+515],258 MOV AX, [SI+BX+258] MOV AH,4CH INT 21H MYPROC ENDP MOVE2 ENDS DATA SEGMENT X DB 1 Y DW 2 DATA ENDS END MYPROC
ЛАБОРАТОРНАЯ РАБОТА № 5,6
ВЫВОД НА ЭКРАН В ТЕКСТОВОМ РЕЖИМЕ
Цель работы: Ознакомится с основными средствами вывода текстовых данных на экран посредством средств операционной системы DOS, средствами BIOS и средствами непосредственного (прямого) отображением в видеобуфер.
Средства DOS.
1.1 Функция DOS 02h.
Функция DOS 02h - Записать символ в STDOUT с проверкой на Ctrl-Break
Ввод: | АН = 02h DL = ASCII-код символа |
Вывод: | Никакого, согласно документации, но на самом деле: AL = код последнего записанного символа (равен DL, кроме случая, когда DL = 09h (табуляция), тогда в AL возвращается 20h). |
Эта функция при выводе на экран обрабатывает некоторые управляющие символы - вывод символа BEL (07h) приводит к звуковому сигналу, символ BS (08h) приводит к движению курсора влево на одну позицию, символ НТ (09h) заменяется на несколько пробелов, символ LF (0Ah) опускает курсор на одну позицию вниз, и CR (0Dh) приводит к переходу на начало текущей строки.
Если в ходе работы этой функции была нажата комбинация клавиш Ctrl-Break, вызывается прерывание 23h, которое по умолчанию осуществляет выход из программы.
Простой пример работы функции DOS 02h.
Пример № 1.1
. model tiny | ; модель памяти в которой сегменты кода, данных и стека объединены. |
. code | ; сегмент кода, который содержит данные. |
org 100h | ; начало СОМ-файла |
begin: | ; метка начала кода программы |
mov dl,< ASCII-код символа > | ; заносим в регистр dl - любой ASCII-код символа |
mov ah,2 | ; номер функции DOS "вывод символа" |
int 21h | ; вызов DOS |
ret | ; функция DOS "завершить программу" |
end begin | ; метка окончания кода программы |
Эта программа, выводит на экран любой ASCII-символ, в установленную позицию курсора.
Все функции DOS вывода на экран используют устройство STDOUT, стандартный вывод. Это позволяет перенаправлять вывод программы в файл или на стандартный ввод другой программы. Например, если откомпилировать приведен пример (создать файл cod.com) и написать в командной строке
cod.com > cod. out
то на экран ничего выдано не будет, а в текущем каталоге появится файл cod. out, содержащий ASCII-код символа.
Функция DOS 06h.
Функция DOS 06h - Записать символ в STDOUT без проверки на Ctrl-Break
Ввод: | АН = 06h DL = ASCII-код символа (кроме FFh) |
Вывод: | Никакого, согласно документации, но на самом деле: AL = код записанного символа (копия DL) |
Эта функция не обрабатывает управляющие символы (CR, LF, HT и BS выполняют свои функции при выводе на экран, но сохраняются при перенаправлении вывода в файл) и не проверяет нажатие Ctrl-Break.