From 5cf84a4bd96a4eb81121e9cb4c275c96c19493b4 Mon Sep 17 00:00:00 2001 From: Cristian Maglie <c.maglie@arduino.cc> Date: Fri, 26 Sep 2014 13:34:13 +0200 Subject: [PATCH] wiring_analog.c: factored out SYNCBUSY loops --- cores/arduino/wiring_analog.c | 43 ++++++++++++++++++++++------------- 1 file changed, 27 insertions(+), 16 deletions(-) diff --git a/cores/arduino/wiring_analog.c b/cores/arduino/wiring_analog.c index 18658fe9..317ac8b8 100644 --- a/cores/arduino/wiring_analog.c +++ b/cores/arduino/wiring_analog.c @@ -27,20 +27,32 @@ extern "C" { static int _readResolution = 10; static int _writeResolution = 10; +// Wait for synchronization of registers between the clock domains +static __inline__ void syncADC() __attribute__((always_inline, unused)); +static void syncADC() { + while (ADC->STATUS.bit.SYNCBUSY == 1) + ; +} + +// Wait for synchronization of registers between the clock domains +static __inline__ void syncDAC() __attribute__((always_inline, unused)); +static void syncDAC() { + while (DAC->STATUS.bit.SYNCBUSY == 1) + ; +} + void analogReadResolution( int res ) { + syncADC(); switch ( res ) { case 12: - while( ADC->STATUS.bit.SYNCBUSY == 1 ); ADC->CTRLB.bit.RESSEL = ADC_CTRLB_RESSEL_12BIT_Val; break; case 8: - while( ADC->STATUS.bit.SYNCBUSY == 1 ); ADC->CTRLB.bit.RESSEL = ADC_CTRLB_RESSEL_8BIT_Val; break; default: - while( ADC->STATUS.bit.SYNCBUSY == 1 ); ADC->CTRLB.bit.RESSEL = ADC_CTRLB_RESSEL_10BIT_Val; break; } @@ -77,7 +89,7 @@ static inline uint32_t mapResolution( uint32_t value, uint32_t from, uint32_t to */ void analogReference( eAnalogReference ulMode ) { - while ( ADC->STATUS.bit.SYNCBUSY == 1 ); + syncADC(); switch ( ulMode ) { case AR_INTERNAL: @@ -122,15 +134,15 @@ uint32_t analogRead( uint32_t ulPin ) if (ulPin == A0) // Disable DAC, if analogWrite(A0,dval) used previously the DAC is enabled { - while ( DAC->STATUS.bit.SYNCBUSY == 1 ); + syncDAC(); DAC->CTRLA.bit.ENABLE = 0x00; // Disable DAC //DAC->CTRLB.bit.EOEN = 0x00; // The DAC output is turned off. - while ( DAC->STATUS.bit.SYNCBUSY == 1 ); + syncDAC(); } pinPeripheral(ulPin, g_APinDescription[ulPin].ulPinType); - while ( ADC->STATUS.bit.SYNCBUSY == 1 ); + syncADC(); ADC->INPUTCTRL.bit.MUXPOS = g_APinDescription[ulPin].ulADCChannelNumber; // Selection for the positive ADC input // Control A @@ -145,28 +157,27 @@ uint32_t analogRead( uint32_t ulPin ) * Before enabling the ADC, the asynchronous clock source must be selected and enabled, and the ADC reference must be * configured. The first conversion after the reference is changed must not be used. */ - while ( ADC->STATUS.bit.SYNCBUSY == 1 ); + syncADC(); ADC->CTRLA.bit.ENABLE = 0x01; // Enable ADC - while ( ADC->STATUS.bit.SYNCBUSY == 1 ); // Start conversion - while ( ADC->STATUS.bit.SYNCBUSY == 1 ); + syncADC(); ADC->SWTRIG.bit.START = 1; // Clear the Data Ready flag ADC->INTFLAG.bit.RESRDY = 1; // Start conversion again, since The first conversion after the reference is changed must not be used. - while ( ADC->STATUS.bit.SYNCBUSY == 1 ); + syncADC(); ADC->SWTRIG.bit.START = 1; // Store the value while ( ADC->INTFLAG.bit.RESRDY == 0 ); // Waiting for conversion to complete valueRead = ADC->RESULT.reg; - while ( ADC->STATUS.bit.SYNCBUSY == 1 ); + syncADC(); ADC->CTRLA.bit.ENABLE = 0x00; // Disable ADC - while ( ADC->STATUS.bit.SYNCBUSY == 1 ); + syncADC(); return valueRead; } @@ -192,11 +203,11 @@ void analogWrite( uint32_t ulPin, uint32_t ulValue ) return; } - while ( DAC->STATUS.bit.SYNCBUSY == 1 ); + syncDAC(); DAC->DATA.reg = ulValue & 0x3FF; // DAC on 10 bits. - while ( DAC->STATUS.bit.SYNCBUSY == 1 ); + syncDAC(); DAC->CTRLA.bit.ENABLE = 0x01; //Enable ADC - while ( DAC->STATUS.bit.SYNCBUSY == 1 ); + syncDAC(); return ; } -- GitLab