RT_thread 獨立看門狗 watchdog 不斷自動復位的解決方法

  記錄一下,這個問題把我坑慘了,搞了3天都沒有解決,甚至都有點懷疑人生了。本着學習的態度跑一遍官網給的各種案例,再慢慢學習用到項目上,結果上來就悶頭一棒。

   可能是這點坑了自己,我並沒有直接從官網上去下載最新源碼。我用了之前RT_thread來重慶培訓的時候拷貝給我的源碼。我一看 這不有個 v4.0.1 版本的嗎,一想現在不也就最高 v4.0.2。從這裏開始我就入坑了,之前利用的那些串口、IIC、SPI都沒出現過問題,就唯獨看門狗啓動不了,還不斷自動復位。注意這裏我選用了rt-thread-v4.01裏面的文件。

    

  使用平臺:  STM32F103ZET6核心板

   編譯器   :  MDK5    

  直接複製RT_thread的官網文檔資料上的源碼。如下所示

/*
 * 程序清單:這是一個獨立看門狗設備使用例程
 * 例程導出了 wdt_sample 命令到控制終端
 * 命令調用格式:wdt_sample wdt
 * 命令解釋:命令第二個參數是要使用的看門狗設備名稱,爲空則使用例程默認的看門狗設備。
 * 程序功能:程序通過設備名稱查找看門狗設備,然後初始化設備並設置看門狗設備溢出時間。
 *           然後設置空閒線程回調函數,在回調函數裏會餵狗。
*/

#include <rtthread.h>
#include <rtdevice.h>

#define WDT_DEVICE_NAME    "wdt"    /* 看門狗設備名稱 */

static rt_device_t wdg_dev;         /* 看門狗設備句柄 */

static void idle_hook(void)
{
    /* 在空閒線程的回調函數裏餵狗 */
    rt_device_control(wdg_dev, RT_DEVICE_CTRL_WDT_KEEPALIVE, NULL);
    rt_kprintf("feed the dog!\n ");
}

static int wdt_sample(int argc, char *argv[])
{
    rt_err_t ret = RT_EOK;
    rt_uint32_t timeout = 1;        /* 溢出時間,單位:秒 */
    char device_name[RT_NAME_MAX];

    /* 判斷命令行參數是否給定了設備名稱 */
    if (argc == 2)
    {
        rt_strncpy(device_name, argv[1], RT_NAME_MAX);
    }
    else
    {
        rt_strncpy(device_name, WDT_DEVICE_NAME, RT_NAME_MAX);
    }
    /* 根據設備名稱查找看門狗設備,獲取設備句柄 */
    wdg_dev = rt_device_find(device_name);
    if (!wdg_dev)
    {
        rt_kprintf("find %s failed!\n", device_name);
        return RT_ERROR;
    }
    /* 初始化設備 */
    ret = rt_device_init(wdg_dev);
    if (ret != RT_EOK)
    {
        rt_kprintf("initialize %s failed!\n", device_name);
        return RT_ERROR;
    }
    /* 設置看門狗溢出時間 */
    ret = rt_device_control(wdg_dev, RT_DEVICE_CTRL_WDT_SET_TIMEOUT, &timeout);
    if (ret != RT_EOK)
    {
        rt_kprintf("set %s timeout failed!\n", device_name);
        return RT_ERROR;
    }
    /* 啓動看門狗 */
    ret = rt_device_control(wdg_dev, RT_DEVICE_CTRL_WDT_START, RT_NULL);
    if (ret != RT_EOK)
    {
        rt_kprintf("start %s failed!\n", device_name);
        return -RT_ERROR;
    }
    /* 設置空閒線程回調函數 */
    rt_thread_idle_sethook(idle_hook);

    return ret;
}
/* 導出到 msh 命令列表中 */
MSH_CMD_EXPORT(wdt_sample, wdt sample);

源碼上導出到msh命令行列表中,通過命令行啓動這個例子。

  • 通過CubeMX開啓IWDG

  • 在env圖形配置工具中開啓watcdog

  • 直接測試代碼

   開始的時候,看門狗復位時間設置爲1s,看不到錯誤輸出信息就復位了。加長看門狗復位時間,會看到裏面是看門狗啓動失敗。

  • 繼續DUG調試
    /* 啓動看門狗 */
    ret = rt_device_control(wdg_dev, RT_DEVICE_CTRL_WDT_START, RT_NULL);

 發現輸入命令參數的宏定義是 5 啓動看門狗

#define RT_DEVICE_CTRL_WDT_START          (5) /* start watchdog */

 但是繼續單步調試下去,發現在內部一個switch case 語句中 並沒有5這個選項導致錯誤。

然後我就。。。。

 

  • 解決方法,下載最新的RT_thread ,比如我使用第一個圖中的 rtthread-rt-thread-master 文件夾的內容 ,完美運行。

引用論壇一位網友的原話:

"你的HAL Driver的版本太老了,上github下載最新的RTThread就好了 https://github.com/RT-Thread/rt-threa ."

我也進去看了 兩個文件中的 drv_wdt.c 確實有一些不同,不過我困惑的是既然是 v4.0.1 ,爲什麼還會這樣,具體等論壇中網友回覆吧。留下一個論壇網址 https://www.rt-thread.org/qa/thread-423347-1-1.html

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章