Używanie nazwanych potoków wejścia / wyjścia dla połączenia TCP

15

Przez jakiś czas majstrowałem przy tym, żeby to zadziałało, więc podejrzewam jakieś podstawowe nieporozumienie na temat działania rur, które jest główną przyczyną moich problemów.

Moim celem jest zainicjowanie połączenia TCP z jakimś zdalnym hostem za pośrednictwem netcati posiadanie dwóch nazwanych potoków w systemie plików: jeden, z którego procesy mogą czytać, aby uzyskać przychodzące dane, a drugi, który procesy mogą zapisywać, służą jako dane wychodzące. Obecnie używam następującej konstrukcji:

mkfifo in
mkfifo out
cat out | netcat foo.bar.org 4000 > in &

Odtąd chciałbym zezwolić innym procesom na odczyt i zapis do / z tego otwartego połączenia TCP. Czy to „po prostu działa”, czy może jest powód, dla którego taki konstrukt nie może działać?

Co wydaje się stać w chwili obecnej jest to, że mogę odczytać z outbez problemu, ale gdy piszę aby inuzyskać wyjście wspomnieć o podziale rury i wszystkie kolejne pojawi komunikacyjnych być martwy. Myśli?

(Powiązane: pierwotnie użyłem:

netcat foo.bar.org 4000 < out > in &

ale stwierdził, że blokuje oczekiwanie na dane wejściowe. Ciekawi mnie to również, ale prawdopodobnie lepiej jest to rozwiązać w osobnym pytaniu).

noffle
źródło

Odpowiedzi:

6
cat out | netcat foo.bar.org 4000 > in &

Myślę, że problem polega na tym, catże wyjdzie, gdy tylko otrzyma EOFz outrury. A kiedy catwychodzi, reszta rurociągu (w tym netcat) również zostaje zakończona.

Wypróbuj coś takiego:

while true; do cat out; done | netcat foo.bar.org 4000 > in &

W ten sposób catjest uruchamiany ponownie tak często, jak to konieczne, a wszelkie EOFs pojawiające się w outrurze są skutecznie obsługiwane.

Steven Monday
źródło
Próbowałem tego, ale nadal otrzymuję write(stdout): Broken pipepo (lub wkrótce po) pisaniu do outpotoku.
noffle
2

Miałem też do czynienia z tym problemem. Głównym problemem jest netcat. To świetne narzędzie, ale zamyka połączenie, gdy jeden z podłączonych deskryptorów plików wejściowych lub wyjściowych jest zamknięty. Nie robi nic, gdy serwer nie nasłuchuje i kończy działanie, gdy drugi peer jest zamknięty. Tak długo, jak poprawnie skonfigurujesz serwer i utrzymasz otwarte deskryptory plików, będzie działać. Na przykład przetestowałem następujący scenariusz i działał bardzo dobrze: w konfiguracji terminalu serwer echa (ustawiłem go jak poniżej):

mkfifo loopFF
netcat -t -l -p 4000 <loopFF | tee loopFF

teraz w innym terminalu skonfiguruj połączenie fifo z serwerem:

mkfifo in
mkfifo out
netcat 127.0.0.1 4000 <out >in &

wydrukuj wszystko, co serwer ci wysyła (i utrzymuj, że działa, jeśli używasz infifo w aplikacji, która zamyka jeden koniec po zakończeniu, netcatzamyka połączenie)

cat in &

i na tym samym terminalu:

cat > out

teraz cokolwiek wpiszesz, zostanie wydrukowane ponownie (po naciśnięciu Enter). Zamknięcie tego polecenia spowoduje również zamknięcie połączenia.

saeedn
źródło
Widzę, że nie jest tak, gdy sam go wypróbuję, ale dlaczego netcat -t -l -p 4000 < loopFF | tee loopFFnie powoduje sam w sobie nieskończonej pętli sprzężenia zwrotnego?
noffle
@ noffle, ponieważ, jak powiedziałem, netcatzostanie zamknięty za każdym razem, gdy jedno z jego połączeń sieciowych zostanie zamknięte. Jeśli zamkniesz klienta (który wysyła ciąg i odbiera ten sam ciąg), netcatserwer również zostanie zamknięty. W tym przypadku napisałem dla siebie kod serwera, który każe sobie obsługiwać wielu klientów i łączyć się z nimi ponownie.
saeedn
2

Analiza Steven Monday wygląda dla mnie dobrze: catwraca po pierwszym napisaniu do, outponieważ jest fifo empty. Aby tego uniknąć, rozwiązaniem jest utrzymanie procesu z piątym otwartym w trybie zapisu, pierwszymcat w poniższym przykładzie:

mkfifo in
mkfifo out
cat > out &
echo $! > out-pid
cat out | netcat foo.bar.org 4000 > in &

(Plik out-pid jest sposobem na zatrzymanie całej sprawy:. kill -9 $(cat out-pid))

Kolejny przykład tutaj .

jfg956
źródło