dirmngr: Add option --standard-resolver.
[gnupg.git] / dirmngr / dns-stuff.c
1 /* dns-stuff.c - DNS related code including CERT RR (rfc-4398)
2  * Copyright (C) 2003, 2005, 2006, 2009 Free Software Foundation, Inc.
3  * Copyright (C) 2005, 2006, 2009, 2015. 2016 Werner Koch
4  *
5  * This file is part of GnuPG.
6  *
7  * This file is free software; you can redistribute it and/or modify
8  * it under the terms of either
9  *
10  *   - the GNU Lesser General Public License as published by the Free
11  *     Software Foundation; either version 3 of the License, or (at
12  *     your option) any later version.
13  *
14  * or
15  *
16  *   - the GNU General Public License as published by the Free
17  *     Software Foundation; either version 2 of the License, or (at
18  *     your option) any later version.
19  *
20  * or both in parallel, as here.
21  *
22  * This file is distributed in the hope that it will be useful,
23  * but WITHOUT ANY WARRANTY; without even the implied warranty of
24  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
25  * GNU General Public License for more details.
26  *
27  * You should have received a copy of the GNU General Public License
28  * along with this program; if not, see <https://www.gnu.org/licenses/>.
29  */
30
31 #include <config.h>
32 #include <sys/types.h>
33 #ifdef HAVE_W32_SYSTEM
34 # ifdef HAVE_WINSOCK2_H
35 #  include <winsock2.h>
36 # endif
37 # include <windows.h>
38 #else
39 # if HAVE_SYSTEM_RESOLVER
40 #  include <netinet/in.h>
41 #  include <arpa/nameser.h>
42 #  include <resolv.h>
43 # endif
44 # include <netdb.h>
45 #endif
46 #include <string.h>
47 #include <unistd.h>
48 #ifdef USE_ADNS
49 # include <adns.h>
50 #endif
51
52 #if !defined(HAVE_GETADDRINFO) && !defined(USE_ADNS)
53 # error Either getaddrinfo or the ADNS library is required.
54 #endif
55
56 #ifdef WITHOUT_NPTH /* Give the Makefile a chance to build without Pth.  */
57 # undef USE_NPTH
58 #endif
59 #ifdef USE_NPTH
60 # include <npth.h>
61 #endif
62
63 #include "util.h"
64 #include "host2net.h"
65 #include "dns-stuff.h"
66
67 #ifdef USE_NPTH
68 # define my_unprotect()        npth_unprotect ()
69 # define my_protect()          npth_protect ()
70 #else
71 # define my_unprotect()        do { } while(0)
72 # define my_protect()          do { } while(0)
73 #endif
74
75 /* We allow the use of 0 instead of AF_UNSPEC - check this assumption.  */
76 #if AF_UNSPEC != 0
77 # error AF_UNSPEC does not have the value 0
78 #endif
79
80 /* Windows does not support the AI_ADDRCONFIG flag - use zero instead.  */
81 #ifndef AI_ADDRCONFIG
82 # define AI_ADDRCONFIG 0
83 #endif
84
85 /* Provide a replacement function for older ADNS versions.  */
86 #ifndef HAVE_ADNS_FREE
87 # define adns_free(a) free ((a))
88 #endif
89
90 /* Not every installation has gotten around to supporting SRVs or
91    CERTs yet... */
92 #ifndef T_SRV
93 #define T_SRV 33
94 #endif
95 #ifndef T_CERT
96 # define T_CERT 37
97 #endif
98
99 /* ADNS has no support for CERT yet. */
100 #define my_adns_r_cert 37
101
102
103 /* The default nameserver used with ADNS in Tor mode.  */
104 #define DEFAULT_NAMESERVER "8.8.8.8"
105
106 /* If set force the use of the standard resolver.  */
107 static int standard_resolver;
108
109 /* If set Tor mode shall be used.  */
110 static int tor_mode;
111
112 /* A string with the nameserver IP address used with Tor.
113   (40 should be sufficient for v6 but we add some extra for a scope.) */
114 static char tor_nameserver[40+20];
115
116 /* A string to hold the credentials presented to Tor.  */
117 #ifdef USE_ADNS
118 static char tor_credentials[50];
119 #endif
120
121
122 /* Calling this function with YES set to True forces the use of the
123  * standard resolver even if dirmngr has been built with support for
124  * an alternative resolver.  */
125 void
126 enable_standard_resolver (int yes)
127 {
128   standard_resolver = yes;
129 }
130
131
132 /* Return true if the standard resolver is used.  */
133 int
134 standard_resolver_p (void)
135 {
136   return standard_resolver;
137 }
138
139
140 /* Sets the module in Tor mode.  Returns 0 is this is possible or an
141    error code.  */
142 gpg_error_t
143 enable_dns_tormode (int new_circuit)
144 {
145   (void) new_circuit;
146
147 #ifdef USE_ADNS
148 # if HAVE_ADNS_IF_TORMODE
149    if (!*tor_credentials || new_circuit)
150      {
151        static unsigned int counter;
152
153        gpgrt_snprintf (tor_credentials, sizeof tor_credentials,
154                        "dirmngr-%lu:p%u",
155                        (unsigned long)getpid (), counter);
156        counter++;
157      }
158    tor_mode = 1;
159    return 0;
160 # endif
161 #endif
162
163   return gpg_error (GPG_ERR_NOT_IMPLEMENTED);
164 }
165
166
167 /* Change the default IP address of the nameserver to IPADDR.  The
168    address needs to be a numerical IP address and will be used for the
169    next DNS query.  Note that this is only used in Tor mode.  */
170 void
171 set_dns_nameserver (const char *ipaddr)
172 {
173   strncpy (tor_nameserver, ipaddr? ipaddr : DEFAULT_NAMESERVER,
174            sizeof tor_nameserver -1);
175   tor_nameserver[sizeof tor_nameserver -1] = 0;
176 }
177
178
179 /* Free an addressinfo linked list as returned by resolve_dns_name.  */
180 void
181 free_dns_addrinfo (dns_addrinfo_t ai)
182 {
183   while (ai)
184     {
185       dns_addrinfo_t next = ai->next;
186       xfree (ai);
187       ai = next;
188     }
189 }
190
191
192 static gpg_error_t
193 map_eai_to_gpg_error (int ec)
194 {
195   gpg_error_t err;
196
197   switch (ec)
198     {
199     case EAI_AGAIN:     err = gpg_error (GPG_ERR_EAGAIN); break;
200     case EAI_BADFLAGS:  err = gpg_error (GPG_ERR_INV_FLAG); break;
201     case EAI_FAIL:      err = gpg_error (GPG_ERR_SERVER_FAILED); break;
202     case EAI_MEMORY:    err = gpg_error (GPG_ERR_ENOMEM); break;
203 #ifdef EAI_NODATA
204     case EAI_NODATA:    err = gpg_error (GPG_ERR_NO_DATA); break;
205 #endif
206     case EAI_NONAME:    err = gpg_error (GPG_ERR_NO_NAME); break;
207     case EAI_SERVICE:   err = gpg_error (GPG_ERR_NOT_SUPPORTED); break;
208     case EAI_FAMILY:    err = gpg_error (GPG_ERR_EAFNOSUPPORT); break;
209     case EAI_SOCKTYPE:  err = gpg_error (GPG_ERR_ESOCKTNOSUPPORT); break;
210 #ifndef HAVE_W32_SYSTEM
211 # ifdef EAI_ADDRFAMILY
212     case EAI_ADDRFAMILY:err = gpg_error (GPG_ERR_EADDRNOTAVAIL); break;
213 # endif
214     case EAI_SYSTEM:    err = gpg_error_from_syserror (); break;
215 #endif
216     default:            err = gpg_error (GPG_ERR_UNKNOWN_ERRNO); break;
217     }
218   return err;
219 }
220
221 #ifdef USE_ADNS
222 static gpg_error_t
223 map_adns_status_to_gpg_error (adns_status status)
224 {
225   gpg_err_code_t ec;
226
227   switch (status)
228     {
229     /* case adns_s_netunreach: ec = GPG_ERR_ENETUNREACH; break; */
230     default: ec = GPG_ERR_GENERAL; break;
231     }
232   return gpg_error (ec);
233 }
234 #endif /*USE_ADNS*/
235
236
237 #ifdef USE_ADNS
238 /* Init ADNS and store the new state at R_STATE.  Returns 0 on
239    success; prints an error message and returns an error code on
240    failure.  */
241 static gpg_error_t
242 my_adns_init (adns_state *r_state)
243 {
244   gpg_error_t err = 0;
245   int ret;
246
247   if (tor_mode)
248     {
249       char *cfgstr;
250
251       if (!*tor_nameserver)
252         set_dns_nameserver (NULL);
253
254       cfgstr = xtryasprintf ("nameserver %s\n"
255                              "options adns_tormode adns_sockscred:%s",
256                              tor_nameserver, tor_credentials);
257       if (!cfgstr)
258         err = gpg_error_from_syserror ();
259       else
260         {
261           ret = adns_init_strcfg (r_state, adns_if_debug /*adns_if_noerrprint*/, NULL, cfgstr);
262           if (ret)
263             err = gpg_error_from_errno (ret);
264           xfree (cfgstr);
265         }
266     }
267   else
268     {
269       ret = adns_init (r_state, adns_if_noerrprint, NULL);
270       if (ret)
271         err = gpg_error_from_errno (ret);
272     }
273
274   if (err)
275     {
276       log_error ("error initializing adns: %s\n", gpg_strerror (err));
277       return err;
278     }
279   return 0;
280 }
281 #endif /*USE_ADNS*/
282
283
284 #ifdef USE_ADNS
285 /* Resolve a name using the ADNS library.  See resolve_dns_name for
286    the description.  */
287 static gpg_error_t
288 resolve_name_adns (const char *name, unsigned short port,
289                    int want_family, int want_socktype,
290                    dns_addrinfo_t *r_dai, char **r_canonname)
291 {
292   gpg_error_t err = 0;
293   int ret;
294   dns_addrinfo_t daihead = NULL;
295   dns_addrinfo_t dai;
296   adns_state state;
297   adns_answer *answer = NULL;
298   int count;
299
300   (void)want_family;
301
302   *r_dai = NULL;
303   if (r_canonname)
304     *r_canonname = NULL;
305
306   if (want_socktype != SOCK_STREAM && want_socktype != SOCK_DGRAM)
307     return gpg_error (GPG_ERR_ESOCKTNOSUPPORT);
308
309   err = my_adns_init (&state);
310   if (err)
311     return err;
312
313   my_unprotect ();
314   ret = adns_synchronous (state, name, adns_r_addr,
315                           adns_qf_quoteok_query, &answer);
316   my_protect ();
317   if (ret)
318     {
319       err = gpg_error (gpg_err_code_from_errno (ret));
320       log_error ("DNS query failed: %s\n", gpg_strerror (err));
321       goto leave;
322     }
323
324   err = gpg_error (GPG_ERR_NOT_FOUND);
325   if (answer->status != adns_s_ok || answer->type != adns_r_addr)
326     {
327       err = map_adns_status_to_gpg_error (answer->status);
328       if (gpg_err_code (err) == GPG_ERR_GENERAL)
329         err = gpg_error (GPG_ERR_NOT_FOUND);
330       log_error ("DNS query returned an error: %s (%s)\n",
331                  adns_strerror (answer->status),
332                  adns_errabbrev (answer->status));
333       goto leave;
334     }
335
336   if (r_canonname && answer->cname)
337     {
338       *r_canonname = xtrystrdup (answer->cname);
339       if (!*r_canonname)
340         {
341           err = gpg_error_from_syserror ();
342           goto leave;
343         }
344     }
345
346   for (count = 0; count < answer->nrrs; count++)
347     {
348       int len;
349       adns_rr_addr *addr;
350
351       len  = answer->rrs.addr[count].len;
352       addr = &answer->rrs.addr[count];
353       if (addr->addr.sa.sa_family != AF_INET6
354           && addr->addr.sa.sa_family != AF_INET)
355         continue;
356
357       dai = xtrymalloc (sizeof *dai + len - 1);
358       if (!dai)
359         {
360           err = gpg_error_from_syserror ();
361           goto leave;
362         }
363       dai->family = addr->addr.sa.sa_family;
364       dai->socktype = want_socktype == SOCK_STREAM? SOCK_STREAM : SOCK_DGRAM;
365       dai->protocol = want_socktype == SOCK_STREAM? IPPROTO_TCP : IPPROTO_UDP;
366       dai->addrlen = len;
367       memcpy (dai->addr, &addr->addr.sa, len);
368       ((struct sockaddr_in *) dai->addr)->sin_port = htons (port);
369       dai->next = daihead;
370       daihead = dai;
371       err = 0;
372     }
373
374  leave:
375   adns_free (answer);
376   adns_finish (state);
377   if (err)
378     {
379       if (r_canonname)
380         {
381           xfree (*r_canonname);
382           *r_canonname = NULL;
383         }
384       free_dns_addrinfo (daihead);
385     }
386   else
387     *r_dai = daihead;
388   return err;
389 }
390 #endif /*USE_ADNS*/
391
392
393 /* Resolve a name using the standard system function.  */
394 static gpg_error_t
395 resolve_name_standard (const char *name, unsigned short port,
396                        int want_family, int want_socktype,
397                        dns_addrinfo_t *r_dai, char **r_canonname)
398 {
399   gpg_error_t err = 0;
400   dns_addrinfo_t daihead = NULL;
401   dns_addrinfo_t dai;
402   struct addrinfo *aibuf = NULL;
403   struct addrinfo hints, *ai;
404   char portstr[21];
405   int ret;
406
407   *r_dai = NULL;
408   if (r_canonname)
409     *r_canonname = NULL;
410
411   memset (&hints, 0, sizeof hints);
412   hints.ai_family = want_family;
413   hints.ai_socktype = want_socktype;
414   hints.ai_flags = AI_ADDRCONFIG;
415   if (r_canonname)
416     hints.ai_flags |= AI_CANONNAME;
417
418   if (port)
419     snprintf (portstr, sizeof portstr, "%hu", port);
420   else
421     *portstr = 0;
422
423   /* We can't use the the AI_IDN flag because that does the conversion
424      using the current locale.  However, GnuPG always used UTF-8.  To
425      support IDN we would need to make use of the libidn API.  */
426   ret = getaddrinfo (name, *portstr? portstr : NULL, &hints, &aibuf);
427   if (ret)
428     {
429       aibuf = NULL;
430       err = map_eai_to_gpg_error (ret);
431       if (gpg_err_code (err) == GPG_ERR_NO_NAME)
432         {
433           /* There seems to be a bug in the glibc getaddrinfo function
434              if the CNAME points to a long list of A and AAAA records
435              in which case the function return NO_NAME.  Let's do the
436              CNAME redirection again.  */
437           char *cname;
438
439           if (get_dns_cname (name, &cname))
440             goto leave; /* Still no success.  */
441
442           ret = getaddrinfo (cname, *portstr? portstr : NULL, &hints, &aibuf);
443           xfree (cname);
444           if (ret)
445             {
446               aibuf = NULL;
447               err = map_eai_to_gpg_error (ret);
448               goto leave;
449             }
450           err = 0; /* Yep, now it worked.  */
451         }
452       else
453         goto leave;
454     }
455
456   if (r_canonname && aibuf && aibuf->ai_canonname)
457     {
458       *r_canonname = xtrystrdup (aibuf->ai_canonname);
459       if (!*r_canonname)
460         {
461           err = gpg_error_from_syserror ();
462           goto leave;
463         }
464     }
465
466   for (ai = aibuf; ai; ai = ai->ai_next)
467     {
468       if (ai->ai_family != AF_INET6 && ai->ai_family != AF_INET)
469         continue;
470
471       dai = xtrymalloc (sizeof *dai + ai->ai_addrlen - 1);
472       dai->family = ai->ai_family;
473       dai->socktype = ai->ai_socktype;
474       dai->protocol = ai->ai_protocol;
475       dai->addrlen = ai->ai_addrlen;
476       memcpy (dai->addr, ai->ai_addr, ai->ai_addrlen);
477       dai->next = daihead;
478       daihead = dai;
479     }
480
481  leave:
482   if (aibuf)
483     freeaddrinfo (aibuf);
484   if (err)
485     {
486       if (r_canonname)
487         {
488           xfree (*r_canonname);
489           *r_canonname = NULL;
490         }
491       free_dns_addrinfo (daihead);
492     }
493   else
494     *r_dai = daihead;
495   return err;
496 }
497
498
499 /* Resolve an address using the standard system function.  */
500 static gpg_error_t
501 resolve_addr_standard (const struct sockaddr *addr, int addrlen,
502                        unsigned int flags, char **r_name)
503 {
504   gpg_error_t err;
505   int ec;
506   char *buffer, *p;
507   int buflen;
508
509   *r_name = NULL;
510
511   buflen = NI_MAXHOST;
512   buffer = xtrymalloc (buflen + 2 + 1);
513   if (!buffer)
514     return gpg_error_from_syserror ();
515
516   if ((flags & DNS_NUMERICHOST) || tor_mode)
517     ec = EAI_NONAME;
518   else
519     ec = getnameinfo (addr, addrlen, buffer, buflen, NULL, 0, NI_NAMEREQD);
520
521   if (!ec && *buffer == '[')
522     ec = EAI_FAIL;  /* A name may never start with a bracket.  */
523   else if (ec == EAI_NONAME)
524     {
525       p = buffer;
526       if (addr->sa_family == AF_INET6 && (flags & DNS_WITHBRACKET))
527         {
528           *p++ = '[';
529           buflen -= 2;
530         }
531       ec = getnameinfo (addr, addrlen, p, buflen, NULL, 0, NI_NUMERICHOST);
532       if (!ec && addr->sa_family == AF_INET6 && (flags & DNS_WITHBRACKET))
533         strcat (buffer, "]");
534     }
535
536   if (ec)
537     err = map_eai_to_gpg_error (ec);
538   else
539     {
540       p = xtryrealloc (buffer, strlen (buffer)+1);
541       if (!p)
542         err = gpg_error_from_syserror ();
543       else
544         {
545           buffer = p;
546           err = 0;
547         }
548     }
549
550   if (err)
551     xfree (buffer);
552   else
553     *r_name = buffer;
554
555   return err;
556 }
557
558
559 /* This a wrapper around getaddrinfo with slightly different semantics.
560    NAME is the name to resolve.
561    PORT is the requested port or 0.
562    WANT_FAMILY is either 0 (AF_UNSPEC), AF_INET6, or AF_INET4.
563    WANT_SOCKETTYPE is either SOCK_STREAM or SOCK_DGRAM.
564
565    On success the result is stored in a linked list with the head
566    stored at the address R_AI; the caller must call gpg_addrinfo_free
567    on this.  If R_CANONNAME is not NULL the official name of the host
568    is stored there as a malloced string; if that name is not available
569    NULL is stored.  */
570 gpg_error_t
571 resolve_dns_name (const char *name, unsigned short port,
572                   int want_family, int want_socktype,
573                   dns_addrinfo_t *r_ai, char **r_canonname)
574 {
575 #ifdef USE_ADNS
576   if (!standard_resolver)
577     return resolve_name_adns (name, port, want_family, want_socktype,
578                               r_ai, r_canonname);
579 #endif
580   return resolve_name_standard (name, port, want_family, want_socktype,
581                                 r_ai, r_canonname);
582 }
583
584
585 gpg_error_t
586 resolve_dns_addr (const struct sockaddr *addr, int addrlen,
587                   unsigned int flags, char **r_name)
588 {
589   return resolve_addr_standard (addr, addrlen, flags, r_name);
590 }
591
592
593 /* Check whether NAME is an IP address.  Returns true if it is either
594    an IPv6 or IPv4 numerical address.  */
595 int
596 is_ip_address (const char *name)
597 {
598   const char *s;
599   int ndots, dblcol, n;
600
601   if (*name == '[')
602     return 1; /* yes: A legal DNS name may not contain this character;
603                  this mut be bracketed v6 address.  */
604   if (*name == '.')
605     return 0; /* No.  A leading dot is not a valid IP address.  */
606
607   /* Check whether this is a v6 address.  */
608   ndots = n = dblcol = 0;
609   for (s=name; *s; s++)
610     {
611       if (*s == ':')
612         {
613           ndots++;
614           if (s[1] == ':')
615             {
616               ndots++;
617               if (dblcol)
618                 return 0; /* No: Only one "::" allowed.  */
619               dblcol++;
620               if (s[1])
621                 s++;
622             }
623           n = 0;
624         }
625       else if (*s == '.')
626         goto legacy;
627       else if (!strchr ("0123456789abcdefABCDEF", *s))
628         return 0; /* No: Not a hex digit.  */
629       else if (++n > 4)
630         return 0; /* To many digits in a group.  */
631     }
632   if (ndots > 7)
633     return 0; /* No: Too many colons.  */
634   else if (ndots > 1)
635     return 1; /* Yes: At least 2 colons indicate an v6 address.  */
636
637  legacy:
638   /* Check whether it is legacy IP address.  */
639   ndots = n = 0;
640   for (s=name; *s; s++)
641     {
642       if (*s == '.')
643         {
644           if (s[1] == '.')
645             return 0; /* No:  Douple dot. */
646           if (atoi (s+1) > 255)
647             return 0; /* No:  Ipv4 byte value too large.  */
648           ndots++;
649           n = 0;
650         }
651       else if (!strchr ("0123456789", *s))
652         return 0; /* No: Not a digit.  */
653       else if (++n > 3)
654         return 0; /* No: More than 3 digits.  */
655     }
656   return !!(ndots == 3);
657 }
658
659
660 /* Return true if NAME is an onion address.  */
661 int
662 is_onion_address (const char *name)
663 {
664   size_t len;
665
666   len = name? strlen (name) : 0;
667   if (len < 8 || strcmp (name + len - 6, ".onion"))
668     return 0;
669   /* Note that we require at least 2 characters before the suffix.  */
670   return 1;  /* Yes.  */
671 }
672
673
674 #ifdef USE_ADNS
675 /* ADNS version of get_dns_cert.  */
676 static gpg_error_t
677 get_dns_cert_adns (const char *name, int want_certtype,
678                    void **r_key, size_t *r_keylen,
679                    unsigned char **r_fpr, size_t *r_fprlen, char **r_url)
680 {
681   gpg_error_t err;
682   int ret;
683   adns_state state;
684   adns_answer *answer = NULL;
685   unsigned int ctype;
686   int count;
687
688   err = my_adns_init (&state);
689   if (err)
690     return err;
691
692   my_unprotect ();
693   ret = adns_synchronous (state, name,
694                           (adns_r_unknown
695                            | (want_certtype < DNS_CERTTYPE_RRBASE
696                               ? my_adns_r_cert
697                               : (want_certtype - DNS_CERTTYPE_RRBASE))),
698                           adns_qf_quoteok_query, &answer);
699   my_protect ();
700   if (ret)
701     {
702       err = gpg_error (gpg_err_code_from_errno (ret));
703       /* log_error ("DNS query failed: %s\n", gpg_strerror (err)); */
704       adns_finish (state);
705       return err;
706     }
707   if (answer->status != adns_s_ok)
708     {
709       /* log_error ("DNS query returned an error: %s (%s)\n", */
710       /*            adns_strerror (answer->status), */
711       /*            adns_errabbrev (answer->status)); */
712       err = map_adns_status_to_gpg_error (answer->status);
713       if (gpg_err_code (err) == GPG_ERR_GENERAL)
714         err = gpg_error (GPG_ERR_NOT_FOUND);
715       goto leave;
716     }
717
718   err = gpg_error (GPG_ERR_NOT_FOUND);
719   for (count = 0; count < answer->nrrs; count++)
720     {
721       int datalen = answer->rrs.byteblock[count].len;
722       const unsigned char *data = answer->rrs.byteblock[count].data;
723
724       /* First check for our generic RR hack.  */
725       if (datalen
726           && want_certtype >= DNS_CERTTYPE_RRBASE
727           && ((want_certtype - DNS_CERTTYPE_RRBASE)
728               == (answer->type & ~adns_r_unknown)))
729         {
730           /* Found the requested record - return it.  */
731           *r_key = xtrymalloc (datalen);
732           if (!*r_key)
733             err = gpg_error_from_syserror ();
734           else
735             {
736               memcpy (*r_key, data, datalen);
737               *r_keylen = datalen;
738               err = 0;
739             }
740           goto leave;
741         }
742
743       if (datalen < 5)
744         continue;  /* Truncated CERT record - skip.  */
745
746       ctype = buf16_to_uint (data);
747       /* (key tag and algorithm fields are not required.) */
748       data += 5;
749       datalen -= 5;
750
751       if (want_certtype && want_certtype != ctype)
752         ; /* Not of the requested certtype.  */
753       else if (ctype == DNS_CERTTYPE_PGP && datalen >= 11 && r_key && r_keylen)
754         {
755           /* CERT type is PGP.  Gpg checks for a minimum length of 11,
756              thus we do the same.  */
757           *r_key = xtrymalloc (datalen);
758           if (!*r_key)
759             err = gpg_error_from_syserror ();
760           else
761             {
762               memcpy (*r_key, data, datalen);
763               *r_keylen = datalen;
764               err = 0;
765             }
766           goto leave;
767         }
768       else if (ctype == DNS_CERTTYPE_IPGP && datalen && datalen < 1023
769                && datalen >= data[0] + 1 && r_fpr && r_fprlen && r_url)
770         {
771           /* CERT type is IPGP.  We made sure that the data is
772              plausible and that the caller requested this
773              information.  */
774           *r_fprlen = data[0];
775           if (*r_fprlen)
776             {
777               *r_fpr = xtrymalloc (*r_fprlen);
778               if (!*r_fpr)
779                 {
780                   err = gpg_error_from_syserror ();
781                   goto leave;
782                 }
783               memcpy (*r_fpr, data + 1, *r_fprlen);
784             }
785           else
786             *r_fpr = NULL;
787
788           if (datalen > *r_fprlen + 1)
789             {
790               *r_url = xtrymalloc (datalen - (*r_fprlen + 1) + 1);
791               if (!*r_url)
792                 {
793                   err = gpg_error_from_syserror ();
794                   xfree (*r_fpr);
795                   *r_fpr = NULL;
796                   goto leave;
797                 }
798               memcpy (*r_url,
799                       data + (*r_fprlen + 1), datalen - (*r_fprlen + 1));
800               (*r_url)[datalen - (*r_fprlen + 1)] = '\0';
801             }
802           else
803             *r_url = NULL;
804
805           err = 0;
806           goto leave;
807         }
808     }
809
810  leave:
811   adns_free (answer);
812   adns_finish (state);
813   return err;
814 }
815 #endif /*!USE_ADNS */
816
817
818 /* Standard resolver version of get_dns_cert.  */
819 static gpg_error_t
820 get_dns_cert_standard (const char *name, int want_certtype,
821                        void **r_key, size_t *r_keylen,
822                        unsigned char **r_fpr, size_t *r_fprlen, char **r_url)
823 {
824 #ifdef HAVE_SYSTEM_RESOLVER
825   gpg_error_t err;
826   unsigned char *answer;
827   int r;
828   u16 count;
829
830   /* Allocate a 64k buffer which is the limit for an DNS response.  */
831   answer = xtrymalloc (65536);
832   if (!answer)
833     return gpg_error_from_syserror ();
834
835   err = gpg_error (GPG_ERR_NOT_FOUND);
836   r = res_query (name, C_IN,
837                  (want_certtype < DNS_CERTTYPE_RRBASE
838                   ? T_CERT
839                   : (want_certtype - DNS_CERTTYPE_RRBASE)),
840                  answer, 65536);
841   /* Not too big, not too small, no errors and at least 1 answer. */
842   if (r >= sizeof (HEADER) && r <= 65536
843       && (((HEADER *)(void *) answer)->rcode) == NOERROR
844       && (count = ntohs (((HEADER *)(void *) answer)->ancount)))
845     {
846       int rc;
847       unsigned char *pt, *emsg;
848
849       emsg = &answer[r];
850
851       pt = &answer[sizeof (HEADER)];
852
853       /* Skip over the query */
854
855       rc = dn_skipname (pt, emsg);
856       if (rc == -1)
857         {
858           err = gpg_error (GPG_ERR_INV_OBJ);
859           goto leave;
860         }
861       pt += rc + QFIXEDSZ;
862
863       /* There are several possible response types for a CERT request.
864          We're interested in the PGP (a key) and IPGP (a URI) types.
865          Skip all others.  TODO: A key is better than a URI since
866          we've gone through all this bother to fetch it, so favor that
867          if we have both PGP and IPGP? */
868
869       while (count-- > 0 && pt < emsg)
870         {
871           u16 type, class, dlen, ctype;
872
873           rc = dn_skipname (pt, emsg);  /* the name we just queried for */
874           if (rc == -1)
875             {
876               err = gpg_error (GPG_ERR_INV_OBJ);
877               goto leave;
878             }
879
880           pt += rc;
881
882           /* Truncated message? 15 bytes takes us to the point where
883              we start looking at the ctype. */
884           if ((emsg - pt) < 15)
885             break;
886
887           type = buf16_to_u16 (pt);
888           pt += 2;
889
890           class = buf16_to_u16 (pt);
891           pt += 2;
892
893           if (class != C_IN)
894             break;
895
896           /* ttl */
897           pt += 4;
898
899           /* data length */
900           dlen = buf16_to_u16 (pt);
901           pt += 2;
902
903           /* Check the type and parse.  */
904           if (want_certtype >= DNS_CERTTYPE_RRBASE
905               && type == (want_certtype - DNS_CERTTYPE_RRBASE)
906               && r_key)
907             {
908               *r_key = xtrymalloc (dlen);
909               if (!*r_key)
910                 err = gpg_error_from_syserror ();
911               else
912                 {
913                   memcpy (*r_key, pt, dlen);
914                   *r_keylen = dlen;
915                   err = 0;
916                 }
917               goto leave;
918             }
919           else if (want_certtype >= DNS_CERTTYPE_RRBASE)
920             {
921               /* We did not found the requested RR.  */
922               pt += dlen;
923             }
924           else if (type == T_CERT)
925             {
926               /* We got a CERT type.   */
927               ctype = buf16_to_u16 (pt);
928               pt += 2;
929
930               /* Skip the CERT key tag and algo which we don't need. */
931               pt += 3;
932
933               dlen -= 5;
934
935               /* 15 bytes takes us to here */
936               if (want_certtype && want_certtype != ctype)
937                 ; /* Not of the requested certtype.  */
938               else if (ctype == DNS_CERTTYPE_PGP && dlen && r_key && r_keylen)
939                 {
940                   /* PGP type */
941                   *r_key = xtrymalloc (dlen);
942                   if (!*r_key)
943                     err = gpg_error_from_syserror ();
944                   else
945                     {
946                       memcpy (*r_key, pt, dlen);
947                       *r_keylen = dlen;
948                       err = 0;
949                     }
950                   goto leave;
951                 }
952               else if (ctype == DNS_CERTTYPE_IPGP
953                        && dlen && dlen < 1023 && dlen >= pt[0] + 1)
954                 {
955                   /* IPGP type */
956                   *r_fprlen = pt[0];
957                   if (*r_fprlen)
958                     {
959                       *r_fpr = xtrymalloc (*r_fprlen);
960                       if (!*r_fpr)
961                         {
962                           err = gpg_error_from_syserror ();
963                           goto leave;
964                         }
965                       memcpy (*r_fpr, &pt[1], *r_fprlen);
966                     }
967                   else
968                     *r_fpr = NULL;
969
970                   if (dlen > *r_fprlen + 1)
971                     {
972                       *r_url = xtrymalloc (dlen - (*r_fprlen + 1) + 1);
973                       if (!*r_fpr)
974                         {
975                           err = gpg_error_from_syserror ();
976                           xfree (*r_fpr);
977                           *r_fpr = NULL;
978                           goto leave;
979                         }
980                       memcpy (*r_url, &pt[*r_fprlen + 1],
981                               dlen - (*r_fprlen + 1));
982                       (*r_url)[dlen - (*r_fprlen + 1)] = '\0';
983                     }
984                   else
985                     *r_url = NULL;
986
987                   err = 0;
988                   goto leave;
989                 }
990
991               /* No subtype matches, so continue with the next answer. */
992               pt += dlen;
993             }
994           else
995             {
996               /* Not a requested type - might be a CNAME. Try next item.  */
997               pt += dlen;
998             }
999         }
1000     }
1001
1002  leave:
1003   xfree (answer);
1004   return err;
1005
1006 #else /*!HAVE_SYSTEM_RESOLVER*/
1007
1008   (void)name;
1009   (void)want_certtype;
1010   (void)r_key;
1011   (void)r_keylen;
1012   (void)r_fpr;
1013   (void)r_fprlen;
1014   (void)r_url;
1015   return gpg_error (GPG_ERR_NOT_SUPPORTED);
1016
1017 #endif /*!HAVE_SYSTEM_RESOLVER*/
1018 }
1019
1020
1021 /* Returns 0 on success or an error code.  If a PGP CERT record was
1022    found, the malloced data is returned at (R_KEY, R_KEYLEN) and
1023    the other return parameters are set to NULL/0.  If an IPGP CERT
1024    record was found the fingerprint is stored as an allocated block at
1025    R_FPR and its length at R_FPRLEN; an URL is is allocated as a
1026    string and returned at R_URL.  If WANT_CERTTYPE is 0 this function
1027    returns the first CERT found with a supported type; it is expected
1028    that only one CERT record is used.  If WANT_CERTTYPE is one of the
1029    supported certtypes only records with this certtype are considered
1030    and the first found is returned.  (R_KEY,R_KEYLEN) are optional. */
1031 gpg_error_t
1032 get_dns_cert (const char *name, int want_certtype,
1033               void **r_key, size_t *r_keylen,
1034               unsigned char **r_fpr, size_t *r_fprlen, char **r_url)
1035 {
1036   if (r_key)
1037     *r_key = NULL;
1038   if (r_keylen)
1039     *r_keylen = 0;
1040   *r_fpr = NULL;
1041   *r_fprlen = 0;
1042   *r_url = NULL;
1043
1044 #ifdef USE_ADNS
1045   if (!standard_resolver)
1046     return get_dns_cert_adns (name, want_certtype, r_key, r_keylen,
1047                               r_fpr, r_fprlen, r_url);
1048 #endif /*!USE_ADNS */
1049   return get_dns_cert_standard (name, want_certtype, r_key, r_keylen,
1050                                 r_fpr, r_fprlen, r_url);
1051 }
1052
1053
1054 static int
1055 priosort(const void *a,const void *b)
1056 {
1057   const struct srventry *sa=a,*sb=b;
1058   if(sa->priority>sb->priority)
1059     return 1;
1060   else if(sa->priority<sb->priority)
1061     return -1;
1062   else
1063     return 0;
1064 }
1065
1066
1067 #ifdef USE_ADNS
1068 /* ADNS based helper for getsrv.  */
1069 static int
1070 getsrv_adns (const char *name, struct srventry **list)
1071 {
1072   int srvcount = 0;
1073   u16 count;
1074   int rc;
1075   adns_state state;
1076   adns_answer *answer = NULL;
1077
1078   if (my_adns_init (&state))
1079     return -1;
1080
1081   my_unprotect ();
1082   rc = adns_synchronous (state, name, adns_r_srv, adns_qf_quoteok_query,
1083                          &answer);
1084   my_protect ();
1085   if (rc)
1086     {
1087       log_error ("DNS query failed: %s\n", strerror (rc));
1088       adns_finish (state);
1089       return -1;
1090     }
1091   if (answer->status != adns_s_ok
1092       || answer->type != adns_r_srv || !answer->nrrs)
1093     {
1094         log_error ("DNS query returned an error or no records: %s (%s)\n",
1095                    adns_strerror (answer->status),
1096                    adns_errabbrev (answer->status));
1097         adns_free (answer);
1098         adns_finish (state);
1099         return 0;
1100     }
1101
1102   for (count = 0; count < answer->nrrs; count++)
1103     {
1104       struct srventry *srv = NULL;
1105       struct srventry *newlist;
1106
1107       if (strlen (answer->rrs.srvha[count].ha.host) >= sizeof srv->target)
1108         {
1109           log_info ("hostname in SRV record too long - skipped\n");
1110           continue;
1111         }
1112
1113       newlist = xtryrealloc (*list, (srvcount+1)*sizeof(struct srventry));
1114       if (!newlist)
1115         {
1116           xfree (*list);
1117           *list = NULL;
1118           return -1;
1119         }
1120       *list = newlist;
1121       memset (&(*list)[srvcount], 0, sizeof(struct srventry));
1122       srv = &(*list)[srvcount];
1123       srvcount++;
1124
1125       srv->priority = answer->rrs.srvha[count].priority;
1126       srv->weight   = answer->rrs.srvha[count].weight;
1127       srv->port     = answer->rrs.srvha[count].port;
1128       strcpy (srv->target, answer->rrs.srvha[count].ha.host);
1129     }
1130
1131   adns_free (answer);
1132   adns_finish (state);
1133
1134   return srvcount;
1135 }
1136 #endif /*USE_ADNS*/
1137
1138
1139 /* Standard resolver based helper for getsrv.  */
1140 static int
1141 getsrv_standard (const char *name, struct srventry **list)
1142 {
1143 #ifdef HAVE_SYSTEM_RESOLVER
1144   union {
1145     unsigned char ans[2048];
1146     HEADER header[1];
1147   } res;
1148   unsigned char *answer = res.ans;
1149   HEADER *header = res.header;
1150   unsigned char *pt, *emsg;
1151   int r, rc;
1152   u16 dlen;
1153   int srvcount=0;
1154   u16 count;
1155
1156   /* Do not allow a query using the standard resolver in Tor mode.  */
1157   if (tor_mode)
1158     return -1;
1159
1160   my_unprotect ();
1161   r = res_query (name, C_IN, T_SRV, answer, sizeof answer);
1162   my_protect ();
1163   if (r < sizeof (HEADER) || r > sizeof answer
1164       || header->rcode != NOERROR || !(count=ntohs (header->ancount)))
1165     return 0; /* Error or no record found.  */
1166
1167   emsg = &answer[r];
1168   pt = &answer[sizeof(HEADER)];
1169
1170   /* Skip over the query */
1171   rc = dn_skipname (pt, emsg);
1172   if (rc == -1)
1173     goto fail;
1174
1175   pt += rc + QFIXEDSZ;
1176
1177   while (count-- > 0 && pt < emsg)
1178     {
1179       struct srventry *srv = NULL;
1180       u16 type, class;
1181       struct srventry *newlist;
1182
1183       newlist = xtryrealloc (*list, (srvcount+1)*sizeof(struct srventry));
1184       if (!newlist)
1185         goto fail;
1186       *list = newlist;
1187       memset (&(*list)[srvcount], 0, sizeof(struct srventry));
1188       srv = &(*list)[srvcount];
1189       srvcount++;
1190
1191       rc = dn_skipname (pt, emsg); /* The name we just queried for.  */
1192       if (rc == -1)
1193         goto fail;
1194       pt += rc;
1195
1196       /* Truncated message? */
1197       if ((emsg-pt) < 16)
1198         goto fail;
1199
1200       type = buf16_to_u16 (pt);
1201       pt += 2;
1202       /* We asked for SRV and got something else !? */
1203       if (type != T_SRV)
1204         goto fail;
1205
1206       class = buf16_to_u16 (pt);
1207       pt += 2;
1208       /* We asked for IN and got something else !? */
1209       if (class != C_IN)
1210         goto fail;
1211
1212       pt += 4; /* ttl */
1213       dlen = buf16_to_u16 (pt);
1214       pt += 2;
1215
1216       srv->priority = buf16_to_ushort (pt);
1217       pt += 2;
1218       srv->weight = buf16_to_ushort (pt);
1219       pt += 2;
1220       srv->port = buf16_to_ushort (pt);
1221       pt += 2;
1222
1223       /* Get the name.  2782 doesn't allow name compression, but
1224        * dn_expand still works to pull the name out of the packet. */
1225       rc = dn_expand (answer, emsg, pt, srv->target, sizeof srv->target);
1226       if (rc == 1 && srv->target[0] == 0) /* "." */
1227         {
1228           xfree(*list);
1229           *list = NULL;
1230           return 0;
1231         }
1232       if (rc == -1)
1233         goto fail;
1234       pt += rc;
1235       /* Corrupt packet? */
1236       if (dlen != rc+6)
1237         goto fail;
1238     }
1239
1240   return srvcount;
1241
1242  fail:
1243   xfree (*list);
1244   *list = NULL;
1245   return -1;
1246
1247 #else /*!HAVE_SYSTEM_RESOLVER*/
1248
1249   (void)name;
1250   (void)list;
1251   return -1;
1252
1253 #endif /*!HAVE_SYSTEM_RESOLVER*/
1254 }
1255
1256
1257 int
1258 getsrv (const char *name, struct srventry **list)
1259 {
1260   int srvcount;
1261   int i;
1262
1263   *list = NULL;
1264
1265   if (0)
1266     ;
1267 #ifdef USE_ADNS
1268   else if (!standard_resolver)
1269     srvcount = getsrv_adns (name, list);
1270 #endif /*!USE_ADNS*/
1271   else
1272     srvcount = getsrv_standard (name, list);
1273
1274   if (srvcount <= 0)
1275     return srvcount;
1276
1277   /* Now we have an array of all the srv records. */
1278
1279   /* Order by priority */
1280   qsort(*list,srvcount,sizeof(struct srventry),priosort);
1281
1282   /* For each priority, move the zero-weighted items first. */
1283   for (i=0; i < srvcount; i++)
1284     {
1285       int j;
1286
1287       for (j=i;j < srvcount && (*list)[i].priority == (*list)[j].priority; j++)
1288         {
1289           if((*list)[j].weight==0)
1290             {
1291               /* Swap j with i */
1292               if(j!=i)
1293                 {
1294                   struct srventry temp;
1295
1296                   memcpy (&temp,&(*list)[j],sizeof(struct srventry));
1297                   memcpy (&(*list)[j],&(*list)[i],sizeof(struct srventry));
1298                   memcpy (&(*list)[i],&temp,sizeof(struct srventry));
1299                 }
1300
1301               break;
1302             }
1303         }
1304     }
1305
1306   /* Run the RFC-2782 weighting algorithm.  We don't need very high
1307      quality randomness for this, so regular libc srand/rand is
1308      sufficient.  */
1309
1310   {
1311     static int done;
1312     if (!done)
1313       {
1314         done = 1;
1315         srand (time (NULL)*getpid());
1316       }
1317   }
1318
1319   for (i=0; i < srvcount; i++)
1320     {
1321       int j;
1322       float prio_count=0,chose;
1323
1324       for (j=i; j < srvcount && (*list)[i].priority == (*list)[j].priority; j++)
1325         {
1326           prio_count+=(*list)[j].weight;
1327           (*list)[j].run_count=prio_count;
1328         }
1329
1330       chose=prio_count*rand()/RAND_MAX;
1331
1332       for (j=i;j<srvcount && (*list)[i].priority==(*list)[j].priority;j++)
1333         {
1334           if (chose<=(*list)[j].run_count)
1335             {
1336               /* Swap j with i */
1337               if(j!=i)
1338                 {
1339                   struct srventry temp;
1340
1341                   memcpy(&temp,&(*list)[j],sizeof(struct srventry));
1342                   memcpy(&(*list)[j],&(*list)[i],sizeof(struct srventry));
1343                   memcpy(&(*list)[i],&temp,sizeof(struct srventry));
1344                 }
1345               break;
1346             }
1347         }
1348     }
1349
1350   return srvcount;
1351 }
1352
1353
1354 #ifdef USE_ADNS
1355 /* ADNS version of get_dns_cname.  */
1356 gpg_error_t
1357 get_dns_cname_adns (const char *name, char **r_cname)
1358 {
1359   gpg_error_t err;
1360   int rc;
1361   adns_state state;
1362   adns_answer *answer = NULL;
1363
1364   if (my_adns_init (&state))
1365     return gpg_error (GPG_ERR_GENERAL);
1366
1367   my_unprotect ();
1368   rc = adns_synchronous (state, name, adns_r_cname, adns_qf_quoteok_query,
1369                          &answer);
1370   my_protect ();
1371   if (rc)
1372     {
1373       err = gpg_error (gpg_err_code_from_errno (rc));
1374       log_error ("DNS query failed: %s\n", gpg_strerror (err));
1375       adns_finish (state);
1376       return err;
1377     }
1378   if (answer->status != adns_s_ok
1379       || answer->type != adns_r_cname || answer->nrrs != 1)
1380     {
1381       err = map_adns_status_to_gpg_error (answer->status);
1382       log_error ("DNS query returned an error or no records: %s (%s)\n",
1383                  adns_strerror (answer->status),
1384                  adns_errabbrev (answer->status));
1385       adns_free (answer);
1386       adns_finish (state);
1387       return err;
1388     }
1389   *r_cname = xtrystrdup (answer->rrs.str[0]);
1390   if (!*r_cname)
1391     err = gpg_error_from_syserror ();
1392   else
1393     err = 0;
1394
1395   adns_free (answer);
1396   adns_finish (state);
1397   return err;
1398 }
1399 #endif /*USE_ADNS*/
1400
1401
1402 /* Standard resolver version of get_dns_cname.  */
1403 gpg_error_t
1404 get_dns_cname_standard (const char *name, char **r_cname)
1405 {
1406 #ifdef HAVE_SYSTEM_RESOLVER
1407   gpg_error_t err;
1408   int rc;
1409   union {
1410     unsigned char ans[2048];
1411     HEADER header[1];
1412   } res;
1413   unsigned char *answer = res.ans;
1414   HEADER *header = res.header;
1415   unsigned char *pt, *emsg;
1416   int r;
1417   char *cname;
1418   int cnamesize = 1025;
1419   u16 count;
1420
1421   /* Do not allow a query using the standard resolver in Tor mode.  */
1422   if (tor_mode)
1423     return -1;
1424
1425   r = res_query (name, C_IN, T_CERT, answer, sizeof answer);
1426   if (r < sizeof (HEADER) || r > sizeof answer)
1427     return gpg_error (GPG_ERR_SERVER_FAILED);
1428   if (header->rcode != NOERROR || !(count=ntohs (header->ancount)))
1429     return gpg_error (GPG_ERR_NO_NAME); /* Error or no record found.  */
1430   if (count != 1)
1431     return gpg_error (GPG_ERR_SERVER_FAILED);
1432
1433   emsg = &answer[r];
1434   pt = &answer[sizeof(HEADER)];
1435   rc = dn_skipname (pt, emsg);
1436   if (rc == -1)
1437     return gpg_error (GPG_ERR_SERVER_FAILED);
1438
1439   pt += rc + QFIXEDSZ;
1440   if (pt >= emsg)
1441     return gpg_error (GPG_ERR_SERVER_FAILED);
1442
1443   rc = dn_skipname (pt, emsg);
1444   if (rc == -1)
1445     return gpg_error (GPG_ERR_SERVER_FAILED);
1446   pt += rc + 2 + 2 + 4;
1447   if (pt+2 >= emsg)
1448     return gpg_error (GPG_ERR_SERVER_FAILED);
1449   pt += 2;  /* Skip rdlen */
1450
1451   cname = xtrymalloc (cnamesize);
1452   if (!cname)
1453     return gpg_error_from_syserror ();
1454
1455   rc = dn_expand (answer, emsg, pt, cname, cnamesize -1);
1456   if (rc == -1)
1457     {
1458       xfree (cname);
1459       return gpg_error (GPG_ERR_SERVER_FAILED);
1460     }
1461   *r_cname = xtryrealloc (cname, strlen (cname)+1);
1462   if (!*r_cname)
1463     {
1464       err = gpg_error_from_syserror ();
1465       xfree (cname);
1466       return err;
1467     }
1468   return 0;
1469
1470 #else /*!HAVE_SYSTEM_RESOLVER*/
1471
1472   (void)name;
1473   (void)r_cname;
1474   return -1;
1475
1476 #endif /*!HAVE_SYSTEM_RESOLVER*/
1477 }
1478
1479
1480 gpg_error_t
1481 get_dns_cname (const char *name, char **r_cname)
1482 {
1483   *r_cname = NULL;
1484
1485 #ifdef USE_ADNS
1486   if (!standard_resolver)
1487     return get_dns_cname_adns (name, r_cname);
1488 #endif /*!USE_ADNS*/
1489
1490   return get_dns_cname_standard (name, r_cname);
1491 }