- •1. Внутренние регистры
- •1.1. Регистры данных
- •1.2. Регистры сегментов
- •1.3. Регистры указателей и индексов
- •1.4. Регистр командного указателя
- •1.5. Флаговый регистр
- •2. Структура и процесс разработки программы на языке ассемблера
- •2.1. Команды
- •2.2. Псевдооператоры
- •2.2.1. Псевдооператор segment
- •2.2.2. Псевдооператор proc
- •2.2.3. Псевдооператор assume
- •2.2.4. Псевдооператор end
- •2.2.5. Псевдооператоры определения данных
- •2.3. Инициализация программы
- •3. Команды пересылки данных
- •3.1. Команда mov
- •3.2. Команды push и рор
- •4. Режимы адресации
- •4.1. Регистровая и непосредственная адресация
- •4.2. Исполнительный адрес
- •4.3. Прямая адресация
- •4.4. Косвенная регистровая адресация
- •4.5. Адресация по базе
- •4.6. Прямая адресация с индексированием
- •4.7. Адресация по базе с индексированием
- •5. Команды передачи управления
- •5.1. Команды call и ret
- •5.2. Команда безусловного перехода jmp
- •5.3. Команды условной передачи управления
- •5.4. Команды управления циклами
- •6. Команды обработки строк
- •6.1. Команды пересылки строк movs, movsb, movsw
- •6.2. Префиксы повторения
- •6.3. Команды сравнения строк. Команда cmps.
- •6.4. Команды сканирования строк
- •6.5. Команды загрузки и сохранения строки
- •7. Взаимодействие языков Си и Ассемблера
- •7.1. Внутренняя структура программы на языке Си для ibm pc
- •7.2. Использование функций на языке Ассемблера
- •7.2.1. Основы взаимодействия языков Си и Ассемблера
- •7.2.2. Передача управления в подпрограмму и обратно
- •7.2.3. Использование глобальных данных
- •7.2.4. Использование аргументов функции
- •7.2.5. Возвращение значения через имя подпрограммы
- •7.2.6. Использование аргументов
- •7.3. Вызов функций на языке Си из программ на языке Ассемблера
- •7.4. Использование локальных данных
- •8. Арифметические команды
- •8.1. Форматы хранения десятичных чисел
- •8.2. Команды сложения
- •8.3. Коррекция результата сложения для bcd-форматов
- •8.4. Команда приращения значения приемника на единицу
- •8.5. Команды вычитания
- •8.6. Коррекция результата вычитания для bcd-форматов
- •8.7. Команда уменьшения содержимого приемника на единицу
- •8.8. Команда обращения знака
- •8.9. Команды умножения
- •8.10. Коррекция результатов умножения
- •8.11. Команды деления
- •8.12. Коррекция результатов деления
- •8.13. Команды расширения знака
- •9. Команды манипулирования битами
- •9.1. Логические команды and, or и xor
- •9.2. Команда логического отрицания nот
- •9.3. Команда проверки test
- •9.4. Команды сдвига и циклического сдвига
- •9.4.1. Команды сдвига
- •9.4.2. Команды циклического сдвига
- •10. Команды работы с флагами
- •10.1. Команды управления флагами
- •10.2. Команды пересылки флагов
- •11. Псевдооператоры определения идентификаторов и операции
- •11.1. Псевдооператоры определения идентификаторов
- •11.2. Операции
- •11.2.1. Арифметические операции
- •11.2.2. Логические операции
- •11.2.3. Операции отношения
- •11.2.4. Операции, возвращающие значения
- •11.2.5. Операции присваивания атрибутов
- •12. Условные псевдооператоры
- •13. Макроопределения
- •13.1. Сравнение макроопределений и процедур
- •13.2. Состав макроопределений
- •13.3. Псевдооператоры макроассемблера
- •13.3.1. Псевдооператор local
- •13.3.2. Псевдооператоры повторения
- •13.3.3. Условные псевдооператоры
- •13.3.4. Псевдооператор eхiтм
- •13.4. Операции в макроопределениях
- •13.5. Задание макроопределений в исходных программах
- •13.5.1. Использование библиотеки макроопределений
- •13.5.2. Указания для задания макроопределений
- •13.5.3. Считывание библиотеки макроопределений в программу
- •13.5.4. Удаление макроопределений
9. Команды манипулирования битами
Данные команды манипулируют группами битов в регистрах или ячейках памяти. Они разделяются на три группы: логические команды, команды сдвига и команды циклического сдвига.
9.1. Логические команды and, or и xor
Эти команды имеют мнемокоды AND (И), OR (ИЛИ) и XOR (Исключающее ИЛИ). Операции выполняются побитно. Формат команд
AND приемник, источник
Операндами команд AND, OR и XOR могут быть байты или слова. В этих командах можно сочетать два регистра, регистр с ячейкой памяти или непосредственное значение с регистром или ячейкой памяти.
Команды изменяют ряд флагов.
Примеры:
AND АХ, ВХ
AND АL, МЕМ_ВУТЕ
9.2. Команда логического отрицания nот
Команда NOT (НЕ) обращает состояние каждого бита регистра или ячейки памяти и ни на какие флаги не воздействует.
9.3. Команда проверки test
Команда TEST (проверить) выполняет операцию AND над операндами, но воздействует только на флаги и не изменяет значения операндов.
Команда TEST обычно используется совместно с идущей вслед за ней командой условного перехода.
9.4. Команды сдвига и циклического сдвига
У микропроцессора 8088 имеются команды, осуществляющие сдвиг 8- или 16-битового содержимого регистров или ячеек памяти на одну или несколько позиций влево или вправо.
Для всех команд флаг переноса CF является (в некотором смысле) расширением операнда битом 9 или битом 17. Иначе говоря, флаг CF приобретает значение бита, сдвинутого за один из концов операнда.
Команды сдвига и циклического сдвига вправо помещают во флаг CF значение нулевого бита.
Команды сдвига и циклического сдвига влево помещают в него значение бита 7 (при операциях над байтом) или бита 15 (при операциях над словом).
Команды сдвига и циклического сдвига распадаются на две группы.
1. Логические команды сдвигают операнд, не считаясь с его знаком. Они используются для действий над числами без знака или над нечисловыми значениями,
2. Арифметические команды сохраняют старший, знаковый бит операнда. Они используются для действий над числами со знаком.
Команды сдвига и циклического сдвига имеют два операнда: приемник и счетчик.
Приемником может быть 8- или 16-битовый регистр общего назначения или ячейка памяти. Счетчик может быть цифрой или значением без знака в регистре CL (воспринимаются только 5 младших битов 0..31).
9.4.1. Команды сдвига
Команды SAL (сдвинуть влево арифметически) и SAR (сдвинуть вправо арифметически) сдвигают числа со знаком.
Команда SAR сохраняет знак операнда, репродуцируя его при выполнении сдвига.
Команда SAL не сохраняет знак, но заносит 1 во флаг переполнения OF в случае изменения знака операнда. При каждом сдвиге операнда команда SAL заносит 0 в вакантный нулевой бит этого операнда.
Команды SHL (сдвинуть влево логически) и SHR (сдвинуть вправо логически) сдвигают числа без знака.
Команда SHL идентична команде SAL.
Команда SHR аналогична команде SHL, но сдвигает операнд не влево, а вправо. При каждом сдвиге операнда команда SHR заносит 0 в вакантный старший бит этого операнда (бит 7 при сдвиге байта, бит 15 при сдвиге слова).
Пример.
Предположим, что регистр AL содержит 10110100, а флаг переноса CF равен 1.
Команды сдвига воздействуют на регистр AL и флаг CF следующим образом:
После SAL AL, 1: AL= 01101000 CF = 1
После SAR AL, 1: AL = 11011010 CF = 0
После SHL AL, 1: AL = 01101000 CF = 1
После SHR AL, 1: AL = 01011010 CF = 0
Рассмотрим несколько полезных примеров применения команд сдвига.
Пример.
Команда SHL используется для преобразования двух неупакованных BCD-чисел в упакованное BCD-число. Старшая цифра извлекается из регистра BL, младшая – из регистра AL, а результат помещается в регистр AL.
MOV CL, 4 ; Загрузить счетчик сдвига в CL
SHL BL, CL ; Сдвинуть старшую цифру в старшие четыре бита BL
OR AL, BL ; Получить упакованное BCD-число слиянием AL и BL
Сдвиг операнда на один бит влево удваивает значение операнда (умножает на 2), а сдвиг на один бит вправо уменьшает значение операнда вдвое (делит на 2). Поэтому команды сдвига можно использовать в качестве команд быстрого умножения и деления.
Пример.
Умножим и разделим на четыре содержимое регистра АХ. При этом регистр CL должен содержать 2.
SHL AX, CL ; Умножить число без знака на 4
SAL AX, CL ; Умножить число со знаком на 4
SHR AX, CL ; Разделить число без знака на 4
SAR AX, CL ; Разделить число со знаком на 4
Применение команд сдвига вместо команд умножения и деления позволяет сэкономить время, так как команды сдвига выполняют данные действия в шесть-восемь раз быстрее.
В то время как отдельная команда сдвига может умножить или разделить только на степень числа 2, манипулирование несколькими регистрами позволяет выполнить умножение или деление на другие числа.
Пример.
Разделим содержимое регистра АХ на 10:
MOV ВХ, АX ; Сохранить содержимое АХ в ВХ
SHL АХ, 2 ; Сдвинуть АХ (умножить на 4)
ADD АX, BX ; Сложить с исходным значением АХ
; (умножить на 5)
SHL АX, 1 ; Сдвинуть АХ еще раз (умножить на 10)
Хотя в этой последовательности 4 команды, но выполняется она в 11 раз быстрее одной команды MUL.
