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 #ifndef __RTC_H__ 15 #define __RTC_H__ 16 17 #pragma once 18 19 #include <stdbool.h> 20 #include <stddef.h> 21 #include <stdint.h> 22 #include "soc/soc.h" 23 #include "soc/rtc_periph.h" 24 25 #define MHZ (1000000) 26 27 28 #ifdef __cplusplus 29 extern "C" { 30 #endif /* __cplusplus */ 31 32 /** 33 * @file rtc.h 34 * @brief Low-level RTC power, clock, and sleep functions. 35 * 36 * Functions in this file facilitate configuration of ESP32's RTC_CNTL peripheral. 37 * RTC_CNTL peripheral handles many functions: 38 * - enables/disables clocks and power to various parts of the chip; this is 39 * done using direct register access (forcing power up or power down) or by 40 * allowing state machines to control power and clocks automatically 41 * - handles sleep and wakeup functions 42 * - maintains a 48-bit counter which can be used for timekeeping 43 * 44 * These functions are not thread safe, and should not be viewed as high level 45 * APIs. For example, while this file provides a function which can switch 46 * CPU frequency, this function is on its own is not sufficient to implement 47 * frequency switching in ESP-IDF context: some coordination with RTOS, 48 * peripheral drivers, and WiFi/BT stacks is also required. 49 * 50 * These functions will normally not be used in applications directly. 51 * ESP-IDF provides, or will provide, drivers and other facilities to use 52 * RTC subsystem functionality. 53 * 54 * The functions are loosely split into the following groups: 55 * - rtc_clk: clock switching, calibration 56 * - rtc_time: reading RTC counter, conversion between counter values and time 57 * - rtc_sleep: entry into sleep modes 58 * - rtc_init: initialization 59 */ 60 61 62 /** 63 * @brief Possible main XTAL frequency values. 64 * 65 * Enum values should be equal to frequency in MHz. 66 */ 67 typedef enum { 68 RTC_XTAL_FREQ_AUTO = 0, //!< Automatic XTAL frequency detection 69 RTC_XTAL_FREQ_40M = 40, //!< 40 MHz XTAL 70 RTC_XTAL_FREQ_26M = 26, //!< 26 MHz XTAL 71 RTC_XTAL_FREQ_24M = 24, //!< 24 MHz XTAL 72 } rtc_xtal_freq_t; 73 74 /** 75 * @brief CPU frequency values 76 */ 77 typedef enum { 78 RTC_CPU_FREQ_XTAL = 0, //!< Main XTAL frequency 79 RTC_CPU_FREQ_80M = 1, //!< 80 MHz 80 RTC_CPU_FREQ_160M = 2, //!< 160 MHz 81 RTC_CPU_FREQ_240M = 3, //!< 240 MHz 82 RTC_CPU_FREQ_2M = 4, //!< 2 MHz 83 } rtc_cpu_freq_t; 84 85 /** 86 * @brief CPU clock source 87 */ 88 typedef enum { 89 RTC_CPU_FREQ_SRC_XTAL, //!< XTAL 90 RTC_CPU_FREQ_SRC_PLL, //!< PLL (480M or 320M) 91 RTC_CPU_FREQ_SRC_8M, //!< Internal 8M RTC oscillator 92 RTC_CPU_FREQ_SRC_APLL //!< APLL 93 } rtc_cpu_freq_src_t; 94 95 /** 96 * @brief CPU clock configuration structure 97 */ 98 typedef struct rtc_cpu_freq_config_s { 99 rtc_cpu_freq_src_t source; //!< The clock from which CPU clock is derived 100 uint32_t source_freq_mhz; //!< Source clock frequency 101 uint32_t div; //!< Divider, freq_mhz = source_freq_mhz / div 102 uint32_t freq_mhz; //!< CPU clock frequency 103 } rtc_cpu_freq_config_t; 104 105 /** 106 * @brief RTC SLOW_CLK frequency values 107 */ 108 typedef enum { 109 RTC_SLOW_FREQ_RTC = 0, //!< Internal 150 kHz RC oscillator 110 RTC_SLOW_FREQ_32K_XTAL = 1, //!< External 32 kHz XTAL 111 RTC_SLOW_FREQ_8MD256 = 2, //!< Internal 8 MHz RC oscillator, divided by 256 112 } rtc_slow_freq_t; 113 114 /** 115 * @brief RTC FAST_CLK frequency values 116 */ 117 typedef enum { 118 RTC_FAST_FREQ_XTALD4 = 0, //!< Main XTAL, divided by 4 119 RTC_FAST_FREQ_8M = 1, //!< Internal 8 MHz RC oscillator 120 } rtc_fast_freq_t; 121 122 /* With the default value of CK8M_DFREQ, 8M clock frequency is 8.5 MHz +/- 7% */ 123 #define RTC_FAST_CLK_FREQ_APPROX 8500000 124 125 /** 126 * @brief Clock source to be calibrated using rtc_clk_cal function 127 */ 128 typedef enum { 129 RTC_CAL_RTC_MUX = 0, //!< Currently selected RTC SLOW_CLK 130 RTC_CAL_8MD256 = 1, //!< Internal 8 MHz RC oscillator, divided by 256 131 RTC_CAL_32K_XTAL = 2 //!< External 32 kHz XTAL 132 } rtc_cal_sel_t; 133 134 /** 135 * Initialization parameters for rtc_clk_init 136 */ 137 typedef struct rtc_clk_config_s { 138 rtc_xtal_freq_t xtal_freq : 8; //!< Main XTAL frequency 139 uint32_t cpu_freq_mhz : 10; //!< CPU frequency to set, in MHz 140 rtc_fast_freq_t fast_freq : 1; //!< RTC_FAST_CLK frequency to set 141 rtc_slow_freq_t slow_freq : 2; //!< RTC_SLOW_CLK frequency to set 142 uint32_t clk_8m_div : 3; //!< RTC 8M clock divider (division is by clk_8m_div+1, i.e. 0 means 8MHz frequency) 143 uint32_t slow_clk_dcap : 8; //!< RTC 150k clock adjustment parameter (higher value leads to lower frequency) 144 uint32_t clk_8m_dfreq : 8; //!< RTC 8m clock adjustment parameter (higher value leads to higher frequency) 145 } rtc_clk_config_t; 146 147 /** 148 * Default initializer for rtc_clk_config_t 149 */ 150 #define RTC_CLK_CONFIG_DEFAULT() { \ 151 .xtal_freq = RTC_XTAL_FREQ_AUTO, \ 152 .cpu_freq_mhz = 80, \ 153 .fast_freq = RTC_FAST_FREQ_8M, \ 154 .slow_freq = RTC_SLOW_FREQ_RTC, \ 155 .clk_8m_div = 0, \ 156 .slow_clk_dcap = RTC_CNTL_SCK_DCAP_DEFAULT, \ 157 .clk_8m_dfreq = RTC_CNTL_CK8M_DFREQ_DEFAULT, \ 158 } 159 160 /** 161 * Initialize clocks and set CPU frequency 162 * 163 * If cfg.xtal_freq is set to RTC_XTAL_FREQ_AUTO, this function will attempt 164 * to auto detect XTAL frequency. Auto detection is performed by comparing 165 * XTAL frequency with the frequency of internal 8MHz oscillator. Note that at 166 * high temperatures the frequency of the internal 8MHz oscillator may drift 167 * enough for auto detection to be unreliable. 168 * Auto detection code will attempt to distinguish between 26MHz and 40MHz 169 * crystals. 24 MHz crystals are not supported by auto detection code. 170 * If XTAL frequency can not be auto detected, this 26MHz frequency will be used. 171 * 172 * @param cfg clock configuration as rtc_clk_config_t 173 */ 174 void rtc_clk_init(rtc_clk_config_t cfg); 175 176 /** 177 * @brief Get main XTAL frequency 178 * 179 * This is the value stored in RTC register RTC_XTAL_FREQ_REG by the bootloader. As passed to 180 * rtc_clk_init function, or if the value was RTC_XTAL_FREQ_AUTO, the detected 181 * XTAL frequency. 182 * 183 * @return XTAL frequency, one of rtc_xtal_freq_t 184 */ 185 rtc_xtal_freq_t rtc_clk_xtal_freq_get(void); 186 187 /** 188 * @brief Update XTAL frequency 189 * 190 * Updates the XTAL value stored in RTC_XTAL_FREQ_REG. Usually this value is ignored 191 * after startup. 192 * 193 * @param xtal_freq New frequency value 194 */ 195 void rtc_clk_xtal_freq_update(rtc_xtal_freq_t xtal_freq); 196 197 /** 198 * @brief Enable or disable 32 kHz XTAL oscillator 199 * @param en true to enable, false to disable 200 */ 201 void rtc_clk_32k_enable(bool en); 202 203 /** 204 * @brief Configure 32 kHz XTAL oscillator to accept external clock signal 205 */ 206 void rtc_clk_32k_enable_external(void); 207 208 /** 209 * @brief Get the state of 32k XTAL oscillator 210 * @return true if 32k XTAL oscillator has been enabled 211 */ 212 bool rtc_clk_32k_enabled(void); 213 214 /** 215 * @brief Enable 32k oscillator, configuring it for fast startup time. 216 * Note: to achieve higher frequency stability, rtc_clk_32k_enable function 217 * must be called one the 32k XTAL oscillator has started up. This function 218 * will initially disable the 32k XTAL oscillator, so it should not be called 219 * when the system is using 32k XTAL as RTC_SLOW_CLK. 220 * 221 * @param cycle Number of 32kHz cycles to bootstrap external crystal. 222 * If 0, no square wave will be used to bootstrap crystal oscillation. 223 */ 224 void rtc_clk_32k_bootstrap(uint32_t cycle); 225 226 /** 227 * @brief Enable or disable 8 MHz internal oscillator 228 * 229 * Output from 8 MHz internal oscillator is passed into a configurable 230 * divider, which by default divides the input clock frequency by 256. 231 * Output of the divider may be used as RTC_SLOW_CLK source. 232 * Output of the divider is referred to in register descriptions and code as 233 * 8md256 or simply d256. Divider values other than 256 may be configured, but 234 * this facility is not currently needed, so is not exposed in the code. 235 * 236 * When 8MHz/256 divided output is not needed, the divider should be disabled 237 * to reduce power consumption. 238 * 239 * @param clk_8m_en true to enable 8MHz generator 240 * @param d256_en true to enable /256 divider 241 */ 242 void rtc_clk_8m_enable(bool clk_8m_en, bool d256_en); 243 244 /** 245 * @brief Get the state of 8 MHz internal oscillator 246 * @return true if the oscillator is enabled 247 */ 248 bool rtc_clk_8m_enabled(void); 249 250 /** 251 * @brief Get the state of /256 divider which is applied to 8MHz clock 252 * @return true if the divided output is enabled 253 */ 254 bool rtc_clk_8md256_enabled(void); 255 256 /** 257 * @brief Enable or disable APLL 258 * 259 * Output frequency is given by the formula: 260 * apll_freq = xtal_freq * (4 + sdm2 + sdm1/256 + sdm0/65536)/((o_div + 2) * 2) 261 * 262 * The dividend in this expression should be in the range of 240 - 600 MHz. 263 * 264 * In rev. 0 of ESP32, sdm0 and sdm1 are unused and always set to 0. 265 * 266 * @param enable true to enable, false to disable 267 * @param sdm0 frequency adjustment parameter, 0..255 268 * @param sdm1 frequency adjustment parameter, 0..255 269 * @param sdm2 frequency adjustment parameter, 0..63 270 * @param o_div frequency divider, 0..31 271 */ 272 void rtc_clk_apll_enable(bool enable, uint32_t sdm0, uint32_t sdm1, 273 uint32_t sdm2, uint32_t o_div); 274 275 /** 276 * @brief Select source for RTC_SLOW_CLK 277 * @param slow_freq clock source (one of rtc_slow_freq_t values) 278 */ 279 void rtc_clk_slow_freq_set(rtc_slow_freq_t slow_freq); 280 281 /** 282 * @brief Get the RTC_SLOW_CLK source 283 * @return currently selected clock source (one of rtc_slow_freq_t values) 284 */ 285 rtc_slow_freq_t rtc_clk_slow_freq_get(void); 286 287 /** 288 * @brief Get the approximate frequency of RTC_SLOW_CLK, in Hz 289 * 290 * - if RTC_SLOW_FREQ_RTC is selected, returns ~150000 291 * - if RTC_SLOW_FREQ_32K_XTAL is selected, returns 32768 292 * - if RTC_SLOW_FREQ_8MD256 is selected, returns ~33000 293 * 294 * rtc_clk_cal function can be used to get more precise value by comparing 295 * RTC_SLOW_CLK frequency to the frequency of main XTAL. 296 * 297 * @return RTC_SLOW_CLK frequency, in Hz 298 */ 299 uint32_t rtc_clk_slow_freq_get_hz(void); 300 301 /** 302 * @brief Select source for RTC_FAST_CLK 303 * @param fast_freq clock source (one of rtc_fast_freq_t values) 304 */ 305 void rtc_clk_fast_freq_set(rtc_fast_freq_t fast_freq); 306 307 /** 308 * @brief Get the RTC_FAST_CLK source 309 * @return currently selected clock source (one of rtc_fast_freq_t values) 310 */ 311 rtc_fast_freq_t rtc_clk_fast_freq_get(void); 312 313 /** 314 * @brief Get CPU frequency config corresponding to a rtc_cpu_freq_t value 315 * @param cpu_freq CPU frequency enumeration value 316 * @param[out] out_config Output, CPU frequency configuration structure 317 */ 318 void rtc_clk_cpu_freq_to_config(rtc_cpu_freq_t cpu_freq, rtc_cpu_freq_config_t* out_config); 319 320 /** 321 * @brief Get CPU frequency config for a given frequency 322 * @param freq_mhz Frequency in MHz 323 * @param[out] out_config Output, CPU frequency configuration structure 324 * @return true if frequency can be obtained, false otherwise 325 */ 326 bool rtc_clk_cpu_freq_mhz_to_config(uint32_t freq_mhz, rtc_cpu_freq_config_t* out_config); 327 328 /** 329 * @brief Switch CPU frequency 330 * 331 * This function sets CPU frequency according to the given configuration 332 * structure. It enables PLLs, if necessary. 333 * 334 * @note This function in not intended to be called by applications in FreeRTOS 335 * environment. This is because it does not adjust various timers based on the 336 * new CPU frequency. 337 * 338 * @param config CPU frequency configuration structure 339 */ 340 void rtc_clk_cpu_freq_set_config(const rtc_cpu_freq_config_t* config); 341 342 /** 343 * @brief Switch CPU frequency (optimized for speed) 344 * 345 * This function is a faster equivalent of rtc_clk_cpu_freq_set_config. 346 * It works faster because it does not disable PLLs when switching from PLL to 347 * XTAL and does not enabled them when switching back. If PLL is not already 348 * enabled when this function is called to switch from XTAL to PLL frequency, 349 * or the PLL which is enabled is the wrong one, this function will fall back 350 * to calling rtc_clk_cpu_freq_set_config. 351 * 352 * Unlike rtc_clk_cpu_freq_set_config, this function relies on static data, 353 * so it is less safe to use it e.g. from a panic handler (when memory might 354 * be corrupted). 355 * 356 * @note This function in not intended to be called by applications in FreeRTOS 357 * environment. This is because it does not adjust various timers based on the 358 * new CPU frequency. 359 * 360 * @param config CPU frequency configuration structure 361 */ 362 void rtc_clk_cpu_freq_set_config_fast(const rtc_cpu_freq_config_t* config); 363 364 /** 365 * @brief Get the currently used CPU frequency configuration 366 * @param[out] out_config Output, CPU frequency configuration structure 367 */ 368 void rtc_clk_cpu_freq_get_config(rtc_cpu_freq_config_t* out_config); 369 370 /** 371 * @brief Switch CPU clock source to XTAL 372 * 373 * Short form for filling in rtc_cpu_freq_config_t structure and calling 374 * rtc_clk_cpu_freq_set_config when a switch to XTAL is needed. 375 * Assumes that XTAL frequency has been determined — don't call in startup code. 376 */ 377 void rtc_clk_cpu_freq_set_xtal(void); 378 379 380 /** 381 * @brief Store new APB frequency value into RTC_APB_FREQ_REG 382 * 383 * This function doesn't change any hardware clocks. 384 * 385 * Functions which perform frequency switching and change APB frequency call 386 * this function to update the value of APB frequency stored in RTC_APB_FREQ_REG 387 * (one of RTC general purpose retention registers). This should not normally 388 * be called from application code. 389 * 390 * @param apb_freq new APB frequency, in Hz 391 */ 392 void rtc_clk_apb_freq_update(uint32_t apb_freq); 393 394 /** 395 * @brief Get the current stored APB frequency. 396 * @return The APB frequency value as last set via rtc_clk_apb_freq_update(), in Hz. 397 */ 398 uint32_t rtc_clk_apb_freq_get(void); 399 400 #define RTC_CLK_CAL_FRACT 19 //!< Number of fractional bits in values returned by rtc_clk_cal 401 402 /** 403 * @brief Measure RTC slow clock's period, based on main XTAL frequency 404 * 405 * This function will time out and return 0 if the time for the given number 406 * of cycles to be counted exceeds the expected time twice. This may happen if 407 * 32k XTAL is being calibrated, but the oscillator has not started up (due to 408 * incorrect loading capacitance, board design issue, or lack of 32 XTAL on board). 409 * 410 * @param cal_clk clock to be measured 411 * @param slow_clk_cycles number of slow clock cycles to average 412 * @return average slow clock period in microseconds, Q13.19 fixed point format, 413 * or 0 if calibration has timed out 414 */ 415 uint32_t rtc_clk_cal(rtc_cal_sel_t cal_clk, uint32_t slow_clk_cycles); 416 417 /** 418 * @brief Measure ratio between XTAL frequency and RTC slow clock frequency 419 * @param cal_clk slow clock to be measured 420 * @param slow_clk_cycles number of slow clock cycles to average 421 * @return average ratio between XTAL frequency and slow clock frequency, 422 * Q13.19 fixed point format, or 0 if calibration has timed out. 423 */ 424 uint32_t rtc_clk_cal_ratio(rtc_cal_sel_t cal_clk, uint32_t slow_clk_cycles); 425 426 /** 427 * @brief Convert time interval from microseconds to RTC_SLOW_CLK cycles 428 * @param time_in_us Time interval in microseconds 429 * @param slow_clk_period Period of slow clock in microseconds, Q13.19 430 * fixed point format (as returned by rtc_slowck_cali). 431 * @return number of slow clock cycles 432 */ 433 uint64_t rtc_time_us_to_slowclk(uint64_t time_in_us, uint32_t period); 434 435 /** 436 * @brief Convert time interval from RTC_SLOW_CLK to microseconds 437 * @param time_in_us Time interval in RTC_SLOW_CLK cycles 438 * @param slow_clk_period Period of slow clock in microseconds, Q13.19 439 * fixed point format (as returned by rtc_slowck_cali). 440 * @return time interval in microseconds 441 */ 442 uint64_t rtc_time_slowclk_to_us(uint64_t rtc_cycles, uint32_t period); 443 444 /** 445 * @brief Get current value of RTC counter 446 * 447 * RTC has a 48-bit counter which is incremented by 2 every 2 RTC_SLOW_CLK 448 * cycles. Counter value is not writable by software. The value is not adjusted 449 * when switching to a different RTC_SLOW_CLK source. 450 * 451 * Note: this function may take up to 1 RTC_SLOW_CLK cycle to execute 452 * 453 * @return current value of RTC counter 454 */ 455 uint64_t rtc_time_get(void); 456 457 /** 458 * @brief Busy loop until next RTC_SLOW_CLK cycle 459 * 460 * This function returns not earlier than the next RTC_SLOW_CLK clock cycle. 461 * In some cases (e.g. when RTC_SLOW_CLK cycle is very close), it may return 462 * one RTC_SLOW_CLK cycle later. 463 */ 464 void rtc_clk_wait_for_slow_cycle(void); 465 466 /** 467 * @brief Enable the rtc digital 8M clock 468 * 469 * This function is used to enable the digital rtc 8M clock to support peripherals. 470 * For enabling the analog 8M clock, using `rtc_clk_8M_enable` function above. 471 */ 472 void rtc_dig_clk8m_enable(void); 473 474 /** 475 * @brief Disable the rtc digital 8M clock 476 * 477 * This function is used to disable the digital rtc 8M clock, which is only used to support peripherals. 478 */ 479 void rtc_dig_clk8m_disable(void); 480 481 /** 482 * @brief Calculate the real clock value after the clock calibration 483 * 484 * @param cal_val Average slow clock period in microseconds, fixed point value as returned from `rtc_clk_cal` 485 * @return Frequency of the clock in Hz 486 */ 487 uint32_t rtc_clk_freq_cal(uint32_t cal_val); 488 489 /** 490 * @brief sleep configuration for rtc_sleep_init function 491 */ 492 typedef struct rtc_sleep_config_s { 493 uint32_t lslp_mem_inf_fpu : 1; //!< force normal voltage in sleep mode (digital domain memory) 494 uint32_t rtc_mem_inf_fpu : 1; //!< force normal voltage in sleep mode (RTC memory) 495 uint32_t rtc_mem_inf_follow_cpu : 1;//!< keep low voltage in sleep mode (even if ULP/touch is used) 496 uint32_t rtc_fastmem_pd_en : 1; //!< power down RTC fast memory 497 uint32_t rtc_slowmem_pd_en : 1; //!< power down RTC slow memory 498 uint32_t rtc_peri_pd_en : 1; //!< power down RTC peripherals 499 uint32_t wifi_pd_en : 1; //!< power down WiFi 500 uint32_t rom_mem_pd_en : 1; //!< power down main RAM and ROM 501 uint32_t deep_slp : 1; //!< power down digital domain 502 uint32_t wdt_flashboot_mod_en : 1; //!< enable WDT flashboot mode 503 uint32_t dig_dbias_wak : 3; //!< set bias for digital domain, in active mode 504 uint32_t dig_dbias_slp : 3; //!< set bias for digital domain, in sleep mode 505 uint32_t rtc_dbias_wak : 3; //!< set bias for RTC domain, in active mode 506 uint32_t rtc_dbias_slp : 3; //!< set bias for RTC domain, in sleep mode 507 uint32_t lslp_meminf_pd : 1; //!< remove all peripheral force power up flags 508 uint32_t vddsdio_pd_en : 1; //!< power down VDDSDIO regulator 509 uint32_t xtal_fpu : 1; //!< keep main XTAL powered up in sleep 510 } rtc_sleep_config_t; 511 512 /** 513 * Default initializer for rtc_sleep_config_t 514 * 515 * This initializer sets all fields to "reasonable" values (e.g. suggested for 516 * production use) based on a combination of RTC_SLEEP_PD_x flags. 517 * 518 * @param RTC_SLEEP_PD_x flags combined using bitwise OR 519 */ 520 #define RTC_SLEEP_CONFIG_DEFAULT(sleep_flags) { \ 521 .lslp_mem_inf_fpu = 0, \ 522 .rtc_mem_inf_fpu = 0, \ 523 .rtc_mem_inf_follow_cpu = ((sleep_flags) & RTC_SLEEP_PD_RTC_MEM_FOLLOW_CPU) ? 1 : 0, \ 524 .rtc_fastmem_pd_en = ((sleep_flags) & RTC_SLEEP_PD_RTC_FAST_MEM) ? 1 : 0, \ 525 .rtc_slowmem_pd_en = ((sleep_flags) & RTC_SLEEP_PD_RTC_SLOW_MEM) ? 1 : 0, \ 526 .rtc_peri_pd_en = ((sleep_flags) & RTC_SLEEP_PD_RTC_PERIPH) ? 1 : 0, \ 527 .wifi_pd_en = 0, \ 528 .rom_mem_pd_en = 0, \ 529 .deep_slp = ((sleep_flags) & RTC_SLEEP_PD_DIG) ? 1 : 0, \ 530 .wdt_flashboot_mod_en = 0, \ 531 .dig_dbias_wak = RTC_CNTL_DBIAS_1V10, \ 532 .dig_dbias_slp = RTC_CNTL_DBIAS_0V90, \ 533 .rtc_dbias_wak = RTC_CNTL_DBIAS_1V10, \ 534 .rtc_dbias_slp = RTC_CNTL_DBIAS_0V90, \ 535 .lslp_meminf_pd = 1, \ 536 .vddsdio_pd_en = ((sleep_flags) & RTC_SLEEP_PD_VDDSDIO) ? 1 : 0, \ 537 .xtal_fpu = ((sleep_flags) & RTC_SLEEP_PD_XTAL) ? 0 : 1 \ 538 }; 539 540 #define RTC_SLEEP_PD_DIG BIT(0) //!< Deep sleep (power down digital domain) 541 #define RTC_SLEEP_PD_RTC_PERIPH BIT(1) //!< Power down RTC peripherals 542 #define RTC_SLEEP_PD_RTC_SLOW_MEM BIT(2) //!< Power down RTC SLOW memory 543 #define RTC_SLEEP_PD_RTC_FAST_MEM BIT(3) //!< Power down RTC FAST memory 544 #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 545 #define RTC_SLEEP_PD_VDDSDIO BIT(5) //!< Power down VDDSDIO regulator 546 #define RTC_SLEEP_PD_XTAL BIT(6) //!< Power down main XTAL 547 548 /* Various delays to be programmed into power control state machines */ 549 #define RTC_CNTL_XTL_BUF_WAIT_SLP_US (500) 550 #define RTC_CNTL_PLL_BUF_WAIT_SLP_CYCLES (1) 551 #define RTC_CNTL_CK8M_WAIT_SLP_CYCLES (4) 552 #define RTC_CNTL_WAKEUP_DELAY_CYCLES (7) 553 #define RTC_CNTL_OTHER_BLOCKS_POWERUP_CYCLES (1) 554 #define RTC_CNTL_OTHER_BLOCKS_WAIT_CYCLES (1) 555 556 /** 557 * @brief Prepare the chip to enter sleep mode 558 * 559 * This function configures various power control state machines to handle 560 * entry into light sleep or deep sleep mode, switches APB and CPU clock source 561 * (usually to XTAL), and sets bias voltages for digital and RTC power domains. 562 * 563 * This function does not actually enter sleep mode; this is done using 564 * rtc_sleep_start function. Software may do some other actions between 565 * rtc_sleep_init and rtc_sleep_start, such as set wakeup timer and configure 566 * wakeup sources. 567 * @param cfg sleep mode configuration 568 */ 569 void rtc_sleep_init(rtc_sleep_config_t cfg); 570 571 /** 572 * @brief Low level initialize for rtc state machine waiting cycles after waking up 573 * 574 * This function configures the cycles chip need to wait for internal 8MHz 575 * oscillator and external 40MHz crystal. As we configure fixed time for waiting 576 * crystal, we need to pass period to calculate cycles. Now this function only 577 * used in lightsleep mode. 578 * 579 * @param slowclk_period re-calibrated slow clock period 580 */ 581 void rtc_sleep_low_init(uint32_t slowclk_period); 582 583 /** 584 * @brief Set target value of RTC counter for RTC_TIMER_TRIG_EN wakeup source 585 * @param t value of RTC counter at which wakeup from sleep will happen; 586 * only the lower 48 bits are used 587 */ 588 void rtc_sleep_set_wakeup_time(uint64_t t); 589 590 591 #define RTC_EXT0_TRIG_EN BIT(0) //!< EXT0 GPIO wakeup 592 #define RTC_EXT1_TRIG_EN BIT(1) //!< EXT1 GPIO wakeup 593 #define RTC_GPIO_TRIG_EN BIT(2) //!< GPIO wakeup (light sleep only) 594 #define RTC_TIMER_TRIG_EN BIT(3) //!< Timer wakeup 595 #define RTC_SDIO_TRIG_EN BIT(4) //!< SDIO wakeup (light sleep only) 596 #define RTC_MAC_TRIG_EN BIT(5) //!< MAC wakeup (light sleep only) 597 #define RTC_UART0_TRIG_EN BIT(6) //!< UART0 wakeup (light sleep only) 598 #define RTC_UART1_TRIG_EN BIT(7) //!< UART1 wakeup (light sleep only) 599 #define RTC_TOUCH_TRIG_EN BIT(8) //!< Touch wakeup 600 #define RTC_ULP_TRIG_EN BIT(9) //!< ULP wakeup 601 #define RTC_BT_TRIG_EN BIT(10) //!< BT wakeup (light sleep only) 602 603 /** 604 * @brief Enter deep or light sleep mode 605 * 606 * This function enters the sleep mode previously configured using rtc_sleep_init 607 * function. Before entering sleep, software should configure wake up sources 608 * appropriately (set up GPIO wakeup registers, timer wakeup registers, 609 * and so on). 610 * 611 * If deep sleep mode was configured using rtc_sleep_init, and sleep is not 612 * rejected by hardware (based on reject_opt flags), this function never returns. 613 * When the chip wakes up from deep sleep, CPU is reset and execution starts 614 * from ROM bootloader. 615 * 616 * If light sleep mode was configured using rtc_sleep_init, this function 617 * returns on wakeup, or if sleep is rejected by hardware. 618 * 619 * @param wakeup_opt bit mask wake up reasons to enable (RTC_xxx_TRIG_EN flags 620 * combined with OR) 621 * @param reject_opt bit mask of sleep reject reasons: 622 * - RTC_CNTL_GPIO_REJECT_EN 623 * - RTC_CNTL_SDIO_REJECT_EN 624 * These flags are used to prevent entering sleep when e.g. 625 * an external host is communicating via SDIO slave 626 * @return non-zero if sleep was rejected by hardware 627 */ 628 uint32_t rtc_sleep_start(uint32_t wakeup_opt, uint32_t reject_opt); 629 630 /** 631 * @brief Enter deep sleep mode 632 * 633 * Similar to rtc_sleep_start(), but additionally uses hardware to calculate the CRC value 634 * of RTC FAST memory. On wake, this CRC is used to determine if a deep sleep wake 635 * stub is valid to execute (if a wake address is set). 636 * 637 * No RAM is accessed while calculating the CRC and going into deep sleep, which makes 638 * this function safe to use even if the caller's stack is in RTC FAST memory. 639 * 640 * @note If no deep sleep wake stub address is set then calling rtc_sleep_start() will 641 * have the same effect and takes less time as CRC calculation is skipped. 642 * 643 * @note This function should only be called after rtc_sleep_init() has been called to 644 * configure the system for deep sleep. 645 * 646 * @param wakeup_opt - same as for rtc_sleep_start 647 * @param reject_opt - same as for rtc_sleep_start 648 * 649 * @return non-zero if sleep was rejected by hardware 650 */ 651 uint32_t rtc_deep_sleep_start(uint32_t wakeup_opt, uint32_t reject_opt); 652 653 /** 654 * RTC power and clock control initialization settings 655 */ 656 typedef struct rtc_config_s { 657 uint32_t ck8m_wait : 8; //!< Number of rtc_fast_clk cycles to wait for 8M clock to be ready 658 uint32_t xtal_wait : 8; //!< Number of rtc_fast_clk cycles to wait for XTAL clock to be ready 659 uint32_t pll_wait : 8; //!< Number of rtc_fast_clk cycles to wait for PLL to be ready 660 uint32_t clkctl_init : 1; //!< Perform clock control related initialization 661 uint32_t pwrctl_init : 1; //!< Perform power control related initialization 662 uint32_t rtc_dboost_fpd : 1; //!< Force power down RTC_DBOOST 663 } rtc_config_t; 664 665 /** 666 * Default initializer of rtc_config_t. 667 * 668 * This initializer sets all fields to "reasonable" values (e.g. suggested for 669 * production use). 670 */ 671 #define RTC_CONFIG_DEFAULT() {\ 672 .ck8m_wait = RTC_CNTL_CK8M_WAIT_DEFAULT, \ 673 .xtal_wait = RTC_CNTL_XTL_BUF_WAIT_DEFAULT, \ 674 .pll_wait = RTC_CNTL_PLL_BUF_WAIT_DEFAULT, \ 675 .clkctl_init = 1, \ 676 .pwrctl_init = 1, \ 677 .rtc_dboost_fpd = 1 \ 678 } 679 680 /** 681 * Initialize RTC clock and power control related functions 682 * @param cfg configuration options as rtc_config_t 683 */ 684 void rtc_init(rtc_config_t cfg); 685 686 #define RTC_VDDSDIO_TIEH_1_8V 0 //!< TIEH field value for 1.8V VDDSDIO 687 #define RTC_VDDSDIO_TIEH_3_3V 1 //!< TIEH field value for 3.3V VDDSDIO 688 689 /** 690 * Structure describing vddsdio configuration 691 */ 692 typedef struct rtc_vddsdio_config_s { 693 uint32_t force : 1; //!< If 1, use configuration from RTC registers; if 0, use EFUSE/bootstrapping pins. 694 uint32_t enable : 1; //!< Enable VDDSDIO regulator 695 uint32_t tieh : 1; //!< Select VDDSDIO voltage. One of RTC_VDDSDIO_TIEH_1_8V, RTC_VDDSDIO_TIEH_3_3V 696 uint32_t drefh : 2; //!< Tuning parameter for VDDSDIO regulator 697 uint32_t drefm : 2; //!< Tuning parameter for VDDSDIO regulator 698 uint32_t drefl : 2; //!< Tuning parameter for VDDSDIO regulator 699 } rtc_vddsdio_config_t; 700 701 /** 702 * Get current VDDSDIO configuration 703 * If VDDSDIO configuration is overridden by RTC, get values from RTC 704 * Otherwise, if VDDSDIO is configured by EFUSE, get values from EFUSE 705 * Otherwise, use default values and the level of MTDI bootstrapping pin. 706 * @return currently used VDDSDIO configuration 707 */ 708 rtc_vddsdio_config_t rtc_vddsdio_get_config(void); 709 710 /** 711 * Set new VDDSDIO configuration using RTC registers. 712 * If config.force == 1, this overrides configuration done using bootstrapping 713 * pins and EFUSE. 714 * 715 * @param config new VDDSDIO configuration 716 */ 717 void rtc_vddsdio_set_config(rtc_vddsdio_config_t config); 718 719 720 #ifdef __cplusplus 721 } 722 #endif /* __cplusplus */ 723 #endif /* __RTC_H__ */