1

我正在寻找有关 Windows 网络编程的信息。主要是如何获得单个可执行文件来应对 1000 个连接。

我们在 unix 上使用 select() FD_ISSET 等,这非常快。在 Windows 上,这些 API 很差。FD_SET 慢很多,但即使解决这个问题,Windows 也比 HPUX 慢很多。

我正在寻找一个我可以使用的 win32 API 调用,而不是不需要太多 CPU/时间的 select() 调用。目前我们在 select() 中花费了 50% 的时间(和 CPU),而在 unix 上花费的时间在 send() 和 recv() 中,这是我所期望的。

谢谢尼尔

4

2 回答 2

2

您可能正在寻找Windows I/O Completion Ports。这是一篇来自SysInternals的文章。

于 2011-05-11T14:30:25.963 回答
1

如果您真的喜欢可扩展的套接字编程,那么在 Windows 上没有什么比 IO 完成端口更好的了。

话虽如此,您的程序可能需要对完成端口模型进行大量重写。

但是,即使使用 select()/FD_ISSET,也可以提高性能。

这是如何完成的:在 winsock2.h 中,fd_set 被定义为一个 SOCKET 数组和一个元素计数器

typedef struct fd_set {
    u_int fd_count;               /* how many are SET? */
    SOCKET  fd_array[FD_SETSIZE];   /* an array of SOCKETs */
} fd_set;

同样在 winsock2.h 中,您会发现 FD_SET 在该数组的末尾添加了一个 SOCKET,并且 FD_ISSET 正在数组中进行线性搜索。

现在,如果您更改宏以使用 SOCKET 的排序数组,即

  • FD_SET 按排序顺序添加套接字
  • FD_ISSET 进行二分查找而不是线性查找

然后依赖于数组的大小 FD_ISSET 可以大大提高(虽然 FD_SET 的性能会有所下降,但我们假设 FD_SET 是一个很少的操作)。

在 Unix 上,select() 的性能更好,因为它们 FD_SET 作为位图,FD_SET/FD_ISSET 只会测试或设置一个位。在 Windows 上,此技术不适用,因为套接字不是一个小的正文件描述符数,它是一个句柄,句柄的标量值可能很大。

于 2011-05-11T14:48:53.727 回答