Navigation


Dispatcher

  1. Der Dispatcher hat drei Aufgaben:
    • Ist die laufende Task nicht länger lauffähig oder wurde eine höherpriore Task lauffähig, rettet er den Taskkontext dieser Task.
    • Wird eine "schlafende" Task lauffähig, die höher priorisiert ist als die Lauffähige, reserviert der Dispatcher freien Speicher, der neben den Task-Variablen auch Platz für den Kontext enthält. Anschließend teilt er der Task die CPU zu.
    • Lief die höchstpriore lauffähige Task schon einmal, lädt er deren Kontext und teilt der Task die CPU zu. Der Dispatcher macht selbst kein I/O.
  2. Stellt der Dispatcher bei einem Lauf fest, dass die vorher laufende Task auch weiterhin die CPU behalten darf, wird kein Kontext gerettet bzw. geladen und die Task einfach fortgesetzt.
  3. Der Dispatcher prüft als erstes, ob einer der beiden Scheduler laufen muß. Ist das der Fall, verzweigt er in den Scheduler, dessen Lauf von einer IRSR gewünscht wurde.
  4. Der Dispatcher läuft nur an, wenn der "Outer-State" der User-Mode ist. Ist der "Outer-State" der Supervisor-Mode, setzt er lediglich das DPC-Flag, und setzt den Prozeß erster Art, auf den der System-Stack-Pointer zeigt, mit dem Assembler-Befehl "Return from Interrupt" fort. Dies passiert z.B. wenn:
    • Sich eine IRSR durch Dispatcheransprung beendet, diese IRSR jedoch eine niederpriore IRSR unterbrochen hatte.
    • Sich eine IRSR durch Dispatcheransprung beendet, diese IRSR jedoch einen Trap unterbrochen hatte.
    • Sich ein Prozeß zweiter Art in den Supervisor-Mode begeben hat (Trap "OFF") und dann einen anderen Trap (außer "DPC") aufruft, bevor er den Supervisor-Mode mit dem Trap "DPC" verlassen hat. Diese nicht erlaubte, aber vom System beherrschte Variante ist nur in Assemblerprogrammen möglich.

      Ausnahme: Der Dispatcher kann anlaufen, wenn im Supervisor-Mode Ausnahmebehandlungen forciert wurden, wie zum Beispiel Wrong-Opcode-Error und Bus-Error.

  5. Nach dem Anlauf löscht der Dispatcher als erstes bei gesetzter Interruptsperre des Prozessors das DPC-Flag.
  6. Beendet sich eine IRSR, die einen Prozeß zweiter Art unterbrochen hat, durch Aussprung in den Dispatcher und hat kein Prozeß erster Art in der Zwischenzeit das DPC-Flag gesetzt, läuft der Dispatcher gar nicht erst an und kehrt in den Prozeß zweiter Art zurück.
  7. Hat der Dispatcher den Kontext einer Task gerettet, löscht er die Zelle mit der Taskadresse. Auf diese Weise kann er im Inter-Task-State erneut anlaufen oder auch zwischendurch, falls benötigt, die Scheduler aufrufen.
  8. Unmittelbar nach dem Laden eines Taskkontextes schreibt der Dispatcher die Taskadresse in die entsprechende Systemzelle.
  9. Der Dispatcher läuft zwar im Supervisor-Mode, die Interruptsperre des Prozessors ist allerdings fast nie gesetzt.
  10. Während der Dispatcher läuft, kann er erneut für den Aufruf vorgemerkt werden bzw. sogar angesprungen werden. Beendet sich eine IRSR durch Sprung in den Dispatcher, dann erkennt der Dispatcher, daß der "Outer-State" der Supervisor-Mode ist und kehrt per Assembler-Befehl "Return from Interrupt" an die Stelle des Dispatchers zurück, die auf dem Supervisor-Stack liegt.
  11. Auch der Dispatcher prüft an verschiedenen Stellen, ob ein Re-Dispatching notwendig ist und startet ggf. (durch einen Sprung und nicht durch einen Procedure-Call!!!) von vorne. Die vorletzte Prüfung erfolgt im Inter-Task-State. Ein letzter Test erfolgt bei gesetzter Interruptsperre des Prozessors, kurz bevor der höchstpriore lauffähige Prozeß zweiter Art im User-Mode fortgesetzt bzw. gestartet wird.
  12. Im System gibt es immer eine lauffähige Task, die sogenannte Idle-Task. Sie hat die niedrigste Priorität. Ihr einziger Befehl lautet "BRA $" (Sprung auf sich selbst).
  13. Seitdem selbst der Dispatcher preemptionfähig ist, ist die Idle-Task eigentlich überflüssig geworden. Hat keine Task den Zustand lauffähig, können nur noch IRSR oder die beiden Scheduler eine Task in den Zustand lauffähig versetzen. Beides bekommt der Dispatcher mit.