FreeRTOS 低功耗之 tickless 模式
tickless 低功耗模式介紹
??tickless 低功耗機制是當前小型 RTOS 所采用的通用低功耗方法,比如 embOS,RTX 和 uCOS-III (類似方法)都有這種機制。FreeRTOS 的低功耗也是采用的這種方式。
??那么 tickless 又是怎樣一種模式呢?僅從字母上看 tick 是滴答時鐘的意思,less 是 tick 的后綴,表示較少的,這里的含義可以表示為無滴答時鐘。整體看這個字母就是表示滴答時鐘節拍停止運行的情況。
??反映在 FreeRTOS 上,tickless 又是怎樣一種情況呢?我們都知道,當用戶任務都被掛起或者阻塞時,最低優先級的空閑任務會得到執行。 那么 STM32 支持的睡眠模式,停機模式就可以放在空閑任務里面實現。但是,為了實現低功耗最優設計,我們還不能直接把睡眠或者停機模式直接放在空閑任務里。
??進入空閑任務后,首先要計算可以執行低功耗的最大時間,也就是求出下一個要執行的高優先級任務還剩多少時間。 然后就是把低功耗的喚醒時間設置為這個求出的時間,到時間后系統會從低功耗模式被喚醒,繼續執行多任務。這個就是所謂的 tickless 模式。
??從上面的講解中可以看出,實現 tickless 模式最麻煩是低功耗可以執行的時間如何獲取。 關于這個問題,FreeRTOS 已經為我們做好了。
FreeRTOS 的低功耗模式介紹
??對于 Cortex-M3 和 M4 內核來說,FreeRTOS 已經提供了 tickless 低功耗代碼的實現,通過調用指令WFI實現睡眠模式,具體代碼的實現就在 port.c文件中,用戶只需在 FreeRTOSConfig.h 文件中配置 宏定義 configUSE_TICKLESS_IDLE 為 1 即可。
注意:如果配置此參數為 2,那么用戶可以自定義 tickless 低功耗模式的實現。
??當用戶將宏定義 configUSE_TICKLESS_IDLE 配置為 1 且系統運行滿足以下兩個條件時,系統內核會自動的調用低功耗宏定義函數 portSUPPRESS_TICKS_AND_SLEEP():
- 當前空閑任務正在運行,所有其它的任務處在掛起狀態或者阻塞狀態。
- 根據用戶配置configEXPECTED_IDLE_TIME_BEFORE_SLEEP的大小,只有當系統可運行于低功耗模式的時鐘節拍數大于等于這個參數時,系統才可以進入到低功耗模式。 此參數默認已經在 FreeRTOS.h文件進行定義了,下面是具體的定義內容(當然,用戶也可以在 FreeRTOSConfig.h 文件中重新定義):
默認定義的大小是 2 個系統時鐘節拍,且用戶自定義的話,不可以小于 2 個系統時鐘節拍。
函數 portSUPPRESS_TICKS_AND_SLEEP(); 是 FreeRTOS 實現 tickless模式的關鍵,此函數被空閑任務調用,其定義是在 portmacro.h 文件中:
FreeRTOS 在線電子手冊低功耗的說明 http://www.freertos.org/low-power-tickless-rtos.html
FreeRTOS 的低功耗模式配置
??關于 FreeRTOS 低功耗方面的配置主要涉及到以下幾個問題。
滴答定時器頻率與系統主頻的關系
??對于Cortex-M3 和 M4 內核的微控制器來說,實時操作系統一般都是采用滴答定時器做系統時鐘,FreeRTOS 也不例外。 SysTick 滴答定時器是一個 24bit 的遞減計數器,有兩種時鐘源可選擇,一個是系統主頻,另一個是系統主頻的八分頻,默認的 port.c 移植文件中是用的系統主頻。 這里我們就根據這兩種時鐘源來說一說配置上的不同。- SysTick 滴答定時器時鐘源選擇系統主頻
如果滴答定時器選擇系統主頻的話,那么需要配置 configSYSTICK_CLOCK_HZ 等于configCPU_CLOCK_HZ,這種關系已經在 port.c 文件中進行默認配置了:
其中系統主頻 configCPU_CLOCK_HZ 是在 FreeRTOSConfig.h文件中進行定義的。 - SysTick 滴答定時器時鐘源選擇系統主頻的八分頻
這種情況的話,需要用戶在 FreeRTOSConfig.h 文件中專門配置 configSYSTICK_CLOCK_HZ為實際需要的頻率,即系統主頻的八分頻大小。
系統時鐘節拍不使用滴答定時器。這種情況我們這里不做討論,用戶看 FreeRTOS 官網此處的說明即可:http://www.freertos.org/low-power-ARM-cortex-rtos.html
- SysTick 滴答定時器時鐘源選擇系統主頻
如何使用微控制器其它低功耗模式
??前面我們說了,對 Cortex-M3 和 M4 內核來說,FreeRTOS 自帶的低功耗模式是通過指令WFI 讓系統進入睡眠模式,如果想讓系統進入停機模式,又該怎么修改呢?FreeRTOS 為我們提供了兩個函數:
configPRE_SLEEP_PROCESSING( xExpectedIdleTime ); configPOST_SLEEP_PROCESSING( xExpectedIdleTime );這兩個函數的定義是在FreeRTOS.h 文件中定義的,什么都沒有執行:
如果需要實際執行代碼,需要用戶在 FreeRTOSConfig.h 文件中重新進行宏定義,將其映射到一個實際的函數中。 另外,這兩個函數是在 port.c 文件中被函數 vPortSuppressTicksAndSleep 調用,具體位置如下:
這兩個函數位于指令 wfi 的前面和后面,用戶想實現其它低功耗方式的關鍵就在這兩個函數里面:
- configPRE_SLEEP_PROCESSING( xExpectedIdleTime )
執行低功耗模式前,用戶可以在這個函數里面關閉外設時鐘來進一步降低系統功耗。 設置其它低功耗方式也是在這個函數里面,用戶只需設置參數 xExpectedIdleTime=0 即可屏蔽掉默認的 wfi 指令執行方式,因為退出這個函數后會通過 if 語句檢測此參數是否大于 0,即上面的代碼所示。 因此,如果用 戶 想 實 現 其 它 低 功 耗 模 式 還 是 比 較 方 便 的 , 配 置 好 其 它 低 功 耗 模 式 后 , 設 置 參 數xExpectedIdleTime = 0 即可,但切不可將此參數隨意設置為 0 以外的其它數值。 - configPOST_SLEEP_PROCESSING ( xExpectedIdleTime )
退出低功耗模式后,此函數會得到調用,之前在 configPRE_SLEEP_PROCESSING里面關閉的外設時鐘,可以在此函數里面重新打開,讓系統恢復到正常運行狀態。
FreeRTOS 實現 tickless 模式的框架
??對 Cortex-M3 和 M4 內核的微控制器來說,FreeRTOS 已經提供了 tickless 低功耗模式的代碼,對于沒有支持的微控制器,用戶可以在 FreeRTOSConfig.h 文件中配置 portSUPPRESS_TICKS_AND_SLEEP宏定義,來映射實際執行函數。如果用戶不想使用 FreeRTOS 提供的的 tickless 也可以自定義,方法也是在 FreeRTOSConfig.h 文件中配置 portSUPPRESS_TICKS_AND_SLEEP 宏定義,來映射實際執行函數。下面是 FreeRTOS 實現低功耗 tickless 模式的代碼框架,方便用戶對 tickles 模式有一個認識,同時也方便 FreeRTOS 沒有支持的微控制器,用戶可以參考實現。 當然,不局限于這種方法,用戶有更好的方法,也可以的。 其中函數 vTaskStepTick 和eTaskConfirmSleepModeStatus 是 FreeRTOS 提供的,其余的函數是需要用戶實現的。
顯然用戶自己配置要麻煩得多,好在FreeRTOS為M3,M4內核的做好了低功耗之睡眠模式,使得我們使用STM32 F1,F4系列的時候可以很簡單,只需要在配置文件FreeRTOSConfig.h中加上一個宏定義:#define configUSE_TICKLESS_IDLE 1
鳴謝
文章原地址:http://www.cnblogs.com/yangguang-it/p/7232448.html,感謝原作者。
在此基礎上,添加修改了一些東西!
總結
以上是生活随笔為你收集整理的FreeRTOS 低功耗之 tickless 模式的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Qt 之 Qt/Qt Lite 自编译详
- 下一篇: STM32 之五 Core Couple