aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDario Nieuwenhuis <[email protected]>2025-03-11 18:09:47 +0000
committerGitHub <[email protected]>2025-03-11 18:09:47 +0000
commit38f26137fc67beb874aa73c9a7ab2150d9f3d372 (patch)
tree84d33d192ffdc78dbb5a1482fb520235d7cbbc0c
parent5af720d9bb74f39d376d4dc22def649146da1d68 (diff)
parent5e3cfc7b5c3b0dbadb37870462741d6b417cf028 (diff)
Merge pull request #3950 from Matt-Allen-Bose/stm32-pwm-pin-config
Add ability to create STM32 timer channels with full pin configuration
-rw-r--r--embassy-stm32/src/lptim/pwm.rs44
-rw-r--r--embassy-stm32/src/timer/simple_pwm.rs47
2 files changed, 82 insertions, 9 deletions
diff --git a/embassy-stm32/src/lptim/pwm.rs b/embassy-stm32/src/lptim/pwm.rs
index 1f43eb6ee..132f5815e 100644
--- a/embassy-stm32/src/lptim/pwm.rs
+++ b/embassy-stm32/src/lptim/pwm.rs
@@ -10,6 +10,8 @@ use super::OutputPin;
10#[cfg(any(lptim_v2a, lptim_v2b))] 10#[cfg(any(lptim_v2a, lptim_v2b))]
11use super::{channel::Channel, timer::ChannelDirection, Channel1Pin, Channel2Pin}; 11use super::{channel::Channel, timer::ChannelDirection, Channel1Pin, Channel2Pin};
12use super::{BasicInstance, Instance}; 12use super::{BasicInstance, Instance};
13#[cfg(gpio_v2)]
14use crate::gpio::Pull;
13use crate::gpio::{AfType, AnyPin, OutputType, Speed}; 15use crate::gpio::{AfType, AnyPin, OutputType, Speed};
14use crate::time::Hertz; 16use crate::time::Hertz;
15use crate::Peripheral; 17use crate::Peripheral;
@@ -29,8 +31,21 @@ pub struct PwmPin<'d, T, C> {
29 phantom: PhantomData<(T, C)>, 31 phantom: PhantomData<(T, C)>,
30} 32}
31 33
34/// PWM pin config
35///
36/// This configures the pwm pin settings
37pub struct PwmPinConfig {
38 /// PWM Pin output type
39 pub output_type: OutputType,
40 /// PWM Pin speed
41 pub speed: Speed,
42 /// PWM Pin pull type
43 #[cfg(gpio_v2)]
44 pub pull: Pull,
45}
46
32macro_rules! channel_impl { 47macro_rules! channel_impl {
33 ($new_chx:ident, $channel:ident, $pin_trait:ident) => { 48 ($new_chx:ident, $new_chx_with_config:ident, $channel:ident, $pin_trait:ident) => {
34 impl<'d, T: BasicInstance> PwmPin<'d, T, $channel> { 49 impl<'d, T: BasicInstance> PwmPin<'d, T, $channel> {
35 #[doc = concat!("Create a new ", stringify!($channel), " PWM pin instance.")] 50 #[doc = concat!("Create a new ", stringify!($channel), " PWM pin instance.")]
36 pub fn $new_chx(pin: impl Peripheral<P = impl $pin_trait<T>> + 'd) -> Self { 51 pub fn $new_chx(pin: impl Peripheral<P = impl $pin_trait<T>> + 'd) -> Self {
@@ -47,16 +62,37 @@ macro_rules! channel_impl {
47 phantom: PhantomData, 62 phantom: PhantomData,
48 } 63 }
49 } 64 }
65 #[doc = concat!("Create a new ", stringify!($channel), " PWM pin instance with config.")]
66 pub fn $new_chx_with_config(
67 pin: impl Peripheral<P = impl $pin_trait<T>> + 'd,
68 pin_config: PwmPinConfig,
69 ) -> Self {
70 into_ref!(pin);
71 critical_section::with(|_| {
72 pin.set_low();
73 pin.set_as_af(
74 pin.af_num(),
75 #[cfg(gpio_v1)]
76 AfType::output(pin_config.output_type, pin_config.speed),
77 #[cfg(gpio_v2)]
78 AfType::output_pull(pin_config.output_type, pin_config.speed, pin_config.pull),
79 );
80 });
81 PwmPin {
82 _pin: pin.map_into(),
83 phantom: PhantomData,
84 }
85 }
50 } 86 }
51 }; 87 };
52} 88}
53 89
54#[cfg(not(any(lptim_v2a, lptim_v2b)))] 90#[cfg(not(any(lptim_v2a, lptim_v2b)))]
55channel_impl!(new, Output, OutputPin); 91channel_impl!(new, new_with_config, Output, OutputPin);
56#[cfg(any(lptim_v2a, lptim_v2b))] 92#[cfg(any(lptim_v2a, lptim_v2b))]
57channel_impl!(new_ch1, Ch1, Channel1Pin); 93channel_impl!(new_ch1, new_ch1_with_config, Ch1, Channel1Pin);
58#[cfg(any(lptim_v2a, lptim_v2b))] 94#[cfg(any(lptim_v2a, lptim_v2b))]
59channel_impl!(new_ch2, Ch2, Channel2Pin); 95channel_impl!(new_ch2, new_ch2_with_config, Ch2, Channel2Pin);
60 96
61/// PWM driver. 97/// PWM driver.
62pub struct Pwm<'d, T: Instance> { 98pub struct Pwm<'d, T: Instance> {
diff --git a/embassy-stm32/src/timer/simple_pwm.rs b/embassy-stm32/src/timer/simple_pwm.rs
index 1dff3f9ae..c5a366cd5 100644
--- a/embassy-stm32/src/timer/simple_pwm.rs
+++ b/embassy-stm32/src/timer/simple_pwm.rs
@@ -7,6 +7,8 @@ use embassy_hal_internal::{into_ref, PeripheralRef};
7 7
8use super::low_level::{CountingMode, OutputCompareMode, OutputPolarity, Timer}; 8use super::low_level::{CountingMode, OutputCompareMode, OutputPolarity, Timer};
9use super::{Channel, Channel1Pin, Channel2Pin, Channel3Pin, Channel4Pin, GeneralInstance4Channel, TimerBits}; 9use super::{Channel, Channel1Pin, Channel2Pin, Channel3Pin, Channel4Pin, GeneralInstance4Channel, TimerBits};
10#[cfg(gpio_v2)]
11use crate::gpio::Pull;
10use crate::gpio::{AfType, AnyPin, OutputType, Speed}; 12use crate::gpio::{AfType, AnyPin, OutputType, Speed};
11use crate::time::Hertz; 13use crate::time::Hertz;
12use crate::Peripheral; 14use crate::Peripheral;
@@ -28,8 +30,21 @@ pub struct PwmPin<'d, T, C> {
28 phantom: PhantomData<(T, C)>, 30 phantom: PhantomData<(T, C)>,
29} 31}
30 32
33/// PWM pin config
34///
35/// This configures the pwm pin settings
36pub struct PwmPinConfig {
37 /// PWM Pin output type
38 pub output_type: OutputType,
39 /// PWM Pin speed
40 pub speed: Speed,
41 /// PWM Pin pull type
42 #[cfg(gpio_v2)]
43 pub pull: Pull,
44}
45
31macro_rules! channel_impl { 46macro_rules! channel_impl {
32 ($new_chx:ident, $channel:ident, $pin_trait:ident) => { 47 ($new_chx:ident, $new_chx_with_config:ident, $channel:ident, $pin_trait:ident) => {
33 impl<'d, T: GeneralInstance4Channel> PwmPin<'d, T, $channel> { 48 impl<'d, T: GeneralInstance4Channel> PwmPin<'d, T, $channel> {
34 #[doc = concat!("Create a new ", stringify!($channel), " PWM pin instance.")] 49 #[doc = concat!("Create a new ", stringify!($channel), " PWM pin instance.")]
35 pub fn $new_chx(pin: impl Peripheral<P = impl $pin_trait<T>> + 'd, output_type: OutputType) -> Self { 50 pub fn $new_chx(pin: impl Peripheral<P = impl $pin_trait<T>> + 'd, output_type: OutputType) -> Self {
@@ -43,14 +58,36 @@ macro_rules! channel_impl {
43 phantom: PhantomData, 58 phantom: PhantomData,
44 } 59 }
45 } 60 }
61
62 #[doc = concat!("Create a new ", stringify!($channel), " PWM pin instance with config.")]
63 pub fn $new_chx_with_config(
64 pin: impl Peripheral<P = impl $pin_trait<T>> + 'd,
65 pin_config: PwmPinConfig,
66 ) -> Self {
67 into_ref!(pin);
68 critical_section::with(|_| {
69 pin.set_low();
70 pin.set_as_af(
71 pin.af_num(),
72 #[cfg(gpio_v1)]
73 AfType::output(pin_config.output_type, pin_config.speed),
74 #[cfg(gpio_v2)]
75 AfType::output_pull(pin_config.output_type, pin_config.speed, pin_config.pull),
76 );
77 });
78 PwmPin {
79 _pin: pin.map_into(),
80 phantom: PhantomData,
81 }
82 }
46 } 83 }
47 }; 84 };
48} 85}
49 86
50channel_impl!(new_ch1, Ch1, Channel1Pin); 87channel_impl!(new_ch1, new_ch1_with_config, Ch1, Channel1Pin);
51channel_impl!(new_ch2, Ch2, Channel2Pin); 88channel_impl!(new_ch2, new_ch2_with_config, Ch2, Channel2Pin);
52channel_impl!(new_ch3, Ch3, Channel3Pin); 89channel_impl!(new_ch3, new_ch3_with_config, Ch3, Channel3Pin);
53channel_impl!(new_ch4, Ch4, Channel4Pin); 90channel_impl!(new_ch4, new_ch4_with_config, Ch4, Channel4Pin);
54 91
55/// A single channel of a pwm, obtained from [`SimplePwm::split`], 92/// A single channel of a pwm, obtained from [`SimplePwm::split`],
56/// [`SimplePwm::channel`], [`SimplePwm::ch1`], etc. 93/// [`SimplePwm::channel`], [`SimplePwm::ch1`], etc.