当前位置:首页 > 单片机 > 单片机
[导读]以下出自–《cortex-M3权威指南》特殊功能寄存器组:程序状态寄存器组(PSRs 或曰xPSR)中断屏蔽寄存器组(PRIMASK, FAULTMASK,以及BASEPRI)控制寄存器(CONTROL)xPSR:记录ALU算数逻辑单元(Arithmetic Logic Unit

以下出自–《cortex-M3权威指南》

特殊功能寄存器组:

程序状态寄存器组(PSRs 或曰xPSR)

中断屏蔽寄存器组(PRIMASK, FAULTMASK,以及BASEPRI)

控制寄存器(CONTROL)
xPSR:
记录ALU算数逻辑单元(Arithmetic Logic Unit) 标志(0 标志,进位标志,负数标志,溢出标志),执行状态,以及当前正服务的中断号。

应用程序 PSR(APSR)

中断号 PSR(IPSR)

执行 PSR(EPSR)
这里唠叨下,只因不熟悉。。。。
通过MRS/MSR 指令,这3 个PSRs 即可以单独访问,也可以组合访问(2 个组合,3 个组合都可以)。当使用三合一的方式访问时,应使用名字“xPSR”或者“PSR”。
关于ICI/IT、T:
ICI:在中断延迟中有提到,与LDM/STM的处理机制有关。LDM/STM是一串LDR/STR的速度优化版。于是,为了加速中断的响应,CM3支持LDM/STM指令的中止和继续,就好像它们只是普通的一串LDR/STR一样。为了实现“指令撕裂与粘合”的目的,需要记录中断时数据传送的进程。为此,CM3在xPSR中开出若干个“ICI位”,记录下一个即将传送的寄存器是哪一个(LDM/STM在汇编时,都把寄存器号升序排序)。在服务例程返回后,xPSR被弹出,CM3再从ICI bits中获取当时LDM/STM执行的进度,从而可以继续传送。
这个办法听起来是个好主意,只是在个别情况下还有一点限制:IF‐THEN(IT)指令的执行也需要在xPSR中使用几个位,可它需要的位刚好与ICI位重合(类似C中的union)——both ICI bits和IT条件都记录在EPSR中。所以,如果在IF‐THEN中使用了LDM/STM,则不再记录LDM/STM
的执行进度。但尽管如此,及时响应中断依然是首要任务。此时只好把LDM/STM取消,待中断返回后继续执行。–这里待续++

中断屏蔽寄存器组:

PRIMASK:除能所有的中断——当然了,不可屏蔽中断(NMI)才不甩它呢。

FAULTMASK:除能所有的fault——NMI 依然不受影响,而且被除能的faults 会“上访”。

BASEPRI:除能所有优先级不高于某个具体数值的中断。

控制寄存器:

CONTROL:定义特权状态(见后续章节对特权的叙述),并且决定使用哪一个堆栈指针

只有在特权级下,才允许访问这3 个寄存器。

一个指定PSP 进行更新的例子:

LDRR0,=0x20008000MSRPSP,R0BXLR;如果是从异常返回到线程状态,则使用新的PSP的值作为栈顶指针123123

cortex-M3权威指南,有这样一段:


为了快速地开关中断,CM3 还专门设置了一条CPS 指令,有4 种用法

CPSIDI;PRIMASK=1;关中断CPSIEI;PRIMASK=0;开中断CPSIDF;FAULTMASK=1;关异常CPSIEF;FAULTMASK=0;开异常12341234

?CPS指令是?==改变处理器状态==change processor state
这款内核也许就这两个CPS指令

SVC和PendSV

SVC(系统服务调用,亦简称系统调用)和PendSV(可悬起系统调用),它们多用于在操作系统之上的软件开发中。SVC 用于产生系统函数的调用请求。例如,操作系统不让用户程序直接访问硬件,而是通过提供一些系统服务函数,用户程序使用SVC 发出对系统服务函数的呼叫请求,以这种方法调用它们来间接访问硬件。因此,当用户程序想要控制特定的硬件时,它就会产生一个SVC 异常,然后操作系统提供的SVC 异常服务例程得到执行,它再调用相关的操作系统函数,后者完成用户程序请求的服务。
这种“提出要求——得到满足”的方式,很好、很强大、很方便、很灵活、很能可持续发展。首先,它使用户程序从控制硬件的繁文缛节中解脱出来,而是由OS 负责控制具体的硬件。第二,OS 的代码可以经过充分的测试,从而能使系统更加健壮和可靠。第三,它使用户程序无需在特权级下执行,用户程序无需承担因误操作而瘫痪整个系统的风险。第四,通过SVC 的机制,还让用户程序变得与硬件无关,因此在开发应用程序时无需了解硬件的操作细节,从而简化了开发的难度和繁琐度,并且使应用程序跨硬件平台移植成为可能。开发应用程序唯一需要知道的就是操作系统提供的应用编程接口(API),并且了解各个请求代号和参数表,然后就可以使用SVC 来提出要求了(事实上,为使用方便,操作系统往往会提供
一层封皮,以使系统调用的形式看起来和普通的函数调用一致。各封皮函数会正确使用SVC指令来执行系统调用——译者注)。其实,严格地讲,操作硬件的工作是由设备驱动程序完成的,只是对应用程序来说,它们也是操作系统的一部分。如图7.14 所示

SVC 异常通过执行”SVC”指令来产生。该指令需要一个立即数,充当系统调用代号。SVC异常服务例程稍后会提取出此代号,从而解释本次调用的具体要求,再调用相应的服务函数。例如,

SVC0x3;调用3号系统服务11

在SVC 服务例程执行后,上次执行的SVC 指令地址可以根据自动入栈的返回地址计算出。找到了SVC 指令后,就可以读取该SVC 指令的机器码,从机器码中萃取出立即数,就获知了请求执行的功能代号。如果用户程序使用的是PSP,服务例程还需要先执行

MRSRn,PSP11

指令来获取应用程序的堆栈指针。通过分析LR 的值,可以获知在SVC 指令执行时,正在使用哪个堆栈。
由CM3 的中断优先级模型可知,你不能在SVC 服务例程中嵌套使用SVC 指令(事实上这样做也没意义),因为同优先级的异常不能抢占自身。这种作法会产生一个用法fault。同理,在NMI 服务例程中也不得使用SVC,否则将触发硬fault。

PendSV:
另一个相关的异常是PendSV(可悬起的系统调用),它和SVC 协同使用。一方面,SVC异常是必须立即得到响应的(若因优先级不比当前正处理的高,或是其它原因使之无法立即响应,将上访成硬fault——译者注),应用程序执行SVC 时都是希望所需的请求立即得到响应。另一方面,PendSV 则不同,它是可以像普通的中断一样被悬起的(不像SVC 那样会上访)。OS 可以利用它“缓期执行”一个异常——直到其它重要的任务完成后才执行动作。悬起PendSV 的方法是:手工往NVIC 的PendSV 悬起寄存器中写1。悬起后,如果优先级不够高,则将缓期等待执行。
PendSV 的典型使用场合是在上下文切换时(在不同任务之间切换)。例如,一个系统中有两个就绪的任务,上下文切换被触发的场合可以是:

执行一个系统调用

系统滴答定时器(SYSTICK)中断,(轮转调度中需要)
举个简单的例子来辅助理解。假设有这么一个系统,里面有两个就绪的任务,并且通过SysTick 异常启动上下文切换。如图7.15 所示。

上图是两个任务轮转调度的示意图。但若在产生SysTick 异常时正在响应一个中断,则SysTick 异常会抢占其ISR。在这种情况下,OS 不得执行上下文切换,否则将使中断请求被延迟,而且在真实系统中延迟时间还往往不可预知——任何有一丁点实时要求的系统都决不能容忍这种事。因此,在CM3 中也是严禁没商量——如果OS 在某中断活跃时尝试切入线程模式,将触犯用法fault 异常。

为解决此问题,早期的OS 大多会检测当前是否有中断在活跃中,只有没有任何中断需要响应时,才执行上下文切换(切换期间无法响应中断)。然而,这种方法的弊端在于,它可以把任务切换动作拖延很久(因为如果抢占了IRQ,则本次SysTick 在执行后不得作上下文切换,只能等待下一次SysTick 异常),尤其是当某中断源的频率和SysTick 异常的频率比较接近时,会发生“共振”。
现在好了,PendSV 来完美解决这个问题了。PendSV 异常会自动延迟上下文切换的请求,直到其它的ISR 都完成了处理后才放行。为实现这个机制,需要把PendSV 编程为最低优先级的异常。如果OS 检测到某IRQ 正在活动并且被SysTick 抢占,它将悬起一个PendSV 异常,以便缓期执行上下文切换。如图7.17 所示

个中事件的流水账记录如下:

任务 A 呼叫SVC 来请求任务切换(例如,等待某些工作完成)

OS 接收到请求,做好上下文切换的准备,并且pend 一个PendSV 异常。

当 CPU 退出SVC 后,它立即进入PendSV,从而执行上下文切换。

当 PendSV 执行完毕后,将返回到任务B,同时进入线程模式。

发生了一个中断,并且中断服务程序开始执行

在 ISR 执行过程中,发生SysTick 异常,并且抢占了该ISR。

OS 执行必要的操作,然后pend 起PendSV 异常以作好上下文切换的准备。

当 SysTick 退出后,回到先前被抢占的ISR 中,ISR 继续执行

ISR 执行完毕并退出后,PendSV 服务例程开始执行,并且在里面执行上下文切换

当 PendSV 执行完毕后,回到任务A,同时系统再次进入线程模式。


本站声明: 本文章由作者或相关机构授权发布,目的在于传递更多信息,并不代表本站赞同其观点,本站亦不保证或承诺内容真实性等。需要转载请联系该专栏作者,如若文章内容侵犯您的权益,请及时联系本站删除。
换一批
延伸阅读

湖北某大型钢股份有限公司供配电系统由220 kV 总降、自备热电厂及三座 110 kV分厂变电站构成。 该钢厂热轧主传动采用新型的高压大功率变频设备,致使配电系统高次谐波和电压波动问题严

关键字: svc 电能 福禄克

近日,东芝宣布推出新品——“M3H族”微控制器,该产品基于全球标准的Arm Cortex-M3内核,专为电机控制而设计,可满足消费设备和工业设备的各种需求。新产品的出现扩大了 “TXZ?系列”微控制器的产品阵容。

关键字: ARM cortex-m3 内核 微控制器 电源新品

已经是很久没有写文章了,因为没有时间,人家都说大四不考研,天天像过年,可我依旧没能有那份闲暇的时间。现在几乎人人的手里都是一款安卓智能机这是我非常羡慕的,而我手

关键字: adxl345 cortex-m3 单片机 电源技术解析 重力感应

1. 摘要 Cortex-M内核实现了一个高效异常处理模块,可以捕获非法内存访问和数个程序错误条件。本应用笔记从程序员角度描述Cortex-M Fault异常,并且讲述在软件开发周期中的Fault用法。 2. 简介...

关键字: cortex-m3 cortex-m4 fault异常

1.1 启动代码内容1) 硬件初始化:最起码的是要初始化堆栈指针。2) C语言环境 :在main函数调用之前要完成对一些变量的初始化。3) 应用初始化: 这主要取决于你的应用。比如设置系统的晶振、时钟。1.2 图解M3启...

关键字: cortex-m3 启动代码

有時候切換了編譯方式如從ARMCC轉變為GCC編譯器,編譯下載時會出現Error:FlashDownloadfailed:-"Cortex-M3"這個錯誤。目前,自己測試解決的方式是:刪除相同目錄下的...

关键字: cortex-m3 error keil

在项目处于调试期间,Fault处理程序可能只是一个断点指令,调试器遇到这个指令后停止程序的运行。默认情况下,由于非硬Fault被禁能,所有发生的非Fault都会上访成硬Fault,因此只要在硬Fault处理程序中设...

关键字: cortex-m3 cortex-m4 fault fault处理函数

1 Cortex-M3/4的Fault简介 Cortex-M3/4的Fault异常是由于非法的存储器访问(比如访问0地址、写只读存储位置等)和非法的程序行为(比如除以0等)等造成的。常见的4种异常及产生异常的情况如...

关键字: 4 cortex-m3 调试方法 hard fault

在编译下面一段代码时:STACK_TOPEQU0x20002000AREAReset,CODE,READONLYDCD0x20002000DCDStartENTRY;CODE16Startldrr2,=TestLDRD...

关键字: cortex-m3 keil编译 纯汇编 align地址

STM32(Cortex-M3)中有两个优先级的概念——抢占式优先级和响应优先级,有人把响应优先级称作'亚优先级'或'副优先级',每个中断源都需要被指定这两...

关键字: cortex-m3 STM32 中断优先级
关闭
关闭