2010-04-14 103 views
4

我需要我的erlang应用程序通过命名管道进行读写操作。如何从erlang读取/写入命名管道?

打开命名管道作为文件将失败eisdir

我写了下面的模块,但它很脆弱,在很多方面都感觉不对。一段时间后,它也不能阅读。有没有办法让它更优雅?

-module(port_forwarder). 
-export([start/2, forwarder/2]). 

-include("logger.hrl"). 

start(From, To)-> 
    spawn(fun() -> forwarder(From, To) end). 

forwarder(FromFile, ToFile) -> 
    To = open_port({spawn,"/bin/cat > " ++ ToFifo}, 
        [binary, out, eof,{packet, 4}]), 
    From = open_port({spawn,"/bin/cat " ++ FromFifo}, 
        [binary, in, eof, {packet, 4}]), 
    forwarder(From, To, nil). 

forwarder(From, To, Pid) -> 
    receive 
    {Manager, {command, Bin}} -> 
     ?ERROR("Sending : ~p", [Bin]), 
     To ! {self(), {command, Bin}}, 
     forwarder(From, To, Manager); 
    {From ,{data,Data}} -> 
     Pid ! {self(), {data, Data}}, 
     forwarder(From, To, Pid); 
    E -> 
     ?ERROR("Quitting, first message not understood : ~p", [E]) 
    end. 

正如您可能已经注意到的,它在模拟接受或返回的端口格式。 我希望它取代将读取管道另一端并从调试器启动的C代码。

回答

2

我认为eisdir失败来自这个代码,假设你在Unix上运行。

https://github.com/erlang/otp/blob/master/erts/emulator/drivers/unix/unix_efile.c

efile_openfileefile_may_openfile。他们都进行检查,假设文件是​​!IS_REG(f),那么它是一个目录。这似乎有缺陷,但也许有很好的理由不打开非常规文件。 /dev/null的kludge也是一个有趣的阅读。

我以前也遇到过这个问题。也许是时候搔痒了。

+0

感谢您的指针。我可能会划伤。 – cstar 2010-04-16 19:33:43