Erlang TCP Socket的接收進程的2種方案


轉自:http://blog.csdn.net/summerhust/article/details/8740973

 

一旦打開了一個使用TCP連接的套接字,它就始終保持打開狀態,直至任何一方關閉它或因為一個錯誤而終止。在建立一個連接時,一般為每一次請求產生一個新進程,只要有請求被處理,就保持這個進程的存活。

假設有一個監聽進程,其任務是等待傳入的TCP請求。只要一個請求到達,響應該連接請求的進程就變成了接收進程,有2種方案:

1. 產生新的進程並成為接收進程,而監聽者返回並繼續監聽下一個新的連接請求:

server() ->  

    {ok, ListenSocket} = gen_tcp:listen(1234, [binary, {active, false}]),  

    wait_connect(ListenSocket,0).  

 wait_connect(ListenSocket, Count) ->  

    {ok, Socket} = gen_tcp:accept(ListenSocket),  

    Pid = spawn(?MODULE, get_request, [Socket, [], Count]),  

    %將該套接字的控制進程改為Pid進程  

    gen_tcp:controlling_process(Socket, Pid),  

    wait_connect(ListenSocket, Count+1).  

      

  

get_request(Socket, BinaryList, Count) ->  

    case gen_tcp:recv(Socket, 0, 5000) of  

    {ok, Binary} ->  

        io:format("received data: ~p~n", [binary_to_list(Binary)]),  

        get_request(Socket, [Binary|BinaryList], Count);  

    {error, closed} ->  

        handle(lists:reverse(BinaryList), Count)  

    end.  

 

2. 使監聽進程成為接收進程,並使產生的新進程成為新的監聽者:

 

server() ->  

    {ok, ListenSocket} = gen_tcp:listen(1234, [binary, {active, false}]),  

    wait_connect(ListenSocket,0). 

 

wait_connect(ListenSocket, Count) ->  

    {ok, Socket} = gen_tcp:accept(ListenSocket),  

    spawn(?MODULE, wait_connect, [ListenSocket, Count+1]),  

    get_request(Socket, [], Count).  

 

說明:

(1)  創建一個套接字的進程(通過調用gen_tcp:accept或gen_tcp:connect)也就是該套接字的控制進程,該套接字所收到的任何消息都會轉發給這個控制進程,如果控制進程消亡,那么該套接字也會自行關閉。我們可以通過gen_tcp:controlling_process(Socket, NewPid)函數來把一個套接字的控制進程改為新的控制進程NewPid;

(2) gen_tcp:accept和gen_tcp:recv是阻塞的,可以用prim_inet:async_accept和prim_inet:async_recv實現非阻塞。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM