ные, объявленные внутри процедуры). Память стека используется по правилу «последним пришел – первым ушел»: самый последний помещенный в стек операнд будетпервым извлекаться из него.
Регистр SP. Указывает на вершину стека, т.е. совместно с ре- гистром SS адресует ячейку памяти, куда будет помещаться опе- ранд или откуда он будет извлекаться. Содержимое этого регистра
автоматически уменьшается после размещения в стеке очередного операнда и увеличивается после извлечения операнда из стека.
Регистр ВР. Так называемый указатель базы. Облегчает соз- дание и использование локального стека (т.е. стека для использова- ния внутри процедуры).
Регистр ES. Дополнительный сегментный регистр ES исполь- зуется для межсегментного обмена данными и в некоторых строко- вых операциях.
Регистр SI. Определяет адрес источника информации при ин- дексной адресации данных (например, при обработке массивов). Обычно используется в паре с регистром DS.
Регистр DI. В паре с регистром ES определяет приемник ин- формации при межсегментном обмене данными.
Регистр флагов. Отдельные разряды (биты) этого регистра имеют следующее назначение.
Флаг переноса CF. Содержит 1, если произошел перенос еди- ницы при сложении или заем единицы при вычитании. Использует- ся также в циклических операциях и операциях сравнения.
Флаг четности PF. Содержит 1, если в результате операции получено число с четным количеством значащих разрядов, т.е. до- полняет результатдо нечета – используется в операциях обмена для контроля данных.
Флаг внешнего переноса АР. Контролирует перенос из 3-го би- та данных. Используется при операциях над упакованными деся- тичными числами.
Флаг нуля ZF. Равен 1, если в результате операции получен ноль, и равен 0 в противном случае.
Флаг знака SF. Равен 1, если в результате операции получено отрицательное число (с единицей в старшем разряде).
Флаг трассировки TF. Равен 1, если программа исполняется по шагам, с передачей управления после каждой выполненной ко- манды по прерыванию с вектором 1.
Флаг прерываний IF. Содержит 1, если микропроцессору раз- решена обработка прерываний.
Флаг направления DF. Управляет направлением передачи дан- ных: если он содержит 0, то после каждой индексной операции со- держимое индексных регистров увеличивается на 1, в противном случае – уменьшается на 1.
Флаг переполнения OF. Устанавливается в единицу, если в ре- зультате операции получено число, выходящее за разрядную сетку микропроцессора.
Адресация
В архитектуре МП 8086/8088 адрес любого байта задается двумя 16- битовыми словами – сегментом и смещением. При формировании 20-разрядного полного адреса, необходимогодля адресации в пре- делах 1 Мбайт, сегмент сдвигается влево на 4 разряда (умножается на 16) и складывается со смещением. Поскольку емкость 16- разрядного смещения составляет 65536 значений, в пределах одно- го сегмента можно адресовать до 64 Кбайт.
Архитектура МП позволяет использовать семь различных способов адресации.
Регистровая
Извлекает операнд из регистра или помещает его в регистр. Приме- ры:
mov ax, bx |
{Извлекаем из ВХ и помещаем в АХ} |
add сх, ах |
{Содержимое АХ прибавляем к СХ} |
push сх |
{Заталкиваем в стек содержимое СХ} |
Непосредственная
Операнд (8- или 16-разрядная константа) содержится непосредст- венно в теле команды. Примеры:
mov ах, 100 |
{Загружаем в АХ значение 100} |
add ax, 5 |
{К содержимому АХ прибавляем 5} |
mov cx, $FFFF |
{Помещаем в СХ значение 65535} |
Прямая
Смещение операнда задается в теле программы и складывается с регистром DS; например:
Var
X: Word;
В: Byte;
………
mov ах, Х |
{Пересылаем значение переменной Х в регистр АX} |
add ah, В |
{К содержимому регистра АН прибавляем значение переменной В} |
mov Х, ах |
{Пересылаем содержимое регистра АХ в область памяти переменной X} |
Косвенная регистровая
Исполнительный адрес операнда (его смещение) содержится в од- ном из регистров ВХ, ВР, SI или DI. Для указания косвенной адреса- ции этот регистр должен заключаться в квадратные скобки, напри- мер:
mov ax, [bx] |
{Содержимое 16-разрядного слова, хранящегося в памяти по адресу |
|
DS:BX, пересылаем в регистр АХ}; |
Каждый из регистров BX...DI по умолчанию работает со своим сег- ментным регистром:
DS:BX, SS:BP, DS:SI, ES:DI
Допускается явное указание сегментного регистра, если он отлича- ется от умалчиваемого, например:
mov ax, es:[bx]
Адресация по базе
Базовый регистр ВХ (или ВР) содержит базу (адрес начала некото- рого фрагмента памяти), относительно которой ассемблер вычисля- ет смещение, например:
mov ах, [bх]+10 {Загружаем в АХ 10-й по счету байт от начала базы памяти по адресу DS:BX};
Индексная адресация
Один из индексных регистров SI или DI указывает положение эле- мента относительно начала некоторой области памяти. Пусть, на- пример, АОВ – имя массива значений типа Byte. Тогда можно ис- пользовать такие фрагменты:
mov si, 15 |
{Помещаем в SI константу 15} |
mov ah, АОВ[si] |
{Пересылаем в АН 16-й по порядку байт от начала массива} |
mov si, 0 |
{Пересылаем полученное в самый первый элемент массива} |
mov АОВ[si], ah |
Адресация по базе с индексированием
Вариант индексной адресации для случая, когда индексируемая об- ласть памяти задается своей базой. Например:
mov ax, [bx][si]
Этот тип адресации удобен при обработке двумерных массивов. Если, например, АОВ есть массив из 10×10 байт вида
Var
АОВ: array [0..9, 0..9] of Byte;
то для доступа к элементу АОВ [2,3] можно использовать такой
фрагмент
Mov bx, 20 |
{База строки 2} |
Mov si, 2 |
{Номер 3-го элемента} |
Mov ax, АОВ[bx][si] |
{Доступ к элементу} |
Система команд
В приводимых ниже таблицах указывается мнемоника всех допус- тимых инструкций для МП 8086/8088. Для удобства пользования все команды разбиты на 6 функциональных групп – пересылки данных, арифметические, битовые, строковые, передачи управления, пре- рываний. Внутри каждой группы команды объединяются в под- группы по общим дополнительным признакам.
Детальный анализ всех команд МП 8086/8088 занял бы слишком много места, поэтому в идущих за таблицами пояснениях рассмат- риваются лишь наиболее популярные команды.
Команды пересылки данных
Мнемоника |
Формат |
Пояснение |
|
|
|
|
КОМАНДЫ ОБЩЕГО НАЗНАЧЕНИЯ |
|
|
|
MOV |
MOV приемник, источник |
Переслать значение |
|
|
|
PUSH |
PUSH источник |
Поместить в стек |
|
|
|
POP |
POP приемник |
Извлечь из стека |
|
|
|
|
Встроенный ассемблер |
|
327 |
|
|
|
|
|
|
|
|
|
|
|
XCHG |
XCHG приемник, источник |
Обменять значения |
|
|
|
|
|
|
|
XLAT |
XLAT таблица |
Загрузить в AL байт из |
|
|
|
|
таблицы |
|
|
|
|
Команды ввода-вывода |
|
|
|
|
|
|
|
|
IN |
IN аккумулятор, порт |
Читать из порта |
|
|
|
|
|
|
|
OUT |
OUT порт, аккумулятор |
Записать в порт |
|
|
|
|
|
|
|
|
|
Команды пересылки адреса |
|
|
|
|
|
|
|
|
|
LEA |
LEA регистр 16, память 16 |
Загрузить |
исполнительный |
|
|
|
|
адрес |
|
|
|
LDS |
LDS регистр 16, память 32 |
Загрузить в DS регистр 16 |
|
|
|
|
полный адрес |
|
|
|
LES |
LES регистр 16, память 32 |
Загрузить в ES регистр 16 |
|
|
|
|
полный адрес |
|
|
|
|
Команды пересылки флагов |
|
|
|
|
|
|
|
|
LAHF |
LAHF |
Загрузить флаги в АН |
|
|
|
|
|
|
|
SAHF |
SAHF |
Установить флаги из АН |
|
|
|
|
|
|
|
PUSHF |
PUSHF |
Поместить флаги в стек |
|
|
|
|
|
|
|
POPF |
POPF |
Извлечь флаги из стека |
|
|
|
|
|
|
|
Одна из наиболее часто используемых команд – MOV позволяет в защищенном режиме переслать байт или слово из регистра в ре- гистр из памяти в регистр или из регистра в память. Тип пересы- лаемых данных (байт или слово) определяется регистром, участ- вующим в пересылке. Ниже приводятся примеры использования команды:
mov ax, Table |
{Пересылка слова из памяти в АХ} |
mov Table, ah |
{Пересылка байта из АН в память} |
mov ds, ax |
{Пересылка в сегмент данных} |
mov es:[bx], ax |
{Пересылка слова в память: базовая адресация с заменой |
|
сегмента} |
mov ch, -17 |
{Переслать константу в регистр} |
mov Table, $FF |
{Переслать константу в память} |
С помощью MOV нельзя пересылать:
− из памяти в память, например, вместо
mov Mem1, Mem2
следует использовать
mov ax, Mem2 mov Mem1, ах
− константу или переменную в DS, например, нельзя
mov ds, Data_Seg
нужно:
mov ax, Data_Seg mov ds, ax
− один сегментный регистр в другой, например, нельзя
mov es, ds
но можно
mov ax, ds mov es, ax
−в регистр CS; значение этого регистра (сегмента кода) автомати- чески меняется при выполнении дальних команд CALL и JMP; кроме того, он загружается из стека при выполнении команды
RETF (выход из дальней процедуры).
Для временного сохранения регистров и данных, а также для обме-
на значениями между регистрами широко используются стековые команды PUSH и POP. Каждая из них работает со словом, т.е. в стек нельзя поместить или извлечь из него одиночный байт. При выпол- нении PUSH вначале уменьшается на 2 содержимое указателя SP, а затем операнд помещается по адресу SS:SP. При извлечении из стека сначала читается память по адресу SS:SP, а затем SP увели- чивается на 2. Таким образом, при заполнении указатель вершины стека SP смещается к младшим адресам, а при освобождении – к старшим. При работе со стеком следует помнить о специфике ис- пользования стековой памяти («последним пришел – первым ушел»), а также о том, что эта память интенсивно используется при вызове процедур, т.е. состояние стека к моменту выхода из проце- дуры должно быть строго согласовано с дальнейшей работой про- граммы. Первое условие определяет порядок извлечения данных из стека – он должен быть обратным порядку, в котором эти данные помещались в стек. Второе условие фактически означает, что после выхода из процедуры указатель SP должен содержать то же смеще- ние, что и к моменту входа в нее. Иными словами, процедура не должна «забыть» в стеке лишнее слово или взять из него больше нужного.
Команда загрузки адреса LEA загружает в регистр адрес (смещение) нужного участка памяти. Этого же можно достичь с помощью заре-
зервированного слова OFFSET, стоящего перед именем перемен- ной. Например:
Var
X: Word;
………….
Asm
mov ax, OFFSET X |
{Загружаем смещение X в АХ} |
lea ax, X |
{To же действие} |
end; |
|
Разница состоит в том, что в случае команды LEA разрешается ис- пользовать индексную адресацию, что особенно удобно при пере- сылке массивов данных.
Две другие команды адресной загрузки – LDS и LES загружают первое 16-разрядное слово из источника в регистр-приемник, а за- тем следующее слово – в регистр DS или ES, т.е. они рассчитаны на загрузку полного адреса операнда (сегмента и смещения).
Арифметические команды
Мнемоника |
Формат |
Комментарий |
|
|
|
|
|
Команды сложения |
|
ADD |
ADD приемник, источник |
Сложить |
|
|
|
|
ADC |
ADC приемник, источник |
Сложить, добавить перенос |
|
|
|
ААА |
ААА |
Скорректировать сложение для |
|
|
таблицы ASCII |
|
|
|
|
DAA |
DAA |
Скорректировать сложение для |
|
|
двоично-десятичных чисел |
|
|
|
INC |
INC приемник |
Увеличить на единицу |
|
|
|
|
|
Команды вычитания |
|
|
|
|
|
SUB |
SUB приемник, источник |
Вычесть |
|
|
|
|
|
SBB |
SBB приемник, источник |
Вычесть с заемом |
|
|
|
|
|
AAS |
AAS |
Скорректировать |
вычитание |
|
|
для таблицы ASCII |
|
|
|
|
|
DAS |
DAS |
Скорректировать |
вычитание |
|
|
для двоично-десятичных чисел |
|
|
|
DEC |
DEC приемник |
Уменьшить на единицу |
|
|
|
|
NEG |
NBG приемник |
Обратить знак |
|
|
|
|
|
СМР |
СМР приемник, источник |
Сравнить |
|
|
|
|
|
Команды умножения
MUL |
MUL источник |
Умножить без знака |
|
|
|
|
|
IMUL |
IMUL источник |
Умножить со знаком |
|
|
|
|
|
ААМ |
ААМ |
Скорректировать |
умножение |
|
|
для таблицы ASCII |
|
|
|
|
|
|
|
Команды деления |
|
|
|
|
|
|
|
DIV |
DIV источник |
Делить без знака |
|
|
|
|
|
|
|
IDIV |
IDIV источник |
Делить со знаком |
|
|
|
|
|
|
AAD |
AAD |
Скорректировать |
деление для |
|
|
таблицы ASCII |
|
|
|
|
|
|
|
|
Команды расширения знака |
|
|
|
|
|
|
CBW |
CBW |
Преобразовать байт в слово |
|
|
|
|
|
|
CWD |
CWD |
Преобразовать |
слово |
в |
|
|
двойное слово |
|
|
|
|
|
|
|
При использовании арифметических команд следует помнить о том, что МП может обрабатывать знаковые числа, числа без знака, а также двоично-десятичные числа. В беззнаковых числах для пред- ставления значения используются все биты, т.е. они эквивалентны типам Byte и Word, в то время как знаковые числа в старшем разря- де хранят знак числа и эквивалентны типам Shortint и Integer. Дво- ично-десятичные числа используют по 4 бита для каждого десятич- ного разряда и могут быть упакованными или неупакованными. В первом случае один байт хранит 2 десятичные цифры (старшая – в старшем полубайте), во втором – только одну (старший полубайт не используется). Основные арифметические команды МП (ADD, SUB, MUL, DIV) не учитывают двоично-десятичную форму пред- ставления чисел, поэтому в архитектуру МП включены команды коррекции результата.
Битовые команды
Мнемоника |
Формат |
Комментарий |
|
|
|
|
Логические команды |
|
|
|
AND |
AND приемник, источник |
Выполнить AND |
|
|
|
OR |
OR приемник, источник |
Выполнить OR |
|
|
|
XOR |
XOR приемник, источник |
Выполнить XOR |
|
|
|
NOT |
NOT приемник |
Выполнить NOT |
|
|
|
|
Встроенный ассемблер |
331 |
|
|
|
|
|
|
|
|
|
|
|
TEST |
TEST приемник, источник |
Проверить |
|
|
|
|
|
|
|
Сдвиговые команды |
|
|
|
|
|
|
SAL/SHL |
SAL приемник, счетчик |
Сдвинуть влево |
|
|
|
|
|
|
SAR/SHR |
SAR приемник, счетчик |
Сдвинуть вправо |
|
|
|
|
|
|
ROL |
ROL приемник, счетчик |
Сдвинуть влево циклически |
|
|
|
|
|
|
ROR |
ROR приемник, счетчик |
Сдвинуть вправо циклически |
|
|
|
|
|
|
RCL |
RCL приемник, счетчик |
Сдвинуть влево с переносом |
|
|
|
|
|
|
RCR |
RCR приемник, счетчик |
Сдвинуть вправо с переносом |
|
|
|
|
|
Битовые команды используются при исчислении логических выра- жений, а также в тех случаях, когда необходимо изменить отдель- ные разряды операнда. Логические команды AND, OR, XOR и NOT эквивалентны соответствующим операциям Турбо Паскаля в случае, когда операндами являются целочисленные выражения. Команда TEST выполняет целочисленную операцию поразрядного суммиро- вания AND, но не изменяет значения операндов, а лишь устанавли- вает флаги в соответствии со значением результата сравнения: об- нуляет CF и OF, изменяет PF, ZF, SFи не меняет AF (флаг ZF уста- новится в 1 в том случае, когда оба операнда содержат по единице хотя бы в одном соответствующем разряде). Команды сдвига SHL/SHR эквивалентны одноименным операциям Турбо Паскаля и отличаются от команд циклического сдвига ROL/ROR тем, что вы- тесненные в ходе их выполнения значащие разряды теряются, в то время как при циклическом сдвиге эти разряды появляются «с дру- гой стороны». Например, если выполнить фрагмент
mov a1, 1 |
{Загружаем в AL единицу} |
shr a1, 1 |
{Сдвигаем вправо на 1 разряд} |
регистр AL будет содержать 0 (вытесненная вправо единица будет помещена в CF), в то время как после замены команды SHR на ROR в нем будет значение $80=128 (вытесненная единица будет поме- щена в старший бит регистра).
Заметим, что счетчиком в командах сдвига может быть цифра 1 или количество сдвигов, указываемое в регистре CL.
Команды передачи управления
Мнемоника |
Формат |
Комментарий |
|
|
|
|
|
|
|
|
Безусловные переходы |
|
|
|
|
|
|
|
CALL |
CALL имя |
Войти в процедуру |
|
|
|
|
|
|
|
RET |
RET [количество_пара- |
Вернуться из процедуры |
|
метров] |
|
|
|
|
|
|
|
|
|
|
|
|
JUMP |
JUMP имя |
Перейти |
|
|
|
|
|
|
|
|
|
|
Условные переходы |
|
|
|
|
|
|
JA/JNBE |
|
Перейти, если выше (после |
JA близкая метка |
сравнения |
|
беззнаковых |
|
|
операндов) |
|
|
|
|
|
|
|
|
JAE/JNB |
JAE близкая метка |
Перейти |
если |
выше |
или |
равно |
|
|
|
|
|
|
|
|
|
|
|
|
JB/JBAE/JC |
JB близкая метка |
Перейти, если ниже |
|
|
|
|
JBE/JNA |
JBE близкая метка |
Перейти если ниже или равно |
|
|
|
|
JCXZ |
JCXZ близкая метка |
Перейти, если СХ=0 |
|
|
|
|
|
JE/JZ |
JE близкая метка |
Перейти, если равно |
|
|
|
|
JG/JNLE |
|
Перейти, если больше (после |
JG близкая метка |
сравнения |
знаковых операн- |
|
|
дов) |
|
|
|
|
|
|
|
|
|
JGE/JNL |
LGE близкая метка |
Перейти, |
если |
больше |
или |
равно |
|
|
|
|
|
|
|
|
|
|
|
|
JL/JNGE |
JL близкая метка |
Перейти, если меньше |
|
|
|
|
|
|
|
JLE/JNG |
JLE близкая метка |
Перейти, |
если |
меньше |
или |
равно |
|
|
|
|
|
|
|
|
|
|
|
JNC |
JNC близкая метка |
Перейти, если нет переноса |
|
|
|
|
JNE/JNZ |
JNE близкая метка |
Перейти, если не равно |
|
|
|
|
|
|
JNO |
JNO близкая метка |
Перейти, |
если |
нет перепол- |
нения |
|
|
|
|
|
|
|
|
|
|
|
|
JNP/JPO |
JNP близкая метка |
Перейти, если нечетный |
|
|
|
|
|
JO |
JO близкая метка |
Перейти, если перенос |
|
|
|
|
|
JP/JPE |
JP близкая метка |
Перейти, если четный |
|
|
|
|
JS |
JS близкая метка |
Перейти, если отрицательный |
|
|
|
|
|
|