寻址操作指令总结
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
一、寄存器寻址
操作数的值在寄存器中,指令中的地址码字段指出的是寄存器编号,指令执行时直接取出寄存器自来操作。
例如:SUB R0,R1,R2 ;R1 - R2 R0
该指令将R1的值减去R2的值,结果保存得到R0中。
这种寻址方式是各类微处理器经常采用的一种方式,也是一种执行效率较高的寻址方式。
练习:AREA TEXT,CODE,READONLY
ENTRY
START
①MOV R1,#0x80
②MOV R2,#0x40
③SUB R0,R1,R2
END
①
将立即数0x80装入R1中
②
将立即数0x40装入R2中
③
将R1的值减去R2的值,结果保存到R0中
二、立即寻址
立即寻址指令中的操作码字段后面的地址码部分就是操作数本身,也就是说,数据就包含在指令当中,取出指令也就取除了可以立即使用的操作数(立即数)。
立即寻址也叫立即数寻址。
例如:SUBS R0,R0,#1 ;R0 - 1 R0
MOV R0,#0xff00 ;0xff00 R0
第1条指令将R0减1,结果保存到R0中,并影响标志位。
第2条指令将立即数0xff00装入R0中。
练习:AREA TEXT,CODE,READONLY
ENTRY
START
①MOV R0,#0x80
②SUBS R0,R0,#0x20
③MOV R0,#0xff00
END
①
将立即数0x80装入R0中
②
R0减1,结果保存到R0中,并影响标志位
③
将立即数0xff00装入R0中
三、寄存器偏移寻址
寄存器偏移寻址是ARM指令集特有的寻址方式,当第2操作数是寄存器偏移方式时,第2个寄存器操作数在与第1个操作数结合之前,选择进行移位操作。
MOV Rd,Rn,Rm,{<shift>}
Rm 称为第2操作数寄存器
<shift> 用来指定一位类型和移位位数,有两种形式:
5位立即数(其值小于32);
寄存器(用Rs表示) (其值小于32)。
例如:MOV R1,R2,LSL #3 ;R2的值左移3位,结果放入R0,即R0=R2*8 ANDS R1,R1,R2,LSL R3 ;R2的值左移R3位,然后和R1相与操作,结果放入R1 练习:AREA TEXT,CODE,READONLY
ENTRY
START
①MOV R1,#0x06
②MOV R2,#0x01
③MOV R3,#0x02
④MOV R0,R2,LSL #3
⑤ANDS R1,R1,R2,LSL R3
END
①
将立即数0x06装入R1中
②
将立即数0x01装入R2中
③
将立即数0x02装入R3中
④
R2的值左移3位,结果放入R0,即R0=R2*8
⑤
R2的值左移R3位,然后和R1相与操作,结果放入R1
第2操作数移位方式
共有六种移位方式:
LSL逻辑左移LSR逻辑右移
ASL算术左移ASR算术右移
ROR循环右移RRX带扩展的循环右移
1)LSL:逻辑左移,寄存器中字的低端空出的位补0.
2)LSR:逻辑右移,寄存器中字的高端空出的位补0.
SUB R3,R2,R1,LSL #2 ;R3 R2 - (R1逻辑左移2位)SUB R3,R2,R1,LSR R0 ;R3 R2 - (R1逻辑右移R0位)练习:AREA TEXT,CODE,READONLY
ENTRY
START
①MOV R0,#1
②MOV R1,#2
③MOV R2,#8
④SUB R3,R2,R2,LSL #2
⑤SUB R3,R2,R1,LSR R0
NOP
END
①
将立即数1装入R0中
②
将立即数2装入R1中
③
将立即数8装入R2中
④
R2的值减去R2左移两位的值放入R3中⑤
R1的值减去R1右移R0位的值放入R3
3)ASL:算术左移,由于左移空出的有效位用0填充,因此它与LSL同义、
4)ASR:算术右移,移位过程中保持符号位不变,即如果源操作数为整数,则自的高端空出的位补0,否则补1.
ADD R3,R2,R1,ASL #2 ;R3 R2+(R1算术左移2位)
SUB R3,R2,R1,ASR R3 ;R3 R2-(R1算术右移R3位)
5)ROR:循环右移,由字的低端移出的位填入自的高端空出的位。
SUB R3,R2,R1,ROR #2 ;R3 R2-(R1算术右移2位)
6)RRX:带扩展的循环右移,操作数右移一位,高端空出的位用原C标志值填充。
SUB R3,R2,R1,RRX R0 ;R3 R2-(R1带进位位循环右移R0位)
第2操作数的移位位数
移位位数可以停用立即数或者寄存器方式给出,其值均小于32,应为0~30.
ADD R3,R2,R1,LSR #2 ;R3 R2+(R1右移2位)
ADD R3,R2,R1,LSR R4 ;R3 R2+(R1右移R4位)
四、寄存器间接寻址
寄存器间接寻址指令中的地址码给出的是一个通用寄存器编号,所需要的操作数保存在寄存器指定地址的存储单元中,即寄存器为操作数的地址指针。
例如:LDR R0,[R1] ;R0 [R1]
STR R0,[R1] ;[R1] R0
第1条指令将以R1的值为地址的存储单元中的内容加载到寄存器R0中。
第2条指令将R0的内容存储到以R1的值位地址的存储单元中。
R1——基址寄存器;R1的内容——基地址
练习:AREA TEXT,CODE,READONLY
ENTRY
START
LDR R1,=DA TA1
①LDR R0,[R1]
②STR R0,[R2]
SWI 0x123456
AREA lianxi,DA TA,READWRITE
DA TA1 DCD 0x1234
END
①
将以R1的值为地址的存储单元中的内容加载到寄存器R0中
②将R0的内容存储到以R2的值位地址的存储单元中
五、基址寻址
基址寻址是将基址寄存器的内容与指令中给出的偏移量相加,形成操作数的有效地址,基址寻址用于访问基址附近的存储单元,常用于查表、数组操作和功能部件寄存器访问等。
例如:LDR R2,[R3,#0x0F] ;将R3中的数值加0x0F作为地址,取出此地址的数值
保存在R2中
STR R1,[R0,#-2] ;将R0中的数值减2作为地址,把R1中的内容保存到
此地址位置
练习:AREA TEXT,CODE,READONLY
ENTRY
SRART
①MOV R0,#0x06
②MOV R3,#0x08
③LDR R2,[R3,#0x0F]
④STR R1,[R0,#-2]
NOP
END
①
将立即数0x06装入R0中
②
将立即数0x08装入R3中
③
将R3中的数值加0x0F作为地址,取出此地址的数值保存在R2中
④
将R0中的数值减2作为地址,把R1中的内容保存到此地址位置
有3种加偏址的方式:
1)前变址模式(不修改基址寄存器)
先基址+偏址,生成操作数地址,做指令的操作,也叫前索引偏移。
例如:STR R0,[R1,#12] ;R1:基址寄存器,不改变。
12:偏移量练习:AREA TEXT,CODE,READONLY
ENTRY
SRART
①MOV R1,#0x02
②STR R0,[R1,#6]
NOP
END
①
将立即数2装入R1中
②
将R0的值放入到R1偏移6位后所指地址的内存中
2)自动变址模式(修改基址寄存器)
先基址+偏址,生成操作数地址,做指令的操作,在自动修改基址寄存器。
例如:LDR R0,[R1,#4]!;R0 mem32[R1+4],,R1 R1+4,!表示更新基址寄存器练习:AREA TEXT,CODE,READONLY
ENTRY
SRART
①MOV R1,#0x04
②LDR R0,[R1,#4]!
NOP
END
①
②
将R1偏移4位后地址内存中的内容存到R0中,基址R1不变
3)后变址模式(修改基址寄存器)
基址寄存器不加偏移作为操作数地址。
完成指令操作后,用(基址+偏移—)的值修改基址寄存器。
即先用基地址传数,然后修改基地址(基址+偏移),也叫后索引偏移。
偏移地址形式可以是一个立即数,也可以是另一个寄存器,并且还可以是寄存器移位操作。
例如:LDR R0,[R1,R2] ;R0 mem32[R1+R2]
LDR R0,[R1,R2,LSL #2] ;R0 mem32[R1+R2*4]
练习:AREA TEXT,CODE,READONLY
ENTRY
SRART
①MOV R1,#0x04
②MOV R2,#0x02
③LDR R0,[R1],R2
④LDR R0,[R1,R2,LSL #2]
NOP
END
①
②
③
R1加R2值地址所指内容存到R0中,基址R1改变
④
R2左移两位加R1值地址所指内容存到R0中
六、多寄存器寻址
多寄存器寻址就是一次可以传送几个寄存器值,允许一条指令传送16个寄存器的任何子集或所有寄存器。
例如:LDMIA R1!,{R2-R7,R12} ;将R1单元中的数据读出到R2~R7,R12和R1自动加1 STMIA R0!,{R3-R6,R10} ;将R3~R6,R10中的数据保存到R0指向的地址,R0自动加1 使用多寄存器寻指令时,寄存器自己的顺序按有小到大的顺序排列,连续的寄存器可用“—”连接,否则,用“,”分隔书写。
七、堆栈寻址
堆栈是一种数据结构,存储区的操作顺序分为“后进先出”和“先进后出”,堆栈寻址是隐含的,它是用一个专门的寄存器(堆栈指针SP)指向一块存储区域(堆栈)。
指针所指向的存储单元就是堆栈的栈顶。
存储器对战可分为两种:
1)向上生长:向高地址方向生子,成为递增堆栈;
2)向上生长:向高地址方向生子,成为递增堆栈;
堆栈指针指向最后压入堆栈的有效数据项,称为满堆栈;堆栈指针指向下一个要放入的空位置,称为空堆栈。
这样就有4种类型的堆栈表示递增和递减的满堆栈和空堆栈的各种组合。
满递增:堆栈通过增大存储器的地址向上增长,堆栈指针指向内含有效数据向的最高地址。
指令如LDMFA和STMFA等。
空递增:堆栈通过增大存储器的地址向上增长,堆栈指针指向堆栈上的第一个空位置。
指令如LDMEA和STMEA等。
满递减:堆栈通过减小存储器的地址向下增长,堆栈指针指向内含有效数据向的最低地址。
指令如LDMFD和STMFD等。
满递增:堆栈通过增大存储器的地址向上增长,堆栈指针指向堆栈下的第一个空位置。
指令如LDMED和STMED等。
例如:STMFD SP!,{R4-R7,R1} ;满递减
LDMFA SP!,{R4-R7,pc} ;满递增
练习:AREA TEXT,CODE,READONLY
ENTRY
START
①LDR R3,=data1
②LDR R4,[R3]
③ADD R3,R3,#4
LDR R5,[R3]
ADD R3,R3,#4
LDR R6,[R3]
④MOV LR,PC
⑤LDR SP,USE_STACK
⑥STMFD sp!,{R4 - R6,LR}
⑦LDMFA sp!,{R7 - R9,R10}
SWI 0x123456
AREA lianxi,DA TA,READWRITE
USE_STACK DCD 0x10
data1 DCD 0x1,0x2,0x3
END
①②③
④
⑤⑥
⑦
八、块复制寻址
块复制寻找是把存储其中的一个数据块加载到多个寄存器中,或者是把多个寄存其中的内容保存到存储器中。
应用指令:块复制寻址是多寄存器传送指令LDM/STM的寻址方式,因此也较多寄存器寻址。
块复制寻址中的寄存器,可以是R0~R15这16个寄存器的子集(一部分),或是所有寄存器。
它有4种寻址操作:
LDMIA/STMIA(先传送,后地址加4)
LDMIB/STMIB (先地址加4,后传送)
LDMDA/STMDA(先传送,后地址减4)
LDMDB/STMDB (先地址减4,后传送)
例如:STMIA R0!,{R1 – R7} ;将R1~R7的数据保存到存储器中,存储器指针在保存第1
个值之后增加,增长方向为向上增长
STMIB R0!,{R1 – R7} ;将R1~R7的数据保存到存储器中,存储器指针在保存第1
个值之后增加,增长方向为向上增长
练习:AREA XU,DA TA,READWRITE
da1 DCD 0x1,0x2,0x3,0x4
da2 SPACE 16
AREA WANG,CODE,READONLY
ENTRY
start
LDR R0,=da1+12
;ADD R0,R0,#12
LDR R1,=da2+12
; ADD R1,R1,#12
LDMDA R0,{R2,R5,R4,R3}
STMDA R1,{R2,R5,R4,R3}
SWI 0x123456
END
寄存器的变化:
内存的变化:
九、相对寻址
相对寻址是基址寻址的一种变通,有程序计数器PC提供基准地址,指令中的地址码字段作为偏移量,两者相加后得到的地址几位操作数的有效地址。