【发布时间】:2010-12-29 13:06:07
【问题描述】:
我正在开发 POSIX C++ 程序的 Windows 端口。
问题在于,像 accept() 或 bind() 这样的标准 POSIX 函数需要一个“int”作为第一个参数,而它的 WinSock 对应函数使用“SOCKET”。
当编译为 32 位时,一切都很好,因为两者都是 32 位,但在 Win64 下 SOCKET 是 64 位,而 int 仍然是 32 位,它会产生很多编译器警告,如下所示:warning C4244: '=' : conversion from 'SOCKET' to 'int', possible loss of data
我尝试使用 typedef 来解决这个问题:
#ifdef _WIN32
typedef SOCKET sock_t;
#else
typedef int sock_t;
#endif
并在适当的地方用 sock_t 替换“int”。
这很好,直到我到达调用 OpenSSL API 的部分代码。
事实证明,即使在 Win64 上,OpenSSL 也使用整数作为套接字。这看起来很奇怪,所以我开始寻找答案,但我发现的唯一内容是 openssl-dev 邮件列表上的一篇旧帖子,其中提到了评论 e_os.h:
/*
* Even though sizeof(SOCKET) is 8, it's safe to cast it to int, because
* the value constitutes an index in per-process table of limited size
* and not a real pointer.
*/
所以我的问题是:
将 SOCKET 转换为 int 真的安全吗?
我希望看到某种文档证明 SOCKET 的值不能大于 2^32。
提前致谢!
瑞克
【问题讨论】:
-
JPeterMugaas 于 2018 年 9 月创建的 OpenSSL 错误“MINGW-W64 和 SOCKET 类型(不应为 int)#7282”似乎是同一个问题:github.com/openssl/openssl/issues/7282。截至 2021 年 1 月,它目前被忽略。
-
还有这个 2019 版本的相同错误“windows x64 使用 SOCKET(64 位)而不是 int(32 位)作为描述符。BIO_new_socket 采用 int #8169”github.com/openssl/openssl/issues/8169。问题报告者 leleftheriades 决定几乎立即关闭该问题,因为他决定 OpenSSL 维护人员在它真正破坏某些东西之前不会修复该问题。伤心。