ESP8266 系列芯片提供三種可配置的睡眠模式,針對這些睡眠模式,我們提供了多種低功耗解決方案,用戶可以結合具體需求選擇睡眠模式並進行配置。三種睡眠模式如下:
ESP8266低功耗解決方案之深度睡眠Deep-sleep:
相對於其他兩種模式,系統無法自動進入 Deep-sleep,需要由用戶調用接口函數system_deep_sleep 來控制。在該模式下,芯⽚片會斷開所有 Wi-Fi 連接與數據連接,進入睡眠模式,只有 RTC 模塊仍然⼯工作,負責芯片的定時喚醒。在 Deep-sleep 狀態下,GPIO 電平狀態可以保持,具有 2 μA 的驅動能⼒。
應用場合:
Deep-sleep 可以用於低功耗的傳感器應用,或者大部分時間都不需要進行數據傳輸的情況。設備可以每隔一段時間從 Deep-sleep 狀態醒來測量量數據並上傳,之後繼續進入Deep-sleep。也可以將多個數據存儲於 RTC memory(RTC memory 在 Deep-sleep 模式下仍然可以保存數據),然後一次發送出去。
自動喚醒和外部喚醒:
自動喚醒:在 Deep-sleep 狀態下,可以將 GPIO16 (XPD_DCDC) 連接至 EXT_RSTB。計時到達睡眠時間後,GPIO16 輸出低電平給 EXT_RSTB 管腳,芯片即可被重置並被喚醒。
外部喚醒:在 Deep-sleep 狀態下,可以通過外部 IO 在芯片 EXT_RSTB 管腳上產生⼀一個低電平脈衝,芯片即可被重置並被喚醒。
使能深度睡眠接口:
/**
* @brief Set the chip to deep-sleep mode.
*
* The device will automatically wake up after the deep-sleep time set
* by the users. Upon waking up, the device boots up from user_init.
*
* @attention 1. XPD_DCDC should be connected to EXT_RSTB through 0 ohm resistor
* in order to support deep-sleep wakeup.
* @attention 2. system_deep_sleep(0): there is no wake up timer; in order to wake
* up, connect a GPIO to pin RST, the chip will wake up by a falling-edge
* on pin RST
*
* @param time_in_us deep-sleep time, unit: microsecond
*
* @return null
*/
void esp_deep_sleep(uint32_t time_in_us);
配置深度睡眠接口:
/**
* @brief Call this API before esp_deep_sleep and esp_wifi_init to set the activity after the
* next deep-sleep wakeup.
*
* If this API is not called, default to be esp_deep_sleep_set_rf_option(1).
*
* @param option radio option
* 0 : Radio calibration after the deep-sleep wakeup is decided by byte
* 108 of esp_init_data_default.bin (0~127byte).
* 1 : Radio calibration will be done after the deep-sleep wakeup. This
* will lead to stronger current.
* 2 : Radio calibration will not be done after the deep-sleep wakeup.
* This will lead to weaker current.
* 4 : Disable radio calibration after the deep-sleep wakeup (the same
* as modem-sleep). This will lead to the weakest current, but the device
* can't receive or transmit data after waking up.
*
* @return null
*/
void esp_deep_sleep_set_rf_option(uint8_t option);
提供了以下幾種種方案來減少 Deep-sleep 模式的功耗:
============================================================================
1. 設置立即進入 Deep-sleep,縮短設備進入 Deep-sleep 的時間:
void system_deep_sleep_instant(uint32 time_in_us)
2.設置 Deep-sleep 喚醒後不進行射頻校準,以縮短芯片初始化的時間和降低芯片初始化時的電流:
void esp_deep_sleep_set_rf_option(uint8_t option)
3.適當降低射頻功耗,舊版:修改esp_init_data_default.bin文件
4.使⽤用以下指令修改 BIN ⽂文件,縮短 flash 初始化的時間並降低 flash 初始化時的電流:
python add_low-power_deepsleep_cmd.py ./bin file
5.選擇 Flash 型號和工作模式,選擇特殊型號的 flash,可明顯縮短從 flash 加載固件的時間,例如 ISSI-IS25LQ025。
適當的工作模式,也可以縮短從 flash 加載固件的時間,建議 flash 工作模式盡量選擇四線工作模式。
6.設置清空 UART FIFO,減少打印時間,FIFO(先入先出隊列列)是 UART 的緩存器器,強制將串行通信的每個字節按照接收的順序進行傳送。FIFO 打印消耗時間較多,盡量避免大量打印。所以在設置休眠前應清空UART FIFO,否則,系統會等待 UART FIFO 打印結束才進入睡眠,將消耗較多時間。
7.集中發包,因爲發包動作持續時間短(與睡眠醒來的時間相比)、消耗能量少,建議集中發送數據,在 Deep-sleep 醒來之後,一次發送多個數據包。
===========================================================================
注意:實際測試中發現,由於 Light-sleep 硬件喚醒時間短(約爲 3 ms),如果應⽤用場景中設備睡眠時間 <2s,宜採⽤用 Light-sleep ⼯工作模式,更更節省功耗;如果睡眠時間 >2s,則宜採⽤用 Deep-sleep ⼯工作模式,更更節省功耗。
實測:芯片級理論值能達到20uA,但是模組級實測值達到100uA左右。
附帶示例源碼:
/******************************************************************************
* @ 10秒後系統進入深度睡眠模式,外部喚醒
* @ EXT_RSTB 管腳拉低,芯片重置並喚醒
*******************************************************************************/
void app_main(void)
{
for (int timer = 0; timer < 10; timer++) {
ESP_LOGI(TAG, "timer: %d\n",timer);
vTaskDelay(1000 / portTICK_RATE_MS);
}
ESP_LOGI(TAG, "start esp_deep_sleep\n");
/* 發現進入深度睡眠後無法再次燒錄固件 */
esp_deep_sleep(0);
}