ARM汇编编程基础之一 —— 寄存器
ARM的汇编编程,本质上就是针对CPU寄存器的编程,所以我们首先要弄清楚ARM有哪些寄存器?这些寄存器都是如何使用的?
ARM寄存器分为2类,普通寄存器和状态寄存器
寄存器类别 |
寄存器在汇编中的名称 |
各模式下实际访问的寄存器 |
||||||
用户 |
系统 |
管理 |
中止 |
未定义 |
中断 |
快中断 |
||
通用寄存器和程序计数器 |
R0(a1) |
R0 |
||||||
R1(a2) |
R1 |
|||||||
R2(a3) |
R2 |
|||||||
R3(a4) |
R3 |
|||||||
R4(v1) |
R4 |
|||||||
R5(v2) |
R5 |
|||||||
R6(v3) |
R6 |
|||||||
R7(v4) |
R7 |
|||||||
R8(v5) |
R8 |
R8_fiq |
||||||
R9(SB,v6) |
R9 |
R9_fiq |
||||||
R10(SL,v7) |
R10 |
R10_fiq |
||||||
R11(FP,v8) |
R11 |
R11_fiq |
||||||
R12(IP) |
R12 |
R12_fiq |
||||||
R13(SP) |
R13 |
R13_svc |
R13_abt |
R13_und |
R13_irq |
R13_fiq |
||
R14(LR) |
R14 |
R14_svc |
R14_abt |
R14_und |
R14_irq |
R14_fiq |
||
R15(PC) |
R15 |
|||||||
状态寄存器 |
CPSR |
CPSR |
||||||
SPSR |
无 |
SPSR_abt |
SPSR_abt |
SPSR_und |
SPSR_irq |
SPSR_fiq |
请看上表的第2列,普通寄存器总共16个,分别为R0-R15;状态寄存器共2个,分别为CPSR和SPSR
普通寄存器中特别要提出来的是R13、R14、R15。
R15别名PC(program counter),中文称为程序计数器,它的值是当前正在执行的指令在内存中的位置(不考虑流水线的影响,参见流水线对PC值的影响一文),而当指令执行结束后,CPU硬件会自动将PC的值加上一个单位,从而使得PC的值为下一条即将执行的指令在内存中的位置,这样CPU硬件就可以根据PC的值自动完成取指的操作。正是由于有PC的存在,以及CPU硬件会自动增加PC的值,并根据PC的值完成取指操作,才使得CPU一旦上电就永不停歇地运转,由此可见PC寄存器对于计算机的重要性。对于我们进行汇编程序编写而言,PC寄存器亦是十分重要,因为当程序员通过汇编指令完成了对PC寄存器的赋值操作的时候,其实就是完成了一次无条件跳转,这一点非常重要,请务必要牢记。
R14别名LR(linked register),中文称为链接寄存器,它与子程序调用密切相关,用于存放子程序的返回地址,它是ARM程序实现子程序调用的关键所在。下面我们用C语言中对子程序调用的实现细节来说明LR是如何被使用的。
1 int main(void)
2 {
3 int k, i = 1, j = 2;
4 addsub(i, j);
5 k = 3;
6 }
7 int addsub(int a, int b)
8 {
9 int c;
10 c = a + b;
11 return c;
12 }
对于上面的程序,编译器会将第4行编译为指令:BL addsub,将第11行编译为指令:MOV pc, lr。(关于BL和MOV指令详见“基本寻址模式与基本指令”)
在这里,关键指令BL addsub会完成2件事情:1、将子程序的返回地址(也就是第5行代码在内存中的位置)保存到寄存器LR中;2、跳转到子程序addsub的第1条指令处。这样就完成了子程序的调用。而指令MOV pc, lr则将保存在lr中的返回地址赋给pc,这样就完成了从子程序的返回。由此可见,lr是用于存放子程序的返回地址的。
另外一个要引起注意的问题是,如果子程序又调用了孙子程序,那么根据前面的分析,在调用孙子程序时,lr寄存器中的值将从子程序的返回地址变为孙子程序的返回地址,这将导致从孙子程序返回子程序没有问题,但从子程序返回父程序则会出错。那么这个问题如何解决呢?其实,如果我们编写的是C程序,那么我们一点也不用担心,因为编译器会为我们考虑一切,针对这个问题,编译器会在孙子程序的入口处增加入栈操作将lr的值入栈,然后在孙子程序的返回处增加出栈操作,将lr的值恢复,从而解决这个难题。不过我们一定要保持头脑的清醒,因为你要知道,我们现在是在编写汇编子程序,此时编译器已经不能在这方面给我们提供保障,所以当你在编写汇编子程序的时候,发现该子程序还要再调用孙子程序,那么请你务必记住,一定要在子程序的入口处保存lr寄存器的值。
好了,现在轮到寄存器R13了,R13又名SP(stack pointer),中文名称栈指针寄存器。顾名思义,它是用于存放堆栈的栈顶地址的。也就是说,每次当我们进行出栈和入栈的时候,都将根据该寄存器的值来决定访问内存的位置(即:出入栈的内存位置),同时在出栈和入栈操作完成后,SP寄存器的值也应该相应增加或减少。这里要特别说明的是,其实在32位的ARM指令集中没有专门的入栈指令和出栈指令,所以并不是一定要用SP来作为栈指针寄存器,除了PC外,任何普通寄存器均可作为栈指针寄存器,只不过,约定俗成都使用SP罢了。我们将在“其它寻址模式与其它指令”一文中见到ARM中使用SP作为栈指针寄存器的出入栈指令。
寄存器R0-R12是普通的数据寄存器,可用于任何地方。在不涉及ATPCS规则(在“ATPCS与混合编程”一文中详细介绍)的情况下,他们并没有什么特别的用法。
状态寄存器CPSR(current program status register),中文名称:当前程序状态寄存器,顾名思义它是用于保存程序的当前状态的。那么,程序的哪些状态是需要保存的呢?
上图是CPSR寄存器的内容,主要由以下部分组成:
1、条件代码标志位。它们是ARM指令条件执行的依据。
N:运算结果的最高位反映在该标志位。对于有符号二进制补码,结果为负数时N=1,结果为正数或零时N=0;
Z:指令结果为0时Z=1(通常表示比较结果“相等”),否则Z=0;
C:当进行加法运算(包括CMN指令),并且最高位产生进位时C=1,否则C=0。当进行减法运算(包括CMP 指令),并且最高位产生借位时C=0,否则C=1。对于结合移位操作的非加法/减法指令,C为从最高位最后移出的值,其它指令C通常不变
V:当进行加法/减法运算,并且发生有符号溢出时V=1,否则V=0,其它指令V通常不变
2、控制位。它们将控制CPU是否响应中断。
I:中断禁止位,当I位置位时,IRQ中断被禁止
F:快中断禁止位,当F位置位时,FIQ中断被禁止
T:反映了CPU当前的状态。当T位置位时,处理器正在Thumb状态下运行;当T位清零时,处理器正在ARM状态下运行
3、模式位
包括M4、M3、M2、M1和M0,这些位决定了处理器的模式(关于处理器模式详见“ARM处理器模式与异常初步”一文)。
总共有7种模式:用户、快中断、中断、管理、中止、未定义、系统,分别会用于不同的情况和异常。由此可见,不是所有模式位的组合都定义了有效的处理器模式,如果使用了错误的设置,将引起一个无法恢复的错误。
SPSR(saved program status register),中文名称:保存的程序状态寄存器
该寄存器的结构与CPSR完全一样,在异常发生时(关于异常,请参见“ARM处理器模式与异常初步”一文),由硬件自动将异常发生前的CPSR的值存放到SPSR中,以便将来在异常处理结束后,程序能恢复原来CPSR的值。
ARM汇编编程基础之一 —— 寄存器的更多相关文章
- 《深入浅出嵌入式底层软件开发》—1. ARM汇编编程基础
1.1 ARM CPU寄存器 ARM的汇编编程,本质上就是针对CPU寄存器的编程,所以要搞清楚ARM有哪些寄存器:ARM寄存器分为两类:普通寄存器和状态寄存器:普通寄存器一共有16个,分别为R0——R ...
- 3.1 ARM汇编编程概述
1. 汇编编程 为什么要学习汇编 1). Bootloader初始化 2). Linux kernel 3). 高效 2. ARM汇编分类 1. ARM标准汇编:ARM公司得汇编器适合在Windows ...
- ARM汇编编程概述
1.为什么需要学些汇编指令 2.ARM汇编指令分类 3.汇编程序框架 4.编程准备 +++++++++++++++++++++++++++++++++++ 1.为什么需要学些汇编指令 bootload ...
- [国嵌笔记][024][ARM汇编编程概述]
汇编程序用途 1.在bootloader与内核初始化时,还没有建立C语言运行环境,需要用到汇编程序 2.在对访问效率要求很高的情况下,需要用到汇编程序 ARM汇编分类 1.ARM标准汇编:适合于Win ...
- ARM的编程模式及寄存器
根据朱老师的课程及下面博客整理 http://blog.chinaunix.net/uid-20443992-id-5700979.html ARM 采用的是32位架构 ARM 约定: Byte : ...
- ARM 汇编访问 CPSR / SPSR 寄存器 【 msr ,mrs 】
状态寄存器访问过程:读 - 改 - 写 读 CPSR / SPSR 指令[ mrs ] 格式:<opcode><cond> Rn, cpsr/spsr 写 CPSR / ...
- ARM汇编
ARM汇编 ISA ISA即指指令集架构(Instruction Set Architecture)是与程序设计有关的计算机架构的一部分,包括本地数据类型.指令.寄存器.地址模式.内存架构.中断和意外 ...
- iOS 逆向之ARM汇编
最近对iOS逆向工程很感兴趣. 目前iOS逆向的书籍有: <Hacking and Securing IOS Applications>, <iOS Hacker's Handboo ...
- GNU ARM 汇编基础
ARM GNU汇编基础 0 前言 全文补充提醒: 笔者在阅读ARM官方文档及查阅实际的u-boot源码中的汇编代码后,发现了一些不同于ARM官方文档中的汇编语法,查阅相关资料后,才发现主要由于汇编器的 ...
随机推荐
- [转载]win7休眠后网络断开怎么办?如何设置?
http://jingyan.baidu.com/article/8065f87fc87d0423312498af.html 有时会遇到在Windows7系统休眠模式下会自动断开网络连接,唤醒系统也是 ...
- 【BZOJ】1095: [ZJOI2007]Hide 捉迷藏 括号序列+线段树
[题目]BZOJ 1095 [题意]给定n个黑白点的树,初始全为黑点,Q次操作翻转一个点的颜色,或询问最远的两个黑点的距离,\(n \leq 10^5,Q \leq 5*10^5\). [算法]括号序 ...
- 分布式监控工具Ganglia 介绍 与 集群部署.
如果你目的很明确就是冲着标题来的,不爱看我唠叨,请直接进入第二个分割线之后的内容. 其实之前就是有做Swift监控平台的打算的,但是因为没什么硬性需求么,也不要紧的,就一直搁置了.最近实验室来了个大二 ...
- mongoDB - 日常操作四
python 使用 mongodb easy_install pymongo # 安装(python2.+) import pymongo connection=pymongo.Connection( ...
- 第9月第5天 AVVideoAverageBitRateKey
1. https://stackoverflow.com/questions/11751883/how-can-i-reduce-the-file-size-of-a-video-created-wi ...
- linux 查看有哪些service
一.利用进程来查看命令里 ps -aux | grep xxx 是查看某个进程或者服务是否存在.二.利用chkconfig配置工具chkconfig --list 可以列出所有的服务在各个runlev ...
- Useful Online Resources for New Hackers
出处:https://www.hackerone.com/blog/resources-for-new-hackers HackerOne喜欢花时间与活跃的黑客和有兴趣学习如何破解的人交谈. 就在上周 ...
- BAT修改文本内容
@echo off (for /f "delims=" %%a in (文件名) do ( set "str=%%a" setlocal enabledelay ...
- android 调用系统照相机拍照后保存到系统相册,在系统图库中能看到
需求: 调用系统照相机进行拍照,并且保存到系统相册,调用系统相册的时候能看到 系统相册的路径:String cameraPath= Environment.getExternalStorageD ...
- device-pixel-radio
移动web开发之像素和DPR 今天看到一个面试题,为iphone6s的自适应,答案是@media(min-device-width:414px) and(max-device-width:736px) ...