AVR: Vcc gegen interne Referenz messen möglich?

Gast #1316417
Lesenswert?

Hallo!

Ich sehe gerade in diesem Beitrag dass die interne Referenz mit der VCC 
benutzt wird. Ich habe ein ähnliches Problem. ich möchte bei meinem 
ATtiny 24V eine Batterieüberwachung ausführen. Habe dafür eine 3 V 
Lithium Knopfzelle. Es soll eine Lampe angehen wenn die Spannung auf 2,4 
V abgesunken ist.
Wie programmiere ich das am einfachsten. Im ADMUX muss dann 0010.0001 
stehen. Wenn ich praktisch 2,4 V VCC erreicht habe muss ich 2,4 V 
geteilt durch 1024 rechnen. Dann könnte ich wiederrum sagen wieviele 
Stufen sind dann 1,1 V. Nur wie sage ich das. If-Schleife. 1,1 V wären 
bei VCC 2,4 V ca. 469d Stufen.

Gruß
Thomas
#1316440
Lesenswert?

Weiter oben steht doch die Formel.
Bei dir dann eben 1024 anstelle von 256

Du rechnest   1024 * Vbg / ADC_Wert

Jetzt kommt es drauf an, wieviele Nachkommastellen du haben willst.
Sagen wir einfach mal 1 reicht aus.

Dein ADC_Wert sei 470 gewesen. Vbg (also die Bandgapspannung) sei 1.1V

   1024 * 11 / 470 =

   11264 / 470  = 23

Deine Versorgunsspannung wäre demnach 2.3 Volt
Genau genommen ist sie aber 2.39V. Da aber nicht gerundet wird, kommt 
2.3 raus.

Beachte: Da die Bandgapspannung konstant 1.1V ist und sich bei einem 
Tiny nicht mehr verändert, ist der Ausdruck 1024 * 11 konstant. Du 
kannst ihn also bereits zur Compiletime ausrechnen und zur Laufzeit nur 
noch durch den ADC_Wert dividieren.


Das ist doch simples Dreisatzrechnen:
Eine Apfel wiegt 30 Gramm. Wenn der Inhalt einer Kiste Äpfel 2 Kilo 50 
wiegt, wieviele Äpfel sind dann in der Kiste.
Oder so (Hab jetzt nicht kontrolliert ob die Berechnung in diesem 
Dreisatz dem obigen entspricht)

Und ja: Man kann Formeln nach den Regeln der Mathematik auch so 
umstellen, dass man möglichst viel schon konstant ausgerechnet hat, ehe 
die Division davon was wegschmeisst.
Und nein: Wenn man denkt, dass man zum Berechnen von Geldbeträgen in 
Euro Gleitkomma benötigt, der hat einfach nicht bedacht, dass man 
anstelle von Euros auch in Cent rechnen kann. Aus 2 Euro 58  (also 2.58) 
werden so 258 Cent (also eine ganze Zahl)
Gast #1316458
Lesenswert?

Ja aber mein Hauptproblem ist ja wie kann ich ausdrücken dass er was 
machen soll wenn die interne Referenz genau 470 Stufen beträgt. Wie kann 
man das programmieren. Ich komme nur auf eine IF Abfrage nur habe ich 
keine Ahnung wie man das dann abfragt. Ich gehe ja mal davon aus dass 
immer wieder der Hex Wert von meinen 1,1 V in ADC geschrieben wird.
Müßte also ungefähr dann so lauten:

ADMUX = 0x21h;                     // 0010.0001 b
if (ADC == 470)                   // 470 entspricht 1,1 V
   {
      PORTB |= (0<<PB1);         // PB1 auf 0 damit LED leuchtet
    }
#1316461
Lesenswert?

Bastler schrieb:

> Ja aber mein Hauptproblem ist ja wie kann ich ausdrücken dass er
> was machen soll wenn die interne Referenz genau 470 Stufen beträgt.
>

Na wie macht man denn in C eine Unterscheidung, so dass etwas passieert, 
wenn eine bestimmte Bedingung vorliegt.
Mit einem if. Genau das ist sein Verwendungszweck.

Kann es sein, dass du auch noch massive C-Probleme (unabhängig vom µC 
Programmieren) hast?

> genau 470 Stufen
vergiss die Idee mit genau gleich wieder. Dein ADC wird eher selten 
exakt 470 ausspucken. Das kann mal 471 sein oder auch 469.
Defensiv programmieren!

  if( .... > 471 )

Das wird immer dann wahr, wenn .... den Wert 470 oder größer ergibt.
Du willst ja deinen µC auch dann schlafen legen, wenn die Batterie nach 
dem Einschalten schon leer ist (also weniger als die ominösen 2.4V hat).


> Müßte also ungefähr dann so lauten:
>
> ADMUX = 0x21h;                     // 0010.0001 b
> if (ADC == 470)                   // 470 entspricht 1,1 V
>    {
>       PORTB |= (0<<PB1);         // PB1 auf 0 damit LED leuchtet
>     }

Nein.
Noch nicht mal ungefähr (das if ist schon richtig. aber das davor ist 
Unsinn).


> meinen Hex Wert

Vergiss in diesem Zusammenhang Hex. Du hast eine Zahl. Die muss einer 
bestimmten Bedingung genügen. Ob du das jetzt alles in Hex Schreibweise 
notierst, oder dezimal oder zur Basis 19 ist Jacke wie Hose. Für dich 
als Mensch ist dezimal am leichtesten zu lesen. Also benutz auch 
dezimal.


Es wird Zeit das Tutorial zu studieren, wie man den ADC abfrägt.
#1316476
Lesenswert?

Bastler schrieb:
> Müßte also ungefähr dann so lauten:
>
> ADMUX = 0x21h;                     // 0010.0001 b
> if (ADC == 470)                   // 470 entspricht 1,1 V

Der Kandidat erhält 10 Strafpunkte, gehe zurück über Los:

http://www.mikrocontroller.net/articles/AVR-GCC-Tutorial#Der_interne_ADC_im_AVR

Du solltest erstmal mit ner Blink-LED anfangen, dann Taste usw.

Nen 2. Thread aufzumachen gibt auch keine Pluspunkte.


Peter
Gast #1316490
Lesenswert?

Ich habe da nichts neues aufgemacht sondern meine Frage bei einem 
ähnlichen Thema reingeschrieben. Ich habe für meinen Sensor schon die 
gleiche IF-Abfrage. Darum dachte ich das muss auch dieses Mal so gehen 
dass wenn ein bestimmter Wert im ADC steht ich meine LED zum leuchten 
bringe. Und das mit dem ADMUX habe ich so geschrieben weil es davor drin 
stand. Sprich ich benutze schon VCC als Referenz aber die 1,1 V als 
festen Wert. Darum verstehe ich jetzt auch nicht warum das so falsch 
ist. Dass es nicht funktioniert sehe ich selber auch gerade. Jetzt 
funktioniert die AD-Wandlung vom Sensor nämlich auch nicht mehr obwohl 
ich danach das ADMUX Register wieder umschreibe auf ADMUX = 0x00h. Dass 
man bitweise programmieren kann weiss ich schon aber in dem Fall müßte 
es ja so auch funktionieren.
#1316497
Lesenswert?

Bastler schrieb:

> ich danach das ADMUX Register wieder umschreibe auf ADMUX = 0x00h.

Als erstes änderst du jetzt mal deine Schreibweise.
Anstatt das da alles in eine Hex-Zahl zusammenzufassen, benutzt du die 
(1<<BIT_NAME) Schreibweise (so wie man sie auch im Tutorial sieht). Hier 
hat nämlich keiner Lust, Zahlen in Bits aufzudröseln um dann im 
Datenblatt nachzusehen, was du da eingestellt hast.

Und dann postest du bitte vollständigen Code und nicht nur 3 Zeilen.

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren