Remove unused debug flags and add "dns" and "network".
[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 # define WIN32_LEAN_AND_MEAN
35 # ifdef HAVE_WINSOCK2_H
36 #  include <winsock2.h>
37 # endif
38 # include <windows.h>
39 # include <iphlpapi.h>
40 #else
41 # if HAVE_SYSTEM_RESOLVER
42 #  include <netinet/in.h>
43 #  include <arpa/nameser.h>
44 #  include <resolv.h>
45 # endif
46 # include <netdb.h>
47 #endif
48 #include <string.h>
49 #include <unistd.h>
50
51
52 /* William Ahern's DNS library, included as a source copy.  */
53 #ifdef USE_LIBDNS
54 # include "dns.h"
55 #endif
56
57 /* dns.c has a dns_p_free but it is not exported.  We use our own
58  * wrapper here so that we do not accidentally use xfree which would
59  * be wrong for dns.c allocated data.  */
60 #define dns_free(a)  free ((a))
61
62
63 #ifdef WITHOUT_NPTH /* Give the Makefile a chance to build without Pth.  */
64 # undef USE_NPTH
65 #endif
66 #ifdef USE_NPTH
67 # include <npth.h>
68 #endif
69
70 #include "./dirmngr-err.h"
71 #include "util.h"
72 #include "host2net.h"
73 #include "dns-stuff.h"
74
75 #ifdef USE_NPTH
76 # define my_unprotect()        npth_unprotect ()
77 # define my_protect()          npth_protect ()
78 #else
79 # define my_unprotect()        do { } while(0)
80 # define my_protect()          do { } while(0)
81 #endif
82
83 /* We allow the use of 0 instead of AF_UNSPEC - check this assumption.  */
84 #if AF_UNSPEC != 0
85 # error AF_UNSPEC does not have the value 0
86 #endif
87
88 /* Windows does not support the AI_ADDRCONFIG flag - use zero instead.  */
89 #ifndef AI_ADDRCONFIG
90 # define AI_ADDRCONFIG 0
91 #endif
92
93 /* Not every installation has gotten around to supporting SRVs or
94    CERTs yet... */
95 #ifndef T_SRV
96 #define T_SRV 33
97 #endif
98 #ifndef T_CERT
99 # define T_CERT 37
100 #endif
101
102 /* The standard SOCKS and TOR ports.  */
103 #define SOCKS_PORT 1080
104 #define TOR_PORT   9050
105 #define TOR_PORT2  9150   /* (Used by the Tor browser) */
106
107
108 /* The default nameserver used in Tor mode.  */
109 #define DEFAULT_NAMESERVER "8.8.8.8"
110
111 /* If set force the use of the standard resolver.  */
112 static int standard_resolver;
113
114 /* If set use recursive resolver when available. */
115 static int recursive_resolver;
116
117 /* If set Tor mode shall be used.  */
118 static int tor_mode;
119
120 /* A string with the nameserver IP address used with Tor.
121   (40 should be sufficient for v6 but we add some extra for a scope.) */
122 static char tor_nameserver[40+20];
123
124 /* Two strings to hold the credentials presented to Tor.  */
125 static char tor_socks_user[30];
126 static char tor_socks_password[20];
127
128
129 #ifdef USE_LIBDNS
130 /* Libdns gobal data.  */
131 struct libdns_s
132 {
133   struct dns_resolv_conf *resolv_conf;
134   struct dns_hosts *hosts;
135   struct dns_hints *hints;
136
137   struct sockaddr_storage socks_host;
138 } libdns;
139
140 /* If this flag is set, libdns shall be reinited for the next use.  */
141 static int libdns_reinit_pending;
142
143 /* The Tor port to be used.  */
144 static int libdns_tor_port;
145
146 #endif /*USE_LIBDNS*/
147
148
149 /* Calling this function with YES set to True forces the use of the
150  * standard resolver even if dirmngr has been built with support for
151  * an alternative resolver.  */
152 void
153 enable_standard_resolver (int yes)
154 {
155   standard_resolver = yes;
156 }
157
158
159 /* Return true if the standard resolver is used.  */
160 int
161 standard_resolver_p (void)
162 {
163   return standard_resolver;
164 }
165
166
167 /* Calling this function with YES switches libdns into recursive mode.
168  * It has no effect on the standard resolver.  */
169 void
170 enable_recursive_resolver (int yes)
171 {
172   recursive_resolver = yes;
173   libdns_reinit_pending = 1;
174 }
175
176
177 /* Return true iff the recursive resolver is used.  */
178 int
179 recursive_resolver_p (void)
180 {
181 #if USE_LIBDNS
182   return !standard_resolver && recursive_resolver;
183 #else
184   return 0;
185 #endif
186 }
187
188
189 /* Sets the module in Tor mode.  Returns 0 is this is possible or an
190    error code.  */
191 gpg_error_t
192 enable_dns_tormode (int new_circuit)
193 {
194   if (!*tor_socks_user || new_circuit)
195     {
196       static unsigned int counter;
197
198       gpgrt_snprintf (tor_socks_user, sizeof tor_socks_user,
199                       "dirmngr-%lu", (unsigned long)getpid ());
200       gpgrt_snprintf (tor_socks_password, sizeof tor_socks_password,
201                       "p%u", counter);
202       counter++;
203     }
204   tor_mode = 1;
205   return 0;
206 }
207
208
209 /* Change the default IP address of the nameserver to IPADDR.  The
210    address needs to be a numerical IP address and will be used for the
211    next DNS query.  Note that this is only used in Tor mode.  */
212 void
213 set_dns_nameserver (const char *ipaddr)
214 {
215   strncpy (tor_nameserver, ipaddr? ipaddr : DEFAULT_NAMESERVER,
216            sizeof tor_nameserver -1);
217   tor_nameserver[sizeof tor_nameserver -1] = 0;
218   libdns_reinit_pending = 1;
219   libdns_tor_port = 0;  /* Start again with the default port.  */
220 }
221
222
223 /* Free an addressinfo linked list as returned by resolve_dns_name.  */
224 void
225 free_dns_addrinfo (dns_addrinfo_t ai)
226 {
227   while (ai)
228     {
229       dns_addrinfo_t next = ai->next;
230       xfree (ai);
231       ai = next;
232     }
233 }
234
235
236 #ifndef HAVE_W32_SYSTEM
237 /* Return H_ERRNO mapped to a gpg-error code.  Will never return 0. */
238 static gpg_error_t
239 get_h_errno_as_gpg_error (void)
240 {
241   gpg_err_code_t ec;
242
243   switch (h_errno)
244     {
245     case HOST_NOT_FOUND: ec = GPG_ERR_UNKNOWN_HOST; break;
246     case TRY_AGAIN:      ec = GPG_ERR_TRY_LATER; break;
247     case NO_RECOVERY:    ec = GPG_ERR_SERVER_FAILED; break;
248     case NO_DATA:        ec = GPG_ERR_NO_DATA; break;
249     default:             ec = GPG_ERR_UNKNOWN_ERRNO; break;
250     }
251   return gpg_error (ec);
252 }
253 #endif /*!HAVE_W32_SYSTEM*/
254
255 static gpg_error_t
256 map_eai_to_gpg_error (int ec)
257 {
258   gpg_error_t err;
259
260   switch (ec)
261     {
262     case EAI_AGAIN:     err = gpg_error (GPG_ERR_EAGAIN); break;
263     case EAI_BADFLAGS:  err = gpg_error (GPG_ERR_INV_FLAG); break;
264     case EAI_FAIL:      err = gpg_error (GPG_ERR_SERVER_FAILED); break;
265     case EAI_MEMORY:    err = gpg_error (GPG_ERR_ENOMEM); break;
266 #ifdef EAI_NODATA
267     case EAI_NODATA:    err = gpg_error (GPG_ERR_NO_DATA); break;
268 #endif
269     case EAI_NONAME:    err = gpg_error (GPG_ERR_NO_NAME); break;
270     case EAI_SERVICE:   err = gpg_error (GPG_ERR_NOT_SUPPORTED); break;
271     case EAI_FAMILY:    err = gpg_error (GPG_ERR_EAFNOSUPPORT); break;
272     case EAI_SOCKTYPE:  err = gpg_error (GPG_ERR_ESOCKTNOSUPPORT); break;
273 #ifndef HAVE_W32_SYSTEM
274 # ifdef EAI_ADDRFAMILY
275     case EAI_ADDRFAMILY:err = gpg_error (GPG_ERR_EADDRNOTAVAIL); break;
276 # endif
277     case EAI_SYSTEM:    err = gpg_error_from_syserror (); break;
278 #endif
279     default:            err = gpg_error (GPG_ERR_UNKNOWN_ERRNO); break;
280     }
281   return err;
282 }
283
284
285 #ifdef USE_LIBDNS
286 static gpg_error_t
287 libdns_error_to_gpg_error (int serr)
288 {
289   gpg_err_code_t ec;
290
291   switch (serr)
292     {
293     case 0: ec = 0; break;
294
295     case DNS_ENOBUFS:  ec = GPG_ERR_BUFFER_TOO_SHORT; break;
296     case DNS_EILLEGAL: ec = GPG_ERR_INV_OBJ; break;
297     case DNS_EORDER:   ec = GPG_ERR_INV_ORDER; break;
298     case DNS_ESECTION: ec = GPG_ERR_DNS_SECTION; break;
299     case DNS_EUNKNOWN: ec = GPG_ERR_DNS_UNKNOWN; break;
300     case DNS_EADDRESS: ec = GPG_ERR_DNS_ADDRESS; break;
301     case DNS_ENOQUERY: ec = GPG_ERR_DNS_NO_QUERY; break;
302     case DNS_ENOANSWER:ec = GPG_ERR_DNS_NO_ANSWER; break;
303     case DNS_EFETCHED: ec = GPG_ERR_ALREADY_FETCHED; break;
304     case DNS_ESERVICE: ec = GPG_ERR_NOT_SUPPORTED; break;
305     case DNS_ENONAME:  ec = GPG_ERR_NO_NAME; break;
306     case DNS_EFAIL:    ec = GPG_ERR_SERVER_FAILED; break;
307     case DNS_ECONNFIN: ec = GPG_ERR_DNS_CLOSED; break;
308     case DNS_EVERIFY:  ec = GPG_ERR_DNS_VERIFY; break;
309
310     default:
311       if (serr >= 0)
312         ec = gpg_err_code_from_errno (serr);
313       else
314         ec = GPG_ERR_DNS_UNKNOWN;
315       break;
316     }
317   return gpg_error (ec);
318 }
319 #endif /*USE_LIBDNS*/
320
321
322 #ifdef USE_LIBDNS
323 /* Initialize libdns.  Returns 0 on success; prints a diagnostic and
324  * returns an error code on failure.  */
325 static gpg_error_t
326 libdns_init (void)
327 {
328   gpg_error_t err;
329   struct libdns_s ld;
330   int derr;
331   char *cfgstr = NULL;
332
333   if (libdns.resolv_conf)
334     return 0; /* Already initialized.  */
335
336   memset (&ld, 0, sizeof ld);
337
338   ld.resolv_conf = dns_resconf_open (&derr);
339   if (!ld.resolv_conf)
340     {
341       err = libdns_error_to_gpg_error (derr);
342       log_error ("failed to allocate DNS resconf object: %s\n",
343                  gpg_strerror (err));
344       goto leave;
345     }
346
347   if (tor_mode)
348     {
349       if (!*tor_nameserver)
350         set_dns_nameserver (NULL);
351
352       if (!libdns_tor_port)
353         libdns_tor_port = TOR_PORT;
354
355       cfgstr = xtryasprintf ("[%s]:53", tor_nameserver);
356       if (!cfgstr)
357         err = gpg_error_from_syserror ();
358       else
359         err = libdns_error_to_gpg_error
360           (dns_resconf_pton (&ld.resolv_conf->nameserver[0], cfgstr));
361       if (err)
362         log_error ("failed to set nameserver '%s': %s\n",
363                    cfgstr, gpg_strerror (err));
364       if (err)
365         goto leave;
366
367       ld.resolv_conf->options.tcp = DNS_RESCONF_TCP_SOCKS;
368
369       xfree (cfgstr);
370       cfgstr = xtryasprintf ("[%s]:%d", "127.0.0.1", libdns_tor_port);
371       if (!cfgstr)
372         err = gpg_error_from_syserror ();
373       else
374         err = libdns_error_to_gpg_error
375           (dns_resconf_pton (&ld.socks_host, cfgstr));
376       if (err)
377         {
378           log_error ("failed to set socks server '%s': %s\n",
379                      cfgstr, gpg_strerror (err));
380           goto leave;
381         }
382     }
383   else
384     {
385 #ifdef HAVE_W32_SYSTEM
386       ULONG ninfo_len;
387       PFIXED_INFO ninfo;
388       PIP_ADDR_STRING pip;
389       int idx;
390
391       ninfo_len = 2048;
392       ninfo = xtrymalloc (ninfo_len);
393       if (!ninfo)
394         {
395           err = gpg_error_from_syserror ();
396           goto leave;
397         }
398
399       if (GetNetworkParams (ninfo, &ninfo_len))
400         {
401           log_error ("GetNetworkParms failed: %s\n", w32_strerror (-1));
402           err = gpg_error (GPG_ERR_GENERAL);
403           xfree (ninfo);
404           goto leave;
405         }
406
407       for (idx=0, pip = &(ninfo->DnsServerList);
408            pip && idx < DIM (ld.resolv_conf->nameserver);
409            pip = pip->Next)
410         {
411           log_debug ("ninfo->dnsserver[%d] '%s'\n", idx, pip->IpAddress.String);
412           err = libdns_error_to_gpg_error
413             (dns_resconf_pton (&ld.resolv_conf->nameserver[idx],
414                                pip->IpAddress.String));
415           if (err)
416             log_error ("failed to set nameserver[%d] '%s': %s\n",
417                        idx, pip->IpAddress.String, gpg_strerror (err));
418           else
419             idx++;
420         }
421       xfree (ninfo);
422
423 #else /* Unix */
424       const char *fname;
425
426       fname = "/etc/resolv.conf";
427       err = libdns_error_to_gpg_error
428         (dns_resconf_loadpath (ld.resolv_conf, fname));
429       if (err)
430         {
431           log_error ("failed to load '%s': %s\n", fname, gpg_strerror (err));
432           goto leave;
433         }
434
435       fname = "/etc/nsswitch.conf";
436       err = libdns_error_to_gpg_error
437         (dns_nssconf_loadpath (ld.resolv_conf, fname));
438       if (err)
439         {
440           log_error ("failed to load '%s': %s\n", fname, gpg_strerror (err));
441           goto leave;
442         }
443
444 #endif /* Unix */
445     }
446
447   ld.hosts = dns_hosts_open (&derr);
448   if (!ld.hosts)
449     {
450       log_error ("failed to load hosts file: %s\n", gpg_strerror (err));
451       err = libdns_error_to_gpg_error (derr);
452       goto leave;
453     }
454
455   /* dns_hints_local for stub mode, dns_hints_root for recursive.  */
456   ld.hints = (recursive_resolver
457               ? dns_hints_root  (ld.resolv_conf, &derr)
458               : dns_hints_local (ld.resolv_conf, &derr));
459   if (!ld.hints)
460     {
461       log_error ("failed to load DNS hints: %s\n", gpg_strerror (err));
462       err = libdns_error_to_gpg_error (derr);
463       goto leave;
464     }
465
466   /* All fine.  Make the data global.  */
467   libdns = ld;
468
469  leave:
470   xfree (cfgstr);
471   return err;
472 }
473 #endif /*USE_LIBDNS*/
474
475
476 #ifdef USE_LIBDNS
477 /* Deinitialize libdns.  */
478 static void
479 libdns_deinit (void)
480 {
481   struct libdns_s ld;
482
483   if (!libdns.resolv_conf)
484     return; /* Not initialized.  */
485
486   ld = libdns;
487   memset (&libdns, 0, sizeof libdns);
488   dns_hints_close (ld.hints);
489   dns_hosts_close (ld.hosts);
490   dns_resconf_close (ld.resolv_conf);
491 }
492 #endif /*USE_LIBDNS*/
493
494
495 /* SIGHUP action handler for this module.  With FORCE set objects are
496  * all immediately released. */
497 void
498 reload_dns_stuff (int force)
499 {
500   if (force)
501     {
502 #ifdef USE_LIBDNS
503       libdns_deinit ();
504 #endif
505       libdns_reinit_pending = 0;
506     }
507   else
508     libdns_reinit_pending = 1;
509 }
510
511
512 #ifdef USE_LIBDNS
513 /*
514  * Initialize libdns if needed and open a dns_resolver context.
515  * Returns 0 on success and stores the new context at R_RES.  On
516  * failure an error code is returned and NULL stored at R_RES.
517  */
518 static gpg_error_t
519 libdns_res_open (struct dns_resolver **r_res)
520 {
521   gpg_error_t err;
522   struct dns_resolver *res;
523   int derr;
524
525   *r_res = NULL;
526
527   if (libdns_reinit_pending)
528     {
529       libdns_reinit_pending = 0;
530       libdns_deinit ();
531     }
532
533   err = libdns_init ();
534   if (err)
535     return err;
536
537   res = dns_res_open (libdns.resolv_conf, libdns.hosts, libdns.hints, NULL,
538                       dns_opts (.socks_host     = &libdns.socks_host,
539                                 .socks_user     = tor_socks_user,
540                                 .socks_password = tor_socks_password ),
541                       &derr);
542   if (!res)
543     return libdns_error_to_gpg_error (derr);
544
545   *r_res = res;
546   return 0;
547 }
548 #endif /*USE_LIBDNS*/
549
550
551 #ifdef USE_LIBDNS
552 /* Helper to test whether we need totry again after having swicthed
553  * the Tor port.  */
554 static int
555 libdns_switch_port_p (gpg_error_t err)
556 {
557   if (tor_mode && gpg_err_code (err) == GPG_ERR_ECONNREFUSED
558       && libdns_tor_port == TOR_PORT)
559     {
560       /* Switch port and try again.  */
561       libdns_tor_port = TOR_PORT2;
562       libdns_reinit_pending = 1;
563       return 1;
564     }
565   return 0;
566 }
567 #endif /*USE_LIBDNS*/
568
569
570 #ifdef USE_LIBDNS
571 /* Wrapper around dns_res_submit.  */
572 static gpg_error_t
573 libdns_res_submit (struct dns_resolver *res, const char *qname,
574                    enum dns_type qtype, enum dns_class qclass)
575 {
576   return libdns_error_to_gpg_error (dns_res_submit (res, qname, qtype, qclass));
577 }
578 #endif /*USE_LIBDNS*/
579
580
581 #ifdef USE_LIBDNS
582 /* Standard event handling loop.  */
583 gpg_error_t
584 libdns_res_wait (struct dns_resolver *res)
585 {
586   gpg_error_t err;
587
588   while ((err = libdns_error_to_gpg_error (dns_res_check (res)))
589          && gpg_err_code (err) == GPG_ERR_EAGAIN)
590     {
591       if (dns_res_elapsed (res) > 30)
592         {
593           err = gpg_error (GPG_ERR_DNS_TIMEOUT);
594           break;
595         }
596
597       my_unprotect ();
598       dns_res_poll (res, 1);
599       my_protect ();
600     }
601
602   return err;
603 }
604 #endif /*USE_LIBDNS*/
605
606
607 #ifdef USE_LIBDNS
608 static gpg_error_t
609 resolve_name_libdns (const char *name, unsigned short port,
610                      int want_family, int want_socktype,
611                      dns_addrinfo_t *r_dai, char **r_canonname)
612 {
613   gpg_error_t err;
614   dns_addrinfo_t daihead = NULL;
615   dns_addrinfo_t dai;
616   struct dns_resolver *res = NULL;
617   struct dns_addrinfo *ai = NULL;
618   struct addrinfo hints;
619   struct addrinfo *ent;
620   char portstr_[21];
621   char *portstr = NULL;
622   int derr;
623
624   *r_dai = NULL;
625   if (r_canonname)
626     *r_canonname = NULL;
627
628   memset (&hints, 0, sizeof hints);
629   hints.ai_family = want_family;
630   hints.ai_socktype = want_socktype;
631   hints.ai_flags = AI_ADDRCONFIG;
632   if (r_canonname)
633     hints.ai_flags |= AI_CANONNAME;
634
635   if (port)
636     {
637       snprintf (portstr_, sizeof portstr_, "%hu", port);
638       portstr = portstr_;
639     }
640
641   err = libdns_res_open (&res);
642   if (err)
643     goto leave;
644
645   ai = dns_ai_open (name, portstr, 0, &hints, res, &derr);
646   if (!ai)
647     {
648       err = libdns_error_to_gpg_error (derr);
649       goto leave;
650     }
651
652   /* Loop over all records.  */
653   for (;;)
654     {
655       err = libdns_error_to_gpg_error (dns_ai_nextent (&ent, ai));
656       if (gpg_err_code (err) == GPG_ERR_ENOENT)
657         {
658           if (daihead)
659             err = 0; /* We got some results, we're good.  */
660           break; /* Ready.  */
661         }
662       if (gpg_err_code (err) == GPG_ERR_EAGAIN)
663         {
664           if (dns_ai_elapsed (ai) > 30)
665             {
666               err = gpg_error (GPG_ERR_DNS_TIMEOUT);
667               goto leave;
668             }
669
670           my_unprotect ();
671           dns_ai_poll (ai, 1);
672           my_protect ();
673           continue;
674         }
675       if (err)
676         goto leave;
677
678       if (r_canonname && ! *r_canonname && ent && ent->ai_canonname)
679         {
680           *r_canonname = xtrystrdup (ent->ai_canonname);
681           if (!*r_canonname)
682             {
683               err = gpg_error_from_syserror ();
684               goto leave;
685             }
686         }
687
688       dai = xtrymalloc (sizeof *dai + ent->ai_addrlen -1);
689       if (dai == NULL)
690         {
691           err = gpg_error_from_syserror ();
692           goto leave;
693         }
694
695       dai->family = ent->ai_family;
696       dai->socktype = ent->ai_socktype;
697       dai->protocol = ent->ai_protocol;
698       dai->addrlen = ent->ai_addrlen;
699       memcpy (dai->addr, ent->ai_addr, ent->ai_addrlen);
700       dai->next = daihead;
701       daihead = dai;
702
703       xfree (ent);
704   }
705
706  leave:
707   dns_ai_close (ai);
708   dns_res_close (res);
709
710   if (err)
711     {
712       if (r_canonname)
713         {
714           xfree (*r_canonname);
715           *r_canonname = NULL;
716         }
717       free_dns_addrinfo (daihead);
718     }
719   else
720     *r_dai = daihead;
721
722   return err;
723 }
724 #endif /*USE_LIBDNS*/
725
726
727 /* Resolve a name using the standard system function.  */
728 static gpg_error_t
729 resolve_name_standard (const char *name, unsigned short port,
730                        int want_family, int want_socktype,
731                        dns_addrinfo_t *r_dai, char **r_canonname)
732 {
733   gpg_error_t err = 0;
734   dns_addrinfo_t daihead = NULL;
735   dns_addrinfo_t dai;
736   struct addrinfo *aibuf = NULL;
737   struct addrinfo hints, *ai;
738   char portstr[21];
739   int ret;
740
741   *r_dai = NULL;
742   if (r_canonname)
743     *r_canonname = NULL;
744
745   memset (&hints, 0, sizeof hints);
746   hints.ai_family = want_family;
747   hints.ai_socktype = want_socktype;
748   hints.ai_flags = AI_ADDRCONFIG;
749   if (r_canonname)
750     hints.ai_flags |= AI_CANONNAME;
751
752   if (port)
753     snprintf (portstr, sizeof portstr, "%hu", port);
754   else
755     *portstr = 0;
756
757   /* We can't use the the AI_IDN flag because that does the conversion
758      using the current locale.  However, GnuPG always used UTF-8.  To
759      support IDN we would need to make use of the libidn API.  */
760   ret = getaddrinfo (name, *portstr? portstr : NULL, &hints, &aibuf);
761   if (ret)
762     {
763       aibuf = NULL;
764       err = map_eai_to_gpg_error (ret);
765       if (gpg_err_code (err) == GPG_ERR_NO_NAME)
766         {
767           /* There seems to be a bug in the glibc getaddrinfo function
768              if the CNAME points to a long list of A and AAAA records
769              in which case the function return NO_NAME.  Let's do the
770              CNAME redirection again.  */
771           char *cname;
772
773           if (get_dns_cname (name, &cname))
774             goto leave; /* Still no success.  */
775
776           ret = getaddrinfo (cname, *portstr? portstr : NULL, &hints, &aibuf);
777           xfree (cname);
778           if (ret)
779             {
780               aibuf = NULL;
781               err = map_eai_to_gpg_error (ret);
782               goto leave;
783             }
784           err = 0; /* Yep, now it worked.  */
785         }
786       else
787         goto leave;
788     }
789
790   if (r_canonname && aibuf && aibuf->ai_canonname)
791     {
792       *r_canonname = xtrystrdup (aibuf->ai_canonname);
793       if (!*r_canonname)
794         {
795           err = gpg_error_from_syserror ();
796           goto leave;
797         }
798     }
799
800   for (ai = aibuf; ai; ai = ai->ai_next)
801     {
802       if (ai->ai_family != AF_INET6 && ai->ai_family != AF_INET)
803         continue;
804
805       dai = xtrymalloc (sizeof *dai + ai->ai_addrlen - 1);
806       dai->family = ai->ai_family;
807       dai->socktype = ai->ai_socktype;
808       dai->protocol = ai->ai_protocol;
809       dai->addrlen = ai->ai_addrlen;
810       memcpy (dai->addr, ai->ai_addr, ai->ai_addrlen);
811       dai->next = daihead;
812       daihead = dai;
813     }
814
815  leave:
816   if (aibuf)
817     freeaddrinfo (aibuf);
818   if (err)
819     {
820       if (r_canonname)
821         {
822           xfree (*r_canonname);
823           *r_canonname = NULL;
824         }
825       free_dns_addrinfo (daihead);
826     }
827   else
828     *r_dai = daihead;
829   return err;
830 }
831
832
833 /* Resolve an address using the standard system function.  */
834 static gpg_error_t
835 resolve_addr_standard (const struct sockaddr *addr, int addrlen,
836                        unsigned int flags, char **r_name)
837 {
838   gpg_error_t err;
839   int ec;
840   char *buffer, *p;
841   int buflen;
842
843   *r_name = NULL;
844
845   buflen = NI_MAXHOST;
846   buffer = xtrymalloc (buflen + 2 + 1);
847   if (!buffer)
848     return gpg_error_from_syserror ();
849
850   if ((flags & DNS_NUMERICHOST) || tor_mode)
851     ec = EAI_NONAME;
852   else
853     ec = getnameinfo (addr, addrlen, buffer, buflen, NULL, 0, NI_NAMEREQD);
854
855   if (!ec && *buffer == '[')
856     ec = EAI_FAIL;  /* A name may never start with a bracket.  */
857   else if (ec == EAI_NONAME)
858     {
859       p = buffer;
860       if (addr->sa_family == AF_INET6 && (flags & DNS_WITHBRACKET))
861         {
862           *p++ = '[';
863           buflen -= 2;
864         }
865       ec = getnameinfo (addr, addrlen, p, buflen, NULL, 0, NI_NUMERICHOST);
866       if (!ec && addr->sa_family == AF_INET6 && (flags & DNS_WITHBRACKET))
867         strcat (buffer, "]");
868     }
869
870   if (ec)
871     err = map_eai_to_gpg_error (ec);
872   else
873     {
874       p = xtryrealloc (buffer, strlen (buffer)+1);
875       if (!p)
876         err = gpg_error_from_syserror ();
877       else
878         {
879           buffer = p;
880           err = 0;
881         }
882     }
883
884   if (err)
885     xfree (buffer);
886   else
887     *r_name = buffer;
888
889   return err;
890 }
891
892
893 /* This a wrapper around getaddrinfo with slightly different semantics.
894    NAME is the name to resolve.
895    PORT is the requested port or 0.
896    WANT_FAMILY is either 0 (AF_UNSPEC), AF_INET6, or AF_INET4.
897    WANT_SOCKETTYPE is either SOCK_STREAM or SOCK_DGRAM.
898
899    On success the result is stored in a linked list with the head
900    stored at the address R_AI; the caller must call gpg_addrinfo_free
901    on this.  If R_CANONNAME is not NULL the official name of the host
902    is stored there as a malloced string; if that name is not available
903    NULL is stored.  */
904 gpg_error_t
905 resolve_dns_name (const char *name, unsigned short port,
906                   int want_family, int want_socktype,
907                   dns_addrinfo_t *r_ai, char **r_canonname)
908 {
909 #ifdef USE_LIBDNS
910   if (!standard_resolver)
911     {
912       gpg_error_t err;
913
914       err = resolve_name_libdns (name, port, want_family, want_socktype,
915                                   r_ai, r_canonname);
916       if (err && libdns_switch_port_p (err))
917         err = resolve_name_libdns (name, port, want_family, want_socktype,
918                                    r_ai, r_canonname);
919       return err;
920     }
921 #endif /*USE_LIBDNS*/
922
923   return resolve_name_standard (name, port, want_family, want_socktype,
924                                 r_ai, r_canonname);
925 }
926
927
928 gpg_error_t
929 resolve_dns_addr (const struct sockaddr *addr, int addrlen,
930                   unsigned int flags, char **r_name)
931 {
932   return resolve_addr_standard (addr, addrlen, flags, r_name);
933 }
934
935
936 /* Check whether NAME is an IP address.  Returns true if it is either
937    an IPv6 or IPv4 numerical address.  */
938 int
939 is_ip_address (const char *name)
940 {
941   const char *s;
942   int ndots, dblcol, n;
943
944   if (*name == '[')
945     return 1; /* yes: A legal DNS name may not contain this character;
946                  this mut be bracketed v6 address.  */
947   if (*name == '.')
948     return 0; /* No.  A leading dot is not a valid IP address.  */
949
950   /* Check whether this is a v6 address.  */
951   ndots = n = dblcol = 0;
952   for (s=name; *s; s++)
953     {
954       if (*s == ':')
955         {
956           ndots++;
957           if (s[1] == ':')
958             {
959               ndots++;
960               if (dblcol)
961                 return 0; /* No: Only one "::" allowed.  */
962               dblcol++;
963               if (s[1])
964                 s++;
965             }
966           n = 0;
967         }
968       else if (*s == '.')
969         goto legacy;
970       else if (!strchr ("0123456789abcdefABCDEF", *s))
971         return 0; /* No: Not a hex digit.  */
972       else if (++n > 4)
973         return 0; /* To many digits in a group.  */
974     }
975   if (ndots > 7)
976     return 0; /* No: Too many colons.  */
977   else if (ndots > 1)
978     return 1; /* Yes: At least 2 colons indicate an v6 address.  */
979
980  legacy:
981   /* Check whether it is legacy IP address.  */
982   ndots = n = 0;
983   for (s=name; *s; s++)
984     {
985       if (*s == '.')
986         {
987           if (s[1] == '.')
988             return 0; /* No:  Douple dot. */
989           if (atoi (s+1) > 255)
990             return 0; /* No:  Ipv4 byte value too large.  */
991           ndots++;
992           n = 0;
993         }
994       else if (!strchr ("0123456789", *s))
995         return 0; /* No: Not a digit.  */
996       else if (++n > 3)
997         return 0; /* No: More than 3 digits.  */
998     }
999   return !!(ndots == 3);
1000 }
1001
1002
1003 /* Return true if NAME is an onion address.  */
1004 int
1005 is_onion_address (const char *name)
1006 {
1007   size_t len;
1008
1009   len = name? strlen (name) : 0;
1010   if (len < 8 || strcmp (name + len - 6, ".onion"))
1011     return 0;
1012   /* Note that we require at least 2 characters before the suffix.  */
1013   return 1;  /* Yes.  */
1014 }
1015
1016
1017 /* libdns version of get_dns_cert.  */
1018 #ifdef USE_LIBDNS
1019 static gpg_error_t
1020 get_dns_cert_libdns (const char *name, int want_certtype,
1021                      void **r_key, size_t *r_keylen,
1022                      unsigned char **r_fpr, size_t *r_fprlen, char **r_url)
1023 {
1024   gpg_error_t err;
1025   struct dns_resolver *res = NULL;
1026   struct dns_packet *ans = NULL;
1027   struct dns_rr rr;
1028   struct dns_rr_i rri;
1029   char host[DNS_D_MAXNAME + 1];
1030   int derr;
1031   int qtype;
1032
1033   /* Gte the query type from WANT_CERTTYPE (which in general indicates
1034    * the subtype we want). */
1035   qtype = (want_certtype < DNS_CERTTYPE_RRBASE
1036            ? T_CERT
1037            : (want_certtype - DNS_CERTTYPE_RRBASE));
1038
1039
1040   err = libdns_res_open (&res);
1041   if (err)
1042     goto leave;
1043
1044   if (dns_d_anchor (host, sizeof host, name, strlen (name)) >= sizeof host)
1045     {
1046       err = gpg_error (GPG_ERR_ENAMETOOLONG);
1047       goto leave;
1048     }
1049
1050   err = libdns_res_submit (res, name, qtype, DNS_C_IN);
1051   if (err)
1052     goto leave;
1053
1054   err = libdns_res_wait (res);
1055   if (err)
1056     goto leave;
1057
1058   ans = dns_res_fetch (res, &derr);
1059   if (!ans)
1060     {
1061       err = libdns_error_to_gpg_error (derr);
1062       goto leave;
1063     }
1064
1065   /* Check the rcode.  */
1066   switch (dns_p_rcode (ans))
1067     {
1068     case DNS_RC_NOERROR: break;
1069     case DNS_RC_NXDOMAIN: err = gpg_error (GPG_ERR_NO_NAME); break;
1070     default: err = GPG_ERR_SERVER_FAILED; break;
1071     }
1072   if (err)
1073     goto leave;
1074
1075   memset (&rri, 0, sizeof rri);
1076   dns_rr_i_init (&rri, ans);
1077   rri.section = DNS_S_ALL & ~DNS_S_QD;
1078   rri.name    = host;
1079   rri.type    = qtype;
1080
1081   err = gpg_error (GPG_ERR_NOT_FOUND);
1082   while (dns_rr_grep (&rr, 1, &rri, ans, &derr))
1083     {
1084       unsigned char *rp  = ans->data + rr.rd.p;
1085       unsigned short len = rr.rd.len;
1086       u16 subtype;
1087
1088        if (!len)
1089         {
1090           /* Definitely too short - skip.  */
1091         }
1092       else if (want_certtype >= DNS_CERTTYPE_RRBASE
1093           && rr.type == (want_certtype - DNS_CERTTYPE_RRBASE)
1094           && r_key)
1095         {
1096           *r_key = xtrymalloc (len);
1097           if (!*r_key)
1098             err = gpg_error_from_syserror ();
1099           else
1100             {
1101               memcpy (*r_key, rp, len);
1102               *r_keylen = len;
1103               err = 0;
1104             }
1105           goto leave;
1106         }
1107       else if (want_certtype >= DNS_CERTTYPE_RRBASE)
1108         {
1109           /* We did not found the requested RR - skip. */
1110         }
1111       else if (rr.type == T_CERT && len > 5)
1112         {
1113           /* We got a CERT type.   */
1114           subtype = buf16_to_u16 (rp);
1115           rp += 2; len -= 2;
1116
1117           /* Skip the CERT key tag and algo which we don't need.  */
1118           rp += 3; len -= 3;
1119
1120           if (want_certtype && want_certtype != subtype)
1121             ; /* Not the requested subtype - skip.  */
1122           else if (subtype == DNS_CERTTYPE_PGP && len && r_key && r_keylen)
1123             {
1124               /* PGP subtype */
1125               *r_key = xtrymalloc (len);
1126               if (!*r_key)
1127                 err = gpg_error_from_syserror ();
1128               else
1129                 {
1130                   memcpy (*r_key, rp, len);
1131                   *r_keylen = len;
1132                   err = 0;
1133                 }
1134               goto leave;
1135             }
1136           else if (subtype == DNS_CERTTYPE_IPGP
1137                    && len && len < 1023 && len >= rp[0] + 1)
1138             {
1139               /* IPGP type */
1140               *r_fprlen = rp[0];
1141               if (*r_fprlen)
1142                 {
1143                   *r_fpr = xtrymalloc (*r_fprlen);
1144                   if (!*r_fpr)
1145                     {
1146                       err = gpg_error_from_syserror ();
1147                       goto leave;
1148                     }
1149                   memcpy (*r_fpr, rp+1, *r_fprlen);
1150                 }
1151               else
1152                 *r_fpr = NULL;
1153
1154               if (len > *r_fprlen + 1)
1155                 {
1156                   *r_url = xtrymalloc (len - (*r_fprlen + 1) + 1);
1157                   if (!*r_url)
1158                     {
1159                       err = gpg_error_from_syserror ();
1160                       xfree (*r_fpr);
1161                       *r_fpr = NULL;
1162                       goto leave;
1163                     }
1164                   memcpy (*r_url, rp + *r_fprlen + 1, len - (*r_fprlen + 1));
1165                   (*r_url)[len - (*r_fprlen + 1)] = 0;
1166                 }
1167               else
1168                 *r_url = NULL;
1169
1170               err = 0;
1171               goto leave;
1172             }
1173           else
1174             {
1175               /* Unknown subtype or record too short - skip.  */
1176             }
1177         }
1178       else
1179         {
1180           /* Not a requested type - skip.  */
1181         }
1182     }
1183
1184  leave:
1185   dns_free (ans);
1186   dns_res_close (res);
1187   return err;
1188 }
1189 #endif /*USE_LIBDNS*/
1190
1191
1192 /* Standard resolver version of get_dns_cert.  */
1193 static gpg_error_t
1194 get_dns_cert_standard (const char *name, int want_certtype,
1195                        void **r_key, size_t *r_keylen,
1196                        unsigned char **r_fpr, size_t *r_fprlen, char **r_url)
1197 {
1198 #ifdef HAVE_SYSTEM_RESOLVER
1199   gpg_error_t err;
1200   unsigned char *answer;
1201   int r;
1202   u16 count;
1203
1204   /* Allocate a 64k buffer which is the limit for an DNS response.  */
1205   answer = xtrymalloc (65536);
1206   if (!answer)
1207     return gpg_error_from_syserror ();
1208
1209   err = gpg_error (GPG_ERR_NOT_FOUND);
1210   r = res_query (name, C_IN,
1211                  (want_certtype < DNS_CERTTYPE_RRBASE
1212                   ? T_CERT
1213                   : (want_certtype - DNS_CERTTYPE_RRBASE)),
1214                  answer, 65536);
1215   /* Not too big, not too small, no errors and at least 1 answer. */
1216   if (r >= sizeof (HEADER) && r <= 65536
1217       && (((HEADER *)(void *) answer)->rcode) == NOERROR
1218       && (count = ntohs (((HEADER *)(void *) answer)->ancount)))
1219     {
1220       int rc;
1221       unsigned char *pt, *emsg;
1222
1223       emsg = &answer[r];
1224
1225       pt = &answer[sizeof (HEADER)];
1226
1227       /* Skip over the query */
1228
1229       rc = dn_skipname (pt, emsg);
1230       if (rc == -1)
1231         {
1232           err = gpg_error (GPG_ERR_INV_OBJ);
1233           goto leave;
1234         }
1235       pt += rc + QFIXEDSZ;
1236
1237       /* There are several possible response types for a CERT request.
1238          We're interested in the PGP (a key) and IPGP (a URI) types.
1239          Skip all others.  TODO: A key is better than a URI since
1240          we've gone through all this bother to fetch it, so favor that
1241          if we have both PGP and IPGP? */
1242
1243       while (count-- > 0 && pt < emsg)
1244         {
1245           u16 type, class, dlen, ctype;
1246
1247           rc = dn_skipname (pt, emsg);  /* the name we just queried for */
1248           if (rc == -1)
1249             {
1250               err = gpg_error (GPG_ERR_INV_OBJ);
1251               goto leave;
1252             }
1253
1254           pt += rc;
1255
1256           /* Truncated message? 15 bytes takes us to the point where
1257              we start looking at the ctype. */
1258           if ((emsg - pt) < 15)
1259             break;
1260
1261           type = buf16_to_u16 (pt);
1262           pt += 2;
1263
1264           class = buf16_to_u16 (pt);
1265           pt += 2;
1266
1267           if (class != C_IN)
1268             break;
1269
1270           /* ttl */
1271           pt += 4;
1272
1273           /* data length */
1274           dlen = buf16_to_u16 (pt);
1275           pt += 2;
1276
1277           /* Check the type and parse.  */
1278           if (want_certtype >= DNS_CERTTYPE_RRBASE
1279               && type == (want_certtype - DNS_CERTTYPE_RRBASE)
1280               && r_key)
1281             {
1282               *r_key = xtrymalloc (dlen);
1283               if (!*r_key)
1284                 err = gpg_error_from_syserror ();
1285               else
1286                 {
1287                   memcpy (*r_key, pt, dlen);
1288                   *r_keylen = dlen;
1289                   err = 0;
1290                 }
1291               goto leave;
1292             }
1293           else if (want_certtype >= DNS_CERTTYPE_RRBASE)
1294             {
1295               /* We did not found the requested RR.  */
1296               pt += dlen;
1297             }
1298           else if (type == T_CERT)
1299             {
1300               /* We got a CERT type.   */
1301               ctype = buf16_to_u16 (pt);
1302               pt += 2;
1303
1304               /* Skip the CERT key tag and algo which we don't need. */
1305               pt += 3;
1306
1307               dlen -= 5;
1308
1309               /* 15 bytes takes us to here */
1310               if (want_certtype && want_certtype != ctype)
1311                 ; /* Not of the requested certtype.  */
1312               else if (ctype == DNS_CERTTYPE_PGP && dlen && r_key && r_keylen)
1313                 {
1314                   /* PGP type */
1315                   *r_key = xtrymalloc (dlen);
1316                   if (!*r_key)
1317                     err = gpg_error_from_syserror ();
1318                   else
1319                     {
1320                       memcpy (*r_key, pt, dlen);
1321                       *r_keylen = dlen;
1322                       err = 0;
1323                     }
1324                   goto leave;
1325                 }
1326               else if (ctype == DNS_CERTTYPE_IPGP
1327                        && dlen && dlen < 1023 && dlen >= pt[0] + 1)
1328                 {
1329                   /* IPGP type */
1330                   *r_fprlen = pt[0];
1331                   if (*r_fprlen)
1332                     {
1333                       *r_fpr = xtrymalloc (*r_fprlen);
1334                       if (!*r_fpr)
1335                         {
1336                           err = gpg_error_from_syserror ();
1337                           goto leave;
1338                         }
1339                       memcpy (*r_fpr, &pt[1], *r_fprlen);
1340                     }
1341                   else
1342                     *r_fpr = NULL;
1343
1344                   if (dlen > *r_fprlen + 1)
1345                     {
1346                       *r_url = xtrymalloc (dlen - (*r_fprlen + 1) + 1);
1347                       if (!*r_url)
1348                         {
1349                           err = gpg_error_from_syserror ();
1350                           xfree (*r_fpr);
1351                           *r_fpr = NULL;
1352                           goto leave;
1353                         }
1354                       memcpy (*r_url, &pt[*r_fprlen + 1],
1355                               dlen - (*r_fprlen + 1));
1356                       (*r_url)[dlen - (*r_fprlen + 1)] = '\0';
1357                     }
1358                   else
1359                     *r_url = NULL;
1360
1361                   err = 0;
1362                   goto leave;
1363                 }
1364
1365               /* No subtype matches, so continue with the next answer. */
1366               pt += dlen;
1367             }
1368           else
1369             {
1370               /* Not a requested type - might be a CNAME. Try next item.  */
1371               pt += dlen;
1372             }
1373         }
1374     }
1375
1376  leave:
1377   xfree (answer);
1378   return err;
1379
1380 #else /*!HAVE_SYSTEM_RESOLVER*/
1381
1382   (void)name;
1383   (void)want_certtype;
1384   (void)r_key;
1385   (void)r_keylen;
1386   (void)r_fpr;
1387   (void)r_fprlen;
1388   (void)r_url;
1389   return gpg_error (GPG_ERR_NOT_SUPPORTED);
1390
1391 #endif /*!HAVE_SYSTEM_RESOLVER*/
1392 }
1393
1394
1395 /* Returns 0 on success or an error code.  If a PGP CERT record was
1396    found, the malloced data is returned at (R_KEY, R_KEYLEN) and
1397    the other return parameters are set to NULL/0.  If an IPGP CERT
1398    record was found the fingerprint is stored as an allocated block at
1399    R_FPR and its length at R_FPRLEN; an URL is is allocated as a
1400    string and returned at R_URL.  If WANT_CERTTYPE is 0 this function
1401    returns the first CERT found with a supported type; it is expected
1402    that only one CERT record is used.  If WANT_CERTTYPE is one of the
1403    supported certtypes only records with this certtype are considered
1404    and the first found is returned.  (R_KEY,R_KEYLEN) are optional. */
1405 gpg_error_t
1406 get_dns_cert (const char *name, int want_certtype,
1407               void **r_key, size_t *r_keylen,
1408               unsigned char **r_fpr, size_t *r_fprlen, char **r_url)
1409 {
1410   if (r_key)
1411     *r_key = NULL;
1412   if (r_keylen)
1413     *r_keylen = 0;
1414   *r_fpr = NULL;
1415   *r_fprlen = 0;
1416   *r_url = NULL;
1417
1418 #ifdef USE_LIBDNS
1419   if (!standard_resolver)
1420     {
1421       gpg_error_t err;
1422
1423       err = get_dns_cert_libdns (name, want_certtype, r_key, r_keylen,
1424                                  r_fpr, r_fprlen, r_url);
1425       if (err && libdns_switch_port_p (err))
1426         err = get_dns_cert_libdns (name, want_certtype, r_key, r_keylen,
1427                                    r_fpr, r_fprlen, r_url);
1428       return err;
1429     }
1430 #endif /*USE_LIBDNS*/
1431
1432   return get_dns_cert_standard (name, want_certtype, r_key, r_keylen,
1433                                 r_fpr, r_fprlen, r_url);
1434 }
1435
1436
1437 static int
1438 priosort(const void *a,const void *b)
1439 {
1440   const struct srventry *sa=a,*sb=b;
1441   if(sa->priority>sb->priority)
1442     return 1;
1443   else if(sa->priority<sb->priority)
1444     return -1;
1445   else
1446     return 0;
1447 }
1448
1449
1450 /* Libdns based helper for getsrv.  Note that it is expected that NULL
1451  * is stored at the address of LIST and 0 is stored at the address of
1452  * R_COUNT.  */
1453 #ifdef USE_LIBDNS
1454 static gpg_error_t
1455 getsrv_libdns (const char *name, struct srventry **list, int *r_count)
1456 {
1457   gpg_error_t err;
1458   struct dns_resolver *res = NULL;
1459   struct dns_packet *ans = NULL;
1460   struct dns_rr rr;
1461   struct dns_rr_i rri;
1462   char host[DNS_D_MAXNAME + 1];
1463   int derr;
1464   int srvcount=0;
1465
1466   err = libdns_res_open (&res);
1467   if (err)
1468     goto leave;
1469
1470   if (dns_d_anchor (host, sizeof host, name, strlen (name)) >= sizeof host)
1471     {
1472       err = gpg_error (GPG_ERR_ENAMETOOLONG);
1473       goto leave;
1474     }
1475
1476   err = libdns_res_submit (res, name, DNS_T_SRV, DNS_C_IN);
1477   if (err)
1478     goto leave;
1479
1480   err = libdns_res_wait (res);
1481   if (err)
1482     goto leave;
1483
1484   ans = dns_res_fetch (res, &derr);
1485   if (!ans)
1486     {
1487       err = libdns_error_to_gpg_error (derr);
1488       goto leave;
1489     }
1490
1491   /* Check the rcode.  */
1492   switch (dns_p_rcode (ans))
1493     {
1494     case DNS_RC_NOERROR: break;
1495     case DNS_RC_NXDOMAIN: err = gpg_error (GPG_ERR_NO_NAME); break;
1496     default: err = GPG_ERR_SERVER_FAILED; break;
1497     }
1498   if (err)
1499     goto leave;
1500
1501   memset (&rri, 0, sizeof rri);
1502   dns_rr_i_init (&rri, ans);
1503   rri.section = DNS_S_ALL & ~DNS_S_QD;
1504   rri.name        = host;
1505   rri.type        = DNS_T_SRV;
1506
1507   while (dns_rr_grep (&rr, 1, &rri, ans, &derr))
1508     {
1509       struct dns_srv dsrv;
1510       struct srventry *srv;
1511       struct srventry *newlist;
1512
1513       err = libdns_error_to_gpg_error (dns_srv_parse(&dsrv, &rr, ans));
1514       if (err)
1515         goto leave;
1516
1517       newlist = xtryrealloc (*list, (srvcount+1)*sizeof(struct srventry));
1518       if (!newlist)
1519         {
1520           err = gpg_error_from_syserror ();
1521           goto leave;
1522         }
1523       *list = newlist;
1524       memset (&(*list)[srvcount], 0, sizeof(struct srventry));
1525       srv = &(*list)[srvcount];
1526       srvcount++;
1527       srv->priority = dsrv.priority;
1528       srv->weight   = dsrv.weight;
1529       srv->port     = dsrv.port;
1530       mem2str (srv->target, dsrv.target, sizeof srv->target);
1531     }
1532
1533   *r_count = srvcount;
1534
1535  leave:
1536   if (err)
1537     {
1538       xfree (*list);
1539       *list = NULL;
1540     }
1541   dns_free (ans);
1542   dns_res_close (res);
1543   return err;
1544 }
1545 #endif /*USE_LIBDNS*/
1546
1547
1548 /* Standard resolver based helper for getsrv.  Note that it is
1549  * expected that NULL is stored at the address of LIST and 0 is stored
1550  * at the address of R_COUNT.  */
1551 static gpg_error_t
1552 getsrv_standard (const char *name, struct srventry **list, int *r_count)
1553 {
1554 #ifdef HAVE_SYSTEM_RESOLVER
1555   union {
1556     unsigned char ans[2048];
1557     HEADER header[1];
1558   } res;
1559   unsigned char *answer = res.ans;
1560   HEADER *header = res.header;
1561   unsigned char *pt, *emsg;
1562   int r, rc;
1563   u16 dlen;
1564   int srvcount=0;
1565   u16 count;
1566
1567   /* Do not allow a query using the standard resolver in Tor mode.  */
1568   if (tor_mode)
1569     return gpg_error (GPG_ERR_NOT_ENABLED);
1570
1571   my_unprotect ();
1572   r = res_query (name, C_IN, T_SRV, answer, sizeof res.ans);
1573   my_protect ();
1574   if (r < 0)
1575     return get_h_errno_as_gpg_error ();
1576   if (r < sizeof (HEADER))
1577     return gpg_error (GPG_ERR_SERVER_FAILED);
1578   if (r > sizeof res.ans)
1579     return gpg_error (GPG_ERR_SYSTEM_BUG);
1580   if (header->rcode != NOERROR || !(count=ntohs (header->ancount)))
1581     return gpg_error (GPG_ERR_NO_NAME); /* Error or no record found.  */
1582
1583   emsg = &answer[r];
1584   pt = &answer[sizeof(HEADER)];
1585
1586   /* Skip over the query */
1587   rc = dn_skipname (pt, emsg);
1588   if (rc == -1)
1589     goto fail;
1590
1591   pt += rc + QFIXEDSZ;
1592
1593   while (count-- > 0 && pt < emsg)
1594     {
1595       struct srventry *srv;
1596       u16 type, class;
1597       struct srventry *newlist;
1598
1599       newlist = xtryrealloc (*list, (srvcount+1)*sizeof(struct srventry));
1600       if (!newlist)
1601         goto fail;
1602       *list = newlist;
1603       memset (&(*list)[srvcount], 0, sizeof(struct srventry));
1604       srv = &(*list)[srvcount];
1605       srvcount++;
1606
1607       rc = dn_skipname (pt, emsg); /* The name we just queried for.  */
1608       if (rc == -1)
1609         goto fail;
1610       pt += rc;
1611
1612       /* Truncated message? */
1613       if ((emsg-pt) < 16)
1614         goto fail;
1615
1616       type = buf16_to_u16 (pt);
1617       pt += 2;
1618       /* We asked for SRV and got something else !? */
1619       if (type != T_SRV)
1620         goto fail;
1621
1622       class = buf16_to_u16 (pt);
1623       pt += 2;
1624       /* We asked for IN and got something else !? */
1625       if (class != C_IN)
1626         goto fail;
1627
1628       pt += 4; /* ttl */
1629       dlen = buf16_to_u16 (pt);
1630       pt += 2;
1631
1632       srv->priority = buf16_to_ushort (pt);
1633       pt += 2;
1634       srv->weight = buf16_to_ushort (pt);
1635       pt += 2;
1636       srv->port = buf16_to_ushort (pt);
1637       pt += 2;
1638
1639       /* Get the name.  2782 doesn't allow name compression, but
1640        * dn_expand still works to pull the name out of the packet. */
1641       rc = dn_expand (answer, emsg, pt, srv->target, sizeof srv->target);
1642       if (rc == 1 && srv->target[0] == 0) /* "." */
1643         {
1644           xfree(*list);
1645           *list = NULL;
1646           return 0;
1647         }
1648       if (rc == -1)
1649         goto fail;
1650       pt += rc;
1651       /* Corrupt packet? */
1652       if (dlen != rc+6)
1653         goto fail;
1654     }
1655
1656   *r_count = srvcount;
1657   return 0;
1658
1659  fail:
1660   xfree (*list);
1661   *list = NULL;
1662   return gpg_error (GPG_ERR_GENERAL);
1663
1664 #else /*!HAVE_SYSTEM_RESOLVER*/
1665
1666   (void)name;
1667   (void)list;
1668   (void)r_count;
1669   return gpg_error (GPG_ERR_NOT_SUPPORTED);
1670
1671 #endif /*!HAVE_SYSTEM_RESOLVER*/
1672 }
1673
1674
1675 int
1676 getsrv (const char *name, struct srventry **list)
1677 {
1678   gpg_error_t err;
1679   int srvcount;
1680   int i;
1681
1682   *list = NULL;
1683   srvcount = 0;
1684 #ifdef USE_LIBDNS
1685   if (!standard_resolver)
1686     {
1687       err = getsrv_libdns (name, list, &srvcount);
1688       if (err && libdns_switch_port_p (err))
1689         err = getsrv_libdns (name, list, &srvcount);
1690     }
1691   else
1692 #endif /*USE_LIBDNS*/
1693     err = getsrv_standard (name, list, &srvcount);
1694
1695   if (err)
1696     return -1;  /* Ugly.  FIXME: Return an error code. */
1697
1698   /* Now we have an array of all the srv records. */
1699
1700   /* Order by priority */
1701   qsort(*list,srvcount,sizeof(struct srventry),priosort);
1702
1703   /* For each priority, move the zero-weighted items first. */
1704   for (i=0; i < srvcount; i++)
1705     {
1706       int j;
1707
1708       for (j=i;j < srvcount && (*list)[i].priority == (*list)[j].priority; j++)
1709         {
1710           if((*list)[j].weight==0)
1711             {
1712               /* Swap j with i */
1713               if(j!=i)
1714                 {
1715                   struct srventry temp;
1716
1717                   memcpy (&temp,&(*list)[j],sizeof(struct srventry));
1718                   memcpy (&(*list)[j],&(*list)[i],sizeof(struct srventry));
1719                   memcpy (&(*list)[i],&temp,sizeof(struct srventry));
1720                 }
1721
1722               break;
1723             }
1724         }
1725     }
1726
1727   /* Run the RFC-2782 weighting algorithm.  We don't need very high
1728      quality randomness for this, so regular libc srand/rand is
1729      sufficient.  */
1730
1731   {
1732     static int done;
1733     if (!done)
1734       {
1735         done = 1;
1736         srand (time (NULL)*getpid());
1737       }
1738   }
1739
1740   for (i=0; i < srvcount; i++)
1741     {
1742       int j;
1743       float prio_count=0,chose;
1744
1745       for (j=i; j < srvcount && (*list)[i].priority == (*list)[j].priority; j++)
1746         {
1747           prio_count+=(*list)[j].weight;
1748           (*list)[j].run_count=prio_count;
1749         }
1750
1751       chose=prio_count*rand()/RAND_MAX;
1752
1753       for (j=i;j<srvcount && (*list)[i].priority==(*list)[j].priority;j++)
1754         {
1755           if (chose<=(*list)[j].run_count)
1756             {
1757               /* Swap j with i */
1758               if(j!=i)
1759                 {
1760                   struct srventry temp;
1761
1762                   memcpy(&temp,&(*list)[j],sizeof(struct srventry));
1763                   memcpy(&(*list)[j],&(*list)[i],sizeof(struct srventry));
1764                   memcpy(&(*list)[i],&temp,sizeof(struct srventry));
1765                 }
1766               break;
1767             }
1768         }
1769     }
1770
1771   return srvcount;
1772 }
1773
1774
1775 \f
1776 #ifdef USE_LIBDNS
1777 /* libdns version of get_dns_cname.  */
1778 gpg_error_t
1779 get_dns_cname_libdns (const char *name, char **r_cname)
1780 {
1781   gpg_error_t err;
1782   struct dns_resolver *res;
1783   struct dns_packet *ans = NULL;
1784   struct dns_cname cname;
1785   int derr;
1786
1787   err = libdns_res_open (&res);
1788   if (err)
1789     goto leave;
1790
1791   err = libdns_res_submit (res, name, DNS_T_CNAME, DNS_C_IN);
1792   if (err)
1793     goto leave;
1794
1795   err = libdns_res_wait (res);
1796   if (err)
1797     goto leave;
1798
1799   ans = dns_res_fetch (res, &derr);
1800   if (!ans)
1801     {
1802       err = libdns_error_to_gpg_error (derr);
1803       goto leave;
1804     }
1805
1806   /* Check the rcode.  */
1807   switch (dns_p_rcode (ans))
1808     {
1809     case DNS_RC_NOERROR: break;
1810     case DNS_RC_NXDOMAIN: err = gpg_error (GPG_ERR_NO_NAME); break;
1811     default: err = GPG_ERR_SERVER_FAILED; break;
1812     }
1813   if (err)
1814     goto leave;
1815
1816   /* Parse the result into CNAME.  */
1817   err = libdns_error_to_gpg_error (dns_p_study (ans));
1818   if (err)
1819     goto leave;
1820
1821   if (!dns_d_cname (&cname, sizeof cname, name, strlen (name), ans, &derr))
1822     {
1823       err = libdns_error_to_gpg_error (derr);
1824       goto leave;
1825     }
1826
1827   /* Copy result.  */
1828   *r_cname = xtrystrdup (cname.host);
1829   if (!*r_cname)
1830     err = gpg_error_from_syserror ();
1831
1832  leave:
1833   dns_free (ans);
1834   dns_res_close (res);
1835   return err;
1836 }
1837 #endif /*USE_LIBDNS*/
1838
1839
1840 /* Standard resolver version of get_dns_cname.  */
1841 gpg_error_t
1842 get_dns_cname_standard (const char *name, char **r_cname)
1843 {
1844 #ifdef HAVE_SYSTEM_RESOLVER
1845   gpg_error_t err;
1846   int rc;
1847   union {
1848     unsigned char ans[2048];
1849     HEADER header[1];
1850   } res;
1851   unsigned char *answer = res.ans;
1852   HEADER *header = res.header;
1853   unsigned char *pt, *emsg;
1854   int r;
1855   char *cname;
1856   int cnamesize = 1025;
1857   u16 count;
1858
1859   /* Do not allow a query using the standard resolver in Tor mode.  */
1860   if (tor_mode)
1861     return -1;
1862
1863   my_unprotect ();
1864   r = res_query (name, C_IN, T_CERT, answer, sizeof res.ans);
1865   my_protect ();
1866   if (r < 0)
1867     return get_h_errno_as_gpg_error ();
1868   if (r < sizeof (HEADER))
1869     return gpg_error (GPG_ERR_SERVER_FAILED);
1870   if (r > sizeof res.ans)
1871     return gpg_error (GPG_ERR_SYSTEM_BUG);
1872   if (header->rcode != NOERROR || !(count=ntohs (header->ancount)))
1873     return gpg_error (GPG_ERR_NO_NAME); /* Error or no record found.  */
1874   if (count != 1)
1875     return gpg_error (GPG_ERR_SERVER_FAILED);
1876
1877   emsg = &answer[r];
1878   pt = &answer[sizeof(HEADER)];
1879   rc = dn_skipname (pt, emsg);
1880   if (rc == -1)
1881     return gpg_error (GPG_ERR_SERVER_FAILED);
1882
1883   pt += rc + QFIXEDSZ;
1884   if (pt >= emsg)
1885     return gpg_error (GPG_ERR_SERVER_FAILED);
1886
1887   rc = dn_skipname (pt, emsg);
1888   if (rc == -1)
1889     return gpg_error (GPG_ERR_SERVER_FAILED);
1890   pt += rc + 2 + 2 + 4;
1891   if (pt+2 >= emsg)
1892     return gpg_error (GPG_ERR_SERVER_FAILED);
1893   pt += 2;  /* Skip rdlen */
1894
1895   cname = xtrymalloc (cnamesize);
1896   if (!cname)
1897     return gpg_error_from_syserror ();
1898
1899   rc = dn_expand (answer, emsg, pt, cname, cnamesize -1);
1900   if (rc == -1)
1901     {
1902       xfree (cname);
1903       return gpg_error (GPG_ERR_SERVER_FAILED);
1904     }
1905   *r_cname = xtryrealloc (cname, strlen (cname)+1);
1906   if (!*r_cname)
1907     {
1908       err = gpg_error_from_syserror ();
1909       xfree (cname);
1910       return err;
1911     }
1912   return 0;
1913
1914 #else /*!HAVE_SYSTEM_RESOLVER*/
1915
1916   (void)name;
1917   (void)r_cname;
1918   return gpg_error (GPG_ERR_NOT_IMPLEMENTED);
1919
1920 #endif /*!HAVE_SYSTEM_RESOLVER*/
1921 }
1922
1923
1924 gpg_error_t
1925 get_dns_cname (const char *name, char **r_cname)
1926 {
1927   *r_cname = NULL;
1928
1929 #ifdef USE_LIBDNS
1930   if (!standard_resolver)
1931     {
1932       gpg_error_t err;
1933
1934       err = get_dns_cname_libdns (name, r_cname);
1935       if (err && libdns_switch_port_p (err))
1936         err = get_dns_cname_libdns (name, r_cname);
1937       return err;
1938     }
1939 #endif /*USE_LIBDNS*/
1940
1941   return get_dns_cname_standard (name, r_cname);
1942 }