Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
прогр.docx
Скачиваний:
23
Добавлен:
21.12.2018
Размер:
2.58 Mб
Скачать

5. Структурные операнды используются для доступа к конкретному элементу структуры.

6. Записи (аналогично структурному типу) используются для доступа к битовому полю некоторой записи.

18. . Оператори мови асемблер. Оператори зсуву, порівняння та отримання

   Оператор LENGTH                             -----------------      Оператор LENGTH возвращает число  элементов,  определенных  операндом DUP. Например, следующая команда MOV заносит в регистр DX значение 10:

               TABLEA    DW     10 DUP(?)                          ...                          MOV    DX,LENGTH TABLEA

      Если операнд DUP отсутствует, то оператор LENGTH возвращает значение 01. См. операторы SIZE и TYPE в этом разделе.                              Оператор  OFFSET                             ------------------      Оператор OFFSET возвращает относительный адрес переменной  или  метки внутри сегмента данных или кода. Оператор имеет следующий формат:

               OFFSET переменная или метка

     Например, команда

               MOV  DX,OFFSET TABLEA

устанавливает в регистре DX относительный адрес (смещение) поля  TABLEA  в сегменте данных. (Заметим, что команда LEA выполняет аналогичное действие, но без использования оператора OFFSET.)                               Оператор  PTR                              ---------------      Оператор PTR используется совместно с атрибутами типа BYTE, WORD  или DWORD для локальной отмены определенных  типов  (DB,  DW  или  DD)  или  с атрибутами NEAR или FAR для отмены значения дистанции по умолчанию. Формат оператора следующий:

               тип  PTR  выражение

В поле "тип" указывается новый атрибут,  например  BYTE.  Выражение  имеет ссылку на переменную или константу.  Приведем несколько примеров оператора PTR:

          FLDB DB        22H                DB        35H           FLDW DW        2672H               ;0бьектный код 7226                MOV       AН,BYTE PTR FLDW    ;Пересылает 1-й байт (72)                ADD       BL,BYTE PTR FLDW+1  ;Прибавляет 2-й байт (26)                MOV       BYTE PTR FLDW,05    ;Пересылает 05 в 1-й байт                MOV       AX,WORD PTR FLDB    ;3аносит в АХ байты (2235)                CALL      FAR PTR[BX]         ;Длинный вызов процедуры

     Директива LABEL, описанная в следующем  разделе,  выполняет  функцию, аналогичную оператору PTR.

                              Оператор SEG                               --------------      Оператор  SEG  возвращает  адрес  сегмента,  в  котором   расположена указанная переменная или метка. Наиболее подходящим является использование этого  оператора  в  программах,  состоящих   из    нескольких    отдельно ассемблируемых сегментов. Формат оператора:

               SEG переменная или метка

     Примеры применения оператора SEG в командах MOV:

               MOV     DX,SEG FLOW    ;Адрес сегмента данных                MOV     DX,SEG A20     ;Адрес сегмента кода                               Оператор SHORT                              ----------------      Назначение оператора SHORT - модификация атрибута NEAR в команде JMP, если переход не превышает границы +127 и -128 байт:

               JMP     SHORT метка

      В результате ассемблер сокращает машинный код операнда  от  двух  до одного байта.  Эта возможность оказывается полезной для коротких переходов вперед, так как в этом случае ассемблер не может сам определить расстояние до адреса перехода и резервирует два байта при отсутствии оператора SHORT.                               Оператор SIZE                              ---------------      Оператор SIZE возвращает произведение длины  LENGTH  и  типа  TYPE  и полезен  только  при  ссылках  на  переменную  с  операндом  DUP.   Формат оператора:

               SIZE переменная

     См. пример для оператора TYPE.                               Оператор TYPE                              ---------------      Оператор TYPE возвращает число  байтов,  соответствующее  определению указанной переменной:

               Определение    Число байтов

               DB             1                DW             2                DD             4                DQ             8                DT             10                STRUC          Число байтов, определённых в STRUC                NEAR метка     FFFF                FAR метка      FFFE

Формат оператора TYPE:

               TYPE      переменная или метка

Ниже приведены примеры, иллюстрирующие применение операторов TYPE,  LENGTH и SIZE:

FLDB      DB   ? TABLEA    DW   20 DUP(?)           ;Определение 20 слов           ...           MOV  AX,TYPE FLDB        ;AX = 0001           MOV  AX,TYPE TABLEA      ;AX = 0002           MOV  CX,LENGTH TABLEA    ;CX = 000A (10)           MOV  DX,SIZE TABLEA      ;DX = 0014 (20)

     Так как область TABLEA определена как DW, то оператор TYPE возвращает 0002Н, LENGTH - 000АН (соответственно операнду DUP) и SIZE -  произведение типа и длины, т.е. 14Н (20).

19. . Мітки даних. Символьні мітки. Приклади використання. Переходи. Умовні та безумовні переходи. Цикли. Організація циклів. Приклади

Для условной пересылки данных используется команда:

CMOVcc <приёмник><источник>

Набор команд, которые копируют содержимое источника в приемник, если удовлетворяется то или иное условие.

Можно использовать команды CMOVcc сразу после команды СМР (сравнение) с теми же операндами, например:

cmp ах,bх ; сравнить ах и bх

cmovl ax,bx ; если ах < bх, скопировать bх в ах

Слова «выше» и «ниже» в таблице 1 относятся к сравнению чисел без знака, слова «больше» и «меньше» учитывают знак.

Метка – это символическое имя, обозначающее определённую ячейку памяти, предназначенное для использования в качестве операнда в командах передачи управления.

Транслятор ассемблера присваивает метке три атрибута:

имя сегмента кода, где эта метка описана;

смещение – расстояние в байтах от начала сегмента кода, в котором описана метка;

тип метки или атрибут расстояния.

Тип метки может принимать два значения:

near (ближняя метка) – переход на эту метку возможен только в пределах сегмента кода, где эта метка описана. Физически это означает, что для перехода на метку достаточно изменить только содержимое регистра eip/ip.

far (дальняя метка) – переход на эту метку возможен только в результате межсегментной передачи управления, для осуществления которой требуется изменения содержимого как регистра eip/ip так и регистра cs.

Метку можно определить двумя способами:

оператором : (двоеточие);

директивой label.

Синтаксис первого способа таков:

Символическое имя :

Команда ассемблера

С помощью данного способа можно определить метку только ближнего типа – near.

Синтаксис второго способа таков:

Символическое имя label тип метки

При этом тип метки может принимать значения как near так и far. Пример эквивалентного описания метки ближнего типа:

m1:

mov ax,pole_1

и

m1 label near

mov ax,pole_1

Организация циклов

В системе команд микропроцессора существует три команды для работы с циклами. Данные команды:

1) loop метка_перехода – повторить цикл. Работа команды заключается в выполнении следующих действий:

а) декремента регистра есх/сх;

б) сравнение регистра есх/сх с нулём;

если (есх/сх)>0, то управление передаётся на метку перехода;

если (есх/сх)=0, то управление передаётся на следующую после loop команду;

2) loope/loopz метка_перехода – повторить цикл пока сх<>0 или zf=0. Команды loope и loopz – абсолютные синонимы. Работа команд заключается в выполнении следующих действий:

а) декремента регистра есх/сх;

б) сравнение регистра есх/сх с нулём;

в) анализа состояния флага нуля zf;

если (есх/сх)>0, и zf=1, управление передаётся на метку перехода;

если (есх/сх)=0, или zf=0, управление передаётся на следующую после loop команду;

3) loopne/loopnz метка_перехода – повторить цикл пока сх<>0 или zf=1. Команды loope и loopz – абсолютные синонимы. Работа команд заключается в выполнении следующих действий:

а) декремента регистра есх/сх;

б) сравнение регистра есх/сх с нулём;

в) анализа состояния флага нуля zf;

если (есх/сх)>0, и zf=0, управление передаётся на метку перехода;

если (есх/сх)=0, или zf=1, управление передаётся на следующую после loop команду;

Команды loop loope/loopz и loopne/loopnz реализуют только короткие переходы (от -128 до _127 байтов). Для работы с длинными циклами необходимо использовать команду jmp.

При работе с вложенными циклами возникает проблема сохранения значения счётчика внешнего цикла есх/сх на время выполнения внутреннего цикла. Для этого можно использовать регистры, ячейки памяти или стек.

Пример программы, содержащей три цикла вложенных один в другой.

Микропроцессор имеет 18 команд условного перехода, позволяющие проверить:

отношение между операндами со знаком (больше-меньше);

отношение между операндами без знака (выше-ниже);

состояние арифметических флагов zf,sf, cf, of, pf.

Команды условного перехода имеют одинаковый синтаксис:

Jcc метка_перехода

Межсегментной передачи управления в условных переходах не допускается (максимальный переход равен размеру сегмента).

Источниками условия для перехода могут быть:

любая команда, изменяющая состояние арифметических флагов;

команда сравнения cmp;

состояние регистра ecx/cx.

Команда cmp выполняет вычитание операторов и устанавливает флаги, не записывает результат вычитания на место первого операнда.

Cmp операнд_1, операнд_2

Опкод

Значение(переход,если...)

Условие

JA

Jump if above (X > Y)

CF=0 & ZF=0

JAE

Jump if above or equal (X >= Y)

CF=0

JB

Jump if below (X < Y)

CF=1

JBE

Jump if below or equal (X < Y)

CF=1 or ZF=1

JC

Jump if carry (cf=1)

CF=1

JCXZ

Jump if CX=0

регистр CX=0

JE (то же, что и JZ)

Jump if equal (X = Y)

ZF=1

JG

Jump if greater (signed) (X > Y)

ZF=0 & SF=OF

JGE

Jump if greater or equal (signed) (X >= Y)

SF=OF

JL

Jump if less (signed) (X < Y)

SF != OF

JLE

Jump if less or equal (signed) (X <= Y)

ZF=1 or SF!=OF

JMP

Безусловный переход

-

JNA

Jump if not above (X <= Y)

CF=1 or ZF=1

JNAE

Jump if not above or equal (X < Y)

CF=1

JNB

Jump if not below (X >= Y)

CF=0

JNBE

Jump if not below or equal (X > Y)

CF=1 & ZF=0

JNC

Jump if not carry (cf=0)

CF=0

JNE

Jump if not equal (X != Y)

ZF=0

JNG

Jump if not greater (signed) (X <= Y)

ZF=1 or SF!=OF

JNGE

Jump if not greater or equal (signed) (X < Y)

SF!=OF

JNL

Jump if not less (signed) (X >= Y)

SF=OF

JNLE

Jump if not less or equal (signed) (X > Y)

ZF=0 & SF=OF

JNO

Jump if not overflow (signed) (of=0)

OF=0

JNP

Jump if no parity (pf=0)

PF=0

JNS

Jump if not signed (signed) (sf=0)

SF=0

JNZ

Jump if not zero (X != Y)

ZF=0

JO

Jump if overflow (signed) (of=1)

OF=1

JP

Jump if parity (pf=1)

PF=1

JP

Jump if parity (pf=1)

PF=1

JPE

Jump if parity even

PF=1

JPO

Jump if parity odd

PF=0

JS

Jump if signed (signed)

SF=1

JZ

Jump if zero (X = Y)

ZF=1

20.Способи задавання операндів. Способи адресації. Косвенна базова (регістрова) адресація зі зміщенням. Приклади використання. Основні регістри процесора Intel (Pentium III)

Пересылка данных

mov <операнд_назначения>, <операнд_источник>

Поддерживаются начиная с процессора 8086.

xchg <операнд1>, <операнд2>

cmovcc <приёмник>,<источник>

bswap <регистр 32>

Особенности команды mov:

1) нельзя осуществлять пересылку из одной области памяти в другую. При такой необходимости нужно использовать в качестве промежуточного буфера любой доступный регистр общего назначения. Пример: переслать байты из ячейки памяти fls в ячейку fld:

.data

fls dd 947503b3h

fld dd ?

.code

Start

----

mov eax, fls

mov fld,eax

----

end start

2) нельзя загрузить в сегментный регистр значение непосредственно из памяти. Для выполнения такой загрузки нужно использовать промежуточный объект (регистр общего назначения или стек).

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

Пример: инициализировать регистр es значением регистра ds:

mov ax,ds

move es,ax

Можно также использовать стек и команды push и pop:

push ds ; поместить значение регистра ds в стек

pop es ; записать в es число из стека