diff --git a/esp-hal/CHANGELOG.md b/esp-hal/CHANGELOG.md index 133e505ec..67142ca5e 100644 --- a/esp-hal/CHANGELOG.md +++ b/esp-hal/CHANGELOG.md @@ -47,6 +47,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 - `ShaDigest::finish` has been reimplemented to be properly non-blocking (#3948) - Replace Timer's `pub fn enable_interrupt(&mut self, enable: bool)` with `pub fn listen(&mut self)` and `pub fn unlisten(&mut self)` (#3933) - ESP32-S3: `PsramConfig::core_clock` is now an `Option` (#3974) +- `RtcSlowClock::RtcFastClock8m` has been renamed to `RtcFastClock::RtcFastClockRcFast` (#3993) +- `RtcSlowClock::RtcSlowClockRtc` has been renamed to `RtcSlowClock::RtcSlowClockRcSlow` (#3993) ### Fixed diff --git a/esp-hal/src/rtc_cntl/mod.rs b/esp-hal/src/rtc_cntl/mod.rs index aebfca1b1..1bca38a72 100644 --- a/esp-hal/src/rtc_cntl/mod.rs +++ b/esp-hal/src/rtc_cntl/mod.rs @@ -120,12 +120,10 @@ use crate::rtc_cntl::sleep::{RtcSleepConfig, WakeSource, WakeTriggers}; use crate::{ clock::{Clock, XtalClock}, interrupt::{self, InterruptHandler}, - peripherals::{Interrupt, TIMG0}, + peripherals::{Interrupt, LPWR, TIMG0}, system::{Cpu, SleepSource}, - time::Duration, + time::{Duration, Rate}, }; -#[cfg(not(any(esp32c6, esp32h2)))] -use crate::{peripherals::LPWR, time::Rate}; // only include sleep where it's been implemented #[cfg(any(esp32, esp32s2, esp32s3, esp32c3, esp32c6, esp32c2))] pub mod sleep; @@ -144,8 +142,6 @@ cfg_if::cfg_if! { use crate::peripherals::LP_WDT; use crate::peripherals::LP_TIMER; use crate::peripherals::LP_AON; - - use rtc::{RtcSlowClock, RtcCalSel}; // TODO: bring the types into this module } else { use crate::peripherals::LPWR as LP_WDT; use crate::peripherals::LPWR as LP_TIMER; @@ -194,28 +190,35 @@ bitflags::bitflags! { } } -#[cfg(not(any(esp32c6, esp32h2)))] -#[allow(unused)] #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] #[cfg_attr(feature = "defmt", derive(defmt::Format))] #[allow(clippy::enum_variant_names)] // FIXME: resolve this -/// RTC SLOW_CLK frequency values +/// RTC FAST_CLK frequency values pub(crate) enum RtcFastClock { /// Main XTAL, divided by 4 - RtcFastClockXtalD4 = 0, + #[cfg(not(any(esp32c6, esp32h2)))] + #[expect(unused)] + RtcFastClockXtalD4, + + /// Select XTAL_D2_CLK as RTC_FAST_CLK source + #[cfg(any(esp32c6, esp32h2))] + #[expect(unused)] + RtcFastClockXtalD2, + /// Internal fast RC oscillator - RtcFastClock8m = 1, + RtcFastClockRcFast, } -#[cfg(not(any(esp32c6, esp32h2)))] impl Clock for RtcFastClock { fn frequency(&self) -> Rate { match self { + #[cfg(not(any(esp32c6, esp32h2)))] RtcFastClock::RtcFastClockXtalD4 => Rate::from_hz(40_000_000 / 4), - #[cfg(any(esp32, esp32s2))] - RtcFastClock::RtcFastClock8m => Rate::from_hz(8_500_000), - #[cfg(any(esp32c2, esp32c3, esp32c6, esp32h2, esp32s3))] - RtcFastClock::RtcFastClock8m => Rate::from_hz(17_500_000), + + #[cfg(any(esp32c6, esp32h2))] + RtcFastClock::RtcFastClockXtalD2 => Rate::from_hz(property!("soc.xtal_frequency") / 2), + + RtcFastClock::RtcFastClockRcFast => Rate::from_hz(property!("soc.rc_fast_clk_default")), } } } @@ -228,28 +231,44 @@ impl Clock for RtcFastClock { /// RTC SLOW_CLK frequency values pub enum RtcSlowClock { /// Internal slow RC oscillator - RtcSlowClockRtc = 0, + RtcSlowClockRcSlow = 0, /// External 32 KHz XTAL RtcSlowClock32kXtal = 1, /// Internal fast RC oscillator, divided by 256 RtcSlowClock8mD256 = 2, } -#[cfg(not(any(esp32c6, esp32h2)))] +/// RTC SLOW_CLK frequency values +#[allow(clippy::enum_variant_names)] +#[derive(Debug, Clone, Copy)] +#[non_exhaustive] +#[cfg(any(esp32c6, esp32h2))] +pub enum RtcSlowClock { + /// Select RC_SLOW_CLK as RTC_SLOW_CLK source + RtcSlowClockRcSlow = 0, + /// Select XTAL32K_CLK as RTC_SLOW_CLK source + RtcSlowClock32kXtal = 1, + /// Select RC32K_CLK as RTC_SLOW_CLK source + RtcSlowClock32kRc = 2, + /// Select OSC_SLOW_CLK (external slow clock) as RTC_SLOW_CLK source + RtcSlowOscSlow = 3, +} + impl Clock for RtcSlowClock { fn frequency(&self) -> Rate { match self { - #[cfg(esp32)] - RtcSlowClock::RtcSlowClockRtc => Rate::from_hz(150_000), - #[cfg(esp32s2)] - RtcSlowClock::RtcSlowClockRtc => Rate::from_hz(90_000), - #[cfg(any(esp32c2, esp32c3, esp32s3))] - RtcSlowClock::RtcSlowClockRtc => Rate::from_hz(136_000), + RtcSlowClock::RtcSlowClockRcSlow => Rate::from_hz(property!("soc.rc_slow_clock")), + RtcSlowClock::RtcSlowClock32kXtal => Rate::from_hz(32_768), - #[cfg(any(esp32, esp32s2))] - RtcSlowClock::RtcSlowClock8mD256 => Rate::from_hz(8_500_000 / 256), - #[cfg(any(esp32c2, esp32c3, esp32s3))] - RtcSlowClock::RtcSlowClock8mD256 => Rate::from_hz(17_500_000 / 256), + + #[cfg(not(any(esp32c6, esp32h2)))] + RtcSlowClock::RtcSlowClock8mD256 => RtcFastClock::RtcFastClockRcFast.frequency() / 256, + + #[cfg(any(esp32c6, esp32h2))] + RtcSlowClock::RtcSlowClock32kRc => Rate::from_hz(32_768), + + #[cfg(any(esp32c6, esp32h2))] + RtcSlowClock::RtcSlowOscSlow => Rate::from_hz(32_768), } } } @@ -272,6 +291,25 @@ pub(crate) enum RtcCalSel { RtcCalInternalOsc = 3, } +#[derive(Debug, Clone, Copy, PartialEq)] +#[cfg(any(esp32c6, esp32h2))] +/// Clock source to be calibrated using rtc_clk_cal function +pub(crate) enum RtcCalSel { + /// Currently selected RTC SLOW_CLK + RtcCalRtcMux = -1, + /// Internal 150kHz RC oscillator + RtcCalRcSlow = 0, + /// External 32kHz XTAL, as one type of 32k clock + RtcCal32kXtal = 1, + /// Internal 32kHz RC oscillator, as one type of 32k clock + RtcCal32kRc = 2, + /// External slow clock signal input by lp_pad_gpio0, as one type of 32k + /// clock + RtcCal32kOscSlow = 3, + /// Internal MHz-range RC oscillator + RtcCalRcFast, +} + /// Low-power Management pub struct Rtc<'d> { _inner: crate::peripherals::LPWR<'d>, @@ -537,7 +575,8 @@ impl crate::interrupt::InterruptConfigurable for Rtc<'_> { } } -/// RTC Watchdog Timer. +/// Clocks. +// TODO: this type belongs in `esp_hal::clock`. pub struct RtcClock; /// RTC Watchdog Timer driver. @@ -588,7 +627,7 @@ impl RtcClock { #[cfg(not(any(esp32c6, esp32h2)))] pub fn slow_freq() -> RtcSlowClock { match LPWR::regs().clk_conf().read().ana_clk_rtc_sel().bits() { - 0 => RtcSlowClock::RtcSlowClockRtc, + 0 => RtcSlowClock::RtcSlowClockRcSlow, 1 => RtcSlowClock::RtcSlowClock32kXtal, 2 => RtcSlowClock::RtcSlowClock8mD256, _ => unreachable!(), @@ -623,7 +662,7 @@ impl RtcClock { fn set_fast_freq(fast_freq: RtcFastClock) { LPWR::regs().clk_conf().modify(|_, w| { w.fast_clk_rtc_sel().bit(match fast_freq { - RtcFastClock::RtcFastClock8m => true, + RtcFastClock::RtcFastClockRcFast => true, RtcFastClock::RtcFastClockXtalD4 => false, }) }); @@ -631,6 +670,56 @@ impl RtcClock { crate::rom::ets_delay_us(3u32); } + // TODO: IDF-5781 Some of esp32c6 SOC_RTC_FAST_CLK_SRC_XTAL_D2 rtc_fast clock + // has timing issue. Force to use SOC_RTC_FAST_CLK_SRC_RC_FAST since 2nd + // stage bootloader https://github.com/espressif/esp-idf/blob/master/components/bootloader_support/src/bootloader_clock_init.c#L65-L67 + #[cfg(any(esp32h2, esp32c6))] + fn set_fast_freq(fast_freq: RtcFastClock) { + #[cfg(esp32h2)] + LPWR::regs().lp_clk_conf().modify(|_, w| unsafe { + w.fast_clk_sel().bits(match fast_freq { + RtcFastClock::RtcFastClockRcFast => 0b00, + RtcFastClock::RtcFastClockXtalD2 => 0b01, + }) + }); + + #[cfg(esp32c6)] + LPWR::regs().lp_clk_conf().modify(|_, w| { + w.fast_clk_sel().bit(match fast_freq { + RtcFastClock::RtcFastClockRcFast => false, + RtcFastClock::RtcFastClockXtalD2 => true, + }) + }); + + crate::rom::ets_delay_us(3); + } + + #[cfg(any(esp32h2, esp32c6))] + fn set_slow_freq(slow_freq: RtcSlowClock) { + LPWR::regs() + .lp_clk_conf() + .modify(|_, w| unsafe { w.slow_clk_sel().bits(slow_freq as u8) }); + + LPWR::regs().clk_to_hp().modify(|_, w| { + w.icg_hp_xtal32k() + .bit(matches!(slow_freq, RtcSlowClock::RtcSlowClock32kXtal)); + w.icg_hp_osc32k() + .bit(matches!(slow_freq, RtcSlowClock::RtcSlowClock32kRc)) + }); + } + + /// Get the RTC_SLOW_CLK source + #[cfg(any(esp32h2, esp32c6))] + pub fn slow_freq() -> RtcSlowClock { + match LPWR::regs().lp_clk_conf().read().slow_clk_sel().bits() { + 0 => RtcSlowClock::RtcSlowClockRcSlow, + 1 => RtcSlowClock::RtcSlowClock32kXtal, + 2 => RtcSlowClock::RtcSlowClock32kRc, + 3 => RtcSlowClock::RtcSlowOscSlow, + _ => unreachable!(), + } + } + /// Calibration of RTC_SLOW_CLK is performed using a special feature of /// TIMG0. This feature counts the number of XTAL clock cycles within a /// given number of RTC_SLOW_CLK cycles. @@ -719,7 +808,7 @@ impl RtcClock { timg0.rtccalicfg2().modify(|_, w| unsafe { w.rtc_cali_timeout_thres().bits(slowclk_cycles << 10) }); - RtcSlowClock::RtcSlowClockRtc + RtcSlowClock::RtcSlowClockRcSlow } }; @@ -768,6 +857,290 @@ impl RtcClock { cal_val } + /// Calibration of RTC_SLOW_CLK is performed using a special feature of + /// TIMG0. This feature counts the number of XTAL clock cycles within a + /// given number of RTC_SLOW_CLK cycles. + #[cfg(any(esp32c6, esp32h2))] + pub(crate) fn calibrate_internal(mut cal_clk: RtcCalSel, slowclk_cycles: u32) -> u32 { + use crate::peripherals::{LP_CLKRST, PCR, PMU}; + + #[derive(Clone, Copy)] + enum RtcCaliClkSel { + CaliClkRcSlow = 0, + CaliClkRcFast = 1, + CaliClk32k = 2, + } + + if cal_clk == RtcCalSel::RtcCalRtcMux { + cal_clk = match cal_clk { + RtcCalSel::RtcCalRtcMux => match RtcClock::slow_freq() { + RtcSlowClock::RtcSlowClock32kXtal => RtcCalSel::RtcCal32kXtal, + RtcSlowClock::RtcSlowClock32kRc => RtcCalSel::RtcCal32kRc, + _ => cal_clk, + }, + RtcCalSel::RtcCal32kOscSlow => RtcCalSel::RtcCalRtcMux, + _ => cal_clk, + }; + } + + let clk_src = RtcClock::slow_freq(); + + if cal_clk == RtcCalSel::RtcCalRtcMux { + cal_clk = match clk_src { + RtcSlowClock::RtcSlowClockRcSlow => RtcCalSel::RtcCalRcSlow, + RtcSlowClock::RtcSlowClock32kXtal => RtcCalSel::RtcCal32kXtal, + RtcSlowClock::RtcSlowClock32kRc => RtcCalSel::RtcCal32kRc, + RtcSlowClock::RtcSlowOscSlow => RtcCalSel::RtcCal32kOscSlow, + }; + } + + let cali_clk_sel; + if cal_clk == RtcCalSel::RtcCalRtcMux { + cal_clk = match clk_src { + RtcSlowClock::RtcSlowClockRcSlow => RtcCalSel::RtcCalRcSlow, + RtcSlowClock::RtcSlowClock32kXtal => RtcCalSel::RtcCal32kXtal, + RtcSlowClock::RtcSlowClock32kRc => RtcCalSel::RtcCal32kRc, + RtcSlowClock::RtcSlowOscSlow => RtcCalSel::RtcCalRcSlow, + } + } + + if cal_clk == RtcCalSel::RtcCalRcFast { + cali_clk_sel = RtcCaliClkSel::CaliClkRcFast; + } else if cal_clk == RtcCalSel::RtcCalRcSlow { + cali_clk_sel = RtcCaliClkSel::CaliClkRcSlow; + } else { + cali_clk_sel = RtcCaliClkSel::CaliClk32k; + + match cal_clk { + RtcCalSel::RtcCalRtcMux | RtcCalSel::RtcCalRcSlow | RtcCalSel::RtcCalRcFast => {} + RtcCalSel::RtcCal32kRc => { + PCR::regs() + .ctrl_32k_conf() + .modify(|_, w| unsafe { w.clk_32k_sel().bits(0) }); + } + RtcCalSel::RtcCal32kXtal => { + PCR::regs() + .ctrl_32k_conf() + .modify(|_, w| unsafe { w.clk_32k_sel().bits(1) }); + } + RtcCalSel::RtcCal32kOscSlow => { + PCR::regs() + .ctrl_32k_conf() + .modify(|_, w| unsafe { w.clk_32k_sel().bits(2) }); + } + } + } + + // Enable requested clock (150k is always on) + // Some delay is required before the time is stable + // Only enable if originaly was disabled + // If clock is already on, do nothing + + let dig_32k_xtal_enabled = LP_CLKRST::regs() + .clk_to_hp() + .read() + .icg_hp_xtal32k() + .bit_is_set(); + + if cal_clk == RtcCalSel::RtcCal32kXtal && !dig_32k_xtal_enabled { + LP_CLKRST::regs() + .clk_to_hp() + .modify(|_, w| w.icg_hp_xtal32k().set_bit()); + } + + // TODO: very hacky - icg_hp_xtal32k is already set in the above condition? + // in ESP-IDF these are not called in this function but the fields are set + LP_CLKRST::regs() + .clk_to_hp() + .modify(|_, w| w.icg_hp_xtal32k().set_bit()); + PMU::regs().hp_sleep_lp_ck_power().modify(|_, w| { + w.hp_sleep_xpd_xtal32k().set_bit(); + w.hp_sleep_xpd_rc32k().set_bit() + }); + + let rc_fast_enabled = PMU::regs() + .hp_sleep_lp_ck_power() + .read() + .hp_sleep_xpd_fosc_clk() + .bit_is_set(); + let dig_rc_fast_enabled = LP_CLKRST::regs() + .clk_to_hp() + .read() + .icg_hp_fosc() + .bit_is_set(); + + if cal_clk == RtcCalSel::RtcCalRcFast { + if !rc_fast_enabled { + PMU::regs() + .hp_sleep_lp_ck_power() + .modify(|_, w| w.hp_sleep_xpd_fosc_clk().set_bit()); + crate::rom::ets_delay_us(50); + } + + if !dig_rc_fast_enabled { + LP_CLKRST::regs() + .clk_to_hp() + .modify(|_, w| w.icg_hp_fosc().set_bit()); + crate::rom::ets_delay_us(5); + } + } + + let rc32k_enabled = PMU::regs() + .hp_sleep_lp_ck_power() + .read() + .hp_sleep_xpd_rc32k() + .bit_is_set(); + let dig_rc32k_enabled = LP_CLKRST::regs() + .clk_to_hp() + .read() + .icg_hp_osc32k() + .bit_is_set(); + + if cal_clk == RtcCalSel::RtcCal32kRc { + if !rc32k_enabled { + PMU::regs() + .hp_sleep_lp_ck_power() + .modify(|_, w| w.hp_sleep_xpd_rc32k().set_bit()); + crate::rom::ets_delay_us(300); + } + + if !dig_rc32k_enabled { + LP_CLKRST::regs() + .clk_to_hp() + .modify(|_, w| w.icg_hp_osc32k().set_bit()); + } + } + + // Check if there is already running calibration process + // TODO: &mut TIMG0 for calibration + let timg0 = TIMG0::regs(); + + if timg0 + .rtccalicfg() + .read() + .rtc_cali_start_cycling() + .bit_is_set() + { + timg0 + .rtccalicfg2() + .modify(|_, w| unsafe { w.rtc_cali_timeout_thres().bits(1) }); + + // Set small timeout threshold to accelerate the generation of timeot + // Internal circuit will be reset when timeout occurs and will not affect the + // next calibration + while !timg0.rtccalicfg().read().rtc_cali_rdy().bit_is_set() + && !timg0.rtccalicfg2().read().rtc_cali_timeout().bit_is_set() + {} + } + + // Prepare calibration + timg0 + .rtccalicfg() + .modify(|_, w| unsafe { w.rtc_cali_clk_sel().bits(cali_clk_sel as u8) }); + timg0 + .rtccalicfg() + .modify(|_, w| w.rtc_cali_start_cycling().clear_bit()); + timg0 + .rtccalicfg() + .modify(|_, w| unsafe { w.rtc_cali_max().bits(slowclk_cycles as u16) }); + + let expected_frequency = match cali_clk_sel { + RtcCaliClkSel::CaliClk32k => { + timg0.rtccalicfg2().modify(|_, w| unsafe { + w.rtc_cali_timeout_thres().bits(slowclk_cycles << 12) + }); + RtcSlowClock::RtcSlowClock32kXtal.frequency() + } + RtcCaliClkSel::CaliClkRcFast => { + timg0 + .rtccalicfg2() + .modify(|_, w| unsafe { w.rtc_cali_timeout_thres().bits(0x01FFFFFF) }); + RtcFastClock::RtcFastClockRcFast.frequency() + } + RtcCaliClkSel::CaliClkRcSlow => { + timg0.rtccalicfg2().modify(|_, w| unsafe { + w.rtc_cali_timeout_thres().bits(slowclk_cycles << 10) + }); + RtcSlowClock::RtcSlowClockRcSlow.frequency() + } + }; + + let us_time_estimate = Rate::from_mhz(slowclk_cycles) / expected_frequency; + + // Start calibration + timg0 + .rtccalicfg() + .modify(|_, w| w.rtc_cali_start().clear_bit()); + timg0 + .rtccalicfg() + .modify(|_, w| w.rtc_cali_start().set_bit()); + + // Wait for calibration to finish up to another us_time_estimate + crate::rom::ets_delay_us(us_time_estimate); + + let cal_val = loop { + if timg0.rtccalicfg().read().rtc_cali_rdy().bit_is_set() { + // The Fosc CLK of calibration circuit is divided by 32 for ECO1. + // So we need to multiply the frequency of the Fosc for ECO1 and above chips by + // 32 times. And ensure that this modification will not affect + // ECO0. + // https://github.com/espressif/esp-idf/commit/e3148369f32fdc6de62c35a67f7adb6f4faef4e3 + #[cfg(esp32c6)] + if Efuse::chip_revision() > 0 && cal_clk == RtcCalSel::RtcCalRcFast { + break timg0.rtccalicfg1().read().rtc_cali_value().bits() >> 5; + } + break timg0.rtccalicfg1().read().rtc_cali_value().bits(); + } + + if timg0.rtccalicfg2().read().rtc_cali_timeout().bit_is_set() { + // Timed out waiting for calibration + break 0; + } + }; + + timg0 + .rtccalicfg() + .modify(|_, w| w.rtc_cali_start().clear_bit()); + + if cal_clk == RtcCalSel::RtcCal32kXtal && !dig_32k_xtal_enabled { + LP_CLKRST::regs() + .clk_to_hp() + .modify(|_, w| w.icg_hp_xtal32k().clear_bit()); + } + + if cal_clk == RtcCalSel::RtcCalRcFast { + if rc_fast_enabled { + PMU::regs() + .hp_sleep_lp_ck_power() + .modify(|_, w| w.hp_sleep_xpd_fosc_clk().set_bit()); + crate::rom::ets_delay_us(50); + } + + if dig_rc_fast_enabled { + LP_CLKRST::regs() + .clk_to_hp() + .modify(|_, w| w.icg_hp_fosc().set_bit()); + crate::rom::ets_delay_us(5); + } + } + + if cal_clk == RtcCalSel::RtcCal32kRc { + if rc32k_enabled { + PMU::regs() + .hp_sleep_lp_ck_power() + .modify(|_, w| w.hp_sleep_xpd_rc32k().set_bit()); + crate::rom::ets_delay_us(300); + } + if dig_rc32k_enabled { + LP_CLKRST::regs() + .clk_to_hp() + .modify(|_, w| w.icg_hp_osc32k().set_bit()); + } + } + + cal_val + } + /// Measure RTC slow clock's period, based on main XTAL frequency /// /// This function will time out and return 0 if the time for the given @@ -808,7 +1181,7 @@ impl RtcClock { }; } else { let calibration_clock = match RtcClock::slow_freq() { - RtcSlowClock::RtcSlowClockRtc => RtcCalSel::RtcCalRtcMux, + RtcSlowClock::RtcSlowClockRcSlow => RtcCalSel::RtcCalRtcMux, RtcSlowClock::RtcSlowClock32kXtal => RtcCalSel::RtcCal32kXtal, RtcSlowClock::RtcSlowClock8mD256 => RtcCalSel::RtcCal8mD256, }; @@ -829,13 +1202,7 @@ impl RtcClock { // TODO: this could reuse Self::calibrate_internal const SLOW_CLOCK_CYCLES: u32 = 100; - cfg_if::cfg_if! { - if #[cfg(any(esp32h2, esp32c6))] { - let calibration_clock = rtc::RtcSlowClock::RtcSlowClockRcSlow; - } else { - let calibration_clock = RtcSlowClock::RtcSlowClockRtc; - } - } + let calibration_clock = RtcSlowClock::RtcSlowClockRcSlow; // Make sure the process doesn't time out due to some spooky configuration. #[cfg(not(esp32))] diff --git a/esp-hal/src/rtc_cntl/rtc/esp32.rs b/esp-hal/src/rtc_cntl/rtc/esp32.rs index 3161e0e6d..b9dc75dad 100644 --- a/esp-hal/src/rtc_cntl/rtc/esp32.rs +++ b/esp-hal/src/rtc_cntl/rtc/esp32.rs @@ -8,10 +8,10 @@ use crate::{ pub(crate) fn init() {} pub(crate) fn configure_clock() { - RtcClock::set_fast_freq(RtcFastClock::RtcFastClock8m); + RtcClock::set_fast_freq(RtcFastClock::RtcFastClockRcFast); let cal_val = loop { - RtcClock::set_slow_freq(RtcSlowClock::RtcSlowClockRtc); + RtcClock::set_slow_freq(RtcSlowClock::RtcSlowClockRcSlow); let res = RtcClock::calibrate(RtcCalSel::RtcCalRtcMux, 1024); if res != 0 { diff --git a/esp-hal/src/rtc_cntl/rtc/esp32c2.rs b/esp-hal/src/rtc_cntl/rtc/esp32c2.rs index 778131bb9..9034b88e6 100644 --- a/esp-hal/src/rtc_cntl/rtc/esp32c2.rs +++ b/esp-hal/src/rtc_cntl/rtc/esp32c2.rs @@ -47,10 +47,10 @@ pub(crate) fn configure_clock() { // esp_rom_delay_us(SOC_DELAY_RC_FAST_ENABLE); crate::rom::ets_delay_us(50); } - RtcClock::set_fast_freq(RtcFastClock::RtcFastClock8m); + RtcClock::set_fast_freq(RtcFastClock::RtcFastClockRcFast); let cal_val = loop { - RtcClock::set_slow_freq(RtcSlowClock::RtcSlowClockRtc); + RtcClock::set_slow_freq(RtcSlowClock::RtcSlowClockRcSlow); let res = RtcClock::calibrate(RtcCalSel::RtcCalRtcMux, 1024); if res != 0 { diff --git a/esp-hal/src/rtc_cntl/rtc/esp32c3.rs b/esp-hal/src/rtc_cntl/rtc/esp32c3.rs index 20707f36b..89d69fdca 100644 --- a/esp-hal/src/rtc_cntl/rtc/esp32c3.rs +++ b/esp-hal/src/rtc_cntl/rtc/esp32c3.rs @@ -65,10 +65,10 @@ pub(crate) fn configure_clock() { // esp_rom_delay_us(SOC_DELAY_RC_FAST_ENABLE); crate::rom::ets_delay_us(50); } - RtcClock::set_fast_freq(RtcFastClock::RtcFastClock8m); + RtcClock::set_fast_freq(RtcFastClock::RtcFastClockRcFast); let cal_val = loop { - RtcClock::set_slow_freq(RtcSlowClock::RtcSlowClockRtc); + RtcClock::set_slow_freq(RtcSlowClock::RtcSlowClockRcSlow); let res = RtcClock::calibrate(RtcCalSel::RtcCalRtcMux, 1024); if res != 0 { diff --git a/esp-hal/src/rtc_cntl/rtc/esp32c6.rs b/esp-hal/src/rtc_cntl/rtc/esp32c6.rs index 521bb7375..a3ec2b96a 100644 --- a/esp-hal/src/rtc_cntl/rtc/esp32c6.rs +++ b/esp-hal/src/rtc_cntl/rtc/esp32c6.rs @@ -17,11 +17,9 @@ use crate::{ esp32c6_rtc_update_to_xtal_raw, }, }, - efuse::Efuse, - peripherals::{LP_AON, LP_CLKRST, MODEM_LPCON, MODEM_SYSCON, PCR, PMU, TIMG0}, - rtc_cntl::RtcClock, + peripherals::{LP_AON, LP_CLKRST, MODEM_LPCON, MODEM_SYSCON, PCR, PMU}, + rtc_cntl::{RtcCalSel, RtcClock, RtcFastClock, RtcSlowClock}, soc::regi2c, - time::Rate, }; fn pmu_power_domain_force_default() { @@ -1186,398 +1184,6 @@ pub enum SocResetReason { Cpu0JtagCpu = 0x18, } -#[allow(unused)] -#[derive(Debug, Clone, Copy)] -/// RTC SLOW_CLK frequency values -pub(crate) enum RtcFastClock { - /// Select RC_FAST_CLK as RTC_FAST_CLK source - RtcFastClockRcFast = 0, - /// Select XTAL_D2_CLK as RTC_FAST_CLK source - RtcFastClockXtalD2 = 1, -} - -impl Clock for RtcFastClock { - fn frequency(&self) -> Rate { - match self { - RtcFastClock::RtcFastClockXtalD2 => { - // TODO: Is the value correct? - Rate::from_hz(40_000_000 / 2) - } - RtcFastClock::RtcFastClockRcFast => Rate::from_hz(property!("soc.rc_fast_clk_default")), - } - } -} - -#[allow(clippy::enum_variant_names)] -#[derive(Debug, Clone, Copy, PartialEq)] -/// RTC SLOW_CLK frequency values -pub enum RtcSlowClock { - /// Select RC_SLOW_CLK as RTC_SLOW_CLK source - RtcSlowClockRcSlow = 0, - /// Select XTAL32K_CLK as RTC_SLOW_CLK source - RtcSlowClock32kXtal = 1, - /// Select RC32K_CLK as RTC_SLOW_CLK source - RtcSlowClock32kRc = 2, - /// Select OSC_SLOW_CLK (external slow clock) as RTC_SLOW_CLK source - RtcSlowOscSlow = 3, -} - -impl Clock for RtcSlowClock { - fn frequency(&self) -> Rate { - match self { - RtcSlowClock::RtcSlowClockRcSlow => Rate::from_hz(136_000), - RtcSlowClock::RtcSlowClock32kXtal => Rate::from_hz(32_768), - RtcSlowClock::RtcSlowClock32kRc => Rate::from_hz(32_768), - RtcSlowClock::RtcSlowOscSlow => Rate::from_hz(32_768), - } - } -} - -#[derive(Debug, Clone, Copy, PartialEq)] -/// Clock source to be calibrated using rtc_clk_cal function -pub(crate) enum RtcCalSel { - /// Currently selected RTC SLOW_CLK - RtcCalRtcMux = -1, - /// Internal 150kHz RC oscillator - RtcCalRcSlow = 0, - /// External 32kHz XTAL, as one type of 32k clock - RtcCal32kXtal = 1, - /// Internal 32kHz RC oscillator, as one type of 32k clock - RtcCal32kRc = 2, - /// External slow clock signal input by lp_pad_gpio0, as one type of 32k - /// clock - RtcCal32kOscSlow = 3, - /// Internal 20MHz RC oscillator - RtcCalRcFast, -} - -#[derive(Clone)] -pub(crate) enum RtcCaliClkSel { - CaliClkRcSlow = 0, - CaliClkRcFast = 1, - CaliClk32k = 2, -} - -/// RTC Watchdog Timer driver -impl RtcClock { - /// Get the RTC_SLOW_CLK source - pub fn slow_freq() -> RtcSlowClock { - match LP_CLKRST::regs().lp_clk_conf().read().slow_clk_sel().bits() { - 0 => RtcSlowClock::RtcSlowClockRcSlow, - 1 => RtcSlowClock::RtcSlowClock32kXtal, - 2 => RtcSlowClock::RtcSlowClock32kRc, - 3 => RtcSlowClock::RtcSlowOscSlow, - _ => unreachable!(), - } - } - - fn set_slow_freq(slow_freq: RtcSlowClock) { - unsafe { - LP_CLKRST::regs() - .lp_clk_conf() - .modify(|_, w| w.slow_clk_sel().bits(slow_freq as u8)); - } - - LP_CLKRST::regs().clk_to_hp().modify(|_, w| { - w.icg_hp_xtal32k() - .bit(matches!(slow_freq, RtcSlowClock::RtcSlowClock32kXtal)); - w.icg_hp_osc32k() - .bit(matches!(slow_freq, RtcSlowClock::RtcSlowClock32kRc)) - }); - } - - // TODO: IDF-5781 Some of esp32c6 SOC_RTC_FAST_CLK_SRC_XTAL_D2 rtc_fast clock - // has timing issue Force to use SOC_RTC_FAST_CLK_SRC_RC_FAST since 2nd - // stage bootloader https://github.com/espressif/esp-idf/blob/master/components/bootloader_support/src/bootloader_clock_init.c#L65-L67 - fn set_fast_freq(fast_freq: RtcFastClock) { - LP_CLKRST::regs().lp_clk_conf().modify(|_, w| { - w.fast_clk_sel().bit(match fast_freq { - RtcFastClock::RtcFastClockRcFast => false, - RtcFastClock::RtcFastClockXtalD2 => true, - }) - }); - - crate::rom::ets_delay_us(3); - } - - /// Calibration of RTC_SLOW_CLK is performed using a special feature of - /// TIMG0. This feature counts the number of XTAL clock cycles within a - /// given number of RTC_SLOW_CLK cycles. - pub(crate) fn calibrate_internal(mut cal_clk: RtcCalSel, slowclk_cycles: u32) -> u32 { - const SOC_CLK_RC_FAST_FREQ_APPROX: u32 = 17_500_000; - const SOC_CLK_RC_SLOW_FREQ_APPROX: u32 = 136_000; - const SOC_CLK_XTAL32K_FREQ_APPROX: u32 = 32768; - - if cal_clk == RtcCalSel::RtcCalRtcMux { - cal_clk = match cal_clk { - RtcCalSel::RtcCalRtcMux => match RtcClock::slow_freq() { - RtcSlowClock::RtcSlowClock32kXtal => RtcCalSel::RtcCal32kXtal, - RtcSlowClock::RtcSlowClock32kRc => RtcCalSel::RtcCal32kRc, - _ => cal_clk, - }, - RtcCalSel::RtcCal32kOscSlow => RtcCalSel::RtcCalRtcMux, - _ => cal_clk, - }; - } - - let clk_src = RtcClock::slow_freq(); - - if cal_clk == RtcCalSel::RtcCalRtcMux { - cal_clk = match clk_src { - RtcSlowClock::RtcSlowClockRcSlow => RtcCalSel::RtcCalRcSlow, - RtcSlowClock::RtcSlowClock32kXtal => RtcCalSel::RtcCal32kXtal, - RtcSlowClock::RtcSlowClock32kRc => RtcCalSel::RtcCal32kRc, - RtcSlowClock::RtcSlowOscSlow => RtcCalSel::RtcCal32kOscSlow, - }; - } - - let cali_clk_sel; - if cal_clk == RtcCalSel::RtcCalRtcMux { - cal_clk = match clk_src { - RtcSlowClock::RtcSlowClockRcSlow => RtcCalSel::RtcCalRcSlow, - RtcSlowClock::RtcSlowClock32kXtal => RtcCalSel::RtcCal32kXtal, - RtcSlowClock::RtcSlowClock32kRc => RtcCalSel::RtcCal32kRc, - RtcSlowClock::RtcSlowOscSlow => RtcCalSel::RtcCalRcSlow, - } - } - - if cal_clk == RtcCalSel::RtcCalRcFast { - cali_clk_sel = RtcCaliClkSel::CaliClkRcFast; - } else if cal_clk == RtcCalSel::RtcCalRcSlow { - cali_clk_sel = RtcCaliClkSel::CaliClkRcSlow; - } else { - cali_clk_sel = RtcCaliClkSel::CaliClk32k; - - match cal_clk { - RtcCalSel::RtcCalRtcMux | RtcCalSel::RtcCalRcSlow | RtcCalSel::RtcCalRcFast => {} - RtcCalSel::RtcCal32kRc => { - PCR::regs() - .ctrl_32k_conf() - .modify(|_, w| unsafe { w.clk_32k_sel().bits(0) }); - } - RtcCalSel::RtcCal32kXtal => { - PCR::regs() - .ctrl_32k_conf() - .modify(|_, w| unsafe { w.clk_32k_sel().bits(1) }); - } - RtcCalSel::RtcCal32kOscSlow => { - PCR::regs() - .ctrl_32k_conf() - .modify(|_, w| unsafe { w.clk_32k_sel().bits(2) }); - } - } - } - - // Enable requested clock (150k is always on) - // Some delay is required before the time is stable - // Only enable if originaly was disabled - // If clock is already on, do nothing - - let dig_32k_xtal_enabled = LP_CLKRST::regs() - .clk_to_hp() - .read() - .icg_hp_xtal32k() - .bit_is_set(); - - if cal_clk == RtcCalSel::RtcCal32kXtal && !dig_32k_xtal_enabled { - LP_CLKRST::regs() - .clk_to_hp() - .modify(|_, w| w.icg_hp_xtal32k().set_bit()); - } - - // TODO: very hacky - icg_hp_xtal32k is already set in the above condition? - // in ESP-IDF these are not called in this function but the fields are set - LP_CLKRST::regs() - .clk_to_hp() - .modify(|_, w| w.icg_hp_xtal32k().set_bit()); - PMU::regs().hp_sleep_lp_ck_power().modify(|_, w| { - w.hp_sleep_xpd_xtal32k().set_bit(); - w.hp_sleep_xpd_rc32k().set_bit() - }); - - let rc_fast_enabled = PMU::regs() - .hp_sleep_lp_ck_power() - .read() - .hp_sleep_xpd_fosc_clk() - .bit_is_set(); - let dig_rc_fast_enabled = LP_CLKRST::regs() - .clk_to_hp() - .read() - .icg_hp_fosc() - .bit_is_set(); - - if cal_clk == RtcCalSel::RtcCalRcFast { - if !rc_fast_enabled { - PMU::regs() - .hp_sleep_lp_ck_power() - .modify(|_, w| w.hp_sleep_xpd_fosc_clk().set_bit()); - crate::rom::ets_delay_us(50); - } - - if !dig_rc_fast_enabled { - LP_CLKRST::regs() - .clk_to_hp() - .modify(|_, w| w.icg_hp_fosc().set_bit()); - crate::rom::ets_delay_us(5); - } - } - - let rc32k_enabled = PMU::regs() - .hp_sleep_lp_ck_power() - .read() - .hp_sleep_xpd_rc32k() - .bit_is_set(); - let dig_rc32k_enabled = LP_CLKRST::regs() - .clk_to_hp() - .read() - .icg_hp_osc32k() - .bit_is_set(); - - if cal_clk == RtcCalSel::RtcCal32kRc { - if !rc32k_enabled { - PMU::regs() - .hp_sleep_lp_ck_power() - .modify(|_, w| w.hp_sleep_xpd_rc32k().set_bit()); - crate::rom::ets_delay_us(300); - } - - if !dig_rc32k_enabled { - LP_CLKRST::regs() - .clk_to_hp() - .modify(|_, w| w.icg_hp_osc32k().set_bit()); - } - } - - // Check if there is already running calibration process - // TODO: &mut TIMG0 for calibration - let timg0 = TIMG0::regs(); - - if timg0 - .rtccalicfg() - .read() - .rtc_cali_start_cycling() - .bit_is_set() - { - timg0 - .rtccalicfg2() - .modify(|_, w| unsafe { w.rtc_cali_timeout_thres().bits(1) }); - - // Set small timeout threshold to accelerate the generation of timeot - // Internal circuit will be reset when timeout occurs and will not affect the - // next calibration - while !timg0.rtccalicfg().read().rtc_cali_rdy().bit_is_set() - && !timg0.rtccalicfg2().read().rtc_cali_timeout().bit_is_set() - {} - } - - // Prepare calibration - timg0 - .rtccalicfg() - .modify(|_, w| unsafe { w.rtc_cali_clk_sel().bits(cali_clk_sel.clone() as u8) }); - timg0 - .rtccalicfg() - .modify(|_, w| w.rtc_cali_start_cycling().clear_bit()); - timg0 - .rtccalicfg() - .modify(|_, w| unsafe { w.rtc_cali_max().bits(slowclk_cycles as u16) }); - - let expected_freq = match cali_clk_sel { - RtcCaliClkSel::CaliClk32k => { - timg0.rtccalicfg2().modify(|_, w| unsafe { - w.rtc_cali_timeout_thres().bits(slowclk_cycles << 12) - }); - SOC_CLK_XTAL32K_FREQ_APPROX - } - RtcCaliClkSel::CaliClkRcFast => { - timg0 - .rtccalicfg2() - .modify(|_, w| unsafe { w.rtc_cali_timeout_thres().bits(0x01FFFFFF) }); - SOC_CLK_RC_FAST_FREQ_APPROX - } - _ => { - timg0.rtccalicfg2().modify(|_, w| unsafe { - w.rtc_cali_timeout_thres().bits(slowclk_cycles << 10) - }); - SOC_CLK_RC_SLOW_FREQ_APPROX - } - }; - - let us_time_estimate = (Rate::from_mhz(slowclk_cycles) / expected_freq).as_hz(); - - // Start calibration - timg0 - .rtccalicfg() - .modify(|_, w| w.rtc_cali_start().clear_bit()); - timg0 - .rtccalicfg() - .modify(|_, w| w.rtc_cali_start().set_bit()); - - // Wait for calibration to finish up to another us_time_estimate - crate::rom::ets_delay_us(us_time_estimate); - - let cal_val = loop { - if timg0.rtccalicfg().read().rtc_cali_rdy().bit_is_set() { - // The Fosc CLK of calibration circuit is divided by 32 for ECO1. - // So we need to multiply the frequency of the Fosc for ECO1 and above chips by - // 32 times. And ensure that this modification will not affect - // ECO0. - // https://github.com/espressif/esp-idf/commit/e3148369f32fdc6de62c35a67f7adb6f4faef4e3 - if Efuse::chip_revision() > 0 && cal_clk == RtcCalSel::RtcCalRcFast { - break timg0.rtccalicfg1().read().rtc_cali_value().bits() >> 5; - } - break timg0.rtccalicfg1().read().rtc_cali_value().bits(); - } - - if timg0.rtccalicfg2().read().rtc_cali_timeout().bit_is_set() { - // Timed out waiting for calibration - break 0; - } - }; - - timg0 - .rtccalicfg() - .modify(|_, w| w.rtc_cali_start().clear_bit()); - - if cal_clk == RtcCalSel::RtcCal32kXtal && !dig_32k_xtal_enabled { - LP_CLKRST::regs() - .clk_to_hp() - .modify(|_, w| w.icg_hp_xtal32k().clear_bit()); - } - - if cal_clk == RtcCalSel::RtcCalRcFast { - if rc_fast_enabled { - PMU::regs() - .hp_sleep_lp_ck_power() - .modify(|_, w| w.hp_sleep_xpd_fosc_clk().set_bit()); - crate::rom::ets_delay_us(50); - } - - if dig_rc_fast_enabled { - LP_CLKRST::regs() - .clk_to_hp() - .modify(|_, w| w.icg_hp_fosc().set_bit()); - crate::rom::ets_delay_us(5); - } - } - - if cal_clk == RtcCalSel::RtcCal32kRc { - if rc32k_enabled { - PMU::regs() - .hp_sleep_lp_ck_power() - .modify(|_, w| w.hp_sleep_xpd_rc32k().set_bit()); - crate::rom::ets_delay_us(300); - } - if dig_rc32k_enabled { - LP_CLKRST::regs() - .clk_to_hp() - .modify(|_, w| w.icg_hp_osc32k().set_bit()); - } - } - - cal_val - } -} - pub(crate) fn rtc_clk_cpu_freq_set_xtal() { // rtc_clk_cpu_set_to_default_config let freq = RtcClock::xtal_freq().mhz(); diff --git a/esp-hal/src/rtc_cntl/rtc/esp32h2.rs b/esp-hal/src/rtc_cntl/rtc/esp32h2.rs index 2268fbbd7..8015c6134 100644 --- a/esp-hal/src/rtc_cntl/rtc/esp32h2.rs +++ b/esp-hal/src/rtc_cntl/rtc/esp32h2.rs @@ -1,10 +1,9 @@ use strum::FromRepr; use crate::{ - clock::{Clock, clocks_ll::regi2c_write_mask}, - peripherals::{LP_AON, LPWR, PCR, PMU, TIMG0}, - rtc_cntl::RtcClock, - time::Rate, + clock::clocks_ll::regi2c_write_mask, + peripherals::{LP_AON, PMU}, + rtc_cntl::{RtcCalSel, RtcClock, RtcFastClock, RtcSlowClock}, }; const I2C_PMU: u8 = 0x6d; @@ -188,372 +187,3 @@ pub enum SocResetReason { /// Glitch on power resets the digital core CorePwrGlitch = 0x17, } - -/// RTC SLOW_CLK frequency values -#[derive(Debug, Clone, Copy)] -pub(crate) enum RtcFastClock { - /// Select RC_FAST_CLK as RTC_FAST_CLK source - RtcFastClockRcFast = 0, - #[allow(dead_code)] - /// Select XTAL_D2_CLK as RTC_FAST_CLK source - RtcFastClockXtalD2 = 1, -} - -impl Clock for RtcFastClock { - fn frequency(&self) -> Rate { - match self { - RtcFastClock::RtcFastClockXtalD2 => Rate::from_hz(16_000_000), - RtcFastClock::RtcFastClockRcFast => Rate::from_hz(property!("soc.rc_fast_clk_default")), - } - } -} - -/// RTC SLOW_CLK frequency values -#[allow(clippy::enum_variant_names)] -#[derive(Debug, Clone, Copy)] -#[non_exhaustive] -pub enum RtcSlowClock { - /// Select RC_SLOW_CLK as RTC_SLOW_CLK source - RtcSlowClockRcSlow = 0, - /// Select XTAL32K_CLK as RTC_SLOW_CLK source - RtcSlowClock32kXtal = 1, - /// Select RC32K_CLK as RTC_SLOW_CLK source - RtcSlowClock32kRc = 2, - /// Select OSC_SLOW_CLK (external slow clock) as RTC_SLOW_CLK source - RtcSlowOscSlow = 3, -} - -impl Clock for RtcSlowClock { - fn frequency(&self) -> Rate { - match self { - RtcSlowClock::RtcSlowClockRcSlow => Rate::from_hz(150_000), - RtcSlowClock::RtcSlowClock32kXtal => Rate::from_hz(32_768), - RtcSlowClock::RtcSlowClock32kRc => Rate::from_hz(32_768), - RtcSlowClock::RtcSlowOscSlow => Rate::from_hz(32_768), - } - } -} - -#[derive(Debug, Clone, Copy, PartialEq)] -/// Clock source to be calibrated using rtc_clk_cal function -pub(crate) enum RtcCalSel { - /// Currently selected RTC SLOW_CLK - RtcCalRtcMux = -1, - /// Internal 150kHz RC oscillator - RtcCalRcSlow = 0, - /// External 32kHz XTAL, as one type of 32k clock - RtcCal32kXtal = 1, - /// Internal 32kHz RC oscillator, as one type of 32k clock - RtcCal32kRc = 2, - /// External slow clock signal input by lp_pad_gpio0, as one type of 32k - /// clock - RtcCal32kOscSlow = 3, - /// Internal 20MHz RC oscillator - RtcCalRcFast, -} - -#[derive(Clone)] -pub(crate) enum RtcCaliClkSel { - CaliClkRcSlow = 0, - CaliClkRcFast = 1, - CaliClk32k = 2, -} - -/// RTC Watchdog Timer driver -impl RtcClock { - fn set_fast_freq(fast_freq: RtcFastClock) { - // components/hal/esp32s2/include/hal/clk_tree_ll.h - LPWR::regs().lp_clk_conf().modify(|_, w| unsafe { - w.fast_clk_sel().bits(match fast_freq { - RtcFastClock::RtcFastClockRcFast => 0b00, - RtcFastClock::RtcFastClockXtalD2 => 0b01, - }) - }); - - crate::rom::ets_delay_us(3); - } - - fn set_slow_freq(slow_freq: RtcSlowClock) { - LPWR::regs() - .lp_clk_conf() - .modify(|_, w| unsafe { w.slow_clk_sel().bits(slow_freq as u8) }); - - LPWR::regs().clk_to_hp().modify(|_, w| { - w.icg_hp_xtal32k() - .bit(matches!(slow_freq, RtcSlowClock::RtcSlowClock32kXtal)); - w.icg_hp_osc32k() - .bit(matches!(slow_freq, RtcSlowClock::RtcSlowClock32kRc)) - }); - } - - /// Get the RTC_SLOW_CLK source - pub fn slow_freq() -> RtcSlowClock { - match LPWR::regs().lp_clk_conf().read().slow_clk_sel().bits() { - 0 => RtcSlowClock::RtcSlowClockRcSlow, - 1 => RtcSlowClock::RtcSlowClock32kXtal, - 2 => RtcSlowClock::RtcSlowClock32kRc, - 3 => RtcSlowClock::RtcSlowOscSlow, - _ => unreachable!(), - } - } - - /// Calibration of RTC_SLOW_CLK is performed using a special feature of - /// TIMG0. This feature counts the number of XTAL clock cycles within a - /// given number of RTC_SLOW_CLK cycles. - pub(crate) fn calibrate_internal(mut cal_clk: RtcCalSel, slowclk_cycles: u32) -> u32 { - const SOC_CLK_RC_FAST_FREQ_APPROX: u32 = 17_500_000; - const SOC_CLK_RC_SLOW_FREQ_APPROX: u32 = 136_000; - const SOC_CLK_XTAL32K_FREQ_APPROX: u32 = 32768; - - if cal_clk == RtcCalSel::RtcCalRtcMux { - cal_clk = match cal_clk { - RtcCalSel::RtcCalRtcMux => match RtcClock::slow_freq() { - RtcSlowClock::RtcSlowClock32kXtal => RtcCalSel::RtcCal32kXtal, - RtcSlowClock::RtcSlowClock32kRc => RtcCalSel::RtcCal32kRc, - _ => cal_clk, - }, - RtcCalSel::RtcCal32kOscSlow => RtcCalSel::RtcCalRtcMux, - _ => cal_clk, - }; - } - - let clk_src = RtcClock::slow_freq(); - - if cal_clk == RtcCalSel::RtcCalRtcMux { - cal_clk = match clk_src { - RtcSlowClock::RtcSlowClockRcSlow => RtcCalSel::RtcCalRcSlow, - RtcSlowClock::RtcSlowClock32kXtal => RtcCalSel::RtcCal32kXtal, - RtcSlowClock::RtcSlowClock32kRc => RtcCalSel::RtcCal32kRc, - RtcSlowClock::RtcSlowOscSlow => RtcCalSel::RtcCal32kOscSlow, - }; - } - - let cali_clk_sel; - if cal_clk == RtcCalSel::RtcCalRtcMux { - cal_clk = match clk_src { - RtcSlowClock::RtcSlowClockRcSlow => RtcCalSel::RtcCalRcSlow, - RtcSlowClock::RtcSlowClock32kXtal => RtcCalSel::RtcCal32kXtal, - RtcSlowClock::RtcSlowClock32kRc => RtcCalSel::RtcCal32kRc, - RtcSlowClock::RtcSlowOscSlow => RtcCalSel::RtcCalRcSlow, - } - } - - if cal_clk == RtcCalSel::RtcCalRcFast { - cali_clk_sel = RtcCaliClkSel::CaliClkRcFast; - } else if cal_clk == RtcCalSel::RtcCalRcSlow { - cali_clk_sel = RtcCaliClkSel::CaliClkRcSlow; - } else { - cali_clk_sel = RtcCaliClkSel::CaliClk32k; - match cal_clk { - RtcCalSel::RtcCalRtcMux | RtcCalSel::RtcCalRcSlow | RtcCalSel::RtcCalRcFast => {} - RtcCalSel::RtcCal32kRc => { - PCR::regs() - .ctrl_32k_conf() - .modify(|_, w| unsafe { w.clk_32k_sel().bits(0) }); - } - RtcCalSel::RtcCal32kXtal => { - PCR::regs() - .ctrl_32k_conf() - .modify(|_, w| unsafe { w.clk_32k_sel().bits(1) }); - } - RtcCalSel::RtcCal32kOscSlow => { - PCR::regs() - .ctrl_32k_conf() - .modify(|_, w| unsafe { w.clk_32k_sel().bits(2) }); - } - } - } - - // Enable requested clock (150k is always on) - // Some delay is required before the time is stable - // Only enable if originaly was disabled - // If clock is already on, do nothing - - let dig_32k_xtal_enabled = LPWR::regs() - .clk_to_hp() - .read() - .icg_hp_xtal32k() - .bit_is_set(); - - if cal_clk == RtcCalSel::RtcCal32kXtal && !dig_32k_xtal_enabled { - LPWR::regs() - .clk_to_hp() - .modify(|_, w| w.icg_hp_xtal32k().set_bit()); - } - - // TODO: very hacky - icg_hp_xtal32k is already set in the above condition? - // in ESP-IDF these are not called in this function but the fields are set - LPWR::regs() - .clk_to_hp() - .modify(|_, w| w.icg_hp_xtal32k().set_bit()); - PMU::regs().hp_sleep_lp_ck_power().modify(|_, w| { - w.hp_sleep_xpd_xtal32k().set_bit(); - w.hp_sleep_xpd_rc32k().set_bit() - }); - - let rc_fast_enabled = PMU::regs() - .hp_sleep_lp_ck_power() - .read() - .hp_sleep_xpd_fosc_clk() - .bit_is_set(); - let dig_rc_fast_enabled = LPWR::regs().clk_to_hp().read().icg_hp_fosc().bit_is_set(); - - if cal_clk == RtcCalSel::RtcCalRcFast { - if !rc_fast_enabled { - PMU::regs() - .hp_sleep_lp_ck_power() - .modify(|_, w| w.hp_sleep_xpd_fosc_clk().set_bit()); - crate::rom::ets_delay_us(50); - } - - if !dig_rc_fast_enabled { - LPWR::regs() - .clk_to_hp() - .modify(|_, w| w.icg_hp_fosc().set_bit()); - crate::rom::ets_delay_us(5); - } - } - - let rc32k_enabled = PMU::regs() - .hp_sleep_lp_ck_power() - .read() - .hp_sleep_xpd_rc32k() - .bit_is_set(); - let dig_rc32k_enabled = LPWR::regs().clk_to_hp().read().icg_hp_osc32k().bit_is_set(); - - if cal_clk == RtcCalSel::RtcCal32kRc { - if !rc32k_enabled { - PMU::regs() - .hp_sleep_lp_ck_power() - .modify(|_, w| w.hp_sleep_xpd_rc32k().set_bit()); - crate::rom::ets_delay_us(300); - } - - if !dig_rc32k_enabled { - LPWR::regs() - .clk_to_hp() - .modify(|_, w| w.icg_hp_osc32k().set_bit()); - } - } - - // Check if there is already running calibration process - // TODO: &mut TIMG0 for calibration - let timg0 = TIMG0::regs(); - - if timg0 - .rtccalicfg() - .read() - .rtc_cali_start_cycling() - .bit_is_set() - { - timg0 - .rtccalicfg2() - .modify(|_, w| unsafe { w.rtc_cali_timeout_thres().bits(1) }); - - // Set small timeout threshold to accelerate the generation of timeot - // Internal circuit will be reset when timeout occurs and will not affect the - // next calibration - while !timg0.rtccalicfg().read().rtc_cali_rdy().bit_is_set() - && !timg0.rtccalicfg2().read().rtc_cali_timeout().bit_is_set() - {} - } - - // Prepare calibration - timg0 - .rtccalicfg() - .modify(|_, w| unsafe { w.rtc_cali_clk_sel().bits(cali_clk_sel.clone() as u8) }); - timg0 - .rtccalicfg() - .modify(|_, w| w.rtc_cali_start_cycling().clear_bit()); - timg0 - .rtccalicfg() - .modify(|_, w| unsafe { w.rtc_cali_max().bits(slowclk_cycles as u16) }); - - let expected_freq = match cali_clk_sel { - RtcCaliClkSel::CaliClk32k => { - timg0.rtccalicfg2().modify(|_, w| unsafe { - w.rtc_cali_timeout_thres().bits(slowclk_cycles << 12) - }); - SOC_CLK_XTAL32K_FREQ_APPROX - } - RtcCaliClkSel::CaliClkRcFast => { - timg0 - .rtccalicfg2() - .modify(|_, w| unsafe { w.rtc_cali_timeout_thres().bits(0x01FFFFFF) }); - SOC_CLK_RC_FAST_FREQ_APPROX - } - _ => { - timg0.rtccalicfg2().modify(|_, w| unsafe { - w.rtc_cali_timeout_thres().bits(slowclk_cycles << 10) - }); - SOC_CLK_RC_SLOW_FREQ_APPROX - } - }; - - let us_time_estimate = (Rate::from_mhz(slowclk_cycles) / expected_freq).as_hz(); - - // Start calibration - timg0 - .rtccalicfg() - .modify(|_, w| w.rtc_cali_start().clear_bit()); - timg0 - .rtccalicfg() - .modify(|_, w| w.rtc_cali_start().set_bit()); - - // Wait for calibration to finish up to another us_time_estimate - crate::rom::ets_delay_us(us_time_estimate); - - let cal_val = loop { - if timg0.rtccalicfg().read().rtc_cali_rdy().bit_is_set() { - break timg0.rtccalicfg1().read().rtc_cali_value().bits(); - } - - if timg0.rtccalicfg2().read().rtc_cali_timeout().bit_is_set() { - // Timed out waiting for calibration - break 0; - } - }; - - timg0 - .rtccalicfg() - .modify(|_, w| w.rtc_cali_start().clear_bit()); - - if cal_clk == RtcCalSel::RtcCal32kXtal && !dig_32k_xtal_enabled { - LPWR::regs() - .clk_to_hp() - .modify(|_, w| w.icg_hp_xtal32k().clear_bit()); - } - - if cal_clk == RtcCalSel::RtcCalRcFast { - if rc_fast_enabled { - PMU::regs() - .hp_sleep_lp_ck_power() - .modify(|_, w| w.hp_sleep_xpd_fosc_clk().set_bit()); - crate::rom::ets_delay_us(50); - } - - if dig_rc_fast_enabled { - LPWR::regs() - .clk_to_hp() - .modify(|_, w| w.icg_hp_fosc().set_bit()); - crate::rom::ets_delay_us(5); - } - } - - if cal_clk == RtcCalSel::RtcCal32kRc { - if rc32k_enabled { - PMU::regs() - .hp_sleep_lp_ck_power() - .modify(|_, w| w.hp_sleep_xpd_rc32k().set_bit()); - crate::rom::ets_delay_us(300); - } - if dig_rc32k_enabled { - LPWR::regs() - .clk_to_hp() - .modify(|_, w| w.icg_hp_osc32k().set_bit()); - } - } - - cal_val - } -} diff --git a/esp-hal/src/rtc_cntl/rtc/esp32s2.rs b/esp-hal/src/rtc_cntl/rtc/esp32s2.rs index ff9af0d67..3fade7d8d 100644 --- a/esp-hal/src/rtc_cntl/rtc/esp32s2.rs +++ b/esp-hal/src/rtc_cntl/rtc/esp32s2.rs @@ -8,10 +8,10 @@ use crate::{ pub(crate) fn init() {} pub(crate) fn configure_clock() { - RtcClock::set_fast_freq(RtcFastClock::RtcFastClock8m); + RtcClock::set_fast_freq(RtcFastClock::RtcFastClockRcFast); let cal_val = loop { - RtcClock::set_slow_freq(RtcSlowClock::RtcSlowClockRtc); + RtcClock::set_slow_freq(RtcSlowClock::RtcSlowClockRcSlow); let res = RtcClock::calibrate(RtcCalSel::RtcCalRtcMux, 1024); if res != 0 { diff --git a/esp-hal/src/rtc_cntl/rtc/esp32s3.rs b/esp-hal/src/rtc_cntl/rtc/esp32s3.rs index 831282a30..4b5fae1a9 100644 --- a/esp-hal/src/rtc_cntl/rtc/esp32s3.rs +++ b/esp-hal/src/rtc_cntl/rtc/esp32s3.rs @@ -8,10 +8,10 @@ use crate::{ pub(crate) fn init() {} pub(crate) fn configure_clock() { - RtcClock::set_fast_freq(RtcFastClock::RtcFastClock8m); + RtcClock::set_fast_freq(RtcFastClock::RtcFastClockRcFast); let cal_val = loop { - RtcClock::set_slow_freq(RtcSlowClock::RtcSlowClockRtc); + RtcClock::set_slow_freq(RtcSlowClock::RtcSlowClockRcSlow); let res = RtcClock::calibrate(RtcCalSel::RtcCalRtcMux, 1024); if res != 0 { diff --git a/esp-hal/src/rtc_cntl/sleep/esp32c6.rs b/esp-hal/src/rtc_cntl/sleep/esp32c6.rs index 9d38e9322..b58732124 100644 --- a/esp-hal/src/rtc_cntl/sleep/esp32c6.rs +++ b/esp-hal/src/rtc_cntl/sleep/esp32c6.rs @@ -6,6 +6,7 @@ use crate::{ gpio::RtcFunction, rtc_cntl::{ Rtc, + RtcCalSel, RtcClock, rtc::{ HpAnalog, @@ -13,7 +14,6 @@ use crate::{ HpSysPower, LpAnalog, LpSysPower, - RtcCalSel, SavedClockConfig, rtc_clk_cpu_freq_set_xtal, }, diff --git a/esp-metadata-generated/src/_build_script_utils.rs b/esp-metadata-generated/src/_build_script_utils.rs index d3f5388b0..2924ca096 100644 --- a/esp-metadata-generated/src/_build_script_utils.rs +++ b/esp-metadata-generated/src/_build_script_utils.rs @@ -265,8 +265,10 @@ impl Chip { "uart_uart2", "soc_ref_tick_hz=\"1000000\"", "soc_ref_tick_hz_is_set", - "soc_rc_fast_clk_default=\"8000000\"", + "soc_rc_fast_clk_default=\"8500000\"", "soc_rc_fast_clk_default_is_set", + "soc_rc_slow_clock=\"150000\"", + "soc_rc_slow_clock_is_set", "soc_has_multiple_xtal_options", "aes_endianness_configurable", "gpio_has_bank_1", @@ -419,8 +421,10 @@ impl Chip { "cargo:rustc-cfg=uart_uart2", "cargo:rustc-cfg=soc_ref_tick_hz=\"1000000\"", "cargo:rustc-cfg=soc_ref_tick_hz_is_set", - "cargo:rustc-cfg=soc_rc_fast_clk_default=\"8000000\"", + "cargo:rustc-cfg=soc_rc_fast_clk_default=\"8500000\"", "cargo:rustc-cfg=soc_rc_fast_clk_default_is_set", + "cargo:rustc-cfg=soc_rc_slow_clock=\"150000\"", + "cargo:rustc-cfg=soc_rc_slow_clock_is_set", "cargo:rustc-cfg=soc_has_multiple_xtal_options", "cargo:rustc-cfg=aes_endianness_configurable", "cargo:rustc-cfg=gpio_has_bank_1", @@ -537,6 +541,8 @@ impl Chip { "soc_cpu_has_csr_pc", "soc_rc_fast_clk_default=\"17500000\"", "soc_rc_fast_clk_default_is_set", + "soc_rc_slow_clock=\"136000\"", + "soc_rc_slow_clock_is_set", "soc_has_multiple_xtal_options", "assist_debug_has_sp_monitor", "gpio_gpio_function=\"1\"", @@ -652,6 +658,8 @@ impl Chip { "cargo:rustc-cfg=soc_cpu_has_csr_pc", "cargo:rustc-cfg=soc_rc_fast_clk_default=\"17500000\"", "cargo:rustc-cfg=soc_rc_fast_clk_default_is_set", + "cargo:rustc-cfg=soc_rc_slow_clock=\"136000\"", + "cargo:rustc-cfg=soc_rc_slow_clock_is_set", "cargo:rustc-cfg=soc_has_multiple_xtal_options", "cargo:rustc-cfg=assist_debug_has_sp_monitor", "cargo:rustc-cfg=gpio_gpio_function=\"1\"", @@ -788,6 +796,8 @@ impl Chip { "soc_cpu_has_csr_pc", "soc_rc_fast_clk_default=\"17500000\"", "soc_rc_fast_clk_default_is_set", + "soc_rc_slow_clock=\"136000\"", + "soc_rc_slow_clock_is_set", "soc_xtal_frequency=\"40\"", "aes_dma", "aes_dma_mode_ecb", @@ -933,6 +943,8 @@ impl Chip { "cargo:rustc-cfg=soc_cpu_has_csr_pc", "cargo:rustc-cfg=soc_rc_fast_clk_default=\"17500000\"", "cargo:rustc-cfg=soc_rc_fast_clk_default_is_set", + "cargo:rustc-cfg=soc_rc_slow_clock=\"136000\"", + "cargo:rustc-cfg=soc_rc_slow_clock_is_set", "cargo:rustc-cfg=soc_xtal_frequency=\"40\"", "cargo:rustc-cfg=aes_dma", "cargo:rustc-cfg=aes_dma_mode_ecb", @@ -1133,6 +1145,8 @@ impl Chip { "soc_cpu_has_prv_mode", "soc_rc_fast_clk_default=\"17500000\"", "soc_rc_fast_clk_default_is_set", + "soc_rc_slow_clock=\"136000\"", + "soc_rc_slow_clock_is_set", "soc_xtal_frequency=\"40\"", "aes_dma", "aes_dma_mode_ecb", @@ -1333,6 +1347,8 @@ impl Chip { "cargo:rustc-cfg=soc_cpu_has_prv_mode", "cargo:rustc-cfg=soc_rc_fast_clk_default=\"17500000\"", "cargo:rustc-cfg=soc_rc_fast_clk_default_is_set", + "cargo:rustc-cfg=soc_rc_slow_clock=\"136000\"", + "cargo:rustc-cfg=soc_rc_slow_clock_is_set", "cargo:rustc-cfg=soc_xtal_frequency=\"40\"", "cargo:rustc-cfg=aes_dma", "cargo:rustc-cfg=aes_dma_mode_ecb", @@ -1512,8 +1528,10 @@ impl Chip { "uart_uart1", "soc_cpu_has_csr_pc", "soc_cpu_has_prv_mode", - "soc_rc_fast_clk_default=\"8000000\"", + "soc_rc_fast_clk_default=\"8500000\"", "soc_rc_fast_clk_default_is_set", + "soc_rc_slow_clock=\"136000\"", + "soc_rc_slow_clock_is_set", "soc_xtal_frequency=\"32\"", "aes_dma", "aes_dma_mode_ecb", @@ -1687,8 +1705,10 @@ impl Chip { "cargo:rustc-cfg=uart_uart1", "cargo:rustc-cfg=soc_cpu_has_csr_pc", "cargo:rustc-cfg=soc_cpu_has_prv_mode", - "cargo:rustc-cfg=soc_rc_fast_clk_default=\"8000000\"", + "cargo:rustc-cfg=soc_rc_fast_clk_default=\"8500000\"", "cargo:rustc-cfg=soc_rc_fast_clk_default_is_set", + "cargo:rustc-cfg=soc_rc_slow_clock=\"136000\"", + "cargo:rustc-cfg=soc_rc_slow_clock_is_set", "cargo:rustc-cfg=soc_xtal_frequency=\"32\"", "cargo:rustc-cfg=aes_dma", "cargo:rustc-cfg=aes_dma_mode_ecb", @@ -1861,8 +1881,10 @@ impl Chip { "uart_uart1", "soc_ref_tick_hz=\"1000000\"", "soc_ref_tick_hz_is_set", - "soc_rc_fast_clk_default=\"8000000\"", + "soc_rc_fast_clk_default=\"8500000\"", "soc_rc_fast_clk_default_is_set", + "soc_rc_slow_clock=\"90000\"", + "soc_rc_slow_clock_is_set", "soc_xtal_frequency=\"40\"", "aes_dma", "aes_dma_mode_ecb", @@ -2027,8 +2049,10 @@ impl Chip { "cargo:rustc-cfg=uart_uart1", "cargo:rustc-cfg=soc_ref_tick_hz=\"1000000\"", "cargo:rustc-cfg=soc_ref_tick_hz_is_set", - "cargo:rustc-cfg=soc_rc_fast_clk_default=\"8000000\"", + "cargo:rustc-cfg=soc_rc_fast_clk_default=\"8500000\"", "cargo:rustc-cfg=soc_rc_fast_clk_default_is_set", + "cargo:rustc-cfg=soc_rc_slow_clock=\"90000\"", + "cargo:rustc-cfg=soc_rc_slow_clock_is_set", "cargo:rustc-cfg=soc_xtal_frequency=\"40\"", "cargo:rustc-cfg=aes_dma", "cargo:rustc-cfg=aes_dma_mode_ecb", @@ -2213,6 +2237,8 @@ impl Chip { "uart_uart2", "soc_rc_fast_clk_default=\"17500000\"", "soc_rc_fast_clk_default_is_set", + "soc_rc_slow_clock=\"136000\"", + "soc_rc_slow_clock_is_set", "soc_xtal_frequency=\"40\"", "aes_dma", "aes_dma_mode_ecb", @@ -2395,6 +2421,8 @@ impl Chip { "cargo:rustc-cfg=uart_uart2", "cargo:rustc-cfg=soc_rc_fast_clk_default=\"17500000\"", "cargo:rustc-cfg=soc_rc_fast_clk_default_is_set", + "cargo:rustc-cfg=soc_rc_slow_clock=\"136000\"", + "cargo:rustc-cfg=soc_rc_slow_clock_is_set", "cargo:rustc-cfg=soc_xtal_frequency=\"40\"", "cargo:rustc-cfg=aes_dma", "cargo:rustc-cfg=aes_dma_mode_ecb", @@ -2574,6 +2602,7 @@ impl Config { println!("cargo:rustc-check-cfg=cfg(uart_uart2)"); println!("cargo:rustc-check-cfg=cfg(soc_ref_tick_hz_is_set)"); println!("cargo:rustc-check-cfg=cfg(soc_rc_fast_clk_default_is_set)"); + println!("cargo:rustc-check-cfg=cfg(soc_rc_slow_clock_is_set)"); println!("cargo:rustc-check-cfg=cfg(soc_has_multiple_xtal_options)"); println!("cargo:rustc-check-cfg=cfg(aes_endianness_configurable)"); println!("cargo:rustc-check-cfg=cfg(gpio_has_bank_1)"); @@ -2729,7 +2758,10 @@ impl Config { println!("cargo:rustc-check-cfg=cfg(camera)"); println!("cargo:rustc-check-cfg=cfg(soc_ref_tick_hz, values(\"1000000\"))"); println!( - "cargo:rustc-check-cfg=cfg(soc_rc_fast_clk_default, values(\"8000000\",\"17500000\"))" + "cargo:rustc-check-cfg=cfg(soc_rc_fast_clk_default, values(\"8500000\",\"17500000\"))" + ); + println!( + "cargo:rustc-check-cfg=cfg(soc_rc_slow_clock, values(\"150000\",\"136000\",\"90000\"))" ); println!("cargo:rustc-check-cfg=cfg(gpio_gpio_function, values(\"2\",\"1\"))"); println!("cargo:rustc-check-cfg=cfg(gpio_constant_0_input, values(\"48\",\"31\",\"60\"))"); diff --git a/esp-metadata-generated/src/_generated_esp32.rs b/esp-metadata-generated/src/_generated_esp32.rs index bfc4fb15c..e14b85e5c 100644 --- a/esp-metadata-generated/src/_generated_esp32.rs +++ b/esp-metadata-generated/src/_generated_esp32.rs @@ -49,10 +49,16 @@ macro_rules! property { stringify!(1000000) }; ("soc.rc_fast_clk_default") => { - 8000000 + 8500000 }; ("soc.rc_fast_clk_default", str) => { - stringify!(8000000) + stringify!(8500000) + }; + ("soc.rc_slow_clock") => { + 150000 + }; + ("soc.rc_slow_clock", str) => { + stringify!(150000) }; ("soc.has_multiple_xtal_options") => { true diff --git a/esp-metadata-generated/src/_generated_esp32c2.rs b/esp-metadata-generated/src/_generated_esp32c2.rs index b07c5e0dc..75434c5b2 100644 --- a/esp-metadata-generated/src/_generated_esp32c2.rs +++ b/esp-metadata-generated/src/_generated_esp32c2.rs @@ -48,6 +48,12 @@ macro_rules! property { ("soc.rc_fast_clk_default", str) => { stringify!(17500000) }; + ("soc.rc_slow_clock") => { + 136000 + }; + ("soc.rc_slow_clock", str) => { + stringify!(136000) + }; ("soc.has_multiple_xtal_options") => { true }; diff --git a/esp-metadata-generated/src/_generated_esp32c3.rs b/esp-metadata-generated/src/_generated_esp32c3.rs index 46465b42d..0bb8a27da 100644 --- a/esp-metadata-generated/src/_generated_esp32c3.rs +++ b/esp-metadata-generated/src/_generated_esp32c3.rs @@ -48,6 +48,12 @@ macro_rules! property { ("soc.rc_fast_clk_default", str) => { stringify!(17500000) }; + ("soc.rc_slow_clock") => { + 136000 + }; + ("soc.rc_slow_clock", str) => { + stringify!(136000) + }; ("soc.xtal_frequency") => { 40 }; diff --git a/esp-metadata-generated/src/_generated_esp32c6.rs b/esp-metadata-generated/src/_generated_esp32c6.rs index ef12f038f..91ceff2e7 100644 --- a/esp-metadata-generated/src/_generated_esp32c6.rs +++ b/esp-metadata-generated/src/_generated_esp32c6.rs @@ -48,6 +48,12 @@ macro_rules! property { ("soc.rc_fast_clk_default", str) => { stringify!(17500000) }; + ("soc.rc_slow_clock") => { + 136000 + }; + ("soc.rc_slow_clock", str) => { + stringify!(136000) + }; ("soc.xtal_frequency") => { 40 }; diff --git a/esp-metadata-generated/src/_generated_esp32h2.rs b/esp-metadata-generated/src/_generated_esp32h2.rs index e0daf1868..27eb00774 100644 --- a/esp-metadata-generated/src/_generated_esp32h2.rs +++ b/esp-metadata-generated/src/_generated_esp32h2.rs @@ -43,10 +43,16 @@ macro_rules! property { true }; ("soc.rc_fast_clk_default") => { - 8000000 + 8500000 }; ("soc.rc_fast_clk_default", str) => { - stringify!(8000000) + stringify!(8500000) + }; + ("soc.rc_slow_clock") => { + 136000 + }; + ("soc.rc_slow_clock", str) => { + stringify!(136000) }; ("soc.xtal_frequency") => { 32 diff --git a/esp-metadata-generated/src/_generated_esp32s2.rs b/esp-metadata-generated/src/_generated_esp32s2.rs index 1fddc5b3e..07a8f0c2a 100644 --- a/esp-metadata-generated/src/_generated_esp32s2.rs +++ b/esp-metadata-generated/src/_generated_esp32s2.rs @@ -49,10 +49,16 @@ macro_rules! property { stringify!(1000000) }; ("soc.rc_fast_clk_default") => { - 8000000 + 8500000 }; ("soc.rc_fast_clk_default", str) => { - stringify!(8000000) + stringify!(8500000) + }; + ("soc.rc_slow_clock") => { + 90000 + }; + ("soc.rc_slow_clock", str) => { + stringify!(90000) }; ("soc.xtal_frequency") => { 40 diff --git a/esp-metadata-generated/src/_generated_esp32s3.rs b/esp-metadata-generated/src/_generated_esp32s3.rs index 7a68ab0f9..862d7bb4d 100644 --- a/esp-metadata-generated/src/_generated_esp32s3.rs +++ b/esp-metadata-generated/src/_generated_esp32s3.rs @@ -48,6 +48,12 @@ macro_rules! property { ("soc.rc_fast_clk_default", str) => { stringify!(17500000) }; + ("soc.rc_slow_clock") => { + 136000 + }; + ("soc.rc_slow_clock", str) => { + stringify!(136000) + }; ("soc.xtal_frequency") => { 40 }; diff --git a/esp-metadata/devices/esp32.toml b/esp-metadata/devices/esp32.toml index 7a854439d..cb7f9c02b 100644 --- a/esp-metadata/devices/esp32.toml +++ b/esp-metadata/devices/esp32.toml @@ -104,7 +104,8 @@ memory = [{ name = "dram", start = 0x3FFA_E000, end = 0x4000_0000 }] [device.soc] ref_tick_hz = 1_000_000 -rc_fast_clk_default = 8_000_000 +rc_fast_clk_default = 8_500_000 +rc_slow_clock = 150_000 xtal_options = [26, 40] [device.adc] diff --git a/esp-metadata/devices/esp32c2.toml b/esp-metadata/devices/esp32c2.toml index 0fd168c01..f03d3b46d 100644 --- a/esp-metadata/devices/esp32c2.toml +++ b/esp-metadata/devices/esp32c2.toml @@ -83,6 +83,7 @@ memory = [{ name = "dram", start = 0x3FCA_0000, end = 0x3FCE_0000 }] [device.soc] cpu_has_csr_pc = true rc_fast_clk_default = 17_500_000 +rc_slow_clock = 136_000 xtal_options = [26, 40] [device.adc] diff --git a/esp-metadata/devices/esp32c3.toml b/esp-metadata/devices/esp32c3.toml index 7fd3050a0..66cc78ec6 100644 --- a/esp-metadata/devices/esp32c3.toml +++ b/esp-metadata/devices/esp32c3.toml @@ -92,6 +92,7 @@ memory = [{ name = "dram", start = 0x3FC8_0000, end = 0x3FCE_0000 }] [device.soc] cpu_has_csr_pc = true rc_fast_clk_default = 17_500_000 +rc_slow_clock = 136_000 xtal_options = [40] [device.adc] diff --git a/esp-metadata/devices/esp32c6.toml b/esp-metadata/devices/esp32c6.toml index 8032004ab..31b9296d7 100644 --- a/esp-metadata/devices/esp32c6.toml +++ b/esp-metadata/devices/esp32c6.toml @@ -134,6 +134,7 @@ memory = [{ name = "dram", start = 0x4080_0000, end = 0x4088_0000 }] cpu_has_csr_pc = true cpu_has_prv_mode = true rc_fast_clk_default = 17_500_000 +rc_slow_clock = 136_000 xtal_options = [40] [device.adc] diff --git a/esp-metadata/devices/esp32h2.toml b/esp-metadata/devices/esp32h2.toml index a3e170fbd..14c7d5e22 100644 --- a/esp-metadata/devices/esp32h2.toml +++ b/esp-metadata/devices/esp32h2.toml @@ -112,7 +112,8 @@ memory = [{ name = "dram", start = 0x4080_0000, end = 0x4085_0000 }] [device.soc] cpu_has_csr_pc = true cpu_has_prv_mode = true -rc_fast_clk_default = 8_000_000 +rc_fast_clk_default = 8_500_000 +rc_slow_clock = 136_000 xtal_options = [32] [device.adc] diff --git a/esp-metadata/devices/esp32s2.toml b/esp-metadata/devices/esp32s2.toml index 791b25863..0ee2c550c 100644 --- a/esp-metadata/devices/esp32s2.toml +++ b/esp-metadata/devices/esp32s2.toml @@ -103,7 +103,8 @@ memory = [{ name = "dram", start = 0x3FFB_0000, end = 0x4000_0000 }] [device.soc] ref_tick_hz = 1_000_000 -rc_fast_clk_default = 8_000_000 +rc_fast_clk_default = 8_500_000 +rc_slow_clock = 90_000 xtal_options = [40] [device.adc] diff --git a/esp-metadata/devices/esp32s3.toml b/esp-metadata/devices/esp32s3.toml index d35847c7d..bb384b013 100644 --- a/esp-metadata/devices/esp32s3.toml +++ b/esp-metadata/devices/esp32s3.toml @@ -116,6 +116,7 @@ memory = [{ name = "dram", start = 0x3FC8_8000, end = 0x3FD0_0000 }] [device.soc] rc_fast_clk_default = 17_500_000 +rc_slow_clock = 136_000 xtal_options = [40] [device.adc] diff --git a/esp-metadata/src/cfg.rs b/esp-metadata/src/cfg.rs index 8d78bae2f..468c36bfc 100644 --- a/esp-metadata/src/cfg.rs +++ b/esp-metadata/src/cfg.rs @@ -285,6 +285,8 @@ driver_configs![ ref_tick_hz: Option, #[serde(default)] rc_fast_clk_default: Option, + #[serde(default)] + rc_slow_clock: Option, xtal_options: Vec, } },