如何解决列出适配器地址和IPv4和IPv6的掩码/前缀GetAdaptersAddresses
我的任务是列出本地计算机上的所有单播接口(通过网络掩码(IPv4)或前缀长度(IPv6)的IP地址和子网)。作为Win32 API的新手,我正在阅读GetAdaptersAddress docs。有一个例子很清楚:
- 使用增大的缓冲区大小调用
GetAdaptersAddresses
,直到结果适合分配的内存块为止 - 遍历返回的PIP_ADAPTER_ADDRESSES(
pCurrAddresses
)链接列表:- 遍历PIP_ADAPTER_UNICAST_ADDRESS*
pCurrAddresses->FirstUnicastAddresses
链接列表以检索所有IP地址(SOCKET_ADDRESS及其LPSOCKADDRAddress->lpSockAddr
成员);是sockaddr_in*
或sockaddr_in6*
,具体取决于lpSockAddr.sa_family
(AF_INET
或AF_INET6
)
- 遍历PIP_ADAPTER_UNICAST_ADDRESS*
此刻,我有IP地址。
网络掩码/前缀如何?这似乎就是PIP_ADAPTER_PREFIX_XP(及其SOCKET_ADDRESS Address
字段)的含义。这是另一个链接列表,可以从PIP_ADAPTER_ADDRESSES
到->FirstPrefix
访问。
无奈地,the docs state前缀的排序方式可能与地址的排序方式不同:
此外,链接的IP_ADAPTER_UNICAST_ADDRESS结构指向 由FirstUnicastAddress成员链接到 FirstPrefix成员指向的IP_ADAPTER_PREFIX结构为 由操作系统维护为单独的内部链接列表。 结果,链接的IP_ADAPTER_UNICAST_ADDRESS结构的顺序 FirstUnicastAddress成员指向的指针没有任何 与链接的IP_ADAPTER_PREFIX结构的顺序的关系 由FirstPrefix成员指向。
解决方案是什么?我缺少明显的东西吗?
某些代码(例如zeroMQ)仅对每个适配器使用第一个单播地址和第一个前缀。这样安全吗?我会错过界面吗?
解决方法
IP_ADAPTER_ADDRESSES::FirstPrefix
字段为您提供了分配给适配器的子网/前缀的列表,但是根据文档说明,GetAdaptersAddresses()
不会告诉您适配器上的哪个特定IP地址对应于哪个子网/前缀。因此,要确定每个IP地址的特定子网/前缀,您必须查看IP_ADAPTER_ADDRESSES::FirstUnicastAddresses
列表中的各个条目。
在Windows Vista和更高版本上,IP_ADAPTER_UNICAST_ADDRESS::OnLinkPrefixLength
字段提供AF_INET
地址的IPv4子网掩码的长度以及AF_INET6
地址的IPv6前缀的长度。对于IPv4,如果需要实际的子网掩码,则可以将长度传递给ConvertLengthToIpv4Mask()
函数。
在Windows XP上,OnLinkPrefixLength
字段不存在。幸运的是,可以通过调用GetIpAddrTable()
函数,然后在表中(在AF_INET
字段中查找IP地址)来检索MIB_IPADDRROW::dwAddr
地址的IPv4子网掩码。 MIB_IPADDRROW::dwMask
字段。
如果需要,我不知道如何在XP上获取AF_INET6
地址的IPv6前缀长度。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。