www.mikrocontroller.net

Forum: Compiler & IDEs tiny24 analog comparator input capture resetet mc


Autor: Reinhold B. (kangarnix)
Datum:
Angehängte Dateien:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,

ich wollte mit dem tiny24 eine Ultraschall-Entfernungsmesser bauen, der 
über den i2c bus abgefragt werden kann.
Für den i2c-bus benutze ich die dateien aus diesem beitrag: 
Beitrag "TWI Slave mit USI AVR312"
I2c funktioniert.
Synchronisation erfolgt über Interrupt0. Signal ist mit nem Oszi zu 
erkennen.
Ultraschall Signal wird vom Empfänger auch detektiert. Gibt ein schönes 
deutliches Signal. der MC reagiert aber nicht wie erwartet.

ich habe zum Fehlersuchen 2 Led auf der platine (PA0 und PA3)
/*Wenn Reset Flag gesetzt Lampen an*/
if ( MCUSR & (1<<WDRF) )
{
  PORTA &= ~(1<<PA3);//test led setzen
  PORTA |= (1<<PA0); 
}
if ( MCUSR & (1<<BORF) )
{
  PORTA |= (1<<PA3);//test led setzen
  PORTA &= ~(1<<PA0); 
}
if ( MCUSR & (1<<EXTRF) )
{
  PORTA &= ~(1<<PA3);//test led setzen
  PORTA &= ~(1<<PA0); 
}
if ( MCUSR & (1<<PORF) )
{
  PORTA |= (1<<PA3);//test led setzen
  PORTA |= (1<<PA0); 
}
  MCUSR &= ~ ((1<<WDRF) | (1<<BORF) | (1<<EXTRF) | (1<< PORF)); //Flags wieder löschen

Damit sollten ja beide LEDs angehen wenn es ein einfacher Power down 
Reset war.
void AC_Initialise(void)
{
//Analog Comparator
  ACSR |= (1<<ACI); // Interrupt Flag clearen

  ACSR   |= (1<<ACIS1)    // Output Rising Edge
    | (1<<ACIS0)   // Output Rising Edge
    | (1<<ACIC);  // Input Capture Timer1

  //nach sei(); noch ACSR |= (1<<ACIE) zum Enablen
  
  //     PORTA &= ~((1<<PA0) | (1 << PA3) | (1 << PA7)); //alle test Led löschen

//Timer1  
  TCCR1B |= (1 << CS11); //Prescaler = 8   //Timer läuft

  TIFR1 |= (1<<ICF1) | (1 << TOV1); // Input Capture Flag + Timer overflow flag clearen // Pending interrupts beenden
  TIMSK1 |= ((1<<ICIE1) | (1<<TOIE1)) ; //Input Capture Interrupt enable + timer overflow interrupt enable  

  //Timer reseten
  TCNT1 = 0;
  
  PINA = _BV(PA3);//test led togglen
}

dieser Aufruf soll PA3 toggeln also led2 auschalten
ISR(ANA_COMP_vect)
{
  Timestamp = 53; //ICR1;
  dataInTimestamp = TRUE;

//  PORTA &= ~(1<<PA3);//test led löschen
  PINA = _BV(PA0);
}
Das ist meine Interrupt-Routine für den Input Capture Interrupt. Sobald 
die auslöst soll (PA0) led1 toggeln, um festzustellen, dass es 
tatsächlich aufgerufen wurde.

Problem:
Wenn ich die Spanung anschließe, leuchten beide leds auf //OK
Led2 geht ganz kurz danach aus //OK
empfange ich ultraschall und das synchronisationssignal, leuchtet led2 
kurz wieder auf //Fehler, hat der MC sich gerade resetet?

ich lese mit dem i2c-master immer nur 52 aus.
demnach immer overflow?
weshalb leuchtet die led kurz auf?

hab diesen beitrag bei meiner fehlersuche gefunden
Beitrag "Kein Zugriff auf globale Variable im Interrupt"
das ist das erste projekt mit dem gcc und nem tiny24 von mir.

Würde mich freuen wenn mir jemand weiterhelfen kann.

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

Bewertung
0 lesenswert
nicht lesenswert
Reinhold B. wrote:
> Das ist meine Interrupt-Routine für den Input Capture Interrupt.
Nö. Das ist der Handler für den Analog-Komparator-Interrupt und nicht 
für Input Capture. Da der Capture-Interrupt freigegeben ist, nicht aber 
der Analog-Komparator-Interrupt, vermute ich mal, dass Du da irgendwo 
ganz gewaltig durcheinander geraten bist.

BTW:
Ein Reset deutet darauf hin, dass tatsächlich ein Interrupt freigegeben 
sein könnte, für den kein Handler existiert.

Autor: Reinhold B. (kangarnix)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
du hast recht gehabt.

ich hab zusätzlich das hier eingefügt
ISR(TIM1_CAPT_vect)
{
  Timestamp = 54; //ICR1;
  dataInTimestamp = TRUE;
  TCCR1B &= ~((1<<CS10) | (1<<CS11) | (1<<CS12)); // Timerstop
  PINA = _BV(PA0);
}

und beim externen Interrupt:
ISR(INT0_vect)
{
  Timestamp = 51;
  TCNT1= 0; //Timer reset
  TCCR1B |= (1 << CS11); //Prescaler = 8   //Timer läuft    
}

jetzt toggelt led1 schön und ich erhalte 54 vom i2c-master zurück.

Vielen Dank!

jetzt werden ja beide Interrupts (Input Capture/ Analog Comparator) 
aufgerufen.  und anscheinend IC zuletzt. Kann ich dann die gesamte 
Routine für ANA_COMP_vect entfernen, oder rationalisiert der compiler 
dann den ganzen Interrupt-handler weg und ich hab wieder nen reset drin?

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

Bewertung
0 lesenswert
nicht lesenswert
Für einen freigegebenen Interrupt muss immer ein Handler existieren. 
Wenn Du keinen schreibst, dann gibt es eben keinen (und das hat nichts 
mit "wegrationalisieren" zu tun).

Abgesehen davon bietet die interrupt.h die Möglichkeiten eines leeren 
Handlers (in dem dann auch nicht zeitraubend Register gepusht und gepopt 
werden) und eines Default-Handlers, der alle freigegebenen Interrupts 
auffängt, für die kein eigener Handler existiert. Ohne explizit 
angegebenen Default-Handler führt ein solcher Interrupt zu einem 
Neustart des Programms (was strenggenommen kein echter Reset ist, aber 
vom Ablauf her wie einer aussieht).

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.