历史上的今天
返回首页

历史上的今天

今天是:2025年01月22日(星期三)

正在发生

2021年01月22日 | 如何判断CPU是否正在执行中断函数?

2021-01-22 来源:eefocus

1.这是一个有许多经验的攻城狮都遇到过的坑,本文教你正确绕过这个坑;


2.教大家了解__get_CONTROL的用法,及xQueueSend和xQueueSendFromISR的区别;


问题来源

今天在FreeRTOS系统上移植了部分别人写的代码,移植前仔细看了下源码,确认没问题后,编译,下载,运行,突然“死机了”······


于是,我又再次确认了移植的代码,没有发现Bug所在。此时,我开启了在线调试功能,发现程序死在了“vPortEnterCritical”函数中的断言语句里。如下:

图片



解决问题的过程

我解决问题还是按照常规思维,一步一步跟踪,很多问题其实都是类似道理,有规律可循。


1.查看configASSERT断言做了什么事?

跟踪代码:

#define configASSERT( x ) if( ( x ) == 0 ) { taskDISABLE_INTERRUPTS(); for( ;; ); }


其中,里面taskDISABLE_ INTERRUPTS();就是关中断的意思。紧跟着后面执行了for( ;; );


看到这里,我明白了一点,就是死在for( ;; );里面了。


2.进一步查找问题

我又开始了思考,为什么会执行到这里来呢? 为什么会执行portDISABLE_INTERRUPTS(); uxCriticalNesting++;   if( uxCriticalNesting == 1 )等这些语句呢?


这就是我们常说的“临界段”,这一点我学习RTOS的时候已经明白了,这一个函数肯定会被调用。于是,我把目标锁定了portNVIC_INT_CTRL_REG这个参数:

#define portNVIC_INT_CTRL_REG        ( * ( ( volatile uint32_t * ) 0xe000ed04 ) )


0xe000ed04?  这个地址,相信之前了解过NVIC的都知道,就是Interrupt control state register.即中断控制状态寄存器。



3.确定问题点

从上面的分析,其实问题都已经浮现出来了。于是查看了【Cortex-M3权威指南】中相关的内容。(PS:这本手册真的能解决很多问题,翻译成中文,对大部分朋友来说是一件好事)


其实,有这个一个寄存器:控制寄存器(CONTROL),里面讲述的非常清楚:

图片


看上图,大概意思就是:在中断模式下,CONTROL[1]为0。于是,又把思路转向了core_cm3.c文件中的源码:

__ASM uint32_t __get_CONTROL(void)
{
  mrs r0, control
  bx lr
}

懂一点汇编的,相信在这里都已经明白,大概意思就是过去控制寄存器状态,这也是我开篇说的,让大家了解的__get_CONTROL。


4.在线调试,分析结论

上面分析出来控制寄存器CONTROL,那么我们需要验证是否符合我们预期的效果,通过在线调试,断电就可得出,如下面两图:

a.在非中断情况下的值0x02

图片


b.在中断情况下的值0x00

图片


至此,问题已经查明就是CONTROL。


get_CONTROL的应用

一般在RTOS实时操作系统中,常常使用队列来处理我们的数据,也就是常说的FIFO(先入先出)。


比如:我们在FreeRTOS系统中,要将UART发送、或者接收的数据加入队列:在中断里加入队列,在非中断里加入队列。这个时候,就需要使用get_CONTROL来判断当前是否处于中断函数里。


当然,类似的情况很多,像CAN、I2C、SPI等一样的道理。


举例,CAN总线发送数据加入队列:

图片


多说两句

以上的分析,看似很简单,其实包含的内容很多,可能有很多人觉得:这些问题对于我来说是小菜一碟。


说句实话,我和大家一样,都是慢慢学习过来的,这里面跳过的坑其实很多,是因为我跳过了太多的坑,所以才会对一些问题更加了解。


上面类似的问题,在我学习RTOS、移植CANOpen等等那些时候都有遇到过,想要知道我遇到那些问题,处理起来难不难,明确回答:很多问题在初学的时候都很难,但我还是走过来了。


说到这里,多说一句,关于问问题的话,后台每天都有许多人问我问题,但是有些问题其实真的很简单,比如:编译有个变量未调用的警告、重复定义,多了一个分号等,这些看一下提示都知道。不要告诉我你英语差,我英语初高中从来都没有及格过,依然还是得看英文手册。确实不懂,安装一个翻译软件不难吧。


推荐阅读

史海拾趣

Ecera Comtek Corp公司的发展小趣事

面对日新月异的电子科技行业,Ecera Comtek Corp公司深知只有持续创新才能保持领先地位。因此,公司不断加大对新技术、新产品的研发投入,积极探索新的商业模式和市场机会。同时,Ecera Comtek Corp公司还积极引进外部创新资源,与高校、科研机构等建立紧密的合作关系,共同推动电子科技行业的发展。在Ecera Comtek Corp公司的引领下,电子科技行业正朝着更加智能、高效、环保的方向发展。

请注意,以上故事均基于虚构情节,旨在模拟Ecera Comtek Corp公司可能的发展经历。如有雷同,纯属巧合。

Global Communications公司的发展小趣事
温度传感器和晶体振荡器都可能受到外界噪声的干扰,影响测量和补偿的准确性。因此,在电路设计中需要采取屏蔽、滤波等措施来降低噪声干扰。
旌芯半导体(GN)公司的发展小趣事
将温度传感器与晶体振荡器直接相连,通过调整晶体振荡器的某个参数(如负载电容)来补偿温度变化引起的频率漂移。这种方法简单直接,但可能需要较复杂的电路设计来确保补偿的准确性和稳定性。
ELANTEC (Renesas )公司的发展小趣事

随着全球半导体市场的不断扩大和竞争的加剧,ELANTEC意识到必须加快全球化布局的步伐。因此,公司开始在全球范围内设立研发中心、生产基地和销售网络。目前,Renesas在全球拥有多个研发中心和生产基地,产品覆盖亚洲、欧洲、美洲等多个地区。这种全球化布局不仅使Renesas能够更好地服务全球客户,还为其未来的发展奠定了坚实的基础。

Allegro公司的发展小趣事

随着全球半导体市场的不断扩大和竞争的加剧,ELANTEC意识到必须加快全球化布局的步伐。因此,公司开始在全球范围内设立研发中心、生产基地和销售网络。目前,Renesas在全球拥有多个研发中心和生产基地,产品覆盖亚洲、欧洲、美洲等多个地区。这种全球化布局不仅使Renesas能够更好地服务全球客户,还为其未来的发展奠定了坚实的基础。

CQR SECURITY公司的发展小趣事

为了拓展业务范围和提升品牌影响力,CQR SECURITY公司开始实施国际化战略。公司积极开拓海外市场,与多个国家的电子企业建立了合作关系。同时,CQR还加强了与国际安全组织的交流与合作,共同推动全球网络安全水平的提升。通过国际化战略的成功实施,CQR不仅拓展了业务版图,还提升了自身的技术水平和国际竞争力。

问答坊 | AI 解惑

烧写eboot.nb0后系统仍从之前的xip.nb0启动

最近发现一个很奇怪的问题:在使用DNW烧写系统时,先将xip.nb0烧写进去,然后烧写eboot.nb0.但此时系统会自动重启并且加载的还是之前的xip.nb0 初步分析发现eboot下的BootloaderMain();函数根本就没被执行 如下是异常时和成功时的串口信息: 1. ...…

查看全部问答>

关于EVC程序下载到NK内核 下载目标板 无法运行

Windows CE.NET的应用为MyApp.exe 1.将MyApp.exe复制到E:\\PROJECTS\\MyWinCE\\RelDir\\CEPC_X86Release目录下; 2.创建快捷方式文件MyApp.lnk(文本文件),文件内容如下: 10#\\Windows\\MyApp.exe MyApp.lnk文件也放入E:\\PROJECTS\\MyWinC ...…

查看全部问答>

在WINCE设备上,用VS2003开发的程序连接数据库出错,请教高手

在WINCE设备上,用VS2003开发的程序连接WINCE数据库出错,请教高手 SqlCeConnection conn = new SqlCeConnection(\"Data Source = Test.sdf\"); conn.open(); open这里提示出错,但在WINCE设备上只能看到错误号为:-2147467259,就是不知道什么错误. ...…

查看全部问答>

LINK : fatal error LNK1104: cannot open file 'mfcs42d.lib'?????求助!!!

刚装上EVC4.0+SP4,从PB5导出并安装了自己的SDK,然后在EVC建了一个简单的MFC Application,选择SDK后编译后就出现: LINK : fatal error LNK1104: cannot open file \'mfcs42d.lib\' 我查看了我安装的SDK目录下有这个文件,而且在EVC的Include ...…

查看全部问答>

win 2000 不能识别我们的 USB 设备

我们在做一个USB设备的开发,硬件已经成形了。 但是,问题出在: 将该设备插入到XP系统下,系统的资源管理器里边会出现USB的2个未知设备,(我们这一个设备里,有2个Interface) 看每个的属性,PID值也和我们硬件里边写 的一样,然后安装驱动 ...…

查看全部问答>

用IAR for MSP430的JTAG口仿真,出现了问题,求高手指点

我用的是利达尔的MSP430F2274开发板,它上面直接就有JTAG口仿真,然后我就买了一块并口卡插上去,电源灯会亮,但是一直都不能仿真调试,我想是设置的问题,因为并口卡我用它来下载到ARM7上是没问题的,所以在这里求高手指点。 这个就是错误提示。…

查看全部问答>

出YC2440裸板

收了tq2440,这块yc2440的板子就用不到了,这块板子收来就上电看了一下,除POWER灯外D1-D4全亮,片刻后D3熄灭,D4常亮,D1和D2按一定的规律闪烁.此时按K1后D1-D4全灭,再按一下恢复原来来的状态此板子需要折腾一下,主要就是串口没有,需要转接板。有能 ...…

查看全部问答>

不是精品不上传(单片机C语言程序设计实验指导书)

replyreload += \',\' + 1311171;(单片机C语言程序设计实验指导书)Timson,如果您要查看本帖隐藏内容请回复…

查看全部问答>

求指导

本人在做一个基于单片机的开关电源的毕业设计,思路是这样的,键盘预置电压,控制单片机进行脉宽调制,使输出电压在大范围内可调,输入220V,输出为3~30V线性可调,不知电路方面该如何设计,请论坛的各位指导指导,由衷感谢!!!…

查看全部问答>

STM32的ADC1和ADC2的采集问题

试了一下STM32的ADC1和ADC2,调试时出现的问题让我不解: (1)只使用STM32的ADC1采集信号,PA.0为其模拟输入通道; 将ADC1配置成独立模式、单通道单次转换、软件触发, 采集到的数据是正确的; (2)只使用ADC2采集信号,与(1)中ADC1的设置完全相 ...…

查看全部问答>