在 erlang 中中断 gen_tcp:recv
Interrupting gen_tcp:recv in erlang
我们有一个 gen_server 进程,它通过创建被动套接字池并为其他进程借用它们来管理客户端的被动套接字池。任何其他进程都可以借用一个套接字,使用该套接字向服务器发送请求,通过gen_tcp:recv得到回复,然后将套接字释放给gen_server套接字池进程。
套接字池进程监控所有借用套接字的进程。如果任何借用的进程挂了,它会从它那里得到一个挂机信号:
handle_info({'DOWN', Ref, process, _Pid, _Reason}, State) ->
在这种情况下,我们想排出借用的套接字,并通过放回池中来重新使用它。问题是,在尝试使用 gen_tcp:recv(Socket, 0, 0)
排空套接字时,我们收到 inet ealready
错误消息,这意味着 recv
操作正在进行中。
所以问题是如何中断之前的recv
,成功地排空套接字,并重新用于其他进程。
谢谢。
多一层间接将大大简化情况。
不是将 sockets 传递给需要使用它们的进程,而是让每个套接字由拥有它的单独进程控制并且 表示 系统内的套接字。根据需要将 Erlang 端消息路由到套接字以实现套接字的 "borrowing" (更灵活的是,向套接字控制器传递一个使用给定协议的回调模块,因此一旦数据通过网络在内部解释为 Erlang 消息)。
如果完成此操作,您将不会失去对套接字的控制或使它们处于不确定状态——相反,它们将一直由一个拥有所有权的进程持有。让套接字控制器监视其当前使用进程,而不是让 route-manager/pool-manager 进程接收 'DOWN'
消息。当收到 'DOWN'
时,您可以根据需要更改状态。
您可能会遇到一些奇怪的情况,即在未指定为所有者的套接字之间传递打开的文件描述符、套接字和其他类型的端口。如果您需要跨多个节点扩展程序,那么传递端口和套接字也会成为一个问题(突然间您必须关心事物传递到哪里以及它们在哪个节点上,等等)。
我们有一个 gen_server 进程,它通过创建被动套接字池并为其他进程借用它们来管理客户端的被动套接字池。任何其他进程都可以借用一个套接字,使用该套接字向服务器发送请求,通过gen_tcp:recv得到回复,然后将套接字释放给gen_server套接字池进程。
套接字池进程监控所有借用套接字的进程。如果任何借用的进程挂了,它会从它那里得到一个挂机信号:
handle_info({'DOWN', Ref, process, _Pid, _Reason}, State) ->
在这种情况下,我们想排出借用的套接字,并通过放回池中来重新使用它。问题是,在尝试使用 gen_tcp:recv(Socket, 0, 0)
排空套接字时,我们收到 inet ealready
错误消息,这意味着 recv
操作正在进行中。
所以问题是如何中断之前的recv
,成功地排空套接字,并重新用于其他进程。
谢谢。
多一层间接将大大简化情况。
不是将 sockets 传递给需要使用它们的进程,而是让每个套接字由拥有它的单独进程控制并且 表示 系统内的套接字。根据需要将 Erlang 端消息路由到套接字以实现套接字的 "borrowing" (更灵活的是,向套接字控制器传递一个使用给定协议的回调模块,因此一旦数据通过网络在内部解释为 Erlang 消息)。
如果完成此操作,您将不会失去对套接字的控制或使它们处于不确定状态——相反,它们将一直由一个拥有所有权的进程持有。让套接字控制器监视其当前使用进程,而不是让 route-manager/pool-manager 进程接收 'DOWN'
消息。当收到 'DOWN'
时,您可以根据需要更改状态。
您可能会遇到一些奇怪的情况,即在未指定为所有者的套接字之间传递打开的文件描述符、套接字和其他类型的端口。如果您需要跨多个节点扩展程序,那么传递端口和套接字也会成为一个问题(突然间您必须关心事物传递到哪里以及它们在哪个节点上,等等)。