PDA

Archiv verlassen und diese Seite im Standarddesign anzeigen : Problem mit dem ADC beim ATMega32



DarkFire
25.04.2006, 18:01
Hallo,
ich habe heute versucht mit dem eingebauten ADC im ATMEGA32 ein analoges Spannungssignal zu messen. Bzw. wenn man es genau nimmt, messe ich 4 Signale hintereinander.
Für eine Messung nehme ich den Mittelwert aus 4 Messungen.

Das eigentliche Problem liegt darin, das ich den ersten Wert mit der internen Spannung von 2,56V (bei mir 2,37V) messe, die anderen mit der Versorgungsspannung als Referenzspg.

Nun bekomme ich für den ersten Wert bei der ersten Messung den richtigen Wert, bei den darauffolgenden Messungen aber einen falschen Messwert (ca. halb so groß, bzw. genau der Faktor 5/2,37).
Ich habe nachgemessen, und bei den darauffolgenden Messungen liegen am AREF pin die 5V Versorgungsspg an.
Mache ich bei der Messung irgendetwas falsch?
Hier mein Quellcode:


uint16_t Messung (int Messkanal) {

uint16_t result = 0;
uint8_t m = 0;

ADCSRA = (1<<ADEN) | (1<<ADPS1) | (1<<ADPS2) | (1<<ADPS0); //Initialiserung ADC, Frequenzteiler: 128
ADMUX = Messkanal; //Zu verwendender Pin

if (Messkanal == 0x01) ADMUX |= (1<<REFS1) | (1<<REFS0); //interne Referenzspg.

else ADMUX |= (1<<REFS0); //Versorgungsspg.

//Dummy-Messung

ADCSRA |= (1<<ADSC); // eine ADC-Wandlung
while(!(ADCSRA & (1<<ADIF)));
ADCSRA |= (1<<ADIF); // ADIF löschen

// Eigentliche Messung - Mittelwert aus 4 aufeinanderfolgenden Wandlungen
for(m=0;m<4;m++)
{
ADCSRA |= (1<<ADSC); // eine Wandlung "single conversion"
while(!(ADCSRA & (1<<ADIF)));
result += ADC; ADCSRA |= (1<<ADIF); //ADIF löschen
}

ADCSRA &= ~(1<<ADEN); // ADC deaktivieren (2)
result /= 4; // Summe durch vier teilen = arithm. Mittelwert
ADMUX = 0x00; // ADMUX löschen

return result;
}

BlueNature
26.04.2006, 06:30
Servus DarkFire,

Die ADC-Eingänge sind doch nur gemultiplext und führen zusammen auf einen internen realen ADC. Wenn du nun die externe Referenzspannung anlegst und den ADC auf interne Referenz programmierst schiebst du deiner Spannungsreferenz eine 5V-Spannung ein was der nicht gut tut und eh meist einen Schaden am AVR anrichtet. Mußt dich entscheiden ob intern oder extern oder wenn du extern speist softwareseitig und extern dafür Sorge tragen (gegenseitige sichere Verriegelung) das der kritische Fall nie eintreten kann.

...drück dir mal die Daumen das dein AVR noch intakt ist :)

Grüße Wolfgang

DarkFire
26.04.2006, 06:51
Hallo, da hast du was falsch verstanden.
Ich habe nicht extern an den AREF pin eine Spannung angelegt, sonden im ADMUX Register eingestellt, er soll einmal die interne Referenzsspg vom 2,56V und einmal die Versorgungsspg als Referenz verwenden.

BlueNature
26.04.2006, 07:23
Hast du am AREF-Pin auch den vorgeschriebenen 100nF-Kondensator gegen GND beschaltet? Habe deinen Code durchgesehen mit dem PDF zur Hand, sehe da aber keine Fehler so direkt in den Registeransprachen.

PDF S. 208 von 347
http://www.atmel.com/dyn/resources/prod_documents/doc2503.pdf

Grüße Wolfang

DarkFire
26.04.2006, 11:19
Ja, den 100nF Kondensator habe ich bestückt, und auch die 10µF Induktivität.

ogni42
26.04.2006, 13:17
Also wenn die interne Referenzspannung 2.56V ist und die externe 5V misst der doch genau richtig.

DarkFire
26.04.2006, 17:23
Das Problem ist, wenn ich als Referenzspg. die INTERNE von 2,56V wähle, dann vergleicht er trotzdem mit der Versorrgungsspg. von 5V.
Meiner Meinung nach deshalb, weil diese auch am AREF pin anliegt, wenn ich messe ( ich habe keine externe Spg an den Pin angelegt).

Außer bei der ersten Messung, da liegen die 2,56 bzw. bei mir 2,37V an.

SprinterSB
26.04.2006, 17:56
Wenn Messkanal != 1 ist, nimmst du AVCC als Referenz. Ist Messkanal immer auf 1?

DarkFire
26.04.2006, 21:23
Hallo, da ich 4 Signale messe, ist Messkanal natürlich nicht immer auf 1.
Ich habe aber gerade einen Fehler bemerkt.
Eigentlich wollte ich das Signal am Pin A0 also dann 0x00 bei ADMUX mit der interen Referenzspg. von 2,56V vergleichen, und nicht das am Pin1.
PinA0 ist doch 0 und PinA1 ist 1 beim ADC und nicht wie bei der normalen Portansteuerung Pin0 = 0x01, Pin1 = 0x02.... oder?

Ich habe das natürlich umgeschrieben, aber ohne Erfolg. Nach wie vor stimmt das Ergebnis bei der ersten Messung, bei den darauffolgenen verwendet er wieder die Versorgungsspg als Referenz.