Update.
[glibc.git] / sysdeps / posix / getaddrinfo.c
blob3ffa329f732aa2364fd3c602e9577be6b07c045b
1 /* The Inner Net License, Version 2.00
3 The author(s) grant permission for redistribution and use in source and
4 binary forms, with or without modification, of the software and documentation
5 provided that the following conditions are met:
7 0. If you receive a version of the software that is specifically labelled
8 as not being for redistribution (check the version message and/or README),
9 you are not permitted to redistribute that version of the software in any
10 way or form.
11 1. All terms of the all other applicable copyrights and licenses must be
12 followed.
13 2. Redistributions of source code must retain the authors' copyright
14 notice(s), this list of conditions, and the following disclaimer.
15 3. Redistributions in binary form must reproduce the authors' copyright
16 notice(s), this list of conditions, and the following disclaimer in the
17 documentation and/or other materials provided with the distribution.
18 4. [The copyright holder has authorized the removal of this clause.]
19 5. Neither the name(s) of the author(s) nor the names of its contributors
20 may be used to endorse or promote products derived from this software
21 without specific prior written permission.
23 THIS SOFTWARE IS PROVIDED BY ITS AUTHORS AND CONTRIBUTORS ``AS IS'' AND ANY
24 EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
25 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
26 DISCLAIMED. IN NO EVENT SHALL THE AUTHORS OR CONTRIBUTORS BE LIABLE FOR ANY
27 DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
28 (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
29 LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
30 ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
31 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
32 SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
34 If these license terms cause you a real problem, contact the author. */
36 /* This software is Copyright 1996 by Craig Metz, All Rights Reserved. */
38 #include <assert.h>
39 #include <errno.h>
40 #include <ifaddrs.h>
41 #include <netdb.h>
42 #include <resolv.h>
43 #include <stdbool.h>
44 #include <stdio.h>
45 #include <stdlib.h>
46 #include <string.h>
47 #include <unistd.h>
48 #include <arpa/inet.h>
49 #include <sys/socket.h>
50 #include <netinet/in.h>
51 #include <sys/types.h>
52 #include <sys/un.h>
53 #include <sys/utsname.h>
54 #include <net/if.h>
55 #include <nsswitch.h>
56 #include <not-cancel.h>
58 #ifdef HAVE_LIBIDN
59 extern int __idna_to_ascii_lz (const char *input, char **output, int flags);
60 extern int __idna_to_unicode_lzlz (const char *input, char **output,
61 int flags);
62 # include <libidn/idna.h>
63 #endif
65 #define GAIH_OKIFUNSPEC 0x0100
66 #define GAIH_EAI ~(GAIH_OKIFUNSPEC)
68 #ifndef UNIX_PATH_MAX
69 #define UNIX_PATH_MAX 108
70 #endif
72 struct gaih_service
74 const char *name;
75 int num;
78 struct gaih_servtuple
80 struct gaih_servtuple *next;
81 int socktype;
82 int protocol;
83 int port;
86 static const struct gaih_servtuple nullserv;
88 struct gaih_addrtuple
90 struct gaih_addrtuple *next;
91 int family;
92 uint32_t addr[4];
93 uint32_t scopeid;
96 struct gaih_typeproto
98 int socktype;
99 int protocol;
100 char name[4];
101 int protoflag;
104 /* Values for `protoflag'. */
105 #define GAI_PROTO_NOSERVICE 1
106 #define GAI_PROTO_PROTOANY 2
108 static const struct gaih_typeproto gaih_inet_typeproto[] =
110 { 0, 0, "", 0 },
111 { SOCK_STREAM, IPPROTO_TCP, "tcp", 0 },
112 { SOCK_DGRAM, IPPROTO_UDP, "udp", 0 },
113 { SOCK_RAW, 0, "raw", GAI_PROTO_PROTOANY|GAI_PROTO_NOSERVICE },
114 { 0, 0, "", 0 }
117 struct gaih
119 int family;
120 int (*gaih)(const char *name, const struct gaih_service *service,
121 const struct addrinfo *req, struct addrinfo **pai);
124 static const struct addrinfo default_hints =
126 .ai_flags = AI_DEFAULT,
127 .ai_family = PF_UNSPEC,
128 .ai_socktype = 0,
129 .ai_protocol = 0,
130 .ai_addrlen = 0,
131 .ai_addr = NULL,
132 .ai_canonname = NULL,
133 .ai_next = NULL
137 #if 0
138 /* Using Unix sockets this way is a security risk. */
139 static int
140 gaih_local (const char *name, const struct gaih_service *service,
141 const struct addrinfo *req, struct addrinfo **pai)
143 struct utsname utsname;
145 if ((name != NULL) && (req->ai_flags & AI_NUMERICHOST))
146 return GAIH_OKIFUNSPEC | -EAI_NONAME;
148 if ((name != NULL) || (req->ai_flags & AI_CANONNAME))
149 if (uname (&utsname) < 0)
150 return -EAI_SYSTEM;
152 if (name != NULL)
154 if (strcmp(name, "localhost") &&
155 strcmp(name, "local") &&
156 strcmp(name, "unix") &&
157 strcmp(name, utsname.nodename))
158 return GAIH_OKIFUNSPEC | -EAI_NONAME;
161 if (req->ai_protocol || req->ai_socktype)
163 const struct gaih_typeproto *tp = gaih_inet_typeproto + 1;
165 while (tp->name[0]
166 && ((tp->protoflag & GAI_PROTO_NOSERVICE) != 0
167 || (req->ai_socktype != 0 && req->ai_socktype != tp->socktype)
168 || (req->ai_protocol != 0
169 && !(tp->protoflag & GAI_PROTO_PROTOANY)
170 && req->ai_protocol != tp->protocol)))
171 ++tp;
173 if (! tp->name[0])
175 if (req->ai_socktype)
176 return (GAIH_OKIFUNSPEC | -EAI_SOCKTYPE);
177 else
178 return (GAIH_OKIFUNSPEC | -EAI_SERVICE);
182 *pai = malloc (sizeof (struct addrinfo) + sizeof (struct sockaddr_un)
183 + ((req->ai_flags & AI_CANONNAME)
184 ? (strlen(utsname.nodename) + 1): 0));
185 if (*pai == NULL)
186 return -EAI_MEMORY;
188 (*pai)->ai_next = NULL;
189 (*pai)->ai_flags = req->ai_flags;
190 (*pai)->ai_family = AF_LOCAL;
191 (*pai)->ai_socktype = req->ai_socktype ? req->ai_socktype : SOCK_STREAM;
192 (*pai)->ai_protocol = req->ai_protocol;
193 (*pai)->ai_addrlen = sizeof (struct sockaddr_un);
194 (*pai)->ai_addr = (void *) (*pai) + sizeof (struct addrinfo);
196 #if SALEN
197 ((struct sockaddr_un *) (*pai)->ai_addr)->sun_len =
198 sizeof (struct sockaddr_un);
199 #endif /* SALEN */
201 ((struct sockaddr_un *)(*pai)->ai_addr)->sun_family = AF_LOCAL;
202 memset(((struct sockaddr_un *)(*pai)->ai_addr)->sun_path, 0, UNIX_PATH_MAX);
204 if (service)
206 struct sockaddr_un *sunp = (struct sockaddr_un *) (*pai)->ai_addr;
208 if (strchr (service->name, '/') != NULL)
210 if (strlen (service->name) >= sizeof (sunp->sun_path))
211 return GAIH_OKIFUNSPEC | -EAI_SERVICE;
213 strcpy (sunp->sun_path, service->name);
215 else
217 if (strlen (P_tmpdir "/") + 1 + strlen (service->name) >=
218 sizeof (sunp->sun_path))
219 return GAIH_OKIFUNSPEC | -EAI_SERVICE;
221 __stpcpy (__stpcpy (sunp->sun_path, P_tmpdir "/"), service->name);
224 else
226 /* This is a dangerous use of the interface since there is a time
227 window between the test for the file and the actual creation
228 (done by the caller) in which a file with the same name could
229 be created. */
230 char *buf = ((struct sockaddr_un *) (*pai)->ai_addr)->sun_path;
232 if (__builtin_expect (__path_search (buf, L_tmpnam, NULL, NULL, 0),
233 0) != 0
234 || __builtin_expect (__gen_tempname (buf, __GT_NOCREATE), 0) != 0)
235 return -EAI_SYSTEM;
238 if (req->ai_flags & AI_CANONNAME)
239 (*pai)->ai_canonname = strcpy ((char *) *pai + sizeof (struct addrinfo)
240 + sizeof (struct sockaddr_un),
241 utsname.nodename);
242 else
243 (*pai)->ai_canonname = NULL;
244 return 0;
246 #endif /* 0 */
248 static int
249 gaih_inet_serv (const char *servicename, const struct gaih_typeproto *tp,
250 const struct addrinfo *req, struct gaih_servtuple *st)
252 struct servent *s;
253 size_t tmpbuflen = 1024;
254 struct servent ts;
255 char *tmpbuf;
256 int r;
260 tmpbuf = __alloca (tmpbuflen);
262 r = __getservbyname_r (servicename, tp->name, &ts, tmpbuf, tmpbuflen,
263 &s);
264 if (r != 0 || s == NULL)
266 if (r == ERANGE)
267 tmpbuflen *= 2;
268 else
269 return GAIH_OKIFUNSPEC | -EAI_SERVICE;
272 while (r);
274 st->next = NULL;
275 st->socktype = tp->socktype;
276 st->protocol = ((tp->protoflag & GAI_PROTO_PROTOANY)
277 ? req->ai_protocol : tp->protocol);
278 st->port = s->s_port;
280 return 0;
283 #define gethosts(_family, _type) \
285 int i; \
286 int herrno; \
287 struct hostent th; \
288 no_data = 0; \
289 while (1) { \
290 rc = 0; \
291 status = DL_CALL_FCT (fct, (name, _family, &th, tmpbuf, \
292 tmpbuflen, &rc, &herrno)); \
293 if (rc != ERANGE || herrno != NETDB_INTERNAL) \
294 break; \
295 tmpbuf = extend_alloca (tmpbuf, tmpbuflen, 2 * tmpbuflen); \
297 if (status == NSS_STATUS_SUCCESS && rc == 0) \
298 h = &th; \
299 else \
300 h = NULL; \
301 if (rc != 0) \
303 if (herrno == NETDB_INTERNAL) \
305 __set_h_errno (herrno); \
306 return -EAI_SYSTEM; \
308 if (herrno == TRY_AGAIN) \
309 no_data = EAI_AGAIN; \
310 else \
311 no_data = herrno == NO_DATA; \
313 else if (h != NULL) \
315 for (i = 0; h->h_addr_list[i]; i++) \
317 if (*pat == NULL) \
319 *pat = __alloca (sizeof (struct gaih_addrtuple)); \
320 (*pat)->scopeid = 0; \
322 uint32_t *addr = (*pat)->addr; \
323 (*pat)->next = NULL; \
324 if (_family == AF_INET && req->ai_family == AF_INET6) \
326 (*pat)->family = AF_INET6; \
327 addr[3] = *(uint32_t *) h->h_addr_list[i]; \
328 addr[2] = htonl (0xffff); \
329 addr[1] = 0; \
330 addr[0] = 0; \
332 else \
334 (*pat)->family = _family; \
335 memcpy (addr, h->h_addr_list[i], sizeof(_type)); \
337 pat = &((*pat)->next); \
340 if (_family == AF_INET6 && i > 0) \
341 got_ipv6 = true; \
346 typedef enum nss_status (*nss_gethostbyname2_r)
347 (const char *name, int af, struct hostent *host,
348 char *buffer, size_t buflen, int *errnop,
349 int *h_errnop);
350 typedef enum nss_status (*nss_getcanonname_r)
351 (const char *name, char *buffer, size_t buflen, char **result,
352 int *errnop, int *h_errnop);
353 extern service_user *__nss_hosts_database attribute_hidden;
355 static int
356 gaih_inet (const char *name, const struct gaih_service *service,
357 const struct addrinfo *req, struct addrinfo **pai)
359 const struct gaih_typeproto *tp = gaih_inet_typeproto;
360 struct gaih_servtuple *st = (struct gaih_servtuple *) &nullserv;
361 struct gaih_addrtuple *at = NULL;
362 int rc;
363 bool got_ipv6 = false;
364 const char *canon = NULL;
365 const char *orig_name = name;
367 if (req->ai_protocol || req->ai_socktype)
369 ++tp;
371 while (tp->name[0]
372 && ((req->ai_socktype != 0 && req->ai_socktype != tp->socktype)
373 || (req->ai_protocol != 0
374 && !(tp->protoflag & GAI_PROTO_PROTOANY)
375 && req->ai_protocol != tp->protocol)))
376 ++tp;
378 if (! tp->name[0])
380 if (req->ai_socktype)
381 return (GAIH_OKIFUNSPEC | -EAI_SOCKTYPE);
382 else
383 return (GAIH_OKIFUNSPEC | -EAI_SERVICE);
387 if (service != NULL)
389 if ((tp->protoflag & GAI_PROTO_NOSERVICE) != 0)
390 return (GAIH_OKIFUNSPEC | -EAI_SERVICE);
392 if (service->num < 0)
394 if (tp->name[0])
396 st = (struct gaih_servtuple *)
397 __alloca (sizeof (struct gaih_servtuple));
399 if ((rc = gaih_inet_serv (service->name, tp, req, st)))
400 return rc;
402 else
404 struct gaih_servtuple **pst = &st;
405 for (tp++; tp->name[0]; tp++)
407 struct gaih_servtuple *newp;
409 if ((tp->protoflag & GAI_PROTO_NOSERVICE) != 0)
410 continue;
412 if (req->ai_socktype != 0
413 && req->ai_socktype != tp->socktype)
414 continue;
415 if (req->ai_protocol != 0
416 && !(tp->protoflag & GAI_PROTO_PROTOANY)
417 && req->ai_protocol != tp->protocol)
418 continue;
420 newp = (struct gaih_servtuple *)
421 __alloca (sizeof (struct gaih_servtuple));
423 if ((rc = gaih_inet_serv (service->name, tp, req, newp)))
425 if (rc & GAIH_OKIFUNSPEC)
426 continue;
427 return rc;
430 *pst = newp;
431 pst = &(newp->next);
433 if (st == (struct gaih_servtuple *) &nullserv)
434 return (GAIH_OKIFUNSPEC | -EAI_SERVICE);
437 else
439 st = __alloca (sizeof (struct gaih_servtuple));
440 st->next = NULL;
441 st->socktype = tp->socktype;
442 st->protocol = ((tp->protoflag & GAI_PROTO_PROTOANY)
443 ? req->ai_protocol : tp->protocol);
444 st->port = htons (service->num);
447 else if (req->ai_socktype || req->ai_protocol)
449 st = __alloca (sizeof (struct gaih_servtuple));
450 st->next = NULL;
451 st->socktype = tp->socktype;
452 st->protocol = ((tp->protoflag & GAI_PROTO_PROTOANY)
453 ? req->ai_protocol : tp->protocol);
454 st->port = 0;
456 else
458 /* Neither socket type nor protocol is set. Return all socket types
459 we know about. */
460 struct gaih_servtuple **lastp = &st;
461 for (++tp; tp->name[0]; ++tp)
463 struct gaih_servtuple *newp;
465 newp = __alloca (sizeof (struct gaih_servtuple));
466 newp->next = NULL;
467 newp->socktype = tp->socktype;
468 newp->protocol = tp->protocol;
469 newp->port = 0;
471 *lastp = newp;
472 lastp = &newp->next;
476 if (name != NULL)
478 at = __alloca (sizeof (struct gaih_addrtuple));
480 at->family = AF_UNSPEC;
481 at->scopeid = 0;
482 at->next = NULL;
484 #ifdef HAVE_LIBIDN
485 if (req->ai_flags & AI_IDN)
487 int idn_flags = 0;
488 if (req->ai_flags & AI_IDN_ALLOW_UNASSIGNED)
489 idn_flags |= IDNA_ALLOW_UNASSIGNED;
490 if (req->ai_flags & AI_IDN_USE_STD3_ASCII_RULES)
491 idn_flags |= IDNA_USE_STD3_ASCII_RULES;
493 char *p = NULL;
494 rc = __idna_to_ascii_lz (name, &p, idn_flags);
495 if (rc != IDNA_SUCCESS)
497 if (rc == IDNA_MALLOC_ERROR)
498 return -EAI_MEMORY;
499 if (rc == IDNA_DLOPEN_ERROR)
500 return -EAI_SYSTEM;
501 return -EAI_IDN_ENCODE;
503 /* In case the output string is the same as the input string
504 no new string has been allocated. */
505 if (p != name)
507 name = strdupa (p);
508 free (p);
511 #endif
513 if (__inet_aton (name, (struct in_addr *) at->addr) != 0)
515 if (req->ai_family == AF_UNSPEC || req->ai_family == AF_INET)
516 at->family = AF_INET;
517 else if (req->ai_family == AF_INET6 && req->ai_flags & AI_V4MAPPED)
519 at->addr[3] = at->addr[0];
520 at->addr[2] = htonl (0xffff);
521 at->addr[1] = 0;
522 at->addr[0] = 0;
523 at->family = AF_INET6;
525 else
526 return -EAI_ADDRFAMILY;
529 if (at->family == AF_UNSPEC)
531 char *namebuf = strdupa (name);
532 char *scope_delim;
534 scope_delim = strchr (namebuf, SCOPE_DELIMITER);
535 if (scope_delim != NULL)
536 *scope_delim = '\0';
538 if (inet_pton (AF_INET6, namebuf, at->addr) > 0)
540 if (req->ai_family == AF_UNSPEC || req->ai_family == AF_INET6)
541 at->family = AF_INET6;
542 else if (req->ai_family == AF_INET
543 && IN6_IS_ADDR_V4MAPPED (at->addr))
545 at->addr[0] = at->addr[3];
546 at->family = AF_INET;
548 else
549 return -EAI_ADDRFAMILY;
551 if (scope_delim != NULL)
553 int try_numericscope = 0;
554 if (IN6_IS_ADDR_LINKLOCAL (at->addr)
555 || IN6_IS_ADDR_MC_LINKLOCAL (at->addr))
557 at->scopeid = if_nametoindex (scope_delim + 1);
558 if (at->scopeid == 0)
559 try_numericscope = 1;
561 else
562 try_numericscope = 1;
564 if (try_numericscope != 0)
566 char *end;
567 assert (sizeof (uint32_t) <= sizeof (unsigned long));
568 at->scopeid = (uint32_t) strtoul (scope_delim + 1, &end,
569 10);
570 if (*end != '\0')
571 return GAIH_OKIFUNSPEC | -EAI_NONAME;
577 if (at->family == AF_UNSPEC && (req->ai_flags & AI_NUMERICHOST) == 0)
579 struct hostent *h = NULL;
580 struct gaih_addrtuple **pat = &at;
581 int no_data = 0;
582 int no_inet6_data = 0;
583 service_user *nip = NULL;
584 enum nss_status inet6_status = NSS_STATUS_UNAVAIL;
585 enum nss_status status = NSS_STATUS_UNAVAIL;
586 int no_more;
587 nss_gethostbyname2_r fct;
588 int old_res_options;
589 size_t tmpbuflen = 512;
590 char *tmpbuf = alloca (tmpbuflen);
592 if (__nss_hosts_database != NULL)
594 no_more = 0;
595 nip = __nss_hosts_database;
597 else
598 no_more = __nss_database_lookup ("hosts", NULL,
599 "dns [!UNAVAIL=return] files",
600 &nip);
602 if (__res_maybe_init (&_res, 0) == -1)
603 no_more = 1;
605 /* If we are looking for both IPv4 and IPv6 address we don't
606 want the lookup functions to automatically promote IPv4
607 addresses to IPv6 addresses. Currently this is decided
608 by setting the RES_USE_INET6 bit in _res.options. */
609 old_res_options = _res.options;
610 _res.options &= ~RES_USE_INET6;
612 while (!no_more)
614 fct = __nss_lookup_function (nip, "gethostbyname2_r");
616 if (fct != NULL)
618 if (req->ai_family == AF_INET6
619 || req->ai_family == AF_UNSPEC)
621 gethosts (AF_INET6, struct in6_addr);
622 no_inet6_data = no_data;
623 inet6_status = status;
625 if (req->ai_family == AF_INET
626 || req->ai_family == AF_UNSPEC
627 || (req->ai_family == AF_INET6
628 && (req->ai_flags & AI_V4MAPPED)
629 /* Avoid generating the mapped addresses if we
630 know we are not going to need them. */
631 && ((req->ai_flags & AI_ALL) || !got_ipv6)))
633 gethosts (AF_INET, struct in_addr);
635 if (req->ai_family == AF_INET)
637 no_inet6_data = no_data;
638 inet6_status = status;
642 /* If we found one address for AF_INET or AF_INET6,
643 don't continue the search. */
644 if (inet6_status == NSS_STATUS_SUCCESS
645 || status == NSS_STATUS_SUCCESS)
647 if ((req->ai_flags & AI_CANONNAME) != 0)
649 /* If we need the canonical name, get it
650 from the same service as the result. */
651 nss_getcanonname_r cfct;
652 int herrno;
654 cfct = __nss_lookup_function (nip, "getcanonname_r");
655 if (cfct != NULL)
657 const size_t max_fqdn_len = 256;
658 char *buf = alloca (max_fqdn_len);
659 char *s;
661 if (DL_CALL_FCT (cfct, (h->h_name ?: name, buf,
662 max_fqdn_len, &s, &rc,
663 &herrno))
664 == NSS_STATUS_SUCCESS)
665 canon = s;
666 else
667 /* Set to name now to avoid using
668 gethostbyaddr. */
669 canon = name;
673 break;
676 /* We can have different states for AF_INET and
677 AF_INET6. Try to find a useful one for both. */
678 if (inet6_status == NSS_STATUS_TRYAGAIN)
679 status = NSS_STATUS_TRYAGAIN;
680 else if (status == NSS_STATUS_UNAVAIL &&
681 inet6_status != NSS_STATUS_UNAVAIL)
682 status = inet6_status;
685 if (nss_next_action (nip, status) == NSS_ACTION_RETURN)
686 break;
688 if (nip->next == NULL)
689 no_more = -1;
690 else
691 nip = nip->next;
694 _res.options = old_res_options;
696 if (no_data != 0 && no_inet6_data != 0)
698 /* If both requests timed out report this. */
699 if (no_data == EAI_AGAIN && no_inet6_data == EAI_AGAIN)
700 return -EAI_AGAIN;
702 /* We made requests but they turned out no data. The name
703 is known, though. */
704 return (GAIH_OKIFUNSPEC | -EAI_NODATA);
708 if (at->family == AF_UNSPEC)
709 return (GAIH_OKIFUNSPEC | -EAI_NONAME);
711 else
713 struct gaih_addrtuple *atr;
714 atr = at = __alloca (sizeof (struct gaih_addrtuple));
715 memset (at, '\0', sizeof (struct gaih_addrtuple));
717 if (req->ai_family == AF_UNSPEC)
719 at->next = __alloca (sizeof (struct gaih_addrtuple));
720 memset (at->next, '\0', sizeof (struct gaih_addrtuple));
723 if (req->ai_family == AF_UNSPEC || req->ai_family == AF_INET6)
725 at->family = AF_INET6;
726 if ((req->ai_flags & AI_PASSIVE) == 0)
727 memcpy (at->addr, &in6addr_loopback, sizeof (struct in6_addr));
728 atr = at->next;
731 if (req->ai_family == AF_UNSPEC || req->ai_family == AF_INET)
733 atr->family = AF_INET;
734 if ((req->ai_flags & AI_PASSIVE) == 0)
735 atr->addr[0] = htonl (INADDR_LOOPBACK);
739 if (pai == NULL)
740 return 0;
743 struct gaih_servtuple *st2;
744 struct gaih_addrtuple *at2 = at;
745 size_t socklen;
746 sa_family_t family;
749 buffer is the size of an unformatted IPv6 address in printable format.
751 while (at2 != NULL)
753 /* Only the first entry gets the canonical name. */
754 if (at2 == at && (req->ai_flags & AI_CANONNAME) != 0)
756 if (canon == NULL)
758 struct hostent *h = NULL;
759 int herrno;
760 struct hostent th;
761 size_t tmpbuflen = 512;
762 char *tmpbuf = NULL;
766 tmpbuf = extend_alloca (tmpbuf, tmpbuflen, tmpbuflen * 2);
767 rc = __gethostbyaddr_r (at2->addr,
768 ((at2->family == AF_INET6)
769 ? sizeof (struct in6_addr)
770 : sizeof (struct in_addr)),
771 at2->family, &th, tmpbuf,
772 tmpbuflen, &h, &herrno);
774 while (rc == ERANGE && herrno == NETDB_INTERNAL);
776 if (rc != 0 && herrno == NETDB_INTERNAL)
778 __set_h_errno (herrno);
779 return -EAI_SYSTEM;
782 if (h != NULL)
783 canon = h->h_name;
784 else
786 assert (orig_name != NULL);
787 /* If the canonical name cannot be determined, use
788 the passed in string. */
789 canon = orig_name;
793 #ifdef HAVE_LIBIDN
794 if (req->ai_flags & AI_CANONIDN)
796 int idn_flags = 0;
797 if (req->ai_flags & AI_IDN_ALLOW_UNASSIGNED)
798 idn_flags |= IDNA_ALLOW_UNASSIGNED;
799 if (req->ai_flags & AI_IDN_USE_STD3_ASCII_RULES)
800 idn_flags |= IDNA_USE_STD3_ASCII_RULES;
802 char *out;
803 int rc = __idna_to_unicode_lzlz (canon, &out, idn_flags);
804 if (rc != IDNA_SUCCESS)
806 if (rc == IDNA_MALLOC_ERROR)
807 return -EAI_MEMORY;
808 if (rc == IDNA_DLOPEN_ERROR)
809 return -EAI_SYSTEM;
810 return -EAI_IDN_ENCODE;
812 /* In case the output string is the same as the input
813 string no new string has been allocated. Otherwise
814 make a copy. */
815 if (out == canon)
816 goto make_copy;
818 else
819 #endif
821 #ifdef HAVE_LIBIDN
822 make_copy:
823 #endif
824 canon = strdup (canon);
825 if (canon == NULL)
826 return -EAI_MEMORY;
830 if (at2->family == AF_INET6)
832 family = AF_INET6;
833 socklen = sizeof (struct sockaddr_in6);
835 /* If we looked up IPv4 mapped address discard them here if
836 the caller isn't interested in all address and we have
837 found at least one IPv6 address. */
838 if (got_ipv6
839 && (req->ai_flags & (AI_V4MAPPED|AI_ALL)) == AI_V4MAPPED
840 && IN6_IS_ADDR_V4MAPPED (at2->addr))
841 goto ignore;
843 else
845 family = AF_INET;
846 socklen = sizeof (struct sockaddr_in);
849 for (st2 = st; st2 != NULL; st2 = st2->next)
851 struct addrinfo *ai;
852 ai = *pai = malloc (sizeof (struct addrinfo) + socklen);
853 if (ai == NULL)
854 return -EAI_MEMORY;
856 ai->ai_flags = req->ai_flags;
857 ai->ai_family = family;
858 ai->ai_socktype = st2->socktype;
859 ai->ai_protocol = st2->protocol;
860 ai->ai_addrlen = socklen;
861 ai->ai_addr = (void *) (ai + 1);
863 /* We only add the canonical name once. */
864 ai->ai_canonname = (char *) canon;
865 canon = NULL;
867 #if SALEN
868 ai->ai_addr->sa_len = socklen;
869 #endif /* SALEN */
870 ai->ai_addr->sa_family = family;
872 if (family == AF_INET6)
874 struct sockaddr_in6 *sin6p =
875 (struct sockaddr_in6 *) ai->ai_addr;
877 sin6p->sin6_port = st2->port;
878 sin6p->sin6_flowinfo = 0;
879 memcpy (&sin6p->sin6_addr,
880 at2->addr, sizeof (struct in6_addr));
881 sin6p->sin6_scope_id = at2->scopeid;
883 else
885 struct sockaddr_in *sinp =
886 (struct sockaddr_in *) ai->ai_addr;
887 sinp->sin_port = st2->port;
888 memcpy (&sinp->sin_addr,
889 at2->addr, sizeof (struct in_addr));
890 memset (sinp->sin_zero, '\0', sizeof (sinp->sin_zero));
893 pai = &(ai->ai_next);
895 *pai = NULL;
897 ignore:
898 at2 = at2->next;
901 return 0;
904 static struct gaih gaih[] =
906 { PF_INET6, gaih_inet },
907 { PF_INET, gaih_inet },
908 #if 0
909 { PF_LOCAL, gaih_local },
910 #endif
911 { PF_UNSPEC, NULL }
914 struct sort_result
916 struct addrinfo *dest_addr;
917 struct sockaddr_storage source_addr;
918 bool got_source_addr;
922 static int
923 get_scope (const struct sockaddr_storage *ss)
925 int scope;
926 if (ss->ss_family == PF_INET6)
928 const struct sockaddr_in6 *in6 = (const struct sockaddr_in6 *) ss;
930 if (! IN6_IS_ADDR_MULTICAST (&in6->sin6_addr))
932 if (IN6_IS_ADDR_LINKLOCAL (&in6->sin6_addr))
933 scope = 2;
934 else if (IN6_IS_ADDR_SITELOCAL (&in6->sin6_addr))
935 scope = 5;
936 else
937 /* XXX Is this the correct default behavior? */
938 scope = 14;
940 else
941 scope = in6->sin6_addr.s6_addr[1] & 0xf;
943 else if (ss->ss_family == PF_INET)
945 const struct sockaddr_in *in = (const struct sockaddr_in *) ss;
946 const uint8_t *addr = (const uint8_t *) &in->sin_addr;
948 /* RFC 3484 specifies how to map IPv6 addresses to scopes.
949 169.254/16 and 127/8 are link-local. */
950 if ((addr[0] == 169 && addr[1] == 254) || addr[0] == 127)
951 scope = 2;
952 else if (addr[0] == 10 || (addr[0] == 172 && addr[1] == 16)
953 || (addr[0] == 192 && addr[1] == 168))
954 scope = 5;
955 else
956 scope = 14;
958 else
959 /* XXX What is a good default? */
960 scope = 15;
962 return scope;
966 /* XXX The system administrator should be able to install other
967 tables. We need to make this configurable. The problem is that
968 the kernel is also involved since it needs the same table. */
969 static const struct prefixlist
971 struct in6_addr prefix;
972 unsigned int bits;
973 int val;
974 } default_labels[] =
976 /* See RFC 3484 for the details. */
977 { { .in6_u = { .u6_addr16 = { 0x0000, 0x0000, 0x0000, 0x0000,
978 0x0000, 0x0000, 0x0000, 0x0001 } } },
979 128, 0 },
980 { { .in6_u = { .u6_addr16 = { 0x2002, 0x0000, 0x0000, 0x0000,
981 0x0000, 0x0000, 0x0000, 0x0000 } } },
982 16, 2 },
983 { { .in6_u = { .u6_addr16 = { 0x0000, 0x0000, 0x0000, 0x0000,
984 0x0000, 0x0000, 0x0000, 0x0000 } } },
985 96, 3 },
986 { { .in6_u = { .u6_addr16 = { 0x0000, 0x0000, 0x0000, 0x0000,
987 0x0000, 0xffff, 0x0000, 0x0000 } } },
988 96, 4 },
989 { { .in6_u = { .u6_addr16 = { 0x0000, 0x0000, 0x0000, 0x0000,
990 0x0000, 0x0000, 0x0000, 0x0000 } } },
991 0, 1 }
995 static const struct prefixlist default_precedence[] =
997 /* See RFC 3484 for the details. */
998 { { .in6_u = { .u6_addr16 = { 0x0000, 0x0000, 0x0000, 0x0000,
999 0x0000, 0x0000, 0x0000, 0x0001 } } },
1000 128, 50 },
1001 { { .in6_u = { .u6_addr16 = { 0x2002, 0x0000, 0x0000, 0x0000,
1002 0x0000, 0x0000, 0x0000, 0x0000 } } },
1003 16, 30 },
1004 { { .in6_u = { .u6_addr16 = { 0x0000, 0x0000, 0x0000, 0x0000,
1005 0x0000, 0x0000, 0x0000, 0x0000 } } },
1006 96, 20 },
1007 { { .in6_u = { .u6_addr16 = { 0x0000, 0x0000, 0x0000, 0x0000,
1008 0x0000, 0xffff, 0x0000, 0x0000 } } },
1009 96, 10 },
1010 { { .in6_u = { .u6_addr16 = { 0x0000, 0x0000, 0x0000, 0x0000,
1011 0x0000, 0x0000, 0x0000, 0x0000 } } },
1012 0, 40 }
1016 static int
1017 match_prefix (const struct sockaddr_storage *ss, const struct prefixlist *list,
1018 int default_val)
1020 int idx;
1021 struct sockaddr_in6 in6_mem;
1022 const struct sockaddr_in6 *in6;
1024 if (ss->ss_family == PF_INET6)
1025 in6 = (const struct sockaddr_in6 *) ss;
1026 else if (ss->ss_family == PF_INET)
1028 const struct sockaddr_in *in = (const struct sockaddr_in *) ss;
1030 /* Convert to IPv6 address. */
1031 in6_mem.sin6_family = PF_INET6;
1032 in6_mem.sin6_port = in->sin_port;
1033 in6_mem.sin6_flowinfo = 0;
1034 if (in->sin_addr.s_addr == htonl (0x7f000001))
1035 in6_mem.sin6_addr = (struct in6_addr) IN6ADDR_LOOPBACK_INIT;
1036 else
1038 /* Construct a V4-to-6 mapped address. */
1039 memset (&in6_mem.sin6_addr, '\0', sizeof (in6_mem.sin6_addr));
1040 in6_mem.sin6_addr.s6_addr16[5] = 0xffff;
1041 in6_mem.sin6_addr.s6_addr32[3] = in->sin_addr.s_addr;
1042 in6_mem.sin6_scope_id = 0;
1045 in6 = &in6_mem;
1047 else
1048 return default_val;
1050 for (idx = 0; ; ++idx)
1052 unsigned int bits = list[idx].bits;
1053 uint8_t *mask = list[idx].prefix.s6_addr;
1054 uint8_t *val = in6->sin6_addr.s6_addr;
1056 while (bits > 8)
1058 if (*mask != *val)
1059 break;
1061 ++mask;
1062 ++val;
1063 bits -= 8;
1066 if (bits < 8)
1068 if ((*mask & (0xff00 >> bits)) == (*val & (0xff00 >> bits)))
1069 /* Match! */
1070 break;
1074 return list[idx].val;
1078 static int
1079 get_label (const struct sockaddr_storage *ss)
1081 /* XXX What is a good default value? */
1082 return match_prefix (ss, default_labels, INT_MAX);
1086 static int
1087 get_precedence (const struct sockaddr_storage *ss)
1089 /* XXX What is a good default value? */
1090 return match_prefix (ss, default_precedence, 0);
1094 static int
1095 rfc3484_sort (const void *p1, const void *p2)
1097 const struct sort_result *a1 = (const struct sort_result *) p1;
1098 const struct sort_result *a2 = (const struct sort_result *) p2;
1100 /* Rule 1: Avoid unusable destinations.
1101 We have the got_source_addr flag set if the destination is reachable. */
1102 if (a1->got_source_addr && ! a2->got_source_addr)
1103 return -1;
1104 if (! a1->got_source_addr && a2->got_source_addr)
1105 return 1;
1108 /* Rule 2: Prefer matching scope. Only interesting if both
1109 destination addresses are IPv6. */
1110 int a1_dst_scope
1111 = get_scope ((struct sockaddr_storage *) a1->dest_addr->ai_addr);
1113 int a2_dst_scope
1114 = get_scope ((struct sockaddr_storage *) a2->dest_addr->ai_addr);
1116 if (a1->got_source_addr)
1118 int a1_src_scope = get_scope (&a1->source_addr);
1119 int a2_src_scope = get_scope (&a2->source_addr);
1121 if (a1_dst_scope == a1_src_scope && a2_dst_scope != a2_src_scope)
1122 return -1;
1123 if (a1_dst_scope != a1_src_scope && a2_dst_scope == a2_src_scope)
1124 return 1;
1128 /* Rule 3: Avoid deprecated addresses.
1129 That's something only the kernel could decide. */
1131 /* Rule 4: Prefer home addresses.
1132 Another thing only the kernel can decide. */
1134 /* Rule 5: Prefer matching label. */
1135 if (a1->got_source_addr)
1137 int a1_dst_label
1138 = get_label ((struct sockaddr_storage *) a1->dest_addr->ai_addr);
1139 int a1_src_label = get_label (&a1->source_addr);
1141 int a2_dst_label
1142 = get_label ((struct sockaddr_storage *) a2->dest_addr->ai_addr);
1143 int a2_src_label = get_label (&a2->source_addr);
1145 if (a1_dst_label == a1_src_label && a2_dst_label != a2_src_label)
1146 return -1;
1147 if (a1_dst_label != a1_src_label && a2_dst_label == a2_src_label)
1148 return 1;
1152 /* Rule 6: Prefer higher precedence. */
1153 int a1_prec
1154 = get_precedence ((struct sockaddr_storage *) a1->dest_addr->ai_addr);
1155 int a2_prec
1156 = get_precedence ((struct sockaddr_storage *) a2->dest_addr->ai_addr);
1158 if (a1_prec > a2_prec)
1159 return -1;
1160 if (a1_prec < a2_prec)
1161 return 1;
1164 /* Rule 7: Prefer native transport.
1165 XXX How to recognize tunnels? */
1168 /* Rule 8: Prefer smaller scope. */
1169 if (a1_dst_scope < a2_dst_scope)
1170 return -1;
1171 if (a1_dst_scope > a2_dst_scope)
1172 return 1;
1175 /* Rule 9: Use longest matching prefix. */
1176 if (a1->got_source_addr
1177 && a1->dest_addr->ai_family == a2->dest_addr->ai_family)
1179 int bit1 = 0;
1180 int bit2 = 0;
1182 if (a1->dest_addr->ai_family == PF_INET)
1184 assert (a1->source_addr.ss_family == PF_INET);
1185 assert (a2->source_addr.ss_family == PF_INET);
1187 struct sockaddr_in *in1_dst;
1188 struct sockaddr_in *in1_src;
1189 struct sockaddr_in *in2_dst;
1190 struct sockaddr_in *in2_src;
1192 in1_dst = (struct sockaddr_in *) a1->dest_addr->ai_addr;
1193 in1_src = (struct sockaddr_in *) &a1->source_addr;
1194 in2_dst = (struct sockaddr_in *) a2->dest_addr->ai_addr;
1195 in2_src = (struct sockaddr_in *) &a2->source_addr;
1197 bit1 = ffs (in1_dst->sin_addr.s_addr ^ in1_src->sin_addr.s_addr);
1198 bit2 = ffs (in2_dst->sin_addr.s_addr ^ in2_src->sin_addr.s_addr);
1200 else if (a1->dest_addr->ai_family == PF_INET6)
1202 assert (a1->source_addr.ss_family == PF_INET6);
1203 assert (a2->source_addr.ss_family == PF_INET6);
1205 struct sockaddr_in6 *in1_dst;
1206 struct sockaddr_in6 *in1_src;
1207 struct sockaddr_in6 *in2_dst;
1208 struct sockaddr_in6 *in2_src;
1210 in1_dst = (struct sockaddr_in6 *) a1->dest_addr->ai_addr;
1211 in1_src = (struct sockaddr_in6 *) &a1->source_addr;
1212 in2_dst = (struct sockaddr_in6 *) a2->dest_addr->ai_addr;
1213 in2_src = (struct sockaddr_in6 *) &a2->source_addr;
1215 int i;
1216 for (i = 0; i < 4; ++i)
1217 if (in1_dst->sin6_addr.s6_addr32[i]
1218 != in1_src->sin6_addr.s6_addr32[i]
1219 || (in2_dst->sin6_addr.s6_addr32[i]
1220 != in2_src->sin6_addr.s6_addr32[i]))
1221 break;
1223 if (i < 4)
1225 bit1 = ffs (in1_dst->sin6_addr.s6_addr32[i]
1226 ^ in1_src->sin6_addr.s6_addr32[i]);
1227 bit2 = ffs (in2_dst->sin6_addr.s6_addr32[i]
1228 ^ in2_src->sin6_addr.s6_addr32[i]);
1232 if (bit1 > bit2)
1233 return -1;
1234 if (bit1 < bit2)
1235 return 1;
1239 /* Rule 10: Otherwise, leave the order unchanged. */
1240 return 0;
1245 getaddrinfo (const char *name, const char *service,
1246 const struct addrinfo *hints, struct addrinfo **pai)
1248 int i = 0, j = 0, last_i = 0;
1249 int nresults = 0;
1250 struct addrinfo *p = NULL, **end;
1251 struct gaih *g = gaih, *pg = NULL;
1252 struct gaih_service gaih_service, *pservice;
1253 struct addrinfo local_hints;
1255 if (name != NULL && name[0] == '*' && name[1] == 0)
1256 name = NULL;
1258 if (service != NULL && service[0] == '*' && service[1] == 0)
1259 service = NULL;
1261 if (name == NULL && service == NULL)
1262 return EAI_NONAME;
1264 if (hints == NULL)
1265 hints = &default_hints;
1267 if (hints->ai_flags
1268 & ~(AI_PASSIVE|AI_CANONNAME|AI_NUMERICHOST|AI_ADDRCONFIG|AI_V4MAPPED
1269 #ifdef HAVE_LIBIDN
1270 |AI_IDN|AI_CANONIDN|AI_IDN_ALLOW_UNASSIGNED
1271 |AI_IDN_USE_STD3_ASCII_RULES
1272 #endif
1273 |AI_NUMERICSERV|AI_ALL))
1274 return EAI_BADFLAGS;
1276 if ((hints->ai_flags & AI_CANONNAME) && name == NULL)
1277 return EAI_BADFLAGS;
1279 if (hints->ai_flags & AI_ADDRCONFIG)
1281 /* Determine whether we have IPv4 or IPv6 interfaces or both.
1282 We cannot cache the results since new interfaces could be
1283 added at any time. */
1284 bool seen_ipv4;
1285 bool seen_ipv6;
1286 __check_pf (&seen_ipv4, &seen_ipv6);
1288 /* Now make a decision on what we return, if anything. */
1289 if (hints->ai_family == PF_UNSPEC && (seen_ipv4 || seen_ipv6))
1291 /* If we haven't seen both IPv4 and IPv6 interfaces we can
1292 narrow down the search. */
1293 if (! seen_ipv4 || ! seen_ipv6)
1295 local_hints = *hints;
1296 local_hints.ai_family = seen_ipv4 ? PF_INET : PF_INET6;
1297 hints = &local_hints;
1300 else if ((hints->ai_family == PF_INET && ! seen_ipv4)
1301 || (hints->ai_family == PF_INET6 && ! seen_ipv6))
1302 /* We cannot possibly return a valid answer. */
1303 return EAI_NONAME;
1306 if (service && service[0])
1308 char *c;
1309 gaih_service.name = service;
1310 gaih_service.num = strtoul (gaih_service.name, &c, 10);
1311 if (*c != '\0')
1313 if (hints->ai_flags & AI_NUMERICSERV)
1314 return EAI_NONAME;
1316 gaih_service.num = -1;
1318 else
1319 /* Can't specify a numerical socket unless a protocol family was
1320 given. */
1321 if (hints->ai_socktype == 0 && hints->ai_protocol == 0)
1322 return EAI_SERVICE;
1323 pservice = &gaih_service;
1325 else
1326 pservice = NULL;
1328 if (pai)
1329 end = &p;
1330 else
1331 end = NULL;
1333 while (g->gaih)
1335 if (hints->ai_family == g->family || hints->ai_family == AF_UNSPEC)
1337 j++;
1338 if (pg == NULL || pg->gaih != g->gaih)
1340 pg = g;
1341 i = g->gaih (name, pservice, hints, end);
1342 if (i != 0)
1344 /* EAI_NODATA is a more specific result as it says that
1345 we found a result but it is not usable. */
1346 if (last_i != (GAIH_OKIFUNSPEC | -EAI_NODATA))
1347 last_i = i;
1349 if (hints->ai_family == AF_UNSPEC && (i & GAIH_OKIFUNSPEC))
1351 ++g;
1352 continue;
1355 freeaddrinfo (p);
1357 return -(i & GAIH_EAI);
1359 if (end)
1360 while (*end)
1362 end = &((*end)->ai_next);
1363 ++nresults;
1367 ++g;
1370 if (j == 0)
1371 return EAI_FAMILY;
1373 if (nresults > 1)
1375 /* Sort results according to RFC 3484. */
1376 struct sort_result results[nresults];
1377 struct addrinfo *q;
1378 char *canonname = NULL;
1380 for (i = 0, q = p; q != NULL; ++i, q = q->ai_next)
1382 results[i].dest_addr = q;
1383 results[i].got_source_addr = false;
1385 /* We overwrite the type with SOCK_DGRAM since we do not
1386 want connect() to connect to the other side. If we
1387 cannot determine the source address remember this
1388 fact. */
1389 int fd = __socket (q->ai_family, SOCK_DGRAM, IPPROTO_IP);
1390 if (fd != -1)
1392 socklen_t sl = sizeof (results[i].source_addr);
1393 if (__connect (fd, q->ai_addr, q->ai_addrlen) == 0
1394 && __getsockname (fd,
1395 (struct sockaddr *) &results[i].source_addr,
1396 &sl) == 0)
1397 results[i].got_source_addr = true;
1399 close_not_cancel_no_status (fd);
1402 /* Remember the canonical name. */
1403 if (q->ai_canonname != NULL)
1405 assert (canonname == NULL);
1406 canonname = q->ai_canonname;
1407 q->ai_canonname = NULL;
1411 /* We got all the source addresses we can get, now sort using
1412 the information. */
1413 qsort (results, nresults, sizeof (results[0]), rfc3484_sort);
1415 /* Queue the results up as they come out of sorting. */
1416 q = p = results[0].dest_addr;
1417 for (i = 1; i < nresults; ++i)
1418 q = q->ai_next = results[i].dest_addr;
1419 q->ai_next = NULL;
1421 /* Fill in the canonical name into the new first entry. */
1422 p->ai_canonname = canonname;
1425 if (p)
1427 *pai = p;
1428 return 0;
1431 if (pai == NULL && last_i == 0)
1432 return 0;
1434 return last_i ? -(last_i & GAIH_EAI) : EAI_NONAME;
1436 libc_hidden_def (getaddrinfo)
1438 static_link_warning (getaddrinfo)
1440 void
1441 freeaddrinfo (struct addrinfo *ai)
1443 struct addrinfo *p;
1445 while (ai != NULL)
1447 p = ai;
1448 ai = ai->ai_next;
1449 free (p->ai_canonname);
1450 free (p);
1453 libc_hidden_def (freeaddrinfo)