| Summary: |
GETAI(AF_UNSPEC) does not return both IPv6 and IPv4 addresses on first request from /etc/hosts |
| Product: |
[Fedora] Fedora
|
Reporter: |
Siddhesh Poyarekar <spoyarek> |
| Component: |
glibc | Assignee: |
Siddhesh Poyarekar <spoyarek> |
| Status: |
CLOSED
RAWHIDE
|
QA Contact: |
Fedora Extras Quality Assurance <extras-qa> |
| Severity: |
high
|
Docs Contact: |
|
| Priority: |
urgent
|
|
|
| Version: |
rawhide | CC: |
akarlsso, ashankar, codonell, fweimer, jakub, jdonohue, law, mfranc, mnewsome, pfrankli, richard.alpe, schwab, snagar, spoyarek
|
| Target Milestone: |
--- | |
|
| Target Release: |
--- | |
|
| Hardware: |
All | |
|
| OS: |
Linux | |
|
| Whiteboard: |
|
|
Fixed In Version:
|
|
Doc Type:
|
Bug Fix
|
|
Doc Text:
|
|
Story Points:
|
---
|
|
Clone Of:
|
|
Environment:
|
|
|
Last Closed:
|
2013-08-26 10:12:57 UTC
|
Type:
|
Bug
|
|
Regression:
|
---
|
Mount Type:
|
---
|
|
Documentation:
|
---
|
CRM:
|
|
|
Verified Versions:
|
|
Category:
|
---
|
|
oVirt Team:
|
---
|
RHEL 7.3 requirements from Atomic Host:
|
|
|
Cloudforms Team:
|
---
|
Target Upstream Version:
|
|
|
Embargoed:
|
|
| |
GETAI only returns the IPv4 result via nscd on first request via getaddrinfo (PF_UNSPEC) if the host is resolved from /etc/hosts (localhost for example). One may run `nscd -i hosts` and then call getaddrinfo to work around this. How to reproduce: Sample program: #include <stdio.h> #include <stdlib.h> #include <netdb.h> #include <netinet/in.h> #include <sys/socket.h> #include <arpa/inet.h> #include <strings.h> #ifndef NI_MAXHOST #define NI_MAXHOST 1025 #endif int main(int argc, char *argv[]) { struct addrinfo *result; struct addrinfo hints = {0}; struct addrinfo *res; int error; char *host = argv[1]; if (argc > 2) { if (strcasecmp(argv[1], "AF_INET6") == 0) hints.ai_family = AF_INET6; if (strcasecmp(argv[1], "AF_INET") == 0) hints.ai_family = AF_INET; host = argv[2]; } printf("Hints family=%d\n", hints.ai_family); /* resolve the domain name into a list of addresses */ error = getaddrinfo(host, NULL, &hints, &result); if (error != 0) { if (error == EAI_SYSTEM) { perror("getaddrinfo"); } else { fprintf(stderr, "error in getaddrinfo: %s\n", gai_strerror(error)); } exit(EXIT_FAILURE); } /* loop over all returned results and do inverse lookup */ for (res = result; res != NULL; res = res->ai_next) { char hostname[NI_MAXHOST] = ""; char buf[130] = {0}; error = getnameinfo(res->ai_addr, res->ai_addrlen, hostname, NI_MAXHOST, NULL, 0, 0); if (error != 0) { fprintf(stderr, "error in getnameinfo: %s\n", gai_strerror(error)); continue; } if (*hostname != '\0') { if (res->ai_family == AF_INET) inet_ntop(res->ai_family, &((struct sockaddr_in *)res->ai_addr)->sin_addr, buf, sizeof(buf)); if (res->ai_family == AF_INET6) inet_ntop(res->ai_family, &((struct sockaddr_in6 *)res->ai_addr)->sin6_addr, buf, sizeof(buf)); printf("host=%s, family=%d addr=%s\n", hostname, res->ai_family, buf); } } freeaddrinfo(result); printf("\n"); return 0; } Delete nscd cache, Build and run program: # service nscd stop # rm -f /var/db/nscd/* # service nscd start # gcc foo.c # ./a.out localhost Actual Result: Hints family=0 host=localhost, family=2 addr=127.0.0.1 host=localhost, family=2 addr=127.0.0.1 host=localhost, family=2 addr=127.0.0.1 Expected Result: Hints family=0 host=localhost, family=10 addr=::1 host=localhost, family=10 addr=::1 host=localhost, family=10 addr=::1 host=localhost, family=2 addr=127.0.0.1 host=localhost, family=2 addr=127.0.0.1 host=localhost, family=2 addr=127.0.0.1 This is because res_hconf is not initialized in aicache.c.