当前位置: 首页 > news >正文

ARM 汇编指令:(七) STM/LDM多寄存器加载/多存储指令

目录

一.四种栈

1.满增栈:进栈(先移动指针再入栈,指针往地址增大的方向移动);出 栈(先出栈,栈指针往地址减小的地方移动)。

2.满减栈:进栈(先移动指针再入栈,指针往地址减小的方向移动);出栈(先出栈,栈指针往地址增大的地方移动)。

3.空增栈:进栈(先进栈,栈指针往地址增大的方向移动);出栈(先移动指针再出栈,栈指针往地址减小的方向移动

4.空减栈:进栈(先进栈,栈指针往地址减小的方向移动);出栈(先移动指针再出栈,栈指针往地址增大的方向移动) 

二.LDM(多寄存器加载)和STM(多存储内存)

1.LDM指令格式

2.STM指令格式

3.LDM和STM多种模式

4.arm 满递减栈使用

1)STMFD 压栈操作

2)LDMFD 寄存器加载操作

3)实际场景分析


一.四种栈

考验大家理解能力的地方来了,专心点,嘿嘿!!

1.满增栈:进栈(先移动指针再入栈,指针往地址增大的方向移动);出 栈(先出栈,栈指针往地址减小的地方移动)。

2.满减栈:进栈(先移动指针再入栈,指针往地址减小的方向移动);出栈(先出栈,栈指针往地址增大的地方移动)。

3.空增栈:进栈(先进栈,栈指针往地址增大的方向移动);出栈(先移动指针再出栈,栈指针往地址减小的方向移动

 

4.空减栈:进栈(先进栈,栈指针往地址减小的方向移动);出栈(先移动指针再出栈,栈指针往地址增大的方向移动) 

 

  满栈:当堆栈指针总是指向最后压入堆栈的数据

  空栈:当堆栈指针总是指向下一个将要放入数据的空位置

二.LDM(多寄存器加载)和STM(多存储内存)

1.LDM指令格式

LDM{cond}<模式>  Rn{!},reglist{^} ;

reglist :表示寄存器列表,可以包含多个寄存器,它们使用“,”隔开,如{R1,R2,R6-R9},寄存器由小到大排列; 

2.STM指令格式

STM{cond}<模式>  Rn{!},reglist{^} ;

3.LDM和STM多种模式

模式

说明

模式

说明

IA

每次传送后地址加4

FD

满递减堆栈

IB

每次传送前地址加4

ED

空递减堆栈

DA

每次传送后地址减4

FA

满递增堆栈

DB

每次传送前地址减4

EA

空递增堆栈

数据块传送操作

堆栈操作

4.arm 满递减栈使用

ARM 微处理器支持这四种类型的堆栈工作方式,一般使用那种栈都是由编译器决定的,arm_gcc是使用的满递减栈,那么我们写.s也按照满递减栈才方便。

1)STMFD 压栈操作
STMFD SP!,{r0,r1,R2,r14}

满递减入栈,r13(lr)为基址地址:

这里需要注意,寄存器r0 r1 r2 r14,哪一个先压得栈?这里有一个总结:不管递减存还是递增存,寄存器组里的高位寄存器(r14)对应到高地址,低位寄存器(r0)对应到低地址。那么取也就好理解了,高地址得load到高位寄存器,低地址得内容load到低位寄存器。

2)LDMFD 寄存器加载操作
LDMFD SP!,{r0,r1,R2,r14}

3)实际场景分析
__swi_entry:   //svc_mode
stmfd sp!, lr;  //保存管理模式下得lr save svc_mod:lr
stmfd sp!,{r0-lr}^;  //保存用户模式下得寄存器 usr_mode:r0-r14...
bl ker_syscall;  //系统调用...
//这里可能产生调度
ldmfd sp!,{r0-lr}^;  //调度回来,为用户态寄存器恢复线程得现场。
ldmfd sp!,{pc}^;     //修改pc指针,并且改CRSP得状态。

1). "!":

表示在操作结束后,将最后的地址写回Rn中;

2). "^":

可选后缀,它的作用就是在IRQ FIQ ABT UNDEF这些模式下,直接可以获取到user的r0-r14寄存器,而不用切模式。通常用作异常进入的压栈和异常退出时的恢复寄存器。(不能在USR模式和SYS模式下使用该符号,因为user和sys模式是公用r0-r14的,所以这两个模式下都不能用^。)

LDM寄存器列表如果包含R15(PC)时,那么除了正常的多寄存器传送外,还将SPSR也复制到CPSR中。这用于异常处理返回,仅在异常模式下使用

相关文章:

  • Python的Selenium库中的模块、类和异常的汇总
  • react可视化编辑器 第一章 拖拽
  • C语言如何进⾏字符数组的连接?
  • 2023年中国抗DDoS市场规模现状及竞争格局,公有云抗DDoS是主要增长点
  • 数学建模--MATLAB基本使用
  • Day39:安全开发-JavaEE应用SpringBoot框架Actuator监控泄漏Swagger自动化
  • 科研绘图一:箱线图(添加贝赛尔曲线)
  • 获取扇区航班数
  • Linux-网络基础
  • 【解惑】离线版本的软件如何实现“授权验证”和“使用有效期”验证的
  • iPhone 的健康数据采用的是 FHIR 传输格式
  • RK3568平台开发系列讲解(基础篇)内核是如何发送事件到用户空间
  • 计算机网络----计算机网络的基础
  • vue防止用户连续点击造成多次提交
  • ISIS接口认证实验简述
  • Android 初级面试者拾遗(前台界面篇)之 Activity 和 Fragment
  • AWS实战 - 利用IAM对S3做访问控制
  • eclipse的离线汉化
  • JavaScript设计模式系列一:工厂模式
  • js ES6 求数组的交集,并集,还有差集
  • node.js
  • Nodejs和JavaWeb协助开发
  • PAT A1050
  • Promise面试题2实现异步串行执行
  • swift基础之_对象 实例方法 对象方法。
  • WordPress 获取当前文章下的所有附件/获取指定ID文章的附件(图片、文件、视频)...
  • 简析gRPC client 连接管理
  • 买一台 iPhone X,还是创建一家未来的独角兽?
  • 批量截取pdf文件
  • 如何使用 JavaScript 解析 URL
  • 数组的操作
  • 思否第一天
  • 思维导图—你不知道的JavaScript中卷
  • 携程小程序初体验
  • 学习使用ExpressJS 4.0中的新Router
  • 找一份好的前端工作,起点很重要
  • nb
  • ​configparser --- 配置文件解析器​
  • ​DB-Engines 11月数据库排名:PostgreSQL坐稳同期涨幅榜冠军宝座
  • # .NET Framework中使用命名管道进行进程间通信
  • ###51单片机学习(2)-----如何通过C语言运用延时函数设计LED流水灯
  • #{}和${}的区别是什么 -- java面试
  • #if 1...#endif
  • #stm32驱动外设模块总结w5500模块
  • $con= MySQL有关填空题_2015年计算机二级考试《MySQL》提高练习题(10)
  • (1)常见O(n^2)排序算法解析
  • (LNMP) How To Install Linux, nginx, MySQL, PHP
  • (第27天)Oracle 数据泵转换分区表
  • (蓝桥杯每日一题)love
  • (淘宝无限适配)手机端rem布局详解(转载非原创)
  • (译)计算距离、方位和更多经纬度之间的点
  • .htaccess配置重写url引擎
  • .Net mvc总结
  • .NET Project Open Day(2011.11.13)
  • .NET开发不可不知、不可不用的辅助类(三)(报表导出---终结版)