[Intel汇编-MASM]内存单元访问扩展

1. 偏移地址的表示方式汇总:

    1) 偏移地址表示规则:在中括号[ ]中最多有一个基址寄存器、最多有一个索引寄存器、最多有一个立即数,这三者的顺序可以任意,之间必须用+相连,不得用其它符号;

    2) 基址寄存器:是指bx(base register基址寄存器)和bp(base pointer基址指针),两者都属于基址寄存器,只不过bx作为偏移地址时默认ds为段基,而bp作为偏移地址时默认ss作为段基;

    3) 索引寄存器:是指si和di(Source/Destination Index Register),但它们也称为串操作变址寄存器;

串操作是指在两个数组之间进行数据传递,一个作为源数组(偏移地址用si表示)另一个作为目的数组(偏移地址用di表示),由于使用这两个寄存器作为偏移地址时CPU有特殊的指令实现串操作而使速率非常快,因此数组之间数据传递尽量使用这两个寄存器而不要使用其它寄存器作为偏移地址,这也是传操作变址寄存器名字的由来;

!注意:当偏移地址中不包含基址寄存器时一律将ds作为默认段基;

    4) 立即数前缀表示法:比如10[bx]就等于[bx + 10],es:2FH[si + bx]就等于es:[bx + si + 2FH];

    5) 多维数组表示法:可以将三个部分分别用三个中括号[ ]括起来,比如[10H][bp][si],三者顺序可以任意,[si][10H][bx]也行!

!注意:偏移地址中的立即数是对后缀敏感的,同样需要用后缀识别它是几进制的,进制问题在汇编代码中是全局的!

    5) 举例:

ds默认前缀:
[si]
[di]
[si + 3]
[si][9]
[8][di]
[0FH + di]
[bx + di]
[di][3][bp]
[bx][si][30H]
[di + bx + 3]
[3 + si + bx]
3H[si + bx] == [si + bx + 3H]
[5]

ss默认前缀:
[bp]
[bp + si + 3]
[bp][3H][di]
7[si + bp]

**可以看见[ ]内顺序可以任意,如果使用段前缀表示法,比如ds:[bp + si + 9]则能精确确定是哪个段的内存单元了!

    6) 一个使用bp、si、di的示例:

将第一行welcome to masm!挪到第二行的内存空间中

assume cs:codesg

codesg segment
	db 'welcome to masm!'
	db 16 dup('9')

start:
	mov		ax, codesg
	mov		ds, ax
	mov		ss, ax

	mov		bx, 0
	mov		si, 0
	mov		bp, 0
	mov		di, 16

	mov		cx, 16
lp:
	mov		al, [bx][si]
	mov		[bp][di], al
	inc		si
	inc		di
	loop	lp

	mov		ax, 4C00H
	int		21H
codesg ends

end start
运行结果:



2. 示例:将每行的第一个字母变为大写(每行刚好16个字符):

assume cs:codesg, ss:datasg

datasg segment
	db '1. file         ' 
	db '2. edit         ' 
	db '3. search       '
	db '4. view         ' 
	db '5. options      '
	db '6. help         '
datasg ends

codesg segment

start:
	mov		ax, datasg
	mov		ss, ax
	mov		al, 11011111B
	mov		bp, 3

	mov		cx, 6
lp:
	and		[bp], al
	add		bp, 16
	loop	lp

	mov		ax, 4C00H
	int		21H
codesg ends

end start


3. 内存单元和立即数作用或者内存单元作为唯一的操作数的情况:

    1) 在这种情况下就需要显式指明内存单元的类型了,可以使用byte ptr或word ptr操作符来指明内存单元是字节型的还是字型的;

!注意:这两个操作符是编译器提供的操作符,并不是汇编指令,不能直接一步翻译成二进制码;

    2) 使用的情形:

         i. 第一个操作数是内存单元而第二个操作数是立即数;

         ii. 指令是单操作数,且该操作数是内存单元;

!!!!注意:如果内存单元和寄存器相互作用虽然显示指明内存单元类型不会编译报错,但是千万不要这样多此一举,有时会发生未知错误!

    3) 示例:

mov		byte ptr 10H[bx], 9
and		word ptr [bp][di][0FCH], 1AH
inc		byte ptr [bx]

<span style="font-family: Arial, Helvetica, sans-serif; background-color: rgb(255, 255, 255);">!注意:还是不能将[立即数]作为第一个操作数,编译器会将其理解成一个立即数看待的!</span>

你可能感兴趣的:(masm,intel汇编,内存访问)