Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
- Add unified field-based efuse access
- Add `timer_interrupt` example in ESP32-H2 and refactor `clk_src` configuration (#576)
- Move `esp-riscv-rt` into esp-hal (#578)
- Add initial implementation of radio clocks for ESP32-H2 (#577)

### Changed

Expand Down
10 changes: 7 additions & 3 deletions esp-hal-common/devices/esp32h2.toml
Original file line number Diff line number Diff line change
Expand Up @@ -31,14 +31,14 @@ peripherals = [
"lp_wdt",
"mcpwm0",
"mem_monitor",
# "modem_lpcon",
# "modem_syscon",
"modem_lpcon",
"modem_syscon",
# "otp_debug",
# "parl_io",
# "pau",
"pcnt",
"pcr",
# "pmu",
"pmu",
"rmt",
# "rng",
"rsa",
Expand All @@ -64,4 +64,8 @@ peripherals = [
"assist_debug_region_monitor",
"gdma",
"plic",
"radio",
"phy",
"bt",
"ieee802154",
]
6 changes: 3 additions & 3 deletions esp-hal-common/src/soc/esp32h2/peripherals.rs
Original file line number Diff line number Diff line change
Expand Up @@ -33,14 +33,14 @@ crate::peripherals! {
LP_WDT => true,
MCPWM0 => true,
MEM_MONITOR => true,
// MODEM_LPCON => true,
// MODEM_SYSCON => true,
MODEM_LPCON => true,
MODEM_SYSCON => true,
// OTP_DEBUG => true,
// PARL_IO => true,
// PAU => true,
PCNT => true,
PCR => true,
// PMU => true,
PMU => true,
RMT => true,
// RNG => true,
RSA => true,
Expand Down
138 changes: 138 additions & 0 deletions esp-hal-common/src/soc/esp32h2/radio_clocks.rs
Original file line number Diff line number Diff line change
@@ -1 +1,139 @@
use crate::system::{RadioClockControl, RadioClockController, RadioPeripherals};

impl RadioClockController for RadioClockControl {
fn enable(&mut self, peripheral: RadioPeripherals) {
match peripheral {
RadioPeripherals::Phy => enable_phy(),
RadioPeripherals::Bt => todo!("BLE not yet supported"),
RadioPeripherals::Ieee802154 => ieee802154_clock_enable(),
}
}

fn disable(&mut self, peripheral: RadioPeripherals) {
match peripheral {
RadioPeripherals::Phy => disable_phy(),
RadioPeripherals::Bt => todo!("BLE not yet supported"),
RadioPeripherals::Ieee802154 => ieee802154_clock_disable(),
}
}

fn reset_mac(&mut self) {
reset_mac();
}

fn init_clocks(&mut self) {
init_clocks();
}

fn ble_rtc_clk_init(&mut self) {
// nothing for this target (yet)
}

fn reset_rpa(&mut self) {
// nothing for this target (yet)
}
}

fn enable_phy() {
unsafe { &*esp32h2::MODEM_LPCON::PTR }
.clk_conf
.modify(|_, w| w.clk_i2c_mst_en().set_bit());
}

fn disable_phy() {
unsafe { &*esp32h2::MODEM_LPCON::PTR }
.clk_conf
.modify(|_, w| w.clk_i2c_mst_en().clear_bit());
}

fn ieee802154_clock_enable() {
let modem_lpcon = unsafe { &*esp32h2::MODEM_LPCON::PTR };
let modem_syscon = unsafe { &*esp32h2::MODEM_SYSCON::PTR };

modem_syscon
.clk_conf
.modify(|_, w| w.clk_zb_apb_en().set_bit().clk_zb_mac_en().set_bit());

modem_syscon.clk_conf1.modify(|_, w| {
w.clk_bt_apb_en()
.set_bit()
.clk_bt_en()
.set_bit()
.clk_fe_16m_en()
.set_bit()
.clk_fe_32m_en()
.set_bit()
.clk_fe_adc_en()
.set_bit()
.clk_fe_apb_en()
.set_bit()
.clk_fe_sdm_en()
.set_bit()
});

modem_lpcon
.clk_conf
.modify(|_, w| w.clk_coex_en().set_bit());
}

fn ieee802154_clock_disable() {
let modem_lpcon = unsafe { &*esp32h2::MODEM_LPCON::PTR };
let modem_syscon = unsafe { &*esp32h2::MODEM_SYSCON::PTR };

modem_syscon
.clk_conf
.modify(|_, w| w.clk_zb_apb_en().clear_bit().clk_zb_mac_en().clear_bit());

modem_syscon.clk_conf1.modify(|_, w| {
w.clk_bt_apb_en()
.clear_bit()
.clk_bt_en()
.clear_bit()
.clk_fe_16m_en()
.clear_bit()
.clk_fe_32m_en()
.clear_bit()
.clk_fe_adc_en()
.clear_bit()
.clk_fe_apb_en()
.clear_bit()
.clk_fe_sdm_en()
.clear_bit()
});

modem_lpcon
.clk_conf
.modify(|_, w| w.clk_coex_en().clear_bit());
}

fn reset_mac() {
// empty
}

fn init_clocks() {
unsafe {
let pmu = &*esp32h2::PMU::PTR;

pmu.hp_sleep_icg_modem
.modify(|_, w| w.hp_sleep_dig_icg_modem_code().variant(0));
pmu.hp_modem_icg_modem
.modify(|_, w| w.hp_modem_dig_icg_modem_code().variant(1));
pmu.hp_active_icg_modem
.modify(|_, w| w.hp_active_dig_icg_modem_code().variant(2));
pmu.imm_modem_icg
.as_ptr()
.write_volatile(pmu.imm_modem_icg.as_ptr().read_volatile() | 1 << 31);
pmu.imm_sleep_sysclk
.as_ptr()
.write_volatile(pmu.imm_sleep_sysclk.as_ptr().read_volatile() | 1 << 28);

(&*esp32h2::MODEM_LPCON::PTR).clk_conf.modify(|_, w| {
w.clk_i2c_mst_en()
.set_bit()
.clk_coex_en()
.set_bit()
.clk_fe_mem_en()
.set_bit()
});
}
}