aboutsummaryrefslogtreecommitdiff
path: root/sysdeps/posix/getaddrinfo.c
diff options
context:
space:
mode:
authorUlrich Drepper <drepper@redhat.com>2002-08-29 08:51:26 +0000
committerUlrich Drepper <drepper@redhat.com>2002-08-29 08:51:26 +0000
commit160d067b046c2ee3296853129d1ea9a99156e2b8 (patch)
tree77134f8afec02ad11c0582ac323ef25c0bf04975 /sysdeps/posix/getaddrinfo.c
parent01beb5b9ff8fb38f6517837b42eea8f5ff7060d9 (diff)
downloadglibc-160d067b046c2ee3296853129d1ea9a99156e2b8.tar
glibc-160d067b046c2ee3296853129d1ea9a99156e2b8.tar.gz
glibc-160d067b046c2ee3296853129d1ea9a99156e2b8.tar.bz2
glibc-160d067b046c2ee3296853129d1ea9a99156e2b8.zip
(gaih_inet): Fix code to determine canonical name.
Diffstat (limited to 'sysdeps/posix/getaddrinfo.c')
-rw-r--r--sysdeps/posix/getaddrinfo.c54
1 files changed, 41 insertions, 13 deletions
diff --git a/sysdeps/posix/getaddrinfo.c b/sysdeps/posix/getaddrinfo.c
index 5e09a9f765..2dc5e90a32 100644
--- a/sysdeps/posix/getaddrinfo.c
+++ b/sysdeps/posix/getaddrinfo.c
@@ -564,8 +564,6 @@ gaih_inet (const char *name, const struct gaih_service *service,
/*
buffer is the size of an unformatted IPv6 address in printable format.
*/
- char buffer[sizeof "ffff:ffff:ffff:ffff:ffff:ffff:255.255.255.255"];
-
while (at2 != NULL)
{
if (req->ai_flags & AI_CANONNAME)
@@ -582,9 +580,6 @@ gaih_inet (const char *name, const struct gaih_service *service,
tmpbuflen *= 2;
tmpbuf = __alloca (tmpbuflen);
- if (tmpbuf == NULL)
- return -EAI_MEMORY;
-
rc = __gethostbyaddr_r (at2->addr,
((at2->family == AF_INET6)
? sizeof(struct in6_addr)
@@ -601,10 +596,42 @@ gaih_inet (const char *name, const struct gaih_service *service,
return -EAI_SYSTEM;
}
- if (h == NULL)
- c = inet_ntop (at2->family, at2->addr, buffer, sizeof(buffer));
- else
+ if (h != NULL)
c = h->h_name;
+ else
+ {
+ /* We have to try to get the canonical in some other
+ way. If we are looking for either AF_INET or
+ AF_INET6 try the other line. */
+ if (req->ai_family == AF_UNSPEC)
+ {
+ struct addrinfo *p = NULL;
+ struct addrinfo **end = &p;
+ struct addrinfo localreq = *req;
+ struct addrinfo *runp;
+
+ localreq.ai_family = AF_INET + AF_INET6 - at2->family;
+ (void) gaih_inet (name, service, &localreq, end);
+
+ runp = p;
+ while (runp != NULL)
+ {
+ if (p->ai_canonname != name)
+ {
+ c = strdupa (p->ai_canonname);
+ break;
+ }
+ runp = runp->ai_next;
+ }
+
+ freeaddrinfo (p);
+ }
+
+ /* If this code is used the missing canonical name is
+ substituted with the name passed in by the user. */
+ if (c == NULL)
+ c = name;
+ }
if (c == NULL)
return GAIH_OKIFUNSPEC | -EAI_NONAME;
@@ -758,10 +785,12 @@ getaddrinfo (const char *name, const char *service,
last_i = i;
if (hints->ai_family == AF_UNSPEC && (i & GAIH_OKIFUNSPEC))
- continue;
+ {
+ ++g;
+ continue;
+ }
- if (p)
- freeaddrinfo (p);
+ freeaddrinfo (p);
return -(i & GAIH_EAI);
}
@@ -784,8 +813,7 @@ getaddrinfo (const char *name, const char *service,
if (pai == NULL && last_i == 0)
return 0;
- if (p)
- freeaddrinfo (p);
+ freeaddrinfo (p);
return last_i ? -(last_i & GAIH_EAI) : EAI_NONAME;
}