stm32g0xx_hal/timer/
qei.rs1use crate::hal::{self, Direction};
3use crate::rcc::*;
4
5#[cfg(feature = "stm32g0x1")]
6use crate::stm32::{TIM1, TIM2, TIM3};
7#[cfg(feature = "stm32g0x0")]
8use crate::stm32::{TIM1, TIM3};
9
10use crate::timer::pins::TimerPin;
11use crate::timer::*;
12
13pub struct Qei<TIM, PINS> {
14 tim: TIM,
15 pins: PINS,
16}
17
18pub trait QeiPins<TIM> {
19 fn setup(&self);
20 fn release(self) -> Self;
21}
22
23impl<TIM, P1, P2> QeiPins<TIM> for (P1, P2)
24where
25 P1: TimerPin<TIM, Channel = Channel1>,
26 P2: TimerPin<TIM, Channel = Channel2>,
27{
28 fn setup(&self) {
29 self.0.setup();
30 self.1.setup();
31 }
32
33 fn release(self) -> Self {
34 (self.0.release(), self.1.release())
35 }
36}
37
38pub trait QeiExt<TIM, PINS>
39where
40 PINS: QeiPins<TIM>,
41{
42 fn qei(self, pins: PINS, rcc: &mut Rcc) -> Qei<TIM, PINS>;
43}
44
45macro_rules! qei {
46 ($($TIMX:ident: ($tim:ident, $arr:ident, $cnt:ident),)+) => {
47 $(
48 impl<PINS> Qei<$TIMX, PINS> where PINS: QeiPins<$TIMX> {
49 fn $tim(tim: $TIMX, pins: PINS, rcc: &mut Rcc) -> Self {
50 $TIMX::enable(rcc);
52 $TIMX::reset(rcc);
53
54 tim.ccmr1_output().write(|w| unsafe {
56 w.cc1s().bits(0b01).cc2s().bits(0b01)
57 });
58
59 tim.smcr.write(|w| unsafe { w.sms().bits(0b010) });
61
62 tim.ccer.write(|w| {
64 w.cc1e()
65 .set_bit()
66 .cc2e()
67 .set_bit()
68 .cc1p()
69 .clear_bit()
70 .cc2p()
71 .clear_bit()
72 .cc1np()
73 .clear_bit()
74 .cc2np()
75 .clear_bit()
76 });
77
78 pins.setup();
79
80 tim.cr1.write(|w| w.cen().set_bit());
81 Qei { tim, pins }
82 }
83
84 pub fn release(self) -> ($TIMX, PINS) {
85 (self.tim, self.pins.release())
86 }
87 }
88
89 impl<PINS> hal::Qei for Qei<$TIMX, PINS> {
90 type Count = u16;
91
92 fn count(&self) -> u16 {
93 self.tim.cnt.read().$cnt().bits()
94 }
95
96 fn direction(&self) -> Direction {
97 if self.tim.cr1.read().dir().bit_is_clear() {
98 hal::Direction::Upcounting
99 } else {
100 hal::Direction::Downcounting
101 }
102 }
103 }
104
105 impl<PINS> QeiExt<$TIMX, PINS> for $TIMX where PINS: QeiPins<$TIMX> {
106 fn qei(self, pins: PINS, rcc: &mut Rcc) -> Qei<$TIMX, PINS> {
107 Qei::$tim(self, pins, rcc)
108 }
109 }
110 )+
111 }
112}
113
114qei! {
115 TIM1: (tim1, arr, cnt),
116 TIM3: (tim3, arr_l, cnt_l),
117}
118
119#[cfg(feature = "stm32g0x1")]
120qei! {
121 TIM2: (tim2, arr_l, cnt_l),
122}