stm32/adc: Factor out conversion logic
Also guard errata workaround correctly.
This commit is contained in:
		@@ -229,6 +229,27 @@ impl<'d, T: Instance> Adc<'d, T> {
 | 
				
			|||||||
    }
 | 
					    }
 | 
				
			||||||
     */
 | 
					     */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    /// Perform a single conversion.
 | 
				
			||||||
 | 
					    fn convert(&mut self) -> u16 {
 | 
				
			||||||
 | 
					        unsafe {
 | 
				
			||||||
 | 
					            T::regs().isr().modify(|reg| {
 | 
				
			||||||
 | 
					                reg.set_eos(true);
 | 
				
			||||||
 | 
					                reg.set_eoc(true);
 | 
				
			||||||
 | 
					            });
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					            // Start conversion
 | 
				
			||||||
 | 
					            T::regs().cr().modify(|reg| {
 | 
				
			||||||
 | 
					                reg.set_adstart(true);
 | 
				
			||||||
 | 
					            });
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					            while !T::regs().isr().read().eos() {
 | 
				
			||||||
 | 
					                // spin
 | 
				
			||||||
 | 
					            }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					            T::regs().dr().read().0 as u16
 | 
				
			||||||
 | 
					        }
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    pub fn read(&mut self, pin: &mut impl AdcPin<T>) -> u16 {
 | 
					    pub fn read(&mut self, pin: &mut impl AdcPin<T>) -> u16 {
 | 
				
			||||||
        unsafe {
 | 
					        unsafe {
 | 
				
			||||||
            // Make sure bits are off
 | 
					            // Make sure bits are off
 | 
				
			||||||
@@ -259,38 +280,16 @@ impl<'d, T: Instance> Adc<'d, T> {
 | 
				
			|||||||
            // Select channel
 | 
					            // Select channel
 | 
				
			||||||
            T::regs().sqr1().write(|reg| reg.set_sq(0, pin.channel()));
 | 
					            T::regs().sqr1().write(|reg| reg.set_sq(0, pin.channel()));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
            // Start conversion
 | 
					            // Some models are affected by an erratum:
 | 
				
			||||||
            T::regs().isr().modify(|reg| {
 | 
					            // If we perform conversions slower than 1 kHz, the first read ADC value can be
 | 
				
			||||||
                reg.set_eos(true);
 | 
					            // corrupted, so we discard it and measure again.
 | 
				
			||||||
                reg.set_eoc(true);
 | 
					            //
 | 
				
			||||||
            });
 | 
					            // STM32L471xx: Section 2.7.3
 | 
				
			||||||
            T::regs().cr().modify(|reg| {
 | 
					            // STM32G4: Section 2.7.3
 | 
				
			||||||
                reg.set_adstart(true);
 | 
					            #[cfg(any(rcc_l4, rcc_g4))]
 | 
				
			||||||
            });
 | 
					            let _ = self.convert();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
            while !T::regs().isr().read().eos() {
 | 
					            let val = self.convert();
 | 
				
			||||||
                // spin
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
            // Read ADC value first time and discard it, as per errata sheet.
 | 
					 | 
				
			||||||
            // The errata states that if we do conversions slower than 1 kHz, the
 | 
					 | 
				
			||||||
            // first read ADC value can be corrupted, so we discard it and measure again.
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
            let _ = T::regs().dr().read();
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
            T::regs().isr().modify(|reg| {
 | 
					 | 
				
			||||||
                reg.set_eos(true);
 | 
					 | 
				
			||||||
                reg.set_eoc(true);
 | 
					 | 
				
			||||||
            });
 | 
					 | 
				
			||||||
            T::regs().cr().modify(|reg| {
 | 
					 | 
				
			||||||
                reg.set_adstart(true);
 | 
					 | 
				
			||||||
            });
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
            while !T::regs().isr().read().eos() {
 | 
					 | 
				
			||||||
                // spin
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
            let val = T::regs().dr().read().0 as u16;
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
            T::regs().cr().modify(|reg| reg.set_addis(true));
 | 
					            T::regs().cr().modify(|reg| reg.set_addis(true));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user