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

0030:4012 (Всё шестнадцатиричное)

Это означает: сегмент 30, смещение 4012. Чтобы узнать, что находится по этому адресу, сначала необходимо перейти на сегмент 30, а затем в сегменте сместиться на 4012.

Сегментные регистры:

CS - Сегмент кода

DS - Сегмент данных

SS - Сегмент стека

ES - Дополнительный сегмент

FS - Универсальный сегмент

GS - Универсальный сегмент

Первая команда в ассемблере MOV

Эта команда используется для копирования значения из приёмника в источник. Синтаксис команды:

mov приемник, источник

Пример:

mov edx, ecx ; правильно

Размер источника и приемника должны быть одинаковыми.

mov al, ecx; не правильно

Этот код пытается поместить DWORD (32-битное) значение в байт (8 битов).

Правильные команды:

mov al, bl

mov cl, dl

mov cx, dx

mov ecx, ebx

Можно получить значение из памяти и поместить его в регистр. Например, имеем следующую схему памяти:

 

смещение

34

35

36

37

38

39

3A

3B

3C

3D

3E

3F

40

41

42

данные

0D

0A

50

32

44

57

25

7A

5E

72

EF

7D

FF

AD

C7

Данные, которые имеют смещение 3A: 25, 7A, 5E, 72, EF, и т.д. Чтобы поместить значение со смещения 3A, например, в регистр, можно воспользоваться командой mov:

mov eax, dword ptr [0000003Ah] ; eax=725E7A25h

При работе с памятью самый младший байт сохраняется в наиболее значимом байте: порядок байтов задом на перед.

dword (32-бит) значение 10203040 шестнадцатиричное сохраняется в памяти как: 40, 30, 20, 10

word (16-бит) значение 4050 шестнадцатиричное сохраняется в памяти как:  50, 40

Пример2:

mov cl, byte ptr [34h] ; cl получит значение 0Dh

mov dx, word ptr [3Eh] ; dx получит значение 7DEFh

Размеры данных для префикса ptr:

Byte - 1 байт

Word - 2 байта

Dword - 4 байта

Размер можно не указывать:

mov eax, [00403045h]

Пример3:

mov eax, 403045h ; eax= 00403045h

mov cx, [eax] ; CX=значение (размера word) из памяти указанной в EAX (403045)

Стековые операции - PUSH, POP.

Стек это область в памяти, на которую указывает регистр стека ESP(SP). Есть две команды, для размещения значения в стеке и извлечения его из стека: PUSH и POP. Команда PUSH размещает значение в стеке, т.е. помещает значение в ячейку памяти, на которую указывает регистр ESP, после этого значение регистра ESP уменьшается на 4. Команда POP извлекает значение из стека, т.е. извлекает значение из ячейки памяти, на которую указывает регистр ESP, после этого увеличивается значение регистра ESP на 4. Значение, помещенное в стек последним, извлекается первым.

Пример:

(1) mov ecx, 100

(2) mov eax, 200

(3) push ecx

(4) push eax

(5) xor ecx, eax

(6) add ecx, 400

(7) mov edx, ecx

(8) pop ebx

(9) pop ecx

Анализ:

1: поместить 100 в ecx

2: поместить 200 в eax

3: разместить значение из ecx (=100) в стеке (размещается первым)

4: разместить значение из eax (=200) в стеке (размещается последним)

5/6/7: выполнение операций над ecx, значение в ecx изменяется

8: извлечение значения из стека в ebx: ebx=200.

9: извлечение значения из стека в ecx: ecx=100.

Пример: Работа со стеком.

Смещение

1203

1204

1205

1206

1207

1208

1209

120A

120B

Значение

00

00

00

00

00

00

00

00

00

 

 

 

 

 

ESP

 

 

 

 

ESP стоит в том месте, на которое он указывает)

mov ax, 4560h

push ax

Смещение

1203

1204

1205

1206

1207

1208

1209

120A

120B

Значение

00

00

60

45

00

00

00

00

00

 

 

 

 ESP

 

 

 

 

 

 

mov cx, FFFFh

push cx

Смещение

1203

1204

1205

1206

1207

1208

1209

120A

120B

Значение

FF

FF

60

45

00

00

00

00

00

 

ESP

 

 

 

 

 

 

 

 

pop edx

Смещение

1203

1204

1205

1206

1207

1208

1209

120A

120B

Значение

FF

FF

60

45

00

00

00

00

00

 

 

 

 

 

ESP

 

 

 

 

edx = 4560FFFFh.

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

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 число из стека