Ассемблер

Содержание

Слайд 2

Как создать проект с ASM-кодом Создаём консольное приложение Win32. Заходим в

Как создать проект с ASM-кодом

Создаём консольное приложение Win32.
Заходим в «Настройки построения»

проекта и ставим флажок «masm (.targets, .props)».
Заходим в «Свойства» проекта и в поле «Свойства конфигурации > Компоновщик > Включить инкрементную компоновку» ставим «Нет».
Добавляем необходимые файлы исходного кода в проект. Файлам, полностью написанным на ассемблере, устанавливаем расширение .asm.
Заходим в «Свойства» всех файлов с расширением .asm и устанавливаем тип элемента «Microsoft Macro Assembler».
Слайд 3

Структура программы на ассемблере Общий синтаксис: .MODEL .STACK .DATA .CODE :

Структура программы на ассемблере

Общий синтаксис:
<набор команд ЦП> .MODEL <модель памяти> .STACK <сегмент стека>
.DATA
<сегмент

данных> .CODE <метка процедуры>:
<команды>
RET END <метка процедуры>

Пример:
.686P
.MODEL FLAT, C
.STACK 4096
.DATA
a DW 5
.CODE
MAIN:
MOV AX, a
INC AX
PUSH AX
SUB AX, 2
MOV a, AX
POP AX
ADD AX, a
MOV a, AX
RET
END MAIN

Слайд 4

Структура программы на ассемблере .686P ; 686 — набор команд P6

Структура программы на ассемблере

.686P ; 686 — набор команд P6 (Pentium II),

P — защищённый режим
.MODEL FLAT, C ; плоская модель памяти, вызов как в языке C
.STACK 4096 ; устанавливаем размер стека
.DATA ; начало сегмента данных
a DW 5 ; переменная a типа «слово», a = 5
.CODE ; начало сегмента кода
MAIN: ; начало основной процедуры
MOV AX, a ; переместить значение a в регистр AX
INC AX ; увеличить AX на 1
PUSH AX ; положить AX в стек
SUB AX, 2 ; вычесть из AX 2
MOV a, AX ; переместить значение из AX в a
POP AX ; извлечь в AX значение из стека
ADD AX, a ; сложить AX и a
MOV a, AX ; переместить значение из AX в a
RET ; выйти из процедуры
END MAIN ; конец процедуры MAIN
Слайд 5

Основные типы данных Форматы: DB — байт; DW — слово; DD

Основные типы данных

Форматы:
DB — байт;
DW — слово;
DD — двойное слово;
DQ —

учетверённое слово;
DT — 10 байт.
Целые числа: DB, DW, DD, DQ.
Числа с плавающей точкой: DD, DQ, DT.
Символьные строки: DB.
Слайд 6

Задание числовых переменных Переменные определяются в сегменте данных. Синтаксис: ; комментарий

Задание числовых переменных

Переменные определяются в сегменте данных.
Синтаксис:
<идентификатор> <тип данных> <значение> ;

комментарий
Модификатор d (или отсутствие модификатора) задаёт десятичное число, h — шестнадцатеричное, b — двоичное, q — восьмеричное:
a DB 14
a DB 0Eh
a DB 00001110b
a DB 16q
Неопределённое значение обозначается с помощью вопросительного знака:
a DB ?
Слайд 7

Задание символьных строк Символьные строки задаются в одинарных или двойных кавычках,

Задание символьных строк

Символьные строки задаются в одинарных или двойных кавычках, либо

в виде кодов символов, перечисленных через запятую.
13 — возврат строки, 10 — перевод каретки, 0 — конец строки.
Синтаксис:
<идентификатор> DB <строка> ; комментарий
Примеры:
STR1 DB 'Первая строка', 0
STR2 DB "Вторая строка", 13, 10, 0
Слайд 8

Задание массивов Синтаксис: ; комментарий DUP( ) Примеры: ARR1 DB 0,1,2,3,4,5,6,7,8,9

Задание массивов

Синтаксис:
<идентификатор> <тип данных> <значения> ; комментарий
<идентификатор> <тип данных> <размер> DUP(<значение>)
Примеры:
ARR1

DB 0,1,2,3,4,5,6,7,8,9
ARR2 DB 0,1,2,3
DB 4,5,6,7
DB 8,9
ARR3 DB 200 DUP (0)
ARR4 DB 200 DUP (?)
ARR5 DB 10 DUP(20 DUP (?))
N EQU 10
ARR6 DW N DUP(?)
В последнем примере с помощью команды EQU мы определили константу.
Слайд 9

Структура команды : ; комментарий Обязательной частью является только сама команда.

Структура команды
<метка>: <команда> <операнд(ы)> ; комментарий
Обязательной частью является только сама команда.
Задаётся

0, 1 или 2 операнда.
Слайд 10

Операнды Операнд, заданный на микропрограммном уровне, в команде не указывается; он

Операнды

Операнд, заданный на микропрограммном уровне, в команде не указывается; он подставляется

неявно:
MUL EBX ; EAX = EAX * EBX
Непосредственный операнд (константа) в команде может стоять только на втором месте:
ADD EAX, 320
Регистровый операнд задаётся именем регистра:
32-разрядные регистры: ЕАХ, ЕВХ, ЕСХ, EDX, ESI, EDI, ESP, EBP;
16-разрядные регистры: АХ, ВХ, СХ, DX, SI, DI, SP, ВР;
8-разрядные регистры: АН, AL, BH, BL, CH, CL, DH, DL;
сегментные регистры: CS, DS, SS, ES, FS, GS.
Слайд 11

Операнды в оперативной памяти Прямая адресация — по имени операнда: ADD

Операнды в оперативной памяти

Прямая адресация — по имени операнда:
ADD EAX, var1
Косвенная

базовая адресация — адрес находится в одном из РОН, кроме ESP и EBP, тогда обращение происходит по типу [<регистр>]:
ADD EAX, [EBX]
Косвенная базовая адресация со смещением — [<регистр> + <число>]:
ADD EAX, [EBX + 4]
Косвенная индексная адресация — <имя>[<индекс>*<масштаб>]:
ADD EAX, arr[ESI]
ADD EAX, arr[ESI * 4]
Косвенная базовая индексная адресация — [<регистр>][<индекс>]:
ADD EAX, [EBX][ESI]
Слайд 12

Ограничения на операнды Нельзя в одной команде оперировать двумя областями памяти

Ограничения на операнды

Нельзя в одной команде оперировать двумя областями памяти одновременно.
Нельзя

оперировать сегментным регистром и значением непосредственно из памяти.
Нельзя оперировать двумя сегментными регистрами.
Нельзя использовать сегментный регистр CS в качестве операнда-приёмника.
Операнды команды, если это не оговаривается дополнительно в описании команды, должны быть одного размера.
В случае необходимости выполнить действие из пп. 1-3 следует использовать свободный регистр общего назначения или стек в качестве промежуточного буфера.
Слайд 13

Основные флаги регистра EFLAGS CF — бит переноса. Этот флаг показывает

Основные флаги регистра EFLAGS

CF — бит переноса. Этот флаг показывает состояние

переполнения для беззнаковых целочисленных арифметических действий.
PF — бит чётности: устанавливается в 1, если результат последней операции имеет чётное число единиц.
AF — бит вспомогательного переноса: устанавливается в 1, если арифметическая операция генерирует перенос из младшей тетрады битов (из 3 бита в 4), сбрасывается в 0 в противном случае. Этот флаг используется в двоично-десятичной арифметике.
ZF — бит нулевого значения: устанавливается в 1, если результат нулевой, сбрасывается в 0 в противном случае.
SF — знаковый бит: устанавливается равным старшему биту результата, который определяет знак в знаковых целочисленных операциях (0 – положительное число, 1 – отрицательное число).
OF — бит переполнения: устанавливается в 1, если целочисленный результат выходит за пределы разрядной сетки.
Слайд 14

Команды пересылки Пересылка операндов: MOV dest, src Обмен операндов: XCHG op1,

Команды пересылки

Пересылка операндов:
MOV dest, src
Обмен операндов:
XCHG op1, op2
Загрузка эффективного адреса в

указанный регистр:
LEA reg, mem
Загрузка в сегментный регистр и указанный РОН сегмента и эффективного адреса элемента:
LDS reg, mem
LSS reg, mem
LES reg, mem
LFS reg, mem
LGS reg, mem
Слайд 15

Команды работы со стеком Поместить операнд в вершину стека: PUSH src

Команды работы со стеком

Поместить операнд в вершину стека:
PUSH src
Извлечь значение из

вершины стека, поместить в операнд:
POP dest
Поместить в стек регистры EAX, EBX, ECX, EDX, ESI, EDI, EBP, ESP:
PUSHA
Извлечь из стека регистры EAX, EBX, ECX, EDX, ESI, EDI, EBP, ESP:
POPA
Поместить в стек регистр EFLAGS:
PUSHF
Извлечь из стека регистр EFLAGS:
POPF
Слайд 16

Арифметические команды Сложение двух операндов: ADD dest, src Сложение двух операндов

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

Сложение двух операндов:
ADD dest, src
Сложение двух операндов и регистра CF:
ADC

dest, src
Вычитание из первого операнда второго:
SUB dest, src
Вычитание из первого операнда второго и регистра CF:
SBB dest, src
Увеличение/ уменьшение на 1:
INC dest
DEC dest
Смена знака числа:
NEG dest
Слайд 17

Арифметические команды Беззнаковое умножение: MUL src Первый операнд задан неявно —

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

Беззнаковое умножение:
MUL src
Первый операнд задан неявно — это регистр AL,

AX или EAX.
Результат помещается в AH:AL, DX:AX или EDX:EAX соответственно.
Знаковое умножение:
IMUL src
IMUL dest, src
Первый вариант работает так же, как в беззнаковом случае.
Во втором варианте результат помещается в первый операнд. Последний операнд может быть непосредственным 8-битным операндом.
Слайд 18

Арифметические команды Беззнаковое деление: DIV src Первый операнд задан неявно —

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

Беззнаковое деление:
DIV src
Первый операнд задан неявно — это регистры AH:AL,

DX:AX или EDX:EAX.
Частное помещается в AL, AX или EAX соответственно.
Остаток помещается в AH, DX или EDX соответственно.
Знаковое деление:
IDIV src
Сравнение целых чисел:
CMP op1, op2
Вычитает второй операнд из первого и не сохраняет результат, а устанавливает биты OF, SF, ZF, AF, PF, CF регистра признаков EFLAGS в соответствии с результатом.
Обычно предшествует команде условного перехода.
Слайд 19

Логические команды Побитовая конъюнкция: AND dest, src Побитовая дизъюнкция: OR dest,

Логические команды

Побитовая конъюнкция:
AND dest, src
Побитовая дизъюнкция:
OR dest, src
Побитовая инверсия:
NOT dest
Побитовое сложение

по модулю 2:
XOR dest, src
Слайд 20

Сдвиговые команды Логический сдвиг вправо (заполнение нулями): SHR dest, steps SHR

Сдвиговые команды

Логический сдвиг вправо (заполнение нулями):
SHR dest, steps
SHR dest
Арифметический сдвиг вправо

(деление на 2steps):
SAR dest, steps
SAR dest
Логический сдвиг влево (заполнение нулями):
SHL dest, steps
SHL dest
Арифметический сдвиг влево (умножение на 2steps):
SAL dest, steps
SAL dest
Если параметр один, steps = 1 неявно.
В качестве второго параметра указывается константа или регистр CL.
Слайд 21

Сдвиговые команды Циклический сдвиг вправо: ROR dest, steps ROR dest Циклический

Сдвиговые команды

Циклический сдвиг вправо:
ROR dest, steps
ROR dest
Циклический сдвиг вправо через перенос:
RCR

dest, steps
RCR dest
Циклический сдвиг влево:
ROL dest, steps
ROL dest
Циклический сдвиг влево через перенос:
RCL dest, steps
RCL dest
Если параметр один, steps = 1 неявно.
В качестве второго параметра указывается константа или регистр CL.
Слайд 22

Команды преобразования типов Команды расширяют данные, хранящиеся в AL, AX или

Команды преобразования типов

Команды расширяют данные, хранящиеся в AL, AX или EAX.
Расширение

AL до AX:
CBW
Расширение AX до EAX:
CWDE
Расширение AX до DX:AX:
CWD
Расширение EAX до EDX:EAX:
CDQ
Слайд 23

Команды установки единичного бита Операнд — 8-битный регистр или переменная; проверяется

Команды установки единичного бита

Операнд — 8-битный регистр или переменная; проверяется условие


на флаги, если оно выполнено, младший бит устанавливается в 1, иначе — в 0.
Общий синтаксис (вместо подставляется нужная комбинация):
SET dest
Слайд 24

Команды управления флагами Сброс флага CF (CF = 0): CLC Установка

Команды управления флагами

Сброс флага CF (CF = 0):
CLC
Установка флага CF (CF

= 1):
CMC
Инверсия флага CF (CF = ¬CF):
STC
Слайд 25

Оператор переопределения типа Оператор переопределения типа PTR применяется для переопределения или

Оператор переопределения типа

Оператор переопределения типа PTR применяется для переопределения или уточнения

типа метки или переменной, определяемых выражением.
<тип> PTR <выражение>
Типы:
BYTE — 1 байт;
WORD — 2 байта;
DWORD — 4 байта;
QWORD — 8 байт;
TWORD — 10 байт;
NEAR — ближний указатель на функцию;
FAR — дальний указатель на функцию
Примеры:
MOV AX, WORD PTR a
MOV BYTE PTR [esi], 18
Слайд 26

Оператор получения сегмента и смещения Оператор получения сегментной составляющей адреса выражения

Оператор получения сегмента и смещения

Оператор получения сегментной составляющей адреса выражения SEG

возвращает физический адрес сегмента для выражения, в качестве которого могут выступать метка, переменная, имя сегмента, имя группы или некоторое символическое имя.
Оператор получения смещения выражения OFFSET позволяет получить значение смещения выражения в байтах относительно начала того сегмента, в котором выражение определено.
Пример:
MOV ESI, OFFSET arr1
MOV EAX, [ESI]
ADD EAX, [ESI + 4]
ADD EAX, 8[ESI]
Слайд 27

Операторы определения длины Оператор определения длины массива LENGTH возвращает число элементов,

Операторы определения длины

Оператор определения длины массива LENGTH возвращает число элементов, определённых

операндом DUP. Если операнд DUP отсутствует, то оператор LENGTH возвращает значение 1.
Оператор TYPE возвращает число байтов, соответствующее определению указанной переменной.
Оператор SIZE возвращает произведение длины LENGTH и типа TYPE и используется при ссылках на переменную с операндом DUP.
Пример:
MOV EAX, SIZE arr1
Слайд 28

Консольный ввод/вывод Консольный вывод в DOS: .DATA STR1 DB "Console Output",0

Консольный ввод/вывод

Консольный вывод в DOS:
.DATA
STR1 DB "Console Output",0
.CODE
MAIN:
LEA DX, STR1
MOV AH,

9
INT 21h
END MAIN
Слайд 29

Консольный ввод/вывод .686P ;плоская модель памяти .MODEL FLAT, stdcall ;константы STD_OUTPUT_HANDLE

Консольный ввод/вывод

.686P
;плоская модель памяти
.MODEL FLAT, stdcall
;константы
STD_OUTPUT_HANDLE equ -11
;прототипы внешних процедур
EXTERN GetStdHandle@4:NEAR
EXTERN

WriteConsoleA@20:NEAR
EXTERN ExitProcess@4:NEAR
;директивы компоновщику для подключения библиотек
includelib c:\masm32\lib\user32.lib
includelib c:\masm32\lib\kernel32.lib
;------------------------------------------------
;сегмент данных
_DATA SEGMENT
;строка в OEM-кодировке
STR1 DB "Console Output",0
LENS DD ? ;количество выведенных символов
RES DD ?
_DATA ENDS
;сегмент кода
_TEXT SEGMENT
START:
;получить HANDLE вывода
PUSH STD_OUTPUT_HANDLE
CALL GetStdHandle@4
;длина строки
PUSH OFFSET STR1
CALL LENSTR
;вывести строку
PUSH OFFSET RES ; резерв
PUSH OFFSET LENS ; выведено символов
PUSH EBX ; длина строки
PUSH OFFSET STR1 ; адрес строки
PUSH EAX ; дескриптор вывода
CALL WriteConsoleA@20
PUSH 0
CALL ExitProcess@4
;строка - [EBP+08H]
;длина в EBX
LENSTR PROC
PUSH EBP
MOV EBP,ESP
PUSH EAX
PUSH EDI
;--------------------
CLD
MOV EDI,DWORD PTR [EBP+08H]
MOV EBX,EDI
MOV ECX,100 ; ограничить длину строки
XOR AL,AL
REPNE SCASB ; найти символ 0
SUB EDI,EBX ; длина строки, включая 0
MOV EBX,EDI
DEC EBX
;--------------------
POP EDI
POP EAX
POP EBP
RET 4
LENSTR ENDP
_TEXT ENDS
END START

Консольный вывод в Windows: