Update.
[glibc.git] / sysdeps / posix / getaddrinfo.c
blob9de286032320bb3d611f53d5c818ed855cba53c1
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;
366 if (req->ai_protocol || req->ai_socktype)
368 ++tp;
370 while (tp->name[0]
371 && ((req->ai_socktype != 0 && req->ai_socktype != tp->socktype)
372 || (req->ai_protocol != 0
373 && !(tp->protoflag & GAI_PROTO_PROTOANY)
374 && req->ai_protocol != tp->protocol)))
375 ++tp;
377 if (! tp->name[0])
379 if (req->ai_socktype)
380 return (GAIH_OKIFUNSPEC | -EAI_SOCKTYPE);
381 else
382 return (GAIH_OKIFUNSPEC | -EAI_SERVICE);
386 if (service != NULL)
388 if ((tp->protoflag & GAI_PROTO_NOSERVICE) != 0)
389 return (GAIH_OKIFUNSPEC | -EAI_SERVICE);
391 if (service->num < 0)
393 if (tp->name[0])
395 st = (struct gaih_servtuple *)
396 __alloca (sizeof (struct gaih_servtuple));
398 if ((rc = gaih_inet_serv (service->name, tp, req, st)))
399 return rc;
401 else
403 struct gaih_servtuple **pst = &st;
404 for (tp++; tp->name[0]; tp++)
406 struct gaih_servtuple *newp;
408 if ((tp->protoflag & GAI_PROTO_NOSERVICE) != 0)
409 continue;
411 if (req->ai_socktype != 0
412 && req->ai_socktype != tp->socktype)
413 continue;
414 if (req->ai_protocol != 0
415 && !(tp->protoflag & GAI_PROTO_PROTOANY)
416 && req->ai_protocol != tp->protocol)
417 continue;
419 newp = (struct gaih_servtuple *)
420 __alloca (sizeof (struct gaih_servtuple));
422 if ((rc = gaih_inet_serv (service->name, tp, req, newp)))
424 if (rc & GAIH_OKIFUNSPEC)
425 continue;
426 return rc;
429 *pst = newp;
430 pst = &(newp->next);
432 if (st == (struct gaih_servtuple *) &nullserv)
433 return (GAIH_OKIFUNSPEC | -EAI_SERVICE);
436 else
438 st = __alloca (sizeof (struct gaih_servtuple));
439 st->next = NULL;
440 st->socktype = tp->socktype;
441 st->protocol = ((tp->protoflag & GAI_PROTO_PROTOANY)
442 ? req->ai_protocol : tp->protocol);
443 st->port = htons (service->num);
446 else if (req->ai_socktype || req->ai_protocol)
448 st = __alloca (sizeof (struct gaih_servtuple));
449 st->next = NULL;
450 st->socktype = tp->socktype;
451 st->protocol = ((tp->protoflag & GAI_PROTO_PROTOANY)
452 ? req->ai_protocol : tp->protocol);
453 st->port = 0;
455 else
457 /* Neither socket type nor protocol is set. Return all socket types
458 we know about. */
459 struct gaih_servtuple **lastp = &st;
460 for (++tp; tp->name[0]; ++tp)
462 struct gaih_servtuple *newp;
464 newp = __alloca (sizeof (struct gaih_servtuple));
465 newp->next = NULL;
466 newp->socktype = tp->socktype;
467 newp->protocol = tp->protocol;
468 newp->port = 0;
470 *lastp = newp;
471 lastp = &newp->next;
475 if (name != NULL)
477 at = __alloca (sizeof (struct gaih_addrtuple));
479 at->family = AF_UNSPEC;
480 at->scopeid = 0;
481 at->next = NULL;
483 #ifdef HAVE_LIBIDN
484 if (req->ai_flags & AI_IDN)
486 int idn_flags = 0;
487 if (req->ai_flags & AI_IDN_ALLOW_UNASSIGNED)
488 idn_flags |= IDNA_ALLOW_UNASSIGNED;
489 if (req->ai_flags & AI_IDN_USE_STD3_ASCII_RULES)
490 idn_flags |= IDNA_USE_STD3_ASCII_RULES;
492 char *p = NULL;
493 rc = __idna_to_ascii_lz (name, &p, idn_flags);
494 if (rc != IDNA_SUCCESS)
496 if (rc == IDNA_MALLOC_ERROR)
497 return -EAI_MEMORY;
498 if (rc == IDNA_DLOPEN_ERROR)
499 return -EAI_SYSTEM;
500 return -EAI_IDN_ENCODE;
502 /* In case the output string is the same as the input string
503 no new string has been allocated. */
504 if (p != name)
506 name = strdupa (p);
507 free (p);
510 #endif
512 if (__inet_aton (name, (struct in_addr *) at->addr) != 0)
514 if (req->ai_family == AF_UNSPEC || req->ai_family == AF_INET)
515 at->family = AF_INET;
516 else if (req->ai_family == AF_INET6 && req->ai_flags & AI_V4MAPPED)
518 at->addr[3] = at->addr[0];
519 at->addr[2] = htonl (0xffff);
520 at->addr[1] = 0;
521 at->addr[0] = 0;
522 at->family = AF_INET6;
524 else
525 return -EAI_ADDRFAMILY;
528 if (at->family == AF_UNSPEC)
530 char *namebuf = strdupa (name);
531 char *scope_delim;
533 scope_delim = strchr (namebuf, SCOPE_DELIMITER);
534 if (scope_delim != NULL)
535 *scope_delim = '\0';
537 if (inet_pton (AF_INET6, namebuf, at->addr) > 0)
539 if (req->ai_family == AF_UNSPEC || req->ai_family == AF_INET6)
540 at->family = AF_INET6;
541 else if (req->ai_family == AF_INET
542 && IN6_IS_ADDR_V4MAPPED (at->addr))
544 at->addr[0] = at->addr[3];
545 at->family = AF_INET;
547 else
548 return -EAI_ADDRFAMILY;
550 if (scope_delim != NULL)
552 int try_numericscope = 0;
553 if (IN6_IS_ADDR_LINKLOCAL (at->addr)
554 || IN6_IS_ADDR_MC_LINKLOCAL (at->addr))
556 at->scopeid = if_nametoindex (scope_delim + 1);
557 if (at->scopeid == 0)
558 try_numericscope = 1;
560 else
561 try_numericscope = 1;
563 if (try_numericscope != 0)
565 char *end;
566 assert (sizeof (uint32_t) <= sizeof (unsigned long));
567 at->scopeid = (uint32_t) strtoul (scope_delim + 1, &end,
568 10);
569 if (*end != '\0')
570 return GAIH_OKIFUNSPEC | -EAI_NONAME;
576 if (at->family == AF_UNSPEC && (req->ai_flags & AI_NUMERICHOST) == 0)
578 struct hostent *h;
579 struct gaih_addrtuple **pat = &at;
580 int no_data = 0;
581 int no_inet6_data = 0;
582 service_user *nip = NULL;
583 enum nss_status inet6_status = NSS_STATUS_UNAVAIL;
584 enum nss_status status = NSS_STATUS_UNAVAIL;
585 int no_more;
586 nss_gethostbyname2_r fct;
587 int old_res_options;
588 size_t tmpbuflen = 512;
589 char *tmpbuf = alloca (tmpbuflen);
591 if (__nss_hosts_database != NULL)
593 no_more = 0;
594 nip = __nss_hosts_database;
596 else
597 no_more = __nss_database_lookup ("hosts", NULL,
598 "dns [!UNAVAIL=return] files",
599 &nip);
601 if (__res_maybe_init (&_res, 0) == -1)
602 no_more = 1;
604 /* If we are looking for both IPv4 and IPv6 address we don't
605 want the lookup functions to automatically promote IPv4
606 addresses to IPv6 addresses. Currently this is decided
607 by setting the RES_USE_INET6 bit in _res.options. */
608 old_res_options = _res.options;
609 _res.options &= ~RES_USE_INET6;
611 while (!no_more)
613 fct = __nss_lookup_function (nip, "gethostbyname2_r");
615 if (fct != NULL)
617 if (req->ai_family == AF_INET6
618 || req->ai_family == AF_UNSPEC)
620 gethosts (AF_INET6, struct in6_addr);
621 no_inet6_data = no_data;
622 inet6_status = status;
624 if (req->ai_family == AF_INET
625 || req->ai_family == AF_UNSPEC
626 || (req->ai_family == AF_INET6
627 && (req->ai_flags & AI_V4MAPPED)
628 /* Avoid generating the mapped addresses if we
629 know we are not going to need them. */
630 && ((req->ai_flags & AI_ALL) || !got_ipv6)))
632 gethosts (AF_INET, struct in_addr);
634 if (req->ai_family == AF_INET)
636 no_inet6_data = no_data;
637 inet6_status = status;
641 /* If we found one address for AF_INET or AF_INET6,
642 don't continue the search. */
643 if (inet6_status == NSS_STATUS_SUCCESS
644 || status == NSS_STATUS_SUCCESS)
646 /* If we need the canonical name, get it from the same
647 service as the result. */
648 nss_getcanonname_r cfct;
649 int herrno;
651 cfct = __nss_lookup_function (nip, "getcanonname_r");
652 if (cfct != NULL)
654 const size_t max_fqdn_len = 256;
655 char *buf = alloca (max_fqdn_len);
656 char *s;
658 if (DL_CALL_FCT (cfct, (name, buf, max_fqdn_len,
659 &s, &rc, &herrno))
660 == NSS_STATUS_SUCCESS)
661 canon = s;
662 else
663 /* Set to name now to avoid using
664 gethostbyaddr. */
665 canon = name;
668 break;
671 /* We can have different states for AF_INET and
672 AF_INET6. Try to find a useful one for both. */
673 if (inet6_status == NSS_STATUS_TRYAGAIN)
674 status = NSS_STATUS_TRYAGAIN;
675 else if (status == NSS_STATUS_UNAVAIL &&
676 inet6_status != NSS_STATUS_UNAVAIL)
677 status = inet6_status;
680 if (nss_next_action (nip, status) == NSS_ACTION_RETURN)
681 break;
683 if (nip->next == NULL)
684 no_more = -1;
685 else
686 nip = nip->next;
689 _res.options = old_res_options;
691 if (no_data != 0 && no_inet6_data != 0)
693 /* If both requests timed out report this. */
694 if (no_data == EAI_AGAIN && no_inet6_data == EAI_AGAIN)
695 return -EAI_AGAIN;
697 /* We made requests but they turned out no data. The name
698 is known, though. */
699 return (GAIH_OKIFUNSPEC | -EAI_NODATA);
703 if (at->family == AF_UNSPEC)
704 return (GAIH_OKIFUNSPEC | -EAI_NONAME);
706 else
708 struct gaih_addrtuple *atr;
709 atr = at = __alloca (sizeof (struct gaih_addrtuple));
710 memset (at, '\0', sizeof (struct gaih_addrtuple));
712 if (req->ai_family == AF_UNSPEC)
714 at->next = __alloca (sizeof (struct gaih_addrtuple));
715 memset (at->next, '\0', sizeof (struct gaih_addrtuple));
718 if (req->ai_family == AF_UNSPEC || req->ai_family == AF_INET6)
720 at->family = AF_INET6;
721 if ((req->ai_flags & AI_PASSIVE) == 0)
722 memcpy (at->addr, &in6addr_loopback, sizeof (struct in6_addr));
723 atr = at->next;
726 if (req->ai_family == AF_UNSPEC || req->ai_family == AF_INET)
728 atr->family = AF_INET;
729 if ((req->ai_flags & AI_PASSIVE) == 0)
730 atr->addr[0] = htonl (INADDR_LOOPBACK);
734 if (pai == NULL)
735 return 0;
738 struct gaih_servtuple *st2;
739 struct gaih_addrtuple *at2 = at;
740 size_t socklen;
741 size_t canonlen;
742 sa_family_t family;
745 buffer is the size of an unformatted IPv6 address in printable format.
747 while (at2 != NULL)
749 /* Only the first entry gets the canonical name. */
750 if (at2 == at && (req->ai_flags & AI_CANONNAME) != 0)
752 if (canon == NULL)
754 struct hostent *h = NULL;
755 int herrno;
756 struct hostent th;
757 size_t tmpbuflen = 512;
758 char *tmpbuf = NULL;
762 tmpbuf = extend_alloca (tmpbuf, tmpbuflen, tmpbuflen * 2);
763 rc = __gethostbyaddr_r (at2->addr,
764 ((at2->family == AF_INET6)
765 ? sizeof (struct in6_addr)
766 : sizeof (struct in_addr)),
767 at2->family, &th, tmpbuf,
768 tmpbuflen, &h, &herrno);
770 while (rc == ERANGE && herrno == NETDB_INTERNAL);
772 if (rc != 0 && herrno == NETDB_INTERNAL)
774 __set_h_errno (herrno);
775 return -EAI_SYSTEM;
778 if (h != NULL)
779 canon = h->h_name;
780 else
782 assert (name != NULL);
783 /* If the canonical name cannot be determined, use
784 the passed in string. */
785 canon = name;
789 #ifdef HAVE_LIBIDN
790 if (req->ai_flags & AI_CANONIDN)
792 int idn_flags = 0;
793 if (req->ai_flags & AI_IDN_ALLOW_UNASSIGNED)
794 idn_flags |= IDNA_ALLOW_UNASSIGNED;
795 if (req->ai_flags & AI_IDN_USE_STD3_ASCII_RULES)
796 idn_flags |= IDNA_USE_STD3_ASCII_RULES;
798 char *out;
799 int rc = __idna_to_unicode_lzlz (canon, &out, idn_flags);
800 if (rc != IDNA_SUCCESS)
802 if (rc == IDNA_MALLOC_ERROR)
803 return -EAI_MEMORY;
804 if (rc == IDNA_DLOPEN_ERROR)
805 return -EAI_SYSTEM;
806 return -EAI_IDN_ENCODE;
808 /* In case the output string is the same as the input
809 string no new string has been allocated. */
810 if (out != canon)
812 canon = strdupa (out);
813 free (out);
816 #endif
818 canonlen = strlen (canon) + 1;
820 else
821 canonlen = 0;
823 if (at2->family == AF_INET6)
825 family = AF_INET6;
826 socklen = sizeof (struct sockaddr_in6);
828 /* If we looked up IPv4 mapped address discard them here if
829 the caller isn't interested in all address and we have
830 found at least one IPv6 address. */
831 if (got_ipv6
832 && (req->ai_flags & (AI_V4MAPPED|AI_ALL)) == AI_V4MAPPED
833 && IN6_IS_ADDR_V4MAPPED (at2->addr))
834 goto ignore;
836 else
838 family = AF_INET;
839 socklen = sizeof (struct sockaddr_in);
842 for (st2 = st; st2 != NULL; st2 = st2->next)
844 *pai = malloc (sizeof (struct addrinfo) + socklen + canonlen);
845 if (*pai == NULL)
846 return -EAI_MEMORY;
848 (*pai)->ai_flags = req->ai_flags;
849 (*pai)->ai_family = family;
850 (*pai)->ai_socktype = st2->socktype;
851 (*pai)->ai_protocol = st2->protocol;
852 (*pai)->ai_addrlen = socklen;
853 (*pai)->ai_addr = (void *) (*pai + 1);
854 #if SALEN
855 (*pai)->ai_addr->sa_len = socklen;
856 #endif /* SALEN */
857 (*pai)->ai_addr->sa_family = family;
859 if (family == AF_INET6)
861 struct sockaddr_in6 *sin6p =
862 (struct sockaddr_in6 *) (*pai)->ai_addr;
864 sin6p->sin6_port = st2->port;
865 sin6p->sin6_flowinfo = 0;
866 memcpy (&sin6p->sin6_addr,
867 at2->addr, sizeof (struct in6_addr));
868 sin6p->sin6_scope_id = at2->scopeid;
870 else
872 struct sockaddr_in *sinp =
873 (struct sockaddr_in *) (*pai)->ai_addr;
874 sinp->sin_port = st2->port;
875 memcpy (&sinp->sin_addr,
876 at2->addr, sizeof (struct in_addr));
877 memset (sinp->sin_zero, '\0', sizeof (sinp->sin_zero));
880 if (canonlen != 0)
882 (*pai)->ai_canonname = ((void *) (*pai) +
883 sizeof (struct addrinfo) + socklen);
884 strcpy ((*pai)->ai_canonname, canon);
886 /* We do not need to allocate the canonical name anymore. */
887 canonlen = 0;
889 else
890 (*pai)->ai_canonname = NULL;
892 (*pai)->ai_next = NULL;
893 pai = &((*pai)->ai_next);
896 ignore:
897 at2 = at2->next;
900 return 0;
903 static struct gaih gaih[] =
905 { PF_INET6, gaih_inet },
906 { PF_INET, gaih_inet },
907 #if 0
908 { PF_LOCAL, gaih_local },
909 #endif
910 { PF_UNSPEC, NULL }
913 struct sort_result
915 struct addrinfo *dest_addr;
916 struct sockaddr_storage source_addr;
917 bool got_source_addr;
921 static int
922 get_scope (const struct sockaddr_storage *ss)
924 int scope;
925 if (ss->ss_family == PF_INET6)
927 const struct sockaddr_in6 *in6 = (const struct sockaddr_in6 *) ss;
929 if (! IN6_IS_ADDR_MULTICAST (&in6->sin6_addr))
931 if (IN6_IS_ADDR_LINKLOCAL (&in6->sin6_addr))
932 scope = 2;
933 else if (IN6_IS_ADDR_SITELOCAL (&in6->sin6_addr))
934 scope = 5;
935 else
936 /* XXX Is this the correct default behavior? */
937 scope = 14;
939 else
940 scope = in6->sin6_addr.s6_addr[1] & 0xf;
942 else if (ss->ss_family == PF_INET)
944 const struct sockaddr_in *in = (const struct sockaddr_in *) ss;
945 const uint8_t *addr = (const uint8_t *) &in->sin_addr;
947 /* RFC 3484 specifies how to map IPv6 addresses to scopes.
948 169.254/16 and 127/8 are link-local. */
949 if ((addr[0] == 169 && addr[1] == 254) || addr[0] == 127)
950 scope = 2;
951 else if (addr[0] == 10 || (addr[0] == 172 && addr[1] == 16)
952 || (addr[0] == 192 && addr[1] == 168))
953 scope = 5;
954 else
955 scope = 14;
957 else
958 /* XXX What is a good default? */
959 scope = 15;
961 return scope;
965 /* XXX The system administrator should be able to install other
966 tables. We need to make this configurable. The problem is that
967 the kernel is also involved since it needs the same table. */
968 static const struct prefixlist
970 struct in6_addr prefix;
971 unsigned int bits;
972 int val;
973 } default_labels[] =
975 /* See RFC 3484 for the details. */
976 { { .in6_u = { .u6_addr16 = { 0x0000, 0x0000, 0x0000, 0x0000,
977 0x0000, 0x0000, 0x0000, 0x0001 } } },
978 128, 0 },
979 { { .in6_u = { .u6_addr16 = { 0x2002, 0x0000, 0x0000, 0x0000,
980 0x0000, 0x0000, 0x0000, 0x0000 } } },
981 16, 2 },
982 { { .in6_u = { .u6_addr16 = { 0x0000, 0x0000, 0x0000, 0x0000,
983 0x0000, 0x0000, 0x0000, 0x0000 } } },
984 96, 3 },
985 { { .in6_u = { .u6_addr16 = { 0x0000, 0x0000, 0x0000, 0x0000,
986 0x0000, 0xffff, 0x0000, 0x0000 } } },
987 96, 4 },
988 { { .in6_u = { .u6_addr16 = { 0x0000, 0x0000, 0x0000, 0x0000,
989 0x0000, 0x0000, 0x0000, 0x0000 } } },
990 0, 1 }
994 static const struct prefixlist default_precedence[] =
996 /* See RFC 3484 for the details. */
997 { { .in6_u = { .u6_addr16 = { 0x0000, 0x0000, 0x0000, 0x0000,
998 0x0000, 0x0000, 0x0000, 0x0001 } } },
999 128, 50 },
1000 { { .in6_u = { .u6_addr16 = { 0x2002, 0x0000, 0x0000, 0x0000,
1001 0x0000, 0x0000, 0x0000, 0x0000 } } },
1002 16, 30 },
1003 { { .in6_u = { .u6_addr16 = { 0x0000, 0x0000, 0x0000, 0x0000,
1004 0x0000, 0x0000, 0x0000, 0x0000 } } },
1005 96, 20 },
1006 { { .in6_u = { .u6_addr16 = { 0x0000, 0x0000, 0x0000, 0x0000,
1007 0x0000, 0xffff, 0x0000, 0x0000 } } },
1008 96, 10 },
1009 { { .in6_u = { .u6_addr16 = { 0x0000, 0x0000, 0x0000, 0x0000,
1010 0x0000, 0x0000, 0x0000, 0x0000 } } },
1011 0, 40 }
1015 static int
1016 match_prefix (const struct sockaddr_storage *ss, const struct prefixlist *list,
1017 int default_val)
1019 int idx;
1020 struct sockaddr_in6 in6_mem;
1021 const struct sockaddr_in6 *in6;
1023 if (ss->ss_family == PF_INET6)
1024 in6 = (const struct sockaddr_in6 *) ss;
1025 else if (ss->ss_family == PF_INET)
1027 const struct sockaddr_in *in = (const struct sockaddr_in *) ss;
1029 /* Convert to IPv6 address. */
1030 in6_mem.sin6_family = PF_INET6;
1031 in6_mem.sin6_port = in->sin_port;
1032 in6_mem.sin6_flowinfo = 0;
1033 if (in->sin_addr.s_addr == htonl (0x7f000001))
1034 in6_mem.sin6_addr = (struct in6_addr) IN6ADDR_LOOPBACK_INIT;
1035 else
1037 /* Construct a V4-to-6 mapped address. */
1038 memset (&in6_mem.sin6_addr, '\0', sizeof (in6_mem.sin6_addr));
1039 in6_mem.sin6_addr.s6_addr16[5] = 0xffff;
1040 in6_mem.sin6_addr.s6_addr32[3] = in->sin_addr.s_addr;
1041 in6_mem.sin6_scope_id = 0;
1044 in6 = &in6_mem;
1046 else
1047 return default_val;
1049 for (idx = 0; ; ++idx)
1051 unsigned int bits = list[idx].bits;
1052 uint8_t *mask = list[idx].prefix.s6_addr;
1053 uint8_t *val = in6->sin6_addr.s6_addr;
1055 while (bits > 8)
1057 if (*mask != *val)
1058 break;
1060 ++mask;
1061 ++val;
1062 bits -= 8;
1065 if (bits < 8)
1067 if ((*mask & (0xff00 >> bits)) == (*val & (0xff00 >> bits)))
1068 /* Match! */
1069 break;
1073 return list[idx].val;
1077 static int
1078 get_label (const struct sockaddr_storage *ss)
1080 /* XXX What is a good default value? */
1081 return match_prefix (ss, default_labels, INT_MAX);
1085 static int
1086 get_precedence (const struct sockaddr_storage *ss)
1088 /* XXX What is a good default value? */
1089 return match_prefix (ss, default_precedence, 0);
1093 static int
1094 rfc3484_sort (const void *p1, const void *p2)
1096 const struct sort_result *a1 = (const struct sort_result *) p1;
1097 const struct sort_result *a2 = (const struct sort_result *) p2;
1099 /* Rule 1: Avoid unusable destinations.
1100 We have the got_source_addr flag set if the destination is reachable. */
1101 if (a1->got_source_addr && ! a2->got_source_addr)
1102 return -1;
1103 if (! a1->got_source_addr && a2->got_source_addr)
1104 return 1;
1107 /* Rule 2: Prefer matching scope. Only interesting if both
1108 destination addresses are IPv6. */
1109 int a1_dst_scope
1110 = get_scope ((struct sockaddr_storage *) a1->dest_addr->ai_addr);
1112 int a2_dst_scope
1113 = get_scope ((struct sockaddr_storage *) a2->dest_addr->ai_addr);
1115 if (a1->got_source_addr)
1117 int a1_src_scope = get_scope (&a1->source_addr);
1118 int a2_src_scope = get_scope (&a2->source_addr);
1120 if (a1_dst_scope == a1_src_scope && a2_dst_scope != a2_src_scope)
1121 return -1;
1122 if (a1_dst_scope != a1_src_scope && a2_dst_scope == a2_src_scope)
1123 return 1;
1127 /* Rule 3: Avoid deprecated addresses.
1128 That's something only the kernel could decide. */
1130 /* Rule 4: Prefer home addresses.
1131 Another thing only the kernel can decide. */
1133 /* Rule 5: Prefer matching label. */
1134 if (a1->got_source_addr)
1136 int a1_dst_label
1137 = get_label ((struct sockaddr_storage *) a1->dest_addr->ai_addr);
1138 int a1_src_label = get_label (&a1->source_addr);
1140 int a2_dst_label
1141 = get_label ((struct sockaddr_storage *) a2->dest_addr->ai_addr);
1142 int a2_src_label = get_label (&a2->source_addr);
1144 if (a1_dst_label == a1_src_label && a2_dst_label != a2_src_label)
1145 return -1;
1146 if (a1_dst_label != a1_src_label && a2_dst_label == a2_src_label)
1147 return 1;
1151 /* Rule 6: Prefer higher precedence. */
1152 int a1_prec
1153 = get_precedence ((struct sockaddr_storage *) a1->dest_addr->ai_addr);
1154 int a2_prec
1155 = get_precedence ((struct sockaddr_storage *) a2->dest_addr->ai_addr);
1157 if (a1_prec > a2_prec)
1158 return -1;
1159 if (a1_prec < a2_prec)
1160 return 1;
1163 /* Rule 7: Prefer native transport.
1164 XXX How to recognize tunnels? */
1167 /* Rule 8: Prefer smaller scope. */
1168 if (a1_dst_scope < a2_dst_scope)
1169 return -1;
1170 if (a1_dst_scope > a2_dst_scope)
1171 return 1;
1174 /* Rule 9: Use longest matching prefix. */
1175 if (a1->got_source_addr
1176 && a1->dest_addr->ai_family == a2->dest_addr->ai_family)
1178 int bit1 = 0;
1179 int bit2 = 0;
1181 if (a1->dest_addr->ai_family == PF_INET)
1183 assert (a1->source_addr.ss_family == PF_INET);
1184 assert (a2->source_addr.ss_family == PF_INET);
1186 struct sockaddr_in *in1_dst;
1187 struct sockaddr_in *in1_src;
1188 struct sockaddr_in *in2_dst;
1189 struct sockaddr_in *in2_src;
1191 in1_dst = (struct sockaddr_in *) a1->dest_addr->ai_addr;
1192 in1_src = (struct sockaddr_in *) &a1->source_addr;
1193 in2_dst = (struct sockaddr_in *) a2->dest_addr->ai_addr;
1194 in2_src = (struct sockaddr_in *) &a2->source_addr;
1196 bit1 = ffs (in1_dst->sin_addr.s_addr ^ in1_src->sin_addr.s_addr);
1197 bit2 = ffs (in2_dst->sin_addr.s_addr ^ in2_src->sin_addr.s_addr);
1199 else if (a1->dest_addr->ai_family == PF_INET6)
1201 assert (a1->source_addr.ss_family == PF_INET6);
1202 assert (a2->source_addr.ss_family == PF_INET6);
1204 struct sockaddr_in6 *in1_dst;
1205 struct sockaddr_in6 *in1_src;
1206 struct sockaddr_in6 *in2_dst;
1207 struct sockaddr_in6 *in2_src;
1209 in1_dst = (struct sockaddr_in6 *) a1->dest_addr->ai_addr;
1210 in1_src = (struct sockaddr_in6 *) &a1->source_addr;
1211 in2_dst = (struct sockaddr_in6 *) a2->dest_addr->ai_addr;
1212 in2_src = (struct sockaddr_in6 *) &a2->source_addr;
1214 int i;
1215 for (i = 0; i < 4; ++i)
1216 if (in1_dst->sin6_addr.s6_addr32[i]
1217 != in1_src->sin6_addr.s6_addr32[i]
1218 || (in2_dst->sin6_addr.s6_addr32[i]
1219 != in2_src->sin6_addr.s6_addr32[i]))
1220 break;
1222 if (i < 4)
1224 bit1 = ffs (in1_dst->sin6_addr.s6_addr32[i]
1225 ^ in1_src->sin6_addr.s6_addr32[i]);
1226 bit2 = ffs (in2_dst->sin6_addr.s6_addr32[i]
1227 ^ in2_src->sin6_addr.s6_addr32[i]);
1231 if (bit1 > bit2)
1232 return -1;
1233 if (bit1 < bit2)
1234 return 1;
1238 /* Rule 10: Otherwise, leave the order unchanged. */
1239 return 0;
1244 getaddrinfo (const char *name, const char *service,
1245 const struct addrinfo *hints, struct addrinfo **pai)
1247 int i = 0, j = 0, last_i = 0;
1248 int nresults = 0;
1249 struct addrinfo *p = NULL, **end;
1250 struct gaih *g = gaih, *pg = NULL;
1251 struct gaih_service gaih_service, *pservice;
1252 struct addrinfo local_hints;
1254 if (name != NULL && name[0] == '*' && name[1] == 0)
1255 name = NULL;
1257 if (service != NULL && service[0] == '*' && service[1] == 0)
1258 service = NULL;
1260 if (name == NULL && service == NULL)
1261 return EAI_NONAME;
1263 if (hints == NULL)
1264 hints = &default_hints;
1266 if (hints->ai_flags
1267 & ~(AI_PASSIVE|AI_CANONNAME|AI_NUMERICHOST|AI_ADDRCONFIG|AI_V4MAPPED
1268 #ifdef HAVE_LIBIDN
1269 |AI_IDN|AI_CANONIDN|AI_IDN_ALLOW_UNASSIGNED
1270 |AI_IDN_USE_STD3_ASCII_RULES
1271 #endif
1272 |AI_NUMERICSERV|AI_ALL))
1273 return EAI_BADFLAGS;
1275 if ((hints->ai_flags & AI_CANONNAME) && name == NULL)
1276 return EAI_BADFLAGS;
1278 if (hints->ai_flags & AI_ADDRCONFIG)
1280 /* Determine whether we have IPv4 or IPv6 interfaces or both.
1281 We cannot cache the results since new interfaces could be
1282 added at any time. */
1283 bool seen_ipv4;
1284 bool seen_ipv6;
1285 __check_pf (&seen_ipv4, &seen_ipv6);
1287 /* Now make a decision on what we return, if anything. */
1288 if (hints->ai_family == PF_UNSPEC && (seen_ipv4 || seen_ipv6))
1290 /* If we haven't seen both IPv4 and IPv6 interfaces we can
1291 narrow down the search. */
1292 if (! seen_ipv4 || ! seen_ipv6)
1294 local_hints = *hints;
1295 local_hints.ai_family = seen_ipv4 ? PF_INET : PF_INET6;
1296 hints = &local_hints;
1299 else if ((hints->ai_family == PF_INET && ! seen_ipv4)
1300 || (hints->ai_family == PF_INET6 && ! seen_ipv6))
1301 /* We cannot possibly return a valid answer. */
1302 return EAI_NONAME;
1305 if (service && service[0])
1307 char *c;
1308 gaih_service.name = service;
1309 gaih_service.num = strtoul (gaih_service.name, &c, 10);
1310 if (*c != '\0')
1312 if (hints->ai_flags & AI_NUMERICSERV)
1313 return EAI_NONAME;
1315 gaih_service.num = -1;
1317 else
1318 /* Can't specify a numerical socket unless a protocol family was
1319 given. */
1320 if (hints->ai_socktype == 0 && hints->ai_protocol == 0)
1321 return EAI_SERVICE;
1322 pservice = &gaih_service;
1324 else
1325 pservice = NULL;
1327 if (pai)
1328 end = &p;
1329 else
1330 end = NULL;
1332 while (g->gaih)
1334 if (hints->ai_family == g->family || hints->ai_family == AF_UNSPEC)
1336 j++;
1337 if (pg == NULL || pg->gaih != g->gaih)
1339 pg = g;
1340 i = g->gaih (name, pservice, hints, end);
1341 if (i != 0)
1343 /* EAI_NODATA is a more specific result as it says that
1344 we found a result but it is not usable. */
1345 if (last_i != (GAIH_OKIFUNSPEC | -EAI_NODATA))
1346 last_i = i;
1348 if (hints->ai_family == AF_UNSPEC && (i & GAIH_OKIFUNSPEC))
1350 ++g;
1351 continue;
1354 freeaddrinfo (p);
1356 return -(i & GAIH_EAI);
1358 if (end)
1359 while (*end)
1361 end = &((*end)->ai_next);
1362 ++nresults;
1366 ++g;
1369 if (j == 0)
1370 return EAI_FAMILY;
1372 if (nresults > 1)
1374 /* Sort results according to RFC 3484. */
1375 struct sort_result results[nresults];
1376 struct addrinfo *q;
1377 char *canonname = NULL;
1379 for (i = 0, q = p; q != NULL; ++i, q = q->ai_next)
1381 results[i].dest_addr = q;
1382 results[i].got_source_addr = false;
1384 /* We overwrite the type with SOCK_DGRAM since we do not
1385 want connect() to connect to the other side. If we
1386 cannot determine the source address remember this
1387 fact. */
1388 int fd = __socket (q->ai_family, SOCK_DGRAM, IPPROTO_IP);
1389 if (fd != -1)
1391 socklen_t sl = sizeof (results[i].source_addr);
1392 if (__connect (fd, q->ai_addr, q->ai_addrlen) == 0
1393 && __getsockname (fd,
1394 (struct sockaddr *) &results[i].source_addr,
1395 &sl) == 0)
1396 results[i].got_source_addr = true;
1398 close_not_cancel_no_status (fd);
1401 /* Remember the canonical name. */
1402 if (q->ai_canonname != NULL)
1404 assert (canonname == NULL);
1405 canonname = q->ai_canonname;
1406 q->ai_canonname = NULL;
1410 /* We got all the source addresses we can get, now sort using
1411 the information. */
1412 qsort (results, nresults, sizeof (results[0]), rfc3484_sort);
1414 /* Queue the results up as they come out of sorting. */
1415 q = p = results[0].dest_addr;
1416 for (i = 1; i < nresults; ++i)
1417 q = q->ai_next = results[i].dest_addr;
1418 q->ai_next = NULL;
1420 /* Fill in the canonical name into the new first entry. */
1421 p->ai_canonname = canonname;
1424 if (p)
1426 *pai = p;
1427 return 0;
1430 if (pai == NULL && last_i == 0)
1431 return 0;
1433 return last_i ? -(last_i & GAIH_EAI) : EAI_NONAME;
1435 libc_hidden_def (getaddrinfo)
1437 static_link_warning (getaddrinfo)
1439 void
1440 freeaddrinfo (struct addrinfo *ai)
1442 struct addrinfo *p;
1444 while (ai != NULL)
1446 p = ai;
1447 ai = ai->ai_next;
1448 free (p);
1451 libc_hidden_def (freeaddrinfo)