Hallo,
Es ist eine Funktion aus der API des Schedulers. Also ist es ein Syscall.
Hm, Ansichtssache. Der Punkt ist das ich für Yield trotzdem einen eigenen Einsprungspunkt in den Kernel benötige da der Zeitscheiben-Counter mit Sicherheit keinen Syscall initiieren wird. Wenn dieser dedizierte Einsprungspunkt dann eh vorhanden ist ist eine Zweitnutzung zur Steigerung der Effizienz zwar immer noch ein (kleiner) Konzept-Bruch aber in diesem konkreten Fall meiner Meinung nach absolut okay. Ich bleibe auch der Meinung das Yield, im Gegensatz zu allen anderen Syscalls, keinen
Service anbietet.
dass ein per Software getriggerter IRQ wesentlich krimineller als eine per Software getriggerte Exception ist.
Dem kann und werde ich nicht widersprechen, das wäre ein billiger Trick für ein klein wenig mehr Effizienz (und im Fall das Syscalls über spezielle Befehle gehen auch etwas Code-Ersparnis für eine zusätzliche Return-Methode). Auf x86 gibt es noch genug andere Dinge die man durchaus als
kriminell betrachten kann, da wäre dieser Trick zumindest in guter Gesellschaft.
Es tut mir ja wirklich leid, aber an dieser Stelle muss ich dann auch dein Design mal kritisieren.
Nur zu.
Drei grundsätzlich verschiedene Möglichkeiten, einen Syscall zu machen, spricht dafür, dass dein Design nicht durchdacht genug ist, dass es eine einheitliche Lösung bieten kann.
Der Weg wie meine CPU in den Kernel-Modus wechselt ist immer der selbe (da hat x86 mit mit und ohne Error-Code schon mehr Vielfalt zu bieten), nur der Vector ist jedes mal ein anderer. Auch der Code der am jeweiligen Vector steht ist je nach Aufgabenstellung ein anderer, hier ist mir Effizienz eindeutig wichtiger als Einheitlichkeit (vor allem weil Einheitlichkeit ja nicht zwangsläufig Simplizität ergibt). Nebst dessen das ich immer noch bestreite das Yield ein echter Syscall ist (eine Hardware würde schließlich nie einen Syscall aufrufen). Yield ist IMHO ein Zwischending aus Exception und IRQ, stellt also gegenüber diesen 2 Basis-Konzepten eh schon eine Ausnahme dar.
Wer sagt dir, dass Yield der einzige Syscall ist, der ein bisschen anders ist?
Also mir fällt da nichts weiter ein. Wenn Du da eine Idee haben solltest dann ruhig raus damit. Eine einzige Ausnahme rechtfertigt auf jeden Fall noch nicht ein (deutlich) komplexeres Basis-System.
Solltest du dann nicht Möglichkeiten bieten, ein paar verschiedene, frei definierbare Gruppen von Syscalls anzubieten?
Da hätte ich dann aber immer noch das Problem das ich damit ja nicht den Yield-Exception-Vector erreiche aber das ist ja genau der Grund warum ich einen extra YIELD-Befehl haben will damit der in der CPU genau das selbe auslöst wie eine bestimmte HW-Komponente aber ohne eine HW-Komponente sein zu müssen. Ich könnte auch eine bestimmte Port-Adresse freigeben wo dann bei einem Schreibzugriff der Zeitscheiben-Counter auf 0 gesetzt wird und damit eine Yield-Exception auslöst aber auch das ist ein Sonderweg nur das der nicht primär das CPU-Design betrifft.
Ich weiß, dann landest du bald wieder bei der x86-IDT, aber vielleicht ist das ja doch alles nicht ganz so blöd
Mein Syscall-Befehl ist recht flexibel und es ist auch sehr Effizient möglich im Kernel direkt die richtige Funktion anzuspringen (dazu benötige ich nur 2 Assemblerbefehle). Ich hab sogar vorgesehen das die Syscall-Nummer nicht nur als Immed angegeben werden kann sondern auch aus einem Register kommen darf (quasi eine Art "INT AL").
und Exceptions und IRQs kannst du ja nach wie vor zwingend separat halten
Das sowieso, alles andere wäre ein pures Sicherheitsrisiko.
Dass der Interrupt-Controller den Einsprungspunkt vorgibt, fühlt sich irgendwie komisch an und ich bin mir nicht sicher, ob das so eine tolle Idee ist.
Dann schau Dich mal auf anderen Plattformen um, z.B. bei ARM gibt es auch einen Vectored-IRQ-Controller (VIC) der für jeden seiner IRQs einen individuellen Vector direkt an den CPU-Kern liefern kann, damit werden (gegenüber älteren ARM-CPUs ohne VIC) bei jedem IRQ gleich mal ein paar CPU-Takte eingespart weil die CPU nicht erst den IRQ-Controller befragen muss um welchen IRQ es sich handelt und dann aus einer Tabelle den Funktions-Vector holen muss (man spart also einen Peripherie-Zugriff und einen Speicherzugriff ein). Diese Idee ist nicht nur toll sondern auch flexibel, weil ich als IRQ-Controller-Designer dann immer noch entscheiden kann ob ich so viel Speicherkapazität vorsehe das jeder IRQ einen eigenen Vector bekommen kann (was für einen Monolithen ein echter Vorteil wäre weil man sich dort dann jegliche Form von Dispatcher-Code sparen kann) oder ob der immer den selben Vector liefern soll (was für einen Micro-Kernel keine Einschränkung darstellt weil dieser ja eh IPC-Messages verschickt und damit auch nur einen einzigen generischen IRQ-Handler hat). Das tollste ist aber das diese Flexibilität keine Änderung in der CPU erfordert, man kann also immer die selbe CPU mit verschiedenen IRQ-Controllern kombinieren um je nach Anwendung das Optimum aus Hardware-Kosten und Performance zu gewinnen.
Aber was es auf jeden Fall ist, ist ein weiterer Fall, wo du nicht einheitlich arbeitest.
Ja, das stimmt, zumindest etwas. Meine CPU hat grundsätzlich zwei Möglichkeiten den Einsprungspunkt in den Kernel zu bekommen, einmal aus globalen Controll-Registern (das wird für alle Exceptions und Syscall und Yield so gemacht, sind genau 11 Stück) und dann von Außen als Teil der Antwort des IRQ-Controllers (zusammen mit der IRQ-Nummer und der Anzahl der angelaufenen IRQs) wenn die CPU den IRQ vom IRQ-Controller abholt. Das hat aber nur Auswirkungen auf den Wert in R63 (meinem IP) wenn die CPU vom User-Mode in den Kernel-Mode wechselt, der restliche Zustand (wie z.B. der frische Kernel-Mode-Stack) ist immer identisch.
und genau drei Einsprungspunkte für n Syscalls
Wie kommst du auf 3? Für meinen einen Syscall-Mechanismus hab ich 2 Einsprungspunkte vorgesehen, eigentlich würde das auch mit einem gehen aber bei den zwein macht einer von beiden bestimmte Zusicherungen so das der Code da nichts prüfen muss und schneller zu den eigentlichen Service-Funktionen springen kann (mit nur 2 Assemblerbefehlen, wie oben schon erwähnt). Dieser Zusatz ist natürlich genau auf mein OS abgestimmt und ist im wesentlichen nur eine Hardwarebeschleunigung für etwas das man auch genauso (nur nicht so schnell) in Software machen kann.
die dann im Kernel gemultiplext werden.
Gemultiplext wird bei mir gar nichts im Kernel. Die verschiedenen Einsprungspunkte haben eigenständige Code-Pfade. Die CPU landet bei mir z.B. beim Yield direkt im Code des Schedulers der dann auch sofort seine Arbeit erledigt, es gibt da keine gemeinsame Basis wo alle Mode-Wechsel durch müssen.
Ich habe den subjektiven Eindruck das Du zu x86-lastig denkst.
Grüße
Erik