我正在尝试使用 luv 构建一个 NES 模拟器插件,该插件可以在不暂停游戏模拟的情况下与另一个进程进行通信。当我通过手动输入输入数据来测试它时,我的一些东西运行得很顺利,但是当我去测试通过管道与另一个进程通信时,lua 脚本似乎从未收到任何数据。
作为最小的可重现示例,请使用以下 lua 脚本:
local uv = require("luv")
local stdin = uv.new_poll(1)
stdin:start("r", function() print("uv callback") end)
uv.run("once")
当我手动按 Enter 时,一切都按预期进行:
% lua-5.1 min.lua
uv callback
%
但是,通过管道从另一个程序传递空行似乎不起作用:
% echo | lua-5.1 min.lua
-- nothing happens, and lua-5.1 does not exit
通过额外的测试,我相信这不是缓冲问题:编写一个手动刷新的程序来代替
echo
并在 lua 脚本顶部添加 io.stdin:setvbuf("no")
不会改变行为。 (事实上,通过实验,它似乎以某种方式直接连接到终端:手动按 Enter 仍然会导致回调运行并退出程序!)
为什么我的脚本看不到管道输入的数据,如何更改它才能看到?
标准输入是 FD 0,而不是 FD 1,因此使用
uv.new_poll(0)
而不是 uv.new_poll(1)
。当你手动按 Enter 键而不是通过管道进入它时它起作用的原因是,在没有管道的情况下,所有标准 FD 都是以读写模式打开的 TTY。