Студопедия

Главная страница Случайная страница

КАТЕГОРИИ:

АвтомобилиАстрономияБиологияГеографияДом и садДругие языкиДругоеИнформатикаИсторияКультураЛитератураЛогикаМатематикаМедицинаМеталлургияМеханикаОбразованиеОхрана трудаПедагогикаПолитикаПравоПсихологияРелигияРиторикаСоциологияСпортСтроительствоТехнологияТуризмФизикаФилософияФинансыХимияЧерчениеЭкологияЭкономикаЭлектроника






Арифметические команды






Изучение команд для выполнения арифметических операций начнём с команд сложения и вычитания целых чисел. Определим вид и допустимые операнды у команд сложения и вычитания:

КОП op1, op2, где КОП = add, sub, adc, sbb.

add – сложение,

sub – вычитание:

op1: = op1 ± op2

adc – сложение с учётом флага переноса,

sbb – вычитание с учётом флага переноса:

op1: = op1 ± op2 ± CF

Таблица допустимых операндов для этих команд:

op1 op2
R8 r8, m8, i8
M8 r8, i8
R16 r16, m16, i16
M16 r16, i16

В результате выполнения операций изменяются флаги CF, OF, ZF, SF, которые отмечают соответственно за перенос, переполнение, нулевой результат и знак результата (флагу SF всегда присваивается знаковый бит результата). Эти команды меняют и некоторые другие флаги (см. [5, 9]), но это нас интересовать не будет.

Далее рассмотрим команды умножения и деления целых чисел. Формат этих команд накладывает сильные ограничения на месторасположение операндов. Первый операнд всех команд этого класса явно в команде не указывается и находится в фиксированном регистре, принимаемом по умолчанию. В младшей модели семейства есть следующие команды умножения и деления, в них явно задаётся только второй операнд (второй сомножитель или делитель):

mul op2 – беззнаковое умножение,

imul op2 – знаковое умножение,

div op2 – беззнаковое целочисленное деление,

idiv op2 – знаковое целочисленное деление.

Как видим, в отличие от команд сложения и вычитания, умножение и деление знаковых и беззнаковых целых чисел выполняются разными командами (по разным алгоритмам).

В случае с короткими целыми операндами при умножении вычисление производится по формуле:

AX: = AL * op2

При делении (операции div и mod понимаются в смысле языка Паскаль):

AL: = AX div op2

AH: = AX mod op2

В случае с длинными операндами при умножении вычисление производится по формуле:

(DX, AX): = AX * op2

При делении:

AX: = (DX, AX) div op2

DX: = (DX, AX) mod op2

В этих командах операнд op2 может иметь формат r8, r16, m8 или m16.

Как видим, команды умножения всегда дают точный результат, так как под хранение произведения выделяется в два раза больше места, чем под каждый из сомножителей. Команды деления могут вызывать аварийную ситуацию, если частное не помещается в отведённое для него место, т.е. в регистры AL и AX соответственно. Заметим, что остаток от деления всегда помещается в отводимое для него место на регистрах AH или DX соответственно (докажите это!).

После выполнения команд умножения устанавливаются некоторые флаги, из которых для программиста представляют интерес только флаги переполнения и переноса (CF и OF). Эти флаги устанавливаются по следующему правилу. CF=OF=1, если в произведении столько значащих (двоичных) цифр, что они не помещаются в младшей половине произведения. На практике это означает, что при CF=OF=1 произведение коротких целых чисел не помещается в регистр AL и частично " переползает" в регистр AH, а произведение длинных целых чисел – не помещается в регистре AX и " на самом деле" занимает оба регистра (DX, AX). И наоборот, если CF=OF=0, то в старшей половине произведения (соответственно в регистрах AH и DX) находятся только незначащие двоичные цифры произведения. Другими словами, при CF=OF=0 в качестве результата произведения можно взять его младшую половину.

Команды деления после своего выполнения как-то устанавливают некоторые флаги, но никакой полезной информации из значения этих флагов программист извлечь не может. Можно сказать, что деление " портит" некоторые флаги.

Для написания программ на Ассемблере нам будут полезны также следующие унарные арифметические операции.

neg op1 – взятие обратной величины знакового числа, op1: = -op1;

inc op1 – увеличение (инкремент) аргумента на единицу, op1: = op1+1;

dec op1 – уменьшение (декремент) аргумента на единицу, op1: = op1-1;

Применение этих команд вместо соответствующих по действию команд вычитания и сложения приводит к более компактным программам. Необходимо также отметить, что команды inc и dec, в отличие от эквивалентных им команд add и sub никогда не меняют флаг CF. [9]


Поделиться с друзьями:

mylektsii.su - Мои Лекции - 2015-2024 год. (0.007 сек.)Все материалы представленные на сайте исключительно с целью ознакомления читателями и не преследуют коммерческих целей или нарушение авторских прав Пожаловаться на материал