Zum Inhalt springen
L

Das Video kommt von YouTube: erst beim Abspielen verbindet sich die Seite mit YouTube (Google).

Betriebssysteme erklärt | Vom Transistor zur KI #3

Hood Informatik44:40 29.256 Aufrufe veröffentlicht Auf YouTube

Das Wichtigste aus dem Video

Tipp auf eine Zeit – das Video springt genau dorthin.

Transkriptautomatisch erstellt · 345 Zeilen
Herunterladen
  1. Heute werden wir über Betriebssysteme sprechen. Das ist der dritte Teil meiner Reihe vom Transistor zur KI. Falls ihr die anderen beiden Videos noch nicht
  2. gesehen habt, checkt die gerne ab. Bevor wir anfangen, kurz zurück zum letzten Video. Ihr habt Fragen gestellt. Zwei davon haben mich besonders gefreut, weil
  3. sie zeigen, dass ihr nicht einfach konsumiert, sondern nachdenkt. Die erste, wenn Maschinencode direkt auf die CPU wirkt, warum hat dann jedes
  4. Betriebssystem seine eigene ausführbare Datei? Also Windows hat z.B. pun Excel Dateien und Linux 11. Müsste man die nicht einfach austauschen können? Die
  5. zweite Frage war, wir haben gesagt, alles sind nur Transistoren, die miteinander verschachtelt sind, aber welcher Transistor gibt als erstes das
  6. Signal? Irgendwo muss das alles doch anfangen, also das klassische Henner Ei Problem. Beide Fragen beantworte ich am Ende dieses Videos vollständig und von
  7. Grund auf. Und wenn ihr bei diesem Video selbst Fragen habt, schreibt sie gerne in die Kommentare. Die besten nehme ich mit ins nächste Video. Jetzt aber
  8. Betriebssysteme. Zu allererst klären wir die Frage, warum es überhaupt Betriebssysteme gibt. Du drückst im Grunde einen Knopf, eine App öffnet
  9. sich. Das Ganze klingt simpel, aber dein Computer macht in diesem Moment etwa eine Million Dinge gleichzeitig. Er lädt Daten aus dem RAM, schreibt auf die
  10. Festplatte, wartet auf deine Maus, spielt Audio ab und hält dabei 15 andere Programme am Laufen. Aber wer koordiniert das alles? Niemand oder
  11. besser gesagt etwas etwas, das so tief im System sitzt, dass die meisten gar nicht darüber nachdenken. Das Betriebssystem. Und bevor ich erkläre,
  12. was das ist, kurze Frage. Stell dir vor, jedes Programm dürfte einfach direkt mit der Hardware reden, direkt mit dem RAM, direkt mit der CPU oder direkt mit der
  13. Festplatte. Was passiert dann? Du hast Chaos. Zwei Programme wollen gleichzeitig in die gleiche Speicheradresse schreiben. Ein Programm
  14. hält die CPU fest und lässt keine anderen ran. oder ein schlecht geschriebenes Tool überschreibt die Daten eines anderen Tools. Das
  15. Betriebssystem existiert, weil wir einen Vermittler brauchen, einen Kontrolleur, eine Abstraktion, die jedem Programm das Gefühl gibt, es sei allein auf dem
  16. Computer, obwohl gerade 100 andere laufen. Ein Betriebssystem ist also ein Programm. Das klingt unspektakulär, ist es aber nicht. Es läuft ununterbrochen
  17. im Hintergrund, während du arbeitest, spielst oder streamst. Er startet Programme, es verwaltet den Speicher, es teilt die CPU auf, es spricht mit
  18. Geräten, es verwaltet Dateien und es sorgt dafür, dass nichts in den Bereich des anderen eindringt. Das Betriebssystem ist super interessant,
  19. weil es quasi die Schicht zwischen deiner Hardware und allem, was du als Software kennst, ist. Ohne dem Betriebssystem gibt es keine Apps, kein
  20. Browser, kein Spotify und im Grunde nur Silizium. Jetzt stellt sich die Frage, wie kommt das Betriebssystem überhaupt ins Leben? Wenn der Computer startet,
  21. wer startet überhaupt das Betriebssystem? Wenn du deinen Computer einschaltest, ist der Arbeitsspeicher leer. Die CPU weiß also nichts. Das
  22. Betriebssystem liegt irgendwo auf der Festplatte. Also wie kommt es von dort in den Betrieb? Das Ganze läuft in Stufen ab. Stufe 1: Strom fließt, die
  23. CPU springt an eine fest einprogrammierte Adresse. Dort liegt die Firmware. Firmware ist quasi Software, die direkt in einem Chip auf dem
  24. Motherboard gespeichert ist. Kein RAM, kein Laufwerk, sondern unveränderlich eingebrannter Code. Auf alten Systemen hieß diese Firmware BIOS, auf modernen
  25. System heißt sie UAFi. Der Unterschied ist, UAFI ist schneller, unterstützt größere Festplatten und hat eine grafische Oberfläche. Aber die Grundidee
  26. ist dieselbe. Die Firmware prüft als erstes, ob die Hardware grundlegend funktioniert. Also ist der RAM vorhanden, antwortet die Grafikkarte,
  27. sind die Eingabegeräte da? Dieser Schritt heißt Post, also Power on Self Test. Danach startet die Stufe 2. Die Firmware sucht nach einem Bootlaufwerk,
  28. also Festplatte, USB, Netzwerk, irgendwo muss ein Bootloader liegen. Ein Bootloader ist ein kleines spezialisiertes Programm mit einer
  29. einzigen Aufgabe, das eigentliche Betriebssystem laden. Die Firmware lädt ihn in den RAM und übergibt die Kontrolle und damit beginnt die Stufe 3.
  30. Der Bootloader auf Linux System z.B. Grab, lädt den Kernel in den Arbeitsspeicher und startet ihn. Der Kernel ist der Kern des Betriebssystems,
  31. dazu gleich mehr. Der Kernel übernimmt, aber er allein macht das System noch nicht benutzbar. Er startet deshalb als allererstes einen einzigen Prozess, den
  32. Init Prozess. Auf modern Linux System heißt das System die. Init ist im Grunde der Startschuss für alles, was du als laufendes System kennst. Er fährt der
  33. Reihe nach alle Dienste hoch, also Netzwerkverbindungen aufbauen, Grafik initialisieren, den Login Bildschirm anzeigen, Hintergrunddienste starten und
  34. so weiter. Jeder Prozess, der danach läuft, direkt oder indirekt, wurde von Init gestartet. Er ist der einzige Prozess, den der Kernel selbst startet.
  35. Den Rest startet Init. Ab diesem Moment ist das System hochgefahren. Aber lasst uns hier mal etwas genauer auf den Kernel schauen. Der Kernel ist der Kern
  36. des Betriebssystems. Der Name kommt nicht von ungefähr. Er ist der Teil, der wirklich mit der Hardware redet. Alle anderen, also deine Apps, deine Shell,
  37. dein Browser, bittet den Kernel nur um Dinge. Der Kernel entscheidet dann, ob und wie er das umsetzt. Der Kernel verwaltet die Hardware, indem es z.B.
  38. über die Treiber die Geräte steuert. Es verwaltet den Speicher, also wer bekommt wie viel oder wer darf auf welche Adressen zugreifen und es verwaltet auch
  39. die Prozesse. Das heißt, welches Programm läuft wann auf der CPU? Der Kernel hat besondere Rechte. Er läuft mit vollen Systemrechten im sogenannten
  40. Kernel Mode. Das bedeutet, er darf alles und genau deshalb läuft normaler Code nicht im Kernel. Das werden wir uns später noch genauer anschauen, aber bis
  41. dahin haben wir noch einiges vor. Und zwar läuft jetzt der Kernel, das ist gut, aber wie startet jetzt ein Programm? Du doppelklickst auf eine App,
  42. aber was passiert da eigentlich? Der Desktop ist übrigens selbst ein Prozess, bemerkt den Klick und sagt dem Kernel: "Sarte dieses Programm." Der Kernel ruft
  43. daraufhin den Loader auf. Der Loader ist Teil des Betriebssystems und hat eine klare Aufgabe. Eine ausführbare Datei von der Festplatte nehmen und daraus ein
  44. laufiges Programm im Arbeitsspeicher machen. Das Ganze läuft so ab. Zuerst liest der Loader die ausführbare Datei. Auf Windows ist das eine Punkt Exe. Auf
  45. Linux ein 11 Binary. 11 steht für Executable and Linkable Format. Es ist kein einfacher Text, sondern ein strukturiertes Format, das dem Loader
  46. genau sagt, hier liegt der Code und hier liegen die Daten und hier fängst du an. Dann legt der Loader den Code im RAM ab und richtet zwei wichtige
  47. Speicherbereiche ein, den Stack und den Hieb. Über die haben wir schon im letzten Video gesprochen. Dann lädt der Loader die benötigten Shared Libraries
  48. nach. Das sind Codebibliotheken, die nicht im Programm selbst stecken, sondern separat auf dem System liegen und sich mehrere Programme gleichzeitig
  49. teilen. Wenn zehn Programme alle Fenster zeichnen wollen, müssen sie nicht alle den gleichen Code mitbringen. Sie nutzen einfach alle dieselbe Library, also
  50. weniger Speicherverbrauch und weniger Redundanz. Zuletzt setzt der Loader den EntryP, also die Adresse der ersten Instruktion, die ausgeführt werden soll.
  51. Die CPU bekommt diese Adresse und legt los. Erst jetzt, nach alldem entsteht ein Prozess. Wichtig, eine Datei auf der Festplatte ist kein Prozess. Sie ist nur
  52. Potenzial, ein Prozess zu werten. Ich habe hier den Programmstart noch mal dargestellt. Also, wir sehen hier quasi noch mal den Ablauf, den ich gerade
  53. beschrieben habe, ne? mit Startadresse. CPU beginnt zu laufen und ab da wird ein Programm quasi zu einem Prozess und das erklärt im Grunde den Programmstart. Wir
  54. können also einfach mal weitergehen zu einem Prozess und einmal erklären, was ein Prozess überhaupt ist. Ein Prozess ist, wie eben gerade beschrieben, ein
  55. laufendes Programm. Das klingt simpel, ist es auch, wenn man es richtig denkt. Jeder Prozess hat seinen eigenen Speicherbereich. Er sieht den Speicher
  56. anderer Prozesse nicht. Das ist wirklich wichtig. Er hat eigene Ressourcen, also geöffnete Dateien, Netzwerkverbindungen, Handles. Er ist aber isoliert und das
  57. Schöne, du kannst hunderte Prozesse gleichzeitig haben und jeder glaubt, er ist allein. Das heißt, wir merken uns, jeder Prozess, ich m
  58. alles einzelne Prozesse, die dann selber noch mal in ihrem Prozess einen Speicherbereich haben und so weiter. Die sind alle separiert voneinander. Das
  59. heißt, jeder Prozessor hat seinen eigenen Speicherbereich, seinen eigenen Stack und Hieb und so weiter. Sie können auch nicht der hier der Prozess kann
  60. jetzt nicht auf den Speicher eines anderen Prozesses zugreifen, aber was ist, wenn ein Programm intern mehrere Dinge gleichzeitig tun soll? Dann kommen
  61. Threats ins Spiel. Ein Thread ist eine Ausführungseinheit innerhalb eines Prozesses. Stell dir vor, ein Programm lädt eine große Datei vom Netzwerk. Wenn
  62. es das in einem einzigen Durchlauf tut, friert die Benutzeroberfläche ein, bis der Download fertig ist. Das wäre eine schlechte Erfahrung für den Nutzer bzw.
  63. wir sagen dazu oft eine schlechte User Experience. Mit Threads kann das Programm sagen, einer kümmert sich um die UI, einer liedt die Datei, einer
  64. verarbeitet die Daten. Alles gleichzeitig innerhalb desselben Prozesses. Threats teilen sich den Speicher des Prozesses und das ist der
  65. gravierende Unterschied. Ich male das hier jetzt noch mal kurz auf. Wir haben jetzt hier einen Prozess, so und wir haben einen weiteren Prozess.
  66. So, die beiden Prozesse teilen sich nicht den Speicher, sie haben unterschiedliche Speicher. Okay, so. Jetzt kannst du aber innerhalb eines
  67. Prozesses mehrere Threads haben. Das heißt, wir haben z.B. Thread 1, dann haben wir hier Ther.
  68. So, also mehrere Arbeiter. Ihr könnt euch diese Threads wie so mehrere kleine Arbeiter innerhalb eines Prozesses vorstellen. Der eine arbeitet die
  69. Grafikoberfläche ab, der andere zieht Daten aus dem Internet und der hier verarbeitet die Daten, die der aus dem Internet holt. Sie teilen sich aber
  70. einen Speicher. Unterschiedliche Prozesse teilen sich nicht denselben Speicher, aber mehrere Threats innerhalb eines Prozesses teilen sich den
  71. Speicher. Okay, also Threads teilen sich den Speicher, laufen parallel und ermöglichen im Grunde Multitasking innerhalb eines Programms. Das ist ihre
  72. Stärke, aber genau da liegt auch eine Gefahr. Denn wenn zwei Threats gleichzeitig auf dieselbe Variable zugreifen, einer liest und der andere
  73. schreibt, ohne sich abzusprechen, passiert etwas türkisches, eine sogenannte Race Condition. Um Race Conditions zu verdeutlichen, habe ich
  74. hier mal zwei Threats aufgezeichnet. Okay? Beide Threats sollen, wenn sie mit ihrer Arbeit fertig sind, eine Variable runterzählen. Sagen wir mal, die
  75. Variable steht hier und die Variable ist aktuell auf einer fünf. So, Fred 1 liest jetzt diese fünf, aber Fred 2 liest diese fünf auch vielleicht zurelben
  76. Zeit. Was dann passiert? Fred 1 sagt 5 - 1. Er will ihn ja runterzählen, aber Fred 2 hat zurelben Zeit die 5 gelesen und sagt jetzt hier auch 5 - 1 bzw.
  77. Thread 2 liest den Wert 5, bevor Thread 1 jetzt seine vier hier zurückschreibt. Jetzt schreibt Fred 1: "Okay, ich habe vier, aber Fred 2 hat trotzdem noch die
  78. fünf gelesen und hat hier als Ergebnis auch die vier. Schreibt also jetzt auch die vier zurück. Das heißt, beide haben eine Operation ausgeführt und beide
  79. haben -1 gemacht und das Ergebnis ist trotzdem falsch. Hier müsste eigentlich eine drei stehen. Und das Ergebnis ist nicht nur falsch, sondern noch
  80. schlimmer. Der Fehler tritt vielleicht nur einmal pro 1000 Durchläufen auf, weil er vom genauen Timing abhängt. Solche Bugs sind schwer zu
  81. reproduzieren, schwer zu finden und können den Produktionssystem jahrelang unbemerkt schlummern. Wir brauchen also einen Weg, wie sich Freats absprechen
  82. können. Ein Mechanismus, der sagt, nur einer von euch darf hier gleichzeitig rein. Dieser Mechanismus heißt Mutex. Schauen wir uns den ganz kurz an. Mutex
  83. steht für Mutual Exclusion und ist wie ein Schloss an einer Tür. Es gibt genau einen Schlüssel. Wenn also nehmen wir mal unser Beispiel, der erste Fred den
  84. Newte Teex auf dieser Variable hält, muss Fred 2 warten, bis Fred 1 fertig ist. Das würde also wie folgt aussehen. Machen wir mal alles hier zurück. Fr 1
  85. nimmt sich jetzt diese Variable hier und blockiert die sozusagen somit. Sagen wir mal, hier ist jetzt so eine Art Schloss drumherum. Blockiert diese, das heißt
  86. Fred 2 fragt jetzt zwar an, aber die ist blockiert. Das heißt, er bekommt sie nicht. Das heißt, Fred 1 macht jetzt erstmal 5 - 1 und schreibt den Wert 4
  87. zurück. Zack, das Schloss wird wieder freigegeben und jetzt kann Fred 2 die 4 nehmen und macht 4 - 1 und schreibt die 3 zurück. Und damit hätten wir ein
  88. korrektes Ergebnis und die Race Condition gelöst. Aber was ist, wenn wir nicht nur gleichzeitig rein dürfen, sondern eine begrenzte Anzahl haben?
  89. Stell dir eine Datenbankverbindung vor, die maximal zehn gleichzeitiger Anfragen erlaubt. Ein Meext würde hier zu stark einschränken. Was wir brauchen ist ein
  90. Meex mit Zähler, also ein Simmer vor. Stell dir einen Parkplatz mit zehn Plätzen vor. Der Simmer vor zählt, wie viele Plätze frei sind. Zehn Threads
  91. dürfen gleichzeitig rein. Der elfte wartet. Wenn einer rausfährt, geht der Zähler wieder hoch. Simpel, effektiv und überall dort nützlich, wo mehrere
  92. Threats gleichzeitig auf eine begrenzte Ressource zugreifen müssen. Mutex und Simfor lösen das Problem des gleichzeitigen Zugriffs, aber sie führen
  93. ein neues Problem ein. Was passiert, wenn Fres anfangen, sich gegenseitig warten zu lassen? Schauen wir uns das Beispiel hier unten an. Fred 1 wartet
  94. auf Ressource 1. Ressource 1 gehört aber gerade Fred 2. Fred 2 wartet auf Ressource 2 und Ressource 2 gehört in dem Moment aber Fred 1. Sie blockieren
  95. sich hier gegenseitig und beide warten und zwar für immer. Keiner gibt nach und keiner kommt weiter. Das ist ein sogenannter Deadlock. Das System hängt
  96. nicht, weil die CPU voll ist, sondern weil zwei Freds sich gegenseitig blockieren. Kein Fehler, kein Crash, einfach Stillstand. Deadlocks sind einer
  97. der Hauptgründe für Programme, die plötzlich einfach einfrieren ohne ersichtliche Ursache. Und wie löst man das? Auch hier gibt's mehrere
  98. Strategien, wie z.B. Timeouts, feste Reihenfolgen und so weiter, aber das ist fürs große Ganze erstmal nicht so wichtig. Falls ihr wollt, kann ich dazu
  99. ein separates Video machen, aber hier reicht's erstmal davon gehört zu haben. Wir haben also jetzt Prozesse, Threats und Mechanismen, die Sie in Schach
  100. halten, aber wir haben noch ein offenes Problem. Wir haben potenziell hunderte von Prozessen und nur eine oder wenige CPUs. Wer entscheidet also, wer wann
  101. dran ist? Das Ganze passiert über das Scheduling bzw. Scheduling. Das Scheduling ist die Kunst, viele Prozesse auf wenige CPUs so zu verteilen, dass
  102. sich alles flüssig anfühlt. Die CPU kann nämlich nur einen Prozess gleichzeitig ausführen pro Kern. Das ist sehr interessant, wenn man darüber nachdenkt,
  103. weil du hast vielleicht 200 Prozesse laufen. Was macht also das Betriebssystem? Es wechselt und zwar extrem schnell. Jeder Prozess bekommt
  104. eine kleine Zeitscheibe zugeteilt, einen sogenannten Time Slice, typischerweise nur wenige Millisekunden. Der Prozess läuft, die Zeit läuft ab, er wird
  105. pausiert und dann ist der nächste dran. So schnell, dass es sich anfühlt wie Parallelität, obwohl es im Kern Sequenzen sind. Also bitte macht euch
  106. das mal bewusst. Den Großteil, den ihr am Rechner macht, passiert nicht parallel. Es wirkt nur wie Parallelität, weil extrem schnell zwischen Prozessen
  107. hin und her gewechselt wird. Aber wer entscheidet, wer als nächstes dran ist? Dafür gibt es Scheduling Algorithmen. Der einfachste ist Round Robin. Bei dem
  108. Algorithmus bekommt jeder gleich viel Zeit. Ist also im Grunde fair, aber in der Praxis reicht das nicht, denn nicht alle Prozesse sind gleich wichtig.
  109. Deshalb arbeiten moderne Betriebssysteme mit Prioritäten. Jeder Prozess hat eine Prioritätsstufe. Prozesse mit hoher Priorität bekommen mehr CPUZit, öfter
  110. oder länger. Ein Systemprozess, der Sicherheitschecks durchführt, hat höhere Priorität als ein Hintergrundprozess, der Daten komprimiert. Besonders
  111. interessant ist die Behandlung von interaktiven Prozessen, also Prozessen, die auf eine Eingabe warten. Ein Texteditor z.B. sitzt die meiste Zeit
  112. Idle bzw. im Leerlauf, tut nichts und wartet. Sobald du aber eine Taste drückst, muss er sofort reagieren, sonst fühlt sich die UI träger an. Das
  113. Betriebssystem erkennt solche Prozesse und bevorzugt sie in dem Moment, wo sie aktiv werden. Das ist kein Zufall, das ist bewusstes Design. Das Gegenteil sind
  114. CPU intensive Prozesse, Videoencoding, Simulation und Kompilierung. Diese laufen im Hintergrund, brauchen viel Zeit, aber niemand wartet aktiv auf ihre
  115. Ausgabe. Sie bekommen niedrige Prioritäten und müssen warten, bis interaktive Prozesse fertig sind. Es gibt noch eine weitere wichtige
  116. Unterscheidung. Prätives versus kooperatives Scheduling. Beim kooperativen Modell, das frühere Systeme wie altes MacOS genutzt haben,
  117. entscheidet der Prozess selbst, wann er die CPU abgibt. Das Problem, ein schlecht geschriebenes oder hängendes Programm gibt sie nie ab und blockiert
  118. alles. Beim prätiven Modell, dem Standard auf allen modernen Betriebssystemen, kann das Betriebssystem Prozess die CPU jederzeit
  119. entziehen. Egal, was der Prozess gerade tut, das Betriebssystem hat das letzte Wort. Das Betriebssystem ist dabei nicht fair im naiven Sinne. Es ist
  120. strategisch. Sein Ziel ist nicht Gleichheit, sondern dass sich das System flüssig anfühlt. Okay, kommen wir zum nächsten interessanten Punkt und zwar
  121. virtuellen Speicher und der ist wirklich interessant. Stell dir vor, du vermietest Wohnungen. Sagen wir mal, du hast 20 Mieter, aber nur 10 Wohnungen.
  122. Also, du hast mehr Leute, die in eine Wohnung rein wollen, als dass du Wohnungen hast. Das klingt erstmal nach Betrug. Aber was ist, wenn die Mieter
  123. nie alle gleichzeitig zu Hause sind? Genauso funktioniert virtueller Speicher. Jeder Prozess glaubt, er hat einen riesigen exklusiven Adressraum für
  124. sich allein. Auf einem 4 Bitsystem sind das theoretisch mehrere 100 TB, mehr als irgendjemand je braucht. Natürlich existiert dieser Speicher nicht
  125. wirklich, aber der Prozess weiß das nicht. Und das ist der Punkt. Das Betriebssystem gibt jedem Prozess virtuelle Adressen. Intern übersetzt es
  126. diese Adressen still und heimlich auf echte physische Adressen im RAM. Der Prozess A denkt z.B. Er liegt bei Adresse 0x1000. In Wirklichkeit liegt er
  127. ganz woanders. Prozess B denkt dasselbe und liegt wieder woanders. Das Ganze bringt drei Dinge auf einmal. Isolation, also kein Prozess sieht den Speicher
  128. eines anderen. Sie leben in getrennten Welten, auch wenn sie sich denselben physischen RAM teilen und Flexibilität. Das Betriebssystem kann Speicher intern
  129. verschieben und neu organisieren, ohne dass irgendein Prozess davon mitbekommt. Und Schutz. Wenn ein Prozess auf eine Adresse zugreift, die ihm nicht gehört,
  130. fängt das Betriebssystem es ab. Kein stilles Überschreiben und kein Datenchaos. Aber wie werden diese virtuellen Adressen eigentlich
  131. organisiert? Das Betriebssystem braucht im Grunde einen Weg, den Speicher clever aufzuteilen. Nicht als einen großen Block, sondern in kleine hunterbare
  132. Stücke. Diese Stücke heißen Pages. Der gesamte Adressraum, virtuell wie physisch wird in gleich große Blöcke aufgeteilt. Dieser virtuelle Speicher
  133. ist also das, was euer Prozess eigentlich sieht und dieser physische Memory hier, das ist euer RAM. Und ihr seht, wir teilen die in gleich große
  134. Blöcke auf. Das heißt, jeder dieser Blöcke hier ist in etwa 4 KB groß. Also sowohl hier im virtuellen Speicher als auch im physischen Speicher. Der RAM
  135. besteht aus sogenannten Page Frames, also das sind diese gleich großen physischen Slots. Das Betriebssystem hier hält eine Tabelle, welche virtuelle
  136. Page in welchem physischen Frame liegt. Diese Tabelle heißt Page Table. Hier wird sie Memory Map genannt. Und jetzt kommt der eigentliche Trick. Nicht alle
  137. Pages müssen gleichzeitig im RAM sein. Das Betriebssystem lädt nur die Pages, die gerade wirklich gebraucht werden. Alles andere liegt auf der Festplatte
  138. und wartet. Wenn ein Prozess auf eine Adresse zugreift, deren Page gerade nicht im RAM ist, passiert ein sogenannter Page Fault. Das
  139. Betriebssystem bemerkt das, holt die Page von der Festplatte nach, legt sie in einen freien Frame und aktualisiert diese Page Table hier. Der Prozess läuft
  140. weiter, als wäre nichts gewesen. Du bemerkst davon also nichts, außer vielleicht einer kurzen Verzögerung. Das System hier wirkt also viel größer, als
  141. das eigentlich ist. Jeder Prozess bekommt seine Illusion von unbegrenztem Speicher, während das Betriebssystem im Hintergrund jongliert. Ihr seht es hier
  142. auch im Bild, ne? Der virtuelle Speicher wird größer dargestellt als der eigentliche physische Speicherplatz. Aber was passiert, wenn hier der RAM so
  143. voll ist, dass auch dieses Jonglieren nicht mehr reicht? Wenn wirklich kein freier Frame mehr übrig ist, dann muss das Betriebssystem eine Entscheidung
  144. treffen und zwar welche Page fliegt raus? Es wählt eine Page hier aus dem physischen Memory, die lange nicht mehr genutzt wurde und schiebt sie auf die
  145. Festplatte und zwar in einen reservierten Speicherbereich, den sogenannten Swapbereich. Der Frame ist jetzt frei und kann einer neuen Page
  146. gegeben werden. Das heißt, wir tauschen im Grunde hier Pages aus. Die Festplatte hier fungiert also langsame Verlängerung des RAMs. Wenn die ausgelagerte Page
  147. wieder gebraucht wird, holt das Betriebssystem sie wieder zurück und muss dafür möglicherweise wieder eine andere rausschieben. Das funktioniert,
  148. bis es nicht mehr funktioniert. Wenn das System ständig Pages rein und rausschiebt, weil der RAM chronisch zu voll ist, spricht man von Trashing. Die
  149. CPU verbringt mehr Zeit damit, Pages zu verschieben, als tatsächlich Arbeit zu erledigen. Die Festplatte rattert und alles stockt. Jeder von uns hatte schon
  150. mal dieses Gefühl. Wenn du z.B. zu viele Browser Tabs offen hast und zu wenig RAM. Wichtig, Swap ist kein Ersatz für RAM, er ist ein Notnetz. Wir müssen ja
  151. quasi aus einer langsameren Festplatte die Daten bzw. dem Frame erstmal auf den RAM ziehen und das kostet Zeit. Aber jetzt stellt sich eine Frage. Wer
  152. übersetzt eigentlich die virtuellen Adressen bei jedem einzelnen Speicherzugriff schnell genug, ohne dass man irgendetwas merkt? Das macht die
  153. sogenannte Memory Management Unit. rein in Software würde diese Übersetzung also von virtuellen Adressen zu physischer Adresse bei jedem einzelnen
  154. Speicherzugriff passieren. Tausende Male pro Sekunde prozess. Das wäre viel zu langsam. Deshalb macht das keine Software, das macht Hardware. Die MMU
  155. ist eine Komponente direkt in der CPU. Das Betriebssystem definiert die Page Tables. Also virtuelle Adresse X liegt bei physischer Adresse Y. Die MMU führt
  156. diese Übersetzung dann in Hardware aus und zwar bei jedem Speicherzugriff in immens schneller Zeit, ohne dass die Software eingreifen muss. Software
  157. definiert also die Regeln, aber die Hardware setzt sie um. Das ist eigentlich das Muster hinter vielen Dingen, die wir in dieser Reihe gesehen
  158. haben. Das Betriebssystem legt fest, was erlaubt ist und die Hardware stellt sicher, dass es durchgesetzt wird, schneller, als dass es jede Software tun
  159. könnte. Wir haben jetzt also Speicher im Rahmen. Prozesse laufen, Seiten werden geladen und ausgelagert, aber wenn der Computer ausgeht, ist alles weg. Für
  160. dauerhafte Speicherung brauchen wir etwas anderes und dafür brauchen wir ein Dateisystem. Für alles, was überleben soll, also sowas wie Dokumente,
  161. Programme oder das Betriebssystem selbst, brauchen wir die Festplatte. Aber eine rohe Festplatte ist erstmal nur eine sehr lange Sequenz von Nullen
  162. und Einsen. Kein Anfang, kein Ende, keine Struktur. Wie findet man da irgendwas? Genau dafür gibt es das Dateisystem. Das Dateisystem ist die
  163. Struktur, die festlegt, wie Daten auf einem Speichermedium organisiert werden. Es definiert, was eine Datei ist, was ein Ordner ist und wie Fade aufgebaut
  164. sind, wann wurde die Datei erstellt, wer darf sie lesen, wie groß ist sie, wo auf der Festplatte liegen die Dateien tatsächlich. Ohne Dateisystem weiß
  165. niemand, wo eine Datei anfängt und wo sie aufhört. Bekannte Dateisysteme sind z.B. EXT4 auf Linux oder NTFS auf Windows oder APFS auf MacOS. Sie
  166. unterscheiden sich im Grunde in ihren Details, also wie sie z.B. mit großen Dateien umgehen, wie sie sich nach einem Absturz erholen, wie effizient sie
  167. Speicher nutzen. Aber die Grundidee ist überall dieselbe. Struktur über Chaos legen. Das Betriebssystem kommuniziert mit dem Dateisystem über eine weitere
  168. Schicht und die führt uns direkt zur nächsten Frage. Wie redet das Betriebssystem eigentlich mit der Hardware darunter? Hardware ist
  169. vielfältig. Eine Grafikkarte von Nvidia funktioniert anders als eine von AMD. eine Festplatte von Samsung anders als eine von Western Digital. Jedes Gerät
  170. hat seine eigene Sprache, seine eigenen Befehle und seine eigene Art zu antworten. Das Betriebssystem kann diese Vielfalt nicht kennen. Es wäre unmöglich
  171. für jede Hardwarekombination der Welt speziellen Code im Kernel zu haben. Die Lösung: Treiber. Ein Treiber ist ein Programm, das als Übersetzer fungiert.
  172. Auf der einen Seite spricht er mit dem Betriebssystem in einer standardisierten generischen Sprache. Auf der anderen Seite spricht er mit dem spezifischen
  173. Gerät in dessen eigener Sprache. Das Betriebssystem sagt z.B. Schreibe diese Daten. Der Treiber übersetzt das in die konkreten Befehle, die genau dieses
  174. Gerät versteht. Das Geniale daran, Programme wissen gar nicht, mit welcher Hardware sie reden. Sie sprechen mit dem Treiber. Der Treiber spricht dann mit
  175. dem Gerät. Du kannst die Grafikkarte wechseln, ohne dass eine einzige App angepasst werden muss, solange es einen Treiber gibt. Also wieder Abstraktion.
  176. Es ist immer wieder dasselbe Prinzip. Und jetzt stellt sich die nächste Frage: Wie bitten Programme eigentlich das Betriebssystem um etwas? Wie läuft diese
  177. Kommunikation ab? Also sauber kontrolliert und sicher. Programme laufen in der Regel im User Mode. Das haben wir bereits festgelegt. Sie dürfen
  178. nicht direkt mit Hardware reden. Im Grunde ist das ja auch der Grund, warum wir Betriebssysteme haben. Sie dürfen also nicht einfach in beliebige
  179. Speicherbereiche schreiben. Sie dürfen nicht selbst entscheiden, wann sie auf die Festplatte zugreifen. Wenn Sie etwas brauchen, müssen Sie fragen. Die
  180. Schnittstelle für diese Anfrage heißt System Call. Kurz SIS Call. Wenn ein Programm eine Datei öffnen will, ruft es nicht selbst die Festplatte an. Es ruft
  181. z.B. den Open Befehl auf. Das Betriebssystem übernimmt, prüft, ob das Programm überhaupt das Recht hat, diese Datei zu öffnen, führt die Operation aus
  182. und gibt das Ergebnis zurück. Gleiches gilt für alles, was mit dem System zu tun hat. Also z.B. Netzwerkpakete senden, Speicher anfordern, einen neuen
  183. Prozess starten, die Uhrzeit abfragen und und. Jedes Mal dasselbe Muster. Programm fragt, Betriebssystem entscheidet und Betriebssystem handelt.
  184. Der Syscall ist der einzig legitime Weg aus dem User Mode heraus. Kein Umweg, kein Trick, keine Abkürzungen. Das Betriebssystem ist der Vermittler immer.
  185. Merkt euch das. Aber rohes Ciscalls direkt aufzurufen ist umständlich und fehleranfällig. Deshalb gibt es eine Zwischenschicht, die das für uns
  186. übernimmt und zwar Systembibliotheken. Du kannst z.B. in deinem C-Programm sowas wie Print F aufrufen. Du willst also Text ausgeben, relativ simpel. Was
  187. du dabei nicht siehst, Print F ist kein Sys Call. Es ist eine Funktion der Standardbibliothek. Auf Linux z.B. die GLPC auf Windows die Win 32 API. Diese
  188. Bibliothek nimmt deinen Aufruf, bereitet alles vor und ruft intern die richtigen Sys Calls auf. Du selbst siehst davon aber nichts. Die Systembibliothek ist
  189. also eine weitere Komfortschicht. Sie vereinfacht, validiert und abstrahiert. Sie übersetzt die menschenfreundliche Sprache, die Programmierer schreiben, in
  190. die präzisen strickten Aufrufe, die der Kernel versteht. Programmierer bzw. Entwickler orientieren sich an der Bibliothek und die Bibliothek selbst
  191. redet mit dem Kernel. Das ergibt eine klare Schichtung Programm, Bibliothek, SS Call, Kernel. Jede Schicht hat ihre Aufgabe. Jede Schicht verbirgt die
  192. Komplexität der Schicht darunter. Also auch hier seht ihr wieder dieses Konzept der Abstrahierung, richtig? Wir greifen nicht direkt auf den Kernel zu, sondern
  193. auf Ciss. Und auch nicht auf Cis direkt, sondern auf Bibliotheken. Das heißt, wir abstrahieren im Grunde hoch, so dass es anwenderfreundlich wird. Aber damit das
  194. alles sicher funktioniert und damit ein Programm den Kernel nicht einfach übernehmen kann, brauchen wir noch das Konzept, das wir bisher nur angedeutet
  195. haben. Die CPU ist im Grunde nicht naiv. Sie weiß, dass nicht jeder Code gleich viel Vertrauen verdient. Deshalb kennt sie verschiedene Privilegstufen. Auf x86
  196. System heißen sie Rings. Ring 0 ist der mächtigste und Ring 3 ist der eingeschränkteste. In der Praxis nutzen moderne Betriebssysteme hauptsächlich
  197. zwei davon. Der Kernel läuft in Ring Null, dem Kernel Mode. Er darf alles, also direkter Zugriff auf Hardware, beliebige Speicheradressen und und keine
  198. Einschränkung. Normale Programme laufen in Ring 3, dem sogenannten User Mode. Sie dürfen deutlich weniger. Also, was wir uns hier im Grunde merken können,
  199. ist alles, was über das einfachste hinausgeht, geht über den Kernel. Das ist kein Zufall, das ist das tragende Designprinzip des gesamten Systems.
  200. Stell dir vor, ein Programm hat einen Bug oder schlimmer, es wurde kompromettiert, jemand hat Chartcode eingeschleust. Im User Mode kann dieser
  201. Code nur das, was das Programm darf, nicht mehr. Es kann nicht ins Betriebssystem einbrechen. Es kann nicht den Speicher anderer Prozesse
  202. manipulieren. Es kann nicht die Hardware direkt ansprechen. Es stürzt ab allein und der Rest läuft weiter. User Mode bedeutet Isolation, Kernel Mode bedeutet
  203. Macht und Verantwortung. Ein Bug im Kernel Mode kann das gesamte System zum Absturz bringen. Deshalb läuft dort so wenig Code wie möglich. Aber wie
  204. wechselt das System zwischen diesem Modi? und zwar kontrolliert sicher und ohne, dass ein Programm einfach in den Kernel Mode springen kann. Und zwar
  205. läuft das Ganze über den Mode Switch. Ein Programm im User Mode kann nämlich nicht einfach entscheiden, ich wechsel jetzt in den Kernel Mode. Das wäre ein
  206. fundamentales Sicherheitsproblem, denn jedes Programm könnte sich beliebige Rechte nehmen. Stattdessen läuft der Wechsel streng kontrolliert ab. Das
  207. Programm ruft ein SIS Call auf, z.B. Open. Und anstatt die Operation selbst auszuführen, löst es eine spezielle CPU Instruktion aus. Auf modernen X86 System
  208. heißt sie Sis Call. Das ist kein normaler Funktionsaufruf. Es ist ein Signal an die CPU selbst. Also die Instruktion selbst heißt CSC. Ich habe
  209. eben gerade auch schon SSCs beschrieben, aber auch die Instruktion heißt CSC. Die CPU reagiert darauf, genauso wie sie auf einen Interrupt reagiert. Auf Interrupts
  210. kommen wir später zu sprechen. Die CPU unterbricht den laufenden Code, sichert den aktuellen Zustand und springt zu einer fest definierten Adresse im
  211. Kernel. Eine Adresse, die das Programm weder kennt noch beeinflussen kann. Der Kernel übernimmt, führt die angeforderte Operation aus, prüft Rechte und liefert
  212. das Ergebnis. Dann schaltet die CPU zurück in den User Mode. Das Programm läuft weiter, als wäre nichts gewesen. Der gesamte Vorgang ist super schnell
  213. abgearbeitet. Du merkst davon nichts, aber er passiert bei jedem Dateizugriff, jedem Netzwerkpaket und jeder Speicheranfrage hunderte Male pro
  214. Sekunde prozess. User Mode und Kernel Mode trennen also Macht von Anwendung. Der Mode Switch ist die einzig kontrollierte Brücke dazwischen und
  215. genau das macht sie so wichtig. Wir haben jetzt also verstanden, wie ein einzelnes Programm mit dem Kernel kommuniziert, aber was ist, wenn zwei
  216. Programme miteinander kommunizieren müssen, obwohl sie strikt voneinander isoliert sind? Und damit kommen wir zur Interprozesskommunikation.
  217. Prozesse sind ja eigentlich isoliert, darüber haben wir vorhin schon gesprochen. Jeder hat seinen eigenen Speicher und seine eigene Welt. Das ist
  218. gut für Sicherheit und Stabilität, aber es wirft eine praktische Frage auf. Was ist, wenn Sie zusammenarbeiten müssen? Ein Webserver empfängt z.B. eine Anfrage
  219. und muss sie an einen Datenbankprozess weitergeben. Ein Programm schreibt z.B. die Logs ein anderes liest und analysiert sie. Eine App besteht z.B.
  220. aus einem Front-Endend und einem Backend Prozess, die ständig Daten austauschen. All das ist normale Realität, aber direkt in den Speicher des anderen
  221. Schreiben darf keiner. Dafür gibt es Interprozesskommunikation, kurz IPC. Pipes sind hier das einfachste Modell. Ein Prozess schreibt, ein
  222. anderer liest. Einseitig und simpel. Das Pipesymbol, das du vielleicht aus der Shell kennst, ist genau das. Die Ausgabe eines Programms wird direkt zur Eingabe
  223. des nächsten. Shared Memory ist das schnellste Modell. Das Betriebssystem gibt zwei Prozessen Zugriff auf denselben physischen Speicherbereich.
  224. Kein Kopieren, direkte Kommunikation. der Haken. Sobald zwei Prozesse gleichzeitig schreiben, sind wir wieder bei Race Conditions.
  225. Synchronisierungsprobleme, die wir bei Freds gesehen haben, gelten hier genauso. Dann gibt es noch Sockets. Sockets sind das flexibelste Modell,
  226. ursprünglich für Netzwerkkommunikation gedacht, aber sie funktionieren genauso lokal zwischen zwei Prozessen auf demselben Rechner. Fast alles Moderne
  227. baut darauf, also http, Datenbankverbindungen, Microservices, ein Prozess sendet und der andere empfängt, als würden sie über ein
  228. Netzwerk reden, auch wenn sie nebeneinander auf derselben Maschine laufen. IPC ist also der Grund, warum komplexe Systeme aus vielen kleinen
  229. isolierten Prozessen bestehen können und trotzdem als Ganzes funktionieren. Da ich Security Background habe, sind Rechte und Sicherheiten natürlich
  230. besonders interessant. Das Betriebssystem weiß nämlich nicht, ob du gute Absichten hast. Es geht davon aus, dass du sie hast, aber es vertraut nicht
  231. darauf. Deshalb verwaltet es Rechte nicht nur für Programme, sondern für alles. Also Nutzer, Gruppen, Dateien, Prozesse. Jeder Nutzer hat eine
  232. eindeutige User ID. Jede Datei gehört einem Nutzer und einer Gruppe. Und für jede Datei legt das Betriebssystem drei Dinge fest. Darf der Besitzer sie lesen,
  233. schreiben und ausführen? Darf die Gruppe das? Und darf jeder andere das. Neun Bits und damit ist der Zugriff für alle Fälle geregelt. In Linux sieht das z.B.
  234. so aus und auch ein Prozess läuft immer im Kontext eines Nutzers mit dessen Rechten nicht mehr und nicht weniger. Wenn das Programm versucht auf eine
  235. Datei zuzugreifen, für die es keine Berechtigung hat, verweigert das Betriebssystem den Zugriff ohne Ausnahme, ohne Diskussion. Das klingt
  236. simpel und konzeptuell ist es das auch, aber es ist einer der wirksamsten Mechanismen gegen Angriffe. Das zugrunde liegende Prinzip heißt Least Privilege.
  237. Gib jedem Nutzer, Programm, Dienst nur die Rechte, die er wirklich braucht. Nicht mehr. Wenn ein Programm kompromettiert wird, kann der Angreifer
  238. nur das, was das Programm darf. Ein Webserver, der z.B. von einem Angreifer übernommen wurde, der nur Dateien in einem bestimmten Ordner lesen darf, kann
  239. nicht das gesamte System übernehmen, selbst wenn er gehackt wird. Lease Privilege ist also kein Feature. Es ist eine Philosophie und sie zieht sich
  240. durch das gesamte Design moderner Betriebssysteme. Jetzt möchte ich noch mal ganz kurz über Netzwerke sprechen, wobei ich dazu ein dediziertes Video
  241. machen werde. Also es wird eine eigene Sektion sein. Hier gehen wir erstmal auf Programme und Anwendung und dann wird danach eine Internetsektion kommen. Aber
  242. hier sprechen wir mal ganz kurz darüber. Wenn eine App Daten senden will, ruft sie einen Sys Call auf. Sie übergibt Daten und eine Zieladresse. Mehr muss
  243. sie nicht wissen. Den Rest übernimmt das Betriebssystem. Das Betriebssystem verpackt die Daten in TCP Segmente, verpackt diese in IP und gibt sie an den
  244. Netzwerktreiber weiter und der schickt sie raus auf die Leitung. Macht euch hier bitte keine Sorgen, wenn ihr jetzt TCP, IP und so weiter alles noch nicht
  245. verstanden habt. Dazu kommen wir noch. Ich will einfach nur, dass ihr es schon mal gehört habt. Auch hier gibt es eine Abstraktion, die das für Programme
  246. sichtbar macht. Die heißt Socket. Wir haben vorhin schon darüber gesprochen. Das ist wieder dasselbe Muster. Komplexität nach unten verstecken und
  247. oben eine saubere Schnittstelle lassen. Eine App muss also nicht wissen, wie ein IP-Paket aussieht. Sie muss nur wissen, wohin sie sie senden will. Das
  248. Betriebssystem ist der unsichtbare Netzwerkvermittler für jeden Prozess auf dem System. Aber wie gesagt, Netzwerke werden wir in einem separaten Video
  249. deutlich genauer betrachten. Also gehen wir einfach mal weiter. Das Betriebssystem verwaltet auch noch Zeit. Das klingt erstmal trivial, ist es aber
  250. nicht. Ohne Zeitkontrolle kein Scheduling und ohne Scheduling kein Multitasking. Und ohne einen zuverlässigen Taktgeber gibt es keine
  251. Zeitkontrolle. Hardwareetimer im System generieren in regelmäßigen Abständen Interrupts, ein Signal an die CPU, dass die Zeit vergangen ist. Bei jedem dieser
  252. Interrupts hat das Betriebssystem die Möglichkeit einzugreifen, den laufenden Prozess zu unterbrechen, den nächsten zu starten und die Systemuhr zu
  253. aktualisieren. Ohne diesen Timer Interrupt könnte ein Prozess, der in einer Endlosschleife gerät, die CPU für immer festhalten. Mit ihm hat das
  254. Betriebssystem immer die Möglichkeit, das Steuer zurückzunehmen, egal was der laufende Prozess tut. Zusätzlich synchronisiert das Betriebssystem die
  255. Systemzeit über NTP, das Network Time Protocol, also mit weltweiten Zeitservern. So wissen alle Prozesse auf allen Systemen, was die Uhr geschlagen
  256. hat. Zeit ist im Betriebssystem also keine Nebensache. Sie ist das Fundament, auf dem Scheduling, Logging, Sicherheitszertifikate und verteilte
  257. Systeme aufbauen. Wir haben ja vorhin darüber gesprochen, dass z.B. Prozesse, die eine Eingabe erwarten, eine höhere Priorität bekommen. Aber woher weiß das
  258. Betriebssystem eigentlich, wann du eine Taste drückst oder wann ein Netzwerkpaket ankommt oder wann die Festplatte einen Lesevorgang
  259. abgeschlossen hat? Es könnte permanent nachfragen, also in einer endlosschleife einfach fragen. Wurde eine Taste gedrückt? Nein. Wurde eine Taste
  260. gedrückt? Nein. Wurde eine Taste gedrückt? Nein. Das nennt man Polling. Und es ist so ineffizient, wie es klingt. Die CPU wäre damit vollständig
  261. beschäftigt, auf Ereignisse zu warten, statt Arbeit zu erledigen. Stattdessen gibt es Interrupts. Die Hardware sendet ein Signal direkt an die CPU, ein
  262. Interrupt Request, kurz IRQ. Die CPU unterbricht sofort, was sie gerade tut, sichert ihren aktuellen Zustand und springt zu einem sogenannten Interrupt
  263. Handler, einem kleinen Stück Code im Kernel, der genau für diesen Interrupt vorbereitet ist. Der Händler läuft, Ereignis wird verarbeitet und der
  264. Zustand wird wiederhergestellt. Die CPU macht weiter als wäre nichts gewesen. Das Betriebssystem wartet also nicht aktiv auf Hardware. Es lebt sein Leben
  265. und wenn die Hardware etwas zu sagen hat, unterbricht sie es sofort gezielt und effizient. Dieser Mechanismus, also CPU unterbricht sich, sicher Zustand und
  266. springt woanders hin, steckt übrigens auch hinter etwas, das wir schon besprochen haben und zwar dem Kontextwechsel. Der Kontextwechsel ist
  267. das, was Multitasking erst möglich macht und er ist eleganter als er klingt. Wenn das Scheduling entscheidet, Prozess A hat seine Zeitscheibe aufgebraucht,
  268. jetzt ist Prozess B, dann da muss die CPU den Zustand von A vollständig sichern. Also alle Register, den Programmcounter, der zeigt, wo wir im
  269. Code gerade waren, den Stackpointer, die Flags und so weiter, alles landet im Speicher. Dann lädt die CPU den gesicherten Zustand von B und läuft
  270. weiter, als hätte B nie pausiert. Das passiert hunderte Male pro Sekunde. Du merkst davon überhaupt nichts. In Wirklichkeit ist es also extrem
  271. schnelles Abwechseln. Kein Prozess läuft wirklich gleichzeitig mit einem anderen auf einem einzelnen Kern. Echte Parallelität gibt es nur mit mehreren
  272. CPU-Kern. Dann laufen tatsächlich mehrere Prozesse zur gleichen Zeit und zwar einer pro Kern. Alles andere ist eine sehr überzeugende Illusion. Wir
  273. haben also jetzt das Fundament verstanden, also wie ein Betriebssystem intern funktioniert. Lass uns also jetzt mal einen Blick nach außen werfen.
  274. Welche Betriebssysteme gibt es und warum sind sie so verschieden? Und dabei fokussiere ich mich jetzt erstmal nur auf Linux und Windows. Linux ist ein
  275. Betriebssystem Kernel, aber es ist mehr als das. Es ist ein Experiment, das bewiesen hat, dass offene Zusammenarbeit funktioniert. Ich habe schon ein
  276. separates Video zu Linux gemacht. Schaut euch das gerne an, wenn ihr wollt. Der Quellcode ist hier öffentlich. Jeder kann ihn lesen, verändern,
  277. weiterverteilen. Aus diesem offenen Kern ist ein Ökosystem von hunderten sogenannten Distributionen entstanden. Also Ubunto, Debian, Fedora, Arch Linux.
  278. Sie alle basieren auf demselben Linux Kernel, unterscheiden sich aber in allem Drumherum, also Paketverwaltung, Desktopumgebung und Zielgruppe. Ubunto
  279. z.B. für Einsteiger, Arsch für alle, die alles selber kontrollieren wollen, Debian für Stabilität und so weiter. Auf dem Desktop ist Linux eine Minderheit.
  280. Auf Servern dominiert es. Fast die gesamte Cloud Infrastruktur weltweit läuft auf Linux. Von Amazon über Google bis zu den Systemen hinter den meisten
  281. Apps auf deinem Telefon. Der Grund ist simpel. Linux ist extrem modular. Du kannst einen minimalen Kernel bauen, der nur das Nötigste macht. Kein grafisches
  282. Interface, keine unnötigen Dienste und maximale Effizienz. Perfekt für Server, die rund um die Uhr laufen und nie abgelenkt werden wollen. Der Kernel
  283. selbst ist monolitisch, aber dazu kommen wir gleich. Lass uns noch kurz über Windows sprechen. Windows ist im Grunde das Gegenteil von Linux in fast jeder
  284. Hinsicht. Es ist close source, kommerziell und ein Unternehmen entscheidet, was im Kernel landet und was nicht. Kein öffentlicher Code, kein
  285. externer Beitrag, dafür ein klares Ziel. Es muss auf allem laufen. Das ist der Kern von Windows, also Kompatibilität. Windows läuft auf Hardware von hunderten
  286. Herstellern in Unternehmensumgebungen, die seit Jahrzehnten gewachsen sind mit Software, die manchmal älter ist als manche ihrer Nutzer. Jede neue Windows
  287. Version muss alte Programme noch ausführen können. Code, der vor 20 Jahren geschrieben wurde, soll heute noch funktionieren. Das hat aber seinen
  288. Preis. Jahre von Legacy Code, der nie entfernt werden kann, weil irgendwo noch irgendjemand davon abhängt. Der Kernel von Windows ist Windows NT. Er existiert
  289. in dieser Form seit den frühen 90ern. Er ist gewachsen, erweitert, angepasst worden, aber das Fundament ist dasselbe. Aber warum gibt es überhaupt
  290. unterschiedliche Betriebssysteme? Na ja, weil es unterschiedliche Probleme und unterschiedliche Ziele gibt. Das klingt offensichtlich, aber steckt mehr
  291. dahinter, als man zunächst denkt. Ein Betriebssystem ist kein neutrales Werkzeug. Jede Designentscheidung ist ein Tradeoff. Was du gewinnst, gibst du
  292. irgendwo anders auf. Ein Desktop Betriebssystem optimiert z.B. für den Menschen am Bildschirm, also Benutzeroberfläche,
  293. Reaktionsgeschwindigkeit, breite Hardwarekompatibilität, ein riesiges Softwareökosystem und so weiter. Der Nutzer soll nie warten, nie verwirrt
  294. sein, nie etwas installieren müssen, das nicht sofort funktioniert. Wie gut das bei Windows funktioniert, lasse ich jetzt mal im Raum. Ein Server optimiert
  295. für Maschinen, die mit Maschinen reden, also keine grafische Oberfläche nötig. Dafür maximale Stabilität, Netzwerkleistung und die Fähigkeit,
  296. tausende gleichzeitige Verbindungen zu verwalten. Der Server soll jahrelang laufen ohne Neustart. Dann gibt es noch Embedded OS für Router, Kameras,
  297. Industrieanlagen und Co. Security Betriebssysteme, die optimiert sind für Vertrauen, minimale Angriffsfläche und so weiter. Also im Kern unterschiedliche
  298. Ziele, unterschiedliche Probleme, unterschiedliche Betriebssysteme. Ich möchte nur noch ganz kurz über Kernel Architekturen sprechen. Wir haben Linux
  299. und Windows angesprochen, aber wir haben noch nicht geklärt, warum sie intern so anders gebaut sind. Das liegt an einer grundlegende Frage im
  300. Betriebssystemesign. Was gehört in den Kernel und was nicht? Es gibt drei Antworten darauf. Einmal den monolitischen Kernel wie bei Linux.
  301. Alles läuft im Grunde im Kernel Mode, also Treiber, Dateisystem, Netzwerkstack und so weiter. Ein großer zusammenhängender Block mit vollen
  302. Rechten. Der Vorteil ist Performance, also direkte Aufrufe, keine teuren Mode Switches zwischen Komponenten und maximale Geschwindigkeit. Der Nachteil
  303. ist Risiko. Ein Bug in einem Treiber, der im Kernel Mode läuft, kann das gesamte System zum Absturz bringen. Du kennst das vielleicht, der Kernel Panic
  304. auf Linux. Dann gibt es noch den Micro Kernel. Der Kernel macht nur das absolute Minimum: Prozessverwaltung, Speicherverwaltung und grundlegende
  305. Kommunikation. Alles andere Treiber, Dateisystem, Netzwerk läuft im User Mode, also normale Prozesse. Der Vorteil: Ein fehlerhafter Treiber stürzt
  306. nur sich selbst ab. Das System läuft weiter. Der Nachteil: Jede Kommunikation zwischen Komponenten kostet einen Mode Switch. Das summiert sich und macht
  307. Micro Kernels in der Praxis langsamer. Und zu guter Letzt gibt es hybride Kernel wie Windows NT und MacOS. Ein pragmatischer Kompromiss. Kernfunktionen
  308. laufen im Kernel Mode für Performance und weniger kritische Teile laufen im User Mode für Sicherheit. kein reines Ideal, aber in der Praxis sehr
  309. erfolgreich. Wenn du dich fragst, woher der Bluescreen of Death kommt, genau hier. Windows NT ist Hybrid, aber Treiber laufen teilweise trotzdem im
  310. Kernel Mode. Ein Fehlerhafter Grafiktreiber reicht und das System ist weg. Drei Philosophien, drei Tradeoffs und keine ist falsch. Zum Abschluss ein
  311. Blick auf etwas, dass wir in diesem Video und in den vorherigen Videos die ganze Zeit implizit genutzt haben, ohne es direkt anzusprechen. Wir haben von
  312. RAM gesprochen, von Festplatten, von Pages, die rein und rausgeschoben werden, aber wir haben nie gefragt, warum gibt es überhaupt verschiedene
  313. Arten von Speicher? Warum nicht einfach einen, der schnell, groß und günstig ist? Die Antwort: Na ja, weil es physikalisch nicht möglich ist. Schnelle
  314. Speicher sind teuer und klein. Großer Speicher hingegen ist langsam und günstig. Das ist kein Designfehler, das ist ein Naturgesetz der
  315. Halbleitertechnik. Die Lösung ist eine Hierarchie. Ganz oben haben wir Register, die sind direkt in der CPU. Das sind wenige Dutzend Bites, die
  316. Zugriffszeiten in Nanosekunden ermöglichen. Und hier rechnet die CPU tatsächlich. Darunter haben wir den Cash aufgeteilt in L1, L2 und L3. Das sind
  317. Kilby bis Megabyes. Die sind nahezu so schnell wie Register. Die CPU hält hier die Daten, die sie gerade oder demnächst braucht. Darunter haben wir den RAM, das
  318. ist schon Gigabyte Bereich, also deutlich langsamer als der Cash, aber immer noch schnell genug für laufende Programme. Alles, was aktiv genutzt
  319. wird, soll hier liegen. Ganz unten haben wir Discs, also SSDs, Festplatten und so weiter. Das sind hunderte Gigabytes bis Terabtes. Hier haben wir Millisekunden
  320. statt Nanosekunden, ein Faktor von 1000 oder mehr. Hier liegt also alles, was dauerhaft gespeichert werden muss, aber die Performance ist sehr, sehr langsam.
  321. Das Betriebssystem verwaltet diese Hierarchie ständig, ohne dass irgendjemand es bemerkt. Wie vorhin besprochen, wir haben heute eine weitere
  322. riesige Schicht aufgedeckt und zwar Betriebssysteme. Von der Frage, warum es überhaupt ein Betriebssystem braucht bis zu den Architekturen, die hinter Linux
  323. und Windows stecken. Bootprozess, Kernel, Prozesse, Threats, Synchronisierung, Scheduling, virtueller Speicher und und alles hängt zusammen
  324. und alles baut aufeinander auf. Das Betriebssystem ist die unsichtbare Grundlage von allem, was du am Computer tust. Na ja, ganz ganz so unsichtbar ist
  325. sie nicht, aber jeder Klick, jede Datei, jede Verbindung läuft im Grunde durch die Schichten, die wir heute besprochen haben. Du siehst es nicht immer, aber
  326. jetzt weißt du, dass es da ist. Und jetzt, wie besprochen die zwei Fragen aus dem letzten Video? Wenn Maschinecode direkt auf die CPU wirkt, warum hat dann
  327. jedes Betriebssystem seine eigene ausführbare Datei, also Windows und Linux 11? Müsste man die nicht einfach austauschen können? Im Grunde hast du
  328. recht, aber nur zur Hälfte. Ich habe es eben gerade in diesem Video erst erklärt. Der Maschinencode selbst ist tatsächlich austauschbar, solange die
  329. CPU Architektur stimmt. Ein X6 Befehl ist ein X86 Befehl, egal ob er in einer Echse oder in einem 11 steckt. Aber eine ausführbare Datei ist mehr als
  330. Maschinencode. Sie ist ein Container mit einem Format und einer Struktur, die dem Betriebssystem sagt, wo fängt der Code an, wo liegen die Daten und welche
  331. Bibliotheken brauchst du. Windows kennt z.B. für das Excel Dateienformat Linux nur 11. Nicht weil der Code inkompatibel wäre, sondern weil der Loader des
  332. jeweiligen Betriebssystems nur sein eigenes Format besteht. Dazu kommt Programme rufen z.B. Betriebssystemfunktion auf, eine Windows
  333. App ruft z.B. Create File auf, eine Linux App ruft dagegen Open auf. Das sind verschiedene SIS Calls und verschiedene Bibliotheken und somit
  334. verschiedene Konventionen. Du könntest also den reinen Maschinencode nehmen, aber alles drumherum würde nicht passen. Genau das macht Tools wie z.B. Wine.
  335. Interessant. Die emulieren nicht die CPU, die emulieren das Windows Drumherum, den Loader, die SISCS und die Bibliotheken. Frage 2: Wir haben gesagt,
  336. alles sind nur Transistoren, die verschachtelt sind, aber welcher Transistor gibt das erste Signal ab? Irgendwo muss das doch alles anfangen.
  337. Im Grunde musst du es hier so vorstellen, die Schaltkreise sind physisch so design, dass beim Anlegen von Spannung bestimmte Transistoren
  338. sofort einen definierten Zustand einnehmen, bevor irgendeine Software auch nur eine Zeile ausführt. Das heißt, per Design, wenn Spannung durchfließt,
  339. gehen die in bestimmte Zustände. Das ist also kein Code, das ist Schaltungsdesign, also Hardware Logik, die beim ersten Stromfluss automatisch
  340. die richtige Konstellation erzeugt. Das Ergebnis ist, die CPU zeigt mit ihrem Instruction Pointer, also die Instruktion, die als nächstes ausgeführt
  341. werden soll, zwangsläufig auf den Resetvektor. Nicht weil jemand es ihm sagt, sondern weil die Schaltung gar nichts anderes zulässt. Der Resetvektor
  342. ist dann wiederum nur eine Adresse auf X86, wä diese hier und dort liegt typischerweise einzelner Jumpbefehl, der auf den eigentlichen Firmware Code
  343. weiter verweist und dann passiert das hier, was ich hier schon beschrieben habe. Also das Ganze ist kein Zufall, sondern nur Physik und Design. Und damit
  344. endet dieses Video hier. Wenn ihr bezüglich Betriebssysteme Fragen habt, dann einfach rein in die Kommentare und ich bin auch mega auf euer Feedback
  345. gespannt.

Zum Nachlesen