mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik Problem mit AD - Wandler


Autor: Rumpelstilzchen 123 (billson)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
hallo, ich habe ein problem mit dem analog digitalwandler meines 
atmega16.
das programm lässt sich einwandfrei compilieren. doch wenn ich den 
debugger starte, wird der wert umgewandelt, der interrupt gestartet, und 
wenn er dann in das unterprogramm zurückkehrt, bleibt er in der while 
schleife stecken, die zum warten bis zum abschluss der wandlung gedacht 
war.
kann mir jemand damit helfen?

andabei mein programm: der interrupt muss nicht unbedingt verwendet 
werden, doch ich hab ihn aus experimentellen gründen aktiviert.


#include <avr/io.h>
#include <avr/interrupt.h>


void main()
{

  volatile int messung;

  DDRB=0xff;
  PORTB=0x00;
  ADMUX=0x20;
  ADCSRA=0x00;

  sei();          //Interrupts aktivieren

  while (1)
  {

    messung=ADW();

  }
}




ISR (ADC_vect)

{

  ADCSRA=0x00;

}


void ADW()

{
  int messung;

  ADCSRA =0xC8;

  while(ADSC)        //hier steckt der fehler
  {}

  messung=ADCH;
  return messung;
}

danke für die hilfe

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

Bewertung
0 lesenswert
nicht lesenswert
Wolfgang Graf wrote:
>   while(ADSC)        //hier steckt der fehler
>   {}
Gut erkannt! ADSC ist eine Bitnummer, die in einer Headerdatei definiert 
ist. Und die Nummer ist ungleich Null und dementsprechend immer wahr. 
Die (leere) Schleife wird also bis zum Sankt Nimmerleinstag 
ausgeführt... Schau mal im AVR-GCC-Tutorial nach, wie das mit den 
Bitzugriffen läuft (kleiner Tip: Es hat was mit Schiebeoperatoren zu 
tun)...

Autor: Hubert G. (hubertg)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ist nicht die ISR dafür da zu signalisieren das die Messung beendet ist. 
Worauf wartest du in der while-Schleife.

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

Bewertung
0 lesenswert
nicht lesenswert
Übrigens: Wenn Du am Ende von ADW() einfach
return ADCH;
schreibst, kannst Du Dir die funktionslokale Variable messung 
sparen...

Autor: holger (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
>>  while(ADSC)        //hier steckt der fehler

ADSC ist nur die Bitnummer dieses Bits. Das kannst du
so nicht direkt lesen. Das while(ADSC) endet also nie
weil ADSC ein Wert größer Null ist.

Du musst das Register lesen in dem ADSC steht
und entsprechend verknüpfen:

  while(ADCSRA & (1<<ADSC))

Autor: Herbert vom Karvenzmann (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
So würde ich das Programm nicht strukturieren. Busywait vertrödelt doch 
nur unnötig Rechenleistung. Dazu gibt es doch Alternativen.

Der ADC kann einen Interrupt auslösen wenn er fertig ist.

Der ADC kann im Free-Run-Mode vor sich hin werkeln, im Timer-Interrupt 
fragt (oder hieß das frägt ?) man mal so nebenbei sein letztes 
Ergebnis ab, sichert es und schaltet bei Bedarf den Eingangsmultiplexer 
um.

Das sind alles Methoden, bei denen der AVR nicht im Busywait hängt und 
derweil andere Dinge erledigen kann.

Gruß aus dem Karvendel,
HerBert

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

Bewertung
0 lesenswert
nicht lesenswert
Herbert vom Karvenzmann wrote:
> So würde ich das Programm nicht strukturieren. Busywait vertrödelt doch
> nur unnötig Rechenleistung. Dazu gibt es doch Alternativen.
Ich glaube nicht, dass ein Anfänger in seinem ersten Testprogramm 
irgendeinen Wert auf seine Rechenleistung legt. Warum muss immer alles 
gleich optimiert werden? Lasst ihn doch erst mal überhaupt was aus 
seinem ADC rausbekommen. Wenn er das Tutorial durcharbeitet, kommt er 
früher oder später selbst darauf...

Autor: Martin (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Und ich würde der Funktion einen Datentyp geben, nicht void, bei void 
kannste keine Werte zurückgeben

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

Bewertung
0 lesenswert
nicht lesenswert
Martin wrote:
> Und ich würde der Funktion einen Datentyp geben, nicht void, bei void
> kannste keine Werte zurückgeben
Das stimmt allerdings...

Autor: Rumpelstilzchen 123 (billson)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
danke für die vielen meldungen, das ganze hat mich schon ein stück
weiter gebracht!
mfg

@ johnny m
du hattest recht, das mit der bitnummer war der fehler, ich war es nur 
so gewohnt, weil man bei einem 8051 controller so eine bitnummer direkt 
(so wie ich es obend versucht habe) abfragen kann.

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.