35
35
//! let opamp4 = opamp4.open_loop(gpiob.pb11, gpiob.pb10, Option::<PB12<Analog>>::None);
36
36
//!
37
37
//! // disable opamps
38
- //! let (_opamp1, _pa1, _some_pa2 ) = opamp1.disable();
39
- //! let (_opamp2, _pa7 , _none) = opamp2.disable();
38
+ //! let (opamp1, pa1, some_pa2 ) = opamp1.disable();
39
+ //! let (opamp2, pa7 , _none) = opamp2.disable();
40
40
//!
41
41
//! let (_opamp3, _pb0, _pb2, _some_pb1) = opamp3.disable();
42
42
//! let (_opamp4, _pb11, _pb10, _none) = opamp4.disable();
43
43
//!
44
+ //! let opamp1 = opamp1.pga(pa1, some_pa2);
45
+ //! let opamp2 = opamp2.pga(pa7, Option::<PA6<Analog>>::None);
46
+ //!
47
+ //! let (_opamp1, _pa1, _some_pa2) = opamp1.disable();
48
+ //! let (_opamp2, _pa7, _none) = opamp2.disable();
49
+ //!
44
50
//! loop {}
45
51
//! }
46
52
//! ```
47
53
48
54
// TODO: Add support for locking using the `LOCK` bit in `OPAMPx_CSR`
49
55
// TODO: Add support for calibration
50
- // TODO: Add support for PGA mode
56
+ // TODO: The output can not be a Option<PIN> if we want to handle "route to pin vs adc"
57
+ // in a compile time way. See OPAINTOEN in OPAMPx_CSR
58
+
59
+ /// Pga mode internal
60
+ ///
61
+ /// This mode does not expose the inverting signal on any pin,
62
+ /// only connecting it to the programmable gain divider
63
+ pub struct PgaModeInternal ( NonInvertingGain ) ;
64
+ impl PgaModeInternal {
65
+ /// Create new instance with the given gain setting
66
+ pub fn gain ( gain : NonInvertingGain ) -> Self {
67
+ PgaModeInternal ( gain)
68
+ }
69
+ }
70
+
71
+ /// Same as PgaModeInternal but the inverted signal is routed to pin
72
+ /// to allow external filter
73
+ pub struct PgaModeInvertedInputFiltered < PIN > {
74
+ gain : NonInvertingGain ,
75
+ pin : core:: marker:: PhantomData < PIN > ,
76
+ }
77
+
78
+ /// PGA Gain for non inverted modes
79
+ pub enum NonInvertingGain {
80
+ /// 2x Gain
81
+ Gain2 = 0 ,
82
+
83
+ /// 4x Gain
84
+ Gain4 = 1 ,
85
+
86
+ /// 8x Gain
87
+ Gain8 = 2 ,
88
+
89
+ /// 16x Gain
90
+ Gain16 = 3 ,
91
+
92
+ /// 32x Gain
93
+ Gain32 = 4 ,
94
+
95
+ /// 64x Gain
96
+ Gain64 = 5 ,
97
+ }
51
98
52
99
macro_rules! opamps {
53
100
{
@@ -95,10 +142,38 @@ macro_rules! opamps {
95
142
}
96
143
97
144
$(
145
+ impl From <& PgaModeInternal > for crate :: stm32:: opamp:: [ <$opamp _csr>] :: PGA_GAIN_A {
146
+ fn from( x: & PgaModeInternal ) -> crate :: stm32:: opamp:: [ <$opamp _csr>] :: PGA_GAIN_A {
147
+ use crate :: stm32:: opamp:: [ <$opamp _csr>] :: PGA_GAIN_A ;
148
+
149
+ match x. 0 {
150
+ NonInvertingGain :: Gain2 => PGA_GAIN_A :: Gain2 ,
151
+ NonInvertingGain :: Gain4 => PGA_GAIN_A :: Gain4 ,
152
+ NonInvertingGain :: Gain8 => PGA_GAIN_A :: Gain8 ,
153
+ NonInvertingGain :: Gain16 => PGA_GAIN_A :: Gain16 ,
154
+ NonInvertingGain :: Gain32 => PGA_GAIN_A :: Gain32 ,
155
+ NonInvertingGain :: Gain64 => PGA_GAIN_A :: Gain64 ,
156
+ }
157
+ }
158
+ }
159
+
160
+ impl <PIN > From <& PgaModeInvertedInputFiltered <PIN >> for crate :: stm32:: opamp:: [ <$opamp _csr>] :: PGA_GAIN_A {
161
+ fn from( x: & PgaModeInvertedInputFiltered <PIN >) -> crate :: stm32:: opamp:: [ <$opamp _csr>] :: PGA_GAIN_A {
162
+ use crate :: stm32:: opamp:: [ <$opamp _csr>] :: PGA_GAIN_A ;
163
+
164
+ match x. gain {
165
+ NonInvertingGain :: Gain2 => PGA_GAIN_A :: Gain2FilteringVinm0 ,
166
+ NonInvertingGain :: Gain4 => PGA_GAIN_A :: Gain4FilteringVinm0 ,
167
+ NonInvertingGain :: Gain8 => PGA_GAIN_A :: Gain8FilteringVinm0 ,
168
+ NonInvertingGain :: Gain16 => PGA_GAIN_A :: Gain16FilteringVinm0 ,
169
+ NonInvertingGain :: Gain32 => PGA_GAIN_A :: Gain32FilteringVinm0 ,
170
+ NonInvertingGain :: Gain64 => PGA_GAIN_A :: Gain64FilteringVinm0 ,
171
+ }
172
+ }
173
+ }
174
+
98
175
/// States for opampX.
99
176
pub mod $opamp {
100
- use crate :: stm32:: opamp:: [ <$opamp _csr>] :: PGA_GAIN_A ;
101
-
102
177
#[ allow( unused_imports) ]
103
178
use crate :: gpio:: gpioa:: * ;
104
179
@@ -121,70 +196,6 @@ macro_rules! opamps {
121
196
output: Option <$output>,
122
197
}
123
198
124
- /// State type for opamp running in programmable-gain mode.
125
- pub struct Pga <NonInverting , MODE > {
126
- non_inverting: NonInverting ,
127
- config: MODE ,
128
- output: Option <$output>,
129
- }
130
-
131
- trait PgaMode {
132
- fn pga_gain_bits( & self ) -> PGA_GAIN_A ;
133
- }
134
-
135
- struct PgaModeInternal ( NonInvertingGain ) ;
136
- impl PgaMode for PgaModeInternal {
137
- fn pga_gain_bits( & self ) -> PGA_GAIN_A {
138
- match self . 0 {
139
- NonInvertingGain :: Gain2 => PGA_GAIN_A :: Gain2 ,
140
- NonInvertingGain :: Gain4 => PGA_GAIN_A :: Gain4 ,
141
- NonInvertingGain :: Gain8 => PGA_GAIN_A :: Gain8 ,
142
- NonInvertingGain :: Gain16 => PGA_GAIN_A :: Gain16 ,
143
- NonInvertingGain :: Gain32 => PGA_GAIN_A :: Gain32 ,
144
- NonInvertingGain :: Gain64 => PGA_GAIN_A :: Gain64 ,
145
- }
146
- }
147
- }
148
-
149
- /// Same as PgaModeInternal but the inverted signal is routed to pin to allow external filter
150
- struct PgaModeInvertedInputFiltered <PIN > {
151
- gain: NonInvertingGain ,
152
- pin: core:: marker:: PhantomData <PIN >
153
- }
154
- impl <PIN > PgaMode for PgaModeInvertedInputFiltered <PIN > {
155
- fn pga_gain_bits( & self ) -> PGA_GAIN_A {
156
- match self . gain {
157
- NonInvertingGain :: Gain2 => PGA_GAIN_A :: Gain2FilteringVinm0 ,
158
- NonInvertingGain :: Gain4 => PGA_GAIN_A :: Gain4FilteringVinm0 ,
159
- NonInvertingGain :: Gain8 => PGA_GAIN_A :: Gain8FilteringVinm0 ,
160
- NonInvertingGain :: Gain16 => PGA_GAIN_A :: Gain16FilteringVinm0 ,
161
- NonInvertingGain :: Gain32 => PGA_GAIN_A :: Gain32FilteringVinm0 ,
162
- NonInvertingGain :: Gain64 => PGA_GAIN_A :: Gain64FilteringVinm0 ,
163
- }
164
- }
165
- }
166
-
167
- /// PGA Gain for non inverted modes
168
- pub enum NonInvertingGain {
169
- /// 2x Gain
170
- Gain2 = 0 ,
171
-
172
- /// 4x Gain
173
- Gain4 = 1 ,
174
-
175
- /// 8x Gain
176
- Gain8 = 2 ,
177
-
178
- /// 16x Gain
179
- Gain16 = 3 ,
180
-
181
- /// 32x Gain
182
- Gain32 = 4 ,
183
-
184
- /// 64x Gain
185
- Gain64 = 5
186
- }
187
-
188
199
// TODO: Inverting gain
189
200
190
201
/// Trait for opamps that can be run in follower mode.
@@ -206,6 +217,13 @@ macro_rules! opamps {
206
217
-> OpenLoop <NonInverting , Inverting >;
207
218
}
208
219
220
+ /// State type for opamp running in programmable-gain mode.
221
+ pub struct Pga <NonInverting , MODE > {
222
+ non_inverting: NonInverting ,
223
+ config: MODE ,
224
+ output: Option <$output>,
225
+ }
226
+
209
227
/// Trait for opamps that can be run in programmable gain mode.
210
228
pub trait IntoPga <IntoNonInverting , MODE , IntoOutput , NonInverting >
211
229
where
@@ -466,8 +484,8 @@ macro_rules! opamps {
466
484
$vinm0: ident
467
485
} => {
468
486
$(
469
- opamps!{ @pga $opamp, $output, $non_inverting_mask, $non_inverting, PgaModeInternal }
470
- opamps!{ @pga $opamp, $output, $non_inverting_mask, $non_inverting, PgaModeInvertedInputFiltered <$vinm0<crate :: gpio:: Analog >> }
487
+ opamps!{ @pga $opamp, $output, $non_inverting_mask, $non_inverting, crate :: opamp :: PgaModeInternal }
488
+ opamps!{ @pga $opamp, $output, $non_inverting_mask, $non_inverting, crate :: opamp :: PgaModeInvertedInputFiltered <$vinm0<crate :: gpio:: Analog >> }
471
489
// TODO: Add `PGA mode, non-inverting gain setting (x2/x4/x8/x16/x32/x64) or inverting gain setting (x-1/x-3/x-7/x-15/x-31/x-63)`
472
490
// TODO: Add `PGA mode, non-inverting gain setting (x2/x4/x8/x16/x32/x64) or inverting gain setting (x-1/x-3/x-7/x-15/x-31/x-63) with filtering`
473
491
) *
@@ -511,7 +529,7 @@ macro_rules! opamps {
511
529
. vm_sel( )
512
530
. pga( )
513
531
. pga_gain( )
514
- . variant( config. pga_gain_bits ( ) )
532
+ . variant( ( & config) . into ( ) )
515
533
. opaintoen( )
516
534
. variant( match output {
517
535
Some ( _) => OPAINTOEN_A :: OutputPin ,
0 commit comments