Linux当中的压栈和出栈指令以及跳转指令详细教程

这篇具有很好参考价值的文章主要介绍了Linux当中的压栈和出栈指令以及跳转指令详细教程。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

1.跳压栈出栈指令:

我们通常会在 A 函数中调用 B 函数,当 B 函数执行完以后再回到 A 函数继续执行。要想 再跳回 A 函数以后代码能够接着正常运行,那就必须在跳到 B 函数之前将当前处理器状态保存 起来(就是保存 R0~R15 这些寄存器值),当 B 函数执行完成以后再用前面保存的寄存器值恢复

R0~R15 即可。保存 R0~R15 寄存器的操作就叫做现场保护,恢复 R0~R15 寄存器的操作就叫做 恢复现场。在进行现场保护的时候需要进行压栈(入栈)操作,恢复现场就要进行出栈操作。压栈 的指令为 PUSH,出栈的指令为 POP,PUSH 和 POP 是一种多存储和多加载指令,即可以一次 操作多个寄存器数据,他们利用当前的栈指针 SP 来生成地址,PUSH 和 POP 的用法如表所示:

Linux当中的压栈和出栈指令以及跳转指令详细教程

假如我们现在要将 R0~R3 和 R12 这 5 个寄存器压栈,当前的 SP 指针指向 0X80000000,处理器的堆栈是向下增长的,使用的汇编代码如下:

PUSH {R0~R3, R12} @将 R0~R3 和 R12 压栈 

 压栈完成以后的堆栈如图所示:

Linux当中的压栈和出栈指令以及跳转指令详细教程

上图就是对R0~R3,R12进行压栈以后的堆栈示意图,此时的SP指向了0X7FFFFFEC, 假如我们现在要再将 LR 进行压栈,汇编代码如下

PUSH {LR} @将 LR 进行压栈

对 LR 进行压栈完成以后的堆栈模型如图所示:

Linux当中的压栈和出栈指令以及跳转指令详细教程

 上图就是分两步对 R0~R3,R12 和 LR 进行压栈以后的堆栈模型,如果我们要出栈的话 就是使用如下代码:

POP {LR} @先恢复 LR 
POP {R0~R3,R12} @在恢复 R0~R3,R12 

出栈的就是从栈顶,也就是 SP 当前执行的位置开始,地址依次减小来提取堆栈中的数据 到要恢复的寄存器列表中。PUSH 和 POP 的另外一种写法是“STMFD SP!”和“LDMFD SP!”,

因此上面的汇编代码可以改为:

STMFD SP!,{R0~R3, R12} @R0~R3,R12 入栈 

STMFD SP!,{LR} @LR 入栈 

LDMFD SP!, {LR} @先恢复 LR 

LDMFD SP!, {R0~R3, R12} @再恢复 R0~R3, R12 

        STMFD 可以分为两部分:STM 和 FD,同理,LDMFD 也可以分为 LDM 和 FD。看到 STM和 LDM 有没有觉得似曾相识(不是 STM32 啊啊啊啊),前面我们讲了 LDR 和 STR,这两个是 数据加载和存储指令,但是每次只能读写存储器中的一个数据。STM 和 LDM 就是多存储和多 加载,可以连续的读写存储器中的多个连续数据。

        FD 是 Full Descending 的缩写,即满递减的意思。根据 ATPCS 规则,ARM 使用的 FD 类型 的堆栈,SP 指向最后一个入栈的数值,堆栈是由高地址向下增长的,也就是前面说的向下增长 的堆栈,因此最常用的指令就是 STMFD 和 LDMFD。STM 和 LDM 的指令寄存器列表中编号 小的对应低地址,编号高的对应高地址。

2.跳转指令

我们重点来看一下 B 和 BL 指令,因为这两个是我们用的最多的,如果要在汇编中进行函 数调用使用的就是 B 和 BL 指令:

B 指令

这是最简单的跳转指令,B 指令会将 PC 寄存器的值设置为跳转目标地址, 一旦执行 B 指 令,ARM 处理器就会立即跳转到指定的目标地址。如果要调用的函数不会再返回到原来的执行 处,那就可以用 B 指令,如下示例:

_start: 


    ldr sp,=0X80200000 @设置栈指针 

    b main @跳转到 main 函数 

上述代码就是典型的在汇编中初始化 C 运行环境,然后跳转到 C 文件的 main 函数中运行,上述代码只是初始化了 SP 指针,有些处理器还需要做其他的初始化,比如初始化 DDR 等等。 因为跳转到 C 文件以后再也不会回到汇编了,所以在第 4 行使用了 B 指令来完成跳转。

BL 指令

BL 指令相比 B 指令,在跳转之前会在寄存器 LR(R14)中保存当前 PC 寄存器值,所以可以 通过将 LR 寄存器中的值重新加载到 PC 中来继续从跳转之前的代码处运行,这是子程序调用 一个基本但常用的手段。比如 Cortex-A 处理器的 irq 中断服务函数都是汇编写的,主要用汇编 来实现现场的保护和恢复、获取中断号等。但是具体的中断处理过程都是 C 函数,所以就会存 在汇编中调用 C 函数的问题。而且当 C 语言版本的中断处理函数执行完成以后是需要返回到汇编中断服务函数,因为还要处理其他的工作,一般是恢复现场。这个时候就不能直接使用B 指令了,因为 B 指令一旦跳转就再也不会回来了,这个时候要使用 BL 指令,示例代码如下:

push {r0, r1} @保存 r0,r1 

cps #0x13 @进入 SVC 模式,允许其他中断再次进去 


bl system_irqhandler @加载 C 语言中断处理函数到 r2 寄存器中 

 
cps #0x12 @进入 IRQ 模式 

pop {r0, r1} 

str r0, [r1, #0X10] @中断执行完成,写 EOIR 

上述代码中第 5 行就是执行 C 语言版的中断处理函数,当处理完成以后是需要返回来继续 执行下面的程序,所以使用了 BL 指令。文章来源地址https://www.toymoban.com/news/detail-409169.html

到了这里,关于Linux当中的压栈和出栈指令以及跳转指令详细教程的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 【Linux常见指令以及权限理解】基本指令(3)

    上一篇文章,我们学习了Linux的一些常用指令, 学习了如何理解Linux系统,介绍了对Linux系统的理解:Linux下一切皆文件 介绍了重定向还有管道相关的知识。这里是上一篇博客的链接:http://t.csdn.cn/2d6fc 接下来我会对Linux常用指令进行收尾,并谈一谈如何理解指令。 目录 写在前

    2024年02月04日
    浏览(40)
  • 【Linux常见指令以及权限理解】基本指令(1)

    相信看完上一个博客,我们已经成功搭建好了Linux环境, 如果没有可以去看看:Linux环境搭建。 接下来我会讲述Linux的常见指令以及权限理解相关内容。 这篇文章会介绍一些常用的Linux指令并穿插一些操作系统的概念理解 。 那么不废话我们现在就开始: 目录 写在前面: 1.

    2023年04月21日
    浏览(40)
  • Linux实时监控网卡入流量和出流量(iftop、dstat、nethogs、nload)

    相同配置和相同业务的4台cvm,今天准备下线,检查还有没有业务流量的时候,发现有两台流量不符合预期,就很奇怪,想知道流量是从哪里来的。记录下当时定位思路 先来了解下基本的概念 速度单位,bit 即比特,通常用 b(小写)表示,指一位二进制位; Mbps 即 Milionbit p

    2024年02月15日
    浏览(36)
  • linux相关知识以及有关指令3

    在linux中文件大致分为以下几类: -:普通文件,源代码,可执行程序,库等等。 d:目录文件 c:字符设备文件,键盘,显示器 b:块设备文件 l:链接文件 p:管道文件 上面的字母是各类文件的表示他们位于这个位置: 我们可以看到在linux中文件的前面有很多属性而位于最前

    2024年02月07日
    浏览(36)
  • 【Linux】常见指令以及具体其使用场景

    君兮_的个人主页 即使走的再远,也勿忘启程时的初心 C/C++ 游戏开发 Hello,米娜桑们,这里是君兮_,随着博主的学习,博主掌握的技能也越来越多,今天又根据最近的学习开设一个新的专栏——Linux,相信Linux操作系统在日常开发过程中是必不可少的,今天我们就先来讲讲Lin

    2024年02月06日
    浏览(48)
  • 【Linux常见指令以及权限理解】权限理解

    这篇文章,我们来聊一聊Linux下权限相关的知识,我打算从这几个方面展开: 1. 认识Linux下用户的分类 2. 什么叫做权限 3. 没有权限会是什么样子 4. 如何修改权限 5. 其它重要的问题 那么废话不多说,我们现在开始。 目录 写在前面 1. Linux下用户的分类 如何切换用户 如何提高

    2024年02月05日
    浏览(37)
  • 【Linux常见指令以及权限理解】权限理解(4)

    这篇文章,我们来聊一聊Linux下权限相关的知识,我打算从这几个方面展开: 1. 认识Linux下用户的分类 2. 什么叫做权限 3. 没有权限会是什么样子 4. 如何修改权限 5. 其它重要的问题 那么废话不多说,我们现在开始。 目录 写在前面 1. Linux下用户的分类 如何切换用户 如何提高

    2024年02月05日
    浏览(39)
  • Linux配置yum源以及基本yum指令

    Yum(全称为 Yellow dog Updater, Modified)是一个在Fedora和 RedHa t以及CentOS中的Shell前端软件包管理器。基于RPM包管理,能够从指定的服务器自动下载RPM包并且安装,可以自动处理依赖性关系,并且一次安装所有依赖的软件包,无须繁琐地一次次下载、安装。–来自百度百科 在Linux下

    2024年01月24日
    浏览(44)
  • 深入理解JVM虚拟机第二十七篇:详解JVM当中InvokeDynamic字节码指令,Java是动态类型语言么?

     😉😉 学习交流群: ✅✅1:这是孙哥suns给大家的福利! ✨✨ 2:我们免费分享Netty、Dubbo、k8s、Mybatis、Spring...应用和源码级别的视频资料 🥭🥭3:QQ群: 583783824   📚📚  工作微信: BigTreeJava 拉你进微信群,免费领取! 🍎🍎4:本文章内容出自上述:Spring应用课程!💞💞

    2024年02月04日
    浏览(46)
  • Linux | nslookup详细介绍一下这指令的作用以及用法

    linux 当中,nslookup是一个网络工具,通常用于查询域名系统(DNS)服务器以获取主机名或IP地址相关的信息。它可以用于查找主机名的IP地址,反向查找IP地址的主机名,以及查询DNS记录的其他信息。以下是nslookup命令的用法和示例: 查询主机名的IP地址: nslookup example.com 这个

    2024年04月26日
    浏览(44)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包