where : ibrtses embedded
AVR Pascal (AVRCo) ADC Interrupt
Despite AVRCo offering the ADC as library function, without the source
it sooner or later leads to problems, eg when internal averaging is considered, and is therefore to be avoided.
Here, a replacement with source is provided. Contrary to the provided library
ADC, some more decision have to be made.
the main
In the main, the ADC is handled when the flag ADCDone appears.
VAR
ADCDone:bit;
ADCChannel:byte;
ADCLoop:byte;
CurrentADC:word;
CurrentADClo[@CurrentADC]:byte;
CurrentADChi[@CurrentADC+1]:byte;
ADCBuf:Array[0..7]of word; //averaging location
ADC:Array[0..7]of word; //user location
begin
..
SetupADC;
..
EnableInts;
..
loop
..
if (ADCDone=1) then
.. do whatever here
ADCDone:=0; // clear flag
endif;
..
endloop;
end; // main
The ADC interrupt
The ADC is generally handled with a statemachine what the channel
and averaging concerns. Here, all 8 channels were sampled and averaged
with an "exponential 16" algorithm. The statemachine allows to filter
different channels with different filters.
interrupt ADCRdy; // read ADCL before ADCH
begin
CurrentADClo:=ADCL; //temp var
CurrentADCHi:=ADCH;
ADCBuf[ADCChannel]:=ADCBuf[ADCChannel]+CurrentADC;
if (ADCLoop=15) then // 2^N -1
ADC[ADCChannel]:=ADCBuf[ADCChannel] shr 4;
ADCBuf[ADCChannel]:=0;
if (ADCChannel=7) then
ADCChannel:=0;
ADCLoop:=0;
ADCDone:=true;
else inc(ADCChannel);
endif;
else
inc(ADCChannel);
if (ADCChannel=8) then
inc(ADCLoop);
ADCChannel:=0;
endif;
endif;
ADMUX:=(ADCChannel and $07)or $40;
ADCSRA:=$CF; // enable, start, no free run, div 128, interrupts
end;
Setup the ADC
The setup involves setting the channel, and the speed.
Plus here the involved variables are also set.
procedure SetupADC;
begin
ADMUX:=$40; // AVCC, channel:=0;
ADCSRA:=$CF; // enable, start, no free run, div128, interrupts, 480us/sample
ADCLoop:=0;
ADCChannel:=0;
end;
Questions ?
Suggestions?
Feedback ?
sponsored links
embedded
home
last updated : 10.may.04, or perhaps later
Copyright (99,2004) Ing.Büro R.Tschaggelar