Bevor wir uns mit der Definition eines Linux -Systemaufrufs befassen und die Details seiner Ausführung untersuchen, beginnen Sie am besten mit der Definition der verschiedenen Softwareschichten eines typischen Linux -Systems.
Der Linux -Kernel ist ein spezielles Programm, das auf dem niedrigsten verfügbaren Niveau Ihrer Hardware startet und läuft. Es hat die Aufgabe, alles zu orchestrieren, was auf dem Computer ausgeführt wird, einschließlich der Handhabung von Tastatur-, Festplatten- und Netzwerkveranstaltungen, um Zeitscheiben für die Ausführung mehrerer Programme parallel zu liefern.
Wenn der Kernel ein Programm auf Benutzerebene ausführt, virtualisiert er den Speicherplatz so, dass Programme der Ansicht sind, dass sie der einzige Prozess sind, der im Speicher ausgeführt wird. Diese schützende Blase der Hardware- und Software -Isolation erhöht die Sicherheit und Zuverlässigkeit. Eine nicht privilegierte Anwendung kann nicht auf Speicher zu anderen Programmen zugreifen, und wenn dieses Programm abstürzt, endet der Kernel, so dass sie den Rest des Systems nicht schädigen kann.
Die Barriere mit Linux -Systemaufrufen ausrücken
Diese Isolationsschicht zwischen nicht privilegierten Anwendungen bietet eine hervorragende Grenze, um andere Anwendungen und Benutzer im System zu schützen. Ohne eine Möglichkeit, sich mit den anderen Elementen des Computers und in der Außenwelt zu verbinden, könnten Programme nicht viel von irgendetwas erreichen.
Um die Interaktion zu erleichtern, bezeichnet der Kernel ein Software -Gate, mit dem das laufende Programm anfordern kann, dass das Kernel in seinem Namen handelt. Diese Schnittstelle wird als Systemaufruf bezeichnet.
Da Linux der UNIX -Philosophie von „Alles ist eine Datei“ folgt, können viele Funktionen durch Öffnen und Lesen oder Schreiben in eine Datei ausgeführt werden, die ein Gerät sein könnte. Unter Windows können Sie beispielsweise eine Funktion namens Cryptgenrandom verwenden, um auf zufällige Bytes zuzugreifen. Auf Linux kann dies jedoch durchgeführt werden, indem einfach die "Datei"/dev/urandom geöffnet und Bytes mithilfe von Standarddatei -Eingabe-/Ausgabesystemaufrufen gelesen werden. Dieser entscheidende Unterschied ermöglicht eine einfachere Systemanrufschnittstelle.
Wafer-dünner Wrapper
In den meisten Anwendungen werden Systemanrufe nicht direkt an den Kernel getätigt. Praktisch alle Programme verlinken in der Standard -C -Bibliothek, die einen dünnen, aber wichtigen Wrapper um Linux -Systemaufrufe liefert. Die Bibliothek sorgt dafür. Wenn Daten aus dem Anruf empfangen werden, interpretiert der Wrapper die Ergebnisse und gibt sie auf konsistente Weise wieder an das Programm zurück.
Hinter den Kulissen
Jede Funktion in einem Programm, das mit dem System interagiert. Um dies in Aktion zu sehen, beginnen wir mit einem grundlegenden Beispiel.
void main ()Dies ist wahrscheinlich das trivialste C -Programm, das Sie jemals sehen werden. Es erhält einfach die Kontrolle über den Haupteintrittspunkt und beendet sich dann. Es gibt nicht einmal einen Wert zurück, da das Main als nichtig definiert wird. Speichern Sie die Datei als ctest.c und lasst uns es zusammenstellen:
GCC Ctest.c -o ctestSobald es zusammengestellt ist, können wir die Dateigröße als 8664 Bytes sehen. Es kann leicht in Ihrem System variieren, aber es sollte ungefähr 8K sein. Das ist viel Code, nur um einzugeben und zu beenden! Der Grund, warum es 8k ist, ist, dass die LIBC -Laufzeit aufgenommen wird. Auch wenn wir die Symbole ausziehen, ist es immer noch ein bisschen über 6k.
In einem noch einfacheren Beispiel können wir den Linux -System -Aufruf zum Beenden machen, anstatt von der C -Laufzeit abhängig zu sein, um dies für uns zu tun.
void _start ()Hier verschieben wir 1 in das EAX -Register und löschen Sie das EBX -Register (das sonst den Rückgabewert enthalten würde) und rufen Sie den Linux -System -Aufruf Interrupt 0x80 (oder 128 in Dezimal) auf. Dieser Interrupt löst den Kernel aus, um unseren Anruf zu verarbeiten.
Wenn wir unser neues Beispiel kompilieren, genannt Asmtest.c, und streifen Sie die Symbole aus und schließen Sie die Standardbibliothek aus:
gcc -s -nostdlib asmtest.C -o AsmtestWir werden einen binären Binärer weniger als 1K produzieren (auf meinem System liefert es 984 Bytes). Der größte Teil dieses Codes sind ausführbare Headers. Wir rufen jetzt den direkten Linux -Systemanruf an.
Für alle praktischen Zwecke
In fast allen Fällen müssen Sie niemals direkte Systemanrufe in Ihren C -Programmen tätigen. Wenn Sie jedoch die Versammlungssprache verwenden, kann der Bedarf auftreten. Bei der Optimierung ist es jedoch am besten, die C-Bibliotheksfunktionen die Systeme zum Aufrufen zu lassen und nur Ihren leistungskritischen Code in die Assembly-Richtlinien eingebettet zu lassen.
Wenn Sie eine Liste aller verfügbaren Systemanrufe für Linux anzeigen möchten, können Sie diese Referenzseiten überprüfen: Vollständige Liste der Systemanrufe unter LinuxHint.com, filippo.IO/ Linux-Syscall-table/ und oder syscalls.Kernelgrok.com