听netcat工作但不是grep'able(或其他几个实用程序)

时间:2015-05-15 05:54:53

标签: linux bash shell pipeline netcat

我正在测试一些netcat udp shell工具,并试图获取输出并通过标准管道发送它。在这个例子中,我有一个netcat客户端发送'foo'然后'bar'然后'foo',每次尝试从听众那里发送新行:

[root@localhost ~ 05:40:20 ]# exec 5< <(nc -d -w 0 -6 -l -k -u 9801)
[root@localhost ~ 05:40:25 ]# awk '{print}' <&5
foo
bar
foo
^C
[root@localhost ~ 05:40:48 ]# awk '{print}' <&5 | grep foo
^C
[root@localhost ~ 05:41:12 ]# awk '{print}' <&5 | grep --line-buffered foo
^C
[root@localhost ~ 05:41:37 ]#
[root@localhost ~ 05:44:38 ]# grep foo <&5
foo
foo
^C
[root@localhost ~ 05:44:57 ]#

我已经检查了--line-buffered ...而且我也从'od -bc'得到了相同的行为,即什么都没有。 grep适用于fd ...但是如果我将grep管道输出任何东西(比如od -bc,cut),我会得到相同的(没有)。尝试使用stdbuf -oL为最后一个grep添加前缀无效。可以&gt;提交然后尾随它,但感觉我错过了什么。

更新: 似乎是描述符/订单/时间相关的东西。我创建了一个文件'tailSource'并使用了它,当我运行echo -e "foo\nfoo\nbar\nfoo" >> tailSource

时产生了同样的问题(没有输出)
[root@localhost shm 07:16:18 ]# exec 5< <(tail -n 0 -f tailSource)
[root@localhost shm 07:16:32 ]# awk '{print}' <&5 | grep foo

......当我没有'| grep foo',我得到了我期望的输出。 (GNU bash,版本4.1.2(1)-release(x86_64-redhat-linux-gnu))

2 个答案:

答案 0 :(得分:2)

为了它的价值

$ exec 5< <(echo -e "foo\nbar\nfoo")
$ awk '{print}' <&5 | grep foo

打印

foo
foo

其中

$ exec 5< <(echo -e "foo\nbar\nfoo") 
$ awk '{print}' <&5 
foo 
bar 
foo 
$ awk '{print}' <&5
$

第二个电话不会输出任何内容。

我认为这是因为文件描述符已经结束,您需要回放它,另请参阅this answerthis question问题。

为了使用它,您可以选择在临时文件中捕获它或在一行中执行转换。

答案 1 :(得分:2)

awk在输出未到达终端时进行缓冲。如果你有GNU awk,你可以使用它的fflush()函数在每次打印后刷新

gawk '{print; fflush()}' <&5 | grep foo

在这种特殊情况下,你不需要awk和grep,也可以。

awk /foo/ <&5
grep foo <&5

有关缓冲以及如何解决此问题的更多信息,请参阅BashFAQ 9