Was ist der Grund für das Nebeneinander von rmdir (1) und rm (1)?
17
Ich benutze jeden Tag BSD und Linux, ich hatte noch nie einen Umstand, dass ich rmdir (1) anstelle von rm (1) verwenden muss. Was ist der Zweck der Existenz von rmdir?
Der Hauptgrund ist wahrscheinlich historisch. Zurück in den alten, alten Zeiten gab es keine rmdir(2)und mkdir(2)Systemaufrufe (wir 7th Edition UNIX diskutieren ™ hier), und rmdir(1)war (notgedrungen) ein SUID root Programm , dass der verwendeten unlink(2)Systemaufruf Verzeichnisse zu entfernen.
Der rmBefehl (ein reguläres Nicht-SUID-Programm) hat den rmdir(1)Befehl zum Entfernen leerer Verzeichnisse aufgerufen . Das konnte es selbst nicht. das erforderte root-Rechte. Daher gab es den rmdir(1)Befehl (siehe hier für den Quellcode in Unix V7), um leere Verzeichnisse zu entfernen, und der rmBefehl entfernte leere Verzeichnisse selbst nicht.
Um rmVerzeichnisse zu entfernen, müssen Sie die -rOption angeben.
Es gibt auch ein Symmetrie-Argument. Sie benötigen einen Befehl mkdir(1), um Verzeichnisse zu erstellen. Es erscheint vernünftig, einen Befehl rmdir(1)zu haben, um das, was geschehen ist, rückgängig zu machen mkdir(1). Außerdem sind sie ( in diesen Tagen) einfach exercisors der den rmdir(2)und mkdir(2)Systemaufrufe - ja, zurück in 7. Auflage UNIX, mkdir(1)war auch ein SUID root Programm, das unter Verwendung von mknod(2)Anruf einen Verzeichnisknoten und die zum Erstellen link(2)Aufruf der erstellen .und ..Einträge im Verzeichnis .
Nett. Ich habe gerade eine Kopie von 3BSD überprüft, die ich hier habe, und es gibt auch keine Dokumentation für einen rmdir-Systemaufruf, und rmdir (1) wird immer noch mit unlink implementiert.
Andy Ross
4
Ein wesentlicher Nachteil des mknod + -Link- und -Unlink-Systems war, dass das Erstellen eines Verzeichnisses keine atomare Operation war, sodass Sie möglicherweise ein teilweise vollständiges Verzeichnis erhalten. Es gab viele Programme, die entwickelt wurden, um Dateisysteme auf auftretende Inkonsistenzen zu prüfen. fsck(1)ist derjenige, der überlebt hat.
Jonathan Leffler
@ Jonathan, bringt Erinnerungen an Xenix auf diesem zurück. Yuck! Ja, wirklich schlimme Dinge könnten passieren.
Fiasco Labs
6
"rm" funktioniert nicht bei Verzeichnissen. Sie müssen entweder rmdir verwenden oder den Schalter -r für eine rekursive Löschung angeben. Der Grund dafür ist historisch: unlinkund rmdirsind separate Systemaufrufe und hat aus den frühen Tagen von Unix gewesen.
Ein erfreulicher Nebeneffekt ist, dass Sie ein Verzeichnis mit etwas geringerer Wahrscheinlichkeit versehentlich löschen, wenn Sie nur eine Datei entfernen möchten.
Vielen Dank. Mir ist aufgefallen, dass "rm -r" und "rmdir" die gleiche Anzahl von Tastenanschlägen haben. Gibt es rmdir nur aus historischen Gründen (.. kompatibel mit jahrzehntelangen Unix-Programmen)?
2
Tatsächlich gab es in den Anfängen von Unix weder einen Systemaufruf rmdir(2)noch mkdir(2)einen solchen. Der Benutzer rootkann den mknod(2)Aufruf verwenden, um einen Verzeichnisknoten zu erstellen, und den link(2)Aufruf, um die Einträge .und ..im Verzeichnis zu erstellen . und rootkönnte den unlink(2)Aufruf verwenden, um die Verzeichniseinträge zu entfernen.
Jonathan Leffler
3
Auch rmdir entfernt nur leere Verzeichnisse. Wenn Sie sicherstellen möchten, dass Sie keine zusätzlichen Dateien in einem Verzeichnis löschen, rmdirist dies sicherer als rm -r(es sei denn, Sie haben einen Alias für rm erstellt, sodass Sie immer bestätigen müssen, was Sie löschen, z. B. alias rm='rm -i'in ~ / .bashrc oder was auch immer Sie verwenden ).
Außerdem rmdirmacht es einfach leere Verzeichnisse mit Globbing (Wildcard) Ausdrücke zu entfernen. So entfernen Sie beispielsweise alle leeren Verzeichnisse in, /tmpohne Dateien oder Verzeichnisse mit Inhalten zu berühren:
Erwägen Sie die Verwendung rmdir /tmp/*. Wenn das /tmpVerzeichnis wirklich groß ist, kann es sein, dass aufgrund der zusätzlichen fünf Zeichen pro Name nicht genügend Platz für Argumente vorhanden ist, Sie müssen sich jedoch nicht in cdder Verzeichnishierarchie bewegen. Es lohnt sich auch zu überlegen rmdir /tmp/* 2>/dev/null, um zu vermeiden, dass Fehlermeldungen angezeigt werden (in der Regel wird es eine Menge geben, und fast alle davon sind für die vorliegende Aufgabe irrelevant).
Antworten:
Der Hauptgrund ist wahrscheinlich historisch. Zurück in den alten, alten Zeiten gab es keine
rmdir(2)
undmkdir(2)
Systemaufrufe (wir 7th Edition UNIX diskutieren ™ hier), undrmdir(1)
war (notgedrungen) ein SUID root Programm , dass der verwendetenunlink(2)
Systemaufruf Verzeichnisse zu entfernen.Die UNIX-Handbücher der 7. Auflage sind online unter http://cm.bell-labs.com/7thEdMan verfügbar (zuletzt überprüft am 23.04.2017). Sie sind auch unter http://plan9.bell-labs.com/7thEdMan verfügbar (zuletzt überprüft am 23.04.2017). Es scheint auch mindestens eine alternative Quelle online zu sein - http://wolfram.schneider.org/bsd/7thEdManVol2/ - für die Artikel in Band 2, mit einem Link zur FreeBSD- Site für die Befehle und Systemaufrufe in Band 1 .
Der
rm
Befehl (ein reguläres Nicht-SUID-Programm) hat denrmdir(1)
Befehl zum Entfernen leerer Verzeichnisse aufgerufen . Das konnte es selbst nicht. das erforderte root-Rechte. Daher gab es denrmdir(1)
Befehl (siehe hier für den Quellcode in Unix V7), um leere Verzeichnisse zu entfernen, und derrm
Befehl entfernte leere Verzeichnisse selbst nicht.Um
rm
Verzeichnisse zu entfernen, müssen Sie die-r
Option angeben.Es gibt auch ein Symmetrie-Argument. Sie benötigen einen Befehl
mkdir(1)
, um Verzeichnisse zu erstellen. Es erscheint vernünftig, einen Befehlrmdir(1)
zu haben, um das, was geschehen ist, rückgängig zu machenmkdir(1)
. Außerdem sind sie ( in diesen Tagen) einfach exercisors der denrmdir(2)
undmkdir(2)
Systemaufrufe - ja, zurück in 7. Auflage UNIX,mkdir(1)
war auch ein SUID root Programm, das unter Verwendung vonmknod(2)
Anruf einen Verzeichnisknoten und die zum Erstellenlink(2)
Aufruf der erstellen.
und..
Einträge im Verzeichnis .quelle
fsck(1)
ist derjenige, der überlebt hat."rm" funktioniert nicht bei Verzeichnissen. Sie müssen entweder rmdir verwenden oder den Schalter -r für eine rekursive Löschung angeben. Der Grund dafür ist historisch:
unlink
undrmdir
sind separate Systemaufrufe und hat aus den frühen Tagen von Unix gewesen.quelle
rmdir(2)
nochmkdir(2)
einen solchen. Der Benutzerroot
kann denmknod(2)
Aufruf verwenden, um einen Verzeichnisknoten zu erstellen, und denlink(2)
Aufruf, um die Einträge.
und..
im Verzeichnis zu erstellen . undroot
könnte denunlink(2)
Aufruf verwenden, um die Verzeichniseinträge zu entfernen.Auch rmdir entfernt nur leere Verzeichnisse. Wenn Sie sicherstellen möchten, dass Sie keine zusätzlichen Dateien in einem Verzeichnis löschen,
rmdir
ist dies sicherer alsrm -r
(es sei denn, Sie haben einen Alias für rm erstellt, sodass Sie immer bestätigen müssen, was Sie löschen, z. B.alias rm='rm -i'
in ~ / .bashrc oder was auch immer Sie verwenden ).quelle
Außerdem
rmdir
macht es einfach leere Verzeichnisse mit Globbing (Wildcard) Ausdrücke zu entfernen. So entfernen Sie beispielsweise alle leeren Verzeichnisse in,/tmp
ohne Dateien oder Verzeichnisse mit Inhalten zu berühren:quelle
rmdir /tmp/*
. Wenn das/tmp
Verzeichnis wirklich groß ist, kann es sein, dass aufgrund der zusätzlichen fünf Zeichen pro Name nicht genügend Platz für Argumente vorhanden ist, Sie müssen sich jedoch nicht incd
der Verzeichnishierarchie bewegen. Es lohnt sich auch zu überlegenrmdir /tmp/* 2>/dev/null
, um zu vermeiden, dass Fehlermeldungen angezeigt werden (in der Regel wird es eine Menge geben, und fast alle davon sind für die vorliegende Aufgabe irrelevant).