Hallo, ich habe da mal eine kleine Frage bezüglich Interrupt-Handler. Warum können einem Interrupt grundsätzlich keine Parameter übergeben werden, bzw. warum hat er keine Rückgabewerte? Also es handelt sich hierbei um eine Frage aus einer Klausur. Ich hätte jetzt einfach gedacht, dass das Problem ist, dass der Interrupt irgendwann auslöst und mein main-Programm dadurch unterbrochen wird. Da er an einer X-beliebigen Stelle unterbrochen wird und ich ihn nicht gezielt also z.B. genau in der Codezeile 77 im Programmcode aufrufen kann, also nicht irgendwelchen Variablen angeben kann, die dessen Rückgabewerte speichern sollen, hat es auch keinen Sinn Rückgabeparameter zu verwenden. Außerdem habe ich oft etwas von einem Stack und Variablen sollten volatile sein gelesen und deshalb kann man keine Parameter angeben. Über Hilfe in einfachen und verständlichen Worten wäre ich sehr erfreut! ;) Schonmal Danke an die Leute die sich dafür die Zeit nehmen!
Funktionsparameter werden auf dem Stack uebergeben. Da der Interrupt irgendwann kommt, wie sollten da Parameter auf dem Stack uebergeben werden koennen ? Wenn ein Interrupt vorbei ist, ist alles wie vorher, daher kann auch kein Interrupt resultat auf dem Stack sein. Variablen, die ein Interrupt benoetigt, muessen daher global sein.
Noch nicht Rentner schrieb: > Funktionsparameter werden auf dem Stack uebergeben. Da der Interrupt > irgendwann kommt, wie sollten da Parameter auf dem Stack uebergeben > werden koennen ? die Begründung ist falsch. Das Parameter auf dem Stack übergeben werden ist nirgends festgelegt und je nach Plattform auch nicht (immer) der Fall.
Also erstmal würde nichts dagegen sprechen, daß Parameter an ISRs übergeben würden. Voraussetzung dafür ist allerdings, daß - die Hardware das könnte (da der ISR nicht unter Entwicklerkontrolle aufgerufen wird, muß es der Controller machen) und - die Vorgaben des ABI eingehalten würden (also der/die Paramter an den lt. ABI erwarteten Stellen werden, richtiger Punkt von Peter II). Wie "NochNichtRentner" richtig schreibt, ist das Problem hier des Kontextes; da der ISR nicht kontrolliert aufgerufen wird, muß der Prozessorzustand nach Beendigung des ISRs exakt dem vor Eintritt des ISRs entsprechen. Für Parameter wäre das sogar denkbar (der Prozessorkern müßte je nach ABI nur vor dem Setzen der Parameter die entsprechenden Register pushen und danach wieder poppen oder einen größeren Exception stack frame nutzen), aber der Rückgabewert wäre ein echtes Problem, da der einen Anderen Prozessorzustand impliziert. Parametrierte ISRs würden in gewissen Szenarien sogar Sinn machen, z.B. könnte ein Prozessorkern verschiedene Instanzen von ISRs gleichartiger Funktionalität (z.B. USARTs) über einen gemeinsamen ISR abbilden und Instanzinformationen an den gemeinsamen ISR übergeben (das wird normalerweise über Software gemacht, d.h. jeder ISR hat einen eigenen Eintrag in der IVT, aber jeder Eintrag pusht seine Identifikationsparameter und ruft gemeinsamen Code auf). Allerdings überwiegen m.M. nach die Nachteile so einer möglichen Architektur (größerer Stackbedarf oder ISR Umlaufzeiten, erzwungene ABI Konformität, Fallunterscheidungen je nach benötigter Parameteranzahl etc) die Vorteile (kleinere IVTs, Softwareunterstützung in HW). Mußt Du die Klausur vor oder nach diesem thread schreiben? ;-)
Ok. Anderer Ansatz. Woher sollen die Parameter an die Interrupt Procedur denn ueberhaupt kommen ? Funktionsparameter kommen aus einem Kontext heraus. Welchen Kontext hat eine Interrupt Prozedur ? Genau. Der Kontext ist global. Daher sind auch Interrupt Variablen dort.
Noch ein kleines Detail zum OP: Ein ISR unterbricht nicht notwendigerweise die main() Funktion, sondern irgendwas im Thread Mode, d.h. main() nur wo kein RTOS im Betrieb ist, sonst in der Regel eine vom OS gemanagte task - oder einen anderen, bereits laufenden ISR. Mag wie Haarspalterei klingen, aber in der Praxis werden diese Unterschiede sehr schnell sehr wichtig... ;-)
Es gibt sogar Interrupts mit Parametern -- aber das sind dann sogenannte "Softwareinterrupts", die werden zum Aufrufen von Betriebssystemfunktionen o.ä. verwendet. Der "gute alte" IBM-PC nutzt dieses Konzept zur Kommunikation mit dem BIOS und zum Aufruf von Funktionen von DOS. Die Parameter werden vor Aufruf des Interrupthandlers in Prozessorregistern untergebracht und etwaige Resultate nach Ende des Interrupthandlers wiederum in Prozessorregistern zurückgegeben. Das setzt naturgemäß einen Prozessor voraus, der Softwareinterrupts kennt; die 8-Bit-AVRs kennen so etwas nicht. Hardwareinterrupts hingegen, die völlig asynchron zum Programmablauf auftreten, können keine vom Programm vorgegebenen Parameter übergeben bekommen. Warum das nicht geht, wurde ja schon ausführlich beschrieben.
Ethernut registiert Interrupts mit extern int NutRegisterIrqHandler(IRQ_HANDLER * irh, void (*handler) (void *), void *arg); Die Parameter werden also vorher gespeichert und wenn der Interrupt dann erfolgt, wird der Interruptnutzcode mit Parametern angesprungen.
Das sind dann aber keine Interrupthandler im eigentlichen Sinn mehr, sondern Callback-Funktionen.
Rufus Τ. F. schrieb: > Der "gute alte" IBM-PC nutzt dieses Konzept zur Kommunikation mit dem > BIOS und zum Aufruf von Funktionen von DOS. Ja, INT 0x13. Aber abgesehen davon, dass es ein Software-Interrupt ist, funktioniert das nur mit DOS, in WINDOWS wird der abgefangen und umgeroutet. ARMAnfänger schrieb: > Warum können einem Interrupt grundsätzlich keine Parameter übergeben > werden, bzw. warum hat er keine Rückgabewerte? Also, das stimmt schon mal nicht. Rückgabewerte sind kein Problem, nur - wie sollen diese ausgewertet werden ? Und Parameter könnte nur die CPU übergeben, nur - wie soll die CPU wissen, welche Parameter für Zeile 77 und welche Parameter für Zeile 1234 übergeben werden sollen ?
Rufus Τ. F. schrieb: > Hardwareinterrupts hingegen, die völlig asynchron zum Programmablauf > auftreten, können keine vom Programm vorgegebenen Parameter übergeben > bekommen. Naja, ganz so ist es nicht. Erstens gibt es Hardwareinterrupts, die durchaus synchron zum Programmablauf sind (oder zumindest sein können, wenn man das so will, siehe z.B. Timerinterrupts beim AVR) und zweitens gibt es bei praktisch jeder Architektur die Möglichkeit, die Interruptausführung mittels Interruptsperren zu synchronisieren. In beiden Szenarios sind die Interrupts aus Sicht des zu unterbrechenden Codes nicht mehr unvorhersehbar, sondern deterministisch. Dementsprechend wäre auch in beiden Szenarien eine Parameterübergabe realisierbar. Nur einen Sinn ergibt so ein Konstrukt wohl selten bis garnicht. Da hätte man ja mit mehr oder weniger viel zusätzlichem Aufwand letztlich nur die Funktionalität einer normalen Funktion erreicht und das ganze Konzept von Interrupts ad absurdum geführt. Ich kann mir keinen Anwendungsfall vorstellen, wo das nützlich sein könnte...
c-hater schrieb: > > Naja, ganz so ist es nicht. Erstens gibt es Hardwareinterrupts, die > durchaus synchron zum Programmablauf sind (oder zumindest sein können, > wenn man das so will, siehe z.B. Timerinterrupts beim AVR) und zweitens > gibt es bei praktisch jeder Architektur die Möglichkeit, die > Interruptausführung mittels Interruptsperren zu synchronisieren. In > beiden Szenarios sind die Interrupts aus Sicht des zu unterbrechenden > Codes nicht mehr unvorhersehbar, sondern deterministisch. > Dementsprechend wäre auch in beiden Szenarien eine Parameterübergabe > realisierbar. > ? Stimmt so nicht, wenn ich die obige Aussage richtig interpretiere - es ist im zweiteren Fall deterministisch, wann die Interrupts nicht auftreten können, aber solange die interrupts nicht gesperrt sind, können sie indeterministisch auftreten. Außer man würde sich die Mühe machen, Interrupts so zu sperren, daß sie nur an genau einer Stelle offen sind, aber das würde nun überhaupt keinen Sinn machen...
Okay vielen Dank für die ausführlichen Antworten! Also ich muss die Klausur noch schreiben und die Frage ist mal in einer Klausur gefallen, wurde aber nicht richtig beantwortet. Ich hätte vielleicht präziser sein sollen: Warum kann ein Interrupthandler, der in C wie eine Funktion geschrieben wird - keine Parameter haben oder Rückgabewerte zurückgeben? Also ich nehme jetzt kurz und knapp mit, dass: - es mit "speziellen" Softwareinterrupts durchaus möglich wäre - bei den "normalen/einfachen" ISR jedoch nicht, da der Kontext eine wichtige Rolle spielt. Die CPU kann nicht zuordnen, was mitübergeben werden soll und wer was mit dem Ergebnis anfangen kann. Vielen Dank für die Antworten, ich bewundere es immer wieder, dass es Leute wie euch gibt, die sich die Zeit nehmen um anderen bei solchen Dingen zu helfen! Respekt und Danke! ;)
ARMAnfänger schrieb: > es mit "speziellen" Softwareinterrupts durchaus möglich wäre Softwareinterrupts sind definitiv keine Interrupts, sondern normale Prozeduraufrufe mit einer festen Aufrufaddresse. Sie unterbrechen den Programmablauf auch nicht, sondern werden genau da ausgeführt wo der Programmierer sie aufruft. Wer immer sich die Bezeichnung ausgedacht hat (Intel? Microsoft?) hatte mehr Verschleierung im Sinn als logische Klarheit. Georg
Georg schrieb: > Wer immer sich die Bezeichnung ausgedacht hat Spätestens Intel, mit Einführung des INT-Befehls im Befehlssatz des 8086. Eine Vorform davon war der RST-Befehl des 8080.
ARMAnfänger schrieb: > Warum kann ein Interrupthandler, der in C wie eine Funktion geschrieben > wird - keine Parameter haben oder Rückgabewerte zurückgeben? Es hängt ganz grundsätzlich NICHT von irgend einer Programmiersprache ab. In einem µC oder auf dem PC oder eben sonstwo, wo ein Prozessor werkelt, hat man Maschinencode und der wird abgearbeitet und irgendwann zumeist eben nicht präzise vorhersagbar durch einen Interrupt unterbrochen. Deswegen heißt der auch so: Interrupt. Dabei ist es sonnenklar, daß der Zustand des Systems (Register, Flags und so weiter) bei einem Interrupt, der von der Hardware ausgelöst wird, ebenfalls nicht präzise vorhersagbar ist und deshalb alles, was im Interrupt-Handler benutzt wird, eben zuvor in irgend einer Weise gerettet und hinterher restauriert werden muß. Da gibt es ganz grundsätzlich KEINEN Platz für irgendwelche Datenübergaben. Wenn man mit einem Interrupt-Handler kommunizieren will, dann eben NUR per globalen Variablen und auch nur in einer Art, daß beide Seiten nach irgend einem Schema ihre Kommunikation miteinander synchronisieren. Sonst geht das schief und produziert zufällige Fehler. Eine Ausnahme machen eben die erwähnten Soft-Interrupts, bei ARM werden die SVC's genannt (Supervisor Calls). Das sind aber spezielle Maschinenbefehle (die der GCC nicht kann). Sowas ist gut für das Aufrufen von Funktionalitäten aus Betriebssystemen und so, also immer dann, wenn man eine geordnete Schnittstelle zwischen mehreren separat übersetzten Programmteilen benötigt, denn die tatsächliche Adresse des SVC-Handlers und seiner nachgeordneten Funktionen braucht der aufrufenden Anwendung garnicht bekannt zu sein. Hatte ich vor Jahren bei der Lernbetty schon mal vorgeturnt. W.S.
Marc V. schrieb: > ARMAnfänger schrieb: >> Warum können einem Interrupt grundsätzlich keine Parameter übergeben >> werden, bzw. warum hat er keine Rückgabewerte? > > Also, das stimmt schon mal nicht. > Rückgabewerte sind kein Problem, nur - wie sollen diese ausgewertet > werden ? > Und Parameter könnte nur die CPU übergeben, nur - wie soll die CPU > wissen, welche Parameter für Zeile 77 und welche Parameter für Zeile > 1234 übergeben werden sollen ? Streng genommen haben Interrupts teilweise schon gewisse "Parameter", nur nicht in Form von C-Funktionsparametern, sondern zumeist in irgendwelchen I/O-Registern - beispielsweise bei einer UART-Receive-ISR das empfangene Byte.
ARMAnfänger schrieb: > Warum können einem Interrupt grundsätzlich keine Parameter übergeben > werden, bzw. warum hat er keine Rückgabewerte? Leider ist es etwas aus der Mode gekommen (Programm)Flussdiagramme zu zeichnen. Leider... Denn, wenn man das mal tun würde, dann würde sich fix zeigen, dass für die Anwendung und für die (Hardware)ISR, 2 völlig unabhängige Abläufe gezeichnet werden wollen. Da diese keinen Kontakt haben, ist eine direkte Parameterübergabe unmöglich. Zum Glück, durfte ich mich Damals (TM) noch mit Datenflussdiagrammen rumschlagen. Ein solches würde zeigen, dass sich durch einfügen irgendeiner "shared Memory" Variante, sehr wohl ein Datenfluss realisieren lässt. z.B. der Ringbuffer der Seriellen ist ein typisches Beispiel dafür.
Rolf M. schrieb: > Streng genommen haben Interrupts teilweise schon gewisse "Parameter", > nur nicht in Form von C-Funktionsparametern, sondern zumeist in > irgendwelchen I/O-Registern - beispielsweise bei einer UART-Receive-ISR > das empfangene Byte. Streng genommen sind das keine Parameter, sondern der Zustand der CPU und deren Register. Eine UART-ISR benutzt normalerweise nicht die Timer-Register und eine Timer-ISR interessiert UDR nicht, obwohl sich bei beiden der Zustand wahrscheinlich geändert hat.
:
Bearbeitet durch User
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.