stm32f303xc/
adc.rs

1// Licensed under the Apache License, Version 2.0 or the MIT License.
2// SPDX-License-Identifier: Apache-2.0 OR MIT
3// Copyright Tock Contributors 2022.
4
5//! Analog to Digital Converter Peripheral
6
7use crate::rcc;
8use core::cell::Cell;
9use kernel::hil;
10use kernel::platform::chip::ClockInterface;
11use kernel::utilities::cells::OptionalCell;
12use kernel::utilities::registers::interfaces::{ReadWriteable, Readable};
13use kernel::utilities::registers::{register_bitfields, ReadOnly, ReadWrite};
14use kernel::utilities::StaticRef;
15use kernel::ErrorCode;
16
17#[repr(C)]
18struct AdcRegisters {
19    isr: ReadWrite<u32, ISR::Register>,
20    ier: ReadWrite<u32, IER::Register>,
21    cr: ReadWrite<u32, CR::Register>,
22    cfgr: ReadWrite<u32, CFGR::Register>,
23
24    _reserved0: [u32; 1],
25    smpr1: ReadWrite<u32, SMPR1::Register>,
26    smpr2: ReadWrite<u32, SMPR2::Register>,
27
28    _reserved1: [u32; 1],
29    tr1: ReadWrite<u32, TR1::Register>,
30    tr2: ReadWrite<u32, TR2::Register>,
31    tr3: ReadWrite<u32, TR3::Register>,
32
33    _reserved2: [u32; 1],
34    sqr1: ReadWrite<u32, SQR1::Register>,
35    sqr2: ReadWrite<u32, SQR2::Register>,
36    sqr3: ReadWrite<u32, SQR3::Register>,
37    sqr4: ReadWrite<u32, SQR4::Register>,
38    dr: ReadOnly<u32, DR::Register>,
39    _reserved3: [u32; 2],
40
41    jsqr: ReadWrite<u32, JSQR::Register>,
42    _reserved4: [u32; 4],
43
44    ofr1: ReadWrite<u32, OFR::Register>,
45    ofr2: ReadWrite<u32, OFR::Register>,
46    ofr3: ReadWrite<u32, OFR::Register>,
47    ofr4: ReadWrite<u32, OFR::Register>,
48    _reserved5: [u32; 4],
49
50    jdr1: ReadOnly<u32, JDR::Register>,
51    jdr2: ReadOnly<u32, JDR::Register>,
52    jdr3: ReadOnly<u32, JDR::Register>,
53    jdr4: ReadOnly<u32, JDR::Register>,
54    _reserved6: [u32; 4],
55
56    awd2cr: ReadWrite<u32, AWD2CR::Register>,
57    awd3cr: ReadWrite<u32, AWD3CR::Register>,
58    _reserved7: [u32; 2],
59
60    difsel: ReadWrite<u32, DIFSEL::Register>,
61    calfact: ReadWrite<u32, CALFACT::Register>,
62}
63
64#[repr(C)]
65struct AdcCommonRegisters {
66    csr: ReadOnly<u32, CSR::Register>,
67    _reserved0: [u32; 1],
68
69    ccr: ReadWrite<u32, CCR::Register>,
70    cdr: ReadOnly<u32, CDR::Register>,
71}
72
73register_bitfields![u32,
74    ///interrupt and status register
75    ISR [
76        /// Injected context queue overflow
77        JQOVF OFFSET(10) NUMBITS(1) [],
78        /// Analog watchdog 3 flag
79        AWD3 OFFSET(9) NUMBITS(1) [],
80        /// Analog watchdog 2 flag
81        AWD2 OFFSET(8) NUMBITS(1) [],
82        /// Analog watchdog 1 flag
83        AWD1 OFFSET(7) NUMBITS(1) [],
84        /// Injected channel end of sequence flag
85        JEOS OFFSET(6) NUMBITS(1) [],
86        /// Injected channel end of conversion flag
87        JEOC OFFSET(5) NUMBITS(1) [],
88        /// ADC overrun
89        OVR OFFSET(4) NUMBITS(1) [],
90        /// End of regular sequence flag
91        EOS OFFSET(3) NUMBITS(1) [],
92        /// End of conversion flag
93        EOC OFFSET(2) NUMBITS(1) [],
94        /// End of sampling flag
95        EOSMP OFFSET(1) NUMBITS(1) [],
96        /// ADC ready
97        ADRDY OFFSET(0) NUMBITS(1) []
98    ],
99    /// Interrupt enable register
100    IER [
101        /// Injected context queue overflow interrupt enable
102        JQOVFIE OFFSET(10) NUMBITS(1) [],
103        /// Analog watchdog 3 interrupt enable
104        AWD3IE OFFSET(9) NUMBITS(1) [],
105        /// Analog watchdog 2 interrupt enable
106        AWD2IE OFFSET(8) NUMBITS(1) [],
107        /// Analog watchdog 1 interrupt enable
108        AWD1IE OFFSET(7) NUMBITS(1) [],
109        /// End of injected sequence of conversions interrupt enable
110        JEOSIE OFFSET(6) NUMBITS(1) [],
111        /// End of injected conversion interrupt enable
112        JEOCIE OFFSET(5) NUMBITS(1) [],
113        /// Overrun interrupt enable
114        OVRIE OFFSET(4) NUMBITS(1) [],
115        /// End of regular sequence of conversions interrupt enable
116        EOSIE OFFSET(3) NUMBITS(1) [],
117        /// End of regular conversion interrupt enable
118        EOCIE OFFSET(2) NUMBITS(1) [],
119        /// End of sampling flag interrupt enable for regular conversions
120        EOSMPIE OFFSET(1) NUMBITS(1) [],
121        /// ADC ready interrupt enable
122        ADRDYIE OFFSET(0) NUMBITS(1) []
123    ],
124    /// Control register
125    CR [
126        /// ADC calibration
127        ADCAL OFFSET(31) NUMBITS(1) [],
128        /// Differential mode for calibration
129        ADCALDIF OFFSET(30) NUMBITS(1) [],
130        /// ADC voltage regulator enable
131        ADVREGEN OFFSET(28) NUMBITS(2) [],
132        /// ADC stop of injected conversion command
133        JADSTP OFFSET(5) NUMBITS(1) [],
134        /// ADC stop of regular conversion command
135        ADSTP OFFSET(4) NUMBITS(1) [],
136        /// ADC start of injected conversion
137        JADSTART OFFSET(3) NUMBITS(1) [],
138        /// ADC start of regular conversion
139        ADSTART OFFSET(2) NUMBITS(1) [],
140        /// ADC disable command
141        ADDIS OFFSET(1) NUMBITS(1) [],
142        /// ADC enable control
143        ADEN OFFSET(0) NUMBITS(1) []
144    ],
145    /// Configuration register
146    CFGR [
147        /// Analog watchdog 1 channel selection
148        AWD1CH OFFSET(26) NUMBITS(5) [],
149        /// Automatic injected group conversion
150        JAUTO OFFSET(25) NUMBITS(1) [],
151        /// Analog watchdog 1 enable on injected channels
152        JAWD1EN OFFSET(24) NUMBITS(1) [],
153        /// Analog watchdog 1 enable on regular channels
154        AWD1EN OFFSET(23) NUMBITS(1) [],
155        /// Enable the watchdog 1 on a single channel or on all channels
156        AWD1SGL OFFSET(22) NUMBITS(1) [],
157        /// JSQR queue mode
158        JQM OFFSET(21) NUMBITS(1) [],
159        /// Discontinuous mode on injected channels
160        JDISCEN OFFSET(20) NUMBITS(1) [],
161        /// Discontinuous mode channel count
162        DISCNUM OFFSET(17) NUMBITS(3) [],
163        /// Discontinuous mode for regular channels
164        DISCEN OFFSET(16) NUMBITS(1) [],
165        /// Delayed conversion mode
166        AUTDLY OFFSET(14) NUMBITS(1) [],
167        /// Single / continuous conversion mode for regular conversions
168        CONT OFFSET(13) NUMBITS(1) [],
169        /// Overrun Mode
170        OVRMOD OFFSET(12) NUMBITS(1) [],
171        /// External trigger enable and polarity selection for regular channels
172        EXTEN OFFSET(10) NUMBITS(2) [],
173        /// External trigger selection for regular group
174        EXTSEL OFFSET(6) NUMBITS(4) [],
175        /// Data alignment
176        ALIGN OFFSET(5) NUMBITS(1) [],
177        /// Data resolution
178        RES OFFSET(3) NUMBITS(2) [],
179        /// Direct memory access configuration
180        DMACFG OFFSET(1) NUMBITS(1) [],
181        /// Direct memory access enable
182        DMAEN OFFSET(0) NUMBITS(1) []
183    ],
184    /// Sample time register 1
185    SMPR1 [
186        /// Channel x sampling time selection
187        SMP9 OFFSET(27) NUMBITS(3) [],
188        SMP8 OFFSET(24) NUMBITS(3) [],
189        SMP7 OFFSET(21) NUMBITS(3) [],
190        SMP6 OFFSET(18) NUMBITS(3) [],
191        SMP5 OFFSET(15) NUMBITS(3) [],
192        SMP4 OFFSET(12) NUMBITS(3) [],
193        SMP3 OFFSET(9) NUMBITS(3) [],
194        SMP2 OFFSET(6) NUMBITS(3) [],
195        SMP1 OFFSET(3) NUMBITS(3) []
196    ],
197    /// Sample time register 2
198    SMPR2 [
199        /// Channel x sampling time selection
200        SMP18 OFFSET(24) NUMBITS(3) [],
201        SMP17 OFFSET(21) NUMBITS(3) [],
202        SMP16 OFFSET(18) NUMBITS(3) [],
203        SMP15 OFFSET(15) NUMBITS(3) [],
204        SMP14 OFFSET(12) NUMBITS(3) [],
205        SMP13 OFFSET(9) NUMBITS(3) [],
206        SMP12 OFFSET(6) NUMBITS(3) [],
207        SMP11 OFFSET(3) NUMBITS(3) [],
208        SMP10 OFFSET(0) NUMBITS(3) []
209    ],
210    /// Watchdog threshold register 1
211    TR1 [
212        /// Analog watchdog 1 higher threshold
213        HT1 OFFSET(16) NUMBITS(12) [],
214        /// Analog watchdog 1 lower threshold
215        LT1 OFFSET(0) NUMBITS(12) []
216    ],
217    /// Watchdog threshold register 2
218    TR2 [
219        /// Analog watchdog 2 higher threshold
220        HT2 OFFSET(16) NUMBITS(8) [],
221        /// Analog watchdog 2 lower threshold
222        LT2 OFFSET(0) NUMBITS(8) []
223    ],
224    /// Watchdog threshold register 3
225    TR3 [
226        /// Analog watchdog 3 higher threshold
227        HT3 OFFSET(16) NUMBITS(8) [],
228        /// Analog watchdog 3 lower threshold
229        LT3 OFFSET(0) NUMBITS(8) []
230    ],
231    /// Regular sequence register 1
232    SQR1 [
233        /// 4th conversion in regular sequence
234        SQ4 OFFSET(24) NUMBITS(5) [],
235        /// 3rd conversion in regular sequence
236        SQ3 OFFSET(18) NUMBITS(5) [],
237        /// 2nd conversion in regular sequence
238        SQ2 OFFSET(12) NUMBITS(5) [],
239        /// 1st conversion in regular sequence
240        SQ1 OFFSET(6) NUMBITS(5) [],
241        /// Regular channel sequence length
242        L OFFSET(0) NUMBITS(4) []
243    ],
244    /// Regular sequence register 2
245    SQR2 [
246        SQ9 OFFSET(24) NUMBITS(5) [],
247        /// 9th conversion in regular sequence
248        SQ8 OFFSET(18) NUMBITS(5) [],
249        /// 8th conversion in regular sequence
250        SQ7 OFFSET(12) NUMBITS(5) [],
251        /// 7th conversion in regular sequence
252        SQ6 OFFSET(6) NUMBITS(5) [],
253        /// 6th conversion in regular sequence
254        SQ5 OFFSET(0) NUMBITS(5) []
255    ],
256    /// Regular sequence register 3
257    SQR3 [
258        /// 14th conversion in regular sequence
259        SQ14 OFFSET(24) NUMBITS(5) [],
260        /// 13th conversion in regular sequence
261        SQ13 OFFSET(18) NUMBITS(5) [],
262        /// 12th conversion in regular sequence
263        SQ12 OFFSET(12) NUMBITS(5) [],
264        /// 11th conversion in regular sequence
265        SQ11 OFFSET(6) NUMBITS(5) [],
266        /// 10th conversion in regular sequence
267        SQ10 OFFSET(0) NUMBITS(5) []
268    ],
269    /// Regular sequence register 4
270    SQR4 [
271        /// 16th conversion in regular sequence
272        SQ16 OFFSET(6) NUMBITS(5) [],
273        /// 15th conversion in regular sequence
274        SQ15 OFFSET(0) NUMBITS(5) []
275    ],
276    /// Regular Data Register
277    DR [
278        /// Regular Data converted
279        RDATA OFFSET(0) NUMBITS(16) []
280    ],
281    /// Injected sequence register
282    JSQR [
283        /// 4th conversion in the injected sequence
284        JSQ4 OFFSET(26) NUMBITS(5) [],
285        /// 3rd conversion in the injected sequence
286        JSQ3 OFFSET(20) NUMBITS(5) [],
287        /// 2nd conversion in the injected sequence
288        JSQ2 OFFSET(14) NUMBITS(5) [],
289        /// 1st conversion in the injected sequence
290        JSQ1 OFFSET(8) NUMBITS(5) [],
291        /// External Trigger Enable and Polarity Selection for injected channels
292        JEXTEN OFFSET(6) NUMBITS(2) [],
293        /// External Trigger Selection for injected group
294        JEXTSEL OFFSET(2) NUMBITS(4) [],
295        /// Injected channel sequence length
296        JL OFFSET(0) NUMBITS(2) []
297    ],
298    /// Offset register
299    OFR [
300        /// Offset y Enable
301        OFFSET_EN OFFSET(31) NUMBITS(1) [],
302        /// Channel selection for the Data offset y
303        OFFSET_CH OFFSET(26) NUMBITS(5) [],
304        /// Data offset y for the channel programmed into bits OFFSET_CH[4:0]
305        OFFSETy OFFSET(0) NUMBITS(12) []
306    ],
307    /// Injected data register
308    JDR [
309        /// Injected data
310        JDATA OFFSET(0) NUMBITS(16) []
311    ],
312    /// Analog Watchdog 2 Configuration Register
313    AWD2CR [
314        /// Analog watchdog 2 channel selection
315        AWD2CH OFFSET(1) NUMBITS(18) []
316    ],
317    /// Analog Watchdog 3 Configuration Register
318    AWD3CR [
319        /// Analog watchdog 3 channel selection
320        AWD3CH OFFSET(1) NUMBITS(18) []
321    ],
322    /// Differential Mode Selection Register
323    DIFSEL [
324        /// Differential mode for channels 18 to 16 r
325        /// Differential mode for channels 15 to 1 r/w
326        DIFSEL OFFSET(1) NUMBITS(18) []
327    ],
328    /// Calibration Factors
329    CALFACT [
330        /// Calibration Factors in differential mode
331        CALFACT_D OFFSET(16) NUMBITS(7) [],
332        /// Calibration Factors In Single-Ended mode
333        CALFACT_S OFFSET(0) NUMBITS(7) []
334    ],
335    /// Common status register
336    CSR [
337        /// Injected Context Queue Overflow flag of the slave ADC
338        JQOVF_SLV OFFSET(26) NUMBITS(1) [],
339        /// Analog watchdog 3 flag of the slave ADC
340        AWD3_SLV OFFSET(25) NUMBITS(1) [],
341        /// Analog watchdog 2 flag of the slave ADC
342        AWD2_SLV OFFSET(24) NUMBITS(1) [],
343        /// Analog watchdog 1 flag of the slave ADC
344        AWD1_SLV OFFSET(23) NUMBITS(1) [],
345        /// End of injected sequence flag of the slave ADC
346        JEOS_SLV OFFSET(22) NUMBITS(1) [],
347        /// End of injected conversion flag of the slave ADC
348        JEOC_SLV OFFSET(21) NUMBITS(1) [],
349        /// Overrun flag of the slave ADC
350        OVR_SLV OFFSET(20) NUMBITS(1) [],
351        /// End of regular sequence flag of the slave ADC
352        EOS_SLV OFFSET(19) NUMBITS(1) [],
353        /// End of regular conversion of the slave ADC
354        EOC_SLV OFFSET(18) NUMBITS(1) [],
355        /// End of Sampling phase flag of the slave ADC
356        EOSMP_SLV OFFSET(17) NUMBITS(1) [],
357        /// Slave ADC ready
358        ADRDY_SLV OFFSET(16) NUMBITS(1) [],
359        /// Injected Context Queue Overflow flag of the master ADC
360        JQOVF_MST OFFSET(10) NUMBITS(1) [],
361        /// Analog watchdog 3 flag of the master ADC
362        AWD3_MST OFFSET(9) NUMBITS(1) [],
363        /// Analog watchdog 2 flag of the master ADC
364        AWD2_MST OFFSET(8) NUMBITS(1) [],
365        /// Analog watchdog 1 flag of the master ADC
366        AWD1_MST OFFSET(7) NUMBITS(1) [],
367        /// End of injected sequence flag of the master ADC
368        JEOS_MST OFFSET(6) NUMBITS(1) [],
369        /// End of injected conversion flag of the master ADC
370        JEOC_MST OFFSET(5) NUMBITS(1) [],
371        /// Overrun flag of the master ADC
372        OVR_MST OFFSET(4) NUMBITS(1) [],
373        /// End of regular sequence flag of the master ADC
374        EOS_MST OFFSET(3) NUMBITS(1) [],
375        /// End of regular conversion of the master ADC
376        EOC_MST OFFSET(2) NUMBITS(1) [],
377        /// End of Sampling phase flag of the master ADC
378        EOSMP_MST OFFSET(1) NUMBITS(1) [],
379        /// Master ADC ready
380        ADRDY_MST OFFSET(0) NUMBITS(1) []
381    ],
382    /// Common control register
383    CCR [
384        /// VBAT enable
385        VBATEN OFFSET(24) NUMBITS(1) [],
386        /// Temperature sensor enable
387        TSEN OFFSET(23) NUMBITS(1) [],
388        /// VREFINT enable
389        VREFEN OFFSET(22) NUMBITS(1) [],
390        /// ADC clock mode
391        CKMODE OFFSET(16) NUMBITS(2) [],
392        /// Direct memory access mode for dual ADC mode
393        MDMA OFFSET(14) NUMBITS(2) [],
394        /// DMA configuration (for dual ADC mode)
395        DMACFG OFFSET(13) NUMBITS(1) [],
396        /// Delay between 2 sampling phases
397        DELAY OFFSET(8) NUMBITS(4) [],
398        /// Dual ADC mode selection
399        DUAL OFFSET(0) NUMBITS(5) []
400    ],
401    /// Common regular data register for dual mode
402    CDR [
403        /// Regular data of the slave ADC
404        RDATA_SLV OFFSET(16) NUMBITS(16) [],
405        /// Regular data of the master ADC
406        RDATA_MST OFFSET(0) NUMBITS(16) []
407    ]
408];
409
410const ADC1_BASE: StaticRef<AdcRegisters> =
411    unsafe { StaticRef::new(0x5000_0000 as *const AdcRegisters) };
412
413const ADC12_COMMON_BASE: StaticRef<AdcCommonRegisters> =
414    unsafe { StaticRef::new(0x5000_0300 as *const AdcCommonRegisters) };
415
416#[allow(dead_code)]
417#[repr(u32)]
418#[derive(Copy, Clone, PartialEq)]
419pub enum Channel {
420    Channel0 = 0b00000,
421    Channel1 = 0b00001,
422    Channel2 = 0b00010,
423    Channel3 = 0b00011,
424    Channel4 = 0b00100,
425    Channel5 = 0b00101,
426    Channel6 = 0b00110,
427    Channel7 = 0b00111,
428    Channel8 = 0b01000,
429    Channel9 = 0b01001,
430    Channel10 = 0b01010,
431    Channel11 = 0b01011,
432    Channel12 = 0b01100,
433    Channel13 = 0b01101,
434    Channel14 = 0b01110,
435    Channel15 = 0b01111,
436    Channel16 = 0b10000,
437    Channel17 = 0b10001,
438    Channel18 = 0b10010,
439}
440
441#[allow(dead_code)]
442#[repr(u32)]
443enum DiscontinuousMode {
444    OneChannels = 0b000,
445    TwoChannels = 0b001,
446    ThreeChannels = 0b010,
447    FourChannels = 0b011,
448    FiveChannels = 0b100,
449    SixChannels = 0b101,
450    SevenChannels = 0b110,
451    EightChannels = 0b111,
452}
453
454#[allow(dead_code)]
455#[repr(u32)]
456enum ExternalTriggerDetection {
457    Disabled = 0b00,
458    RisingEdge = 0b01,
459    FallingEdge = 0b10,
460    RisingAndFalling = 0b11,
461}
462
463#[allow(dead_code)]
464#[repr(u32)]
465enum ExternalTriggerSelection {
466    Event0 = 0b0000,
467    Event1 = 0b0001,
468    Event2 = 0b0010,
469    Event3 = 0b0011,
470    Event4 = 0b0100,
471    Event5 = 0b0101,
472    Event6 = 0b0110,
473    Event7 = 0b0111,
474    Event8 = 0b1000,
475    Event9 = 0b1001,
476    Event10 = 0b1010,
477    Event11 = 0b1011,
478    Event12 = 0b1100,
479    Event13 = 0b1101,
480    Event14 = 0b1110,
481    Event15 = 0b1111,
482}
483
484#[allow(dead_code)]
485#[repr(u32)]
486enum DataResolution {
487    Bit12 = 0b00,
488    Bit10 = 0b01,
489    Bit8 = 0b10,
490    Bit6 = 0b11,
491}
492
493#[derive(Copy, Clone, PartialEq)]
494enum ADCStatus {
495    Idle,
496    Off,
497    PoweringOn,
498    OneSample,
499    Continuous,
500}
501
502pub struct Adc<'a> {
503    registers: StaticRef<AdcRegisters>,
504    common_registers: StaticRef<AdcCommonRegisters>,
505    clock: AdcClock<'a>,
506    status: Cell<ADCStatus>,
507    client: OptionalCell<&'a dyn hil::adc::Client>,
508    requested: Cell<ADCStatus>,
509    requested_channel: Cell<u32>,
510    sc_enabled: Cell<bool>,
511}
512
513impl<'a> Adc<'a> {
514    pub const fn new(rcc: &'a rcc::Rcc) -> Self {
515        Self {
516            registers: ADC1_BASE,
517            common_registers: ADC12_COMMON_BASE,
518            clock: AdcClock(rcc::PeripheralClock::new(
519                rcc::PeripheralClockType::AHB(rcc::HCLK::ADC1),
520                rcc,
521            )),
522            status: Cell::new(ADCStatus::Off),
523            client: OptionalCell::empty(),
524            requested: Cell::new(ADCStatus::Idle),
525            requested_channel: Cell::new(0),
526            sc_enabled: Cell::new(false),
527        }
528    }
529
530    pub fn enable_temperature(&self) {
531        self.common_registers.ccr.modify(CCR::TSEN::SET);
532    }
533
534    pub fn enable(&self) {
535        self.status.set(ADCStatus::PoweringOn);
536
537        // Enable adc clock
538        self.enable_clock();
539
540        //Set Synchronous clock mode
541        self.common_registers.ccr.modify(CCR::CKMODE.val(0b01));
542
543        self.registers.cr.modify(CR::ADVREGEN.val(0b00));
544        self.registers.cr.modify(CR::ADVREGEN.val(0b01));
545
546        // Wait for ADVRGEN to enable
547        // This needs to be synchronous because there is no interrupt signaling
548        // when ADVRGEN becomes enabled
549        // we chose 720 because the frequency is 72MHz and it needs 10 us to become enabled
550        for _i in 0..720 {
551            cortexm4f::support::nop()
552        }
553
554        // Enable ADC Ready interrupt
555        self.registers.ier.modify(IER::ADRDYIE::SET);
556
557        // Clear registers
558        self.registers.isr.modify(ISR::ADRDY::CLEAR);
559        self.registers.cr.modify(CR::ADEN::CLEAR);
560        self.registers.cr.modify(CR::ADCALDIF::CLEAR);
561        self.registers.cr.modify(CR::ADCAL::SET);
562
563        // Wait for calibration
564        while self.registers.cr.is_set(CR::ADCAL) {}
565
566        // Enable ADC
567        self.registers.cr.modify(CR::ADEN::SET);
568        // Enable overrun to overwrite old datas
569        self.registers.cfgr.modify(CFGR::OVRMOD::SET);
570    }
571
572    pub fn handle_interrupt(&self) {
573        // Check if ADC is ready
574        if self.registers.isr.is_set(ISR::ADRDY) {
575            // Clear interrupt
576            self.registers.ier.modify(IER::ADRDYIE::CLEAR);
577            // Set Status
578            if self.status.get() == ADCStatus::PoweringOn {
579                self.status.set(ADCStatus::Idle);
580                match self.requested.get() {
581                    ADCStatus::OneSample => {
582                        let _ = self.sample_u32(self.requested_channel.get());
583                        return;
584                    }
585                    _ => {}
586                }
587            }
588        }
589        // Check if regular group conversion ended
590        if self.registers.isr.is_set(ISR::EOC) {
591            // Clear interrupt
592            self.registers.ier.modify(IER::EOCIE::CLEAR);
593            let data = self.registers.dr.read(DR::RDATA);
594            self.client
595                .map(|client| client.sample_ready((data as u16) << 4));
596            if self.status.get() == ADCStatus::Continuous {
597                self.registers.ier.modify(IER::EOCIE::SET);
598            }
599        }
600        // Check if sequence of regular group conversion ended
601        if self.registers.isr.is_set(ISR::EOS) {
602            // Clear interrupt
603            self.registers.ier.modify(IER::EOSIE::CLEAR);
604            self.registers.isr.modify(ISR::EOS::SET);
605            if self.status.get() == ADCStatus::OneSample {
606                // stop adc
607                self.registers.cr.modify(CR::ADSTP::SET);
608                // set state
609                self.status.set(ADCStatus::Idle);
610            }
611        }
612        // Check if sampling ended
613        if self.registers.isr.is_set(ISR::EOSMP) {
614            // Clear interrupt
615            self.registers.ier.modify(IER::EOSMPIE::CLEAR);
616            self.registers.isr.modify(ISR::EOSMP::SET);
617        }
618        // Check if overrun occured
619        if self.registers.isr.is_set(ISR::OVR) {
620            // Clear interrupt
621            self.registers.ier.modify(IER::OVRIE::CLEAR);
622            self.registers.isr.modify(ISR::OVR::SET);
623        }
624    }
625
626    pub fn is_enabled_clock(&self) -> bool {
627        self.clock.is_enabled()
628    }
629
630    pub fn enable_clock(&self) {
631        self.clock.enable();
632    }
633
634    pub fn disable_clock(&self) {
635        self.clock.disable();
636    }
637
638    fn enable_special_channels(&self) {
639        // enabling temperature channel
640        if self.requested_channel.get() == 16 {
641            self.sc_enabled.set(true);
642            self.enable_temperature();
643        }
644    }
645
646    fn sample_u32(&self, channel: u32) -> Result<(), ErrorCode> {
647        if !self.sc_enabled.get() {
648            self.enable_special_channels();
649        }
650        if self.status.get() == ADCStatus::Idle {
651            self.requested.set(ADCStatus::Idle);
652            self.status.set(ADCStatus::OneSample);
653            self.registers.smpr2.modify(SMPR2::SMP16.val(0b100));
654            self.registers.sqr1.modify(SQR1::L.val(0b0000));
655            self.registers.sqr1.modify(SQR1::SQ1.val(channel));
656            self.registers.ier.modify(IER::EOSIE::SET);
657            self.registers.ier.modify(IER::EOCIE::SET);
658            self.registers.ier.modify(IER::EOSMPIE::SET);
659            self.registers.cr.modify(CR::ADSTART::SET);
660            Ok(())
661        } else {
662            Err(ErrorCode::BUSY)
663        }
664    }
665}
666
667struct AdcClock<'a>(rcc::PeripheralClock<'a>);
668
669impl ClockInterface for AdcClock<'_> {
670    fn is_enabled(&self) -> bool {
671        self.0.is_enabled()
672    }
673
674    fn enable(&self) {
675        self.0.enable();
676    }
677
678    fn disable(&self) {
679        self.0.disable();
680    }
681}
682
683impl<'a> hil::adc::Adc<'a> for Adc<'a> {
684    type Channel = Channel;
685
686    fn sample(&self, channel: &Self::Channel) -> Result<(), ErrorCode> {
687        if self.status.get() == ADCStatus::Off {
688            self.requested.set(ADCStatus::OneSample);
689            self.requested_channel.set(*channel as u32);
690            self.enable();
691            Ok(())
692        } else {
693            self.sample_u32(*channel as u32)
694        }
695    }
696
697    fn sample_continuous(
698        &self,
699        _channel: &Self::Channel,
700        _frequency: u32,
701    ) -> Result<(), ErrorCode> {
702        // Has to be implementer with timers because the frequency is too high
703        Err(ErrorCode::NOSUPPORT)
704    }
705
706    fn stop_sampling(&self) -> Result<(), ErrorCode> {
707        if self.status.get() != ADCStatus::Idle && self.status.get() != ADCStatus::Off {
708            self.registers.cr.modify(CR::ADSTP::SET);
709            if self.registers.cfgr.is_set(CFGR::CONT) {
710                self.registers.cfgr.modify(CFGR::CONT::CLEAR);
711            }
712            Ok(())
713        } else {
714            Err(ErrorCode::BUSY)
715        }
716    }
717
718    fn get_resolution_bits(&self) -> usize {
719        12
720    }
721
722    fn get_voltage_reference_mv(&self) -> Option<usize> {
723        Some(3300)
724    }
725
726    fn set_client(&self, client: &'a dyn hil::adc::Client) {
727        self.client.set(client);
728    }
729}
730
731/// Not yet supported
732impl<'a> hil::adc::AdcHighSpeed<'a> for Adc<'a> {
733    /// Capture buffered samples from the ADC continuously at a given
734    /// frequency, calling the client whenever a buffer fills up. The client is
735    /// then expected to either stop sampling or provide an additional buffer
736    /// to sample into. Note that due to hardware constraints the maximum
737    /// frequency range of the ADC is from 187 kHz to 23 Hz (although its
738    /// precision is limited at higher frequencies due to aliasing).
739    ///
740    /// - `channel`: the ADC channel to sample
741    /// - `frequency`: frequency to sample at
742    /// - `buffer1`: first buffer to fill with samples
743    /// - `length1`: number of samples to collect (up to buffer length)
744    /// - `buffer2`: second buffer to fill once the first is full
745    /// - `length2`: number of samples to collect (up to buffer length)
746    fn sample_highspeed(
747        &self,
748        _channel: &Self::Channel,
749        _frequency: u32,
750        buffer1: &'static mut [u16],
751        _length1: usize,
752        buffer2: &'static mut [u16],
753        _length2: usize,
754    ) -> Result<(), (ErrorCode, &'static mut [u16], &'static mut [u16])> {
755        Err((ErrorCode::NOSUPPORT, buffer1, buffer2))
756    }
757
758    /// Provide a new buffer to send on-going buffered continuous samples to.
759    /// This is expected to be called after the `samples_ready` callback.
760    ///
761    /// - `buf`: buffer to fill with samples
762    /// - `length`: number of samples to collect (up to buffer length)
763    fn provide_buffer(
764        &self,
765        buf: &'static mut [u16],
766        _length: usize,
767    ) -> Result<(), (ErrorCode, &'static mut [u16])> {
768        Err((ErrorCode::NOSUPPORT, buf))
769    }
770
771    /// Reclaim buffers after the ADC is stopped.
772    /// This is expected to be called after `stop_sampling`.
773    fn retrieve_buffers(
774        &self,
775    ) -> Result<(Option<&'static mut [u16]>, Option<&'static mut [u16]>), ErrorCode> {
776        Err(ErrorCode::NOSUPPORT)
777    }
778
779    fn set_highspeed_client(&self, _client: &'a dyn hil::adc::HighSpeedClient) {}
780}