Syntaxfrage zur ksh unter Solaris

S

Shark2150

Grünschnabel
Hallo erstmal,

dies ist mein erster Beitrag in diesem Forum und eines Vorweg: ich würde mich durchaus als Unixeinsteiger bezeichnen, daher möge man mir bitte meine Unwissenheit verzeihen :)

Ich besuche eine Vorlesung über UNIX (Solaris im speziellen) und auf einem Übungsblatt eine Frage die ich nicht so recht beantworten kann. Ich soll sagen was das Kommando (in der ksh):

"{ cd /bin; ls; cd /etc; ls } | wc -l; pwd"

ausgibt und ich soll erklären warum. Nun hab ich es einfach mal ausprobiert und gemerkt, das wc -l die Zeilen zählt, die durch die in {}-Klammern ausgeführten Befehle hervorgerufen werden und dass das folgende "pwd" das Directory ausgibt aus welchem der Befehl aufgerufen wurde. Also ist es so als wären die Kommandos in den Klammern nie ausgeführt worden - da man sich ja immer noch im selben Verzeichnis befindet. Auf der Suche nach dem Sinn der {}-Klammern habe ich ein Buch zu Rate gezogen, dass mir folgendes sagt:

(cmd;cmd) Run cmd;cmd in a subshell.
{cmd;cmd} Like (cmd;cmd) without a subshell.

Heißt das nicht, dass die Kommandos ganz normal, also in der selben Shell ausgeführt werden müßten? Bin irgendwie ein wenig verwirrt :hilfe2: und wäre über eine Antwort dankbar,

Shark2150
 
Normalerweise ruft ein Shellkommando eine neue Shell (Subshell) auf, die den Befehl ausfuehrt und danach wieder beendet wird.
Soll nun etwa aber eine Umgebungsvariable oder aehnliches gesetzt werden, dann kann man das nicht mit dieser Methode machen, weil damit nach Beenden der Subshell diese Umgebungsvariablen wieder verloren gingen. Hier wird sogenanntes "sourcing" benutzt, damit kann der Process in der eigentlichen Shell ohne eine Subshell ausgefuehrt werden.
 
Danke für die schnelle Antwort,

allerdings habe ich sie nicht ganz verstanden ?(
Mit normalerweise meinst du "normale" ()-Klammern, oder? Und wenn die {}-Klammern den Prozess ohne Subshell abwickelbar machen, warum werden dann nicht die Verzeichnisse korrekt gewechselt? Die Auswirkung ist ja mehr so etwas wie "so tun als ob", er führt sie insofern aus, dass wc die Zeilen zählen kann, aber wirkliche Verzeichniswechsel finden irgendwie nicht statt...
 
Mit normalerweise meinst du "normale" ()-Klammern, oder?
Nein, generell werden alle Kommandos in einer Subshell ausgefuert. Eine Ausnahme ist, wenn das Kommando mit einem vorangestellen . (Punkt) gesourced wird. Dann wird das Programm nicht in einer Subshell ausgefuehrt und Umgebungsvariablen stehen auch nach Terminierung des Processes weiterhin zur Verfuegung.

Und wenn die {}-Klammern den Prozess ohne Subshell abwickelbar machen, warum werden dann nicht die Verzeichnisse korrekt gewechselt? Die Auswirkung ist ja mehr so etwas wie "so tun als ob", er führt sie insofern aus, dass wc die Zeilen zählen kann, aber wirkliche Verzeichniswechsel finden irgendwie nicht statt...
In diesem Fall werden keine runden Klammern benutzt, damit das Ergebnis aller 4 Processe beim Tunneln ( | ) noch zur Verfuegung steht. Ein Verzeichniswechsel ist nicht vorgesehen.
 
Mhmmm, also wenn ich folgendes eingebe (Ich bin gerade im /bin Verzeichnis):

{ cd /etc ; ls -l } | wc -l

dann zählt er die Zeilen, gibt die Anzahl aus und ich befinde mich nach wie vor im /bin Verzeichnis. Gebe ich aber folgendes ein:

cd /etc ; ls -l | wc -l

gibt er die gezählten Zeilen genau wie vorher aus, ich befinde mich anschließend aber im /etc Verzeichnis. Wieso beeinflussen die {}-Klammern den Verzeichniswechsel, wenn der Befehl darin ausgeführt wird?
 
Ich hoffe ich erklaere das jetzt nicht falsch, falls doch moege man mich bitte berichtigen!

{ cd /etc ; ls -l } | wc -l
Durch die Klammern fuehrt die Shell (hier ohne Subshell) den Codeblock ( == Inhalt der Klammern) aus und gibt aber nur das Ergebnis als sogenannte "local variable" zurueck.

cd /etc ; ls -l | wc -l
In diesem Fall wird zwar auch der Wert von ls ausgegeben, allerdings interpretiert die Shell das nicht als Codeblock sondern fuehrt die Befehle der Reihe nach aus, was hier das gleiche Ergebnis auf der Standardausgabe liefert, allerdings eben mit Verzeichniswechsel.
 

Ähnliche Themen

Problem mit HSPA+ Modem Huawei E353 - Installation unmöglich?

Pipefehler unter Solaris 10 X86

solaris 10 make befehl

Dateisystem defekt (ext3)

OpenSuse 11.1 USB Festplatte wird nicht erkannt

Zurück
Oben