H2: enable TWAI, enable delay test (#2199)
* Add TWAI support for H2 * Enable delay test on h2 * Also enable example * Changelog * De-CAN the example
This commit is contained in:
parent
5de267ab09
commit
d5afeeddc8
@ -25,6 +25,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
||||
- Added APIs to allow connecting signals through the GPIO matrix. (#2128)
|
||||
- Implement `TryFrom<u32>` for `ledc::timer::config::Duty` (#1984)
|
||||
- Expose `RtcClock::get_xtal_freq` and `RtcClock::get_slow_freq` publically for all chips (#2183)
|
||||
- TWAI support for ESP32-H2 (#2199)
|
||||
|
||||
### Changed
|
||||
|
||||
|
||||
@ -662,8 +662,8 @@ impl BaudRate {
|
||||
/// Convert the BaudRate into the timings that the peripheral needs.
|
||||
// See: https://github.com/espressif/esp-idf/tree/master/components/hal/include/hal/twai_types.h
|
||||
const fn timing(self) -> TimingConfig {
|
||||
#[allow(unused_mut)]
|
||||
let mut timing = match self {
|
||||
#[cfg(not(esp32h2))]
|
||||
let timing = match self {
|
||||
Self::B125K => TimingConfig {
|
||||
baud_rate_prescaler: 32,
|
||||
sync_jump_width: 3,
|
||||
@ -695,11 +695,45 @@ impl BaudRate {
|
||||
Self::Custom(timing_config) => timing_config,
|
||||
};
|
||||
|
||||
#[cfg(esp32h2)]
|
||||
let timing = match self {
|
||||
Self::B125K => TimingConfig {
|
||||
baud_rate_prescaler: 8,
|
||||
sync_jump_width: 3,
|
||||
tseg_1: 23,
|
||||
tseg_2: 8,
|
||||
triple_sample: false,
|
||||
},
|
||||
Self::B250K => TimingConfig {
|
||||
baud_rate_prescaler: 8,
|
||||
sync_jump_width: 3,
|
||||
tseg_1: 11,
|
||||
tseg_2: 4,
|
||||
triple_sample: false,
|
||||
},
|
||||
Self::B500K => TimingConfig {
|
||||
baud_rate_prescaler: 4,
|
||||
sync_jump_width: 3,
|
||||
tseg_1: 11,
|
||||
tseg_2: 4,
|
||||
triple_sample: false,
|
||||
},
|
||||
Self::B1000K => TimingConfig {
|
||||
baud_rate_prescaler: 2,
|
||||
sync_jump_width: 3,
|
||||
tseg_1: 11,
|
||||
tseg_2: 4,
|
||||
triple_sample: false,
|
||||
},
|
||||
Self::Custom(timing_config) => timing_config,
|
||||
};
|
||||
|
||||
// clock source on ESP32-C6 is xtal (40MHz)
|
||||
#[cfg(esp32c6)]
|
||||
{
|
||||
// clock source on ESP32-C6 is xtal (40MHz)
|
||||
timing.baud_rate_prescaler /= 2;
|
||||
}
|
||||
let timing = TimingConfig {
|
||||
baud_rate_prescaler: timing.baud_rate_prescaler / 2,
|
||||
..timing
|
||||
};
|
||||
|
||||
timing
|
||||
}
|
||||
@ -802,7 +836,7 @@ where
|
||||
fn set_baud_rate(&mut self, baud_rate: BaudRate) {
|
||||
// TWAI is clocked from the APB_CLK according to Table 6-4 [ESP32C3 Reference Manual](https://www.espressif.com/sites/default/files/documentation/esp32-c3_technical_reference_manual_en.pdf)
|
||||
// Included timings are all for 80MHz so assert that we are running at 80MHz.
|
||||
#[cfg(not(esp32c6))]
|
||||
#[cfg(not(any(esp32h2, esp32c6)))]
|
||||
{
|
||||
let apb_clock = crate::clock::Clocks::get().apb_clock;
|
||||
assert!(apb_clock == fugit::HertzU32::MHz(80));
|
||||
@ -820,22 +854,17 @@ where
|
||||
let tseg_2 = timing.tseg_2 - 1;
|
||||
let triple_sample = timing.triple_sample;
|
||||
|
||||
#[cfg(esp32)]
|
||||
let prescale = prescale as u8;
|
||||
|
||||
// Set up the prescaler and sync jump width.
|
||||
T::register_block()
|
||||
.bus_timing_0()
|
||||
.modify(|_, w| unsafe { w.baud_presc().bits(prescale).sync_jump_width().bits(sjw) });
|
||||
T::register_block().bus_timing_0().modify(|_, w| unsafe {
|
||||
w.baud_presc().bits(prescale as _);
|
||||
w.sync_jump_width().bits(sjw)
|
||||
});
|
||||
|
||||
// Set up the time segment 1, time segment 2, and triple sample.
|
||||
T::register_block().bus_timing_1().modify(|_, w| unsafe {
|
||||
w.time_seg1()
|
||||
.bits(tseg_1)
|
||||
.time_seg2()
|
||||
.bits(tseg_2)
|
||||
.time_samp()
|
||||
.bit(triple_sample)
|
||||
w.time_seg1().bits(tseg_1);
|
||||
w.time_seg2().bits(tseg_2);
|
||||
w.time_samp().bit(triple_sample)
|
||||
});
|
||||
}
|
||||
|
||||
@ -1510,7 +1539,7 @@ impl Instance for crate::peripherals::TWAI0 {
|
||||
#[cfg(any(esp32, esp32c3, esp32s2, esp32s3))]
|
||||
impl OperationInstance for crate::peripherals::TWAI0 {}
|
||||
|
||||
#[cfg(esp32c6)]
|
||||
#[cfg(any(esp32h2, esp32c6))]
|
||||
impl Instance for crate::peripherals::TWAI0 {
|
||||
const SYSTEM_PERIPHERAL: system::Peripheral = system::Peripheral::Twai0;
|
||||
const NUMBER: usize = 0;
|
||||
@ -1554,7 +1583,7 @@ impl Instance for crate::peripherals::TWAI0 {
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(esp32c6)]
|
||||
#[cfg(any(esp32h2, esp32c6))]
|
||||
impl OperationInstance for crate::peripherals::TWAI0 {}
|
||||
|
||||
#[cfg(esp32c6)]
|
||||
@ -1641,7 +1670,7 @@ mod asynch {
|
||||
}
|
||||
}
|
||||
|
||||
const NUM_TWAI: usize = 2;
|
||||
const NUM_TWAI: usize = 1 + cfg!(twai1) as usize;
|
||||
#[allow(clippy::declare_interior_mutable_const)]
|
||||
const NEW_STATE: TwaiAsyncState = TwaiAsyncState::new();
|
||||
pub(crate) static TWAI_STATE: [TwaiAsyncState; NUM_TWAI] = [NEW_STATE; NUM_TWAI];
|
||||
@ -1768,7 +1797,7 @@ mod asynch {
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(esp32c6)]
|
||||
#[cfg(any(esp32h2, esp32c6))]
|
||||
#[handler]
|
||||
pub(super) fn twai0() {
|
||||
let register_block = TWAI0::register_block();
|
||||
|
||||
@ -54,7 +54,7 @@ peripherals = [
|
||||
"timg0",
|
||||
"timg1",
|
||||
"trace0",
|
||||
# "twai0",
|
||||
"twai0",
|
||||
"uart0",
|
||||
"uart1",
|
||||
"uhci0",
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
//! This example sends a CAN message to another ESP and receives it back.
|
||||
//! This example sends a TWAI message to another ESP and receives it back.
|
||||
//!
|
||||
//! This example works without CAN Transceivers by:
|
||||
//! This example works without TWAI transceivers by:
|
||||
//! * setting the tx pins to open drain
|
||||
//! * connecting all rx and tx pins together
|
||||
//! * adding a pull-up to the signal pins
|
||||
@ -17,7 +17,7 @@
|
||||
//! In case you want to use `self-testing`, get rid of everything related to the aforementioned `IS_FIRST_SENDER`
|
||||
//! and follow the advice in the comments related to this mode.
|
||||
|
||||
//% CHIPS: esp32c3 esp32c6 esp32s2 esp32s3
|
||||
//% CHIPS: esp32c3 esp32c6 esp32h2 esp32s2 esp32s3
|
||||
|
||||
#![no_std]
|
||||
#![no_main]
|
||||
@ -39,11 +39,11 @@ fn main() -> ! {
|
||||
|
||||
let io = Io::new(peripherals.GPIO, peripherals.IO_MUX);
|
||||
|
||||
let can_tx_pin = io.pins.gpio0;
|
||||
let can_rx_pin = io.pins.gpio2;
|
||||
let tx_pin = io.pins.gpio0;
|
||||
let rx_pin = io.pins.gpio2;
|
||||
|
||||
// The speed of the CAN bus.
|
||||
const CAN_BAUDRATE: twai::BaudRate = twai::BaudRate::B1000K;
|
||||
const TWAI_BAUDRATE: twai::BaudRate = twai::BaudRate::B1000K;
|
||||
|
||||
// !!! Use `new` when using a transceiver. `new_no_transceiver` sets TX to open-drain
|
||||
// Self-testing also works using the regular `new` function.
|
||||
@ -51,11 +51,11 @@ fn main() -> ! {
|
||||
// Begin configuring the TWAI peripheral. The peripheral is in a reset like
|
||||
// state that prevents transmission but allows configuration.
|
||||
// For self-testing use `SelfTest` mode of the TWAI peripheral.
|
||||
let mut can_config = twai::TwaiConfiguration::new_no_transceiver(
|
||||
let mut twai_config = twai::TwaiConfiguration::new_no_transceiver(
|
||||
peripherals.TWAI0,
|
||||
can_rx_pin,
|
||||
can_tx_pin,
|
||||
CAN_BAUDRATE,
|
||||
rx_pin,
|
||||
tx_pin,
|
||||
TWAI_BAUDRATE,
|
||||
TwaiMode::Normal,
|
||||
);
|
||||
|
||||
@ -67,12 +67,12 @@ fn main() -> ! {
|
||||
// A filter that matches StandardId::ZERO.
|
||||
const FILTER: SingleStandardFilter =
|
||||
SingleStandardFilter::new(b"00000000000", b"x", [b"xxxxxxxx", b"xxxxxxxx"]);
|
||||
can_config.set_filter(FILTER);
|
||||
twai_config.set_filter(FILTER);
|
||||
|
||||
// Start the peripheral. This locks the configuration settings of the peripheral
|
||||
// and puts it into operation mode, allowing packets to be sent and
|
||||
// received.
|
||||
let mut can = can_config.start();
|
||||
let mut can = twai_config.start();
|
||||
|
||||
if IS_FIRST_SENDER {
|
||||
// Send a frame to the other ESP
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
//! Delay Test
|
||||
|
||||
//% CHIPS: esp32 esp32c2 esp32c3 esp32c6 esp32s2 esp32s3
|
||||
//% CHIPS: esp32 esp32c2 esp32c3 esp32c6 esp32h2 esp32s2 esp32s3
|
||||
|
||||
#![no_std]
|
||||
#![no_main]
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
//! TWAI test
|
||||
|
||||
//% CHIPS: esp32c3 esp32c6 esp32s2 esp32s3
|
||||
//% CHIPS: esp32c3 esp32c6 esp32h2 esp32s2 esp32s3
|
||||
|
||||
#![no_std]
|
||||
#![no_main]
|
||||
@ -33,12 +33,12 @@ mod tests {
|
||||
|
||||
let io = Io::new(peripherals.GPIO, peripherals.IO_MUX);
|
||||
|
||||
let (can_tx_pin, can_rx_pin) = hil_test::common_test_pins!(io);
|
||||
let (tx_pin, rx_pin) = hil_test::common_test_pins!(io);
|
||||
|
||||
let mut config = twai::TwaiConfiguration::new(
|
||||
peripherals.TWAI0,
|
||||
can_rx_pin,
|
||||
can_tx_pin,
|
||||
rx_pin,
|
||||
tx_pin,
|
||||
twai::BaudRate::B1000K,
|
||||
TwaiMode::SelfTest,
|
||||
);
|
||||
|
||||
Loading…
Reference in New Issue
Block a user