【问题标题】:Ocaml client-server: Client returns EAGAIN when attempting to connectOcaml 客户端-服务器:客户端在尝试连接时返回 EAGAIN
【发布时间】:2019-11-10 10:00:54
【问题描述】:

我正在尝试在 OCaml 中建立一个简单的客户端-服务器 在我的电脑和朋友的 utop 之间。但是,当我,客户端尝试连接到我朋友的电脑。以下是返回

Unix.Unix_error (Unix.EAGAIN, "connect", "")

我们尝试遵循以下文档 https://caml.inria.fr/pub/docs/oreilly-book/html/book-ora187.html 以及 ocaml API 参考。

服务器代码

  let s = socket PF_INET SOCK_STREAM 0 in
  try
    bind s addr;
    listen s 1000;
    s
  with z -> close s; raise z;;
val install_tcp_server_socket : sockaddr -> file_descr = <fun>
─( 17:17:32 )─< command 29 >─────────────────────────────────────────────────────────────{ counter: 0 }─
utop # let working = install_tcp_server_socket (ADDR_INET ((inet_addr_of_string "10.128.156.94"), 5002));;
val working : file_descr = <abstr>
─( 17:17:52 )─< command 30 >─────────────────────────────────────────────────────────────{ counter: 0 }─
utop # let (connect, client) = accept working;;

客户端代码

utop # let s = Unix.socket (PF_INET) (Unix.SOCK_STREAM) 0;;
val s : Unix.file_descr = <abstr>
─( 17:54:10 )─< command 5 >──────────────────────────────────────────────────────────────────────────────{ counter: 0 }─
utop # let s_addr = Unix.sockaddr ((Unix.inet_addr_of_string "10.128.156.94"), 5002);;
Line 1, characters 13-26:
Error: Unbound value Unix.sockaddr
─( 18:12:32 )─< command 6 >──────────────────────────────────────────────────────────────────────────────{ counter: 0 }─
utop # let s_addr = Unix.ADDR_INET ((Unix.inet_addr_of_string "10.128.156.94"), 5002);;
val s_addr : Unix.sockaddr = Unix.ADDR_INET (<abstr>, 5002)
─( 18:13:55 )─< command 7 >──────────────────────────────────────────────────────────────────────────────{ counter: 0 }─
utop # Unix.connect s s_addr;;
Exception: Unix.Unix_error (Unix.EAGAIN, "connect", "").
─( 18:14:31 )─< command 8 >──────────────────────────────────────────────────────────────────────────────{ counter: 0 }─
utop #

【问题讨论】:

    标签: unix ocaml


    【解决方案1】:

    我刚刚在这里的两个系统上尝试了您的代码,它对我有用。服务器端是 Linux (Ubuntu),客户端是 macOS。

    connect 调用不应返回 EAGAIN。这不是记录在案的错误之一。但是,我在网上看到喋喋不休地说 Linux 内核无论如何都会这样做“当对等方的积压队列已满时”。如果您窥探服务器系统的日志文件,您可能会发现一些有趣的东西。

    您也可以尝试使用较小的积压队列大小值。您正在使用的代码使用 3,但您使用的是 1000。这可能无关紧要,实际上它可能不会有任何区别。但这是我看到的唯一不寻常的东西。

    【讨论】:

    • 这两台都是 Windows 机器,如果有区别的话。
    • 它可能确实有所作为。您可能会查找 EAGAIN 错误应该是什么意思。也许在 Windows 实现中有记录的含义。否则我的建议是一样的。 EAGAIN 是一个如此奇怪的错误,以至于可能有一个有趣的事件出现在日志中。
    • 根据下面的caml.inria.fr/pub/docs/manual-ocaml/libref/Unix.html表示“资源暂时不可用;再试一次”。我认为它可以在互联网上找到我朋友的计算机,但是如果他将其设置为接受请求并且他的容量足够高,那么理论上它应该可以工作。
    • 是的,一般来说就是这个意思,但是当connect返回时,它可能有更具体的含义。它不是connect 操作通常定义的错误之一(在 Unix 中)。我记得它最初(几十年前)仅由 fork() 返回,表示目前没有可用的进程槽。
    猜你喜欢
    • 2016-07-06
    • 2021-06-22
    • 1970-01-01
    • 1970-01-01
    • 2019-02-28
    • 2020-06-26
    • 1970-01-01
    • 2016-02-16
    • 2012-03-27
    相关资源
    最近更新 更多