mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik AVR: Vcc gegen interne Referenz messen möglich?


Autor: Wolf (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hi,

ich glaube, hier mal gelesen zu haben, dass man die Versorgungsspannung 
vom AVR quasi ohne externe Beschaltung messen kann, mithilfe der 
internen Referenz.

Wo steht, wie das geht?

Autor: D. W. (dave) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Nen Spannungsteiler nehmen? Oder meinst du ohne Spannungsteiler?

Autor: Johannes M. (johnny-m)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Wolf wrote:
> Wo steht, wie das geht?
Im Abschnitt "Analog to Digital Converter" im Datenblatt Deines AVR. 
Geht mit der internen Bandgap-Referenz.

Autor: Andreas K. (a-k)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
ADC-Referenz auf Vcc und den ADC-Muxer auf die Bandgap-Referenz 
einstellen, dann messen. Wenn die Bandgap-Referenz hinreichend genau 
bekannt ist, lässt sich Vcc daraus ableiten.

Autor: Johannes M. (johnny-m)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Genau. Musst nur umgekehrt denken. Du misst dann die Bandgap-Referenz 
mit AVCC als Referenzspannung. Um AVCC zu ermitteln musste dann eben 
umrechnen.

Autor: Wolf (Gast)
Datum:

Bewertung
1 lesenswert
nicht lesenswert
Danke für den Hinweis.

Rezept:

- Den Pin AVCC auf Vcc legen.

In ADMUX

- AVCC als Voltage Reference

- 1.18V (VBG) als Input Channel


Bei z.B. 4.72V Vcc wird dann 256*(1.18V/4.72) = 64 gemessen..

Autor: Wolf (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
(Antwort auf 16:18..)

Autor: Johannes M. (johnny-m)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Richtig!

Autor: Wolf (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
256
Vcc = ----- * Vref
       ADC

Autor: Wolf (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
.
       256
Vcc = ----- * Vref
       ADC

Autor: Johannes M. (johnny-m)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Misst Du nur mit 8 Bit? Wenn ja, dann ist es richtig...

Autor: Andreas K. (a-k)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
> - Den Pin AVCC auf Vcc legen.

Das ist immer nötig, ob der ADC nun gebraucht wird oder nicht!!!!

Autor: Andreas K. (a-k)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ach ja: Die Herstellungstoleranz der internen Referenz beachten. Wenn 
man es genauer braucht, sollte man pro Controller-Exemplar mal 
nachmessen (= bekanntes Vcc) und entsprechend einpflegen (EEPROM).

Autor: Bastler (Gast)
Datum:

Bewertung
0 lesenswert
nicht 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

Autor: Stefan Ernst (sternst)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Du hast doch schon einen eigenen länglichen Thread mit kompetenten 
Helfern zu deinem Thema. Wozu holst du jetzt zusätzlich noch einen alten 
fremden Thread aus der Mottenkiste?

Autor: Karl Heinz (kbuchegg) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht 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)

Autor: Bastler (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ja ich dachte nur das geht genau in meine Richtung. Ich mein ich möchte 
ja die VCC messen mit Hilfe meiner internen Referenz. Ich komme da noch 
nicht so ganz weiter.

Autor: Bastler (Gast)
Datum:

Bewertung
0 lesenswert
nicht 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
    }

Autor: Karl Heinz (kbuchegg) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht 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.

Autor: Peter Dannegger (peda)
Datum:

Bewertung
0 lesenswert
nicht 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-Tu...

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

Nen 2. Thread aufzumachen gibt auch keine Pluspunkte.


Peter

Autor: Bastler (Gast)
Datum:

Bewertung
0 lesenswert
nicht 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.

Autor: Karl Heinz (kbuchegg) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht 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.

Autor: Helmut Artmeier (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ein Besipiel für destruktive Kommunikation.

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.