Hi, mal eine Fragen zu AVR ATmega Mikrocontrollern: Ein Timer soll alle 10us einen Interrupt auslösen. Die Interuptroutine benötigt aber stets 20us bis sie abgearbeitet ist und geschlossen wird. Was passiert dann genau? Viele Grüße, 006
Der Interrupt wird abgearbeitet und der Interrupt, welcher während des Abarbeiten ausgelöst wird, wird ignoriert. Es gibt keinen Absturz, aber es passiert nicht das, was du vom Programm erwartetst.
Marcel schrieb: > Der Interrupt wird abgearbeitet und der Interrupt, welcher während des > Abarbeiten ausgelöst wird, wird ignoriert. Nö, der nicht.
:
Bearbeitet durch User
006 schrieb: > Ein Timer soll alle 10us einen Interrupt auslösen. > Die Interuptroutine benötigt aber stets 20us bis sie abgearbeitet ist > und geschlossen wird. Dann würde ich effizientere Programmierung und wenn das nichts hilft einen Schnelleren µC verwenden. Der µC wird die ganze Zeit in einer ISR sein und hat keine Zeit für die Ausführung der main();
:
Bearbeitet durch User
Das entsprechende Interrupt-Flag wird zwar gesetzt, aber nicht direkt abgearbeitet. Alle 10µs kommt ein IRQ, alle 20µs ist der Interrupt fertig. Das Programm arbeitet also nur jeden zweiten IRQ ab. Während der IRQ nicht direkt ignoriert wird, wird er aber auch nicht abgearbeitet. Wenn du per sei() am Anfang des Interrupts wieder neue IRQ zulässt wird der Interrupt immer wieder unterbrochen und es wird niemals einer fertig abgearbeitet.
> Der µC wird die ganze Zeit in einer ISR sein und hat keine Zeit für die > Ausführung der main(); Doch, die wird schon ausgeführt (sofern der IP sich in der main() aufhält), aber ziemlich langsam :-) > Wenn du per sei() am Anfang des Interrupts wieder neue IRQ zulässt wird > der Interrupt immer wieder unterbrochen und es wird niemals einer fertig > abgearbeitet. ..und insbesondere läuft der Stack ratzfatz voll. Also ein gaaanz schlechte Idee.
Marcel schrieb: > Wenn du per sei() am Anfang des Interrupts wieder neue IRQ zulässt wird > der Interrupt immer wieder unterbrochen und es wird niemals einer fertig > abgearbeitet. und dann stützt er wirklich ab, dann damit überschreibst du dir nach einer weile den Stack.
Marcel schrieb: > Wenn du per sei() am Anfang des Interrupts wieder neue IRQ zulässt wird > der Interrupt immer wieder unterbrochen und es wird niemals einer fertig > abgearbeitet. Abgesehen davon, daß der Stack dann schnell überläuft: Warum läßt man das in der Architektur zu, einen Interrupt wieder beginnen zu können, wenn er noch nicht fertig ist? Ich kann es noch gar nicht richtig glauben. Bei 8051 ist das doch besser gelöst, und ein Interrupt wird erst automatisch wieder frei gegeben, wenn er beendet wurde. Zusätzlich ist noch gewährleistet, daß zwischen zwei Interrupts immer ein einziger Befehl des Hauptprogrammes noch abgearbeitet wird, damit dieses nicht ganz stehen bleibt. Dort würden Interrupts einfach nur verschluckt, wenn die Verarbeitung länger ist als die Interruptintervalle. Daß immer ein Hauptprogrammbefehl zwischen Interrupts verarbeitet werden muß, war mal ein Fortschritt zu Zeiten, als 8085 und 8048 und kurz darauf der 8051 entwickelt wurde. Den pegelgetriggerten Interrupt macht man sich so beim 8051 für einen Software-Single-Step zu Nutze. Echten Single-Step kann er ja wegen dynamischem Design nicht. Ich kenne ATmega nicht, frage einfach nur mal locker in die Runde.
Da läuft überhaupt kein Stack voll. Wenn ein neuer Interrupt eintrifft, während der µC noch in der ISR ist, dann wird ein Flag gesetzt, dass ein neuer Interrupt eingetreten ist. Sobald die aktuelle ISR verlassen wird, wird die ISR direkt wieder neu gestartet, da ja das Flag gesetzt ist. Wenn also die Interrupts schneller reinkommen als sie abgearbeitet werden, wird lediglich die ISR dauerhaft aufgerufen und bekommt so 100% CPU-Zeit. Aber da es kein rekursiver Aufruf ist (denn erst nach Verlassen wird die ISR erneut aufgerufen), läuft da auch nix über - schon gar nicht der Stack. Also wie A.K. schon sagte: Kein Absturz.
:
Bearbeitet durch Moderator
Ein Elektroniker schrieb: > Abgesehen davon, daß der Stack dann schnell überläuft: Warum läßt man > das in der Architektur zu, einen Interrupt wieder beginnen zu können, > wenn er noch nicht fertig ist? Ich kann es noch gar nicht richtig > glauben. Standardmäßig passiert das ja nicht. Man kann den Interrupt früher erlauben, als das System es vorsieht - wenn man genau weiß, was man da tut. Deine Frage hört sich an wie: "Warum lässt man bei Autos zu, dass man sich nicht anschnallt und dann gegen eine Wand fährt? Ich kann es noch gar nicht richtig glauben."
Ein Elektroniker schrieb: > Abgesehen davon, daß der Stack dann schnell überläuft: Warum läßt man > das in der Architektur zu, einen Interrupt wieder beginnen zu können, > wenn er noch nicht fertig ist? Sie lsst es von Haus aus nicht zu. Aber sie lässte es zu, dass du dir mit SEI absichtlich oder versehentlich in den Fuss schiesst.
Frank M. schrieb: > Da läuft überhaupt kein Stack voll. Das bezog sich auf die SEI Variante. Dann läuft der sehr wohl voll.
006 schrieb: > Was passiert dann genau? Das siehst du am besten, wenn du mal den Simulator anschmeißt. Da kannst du dir jedes Register angucken, auch den Programm Counter.
A. K. schrieb: > Frank M. schrieb: >> Da läuft überhaupt kein Stack voll. > > Das bezog sich auf die SEI Variante. Dann läuft der sehr wohl voll. Dann natürlich ja. Aber nicht alles ist sinnvoll, was auch erlaubt ist. ;-) Ich wollte nur klarstellen, dass im Standardfall (kein frühzeitiges Interrupt-Enable in der ISR selbst) nichts passieren kann. Wer das dennoch macht, muss sich über die Konsequenzen im Klaren sein.
Frank M. schrieb: > Wenn also die Interrupts schneller reinkommen als sie abgearbeitet > werden, wird lediglich die ISR dauerhaft aufgerufen und bekommt so 100% > CPU-Zeit. Scheinbar kann ich beim ATmega dann nicht mit reden. Wenn wirklich zwischen Interrupts das Hauptprogramm überhaupt nicht mehr läuft, wie der eine Befehl, der beim 8051 immer zwischen zwei Interrupts abgearbeitet wird, was man schon 1975 als Mangel erkannte, dann ist das schlecht. Allerdings waren diese µC auch noch auf Assembler und kleine Programme und nicht C optimiert, und mit Abarbeitung komplexerer C-Funktionen in Main kommt man auch nicht besonders weit, daß das Main-Programm gut weiter läuft.
Ein Elektroniker schrieb: > Scheinbar kann ich beim ATmega dann nicht mit reden. Wenn wirklich > zwischen Interrupts das Hauptprogramm überhaupt nicht mehr läuft, wie > der eine Befehl, der beim 8051 immer zwischen zwei Interrupts > abgearbeitet wird, was man schon 1975 als Mangel erkannte, dann ist das > schlecht. Das ist beim AVR genauso. Wie soll man das sonst lösen? Außerdem gab es 1975 noch gar keinen 8051. mfg.
:
Bearbeitet durch User
Die Cortex Ms hingegen kriegt man auf diese Art stillgelegt. Die sind darauf optimiert, ISRs möglichst fix abzuarbeiten, und es ist fixer, direkt von einer ISR in die nächste zu hüpfen, als zweimal den ganzen Stack-Kram abzuarbeiten. Ob man das freilich als Nachteil sehen sollte? Wer seine Kiste so baut, dass sich über eine längere Zeit ISRs dicht an dicht stapeln und im Hauptprogramm rein garnichts mehr geht, der hat wohl etwas falsch kalkuliert.
> Abgesehen davon, daß der Stack dann schnell überläuft: Warum läßt man > das in der Architektur zu, einen Interrupt wieder beginnen zu können, > wenn er noch nicht fertig ist? Ich kann es noch gar nicht richtig > glauben. Weil das eine Voraussetzung für verschachtelte (softwarepriorisierte) Interrupts ist. Du kannst ja nicht nur Interrupts global sperren, sondern die auch für jede Quelle einzeln ein- und ausschalten. > Bei 8051 ist das doch besser gelöst, und ein Interrupt wird erst > automatisch wieder frei gegeben, wenn er beendet wurde. Das ist auch das normale Verhalten. Für Sonderfälle kann man es aber auch anders machen - niemand zwingt dich.
Bei den 8 bit PICs ist es ähnlich: Das Interrupt Enable Bit wird beim Sprung in die ISR gelöscht und dann mit dem RETFIE (Return from Interrupt Enabele) Befehl wieder gesetzt. Dem Programmierer steht es natürlich frei das Bit, wenn er es für sinnvoll hält, früher wieder zu setzen.
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.