Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
ASM_06_Vyrazheniya_LEC_ukr.doc
Скачиваний:
1
Добавлен:
09.09.2019
Размер:
456.7 Кб
Скачать

ASM: Лекция

Програмні регістри|реєстри|

Регістри - ділянки високошвидкісної пам'яті, розташовані в ЦПУ.

Регістри|реєстри| загального|спільного| призначення

Використовуються для виконання арифметичних операцій і пересилки даних. До кожного регі­стру| можна звернутися|обертатися| як до 32-розрядного або як до 16-розрядного регістра,|реєстру| або як до двох 8-розрядних регістрів|. Наприклад, регістр|реєстр| ЕАХ, АХ, АН або AL|.

Частина|частку| регістрів|реєстрів| мають особливе значення.

  1. ЕАХ - акумулятор (accumulator). Автоматично використовується при виконанні команд множення і ділення.

  2. ЕСХ - лічильник циклу.

Регістр покажчика команд EIP - зберігається адреса наступної виконуваної команди.

Регістр|реєстр| ознак (прапорів) EFLAGS| - Кожен біт цього регістра відображає|відбиває| результат виконання арифметичної чи логічної команди ЦПУ або деяку іншу інформацію . |реєстру|

Якщо прапор встановлений, то значення відповідного йому біта дорівнює 1, а коли скинутий - 0.

Наприклад, ZF - прапор нуля (Zero flag)- встановлюється, якщо при виконанні операції виходить число, рівне нулю. SF - прапор знаку (Sign flag) - встановлюється, якщо при виконанні операції виходить відємне число.

Основні команди цілочисельної арифметики.

Команда MOV|

Mov приймач, джерело

Приклад: скопіювати значення з|із| однієї області пам'яті в іншу

include| irvine32|.inc

.data

n1 DWORD 15

n2 DWORD ?

.code

main PROC

mov eax,n1

mov n2,eax

mov ebx, eax

mov n1,3

exit

main endp

end main

Неправильні записи команд:

mov n1,n2 ; Обидва операнди не можуть бути комірками пам’яті.

mov ах, bl ; Обидва операнди мають бути одного розміру:

Приклад. Скопіювати значення BL| в регістр|реєстр| АХ.

...

main PROC

mov ah,0

mov al,bl

...

Якщо довжина операндів різна, можна використовувати директиву PTR|:

Тип ptr| [вираз|вираження|]

Приклад.

Include| irvine32|.Inc

.data

n1 DWORD 12345678h ; в пам’яті - 00404000 : 78 56 34 12

.code

main PROC

mov ah, BYTE PTR n1 ; eax – 00 00 78 00

exit

main endp

end main

Команди додавання.

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

операнд_1 = операнд_1 + операнд_2

Приклади:

mov| ах, 8 ;заносим у АХ число 8

mov| сх|, 6 ;заносим у СХ число 6

mov| dx|, сх| ;копируем СХ в DX|, DX| = 6

add| dx|, ах ;DX = DX| + АХ

Команда інкремента.

inc операнд

операнд = операнд + 1

Команди віднімання.

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

операнд_1 = операнд_1 - операнд_2

Команда декремента .

dec операнд

операнд = операнд - 1

Целочисельне множення і ділення.|поділ|

В результаті|унаслідок| множення двох чисел можна отримати|одержувати| число, діапазон якого в два рази перевищуватиме діапазон операндів.

Ці команди спроектовані так, що один з операндів і результат знаходяться|перебувають| у фіксованому регістрі|реєстрі|, а другий операнд указується|вказує| програмістом.

Команди множення.

MUL (беззнакові операнди) і IMUL (знакові)

Мнемокод_команди операнд_1

Другий операнд - співмножник заданий неявно в залежності від розміру першого операнда.

Операнд 1

Операнд 2

(за умовчанням)

Результат

Байт

AL|

AL| - молодша частина|частка| результату;

АН - старша частина результату

Слово

АХ

AX - молодша частина результату; DX - старша частина результату

Подвійне слово

ЕАХ

ЕАХ - молодша частина|частка| результату

EDX - старша частина результату

Приклад 1. Помножити значення, збережені в регістрах|реєстрах| ВН і CL|:

Include| irvine32|.Inc

.code

main PROC

mov BH,2

MOV CL,3

mov al,bh ; AL = ВН - заносимо в AL другий операнд

mul CL ; АХ = AL * CL - множимо його на CL

exit

main endp

end main

Вміст регістрів|реєстрів| до виконання команди множення :

BX

BH=2

BL

0

0

0

0

0

0

1

0

0

2



CX

CH

CL=3

0

0

0

0

0

0

0

0

0

0

0

0

0

0

1

1

0

0

0

3

Оскільки операнди команди множення по умові задачі - однобайтові, то для виконання команди множення необхідно|треба| підготувати регістр|реєстр| AL : mov AL, BH

AX

AH

AL=2

0

0

0

0

0

0

1

0

0

2

Вміст регістра|реєстру| AX після виконання команди множення :

AX=6

AH

AL

0

0

0

0

0

1

0

1

0

0

0

6

Приклад 2. Перемножити беззнакові цілі числа 155 і 140 , збережені в регістрах|реєстрах| ВН і CL|:

Результат множення чисел 155*140=21700 не вміщається в один байт, тому результат буде розміщуватися в двох регістрах: AL – молодша частина числа, AH – старша.

Вміст регістрів|реєстрів| до виконання команди множення :

BX

BH=155

BL

1

0

0

1

1

0

1

1

9

B



CX

CH

CL=140

0

0

0

0

0

0

0

0

1

0

0

0

1

1

0

0

8

С

Вміст регістра|реєстру| AX до виконання команди множення :

AX

AH

AL=BH=155

1

0

0

1

1

0

1

1

9

В

Вміст регістра|реєстру| AX після виконання команди множення :

AX=21700

AH

AL

0

1

0

1

0

1

0

0

1

1

0

0

0

1

0

0

5

4

С

4

Для розв’язання наступного прикладу введемо декілька понять.

Є можливість|спроможність| створити одне довге ціле число на основі двох коротких цілих чисел.

Приклад|зразок|. Завантажити 32-розрядне значення, що складається з|із| чотирьох 8-розрядних змінних, в регістр|реєстр| ЕАХ.

include irvine32.inc

.data

LongValue LABEL DWORD

vall BYTE 78h

val2 BYTE 56h

val3 BYTE 34h

val4 BYTE 12h

.code

main PROC

mov eax,LongValue ; EAX = 12345678h

exit

main endp

end main

Тут директива LABEL дозволяє визначити в програмі мітку і|та| призначити їй потрібний атрибут довжини (DWORD), не розподіляючи при цьому фізично пам'ять під змінну.

Можна помітити|зауважити|, що число 12345678h розміщується в пам'яті в перевернутому вигляді: спочатку молодша частина|частка| числа, потім - старша.

У процесорах Intel при вибірці і|та| зберіганні даних в пам'яті використовується прямий порядок|лад| наступністі байтів (little endian order) - молодший байт змінної зберігається в пам'яті за меншою адресою.

Тому подвійне слово 12345678h в памяті:

Значення

78

56

34

12

Зміщення

0000:

0001:

0002:

0003:

У регістрах|реєстрах| дані розташовуються в звичному вигляді.

Приклад|зразок|. Завантажити 32-розрядне значення, що складається з двох 16-розрядних змінних, в регістр|реєстр| ЕАХ.

include irvine32.inc

.data

LongValue LABEL DWORD

vall word 5678h

val2 word 1234h

.code

main PROC

mov eax,LongValue ; EAX = 12345678h

exit

main endp

end main

Приклад. Використання директиви LABEL для визначення в програмі додаткових імен розмірів для змінних, розміщених в сегменті даних.

include irvine32.inc

.data

vall6 LABEL WORD

val32 DWORD 12345678h

.code

main PROC

mov ax,vall6 ; AX = 5678h

mov dx,vall6+2 ; DX = 1234h

mov ecx,val32

exit

main endp

end main

Перед змінною val32 ми оголосили мітку vall6 і|та| присвоїли|привласнили| їй атрибут довжини WORD.

Значення

78

56

34

12

Зміщення

0000

0001

0002

0003

vall6+0

vall6+1

vall6+2

vall6+3

val32

Приклад 3. обчислити 4862

Розробка алгоритму рішення|розв'язання|.

Алгоритм розв’язання задачі – лінійний.

Визначення змінних програми.

Для розв’язання завдання нам знадобиться змінна для представлення цілого беззнакового числа 486. Мінімальна комірка пам’яті, в якої може розміститися число 486 – 2 байти. Для представлення результату, нам знадобиться комірка пам’яті розміром 4 байта (486*486=236196).

За допомогою директив визначення даних в сегменті даних зарезервуємо область пам'яті відповідної довжини для розміщення значень змінних:

digit word 486,0

Додаткове подвійне слово резервуємо для наглядності.

Оскільки|тому що| після виконання команди множення, результат буде збережений в двох регістрах|реєстрах| (AX - молодша частина|частка| числа, в DX - старша частина|частка| числа), для збереження результата в ОП необхідно|треба| виділити комірку розміром 4 байти. Причому, необхідно|треба| потурбуватися|поклопотатися| про доступ до старшої і|та| молодшої частинам|часткам| числа.

Причина того, що результат 16-розрядного множення зберігається в парі DX:AX|, а не в 32-розрядному регістрі, заключається в забезпечені сумісністі з|із| попередніми 16-розрядними процесорами, у|біля| яких не було 32-розрядних регістрів|реєстрів|.

include irvine32.inc

.data

digit word 486,0

result label dword

result_l word ?

result_h word ?

.code

main PROC

mov eax,0

mov ax,digit ; AX = 486

mul ax ; AX * AX -> DX:AX

mov result_l,ax

mov result_h,dx

mov ecx,result

exit

main endp

end main

Вміст регістра|реєстру| AX після виконання команди mov ax,digit

AX=486

0

0

0

0

0

0

0

1

1

1

1

0

0

1

1

0

0

1

Е

6

Вміст регістра|реєстру| AX , DX і ECX після виконання команди множення :

AX

1

0

0

1

1

0

1

0

1

0

1

0

0

1

0

0

9

А

А

4

DX

0

0

0

0

0

0

0

0

0

0

0

0

0

0

1

1

0

0

0

3

ECX=236196

CX

0

0

0

0

0

0

0

0

0

0

0

0

0

0

1

1

1

0

0

1

1

0

1

0

1

0

1

0

0

1

0

0

0

0

0

3

9

А

А

4

Приклад 4. Обчислити|обчисляти| діаметр по радіусу, збереженому в 8-бітовій змінній.

include irvine32.inc

.data

radius byte 25,0

diameter word ?

.code

main PROC

mov al,2 ; AL = 2

mul radius ; AX = radius * 2

mov diameterl,ax ; diameter <- AX

exit

main endp

end main

Множення двійкових чисел із|із| знаком

Соседние файлы в предмете [НЕСОРТИРОВАННОЕ]