ARM嵌入式学习--第三天

发布于:2024-10-15 ⋅ 阅读:(45) ⋅ 点赞:(0)

ARM常用伪指令分析

    ARM伪指令:为了方便程序员使用,编译器设计的指令,这个指令ARM核无法识别,需要编译器对它翻译成ARM核所识别的指令

-LDR  R1,=0xabcdef分析

总结

    编译器在编译的时候,将ldr  r1,=0xabcdef翻译成了ldr  r1,[pc,#0x0004]这一条读内存的指令,根据PC的值加上偏移量算出0xabcdef这个数据在内存的地址,然后使用ldr指令读取这个地址的数据

-LDR  R1,=label分析

 总结:

    LDR  r1,=label指令表示将lable的地址写入r1label的地址由指定的代码段运行地址来决定

        编译器做法:

            1.首先根据指定的代码段开始的地址,,算出label标签对应的地址值

            2.然后将这个表示的地址值放在一个位置

            3.生成内存访问指令,根据pc+固定偏移量,找到标签对应地址存放的位置

        注意:

           当代码编译结束的时候,标签表示的地址值(根据指定的代码段地址)已经编译死存放在程序文件中了

-LDR  R1,label分析

LDR  R1,label表示读取label表示的地址对应的数据

-ADR  R1,label分析

ADR  R1,label指令表示根据当前的pc的值+/-偏移量,动态获取当前label所表示的内存地址) 

 

-如何判别代码在实际内存中运行的地址?

    ADR  R0,_start可以知道因为他是根据pc的值,动态获取

    LDR  R0,=_start无法知道这条指令不论在哪里运行,R0的值都是固定的取决于指定的链接地址

 

ATPCS标准

    ATPCSARM-Thumb的程序调用标准

    规定了一些子程序间调用的基本规则,这些规则包括子程序调用过程中寄存器的使用规则,数据栈的使用规则,参数的使用规则,有了这些规则之后,单独编译的C语言程序就可以和汇编语言相互调用

 

-寄存器的使用规则

    1.子程序间通过寄存器R0~R3传递参数(可记为:a0~a3

    (被调用的子程序在返回前无需恢复寄存器R0~R3的内容

    2.子程序间通过寄存器R4~R11保存局部变量(可记为:v1~v8

    (如果在子程序中使用了寄存器的值,则子程序进入时必须保存这些寄存器的值,在返回前必须回复这些寄存器的值在Thumb程序中,通常只能使用寄存器R4~R7来保存局部变量)     

    3.寄存器R12用作过程调用中间临时寄存器,记作IP

    (常用于子程序之间的链接代码段

    4.寄存器R13用作堆栈指针,记作SP

    (在子程序中寄存器R13不能用作其他用途,寄存器SP在进入子程序时的值和退出子程序的值必须相等

    5.寄存器R14称为连接寄存器,记作LR它用于保存子程序的返回地址

    6.寄存器R15称为程序计数器,记作PC,它不能用作其他用途

 

-参数传递规则

    函数间传递参数的时候,当参数个数不超过4个时,可以使用寄存器R0~R3来传递参数,当参数超过4个时,使用堆栈来传递参数

在传递参数时,将所有参数看作是存放在连续的内存单元的子数据,然后,依次将各字数据传递到寄存器R0,R1,R2和R3中,如果参数多于4个,则将剩余的字数据传递到数据栈中入栈的顺序与参数传递顺序相反,即最后一个字数据先入栈

 

-子程序结果返回规则

    1.结果为一个32位整数时,可以通过寄存器R0返回

    2.结果为一个64位整数时,可以通过寄存器R0和R1返回

    3.结果为一个浮点数时,可以通过浮点计算部件的寄存器f0、d0或s0来返回

    4.结果为复合型浮点数(如复数)时,可以通过寄存器f0~fn或d0~dn来返回

 

-栈帧分析

    栈桢概念

        1.栈桢是一块因函数运行而临时开辟的空间

        2.每调用一个函数就会创建一个独立栈桢

        3.栈桢中存放的是函数中的必要信息局部变量,函数传参,返回值

        4.当函数运行完毕栈桢会销毁

 上图描述的是ARM的栈桢布局方式main  stack  frame调用函数的栈桢func  stack  frame为当前函数(被调用者)的栈桢栈底在高地址,栈向下增长

图中FP就是栈基址它指向函数的栈桢起始地址SP则是函数的栈指针它指向栈顶的位置

ARM压栈的顺序依次为当前函数指针PC、返回指针LR、栈指针SP,传入参数个数及指针、本地变量和临时变量