aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorxoviat <[email protected]>2025-12-01 09:44:07 -0600
committerxoviat <[email protected]>2025-12-01 09:44:07 -0600
commit970138277bdbf176a3a9320c9d0de9256945d21e (patch)
tree77ebf80cf9cc905f07f85be26c1c52af0ab78d51
parenta1236b13c3d5fad687ae931a041ae463ac0612bb (diff)
timer: use u32 for high-level api
-rw-r--r--embassy-stm32/src/timer/complementary_pwm.rs12
-rw-r--r--embassy-stm32/src/timer/simple_pwm.rs28
-rw-r--r--examples/stm32f4/src/bin/pwm_complementary.rs2
-rw-r--r--examples/stm32f4/src/bin/ws2812_pwm.rs2
4 files changed, 20 insertions, 24 deletions
diff --git a/embassy-stm32/src/timer/complementary_pwm.rs b/embassy-stm32/src/timer/complementary_pwm.rs
index 4d04af685..6ca13820a 100644
--- a/embassy-stm32/src/timer/complementary_pwm.rs
+++ b/embassy-stm32/src/timer/complementary_pwm.rs
@@ -177,20 +177,20 @@ impl<'d, T: AdvancedInstance4Channel> ComplementaryPwm<'d, T> {
177 /// Get max duty value. 177 /// Get max duty value.
178 /// 178 ///
179 /// This value depends on the configured frequency and the timer's clock rate from RCC. 179 /// This value depends on the configured frequency and the timer's clock rate from RCC.
180 pub fn get_max_duty(&self) -> u16 { 180 pub fn get_max_duty(&self) -> u32 {
181 if self.inner.get_counting_mode().is_center_aligned() { 181 if self.inner.get_counting_mode().is_center_aligned() {
182 unwrap!(self.inner.get_max_compare_value().try_into()) 182 self.inner.get_max_compare_value().into()
183 } else { 183 } else {
184 unwrap!(self.inner.get_max_compare_value().try_into()) + 1 184 self.inner.get_max_compare_value().into() + 1
185 } 185 }
186 } 186 }
187 187
188 /// Set the duty for a given channel. 188 /// Set the duty for a given channel.
189 /// 189 ///
190 /// The value ranges from 0 for 0% duty, to [`get_max_duty`](Self::get_max_duty) for 100% duty, both included. 190 /// The value ranges from 0 for 0% duty, to [`get_max_duty`](Self::get_max_duty) for 100% duty, both included.
191 pub fn set_duty(&mut self, channel: Channel, duty: u16) { 191 pub fn set_duty(&mut self, channel: Channel, duty: u32) {
192 assert!(duty <= self.get_max_duty()); 192 assert!(duty <= self.get_max_duty());
193 self.inner.set_compare_value(channel, duty.into()) 193 self.inner.set_compare_value(channel, unwrap!(duty.try_into()))
194 } 194 }
195 195
196 /// Set the output polarity for a given channel. 196 /// Set the output polarity for a given channel.
@@ -318,7 +318,7 @@ impl<'d, T: AdvancedInstance4Channel> embedded_hal_02::Pwm for ComplementaryPwm<
318 } 318 }
319 319
320 fn set_duty(&mut self, channel: Self::Channel, duty: Self::Duty) { 320 fn set_duty(&mut self, channel: Self::Channel, duty: Self::Duty) {
321 assert!(duty <= self.get_max_duty()); 321 assert!(duty <= unwrap!(self.get_max_duty().try_into()));
322 self.inner.set_compare_value(channel, unwrap!(duty.try_into())) 322 self.inner.set_compare_value(channel, unwrap!(duty.try_into()))
323 } 323 }
324 324
diff --git a/embassy-stm32/src/timer/simple_pwm.rs b/embassy-stm32/src/timer/simple_pwm.rs
index f4b84670f..b79ed364b 100644
--- a/embassy-stm32/src/timer/simple_pwm.rs
+++ b/embassy-stm32/src/timer/simple_pwm.rs
@@ -99,18 +99,16 @@ impl<'d, T: GeneralInstance4Channel> SimplePwmChannel<'d, T> {
99 /// Get max duty value. 99 /// Get max duty value.
100 /// 100 ///
101 /// This value depends on the configured frequency and the timer's clock rate from RCC. 101 /// This value depends on the configured frequency and the timer's clock rate from RCC.
102 pub fn max_duty_cycle(&self) -> u16 { 102 pub fn max_duty_cycle(&self) -> u32 {
103 let max: u32 = self.timer.get_max_compare_value().into(); 103 self.timer.get_max_compare_value().into() + 1
104 assert!(max < u16::MAX as u32);
105 max as u16 + 1
106 } 104 }
107 105
108 /// Set the duty for a given channel. 106 /// Set the duty for a given channel.
109 /// 107 ///
110 /// The value ranges from 0 for 0% duty, to [`max_duty_cycle`](Self::max_duty_cycle) for 100% duty, both included. 108 /// The value ranges from 0 for 0% duty, to [`max_duty_cycle`](Self::max_duty_cycle) for 100% duty, both included.
111 pub fn set_duty_cycle(&mut self, duty: u16) { 109 pub fn set_duty_cycle(&mut self, duty: u32) {
112 assert!(duty <= (*self).max_duty_cycle()); 110 assert!(duty <= (*self).max_duty_cycle());
113 self.timer.set_compare_value(self.channel, duty.into()) 111 self.timer.set_compare_value(self.channel, unwrap!(duty.try_into()))
114 } 112 }
115 113
116 /// Set the duty cycle to 0%, or always inactive. 114 /// Set the duty cycle to 0%, or always inactive.
@@ -127,21 +125,21 @@ impl<'d, T: GeneralInstance4Channel> SimplePwmChannel<'d, T> {
127 /// 125 ///
128 /// The caller is responsible for ensuring that `num` is less than or equal to `denom`, 126 /// The caller is responsible for ensuring that `num` is less than or equal to `denom`,
129 /// and that `denom` is not zero. 127 /// and that `denom` is not zero.
130 pub fn set_duty_cycle_fraction(&mut self, num: u16, denom: u16) { 128 pub fn set_duty_cycle_fraction(&mut self, num: u32, denom: u32) {
131 assert!(denom != 0); 129 assert!(denom != 0);
132 assert!(num <= denom); 130 assert!(num <= denom);
133 let duty = u32::from(num) * u32::from(self.max_duty_cycle()) / u32::from(denom); 131 let duty = u32::from(num) * u32::from(self.max_duty_cycle()) / u32::from(denom);
134 132
135 // This is safe because we know that `num <= denom`, so `duty <= self.max_duty_cycle()` (u16) 133 // This is safe because we know that `num <= denom`, so `duty <= self.max_duty_cycle()` (u16)
136 #[allow(clippy::cast_possible_truncation)] 134 #[allow(clippy::cast_possible_truncation)]
137 self.set_duty_cycle(duty as u16); 135 self.set_duty_cycle(unwrap!(duty.try_into()));
138 } 136 }
139 137
140 /// Set the duty cycle to `percent / 100` 138 /// Set the duty cycle to `percent / 100`
141 /// 139 ///
142 /// The caller is responsible for ensuring that `percent` is less than or equal to 100. 140 /// The caller is responsible for ensuring that `percent` is less than or equal to 100.
143 pub fn set_duty_cycle_percent(&mut self, percent: u8) { 141 pub fn set_duty_cycle_percent(&mut self, percent: u8) {
144 self.set_duty_cycle_fraction(u16::from(percent), 100) 142 self.set_duty_cycle_fraction(percent as u32, 100)
145 } 143 }
146 144
147 /// Get the duty for a given channel. 145 /// Get the duty for a given channel.
@@ -334,10 +332,8 @@ impl<'d, T: GeneralInstance4Channel> SimplePwm<'d, T> {
334 /// Get max duty value. 332 /// Get max duty value.
335 /// 333 ///
336 /// This value depends on the configured frequency and the timer's clock rate from RCC. 334 /// This value depends on the configured frequency and the timer's clock rate from RCC.
337 pub fn max_duty_cycle(&self) -> u16 { 335 pub fn max_duty_cycle(&self) -> u32 {
338 let max: u32 = self.inner.get_max_compare_value().into(); 336 self.inner.get_max_compare_value().into() + 1
339 assert!(max < u16::MAX as u32);
340 max as u16 + 1
341 } 337 }
342 338
343 /// Generate a sequence of PWM waveform 339 /// Generate a sequence of PWM waveform
@@ -417,11 +413,11 @@ impl<'d, T: GeneralInstance4Channel> embedded_hal_1::pwm::ErrorType for SimplePw
417 413
418impl<'d, T: GeneralInstance4Channel> embedded_hal_1::pwm::SetDutyCycle for SimplePwmChannel<'d, T> { 414impl<'d, T: GeneralInstance4Channel> embedded_hal_1::pwm::SetDutyCycle for SimplePwmChannel<'d, T> {
419 fn max_duty_cycle(&self) -> u16 { 415 fn max_duty_cycle(&self) -> u16 {
420 self.max_duty_cycle() 416 unwrap!(self.max_duty_cycle().try_into())
421 } 417 }
422 418
423 fn set_duty_cycle(&mut self, duty: u16) -> Result<(), Self::Error> { 419 fn set_duty_cycle(&mut self, duty: u16) -> Result<(), Self::Error> {
424 self.set_duty_cycle(duty); 420 self.set_duty_cycle(duty.into());
425 Ok(()) 421 Ok(())
426 } 422 }
427 423
@@ -436,7 +432,7 @@ impl<'d, T: GeneralInstance4Channel> embedded_hal_1::pwm::SetDutyCycle for Simpl
436 } 432 }
437 433
438 fn set_duty_cycle_fraction(&mut self, num: u16, denom: u16) -> Result<(), Self::Error> { 434 fn set_duty_cycle_fraction(&mut self, num: u16, denom: u16) -> Result<(), Self::Error> {
439 self.set_duty_cycle_fraction(num, denom); 435 self.set_duty_cycle_fraction(num.into(), denom.into());
440 Ok(()) 436 Ok(())
441 } 437 }
442 438
diff --git a/examples/stm32f4/src/bin/pwm_complementary.rs b/examples/stm32f4/src/bin/pwm_complementary.rs
index 50008a37b..5e39a06f5 100644
--- a/examples/stm32f4/src/bin/pwm_complementary.rs
+++ b/examples/stm32f4/src/bin/pwm_complementary.rs
@@ -33,7 +33,7 @@ async fn main(_spawner: Spawner) {
33 ); 33 );
34 34
35 let max = pwm.get_max_duty(); 35 let max = pwm.get_max_duty();
36 pwm.set_dead_time(max / 1024); 36 pwm.set_dead_time((max / 1024) as u16);
37 37
38 pwm.enable(Channel::Ch1); 38 pwm.enable(Channel::Ch1);
39 39
diff --git a/examples/stm32f4/src/bin/ws2812_pwm.rs b/examples/stm32f4/src/bin/ws2812_pwm.rs
index ccfd0661e..4e556f0d4 100644
--- a/examples/stm32f4/src/bin/ws2812_pwm.rs
+++ b/examples/stm32f4/src/bin/ws2812_pwm.rs
@@ -61,7 +61,7 @@ async fn main(_spawner: Spawner) {
61 // construct ws2812 non-return-to-zero (NRZ) code bit by bit 61 // construct ws2812 non-return-to-zero (NRZ) code bit by bit
62 // ws2812 only need 24 bits for each LED, but we add one bit more to keep PWM output low 62 // ws2812 only need 24 bits for each LED, but we add one bit more to keep PWM output low
63 63
64 let max_duty = ws2812_pwm.max_duty_cycle(); 64 let max_duty = ws2812_pwm.max_duty_cycle() as u16;
65 let n0 = 8 * max_duty / 25; // ws2812 Bit 0 high level timing 65 let n0 = 8 * max_duty / 25; // ws2812 Bit 0 high level timing
66 let n1 = 2 * n0; // ws2812 Bit 1 high level timing 66 let n1 = 2 * n0; // ws2812 Bit 1 high level timing
67 67