我在 AIX 主机 myscript.sh 上有一个 bash 脚本,如下所示:
MODE="$1"
if [ "$MODE" == "start" ]; then
socat -T100 -lf $LOGF -d -d -d -x TCP4-LISTEN:$LISTENINGPORT,bind=$LISTENINGADDR,reuseaddr,fork EXEC:"$0 proxy" &
PID=$!
echo $PID > $PIDFILE
echo "$0 $MODE started (pid=$PID)"
elif [ "$MODE" == "proxy" ]; then
cat - > $TMPFILE
# process $TMPFILE before the SSL connection.
cat $TMPFILE | socat -T 100 -lf $LOGF -d - OPENSSL:$HOST
rm -f $TMPFILE
当我运行时一切都很好:
$ cat somefile | myscript.sh proxy | xxd
当我使用测试脚本连接到 socat 侦听器时出现问题:
my $file = $ARGV[0];
my $fsize = -s $file;
my $socket = IO::Socket::INET->new("127.0.0.1:$port")
or die "Couldn't connect to remote host: $!";
$socket->autoflush(1);
binmode($socket);
open (FILE,$file);
binmode(FILE);
my $buffer ;
while(sysread(FILE, $buffer, $blocksize)) {
print $socket $buffer ;
}
print "sent\n" ;
close (FILE) ;
my $answer = <$socket>;
if (defined($answer)) {
print $answer; # never reached
print "...\n" ;
} else {
die "connection reset by peer\n";
}
在 myscript.sh 中,它阻塞就行了:
cat - > $TMPFILE
在测试脚本中,它阻塞就行了:
my $answer = <$socket>;
至此,数据已经被socat监听器接收到了(用tcpdump检查)。
但是,当我在 socat 超时之前Ctrl+c测试脚本时,数据会通过管道(即最终联系 SSL 服务器)。
我究竟做错了什么?
更新:感谢有关 cat 和 EOF 的提示。目前,我已经解决了这样的问题:
timeout 0.2 cat -u - > $TMPFILE 2>>/dev/null
# process $TMPFILE before the SSL connection.
cat $TMPFILE | socat -T 100 -lf $LOGF -d - OPENSSL:$HOST
很丑,浪费0.2秒,希望能找到更好的解决方案。但它现在完成了这项工作。2>>/dev/null 部分是因为 AIX 抱怨计数器无效(与 timeout 命令有关)。