Resetting ADC control flags after continuous read (ATMega2560)/Arduino

  adc, arduino, atmega, c++, cpu-registers

I have am using an ATMega2560 with a resistance touch screen (uses the ADC with analogRead commands). – I also use other ADC pins with analogRead (NTC temp sensor). This all works fine.

I have recently been adding a function that requires me to get ADC readings at known intervals and decided that using the automatic sampling was best – I found the code to do this online and it works well for the function it is required for.

My Issue is after I do the continuous sampling I cannot get the ADC analogRead values to return the same as they where before the continuous sample.
I have checked the datasheet and it says the initial value for the ADCSRA, ADCSRB & ADMUX = 0. – I have tried this and quite a few other things with no success.

I have attached some code that does the same as my program – i.e analogRead returns a different value after the continuous sample.

byte samplesADC[100];
int samplesADCCount = 0;
bool ADCEnd = false;

void startADCAcquire(){
  int dacChan = 14;
  Serial.println("Start ADC Aquire: ");
  
  cli();//diable interrupts
  
  //set up continuous sampling of analog pin 0
  //clear ADCSRA and ADCSRB registers
  ADCSRA = 0;
  ADCSRB = 0;
  
  ADMUX |= dacChan&0x07;
  if (dacChan >= 8) 
      ADCSRB |= _BV(MUX5);
  else
      ADCSRB &= ~_BV(MUX5);
  ADMUX |= (1 << REFS0); //set reference voltage
  ADMUX |= (1 << ADLAR); //left align the ADC value- so we can read highest 8 bits from ADCH register only

  ADCSRA |= (1 << ADPS2) | (1 << ADPS0); //set ADC clock with 32 prescaler- 16mHz/32=500kHz
  ADCSRA |= (1 << ADATE); //enabble auto trigger
  ADCSRA |= (1 << ADIE); //enable interrupts when measurement complete
  ADCSRA |= (1 << ADEN); //enable ADC
  ADCSRA |= (1 << ADSC); //start ADC measurements
  sei();//enable interrupts
}

void stopADCAcquire(){
  Serial.println("");
  Serial.println("Stop ADC Acquire");
  cli();//diable interrupts
  
  //set up continuous sampling of analog pin 0
  //clear ADCSRA and ADCSRB registers
  ADCSRA = 0;
 ADCSRB = 0;
  ADMUX = 0;
//  ADCSRB &= ~_BV(MUX5);
//  ADMUX &= ~(1 << ADLAR); 
//   ADCSRA &= ~(1 << ADSC);       // disable adc interrupt
  sei();//enable interrupts 
}

void setup(){
  
  Serial.begin(9600);
  Serial.println("");
  Serial.println("START");
  Serial.print("Pin A2 (1): ");
  Serial.println(analogRead(A2));
  startADCAcquire();
  int i;
  while(ADCEnd == false){
    i++;
  }
  while ((UCSR0A & _BV (TXC0)) == 0)
    {} 
  Serial.print("Pin A2 (2): ");
  Serial.println(analogRead(A2));
  Serial.println("END");
}

ISR(ADC_vect) {//when new ADC value ready
  samplesADC[samplesADCCount] = ADCH;
  Serial.print(samplesADC[samplesADCCount]);
  Serial.print(", ");
  samplesADCCount++;
  if(samplesADCCount == 100){
   
   stopADCAcquire();
    ADCEnd = true;
  }
}

void loop(){
}

Output:

START
Pin A2 (1): 0
Start ADC Aquire: 
127, 127, 127...... (x100) 
Stop ADC Acquire
Pin A2 (2): 510
END

Thanks!

Source: Windows Questions C++

LEAVE A COMMENT