add fancy hardfault handler, increase heater stack size

master
Ondřej Hruška 2 years ago
parent f23f726b2d
commit 60d15b8c07
  1. 1
      Core/Src/Gui/app_gui.c
  2. 2
      Core/Src/app_temp.c
  3. 2
      Core/Src/freertos.c
  4. 174
      Core/Src/stm32f1xx_it.c
  5. 22
      Lib/snprintf/snprintf.c

@ -121,6 +121,7 @@ void app_task_gui(void *argument) {
/** Switch to a different screen handler.
* If "init" is true, immediately call it with the init event. */
void switch_screen(screen_t pScreen, bool init) {
PRINTF("Screen = %p, init=%d\r\n", pScreen, init);
s_app.initial_pushed = s_app.pushed;
s_app.screen = pScreen;
// clear the union field

@ -313,7 +313,7 @@ void app_temp_sample()
float y = s_analog.cal_a * sum + s_analog.cal_b;
float actual_temp = val_to_c(y);
PRINTF("T raw %f %f -> comp %f, temp %f°C\r\n", sum, y, actual_temp);
PRINTF("T raw %f -> comp %f, temp %f°C\r\n", sum, y, actual_temp);
s_analog.oven_temp = actual_temp;
s_analog.oven_temp_raw = sum;

@ -66,7 +66,7 @@ const osThreadAttr_t mainTsk_attributes = {
};
/* Definitions for heaterTsk */
osThreadId_t heaterTskHandle;
uint32_t heaterTskBuffer[ 128 ];
uint32_t heaterTskBuffer[ 256 ];
osStaticThreadDef_t heaterTskControlBlock;
const osThreadAttr_t heaterTsk_attributes = {
.name = "heaterTsk",

@ -26,6 +26,8 @@
/* USER CODE BEGIN Includes */
#include "app_temp.h"
#include "app_knob.h"
#include "app_heater.h"
#include <inttypes.h>
/* USER CODE END Includes */
/* Private typedef -----------------------------------------------------------*/
@ -89,20 +91,174 @@ void NMI_Handler(void)
/* USER CODE END NonMaskableInt_IRQn 1 */
}
#define VERBOSE_HARDFAULT 1
#if VERBOSE_HARDFAULT
void __attribute__((used)) HardFault_DumpRegisters(const uint32_t *origStack, uint32_t lr_value)
{
/* These are volatile to try and prevent the compiler/linker optimising them
away as the variables never actually get used. If the debugger won't show the
values of the variables, make them global my moving their declaration outside
of this function. */
volatile uint32_t stacked_r0;
volatile uint32_t stacked_r1;
volatile uint32_t stacked_r2;
volatile uint32_t stacked_r3;
volatile uint32_t stacked_r12;
volatile uint32_t stacked_lr; /* Link register. */
volatile uint32_t stacked_pc; /* Program counter. */
volatile uint32_t stacked_psr;/* Program status register. */
#if (__CORTEX_M >= 3)
uint32_t cfsr, hfsr, dfsr;
uint32_t bus_fault_address;
uint32_t memmanage_fault_address;
bus_fault_address = SCB->BFAR;
memmanage_fault_address = SCB->MMFAR;
cfsr = SCB->CFSR;
hfsr = SCB->HFSR;
dfsr = SCB->DFSR;
#endif
stacked_r0 = origStack[0];
stacked_r1 = origStack[1];
stacked_r2 = origStack[2];
stacked_r3 = origStack[3];
stacked_r12 = origStack[4];
stacked_lr = origStack[5];
stacked_pc = origStack[6];
stacked_psr = origStack[7];
app_heater_emergency_shutdown();
#define BS(reg, pos, str) (((reg)&(1<<(pos)))?(str" "):"")
#define REDPTR(val) (((val)&0xFF000000) != 0x08000000?"\033[31m":"\033[32m")
PRINTF("\r\n*** HARD FAULT ***\r\n\r\n");
PRINTF("- Stack frame:\r\n");
PRINTF(" R0 = \033[35m0x%"PRIX32"\033[m\r\n", stacked_r0);
PRINTF(" R1 = \033[35m0x%"PRIX32"\033[m\r\n", stacked_r1);
PRINTF(" R2 = \033[35m0x%"PRIX32"\033[m\r\n", stacked_r2);
PRINTF(" R3 = \033[35m0x%"PRIX32"\033[m\r\n", stacked_r3);
PRINTF(" R12 = \033[35m0x%"PRIX32"\033[m\r\n", stacked_r12);
PRINTF(" LR = %s0x%08"PRIX32"\033[m\r\n", REDPTR(stacked_lr), stacked_lr);
PRINTF(" PC = %s0x%08"PRIX32"\033[m\r\n", REDPTR(stacked_pc), stacked_pc);
PRINTF(" PSR = \033[36m0x%08"PRIX32"\033[m", stacked_psr);
uint32_t exc = stacked_psr & 0x3F;
PRINTF(" [ %s%s%s%s%s ]\r\n",
BS(stacked_psr, 31, "N"),
BS(stacked_psr, 30, "Z"),
BS(stacked_psr, 29, "C"),
BS(stacked_psr, 28, "V"),
//BS(stacked_psr, 24, "T"), - thumb, always ON
(exc==0)?"Thread":
(exc==2)?"NMI":
(exc==3)?"HardFault":
(exc==11)?"SVCall":
(exc==14)?"PendSV":
(exc==15)?"SysTick":
(exc>=16)?"IRQ":"Unknown"
);
#if (__CORTEX_M >= 3)
PRINTF("\r\n- FSR/FAR:\r\n");
PRINTF(" CFSR = \033[36m0x%08"PRIX32"\033[m\r\n", cfsr);
PRINTF(" UsageFault: \033[31;1m%s%s%s%s%s%s%s\033[m\r\n"
" BusFault: \033[31;1m%s%s%s%s%s%s%s%s\033[m\r\n"
" MemFault: \033[31;1m%s%s%s%s%s%s%s\033[m\r\n",
BS(cfsr, 0, "IAccViol"),
BS(cfsr, 1, "DAccViol"),
BS(cfsr, 3, "MUnstkErr"),
BS(cfsr, 4, "MStkErr"),
BS(cfsr, 5, "MLSPErr(FPU)"),
BS(cfsr, 7, "MMArValid"),
((cfsr&0xFF)?"":"\033[m- "),
BS(cfsr, 8, "IBusErr"),
BS(cfsr, 9, "PreciseErr"),
BS(cfsr, 10, "ImpreciseErr"),
BS(cfsr, 11, "UnstkErr"),
BS(cfsr, 12, "StkErr"),
BS(cfsr, 13, "LSPErr"),
BS(cfsr, 15, "BFArValid"),
((cfsr&0xFF00)?"":"\033[m- "),
BS(cfsr, 16, "UndefInstr"),
BS(cfsr, 17, "InvState"),
BS(cfsr, 18, "InvPC"),
BS(cfsr, 19, "NoCP"),
BS(cfsr, 24, "Unaligned"),
BS(cfsr, 25, "Div0"),
((cfsr&0xFFFF0000)?"":"\033[m- ")
);
PRINTF(" HFSR = \033[36m0x%08"PRIX32"\033[m", hfsr);
PRINTF(" [ %s%s%s]\r\n",
BS(hfsr, 31, "DebugEvt"),
BS(hfsr, 30, "Forced"),
BS(hfsr, 1, "VectTbl")
);
PRINTF(" DFSR = \033[36m0x%08"PRIX32"\033[m", dfsr);
PRINTF(" [ %s%s%s%s%s]\r\n",
BS(dfsr, 0, "Halted"),
BS(dfsr, 1, "Bkpt"),
BS(dfsr, 2, "DWtTrap"),
BS(dfsr, 3, "VCatch"),
BS(dfsr, 4, "External")
);
if (cfsr & 0x0080) PRINTF(" MMFAR = \033[33m0x%08"PRIX32"\033[m\r\n", memmanage_fault_address);
if (cfsr & 0x8000) PRINTF(" BFAR = \033[33m0x%08"PRIX32"\033[m\r\n", bus_fault_address);
PRINTF("\r\n- Misc\r\n");
PRINTF(" LR/EXC_RETURN= %s0x%08"PRIX32"\033[m\n", REDPTR(lr_value), lr_value);
#endif
while (1);
}
#endif
/**
* @brief This function handles Hard fault interrupt.
*/
void HardFault_Handler(void)
void __attribute__((naked)) HardFault_Handler(void)
{
/* USER CODE BEGIN HardFault_IRQn 0 */
PUTS("HardFault_Handler\r\n");
#if VERBOSE_HARDFAULT
// __asm volatile
// (
// " tst lr, #4 \n"
// " ite eq \n"
// " mrseq r0, msp \n"
// " mrsne r0, psp \n"
// " ldr r1, [r0, #24] \n"
// " mov r2, lr \n"
// " ldr r3, handler2_address_const \n"
// " bx r3 \n"
// " handler2_address_const: .word HardFault_DumpRegisters \n"
// );
//
__asm volatile( ".syntax unified\n"
"MOVS R0, #4 \n"
"MOV R1, LR \n"
"TST R0, R1 \n"
"BEQ _MSP \n"
"MRS R0, PSP \n"
"B HardFault_DumpRegisters \n"
"_MSP: \n"
"MRS R0, MSP \n"
"B HardFault_DumpRegisters \n"
".syntax divided\n") ;
#else
app_emergency_stop();
/* USER CODE END HardFault_IRQn 0 */
while (1) {
/* USER CODE BEGIN W1_HardFault_IRQn 0 */
/* USER CODE END W1_HardFault_IRQn 0 */
}
PRINTF("*** HARD FAULT ***\r\n\r\n");
while (1);
#endif
}
/**

@ -29,6 +29,10 @@
#define my_malloc(len) pvPortMalloc((len))
#define my_free(p) vPortFree((p))
// Use a static buffer to avoid allocating for every printf!
#define S_PRINTF_BUF_LEN 200
static char s_printf_buf[S_PRINTF_BUF_LEN];
// Toggle features
#define size_t size_t /* normally: int, unsigned */
#undef HAVE_LONG_DOUBLE
@ -733,10 +737,12 @@ static void fmtfp(char *buffer, size_t *currlen, size_t maxlen,
// leading zeros in the fractional part
fzeropad = 0;
fzerocnt = max - 1;
if (fzerocnt > 0) {
while (fracpart < POW10(fzerocnt)) {
fzeropad++;
fzerocnt--;
}
}
do {
temp = fracpart;
my_modf(fracpart * 0.1, &fracpart);
@ -800,8 +806,9 @@ static void fmtfp(char *buffer, size_t *currlen, size_t maxlen,
zpadlen = 0;
}
while (fzeropad-- > 0) {
while (fzeropad > 0) {
dopr_outch(buffer, currlen, maxlen, '0');
fzeropad--;
}
while (fplace > 0) {
@ -892,6 +899,18 @@ int printf(const char *format, ...)
va_list ap;
int ret;
va_start(ap, format);
ret = vsnprintf(s_printf_buf, S_PRINTF_BUF_LEN, format, ap);
va_end(ap);
PUTS(s_printf_buf);
return ret;
#if 0
va_list ap;
int ret;
char *ptr = NULL;
va_start(ap, format);
@ -906,6 +925,7 @@ int printf(const char *format, ...)
my_free(ptr);
return ret;
#endif
}
int vprintf(const char *format, va_list ap)

Loading…
Cancel
Save