历史上的今天
返回首页

历史上的今天

今天是:2024年12月10日(星期二)

正在发生

2018年12月10日 | STM32中断和异常

2018-12-10 来源:eefocus

异常主要分为中断(如IO口,UART,等)和系统异常(如NMI,SYCTICK,等),注意区分中断和系统异常,下文异常为统称,


在CMSIS中,IRQn_Type为异常类型的枚举,系统异常一般为负数,中断则从0开始


常用的操作异常的CMSIS函数,为了可移植性,建议使用这些函数操作异常。中断相关寄存器主要在NVIC,系统异常相关寄存器主要在SCB中。



这些函数在core_cm4.h中定义


系统复位时,所有中断都是禁止的,并且优先级为0(最高优先级),所有系统初始化时要调用一次NVIC_PriorityGroupConfig来设置优先级分组情况。


异常优先级分为抢占优先级和子优先级,高抢占优先级的异常(优先级数字较小)可以抢占低抢占优先级(优先级数字较大)的异常。子优先级决定抢占优先级相同的异常谁先执行。如果抢占优先级和子优先级都相同,则异常号小的异常先执行。


hard fault,NMI,reset,优先级为-1,-2,-3,不可设置,其他异常的优先级只能设置0和以上的数字,所以他们在任何时候都可以抢占其他异常。


中断的状态:


中断可以是Enable或Disable或,由软件设置和清除


 中断可以是Pending或Not Pending,当中断产生时Pending位会被硬件置位,中断消失后不会清除,进入中断处理函数时会被硬件清除,也可以软件设置和清除


         中断可以是Active或Inactive,由硬件设置和清除,正在执行的异常为Active,其他为Inactive,当高优先级中断抢占时,被抢占的中断仍是Active


当中断产生时Pending位会硬件被置位,处理器会马上处理Pending的中断,但有些时候,当中断产生时,处理器正在处理其他高优先级的异常,则处理完后,会根据Penging位再处理该中断。如果在处理高优先级异常过程中,Pending位被清除,则高优先级异常处理完成后不会再处理该中断。


如果中断产生时,该中断被屏蔽了,Pending位也会被置位。例如在执行中断时(此时为Active),将该中断Disable,此时又有该中断产生,则该中断Pending位会被置位。


除了NVIC的Pending位以外,EXTI有相应的Pending位在EXTI寄存器中,TIMER等也是,所以在中断处理函数中要调用相应的清除函数EXTI_ClearITPendingBit,TIM_ClearITPendingBit等,而NVIC的Pending位在进入中断处理函数时会被硬件清除


PRIMASK寄存器(只有最低位有用,其他为保留位)用于禁止所有异常,除了NMI和Hard Fault,只能在特权模式下访问


CMSIS操作的函数:


void __enable_irq();


void __disable_irq();


汇编操作:


CPSIE I           ;Clear PRIMASK (Enable interrupts)

CPSID I           ;Set PRIMASK (Disable interrupts)


需要软件触发中断可以使用:NVIC_SetPendingIRQ(Timer0_IRQn);


如果需要中断处理函数在下条指令前执行则需要加Barrier


NVIC_SetPendingIRQ(Timer0_IRQn);

__DSB();               //Data Synchronization Barrier

__ISB();                //Instruction Synchronization Barrier


ARM体系结构的C编译器遵循AAPCS原则,对函数调用由如下规定:


R0-R3, R12, LR, and PSR为调用者保存寄存器,就是当调用一个函数前需要保存这些寄存器,调用完后恢复,如果调用完后不关心这些寄存器则调用前可以不保存。


R4-R11为被调用者保存寄存器,就是任何函数如果要操作这些寄存器则要先保存,函数返回前要恢复。


浮点数单元的寄存器也一样


S0-S15 为调用者保存寄存器


S16-S31 为被调用者保存寄存器


R0-R3也被用作函数输入参数(R0为第一个参数...),R0也用作函数返回值(如果返回值为64bit,则也会用R1)


在进入异常处理函数前,硬件会将如下寄存器入栈(使用PSP或MSP),如果没有浮点数单元,则只有8个(xPSR,返回地址,LR,R12,R3-R0),这些寄存器组称为Stack Frame


根据AAPCS,在函数进入和退出时,SP的值必须double-word对齐,否则会插入padding以保证对齐。该对齐也可以关闭(xPSR的bit9为0时则不对齐)对齐都由硬件根据xPSR的bit9自动完成


操作CCR寄存器对是否对齐进行设置:


SCB->CCR |= SCB_CCR_STKALIGN_Msk;           // Set STKALIGN bit (bit 9) of CCR



进入异常处理函数后,LR寄存器的值被设置为EXC_RETURN,该值根据此时处理器的状态设置为相应的值,如下图。


由于高四位永远是0xF,所以异常处理函数返回地址不能在0xF0000000 到 0xFFFFFFFF之间,但这部分区间是不能执行区,所以对程序并不造成什么问题。



在Thread Mode下可以使用PSP或MSP,在Handler Mode下只能使用MSP。由于EXC_RETURN的bit2决定了入栈时用的SP,所以在出栈时也会用该SP,这样在线程模式进入异常处理模式,以及异常嵌套时都不会造成栈的混乱。也一样模式。

推荐阅读

史海拾趣

问答坊 | AI 解惑

哪位老大有电子类的毕业设计中英文翻译5000字

谢谢了!有的话麻烦发我邮箱manbu_yuzhong@yahoo.cn…

查看全部问答>

FPGA的串口通信程序求助。。。

我现在就是让FPGA给我发一个welcome的字符串,用串口调试助手的十六进制能显示出每个字母的ASCII码的十六进制形式,但是不以十六进制形式表示的话就什么都不显示了。。。这是什么问题啊?…

查看全部问答>

经常自动开机如何解决?

我是海尔A680笔记本,最近老出现自动开机的现象,开机后的状况是:电源灯亮着,显示器不亮,并且关机的唯一办法是把电池写下来。如果只用电池不用外接电源的话,不会有自动开机的现象。是不是硬件有问题呀?我已经杀过好几次毒了。…

查看全部问答>

fade in / fade out

您好.   楼下的兄弟姐妹们好.   这个月一直有个问题让我困扰着我.   在CE中是否可以真正意义上的实现相对于屏幕弹出的窗口或是图片淡入淡出(弹出时)?就是说.在mobile屏幕上(而不是你自己写的窗口或是其它你程序中 ...…

查看全部问答>

[急求]请教一个好像是485的问题。

我的工程应用: (电脑)--(板-无线模块)           (无线模块)---(板子1)--(板子2)..... 上位机接了一个232转485的板子,上面再插了个深圳买的无线模块。然后离电脑300米的仓库顶上也接了一 ...…

查看全部问答>

win ce下能做作语音识别开发吗,有没有什么好的开发包推荐。

我想做个东西主要用于声音控制方面, 关键字不到20几个,不知道用什么开发好,我对wince不熟悉,希望大家能给提示。…

查看全部问答>

有人用过AD756么???

有人用过AD756么 怎么上电后BUSY引脚是高电平?应该转换时是高电平才对吧 有没有人教教我怎么用这块AD 如何编程? 谢谢!…

查看全部问答>

求模拟串口程序:MSP430F149,波特率9600,晶振32.768K

需要3个串口,只能模拟一个了,请大家帮忙。谢谢…

查看全部问答>

求助高手,编程(C语言的)

求助高手帮忙编个小程序,题目是这样的:输入一个字节,要求输出他的右移1--8位后的数。 我想是不是可以用LED点阵实现呢?用BCD编码器将其转化为二进制的,然后右移一位显示在LED点阵的第一行,右移两位显示在点阵的第二行,如此循环?有高手帮帮 ...…

查看全部问答>

最牛B的 Linux Shell 命令

replyreload += \',\' + 1485005; 1、知道 #!! 这个命令是干什么的吗 ? 2、HTTP方式共享当前文件夹的文件 ? 3、抓取LINUX桌面的视频 ? 4、dd是常用的数据拷贝程序 ? 5、查看系统中占用端口的进程 ? 6、通过 SSH 挂载远程主机上的文件 ...…

查看全部问答>