Kann ich zwei beliebige Prozesse miteinander verbinden?

8

Auf dieser Seite aus Das Design und die Implementierung des 4.4BSD-Betriebssystems heißt es:

Ein Hauptunterschied zwischen Pipes und Sockets besteht darin, dass Pipes einen gemeinsamen übergeordneten Prozess zum Einrichten des Kommunikationskanals benötigen

Wenn ich jedoch richtig aufzeichne, ist die einzige Möglichkeit, einen neuen Prozess zu erstellen, forkein vorhandener. Ich kann also nicht wirklich sehen, wie zwei Prozesse keinen gemeinsamen Vorfahren haben könnten. Habe ich dann Recht zu glauben, dass jedes Prozesspaar miteinander verbunden werden kann?

qdii
quelle
1
Wenn es bei Ihrer Frage wirklich um einen "gemeinsamen Vorfahren" geht, steht dies nicht in Ihrem Zitat. Ein Elternteil ist ein Vorfahr, aber nicht alle Vorfahren sind Eltern.
msw
Schauen Sie sich ps auxfeine Idee zu Prozessvorfahren an.
Michas
@msw meinst du, dass die 2 Prozesse das gleiche direkte übergeordnete Element haben müssen? Cousin zu sein (dh einen gemeinsamen Großelternteil zu haben) ist nicht genug?
qdii

Antworten:

7

Habe ich dann Recht zu glauben, dass jedes Prozesspaar miteinander verbunden werden kann?

Nicht wirklich.

Die Rohre müssen vom übergeordneten Prozess eingerichtet werden, bevor das Kind oder die Kinder gegabelt werden. Sobald der untergeordnete Prozess gegabelt ist, können seine Dateideskriptoren nicht mehr "von außen" manipuliert werden (wobei Dinge wie Debugger ignoriert werden). Der übergeordnete Prozess (oder ein anderer Prozess) kann den Teil "Einrichten des Kommunikationskanals" nicht nachträglich ausführen .

Wenn Sie also zwei zufällige Prozesse verwenden, die bereits ausgeführt werden, können Sie keine Pipe direkt zwischen ihnen einrichten. Sie müssen eine Art Socket (oder einen anderen IPC-Mechanismus) verwenden, um die Kommunikation zu ermöglichen. (Beachten Sie jedoch, dass einige Betriebssysteme, darunter auch FreeBSD, das Senden von Dateideskriptoren auf Unix-Domain-Sockets ermöglichen.)

Matte
quelle
4

Dieser Satz ist nicht sehr klar. Erstens Elternteil sollte Vorfahre , da der Prozess das Rohr der Einrichtung kann ein Elternteil oder ein Großelternteil , oder ein Grand-Enkel ... -grandparent, oder eine der kommunizierenden Prozesse. Zweitens bedeutet der Satz nicht "Wenn Sie eine Pipe wollen, muss es einen gemeinsamen Ahnenprozess geben", sondern "Wenn Sie eine Pipe wollen, muss ein gemeinsamer Ahnenprozess sie einrichten".

Unter der Haube baut ein Prozess ein Rohr mit sich selbst auf. Die Pipe ist ein Dateideskriptor wie jeder andere, genauer gesagt ein Paar von Dateideskriptoren, einer für jedes Ende. Der Prozess, der die Pipe erstellt hat, kann sie sofort verwenden, um Daten an sich selbst zu senden, obwohl dies selten nützlich ist (obwohl eine Self-Pipe ihre Verwendung hat).

Eine typische Redewendung besteht darin, dass ein Prozess eine Pipe einrichtet, dann einen untergeordneten Prozess aufteilt und ein Ende der Pipe im übergeordneten und das andere Ende der Pipe im untergeordneten Prozess schließt. Auf diese Weise können der übergeordnete und der untergeordnete Prozess in eine Richtung kommunizieren. Wenn die Prozesse eine bidirektionale Kommunikation benötigen, benötigen sie zwei Pipes (außer bei einigen Unix-Varianten, bei denen Pipes bidirektional sind).

Die Pipes werden wiederum von untergeordneten Elementen geerbt, sodass der Prozess, der die Pipe erstellt hat, möglicherweise nicht an der Kommunikation beteiligt ist. Eine Pipe in einer Shell, die zwischen zwei externen Befehlen erstellt wurde, ls | rot13umfasst beispielsweise die folgenden Schritte:

  • Die Schale erzeugt ein Rohr.
  • Die Shell gibt einen Prozess vor. Das Kind schließt das Leseende der Pipe und ruft execveauf ls.
  • Die Shell gibt einen Prozess vor. Das Kind schließt das Schreibende der Pipe und ruft execveauf rot13.
  • Die Hülle schließt beide Enden des Rohrs und wartet, bis beide Teilprozesse beendet sind.

Wenn zwei vorhandene Prozesse miteinander kommunizieren möchten, können sie eine Named Pipe verwenden . (Nun, es wird auch ein Dateideskriptor übergeben , aber es ist nichts für schwache Nerven.)

Gilles 'SO - hör auf böse zu sein'
quelle
2

Die Shell der Pipeline ist das gemeinsame übergeordnete Element, das einen Kommunikationskanal zwischen den verschiedenen Mitgliedern der Pipeline einrichtet.

Jeder Prozess kann an jeden anderen weitergeleitet werden. Die einzigen Prozesse, die sinnvollerweise miteinander verbunden werden können , sind "Filter", die von stdin lesen und in stdout schreiben.

Zum Beispiel, wenn Sie den Befehl ausgeben

$ tail -f /etc/motd | tail -f | cat > /dev/null

ps -eaH wird zeigen, dass die Katze und ihre zwei Schwänze Kinder der aufrufenden Schale sind:

 1675 pts/0    00:00:00     bash
 2483 pts/0    00:00:00       tail
 2484 pts/0    00:00:00       tail
 2485 pts/0    00:00:00       cat
msw
quelle