improve typing support for UART, PWM, SPI #3

Merged
muellerr merged 1 commits from improve-uart-typing into main 2025-12-08 10:04:35 +01:00
28 changed files with 830 additions and 374 deletions
@@ -65,28 +65,26 @@ async fn main(spawner: Spawner) {
let tx_uart_a = porta.pa9;
let rx_uart_a = porta.pa8;
let uarta = uart::Uart::new_with_interrupt(
let uarta = uart::Uart::new_with_interrupt_uart0(
dp.uarta,
tx_uart_a,
rx_uart_a,
50.MHz(),
115200.Hz().into(),
InterruptConfig::new(pac::Interrupt::OC2, true, true),
)
.unwrap();
);
let tx_uart_b = porta.pa3;
let rx_uart_b = porta.pa2;
let uartb = uart::Uart::new_with_interrupt(
let uartb = uart::Uart::new_with_interrupt_uart1(
dp.uartb,
tx_uart_b,
rx_uart_b,
50.MHz(),
115200.Hz().into(),
InterruptConfig::new(pac::Interrupt::OC3, true, true),
)
.unwrap();
);
let (mut tx_uart_a, rx_uart_a) = uarta.split();
let (tx_uart_b, rx_uart_b) = uartb.split();
let (prod_uart_a, cons_uart_a) = QUEUE_UART_A.take().split();
@@ -53,15 +53,14 @@ async fn main(_spawner: Spawner) {
let tx = porta.pa9;
let rx = porta.pa8;
let uarta = uart::Uart::new_with_interrupt(
let uarta = uart::Uart::new_with_interrupt_uart0(
dp.uarta,
tx,
rx,
50.MHz(),
115200.Hz().into(),
InterruptConfig::new(pac::Interrupt::OC2, true, true),
)
.unwrap();
);
let (tx, _rx) = uarta.split();
let mut async_tx = TxAsync::new(tx);
let mut ticker = Ticker::every(Duration::from_secs(1));
@@ -53,15 +53,14 @@ mod app {
let tx = gpioa.pa9;
let rx = gpioa.pa8;
let irq_uart = uart::Uart::new_with_interrupt(
let irq_uart = uart::Uart::new_with_interrupt_uart0(
dp.uarta,
tx,
rx,
SYSCLK_FREQ,
115200.Hz().into(),
InterruptConfig::new(pac::Interrupt::OC3, true, true),
)
.unwrap();
);
let (tx, rx) = irq_uart.split();
let mut rx = rx.into_rx_with_irq();
+1 -1
View File
@@ -23,7 +23,7 @@ fn main() -> ! {
defmt::println!("-- VA108xx PWM example application--");
let dp = pac::Peripherals::take().unwrap();
let pinsa = PinsA::new(dp.porta);
let mut pwm = pwm::PwmPin::new(pinsa.pa3, dp.tim3, 50.MHz(), 10.Hz()).unwrap();
let mut pwm = pwm::PwmPin::new_with_tim3(pinsa.pa3, dp.tim3, 50.MHz(), 10.Hz());
let mut delay = CountdownTimer::new(dp.tim0, 50.MHz());
let mut current_duty_cycle = 0.0;
pwm.set_duty_cycle(get_duty_from_percent(current_duty_cycle))
+3 -3
View File
@@ -59,19 +59,19 @@ fn main() -> ! {
let mut spi = match SPI_BUS_SEL {
SpiBusSelect::SpiAPortA => {
let (sck, mosi, miso) = (pinsa.pa31, pinsa.pa30, pinsa.pa29);
let mut spia = Spi::new(dp.spia, (sck, miso, mosi), spi_cfg).unwrap();
let mut spia = Spi::new_for_spi0(dp.spia, (sck, miso, mosi), spi_cfg);
spia.set_fill_word(FILL_WORD);
spia
}
SpiBusSelect::SpiAPortB => {
let (sck, mosi, miso) = (pinsb.pb9, pinsb.pb8, pinsb.pb7);
let mut spia = Spi::new(dp.spia, (sck, miso, mosi), spi_cfg).unwrap();
let mut spia = Spi::new_for_spi0(dp.spia, (sck, miso, mosi), spi_cfg);
spia.set_fill_word(FILL_WORD);
spia
}
SpiBusSelect::SpiBPortB => {
let (sck, mosi, miso) = (pinsb.pb5, pinsb.pb4, pinsb.pb3);
let mut spib = Spi::new(dp.spib, (sck, miso, mosi), spi_cfg).unwrap();
let mut spib = Spi::new_for_spi1(dp.spib, (sck, miso, mosi), spi_cfg);
spib.set_fill_word(FILL_WORD);
spib
}
+1 -1
View File
@@ -29,7 +29,7 @@ fn main() -> ! {
let tx = gpioa.pa9;
let rx = gpioa.pa8;
let uart =
uart::Uart::new_without_interrupt(dp.uarta, tx, rx, 50.MHz(), 115200.Hz().into()).unwrap();
uart::Uart::new_without_interrupt_uart0(dp.uarta, tx, rx, 50.MHz(), 115200.Hz().into());
let (mut tx, mut rx) = uart.split();
writeln!(tx, "Hello World\r").unwrap();
+2 -3
View File
@@ -116,15 +116,14 @@ mod app {
let tx = gpioa.pa9;
let rx = gpioa.pa8;
let irq_uart = uart::Uart::new_with_interrupt(
let irq_uart = uart::Uart::new_with_interrupt_uart0(
dp.uarta,
tx,
rx,
SYSCLK_FREQ,
UART_BAUDRATE.Hz().into(),
InterruptConfig::new(pac::Interrupt::OC0, true, true),
)
.unwrap();
);
let (tx, rx) = irq_uart.split();
// Unwrap is okay, we explicitely set the interrupt ID.
let mut rx = rx.into_rx_with_irq();
@@ -46,7 +46,7 @@ fn main() -> ! {
)
.mode(MODE_3)
.slave_output_disable(true);
let mut spi = Spi::new(dp.spib, (sck, miso, mosi), spi_cfg).unwrap();
let mut spi = Spi::new_for_spi1(dp.spib, (sck, miso, mosi), spi_cfg);
spi.cfg_hw_cs(hw_cs_id);
let mut tx_rx_buf: [u8; 3] = [0; 3];
+1 -1
View File
@@ -132,7 +132,7 @@ fn main() -> ! {
Output::new(pinsa.pa16, PinState::Low);
let hw_cs_id = configure_pin_as_hw_cs_pin(pinsa.pa17);
let spi = Spi::new(dp.spib, (sck, miso, mosi), spi_cfg).unwrap();
let spi = Spi::new_for_spi1(dp.spib, (sck, miso, mosi), spi_cfg);
let delay_spi = CountdownTimer::new(dp.tim1, SYS_CLK);
let spi_with_hwcs = SpiWithHwCs::new(spi, hw_cs_id, delay_spi);
+1 -1
View File
@@ -64,7 +64,7 @@ pub struct PageBoundaryExceededError;
impl M95M01 {
pub fn new(spi: pac::Spic, clk_config: SpiClockConfig) -> Self {
let spi = RomSpi::new_for_rom(spi, SpiConfig::default().clk_cfg(clk_config)).unwrap();
let spi = RomSpi::new_for_rom(spi, SpiConfig::default().clk_cfg(clk_config));
let mut spi_dev = Self { spi };
spi_dev.clear_block_protection().unwrap();
spi_dev
@@ -17,7 +17,6 @@ use panic_probe as _;
// Import logger.
use core::cell::RefCell;
use defmt_rtt as _;
use defmt_rtt as _;
use critical_section::Mutex;
use embassy_example::EXTCLK_FREQ;
@@ -63,7 +62,7 @@ async fn main(_spawner: Spawner) {
let mut led = Output::new(portg.pg5, PinState::Low);
let uarta =
uart::Uart::new(dp.uart0, portg.pg0, portg.pg1, &clocks, 115200.Hz().into()).unwrap();
uart::Uart::new_for_uart0(dp.uart0, portg.pg0, portg.pg1, &clocks, 115200.Hz().into());
let (mut tx_uart_a, rx_uart_a) = uarta.split();
let (prod_uart_a, cons_uart_a) = QUEUE_UART_A.take().split();
@@ -61,7 +61,7 @@ async fn main(_spawner: Spawner) {
let mut led = Output::new(pinsg.pg5, PinState::Low);
let uarta =
uart::Uart::new(dp.uart0, pinsg.pg0, pinsg.pg1, &clocks, 115200.Hz().into()).unwrap();
uart::Uart::new_for_uart0(dp.uart0, pinsg.pg0, pinsg.pg1, &clocks, 115200.Hz().into());
let (tx, _rx) = uarta.split();
let mut async_tx = TxAsync::new(tx);
let mut ticker = Ticker::every(Duration::from_secs(1));
@@ -67,14 +67,13 @@ async fn main(spawner: Spawner) {
let portg = PinsG::new(dp.portg);
let uart0 = uart::Uart::new(
let uart0 = uart::Uart::new_for_uart0(
dp.uart0,
portg.pg0,
portg.pg1,
&clocks,
Hertz::from_raw(BAUDRATE).into(),
)
.unwrap();
);
let (mut tx, rx) = uart0.split();
let mut rx = rx.into_rx_with_irq();
rx.start();
+1 -1
View File
@@ -32,7 +32,7 @@ fn main() -> ! {
.unwrap();
let pinsg = PinsG::new(dp.portg);
let mut pwm = PwmPin::new(pinsg.pg2, dp.tim9, &clocks, 10.Hz()).unwrap();
let mut pwm = PwmPin::new_with_tim9(pinsg.pg2, dp.tim9, &clocks, 10.Hz());
let mut delay_timer = CountdownTimer::new(dp.tim0, &clocks);
let mut current_duty_cycle = 0.0;
pwm.set_duty_cycle(get_duty_from_percent(current_duty_cycle))
+1 -1
View File
@@ -61,7 +61,7 @@ fn main() -> ! {
spi_cfg = spi_cfg.loopback(true)
}
// Create SPI peripheral.
let mut spi0 = Spi::new(dp.spi0, (pins_b.pb15, pins_c.pc0, pins_c.pc1), spi_cfg).unwrap();
let mut spi0 = Spi::new_for_spi0(dp.spi0, (pins_b.pb15, pins_c.pc0, pins_c.pc1), spi_cfg);
spi0.set_fill_word(FILL_WORD);
loop {
let tx_buf: [u8; 4] = [1, 2, 3, 0];
+2 -3
View File
@@ -30,14 +30,13 @@ fn main() -> ! {
let gpiog = PinsG::new(dp.portg);
let uart0 = uart::Uart::new(
let uart0 = uart::Uart::new_for_uart0(
dp.uart0,
gpiog.pg0,
gpiog.pg1,
&clocks,
Hertz::from_raw(115200).into(),
)
.unwrap();
);
let (mut tx, mut rx) = uart0.split();
writeln!(tx, "Hello World\n\r").unwrap();
loop {
+2 -3
View File
@@ -167,14 +167,13 @@ mod app {
let gpiog = PinsG::new(cx.device.portg);
let uart0 = Uart::new(
let uart0 = Uart::new_for_uart0(
cx.device.uart0,
gpiog.pg0,
gpiog.pg1,
&clocks,
Hertz::from_raw(UART_BAUDRATE).into(),
)
.unwrap();
);
let (tx, rx) = uart0.split();
let verif_reporter = VerificationReportCreator::new(u11::new(0));
+2 -3
View File
@@ -6,15 +6,14 @@
//!
//! - [Flashloader application](https://egit.irs.uni-stuttgart.de/rust/vorago-rs/src/branch/main/va416xx/flashloader)
use embedded_hal::spi::MODE_0;
use vorago_shared_hal::spi::Spi3Instance as _;
use vorago_shared_hal::{
disable_peripheral_clock, enable_peripheral_clock, reset_peripheral_for_cycles,
};
use crate::clock::Clocks;
use crate::pac;
use crate::spi::{
mode_to_cpo_cph_bit, spi_clk_config_from_div, SpiInstance, SpiWord, BMSTART_BMSTOP_MASK,
};
use crate::spi::{mode_to_cpo_cph_bit, spi_clk_config_from_div, SpiWord, BMSTART_BMSTOP_MASK};
const NVM_CLOCK_DIV: u16 = 2;
+82 -27
View File
@@ -1,13 +1,22 @@
use core::convert::Infallible;
use core::marker::PhantomData;
use crate::gpio::IoPeriphPin;
use crate::gpio::{DynPinId, IoPeriphPin};
use crate::timer::enable_tim_clk;
use crate::timer::regs::{EnableControl, StatusSelect};
use crate::{PeripheralSelect, enable_peripheral_clock};
use crate::{FunctionSelect, PeripheralSelect, enable_peripheral_clock};
use crate::time::Hertz;
use crate::timer::{self, TimId, TimInstance, TimPin};
use crate::timer::{self, TimId};
use crate::timer::{
Tim0Instance, Tim0Pin, Tim1Instance, Tim1Pin, Tim2Instance, Tim2Pin, Tim3Instance, Tim3Pin,
Tim4Instance, Tim4Pin, Tim5Instance, Tim5Pin, Tim6Instance, Tim6Pin, Tim7Instance, Tim7Pin,
Tim8Instance, Tim8Pin, Tim9Instance, Tim9Pin, Tim10Instance, Tim10Pin, Tim11Instance, Tim11Pin,
Tim12Instance, Tim12Pin, Tim13Instance, Tim13Pin, Tim14Instance, Tim14Pin, Tim15Instance,
Tim15Pin, Tim16Instance, Tim16Pin, Tim17Instance, Tim17Pin, Tim18Instance, Tim18Pin,
Tim19Instance, Tim19Pin, Tim20Instance, Tim20Pin, Tim21Instance, Tim21Pin, Tim22Instance,
Tim22Pin, Tim23Instance, Tim23Pin,
};
const DUTY_MAX: u16 = u16::MAX;
@@ -18,14 +27,6 @@ pub enum PwmA {}
#[cfg_attr(feature = "defmt", derive(defmt::Format))]
pub enum PwmB {}
#[derive(Debug, thiserror::Error)]
#[cfg_attr(feature = "defmt", derive(defmt::Format))]
#[error("pin tim ID {pin_tim:?} and timer tim id {tim_id:?} do not match")]
pub struct TimMissmatchError {
pin_tim: TimId,
tim_id: TimId,
}
//==================================================================================================
// PWM pin
//==================================================================================================
@@ -44,25 +45,79 @@ pub struct PwmPin<Mode = PwmA> {
mode: PhantomData<Mode>,
}
macro_rules! impl_pwm_new_methods {
(
$(
($tim_name:ident, $pin_trait:ident, $instance_trait:ident)
),*
$(,)?
) => {
paste::paste! {
$(
#[doc = concat!("Create a new PWM pin using ", stringify!($tim_name))]
pub fn [<new_with_ $tim_name:lower>] <Pin: $pin_trait, Tim: $instance_trait>(
_pin: Pin,
_tim: Tim,
#[cfg(feature = "vor1x")] sys_clk: Hertz,
#[cfg(feature = "vor4x")] clks: &crate::clock::Clocks,
initial_frequency: Hertz,
) -> Self {
Self::new(
Pin::PIN_ID,
Pin::FUNC_SEL,
Tim::ID,
#[cfg(feature = "vor1x")]
sys_clk,
#[cfg(feature = "vor4x")]
clks,
initial_frequency,
)
}
)*
}
};
}
impl<Mode> PwmPin<Mode> {
/// Create a new PWM pin
pub fn new<Pin: TimPin, Tim: TimInstance>(
_pin: Pin,
_tim: Tim,
impl_pwm_new_methods! {
(Tim0, Tim0Pin, Tim0Instance),
(Tim1, Tim1Pin, Tim1Instance),
(Tim2, Tim2Pin, Tim2Instance),
(Tim3, Tim3Pin, Tim3Instance),
(Tim4, Tim4Pin, Tim4Instance),
(Tim5, Tim5Pin, Tim5Instance),
(Tim6, Tim6Pin, Tim6Instance),
(Tim7, Tim7Pin, Tim7Instance),
(Tim8, Tim8Pin, Tim8Instance),
(Tim9, Tim9Pin, Tim9Instance),
(Tim10, Tim10Pin, Tim10Instance),
(Tim11, Tim11Pin, Tim11Instance),
(Tim12, Tim12Pin, Tim12Instance),
(Tim13, Tim13Pin, Tim13Instance),
(Tim14, Tim14Pin, Tim14Instance),
(Tim15, Tim15Pin, Tim15Instance),
(Tim16, Tim16Pin, Tim16Instance),
(Tim17, Tim17Pin, Tim17Instance),
(Tim18, Tim18Pin, Tim18Instance),
(Tim19, Tim19Pin, Tim19Instance),
(Tim20, Tim20Pin, Tim20Instance),
(Tim21, Tim21Pin, Tim21Instance),
(Tim22, Tim22Pin, Tim22Instance),
(Tim23, Tim23Pin, Tim23Instance),
}
fn new(
pin_id: DynPinId,
func_sel: FunctionSelect,
tim_id: TimId,
#[cfg(feature = "vor1x")] sys_clk: Hertz,
#[cfg(feature = "vor4x")] clks: &crate::clock::Clocks,
initial_frequency: Hertz,
) -> Result<Self, TimMissmatchError> {
if Pin::TIM_ID != Tim::ID {
return Err(TimMissmatchError {
pin_tim: Pin::TIM_ID,
tim_id: Tim::ID,
});
}
IoPeriphPin::new(Pin::PIN_ID, Pin::FUN_SEL, None);
) -> Self {
IoPeriphPin::new(pin_id, func_sel, None);
let mut pin = PwmPin {
tim_id: Tim::ID,
regs: timer::regs::Timer::new_mmio(Tim::ID),
tim_id,
regs: timer::regs::Timer::new_mmio(tim_id),
current_duty: 0,
current_lower_limit: 0,
current_period: initial_frequency,
@@ -78,10 +133,10 @@ impl<Mode> PwmPin<Mode> {
#[cfg(feature = "vor1x")]
enable_peripheral_clock(PeripheralSelect::Gpio);
enable_peripheral_clock(PeripheralSelect::IoConfig);
enable_tim_clk(Tim::ID);
enable_tim_clk(tim_id);
pin.enable_pwm_a();
pin.set_period(initial_frequency);
Ok(pin)
pin
}
#[inline]
+120 -44
View File
@@ -23,18 +23,48 @@ pub fn configure_pin_as_hw_cs_pin<P: AnyPin + HwCsProvider>(_pin: P) -> HwChipSe
// Pins and traits.
//==================================================================================================
pub trait PinSck: AnyPin {
const SPI_ID: Bank;
pub trait PinSck0: AnyPin {
const SPI_ID: Bank = Bank::Spi0;
const FUN_SEL: FunctionSelect;
}
pub trait PinMosi: AnyPin {
const SPI_ID: Bank;
pub trait PinMosi0: AnyPin {
const SPI_ID: Bank = Bank::Spi0;
const FUN_SEL: FunctionSelect;
}
pub trait PinMiso: AnyPin {
const SPI_ID: Bank;
pub trait PinMiso0: AnyPin {
const SPI_ID: Bank = Bank::Spi0;
const FUN_SEL: FunctionSelect;
}
pub trait PinSck1: AnyPin {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect;
}
pub trait PinMosi1: AnyPin {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect;
}
pub trait PinMiso1: AnyPin {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect;
}
pub trait PinSck2: AnyPin {
const SPI_ID: Bank = Bank::Spi2;
const FUN_SEL: FunctionSelect;
}
pub trait PinMosi2: AnyPin {
const SPI_ID: Bank = Bank::Spi2;
const FUN_SEL: FunctionSelect;
}
pub trait PinMiso2: AnyPin {
const SPI_ID: Bank = Bank::Spi2;
const FUN_SEL: FunctionSelect;
}
@@ -115,10 +145,24 @@ pub const BMSKIPDATA_MASK: u32 = 1 << 30;
pub const DEFAULT_CLK_DIV: u16 = 2;
/// Common trait implemented by all PAC peripheral access structures. The register block
/// format is the same for all SPI blocks.
pub trait SpiInstance: Sealed {
const ID: Bank;
pub trait Spi0Instance: Sealed {
const ID: Bank = Bank::Spi0;
const PERIPH_SEL: PeripheralSelect;
}
pub trait Spi1Instance: Sealed {
const ID: Bank = Bank::Spi1;
const PERIPH_SEL: PeripheralSelect;
}
pub trait Spi2Instance: Sealed {
const ID: Bank = Bank::Spi2;
const PERIPH_SEL: PeripheralSelect;
}
#[cfg(feature = "vor4x")]
pub trait Spi3Instance: Sealed {
const ID: Bank = Bank::Spi3;
const PERIPH_SEL: PeripheralSelect;
}
@@ -127,7 +171,7 @@ pub type Spi0 = pac::Spia;
#[cfg(feature = "vor4x")]
pub type Spi0 = pac::Spi0;
impl SpiInstance for Spi0 {
impl Spi0Instance for Spi0 {
const ID: Bank = Bank::Spi0;
const PERIPH_SEL: PeripheralSelect = PeripheralSelect::Spi0;
}
@@ -138,7 +182,7 @@ pub type Spi1 = pac::Spib;
#[cfg(feature = "vor4x")]
pub type Spi1 = pac::Spi1;
impl SpiInstance for Spi1 {
impl Spi1Instance for Spi1 {
const ID: Bank = Bank::Spi1;
const PERIPH_SEL: PeripheralSelect = PeripheralSelect::Spi1;
}
@@ -149,14 +193,14 @@ pub type Spi2 = pac::Spic;
#[cfg(feature = "vor4x")]
pub type Spi2 = pac::Spi2;
impl SpiInstance for Spi2 {
impl Spi2Instance for Spi2 {
const ID: Bank = Bank::Spi2;
const PERIPH_SEL: PeripheralSelect = PeripheralSelect::Spi2;
}
impl Sealed for Spi2 {}
#[cfg(feature = "vor4x")]
impl SpiInstance for pac::Spi3 {
impl Spi3Instance for pac::Spi3 {
const ID: Bank = Bank::Spi3;
const PERIPH_SEL: PeripheralSelect = PeripheralSelect::Spi3;
}
@@ -468,10 +512,6 @@ pub fn clk_div_for_target_clock(sys_clk: Hertz, spi_clk: Hertz) -> Option<u16> {
Some(rounded_div as u16)
}
#[derive(Debug, thiserror::Error)]
#[error("peripheral or peripheral pin ID is not consistent")]
pub struct SpiIdMissmatchError;
/// SPI peripheral driver structure.
pub struct Spi<Word = u8> {
id: Bank,
@@ -494,22 +534,23 @@ where
///
/// * `spi` - SPI bus to use
/// * `spi_cfg` - Configuration specific to the SPI bus
pub fn new_for_rom<SpiI: SpiInstance>(
spi: SpiI,
spi_cfg: SpiConfig,
) -> Result<Self, SpiIdMissmatchError> {
#[cfg(feature = "vor1x")]
if SpiI::ID != Bank::Spi2 {
return Err(SpiIdMissmatchError);
}
#[cfg(feature = "vor4x")]
if SpiI::ID != Bank::Spi3 {
return Err(SpiIdMissmatchError);
}
Ok(Self::new_generic(spi, spi_cfg))
#[cfg(feature = "vor1x")]
pub fn new_for_rom<Spi: Spi2Instance>(_spi: Spi, spi_cfg: SpiConfig) -> Self {
Self::new_generic(Spi::ID, Spi::PERIPH_SEL, spi_cfg)
}
/// Create a new SPI peripheral driver.
/// Create a new SPI struct for using SPI with the fixed ROM SPI pins.
///
/// ## Arguments
///
/// * `spi` - SPI bus to use
/// * `spi_cfg` - Configuration specific to the SPI bus
#[cfg(feature = "vor4x")]
pub fn new_for_rom<Spi: Spi3Instance>(_spi: Spi, spi_cfg: SpiConfig) -> Self {
Self::new_generic(Spi::ID, Spi::PERIPH_SEL, spi_cfg)
}
/// Create a new SPI peripheral driver for SPI 0.
///
/// ## Arguments
///
@@ -517,23 +558,58 @@ where
/// * `pins` - Pins to be used for SPI transactions. These pins are consumed
/// to ensure the pins can not be used for other purposes anymore
/// * `spi_cfg` - Configuration specific to the SPI bus
pub fn new<SpiI: SpiInstance, Sck: PinSck, Miso: PinMiso, Mosi: PinMosi>(
spi: SpiI,
pub fn new_for_spi0<Spi: Spi0Instance, Sck: PinSck0, Miso: PinMiso0, Mosi: PinMosi0>(
_spi: Spi,
_pins: (Sck, Miso, Mosi),
spi_cfg: SpiConfig,
) -> Result<Self, SpiIdMissmatchError> {
if SpiI::ID != Sck::SPI_ID || SpiI::ID != Miso::SPI_ID || SpiI::ID != Mosi::SPI_ID {
return Err(SpiIdMissmatchError);
}
) -> Self {
IoPeriphPin::new(Sck::ID, Sck::FUN_SEL, None);
IoPeriphPin::new(Miso::ID, Miso::FUN_SEL, None);
IoPeriphPin::new(Mosi::ID, Mosi::FUN_SEL, None);
Ok(Self::new_generic(spi, spi_cfg))
Self::new_generic(Spi::ID, Spi::PERIPH_SEL, spi_cfg)
}
pub fn new_generic<SpiI: SpiInstance>(_spi: SpiI, spi_cfg: SpiConfig) -> Self {
enable_peripheral_clock(SpiI::PERIPH_SEL);
let mut regs = regs::Spi::new_mmio(SpiI::ID);
/// Create a new SPI peripheral driver for SPI 1.
///
/// ## Arguments
///
/// * `spi` - SPI bus to use
/// * `pins` - Pins to be used for SPI transactions. These pins are consumed
/// to ensure the pins can not be used for other purposes anymore
/// * `spi_cfg` - Configuration specific to the SPI bus
pub fn new_for_spi1<Spi: Spi1Instance, Sck: PinSck1, Miso: PinMiso1, Mosi: PinMosi1>(
_spi: Spi,
_pins: (Sck, Miso, Mosi),
spi_cfg: SpiConfig,
) -> Self {
IoPeriphPin::new(Sck::ID, Sck::FUN_SEL, None);
IoPeriphPin::new(Miso::ID, Miso::FUN_SEL, None);
IoPeriphPin::new(Mosi::ID, Mosi::FUN_SEL, None);
Self::new_generic(Spi::ID, Spi::PERIPH_SEL, spi_cfg)
}
/// Create a new SPI peripheral driver for SPI 2.
///
/// ## Arguments
///
/// * `spi` - SPI bus to use
/// * `pins` - Pins to be used for SPI transactions. These pins are consumed
/// to ensure the pins can not be used for other purposes anymore
/// * `spi_cfg` - Configuration specific to the SPI bus
pub fn new_for_spi2<Spi: Spi2Instance, Sck: PinSck2, Miso: PinMiso2, Mosi: PinMosi2>(
_spi: Spi,
_pins: (Sck, Miso, Mosi),
spi_cfg: SpiConfig,
) -> Self {
IoPeriphPin::new(Sck::ID, Sck::FUN_SEL, None);
IoPeriphPin::new(Miso::ID, Miso::FUN_SEL, None);
IoPeriphPin::new(Mosi::ID, Mosi::FUN_SEL, None);
Self::new_generic(Spi::ID, Spi::PERIPH_SEL, spi_cfg)
}
pub fn new_generic(spi_sel: Bank, periph_sel: PeripheralSelect, spi_cfg: SpiConfig) -> Self {
enable_peripheral_clock(periph_sel);
let mut regs = regs::Spi::new_mmio(spi_sel);
let (cpo_bit, cph_bit) = mode_to_cpo_cph_bit(spi_cfg.init_mode);
regs.write_ctrl0(
regs::Control0::builder()
@@ -571,8 +647,8 @@ where
value
});
Spi {
id: SpiI::ID,
regs: regs::Spi::new_mmio(SpiI::ID),
id: spi_sel,
regs: regs::Spi::new_mmio(spi_sel),
cfg: spi_cfg,
fill_word: Default::default(),
bmstall: spi_cfg.bmstall,
+16 -16
View File
@@ -1,4 +1,4 @@
use super::{HwCsProvider, PinMiso, PinMosi, PinSck};
use super::{HwCsProvider, PinMiso0, PinMiso1, PinMosi0, PinMosi1, PinSck0, PinSck1};
use crate::FunctionSelect;
use crate::gpio::{DynPinId, PinId};
@@ -12,28 +12,28 @@ use super::{Bank, HwChipSelectId};
// SPIA
impl PinSck for Pin<Pa31> {
impl PinSck0 for Pin<Pa31> {
const SPI_ID: Bank = Bank::Spi0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl PinMosi for Pin<Pa30> {
impl PinMosi0 for Pin<Pa30> {
const SPI_ID: Bank = Bank::Spi0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl PinMiso for Pin<Pa29> {
impl PinMiso0 for Pin<Pa29> {
const SPI_ID: Bank = Bank::Spi0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl PinSck for Pin<Pb9> {
impl PinSck0 for Pin<Pb9> {
const SPI_ID: Bank = Bank::Spi0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl PinMosi for Pin<Pb8> {
impl PinMosi0 for Pin<Pb8> {
const SPI_ID: Bank = Bank::Spi0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl PinMiso for Pin<Pb7> {
impl PinMiso0 for Pin<Pb7> {
const SPI_ID: Bank = Bank::Spi0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
@@ -100,15 +100,15 @@ hw_cs_multi_pin!(
// SPIB
impl PinSck for Pin<Pa20> {
impl PinSck1 for Pin<Pa20> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl PinMosi for Pin<Pa19> {
impl PinMosi1 for Pin<Pa19> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl PinMiso for Pin<Pa18> {
impl PinMiso1 for Pin<Pa18> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
@@ -117,28 +117,28 @@ pub type SpiBPortASck = Pin<Pa20>;
pub type SpiBPortAMosi = Pin<Pa19>;
pub type SpiBPortAMiso = Pin<Pa18>;
impl PinSck for Pin<Pb19> {
impl PinSck1 for Pin<Pb19> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl PinMosi for Pin<Pb18> {
impl PinMosi1 for Pin<Pb18> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl PinMiso for Pin<Pb17> {
impl PinMiso1 for Pin<Pb17> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl PinSck for Pin<Pb5> {
impl PinSck1 for Pin<Pb5> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl PinMosi for Pin<Pb4> {
impl PinMosi1 for Pin<Pb4> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl PinMiso for Pin<Pb3> {
impl PinMiso1 for Pin<Pb3> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
}
+27 -24
View File
@@ -11,19 +11,22 @@ use crate::{
#[cfg(not(feature = "va41628"))]
use crate::pins::{Pb5, Pb6, Pb7, Pb8, Pb9, Pb10, Pb11, Pe10, Pe11, Pf2, Pf3, Pf4, Pf5, Pf6, Pf7};
use super::{Bank, HwChipSelectId, HwCsProvider, PinMiso, PinMosi, PinSck};
use super::{
Bank, HwChipSelectId, HwCsProvider, PinMiso0, PinMiso1, PinMiso2, PinMosi0, PinMosi1, PinMosi2,
PinSck0, PinSck1, PinSck2,
};
// SPI0
impl PinSck for Pin<Pb15> {
impl PinSck0 for Pin<Pb15> {
const SPI_ID: Bank = Bank::Spi0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl PinMosi for Pin<Pc1> {
impl PinMosi0 for Pin<Pc1> {
const SPI_ID: Bank = Bank::Spi0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl PinMiso for Pin<Pc0> {
impl PinMiso0 for Pin<Pc0> {
const SPI_ID: Bank = Bank::Spi0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
}
@@ -44,68 +47,68 @@ hw_cs_pins!(
// SPI1
#[cfg(not(feature = "va41628"))]
impl PinSck for Pin<Pb8> {
impl PinSck1 for Pin<Pb8> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
}
#[cfg(not(feature = "va41628"))]
impl PinMosi for Pin<Pb10> {
impl PinMosi1 for Pin<Pb10> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
}
#[cfg(not(feature = "va41628"))]
impl PinMiso for Pin<Pb9> {
impl PinMiso1 for Pin<Pb9> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
}
impl PinSck for Pin<Pc9> {
impl PinSck1 for Pin<Pc9> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl PinMosi for Pin<Pc11> {
impl PinMosi1 for Pin<Pc11> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl PinMiso for Pin<Pc10> {
impl PinMiso1 for Pin<Pc10> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl PinSck for Pin<Pe13> {
impl PinSck1 for Pin<Pe13> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl PinMosi for Pin<Pe15> {
impl PinMosi1 for Pin<Pe15> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl PinMiso for Pin<Pe14> {
impl PinMiso1 for Pin<Pe14> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
#[cfg(not(feature = "va41628"))]
impl PinSck for Pin<Pf3> {
impl PinSck1 for Pin<Pf3> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
}
#[cfg(not(feature = "va41628"))]
impl PinMosi for Pin<Pf5> {
impl PinMosi1 for Pin<Pf5> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
}
#[cfg(not(feature = "va41628"))]
impl PinMiso for Pin<Pf4> {
impl PinMiso1 for Pin<Pf4> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl PinSck for Pin<Pg3> {
impl PinSck1 for Pin<Pg3> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl PinMiso for Pin<Pg4> {
impl PinMiso1 for Pin<Pg4> {
const SPI_ID: Bank = Bank::Spi1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
@@ -149,31 +152,31 @@ hw_cs_multi_pin!(
// SPI2
impl PinSck for Pin<Pa5> {
impl PinSck2 for Pin<Pa5> {
const SPI_ID: Bank = Bank::Spi2;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl PinMosi for Pin<Pa7> {
impl PinMosi2 for Pin<Pa7> {
const SPI_ID: Bank = Bank::Spi2;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl PinMiso for Pin<Pa6> {
impl PinMiso2 for Pin<Pa6> {
const SPI_ID: Bank = Bank::Spi2;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
#[cfg(not(feature = "va41628"))]
impl PinSck for Pin<Pf5> {
impl PinSck2 for Pin<Pf5> {
const SPI_ID: Bank = Bank::Spi2;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
#[cfg(not(feature = "va41628"))]
impl PinMosi for Pin<Pf7> {
impl PinMosi2 for Pin<Pf7> {
const SPI_ID: Bank = Bank::Spi2;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
#[cfg(not(feature = "va41628"))]
impl PinMiso for Pin<Pf6> {
impl PinMiso2 for Pin<Pf6> {
const SPI_ID: Bank = Bank::Spi2;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
}
+153 -66
View File
@@ -69,21 +69,54 @@ pub enum CascadeSelect {
// Valid TIM and PIN combinations
//==================================================================================================
pub trait TimPin: AnyPin {
const PIN_ID: DynPinId;
const FUN_SEL: FunctionSelect;
const TIM_ID: TimId;
macro_rules! define_tim_pin_traits {
([$(($tim_name:ident, $index:expr)),* $(,)?]) => {
$(
pub trait $tim_name: AnyPin {
const PIN_ID: DynPinId;
const FUNC_SEL: FunctionSelect;
const TIM_ID: TimId = TimId::new_unchecked($index);
}
)*
};
}
define_tim_pin_traits!([
(Tim0Pin, 0),
(Tim1Pin, 1),
(Tim2Pin, 2),
(Tim3Pin, 3),
(Tim4Pin, 4),
(Tim5Pin, 5),
(Tim6Pin, 6),
(Tim7Pin, 7),
(Tim8Pin, 8),
(Tim9Pin, 9),
(Tim10Pin, 10),
(Tim11Pin, 11),
(Tim12Pin, 12),
(Tim13Pin, 13),
(Tim14Pin, 14),
(Tim15Pin, 15),
(Tim16Pin, 16),
(Tim17Pin, 17),
(Tim18Pin, 18),
(Tim19Pin, 19),
(Tim20Pin, 20),
(Tim21Pin, 21),
(Tim22Pin, 22),
(Tim23Pin, 23),
]);
pub trait TimInstance: Sealed {
// TIM ID ranging from 0 to 23 for 24 TIM peripherals
const ID: TimId;
#[cfg(feature = "vor4x")]
const IRQ: va416xx::Interrupt;
#[cfg(feature = "vor4x")]
fn clock(clocks: &crate::clock::Clocks) -> Hertz {
if Self::ID.value() <= 15 {
if Self::ID.value() < 16 {
clocks.apb1()
} else {
clocks.apb2()
@@ -91,91 +124,145 @@ pub trait TimInstance: Sealed {
}
}
pub trait Tim0Instance: TimInstance {}
pub trait Tim1Instance: TimInstance {}
pub trait Tim2Instance: TimInstance {}
pub trait Tim3Instance: TimInstance {}
pub trait Tim4Instance: TimInstance {}
pub trait Tim5Instance: TimInstance {}
pub trait Tim6Instance: TimInstance {}
pub trait Tim7Instance: TimInstance {}
pub trait Tim8Instance: TimInstance {}
pub trait Tim9Instance: TimInstance {}
pub trait Tim10Instance: TimInstance {}
pub trait Tim11Instance: TimInstance {}
pub trait Tim12Instance: TimInstance {}
pub trait Tim13Instance: TimInstance {}
pub trait Tim14Instance: TimInstance {}
pub trait Tim15Instance: TimInstance {}
pub trait Tim16Instance: TimInstance {}
pub trait Tim17Instance: TimInstance {}
pub trait Tim18Instance: TimInstance {}
pub trait Tim19Instance: TimInstance {}
pub trait Tim20Instance: TimInstance {}
pub trait Tim21Instance: TimInstance {}
pub trait Tim22Instance: TimInstance {}
pub trait Tim23Instance: TimInstance {}
macro_rules! tim_marker {
($TIMX:path, $ID:expr) => {
($TIMX:path, $Trait:ident, $ID:expr) => {
impl Sealed for $TIMX {}
impl TimInstance for $TIMX {
const ID: TimId = TimId::new_unchecked($ID);
}
impl Sealed for $TIMX {}
impl $Trait for $TIMX {}
};
($TIMX:path, $ID:expr, $IrqId:ident) => {
($TIMX:path, $Trait:ident, $ID:expr, $IrqId:ident) => {
impl Sealed for $TIMX {}
impl TimInstance for $TIMX {
const ID: TimId = TimId::new_unchecked($ID);
const IRQ: va416xx::Interrupt = va416xx::Interrupt::$IrqId;
}
impl Sealed for $TIMX {}
impl $Trait for $TIMX {}
};
}
cfg_if::cfg_if! {
if #[cfg(feature = "vor1x")] {
tim_marker!(pac::Tim0, 0);
tim_marker!(pac::Tim1, 1);
tim_marker!(pac::Tim2, 2);
tim_marker!(pac::Tim3, 3);
tim_marker!(pac::Tim4, 4);
tim_marker!(pac::Tim5, 5);
tim_marker!(pac::Tim6, 6);
tim_marker!(pac::Tim7, 7);
tim_marker!(pac::Tim8, 8);
tim_marker!(pac::Tim9, 9);
tim_marker!(pac::Tim10, 10);
tim_marker!(pac::Tim11, 11);
tim_marker!(pac::Tim12, 12);
tim_marker!(pac::Tim13, 13);
tim_marker!(pac::Tim14, 14);
tim_marker!(pac::Tim15, 15);
tim_marker!(pac::Tim16, 16);
tim_marker!(pac::Tim17, 17);
tim_marker!(pac::Tim18, 18);
tim_marker!(pac::Tim19, 19);
tim_marker!(pac::Tim20, 20);
tim_marker!(pac::Tim21, 21);
tim_marker!(pac::Tim22, 22);
tim_marker!(pac::Tim23, 23);
tim_marker!(pac::Tim0, Tim0Instance, 0);
tim_marker!(pac::Tim1, Tim1Instance, 1);
tim_marker!(pac::Tim2, Tim2Instance, 2);
tim_marker!(pac::Tim3, Tim3Instance, 3);
tim_marker!(pac::Tim4, Tim4Instance, 4);
tim_marker!(pac::Tim5, Tim5Instance, 5);
tim_marker!(pac::Tim6, Tim6Instance, 6);
tim_marker!(pac::Tim7, Tim7Instance, 7);
tim_marker!(pac::Tim8, Tim8Instance, 8);
tim_marker!(pac::Tim9, Tim9Instance, 9);
tim_marker!(pac::Tim10, Tim10Instance, 10);
tim_marker!(pac::Tim11, Tim11Instance, 11);
tim_marker!(pac::Tim12, Tim12Instance, 12);
tim_marker!(pac::Tim13, Tim13Instance, 13);
tim_marker!(pac::Tim14, Tim14Instance, 14);
tim_marker!(pac::Tim15, Tim15Instance, 15);
tim_marker!(pac::Tim16, Tim16Instance, 16);
tim_marker!(pac::Tim17, Tim17Instance, 17);
tim_marker!(pac::Tim18, Tim18Instance, 18);
tim_marker!(pac::Tim19, Tim19Instance, 19);
tim_marker!(pac::Tim20, Tim20Instance, 20);
tim_marker!(pac::Tim21, Tim21Instance, 21);
tim_marker!(pac::Tim22, Tim22Instance, 22);
tim_marker!(pac::Tim23, Tim23Instance, 23);
} else if #[cfg(feature = "vor4x")] {
tim_marker!(pac::Tim0, 0, TIM0);
tim_marker!(pac::Tim1, 1, TIM1);
tim_marker!(pac::Tim2, 2, TIM2);
tim_marker!(pac::Tim3, 3, TIM3);
tim_marker!(pac::Tim4, 4, TIM4);
tim_marker!(pac::Tim5, 5, TIM5);
tim_marker!(pac::Tim6, 6, TIM6);
tim_marker!(pac::Tim7, 7, TIM7);
tim_marker!(pac::Tim8, 8, TIM8);
tim_marker!(pac::Tim9, 9, TIM9);
tim_marker!(pac::Tim10, 10, TIM10);
tim_marker!(pac::Tim11, 11, TIM11);
tim_marker!(pac::Tim12, 12, TIM12);
tim_marker!(pac::Tim13, 13, TIM13);
tim_marker!(pac::Tim14, 14, TIM14);
tim_marker!(pac::Tim15, 15, TIM15);
tim_marker!(pac::Tim16, 16, TIM16);
tim_marker!(pac::Tim17, 17, TIM17);
tim_marker!(pac::Tim18, 18, TIM18);
tim_marker!(pac::Tim19, 19, TIM19);
tim_marker!(pac::Tim20, 20, TIM20);
tim_marker!(pac::Tim21, 21, TIM21);
tim_marker!(pac::Tim22, 22, TIM22);
tim_marker!(pac::Tim23, 23, TIM23);
tim_marker!(pac::Tim0, Tim0Instance, 0, TIM0);
tim_marker!(pac::Tim1, Tim1Instance, 1, TIM1);
tim_marker!(pac::Tim2, Tim2Instance, 2, TIM2);
tim_marker!(pac::Tim3, Tim3Instance, 3, TIM3);
tim_marker!(pac::Tim4, Tim4Instance, 4, TIM4);
tim_marker!(pac::Tim5, Tim5Instance, 5, TIM5);
tim_marker!(pac::Tim6, Tim6Instance, 6, TIM6);
tim_marker!(pac::Tim7, Tim7Instance, 7, TIM7);
tim_marker!(pac::Tim8, Tim8Instance, 8, TIM8);
tim_marker!(pac::Tim9, Tim9Instance, 9, TIM9);
tim_marker!(pac::Tim10, Tim10Instance, 10, TIM10);
tim_marker!(pac::Tim11, Tim11Instance, 11, TIM11);
tim_marker!(pac::Tim12, Tim12Instance, 12, TIM12);
tim_marker!(pac::Tim13, Tim13Instance, 13, TIM13);
tim_marker!(pac::Tim14, Tim14Instance, 14, TIM14);
tim_marker!(pac::Tim15, Tim15Instance, 15, TIM15);
tim_marker!(pac::Tim16, Tim16Instance, 16, TIM16);
tim_marker!(pac::Tim17, Tim17Instance, 17, TIM17);
tim_marker!(pac::Tim18, Tim18Instance, 18, TIM18);
tim_marker!(pac::Tim19, Tim19Instance, 19, TIM19);
tim_marker!(pac::Tim20, Tim20Instance, 20, TIM20);
tim_marker!(pac::Tim21, Tim21Instance, 21, TIM21);
tim_marker!(pac::Tim22, Tim22Instance, 22, TIM22);
tim_marker!(pac::Tim23, Tim23Instance, 23, TIM23);
}
}
pub trait ValidTimAndPin<Pin: TimPin, Tim: TimInstance>: Sealed {}
pub trait ValidTimAndPin0<Pin: Tim0Pin, Tim: Tim0Instance>: Sealed {}
pub trait ValidTimAndPin1<Pin: Tim1Pin, Tim: Tim1Instance>: Sealed {}
pub trait ValidTimAndPin2<Pin: Tim2Pin, Tim: Tim2Instance>: Sealed {}
pub trait ValidTimAndPin3<Pin: Tim3Pin, Tim: Tim3Instance>: Sealed {}
pub trait ValidTimAndPin4<Pin: Tim4Pin, Tim: Tim4Instance>: Sealed {}
pub trait ValidTimAndPin5<Pin: Tim5Pin, Tim: Tim5Instance>: Sealed {}
pub trait ValidTimAndPin6<Pin: Tim6Pin, Tim: Tim6Instance>: Sealed {}
pub trait ValidTimAndPin7<Pin: Tim7Pin, Tim: Tim7Instance>: Sealed {}
pub trait ValidTimAndPin8<Pin: Tim8Pin, Tim: Tim8Instance>: Sealed {}
pub trait ValidTimAndPin9<Pin: Tim9Pin, Tim: Tim9Instance>: Sealed {}
pub trait ValidTimAndPin10<Pin: Tim10Pin, Tim: Tim10Instance>: Sealed {}
pub trait ValidTimAndPin11<Pin: Tim11Pin, Tim: Tim11Instance>: Sealed {}
pub trait ValidTimAndPin12<Pin: Tim12Pin, Tim: Tim12Instance>: Sealed {}
pub trait ValidTimAndPin13<Pin: Tim13Pin, Tim: Tim13Instance>: Sealed {}
pub trait ValidTimAndPin14<Pin: Tim14Pin, Tim: Tim14Instance>: Sealed {}
pub trait ValidTimAndPin15<Pin: Tim15Pin, Tim: Tim15Instance>: Sealed {}
pub trait ValidTimAndPin16<Pin: Tim16Pin, Tim: Tim16Instance>: Sealed {}
pub trait ValidTimAndPin17<Pin: Tim17Pin, Tim: Tim17Instance>: Sealed {}
pub trait ValidTimAndPin18<Pin: Tim18Pin, Tim: Tim18Instance>: Sealed {}
pub trait ValidTimAndPin19<Pin: Tim19Pin, Tim: Tim19Instance>: Sealed {}
pub trait ValidTimAndPin20<Pin: Tim20Pin, Tim: Tim20Instance>: Sealed {}
pub trait ValidTimAndPin21<Pin: Tim21Pin, Tim: Tim21Instance>: Sealed {}
pub trait ValidTimAndPin22<Pin: Tim22Pin, Tim: Tim22Instance>: Sealed {}
pub trait ValidTimAndPin23<Pin: Tim23Pin, Tim: Tim23Instance>: Sealed {}
#[macro_use]
mod macros {
macro_rules! pin_and_tim {
($Px:ident, $FunSel:path, $ID:expr) => {
impl TimPin for Pin<$Px>
where
$Px: PinId,
{
const PIN_ID: DynPinId = $Px::ID;
const FUN_SEL: FunctionSelect = $FunSel;
const TIM_ID: TimId = TimId::new_unchecked($ID);
paste::paste! {
impl [<Tim $ID Pin>] for crate::pins::Pin<$Px>
where
$Px: crate::pins::PinId,
{
const PIN_ID: crate::pins::DynPinId = $Px::ID;
const FUNC_SEL: crate::FunctionSelect = $FunSel;
const TIM_ID: crate::timer::TimId = crate::timer::TimId::new_unchecked($ID);
}
}
};
}
+8 -4
View File
@@ -1,9 +1,13 @@
use super::{TimId, TimPin};
use crate::FunctionSelect;
use crate::pins::{
DynPinId, Pa0, Pa1, Pa2, Pa3, Pa4, Pa5, Pa6, Pa7, Pa8, Pa9, Pa10, Pa11, Pa12, Pa13, Pa14, Pa15,
Pa24, Pa25, Pa26, Pa27, Pa28, Pa29, Pa30, Pa31, Pb0, Pb1, Pb2, Pb3, Pb4, Pb5, Pb6, Pb10, Pb11,
Pb12, Pb13, Pb14, Pb15, Pb16, Pb17, Pb18, Pb19, Pb20, Pb21, Pb22, Pb23, Pin, PinId,
Pa0, Pa1, Pa2, Pa3, Pa4, Pa5, Pa6, Pa7, Pa8, Pa9, Pa10, Pa11, Pa12, Pa13, Pa14, Pa15, Pa24,
Pa25, Pa26, Pa27, Pa28, Pa29, Pa30, Pa31, Pb0, Pb1, Pb2, Pb3, Pb4, Pb5, Pb6, Pb10, Pb11, Pb12,
Pb13, Pb14, Pb15, Pb16, Pb17, Pb18, Pb19, Pb20, Pb21, Pb22, Pb23, PinId,
};
use crate::timer::{
Tim0Pin, Tim1Pin, Tim2Pin, Tim3Pin, Tim4Pin, Tim5Pin, Tim6Pin, Tim7Pin, Tim8Pin, Tim9Pin,
Tim10Pin, Tim11Pin, Tim12Pin, Tim13Pin, Tim14Pin, Tim15Pin, Tim16Pin, Tim17Pin, Tim18Pin,
Tim19Pin, Tim20Pin, Tim21Pin, Tim22Pin, Tim23Pin,
};
pin_and_tim!(Pa0, FunctionSelect::Sel1, 0);
+10 -5
View File
@@ -1,15 +1,20 @@
use super::{FunctionSelect, TimId, TimPin};
use super::FunctionSelect;
use crate::pins::{
DynPinId, Pa0, Pa1, Pa2, Pa3, Pa4, Pa5, Pa6, Pa7, Pa8, Pa10, Pa11, Pa12, Pa13, Pa14, Pa15, Pb0,
Pb1, Pb2, Pb3, Pb4, Pb12, Pb13, Pb14, Pb15, Pc0, Pc1, Pd10, Pd11, Pd12, Pd13, Pd14, Pd15, Pe0,
Pe1, Pe2, Pe3, Pe4, Pe5, Pe6, Pe7, Pe8, Pe9, Pe12, Pe13, Pe14, Pe15, Pf0, Pf1, Pf9, Pf11, Pf12,
Pf13, Pf14, Pf15, Pg0, Pg1, Pg2, Pg3, Pg6, Pin, PinId,
Pa0, Pa1, Pa2, Pa3, Pa4, Pa5, Pa6, Pa7, Pa8, Pa10, Pa11, Pa12, Pa13, Pa14, Pa15, Pb0, Pb1, Pb2,
Pb3, Pb4, Pb12, Pb13, Pb14, Pb15, Pc0, Pc1, Pd10, Pd11, Pd12, Pd13, Pd14, Pd15, Pe0, Pe1, Pe2,
Pe3, Pe4, Pe5, Pe6, Pe7, Pe8, Pe9, Pe12, Pe13, Pe14, Pe15, Pf0, Pf1, Pf9, Pf11, Pf12, Pf13,
Pf14, Pf15, Pg0, Pg1, Pg2, Pg3, Pg6, PinId,
};
#[cfg(not(feature = "va41628"))]
use crate::pins::{
Pb5, Pb6, Pb7, Pb8, Pb9, Pb10, Pb11, Pd0, Pd1, Pd2, Pd3, Pd4, Pd5, Pd6, Pd7, Pd8, Pd9, Pe10,
Pe11, Pf2, Pf3, Pf4, Pf5, Pf6, Pf7, Pf8, Pf10,
};
use crate::timer::{
Tim0Pin, Tim1Pin, Tim2Pin, Tim3Pin, Tim4Pin, Tim5Pin, Tim6Pin, Tim7Pin, Tim8Pin, Tim9Pin,
Tim10Pin, Tim11Pin, Tim12Pin, Tim13Pin, Tim14Pin, Tim15Pin, Tim16Pin, Tim17Pin, Tim18Pin,
Tim19Pin, Tim20Pin, Tim21Pin, Tim22Pin, Tim23Pin,
};
pin_and_tim!(Pa0, FunctionSelect::Sel1, 0);
pin_and_tim!(Pa1, FunctionSelect::Sel1, 1);
+302 -66
View File
@@ -16,7 +16,12 @@ use core::convert::Infallible;
pub mod regs;
#[cfg(feature = "vor1x")]
use crate::InterruptConfig;
use crate::{FunctionSelect, gpio::IoPeriphPin, pins::AnyPin, sealed::Sealed};
use crate::{
FunctionSelect,
gpio::{DynPinId, IoPeriphPin},
pins::AnyPin,
sealed::Sealed,
};
use arbitrary_int::{prelude::*, u6, u18};
use fugit::RateExtU32;
use regs::{ClockScale, Control, Data, Enable, FifoClear, InterruptClear, MmioUart};
@@ -47,13 +52,33 @@ pub use rx_asynch::*;
// Type-Level support
//==================================================================================================
pub trait TxPin: AnyPin {
const BANK: Bank;
const FUN_SEL: FunctionSelect;
pub trait TxPin0: AnyPin {
const BANK: Bank = Bank::Uart0;
const FUNC_SEL: FunctionSelect;
}
pub trait RxPin: AnyPin {
const BANK: Bank;
const FUN_SEL: FunctionSelect;
pub trait RxPin0: AnyPin {
const BANK: Bank = Bank::Uart0;
const FUNC_SEL: FunctionSelect;
}
pub trait TxPin1: AnyPin {
const BANK: Bank = Bank::Uart1;
const FUNC_SEL: FunctionSelect;
}
pub trait RxPin1: AnyPin {
const BANK: Bank = Bank::Uart1;
const FUNC_SEL: FunctionSelect;
}
#[cfg(feature = "vor4x")]
pub trait TxPin2: AnyPin {
const BANK: Bank = Bank::Uart2;
const FUNC_SEL: FunctionSelect;
}
#[cfg(feature = "vor4x")]
pub trait RxPin2: AnyPin {
const BANK: Bank = Bank::Uart2;
const FUNC_SEL: FunctionSelect;
}
//==================================================================================================
@@ -319,8 +344,19 @@ pub struct BufferTooShortError {
// UART peripheral wrapper
//==================================================================================================
pub trait UartInstance: Sealed {
const ID: Bank;
pub trait Uart0Instance: Sealed {
const ID: Bank = Bank::Uart0;
const PERIPH_SEL: PeripheralSelect;
}
pub trait Uart1Instance: Sealed {
const ID: Bank = Bank::Uart1;
const PERIPH_SEL: PeripheralSelect;
}
#[cfg(feature = "vor4x")]
pub trait Uart2Instance: Sealed {
const ID: Bank = Bank::Uart2;
const PERIPH_SEL: PeripheralSelect;
}
@@ -329,7 +365,7 @@ pub type Uart0 = pac::Uarta;
#[cfg(feature = "vor4x")]
pub type Uart0 = pac::Uart0;
impl UartInstance for Uart0 {
impl Uart0Instance for Uart0 {
const ID: Bank = Bank::Uart0;
const PERIPH_SEL: PeripheralSelect = PeripheralSelect::Uart0;
}
@@ -340,25 +376,20 @@ pub type Uart1 = pac::Uartb;
#[cfg(feature = "vor4x")]
pub type Uart1 = pac::Uart1;
impl UartInstance for Uart1 {
impl Uart1Instance for Uart1 {
const ID: Bank = Bank::Uart1;
const PERIPH_SEL: PeripheralSelect = PeripheralSelect::Uart1;
}
impl Sealed for Uart1 {}
#[cfg(feature = "vor4x")]
impl UartInstance for pac::Uart2 {
impl Uart2Instance for pac::Uart2 {
const ID: Bank = Bank::Uart2;
const PERIPH_SEL: PeripheralSelect = PeripheralSelect::Uart2;
}
#[cfg(feature = "vor4x")]
impl Sealed for pac::Uart2 {}
#[derive(Debug, thiserror::Error)]
#[cfg_attr(feature = "defmt", derive(defmt::Format))]
#[error("UART ID missmatch between peripheral and pins.")]
pub struct UartIdMissmatchError;
//==================================================================================================
// UART implementation
//==================================================================================================
@@ -372,27 +403,50 @@ pub struct Uart {
impl Uart {
cfg_if::cfg_if! {
if #[cfg(feature = "vor1x")] {
/// Calls [Self::new] with the interrupt configuration to some valid value.
pub fn new_with_interrupt<UartPeriph: UartInstance, Tx: TxPin, Rx: RxPin>(
uart: UartPeriph,
/// Calls [Self::new_for_uart0] with the interrupt configuration to some valid value.
pub fn new_with_interrupt_uart0<Uart: Uart0Instance, Tx: TxPin0, Rx: RxPin0>(
uart: Uart,
tx_pin: Tx,
rx_pin: Rx,
sys_clk: Hertz,
config: Config,
irq_cfg: InterruptConfig,
) -> Result<Self, UartIdMissmatchError> {
Self::new(uart, tx_pin, rx_pin, sys_clk, config, Some(irq_cfg))
) -> Self {
Self::new_for_uart0(uart, tx_pin, rx_pin, sys_clk, config, Some(irq_cfg))
}
/// Calls [Self::new] with the interrupt configuration to [None].
pub fn new_without_interrupt<UartPeriph: UartInstance, Tx: TxPin, Rx: RxPin>(
uart: UartPeriph,
/// Calls [Self::new_for_uart1] with the interrupt configuration to some valid value.
pub fn new_with_interrupt_uart1<Uart: Uart1Instance, Tx: TxPin1, Rx: RxPin1>(
uart: Uart,
tx_pin: Tx,
rx_pin: Rx,
sys_clk: Hertz,
config: Config,
) -> Result<Self, UartIdMissmatchError> {
Self::new(uart, tx_pin, rx_pin, sys_clk, config, None)
irq_cfg: InterruptConfig,
) -> Self {
Self::new_for_uart1(uart, tx_pin, rx_pin, sys_clk, config, Some(irq_cfg))
}
/// Calls [Self::new_for_uart0] with the interrupt configuration to [None].
pub fn new_without_interrupt_uart0<Uart: Uart0Instance, Tx: TxPin0, Rx: RxPin0>(
uart: Uart,
tx_pin: Tx,
rx_pin: Rx,
sys_clk: Hertz,
config: Config,
) -> Self {
Self::new_for_uart0(uart, tx_pin, rx_pin, sys_clk, config, None)
}
/// Calls [Self::new_for_uart1] with the interrupt configuration to [None].
pub fn new_without_interrupt_uart1<Uart: Uart1Instance, Tx: TxPin1, Rx: RxPin1>(
uart: Uart,
tx_pin: Tx,
rx_pin: Rx,
sys_clk: Hertz,
config: Config,
) -> Self {
Self::new_for_uart1(uart, tx_pin, rx_pin, sys_clk, config, None)
}
/// Create a new UART peripheral driver with an interrupt configuration.
@@ -407,18 +461,61 @@ impl Uart {
/// - `irq_cfg`: Optional interrupt configuration. This should be a valid value if the plan
/// is to use TX or RX functionality relying on interrupts. If only the blocking API without
/// any interrupt support is used, this can be [None].
pub fn new<UartPeriph: UartInstance, Tx: TxPin, Rx: RxPin>(
uart: UartPeriph,
tx_pin: Tx,
rx_pin: Rx,
pub fn new_for_uart0<Uart: Uart0Instance, Tx: TxPin0, Rx: RxPin0>(
_uart: Uart,
_tx_pin: Tx,
_rx_pin: Rx,
sys_clk: Hertz,
config: Config,
opt_irq_cfg: Option<InterruptConfig>,
) -> Result<Self, UartIdMissmatchError> {
Self::new_internal(uart, (tx_pin, rx_pin), sys_clk, config, opt_irq_cfg)
) -> Self {
Self::new_internal(
Uart::PERIPH_SEL,
Uart::ID,
Tx::ID,
Tx::FUNC_SEL,
Rx::ID,
Rx::FUNC_SEL,
sys_clk,
config,
opt_irq_cfg
)
}
/// Create a new UART peripheral driver with an interrupt configuration.
///
/// # Arguments
///
/// - `syscfg`: The system configuration register block
/// - `sys_clk`: The system clock frequency
/// - `uart`: The concrete UART peripheral instance.
/// - `pins`: UART TX and RX pin tuple.
/// - `config`: UART specific configuration parameters like baudrate.
/// - `irq_cfg`: Optional interrupt configuration. This should be a valid value if the plan
/// is to use TX or RX functionality relying on interrupts. If only the blocking API without
/// any interrupt support is used, this can be [None].
pub fn new_for_uart1<Uart: Uart1Instance, Tx: TxPin1, Rx: RxPin1>(
_uart: Uart,
_tx_pin: Tx,
_rx_pin: Rx,
sys_clk: Hertz,
config: Config,
opt_irq_cfg: Option<InterruptConfig>,
) -> Self {
Self::new_internal(
Uart::PERIPH_SEL,
Uart::ID,
Tx::ID,
Tx::FUNC_SEL,
Rx::ID,
Rx::FUNC_SEL,
sys_clk,
config,
opt_irq_cfg
)
}
} else if #[cfg(feature = "vor4x")] {
/// Create a new UART peripheral driver.
/// Create a new UART peripheral driver for UART 0.
///
/// # Arguments
///
@@ -426,21 +523,95 @@ impl Uart {
/// - `uart`: The concrete UART peripheral instance.
/// - `pins`: UART TX and RX pin tuple.
/// - `config`: UART specific configuration parameters like baudrate.
pub fn new<UartI: UartInstance, Tx: TxPin, Rx: RxPin>(
uart: UartI,
tx_pin: Tx,
rx_pin: Rx,
pub fn new_for_uart0<Uart: Uart0Instance, Tx: TxPin0, Rx: RxPin0>(
_uart: Uart,
_tx_pin: Tx,
_rx_pin: Rx,
clks: &Clocks,
config: Config,
) -> Result<Self, UartIdMissmatchError> {
if UartI::ID == Bank::Uart2 {
Self::new_internal(uart, (tx_pin, rx_pin), clks.apb1(), config)
) -> Self {
let clk = if Uart::ID == Bank::Uart2 {
clks.apb1()
} else {
Self::new_internal(uart, (tx_pin, rx_pin), clks.apb2(), config)
}
clks.apb2()
};
Self::new_internal(
Uart::PERIPH_SEL,
Uart::ID,
Tx::ID,
Tx::FUNC_SEL,
Rx::ID,
Rx::FUNC_SEL,
clk,
config
)
}
/// Create a new UART peripheral driver given a reference clock.
/// Create a new UART peripheral driver for UART 1.
///
/// # Arguments
///
/// - `clks`: Frozen system clock configuration.
/// - `uart`: The concrete UART peripheral instance.
/// - `pins`: UART TX and RX pin tuple.
/// - `config`: UART specific configuration parameters like baudrate.
pub fn new_for_uart1<Uart: Uart1Instance, Tx: TxPin1, Rx: RxPin1>(
_uart: Uart,
_tx_pin: Tx,
_rx_pin: Rx,
clks: &Clocks,
config: Config,
) -> Self {
let clk = if Uart::ID == Bank::Uart2 {
clks.apb1()
} else {
clks.apb2()
};
Self::new_internal(
Uart::PERIPH_SEL,
Uart::ID,
Tx::ID,
Tx::FUNC_SEL,
Rx::ID,
Rx::FUNC_SEL,
clk,
config
)
}
/// Create a new UART peripheral driver for UART 2.
///
/// # Arguments
///
/// - `clks`: Frozen system clock configuration.
/// - `uart`: The concrete UART peripheral instance.
/// - `pins`: UART TX and RX pin tuple.
/// - `config`: UART specific configuration parameters like baudrate.
pub fn new_for_uart2<Uart: Uart2Instance, Tx: TxPin2, Rx: RxPin2>(
_uart: Uart,
_tx_pin: Tx,
_rx_pin: Rx,
clks: &Clocks,
config: Config,
) -> Self {
let clk = if Uart::ID == Bank::Uart2 {
clks.apb1()
} else {
clks.apb2()
};
Self::new_internal(
Uart::PERIPH_SEL,
Uart::ID,
Tx::ID,
Tx::FUNC_SEL,
Rx::ID,
Rx::FUNC_SEL,
clk,
config
)
}
/// Create a new UART peripheral driver given a reference clock with UART 0.
///
/// # Arguments
///
@@ -448,33 +619,98 @@ impl Uart {
/// - `uart`: The concrete UART peripheral instance.
/// - `pins`: UART TX and RX pin tuple.
/// - `config`: UART specific configuration parameters like baudrate.
pub fn new_with_ref_clk<Uart: UartInstance, Tx: TxPin, Rx: RxPin>(
uart: Uart,
tx_pin: Tx,
rx_pin: Rx,
pub fn new_with_ref_clk_uart0<Uart: Uart0Instance, Tx: TxPin0, Rx: RxPin0>(
_uart: Uart,
_tx_pin: Tx,
_rx_pin: Rx,
ref_clk: Hertz,
config: Config,
) -> Result<Self, UartIdMissmatchError> {
Self::new_internal(uart,(tx_pin, rx_pin),ref_clk, config)
) -> Self {
Self::new_internal(
Uart::PERIPH_SEL,
Uart::ID,
Tx::ID,
Tx::FUNC_SEL,
Rx::ID,
Rx::FUNC_SEL,
ref_clk,
config
)
}
/// Create a new UART peripheral driver given a reference clock with UART 1.
///
/// # Arguments
///
/// - `ref_clk`: APB1 clock for UART2, APB2 clock otherwise.
/// - `uart`: The concrete UART peripheral instance.
/// - `pins`: UART TX and RX pin tuple.
/// - `config`: UART specific configuration parameters like baudrate.
pub fn new_with_ref_clk_uart1<Uart: Uart1Instance, Tx: TxPin1, Rx: RxPin1>(
_uart: Uart,
_tx_pin: Tx,
_rx_pin: Rx,
ref_clk: Hertz,
config: Config,
) -> Self {
Self::new_internal(
Uart::PERIPH_SEL,
Uart::ID,
Tx::ID,
Tx::FUNC_SEL,
Rx::ID,
Rx::FUNC_SEL,
ref_clk,
config
)
}
/// Create a new UART peripheral driver given a reference clock with UART 2.
///
/// # Arguments
///
/// - `ref_clk`: APB1 clock for UART2, APB2 clock otherwise.
/// - `uart`: The concrete UART peripheral instance.
/// - `pins`: UART TX and RX pin tuple.
/// - `config`: UART specific configuration parameters like baudrate.
pub fn new_with_ref_clk_uart2<Uart: Uart2Instance, Tx: TxPin2, Rx: RxPin2>(
_uart: Uart,
_tx_pin: Tx,
_rx_pin: Rx,
ref_clk: Hertz,
config: Config,
) -> Self {
Self::new_internal(
Uart::PERIPH_SEL,
Uart::ID,
Tx::ID,
Tx::FUNC_SEL,
Rx::ID,
Rx::FUNC_SEL,
ref_clk,
config
)
}
}
}
fn new_internal<UartI: UartInstance, TxPinI: TxPin, RxPinI: RxPin>(
_uart: UartI,
_pins: (TxPinI, RxPinI),
#[allow(clippy::too_many_arguments)]
fn new_internal(
periph_sel: PeripheralSelect,
uart_bank: Bank,
tx_pin_id: DynPinId,
tx_func_sel: FunctionSelect,
rx_pin_id: DynPinId,
rx_func_sel: FunctionSelect,
ref_clk: Hertz,
config: Config,
#[cfg(feature = "vor1x")] opt_irq_cfg: Option<InterruptConfig>,
) -> Result<Self, UartIdMissmatchError> {
if UartI::ID != TxPinI::BANK || UartI::ID != RxPinI::BANK {
return Err(UartIdMissmatchError);
}
IoPeriphPin::new(TxPinI::ID, TxPinI::FUN_SEL, None);
IoPeriphPin::new(RxPinI::ID, TxPinI::FUN_SEL, None);
enable_peripheral_clock(UartI::PERIPH_SEL);
) -> Self {
IoPeriphPin::new(tx_pin_id, tx_func_sel, None);
IoPeriphPin::new(rx_pin_id, rx_func_sel, None);
enable_peripheral_clock(periph_sel);
let mut reg_block = regs::Uart::new_mmio(UartI::ID);
let mut reg_block = regs::Uart::new_mmio(uart_bank);
let baud_multiplier = match config.baud8 {
false => 16,
true => 8,
@@ -529,7 +765,7 @@ impl Uart {
if irq_cfg.route {
enable_peripheral_clock(PeripheralSelect::Irqsel);
unsafe { va108xx::Irqsel::steal() }
.uart(UartI::ID as usize)
.uart(uart_bank as usize)
.write(|w| unsafe { w.bits(irq_cfg.id as u32) });
}
if irq_cfg.enable_in_nvic {
@@ -538,10 +774,10 @@ impl Uart {
}
}
Ok(Uart {
tx: Tx::new(UartI::ID),
rx: Rx::new(UartI::ID),
})
Uart {
tx: Tx::new(uart_bank),
rx: Rx::new(uart_bank),
}
}
#[inline]
+45 -45
View File
@@ -8,105 +8,105 @@ use crate::{
},
};
use super::{Bank, RxPin, TxPin};
use super::{Bank, RxPin0, RxPin1, TxPin0, TxPin1};
impl TxPin for Pin<Pa9> {
impl TxPin0 for Pin<Pa9> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl RxPin for Pin<Pa8> {
impl RxPin0 for Pin<Pa8> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl TxPin for Pin<Pa17> {
impl TxPin0 for Pin<Pa17> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel3;
}
impl RxPin for Pin<Pa16> {
impl RxPin0 for Pin<Pa16> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel3;
}
impl TxPin for Pin<Pa31> {
impl TxPin0 for Pin<Pa31> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel3;
}
impl RxPin for Pin<Pa30> {
impl RxPin0 for Pin<Pa30> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel3;
}
impl TxPin for Pin<Pb9> {
impl TxPin0 for Pin<Pb9> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl RxPin for Pin<Pb8> {
impl RxPin0 for Pin<Pb8> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl TxPin for Pin<Pb23> {
impl TxPin0 for Pin<Pb23> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl RxPin for Pin<Pb22> {
impl RxPin0 for Pin<Pb22> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel1;
}
// UART B pins
impl TxPin for Pin<Pa3> {
impl TxPin1 for Pin<Pa3> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl RxPin for Pin<Pa2> {
impl RxPin1 for Pin<Pa2> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl TxPin for Pin<Pa19> {
impl TxPin1 for Pin<Pa19> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel3;
}
impl RxPin for Pin<Pa18> {
impl RxPin1 for Pin<Pa18> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel3;
}
impl TxPin for Pin<Pa27> {
impl TxPin1 for Pin<Pa27> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel3;
}
impl RxPin for Pin<Pa26> {
impl RxPin1 for Pin<Pa26> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel3;
}
impl TxPin for Pin<Pb7> {
impl TxPin1 for Pin<Pb7> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl RxPin for Pin<Pb6> {
impl RxPin1 for Pin<Pb6> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl TxPin for Pin<Pb19> {
impl TxPin1 for Pin<Pb19> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl RxPin for Pin<Pb18> {
impl RxPin1 for Pin<Pb18> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl TxPin for Pin<Pb21> {
impl TxPin1 for Pin<Pb21> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl RxPin for Pin<Pb20> {
impl RxPin1 for Pin<Pb20> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel1;
}
+37 -37
View File
@@ -6,93 +6,93 @@ use crate::{
pins::{Pa2, Pa3, Pb14, Pb15, Pc4, Pc5, Pc14, Pd11, Pd12, Pe2, Pe3, Pf9, Pf12, Pf13, Pg0, Pg1},
};
use super::{Bank, RxPin, TxPin};
use super::{Bank, RxPin0, RxPin1, RxPin2, TxPin0, TxPin1, TxPin2};
// UART 0 pins
impl TxPin for Pin<Pa2> {
impl TxPin0 for Pin<Pa2> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel3;
}
impl RxPin for Pin<Pa3> {
impl RxPin0 for Pin<Pa3> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel3;
}
impl TxPin for Pin<Pc4> {
impl TxPin0 for Pin<Pc4> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl RxPin for Pin<Pc5> {
impl RxPin0 for Pin<Pc5> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel2;
}
impl TxPin for Pin<Pe2> {
impl TxPin0 for Pin<Pe2> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel3;
}
impl RxPin for Pin<Pe3> {
impl RxPin0 for Pin<Pe3> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel3;
}
impl TxPin for Pin<Pg0> {
impl TxPin0 for Pin<Pg0> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl RxPin for Pin<Pg1> {
impl RxPin0 for Pin<Pg1> {
const BANK: Bank = Bank::Uart0;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel1;
}
// UART 1 pins
impl TxPin for Pin<Pb14> {
impl TxPin1 for Pin<Pb14> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel3;
}
impl RxPin for Pin<Pb15> {
impl RxPin1 for Pin<Pb15> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel3;
}
impl TxPin for Pin<Pd11> {
impl TxPin1 for Pin<Pd11> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel3;
}
impl RxPin for Pin<Pd12> {
impl RxPin1 for Pin<Pd12> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel3;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel3;
}
impl TxPin for Pin<Pf12> {
impl TxPin1 for Pin<Pf12> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl RxPin for Pin<Pf13> {
impl RxPin1 for Pin<Pf13> {
const BANK: Bank = Bank::Uart1;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel1;
}
// UART 2 pins
impl TxPin for Pin<Pc14> {
impl TxPin2 for Pin<Pc14> {
const BANK: Bank = Bank::Uart2;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel2;
}
#[cfg(not(feature = "va41628"))]
impl RxPin for Pin<Pc15> {
impl RxPin2 for Pin<Pc15> {
const BANK: Bank = Bank::Uart2;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel2;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel2;
}
#[cfg(not(feature = "va41628"))]
impl TxPin for Pin<Pf8> {
impl TxPin2 for Pin<Pf8> {
const BANK: Bank = Bank::Uart2;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel1;
}
impl RxPin for Pin<Pf9> {
impl RxPin2 for Pin<Pf9> {
const BANK: Bank = Bank::Uart2;
const FUN_SEL: FunctionSelect = FunctionSelect::Sel1;
const FUNC_SEL: FunctionSelect = FunctionSelect::Sel1;
}