* minip12.c (parse_bag_encrypted_data): Print error if a bad
[gnupg.git] / sm / export.c
1 /* export.c
2  * Copyright (C) 2002, 2003, 2004 Free Software Foundation, Inc.
3  *
4  * This file is part of GnuPG.
5  *
6  * GnuPG is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 2 of the License, or
9  * (at your option) any later version.
10  *
11  * GnuPG is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software
18  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
19  */
20
21 #include <config.h>
22 #include <stdio.h>
23 #include <stdlib.h>
24 #include <string.h>
25 #include <errno.h>
26 #include <unistd.h> 
27 #include <time.h>
28 #include <assert.h>
29 #include <signal.h>
30 #include <fcntl.h>
31 #include <sys/wait.h>
32
33 #include "gpgsm.h"
34 #include <gcrypt.h>
35 #include <ksba.h>
36
37 #include "keydb.h"
38 #include "i18n.h"
39
40 #ifdef _POSIX_OPEN_MAX
41 #define MAX_OPEN_FDS _POSIX_OPEN_MAX
42 #else
43 #define MAX_OPEN_FDS 20
44 #endif
45
46
47 /* A table to store a fingerprint as used in a duplicates table.  We
48    don't need to hash here because a fingerprint is alrady a perfect
49    hash value.  This we use the most significant bits to index the
50    table and then use a linked list for the overflow.  Possible
51    enhancement for very large number of certictates: Add a second
52    level table and then resort to a linked list. */
53 struct duptable_s
54 {
55   struct duptable_s *next;
56
57   /* Note that we only need to store 19 bytes because the first byte
58      is implictly given by the table index (we require at least 8
59      bits). */
60   unsigned char fpr[19];
61 };
62 typedef struct duptable_s *duptable_t;
63 #define DUPTABLE_BITS 12
64 #define DUPTABLE_SIZE (1 << DUPTABLE_BITS)
65
66
67 static void print_short_info (ksba_cert_t cert, FILE *fp);
68 static gpg_error_t export_p12 (ctrl_t ctrl,
69                                const unsigned char *certimg, size_t certimglen,
70                                const char *prompt, const char *keygrip,
71                                FILE **retfp);
72
73
74 /* Create a table used to indetify duplicated certificates. */
75 static duptable_t *
76 create_duptable (void)
77 {
78   return xtrycalloc (DUPTABLE_SIZE, sizeof (duptable_t));
79 }
80
81 static void
82 destroy_duptable (duptable_t *table)
83 {
84   int idx;
85   duptable_t t, t2;
86
87   if (table)
88     {
89       for (idx=0; idx < DUPTABLE_SIZE; idx++) 
90         for (t = table[idx]; t; t = t2)
91           {
92             t2 = t->next;
93             xfree (t);
94           }
95       xfree (table);
96     }
97 }
98
99 /* Insert the 20 byte fingerprint FPR into TABLE.  Sets EXITS to true
100    if the fingerprint already exists in the table. */
101 static gpg_error_t
102 insert_duptable (duptable_t *table, unsigned char *fpr, int *exists)
103 {
104   size_t idx;
105   duptable_t t;
106   
107   *exists = 0;
108   idx = fpr[0];
109 #if DUPTABLE_BITS > 16 || DUPTABLE_BITS < 8
110 #error cannot handle a table larger than 16 bits or smaller than 8 bits
111 #elif DUPTABLE_BITS > 8
112   idx <<= (DUPTABLE_BITS - 8);  
113   idx |= (fpr[1] & ~(~0 << 4)); 
114 #endif  
115
116   for (t = table[idx]; t; t = t->next)
117     if (!memcmp (t->fpr, fpr+1, 19))
118       break;
119   if (t)
120     {
121       *exists = 1;
122       return 0;
123     }
124   /* Insert that fingerprint. */
125   t = xtrymalloc (sizeof *t);
126   if (!t)
127     return gpg_error_from_errno (errno);
128   memcpy (t->fpr, fpr+1, 19);
129   t->next = table[idx];
130   table[idx] = t;
131   return 0;
132 }
133
134
135
136
137 /* Export all certificates or just those given in NAMES. */
138 void
139 gpgsm_export (CTRL ctrl, STRLIST names, FILE *fp)
140 {
141   KEYDB_HANDLE hd = NULL;
142   KEYDB_SEARCH_DESC *desc = NULL;
143   int ndesc;
144   Base64Context b64writer = NULL;
145   ksba_writer_t writer;
146   STRLIST sl;
147   ksba_cert_t cert = NULL;
148   int rc=0;
149   int count = 0;
150   int i;
151   duptable_t *dtable;
152
153   
154   dtable = create_duptable ();
155   if (!dtable)
156     {
157       log_error ("creating duplicates table failed: %s\n", strerror (errno));
158       goto leave;
159     }
160
161   hd = keydb_new (0);
162   if (!hd)
163     {
164       log_error ("keydb_new failed\n");
165       goto leave;
166     }
167
168   if (!names)
169     ndesc = 1;
170   else
171     {
172       for (sl=names, ndesc=0; sl; sl = sl->next, ndesc++) 
173         ;
174     }
175
176   desc = xtrycalloc (ndesc, sizeof *desc);
177   if (!ndesc)
178     {
179       log_error ("allocating memory for export failed: %s\n",
180                  gpg_strerror (OUT_OF_CORE (errno)));
181       goto leave;
182     }
183
184   if (!names)
185     desc[0].mode = KEYDB_SEARCH_MODE_FIRST;
186   else 
187     {
188       for (ndesc=0, sl=names; sl; sl = sl->next) 
189         {
190           rc = keydb_classify_name (sl->d, desc+ndesc);
191           if (rc)
192             {
193               log_error ("key `%s' not found: %s\n",
194                          sl->d, gpg_strerror (rc));
195               rc = 0;
196             }
197           else
198             ndesc++;
199         }
200     }
201
202   /* If all specifications are done by fingerprint, we switch to
203      ephemeral mode so that _all_ currently available and matching
204      certificates are exported. 
205
206      fixme: we should in this case keep a list of certificates to
207      avoid accidential export of duplicate certificates. */
208   if (names && ndesc)
209     {
210       for (i=0; (i < ndesc
211                  && (desc[i].mode == KEYDB_SEARCH_MODE_FPR
212                      || desc[i].mode == KEYDB_SEARCH_MODE_FPR20
213                      || desc[i].mode == KEYDB_SEARCH_MODE_FPR16)); i++)
214         ;
215       if (i == ndesc)
216         keydb_set_ephemeral (hd, 1);
217     }
218       
219   while (!(rc = keydb_search (hd, desc, ndesc)))
220     {
221       unsigned char fpr[20];
222       int exists;
223
224       if (!names) 
225         desc[0].mode = KEYDB_SEARCH_MODE_NEXT;
226
227       rc = keydb_get_cert (hd, &cert);
228       if (rc) 
229         {
230           log_error ("keydb_get_cert failed: %s\n", gpg_strerror (rc));
231           goto leave;
232         }
233
234       gpgsm_get_fingerprint (cert, 0, fpr, NULL);
235       rc = insert_duptable (dtable, fpr, &exists);
236       if (rc)
237         {
238           log_error ("inserting into duplicates table fauiled: %s\n",
239                      gpg_strerror (rc));
240           goto leave;
241         }
242
243       if (!exists && count && !ctrl->create_pem)
244         {
245           log_info ("exporting more than one certificate "
246                     "is not possible in binary mode\n");
247           log_info ("ignoring other certificates\n");
248           break;
249         }
250
251       if (!exists)
252         {
253           const unsigned char *image;
254           size_t imagelen;
255
256           image = ksba_cert_get_image (cert, &imagelen);
257           if (!image)
258             {
259               log_error ("ksba_cert_get_image failed\n");
260               goto leave;
261             }
262
263
264           if (ctrl->create_pem)
265             {
266               if (count)
267                 putc ('\n', fp);
268               print_short_info (cert, fp);
269               putc ('\n', fp);
270             }
271           count++;
272
273           if (!b64writer)
274             {
275               ctrl->pem_name = "CERTIFICATE";
276               rc = gpgsm_create_writer (&b64writer, ctrl, fp, &writer);
277               if (rc)
278                 {
279                   log_error ("can't create writer: %s\n", gpg_strerror (rc));
280                   goto leave;
281                 }
282             }
283
284           rc = ksba_writer_write (writer, image, imagelen);
285           if (rc)
286             {
287               log_error ("write error: %s\n", gpg_strerror (rc));
288               goto leave;
289             }
290
291           if (ctrl->create_pem)
292             {
293               /* We want one certificate per PEM block */
294               rc = gpgsm_finish_writer (b64writer);
295               if (rc) 
296                 {
297                   log_error ("write failed: %s\n", gpg_strerror (rc));
298                   goto leave;
299                 }
300               gpgsm_destroy_writer (b64writer);
301               b64writer = NULL;
302             }
303         }
304
305       ksba_cert_release (cert); 
306       cert = NULL;
307     }
308   if (rc && rc != -1)
309     log_error ("keydb_search failed: %s\n", gpg_strerror (rc));
310   else if (b64writer)
311     {
312       rc = gpgsm_finish_writer (b64writer);
313       if (rc) 
314         {
315           log_error ("write failed: %s\n", gpg_strerror (rc));
316           goto leave;
317         }
318     }
319   
320  leave:
321   gpgsm_destroy_writer (b64writer);
322   ksba_cert_release (cert);
323   xfree (desc);
324   keydb_release (hd);
325   destroy_duptable (dtable);
326 }
327
328
329 /* Export a certificates and its private key. */
330 void
331 gpgsm_p12_export (ctrl_t ctrl, const char *name, FILE *fp)
332 {
333   KEYDB_HANDLE hd;
334   KEYDB_SEARCH_DESC *desc = NULL;
335   Base64Context b64writer = NULL;
336   ksba_writer_t writer;
337   ksba_cert_t cert = NULL;
338   int rc=0;
339   const unsigned char *image;
340   size_t imagelen;
341   char *keygrip = NULL;
342   char *prompt;
343   char buffer[1024];
344   int  nread;
345   FILE *datafp = NULL;
346
347
348   hd = keydb_new (0);
349   if (!hd)
350     {
351       log_error ("keydb_new failed\n");
352       goto leave;
353     }
354
355   desc = xtrycalloc (1, sizeof *desc);
356   if (!desc)
357     {
358       log_error ("allocating memory for export failed: %s\n",
359                  gpg_strerror (OUT_OF_CORE (errno)));
360       goto leave;
361     }
362
363   rc = keydb_classify_name (name, desc);
364   if (rc)
365     {
366       log_error ("key `%s' not found: %s\n",
367                  name, gpg_strerror (rc));
368       goto leave;
369     }
370
371   /* Lookup the certificate an make sure that it is unique. */
372   rc = keydb_search (hd, desc, 1);
373   if (!rc)
374     {
375       rc = keydb_get_cert (hd, &cert);
376       if (rc) 
377         {
378           log_error ("keydb_get_cert failed: %s\n", gpg_strerror (rc));
379           goto leave;
380         }
381       
382       rc = keydb_search (hd, desc, 1);
383       if (!rc)
384         rc = gpg_error (GPG_ERR_AMBIGUOUS_NAME);
385       else if (rc == -1 || gpg_err_code (rc) == GPG_ERR_EOF)
386         rc = 0;
387       if (rc)
388         {
389           log_error ("key `%s' not found: %s\n",
390                      name, gpg_strerror (rc));
391           goto leave;
392         }
393     }
394       
395   keygrip = gpgsm_get_keygrip_hexstring (cert);
396   if (!keygrip || gpgsm_agent_havekey (ctrl, keygrip))
397     {
398       /* Note, that the !keygrip case indicates a bad certificate. */
399       rc = gpg_error (GPG_ERR_NO_SECKEY);
400       log_error ("can't export key `%s': %s\n", name, gpg_strerror (rc));
401       goto leave;
402     }
403   
404   image = ksba_cert_get_image (cert, &imagelen);
405   if (!image)
406     {
407       log_error ("ksba_cert_get_image failed\n");
408       goto leave;
409     }
410
411   if (ctrl->create_pem)
412     {
413       print_short_info (cert, fp);
414       putc ('\n', fp);
415     }
416
417   ctrl->pem_name = "PKCS12";
418   rc = gpgsm_create_writer (&b64writer, ctrl, fp, &writer);
419   if (rc)
420     {
421       log_error ("can't create writer: %s\n", gpg_strerror (rc));
422       goto leave;
423     }
424
425
426   prompt = gpgsm_format_keydesc (cert);
427   rc = export_p12 (ctrl, image, imagelen, prompt, keygrip, &datafp);
428   xfree (prompt);
429   if (rc)
430     goto leave;
431   rewind (datafp);
432   while ( (nread = fread (buffer, 1, sizeof buffer, datafp)) > 0 )
433     if ((rc = ksba_writer_write (writer, buffer, nread)))
434       {
435         log_error ("write failed: %s\n", gpg_strerror (rc));
436         goto leave;
437       }
438   if (ferror (datafp))
439     {
440       rc = gpg_error_from_errno (rc);
441       log_error ("error reading temporary file: %s\n", gpg_strerror (rc));
442       goto leave;
443     }
444
445   if (ctrl->create_pem)
446     {
447       /* We want one certificate per PEM block */
448       rc = gpgsm_finish_writer (b64writer);
449       if (rc) 
450         {
451           log_error ("write failed: %s\n", gpg_strerror (rc));
452           goto leave;
453         }
454       gpgsm_destroy_writer (b64writer);
455       b64writer = NULL;
456     }
457   
458   ksba_cert_release (cert); 
459   cert = NULL;
460
461  leave:
462   if (datafp)
463     fclose (datafp);
464   gpgsm_destroy_writer (b64writer);
465   ksba_cert_release (cert);
466   xfree (desc);
467   keydb_release (hd);
468 }
469
470
471 /* Print some info about the certifciate CERT to FP */
472 static void
473 print_short_info (ksba_cert_t cert, FILE *fp)
474 {
475   char *p;
476   ksba_sexp_t sexp;
477   int idx;
478
479   for (idx=0; (p = ksba_cert_get_issuer (cert, idx)); idx++)
480     {
481       fputs (!idx?   "Issuer ...: "
482                  : "\n   aka ...: ", fp); 
483       gpgsm_print_name (fp, p);
484       xfree (p);
485     }
486   putc ('\n', fp);
487
488   fputs ("Serial ...: ", fp); 
489   sexp = ksba_cert_get_serial (cert);
490   if (sexp)
491     {
492       int len;
493       const unsigned char *s = sexp;
494       
495       if (*s == '(')
496         {
497           s++;
498           for (len=0; *s && *s != ':' && digitp (s); s++)
499             len = len*10 + atoi_1 (s);
500           if (*s == ':')
501             for (s++; len; len--, s++)
502               fprintf (fp, "%02X", *s);
503         }
504       xfree (sexp);
505     }
506   putc ('\n', fp);
507
508   for (idx=0; (p = ksba_cert_get_subject (cert, idx)); idx++)
509     {
510       fputs (!idx?   "Subject ..: "
511                  : "\n    aka ..: ", fp); 
512       gpgsm_print_name (fp, p);
513       xfree (p);
514     }
515   putc ('\n', fp);
516 }
517
518
519 static gpg_error_t
520 popen_protect_tool (const char *pgmname,
521                     FILE *infile, FILE *outfile, FILE **statusfile, 
522                     const char *prompt, const char *keygrip,
523                     pid_t *pid)
524 {
525   gpg_error_t err;
526   int fd, fdout, rp[2];
527   int n, i;
528
529   fflush (infile);
530   rewind (infile);
531   fd = fileno (infile);
532   fdout = fileno (outfile);
533   if (fd == -1 || fdout == -1)
534     log_fatal ("no file descriptor for temporary file: %s\n",
535                strerror (errno));
536
537   /* Now start the protect-tool. */
538   if (pipe (rp) == -1)
539     {
540       err = gpg_error_from_errno (errno);
541       log_error (_("error creating a pipe: %s\n"), strerror (errno));
542       return err;
543     }
544       
545   *pid = fork ();
546   if (*pid == -1)
547     {
548       err = gpg_error_from_errno (errno);
549       log_error (_("error forking process: %s\n"), strerror (errno));
550       close (rp[0]);
551       close (rp[1]);
552       return err;
553     }
554
555   if (!*pid)
556     { /* Child. */
557       const char *arg0;
558
559       arg0 = strrchr (pgmname, '/');
560       if (arg0)
561         arg0++;
562       else
563         arg0 = pgmname;
564
565       /* Connect the infile to stdin. */
566       if (fd != 0 && dup2 (fd, 0) == -1)
567         log_fatal ("dup2 stdin failed: %s\n", strerror (errno));
568
569       /* Connect the outfile to stdout. */
570       if (fdout != 1 && dup2 (fdout, 1) == -1)
571         log_fatal ("dup2 stdout failed: %s\n", strerror (errno));
572       
573       /* Connect stderr to our pipe. */
574       if (rp[1] != 2 && dup2 (rp[1], 2) == -1)
575         log_fatal ("dup2 stderr failed: %s\n", strerror (errno));
576
577       /* Close all other files. */
578       n = sysconf (_SC_OPEN_MAX);
579       if (n < 0)
580         n = MAX_OPEN_FDS;
581       for (i=3; i < n; i++)
582         close(i);
583       errno = 0;
584
585       setup_pinentry_env ();
586
587       execlp (pgmname, arg0,
588               "--homedir", opt.homedir,
589               "--p12-export",
590               "--prompt", prompt?prompt:"", 
591               "--enable-status-msg",
592               "--",
593               keygrip,
594               NULL);
595       /* No way to print anything, as we have closed all streams. */
596       _exit (31);
597     }
598
599   /* Parent. */
600   close (rp[1]);
601   *statusfile = fdopen (rp[0], "r");
602   if (!*statusfile)
603     {
604       err = gpg_error_from_errno (errno);
605       log_error ("can't fdopen pipe for reading: %s", strerror (errno));
606       kill (*pid, SIGTERM);
607       return err;
608     }
609
610   return 0;
611 }
612
613
614 static gpg_error_t
615 export_p12 (ctrl_t ctrl, const unsigned char *certimg, size_t certimglen,
616             const char *prompt, const char *keygrip,
617             FILE **retfp)
618 {
619   const char *pgmname;
620   gpg_error_t err = 0, child_err = 0;
621   int i, c, cont_line;
622   unsigned int pos;
623   FILE *infp = NULL, *outfp = NULL, *fp = NULL;
624   char buffer[1024];
625   pid_t pid = -1;
626   int bad_pass = 0;
627
628   if (!opt.protect_tool_program || !*opt.protect_tool_program)
629     pgmname = GNUPG_DEFAULT_PROTECT_TOOL;
630   else
631     pgmname = opt.protect_tool_program;
632
633   infp = tmpfile ();
634   if (!infp)
635     {
636       err = gpg_error_from_errno (errno);
637       log_error (_("error creating temporary file: %s\n"), strerror (errno));
638       goto cleanup;
639     }
640
641   if (fwrite (certimg, certimglen, 1, infp) != 1)
642     {
643       err = gpg_error_from_errno (errno);
644       log_error (_("error writing to temporary file: %s\n"),
645                  strerror (errno));
646       goto cleanup;
647     }
648
649   outfp = tmpfile ();
650   if (!outfp)
651     {
652       err = gpg_error_from_errno (errno);
653       log_error (_("error creating temporary file: %s\n"), strerror (errno));
654       goto cleanup;
655     }
656
657   err = popen_protect_tool (pgmname, infp, outfp, &fp, prompt, keygrip, &pid);
658   if (err)
659     {
660       pid = -1;
661       goto cleanup;
662     }
663   fclose (infp);
664   infp = NULL;
665
666   /* Read stderr of the protect tool. */
667   pos = 0;
668   cont_line = 0;
669   while ((c=getc (fp)) != EOF)
670     {
671       /* fixme: We could here grep for status information of the
672          protect tool to figure out better error codes for
673          CHILD_ERR. */
674       buffer[pos++] = c;
675       if (pos >= sizeof buffer - 5 || c == '\n')
676         {
677           buffer[pos - (c == '\n')] = 0;
678           if (cont_line)
679             log_printf ("%s", buffer);
680           else
681             {
682               if (!strncmp (buffer, "gpg-protect-tool: [PROTECT-TOOL:] ",34))
683                 {
684                   char *p, *pend;
685
686                   p = buffer + 34;
687                   pend = strchr (p, ' ');
688                   if (pend)
689                     *pend = 0;
690                   if ( !strcmp (p, "bad-passphrase"))
691                     bad_pass++;
692                 }
693               else 
694                 log_info ("%s", buffer);
695             }
696           pos = 0;
697           cont_line = (c != '\n');
698         }
699     }
700
701   if (pos)
702     {
703       buffer[pos] = 0;
704       if (cont_line)
705         log_printf ("%s\n", buffer);
706       else
707         log_info ("%s\n", buffer);
708     }
709   else if (cont_line)
710     log_printf ("\n");
711
712   /* If we found no error in the output of the child, setup a suitable
713      error code, which will later be reset if the exit status of the
714      child is 0. */
715   if (!child_err)
716     child_err = gpg_error (GPG_ERR_DECRYPT_FAILED);
717
718  cleanup:
719   if (infp)
720     fclose (infp);
721   if (fp)
722     fclose (fp);
723   if (pid != -1)
724     {
725       int status;
726
727       while ( (i=waitpid (pid, &status, 0)) == -1 && errno == EINTR)
728         ;
729       if (i == -1)
730         log_error (_("waiting for protect-tools to terminate failed: %s\n"),
731                    strerror (errno));
732       else if (WIFEXITED (status) && WEXITSTATUS (status) == 31)
733         log_error (_("error running `%s': probably not installed\n"), pgmname);
734       else if (WIFEXITED (status) && WEXITSTATUS (status))
735         log_error (_("error running `%s': exit status %d\n"), pgmname,
736                      WEXITSTATUS (status));
737       else if (!WIFEXITED (status))
738         log_error (_("error running `%s': terminated\n"), pgmname);
739       else 
740         child_err = 0;
741     }
742   if (!err)
743     err = child_err;
744   if (err)
745     {
746       if (outfp)
747         fclose (outfp);
748     }
749   else
750     *retfp = outfp;
751   if (bad_pass)
752     {
753       /* During export this is the passphrase used to unprotect the
754          key and not the pkcs#12 thing as in export.  Therefore we can
755          issue the regular passphrase status.  FIXME: replace the all
756          zero keyid by a regular one. */
757       gpgsm_status (ctrl, STATUS_BAD_PASSPHRASE, "0000000000000000");
758     }
759   return err;
760 }
761