1 // Copyright 2015-2017 Espressif Systems (Shanghai) PTE LTD
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 //     http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14 #pragma once
15 
16 #include <stdbool.h>
17 #include <stddef.h>
18 #include <stdint.h>
19 #include "soc/soc.h"
20 
21 #ifdef __cplusplus
22 extern "C" {
23 #endif
24 
25 /**
26  * @file rtc.h
27  * @brief Low-level RTC power, clock, and sleep functions.
28  *
29  * Functions in this file facilitate configuration of ESP32's RTC_CNTL peripheral.
30  * RTC_CNTL peripheral handles many functions:
31  * - enables/disables clocks and power to various parts of the chip; this is
32  *   done using direct register access (forcing power up or power down) or by
33  *   allowing state machines to control power and clocks automatically
34  * - handles sleep and wakeup functions
35  * - maintains a 48-bit counter which can be used for timekeeping
36  *
37  * These functions are not thread safe, and should not be viewed as high level
38  * APIs. For example, while this file provides a function which can switch
39  * CPU frequency, this function is on its own is not sufficient to implement
40  * frequency switching in ESP-IDF context: some coordination with RTOS,
41  * peripheral drivers, and WiFi/BT stacks is also required.
42  *
43  * These functions will normally not be used in applications directly.
44  * ESP-IDF provides, or will provide, drivers and other facilities to use
45  * RTC subsystem functionality.
46  *
47  * The functions are loosely split into the following groups:
48  * - rtc_clk: clock switching, calibration
49  * - rtc_time: reading RTC counter, conversion between counter values and time
50  * - rtc_sleep: entry into sleep modes
51  * - rtc_init: initialization
52  */
53 
54 #ifndef __ZEPHYR__
55 #define MHZ (1000000)
56 #endif
57 
58 #define RTC_SLOW_CLK_X32K_CAL_TIMEOUT_THRES(cycles)  (cycles << 12)
59 #define RTC_SLOW_CLK_8MD256_CAL_TIMEOUT_THRES(cycles)  (cycles << 12)
60 #define RTC_SLOW_CLK_90K_CAL_TIMEOUT_THRES(cycles)  (cycles << 10)
61 
62 #define RTC_SLOW_CLK_FREQ_90K      90000
63 #define RTC_SLOW_CLK_FREQ_8MD256    (RTC_FAST_CLK_FREQ_APPROX / 256)
64 #define RTC_SLOW_CLK_FREQ_32K       32768
65 
66 #define OTHER_BLOCKS_POWERUP        1
67 #define OTHER_BLOCKS_WAIT           1
68 
69 /* Approximate mapping of voltages to RTC_CNTL_DBIAS_WAK, RTC_CNTL_DBIAS_SLP,
70  * RTC_CNTL_DIG_DBIAS_WAK, RTC_CNTL_DIG_DBIAS_SLP values.
71  * Valid if RTC_CNTL_DBG_ATTEN is 0.
72  */
73 #define RTC_CNTL_DBIAS_0V90 0
74 #define RTC_CNTL_DBIAS_0V95 1
75 #define RTC_CNTL_DBIAS_1V00 2
76 #define RTC_CNTL_DBIAS_1V05 3
77 #define RTC_CNTL_DBIAS_1V10 4
78 #define RTC_CNTL_DBIAS_1V15 5
79 #define RTC_CNTL_DBIAS_1V20 6
80 #define RTC_CNTL_DBIAS_1V25 7
81 
82 #define DELAY_FAST_CLK_SWITCH           3
83 #define DELAY_SLOW_CLK_SWITCH           300
84 #define DELAY_8M_ENABLE                 50
85 
86 /* Number of 8M/256 clock cycles to use for XTAL frequency estimation.
87  * 10 cycles will take approximately 300 microseconds.
88  */
89 #define XTAL_FREQ_EST_CYCLES            10
90 
91 /* Core voltage needs to be increased in two cases:
92  * 1. running at 240 MHz
93  * 2. running with 80MHz Flash frequency
94  */
95 #ifdef CONFIG_ESPTOOLPY_FLASHFREQ_80M
96 #define DIG_DBIAS_80M_160M  RTC_CNTL_DBIAS_1V25
97 #else
98 #define DIG_DBIAS_80M_160M  RTC_CNTL_DBIAS_1V10
99 #endif
100 #define DIG_DBIAS_240M      RTC_CNTL_DBIAS_1V25
101 #define DIG_DBIAS_XTAL      RTC_CNTL_DBIAS_1V10
102 #define DIG_DBIAS_2M        RTC_CNTL_DBIAS_1V00
103 
104 #define RTC_CNTL_PLL_BUF_WAIT_DEFAULT  20
105 #define RTC_CNTL_XTL_BUF_WAIT_DEFAULT  100
106 #define RTC_CNTL_CK8M_WAIT_DEFAULT  20
107 #define RTC_CK8M_ENABLE_WAIT_DEFAULT 5
108 
109 /* Various delays to be programmed into power control state machines */
110 #define RTC_CNTL_PLL_BUF_WAIT_SLP_CYCLES    (1)
111 #define RTC_CNTL_XTL_BUF_WAIT_SLP_US    (1000)
112 #define RTC_CNTL_CK8M_WAIT_SLP_CYCLES   (4)
113 #define RTC_CNTL_WAKEUP_DELAY_CYCLES    (4)
114 
115 #define RTC_CNTL_CK8M_DFREQ_DEFAULT 172
116 #define RTC_CNTL_SCK_DCAP_DEFAULT   255
117 
118 #define RTC_CNTL_ULPCP_TOUCH_START_WAIT_IN_SLEEP    (0xFF)
119 #define RTC_CNTL_ULPCP_TOUCH_START_WAIT_DEFAULT     (0x10)
120 
121 /*
122 set sleep_init default param
123 */
124 #define RTC_CNTL_DBG_ATTEN_LIGHTSLEEP_DEFAULT  6
125 #define RTC_CNTL_DBG_ATTEN_LIGHTSLEEP_NODROP  0
126 #define RTC_CNTL_DBG_ATTEN_DEEPSLEEP_DEFAULT  15
127 #define RTC_CNTL_DBG_ATTEN_MONITOR_DEFAULT  0
128 #define RTC_CNTL_BIASSLP_MONITOR_DEFAULT  0
129 #define RTC_CNTL_BIASSLP_SLEEP_ON  0
130 #define RTC_CNTL_BIASSLP_SLEEP_DEFAULT  1
131 #define RTC_CNTL_PD_CUR_MONITOR_DEFAULT  1
132 #define RTC_CNTL_PD_CUR_SLEEP_ON  0
133 #define RTC_CNTL_PD_CUR_SLEEP_DEFAULT  1
134 
135 #define APLL_SDM_STOP_VAL_1         0x09
136 #define APLL_SDM_STOP_VAL_2_REV0    0x69
137 #define APLL_SDM_STOP_VAL_2_REV1    0x49
138 #define APLL_CAL_DELAY_1            0x0f
139 #define APLL_CAL_DELAY_2            0x3f
140 #define APLL_CAL_DELAY_3            0x1f
141 
142 /**
143  * @brief Possible main XTAL frequency values.
144  *
145  * Enum values should be equal to frequency in MHz.
146  */
147 typedef enum {
148     RTC_XTAL_FREQ_40M = 40,     //!< 40 MHz XTAL
149 } rtc_xtal_freq_t;
150 
151 /** @brief Fixed crystal frequency for this SoC
152 
153     On an SoC where only one crystal frequency is supported,
154     using this macro is an alternative to calling rtc_clk_xtal_freq_get()
155  */
156 #define RTC_XTAL_FREQ RTC_XTAL_FREQ_40M
157 
158 /**
159  * @brief CPU frequency values
160  */
161 typedef enum {
162     RTC_CPU_FREQ_XTAL = 0,      //!< Main XTAL frequency
163     RTC_CPU_FREQ_80M = 1,       //!< 80 MHz
164     RTC_CPU_FREQ_160M = 2,      //!< 160 MHz
165     RTC_CPU_FREQ_240M = 3,      //!< 240 MHz
166     RTC_CPU_FREQ_2M = 4,        //!< 2 MHz
167     RTC_CPU_320M_80M = 5,       //!< for test
168     RTC_CPU_320M_160M = 6,      //!< for test
169     RTC_CPU_FREQ_XTAL_DIV2 = 7, //!< XTAL/2 after reset
170 } rtc_cpu_freq_t;
171 
172 /**
173  * @brief CPU clock source
174  */
175 typedef enum {
176     RTC_CPU_FREQ_SRC_XTAL,  //!< XTAL
177     RTC_CPU_FREQ_SRC_PLL,   //!< PLL (480M or 320M)
178     RTC_CPU_FREQ_SRC_8M,    //!< Internal 8M RTC oscillator
179     RTC_CPU_FREQ_SRC_APLL   //!< APLL
180 } rtc_cpu_freq_src_t;
181 
182 /**
183  * @brief CPU clock configuration structure
184  */
185 typedef struct rtc_cpu_freq_config_s {
186     rtc_cpu_freq_src_t source;      //!< The clock from which CPU clock is derived
187     uint32_t source_freq_mhz;       //!< Source clock frequency
188     uint32_t div;                   //!< Divider, freq_mhz = source_freq_mhz / div
189     uint32_t freq_mhz;              //!< CPU clock frequency
190 } rtc_cpu_freq_config_t;
191 
192 /**
193  * @brief RTC SLOW_CLK frequency values
194  */
195 typedef enum {
196     RTC_SLOW_FREQ_RTC = 0,      //!< Internal 90 kHz RC oscillator
197     RTC_SLOW_FREQ_32K_XTAL = 1, //!< External 32 kHz XTAL
198     RTC_SLOW_FREQ_8MD256 = 2,   //!< Internal 8 MHz RC oscillator, divided by 256
199 } rtc_slow_freq_t;
200 
201 /**
202  * @brief RTC FAST_CLK frequency values
203  */
204 typedef enum {
205     RTC_FAST_FREQ_XTALD4 = 0,   //!< Main XTAL, divided by 4
206     RTC_FAST_FREQ_8M = 1,       //!< Internal 8 MHz RC oscillator
207 } rtc_fast_freq_t;
208 
209 /* With the default value of CK8M_DFREQ, 8M clock frequency is 8.5 MHz +/- 7% */
210 #define RTC_FAST_CLK_FREQ_APPROX 8500000
211 
212 #define RTC_CLK_CAL_FRACT  19  //!< Number of fractional bits in values returned by rtc_clk_cal
213 
214 #define RTC_VDDSDIO_TIEH_1_8V 0 //!< TIEH field value for 1.8V VDDSDIO
215 #define RTC_VDDSDIO_TIEH_3_3V 1 //!< TIEH field value for 3.3V VDDSDIO
216 
217 /**
218  * @brief Clock source to be calibrated using rtc_clk_cal function
219  */
220 typedef enum {
221     RTC_CAL_RTC_MUX = 0,       //!< Currently selected RTC SLOW_CLK
222     RTC_CAL_8MD256 = 1,        //!< Internal 8 MHz RC oscillator, divided by 256
223     RTC_CAL_32K_XTAL = 2,      //!< External 32 kHz XTAL
224     RTC_CAL_INTERNAL_OSC = 3   //!< Internal 150 kHz oscillator
225 } rtc_cal_sel_t;
226 
227 /**
228  * Initialization parameters for rtc_clk_init
229  */
230 typedef struct {
231     rtc_xtal_freq_t xtal_freq : 8;  //!< Main XTAL frequency
232     uint32_t cpu_freq_mhz : 10;    //!< CPU frequency to set, in MHz
233     rtc_fast_freq_t fast_freq : 1;  //!< RTC_FAST_CLK frequency to set
234     rtc_slow_freq_t slow_freq : 2;  //!< RTC_SLOW_CLK frequency to set
235     uint32_t clk_rtc_clk_div : 8;
236     uint32_t clk_8m_clk_div : 3;        //!< RTC 8M clock divider (division is by clk_8m_div+1, i.e. 0 means 8MHz frequency)
237     uint32_t slow_clk_dcap : 8;     //!< RTC 90k clock adjustment parameter (higher value leads to lower frequency)
238     uint32_t clk_8m_dfreq : 8;      //!< RTC 8m clock adjustment parameter (higher value leads to higher frequency)
239 } rtc_clk_config_t;
240 
241 /**
242  * Default initializer for rtc_clk_config_t
243  */
244 #define RTC_CLK_CONFIG_DEFAULT() { \
245     .xtal_freq = RTC_XTAL_FREQ_40M, \
246     .cpu_freq_mhz = 80, \
247     .fast_freq = RTC_FAST_FREQ_8M, \
248     .slow_freq = RTC_SLOW_FREQ_RTC, \
249     .clk_rtc_clk_div = 0, \
250     .clk_8m_clk_div = 0, \
251     .slow_clk_dcap = RTC_CNTL_SCK_DCAP_DEFAULT, \
252     .clk_8m_dfreq = RTC_CNTL_CK8M_DFREQ_DEFAULT, \
253 }
254 
255 typedef struct {
256     uint32_t dac : 6;
257     uint32_t dres : 3;
258     uint32_t dgm : 3;
259     uint32_t dbuf: 1;
260 } x32k_config_t;
261 
262 #define X32K_CONFIG_DEFAULT() { \
263     .dac = 3, \
264     .dres = 3, \
265     .dgm = 3, \
266     .dbuf = 1, \
267 }
268 
269 #if 0
270 #define X32K_CONFIG_BOOTSTRAP_DEFAULT() { \
271     .dac = 3, \
272     .dres = 3, \
273     .dgm = 0, \
274 }
275 
276 typedef struct {
277     x32k_config_t x32k_cfg;
278     uint32_t bt_lpck_div_num : 12;
279     uint32_t bt_lpck_div_a : 12;
280     uint32_t bt_lpck_div_b : 12;
281 } x32k_bootstrap_config_t;
282 
283 #define X32K_BOOTSTRAP_CONFIG_DEFAULT() { \
284     .x32k_cfg = X32K_CONFIG_BOOTSTRAP_DEFAULT(), \
285     .bt_lpck_div_num = 2441, \
286     .bt_lpck_div_a = 32, \
287     .bt_lpck_div_b = 13, \
288 }
289 #endif
290 
291 typedef struct {
292     uint16_t wifi_powerup_cycles : 7;
293     uint16_t wifi_wait_cycles : 9;
294     uint16_t rtc_powerup_cycles : 7;
295     uint16_t rtc_wait_cycles : 9;
296     uint16_t dg_wrap_powerup_cycles : 7;
297     uint16_t dg_wrap_wait_cycles : 9;
298     uint16_t rtc_mem_powerup_cycles : 7;
299     uint16_t rtc_mem_wait_cycles : 9;
300 } rtc_init_config_t;
301 
302 #define RTC_INIT_CONFIG_DEFAULT() { \
303     .wifi_powerup_cycles = OTHER_BLOCKS_POWERUP, \
304     .wifi_wait_cycles = OTHER_BLOCKS_WAIT, \
305     .rtc_powerup_cycles = OTHER_BLOCKS_POWERUP, \
306     .rtc_wait_cycles = OTHER_BLOCKS_WAIT, \
307     .dg_wrap_powerup_cycles = OTHER_BLOCKS_POWERUP, \
308     .dg_wrap_wait_cycles = OTHER_BLOCKS_WAIT, \
309     .rtc_mem_powerup_cycles = OTHER_BLOCKS_POWERUP, \
310     .rtc_mem_wait_cycles = OTHER_BLOCKS_WAIT, \
311 }
312 
313 /* Two different calibration mode for slow clock */
314 #define RTC_TIME_CAL_ONEOFF_MODE 0
315 #define RTC_TIME_CAL_CYCLING_MODE 1
316 
317 void rtc_clk_divider_set(uint32_t div);
318 
319 void rtc_clk_8m_divider_set(uint32_t div);
320 
321 /**
322  * Initialize clocks and set CPU frequency
323  *
324  * @param cfg clock configuration as rtc_clk_config_t
325  */
326 void rtc_clk_init(rtc_clk_config_t cfg);
327 
328 /**
329  * @brief Get main XTAL frequency
330  *
331  * Result is a constant as XTAL frequency is fixed.
332  *
333  * @note Function is included for ESP32 compatible code only. Code which only
334  * needs to support this SoC can use the macro RTC_XTAL_FREQ for this SoC's
335  * fixed crystal value.
336  *
337  * @return XTAL frequency in MHz, RTC_XTAL_FREQ_40M
338  */
339 rtc_xtal_freq_t rtc_clk_xtal_freq_get(void);
340 
341 /**
342  * @brief Enable or disable 32 kHz XTAL oscillator
343  * @param en  true to enable, false to disable
344  */
345 void rtc_clk_32k_enable(bool en);
346 
347 /**
348  * @brief Configure 32 kHz XTAL oscillator to accept external clock signal
349  */
350 void rtc_clk_32k_enable_external(void);
351 
352 /**
353  * @brief Get the state of 32k XTAL oscillator
354  * @return true if 32k XTAL oscillator has been enabled
355  */
356 bool rtc_clk_32k_enabled(void);
357 
358 /**
359  * @brief Enable 32k oscillator, configuring it for fast startup time.
360  * Note: to achieve higher frequency stability, rtc_clk_32k_enable function
361  * must be called one the 32k XTAL oscillator has started up. This function
362  * will initially disable the 32k XTAL oscillator, so it should not be called
363  * when the system is using 32k XTAL as RTC_SLOW_CLK.
364  *
365  * @param cycle Number of 32kHz cycles to bootstrap external crystal.
366  *              If 0, no square wave will be used to bootstrap crystal oscillation.
367  */
368 void rtc_clk_32k_bootstrap(uint32_t cycle);
369 
370 /**
371  * @brief Enable or disable 8 MHz internal oscillator
372  *
373  * Output from 8 MHz internal oscillator is passed into a configurable
374  * divider, which by default divides the input clock frequency by 256.
375  * Output of the divider may be used as RTC_SLOW_CLK source.
376  * Output of the divider is referred to in register descriptions and code as
377  * 8md256 or simply d256. Divider values other than 256 may be configured, but
378  * this facility is not currently needed, so is not exposed in the code.
379  *
380  * When 8MHz/256 divided output is not needed, the divider should be disabled
381  * to reduce power consumption.
382  *
383  * @param clk_8m_en true to enable 8MHz generator
384  * @param d256_en true to enable /256 divider
385  */
386 void rtc_clk_8m_enable(bool clk_8m_en, bool d256_en);
387 
388 /**
389  * @brief Get the state of 8 MHz internal oscillator
390  * @return true if the oscillator is enabled
391  */
392 bool rtc_clk_8m_enabled(void);
393 
394 /**
395  * @brief Get the state of /256 divider which is applied to 8MHz clock
396  * @return true if the divided output is enabled
397  */
398 bool rtc_clk_8md256_enabled(void);
399 
400 /**
401  * @brief Enable or disable APLL
402  *
403  * Output frequency is given by the formula:
404  * apll_freq = xtal_freq * (4 + sdm2 + sdm1/256 + sdm0/65536)/((o_div + 2) * 2)
405  *
406  * The dividend in this expression should be in the range of 240 - 600 MHz.
407  *
408  * In rev. 0 of ESP32, sdm0 and sdm1 are unused and always set to 0.
409  *
410  * @param enable  true to enable, false to disable
411  * @param sdm0  frequency adjustment parameter, 0..255
412  * @param sdm1  frequency adjustment parameter, 0..255
413  * @param sdm2  frequency adjustment parameter, 0..63
414  * @param o_div  frequency divider, 0..31
415  */
416 void rtc_clk_apll_enable(bool enable, uint32_t sdm0, uint32_t sdm1, uint32_t sdm2, uint32_t o_div);
417 
418 /**
419  * @brief Select source for RTC_SLOW_CLK
420  * @param slow_freq clock source (one of rtc_slow_freq_t values)
421  */
422 void rtc_clk_slow_freq_set(rtc_slow_freq_t slow_freq);
423 
424 /**
425  * @brief Get the RTC_SLOW_CLK source
426  * @return currently selected clock source (one of rtc_slow_freq_t values)
427  */
428 rtc_slow_freq_t rtc_clk_slow_freq_get(void);
429 
430 /**
431  * @brief Get the approximate frequency of RTC_SLOW_CLK, in Hz
432  *
433  * - if RTC_SLOW_FREQ_RTC is selected, returns ~90000
434  * - if RTC_SLOW_FREQ_32K_XTAL is selected, returns 32768
435  * - if RTC_SLOW_FREQ_8MD256 is selected, returns ~33000
436  *
437  * rtc_clk_cal function can be used to get more precise value by comparing
438  * RTC_SLOW_CLK frequency to the frequency of main XTAL.
439  *
440  * @return RTC_SLOW_CLK frequency, in Hz
441  */
442 uint32_t rtc_clk_slow_freq_get_hz(void);
443 
444 /**
445  * @brief Select source for RTC_FAST_CLK
446  * @param fast_freq clock source (one of rtc_fast_freq_t values)
447  */
448 void rtc_clk_fast_freq_set(rtc_fast_freq_t fast_freq);
449 
450 /**
451  * @brief Get the RTC_FAST_CLK source
452  * @return currently selected clock source (one of rtc_fast_freq_t values)
453  */
454 rtc_fast_freq_t rtc_clk_fast_freq_get(void);
455 
456 /**
457  * @brief Get CPU frequency config for a given frequency
458  * @param freq_mhz  Frequency in MHz
459  * @param[out] out_config Output, CPU frequency configuration structure
460  * @return true if frequency can be obtained, false otherwise
461  */
462 bool rtc_clk_cpu_freq_mhz_to_config(uint32_t freq_mhz, rtc_cpu_freq_config_t* out_config);
463 
464 /**
465  * @brief Switch CPU frequency
466  *
467  * This function sets CPU frequency according to the given configuration
468  * structure. It enables PLLs, if necessary.
469  *
470  * @note This function in not intended to be called by applications in FreeRTOS
471  * environment. This is because it does not adjust various timers based on the
472  * new CPU frequency.
473  *
474  * @param config  CPU frequency configuration structure
475  */
476 void rtc_clk_cpu_freq_set_config(const rtc_cpu_freq_config_t* config);
477 
478 /**
479  * @brief Switch CPU frequency (optimized for speed)
480  *
481  * This function is a faster equivalent of rtc_clk_cpu_freq_set_config.
482  * It works faster because it does not disable PLLs when switching from PLL to
483  * XTAL and does not enabled them when switching back. If PLL is not already
484  * enabled when this function is called to switch from XTAL to PLL frequency,
485  * or the PLL which is enabled is the wrong one, this function will fall back
486  * to calling rtc_clk_cpu_freq_set_config.
487  *
488  * Unlike rtc_clk_cpu_freq_set_config, this function relies on static data,
489  * so it is less safe to use it e.g. from a panic handler (when memory might
490  * be corrupted).
491  *
492  * @note This function in not intended to be called by applications in FreeRTOS
493  * environment. This is because it does not adjust various timers based on the
494  * new CPU frequency.
495  *
496  * @param config  CPU frequency configuration structure
497  */
498 void rtc_clk_cpu_freq_set_config_fast(const rtc_cpu_freq_config_t* config);
499 
500 /**
501  * @brief Get the currently used CPU frequency configuration
502  * @param[out] out_config  Output, CPU frequency configuration structure
503  */
504 void rtc_clk_cpu_freq_get_config(rtc_cpu_freq_config_t* out_config);
505 
506 /**
507  * @brief Switch CPU clock source to XTAL
508  *
509  * Short form for filling in rtc_cpu_freq_config_t structure and calling
510  * rtc_clk_cpu_freq_set_config when a switch to XTAL is needed.
511  * Assumes that XTAL frequency has been determined — don't call in startup code.
512  */
513 void rtc_clk_cpu_freq_set_xtal(void);
514 
515 /**
516  * @brief Store new APB frequency value into RTC_APB_FREQ_REG
517  *
518  * This function doesn't change any hardware clocks.
519  *
520  * Functions which perform frequency switching and change APB frequency call
521  * this function to update the value of APB frequency stored in RTC_APB_FREQ_REG
522  * (one of RTC general purpose retention registers). This should not normally
523  * be called from application code.
524  *
525  * @param apb_freq  new APB frequency, in Hz
526  */
527 void rtc_clk_apb_freq_update(uint32_t apb_freq);
528 
529 /**
530  * @brief Get the current stored APB frequency.
531  * @return The APB frequency value as last set via rtc_clk_apb_freq_update(), in Hz.
532  */
533 uint32_t rtc_clk_apb_freq_get(void);
534 
535 uint32_t rtc_clk_cal_internal(rtc_cal_sel_t cal_clk, uint32_t slowclk_cycles, uint32_t cal_mode);
536 
537 /**
538  * @brief Measure RTC slow clock's period, based on main XTAL frequency
539  *
540  * This function will time out and return 0 if the time for the given number
541  * of cycles to be counted exceeds the expected time twice. This may happen if
542  * 32k XTAL is being calibrated, but the oscillator has not started up (due to
543  * incorrect loading capacitance, board design issue, or lack of 32 XTAL on board).
544  *
545  * @param cal_clk  clock to be measured
546  * @param slow_clk_cycles  number of slow clock cycles to average
547  * @return average slow clock period in microseconds, Q13.19 fixed point format,
548  *         or 0 if calibration has timed out
549  */
550 uint32_t rtc_clk_cal(rtc_cal_sel_t cal_clk, uint32_t slow_clk_cycles);
551 
552 /**
553  * @brief Measure ratio between XTAL frequency and RTC slow clock frequency
554  * @param cal_clk slow clock to be measured
555  * @param slow_clk_cycles number of slow clock cycles to average
556  * @return average ratio between XTAL frequency and slow clock frequency,
557  *         Q13.19 fixed point format, or 0 if calibration has timed out.
558  */
559 uint32_t rtc_clk_cal_ratio(rtc_cal_sel_t cal_clk, uint32_t slow_clk_cycles);
560 
561 /**
562  * @brief Convert time interval from microseconds to RTC_SLOW_CLK cycles
563  * @param time_in_us Time interval in microseconds
564  * @param slow_clk_period  Period of slow clock in microseconds, Q13.19
565  *                         fixed point format (as returned by rtc_slowck_cali).
566  * @return number of slow clock cycles
567  */
568 uint64_t rtc_time_us_to_slowclk(uint64_t time_in_us, uint32_t period);
569 
570 /**
571  * @brief Convert time interval from RTC_SLOW_CLK to microseconds
572  * @param time_in_us Time interval in RTC_SLOW_CLK cycles
573  * @param slow_clk_period  Period of slow clock in microseconds, Q13.19
574  *                         fixed point format (as returned by rtc_slowck_cali).
575  * @return time interval in microseconds
576  */
577 uint64_t rtc_time_slowclk_to_us(uint64_t rtc_cycles, uint32_t period);
578 
579 /**
580  * @brief Get current value of RTC counter
581  *
582  * RTC has a 48-bit counter which is incremented by 2 every 2 RTC_SLOW_CLK
583  * cycles. Counter value is not writable by software. The value is not adjusted
584  * when switching to a different RTC_SLOW_CLK source.
585  *
586  * Note: this function may take up to 1 RTC_SLOW_CLK cycle to execute
587  *
588  * @return current value of RTC counter
589  */
590 uint64_t rtc_time_get(void);
591 
592 uint64_t rtc_light_slp_time_get(void);
593 
594 uint64_t rtc_deep_slp_time_get(void);
595 
596 /**
597  * @brief Busy loop until next RTC_SLOW_CLK cycle
598  *
599  * This function returns not earlier than the next RTC_SLOW_CLK clock cycle.
600  * In some cases (e.g. when RTC_SLOW_CLK cycle is very close), it may return
601  * one RTC_SLOW_CLK cycle later.
602  */
603 void rtc_clk_wait_for_slow_cycle(void);
604 
605 /**
606  * @brief Enable the rtc digital 8M clock
607  *
608  * This function is used to enable the digital rtc 8M clock to support peripherals.
609  * For enabling the analog 8M clock, using `rtc_clk_8M_enable` function above.
610  */
611 void rtc_dig_clk8m_enable(void);
612 
613 /**
614  * @brief Disable the rtc digital 8M clock
615  *
616  * This function is used to disable the digital rtc 8M clock, which is only used to support peripherals.
617  */
618 void rtc_dig_clk8m_disable(void);
619 
620 /**
621  * @brief Calculate the real clock value after the clock calibration
622  *
623  * @param cal_val Average slow clock period in microseconds, fixed point value as returned from `rtc_clk_cal`
624  * @return Frequency of the clock in Hz
625  */
626 uint32_t rtc_clk_freq_cal(uint32_t cal_val);
627 
628 /**
629  * @brief Power down flags for rtc_sleep_pd function
630  */
631 typedef struct {
632     uint32_t dig_fpu : 1;    //!< Set to 1 to power down digital part in sleep
633     uint32_t rtc_fpu : 1;    //!< Set to 1 to power down RTC memories in sleep
634     uint32_t cpu_fpu : 1;    //!< Set to 1 to power down digital memories and CPU in sleep
635     uint32_t i2s_fpu : 1;    //!< Set to 1 to power down I2S in sleep
636     uint32_t bb_fpu : 1;     //!< Set to 1 to power down WiFi in sleep
637     uint32_t nrx_fpu : 1;    //!< Set to 1 to power down WiFi in sleep
638     uint32_t fe_fpu : 1;     //!< Set to 1 to power down WiFi in sleep
639 } rtc_sleep_pd_config_t;
640 
641 /**
642  * Initializer for rtc_sleep_pd_config_t which sets all flags to the same value
643  */
644 #define RTC_SLEEP_PD_CONFIG_ALL(val) {\
645     .dig_fpu = (val), \
646     .rtc_fpu = (val), \
647     .cpu_fpu = (val), \
648     .i2s_fpu = (val), \
649     .bb_fpu = (val), \
650     .nrx_fpu = (val), \
651     .fe_fpu = (val), \
652 }
653 
654 void rtc_sleep_pd(rtc_sleep_pd_config_t cfg);
655 
656 /**
657  * @brief sleep configuration for rtc_sleep_init function
658  */
659 typedef struct {
660     uint32_t lslp_mem_inf_fpu : 1;      //!< force normal voltage in sleep mode (digital domain memory)
661     uint32_t rtc_mem_inf_follow_cpu : 1;//!< keep low voltage in sleep mode (even if ULP/touch is used)
662     uint32_t rtc_fastmem_pd_en : 1;     //!< power down RTC fast memory
663     uint32_t rtc_slowmem_pd_en : 1;     //!< power down RTC slow memory
664     uint32_t rtc_peri_pd_en : 1;        //!< power down RTC peripherals
665     uint32_t wifi_pd_en : 1;            //!< power down WiFi
666     uint32_t int_8m_pd_en : 1;          //!< Power down Internal 8M oscillator
667     uint32_t deep_slp : 1;              //!< power down digital domain
668     uint32_t wdt_flashboot_mod_en : 1;  //!< enable WDT flashboot mode
669     uint32_t dig_dbias_wak : 3;         //!< set bias for digital domain, in active mode
670     uint32_t dig_dbias_slp : 3;         //!< set bias for digital domain, in sleep mode
671     uint32_t rtc_dbias_wak : 3;         //!< set bias for RTC domain, in active mode
672     uint32_t rtc_dbias_slp : 3;         //!< set bias for RTC domain, in sleep mode
673     uint32_t vddsdio_pd_en : 1;         //!< power down VDDSDIO regulator
674     uint32_t xtal_fpu : 1;              //!< keep main XTAL powered up in sleep
675     uint32_t deep_slp_reject : 1;
676     uint32_t light_slp_reject : 1;
677 } rtc_sleep_config_t;
678 
679 /**
680  * Default initializer for rtc_sleep_config_t
681  *
682  * This initializer sets all fields to "reasonable" values (e.g. suggested for
683  * production use) based on a combination of RTC_SLEEP_PD_x flags.
684  *
685  * @param RTC_SLEEP_PD_x flags combined using bitwise OR
686  */
687 #define is_dslp(pd_flags)   ((pd_flags) & RTC_SLEEP_PD_DIG)
688 #define RTC_SLEEP_CONFIG_DEFAULT(sleep_flags) { \
689     .lslp_mem_inf_fpu = 0, \
690     .rtc_mem_inf_follow_cpu = ((sleep_flags) & RTC_SLEEP_PD_RTC_MEM_FOLLOW_CPU) ? 1 : 0, \
691     .rtc_fastmem_pd_en = ((sleep_flags) & RTC_SLEEP_PD_RTC_FAST_MEM) ? 1 : 0, \
692     .rtc_slowmem_pd_en = ((sleep_flags) & RTC_SLEEP_PD_RTC_SLOW_MEM) ? 1 : 0, \
693     .rtc_peri_pd_en = ((sleep_flags) & RTC_SLEEP_PD_RTC_PERIPH) ? 1 : 0, \
694     .wifi_pd_en = ((sleep_flags) & RTC_SLEEP_PD_WIFI) ? 1 : 0, \
695     .int_8m_pd_en = is_dslp(sleep_flags) ? 1 : ((sleep_flags) & RTC_SLEEP_PD_INT_8M) ? 1 : 0, \
696     .deep_slp = ((sleep_flags) & RTC_SLEEP_PD_DIG) ? 1 : 0, \
697     .wdt_flashboot_mod_en = 0, \
698     .dig_dbias_wak = RTC_CNTL_DIG_DBIAS_1V10, \
699     .dig_dbias_slp = is_dslp(sleep_flags)                   ? RTC_CNTL_DIG_DBIAS_0V90 \
700                    : !((sleep_flags) & RTC_SLEEP_PD_INT_8M) ? RTC_CNTL_DIG_DBIAS_1V10 \
701                    : !((sleep_flags) & RTC_SLEEP_PD_XTAL)   ? RTC_CNTL_DIG_DBIAS_1V10 \
702                    : RTC_CNTL_DIG_DBIAS_0V90, \
703     .rtc_dbias_wak = RTC_CNTL_DBIAS_1V10, \
704     .rtc_dbias_slp = is_dslp(sleep_flags)                   ? RTC_CNTL_DBIAS_1V00 \
705                    : !((sleep_flags) & RTC_SLEEP_PD_INT_8M) ? RTC_CNTL_DBIAS_1V10 \
706                    : !((sleep_flags) & RTC_SLEEP_PD_XTAL)   ? RTC_CNTL_DBIAS_1V10 \
707                    : RTC_CNTL_DBIAS_1V00, \
708     .vddsdio_pd_en = ((sleep_flags) & RTC_SLEEP_PD_VDDSDIO) ? 1 : 0, \
709     .xtal_fpu = is_dslp(sleep_flags) ? 0 : ((sleep_flags) & RTC_SLEEP_PD_XTAL) ? 0 : 1, \
710     .deep_slp_reject = 1, \
711     .light_slp_reject = 1 \
712 };
713 
714 #define RTC_SLEEP_PD_DIG                BIT(0)  //!< Deep sleep (power down digital domain)
715 #define RTC_SLEEP_PD_RTC_PERIPH         BIT(1)  //!< Power down RTC peripherals
716 #define RTC_SLEEP_PD_RTC_SLOW_MEM       BIT(2)  //!< Power down RTC SLOW memory
717 #define RTC_SLEEP_PD_RTC_FAST_MEM       BIT(3)  //!< Power down RTC FAST memory
718 #define RTC_SLEEP_PD_RTC_MEM_FOLLOW_CPU BIT(4)  //!< RTC FAST and SLOW memories are automatically powered up and down along with the CPU
719 #define RTC_SLEEP_PD_VDDSDIO            BIT(5)  //!< Power down VDDSDIO regulator
720 #define RTC_SLEEP_PD_WIFI               BIT(6)
721 #define RTC_SLEEP_PD_INT_8M             BIT(7)  //!< Power down Internal 8M oscillator
722 #define RTC_SLEEP_PD_XTAL               BIT(8)  //!< Power down main XTAL
723 
724 /**
725  * @brief Prepare the chip to enter sleep mode
726  *
727  * This function configures various power control state machines to handle
728  * entry into light sleep or deep sleep mode, switches APB and CPU clock source
729  * (usually to XTAL), and sets bias voltages for digital and RTC power domains.
730  *
731  * This function does not actually enter sleep mode; this is done using
732  * rtc_sleep_start function. Software may do some other actions between
733  * rtc_sleep_init and rtc_sleep_start, such as set wakeup timer and configure
734  * wakeup sources.
735  * @param cfg sleep mode configuration
736  */
737 void rtc_sleep_init(rtc_sleep_config_t cfg);
738 
739 /**
740  * @brief Low level initialize for rtc state machine waiting cycles after waking up
741  *
742  * This function configures the cycles chip need to wait for internal 8MHz
743  * oscillator and external 40MHz crystal. As we configure fixed time for waiting
744  * crystal, we need to pass period to calculate cycles. Now this function only
745  * used in lightsleep mode.
746  *
747  * @param slowclk_period re-calibrated slow clock period
748  */
749 void rtc_sleep_low_init(uint32_t slowclk_period);
750 
751 #define RTC_EXT0_TRIG_EN    BIT(0)  //!< EXT0 GPIO wakeup
752 #define RTC_EXT1_TRIG_EN    BIT(1)  //!< EXT1 GPIO wakeup
753 #define RTC_GPIO_TRIG_EN    BIT(2)  //!< GPIO wakeup (light sleep only)
754 #define RTC_TIMER_TRIG_EN   BIT(3)  //!< Timer wakeup
755 #define RTC_SDIO_TRIG_EN    BIT(4)  //!< SDIO wakeup (light sleep only)
756 #define RTC_WIFI_TRIG_EN    BIT(5)  //!< WIFI wakeup (light sleep only)
757 #define RTC_UART0_TRIG_EN   BIT(6)  //!< UART0 wakeup (light sleep only)
758 #define RTC_UART1_TRIG_EN   BIT(7)  //!< UART1 wakeup (light sleep only)
759 #define RTC_TOUCH_TRIG_EN   BIT(8)  //!< Touch wakeup
760 #define RTC_ULP_TRIG_EN     BIT(9)  //!< ULP wakeup
761 #define RTC_BT_TRIG_EN      BIT(10) //!< BT wakeup (light sleep only)
762 #define RTC_COCPU_TRIG_EN   BIT(11)
763 #define RTC_XTAL32K_DEAD_TRIG_EN    BIT(12)
764 #define RTC_COCPU_TRAP_TRIG_EN      BIT(13)
765 #define RTC_USB_TRIG_EN             BIT(14)
766 
767 /**
768  * @brief Enter deep or light sleep mode
769  *
770  * This function enters the sleep mode previously configured using rtc_sleep_init
771  * function. Before entering sleep, software should configure wake up sources
772  * appropriately (set up GPIO wakeup registers, timer wakeup registers,
773  * and so on).
774  *
775  * If deep sleep mode was configured using rtc_sleep_init, and sleep is not
776  * rejected by hardware (based on reject_opt flags), this function never returns.
777  * When the chip wakes up from deep sleep, CPU is reset and execution starts
778  * from ROM bootloader.
779  *
780  * If light sleep mode was configured using rtc_sleep_init, this function
781  * returns on wakeup, or if sleep is rejected by hardware.
782  *
783  * @param wakeup_opt  bit mask wake up reasons to enable (RTC_xxx_TRIG_EN flags
784  *                    combined with OR)
785  * @param reject_opt  bit mask of sleep reject reasons:
786  *                      - RTC_CNTL_GPIO_REJECT_EN
787  *                      - RTC_CNTL_SDIO_REJECT_EN
788  *                    These flags are used to prevent entering sleep when e.g.
789  *                    an external host is communicating via SDIO slave
790  * @param lslp_mem_inf_fpu If non-zero then the low power config is restored
791  *                         immediately on wake. Recommended for light sleep,
792  *                         has no effect if the system goes into deep sleep.
793  * @return non-zero if sleep was rejected by hardware
794  */
795 uint32_t rtc_sleep_start(uint32_t wakeup_opt, uint32_t reject_opt, uint32_t lslp_mem_inf_fpu);
796 
797 /**
798  * @brief Enter deep sleep mode
799  *
800  * Similar to rtc_sleep_start(), but additionally uses hardware to calculate the CRC value
801  * of RTC FAST memory. On wake, this CRC is used to determine if a deep sleep wake
802  * stub is valid to execute (if a wake address is set).
803  *
804  * No RAM is accessed while calculating the CRC and going into deep sleep, which makes
805  * this function safe to use even if the caller's stack is in RTC FAST memory.
806  *
807  * @note If no deep sleep wake stub address is set then calling rtc_sleep_start() will
808  * have the same effect and takes less time as CRC calculation is skipped.
809  *
810  * @note This function should only be called after rtc_sleep_init() has been called to
811  * configure the system for deep sleep.
812  *
813  * @param wakeup_opt - same as for rtc_sleep_start
814  * @param reject_opt - same as for rtc_sleep_start
815  *
816  * @return non-zero if sleep was rejected by hardware
817  */
818 uint32_t rtc_deep_sleep_start(uint32_t wakeup_opt, uint32_t reject_opt);
819 
820 /**
821  * RTC power and clock control initialization settings
822  */
823 typedef struct {
824     uint32_t ck8m_wait : 8;         //!< Number of rtc_fast_clk cycles to wait for 8M clock to be ready
825     uint32_t xtal_wait : 8;         //!< Number of rtc_fast_clk cycles to wait for XTAL clock to be ready
826     uint32_t pll_wait : 8;          //!< Number of rtc_fast_clk cycles to wait for PLL to be ready
827     uint32_t clkctl_init : 1;       //!< Perform clock control related initialization
828     uint32_t pwrctl_init : 1;       //!< Perform power control related initialization
829     uint32_t rtc_dboost_fpd : 1;    //!< Force power down RTC_DBOOST
830     uint32_t xtal_fpu : 1;
831     uint32_t bbpll_fpu : 1;
832     uint32_t cpu_waiti_clk_gate : 1;
833     uint32_t cali_ocode : 1;        //!< Calibrate Ocode to make bangap voltage more precise.
834 } rtc_config_t;
835 
836 /**
837  * Default initializer of rtc_config_t.
838  *
839  * This initializer sets all fields to "reasonable" values (e.g. suggested for
840  * production use).
841  */
842 #define RTC_CONFIG_DEFAULT() {\
843     .ck8m_wait = RTC_CNTL_CK8M_WAIT_DEFAULT, \
844     .xtal_wait = RTC_CNTL_XTL_BUF_WAIT_DEFAULT, \
845     .pll_wait  = RTC_CNTL_PLL_BUF_WAIT_DEFAULT, \
846     .clkctl_init = 1, \
847     .pwrctl_init = 1, \
848     .rtc_dboost_fpd = 1, \
849     .xtal_fpu = 0, \
850     .bbpll_fpu = 0, \
851     .cpu_waiti_clk_gate = 1, \
852     .cali_ocode = 0\
853 }
854 
855 /**
856  * Initialize RTC clock and power control related functions
857  * @param cfg configuration options as rtc_config_t
858  */
859 void rtc_init(rtc_config_t cfg);
860 
861 /**
862  * Structure describing vddsdio configuration
863  */
864 typedef struct {
865     uint32_t force : 1;     //!< If 1, use configuration from RTC registers; if 0, use EFUSE/bootstrapping pins.
866     uint32_t enable : 1;    //!< Enable VDDSDIO regulator
867     uint32_t tieh  : 1;     //!< Select VDDSDIO voltage. One of RTC_VDDSDIO_TIEH_1_8V, RTC_VDDSDIO_TIEH_3_3V
868     uint32_t drefh : 2;     //!< Tuning parameter for VDDSDIO regulator
869     uint32_t drefm : 2;     //!< Tuning parameter for VDDSDIO regulator
870     uint32_t drefl : 2;     //!< Tuning parameter for VDDSDIO regulator
871 } rtc_vddsdio_config_t;
872 
873 /**
874  * Get current VDDSDIO configuration
875  * If VDDSDIO configuration is overridden by RTC, get values from RTC
876  * Otherwise, if VDDSDIO is configured by EFUSE, get values from EFUSE
877  * Otherwise, use default values and the level of MTDI bootstrapping pin.
878  * @return currently used VDDSDIO configuration
879  */
880 rtc_vddsdio_config_t rtc_vddsdio_get_config(void);
881 
882 /**
883  * Set new VDDSDIO configuration using RTC registers.
884  * If config.force == 1, this overrides configuration done using bootstrapping
885  * pins and EFUSE.
886  *
887  * @param config new VDDSDIO configuration
888  */
889 void rtc_vddsdio_set_config(rtc_vddsdio_config_t config);
890 
891 /**
892  * Using valid hardware calibration value to calibrate slowclk
893  * If there is no hardware calibration in process, start hardware calibration and wait for calibration finished
894  * @param cal_clk clock to be measured
895  * @param slowclk_cycles if no hardware calibration in process, use this amount of slow cycles to calibrate slowclk.
896  */
897 uint32_t rtc_clk_cal_cycling(rtc_cal_sel_t cal_clk, uint32_t slowclk_cycles);
898 #ifdef __cplusplus
899 }
900 #endif
901