Hallo, ich habe zwei SIGNAL()-Funktionen. Eine wird ausgelöst, wenn über die USART ein Zeichen empfangen wurde, um das zu verarbeiten und die andere wird in regelmässigen Abständen durch einen internen Timer-Interrupt ausgelöst. Während der Abarbeitung einer SIGNAL-Funktion wird ja nicht in eine andere Interrupt-Funktion gesprungen. Die Frage ist nun, wird denn danach gesprungen? Also, wenn ein Timer-Interrupt ausgelöst wird, aber nicht in die Routine gesprungen wird, weil gerade meine USART-SIGNAL-Funktion läuft, wird dann nach der Abarbeitung der USART-Funktion noch die Timer-Funktion abgearbeitet? Oder fällt die dann unter den Tisch? (Die Genauigkeit des Timers ist hier nicht soo wichtig). Falls es eine Rolle spielt: ATMega32. Danke, Sebastian
Schon wieder ein typischer Fall von Nichtlesen des Datenblattes !!! Darin stehts nämlich: "Reset and Interrupt Handling" Peter
Der Peter ist ja wieder gut drauf :) @Sebastian Ja, sie wird noch abgearbeitet.
Der 2. Interrupt wird abgearbeitet, wenn der erste beendet ist, genauer: wenn das I-Flag im Register SREG (gloabal IR enable) wieder 1 ist. Ein IR geht deshalb nicht verloren (höchstens Du wartest solange, dass schon der 2.Timer-IR aufgetreten ist). Stefan
Eine Interrupt-Funktion kannst du unterbrechbar machen indem du am Anfang der Funktion ein SREG |= 128; schreibst. Michael
>> genauer: >> wenn das I-Flag im Register SREG (gloabal IR enable) wieder 1 ist. ich mag mich ja täuschen, aber dazwischen wird noch eine Instruction aus dem laufenden Programm abgearbeitet. Also für genaues Timing sollte man wirklich das Datenblatt hernehmen, und so gesehen ist Peters Antwort absolut richtig. grüsse leo9
> Eine Interrupt-Funktion kannst du unterbrechbar machen indem du am > Anfang der Funktion ein SREG |= 128; schreibst. Das dürfte so ziemlich der ineffektivste Weg sein. Davon abgesehen, daß die hartcodierte Konstante 128 Sch***e ist (wenn schon, solltest Du (1 << SREG_I) schreiben, damit man auch weiß, wofür's überhaupt gut ist), diese Operation braucht 3 Befehle (IN, ORI, OUT), da SREG nicht mehr in dem Bereich ist, der durch SBI addressiert werden kann. Was glaubst Du, wofür's einen SEI Befehl gibt (in C: sei();)? Der braucht nur einen Befehl. Wenn Du das wirklich gleich am Anfang Deiner ISR haben willst (vorher bitte genau drüber nachdenken -- bei der UART Rx Routine beispielsweise ist das völlig tödlich!), dann kannst Du die ISR auch gleich als INTERRUPT() deklarieren, dann kümmert sich der Compiler bereits darum, bei erster sich bietender Gelegenheit ein SEI einzubauen.
Hallo nochmal. Interessant. Ich wusste nicht (hab auch nicht drüber nachgedacht, wenn ich ehrlich bin), dass man sei() in einer USART-SIGNAL-Funktion aufrufen kann, wenn man (wegen USART) keine INTERRUPT-Routine draus machen kann. Eigentlich logisch. Hab ich aber dieses Mal nicht gemacht. Wie gesagt, so kritisch ist das Timing für mich nicht. Wie auch immer, habe meinen Fehler gefunden (der mich überhaupt zu dieser Frage verleitet hat). War elektrischer Natur (grrrr. Da sucht man tagelang vergeblich nach Fehlern im Code und dann sowas). Danke. Gruß, Sebastian
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.