对ARM异常(Exceptions)的理解

发布者:不染尘埃最新更新时间:2016-04-29 来源: eefocus关键字:ARM异常  Exceptions 手机看文章 扫描二维码
随时随地手机看文章
所有的系统引导程序前面中会有一段类似的代码,如下:

.globl _start                    ;系统复位位置
_start: b       reset            ;各个异常向量对应的跳转代码
        ldr     pc, _undefined_instruction ;未定义的指令异常
        ldr     pc, _software_interrupt     ;软件中断异常
        ldr     pc, _prefetch_abort          ;内存操作异常
        ldr     pc, _data_abort               ;数据异常
        ldr     pc, _not_used                  ;未使用
        ldr     pc, _irq                       ;慢速中断异常
        ldr     pc, _fiq                       ;快速中断异常

从中我们可以看出,ARM支持7种异常。问题时发生了异常后ARM是如何响应的呢?第一个复位异常很好

理解,它放在0x0的位置,一上电就执行它,而且我们的程序总是从复位异常处理程序开始执行的,因

此复位异常处理程序不需要返回。那么怎么会执行到后面几个异常处理函数呢?
看看书后,明白了ARM对异常的响应过程,于是就能够回答以前的这个疑问。
当一个异常出现以后,ARM会自动执行以下几个步骤:
(1)把下一条指令的地址放到连接寄存器LR(通常是R14),这样就能够在处理异常返回时从正确的位置

继续执行。
(2)将相应的CPSR(当前程序状态寄存器)复制到SPSR(备份的程序状态寄存器)中。从异常退出的时

候,就可以由SPSR来恢复CPSR。
(3) 根据异常类型,强制设置CPSR的运行模式位。
(4)强制PC(程序计数器)从相关异常向量地址取出下一条指令执行,从而跳转到相应的异常处理程

序中。
至于这些异常类型各代表什么,我也没有深究。因为平常就关心reset了,也没有必要弄清楚。
ARM规定了异常向量的地址:
        reset            ; 复位 0x0
ldr pc, _undefined_instruction ;未定义的指令异常 0x4
       ldr     pc, _software_interrupt     ;软件中断异常    0x8
       ldr     pc, _prefetch_abort          ;预取指令    0xc
       ldr     pc, _data_abort               ;数据        0x10
       ldr     pc, _not_used                  ;未使用      0x14
       ldr     pc, _irq                       ;慢速中断异常   0x18
        ldr   pc, _fiq                       ;快速中断异常    0x1c
这样理解这段代码就非常简单了。碰到异常时,PC会被强制设置为对应的异常向量,从而跳转到相应的

处理程序,然后再返回到主程序继续执行。
这些引导程序的中断向量,是仅供引导程序自己使用的,一旦引导程序引导Linux内核完毕后,会使用

自己的中断向量。
嗬嗬,这又有问题了。比如,ARM发生中断(irq)的时候,总是会跑到0x18上执行啊。那Linux内核又怎

么能使用自己的中断向量呢?原因在于Linux内核采用页式存储管理。开通MMU的页面映射以后,CPU所

发出的地址就是虚拟地址而不是物理地址。就Linux内核而言,虚拟地址0x18经过映射以后的物理地址

就是0xc000 0018。所以Linux把中断向量放到0xc000 0018就可以了。
MMU的两个主要作用:
(1)安全性:规定访问权限
(2) 提供地址空间:把不连续的空间转换成连续的。
第2点是不是实现页式存储的意思?

.globl _start ;系统复位位置
_start: b reset ;各个异常向量对应的跳转代码
ldr pc, _undefined_instruction ;未定义的指令异常

……

_undefined_instruction :
.word undefined_instruction

也许有人会有疑问,同样是跳转指令,为什么第一句用的是 b reset;
而后面的几个都是用ldr?

为了理解这个问题,我们以未定义的指令异常为例。

当发生了这个异常后,CPU总是跳转到0x4,这个地址是虚拟地址,它映射到哪个物理地址
取决于具体的映射。
ldr pc, _undefined_instruction 
相对寻址,跳转到标号_undefined_instruction,然而真正的跳转地址其实是_undefined_instruction

的内容——undefined_instruction。那句.word的相当于:
_undefined_instruction dw undefined_instruction (详见毕设笔记3)。
这个地址undefined_instruction到底有多远就难说了,也许和标号_undefined_instruction在同一个

页面,也许在很远的地方。不过除了reset,其他的异常是MMU开始工作之后才可能发生的,因此

undefined_instruction 的地址也经过了MMU的映射。
在刚加电的时候,CPU从0x0开始执行,MMU还没有开始工作,此时的虚拟地址和物理地址相同;另一方

面,重启在MMU开始工作后也有可能发生,如果reset也用ldr就有问题了,因为这时候虚拟地址和物理

地址完全不同。

因此,之所以reset用b,就是因为reset在MMU建立前后都有可能发生,而其他的异常只有在MMU建立之

后才会发生。用b reset,reset子程序与reset向量在同一页面,这样就不会有问题(b是相对跳转的)

。如果二者相距太远,那么编译器会报错的


关键字:ARM异常  Exceptions 引用地址:对ARM异常(Exceptions)的理解

上一篇:ARM 中断状态和SVC状态的堆栈切换 (异常)
下一篇:有关arm汇编中的align

推荐阅读最新更新时间:2024-03-16 14:52

ARM基础学习-异常中断处理
中断类型 当异常中断发生的时候,系统执行完当前指令后,将跳转到相应的异常中断处理程序,当处理程序执行完毕后,程序返回到发生中断的指令的下一条指令处执行;在进入异常中断处理程序时,要保存被中断的执行现场,在异常中断处理程序退出时,要恢复被中断的程序的执行现场; 异常中断类型: 1.复位异常发生后,进入到管理模式(svc) 下。 2.软中断发生后, 进入到 管理模式(svc) 下。 3.未定义指令异常发生后, 进入到 未定义指令中止模式(und)下。 4.指令预取中止异常发生后, 进入到 数据访问中止模式(abt)下; 5.数据访问中止异常发生后, 进入到 数据访问中止模式(abt) 下: 6.外部中断发生后, 进入到 外部中
[单片机]
<font color='red'>ARM</font>基础学习-<font color='red'>异常</font>中断处理
ARM程序异常返回操作
异常的发生会导致程序正常运行的被打断, 并将控制流转移到相应的异常处理(异常响应),有些异常(fiq、irq)事件处理后,系统还希望能回 到当初异常发生时被打断的源程序断点处继续完成源程序的执行(异常返回),这就需要一种解决方案, 用于记录源程序的断点位置,以便正确的异常返回。 类似的还有子程序的调用和 返回。在主程序中(通过子程序调用指令)调用子程序时,也需要记录下主程序中的调用点位置,以便将来的子程序的返回。 在ARM处理器中使用 R14实现对断点和调用点的记录,即使用R14用作返 回连接寄存器(LR)。在硬件上和指令执行上,CPU 自动完成相应返回点的记录。在ARM 汇编语言程序设计时,R14和LR通用。 ARM
[单片机]
ARM异常返回修正值
ARM异常返回修正值因异常类型不同而不同,这主要取决于两个方面: a、异常处理完后,返回的地址是异常产生时执行指令的地址还是执行指令下一条指令的地址; b、处理异常时,PC值是否已更新 1、Reset异常 复位异常不需要返回,所以在这不讨论 2、SWI、未定义指令异常 a、SWI、未定义指令异常是由执行该指令时产生的异常,所以,当异常发生时PC值并未更新。 b、链接寄存器LR保存取指的前一条指令,即LR=PC-4,此时PC-4指向执行指令的下1条指令 c、返回时,SWI、未定义指令均已执行完,应返回执行指令的下1条指令,即PC=LR 3、IRQ、FIQ异常 a、处理器处理完当前执行指令后,再去查询IRQ、FIQ引脚是否
[单片机]
<font color='red'>ARM</font><font color='red'>异常</font>返回修正值
ARM处理器的SWI异常中断响应过程
通过SWI异常中断指令,在用户模式下应用程序可以调用系统模式下的代码,在操作系统中表现为系统调用, 那这个过程又是如何实现的呢?带着疑问让我们来学习吧! 在SWI指令中包括一个24位的立即数(中断调用号),该立即数指示了用户要请求的特定的调用功能,所以在SWI的异常中断中要读取这个中断调用号,然后根据中断号,来调用相应的处理程序。这个过程可以分两个步骤: 1.SWI异常中断处理程序 由于是在底层操作所以这个异常中断处理程序得用汇编语言编写,描述如下: area top_swi code readonly export swi_headler swi_headler stmfd sp!, {r0-r12, lr}
[单片机]
ARM异常及向量表
ARM具有7种异常,分别为: 1、复位 2、未定义指令 3、软中断 4、预取指令终止 5、数据终止 6、中断请求(IRQ) 7、快速中断请求(FIQ) 用一句通俗的话去表达ARM的运行情况,那就是ARM总会在运行在以上7种异常情况的某一种之下。初初了解ARM时总会难于去了解这个 异常 是什么样的一个意思,到了现在对ARM有了一点肤浅的理解后,其实可以将这个 异常 理解为 环境 ,或其他表达ARM运行情况的一个形容词就行了。 向量表。现在平时所谓的“表”就是由多项内容构成的一个文字模式,ARM向量表其实也是这样,向量表就是由以上ARM的7种异常的入口地址所构成的。如下表简单示意, 异常类型
[单片机]
基于ARM9芯片S3C2410异常中断程序设计
引言 计算机体系结构中,异常或者中断是处理系统中突发事件的一种机制,几乎所有的处理器都提供这种机制。异常主要是从处理器被动接受的角度出发的一种描述,指意外操作引起的异常。而中断则带有向处理器主动申请的意味。但这两种情况具有一定的共性,都是请求处理器打断正常的程序执行流程,进入特定程序的一种机制。若无特别说明,对“异常”和“中断”都不作严格的区分。本文结合经过实际验证的代码对ARM9中断处理流程进行分析,并设计出基于S3C2410芯片的外部中断处理程序。 1.异常中断响应和返回 系统运行时,异常可能会随时发生。当一个异常出现以后,ARM微处理器会执行以下几步操作: 1) 将下一条指令的地址存入相应连接寄存器LR,以便程序在处
[单片机]
基于<font color='red'>ARM</font>9芯片S3C2410<font color='red'>异常</font>中断程序设计
小广播
添点儿料...
无论热点新闻、行业分析、技术干货……
设计资源 培训 开发板 精华推荐

最新单片机文章
何立民专栏 单片机及嵌入式宝典

北京航空航天大学教授,20余年来致力于单片机与嵌入式系统推广工作。

换一换 更多 相关热搜器件
电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2024 EEWORLD.com.cn, Inc. All rights reserved