Kabuk / bash iki arasında komutlar _and_output giriş bağlanması

oy
10

Okudum ve Stdin / stdout dan yazma iki (UNIX) programları A ve B var.

Benim ilk sorun B'nin stdin'e bir stdout'unu nasıl bağlanacağını olduğunu ve Aïe, A gibi bir şey stdin'e B'nin stdout | B, ancak, iki yönlü bir boru. Ben bu çözebilir şüpheli yönlendirmek için exec ama çalışmak için alamadım. Programlar böylece geçici dosya işe yaramaz interaktif.

İkinci sorun, I programlar arasında geçiş (tabanlı metin satırı) trafik görebilmesi için Stdout'a bir günlük programı vasıtasıyla her bir yönünde ve borunun bir yinelenen istiyoruz olmasıdır. İlk sorunu çözebilir Burada (...)> uzak tişört ile alabilirsiniz.

onlar iyi bilinen çözümler olmalıdır ama bir şey bulmak mümkün değil gibi her ikisi de bu sorunların görünüyor.

Bir POSIX kabuk çözümü tercih veya cygwin bash çalışır en az bir şey olacaktır.

cevaplar sayesinde aşağıdaki çözüm geldi. A / B komutları iki bağlantı dinlemek NC kullanır. günlük programı (tamponsuz işleme -u) ile sed kullanır.

bash-3.2$ fifodir=$(mktemp -d)
bash-3.2$ mkfifo $fifodir/echoAtoB
bash-3.2$ mkfifo $fifodir/echoBtoA
bash-3.2$ sed -u 's/^/A->B: /' $fifodir/echoAtoB &
bash-3.2$ sed -u 's/^/B->A: /' $fifodir/echoBtoA &
bash-3.2$ mkfifo $fifodir/loopback
bash-3.2$ nc -l -p 47002 < $fifodir/loopback \
          | tee $fifodir/echoAtoB \
          | nc -l -p 47001 \
          | tee $fifodir/echoBtoA > $fifodir/loopback

Bu standart çıkışa liman 47001 bağlanmak ve 47002 ve Yankılanmayı tüm trafiği dinler.

2 nolu kabuğun içinde yapılacak:

bash-3.2$ nc localhost 47001

Kabuk 3'te yapın:

bash-3.2$ nc localhost 47002

Şimdi kabuğun 2 girilen satırlar 3 ve tam tersi kabuk yazılır ve trafik gibi bir öğe 1 kabuk kaydedilir:

B->A: input to port 47001
A->B: input to port 47002

Yukarıdaki Cygwin üzerinde test edilmiştir

Güncelleme: Senaryo üzerinde birkaç gün sonra çalışmayı durdurdu (!). Anlaşılan o ki kilitlenmeye. cevaplarında önerilerden bazıları daha güvenilir olabilir.

Oluştur 26/09/2008 saat 14:24
kaynak kullanıcı
Diğer dillerde...                            


8 cevaplar

oy
10

Nasıl bir adlandırılmış kanal hakkında?

# mkfifo foo
# A < foo | B > foo
# rm foo

İkinci kısım için ben tee doğru cevap olduğuna inanıyoruz. Yani o olur:

# A < foo | tee logfile | B > foo
Cevap 26/09/2008 saat 14:33
kaynak kullanıcı

oy
5

Muhtemelen adlandırılmış boruların birlikte kaçmak:

mkfifo pipe
gawk '$1' < pipe | gawk '$1' > pipe
Cevap 26/09/2008 saat 14:30
kaynak kullanıcı

Cevap 26/09/2008 saat 14:26
kaynak kullanıcı

oy
4

Sen kullanabilirsiniz bekleyin .

Expect vb telnet, ftp, passwd, fsck, rlogin, ucu gibi otomatik etkileşimli uygulamalar için bir araçtır

Sen (alınan aşağıdaki kodu kullanabilirsiniz keşfetmek Expect bir başlangıç noktası olarak kitap) - İstediğiniz gibi, PROC2 ve tersi girişine proc1 çıktısını bağlar:

#!/usr/bin/expect -f
spawn proc1
set proc1 $spawn_id
spawn proc2
interact -u $proc1
Cevap 26/09/2008 saat 14:49
kaynak kullanıcı

oy
3

Ben, bu konuda çok fazla zaman harcanan o kadar verdi ve son ksh bu izin verir (Korn kabuğunu), kullanmaya karar verdi.

cmd1 |& cmd2 >&p <&p

burada |&bir ko-işlemini başlatmak için bir (boru) operatör ve &pko-sürecinin dosya tanımlayıcıdır.

Cevap 09/02/2009 saat 10:12
kaynak kullanıcı

oy
2

Bir noktada bu problem vardı ve ben birlikte bu basit C programı attı.

#include <stdio.h>
#include <unistd.h>

#define PERROR_AND_DIE(_x_) {perror(_x_); _exit(1);}

int main(int argc, char **argv) {
    int fd0[2];
    int fd1[2];


    if ( argc != 3 ) {
        fprintf(stdout, "Usage %s: \"[command 1]\" \"[command 2]\"\n", argv[0]);
        _exit(1);
    }

    if ( pipe(fd0) || pipe(fd1) ) PERROR_AND_DIE("pipe")

    pid_t id = fork();
    if ( id == -1 ) PERROR_AND_DIE("fork");

    if ( id ) {
        if ( -1 == close(0) )  PERROR_AND_DIE("P1: close 0");
        if ( -1 == dup2(fd0[0], 0) ) PERROR_AND_DIE("P1: dup 0"); //Read my STDIN from this pipe

        if ( -1 == close(1) )  PERROR_AND_DIE("P1: close 1");
        if ( -1 == dup2(fd1[1], 1) ) PERROR_AND_DIE("P1: dup 1"); //Write my STDOUT here
        execl("/bin/sh", "/bin/sh", "-c", argv[1], NULL);
        PERROR_AND_DIE("P1: exec")
    }

    if ( -1 == close(0) )  PERROR_AND_DIE("P2: close 0");
    if ( -1 == dup2(fd1[0], 0) ) PERROR_AND_DIE("P2: dup 0");

    if ( -1 == close(1) )  PERROR_AND_DIE("P2: close 1");
    if ( -1 == dup2(fd0[1], 1) ) PERROR_AND_DIE("P2: dup 1");


    execl("/bin/sh", "/bin/sh", "-c", argv[2], NULL);
    PERROR_AND_DIE("P2: exec")
}
Cevap 27/10/2011 saat 04:41
kaynak kullanıcı

oy
0

Ben "coproc" öneririm:

#! /bin/bash
# initiator needs argument

if [ $# -gt 0 ]; then
  a=$1
  echo "Question $a"
else
  read a
fi

if [ $# -gt 0 ]; then
  read a
  echo "$a" >&2
else
  echo "Answer to $a is ..."
fi

exit 0

Sonra bu oturumu bkz:

$ coproc ./dialog
$ ./dialog  test  < /dev/fd/${COPROC[0]}  > /dev/fd/${COPROC[1]}
Answer to Question test is ...
Cevap 29/11/2012 saat 14:09
kaynak kullanıcı

oy
0

Bu soru benzer biri daha önce sordum. Başkaları tarafından önerilen çözümler adlandırılmış yöneltme kullanmak, ama ben cygwin onları yok sanıyorum. Şu anda bırakmaya niyetim çözümü kendi (a at girişimi) , ancak gerektirir /dev/fd/0muhtemelen de bizde olmayan.

Ben geçen-komut satırları-olarak-dizeleri açıdan pek hoşlanmadığını rağmen twinpipe(JeeBee (bahsettiği 139495 )), bu cygwin içinde tek seçenek olabilir.

Cevap 26/09/2008 saat 14:53
kaynak kullanıcı

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more