diff --git a/embassy-stm32/src/adc/f1.rs b/embassy-stm32/src/adc/f1.rs index cecf67947..80eaecc14 100644 --- a/embassy-stm32/src/adc/f1.rs +++ b/embassy-stm32/src/adc/f1.rs @@ -3,8 +3,8 @@ use core::marker::PhantomData; use core::task::Poll; use embassy_hal_internal::into_ref; -use embedded_hal_02::blocking::delay::DelayUs; +use super::blocking_delay_us; use crate::adc::{Adc, AdcPin, Instance, SampleTime}; use crate::time::Hertz; use crate::{interrupt, Peripheral}; @@ -48,14 +48,14 @@ impl super::SealedAdcPin for Temperature { } impl<'d, T: Instance> Adc<'d, T> { - pub fn new(adc: impl Peripheral

+ 'd, delay: &mut impl DelayUs) -> Self { + pub fn new(adc: impl Peripheral

+ 'd) -> Self { into_ref!(adc); T::enable_and_reset(); T::regs().cr2().modify(|reg| reg.set_adon(true)); // 11.4: Before starting a calibration, the ADC must have been in power-on state (ADON bit = ‘1’) - // for at least two ADC clock cycles - delay.delay_us((1_000_000 * 2) / Self::freq().0 + 1); + // for at least two ADC clock cycles. + blocking_delay_us((1_000_000 * 2) / Self::freq().0 + 1); // Reset calibration T::regs().cr2().modify(|reg| reg.set_rstcal(true)); @@ -70,7 +70,7 @@ impl<'d, T: Instance> Adc<'d, T> { } // One cycle after calibration - delay.delay_us((1_000_000) / Self::freq().0 + 1); + blocking_delay_us((1_000_000 * 1) / Self::freq().0 + 1); Self { adc, @@ -95,7 +95,7 @@ impl<'d, T: Instance> Adc<'d, T> { } } - pub fn enable_vref(&self, _delay: &mut impl DelayUs) -> Vref { + pub fn enable_vref(&self) -> Vref { T::regs().cr2().modify(|reg| { reg.set_tsvrefe(true); }); diff --git a/embassy-stm32/src/adc/f3.rs b/embassy-stm32/src/adc/f3.rs index c5581dba1..c22a3fe4a 100644 --- a/embassy-stm32/src/adc/f3.rs +++ b/embassy-stm32/src/adc/f3.rs @@ -3,8 +3,8 @@ use core::marker::PhantomData; use core::task::Poll; use embassy_hal_internal::into_ref; -use embedded_hal_02::blocking::delay::DelayUs; +use super::blocking_delay_us; use crate::adc::{Adc, AdcPin, Instance, SampleTime}; use crate::interrupt::typelevel::Interrupt; use crate::time::Hertz; @@ -58,7 +58,6 @@ impl<'d, T: Instance> Adc<'d, T> { pub fn new( adc: impl Peripheral

+ 'd, _irq: impl interrupt::typelevel::Binding> + 'd, - delay: &mut impl DelayUs, ) -> Self { use crate::pac::adc::vals; @@ -71,7 +70,7 @@ impl<'d, T: Instance> Adc<'d, T> { T::regs().cr().modify(|w| w.set_advregen(vals::Advregen::ENABLED)); // Wait for the regulator to stabilize - delay.delay_us(10); + blocking_delay_us(10); assert!(!T::regs().cr().read().aden()); @@ -81,8 +80,8 @@ impl<'d, T: Instance> Adc<'d, T> { while T::regs().cr().read().adcal() {} - // Wait more than 4 clock cycles after adcal is cleared (RM0364 p. 223) - delay.delay_us(1 + (6 * 1_000_000 / Self::freq().0)); + // Wait more than 4 clock cycles after adcal is cleared (RM0364 p. 223). + blocking_delay_us((1_000_000 * 4) / Self::freq().0 + 1); // Enable the adc T::regs().cr().modify(|w| w.set_aden(true)); @@ -117,7 +116,7 @@ impl<'d, T: Instance> Adc<'d, T> { } } - pub fn enable_vref(&self, _delay: &mut impl DelayUs) -> Vref { + pub fn enable_vref(&self) -> Vref { T::common_regs().ccr().modify(|w| w.set_vrefen(true)); Vref {} diff --git a/embassy-stm32/src/adc/mod.rs b/embassy-stm32/src/adc/mod.rs index ead2357ce..24dd7cc3c 100644 --- a/embassy-stm32/src/adc/mod.rs +++ b/embassy-stm32/src/adc/mod.rs @@ -69,6 +69,15 @@ trait SealedInternalChannel { fn channel(&self) -> u8; } +/// Performs a busy-wait delay for a specified number of microseconds. +#[allow(unused)] +pub(crate) fn blocking_delay_us(us: u32) { + #[cfg(time)] + embassy_time::block_for(embassy_time::Duration::from_micros(us)); + #[cfg(not(time))] + cortex_m::asm::delay(unsafe { crate::rcc::get_freqs() }.sys.unwrap().0 * us / 1_000_000); +} + /// ADC instance. #[cfg(not(any(adc_f1, adc_v1, adc_l0, adc_v2, adc_v3, adc_v4, adc_f3, adc_f3_v1_1, adc_g0, adc_h5)))] #[allow(private_bounds)] diff --git a/embassy-stm32/src/adc/v1.rs b/embassy-stm32/src/adc/v1.rs index e9b46be80..1dda28cf2 100644 --- a/embassy-stm32/src/adc/v1.rs +++ b/embassy-stm32/src/adc/v1.rs @@ -3,10 +3,10 @@ use core::marker::PhantomData; use core::task::Poll; use embassy_hal_internal::into_ref; -use embedded_hal_02::blocking::delay::DelayUs; #[cfg(adc_l0)] use stm32_metapac::adc::vals::Ckmode; +use super::blocking_delay_us; use crate::adc::{Adc, AdcPin, Instance, Resolution, SampleTime}; use crate::interrupt::typelevel::Interrupt; use crate::peripherals::ADC; @@ -65,7 +65,6 @@ impl<'d, T: Instance> Adc<'d, T> { pub fn new( adc: impl Peripheral

+ 'd, _irq: impl interrupt::typelevel::Binding> + 'd, - delay: &mut impl DelayUs, ) -> Self { into_ref!(adc); T::enable_and_reset(); @@ -74,7 +73,7 @@ impl<'d, T: Instance> Adc<'d, T> { // // Table 57. ADC characteristics // tstab = 14 * 1/fadc - delay.delay_us(1); + blocking_delay_us(1); // set default PCKL/2 on L0s because HSI is disabled in the default clock config #[cfg(adc_l0)] @@ -114,7 +113,7 @@ impl<'d, T: Instance> Adc<'d, T> { } #[cfg(not(adc_l0))] - pub fn enable_vbat(&self, _delay: &mut impl DelayUs) -> Vbat { + pub fn enable_vbat(&self) -> Vbat { // SMP must be ≥ 56 ADC clock cycles when using HSI14. // // 6.3.20 Vbat monitoring characteristics @@ -123,22 +122,22 @@ impl<'d, T: Instance> Adc<'d, T> { Vbat } - pub fn enable_vref(&self, delay: &mut impl DelayUs) -> Vref { + pub fn enable_vref(&self) -> Vref { // Table 28. Embedded internal reference voltage // tstart = 10μs T::regs().ccr().modify(|reg| reg.set_vrefen(true)); - delay.delay_us(10); + blocking_delay_us(10); Vref } - pub fn enable_temperature(&self, delay: &mut impl DelayUs) -> Temperature { + pub fn enable_temperature(&self) -> Temperature { // SMP must be ≥ 56 ADC clock cycles when using HSI14. // // 6.3.19 Temperature sensor characteristics // tstart ≤ 10μs // ts_temp ≥ 4μs T::regs().ccr().modify(|reg| reg.set_tsen(true)); - delay.delay_us(10); + blocking_delay_us(10); Temperature } diff --git a/embassy-stm32/src/adc/v2.rs b/embassy-stm32/src/adc/v2.rs index a43eb72db..7771cf768 100644 --- a/embassy-stm32/src/adc/v2.rs +++ b/embassy-stm32/src/adc/v2.rs @@ -1,6 +1,6 @@ use embassy_hal_internal::into_ref; -use embedded_hal_02::blocking::delay::DelayUs; +use super::blocking_delay_us; use crate::adc::{Adc, AdcPin, Instance, Resolution, SampleTime}; use crate::peripherals::ADC1; use crate::time::Hertz; @@ -11,9 +11,6 @@ pub const VREF_DEFAULT_MV: u32 = 3300; /// VREF voltage used for factory calibration of VREFINTCAL register. pub const VREF_CALIB_MV: u32 = 3300; -/// ADC turn-on time -pub const ADC_POWERUP_TIME_US: u32 = 3; - pub struct VrefInt; impl AdcPin for VrefInt {} impl super::SealedAdcPin for VrefInt { @@ -97,7 +94,7 @@ impl<'d, T> Adc<'d, T> where T: Instance, { - pub fn new(adc: impl Peripheral

+ 'd, delay: &mut impl DelayUs) -> Self { + pub fn new(adc: impl Peripheral

+ 'd) -> Self { into_ref!(adc); T::enable_and_reset(); @@ -107,7 +104,7 @@ where reg.set_adon(true); }); - delay.delay_us(ADC_POWERUP_TIME_US); + blocking_delay_us(3); Self { adc, diff --git a/embassy-stm32/src/adc/v3.rs b/embassy-stm32/src/adc/v3.rs index e25630be2..4fd8558ba 100644 --- a/embassy-stm32/src/adc/v3.rs +++ b/embassy-stm32/src/adc/v3.rs @@ -1,7 +1,7 @@ use cfg_if::cfg_if; use embassy_hal_internal::into_ref; -use embedded_hal_02::blocking::delay::DelayUs; +use super::blocking_delay_us; use crate::adc::{Adc, AdcPin, Instance, Resolution, SampleTime}; use crate::Peripheral; @@ -74,7 +74,7 @@ cfg_if! { } impl<'d, T: Instance> Adc<'d, T> { - pub fn new(adc: impl Peripheral

+ 'd, delay: &mut impl DelayUs) -> Self { + pub fn new(adc: impl Peripheral

+ 'd) -> Self { into_ref!(adc); T::enable_and_reset(); T::regs().cr().modify(|reg| { @@ -88,7 +88,7 @@ impl<'d, T: Instance> Adc<'d, T> { reg.set_chselrmod(false); }); - delay.delay_us(20); + blocking_delay_us(20); T::regs().cr().modify(|reg| { reg.set_adcal(true); @@ -98,7 +98,7 @@ impl<'d, T: Instance> Adc<'d, T> { // spin } - delay.delay_us(1); + blocking_delay_us(1); Self { adc, @@ -106,7 +106,7 @@ impl<'d, T: Instance> Adc<'d, T> { } } - pub fn enable_vrefint(&self, delay: &mut impl DelayUs) -> VrefInt { + pub fn enable_vrefint(&self) -> VrefInt { #[cfg(not(adc_g0))] T::common_regs().ccr().modify(|reg| { reg.set_vrefen(true); @@ -117,10 +117,8 @@ impl<'d, T: Instance> Adc<'d, T> { }); // "Table 24. Embedded internal voltage reference" states that it takes a maximum of 12 us - // to stabilize the internal voltage reference, we wait a little more. - // TODO: delay 15us - //cortex_m::asm::delay(20_000_000); - delay.delay_us(15); + // to stabilize the internal voltage reference. + blocking_delay_us(15); VrefInt {} } diff --git a/embassy-stm32/src/adc/v4.rs b/embassy-stm32/src/adc/v4.rs index 1ae25bea2..ca87b41ee 100644 --- a/embassy-stm32/src/adc/v4.rs +++ b/embassy-stm32/src/adc/v4.rs @@ -1,9 +1,8 @@ -use embedded_hal_02::blocking::delay::DelayUs; #[allow(unused)] use pac::adc::vals::{Adcaldif, Boost, Difsel, Exten, Pcsel}; use pac::adccommon::vals::Presc; -use super::{Adc, AdcPin, Instance, InternalChannel, Resolution, SampleTime}; +use super::{blocking_delay_us, Adc, AdcPin, Instance, InternalChannel, Resolution, SampleTime}; use crate::time::Hertz; use crate::{pac, Peripheral}; @@ -129,7 +128,7 @@ impl Prescaler { impl<'d, T: Instance> Adc<'d, T> { /// Create a new ADC driver. - pub fn new(adc: impl Peripheral

+ 'd, delay: &mut impl DelayUs) -> Self { + pub fn new(adc: impl Peripheral

+ 'd) -> Self { embassy_hal_internal::into_ref!(adc); T::enable_and_reset(); @@ -161,11 +160,11 @@ impl<'d, T: Instance> Adc<'d, T> { adc, sample_time: SampleTime::from_bits(0), }; - s.power_up(delay); + s.power_up(); s.configure_differential_inputs(); s.calibrate(); - delay.delay_us(1); + blocking_delay_us(1); s.enable(); s.configure(); @@ -173,13 +172,13 @@ impl<'d, T: Instance> Adc<'d, T> { s } - fn power_up(&mut self, delay: &mut impl DelayUs) { + fn power_up(&mut self) { T::regs().cr().modify(|reg| { reg.set_deeppwd(false); reg.set_advregen(true); }); - delay.delay_us(10); + blocking_delay_us(10); } fn configure_differential_inputs(&mut self) { diff --git a/examples/stm32f0/src/bin/adc.rs b/examples/stm32f0/src/bin/adc.rs index c2fb143cd..a5a4186ea 100644 --- a/examples/stm32f0/src/bin/adc.rs +++ b/examples/stm32f0/src/bin/adc.rs @@ -6,7 +6,7 @@ use embassy_executor::Spawner; use embassy_stm32::adc::{Adc, SampleTime}; use embassy_stm32::peripherals::ADC; use embassy_stm32::{adc, bind_interrupts}; -use embassy_time::{Delay, Timer}; +use embassy_time::Timer; use {defmt_rtt as _, panic_probe as _}; bind_interrupts!(struct Irqs { @@ -18,11 +18,11 @@ async fn main(_spawner: Spawner) { let p = embassy_stm32::init(Default::default()); info!("Hello World!"); - let mut adc = Adc::new(p.ADC, Irqs, &mut Delay); + let mut adc = Adc::new(p.ADC, Irqs); adc.set_sample_time(SampleTime::CYCLES71_5); let mut pin = p.PA1; - let mut vrefint = adc.enable_vref(&mut Delay); + let mut vrefint = adc.enable_vref(); let vrefint_sample = adc.read(&mut vrefint).await; let convert_to_millivolts = |sample| { // From https://www.st.com/resource/en/datasheet/stm32f031c6.pdf diff --git a/examples/stm32f1/src/bin/adc.rs b/examples/stm32f1/src/bin/adc.rs index 1440460a9..541ff159e 100644 --- a/examples/stm32f1/src/bin/adc.rs +++ b/examples/stm32f1/src/bin/adc.rs @@ -6,7 +6,7 @@ use embassy_executor::Spawner; use embassy_stm32::adc::Adc; use embassy_stm32::peripherals::ADC1; use embassy_stm32::{adc, bind_interrupts}; -use embassy_time::{Delay, Timer}; +use embassy_time::Timer; use {defmt_rtt as _, panic_probe as _}; bind_interrupts!(struct Irqs { @@ -18,10 +18,10 @@ async fn main(_spawner: Spawner) { let p = embassy_stm32::init(Default::default()); info!("Hello World!"); - let mut adc = Adc::new(p.ADC1, &mut Delay); + let mut adc = Adc::new(p.ADC1); let mut pin = p.PB1; - let mut vrefint = adc.enable_vref(&mut Delay); + let mut vrefint = adc.enable_vref(); let vrefint_sample = adc.read(&mut vrefint).await; let convert_to_millivolts = |sample| { // From http://www.st.com/resource/en/datasheet/CD00161566.pdf diff --git a/examples/stm32f334/src/bin/adc.rs b/examples/stm32f334/src/bin/adc.rs index bd126ce68..0528a9637 100644 --- a/examples/stm32f334/src/bin/adc.rs +++ b/examples/stm32f334/src/bin/adc.rs @@ -7,7 +7,7 @@ use embassy_stm32::adc::{Adc, SampleTime}; use embassy_stm32::peripherals::ADC1; use embassy_stm32::time::mhz; use embassy_stm32::{adc, bind_interrupts, Config}; -use embassy_time::{Delay, Timer}; +use embassy_time::Timer; use {defmt_rtt as _, panic_probe as _}; bind_interrupts!(struct Irqs { @@ -38,13 +38,13 @@ async fn main(_spawner: Spawner) -> ! { info!("create adc..."); - let mut adc = Adc::new(p.ADC1, Irqs, &mut Delay); + let mut adc = Adc::new(p.ADC1, Irqs); adc.set_sample_time(SampleTime::CYCLES601_5); info!("enable vrefint..."); - let mut vrefint = adc.enable_vref(&mut Delay); + let mut vrefint = adc.enable_vref(); let mut temperature = adc.enable_temperature(); loop { diff --git a/examples/stm32f334/src/bin/opamp.rs b/examples/stm32f334/src/bin/opamp.rs index a5c710aa2..2dbf1bdab 100644 --- a/examples/stm32f334/src/bin/opamp.rs +++ b/examples/stm32f334/src/bin/opamp.rs @@ -8,7 +8,7 @@ use embassy_stm32::opamp::{OpAmp, OpAmpGain}; use embassy_stm32::peripherals::ADC2; use embassy_stm32::time::mhz; use embassy_stm32::{adc, bind_interrupts, Config}; -use embassy_time::{Delay, Timer}; +use embassy_time::Timer; use {defmt_rtt as _, panic_probe as _}; bind_interrupts!(struct Irqs { @@ -39,14 +39,14 @@ async fn main(_spawner: Spawner) -> ! { info!("create adc..."); - let mut adc = Adc::new(p.ADC2, Irqs, &mut Delay); + let mut adc = Adc::new(p.ADC2, Irqs); let mut opamp = OpAmp::new(p.OPAMP2); adc.set_sample_time(SampleTime::CYCLES601_5); info!("enable vrefint..."); - let mut vrefint = adc.enable_vref(&mut Delay); + let mut vrefint = adc.enable_vref(); let mut temperature = adc.enable_temperature(); let mut buffer = opamp.buffer_ext(&mut p.PA7, &mut p.PA6, OpAmpGain::Mul1); diff --git a/examples/stm32f4/src/bin/adc.rs b/examples/stm32f4/src/bin/adc.rs index 699c29c05..9473b7b7f 100644 --- a/examples/stm32f4/src/bin/adc.rs +++ b/examples/stm32f4/src/bin/adc.rs @@ -14,7 +14,7 @@ async fn main(_spawner: Spawner) { info!("Hello World!"); let mut delay = Delay; - let mut adc = Adc::new(p.ADC1, &mut delay); + let mut adc = Adc::new(p.ADC1); let mut pin = p.PC1; let mut vrefint = adc.enable_vrefint(); diff --git a/examples/stm32f7/src/bin/adc.rs b/examples/stm32f7/src/bin/adc.rs index f8d7b691f..641157960 100644 --- a/examples/stm32f7/src/bin/adc.rs +++ b/examples/stm32f7/src/bin/adc.rs @@ -4,7 +4,7 @@ use defmt::*; use embassy_executor::Spawner; use embassy_stm32::adc::Adc; -use embassy_time::{Delay, Timer}; +use embassy_time::Timer; use {defmt_rtt as _, panic_probe as _}; #[embassy_executor::main] @@ -12,7 +12,7 @@ async fn main(_spawner: Spawner) { let p = embassy_stm32::init(Default::default()); info!("Hello World!"); - let mut adc = Adc::new(p.ADC1, &mut Delay); + let mut adc = Adc::new(p.ADC1); let mut pin = p.PA3; let mut vrefint = adc.enable_vrefint(); diff --git a/examples/stm32g4/src/bin/adc.rs b/examples/stm32g4/src/bin/adc.rs index ae64bc8e4..68b54e406 100644 --- a/examples/stm32g4/src/bin/adc.rs +++ b/examples/stm32g4/src/bin/adc.rs @@ -5,7 +5,7 @@ use defmt::*; use embassy_executor::Spawner; use embassy_stm32::adc::{Adc, SampleTime}; use embassy_stm32::Config; -use embassy_time::{Delay, Timer}; +use embassy_time::Timer; use {defmt_rtt as _, panic_probe as _}; #[embassy_executor::main] @@ -28,7 +28,7 @@ async fn main(_spawner: Spawner) { let mut p = embassy_stm32::init(config); info!("Hello World!"); - let mut adc = Adc::new(p.ADC2, &mut Delay); + let mut adc = Adc::new(p.ADC2); adc.set_sample_time(SampleTime::CYCLES32_5); loop { diff --git a/examples/stm32h7/src/bin/adc.rs b/examples/stm32h7/src/bin/adc.rs index a5594d10c..0009103d1 100644 --- a/examples/stm32h7/src/bin/adc.rs +++ b/examples/stm32h7/src/bin/adc.rs @@ -5,7 +5,7 @@ use defmt::*; use embassy_executor::Spawner; use embassy_stm32::adc::{Adc, SampleTime}; use embassy_stm32::Config; -use embassy_time::{Delay, Timer}; +use embassy_time::Timer; use {defmt_rtt as _, panic_probe as _}; #[embassy_executor::main] @@ -44,7 +44,7 @@ async fn main(_spawner: Spawner) { info!("Hello World!"); - let mut adc = Adc::new(p.ADC3, &mut Delay); + let mut adc = Adc::new(p.ADC3); adc.set_sample_time(SampleTime::CYCLES32_5); diff --git a/examples/stm32l0/src/bin/adc.rs b/examples/stm32l0/src/bin/adc.rs index 97d41ca4b..507c3204a 100644 --- a/examples/stm32l0/src/bin/adc.rs +++ b/examples/stm32l0/src/bin/adc.rs @@ -6,7 +6,7 @@ use embassy_executor::Spawner; use embassy_stm32::adc::{Adc, SampleTime}; use embassy_stm32::peripherals::ADC; use embassy_stm32::{adc, bind_interrupts}; -use embassy_time::{Delay, Timer}; +use embassy_time::Timer; use {defmt_rtt as _, panic_probe as _}; bind_interrupts!(struct Irqs { @@ -18,11 +18,11 @@ async fn main(_spawner: Spawner) { let p = embassy_stm32::init(Default::default()); info!("Hello World!"); - let mut adc = Adc::new(p.ADC, Irqs, &mut Delay); + let mut adc = Adc::new(p.ADC, Irqs); adc.set_sample_time(SampleTime::CYCLES79_5); let mut pin = p.PA1; - let mut vrefint = adc.enable_vref(&mut Delay); + let mut vrefint = adc.enable_vref(); let vrefint_sample = adc.read(&mut vrefint).await; let convert_to_millivolts = |sample| { // From https://www.st.com/resource/en/datasheet/stm32l051c6.pdf diff --git a/examples/stm32l4/src/bin/adc.rs b/examples/stm32l4/src/bin/adc.rs index a9f4604aa..7a89334e0 100644 --- a/examples/stm32l4/src/bin/adc.rs +++ b/examples/stm32l4/src/bin/adc.rs @@ -4,7 +4,6 @@ use defmt::*; use embassy_stm32::adc::{Adc, Resolution}; use embassy_stm32::Config; -use embassy_time::Delay; use {defmt_rtt as _, panic_probe as _}; #[cortex_m_rt::entry] @@ -18,7 +17,7 @@ fn main() -> ! { } let p = embassy_stm32::init(config); - let mut adc = Adc::new(p.ADC1, &mut Delay); + let mut adc = Adc::new(p.ADC1); //adc.enable_vref(); adc.set_resolution(Resolution::BITS8); let mut channel = p.PC0; diff --git a/tests/stm32/src/bin/dac.rs b/tests/stm32/src/bin/dac.rs index 9d64742df..06501ab14 100644 --- a/tests/stm32/src/bin/dac.rs +++ b/tests/stm32/src/bin/dac.rs @@ -13,7 +13,7 @@ use embassy_executor::Spawner; use embassy_stm32::adc::Adc; use embassy_stm32::dac::{DacCh1, Value}; use embassy_stm32::dma::NoDma; -use embassy_time::{Delay, Timer}; +use embassy_time::Timer; use micromath::F32Ext; use {defmt_rtt as _, panic_probe as _}; @@ -28,7 +28,7 @@ async fn main(_spawner: Spawner) { let mut adc_pin = unsafe { core::ptr::read(&dac_pin) }; let mut dac = DacCh1::new(dac, NoDma, dac_pin); - let mut adc = Adc::new(adc, &mut Delay); + let mut adc = Adc::new(adc); #[cfg(feature = "stm32h755zi")] let normalization_factor = 256;