CH58x晶片Hardfault問題排查

SweetTea_lllpc發表於2024-04-26

前言:

針對RISC-V晶片進入HardFault_Handler函式的問題排查提供講解。

一、通用工程PC指標監控

在公共檔案的sys.c工程中找到HardFault_Handler函式並修改如下:

__INTERRUPT
__HIGH_CODE
__attribute__((weak))
void HardFault_Handler(void)
{
    uint32_t v_mepc,v_mcause,v_mtval;
    printf("hardfault\n");

    v_mepc=__get_MEPC();
    v_mcause=__get_MCAUSE();
    v_mtval=__get_MTVAL();

    printf("mepc:%08x\n",v_mepc);
    printf("mcause:%08x\n",v_mcause);
    printf("mtval:%08x\n",v_mtval);

#if 0
    FLASH_ROM_SW_RESET();
    sys_safe_access_enable();
    R16_INT32K_TUNE = 0xFFFF;
	sys_safe_access_disable();
    sys_safe_access_enable();
    R8_RST_WDOG_CTRL |= RB_SOFTWARE_RESET;
    sys_safe_access_disable();
#endif
    while(1);
}

啟用定時器功能也可以進行PC指標監控,以下函式新增在初始化中即可。並且可以透過定時器中斷判斷晶片是否還在工作狀態。

TMR1_TimerInit(FREQ_SYS);         // 設定定時時間 1000ms
TMR1_ITCfg(ENABLE, TMR0_3_IT_CYC_END); // 開啟中斷
PFIC_EnableIRQ(TMR1_IRQn);

__INTERRUPT
__HIGH_CODE
void TMR1_IRQHandler()
{
    static int seconds = 0;
    if(TMR1_GetITFlag(TMR0_3_IT_CYC_END))
    {
        PRINT("20 = %08x\n",*((uint32_t *)0xE000E020));
        PRINT("24 = %08x\n",*((uint32_t *)0xE000E024));
        PRINT("30 = %08x\n",*((uint32_t *)0xE000E300));
        PRINT("34 = %08x\n",*((uint32_t *)0xE000E304));

        // 清除中斷標誌
        TMR1_ClearITFlag(TMR0_3_IT_CYC_END);
        PRINT("PC_%08x\n",__get_MEPC());
        PRINT("SE_%08x\n",__get_MCAUSE());
        PRINT("VL_%08x\n",__get_MTVAL());

    }
}

二、藍芽工程監控

__INTERRUPT
__HIGH_CODE
__attribute__((weak))
void HardFault_Handler(void)
{
    struct __MEMORY_CTL
    {
      struct __MEMORY_CTL *  pNext;
      uint16_t len;
      uint16_t used;
    };
    typedef struct __MEMORY_CTL    MemoryCtl;

    extern  MemoryCtl * MemCtlStart;
    extern  MemoryCtl * MemCtlEnd;
    MemoryCtl * MemHead;
    MemHead = MemCtlStart;
    while( MemHead != MemCtlEnd  ){
      printf("|%8x,%8x,%8d.....\n",MemHead->used,(uint32_t)MemHead,\
              (uint32_t)(MemHead->pNext) -(uint32_t)MemHead - sizeof(struct __MEMORY_CTL));
      MemHead = MemHead->pNext;
    }printf("\n");

    uint32_t v_mepc,v_mcause,v_mtval;
    printf("hardfault\n");

    v_mepc=__get_MEPC();
    v_mcause=__get_MCAUSE();
    v_mtval=__get_MTVAL();

    printf("mepc:%08x\n",v_mepc);
    printf("mcause:%08x\n",v_mcause);
    printf("mtval:%08x\n",v_mtval);

#if 0
    FLASH_ROM_SW_RESET();
    sys_safe_access_enable();
    R16_INT32K_TUNE = 0xFFFF;
	sys_safe_access_disable();
    sys_safe_access_enable();
    R8_RST_WDOG_CTRL |= RB_SOFTWARE_RESET;
    sys_safe_access_disable();
#endif
    while(1);
}

注意:

監控函式和PC指標可以同時使用。監控函式需要在藍芽工程中使用才有意義,如果列印值為空,檢查是否使用藍芽。

附錄:

PC指標列印資訊排查可以參考青稞V4手冊:QingKeV4_Processor_Manual.PDF - 南京沁恆微電子股份有限公司 (wch.cn)

CH58x晶片Hardfault問題排查

相關文章