【经验】 EFM32工程代码HardFault异常故障调试方法


最近有客户反馈使用EFM32系列MCU开发时,遇到HardFault问题,但是很难定位到导致故障的代码。本篇文章为大家讲解EFM32工程代码HardFault异常故障调试方法,来定位故障原因。使用Simplicity IDE开发环境调试,编译器是GNU ARM v4.8.3,硬件基于EFM32GG-STK3700。
原理介绍
Cortex-M架构定义了硬件故障处理(HardFault Handlers)程序,当内核企图执行无效的操作时,例如操作一个无效的操作码或访问非映射内存,就会进入到这个程序。Cortex-M3或Cortex-M4内核的器件,定义了下面的处理程序:
• Bus Fault
• Memory Management Fault
• Usage Fault
• Hard Fault
前面3个处理程序必须特别启用,如果未启用,将自动升级为第4个硬件故障。当错误发生,SCB->CFSR寄存器包含有关故障原因的信息。此外,硬件在进入硬件故障处理中断程序之前会自动将多个CPU寄存器推送到堆栈上进行保存,如图一。因此在进入中断程序后可以读取到这些值,对其进行检查,以便进一步调试故障的原因。LR是Link Register,它存储子程序、函数调用和异常的返回信息。PC是Program Counter,它指程序运行的地址,而错误产生时保存的就是出现错误时的程序地址。通过LR和PC两个寄存器的值,就可以定位到故障原因。
图一:中断前后堆栈指针指向
添加程序代码
需要在HardFault_Handler(void)函数中使用汇编语句,作用是检查哪个堆栈被使用,并复制堆栈指针到R0寄存器。定义__attribute__( (naked) )是为了避免编译器生成函数修改堆栈指针。添加debugHardfault函数。本文工程中输出是通过SWO引脚输出,因此在工程中还需要添加setupSWOForPrint()函数和retargetio.c文件(路径:
{SimplicityStudio_root}/v4/developer\sdks\exx32\v5.0.0.0\hardwarekits/common/drivers/)。完整代码如下:
#include "em_device.h"
#include "em_chip.h"
#include <stdio.h>
void setupSWOForPrint(void)
{
/* Enable GPIO clock. */
CMU->HFPERCLKEN0 |= CMU_HFPERCLKEN0_GPIO;
/* Enable Serial wire output pin */
GPIO->ROUTE |= GPIO_ROUTE_SWOPEN;
#if defined(_EFM32_GIANT_FAMILY) || defined(_EFM32_LEOPARD_FAMILY) || defined(_EFM32_WONDER_FAMILY)
/* Set location 0 */
GPIO->ROUTE = (GPIO->ROUTE & ~(_GPIO_ROUTE_SWLOCATION_MASK)) | GPIO_ROUTE_SWLOCATION_LOC0;
/* Enable output on pin - GPIO Port F, Pin 2 */
GPIO->P[5].MODEL &= ~(_GPIO_P_MODEL_MODE2_MASK);
GPIO->P[5].MODEL |= GPIO_P_MODEL_MODE2_PUSHPULL;
#else
/* Set location 1 */
GPIO->ROUTE = (GPIO->ROUTE & ~(_GPIO_ROUTE_SWLOCATION_MASK)) |GPIO_ROUTE_SWLOCATION_LOC1;
/* Enable output on pin */
GPIO->P[2].MODEH &= ~(_GPIO_P_MODEH_MODE15_MASK);
GPIO->P[2].MODEH |= GPIO_P_MODEH_MODE15_PUSHPULL;
#endif
/* Enable debug clock AUXHFRCO */
CMU->OSCENCMD = CMU_OSCENCMD_AUXHFRCOEN;
/* Wait until clock is ready */
while (!(CMU->STATUS & CMU_STATUS_AUXHFRCORDY));
/* Enable trace in core debug */
CoreDebug->DEMCR |= CoreDebug_DEMCR_TRCENA_Msk;
ITM->LAR = 0xC5ACCE55;
ITM->TER = 0x0;
ITM->TCR = 0x0;
TPI->SPPR = 2;
TPI->ACPR = 0xf;
ITM->TPR = 0x0;
DWT->CTRL = 0x400003FF;
ITM->TCR = 0x0001000D;
TPI->FFCR = 0x00000100;
ITM->TER = 0x1;
}
void debugHardfault(uint32_t *sp)
{
uint32_t cfsr = SCB->CFSR;
uint32_t hfsr = SCB->HFSR;
uint32_t mmfar = SCB->MMFAR;
uint32_t bfar = SCB->BFAR;
uint32_t r0 = sp[0];
uint32_t r1 = sp[1];
uint32_t r2 = sp[2];
uint32_t r3 = sp[3];
uint32_t r12 = sp[4];
uint32_t lr = sp[5];
uint32_t pc = sp[6];
uint32_t psr = sp[7];
printf("HardFault:\n");
printf("SCB->CFSR 0x%08lx\n", cfsr);
printf("SCB->HFSR 0x%08lx\n", hfsr);
printf("SCB->MMFAR 0x%08lx\n", mmfar);
printf("SCB->BFAR 0x%08lx\n", bfar);
printf("\n");
printf("SP 0x%08lx\n", (uint32_t)sp);
printf("R0 0x%08lx\n", r0);
printf("R1 0x%08lx\n", r1);
printf("R2 0x%08lx\n", r2);
printf("R3 0x%08lx\n", r3);
printf("R12 0x%08lx\n", r12);
printf("LR 0x%08lx\n", lr);
printf("PC 0x%08lx\n", pc);
printf("PSR 0x%08lx\n", psr);
while(1);
}
__attribute__( (naked) )
void HardFault_Handler(void)
{
__asm volatile
(
"tst lr, #4 \n"
"ite eq \n"
"mrseq r0, msp \n"
"mrsne r0, psp \n"
"ldr r1, debugHardfault_address \n"
"bx r1 \n"
"debugHardfault_address: .word debugHardfault \n"
);
}
int RETARGET_ReadChar(void)
{
return 0;
}
int RETARGET_WriteChar(char c)
{
return ITM_SendChar(c);
}
int div(int lho, int rho)
{
return lho/rho;
}
/**************************************************************************//**
* @brief Main function
*****************************************************************************/
int main(void)
{ int a = 10;
int b = 0;
int c;
/* Chip errata */
CHIP_Init();
SCB->CCR |= 0x10;
setupSWOForPrint();
printf("Start\n");
c = div(a, b);
/* Create an invalid function pointer and call it.
* This will trigger a Hard Fault. */
//void (*fp)(void) = (void (*)(void))(0x00000008);
//fp();
/* Infinite loop */
while (1);
}
分析调试结果
上面代码在主函数里调用了一个除数函数div(int lho, int rho),并人为的让分母为0,造成一个异常。将程序下载到MCU运行后,利用Commander SWO终端可以看到输出结果,如下图二:
图二:Commander SWO终端输出结果
在实际开发中我们是不知道是哪个函数导致异常的,那么如何从输出结果中分析出导致异常的函数呢?我们在编译生成的.map文件中找到LR和PC值的地址区间,可以看到LR的值0x000004c5是落在main函数里,main函数在Flash的起始地址是0x00000494。PC的值0x00000482是落在div函数里,div函数在Flash的起始地址是0x00000474,从而定位到导致异常的函数是div函数。定位到异常的函数,大家就可以比较容易查找出错误的原因了。
世强元件电商版权所有,转载请注明来源及链接。
- |
- +1 赞 0
- 收藏
- 评论 4
本网站所有内容禁止转载,否则追究法律责任!
评论
全部评论(4)
-
风云再起 Lv4. 资深工程师 2017-12-09好好干
-
ken2089 Lv4. 资深工程师 2017-12-09学习了
-
沈戈戈 Lv7. 资深专家 2017-12-09感谢分享,资料不错,学习了解下先
-
龙大 Lv7. 资深专家 2017-12-09不错
相关推荐
【经验】MCU EFM32 debug引脚复用引起的代码下载问题分析
在MCU的应用当中,我们经常会利用完MCU的一切资源,比如EFM32中的J-Link调试接口SWDIO和SWCLK,这两个引脚除了作为J-Llink引脚之外,还可以作为通用GPIO来实现其它功能,这样设计并没有问题,但是需要进行代码更新调试或者再次代码下载时,无法进行调试或者下载,具体查看方式为……
【经验】如何使用Simplicity Studio查看MCU内部Flash的数据?
Simplicity Studio是Silicon Labs公司免费提供给客户用于MCU、Wireless SOC等平台的开发工具,其支持C8051F系列、EFM8系列、EFM32系列、EZR32系列以及EFR32系列器件。
【经验】EFM32系列32位超低功耗MCU之复位源读取
EFM32是Silicon Labs公司推出的32位超低功耗MCU系列,由于其超低功耗和丰富的外设等特性,被广泛的使用各种产品开发。很多时候工程师需要监控MCU的复位原因,根据复位原因来查找程序可能存在的问题。但是很多工程师通过读取RMU_RSTCAUSE寄存器得到复位源不准确,本文以EFM32GG-STK3700 Demo为例,指导大家如何正确读取EFM32的复位源。
SILICON LABS 32-bit Microcontroller选型表
SILICON LABS 32位MCU选型,频率24MHz~80MHz,Flash存储4kB~2048kB,RAM存储2kB~512kB。
产品型号
|
品类
|
系列
|
Frequency(MHz)
|
Flash (kB)
|
RAM (kB)
|
Vdd min(V)
|
Vdd max(V)
|
Package Type
|
Package Size (mm)
|
Internal Osc.
|
Debug Interface
|
Cryptography
|
Dig I/O Pins
|
ADC 1
|
DAC
|
USB
|
Cap Sense
|
LCD
|
Temp Sensor
|
Timers (16-bit)
|
UART
|
USART
|
SPI
|
I2C
|
I2S
|
EMIF
|
RTC
|
Comparators
|
EFM32GG290F512-BGA112
|
32位MCU
|
EFM32 Giant Gecko
|
48
|
512
|
128
|
1.98
|
3.8
|
BGA112
|
10x10
|
±2%
|
ETM; SW
|
AES-128 AES-256
|
90
|
12-bit, 8-ch., 1 Msps
|
12-bit, 2 ch.
|
-
|
Cap Sense
|
-
|
Temp Sensor
|
4
|
7
|
3
|
3
|
2
|
1
|
0
|
RTC
|
2
|
Silabs的32位MCU EFM32 SWDIO和SWCLK两个管脚被复用之后,无法下载代码,怎么解决?
解决办法1: 在GPIO初始化之前加入一段较长的延迟,上电之后可以进行代码下载。 解决办法2: 需要外部拉低SWDIO引脚,然后上电,就可以进行代码下载了。
SILICON LABS EFM32PG23/EFM32PG22 32-bit Microcontrollers选型表
EFM32PG23 Series 2 and EFM32PG22 Series 2 MCUs
产品型号
|
品类
|
Series
|
Core
|
Max GPIO
|
Max LCD Segments
|
Max Temperature(℃)
|
Vdd Min (V)
|
Vdd Max (V)
|
Frequency(MHz)
|
Flash (kB)
|
RAM (kB)
|
Dig I/O Pins
|
Security
|
ADC 1
|
USB
|
Temp Sensor
|
UART
|
RTC
|
Package Type
|
Package Size (mm)
|
Internal Osc.
|
Debug Interface
|
Cryptography
|
EFM32PG23B200F128IM40
|
Microcontroller
|
EFM32PG23 Series 2
|
ARM Cortex-M33
|
34
|
4 x 20
|
125
|
1.71
|
3.8
|
80
|
128
|
64
|
29
|
Vault
|
16-bit, 12-ch., 1 Msps
|
×
|
Temp Sensor
|
3
|
RTC
|
QFN40
|
5x5
|
2%
|
Secure; SW; ETM
|
AES-1
AES-256
|
Silicon Labs EFM8BB1系列8位MCU的量产软件有哪些?
Silicon Labs EFM8BB1系列8位MCU的量产软件可以采用Silicon Labs 原厂提供的MCU Production Programmer 和 Flash Programming Utility软件,建议采用前者,下载效率更高;
SILICON LABS EFM32 Wonder Gecko 32-bit Microcontroller选型表
SILICON LABS 32位MCU选型,基于48MHz Frequency,64kB~256kB Flash,32kB RAM等参数进行选型。
产品型号
|
品类
|
Frequency(MHz)
|
Flash (kB)
|
RAM (kB)
|
Dig I/O Pins
|
ADC 1
|
DAC
|
Cap Sense
|
Temp Sensor
|
Timers (16-bit)
|
UART
|
USART
|
SPI
|
I2C
|
I2S
|
EMIF
|
RTC
|
Comparators
|
Vdd min(V)
|
Vdd max(V)
|
Package Type
|
Package Size (mm)
|
Internal Osc.
|
Debug Interface
|
Cryptography
|
ADC
|
EFM32WG230F128-QFN64
|
Microcontroller
|
48
|
128
|
32
|
56
|
12-bit, 8-ch., 1 Msps
|
12-bit, 2 ch.
|
Cap Sense
|
Temp Sensor
|
4
|
5
|
3
|
3
|
2
|
1
|
0
|
RTC
|
2
|
1.98
|
3.8
|
QFN64
|
9x9
|
±2%
|
ETM; SW
|
AES-128 AES-256
|
8 x Ch 500 x MSPS 12 x bit
|
SILICON LABS EFM32 Leopard Gecko 32-bit Microcontroller选型表
SILICON LABS 32位MCU选型,基于48MHz Frequency,64kB~256kB Flash,32kB RAM等参数进行选型。
产品型号
|
品类
|
Frequency(MHz)
|
Flash (kB)
|
RAM (kB)
|
Dig I/O Pins
|
ADC 1
|
DAC
|
Cap Sense
|
Temp Sensor
|
Timers (16-bit)
|
UART
|
USART
|
SPI
|
I2C
|
I2S
|
EMIF
|
RTC
|
Comparators
|
Vdd min(V)
|
Vdd max(V)
|
Package Type
|
Package Size (mm)
|
Internal Osc.
|
Debug Interface
|
Cryptography
|
EFM32LG230F128G-QFN64
|
Microcontroller
|
48
|
128
|
32
|
56
|
12-bit, 8-ch., 1 Msps
|
12-bit, 2 ch.
|
Cap Sense
|
Temp Sensor
|
4
|
5
|
3
|
3
|
2
|
1
|
0
|
RTC
|
2
|
1.98
|
3.8
|
QFN64
|
9x9
|
±2%
|
ETM; SW
|
AES-128 AES-256
|
SILICON LABS EFM32 Gecko 32-bit Microcontroller选型表
SILICON LABS 32位MCU选型,基于32MHz Frequency,16kB~128kB Flash,8kB或16kB RAM等参数进行选型。
产品型号
|
品类
|
Frequency(MHz)
|
Flash (kB)
|
RAM (kB)
|
Dig I/O Pins
|
ADC 1
|
DAC
|
Cap Sense
|
Temp Sensor
|
Timers (16-bit)
|
UART
|
USART
|
SPI
|
I2C
|
I2S
|
EMIF
|
RTC
|
Comparators
|
Vdd min(V)
|
Vdd max(V)
|
Package Type
|
Package Size (mm)
|
Internal Osc.
|
Debug Interface
|
EFM32G200F16-QFN32
|
Microcontroller
|
32
|
16
|
8
|
24
|
12-bit, 4-ch., 1 Msps
|
12-bit, 1-ch.
|
Cap Sense
|
Temp Sensor
|
2
|
0
|
2
|
2
|
1
|
0
|
0
|
RTC
|
2
|
1.98
|
3.8
|
QFN32
|
6x6
|
±2%
|
SW
|
EFM32 MCU中DMA功能传送是否存在优先级?
silicon labs 32位MCU 内的DMA功能传送中分为高优先级和基础优先级。每种优先级下有各通道的自然优先级,通道 数越大自然优先级越小。
silicon labs EFM32G系列32位MCU的TIMER计数器的时钟源有哪些?
silicon labs EFM32G系列32位MCU的TIMER计数器的时钟源如下: 1、由高频外设时钟HFPERCLK经分频后提供给TIMER; 2、由CC1通道输入的外部时钟源,可以选择外部引脚输入或PRS输入; 3、由上一级的TIMER事件作为时钟源。
SILICON LABS EFM32 Tiny Gecko 32-bit Microcontroller选型表
SILICON LABS 32位MCU选型,基于32MHz Frequency,4kB~32kB Flash,2kB或4kB RAM等参数进行选型。
产品型号
|
品类
|
Frequency(MHz)
|
Flash (kB)
|
RAM (kB)
|
Dig I/O Pins
|
ADC 1
|
DAC
|
Cap Sense
|
Temp Sensor
|
Timers (16-bit)
|
UART
|
USART
|
SPI
|
I2C
|
I2S
|
EMIF
|
RTC
|
Comparators
|
Vdd min(V)
|
Vdd max(V)
|
Package Type
|
Package Size (mm)
|
Internal Osc.
|
Debug Interface
|
EFM32TG108F16-QFN24
|
microcontroller
|
32
|
16
|
4
|
17
|
—
|
12-bit
|
Cap Sense
|
Temp Sensor
|
2
|
2
|
1
|
1
|
1
|
1
|
0
|
RTC
|
2
|
1.98
|
3.8
|
QFN24
|
5x5
|
±2%
|
SW
|
世强是否代理st系列MCU?
世强代理有Silicon Labs EFM8/EFM32系列8位MCU/32位MCU,Renesas 汽车级MCU RL78 系列,RH850、V850系列,工业级MCU RX系列等。 没有ST的
SILICON LABS EFM32 Happy Gecko 32-bit Microcontroller选型表
EFM32 Happy Gecko USB-enabled 32-bit Microcontroller
产品型号
|
品类
|
Frequency(MHz)
|
Flash (kB)
|
RAM (kB)
|
Dig I/O Pins
|
ADC 1
|
Cap Sense
|
Temp Sensor
|
Timers (16-bit)
|
UART
|
USART
|
SPI
|
I2C
|
I2S
|
EMIF
|
RTC
|
Comparators
|
Vdd min(V)
|
Vdd max(V)
|
Package Type
|
Package Size (mm)
|
Internal Osc.
|
Debug Interface
|
EFM32HG108F32G-QFN24
|
Microcontroller
|
25
|
32
|
4
|
17
|
—
|
Cap Sense
|
Temp Sensor
|
3
|
3
|
2
|
2
|
1
|
1
|
0
|
RTC
|
1
|
1.98
|
3.8
|
QFN24
|
5x5
|
±2%
|
MTB; SW
|
电子商城
现货市场
服务

可定制显示屏的尺寸0.96”~15.6”,分辨率80*160~3840*2160,TN/IPS视角,支持RGB、MCU、SPI、MIPI、LVDS、HDMI接口,配套定制玻璃、背光、FPCA/PCBA。
最小起订量: 1000 提交需求>

拥有IC烧录机20余款,100余台设备,可以烧录各种封装的IC;可烧录MCU、FLASH、EMMC、NAND FLASH、EPROM等各类型芯片,支持WIFI/BT模组PCBA烧录、测试。
最小起订量: 1 提交需求>
登录 | 立即注册
提交评论