1、单片机stm32 hard faultstm32 hard fault发布: 2009-8-05 11:12 | 作者: learning | 来源: STM32技术社区Hard fault (硬错误,也有译为硬件错误的)是在STM32上编写程序中所产生的错误中原因最为纷繁复杂的一种错误.由于能导致该错误的原因很多,所以一但出现,比较难找到其原因.今天就个人的一些收集整理一下,写出以备各位查找利用.硬fault 是总线fault、存储器管理fault 以及用法fault 上访的结果。如果这些fault 的服务例程无法执行,它们就会成为“硬伤”上访(escalation)成硬fault。另外,在
2、取向量(异常处理是对异常向量表的读取)时产生的总线fault 也按硬fault 处理。在NVIC 中有一个硬fault 状态寄存器(HFSR),它指出产生硬fault 的原因。如果不是由于取向量造成的,则硬fault 服务例程必须检查其它的fault 状态寄存器,以最终决定是谁上访的。硬fault 状态寄存器(地址:0xE000ED2C):h_1.JPG当发生硬错误后,而你又具有在线调试器的话,你可以直接在你的编译器的调试介面去查看0xE000ED2C处的值(如在IAR+JLINK的调试环境下,可通过点View Symbolic Memory,在Go to处输出地址,回车即可跳到该地址)以缩小
3、查找错误的范围.DEBUGEVF:因调试事件导致的fault:1. 断点/观察点事件2. 如果在硬 fault 服务例程的执行过程中,没有使能监视器异常(MON_EN=0)也没有使能停机调试(C_DEBUGEN=0),却执行了BKPT 指令。缺省时,有些C 编译器可能会在半主机代码中使用BKPT 指令。也可以用上面的方法去查看 调试fault状态寄存器(DFSR) 0xE000ED30的值来进一步缩小范围:h_2.JPG一般情况下这一类错误可以给芯片重新上电来解决. learning (2009-8-05 11:14:32)VECTBL:取向量失败,1. 在取向量过程中发生总线 fault2.
4、 向量表偏移量设置有误考虑地址对齐,Flash保护等原因.FORCED:总线fault、存储器管理fault 以及用法fault 上访的结果,因此要重新回头找一下各对应fault来确定到底是哪个出错.总线fault 状态寄存器(BFSR),地址:0xE000_ED29:h_3.JPG各对应位出错可能原因见下表所示:h_4.JPG存储器管理fault 状态寄存器(MFSR) 0xE000_ED28:h_5.JPGMemManage faults 的常见诱因如下所示:1、 访问了 MPU 设置区域覆盖范围之外的地址2、 往只读 region 写数据3、用户级下访问了只允许在特权级下访问的地址yqi
5、n (2009-8-05 11:22:02)终于来解决这个问题的人了,顶啊,是不是好像也碰到过这个问题learning (2009-8-05 11:24:33)i=s 本帖最后由 learning 于 2009-8-5 11:27 编辑 对就各位的错误的原因可见下表:h_6.JPG用法fault 状态寄存器(UFSR),地址:0xE000_ED2A:h_7.JPGlearning (2009-8-05 11:29:12)各对应位错误产生的原因对照下表:h_8.JPGlearning (2009-8-05 11:30:20)假如你没有在线调试器的话也不妨尝试使用串口来打印出各种数据:下面的代码出
6、于一个名为joseph.yiu的人之手。具体出处为:/ hard fault handler wrapper in assembly / it extract the location of stack frame and pass it / to handler in C as pointer. _asm void hard_fault_handler_asm(void) IMPORT hard_fault_handler_c TST LR, #4 ITE EQ MRSEQ R0, MSP MRSNE R0, PSP B hard_fault_handler_c /And then you
7、can extract the stacked registers in C: / hard fault handler in C, / with stack frame location as input parameter void hard_fault_handler_c(unsigned int * hardfault_args) unsigned int stacked_r0; unsigned int stacked_r1; unsigned int stacked_r2; unsigned int stacked_r3; unsigned int stacked_r12; uns
8、igned int stacked_lr; unsigned int stacked_pc; unsigned int stacked_psr; stacked_r0 = (unsigned long) hardfault_args0); stacked_r1 = (unsigned long) hardfault_args1); stacked_r2 = (unsigned long) hardfault_args2); stacked_r3 = (unsigned long) hardfault_args3); stacked_r12 = (unsigned long) hardfault
9、_args4); stacked_lr = (unsigned long) hardfault_args5); stacked_pc = (unsigned long) hardfault_args6); stacked_psr = (unsigned long) hardfault_args7); printf (Hard fault handlern); printf (R0 = %xn, stacked_r0); printf (R1 = %xn, stacked_r1); printf (R2 = %xn, stacked_r2); printf (R3 = %xn, stacked_
10、r3); printf (R12 = %xn, stacked_r12); printf (LR = %xn, stacked_lr); printf (PC = %xn, stacked_pc); printf (PSR = %xn, stacked_psr); printf (BFAR = %xn, (*(volatile unsigned long *)(0xE000ED38); printf (CFSR = %xn, (*(volatile unsigned long *)(0xE000ED28); printf (HFSR = %xn, (*(volatile unsigned lo
11、ng *)(0xE000ED2C); printf (DFSR = %xn, (*(volatile unsigned long *)(0xE000ED30); printf (AFSR = %xn, (*(volatile unsigned long *)(0xE000ED3C); exit(0); / terminate return; learning (2009-8-05 11:33:53)你可以通过写入如下代码进行测试:_asm UndefinedInstruction(void) DCI 0xf123; DCI 0x4567; BX LR; Or create unaligned multiple load/store _asm BadAlignedLDM(void) MOVS r0, #1 LDM r0,r1-r2 BX LR; 想更深入的了解该问题可以参考:
copyright@ 2008-2022 冰豆网网站版权所有
经营许可证编号:鄂ICP备2022015515号-1