OS-Internals #2: Ext2 und Dateien in Linux

Facebooktwittergoogle_plusredditpinterestlinkedinmail
In Linux ist alles eine Datei, selbst Ordner und Geräte.

In Linux ist alles eine Datei, selbst Ordner und Geräte.

In Linux gibt es bezüglich Dingen wie Dateien, Ordnern, Geräten, Schnittstellen und Verknüpfungen eine schöne Regel: „On a UNIX system, everything is a file; if something is not a file, it is a process.“. Bei Linux ist also alles eine Datei (ja, auch Ordner sind Dateien), darum sollten wir mal einen genaueren Blick darauf werfen.

Dateisystem: ext2 und inodes

Da man Dateien nicht einfach hintereinander weg speichern kann (da sich z.B. die Größe ändern kann), greifen UNIX-Systeme meist auf das Konzept der inode (index node) zurück. Um zu verstehen, was eine inode ist, sollte man sich aber anschauen, wie z.B. das ext2 Dateisystem (welches inodes benutzt und auf dem viele weitere Dateisysteme basieren) funktioniert.

Zunächst zur Hardware: Ein Block ist eine Menge von Sektoren einer Festplatte, wobei ein Sektor die kleinste zu adressierende Einheit einer Festplatte ist. Ein Block ist normalerweise 1, 2, 4 oder 8 KiB groß (also ggf. ein Zusammenschluss von Sektoren), was bei der Formatierung der Festplatte angegeben wird. Fasst man mehrere Blöcke zusammen ist es eine block group.

Kommen wir jetzt zur inode, was im Prinzip nichts weiter als eine block group ist. Sie ist 128 bytes groß und enthält Metadaten und Referenzen auf weitere Blöcke.
Jede Datei ist eine Referenz auf genau eine inode, wobei die eigentlichen Daten eben in anderen inodes liegen und referenziert werden. Es gibt 12 direkte Referenzen und 3 weitere Referenzen, die jeweils auf cluster zeigen. Ein cluster enthält 256 Referenzen auf weitere cluster oder inodes. Dadurch kann eine Datei bis zu 2 TiB groß werden.

Ein Ordner ist eine spezielle Datei (s.u.), sprich eine inode, in der einfach eine Liste von sog. directory entries enthalten ist. Der erste Eintrag eines Ordners zeigt auf . (sprich auf sich selbst), der zweite auf .. (sprich auf den übergeordneten Ordner) und alle weiteren zeigen auf weitere inodes.

Inodes können inodex referenzieren.

Eine inode besitzt mehrere Verweise auf weitere inodes. Durch werden große Dateien repräsentiert.

Funfact

Eine inode enthält nicht den eigenen Namen (z.B. den Dateinamen), dieser steht in dem directory entry (s.o.) der Ordner, die auf diese inode referenzieren. Das ist auch der Grund, warum das root directory nur ein slash ist (also nur /... ) und nicht z.B. root/..., da es kein parent directory mit passendem Eintrag für den Namen gibt.

Dateitypen

Da in ext2 also alles aus inodes besteht, muss dort zwischen verschiedenen inode file types unterschieden werden. Nun basiert Linux auf ext2 und somit wird dort eine ganz ähnliche Unterscheidung vorgenommen. Jede Datei in Linux ist zudem mit Rechten verbunden.

Man kann mittels des Befehls ls -l <pfad> die wichtigsten Infos (z.B. Rechte, Besitzer, Größe oder Änderungsdatum) ablesen. Das erste Zeichen in der Zeile zeigt zudem an um welche Art von Datei es sich handelt (z.B. -rw-rw-rw-... ist eine normale Datei und lrwxr-xr-x... ein link).

Es gibt eine Fülle von verschiedenen Dateitypen (s. gnulib/lib/filemode.c), hier erstmal die einzelnen Dateitypen in Linux (mit Kürzel in Klammern):

Regular file (-)

Eine normale Datei ist – wie oben beschrieben – eine inode mit eventuell mehreren Verweisen auf weitere inodes.

Special file

Alles, was keine normale Datei ist, ist eine spezielle Datei (special file). Dies ist eher eine Kategorie von Dateien, als ein eigener Typ. Oftmals wird aber der Begriff special file für ein block special file oder character special file gemeint, was eigentlich Geräte sind (z.B. Festplatten). Doch dazu später mehr.

Directory (d)

Ein Ordner ist – wie ebenfalls oben beschrieben – eine inode mit mehreren Einträgen auf weitere inodes. In jedem Ordner sind zudem grundsätzlich . (aktueller Ordner) und .. (übergeordneter Ordner) enthalten.

Symbolischer Link (l)

Ein symbolischer Link (symbolic link, symlink oder auch soft link) verweist auf eine andere inode. Dadurch kann man (auch über Partitionen hinaus) Verweise erstellen um z.B. Dateien auszulagern oder Redundanz zu vermeiden.

Ein symlink ist tief im Dateisystem verankert, sodass Programme den Pfad zu einem symlink nicht von dem Zielpfad unterscheiden können.

Socket (s)

Ein socket ist eine spezielle Datei, mit der zwei Prozesse kommunizieren können. Er ist nicht mit einem TCP/IP Socket zu verwechseln, hat aber eine ähnliche Funktion.

Prozesse können über einen socket Daten, aber auch file descriptors (Verweise auf andere Dateien) austauschen.

Named pipe (p)

Eine pipe (auch manchmal als fifo bezeichnet) ist – genau wie ein socket – eine spezielle Datei zur Interprozesskommunikation. Sie besitzen jedoch die Einschränkung, dass sich ein Prozess als Sender und ein Prozess als Empfänger anmelden muss. Es ist also keine Duplex-Kommunikation wie bei einem socket möglich.

Hier ein Beispiel:

Einfach zwei Terminalfenster öffnen. Im ersten wird eine pipe erstellt:

mkfifo testFifo

Das zweite Fenster fängt an zu empfangen:

cat testFifo

Im ersten kann man nun Daten senden:

echo Hallo Welt! > testFifo

Diese kommen dann im zweiten Fenster an.

Character device (c)

Die einfachste – im Sinne von „am nächsten zur Hardware dran“ – ist das Benutzen eines character device, welches das lesen und schreiben von Zeichen (also bytes) erlaubt. Es gibt jedoch oftmals gerätespezifische Einschränkungen, wie etwa bei Festplatten (HDDs): Dort ist es Hardware bedingt nur möglich gewisse Mengen an Daten auf einmal zu lesen (Stichwort Sektoren einer Festplatte).

Block device (b)

Anders als das zeichenweise lesen von einem character device, gibt es auch das block device, welches beliebige Größen an Daten verarbeiten kann und zudem einen Buffer besitzt. Dadurch entsteht eine gewisse Abstraktion zur Hardware, was Vorteile, aber auch Nachteile für den Programmierer mit sich bringt: Durch den Buffer weiß man nicht wann genau eine Dateneinheit auf das Gerät geschrieben wurde.

Pseudo-device

Einige Geräte in Linux besitzen keine physikalische Komponente, sondern sind reine Software-Geräte. Diese werden daher oftmals pseudo-device genannt. Unter diesen Geräten befinden sich vor allem folgende:

  • /dev/null : Hierzu gab es bereits einen eigenen Artikel. Das null device schluckt jegliche Eingabe, beim lesen bekommt man aber nur ein end-of-file (EOF) Zeichen
  • /dev/random : Es gibt auch /dev/urandom. Wichtig ist hier, dass beide Geräte einen stream von pseudozufälligen Nummern generieren
  • /dev/zero : Erzeugt einen stream von NUL-Werten (sprich null-bytes)
  • /dev/loop : Ermöglicht weitere Abstraktionen von Dateien. Man bindet eine Datei an /dev/loopn (wobei n eine Zahl ist) und kann so z.B. eine Datei als eigenes Dateisystem interpretieren

Fazit

Wie man unschwer erkennt, kennt Linux tatsächlich nur Dateien. Einige davon sind jedoch besonders und bieten sehr spezielle Funktionalitäten, wie z.B. pipes oder device files. Normale Dateien und Ordner werden im Kernel (zumindest bei ext-Dateisystemen) als inode repräsentiert, wobei alle anderen spezielle Dateien beliebige Formen annehmen können.

Facebooktwittergoogle_plusredditpinterestlinkedinmail

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht.