题
我即将用 C++ 开发一些与套接字相关的东西,并希望该软件从一开始就能够在 Windows 和 Linux 之间尽可能可移植(稍后使其可移植是很棘手的。)
我查看了不同的库,有一个用于 C++ 的库 alhem.net 当然还有 boost::asio。boost::asio 看起来非常有前途,但对于这么小的应用程序来说将是一个非常大的依赖。
是否值得自己编写这些内容,还是应该使用库?如果我自己做的话,主要的陷阱是什么?
解决方案
Winsocks 与 Posix 套接字不太兼容:
- 在 Winsocks 中,套接字的类型是
SOCKET
. 。在 Posix 上它只是一个文件描述符(int
),就可以正常执行了read()
和write()
来电。 - 它们不会以相同的方式返回错误。
- 他们不支持某些选项
recv()
和send()
. - 您必须使用两个特殊函数来初始化和统一化 Winsocks 库。
- 我不认为你可以关闭 Windows 套接字
shutdown()
或者close()
. 。这就像closesocket()
反而。
肯定还有更多的差异,但这就是我现在能记得的。如果您想要 Winsocks 的可移植性,您将拥有一个用于关闭套接字、打印错误消息等的小型库。
我可能会去 boost::asio
, ,就我个人而言(不过我从未使用过它)。
其他提示
我开发了一些围绕套接字的便携式包装器。确保您不会走上由 WinSock2 事件构成的不归路。除此之外,在我看来,最大的区别是:
- 要在 Windows 中启动网络,您需要调用
::WSAStartup()
, ,要在 Windows 中关闭它,请运行::WSACleanup()
;在Linux中什么都不做, close()
在Linux中是closesocket()
在 Windows 中,- 驱动程序和操作系统之间的默认缓冲区大小不同,因此请确保使用以下命令设置它们
SO_RCVBUF
和SO_SNDBUF
, - SO_REUSEADDR在Windows上窃取地址,在Linux上允许频繁重新打开;你可能只想在 Linux 中使用这个标志,
- 使套接字成为非阻塞用途
::ioctlsocket()
在 Windows 中,::fcntl()
在Linux中, - 头文件不同,
<sys/socket.h>
和 Linux 上的朋友们,<WinSock.h>
在 Windows 中, - 要便携,最简单的方法可能是使用
::select()
等待数据到达, fd_set
Windows/Linux 上的情况完全不同;仅当您需要优化初始化时,这才有意义fd_set
s,例如添加/删除任意套接字时,- 在 Windows 中,当套接字关闭时,挂在套接字上的任何线程都会被释放,并带有错误代码;在 Linux 中,线程仍处于等待状态。如果线程阻塞套接字,例如
::recvfrom()
, ,你可以考虑使用::sendto()
释放Linux下的停止线程。
我所需要的其他一切都可以从 låda 中解决。
查看<!>“自适应通信环境<!>”; (ACE)库: (ACE主页) 它在一个支持Windows,MacOS和Linux的便携式库中提供了一些很好的抽象和很多灵活性。 它有一点陡峭的学习曲线,但我从中获得了非常好的价值。
你将使用多少套接字?我已经完成了几个应用程序,其中套接字的东西非常高(开放,读取,写入),并且从Windows到Linux完美地工作。如果不止于此 - 请加强。
老实说,我会先使用boost :: asio作为首选。如果你真的想要了解套接字API,你可以在Windows和Linux上使用标准的BSD风格的套接字API - 只是在Windows上你必须链接到(并初始化)Winsock2,而在Linux你不会有一个单独的库链接。
看看这个...... http://sourceforge.net/projects/cpp-插座/