2017-12-02 7 views
-2

Ich schreibe das Problem neu, da es soweit ich weiß, nicht klar verstanden wird. Ich implementiere meine eigene Shell in C, die alle Befehle des Originals unterstützen muss.Wie man Verzeichnis der Exec-Dateien irgendeines Befehls auf Terminal in C erhält?

Das Problem ist, zu ausführen alle vorhandenen UNIX bash Befehle in Cohneexecvp() oder system() Funktionen, die Sie bereits lassen, dass leicht tun.

Um dies zu tun, muss ich alle erforderlichen Verzeichnisse durchsuchen, die aus beliebigen UNIX-Befehlen bestehen können. Ich möchte nur wissen:

Kann ich wirklich sicher sein, dass ich alle möglichen UNIX-Befehle in einer beliebigen Distribution unterstützt, wenn ich alle Verzeichnisse in meiner Umgebungsvariablen PATH überprüft? (die in meiner Maschine /bin/, /usr/bin/, /usr/local/bin wird)

Ich habe auch ein Verfahren, das das vollständige Verzeichnis eine Datei bekommt man realpath() genannt eingesetzte. Aber leider gibt es (null), wenn ich versuche, das Verzeichnis des Befehls in meine eigene Shell eingefügt zu bekommen.

Was empfehlen Sie mir, dieses Problem zu erreichen? Als letzte Lösung macht es Sinn, den gesamten Computer rekursiv von der Wurzel aus zu suchen, um den eingegebenen Befehl zu finden?

Wenn etwas unklar ist, bitte lassen Sie mich wissen, um zu klären. Ich wäre Ihnen sehr dankbar, wenn Sie mit einem Beispielcode antworten und das Stichwort in der Frage löschen könnten, wenn Sie meinen, dass es ab sofort klar beschrieben wird.

Vielen Dank im Voraus!

+1

wollen Sie nach Dateien suchen, die mit der 'PATH'-Verzeichnisliste env erreichbar sind. Variable. –

+1

Hinweis: '/ bin' steht in der Systemvariablen' PATH'. –

+0

@ Jean-FrançoisFabre schlagen Sie mir vor, nach dem Inhalt von PATH env zu suchen. Variable? Wenn ja, kann ich sicher sein, dass sich alle möglichen UNIX-Befehle nur in der PATH-Systemvariablen befinden? –

Antwort

1

Beachten Sie zuerst, dass realpath() nichts sucht, es bestimmt nur den absoluten Pfad einer bestimmten Datei.

Es gibt keine alle möglichen UNIX-Befehl wie Sie vielleicht denken. Zumindest jede ausführbare Datei kann als UNIX-Befehl betrachtet werden, und ausführbare Dateien sind nicht unbedingt diejenigen, die x rechts davon angehängt haben. Shell-Skripte können durch einen Befehl wie sh myscript ausgeführt werden, selbst wenn kein ausführbarer Zugriff darauf gewährt wird. Nur Binärdateien erfordern, dass das angehängte Recht nativ ausgeführt werden kann. Also gibt es kein echtes Kriterium, das Ihnen helfen kann. Aber Sie haben möglicherweise Dateien, die x richtig haben und die keine ausführbaren Dateien sind!

Eine häufige Verwendung ist, dass ausführbare Dateien in einigen Verzeichnissen /bin, /usr/bin, /usr/local/bin und dergleichen befinden. Ihre Shell hat eine Umgebungsvariable mit dem Namen PATH, die eine Liste von Verzeichnissen enthält, in denen Sie nach einem Befehl suchen können, den Sie in der Befehlszeile frei angegeben haben.

Wie auch immer, wenn Sie ein Kriterium auswählen, indem Sie sich eine erschöpfende Suche zu machen, sagen alle Dateien mit x rechts, dann können Sie Befehl find wie find some_starting_dir -perm +0111 verwenden, um alle Dateien zu erhalten, die x rechts irgendwo haben.

Wenn Sie es programmieren möchten, dann können Sie entweder Legacy readdir() Funktion oder die neuere nftw() verwenden, um Ihr eigenes Verzeichnis Traversal zu machen. Sie werden viele Beispiele von diesen sogar auf SO finden.

+0

"* Aber Sie haben möglicherweise Dateien, die x-Recht haben und die keine ausführbaren Dateien sind! *", Die ich für einen defekten Datei-Modus halten würde. – alk

+1

Ich habe deine Antwort auf das Gegenteil von dem zitiert, worauf sich dein Kommentar bezieht. – alk

+0

@alk Oh, ich entschuldige mich für meinen Fehler ... –

3

Es ist wahr, dass eine UNIX-ausführbare Datei absolut überall sein kann, aber im Kontext einer Hausaufgabe macht es keinen Sinn, das gesamte Dateisystem zu durchsuchen. Was Ihr Instruktor wahrscheinlich von Ihnen verlangt, ist, dass Sie die Funktionalität von execvp selbst implementieren, indem Sie execv verwenden. Was execvp tut, ist erstens sieht es aus, ob es einen Schrägstrich in dem Befehlsnamen gibt. Wenn dies der Fall ist, übergibt es den Befehl und die Argumente direkt an execv - es wird nicht gesucht. Ansonsten iteriert es über die Verzeichnisse in PATH und überprüft, ob der Befehl in beiden ausführbar ist. Entscheidenderweise scannt es NICHT den Inhalt jedes Verzeichnisses; das wäre nicht nur sehr langsam, es würde auch unter bestimmten Bedingungen nicht funktionieren (zB ein Verzeichnis mit --x Berechtigungen) Stattdessen ruft es blind execv mit dem Pfadnamen "$ dir/$ cmd" auf. Wenn das funktioniert, gibt execv nicht zurück. Wenn es nicht funktionierte und errno auf ENOENT festgelegt ist, wird das nächste Verzeichnis im Pfad ausgeführt.

Verwandte Themen