我使用来自BSD套接字API的getnameinfo()函数从主机获取地址,我希望获得所有可用的地址:
struct addrinfo hints;
memset(&hints, 0, sizeof(hints));
hints.ai_flags = AI_ALL;
struct addrinfo *peer_address;
if (getaddrinfo(argv[1], NULL, &hints, &peer_address)) {
fprintf(stderr, "getaddrinfo() ERROR.\n");
return EXIT_FAILURE;
}
printf("Remote address(es):\n");
struct addrinfo *address = peer_address;
while((address = address->ai_next)) {
char address_buffer[100];
getnameinfo(address->ai_addr, address->ai_addrlen,
address_buffer, sizeof(address_buffer), 0, 0, NI_NUMERICHOST);
printf("\t> %s\n", address_buffer);
}
freeaddrinfo(peer_address);然后构建和运行这段代码,我得到了输出:
$lookup google.com
Remote address(es):
> 172.217.203.100
> 172.217.203.100
> 172.217.203.102
> 172.217.203.102
> 172.217.203.102
.
.
.
> 2607:f8b0:400c:c07::8a
> 2607:f8b0:400c:c07::8a
> 2607:f8b0:400c:c07::8a为什么每个IP地址都打印两三次?
发布于 2020-06-07 23:05:39
您正在看到一个过于未指定的hints变量的效果,它通常会将列表缩小到所要求的范围。
当您询问所有内容时,似乎每个IP地址都有一个条目tcp (SOCK_STREAM)、udp (SOCK_DGRAM)加上IP (SOCK_RAW),但是如果只是查找IP地址--而不是服务--我不认为这有什么用处。
解决这个问题的简单方法是更新提示:
struct addrinfo hints;
memset(&hints, 0, sizeof hints);
hints.ai_flags = AI_ALL;
hints.ai_socktype = SOCK_RAW; // ADD ME另外,循环确实跳过了第一个条目,因此另一个选项可能是:
for (struct addrinfo *address = peer_address
; address != 0
; address = address->ai_next )
{
// do stuff有帮助的参考资料:What's the "hints" mean for the addrinfo name in socket programming
https://stackoverflow.com/questions/62252397
复制相似问题