Beschreibung: Prüfungskandidaten sollten ausreichend vertraut mit dem Filesystem Hierarchy Standard, einschließlich typischer Speicherort von Dateien und der Einteilung der Verzeichnisse, sein. Dieses Lernziel beinhaltet das Auffinden von Dateien und Kommandos auf einem Linux-System.
Die wichtigsten Dateien, Bezeichnungen und Anwendungen:
Die Standard-Hierarchie der Unix-Dateisysteme war und ist schon immer einer der großen Vorteile gegenüber anderen Systemen gewesen. Hat man einmal ein Unix-System egal welcher Art kennengelernt, so findet man sich nahezu auf jedem anderen Unix-System mühelos zurecht. Linux bietet einen solchen Standard genauso an und es gibt weltweite Bestrebungen, die Positionen der Dateien und Verzeichnisse innerhalb des Dateisystems, sowie deren Namen festzulegen. Trotzdem finden sich immer Unterschiede zwischen verschiedenen Unixen und selbst zwischen verschiedenen Linux-Distributionen. Um mit diesen Unterschieden umgehen zu können finden sich verschiedene Werkzeuge, die hier näher besprochen werden sollen.
Die wesentlichen Aufgaben dieses Standards sind die Festlegungen, welche Dateien in welche Verzeichnisse gehören und zwar dergestalt, daß es möglich ist, bestimmte Verzeichnisse mit statischen Daten als ReadOnly-Dateisystem einzuhängen, um eine größtmögliche Stabilität des Systems zu gewährleisten.
Im folgenden sollen die wesentlichen Verzeichnisse kurz beschrieben werden, um ihre Aufgaben bzw. die Philosophie, die hinter ihnen steckt zu klären:
Weil dieses Wurzeldateisystem selbst sehr viele systemspezifische Dateien enthält, ist es nicht geeignet, über ein Netz von mehreren Rechnern verwendet zu werden.
Viele der Unterverzeichnisse dieses Dateisystems sind nur Mountpoints, um andere Partitionen dort einzuhängen. Einige Verzeichnisse sollten aber unter keinen Umständen auf anderen Plattenpartitionen liegen, da sie sonst nicht zur Verfügung stehen, wenn während des Bootvorgangs bisher nur das Wurzelverzeichnis gemountet ist. Ein simples Beispiel ist das Programm mount selbst. Dieses Programm muß natürlich irgendwo auf der Partition liegen, die das Wurzelverzeichnis enthält, sonst steht es in dem Moment nicht zur Verfügung, wo andere Platten eingehängt werden sollen!
In der folgenden Darstellung wird immer auch beschrieben, ob ein Verzeichnis geeignet ist, auf eine andere Partition ausgelagert zu werden, oder ob es zwingend auf der Wurzelpartition sein muß.
Ein weiterer Gesichtspunkt ist die Frage, ob ein Verzeichnis statische oder dynamische Dateien enthält. Wenn in einem Verzeichnis ausschließlich statische Dateien liegen - also Dateien, die im laufenden Betrieb nicht verändert werden müssen - so bietet es sich an, dieses Verzeichnis ReadOnly zu mounten. Das Wurzeldateisystem enthält zwingend sowohl statische, als auch dynamische Dateien, muß also ReadWrite gemountet sein.
Dieses Verzeichnis enthält zumeist statische Daten, kann also im normalen Betriebsablauf ReadOnly gemountet werden. Es enthält keine rechnerspezifischen Daten, ist also auch geeignet, um gemeinsam im Netz genutzt zu werden.
Außerdem besitzt hier jeder laufende Prozess ein Unterverzeichnis, das den Namen der PID trägt und prozess-spezifische Informationen bereitstellt.
Bei älteren Unix-Systemen hatte der Systemverwalter kein Home-Verzeichnis, sondern die Wurzel des Systems (root) diente ihm als solches. Das führte aber dazu, daß auf der Wurzel dann einige Dateien lagen, die den Überblick über die Konsistenz des Systems erschwerten. Aus diesem Grund wurde dieses Verzeichnis eingeführt.
Damit auch ältere Programme, die noch immer ins /usr-Verzeichnis schreiben wollen, nicht abstürzen, existieren heute zumeist die folgenden symbolischen Links im /usr-Verzeichnis, die ins /var-Verzeichnis verweisen:
Es ist durchaus möglich, dieses Verzeichnis auf eine eigene Partition zu legen und auch der zumindest teilweisen gemeinsamen Nutzung im Netz steht nichts im Weg. Allerdings enthält das /var-Verzeichnis einige Rechnerspezifische Daten, die im Netz nicht umbedingt geteilt werden sollten (etwa /var/lock - die Lockfiles oder /var/run - die ProzessIDs verschiedener Programme).
Bei dieser Frage müssen wir zwischen Programmen und Dateien unterscheiden. Ein Programm ist eine ausführbare Datei, im folgenden wird der Begriff aber etwas genauer definiert. Linux enthält, wie oben gesehen, einige Verzeichnisse, die für die Aufnahme von Programmen (Binärdateien und Scripts) vorgesehen sind. Zumeist enden diese Verzeichnisse mit den Buchstaben bin. Damit einzelne Programme von überall her aufrufbar sind, ohne jeweils ihren ganzen Pfad eingeben zu müssen, existiert ein sogenannter Programmsuchpfad. Das ist eine Liste all der Verzeichnisse, die von der Shell durchsucht werden, wenn ein Programmaufruf eingegeben wurde. Diese Liste ist in einer Umgebungsvariable namens PATH gespeichert. Ein Normaluser hat hier meist andere Einstellungen als der Systemverwalter, der in seinem Pfad noch die verschiedenen sbin-Einträge hat.
Um herauszufinden, welche Verzeichnisse im Suchpfad stehen reicht der Aufruf von
echo $PATHEine typische Ausgabe für den Systemverwalter wäre z.B
/sbin:/usr/sbin:/usr/local/sbin:/root/bin:/usr/local/bin:/usr/bin:/usr/X11R6/bin: /bin:/usr/games/bin:/usr/games:/opt/gnome/bin:/opt/kde/bin:.Ein Normaluser würde aber eher etwas in der Art vorfinden:
/usr/local/bin:/usr/bin:/usr/X11R6/bin:/bin:/usr/games/bin:/usr/games: /opt/gnome/bin:/opt/kde/bin:.Wenn wir jetzt Programme suchen, so existieren Tools, die nur diesen Suchpfad durchforsten und uns sagen, welche Programme von wo aus aufgerufen werden. Suchen wir hingegen Dateien, so sind wir gezwungen, den gesammten Bestand an Verzeichnissen zu durchsuchen, was natürlich erheblich mehr Arbeit ist und länger dauert.
Für die Programme ist noch anzumerken, daß die Shell, wenn sie einen Programmaufruf ausführt, den Suchpfad von vorne nach hinten (von links nach rechts) durchsucht und das erste gefundene Programm mit dem passenden Namen ausführt. Das kann zu Konflikten führen, wenn wir z.B. zwei Programme gleichen Namens auf dem System haben, das eine in /bin und das andere in /usr/bin. Nachdem /usr/bin im Suchpfad vor /bin steht wird immer das Programm in /usr/bin aufgerufen.
Das Programm which wird zusammen mit einem oder mehreren Programmnamen aufgerufen und gibt uns dann den vollen Pfad des gefundenen Programms zurück. which arbeitet exakt wie die Shell, durchsucht eben den Suchpfad (PATH) und gibt das erste Kommando mit passendem Namen samt Pfad zurück. Der Aufruf von which mount hätte also die folgende Ausgabe gebracht:
/bin/mount
Das Programm type ist eigentlich gar kein Programm sondern eine interne Funktion der Shell (bash). Es zeigt etwas mehr Information als which, weil auch die hash-Mechanismen der Shell berücksichtigt werden und angezeigt wird, ob das gewünschte Kommando eine Shellfunktion, ein Alias, ein interner Shell-Befehl oder ein Programm ist.
Auf vielen Systemen ist tatsächlich etwa das Programm which nur ein Alias auf type -p.
Die Ausgabe von type mount würde folgendermaßen aussehen:
mount is /bin/mountDas Programm whereis ist schließlich neben dem Auffinden von Programmdateien auch in der Lage, die zugehörigen Handbuchseiten und den Quellcode (falls installiert) von Programmen zu lokalisieren.
find bietet aber neben der Fähigkeit Dateien zu suchen auch noch an, beliebige Aktionen mit den gefundenen Dateien auszuführen. Aus diesem Grund ist dieses Programm ein unentbehrliches Hilfsmittel für den Systemvewalter.
Die genauen Parameter, Tests und Aktionen von find sind auf der Handbuchseite aufgelistet, hier soll noch einmal in Beispielen erklärt werden, wie find aufgerufen wird und wie man damit vernünftig arbeiten kann.
Die einfache Aufrufform von find ist
find Startverzeichnis Test Aktion
Dabei sucht find alle Verzeichnisse ab Startverzeichnis nach den Dateien ab, für die die Kriterien Test zutreffen. Für jede gefundene Datei wird dann die Aktion durchgeführt. Wenn die Aktion weggelassen wird, so wird standardmäßig die Aktion -print ausgeführt, d.h. der Dateiname der gefundenen Datei wird zusammen mit seinem Suchpfad (relativ zum angegebenenen Startverzeichnis) ausgegeben.
Um Dateien anhand ihres Namens zu finden, wird der Test -name Muster benutzt. Wenn der Name nicht vollständig bekannt ist, oder nach verschiedenen Dateien mit bestimmten Namen gesucht werden soll, dann kann das Suchmuster auch die Jokerzeichen verwenden, die auch die Shell benutzt (*,?,[...]). Aber Vorsicht: Das Namensmuster muß dann in Anführungszeichen gesetzt werden, weil sonst die Shell die Jokerzeichen interpretieren und durch evt. gefundene Dateien im aktuellen Verzeichnis ersetzen würde.
Um also z.B. alle Dateien des gesamten Systems zu finden, deren Namen mit einem großen oder kleinen M beginnt schreiben wir:
find / -name "[mM]*"Der Slash steht für das Startverzeichnis, hier also das Wurzelverzeichnis. -name leitet den Namenstest ein und "[mM]*" ist das Suchmuster. Die Aktion haben wir hier einfach weggelassen, es wird also die -print Aktion durchgeführt. Das Ergebnis sieht dann etwa so aus:
/usr/X11R6/bin/macptopbm /usr/X11R6/bin/mgrtopbm /usr/X11R6/bin/mtvtoppm /usr/X11R6/bin/makedepend /usr/X11R6/bin/makeg /usr/X11R6/bin/mergelib /usr/X11R6/bin/mkdirhier /usr/X11R6/bin/mkfontdir /usr/X11R6/bin/mksusewmrc /usr/X11R6/bin/manix /usr/X11R6/bin/mirrormagic /usr/X11R6/bin/mogrify /usr/X11R6/bin/montage /usr/X11R6/bin/mtv /usr/X11R6/bin/mtvp /usr/X11R6/bin/mpeg_play /usr/X11R6/include/GL/MesaDrawingArea.h /usr/X11R6/include/GL/MesaDrawingAreaP.h /usr/X11R6/include/GL/MesaMDrawingArea.h /usr/X11R6/include/GL/MesaMDrawingAreaP.h /usr/X11R6/include/GL/MesaWorkstation.h /usr/X11R6/include/GL/MesaWorkstationP.h /usr/X11R6/include/X11/Xaw3d/MenuButtoP.h ...Wenn mit Tests gearbeitet wird, die nummerische Parameter haben, dann gibt es eine Besonderheit. Wird die Zahl einfach, ohne Vorzeichen angegeben, dann heißt das, daß genau diese Zahl gemeint ist. Hat die Zahl als Vorzeichen ein Pluszeichen (+), dann heißt das, daß die Zahl oder eine größere Zahl gemeint ist, ein Minuszeichen bedeutet entsprechend die Zahl oder eine kleinere.
Der Test -size sucht Dateien nach ihrer Größe. Schreiben wir also
find . -size 12kso sucht find nach allen Dateien im aktuellen Verzeichnis (.), die genau 12 Kilobyte groß sind. Wenn wir alle Dateien suchen, die höchstens 12 Kilobyte groß sind, so schreiben wir
find . -size -12kund Dateien, die mindestens 12 Kilobyte groß sind finden wir mit
find . -size +12kWenn wir mehrere Tests angeben, so werden die Dateien gesucht, auf die alle Tests zutreffen, nicht die, die einen von beiden Tests bestehen. Der Befehl
find . -size +12k -name "M*"sucht also nach allen Dateien im aktuellen Verzeichnis, die mindestens 12 Kilobyte groß sind UND deren Namen mit einem M beginnt.
Richtig interessant wird find erst mit der Anwendung von Aktionen. Die wichtigste und sicherlich meistgebrauchte Aktion ist -exec. Mit dieser Aktion lassen sich beliebige Unix-Kommandos ausführen, die mit den gefundenen Dateien angewendet werden. Dabei gibt es zwei wichtige Punkte zu beachten.
find /usr -size +12k -name "M*" -exec cp {} /tmp \;Oder, um ein etwas praktischeres Beispiel zu nennen, wenn der Systemverwalter alle Dateien löschen will, die Usern gehören, die es nicht mehr gibt, dann kann er schreiben:
find / -nouser -exec rm {} \;Das ist zweifellos ein gewisses Risiko, es könnten ja auch wichtige Dateien dabei sein, die durch einen Zufall einer UserID zugewiesen wurden, die nicht bekannt ist. Statt -exec können wir in so einem Fall auch -ok benutzen. Es macht exakt genau das Gleiche wie -exec, fragt aber bei jeder Ausführung vorher nach, ob es die Befehlszeile wirklich ausführen soll.
Dabei kommen unterschiedliche Techiken zum Zuge, es kann sein, daß die Datenbank nur in einer einzigen Datei liegt (z.B. /var/lib/locatedb) oder daß sie verteilt auf verschiedenen Dateisystemen vorliegt. Unter Linux ist bei den meisten Distributionen der Standort /var/lib/locatedb voreingestellt.
Das Programm, das diese Datenbank anlegt und täglich auffrischen sollte heißt updatedb und wird gewöhnlich via cron einmal täglich aufgerufen. Es erstellt eine Datenbank indem es alle angeschlossenen Laufwerke durchscannt und jede einzelne Datei samt Pfad speichert. Da das eine sehr aufwendige Aktion ist, wird dieser Programmaufruf in der Regel mitten in der Nacht ausgeführt und es existieren Möglichkeiten, bestimmte Verzeichnisse oder auch bestimmte Dateisysteme (wie etwa Netzlaufwerke) von der Suche auszunehmen.
In älteren Versionen von updatedb wurde diese Ausnahmeregelung in der Datei /etc/updatedb.conf vorgenommen. Hier wurden einfach Umgebungsvariablen definiert, die verschiedene Pfade ausschlossen, eine typische solche Datei könnte wie folgt aussehen:
# File: /etc/updatedb.conf # This file sets environment variables which are used by updatedb # filesystems which are pruned from updatedb database PRUNEFS="NFS nfs afs proc smbfs autofs auto iso9660 ncpfs coda" export PRUNEFS # paths which are pruned from updatedb database PRUNEPATHS="/tmp /usr/tmp /var/tmp /afs /amd /alex /var/spool" export PRUNEPATHS # netpaths which are added NETPATHS="" export NETPATHSDie erste Anweisung (PRUNEFS="NFS nfs afs proc smbfs ...") definiert Dateisystemtypen, die nicht durchsucht werden sollen. Die zweite (PRUNEPATHS="/tmp /usr/tmp /var/tmp ...")) definiert Pfade, die nicht durchsucht werden sollen.
Neuere Versionen von updatedb arbeiten mit Kommandozeilenoptionen, die den selben Effekt bieten.
Wozu diese Datenbank? Ein schnelles Auffinden von Dateien anhand von Namensmustern ist mit find nicht so einfach möglich. Denn find durchsucht ja tatsächlich die Festplatten nach den Dateien und das dauert. Da aber das Suchen nach Namensmustern sicherlich die häufigste Form ist, existiert das Programm locate. Dieses Programm durchsucht nicht die Festplatten, sondern eben die Datenbank, die durch updatedb erstellt wurde. Das geht enorm schnell und effektiv, hat jedoch den Nachteil, daß Dateien, die seit dem letzten Aufruf von updatedb erstellt wurden natürlich nicht gefunden werden können.
locate erlaubt die Verwendung von Suchmustern wie die Shell sie anbietet, also *, ?, [...]. Allerdings wird tatsächlich der ganze Dateinamenstring sammt Pfad durchsucht, ein Suchmuster von foo*bar würde also auch eine Datei /usr/foo/bla/bar finden.
Neben locate existiert alternativ auch das Programm slocate, das einen sichereren Zugriff gewährleistet. slocate erstellt die zentrale Datenbank und speichert aber zusätzlich auch die Eigentümerschaft und Zugriffsrechte der Dateien ab. So kann ein Normaluser nur die Dateien mit slocate finden, auf die er auch Zugriff hätte.
Insgesammt kann man zusammenfassen, daß locate und slocate eine schnelle und für normale Systemdateien durchaus zufriedenstellende Möglichkeit darstellt, Dateien anhand ihres Namens oder eines Suchmusters im Dateisystem zu finden. Wenn es aber darum geht, Dateien zu finden, die womöglich nach dem letzten Aufruf von updatedb erstellt wurden oder die Suchkriterien nicht den Namen der Datei benutzen, dann muß find benutzt werden.