dirmngr: Auto-enable Tor on startup or reload.
[gnupg.git] / dirmngr / server.c
1 /* server.c - LDAP and Keyserver access server
2  * Copyright (C) 2002 Klarälvdalens Datakonsult AB
3  * Copyright (C) 2003, 2004, 2005, 2007, 2008, 2009, 2011, 2015 g10 Code GmbH
4  * Copyright (C) 2014, 2015, 2016 Werner Koch
5  * Copyright (C) 2016 Bundesamt für Sicherheit in der Informationstechnik
6  *
7  * This file is part of GnuPG.
8  *
9  * GnuPG is free software; you can redistribute it and/or modify
10  * it under the terms of the GNU General Public License as published by
11  * the Free Software Foundation; either version 3 of the License, or
12  * (at your option) any later version.
13  *
14  * GnuPG is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17  * GNU General Public License for more details.
18  *
19  * You should have received a copy of the GNU General Public License
20  * along with this program; if not, see <https://www.gnu.org/licenses/>.
21  */
22
23 #include <config.h>
24 #include <stdio.h>
25 #include <stdlib.h>
26 #include <stddef.h>
27 #include <string.h>
28 #include <assert.h>
29 #include <sys/types.h>
30 #include <sys/stat.h>
31 #include <unistd.h>
32 #include <errno.h>
33
34 #include "dirmngr.h"
35 #include <assuan.h>
36
37 #include "crlcache.h"
38 #include "crlfetch.h"
39 #if USE_LDAP
40 # include "ldapserver.h"
41 #endif
42 #include "ocsp.h"
43 #include "certcache.h"
44 #include "validate.h"
45 #include "misc.h"
46 #if USE_LDAP
47 # include "ldap-wrapper.h"
48 #endif
49 #include "ks-action.h"
50 #include "ks-engine.h"  /* (ks_hkp_print_hosttable) */
51 #if USE_LDAP
52 # include "ldap-parse-uri.h"
53 #endif
54 #include "dns-stuff.h"
55 #include "../common/mbox-util.h"
56 #include "../common/zb32.h"
57 #include "../common/server-help.h"
58
59 /* To avoid DoS attacks we limit the size of a certificate to
60    something reasonable.  The DoS was actually only an issue back when
61    Dirmngr was a system service and not a user service. */
62 #define MAX_CERT_LENGTH (16*1024)
63
64 /* The limit for the CERTLIST inquiry.  We allow for up to 20
65  * certificates but also take PEM encoding into account.  */
66 #define MAX_CERTLIST_LENGTH ((MAX_CERT_LENGTH * 20 * 4)/3)
67
68 /* The same goes for OpenPGP keyblocks, but here we need to allow for
69    much longer blocks; a 200k keyblock is not too unusual for keys
70    with a lot of signatures (e.g. 0x5b0358a2).  9C31503C6D866396 even
71    has 770 KiB as of 2015-08-23.  To avoid adding a runtime option we
72    now use 20MiB which should really be enough.  Well, a key with
73    several pictures could be larger (the parser as a 18MiB limit for
74    attribute packets) but it won't be nice to the keyservers to send
75    them such large blobs.  */
76 #define MAX_KEYBLOCK_LENGTH (20*1024*1024)
77
78
79 #define PARM_ERROR(t) assuan_set_error (ctx, \
80                                         gpg_error (GPG_ERR_ASS_PARAMETER), (t))
81 #define set_error(e,t) assuan_set_error (ctx, gpg_error (e), (t))
82
83
84
85 /* Control structure per connection. */
86 struct server_local_s
87 {
88   /* Data used to associate an Assuan context with local server data */
89   assuan_context_t assuan_ctx;
90
91   /* Per-session LDAP servers.  */
92   ldap_server_t ldapservers;
93
94   /* Per-session list of keyservers.  */
95   uri_item_t keyservers;
96
97   /* If this flag is set to true this dirmngr process will be
98      terminated after the end of this session.  */
99   int stopme;
100
101   /* State variable private to is_tor_running.  */
102   int tor_state;
103
104   /* If the first both flags are set the assuan logging of data lines
105    * is suppressed.  The count variable is used to show the number of
106    * non-logged bytes.  */
107   size_t inhibit_data_logging_count;
108   unsigned int inhibit_data_logging : 1;
109   unsigned int inhibit_data_logging_now : 1;
110 };
111
112
113 /* Cookie definition for assuan data line output.  */
114 static gpgrt_ssize_t data_line_cookie_write (void *cookie,
115                                              const void *buffer, size_t size);
116 static int data_line_cookie_close (void *cookie);
117 static es_cookie_io_functions_t data_line_cookie_functions =
118   {
119     NULL,
120     data_line_cookie_write,
121     NULL,
122     data_line_cookie_close
123   };
124
125
126
127
128 \f
129 /* Accessor for the local ldapservers variable. */
130 ldap_server_t
131 get_ldapservers_from_ctrl (ctrl_t ctrl)
132 {
133   if (ctrl && ctrl->server_local)
134     return ctrl->server_local->ldapservers;
135   else
136     return NULL;
137 }
138
139 /* Release an uri_item_t list.  */
140 static void
141 release_uri_item_list (uri_item_t list)
142 {
143   while (list)
144     {
145       uri_item_t tmp = list->next;
146       http_release_parsed_uri (list->parsed_uri);
147       xfree (list);
148       list = tmp;
149     }
150 }
151
152 /* Release all configured keyserver info from CTRL.  */
153 void
154 release_ctrl_keyservers (ctrl_t ctrl)
155 {
156   if (! ctrl->server_local)
157     return;
158
159   release_uri_item_list (ctrl->server_local->keyservers);
160   ctrl->server_local->keyservers = NULL;
161 }
162
163
164
165 /* Helper to print a message while leaving a command.  */
166 static gpg_error_t
167 leave_cmd (assuan_context_t ctx, gpg_error_t err)
168 {
169   if (err)
170     {
171       const char *name = assuan_get_command_name (ctx);
172       if (!name)
173         name = "?";
174       if (gpg_err_source (err) == GPG_ERR_SOURCE_DEFAULT)
175         log_error ("command '%s' failed: %s\n", name,
176                    gpg_strerror (err));
177       else
178         log_error ("command '%s' failed: %s <%s>\n", name,
179                    gpg_strerror (err), gpg_strsource (err));
180     }
181   return err;
182 }
183
184
185 /* This is a wrapper around assuan_send_data which makes debugging the
186    output in verbose mode easier.  */
187 static gpg_error_t
188 data_line_write (assuan_context_t ctx, const void *buffer_arg, size_t size)
189 {
190   ctrl_t ctrl = assuan_get_pointer (ctx);
191   const char *buffer = buffer_arg;
192   gpg_error_t err;
193
194   /* If we do not want logging, enable it here.  */
195   if (ctrl && ctrl->server_local && ctrl->server_local->inhibit_data_logging)
196     ctrl->server_local->inhibit_data_logging_now = 1;
197
198   if (opt.verbose && buffer && size)
199     {
200       /* Ease reading of output by sending a physical line at each LF.  */
201       const char *p;
202       size_t n, nbytes;
203
204       nbytes = size;
205       do
206         {
207           p = memchr (buffer, '\n', nbytes);
208           n = p ? (p - buffer) + 1 : nbytes;
209           err = assuan_send_data (ctx, buffer, n);
210           if (err)
211             {
212               gpg_err_set_errno (EIO);
213               goto leave;
214             }
215           buffer += n;
216           nbytes -= n;
217           if (nbytes && (err=assuan_send_data (ctx, NULL, 0))) /* Flush line. */
218             {
219               gpg_err_set_errno (EIO);
220               goto leave;
221             }
222         }
223       while (nbytes);
224     }
225   else
226     {
227       err = assuan_send_data (ctx, buffer, size);
228       if (err)
229         {
230           gpg_err_set_errno (EIO);  /* For use by data_line_cookie_write.  */
231           goto leave;
232         }
233     }
234
235  leave:
236   if (ctrl && ctrl->server_local && ctrl->server_local->inhibit_data_logging)
237     {
238       ctrl->server_local->inhibit_data_logging_now = 0;
239       ctrl->server_local->inhibit_data_logging_count += size;
240     }
241
242   return err;
243 }
244
245
246 /* A write handler used by es_fopencookie to write assuan data
247    lines.  */
248 static gpgrt_ssize_t
249 data_line_cookie_write (void *cookie, const void *buffer, size_t size)
250 {
251   assuan_context_t ctx = cookie;
252
253   if (data_line_write (ctx, buffer, size))
254     return -1;
255   return (gpgrt_ssize_t)size;
256 }
257
258
259 static int
260 data_line_cookie_close (void *cookie)
261 {
262   assuan_context_t ctx = cookie;
263
264   if (DBG_IPC)
265     {
266       ctrl_t ctrl = assuan_get_pointer (ctx);
267
268       if (ctrl && ctrl->server_local
269           && ctrl->server_local->inhibit_data_logging
270           && ctrl->server_local->inhibit_data_logging_count)
271         log_debug ("(%zu bytes sent via D lines not shown)\n",
272                    ctrl->server_local->inhibit_data_logging_count);
273     }
274   if (assuan_send_data (ctx, NULL, 0))
275     {
276       gpg_err_set_errno (EIO);
277       return -1;
278     }
279
280   return 0;
281 }
282
283
284 /* Copy the % and + escaped string S into the buffer D and replace the
285    escape sequences.  Note, that it is sufficient to allocate the
286    target string D as long as the source string S, i.e.: strlen(s)+1.
287    Note further that if S contains an escaped binary Nul the resulting
288    string D will contain the 0 as well as all other characters but it
289    will be impossible to know whether this is the original EOS or a
290    copied Nul. */
291 static void
292 strcpy_escaped_plus (char *d, const unsigned char *s)
293 {
294   while (*s)
295     {
296       if (*s == '%' && s[1] && s[2])
297         {
298           s++;
299           *d++ = xtoi_2 ( s);
300           s += 2;
301         }
302       else if (*s == '+')
303         *d++ = ' ', s++;
304       else
305         *d++ = *s++;
306     }
307   *d = 0;
308 }
309
310
311 /* This function returns true if a Tor server is running.  The status
312  * is cached for the current connection.  */
313 static int
314 is_tor_running (ctrl_t ctrl)
315 {
316   /* Check whether we can connect to the proxy.  */
317
318   if (!ctrl || !ctrl->server_local)
319     return 0; /* Ooops.  */
320
321   if (!ctrl->server_local->tor_state)
322     {
323       assuan_fd_t sock;
324
325       sock = assuan_sock_connect_byname (NULL, 0, 0, NULL, ASSUAN_SOCK_TOR);
326       if (sock == ASSUAN_INVALID_FD)
327         ctrl->server_local->tor_state = -1; /* Not running.  */
328       else
329         {
330           assuan_sock_close (sock);
331           ctrl->server_local->tor_state = 1; /* Running.  */
332         }
333     }
334   return (ctrl->server_local->tor_state > 0);
335 }
336
337
338 /* Return an error if the assuan context does not belong to the owner
339    of the process or to root.  On error FAILTEXT is set as Assuan
340    error string.  */
341 static gpg_error_t
342 check_owner_permission (assuan_context_t ctx, const char *failtext)
343 {
344 #ifdef HAVE_W32_SYSTEM
345   /* Under Windows the dirmngr is always run under the control of the
346      user.  */
347   (void)ctx;
348   (void)failtext;
349 #else
350   gpg_err_code_t ec;
351   assuan_peercred_t cred;
352
353   ec = gpg_err_code (assuan_get_peercred (ctx, &cred));
354   if (!ec && cred->uid && cred->uid != getuid ())
355     ec = GPG_ERR_EPERM;
356   if (ec)
357     return set_error (ec, failtext);
358 #endif
359   return 0;
360 }
361
362
363
364 /* Common code for get_cert_local and get_issuer_cert_local. */
365 static ksba_cert_t
366 do_get_cert_local (ctrl_t ctrl, const char *name, const char *command)
367 {
368   unsigned char *value;
369   size_t valuelen;
370   int rc;
371   char *buf;
372   ksba_cert_t cert;
373
374   buf = name? strconcat (command, " ", name, NULL) : xtrystrdup (command);
375   if (!buf)
376     rc = gpg_error_from_syserror ();
377   else
378     {
379       rc = assuan_inquire (ctrl->server_local->assuan_ctx, buf,
380                            &value, &valuelen, MAX_CERT_LENGTH);
381       xfree (buf);
382     }
383   if (rc)
384     {
385       log_error (_("assuan_inquire(%s) failed: %s\n"),
386                  command, gpg_strerror (rc));
387       return NULL;
388     }
389
390   if (!valuelen)
391     {
392       xfree (value);
393       return NULL;
394     }
395
396   rc = ksba_cert_new (&cert);
397   if (!rc)
398     {
399       rc = ksba_cert_init_from_mem (cert, value, valuelen);
400       if (rc)
401         {
402           ksba_cert_release (cert);
403           cert = NULL;
404         }
405     }
406   xfree (value);
407   return cert;
408 }
409
410
411
412 /* Ask back to return a certificate for NAME, given as a regular gpgsm
413  * certificate identifier (e.g. fingerprint or one of the other
414  * methods).  Alternatively, NULL may be used for NAME to return the
415  * current target certificate.  Either return the certificate in a
416  * KSBA object or NULL if it is not available.  */
417 ksba_cert_t
418 get_cert_local (ctrl_t ctrl, const char *name)
419 {
420   if (!ctrl || !ctrl->server_local || !ctrl->server_local->assuan_ctx)
421     {
422       if (opt.debug)
423         log_debug ("get_cert_local called w/o context\n");
424       return NULL;
425     }
426   return do_get_cert_local (ctrl, name, "SENDCERT");
427
428 }
429
430
431 /* Ask back to return the issuing certificate for NAME, given as a
432  * regular gpgsm certificate identifier (e.g. fingerprint or one
433  * of the other methods).  Alternatively, NULL may be used for NAME to
434  * return the current target certificate. Either return the certificate
435  * in a KSBA object or NULL if it is not available.  */
436 ksba_cert_t
437 get_issuing_cert_local (ctrl_t ctrl, const char *name)
438 {
439   if (!ctrl || !ctrl->server_local || !ctrl->server_local->assuan_ctx)
440     {
441       if (opt.debug)
442         log_debug ("get_issuing_cert_local called w/o context\n");
443       return NULL;
444     }
445   return do_get_cert_local (ctrl, name, "SENDISSUERCERT");
446 }
447
448
449 /* Ask back to return a certificate with subject NAME and a
450  * subjectKeyIdentifier of KEYID. */
451 ksba_cert_t
452 get_cert_local_ski (ctrl_t ctrl, const char *name, ksba_sexp_t keyid)
453 {
454   unsigned char *value;
455   size_t valuelen;
456   int rc;
457   char *buf;
458   ksba_cert_t cert;
459   char *hexkeyid;
460
461   if (!ctrl || !ctrl->server_local || !ctrl->server_local->assuan_ctx)
462     {
463       if (opt.debug)
464         log_debug ("get_cert_local_ski called w/o context\n");
465       return NULL;
466     }
467   if (!name || !keyid)
468     {
469       log_debug ("get_cert_local_ski called with insufficient arguments\n");
470       return NULL;
471     }
472
473   hexkeyid = serial_hex (keyid);
474   if (!hexkeyid)
475     {
476       log_debug ("serial_hex() failed\n");
477       return NULL;
478     }
479
480   buf = strconcat ("SENDCERT_SKI ", hexkeyid, " /", name, NULL);
481   if (!buf)
482     {
483       log_error ("can't allocate enough memory: %s\n", strerror (errno));
484       xfree (hexkeyid);
485       return NULL;
486     }
487   xfree (hexkeyid);
488
489   rc = assuan_inquire (ctrl->server_local->assuan_ctx, buf,
490                        &value, &valuelen, MAX_CERT_LENGTH);
491   xfree (buf);
492   if (rc)
493     {
494       log_error (_("assuan_inquire(%s) failed: %s\n"), "SENDCERT_SKI",
495                  gpg_strerror (rc));
496       return NULL;
497     }
498
499   if (!valuelen)
500     {
501       xfree (value);
502       return NULL;
503     }
504
505   rc = ksba_cert_new (&cert);
506   if (!rc)
507     {
508       rc = ksba_cert_init_from_mem (cert, value, valuelen);
509       if (rc)
510         {
511           ksba_cert_release (cert);
512           cert = NULL;
513         }
514     }
515   xfree (value);
516   return cert;
517 }
518
519
520 /* Ask the client via an inquiry to check the istrusted status of the
521    certificate specified by the hexified fingerprint HEXFPR.  Returns
522    0 if the certificate is trusted by the client or an error code.  */
523 gpg_error_t
524 get_istrusted_from_client (ctrl_t ctrl, const char *hexfpr)
525 {
526   unsigned char *value;
527   size_t valuelen;
528   int rc;
529   char request[100];
530
531   if (!ctrl || !ctrl->server_local || !ctrl->server_local->assuan_ctx
532       || !hexfpr)
533     return gpg_error (GPG_ERR_INV_ARG);
534
535   snprintf (request, sizeof request, "ISTRUSTED %s", hexfpr);
536   rc = assuan_inquire (ctrl->server_local->assuan_ctx, request,
537                        &value, &valuelen, 100);
538   if (rc)
539     {
540       log_error (_("assuan_inquire(%s) failed: %s\n"),
541                  request, gpg_strerror (rc));
542       return rc;
543     }
544   /* The expected data is: "1" or "1 cruft" (not a C-string).  */
545   if (valuelen && *value == '1' && (valuelen == 1 || spacep (value+1)))
546     rc = 0;
547   else
548     rc = gpg_error (GPG_ERR_NOT_TRUSTED);
549   xfree (value);
550   return rc;
551 }
552
553
554
555
556 /* Ask the client to return the certificate associated with the
557    current command. This is sometimes needed because the client usually
558    sends us just the cert ID, assuming that the request can be
559    satisfied from the cache, where the cert ID is used as key. */
560 static int
561 inquire_cert_and_load_crl (assuan_context_t ctx)
562 {
563   ctrl_t ctrl = assuan_get_pointer (ctx);
564   gpg_error_t err;
565   unsigned char *value = NULL;
566   size_t valuelen;
567   ksba_cert_t cert = NULL;
568
569   err = assuan_inquire( ctx, "SENDCERT", &value, &valuelen, 0);
570   if (err)
571     return err;
572
573 /*   { */
574 /*     FILE *fp = fopen ("foo.der", "r"); */
575 /*     value = xmalloc (2000); */
576 /*     valuelen = fread (value, 1, 2000, fp); */
577 /*     fclose (fp); */
578 /*   } */
579
580   if (!valuelen) /* No data returned; return a comprehensible error. */
581     return gpg_error (GPG_ERR_MISSING_CERT);
582
583   err = ksba_cert_new (&cert);
584   if (err)
585     goto leave;
586   err = ksba_cert_init_from_mem (cert, value, valuelen);
587   if(err)
588     goto leave;
589   xfree (value); value = NULL;
590
591   err = crl_cache_reload_crl (ctrl, cert);
592
593  leave:
594   ksba_cert_release (cert);
595   xfree (value);
596   return err;
597 }
598
599
600 /* Handle OPTION commands. */
601 static gpg_error_t
602 option_handler (assuan_context_t ctx, const char *key, const char *value)
603 {
604   ctrl_t ctrl = assuan_get_pointer (ctx);
605   gpg_error_t err = 0;
606
607   if (!strcmp (key, "force-crl-refresh"))
608     {
609       int i = *value? atoi (value) : 0;
610       ctrl->force_crl_refresh = i;
611     }
612   else if (!strcmp (key, "audit-events"))
613     {
614       int i = *value? atoi (value) : 0;
615       ctrl->audit_events = i;
616     }
617   else if (!strcmp (key, "http-proxy"))
618     {
619       xfree (ctrl->http_proxy);
620       if (!*value || !strcmp (value, "none"))
621         ctrl->http_proxy = NULL;
622       else if (!(ctrl->http_proxy = xtrystrdup (value)))
623         err = gpg_error_from_syserror ();
624     }
625   else if (!strcmp (key, "honor-keyserver-url-used"))
626     {
627       /* Return an error if we are running in Tor mode.  */
628       if (dirmngr_use_tor ())
629         err = gpg_error (GPG_ERR_FORBIDDEN);
630     }
631   else if (!strcmp (key, "http-crl"))
632     {
633       int i = *value? atoi (value) : 0;
634       ctrl->http_no_crl = !i;
635     }
636   else
637     err = gpg_error (GPG_ERR_UNKNOWN_OPTION);
638
639   return err;
640 }
641
642
643 \f
644 static const char hlp_dns_cert[] =
645   "DNS_CERT <subtype> <name>\n"
646   "DNS_CERT --pka <user_id>\n"
647   "DNS_CERT --dane <user_id>\n"
648   "\n"
649   "Return the CERT record for <name>.  <subtype> is one of\n"
650   "  *     Return the first record of any supported subtype\n"
651   "  PGP   Return the first record of subtype PGP (3)\n"
652   "  IPGP  Return the first record of subtype IPGP (6)\n"
653   "If the content of a certificate is available (PGP) it is returned\n"
654   "by data lines.  Fingerprints and URLs are returned via status lines.\n"
655   "In --pka mode the fingerprint and if available an URL is returned.\n"
656   "In --dane mode the key is returned from RR type 61";
657 static gpg_error_t
658 cmd_dns_cert (assuan_context_t ctx, char *line)
659 {
660   /* ctrl_t ctrl = assuan_get_pointer (ctx); */
661   gpg_error_t err = 0;
662   int pka_mode, dane_mode;
663   char *mbox = NULL;
664   char *namebuf = NULL;
665   char *encodedhash = NULL;
666   const char *name;
667   int certtype;
668   char *p;
669   void *key = NULL;
670   size_t keylen;
671   unsigned char *fpr = NULL;
672   size_t fprlen;
673   char *url = NULL;
674
675   pka_mode = has_option (line, "--pka");
676   dane_mode = has_option (line, "--dane");
677   line = skip_options (line);
678
679   if (pka_mode && dane_mode)
680     {
681       err = PARM_ERROR ("either --pka or --dane may be given");
682       goto leave;
683     }
684
685   if (pka_mode || dane_mode)
686     ; /* No need to parse here - we do this later.  */
687   else
688     {
689       p = strchr (line, ' ');
690       if (!p)
691         {
692           err = PARM_ERROR ("missing arguments");
693           goto leave;
694         }
695       *p++ = 0;
696       if (!strcmp (line, "*"))
697         certtype = DNS_CERTTYPE_ANY;
698       else if (!strcmp (line, "IPGP"))
699         certtype = DNS_CERTTYPE_IPGP;
700       else if (!strcmp (line, "PGP"))
701         certtype = DNS_CERTTYPE_PGP;
702       else
703         {
704           err = PARM_ERROR ("unknown subtype");
705           goto leave;
706         }
707       while (spacep (p))
708         p++;
709       line = p;
710       if (!*line)
711         {
712           err = PARM_ERROR ("name missing");
713           goto leave;
714         }
715     }
716
717   if (pka_mode || dane_mode)
718     {
719       char *domain;     /* Points to mbox.  */
720       char hashbuf[32]; /* For SHA-1 and SHA-256. */
721
722       /* We lowercase ascii characters but the DANE I-D does not allow
723          this.  FIXME: Check after the release of the RFC whether to
724          change this.  */
725       mbox = mailbox_from_userid (line);
726       if (!mbox || !(domain = strchr (mbox, '@')))
727         {
728           err = set_error (GPG_ERR_INV_USER_ID, "no mailbox in user id");
729           goto leave;
730         }
731       *domain++ = 0;
732
733       if (pka_mode)
734         {
735           gcry_md_hash_buffer (GCRY_MD_SHA1, hashbuf, mbox, strlen (mbox));
736           encodedhash = zb32_encode (hashbuf, 8*20);
737           if (!encodedhash)
738             {
739               err = gpg_error_from_syserror ();
740               goto leave;
741             }
742           namebuf = strconcat (encodedhash, "._pka.", domain, NULL);
743           if (!namebuf)
744             {
745               err = gpg_error_from_syserror ();
746               goto leave;
747             }
748           name = namebuf;
749           certtype = DNS_CERTTYPE_IPGP;
750         }
751       else
752         {
753           /* Note: The hash is truncated to 28 bytes and we lowercase
754              the result only for aesthetic reasons.  */
755           gcry_md_hash_buffer (GCRY_MD_SHA256, hashbuf, mbox, strlen (mbox));
756           encodedhash = bin2hex (hashbuf, 28, NULL);
757           if (!encodedhash)
758             {
759               err = gpg_error_from_syserror ();
760               goto leave;
761             }
762           ascii_strlwr (encodedhash);
763           namebuf = strconcat (encodedhash, "._openpgpkey.", domain, NULL);
764           if (!namebuf)
765             {
766               err = gpg_error_from_syserror ();
767               goto leave;
768             }
769           name = namebuf;
770           certtype = DNS_CERTTYPE_RR61;
771         }
772     }
773   else
774     name = line;
775
776   err = get_dns_cert (name, certtype, &key, &keylen, &fpr, &fprlen, &url);
777   if (err)
778     goto leave;
779
780   if (key)
781     {
782       err = data_line_write (ctx, key, keylen);
783       if (err)
784         goto leave;
785     }
786
787   if (fpr)
788     {
789       char *tmpstr;
790
791       tmpstr = bin2hex (fpr, fprlen, NULL);
792       if (!tmpstr)
793         err = gpg_error_from_syserror ();
794       else
795         {
796           err = assuan_write_status (ctx, "FPR", tmpstr);
797           xfree (tmpstr);
798         }
799       if (err)
800         goto leave;
801     }
802
803   if (url)
804     {
805       err = assuan_write_status (ctx, "URL", url);
806       if (err)
807         goto leave;
808     }
809
810
811  leave:
812   xfree (key);
813   xfree (fpr);
814   xfree (url);
815   xfree (mbox);
816   xfree (namebuf);
817   xfree (encodedhash);
818   return leave_cmd (ctx, err);
819 }
820
821
822 \f
823 static const char hlp_wkd_get[] =
824   "WKD_GET [--submission-address|--policy-flags] <user_id>\n"
825   "\n"
826   "Return the key or other info for <user_id>\n"
827   "from the Web Key Directory.";
828 static gpg_error_t
829 cmd_wkd_get (assuan_context_t ctx, char *line)
830 {
831   ctrl_t ctrl = assuan_get_pointer (ctx);
832   gpg_error_t err = 0;
833   char *mbox = NULL;
834   char *domainbuf = NULL;
835   char *domain;     /* Points to mbox or domainbuf.  */
836   char sha1buf[20];
837   char *uri = NULL;
838   char *encodedhash = NULL;
839   int opt_submission_addr;
840   int opt_policy_flags;
841   int no_log = 0;
842   char portstr[20] = { 0 };
843
844   opt_submission_addr = has_option (line, "--submission-address");
845   opt_policy_flags = has_option (line, "--policy-flags");
846   if (has_option (line, "--quick"))
847     ctrl->timeout = opt.connect_quick_timeout;
848   line = skip_options (line);
849
850   mbox = mailbox_from_userid (line);
851   if (!mbox || !(domain = strchr (mbox, '@')))
852     {
853       err = set_error (GPG_ERR_INV_USER_ID, "no mailbox in user id");
854       goto leave;
855     }
856   *domain++ = 0;
857
858   /* Check for SRV records.  */
859   if (1)
860     {
861       struct srventry *srvs;
862       unsigned int srvscount;
863       size_t domainlen, targetlen;
864       int i;
865
866       err = get_dns_srv (domain, "openpgpkey", NULL, &srvs, &srvscount);
867       if (err)
868         goto leave;
869
870       /* Find the first target which also ends in DOMAIN or is equal
871        * to DOMAIN.  */
872       domainlen = strlen (domain);
873       for (i = 0; i < srvscount; i++)
874         {
875           log_debug ("srv: trying '%s:%hu'\n", srvs[i].target, srvs[i].port);
876           targetlen = strlen (srvs[i].target);
877           if ((targetlen > domainlen + 1
878                && srvs[i].target[targetlen - domainlen - 1] == '.'
879                && !ascii_strcasecmp (srvs[i].target + targetlen - domainlen,
880                                      domain))
881               || (targetlen == domainlen
882                   && !ascii_strcasecmp (srvs[i].target, domain)))
883             {
884               /* found.  */
885               domainbuf = xtrystrdup (srvs[i].target);
886               if (!domainbuf)
887                 {
888                   err = gpg_error_from_syserror ();
889                   xfree (srvs);
890                   goto leave;
891                 }
892               domain = domainbuf;
893               if (srvs[i].port)
894                 snprintf (portstr, sizeof portstr, ":%hu", srvs[i].port);
895               break;
896             }
897         }
898       xfree (srvs);
899     }
900
901   gcry_md_hash_buffer (GCRY_MD_SHA1, sha1buf, mbox, strlen (mbox));
902   encodedhash = zb32_encode (sha1buf, 8*20);
903   if (!encodedhash)
904     {
905       err = gpg_error_from_syserror ();
906       goto leave;
907     }
908
909   if (opt_submission_addr)
910     {
911       uri = strconcat ("https://",
912                        domain,
913                        portstr,
914                        "/.well-known/openpgpkey/submission-address",
915                        NULL);
916     }
917   else if (opt_policy_flags)
918     {
919       uri = strconcat ("https://",
920                        domain,
921                        portstr,
922                        "/.well-known/openpgpkey/policy",
923                        NULL);
924     }
925   else
926     {
927       uri = strconcat ("https://",
928                        domain,
929                        portstr,
930                        "/.well-known/openpgpkey/hu/",
931                        encodedhash,
932                        NULL);
933       no_log = 1;
934       if (uri)
935         {
936           err = dirmngr_status_printf (ctrl, "SOURCE", "https://%s%s",
937                                        domain, portstr);
938           if (err)
939             goto leave;
940         }
941     }
942   if (!uri)
943     {
944       err = gpg_error_from_syserror ();
945       goto leave;
946     }
947
948   /* Setup an output stream and perform the get.  */
949   {
950     estream_t outfp;
951
952     outfp = es_fopencookie (ctx, "w", data_line_cookie_functions);
953     if (!outfp)
954       err = set_error (GPG_ERR_ASS_GENERAL,
955                        "error setting up a data stream");
956     else
957       {
958         if (no_log)
959           ctrl->server_local->inhibit_data_logging = 1;
960         ctrl->server_local->inhibit_data_logging_now = 0;
961         ctrl->server_local->inhibit_data_logging_count = 0;
962         err = ks_action_fetch (ctrl, uri, outfp);
963         es_fclose (outfp);
964         ctrl->server_local->inhibit_data_logging = 0;
965       }
966   }
967
968  leave:
969   xfree (uri);
970   xfree (encodedhash);
971   xfree (mbox);
972   xfree (domainbuf);
973   return leave_cmd (ctx, err);
974 }
975
976
977 \f
978 static const char hlp_ldapserver[] =
979   "LDAPSERVER <data>\n"
980   "\n"
981   "Add a new LDAP server to the list of configured LDAP servers.\n"
982   "DATA is in the same format as expected in the configure file.";
983 static gpg_error_t
984 cmd_ldapserver (assuan_context_t ctx, char *line)
985 {
986 #if USE_LDAP
987   ctrl_t ctrl = assuan_get_pointer (ctx);
988   ldap_server_t server;
989   ldap_server_t *last_next_p;
990
991   while (spacep (line))
992     line++;
993   if (*line == '\0')
994     return leave_cmd (ctx, PARM_ERROR (_("ldapserver missing")));
995
996   server = ldapserver_parse_one (line, "", 0);
997   if (! server)
998     return leave_cmd (ctx, gpg_error (GPG_ERR_INV_ARG));
999
1000   last_next_p = &ctrl->server_local->ldapservers;
1001   while (*last_next_p)
1002     last_next_p = &(*last_next_p)->next;
1003   *last_next_p = server;
1004   return leave_cmd (ctx, 0);
1005 #else
1006   (void)line;
1007   return leave_cmd (ctx, gpg_error (GPG_ERR_NOT_IMPLEMENTED));
1008 #endif
1009 }
1010
1011
1012 static const char hlp_isvalid[] =
1013   "ISVALID [--only-ocsp] [--force-default-responder]"
1014   " <certificate_id>|<certificate_fpr>\n"
1015   "\n"
1016   "This command checks whether the certificate identified by the\n"
1017   "certificate_id is valid.  This is done by consulting CRLs or\n"
1018   "whatever has been configured.  Note, that the returned error codes\n"
1019   "are from gpg-error.h.  The command may callback using the inquire\n"
1020   "function.  See the manual for details.\n"
1021   "\n"
1022   "The CERTIFICATE_ID is a hex encoded string consisting of two parts,\n"
1023   "delimited by a single dot.  The first part is the SHA-1 hash of the\n"
1024   "issuer name and the second part the serial number.\n"
1025   "\n"
1026   "Alternatively the certificate's fingerprint may be given in which\n"
1027   "case an OCSP request is done before consulting the CRL.\n"
1028   "\n"
1029   "If the option --only-ocsp is given, no fallback to a CRL check will\n"
1030   "be used.\n"
1031   "\n"
1032   "If the option --force-default-responder is given, only the default\n"
1033   "OCSP responder will be used and any other methods of obtaining an\n"
1034   "OCSP responder URL won't be used.";
1035 static gpg_error_t
1036 cmd_isvalid (assuan_context_t ctx, char *line)
1037 {
1038   ctrl_t ctrl = assuan_get_pointer (ctx);
1039   char *issuerhash, *serialno;
1040   gpg_error_t err;
1041   int did_inquire = 0;
1042   int ocsp_mode = 0;
1043   int only_ocsp;
1044   int force_default_responder;
1045
1046   only_ocsp = has_option (line, "--only-ocsp");
1047   force_default_responder = has_option (line, "--force-default-responder");
1048   line = skip_options (line);
1049
1050   issuerhash = xstrdup (line); /* We need to work on a copy of the
1051                                   line because that same Assuan
1052                                   context may be used for an inquiry.
1053                                   That is because Assuan reuses its
1054                                   line buffer.
1055                                    */
1056
1057   serialno = strchr (issuerhash, '.');
1058   if (serialno)
1059     *serialno++ = 0;
1060   else
1061     {
1062       char *endp = strchr (issuerhash, ' ');
1063       if (endp)
1064         *endp = 0;
1065       if (strlen (issuerhash) != 40)
1066         {
1067           xfree (issuerhash);
1068           return leave_cmd (ctx, PARM_ERROR (_("serialno missing in cert ID")));
1069         }
1070       ocsp_mode = 1;
1071     }
1072
1073
1074  again:
1075   if (ocsp_mode)
1076     {
1077       /* Note, that we ignore the given issuer hash and instead rely
1078          on the current certificate semantics used with this
1079          command. */
1080       if (!opt.allow_ocsp)
1081         err = gpg_error (GPG_ERR_NOT_SUPPORTED);
1082       else
1083         err = ocsp_isvalid (ctrl, NULL, NULL, force_default_responder);
1084       /* Fixme: If we got no ocsp response and --only-ocsp is not used
1085          we should fall back to CRL mode.  Thus we need to clear
1086          OCSP_MODE, get the issuerhash and the serialno from the
1087          current certificate and jump to again. */
1088     }
1089   else if (only_ocsp)
1090     err = gpg_error (GPG_ERR_NO_CRL_KNOWN);
1091   else
1092     {
1093       switch (crl_cache_isvalid (ctrl,
1094                                  issuerhash, serialno,
1095                                  ctrl->force_crl_refresh))
1096         {
1097         case CRL_CACHE_VALID:
1098           err = 0;
1099           break;
1100         case CRL_CACHE_INVALID:
1101           err = gpg_error (GPG_ERR_CERT_REVOKED);
1102           break;
1103         case CRL_CACHE_DONTKNOW:
1104           if (did_inquire)
1105             err = gpg_error (GPG_ERR_NO_CRL_KNOWN);
1106           else if (!(err = inquire_cert_and_load_crl (ctx)))
1107             {
1108               did_inquire = 1;
1109               goto again;
1110             }
1111           break;
1112         case CRL_CACHE_CANTUSE:
1113           err = gpg_error (GPG_ERR_NO_CRL_KNOWN);
1114           break;
1115         default:
1116           log_fatal ("crl_cache_isvalid returned invalid code\n");
1117         }
1118     }
1119
1120   xfree (issuerhash);
1121   return leave_cmd (ctx, err);
1122 }
1123
1124
1125 /* If the line contains a SHA-1 fingerprint as the first argument,
1126    return the FPR vuffer on success.  The function checks that the
1127    fingerprint consists of valid characters and prints and error
1128    message if it does not and returns NULL.  Fingerprints are
1129    considered optional and thus no explicit error is returned. NULL is
1130    also returned if there is no fingerprint at all available.
1131    FPR must be a caller provided buffer of at least 20 bytes.
1132
1133    Note that colons within the fingerprint are allowed to separate 2
1134    hex digits; this allows for easier cutting and pasting using the
1135    usual fingerprint rendering.
1136 */
1137 static unsigned char *
1138 get_fingerprint_from_line (const char *line, unsigned char *fpr)
1139 {
1140   const char *s;
1141   int i;
1142
1143   for (s=line, i=0; *s && *s != ' '; s++ )
1144     {
1145       if ( hexdigitp (s) && hexdigitp (s+1) )
1146         {
1147           if ( i >= 20 )
1148             return NULL;  /* Fingerprint too long.  */
1149           fpr[i++] = xtoi_2 (s);
1150           s++;
1151         }
1152       else if ( *s != ':' )
1153         return NULL; /* Invalid.  */
1154     }
1155   if ( i != 20 )
1156     return NULL; /* Fingerprint to short.  */
1157   return fpr;
1158 }
1159
1160
1161
1162 static const char hlp_checkcrl[] =
1163   "CHECKCRL [<fingerprint>]\n"
1164   "\n"
1165   "Check whether the certificate with FINGERPRINT (SHA-1 hash of the\n"
1166   "entire X.509 certificate blob) is valid or not by consulting the\n"
1167   "CRL responsible for this certificate.  If the fingerprint has not\n"
1168   "been given or the certificate is not known, the function \n"
1169   "inquires the certificate using an\n"
1170   "\n"
1171   "  INQUIRE TARGETCERT\n"
1172   "\n"
1173   "and the caller is expected to return the certificate for the\n"
1174   "request (which should match FINGERPRINT) as a binary blob.\n"
1175   "Processing then takes place without further interaction; in\n"
1176   "particular dirmngr tries to locate other required certificate by\n"
1177   "its own mechanism which includes a local certificate store as well\n"
1178   "as a list of trusted root certificates.\n"
1179   "\n"
1180   "The return value is the usual gpg-error code or 0 for ducesss;\n"
1181   "i.e. the certificate validity has been confirmed by a valid CRL.";
1182 static gpg_error_t
1183 cmd_checkcrl (assuan_context_t ctx, char *line)
1184 {
1185   ctrl_t ctrl = assuan_get_pointer (ctx);
1186   gpg_error_t err;
1187   unsigned char fprbuffer[20], *fpr;
1188   ksba_cert_t cert;
1189
1190   fpr = get_fingerprint_from_line (line, fprbuffer);
1191   cert = fpr? get_cert_byfpr (fpr) : NULL;
1192
1193   if (!cert)
1194     {
1195       /* We do not have this certificate yet or the fingerprint has
1196          not been given.  Inquire it from the client.  */
1197       unsigned char *value = NULL;
1198       size_t valuelen;
1199
1200       err = assuan_inquire (ctrl->server_local->assuan_ctx, "TARGETCERT",
1201                            &value, &valuelen, MAX_CERT_LENGTH);
1202       if (err)
1203         {
1204           log_error (_("assuan_inquire failed: %s\n"), gpg_strerror (err));
1205           goto leave;
1206         }
1207
1208       if (!valuelen) /* No data returned; return a comprehensible error. */
1209         err = gpg_error (GPG_ERR_MISSING_CERT);
1210       else
1211         {
1212           err = ksba_cert_new (&cert);
1213           if (!err)
1214             err = ksba_cert_init_from_mem (cert, value, valuelen);
1215         }
1216       xfree (value);
1217       if(err)
1218         goto leave;
1219     }
1220
1221   assert (cert);
1222
1223   err = crl_cache_cert_isvalid (ctrl, cert, ctrl->force_crl_refresh);
1224   if (gpg_err_code (err) == GPG_ERR_NO_CRL_KNOWN)
1225     {
1226       err = crl_cache_reload_crl (ctrl, cert);
1227       if (!err)
1228         err = crl_cache_cert_isvalid (ctrl, cert, 0);
1229     }
1230
1231  leave:
1232   ksba_cert_release (cert);
1233   return leave_cmd (ctx, err);
1234 }
1235
1236
1237 static const char hlp_checkocsp[] =
1238   "CHECKOCSP [--force-default-responder] [<fingerprint>]\n"
1239   "\n"
1240   "Check whether the certificate with FINGERPRINT (SHA-1 hash of the\n"
1241   "entire X.509 certificate blob) is valid or not by asking an OCSP\n"
1242   "responder responsible for this certificate.  The optional\n"
1243   "fingerprint may be used for a quick check in case an OCSP check has\n"
1244   "been done for this certificate recently (we always cache OCSP\n"
1245   "responses for a couple of minutes). If the fingerprint has not been\n"
1246   "given or there is no cached result, the function inquires the\n"
1247   "certificate using an\n"
1248   "\n"
1249   "   INQUIRE TARGETCERT\n"
1250   "\n"
1251   "and the caller is expected to return the certificate for the\n"
1252   "request (which should match FINGERPRINT) as a binary blob.\n"
1253   "Processing then takes place without further interaction; in\n"
1254   "particular dirmngr tries to locate other required certificates by\n"
1255   "its own mechanism which includes a local certificate store as well\n"
1256   "as a list of trusted root certificates.\n"
1257   "\n"
1258   "If the option --force-default-responder is given, only the default\n"
1259   "OCSP responder will be used and any other methods of obtaining an\n"
1260   "OCSP responder URL won't be used.\n"
1261   "\n"
1262   "The return value is the usual gpg-error code or 0 for ducesss;\n"
1263   "i.e. the certificate validity has been confirmed by a valid CRL.";
1264 static gpg_error_t
1265 cmd_checkocsp (assuan_context_t ctx, char *line)
1266 {
1267   ctrl_t ctrl = assuan_get_pointer (ctx);
1268   gpg_error_t err;
1269   unsigned char fprbuffer[20], *fpr;
1270   ksba_cert_t cert;
1271   int force_default_responder;
1272
1273   force_default_responder = has_option (line, "--force-default-responder");
1274   line = skip_options (line);
1275
1276   fpr = get_fingerprint_from_line (line, fprbuffer);
1277   cert = fpr? get_cert_byfpr (fpr) : NULL;
1278
1279   if (!cert)
1280     {
1281       /* We do not have this certificate yet or the fingerprint has
1282          not been given.  Inquire it from the client.  */
1283       unsigned char *value = NULL;
1284       size_t valuelen;
1285
1286       err = assuan_inquire (ctrl->server_local->assuan_ctx, "TARGETCERT",
1287                            &value, &valuelen, MAX_CERT_LENGTH);
1288       if (err)
1289         {
1290           log_error (_("assuan_inquire failed: %s\n"), gpg_strerror (err));
1291           goto leave;
1292         }
1293
1294       if (!valuelen) /* No data returned; return a comprehensible error. */
1295         err = gpg_error (GPG_ERR_MISSING_CERT);
1296       else
1297         {
1298           err = ksba_cert_new (&cert);
1299           if (!err)
1300             err = ksba_cert_init_from_mem (cert, value, valuelen);
1301         }
1302       xfree (value);
1303       if(err)
1304         goto leave;
1305     }
1306
1307   assert (cert);
1308
1309   if (!opt.allow_ocsp)
1310     err = gpg_error (GPG_ERR_NOT_SUPPORTED);
1311   else
1312     err = ocsp_isvalid (ctrl, cert, NULL, force_default_responder);
1313
1314  leave:
1315   ksba_cert_release (cert);
1316   return leave_cmd (ctx, err);
1317 }
1318
1319
1320
1321 static int
1322 lookup_cert_by_url (assuan_context_t ctx, const char *url)
1323 {
1324   ctrl_t ctrl = assuan_get_pointer (ctx);
1325   gpg_error_t err = 0;
1326   unsigned char *value = NULL;
1327   size_t valuelen;
1328
1329   /* Fetch single certificate given it's URL.  */
1330   err = fetch_cert_by_url (ctrl, url, &value, &valuelen);
1331   if (err)
1332     {
1333       log_error (_("fetch_cert_by_url failed: %s\n"), gpg_strerror (err));
1334       goto leave;
1335     }
1336
1337   /* Send the data, flush the buffer and then send an END. */
1338   err = assuan_send_data (ctx, value, valuelen);
1339   if (!err)
1340     err = assuan_send_data (ctx, NULL, 0);
1341   if (!err)
1342     err = assuan_write_line (ctx, "END");
1343   if (err)
1344     {
1345       log_error (_("error sending data: %s\n"), gpg_strerror (err));
1346       goto leave;
1347     }
1348
1349  leave:
1350
1351   return err;
1352 }
1353
1354
1355 /* Send the certificate, flush the buffer and then send an END. */
1356 static gpg_error_t
1357 return_one_cert (void *opaque, ksba_cert_t cert)
1358 {
1359   assuan_context_t ctx = opaque;
1360   gpg_error_t err;
1361   const unsigned char *der;
1362   size_t derlen;
1363
1364   der = ksba_cert_get_image (cert, &derlen);
1365   if (!der)
1366     err = gpg_error (GPG_ERR_INV_CERT_OBJ);
1367   else
1368     {
1369       err = assuan_send_data (ctx, der, derlen);
1370       if (!err)
1371         err = assuan_send_data (ctx, NULL, 0);
1372       if (!err)
1373         err = assuan_write_line (ctx, "END");
1374     }
1375   if (err)
1376     log_error (_("error sending data: %s\n"), gpg_strerror (err));
1377   return err;
1378 }
1379
1380
1381 /* Lookup certificates from the internal cache or using the ldap
1382    servers. */
1383 static int
1384 lookup_cert_by_pattern (assuan_context_t ctx, char *line,
1385                         int single, int cache_only)
1386 {
1387   gpg_error_t err = 0;
1388   char *p;
1389   strlist_t sl, list = NULL;
1390   int truncated = 0, truncation_forced = 0;
1391   int count = 0;
1392   int local_count = 0;
1393 #if USE_LDAP
1394   ctrl_t ctrl = assuan_get_pointer (ctx);
1395   unsigned char *value = NULL;
1396   size_t valuelen;
1397   struct ldapserver_iter ldapserver_iter;
1398   cert_fetch_context_t fetch_context;
1399 #endif /*USE_LDAP*/
1400   int any_no_data = 0;
1401
1402   /* Break the line down into an STRLIST */
1403   for (p=line; *p; line = p)
1404     {
1405       while (*p && *p != ' ')
1406         p++;
1407       if (*p)
1408         *p++ = 0;
1409
1410       if (*line)
1411         {
1412           sl = xtrymalloc (sizeof *sl + strlen (line));
1413           if (!sl)
1414             {
1415               err = gpg_error_from_errno (errno);
1416               goto leave;
1417             }
1418           memset (sl, 0, sizeof *sl);
1419           strcpy_escaped_plus (sl->d, line);
1420           sl->next = list;
1421           list = sl;
1422         }
1423     }
1424
1425   /* First look through the internal cache.  The certificates returned
1426      here are not counted towards the truncation limit.  */
1427   if (single && !cache_only)
1428     ; /* Do not read from the local cache in this case.  */
1429   else
1430     {
1431       for (sl=list; sl; sl = sl->next)
1432         {
1433           err = get_certs_bypattern (sl->d, return_one_cert, ctx);
1434           if (!err)
1435             local_count++;
1436           if (!err && single)
1437             goto ready;
1438
1439           if (gpg_err_code (err) == GPG_ERR_NO_DATA)
1440             {
1441               err = 0;
1442               if (cache_only)
1443                 any_no_data = 1;
1444             }
1445           else if (gpg_err_code (err) == GPG_ERR_INV_NAME && !cache_only)
1446             {
1447               /* No real fault because the internal pattern lookup
1448                  can't yet cope with all types of pattern.  */
1449               err = 0;
1450             }
1451           if (err)
1452             goto ready;
1453         }
1454     }
1455
1456   /* Loop over all configured servers unless we want only the
1457      certificates from the cache.  */
1458 #if USE_LDAP
1459   for (ldapserver_iter_begin (&ldapserver_iter, ctrl);
1460        !cache_only && !ldapserver_iter_end_p (&ldapserver_iter)
1461          && ldapserver_iter.server->host && !truncation_forced;
1462        ldapserver_iter_next (&ldapserver_iter))
1463     {
1464       ldap_server_t ldapserver = ldapserver_iter.server;
1465
1466       if (DBG_LOOKUP)
1467         log_debug ("cmd_lookup: trying %s:%d base=%s\n",
1468                    ldapserver->host, ldapserver->port,
1469                    ldapserver->base?ldapserver->base : "[default]");
1470
1471       /* Fetch certificates matching pattern */
1472       err = start_cert_fetch (ctrl, &fetch_context, list, ldapserver);
1473       if ( gpg_err_code (err) == GPG_ERR_NO_DATA )
1474         {
1475           if (DBG_LOOKUP)
1476             log_debug ("cmd_lookup: no data\n");
1477           err = 0;
1478           any_no_data = 1;
1479           continue;
1480         }
1481       if (err)
1482         {
1483           log_error (_("start_cert_fetch failed: %s\n"), gpg_strerror (err));
1484           goto leave;
1485         }
1486
1487       /* Fetch the certificates for this query. */
1488       while (!truncation_forced)
1489         {
1490           xfree (value); value = NULL;
1491           err = fetch_next_cert (fetch_context, &value, &valuelen);
1492           if (gpg_err_code (err) == GPG_ERR_NO_DATA )
1493             {
1494               err = 0;
1495               any_no_data = 1;
1496               break; /* Ready. */
1497             }
1498           if (gpg_err_code (err) == GPG_ERR_TRUNCATED)
1499             {
1500               truncated = 1;
1501               err = 0;
1502               break;  /* Ready.  */
1503             }
1504           if (gpg_err_code (err) == GPG_ERR_EOF)
1505             {
1506               err = 0;
1507               break; /* Ready. */
1508             }
1509           if (!err && !value)
1510             {
1511               err = gpg_error (GPG_ERR_BUG);
1512               goto leave;
1513             }
1514           if (err)
1515             {
1516               log_error (_("fetch_next_cert failed: %s\n"),
1517                          gpg_strerror (err));
1518               end_cert_fetch (fetch_context);
1519               goto leave;
1520             }
1521
1522           if (DBG_LOOKUP)
1523             log_debug ("cmd_lookup: returning one cert%s\n",
1524                        truncated? " (truncated)":"");
1525
1526           /* Send the data, flush the buffer and then send an END line
1527              as a certificate delimiter. */
1528           err = assuan_send_data (ctx, value, valuelen);
1529           if (!err)
1530             err = assuan_send_data (ctx, NULL, 0);
1531           if (!err)
1532             err = assuan_write_line (ctx, "END");
1533           if (err)
1534             {
1535               log_error (_("error sending data: %s\n"), gpg_strerror (err));
1536               end_cert_fetch (fetch_context);
1537               goto leave;
1538             }
1539
1540           if (++count >= opt.max_replies )
1541             {
1542               truncation_forced = 1;
1543               log_info (_("max_replies %d exceeded\n"), opt.max_replies );
1544             }
1545           if (single)
1546             break;
1547         }
1548
1549       end_cert_fetch (fetch_context);
1550     }
1551 #endif /*USE_LDAP*/
1552
1553  ready:
1554   if (truncated || truncation_forced)
1555     {
1556       char str[50];
1557
1558       sprintf (str, "%d", count);
1559       assuan_write_status (ctx, "TRUNCATED", str);
1560     }
1561
1562   if (!err && !count && !local_count && any_no_data)
1563     err = gpg_error (GPG_ERR_NO_DATA);
1564
1565  leave:
1566   free_strlist (list);
1567   return err;
1568 }
1569
1570
1571 static const char hlp_lookup[] =
1572   "LOOKUP [--url] [--single] [--cache-only] <pattern>\n"
1573   "\n"
1574   "Lookup certificates matching PATTERN. With --url the pattern is\n"
1575   "expected to be one URL.\n"
1576   "\n"
1577   "If --url is not given:  To allow for multiple patterns (which are ORed)\n"
1578   "quoting is required: Spaces are translated to \"+\" or \"%20\";\n"
1579   "obviously this requires that the usual escape quoting rules are applied.\n"
1580   "\n"
1581   "If --url is given no special escaping is required because URLs are\n"
1582   "already escaped this way.\n"
1583   "\n"
1584   "If --single is given the first and only the first match will be\n"
1585   "returned.  If --cache-only is _not_ given, no local query will be\n"
1586   "done.\n"
1587   "\n"
1588   "If --cache-only is given no external lookup is done so that only\n"
1589   "certificates from the cache may get returned.";
1590 static gpg_error_t
1591 cmd_lookup (assuan_context_t ctx, char *line)
1592 {
1593   gpg_error_t err;
1594   int lookup_url, single, cache_only;
1595
1596   lookup_url = has_leading_option (line, "--url");
1597   single = has_leading_option (line, "--single");
1598   cache_only = has_leading_option (line, "--cache-only");
1599   line = skip_options (line);
1600
1601   if (lookup_url && cache_only)
1602     err = gpg_error (GPG_ERR_NOT_FOUND);
1603   else if (lookup_url && single)
1604     err = gpg_error (GPG_ERR_NOT_IMPLEMENTED);
1605   else if (lookup_url)
1606     err = lookup_cert_by_url (ctx, line);
1607   else
1608     err = lookup_cert_by_pattern (ctx, line, single, cache_only);
1609
1610   return leave_cmd (ctx, err);
1611 }
1612
1613
1614 static const char hlp_loadcrl[] =
1615   "LOADCRL [--url] <filename|url>\n"
1616   "\n"
1617   "Load the CRL in the file with name FILENAME into our cache.  Note\n"
1618   "that FILENAME should be given with an absolute path because\n"
1619   "Dirmngrs cwd is not known.  With --url the CRL is directly loaded\n"
1620   "from the given URL.\n"
1621   "\n"
1622   "This command is usually used by gpgsm using the invocation \"gpgsm\n"
1623   "--call-dirmngr loadcrl <filename>\".  A direct invocation of Dirmngr\n"
1624   "is not useful because gpgsm might need to callback gpgsm to ask for\n"
1625   "the CA's certificate.";
1626 static gpg_error_t
1627 cmd_loadcrl (assuan_context_t ctx, char *line)
1628 {
1629   ctrl_t ctrl = assuan_get_pointer (ctx);
1630   gpg_error_t err = 0;
1631   int use_url = has_leading_option (line, "--url");
1632
1633   line = skip_options (line);
1634
1635   if (use_url)
1636     {
1637       ksba_reader_t reader;
1638
1639       err = crl_fetch (ctrl, line, &reader);
1640       if (err)
1641         log_error (_("fetching CRL from '%s' failed: %s\n"),
1642                    line, gpg_strerror (err));
1643       else
1644         {
1645           err = crl_cache_insert (ctrl, line, reader);
1646           if (err)
1647             log_error (_("processing CRL from '%s' failed: %s\n"),
1648                        line, gpg_strerror (err));
1649           crl_close_reader (reader);
1650         }
1651     }
1652   else
1653     {
1654       char *buf;
1655
1656       buf = xtrymalloc (strlen (line)+1);
1657       if (!buf)
1658         err = gpg_error_from_syserror ();
1659       else
1660         {
1661           strcpy_escaped_plus (buf, line);
1662           err = crl_cache_load (ctrl, buf);
1663           xfree (buf);
1664         }
1665     }
1666
1667   return leave_cmd (ctx, err);
1668 }
1669
1670
1671 static const char hlp_listcrls[] =
1672   "LISTCRLS\n"
1673   "\n"
1674   "List the content of all CRLs in a readable format.  This command is\n"
1675   "usually used by gpgsm using the invocation \"gpgsm --call-dirmngr\n"
1676   "listcrls\".  It may also be used directly using \"dirmngr\n"
1677   "--list-crls\".";
1678 static gpg_error_t
1679 cmd_listcrls (assuan_context_t ctx, char *line)
1680 {
1681   gpg_error_t err;
1682   estream_t fp;
1683
1684   (void)line;
1685
1686   fp = es_fopencookie (ctx, "w", data_line_cookie_functions);
1687   if (!fp)
1688     err = set_error (GPG_ERR_ASS_GENERAL, "error setting up a data stream");
1689   else
1690     {
1691       err = crl_cache_list (fp);
1692       es_fclose (fp);
1693     }
1694   return leave_cmd (ctx, err);
1695 }
1696
1697
1698 static const char hlp_cachecert[] =
1699   "CACHECERT\n"
1700   "\n"
1701   "Put a certificate into the internal cache.  This command might be\n"
1702   "useful if a client knows in advance certificates required for a\n"
1703   "test and wants to make sure they get added to the internal cache.\n"
1704   "It is also helpful for debugging.  To get the actual certificate,\n"
1705   "this command immediately inquires it using\n"
1706   "\n"
1707   "  INQUIRE TARGETCERT\n"
1708   "\n"
1709   "and the caller is expected to return the certificate for the\n"
1710   "request as a binary blob.";
1711 static gpg_error_t
1712 cmd_cachecert (assuan_context_t ctx, char *line)
1713 {
1714   ctrl_t ctrl = assuan_get_pointer (ctx);
1715   gpg_error_t err;
1716   ksba_cert_t cert = NULL;
1717   unsigned char *value = NULL;
1718   size_t valuelen;
1719
1720   (void)line;
1721
1722   err = assuan_inquire (ctrl->server_local->assuan_ctx, "TARGETCERT",
1723                        &value, &valuelen, MAX_CERT_LENGTH);
1724   if (err)
1725     {
1726       log_error (_("assuan_inquire failed: %s\n"), gpg_strerror (err));
1727       goto leave;
1728     }
1729
1730   if (!valuelen) /* No data returned; return a comprehensible error. */
1731     err = gpg_error (GPG_ERR_MISSING_CERT);
1732   else
1733     {
1734       err = ksba_cert_new (&cert);
1735       if (!err)
1736         err = ksba_cert_init_from_mem (cert, value, valuelen);
1737     }
1738   xfree (value);
1739   if(err)
1740     goto leave;
1741
1742   err = cache_cert (cert);
1743
1744  leave:
1745   ksba_cert_release (cert);
1746   return leave_cmd (ctx, err);
1747 }
1748
1749
1750 static const char hlp_validate[] =
1751   "VALIDATE [--systrust] [--tls] [--no-crl]\n"
1752   "\n"
1753   "Validate a certificate using the certificate validation function\n"
1754   "used internally by dirmngr.  This command is only useful for\n"
1755   "debugging.  To get the actual certificate, this command immediately\n"
1756   "inquires it using\n"
1757   "\n"
1758   "  INQUIRE TARGETCERT\n"
1759   "\n"
1760   "and the caller is expected to return the certificate for the\n"
1761   "request as a binary blob.  The option --tls modifies this by asking\n"
1762   "for list of certificates with\n"
1763   "\n"
1764   "  INQUIRE CERTLIST\n"
1765   "\n"
1766   "Here the first certificate is the target certificate, the remaining\n"
1767   "certificates are suggested intermediary certificates.  All certifciates\n"
1768   "need to be PEM encoded.\n"
1769   "\n"
1770   "The option --systrust changes the behaviour to include the system\n"
1771   "provided root certificates as trust anchors.  The option --no-crl\n"
1772   "skips CRL checks";
1773 static gpg_error_t
1774 cmd_validate (assuan_context_t ctx, char *line)
1775 {
1776   ctrl_t ctrl = assuan_get_pointer (ctx);
1777   gpg_error_t err;
1778   ksba_cert_t cert = NULL;
1779   certlist_t certlist = NULL;
1780   unsigned char *value = NULL;
1781   size_t valuelen;
1782   int systrust_mode, tls_mode, no_crl;
1783
1784   systrust_mode = has_option (line, "--systrust");
1785   tls_mode = has_option (line, "--tls");
1786   no_crl = has_option (line, "--no-crl");
1787   line = skip_options (line);
1788
1789   if (tls_mode)
1790     err = assuan_inquire (ctrl->server_local->assuan_ctx, "CERTLIST",
1791                           &value, &valuelen, MAX_CERTLIST_LENGTH);
1792   else
1793     err = assuan_inquire (ctrl->server_local->assuan_ctx, "TARGETCERT",
1794                           &value, &valuelen, MAX_CERT_LENGTH);
1795   if (err)
1796     {
1797       log_error (_("assuan_inquire failed: %s\n"), gpg_strerror (err));
1798       goto leave;
1799     }
1800
1801   if (!valuelen) /* No data returned; return a comprehensible error. */
1802     err = gpg_error (GPG_ERR_MISSING_CERT);
1803   else if (tls_mode)
1804     {
1805       estream_t fp;
1806
1807       fp = es_fopenmem_init (0, "rb", value, valuelen);
1808       if (!fp)
1809         err = gpg_error_from_syserror ();
1810       else
1811         {
1812           err = read_certlist_from_stream (&certlist, fp);
1813           es_fclose (fp);
1814           if (!err && !certlist)
1815             err = gpg_error (GPG_ERR_MISSING_CERT);
1816           if (!err)
1817             {
1818               /* Extraxt the first certificate from the list.  */
1819               cert = certlist->cert;
1820               ksba_cert_ref (cert);
1821             }
1822         }
1823     }
1824   else
1825     {
1826       err = ksba_cert_new (&cert);
1827       if (!err)
1828         err = ksba_cert_init_from_mem (cert, value, valuelen);
1829     }
1830   xfree (value);
1831   if(err)
1832     goto leave;
1833
1834   if (!tls_mode)
1835     {
1836       /* If we have this certificate already in our cache, use the
1837        * cached version for validation because this will take care of
1838        * any cached results.  We don't need to do this in tls mode
1839        * because this has already been done for certificate in a
1840        * certlist_t. */
1841       unsigned char fpr[20];
1842       ksba_cert_t tmpcert;
1843
1844       cert_compute_fpr (cert, fpr);
1845       tmpcert = get_cert_byfpr (fpr);
1846       if (tmpcert)
1847         {
1848           ksba_cert_release (cert);
1849           cert = tmpcert;
1850         }
1851     }
1852
1853   /* Quick hack to make verification work by inserting the supplied
1854    * certs into the cache.  */
1855   if (tls_mode && certlist)
1856     {
1857       certlist_t cl;
1858
1859       for (cl = certlist->next; cl; cl = cl->next)
1860         cache_cert (cl->cert);
1861     }
1862
1863   err = validate_cert_chain (ctrl, cert, NULL,
1864                              (VALIDATE_FLAG_TRUST_CONFIG
1865                               | (tls_mode ? VALIDATE_FLAG_TLS : 0)
1866                               | (systrust_mode ? VALIDATE_FLAG_TRUST_SYSTEM : 0)
1867                               | (no_crl ? VALIDATE_FLAG_NOCRLCHECK : 0)),
1868                              NULL);
1869
1870  leave:
1871   ksba_cert_release (cert);
1872   release_certlist (certlist);
1873   return leave_cmd (ctx, err);
1874 }
1875
1876
1877 \f
1878 /* Parse an keyserver URI and store it in a new uri item which is
1879    returned at R_ITEM.  On error return an error code.  */
1880 static gpg_error_t
1881 make_keyserver_item (const char *uri, uri_item_t *r_item)
1882 {
1883   gpg_error_t err;
1884   uri_item_t item;
1885
1886   *r_item = NULL;
1887   item = xtrymalloc (sizeof *item + strlen (uri));
1888   if (!item)
1889     return gpg_error_from_syserror ();
1890
1891   item->next = NULL;
1892   item->parsed_uri = NULL;
1893   strcpy (item->uri, uri);
1894
1895 #if USE_LDAP
1896   if (ldap_uri_p (item->uri))
1897     err = ldap_parse_uri (&item->parsed_uri, uri);
1898   else
1899 #endif
1900     {
1901       err = http_parse_uri (&item->parsed_uri, uri, 1);
1902     }
1903
1904   if (err)
1905     xfree (item);
1906   else
1907     *r_item = item;
1908   return err;
1909 }
1910
1911
1912 /* If no keyserver is stored in CTRL but a global keyserver has been
1913    set, put that global keyserver into CTRL.  We need use this
1914    function to help migrate from the old gpg based keyserver
1915    configuration to the new dirmngr based configuration.  */
1916 static gpg_error_t
1917 ensure_keyserver (ctrl_t ctrl)
1918 {
1919   gpg_error_t err;
1920   uri_item_t item;
1921   uri_item_t onion_items = NULL;
1922   uri_item_t plain_items = NULL;
1923   uri_item_t ui;
1924   strlist_t sl;
1925
1926   if (ctrl->server_local->keyservers)
1927     return 0; /* Already set for this session.  */
1928   if (!opt.keyserver)
1929     {
1930       /* No global option set.  Fall back to default:  */
1931       return make_keyserver_item (DIRMNGR_DEFAULT_KEYSERVER,
1932                                   &ctrl->server_local->keyservers);
1933     }
1934
1935   for (sl = opt.keyserver; sl; sl = sl->next)
1936     {
1937       err = make_keyserver_item (sl->d, &item);
1938       if (err)
1939         goto leave;
1940       if (item->parsed_uri->onion)
1941         {
1942           item->next = onion_items;
1943           onion_items = item;
1944         }
1945       else
1946         {
1947           item->next = plain_items;
1948           plain_items = item;
1949         }
1950     }
1951
1952   /* Decide which to use.  Note that the session has no keyservers
1953      yet set. */
1954   if (onion_items && !onion_items->next && plain_items && !plain_items->next)
1955     {
1956       /* If there is just one onion and one plain keyserver given, we take
1957          only one depending on whether Tor is running or not.  */
1958       if (is_tor_running (ctrl))
1959         {
1960           ctrl->server_local->keyservers = onion_items;
1961           onion_items = NULL;
1962         }
1963       else
1964         {
1965           ctrl->server_local->keyservers = plain_items;
1966           plain_items = NULL;
1967         }
1968     }
1969   else if (!is_tor_running (ctrl))
1970     {
1971       /* Tor is not running.  It does not make sense to add Onion
1972          addresses.  */
1973       ctrl->server_local->keyservers = plain_items;
1974       plain_items = NULL;
1975     }
1976   else
1977     {
1978       /* In all other cases add all keyservers.  */
1979       ctrl->server_local->keyservers = onion_items;
1980       onion_items = NULL;
1981       for (ui = ctrl->server_local->keyservers; ui && ui->next; ui = ui->next)
1982         ;
1983       if (ui)
1984         ui->next = plain_items;
1985       else
1986         ctrl->server_local->keyservers = plain_items;
1987       plain_items = NULL;
1988     }
1989
1990  leave:
1991   release_uri_item_list (onion_items);
1992   release_uri_item_list (plain_items);
1993
1994   return err;
1995 }
1996
1997
1998 static const char hlp_keyserver[] =
1999   "KEYSERVER [<options>] [<uri>|<host>]\n"
2000   "Options are:\n"
2001   "  --help\n"
2002   "  --clear      Remove all configured keyservers\n"
2003   "  --resolve    Resolve HKP host names and rotate\n"
2004   "  --hosttable  Print table of known hosts and pools\n"
2005   "  --dead       Mark <host> as dead\n"
2006   "  --alive      Mark <host> as alive\n"
2007   "\n"
2008   "If called without arguments list all configured keyserver URLs.\n"
2009   "If called with an URI add this as keyserver.  Note that keyservers\n"
2010   "are configured on a per-session base.  A default keyserver may already be\n"
2011   "present, thus the \"--clear\" option must be used to get full control.\n"
2012   "If \"--clear\" and an URI are used together the clear command is\n"
2013   "obviously executed first.  A RESET command does not change the list\n"
2014   "of configured keyservers.";
2015 static gpg_error_t
2016 cmd_keyserver (assuan_context_t ctx, char *line)
2017 {
2018   ctrl_t ctrl = assuan_get_pointer (ctx);
2019   gpg_error_t err = 0;
2020   int clear_flag, add_flag, help_flag, host_flag, resolve_flag;
2021   int dead_flag, alive_flag;
2022   uri_item_t item = NULL; /* gcc 4.4.5 is not able to detect that it
2023                              is always initialized.  */
2024
2025   clear_flag = has_option (line, "--clear");
2026   help_flag = has_option (line, "--help");
2027   resolve_flag = has_option (line, "--resolve");
2028   host_flag = has_option (line, "--hosttable");
2029   dead_flag = has_option (line, "--dead");
2030   alive_flag = has_option (line, "--alive");
2031   line = skip_options (line);
2032   add_flag = !!*line;
2033
2034   if (help_flag)
2035     {
2036       err = ks_action_help (ctrl, line);
2037       goto leave;
2038     }
2039
2040   if (resolve_flag)
2041     {
2042       err = ensure_keyserver (ctrl);
2043       if (!err)
2044         err = ks_action_resolve (ctrl, ctrl->server_local->keyservers);
2045       if (err)
2046         goto leave;
2047     }
2048
2049   if (alive_flag && dead_flag)
2050     {
2051       err = set_error (GPG_ERR_ASS_PARAMETER, "no support for zombies");
2052       goto leave;
2053     }
2054   if (dead_flag)
2055     {
2056       err = check_owner_permission (ctx, "no permission to use --dead");
2057       if (err)
2058         goto leave;
2059     }
2060   if (alive_flag || dead_flag)
2061     {
2062       if (!*line)
2063         {
2064           err = set_error (GPG_ERR_ASS_PARAMETER, "name of host missing");
2065           goto leave;
2066         }
2067
2068       err = ks_hkp_mark_host (ctrl, line, alive_flag);
2069       if (err)
2070         goto leave;
2071     }
2072
2073   if (host_flag)
2074     {
2075       err = ks_hkp_print_hosttable (ctrl);
2076       if (err)
2077         goto leave;
2078     }
2079   if (resolve_flag || host_flag || alive_flag || dead_flag)
2080     goto leave;
2081
2082   if (add_flag)
2083     {
2084       err = make_keyserver_item (line, &item);
2085       if (err)
2086         goto leave;
2087     }
2088   if (clear_flag)
2089     release_ctrl_keyservers (ctrl);
2090   if (add_flag)
2091     {
2092       item->next = ctrl->server_local->keyservers;
2093       ctrl->server_local->keyservers = item;
2094     }
2095
2096   if (!add_flag && !clear_flag && !help_flag)
2097     {
2098       /* List configured keyservers.  However, we first add a global
2099          keyserver. */
2100       uri_item_t u;
2101
2102       err = ensure_keyserver (ctrl);
2103       if (err)
2104         {
2105           assuan_set_error (ctx, err,
2106                             "Bad keyserver configuration in dirmngr.conf");
2107           goto leave;
2108         }
2109
2110       for (u=ctrl->server_local->keyservers; u; u = u->next)
2111         dirmngr_status (ctrl, "KEYSERVER", u->uri, NULL);
2112     }
2113   err = 0;
2114
2115  leave:
2116   return leave_cmd (ctx, err);
2117 }
2118
2119
2120 \f
2121 static const char hlp_ks_search[] =
2122   "KS_SEARCH {<pattern>}\n"
2123   "\n"
2124   "Search the configured OpenPGP keyservers (see command KEYSERVER)\n"
2125   "for keys matching PATTERN";
2126 static gpg_error_t
2127 cmd_ks_search (assuan_context_t ctx, char *line)
2128 {
2129   ctrl_t ctrl = assuan_get_pointer (ctx);
2130   gpg_error_t err;
2131   strlist_t list, sl;
2132   char *p;
2133   estream_t outfp;
2134
2135   if (has_option (line, "--quick"))
2136     ctrl->timeout = opt.connect_quick_timeout;
2137   line = skip_options (line);
2138
2139   /* Break the line down into an strlist.  Each pattern is
2140      percent-plus escaped. */
2141   list = NULL;
2142   for (p=line; *p; line = p)
2143     {
2144       while (*p && *p != ' ')
2145         p++;
2146       if (*p)
2147         *p++ = 0;
2148       if (*line)
2149         {
2150           sl = xtrymalloc (sizeof *sl + strlen (line));
2151           if (!sl)
2152             {
2153               err = gpg_error_from_syserror ();
2154               goto leave;
2155             }
2156           sl->flags = 0;
2157           strcpy_escaped_plus (sl->d, line);
2158           sl->next = list;
2159           list = sl;
2160         }
2161     }
2162
2163   err = ensure_keyserver (ctrl);
2164   if (err)
2165     goto leave;
2166
2167   /* Setup an output stream and perform the search.  */
2168   outfp = es_fopencookie (ctx, "w", data_line_cookie_functions);
2169   if (!outfp)
2170     err = set_error (GPG_ERR_ASS_GENERAL, "error setting up a data stream");
2171   else
2172     {
2173       err = ks_action_search (ctrl, ctrl->server_local->keyservers,
2174                               list, outfp);
2175       es_fclose (outfp);
2176     }
2177
2178  leave:
2179   free_strlist (list);
2180   return leave_cmd (ctx, err);
2181 }
2182
2183
2184 \f
2185 static const char hlp_ks_get[] =
2186   "KS_GET {<pattern>}\n"
2187   "\n"
2188   "Get the keys matching PATTERN from the configured OpenPGP keyservers\n"
2189   "(see command KEYSERVER).  Each pattern should be a keyid, a fingerprint,\n"
2190   "or an exact name indicated by the '=' prefix.";
2191 static gpg_error_t
2192 cmd_ks_get (assuan_context_t ctx, char *line)
2193 {
2194   ctrl_t ctrl = assuan_get_pointer (ctx);
2195   gpg_error_t err;
2196   strlist_t list, sl;
2197   char *p;
2198   estream_t outfp;
2199
2200   if (has_option (line, "--quick"))
2201     ctrl->timeout = opt.connect_quick_timeout;
2202   line = skip_options (line);
2203
2204   /* Break the line into a strlist.  Each pattern is by
2205      definition percent-plus escaped.  However we only support keyids
2206      and fingerprints and thus the client has no need to apply the
2207      escaping.  */
2208   list = NULL;
2209   for (p=line; *p; line = p)
2210     {
2211       while (*p && *p != ' ')
2212         p++;
2213       if (*p)
2214         *p++ = 0;
2215       if (*line)
2216         {
2217           sl = xtrymalloc (sizeof *sl + strlen (line));
2218           if (!sl)
2219             {
2220               err = gpg_error_from_syserror ();
2221               goto leave;
2222             }
2223           sl->flags = 0;
2224           strcpy_escaped_plus (sl->d, line);
2225           sl->next = list;
2226           list = sl;
2227         }
2228     }
2229
2230   err = ensure_keyserver (ctrl);
2231   if (err)
2232     goto leave;
2233
2234   /* Setup an output stream and perform the get.  */
2235   outfp = es_fopencookie (ctx, "w", data_line_cookie_functions);
2236   if (!outfp)
2237     err = set_error (GPG_ERR_ASS_GENERAL, "error setting up a data stream");
2238   else
2239     {
2240       ctrl->server_local->inhibit_data_logging = 1;
2241       ctrl->server_local->inhibit_data_logging_now = 0;
2242       ctrl->server_local->inhibit_data_logging_count = 0;
2243       err = ks_action_get (ctrl, ctrl->server_local->keyservers, list, outfp);
2244       es_fclose (outfp);
2245       ctrl->server_local->inhibit_data_logging = 0;
2246     }
2247
2248  leave:
2249   free_strlist (list);
2250   return leave_cmd (ctx, err);
2251 }
2252
2253
2254 static const char hlp_ks_fetch[] =
2255   "KS_FETCH <URL>\n"
2256   "\n"
2257   "Get the key(s) from URL.";
2258 static gpg_error_t
2259 cmd_ks_fetch (assuan_context_t ctx, char *line)
2260 {
2261   ctrl_t ctrl = assuan_get_pointer (ctx);
2262   gpg_error_t err;
2263   estream_t outfp;
2264
2265   if (has_option (line, "--quick"))
2266     ctrl->timeout = opt.connect_quick_timeout;
2267   line = skip_options (line);
2268
2269   err = ensure_keyserver (ctrl);  /* FIXME: Why do we needs this here?  */
2270   if (err)
2271     goto leave;
2272
2273   /* Setup an output stream and perform the get.  */
2274   outfp = es_fopencookie (ctx, "w", data_line_cookie_functions);
2275   if (!outfp)
2276     err = set_error (GPG_ERR_ASS_GENERAL, "error setting up a data stream");
2277   else
2278     {
2279       ctrl->server_local->inhibit_data_logging = 1;
2280       ctrl->server_local->inhibit_data_logging_now = 0;
2281       ctrl->server_local->inhibit_data_logging_count = 0;
2282       err = ks_action_fetch (ctrl, line, outfp);
2283       es_fclose (outfp);
2284       ctrl->server_local->inhibit_data_logging = 0;
2285     }
2286
2287  leave:
2288   return leave_cmd (ctx, err);
2289 }
2290
2291
2292 \f
2293 static const char hlp_ks_put[] =
2294   "KS_PUT\n"
2295   "\n"
2296   "Send a key to the configured OpenPGP keyservers.  The actual key material\n"
2297   "is then requested by Dirmngr using\n"
2298   "\n"
2299   "  INQUIRE KEYBLOCK\n"
2300   "\n"
2301   "The client shall respond with a binary version of the keyblock (e.g.,\n"
2302   "the output of `gpg --export KEYID').  For LDAP\n"
2303   "keyservers Dirmngr may ask for meta information of the provided keyblock\n"
2304   "using:\n"
2305   "\n"
2306   "  INQUIRE KEYBLOCK_INFO\n"
2307   "\n"
2308   "The client shall respond with a colon delimited info lines (the output\n"
2309   "of 'for x in keys sigs; do gpg --list-$x --with-colons KEYID; done').\n";
2310 static gpg_error_t
2311 cmd_ks_put (assuan_context_t ctx, char *line)
2312 {
2313   ctrl_t ctrl = assuan_get_pointer (ctx);
2314   gpg_error_t err;
2315   unsigned char *value = NULL;
2316   size_t valuelen;
2317   unsigned char *info = NULL;
2318   size_t infolen;
2319
2320   /* No options for now.  */
2321   line = skip_options (line);
2322
2323   err = ensure_keyserver (ctrl);
2324   if (err)
2325     goto leave;
2326
2327   /* Ask for the key material.  */
2328   err = assuan_inquire (ctx, "KEYBLOCK",
2329                         &value, &valuelen, MAX_KEYBLOCK_LENGTH);
2330   if (err)
2331     {
2332       log_error (_("assuan_inquire failed: %s\n"), gpg_strerror (err));
2333       goto leave;
2334     }
2335
2336   if (!valuelen) /* No data returned; return a comprehensible error. */
2337     {
2338       err = gpg_error (GPG_ERR_MISSING_CERT);
2339       goto leave;
2340     }
2341
2342   /* Ask for the key meta data. Not actually needed for HKP servers
2343      but we do it anyway to test the client implementation.  */
2344   err = assuan_inquire (ctx, "KEYBLOCK_INFO",
2345                         &info, &infolen, MAX_KEYBLOCK_LENGTH);
2346   if (err)
2347     {
2348       log_error (_("assuan_inquire failed: %s\n"), gpg_strerror (err));
2349       goto leave;
2350     }
2351
2352   /* Send the key.  */
2353   err = ks_action_put (ctrl, ctrl->server_local->keyservers,
2354                        value, valuelen, info, infolen);
2355
2356  leave:
2357   xfree (info);
2358   xfree (value);
2359   return leave_cmd (ctx, err);
2360 }
2361
2362
2363 \f
2364 static const char hlp_loadswdb[] =
2365   "LOADSWDB [--force]\n"
2366   "\n"
2367   "Load and verify the swdb.lst from the Net.";
2368 static gpg_error_t
2369 cmd_loadswdb (assuan_context_t ctx, char *line)
2370 {
2371   ctrl_t ctrl = assuan_get_pointer (ctx);
2372   gpg_error_t err;
2373
2374   err = dirmngr_load_swdb (ctrl, has_option (line, "--force"));
2375
2376   return leave_cmd (ctx, err);
2377 }
2378
2379
2380 \f
2381 static const char hlp_getinfo[] =
2382   "GETINFO <what>\n"
2383   "\n"
2384   "Multi purpose command to return certain information.  \n"
2385   "Supported values of WHAT are:\n"
2386   "\n"
2387   "version     - Return the version of the program.\n"
2388   "pid         - Return the process id of the server.\n"
2389   "tor         - Return OK if running in Tor mode\n"
2390   "dnsinfo     - Return info about the DNS resolver\n"
2391   "socket_name - Return the name of the socket.\n";
2392 static gpg_error_t
2393 cmd_getinfo (assuan_context_t ctx, char *line)
2394 {
2395   ctrl_t ctrl = assuan_get_pointer (ctx);
2396   gpg_error_t err;
2397
2398   if (!strcmp (line, "version"))
2399     {
2400       const char *s = VERSION;
2401       err = assuan_send_data (ctx, s, strlen (s));
2402     }
2403   else if (!strcmp (line, "pid"))
2404     {
2405       char numbuf[50];
2406
2407       snprintf (numbuf, sizeof numbuf, "%lu", (unsigned long)getpid ());
2408       err = assuan_send_data (ctx, numbuf, strlen (numbuf));
2409     }
2410   else if (!strcmp (line, "socket_name"))
2411     {
2412       const char *s = dirmngr_get_current_socket_name ();
2413       err = assuan_send_data (ctx, s, strlen (s));
2414     }
2415   else if (!strcmp (line, "tor"))
2416     {
2417       int use_tor;
2418
2419       use_tor = dirmngr_use_tor ();
2420       if (use_tor)
2421         {
2422           if (!is_tor_running (ctrl))
2423             err = assuan_write_status (ctx, "NO_TOR", "Tor not running");
2424           else
2425             err = 0;
2426           if (!err)
2427             assuan_set_okay_line (ctx, use_tor == 1 ? "- Tor mode is enabled"
2428                                   /**/              : "- Tor mode is enforced");
2429         }
2430       else
2431         err = set_error (GPG_ERR_FALSE, "Tor mode is NOT enabled");
2432     }
2433   else if (!strcmp (line, "dnsinfo"))
2434     {
2435       if (standard_resolver_p ())
2436         assuan_set_okay_line
2437           (ctx, "- Forced use of System resolver (w/o Tor support)");
2438       else
2439         {
2440 #ifdef USE_LIBDNS
2441           assuan_set_okay_line (ctx, (recursive_resolver_p ()
2442                                       ? "- Libdns recursive resolver"
2443                                       : "- Libdns stub resolver"));
2444 #else
2445           assuan_set_okay_line (ctx, "- System resolver (w/o Tor support)");
2446 #endif
2447         }
2448       err = 0;
2449     }
2450   else
2451     err = set_error (GPG_ERR_ASS_PARAMETER, "unknown value for WHAT");
2452
2453   return leave_cmd (ctx, err);
2454 }
2455
2456
2457 \f
2458 static const char hlp_killdirmngr[] =
2459   "KILLDIRMNGR\n"
2460   "\n"
2461   "This command allows a user - given sufficient permissions -\n"
2462   "to kill this dirmngr process.\n";
2463 static gpg_error_t
2464 cmd_killdirmngr (assuan_context_t ctx, char *line)
2465 {
2466   ctrl_t ctrl = assuan_get_pointer (ctx);
2467
2468   (void)line;
2469
2470   ctrl->server_local->stopme = 1;
2471   assuan_set_flag (ctx, ASSUAN_FORCE_CLOSE, 1);
2472   return gpg_error (GPG_ERR_EOF);
2473 }
2474
2475
2476 static const char hlp_reloaddirmngr[] =
2477   "RELOADDIRMNGR\n"
2478   "\n"
2479   "This command is an alternative to SIGHUP\n"
2480   "to reload the configuration.";
2481 static gpg_error_t
2482 cmd_reloaddirmngr (assuan_context_t ctx, char *line)
2483 {
2484   (void)ctx;
2485   (void)line;
2486
2487   dirmngr_sighup_action ();
2488   return 0;
2489 }
2490
2491
2492 \f
2493 /* Tell the assuan library about our commands. */
2494 static int
2495 register_commands (assuan_context_t ctx)
2496 {
2497   static struct {
2498     const char *name;
2499     assuan_handler_t handler;
2500     const char * const help;
2501   } table[] = {
2502     { "DNS_CERT",   cmd_dns_cert,   hlp_dns_cert },
2503     { "WKD_GET",    cmd_wkd_get,    hlp_wkd_get },
2504     { "LDAPSERVER", cmd_ldapserver, hlp_ldapserver },
2505     { "ISVALID",    cmd_isvalid,    hlp_isvalid },
2506     { "CHECKCRL",   cmd_checkcrl,   hlp_checkcrl },
2507     { "CHECKOCSP",  cmd_checkocsp,  hlp_checkocsp },
2508     { "LOOKUP",     cmd_lookup,     hlp_lookup },
2509     { "LOADCRL",    cmd_loadcrl,    hlp_loadcrl },
2510     { "LISTCRLS",   cmd_listcrls,   hlp_listcrls },
2511     { "CACHECERT",  cmd_cachecert,  hlp_cachecert },
2512     { "VALIDATE",   cmd_validate,   hlp_validate },
2513     { "KEYSERVER",  cmd_keyserver,  hlp_keyserver },
2514     { "KS_SEARCH",  cmd_ks_search,  hlp_ks_search },
2515     { "KS_GET",     cmd_ks_get,     hlp_ks_get },
2516     { "KS_FETCH",   cmd_ks_fetch,   hlp_ks_fetch },
2517     { "KS_PUT",     cmd_ks_put,     hlp_ks_put },
2518     { "GETINFO",    cmd_getinfo,    hlp_getinfo },
2519     { "LOADSWDB",   cmd_loadswdb,   hlp_loadswdb },
2520     { "KILLDIRMNGR",cmd_killdirmngr,hlp_killdirmngr },
2521     { "RELOADDIRMNGR",cmd_reloaddirmngr,hlp_reloaddirmngr },
2522     { NULL, NULL }
2523   };
2524   int i, j, rc;
2525
2526   for (i=j=0; table[i].name; i++)
2527     {
2528       rc = assuan_register_command (ctx, table[i].name, table[i].handler,
2529                                     table[i].help);
2530       if (rc)
2531         return rc;
2532     }
2533   return 0;
2534 }
2535
2536
2537 /* Note that we do not reset the list of configured keyservers.  */
2538 static gpg_error_t
2539 reset_notify (assuan_context_t ctx, char *line)
2540 {
2541   ctrl_t ctrl = assuan_get_pointer (ctx);
2542   (void)line;
2543
2544 #if USE_LDAP
2545   ldapserver_list_free (ctrl->server_local->ldapservers);
2546 #endif /*USE_LDAP*/
2547   ctrl->server_local->ldapservers = NULL;
2548   return 0;
2549 }
2550
2551
2552 /* This function is called by our assuan log handler to test whether a
2553  * log message shall really be printed.  The function must return
2554  * false to inhibit the logging of MSG.  CAT gives the requested log
2555  * category.  MSG might be NULL. */
2556 int
2557 dirmngr_assuan_log_monitor (assuan_context_t ctx, unsigned int cat,
2558                             const char *msg)
2559 {
2560   ctrl_t ctrl = assuan_get_pointer (ctx);
2561
2562   (void)cat;
2563   (void)msg;
2564
2565   if (!ctrl || !ctrl->server_local)
2566     return 1; /* Can't decide - allow logging.  */
2567
2568   if (!ctrl->server_local->inhibit_data_logging)
2569     return 1; /* Not requested - allow logging.  */
2570
2571   /* Disallow logging if *_now is true.  */
2572   return !ctrl->server_local->inhibit_data_logging_now;
2573 }
2574
2575
2576 /* Startup the server and run the main command loop.  With FD = -1,
2577    use stdin/stdout. */
2578 void
2579 start_command_handler (assuan_fd_t fd)
2580 {
2581   static const char hello[] = "Dirmngr " VERSION " at your service";
2582   static char *hello_line;
2583   int rc;
2584   assuan_context_t ctx;
2585   ctrl_t ctrl;
2586
2587   ctrl = xtrycalloc (1, sizeof *ctrl);
2588   if (ctrl)
2589     ctrl->server_local = xtrycalloc (1, sizeof *ctrl->server_local);
2590   if (!ctrl || !ctrl->server_local)
2591     {
2592       log_error (_("can't allocate control structure: %s\n"),
2593                  strerror (errno));
2594       xfree (ctrl);
2595       return;
2596     }
2597
2598   dirmngr_init_default_ctrl (ctrl);
2599
2600   rc = assuan_new (&ctx);
2601   if (rc)
2602     {
2603       log_error (_("failed to allocate assuan context: %s\n"),
2604                  gpg_strerror (rc));
2605       dirmngr_exit (2);
2606     }
2607
2608   if (fd == ASSUAN_INVALID_FD)
2609     {
2610       assuan_fd_t filedes[2];
2611
2612       filedes[0] = assuan_fdopen (0);
2613       filedes[1] = assuan_fdopen (1);
2614       rc = assuan_init_pipe_server (ctx, filedes);
2615     }
2616   else
2617     {
2618       rc = assuan_init_socket_server (ctx, fd, ASSUAN_SOCKET_SERVER_ACCEPTED);
2619     }
2620
2621   if (rc)
2622     {
2623       assuan_release (ctx);
2624       log_error (_("failed to initialize the server: %s\n"),
2625                  gpg_strerror(rc));
2626       dirmngr_exit (2);
2627     }
2628
2629   rc = register_commands (ctx);
2630   if (rc)
2631     {
2632       log_error (_("failed to the register commands with Assuan: %s\n"),
2633                  gpg_strerror(rc));
2634       dirmngr_exit (2);
2635     }
2636
2637
2638   if (!hello_line)
2639     {
2640       hello_line = xtryasprintf
2641         ("Home: %s\n"
2642          "Config: %s\n"
2643          "%s",
2644          gnupg_homedir (),
2645          opt.config_filename? opt.config_filename : "[none]",
2646          hello);
2647     }
2648
2649   ctrl->server_local->assuan_ctx = ctx;
2650   assuan_set_pointer (ctx, ctrl);
2651
2652   assuan_set_hello_line (ctx, hello_line);
2653   assuan_register_option_handler (ctx, option_handler);
2654   assuan_register_reset_notify (ctx, reset_notify);
2655
2656   for (;;)
2657     {
2658       rc = assuan_accept (ctx);
2659       if (rc == -1)
2660         break;
2661       if (rc)
2662         {
2663           log_info (_("Assuan accept problem: %s\n"), gpg_strerror (rc));
2664           break;
2665         }
2666
2667 #ifndef HAVE_W32_SYSTEM
2668       if (opt.verbose)
2669         {
2670           assuan_peercred_t peercred;
2671
2672           if (!assuan_get_peercred (ctx, &peercred))
2673             log_info ("connection from process %ld (%ld:%ld)\n",
2674                       (long)peercred->pid, (long)peercred->uid,
2675                       (long)peercred->gid);
2676         }
2677 #endif
2678
2679       rc = assuan_process (ctx);
2680       if (rc)
2681         {
2682           log_info (_("Assuan processing failed: %s\n"), gpg_strerror (rc));
2683           continue;
2684         }
2685     }
2686
2687
2688 #if USE_LDAP
2689   ldap_wrapper_connection_cleanup (ctrl);
2690
2691   ldapserver_list_free (ctrl->server_local->ldapservers);
2692 #endif /*USE_LDAP*/
2693   ctrl->server_local->ldapservers = NULL;
2694
2695   release_ctrl_keyservers (ctrl);
2696
2697   ctrl->server_local->assuan_ctx = NULL;
2698   assuan_release (ctx);
2699
2700   if (ctrl->server_local->stopme)
2701     dirmngr_exit (0);
2702
2703   if (ctrl->refcount)
2704     log_error ("oops: connection control structure still referenced (%d)\n",
2705                ctrl->refcount);
2706   else
2707     {
2708       release_ctrl_ocsp_certs (ctrl);
2709       xfree (ctrl->server_local);
2710       dirmngr_deinit_default_ctrl (ctrl);
2711       xfree (ctrl);
2712     }
2713 }
2714
2715
2716 /* Send a status line back to the client.  KEYWORD is the status
2717    keyword, the optional string arguments are blank separated added to
2718    the line, the last argument must be a NULL. */
2719 gpg_error_t
2720 dirmngr_status (ctrl_t ctrl, const char *keyword, ...)
2721 {
2722   gpg_error_t err = 0;
2723   va_list arg_ptr;
2724   const char *text;
2725
2726   va_start (arg_ptr, keyword);
2727
2728   if (ctrl->server_local)
2729     {
2730       assuan_context_t ctx = ctrl->server_local->assuan_ctx;
2731       char buf[950], *p;
2732       size_t n;
2733
2734       p = buf;
2735       n = 0;
2736       while ( (text = va_arg (arg_ptr, const char *)) )
2737         {
2738           if (n)
2739             {
2740               *p++ = ' ';
2741               n++;
2742             }
2743           for ( ; *text && n < DIM (buf)-2; n++)
2744             *p++ = *text++;
2745         }
2746       *p = 0;
2747       err = assuan_write_status (ctx, keyword, buf);
2748     }
2749
2750   va_end (arg_ptr);
2751   return err;
2752 }
2753
2754
2755 /* Print a help status line.  TEXTLEN gives the length of the text
2756    from TEXT to be printed.  The function splits text at LFs.  */
2757 gpg_error_t
2758 dirmngr_status_help (ctrl_t ctrl, const char *text)
2759 {
2760   gpg_error_t err = 0;
2761
2762   if (ctrl->server_local)
2763     {
2764       assuan_context_t ctx = ctrl->server_local->assuan_ctx;
2765       char buf[950], *p;
2766       size_t n;
2767
2768       do
2769         {
2770           p = buf;
2771           n = 0;
2772           for ( ; *text && *text != '\n' && n < DIM (buf)-2; n++)
2773             *p++ = *text++;
2774           if (*text == '\n')
2775             text++;
2776           *p = 0;
2777           err = assuan_write_status (ctx, "#", buf);
2778         }
2779       while (!err && *text);
2780     }
2781
2782   return err;
2783 }
2784
2785
2786 /* This function is similar to print_assuan_status but takes a CTRL
2787  * arg instead of an assuan context as first argument.  */
2788 gpg_error_t
2789 dirmngr_status_printf (ctrl_t ctrl, const char *keyword,
2790                        const char *format, ...)
2791 {
2792   gpg_error_t err;
2793   va_list arg_ptr;
2794   assuan_context_t ctx = ctrl->server_local->assuan_ctx;
2795
2796   va_start (arg_ptr, format);
2797   err = vprint_assuan_status (ctx, keyword, format, arg_ptr);
2798   va_end (arg_ptr);
2799   return err;
2800 }
2801
2802
2803 /* Send a tick progress indicator back.  Fixme: This is only done for
2804    the currently active channel.  */
2805 gpg_error_t
2806 dirmngr_tick (ctrl_t ctrl)
2807 {
2808   static time_t next_tick = 0;
2809   gpg_error_t err = 0;
2810   time_t now = time (NULL);
2811
2812   if (!next_tick)
2813     {
2814       next_tick = now + 1;
2815     }
2816   else if ( now > next_tick )
2817     {
2818       if (ctrl)
2819         {
2820           err = dirmngr_status (ctrl, "PROGRESS", "tick", "? 0 0", NULL);
2821           if (err)
2822             {
2823               /* Take this as in indication for a cancel request.  */
2824               err = gpg_error (GPG_ERR_CANCELED);
2825             }
2826           now = time (NULL);
2827         }
2828
2829       next_tick = now + 1;
2830     }
2831   return err;
2832 }