Add MAC t P12 files.
[gnupg.git] / agent / minip12.c
1 /* minip12.c - A minimal pkcs-12 implementation.
2  * Copyright (C) 2002, 2003, 2004, 2006 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 #ifdef HAVE_CONFIG_H
22 #include <config.h>
23 #endif
24 #include <stdio.h>
25 #include <stdlib.h>
26 #include <string.h>
27 #include <assert.h>
28 #include <gcrypt.h>
29
30 #ifdef TEST
31 #include <sys/stat.h>
32 #include <unistd.h>
33 #include <errno.h>
34 #endif
35
36 #include "../jnlib/logging.h"
37 #include "minip12.h"
38
39 #ifndef DIM
40 #define DIM(v)               (sizeof(v)/sizeof((v)[0]))
41 #endif
42
43 enum
44 {
45   UNIVERSAL = 0,
46   APPLICATION = 1,
47   CONTEXT = 2,
48   PRIVATE = 3
49 };
50
51
52 enum
53 {
54   TAG_NONE = 0,
55   TAG_BOOLEAN = 1,
56   TAG_INTEGER = 2,
57   TAG_BIT_STRING = 3,
58   TAG_OCTET_STRING = 4,
59   TAG_NULL = 5,
60   TAG_OBJECT_ID = 6,
61   TAG_OBJECT_DESCRIPTOR = 7,
62   TAG_EXTERNAL = 8,
63   TAG_REAL = 9,
64   TAG_ENUMERATED = 10,
65   TAG_EMBEDDED_PDV = 11,
66   TAG_UTF8_STRING = 12,
67   TAG_REALTIVE_OID = 13,
68   TAG_SEQUENCE = 16,
69   TAG_SET = 17,
70   TAG_NUMERIC_STRING = 18,
71   TAG_PRINTABLE_STRING = 19,
72   TAG_TELETEX_STRING = 20,
73   TAG_VIDEOTEX_STRING = 21,
74   TAG_IA5_STRING = 22,
75   TAG_UTC_TIME = 23,
76   TAG_GENERALIZED_TIME = 24,
77   TAG_GRAPHIC_STRING = 25,
78   TAG_VISIBLE_STRING = 26,
79   TAG_GENERAL_STRING = 27,
80   TAG_UNIVERSAL_STRING = 28,
81   TAG_CHARACTER_STRING = 29,
82   TAG_BMP_STRING = 30
83 };
84
85
86 static unsigned char const oid_data[9] = {
87   0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x07, 0x01 };
88 static unsigned char const oid_encryptedData[9] = {
89   0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x07, 0x06 };
90 static unsigned char const oid_pkcs_12_pkcs_8ShroudedKeyBag[11] = {
91   0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x0C, 0x0A, 0x01, 0x02 };
92 static unsigned char const oid_pkcs_12_CertBag[11] = {
93   0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x0C, 0x0A, 0x01, 0x03 };
94 static unsigned char const oid_pkcs_12_CrlBag[11] = {
95   0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x0C, 0x0A, 0x01, 0x04 };
96
97 static unsigned char const oid_pbeWithSHAAnd3_KeyTripleDES_CBC[10] = {
98   0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x0C, 0x01, 0x03 };
99 static unsigned char const oid_pbeWithSHAAnd40BitRC2_CBC[10] = {
100   0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x0C, 0x01, 0x06 };
101 static unsigned char const oid_x509Certificate_for_pkcs_12[10] = {
102   0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x09, 0x16, 0x01 };
103
104
105 static unsigned char const oid_rsaEncryption[9] = {
106   0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x01, 0x01 };
107
108
109 static unsigned char const data_3desiter2048[30] = {
110   0x30, 0x1C, 0x06, 0x0A, 0x2A, 0x86, 0x48, 0x86,
111   0xF7, 0x0D, 0x01, 0x0C, 0x01, 0x03, 0x30, 0x0E, 
112   0x04, 0x08, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
113   0xFF, 0xFF, 0x02, 0x02, 0x08, 0x00 };
114 #define DATA_3DESITER2048_SALT_OFF  18
115
116 static unsigned char const data_rc2iter2048[30] = {
117   0x30, 0x1C, 0x06, 0x0A, 0x2A, 0x86, 0x48, 0x86,
118   0xF7, 0x0D, 0x01, 0x0C, 0x01, 0x06, 0x30, 0x0E, 
119   0x04, 0x08, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
120   0xFF, 0xFF, 0x02, 0x02, 0x08, 0x00 };
121 #define DATA_RC2ITER2048_SALT_OFF  18
122
123 static unsigned char const data_mactemplate[51] = {
124   0x30, 0x31, 0x30, 0x21, 0x30, 0x09, 0x06, 0x05,
125   0x2b, 0x0e, 0x03, 0x02, 0x1a, 0x05, 0x00, 0x04,
126   0x14, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
127   0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
128   0xff, 0xff, 0xff, 0xff, 0xff, 0x04, 0x08, 0xff,
129   0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x02,
130   0x02, 0x08, 0x00 }; 
131 #define DATA_MACTEMPLATE_MAC_OFF 17
132 #define DATA_MACTEMPLATE_SALT_OFF 39
133
134 struct buffer_s 
135 {
136   unsigned char *buffer;
137   size_t length;
138 };  
139
140
141 struct tag_info 
142 {
143   int class;
144   int is_constructed;
145   unsigned long tag;
146   unsigned long length;  /* length part of the TLV */
147   int nhdr;
148   int ndef;              /* It is an indefinite length */
149 };
150
151
152 /* Parse the buffer at the address BUFFER which is of SIZE and return
153    the tag and the length part from the TLV triplet.  Update BUFFER
154    and SIZE on success.  Checks that the encoded length does not
155    exhaust the length of the provided buffer. */
156 static int 
157 parse_tag (unsigned char const **buffer, size_t *size, struct tag_info *ti)
158 {
159   int c;
160   unsigned long tag;
161   const unsigned char *buf = *buffer;
162   size_t length = *size;
163
164   ti->length = 0;
165   ti->ndef = 0;
166   ti->nhdr = 0;
167
168   /* Get the tag */
169   if (!length)
170     return -1; /* premature eof */
171   c = *buf++; length--;
172   ti->nhdr++;
173
174   ti->class = (c & 0xc0) >> 6;
175   ti->is_constructed = !!(c & 0x20);
176   tag = c & 0x1f;
177
178   if (tag == 0x1f)
179     {
180       tag = 0;
181       do
182         {
183           tag <<= 7;
184           if (!length)
185             return -1; /* premature eof */
186           c = *buf++; length--;
187           ti->nhdr++;
188           tag |= c & 0x7f;
189         }
190       while (c & 0x80);
191     }
192   ti->tag = tag;
193
194   /* Get the length */
195   if (!length)
196     return -1; /* prematureeof */
197   c = *buf++; length--;
198   ti->nhdr++;
199
200   if ( !(c & 0x80) )
201     ti->length = c;
202   else if (c == 0x80)
203     ti->ndef = 1;
204   else if (c == 0xff)
205     return -1; /* forbidden length value */
206   else
207     {
208       unsigned long len = 0;
209       int count = c & 0x7f;
210
211       for (; count; count--)
212         {
213           len <<= 8;
214           if (!length)
215             return -1; /* premature_eof */
216           c = *buf++; length--;
217           ti->nhdr++;
218           len |= c & 0xff;
219         }
220       ti->length = len;
221     }
222   
223   if (ti->class == UNIVERSAL && !ti->tag)
224     ti->length = 0;
225
226   if (ti->length > length)
227     return -1; /* data larger than buffer. */
228   
229   *buffer = buf;
230   *size = length;
231   return 0;
232 }
233
234
235 /* Given an ASN.1 chunk of a structure like:
236
237      24 NDEF:       OCTET STRING  -- This is not passed to us
238      04    1:         OCTET STRING  -- INPUT point s to here
239             :           30
240      04    1:         OCTET STRING
241             :           80
242           [...]
243      04    2:         OCTET STRING
244             :           00 00
245             :         } -- This denotes a Null tag and are the last 
246                         -- two bytes in INPUT.
247    
248    Create a new buffer with the content of that octet string.  INPUT
249    is the orginal buffer with a length as stored at LENGTH.  Returns
250    NULL on error or a new malloced buffer with the length of this new
251    buffer stored at LENGTH and the number of bytes parsed from input
252    are added to the value stored at INPUT_CONSUMED.  INPUT_CONSUMED is
253    allowed to be passed as NULL if the caller is not interested in
254    this value. */
255 static unsigned char *
256 cram_octet_string (const unsigned char *input, size_t *length,
257                    size_t *input_consumed)
258 {
259   const unsigned char *s = input;
260   size_t n = *length;
261   unsigned char *output, *d;
262   struct tag_info ti;
263
264   /* Allocate output buf.  We know that it won't be longer than the
265      input buffer. */
266   d = output = gcry_malloc (n);
267   if (!output)
268     goto bailout;
269
270   for (;;)
271     {
272       if (parse_tag (&s, &n, &ti))
273         goto bailout;
274       if (ti.class == UNIVERSAL && ti.tag == TAG_OCTET_STRING 
275           && !ti.ndef && !ti.is_constructed)
276         {
277           memcpy (d, s, ti.length);
278           s += ti.length;
279           d += ti.length;
280           n -= ti.length;
281         }
282       else if (ti.class == UNIVERSAL && !ti.tag && !ti.is_constructed)
283         break; /* Ready */ 
284       else
285         goto bailout;
286     }
287
288
289   *length = d - output;
290   if (input_consumed)
291     *input_consumed += s - input;
292   return output;
293
294  bailout:
295   if (input_consumed)
296     *input_consumed += s - input;
297   gcry_free (output);
298   return NULL;
299 }
300
301
302
303 static int 
304 string_to_key (int id, char *salt, size_t saltlen, int iter, const char *pw,
305                int req_keylen, unsigned char *keybuf)
306 {
307   int rc, i, j;
308   gcry_md_hd_t md;
309   gcry_mpi_t num_b1 = NULL;
310   int pwlen;
311   unsigned char hash[20], buf_b[64], buf_i[128], *p;
312   size_t cur_keylen;
313   size_t n;
314
315   cur_keylen = 0;
316   pwlen = strlen (pw);
317   if (pwlen > 63/2)
318     {
319       log_error ("password too long\n");
320       return -1;
321     }
322
323   if (saltlen < 8)
324     {
325       log_error ("salt too short\n");
326       return -1;
327     }
328   
329   /* Store salt and password in BUF_I */
330   p = buf_i;
331   for(i=0; i < 64; i++)
332     *p++ = salt [i%saltlen];
333   for(i=j=0; i < 64; i += 2)
334     {
335       *p++ = 0;
336       *p++ = pw[j];
337       if (++j > pwlen) /* Note, that we include the trailing zero */
338         j = 0;
339     }
340
341   for (;;)
342     {
343       rc = gcry_md_open (&md, GCRY_MD_SHA1, 0);
344       if (rc)
345         {
346           log_error ( "gcry_md_open failed: %s\n", gpg_strerror (rc));
347           return rc;
348         }
349       for(i=0; i < 64; i++)
350         gcry_md_putc (md, id);
351       gcry_md_write (md, buf_i, 128);
352       memcpy (hash, gcry_md_read (md, 0), 20);
353       gcry_md_close (md);
354       for (i=1; i < iter; i++)
355         gcry_md_hash_buffer (GCRY_MD_SHA1, hash, hash, 20);
356
357       for (i=0; i < 20 && cur_keylen < req_keylen; i++)
358         keybuf[cur_keylen++] = hash[i];
359       if (cur_keylen == req_keylen)
360         {
361           gcry_mpi_release (num_b1);
362           return 0; /* ready */
363         }
364       
365       /* need more bytes. */
366       for(i=0; i < 64; i++)
367         buf_b[i] = hash[i % 20];
368       rc = gcry_mpi_scan (&num_b1, GCRYMPI_FMT_USG, buf_b, 64, &n);
369       if (rc)
370         {
371           log_error ( "gcry_mpi_scan failed: %s\n", gpg_strerror (rc));
372           return -1;
373         }
374       gcry_mpi_add_ui (num_b1, num_b1, 1);
375       for (i=0; i < 128; i += 64)
376         {
377           gcry_mpi_t num_ij;
378
379           rc = gcry_mpi_scan (&num_ij, GCRYMPI_FMT_USG, buf_i + i, 64, &n);
380           if (rc)
381             {
382               log_error ( "gcry_mpi_scan failed: %s\n",
383                        gpg_strerror (rc));
384               return -1;
385             }
386           gcry_mpi_add (num_ij, num_ij, num_b1);
387           gcry_mpi_clear_highbit (num_ij, 64*8);
388           rc = gcry_mpi_print (GCRYMPI_FMT_USG, buf_i + i, 64, &n, num_ij);
389           if (rc)
390             {
391               log_error ( "gcry_mpi_print failed: %s\n",
392                           gpg_strerror (rc));
393               return -1;
394             }
395           gcry_mpi_release (num_ij);
396         }
397     }
398 }
399
400
401 static int 
402 set_key_iv (gcry_cipher_hd_t chd, char *salt, size_t saltlen, int iter,
403             const char *pw, int keybytes)
404 {
405   unsigned char keybuf[24];
406   int rc;
407
408   assert (keybytes == 5 || keybytes == 24);
409   if (string_to_key (1, salt, saltlen, iter, pw, keybytes, keybuf))
410     return -1;
411   rc = gcry_cipher_setkey (chd, keybuf, keybytes);
412   if (rc)
413     {
414       log_error ( "gcry_cipher_setkey failed: %s\n", gpg_strerror (rc));
415       return -1;
416     }
417
418   if (string_to_key (2, salt, saltlen, iter, pw, 8, keybuf))
419     return -1;
420   rc = gcry_cipher_setiv (chd, keybuf, 8);
421   if (rc)
422     {
423       log_error ("gcry_cipher_setiv failed: %s\n", gpg_strerror (rc));
424       return -1;
425     }
426   return 0;
427 }
428
429
430 static void
431 crypt_block (unsigned char *buffer, size_t length, char *salt, size_t saltlen,
432              int iter, const char *pw, int cipher_algo, int encrypt)
433 {
434   gcry_cipher_hd_t chd;
435   int rc;
436
437   rc = gcry_cipher_open (&chd, cipher_algo, GCRY_CIPHER_MODE_CBC, 0); 
438   if (rc)
439     {
440       log_error ( "gcry_cipher_open failed: %s\n", gpg_strerror(rc));
441       wipememory (buffer, length);
442       return;
443     }
444   if (set_key_iv (chd, salt, saltlen, iter, pw,
445                   cipher_algo == GCRY_CIPHER_RFC2268_40? 5:24))
446     {
447       wipememory (buffer, length);
448       goto leave;
449     }
450
451   rc = encrypt? gcry_cipher_encrypt (chd, buffer, length, NULL, 0)
452               : gcry_cipher_decrypt (chd, buffer, length, NULL, 0);
453
454   if (rc)
455     {
456       wipememory (buffer, length);
457       log_error ( "en/de-crytion failed: %s\n", gpg_strerror (rc));
458       goto leave;
459     }
460
461  leave:
462   gcry_cipher_close (chd);
463 }
464   
465
466
467 static int
468 parse_bag_encrypted_data (const unsigned char *buffer, size_t length,
469                           int startoffset, size_t *r_consumed, const char *pw,
470                           void (*certcb)(void*, const unsigned char*, size_t),
471                           void *certcbarg)
472 {
473   struct tag_info ti;
474   const unsigned char *p = buffer;
475   const unsigned char *p_start = buffer;
476   size_t n = length;
477   const char *where;
478   char salt[16];
479   size_t saltlen;
480   unsigned int iter;
481   unsigned char *plain = NULL;
482   int bad_pass = 0;
483   unsigned char *cram_buffer = NULL;
484   size_t consumed = 0; /* Number of bytes consumed from the orginal buffer. */
485   
486   where = "start";
487   if (parse_tag (&p, &n, &ti))
488     goto bailout;
489   if (ti.class != CONTEXT || ti.tag)
490     goto bailout;
491   if (parse_tag (&p, &n, &ti))
492     goto bailout;
493   if (ti.tag != TAG_SEQUENCE)
494     goto bailout;
495
496   where = "bag.encryptedData.version";
497   if (parse_tag (&p, &n, &ti))
498     goto bailout;
499   if (ti.tag != TAG_INTEGER || ti.length != 1 || *p != 0)
500     goto bailout;
501   p++; n--;
502   if (parse_tag (&p, &n, &ti))
503     goto bailout;
504   if (ti.tag != TAG_SEQUENCE)
505     goto bailout;
506
507   where = "bag.encryptedData.data";
508   if (parse_tag (&p, &n, &ti))
509     goto bailout;
510   if (ti.tag != TAG_OBJECT_ID || ti.length != DIM(oid_data)
511       || memcmp (p, oid_data, DIM(oid_data)))
512     goto bailout;
513   p += DIM(oid_data);
514   n -= DIM(oid_data);
515
516   where = "bag.encryptedData.keyinfo";
517   if (parse_tag (&p, &n, &ti))
518     goto bailout;
519   if (ti.class || ti.tag != TAG_SEQUENCE)
520     goto bailout;
521   if (parse_tag (&p, &n, &ti))
522     goto bailout;
523   if (!ti.class && ti.tag == TAG_OBJECT_ID 
524       && ti.length == DIM(oid_pbeWithSHAAnd40BitRC2_CBC)
525       && !memcmp (p, oid_pbeWithSHAAnd40BitRC2_CBC,
526                   DIM(oid_pbeWithSHAAnd40BitRC2_CBC)))
527     {
528       p += DIM(oid_pbeWithSHAAnd40BitRC2_CBC);
529       n -= DIM(oid_pbeWithSHAAnd40BitRC2_CBC);
530     }
531   else
532     goto bailout;
533
534   where = "rc2-params";
535   if (parse_tag (&p, &n, &ti))
536     goto bailout;
537   if (ti.class || ti.tag != TAG_SEQUENCE)
538     goto bailout;
539   if (parse_tag (&p, &n, &ti))
540     goto bailout;
541   if (ti.class || ti.tag != TAG_OCTET_STRING
542       || ti.length < 8 || ti.length > 16 )
543     goto bailout;
544   saltlen = ti.length;
545   memcpy (salt, p, saltlen);
546   p += saltlen;
547   n -= saltlen;
548   if (parse_tag (&p, &n, &ti))
549     goto bailout;
550   if (ti.class || ti.tag != TAG_INTEGER || !ti.length )
551     goto bailout;
552   for (iter=0; ti.length; ti.length--)
553     {
554       iter <<= 8;
555       iter |= (*p++) & 0xff; 
556       n--;
557     }
558   
559   where = "rc2-ciphertext";
560   if (parse_tag (&p, &n, &ti))
561     goto bailout;
562
563   consumed = p - p_start;
564   if (ti.class == CONTEXT && ti.tag == 0 && ti.is_constructed && ti.ndef)
565     {
566       /* Mozilla exported certs now come with single byte chunks of
567          octect strings.  (Mozilla Firefox 1.0.4).  Arghh. */
568       where = "cram-rc2-ciphertext";
569       cram_buffer = cram_octet_string ( p, &n, &consumed);
570       if (!cram_buffer)
571         goto bailout;
572       p = p_start = cram_buffer;
573       if (r_consumed)
574         *r_consumed = consumed;
575       r_consumed = NULL; /* Ugly hack to not update that value any further. */
576       ti.length = n;
577     }
578   else if (ti.class == CONTEXT && ti.tag == 0 && ti.length )
579     ;
580   else
581     goto bailout;
582   
583   log_info ("%lu bytes of RC2 encrypted text\n", ti.length);
584
585   plain = gcry_malloc_secure (ti.length);
586   if (!plain)
587     {
588       log_error ("error allocating decryption buffer\n");
589       goto bailout;
590     }
591   memcpy (plain, p, ti.length);
592   crypt_block (plain, ti.length, salt, saltlen,
593                iter, pw, GCRY_CIPHER_RFC2268_40, 0);
594   n = ti.length;
595   startoffset = 0;
596   p_start = p = plain;
597
598 /*   { */
599 /* #  warning debug code is enabled */
600 /*     FILE *fp = fopen ("tmp-rc2-plain.der", "wb"); */
601 /*     if (!fp || fwrite (p, n, 1, fp) != 1) */
602 /*       exit (2); */
603 /*     fclose (fp); */
604 /*   } */
605
606   where = "outer.outer.seq";
607   if (parse_tag (&p, &n, &ti))
608     {
609       bad_pass = 1;
610       goto bailout;
611     }
612   if (ti.class || ti.tag != TAG_SEQUENCE)
613     {
614       bad_pass = 1;
615       goto bailout;
616     }
617
618   if (parse_tag (&p, &n, &ti))
619     {
620       bad_pass = 1;
621       goto bailout;
622     }
623
624   /* Loop over all certificates inside the bag. */
625   while (n)
626     {
627       int isbag = 0;
628
629       where = "certbag.nextcert";
630       if (ti.class || ti.tag != TAG_SEQUENCE)
631         goto bailout;
632
633       where = "certbag.objectidentifier";
634       if (parse_tag (&p, &n, &ti))
635         goto bailout;
636       if (ti.class || ti.tag != TAG_OBJECT_ID)
637         goto bailout;
638       if ( ti.length == DIM(oid_pkcs_12_CertBag)
639            && !memcmp (p, oid_pkcs_12_CertBag, DIM(oid_pkcs_12_CertBag)))
640         {
641           p += DIM(oid_pkcs_12_CertBag);
642           n -= DIM(oid_pkcs_12_CertBag);
643         }
644       else if ( ti.length == DIM(oid_pkcs_12_CrlBag)
645            && !memcmp (p, oid_pkcs_12_CrlBag, DIM(oid_pkcs_12_CrlBag)))
646         {
647           p += DIM(oid_pkcs_12_CrlBag);
648           n -= DIM(oid_pkcs_12_CrlBag);
649           isbag = 1;
650         }
651       else
652         goto bailout;
653
654       where = "certbag.before.certheader";
655       if (parse_tag (&p, &n, &ti))
656         goto bailout;
657       if (ti.class != CONTEXT || ti.tag)
658         goto bailout;
659       if (isbag)
660         {
661           log_info ("skipping unsupported crlBag\n");
662           p += ti.length;
663           n -= ti.length;
664         }
665       else
666         {
667           if (parse_tag (&p, &n, &ti))
668             goto bailout;
669           if (ti.class || ti.tag != TAG_SEQUENCE)
670             goto bailout;
671           if (parse_tag (&p, &n, &ti))
672             goto bailout;
673           if (ti.class || ti.tag != TAG_OBJECT_ID
674               || ti.length != DIM(oid_x509Certificate_for_pkcs_12)
675               || memcmp (p, oid_x509Certificate_for_pkcs_12,
676                          DIM(oid_x509Certificate_for_pkcs_12)))
677             goto bailout;
678           p += DIM(oid_x509Certificate_for_pkcs_12);
679           n -= DIM(oid_x509Certificate_for_pkcs_12);
680           
681           where = "certbag.before.octetstring";
682           if (parse_tag (&p, &n, &ti))
683             goto bailout;
684           if (ti.class != CONTEXT || ti.tag)
685             goto bailout;
686           if (parse_tag (&p, &n, &ti))
687             goto bailout;
688           if (ti.class || ti.tag != TAG_OCTET_STRING || ti.ndef)
689             goto bailout;
690           
691           /* Return the certificate. */
692           if (certcb)
693             certcb (certcbarg, p, ti.length);
694    
695           p += ti.length;
696           n -= ti.length;
697         }
698
699       /* Ugly hack to cope with the padding: Forget about the rest if
700          that is less or equal to the cipher's block length.  We can
701          reasonable assume that all valid data will be longer than
702          just one block. */
703       if (n <= 8)
704         n = 0;  
705
706       /* Skip the optional SET with the pkcs12 cert attributes. */
707       if (n)
708         {
709           where = "bag.attributes";
710           if (parse_tag (&p, &n, &ti))
711             goto bailout;
712           if (!ti.class && ti.tag == TAG_SEQUENCE)
713             ; /* No attributes. */
714           else if (!ti.class && ti.tag == TAG_SET && !ti.ndef)
715             { /* The optional SET. */
716               p += ti.length;
717               n -= ti.length;
718               if (n <= 8)
719                 n = 0;
720               if (n && parse_tag (&p, &n, &ti))
721                 goto bailout;
722             }
723           else
724             goto bailout;
725         }
726     }
727   
728   if (r_consumed)
729     *r_consumed = consumed;
730   gcry_free (plain);
731   gcry_free (cram_buffer);
732   return 0;
733
734  bailout:
735   if (r_consumed)
736     *r_consumed = consumed;
737   gcry_free (plain);
738   gcry_free (cram_buffer);
739   log_error ("encryptedData error at \"%s\", offset %u\n",
740              where, (p - p_start)+startoffset);
741   if (bad_pass)
742     {
743       /* Note, that the following string might be used by other programs
744          to check for a bad passphrase; it should therefore not be
745          translated or changed. */
746       log_error ("possibly bad passphrase given\n");
747     }
748   return -1;
749 }
750
751 static gcry_mpi_t *
752 parse_bag_data (const unsigned char *buffer, size_t length, int startoffset,
753                 size_t *r_consumed, const char *pw)
754 {
755   int rc;
756   struct tag_info ti;
757   const unsigned char *p = buffer;
758   const unsigned char *p_start = buffer;
759   size_t n = length;
760   const char *where;
761   char salt[16];
762   size_t saltlen;
763   unsigned int iter;
764   int len;
765   unsigned char *plain = NULL;
766   gcry_mpi_t *result = NULL;
767   int result_count, i;
768   unsigned char *cram_buffer = NULL;
769   size_t consumed = 0; /* Number of bytes consumed from the orginal buffer. */
770
771   where = "start";
772   if (parse_tag (&p, &n, &ti))
773     goto bailout;
774   if (ti.class != CONTEXT || ti.tag)
775     goto bailout;
776   if (parse_tag (&p, &n, &ti))
777     goto bailout;
778   if (ti.class || ti.tag != TAG_OCTET_STRING)
779     goto bailout;
780
781   consumed = p - p_start;
782   if (ti.is_constructed && ti.ndef)
783     {
784       /* Mozilla exported certs now come with single byte chunks of
785          octect strings.  (Mozilla Firefox 1.0.4).  Arghh. */
786       where = "cram-data.outersegs";
787       cram_buffer = cram_octet_string ( p, &n, &consumed);
788       if (!cram_buffer)
789         goto bailout;
790       p = p_start = cram_buffer;
791       if (r_consumed)
792         *r_consumed = consumed;
793       r_consumed = NULL; /* Ugly hack to not update that value any further. */
794     }
795   
796
797   where = "data.outerseqs";
798   if (parse_tag (&p, &n, &ti))
799     goto bailout;
800   if (ti.class || ti.tag != TAG_SEQUENCE)
801     goto bailout;
802   if (parse_tag (&p, &n, &ti))
803     goto bailout;
804   if (ti.class || ti.tag != TAG_SEQUENCE)
805     goto bailout;
806
807   where = "data.objectidentifier";
808   if (parse_tag (&p, &n, &ti))
809     goto bailout;
810   if (ti.class || ti.tag != TAG_OBJECT_ID
811       || ti.length != DIM(oid_pkcs_12_pkcs_8ShroudedKeyBag)
812       || memcmp (p, oid_pkcs_12_pkcs_8ShroudedKeyBag,
813                  DIM(oid_pkcs_12_pkcs_8ShroudedKeyBag)))
814     goto bailout;
815   p += DIM(oid_pkcs_12_pkcs_8ShroudedKeyBag);
816   n -= DIM(oid_pkcs_12_pkcs_8ShroudedKeyBag);
817
818   where = "shrouded,outerseqs";
819   if (parse_tag (&p, &n, &ti))
820     goto bailout;
821   if (ti.class != CONTEXT || ti.tag)
822     goto bailout;
823   if (parse_tag (&p, &n, &ti))
824     goto bailout;
825   if (ti.class || ti.tag != TAG_SEQUENCE)
826     goto bailout;
827   if (parse_tag (&p, &n, &ti))
828     goto bailout;
829   if (ti.class || ti.tag != TAG_SEQUENCE)
830     goto bailout;
831   if (parse_tag (&p, &n, &ti))
832     goto bailout;
833   if (ti.class || ti.tag != TAG_OBJECT_ID
834       || ti.length != DIM(oid_pbeWithSHAAnd3_KeyTripleDES_CBC)
835       || memcmp (p, oid_pbeWithSHAAnd3_KeyTripleDES_CBC,
836                  DIM(oid_pbeWithSHAAnd3_KeyTripleDES_CBC)))
837     goto bailout;
838   p += DIM(oid_pbeWithSHAAnd3_KeyTripleDES_CBC);
839   n -= DIM(oid_pbeWithSHAAnd3_KeyTripleDES_CBC);
840
841   where = "3des-params";
842   if (parse_tag (&p, &n, &ti))
843     goto bailout;
844   if (ti.class || ti.tag != TAG_SEQUENCE)
845     goto bailout;
846   if (parse_tag (&p, &n, &ti))
847     goto bailout;
848   if (ti.class || ti.tag != TAG_OCTET_STRING
849       || ti.length < 8 || ti.length > 16)
850     goto bailout;
851   saltlen = ti.length;
852   memcpy (salt, p, saltlen);
853   p += saltlen;
854   n -= saltlen;
855   if (parse_tag (&p, &n, &ti))
856     goto bailout;
857   if (ti.class || ti.tag != TAG_INTEGER || !ti.length )
858     goto bailout;
859   for (iter=0; ti.length; ti.length--)
860     {
861       iter <<= 8;
862       iter |= (*p++) & 0xff; 
863       n--;
864     }
865   
866   where = "3des-ciphertext";
867   if (parse_tag (&p, &n, &ti))
868     goto bailout;
869   if (ti.class || ti.tag != TAG_OCTET_STRING || !ti.length )
870     goto bailout;
871   
872   log_info ("%lu bytes of 3DES encrypted text\n", ti.length);
873   
874   plain = gcry_malloc_secure (ti.length);
875   if (!plain)
876     {
877       log_error ("error allocating decryption buffer\n");
878       goto bailout;
879     }
880   memcpy (plain, p, ti.length);
881   consumed += p - p_start + ti.length;
882   crypt_block (plain, ti.length, salt, saltlen, iter, pw, GCRY_CIPHER_3DES, 0);
883   n = ti.length;
884   startoffset = 0;
885   p_start = p = plain;
886
887 /*   { */
888 /* #  warning debug code is enabled */
889 /*     FILE *fp = fopen ("tmp-rc2-plain-key.der", "wb"); */
890 /*     if (!fp || fwrite (p, n, 1, fp) != 1) */
891 /*       exit (2); */
892 /*     fclose (fp); */
893 /*   } */
894
895
896   where = "decrypted-text";
897   if (parse_tag (&p, &n, &ti) || ti.class || ti.tag != TAG_SEQUENCE)
898     goto bailout;
899   if (parse_tag (&p, &n, &ti) || ti.class || ti.tag != TAG_INTEGER
900       || ti.length != 1 || *p)
901     goto bailout;
902   p++; n--;
903   if (parse_tag (&p, &n, &ti) || ti.class || ti.tag != TAG_SEQUENCE)
904     goto bailout;
905   len = ti.length;
906   if (parse_tag (&p, &n, &ti))
907     goto bailout;
908   if (len < ti.nhdr)
909     goto bailout;
910   len -= ti.nhdr;
911   if (ti.class || ti.tag != TAG_OBJECT_ID
912       || ti.length != DIM(oid_rsaEncryption)
913       || memcmp (p, oid_rsaEncryption,
914                  DIM(oid_rsaEncryption)))
915     goto bailout;
916   p += DIM (oid_rsaEncryption);
917   n -= DIM (oid_rsaEncryption);
918   if (len < ti.length)
919     goto bailout;
920   len -= ti.length;
921   if (n < len)
922     goto bailout;
923   p += len;
924   n -= len;
925   if (parse_tag (&p, &n, &ti) || ti.class || ti.tag != TAG_OCTET_STRING)
926     goto bailout;
927   if (parse_tag (&p, &n, &ti) || ti.class || ti.tag != TAG_SEQUENCE)
928     goto bailout;
929   len = ti.length;
930
931   result = gcry_calloc (10, sizeof *result);
932   if (!result)
933     {
934       log_error ( "error allocating result array\n");
935       goto bailout;
936     }
937   result_count = 0;
938
939   where = "reading.key-parameters";
940   for (result_count=0; len && result_count < 9;)
941     {
942       if (parse_tag (&p, &n, &ti) || ti.class || ti.tag != TAG_INTEGER)
943         goto bailout;
944       if (len < ti.nhdr)
945         goto bailout;
946       len -= ti.nhdr;
947       if (len < ti.length)
948         goto bailout;
949       len -= ti.length;
950       if (!result_count && ti.length == 1 && !*p)
951         ; /* ignore the very first one if it is a 0 */
952       else 
953         {
954           rc = gcry_mpi_scan (result+result_count, GCRYMPI_FMT_USG, p,
955                               ti.length, NULL);
956           if (rc)
957             {
958               log_error ("error parsing key parameter: %s\n",
959                          gpg_strerror (rc));
960               goto bailout;
961             }
962           result_count++;
963         }
964       p += ti.length;
965       n -= ti.length;
966     }
967   if (len)
968     goto bailout;
969
970   gcry_free (cram_buffer);
971   if (r_consumed)
972     *r_consumed = consumed;
973   return result;
974
975  bailout:
976   gcry_free (plain);
977   if (result)
978     {
979       for (i=0; result[i]; i++)
980         gcry_mpi_release (result[i]);
981       gcry_free (result);
982     }
983   gcry_free (cram_buffer);
984   log_error ( "data error at \"%s\", offset %u\n",
985               where, (p - buffer) + startoffset);
986   if (r_consumed)
987     *r_consumed = consumed;
988   return NULL;
989 }
990
991
992 /* Parse a PKCS12 object and return an array of MPI representing the
993    secret key parameters.  This is a very limited implementation in
994    that it is only able to look for 3DES encoded encryptedData and
995    tries to extract the first private key object it finds.  In case of
996    an error NULL is returned. CERTCB and CERRTCBARG are used to pass
997    X.509 certificates back to the caller. */
998 gcry_mpi_t *
999 p12_parse (const unsigned char *buffer, size_t length, const char *pw,
1000            void (*certcb)(void*, const unsigned char*, size_t),
1001            void *certcbarg)
1002 {
1003   struct tag_info ti;
1004   const unsigned char *p = buffer;
1005   const unsigned char *p_start = buffer;
1006   size_t n = length;
1007   const char *where;
1008   int bagseqlength, len;
1009   int bagseqndef, lenndef;
1010   gcry_mpi_t *result = NULL;
1011   unsigned char *cram_buffer = NULL;
1012
1013   where = "pfx";
1014   if (parse_tag (&p, &n, &ti))
1015     goto bailout;
1016   if (ti.tag != TAG_SEQUENCE)
1017     goto bailout;
1018
1019   where = "pfxVersion";
1020   if (parse_tag (&p, &n, &ti))
1021     goto bailout;
1022   if (ti.tag != TAG_INTEGER || ti.length != 1 || *p != 3)
1023     goto bailout;
1024   p++; n--;
1025   
1026   where = "authSave";
1027   if (parse_tag (&p, &n, &ti))
1028     goto bailout;
1029   if (ti.tag != TAG_SEQUENCE)
1030     goto bailout;
1031   if (parse_tag (&p, &n, &ti))
1032     goto bailout;
1033   if (ti.tag != TAG_OBJECT_ID || ti.length != DIM(oid_data)
1034       || memcmp (p, oid_data, DIM(oid_data)))
1035     goto bailout;
1036   p += DIM(oid_data);
1037   n -= DIM(oid_data);
1038
1039   if (parse_tag (&p, &n, &ti))
1040     goto bailout;
1041   if (ti.class != CONTEXT || ti.tag)
1042     goto bailout;
1043   if (parse_tag (&p, &n, &ti))
1044     goto bailout;
1045   if (ti.class != UNIVERSAL || ti.tag != TAG_OCTET_STRING)
1046     goto bailout;
1047
1048   if (ti.is_constructed && ti.ndef)
1049     {
1050       /* Mozilla exported certs now come with single byte chunks of
1051          octect strings.  (Mozilla Firefox 1.0.4).  Arghh. */
1052       where = "cram-bags";
1053       cram_buffer = cram_octet_string ( p, &n, NULL);
1054       if (!cram_buffer)
1055         goto bailout;
1056       p = p_start = cram_buffer;
1057     }
1058
1059   where = "bags";
1060   if (parse_tag (&p, &n, &ti))
1061     goto bailout;
1062   if (ti.class != UNIVERSAL || ti.tag != TAG_SEQUENCE)
1063     goto bailout;
1064   bagseqndef = ti.ndef;
1065   bagseqlength = ti.length;
1066   while (bagseqlength || bagseqndef)
1067     {
1068       log_debug ( "at offset %u\n", (p - p_start));
1069       where = "bag-sequence";
1070       if (parse_tag (&p, &n, &ti))
1071         goto bailout;
1072       if (bagseqndef && ti.class == UNIVERSAL && !ti.tag && !ti.is_constructed)
1073         break; /* Ready */ 
1074       if (ti.class != UNIVERSAL || ti.tag != TAG_SEQUENCE)
1075         goto bailout;
1076
1077       if (!bagseqndef)
1078         {
1079           if (bagseqlength < ti.nhdr)
1080             goto bailout;
1081           bagseqlength -= ti.nhdr;
1082           if (bagseqlength < ti.length)
1083             goto bailout;
1084           bagseqlength -= ti.length;
1085         }
1086       lenndef = ti.ndef;
1087       len = ti.length;
1088
1089       if (parse_tag (&p, &n, &ti))
1090         goto bailout;
1091       if (lenndef)
1092         len = ti.nhdr; 
1093       else
1094         len -= ti.nhdr; 
1095
1096       if (ti.tag == TAG_OBJECT_ID && ti.length == DIM(oid_encryptedData)
1097           && !memcmp (p, oid_encryptedData, DIM(oid_encryptedData)))
1098         {
1099           size_t consumed = 0;
1100
1101           p += DIM(oid_encryptedData);
1102           n -= DIM(oid_encryptedData);
1103           if (!lenndef)
1104             len -= DIM(oid_encryptedData);
1105           where = "bag.encryptedData";
1106           if (parse_bag_encrypted_data (p, n, (p - p_start), &consumed, pw,
1107                                         certcb, certcbarg))
1108             goto bailout;
1109           if (lenndef)
1110             len += consumed;
1111         }
1112       else if (ti.tag == TAG_OBJECT_ID && ti.length == DIM(oid_data)
1113                && !memcmp (p, oid_data, DIM(oid_data)))
1114         {
1115           if (result)
1116             {
1117               log_info ("already got an data object, skipping next one\n");
1118               p += ti.length;
1119               n -= ti.length;
1120             }
1121           else
1122             {
1123               size_t consumed = 0;
1124
1125               p += DIM(oid_data);
1126               n -= DIM(oid_data);
1127               if (!lenndef)
1128                 len -= DIM(oid_data);
1129               result = parse_bag_data (p, n, (p - p_start), &consumed, pw);
1130               if (!result)
1131                 goto bailout;
1132               if (lenndef)
1133                 len += consumed;
1134             }
1135         }
1136       else
1137         {
1138           log_info ("unknown bag type - skipped\n");
1139           p += ti.length;
1140           n -= ti.length;
1141         }
1142
1143       if (len < 0 || len > n)
1144         goto bailout;
1145       p += len;
1146       n -= len;
1147       if (lenndef)
1148         {
1149           /* Need to skip the Null Tag. */
1150           if (parse_tag (&p, &n, &ti))
1151             goto bailout;
1152           if (!(ti.class == UNIVERSAL && !ti.tag && !ti.is_constructed))
1153             goto bailout;
1154         }
1155     }
1156   
1157   gcry_free (cram_buffer);
1158   return result;
1159  bailout:
1160   log_error ("error at \"%s\", offset %u\n", where, (p - p_start));
1161   /* fixme: need to release RESULT. */
1162   gcry_free (cram_buffer);
1163   return NULL;
1164 }
1165
1166
1167 \f
1168 static size_t
1169 compute_tag_length (size_t n)
1170 {     
1171   int needed = 0;
1172
1173   if (n < 128)
1174     needed += 2; /* tag and one length byte */
1175   else if (n < 256)
1176     needed += 3; /* tag, number of length bytes, 1 length byte */
1177   else if (n < 65536)
1178     needed += 4; /* tag, number of length bytes, 2 length bytes */
1179   else
1180     {
1181       log_error ("object too larger to encode\n");
1182       return 0;
1183     }
1184   return needed;
1185 }
1186
1187 static unsigned char *
1188 store_tag_length (unsigned char *p, int tag, size_t n)
1189 {     
1190   if (tag == TAG_SEQUENCE)
1191     tag |= 0x20; /* constructed */
1192
1193   *p++ = tag;
1194   if (n < 128)
1195     *p++ = n;
1196   else if (n < 256)
1197     {
1198       *p++ = 0x81;
1199       *p++ = n;
1200     }
1201   else if (n < 65536)
1202     {
1203       *p++ = 0x82;
1204       *p++ = n >> 8;
1205       *p++ = n;
1206     }
1207
1208   return p;
1209 }
1210
1211
1212 /* Create the final PKCS-12 object from the sequences contained in
1213    SEQLIST.  PW is the password. That array is terminated with an NULL
1214    object. */
1215 static unsigned char *
1216 create_final (struct buffer_s *sequences, const char *pw, size_t *r_length)
1217 {
1218   int i;
1219   size_t needed = 0;
1220   size_t len[8], n;
1221   unsigned char *macstart;
1222   size_t maclen;
1223   unsigned char *result, *p;
1224   size_t resultlen;
1225   char salt[8];
1226   unsigned char keybuf[20];
1227   gcry_md_hd_t md;
1228   int rc;
1229
1230   /* 9 steps to create the pkcs#12 Krampf. */
1231
1232   /* 8. The MAC. */
1233   /* We add this at step 0. */
1234
1235   /* 7. All the buffers. */
1236   for (i=0; sequences[i].buffer; i++)
1237     needed += sequences[i].length;
1238
1239   /* 6. This goes into a sequences. */
1240   len[6] = needed;
1241   n = compute_tag_length (needed);
1242   needed += n;
1243
1244   /* 5. Encapsulate all in an octet string. */
1245   len[5] = needed;
1246   n = compute_tag_length (needed);
1247   needed += n;
1248
1249   /* 4. And tag it with [0]. */
1250   len[4] = needed;
1251   n = compute_tag_length (needed);
1252   needed += n;
1253
1254   /* 3. Prepend an data OID. */
1255   needed += 2 + DIM (oid_data);
1256
1257   /* 2. Put all into a sequences. */
1258   len[2] = needed;
1259   n = compute_tag_length (needed);
1260   needed += n;
1261
1262   /* 1. Prepend the version integer 3. */
1263   needed += 3;
1264
1265   /* 0. And the final outer sequence. */
1266   needed += DIM (data_mactemplate);
1267   len[0] = needed;
1268   n = compute_tag_length (needed);
1269   needed += n;
1270
1271   /* Allocate a buffer. */
1272   result = gcry_malloc (needed);
1273   if (!result)
1274     {
1275       log_error ("error allocating buffer\n");
1276       return NULL;
1277     }
1278   p = result;
1279
1280   /* 0. Store the very outer sequence. */
1281   p = store_tag_length (p, TAG_SEQUENCE, len[0]);
1282
1283   /* 1. Store the version integer 3. */
1284   *p++ = TAG_INTEGER;
1285   *p++ = 1; 
1286   *p++ = 3;
1287
1288   /* 2. Store another sequence. */
1289   p = store_tag_length (p, TAG_SEQUENCE, len[2]);
1290
1291   /* 3. Store the data OID. */
1292   p = store_tag_length (p, TAG_OBJECT_ID, DIM (oid_data));
1293   memcpy (p, oid_data, DIM (oid_data)); 
1294   p += DIM (oid_data); 
1295
1296   /* 4. Next comes a context tag. */
1297   p = store_tag_length (p, 0xa0, len[4]);
1298
1299   /* 5. And an octet string. */
1300   p = store_tag_length (p, TAG_OCTET_STRING, len[5]);
1301
1302   /* 6. And the inner sequence. */
1303   macstart = p;
1304   p = store_tag_length (p, TAG_SEQUENCE, len[6]);
1305
1306   /* 7. Append all the buffers. */
1307   for (i=0; sequences[i].buffer; i++)
1308     {
1309       memcpy (p, sequences[i].buffer, sequences[i].length);
1310       p += sequences[i].length;
1311     }
1312
1313   /* Intermezzo to compute the MAC. */
1314   maclen = p - macstart;
1315   gcry_randomize (salt, 8, GCRY_STRONG_RANDOM);
1316   if (string_to_key (3, salt, 8, 2048, pw, 20, keybuf))
1317     {
1318       gcry_free (result);
1319       return NULL;
1320     }
1321   rc = gcry_md_open (&md, GCRY_MD_SHA1, GCRY_MD_FLAG_HMAC);
1322   if (rc)
1323     {
1324       log_error ("gcry_md_open failed: %s\n", gpg_strerror (rc));
1325       gcry_free (result);
1326       return NULL;
1327     }
1328   rc = gcry_md_setkey (md, keybuf, 20);
1329   if (rc)
1330     {
1331       log_error ("gcry_md_setkey failed: %s\n", gpg_strerror (rc));
1332       gcry_md_close (md);
1333       gcry_free (result);
1334       return NULL;
1335     }
1336   gcry_md_write (md, macstart, maclen);
1337
1338   /* 8. Append the MAC template and fix it up. */
1339   memcpy (p, data_mactemplate, DIM (data_mactemplate));
1340   memcpy (p + DATA_MACTEMPLATE_SALT_OFF, salt, 8);
1341   memcpy (p + DATA_MACTEMPLATE_MAC_OFF, gcry_md_read (md, 0), 20);
1342   p += DIM (data_mactemplate);
1343   gcry_md_close (md);
1344
1345   /* Ready. */
1346   resultlen = p - result;
1347   if (needed != resultlen)
1348     log_debug ("length mismatch: %lu, %lu\n",
1349                (unsigned long)needed, (unsigned long)resultlen);
1350
1351   *r_length = resultlen;
1352   return result;
1353 }
1354
1355
1356 /* Build a DER encoded SEQUENCE with the key:
1357
1358    SEQUENCE {
1359      INTEGER 0
1360      SEQUENCE {
1361        OBJECT IDENTIFIER rsaEncryption (1 2 840 113549 1 1 1)
1362        NULL
1363        }
1364      OCTET STRING, encapsulates {
1365        SEQUENCE {
1366          INTEGER 0
1367          INTEGER
1368          INTEGER 
1369          INTEGER
1370          INTEGER
1371          INTEGER
1372          INTEGER
1373          INTEGER
1374          INTEGER
1375          }
1376        }
1377      }
1378 */  
1379   
1380 static unsigned char * 
1381 build_key_sequence (gcry_mpi_t *kparms, size_t *r_length)
1382 {
1383   int rc, i;
1384   size_t needed, n;
1385   unsigned char *plain, *p;
1386   size_t plainlen;
1387   size_t outseqlen, oidseqlen, octstrlen, inseqlen;
1388
1389   needed = 3; /* The version(?) integer of value 0. */
1390   for (i=0; kparms[i]; i++)
1391     {
1392       n = 0;
1393       rc = gcry_mpi_print (GCRYMPI_FMT_STD, NULL, 0, &n, kparms[i]);
1394       if (rc)
1395         {
1396           log_error ("error formatting parameter: %s\n", gpg_strerror (rc));
1397           return NULL;
1398         }
1399       needed += n;
1400       n = compute_tag_length (n);
1401       if (!n)
1402         return NULL;
1403       needed += n;
1404     }
1405   if (i != 8)
1406     {
1407       log_error ("invalid paramters for p12_build\n");
1408       return NULL;
1409     }
1410   /* Now this all goes into a sequence. */
1411   inseqlen = needed;
1412   n = compute_tag_length (needed);
1413   if (!n)
1414     return NULL;
1415   needed += n;
1416   /* Encapsulate all into an octet string. */
1417   octstrlen = needed;
1418   n = compute_tag_length (needed);
1419   if (!n)
1420     return NULL;
1421   needed += n;
1422   /* Prepend the object identifier sequence. */
1423   oidseqlen = 2 + DIM (oid_rsaEncryption) + 2;
1424   needed += 2 + oidseqlen;
1425   /* The version number. */
1426   needed += 3;
1427   /* And finally put the whole thing into a sequence. */
1428   outseqlen = needed;
1429   n = compute_tag_length (needed);
1430   if (!n)
1431     return NULL;
1432   needed += n;
1433   
1434   /* allocate 8 extra bytes for padding */
1435   plain = gcry_malloc_secure (needed+8);
1436   if (!plain)
1437     {
1438       log_error ("error allocating encryption buffer\n");
1439       return NULL;
1440     }
1441   
1442   /* And now fill the plaintext buffer. */
1443   p = plain;
1444   p = store_tag_length (p, TAG_SEQUENCE, outseqlen);
1445   /* Store version. */
1446   *p++ = TAG_INTEGER;
1447   *p++ = 1;
1448   *p++ = 0;
1449   /* Store object identifier sequence. */
1450   p = store_tag_length (p, TAG_SEQUENCE, oidseqlen);
1451   p = store_tag_length (p, TAG_OBJECT_ID, DIM (oid_rsaEncryption));
1452   memcpy (p, oid_rsaEncryption, DIM (oid_rsaEncryption)); 
1453   p += DIM (oid_rsaEncryption); 
1454   *p++ = TAG_NULL;
1455   *p++ = 0;
1456   /* Start with the octet string. */
1457   p = store_tag_length (p, TAG_OCTET_STRING, octstrlen);
1458   p = store_tag_length (p, TAG_SEQUENCE, inseqlen);
1459   /* Store the key parameters. */
1460   *p++ = TAG_INTEGER;
1461   *p++ = 1;
1462   *p++ = 0;
1463   for (i=0; kparms[i]; i++)
1464     {
1465       n = 0;
1466       rc = gcry_mpi_print (GCRYMPI_FMT_STD, NULL, 0, &n, kparms[i]);
1467       if (rc)
1468         {
1469           log_error ("oops: error formatting parameter: %s\n",
1470                      gpg_strerror (rc));
1471           gcry_free (plain);
1472           return NULL;
1473         }
1474       p = store_tag_length (p, TAG_INTEGER, n);
1475       
1476       n = plain + needed - p;
1477       rc = gcry_mpi_print (GCRYMPI_FMT_STD, p, n, &n, kparms[i]);
1478       if (rc)
1479         {
1480           log_error ("oops: error storing parameter: %s\n",
1481                      gpg_strerror (rc));
1482           gcry_free (plain);
1483           return NULL;
1484         }
1485       p += n;
1486     }
1487
1488   plainlen = p - plain;
1489   assert (needed == plainlen);
1490   /* Append some pad characters; we already allocated extra space. */
1491   n = 8 - plainlen % 8;
1492   for (i=0; i < n; i++, plainlen++)
1493     *p++ = n;
1494
1495   *r_length = plainlen;
1496   return plain;
1497 }
1498
1499
1500
1501 static unsigned char *
1502 build_key_bag (unsigned char *buffer, size_t buflen, char *salt,
1503                size_t *r_length)
1504 {
1505   size_t len[11], needed;
1506   unsigned char *p, *keybag;
1507   size_t keybaglen;
1508
1509   /* Walk 11 steps down to collect the info: */
1510
1511   /* 10. The data goes into an octet string. */
1512   needed = compute_tag_length (buflen);
1513   needed += buflen;
1514
1515   /* 9. Prepend the algorithm identifier. */
1516   needed += DIM (data_3desiter2048);
1517
1518   /* 8. Put a sequence around. */
1519   len[8] = needed;
1520   needed += compute_tag_length (needed);
1521
1522   /* 7. Prepend a [0] tag. */
1523   len[7] = needed;
1524   needed += compute_tag_length (needed);
1525
1526   /* 6. Prepend the shroudedKeyBag OID. */
1527   needed += 2 + DIM (oid_pkcs_12_pkcs_8ShroudedKeyBag);
1528
1529   /* 5+4. Put all into two sequences. */
1530   len[5] = needed;
1531   needed += compute_tag_length ( needed);
1532   len[4] = needed;
1533   needed += compute_tag_length (needed);
1534
1535   /* 3. This all goes into an octet string. */
1536   len[3] = needed;
1537   needed += compute_tag_length (needed);
1538
1539   /* 2. Prepend another [0] tag. */
1540   len[2] = needed;
1541   needed += compute_tag_length (needed);
1542
1543   /* 1. Prepend the data OID. */
1544   needed += 2 + DIM (oid_data);
1545
1546   /* 0. Prepend another sequence. */
1547   len[0] = needed;
1548   needed += compute_tag_length (needed);
1549
1550   /* Now that we have all length information, allocate a buffer. */
1551   p = keybag = gcry_malloc (needed);
1552   if (!keybag)
1553     {
1554       log_error ("error allocating buffer\n");
1555       return NULL;
1556     }
1557
1558   /* Walk 11 steps up to store the data. */
1559
1560   /* 0. Store the first sequence. */
1561   p = store_tag_length (p, TAG_SEQUENCE, len[0]);
1562
1563   /* 1. Store the data OID. */
1564   p = store_tag_length (p, TAG_OBJECT_ID, DIM (oid_data));
1565   memcpy (p, oid_data, DIM (oid_data)); 
1566   p += DIM (oid_data); 
1567
1568   /* 2. Store a [0] tag. */
1569   p = store_tag_length (p, 0xa0, len[2]);
1570
1571   /* 3. And an octet string. */
1572   p = store_tag_length (p, TAG_OCTET_STRING, len[3]);
1573
1574   /* 4+5. Two sequences. */
1575   p = store_tag_length (p, TAG_SEQUENCE, len[4]);
1576   p = store_tag_length (p, TAG_SEQUENCE, len[5]);
1577
1578   /* 6. Store the shroudedKeyBag OID. */
1579   p = store_tag_length (p, TAG_OBJECT_ID,
1580                         DIM (oid_pkcs_12_pkcs_8ShroudedKeyBag));
1581   memcpy (p, oid_pkcs_12_pkcs_8ShroudedKeyBag,
1582           DIM (oid_pkcs_12_pkcs_8ShroudedKeyBag)); 
1583   p += DIM (oid_pkcs_12_pkcs_8ShroudedKeyBag); 
1584
1585   /* 7. Store a [0] tag. */
1586   p = store_tag_length (p, 0xa0, len[7]);
1587
1588   /* 8. Store a sequence. */
1589   p = store_tag_length (p, TAG_SEQUENCE, len[8]);
1590
1591   /* 9. Now for the pre-encoded algorithm identifier and the salt. */
1592   memcpy (p, data_3desiter2048, DIM (data_3desiter2048));
1593   memcpy (p + DATA_3DESITER2048_SALT_OFF, salt, 8);
1594   p += DIM (data_3desiter2048);
1595
1596   /* 10. And finally the octet string with the encrypted data. */
1597   p = store_tag_length (p, TAG_OCTET_STRING, buflen);
1598   memcpy (p, buffer, buflen);
1599   p += buflen;
1600   keybaglen = p - keybag;
1601   
1602   if (needed != keybaglen)
1603     log_debug ("length mismatch: %lu, %lu\n",
1604                (unsigned long)needed, (unsigned long)keybaglen);
1605   
1606   *r_length = keybaglen;
1607   return keybag;
1608 }
1609
1610
1611 static unsigned char *
1612 build_cert_bag (unsigned char *buffer, size_t buflen, char *salt,
1613                 size_t *r_length)
1614 {
1615   size_t len[9], needed;
1616   unsigned char *p, *certbag;
1617   size_t certbaglen;
1618
1619   /* Walk 9 steps down to collect the info: */
1620
1621   /* 8. The data goes into an octet string. */
1622   needed = compute_tag_length (buflen);
1623   needed += buflen;
1624
1625   /* 7. The algorithm identifier. */
1626   needed += DIM (data_rc2iter2048);
1627
1628   /* 6. The data OID. */
1629   needed += 2 + DIM (oid_data);
1630
1631   /* 5. A sequence. */
1632   len[5] = needed;
1633   needed += compute_tag_length ( needed);
1634
1635   /* 4. An integer. */
1636   needed += 3;
1637
1638   /* 3. A sequence. */
1639   len[3] = needed;
1640   needed += compute_tag_length (needed);
1641
1642   /* 2.  A [0] tag. */
1643   len[2] = needed;
1644   needed += compute_tag_length (needed);
1645
1646   /* 1. The encryptedData OID. */
1647   needed += 2 + DIM (oid_encryptedData);
1648
1649   /* 0. The first sequence. */
1650   len[0] = needed;
1651   needed += compute_tag_length (needed);
1652
1653   /* Now that we have all length information, allocate a buffer. */
1654   p = certbag = gcry_malloc (needed);
1655   if (!certbag)
1656     {
1657       log_error ("error allocating buffer\n");
1658       return NULL;
1659     }
1660
1661   /* Walk 9 steps up to store the data. */
1662
1663   /* 0. Store the first sequence. */
1664   p = store_tag_length (p, TAG_SEQUENCE, len[0]);
1665
1666   /* 1. Store the encryptedData OID. */
1667   p = store_tag_length (p, TAG_OBJECT_ID, DIM (oid_encryptedData));
1668   memcpy (p, oid_encryptedData, DIM (oid_encryptedData)); 
1669   p += DIM (oid_encryptedData); 
1670
1671   /* 2. Store a [0] tag. */
1672   p = store_tag_length (p, 0xa0, len[2]);
1673
1674   /* 3. Store a sequence. */
1675   p = store_tag_length (p, TAG_SEQUENCE, len[3]);
1676
1677   /* 4. Store the integer 0. */
1678   *p++ = TAG_INTEGER;
1679   *p++ = 1; 
1680   *p++ = 0;
1681
1682   /* 5. Store a sequence. */
1683   p = store_tag_length (p, TAG_SEQUENCE, len[5]);
1684
1685   /* 6. Store the data OID. */
1686   p = store_tag_length (p, TAG_OBJECT_ID, DIM (oid_data));
1687   memcpy (p, oid_data, DIM (oid_data)); 
1688   p += DIM (oid_data); 
1689
1690   /* 7. Now for the pre-encoded algorithm identifier and the salt. */
1691   memcpy (p, data_rc2iter2048, DIM (data_rc2iter2048));
1692   memcpy (p + DATA_RC2ITER2048_SALT_OFF, salt, 8);
1693   p += DIM (data_rc2iter2048);
1694
1695   /* 8. And finally the [0] tag with the encrypted data. */
1696   p = store_tag_length (p, 0x80, buflen);
1697   memcpy (p, buffer, buflen);
1698   p += buflen;
1699   certbaglen = p - certbag;
1700   
1701   if (needed != certbaglen)
1702     log_debug ("length mismatch: %lu, %lu\n",
1703                (unsigned long)needed, (unsigned long)certbaglen);
1704
1705   *r_length = certbaglen;
1706   return certbag;
1707 }
1708
1709
1710 static unsigned char *
1711 build_cert_sequence (unsigned char *buffer, size_t buflen, size_t *r_length)
1712 {
1713   size_t len[8], needed, n;
1714   unsigned char *p, *certseq;
1715   size_t certseqlen;
1716   int i;
1717
1718   /* Walk 8 steps down to collect the info: */
1719
1720   /* 7. The data goes into an octet string. */
1721   needed = compute_tag_length (buflen);
1722   needed += buflen;
1723
1724   /* 6. A [0] tag. */
1725   len[6] = needed;
1726   needed += compute_tag_length (needed);
1727
1728   /* 5. An OID. */
1729   needed += 2 + DIM (oid_x509Certificate_for_pkcs_12);
1730
1731   /* 4. A sequence. */
1732   len[4] = needed;
1733   needed += compute_tag_length (needed);
1734
1735   /* 3. A [0] tag. */
1736   len[3] = needed;
1737   needed += compute_tag_length (needed);
1738
1739   /* 2. An OID. */
1740   needed += 2 + DIM (oid_pkcs_12_CertBag);
1741
1742   /* 1. A sequence. */
1743   len[1] = needed;
1744   needed += compute_tag_length (needed);
1745
1746   /* 0. The first sequence. */
1747   len[0] = needed;
1748   needed += compute_tag_length (needed);
1749
1750   /* Now that we have all length information, allocate a buffer. */
1751   p = certseq = gcry_malloc (needed + 8 /*(for padding)*/);
1752   if (!certseq)
1753     {
1754       log_error ("error allocating buffer\n");
1755       return NULL;
1756     }
1757
1758   /* Walk 8 steps up to store the data. */
1759
1760   /* 0. Store the first sequence. */
1761   p = store_tag_length (p, TAG_SEQUENCE, len[0]);
1762
1763   /* 1. Store the second sequence. */
1764   p = store_tag_length (p, TAG_SEQUENCE, len[1]);
1765
1766   /* 2. Store the pkcs12-cert-bag OID. */
1767   p = store_tag_length (p, TAG_OBJECT_ID, DIM (oid_pkcs_12_CertBag));
1768   memcpy (p, oid_pkcs_12_CertBag, DIM (oid_pkcs_12_CertBag)); 
1769   p += DIM (oid_pkcs_12_CertBag); 
1770
1771   /* 3. Store a [0] tag. */
1772   p = store_tag_length (p, 0xa0, len[3]);
1773
1774   /* 4. Store a sequence. */
1775   p = store_tag_length (p, TAG_SEQUENCE, len[4]);
1776
1777   /* 5. Store the x509Certificate OID. */
1778   p = store_tag_length (p, TAG_OBJECT_ID,
1779                         DIM (oid_x509Certificate_for_pkcs_12));
1780   memcpy (p, oid_x509Certificate_for_pkcs_12,
1781           DIM (oid_x509Certificate_for_pkcs_12)); 
1782   p += DIM (oid_x509Certificate_for_pkcs_12); 
1783
1784   /* 6. Store a [0] tag. */
1785   p = store_tag_length (p, 0xa0, len[6]);
1786
1787   /* 7. And finally the octet string with the actual certificate. */
1788   p = store_tag_length (p, TAG_OCTET_STRING, buflen);
1789   memcpy (p, buffer, buflen);
1790   p += buflen;
1791   certseqlen = p - certseq;
1792   
1793   if (needed != certseqlen)
1794     log_debug ("length mismatch: %lu, %lu\n",
1795                (unsigned long)needed, (unsigned long)certseqlen);
1796   
1797   /* Append some pad characters; we already allocated extra space. */
1798   n = 8 - certseqlen % 8;
1799   for (i=0; i < n; i++, certseqlen++)
1800     *p++ = n;
1801   
1802   *r_length = certseqlen;
1803   return certseq;
1804 }
1805
1806
1807 /* Expect the RSA key parameters in KPARMS and a password in
1808    PW. Create a PKCS structure from it and return it as well as the
1809    length in R_LENGTH; return NULL in case of an error. */
1810 unsigned char * 
1811 p12_build (gcry_mpi_t *kparms, unsigned char *cert, size_t certlen,
1812            const char *pw, size_t *r_length)
1813 {
1814   unsigned char *buffer;
1815   size_t n, buflen;
1816   char salt[8];
1817   struct buffer_s seqlist[3];
1818   int seqlistidx = 0;
1819
1820   n = buflen = 0; /* (avoid compiler warning). */
1821
1822   if (cert && certlen)
1823     {
1824       /* Encode the certificate. */
1825       buffer = build_cert_sequence (cert, certlen, &buflen);
1826       if (!buffer)
1827         goto failure;
1828
1829       /* Encrypt it. */
1830       gcry_randomize (salt, 8, GCRY_STRONG_RANDOM);
1831       crypt_block (buffer, buflen, salt, 8, 2048, pw,
1832                    GCRY_CIPHER_RFC2268_40, 1);
1833       
1834       /* Encode the encrypted stuff into a bag. */
1835       seqlist[seqlistidx].buffer = build_cert_bag (buffer, buflen, salt, &n);
1836       seqlist[seqlistidx].length = n;
1837       gcry_free (buffer);
1838       buffer = NULL;
1839       if (!seqlist[seqlistidx].buffer)
1840         goto failure;
1841       seqlistidx++;
1842     }
1843
1844   if (kparms)
1845     {
1846       /* Encode the key. */
1847       buffer = build_key_sequence (kparms, &buflen);
1848       if (!buffer)
1849         goto failure;
1850       
1851       /* Encrypt it. */
1852       gcry_randomize (salt, 8, GCRY_STRONG_RANDOM);
1853       crypt_block (buffer, buflen, salt, 8, 2048, pw, GCRY_CIPHER_3DES, 1);
1854
1855       /* Encode the encrypted stuff into a bag. */
1856       seqlist[seqlistidx].buffer = build_key_bag (buffer, buflen, salt, &n);
1857       seqlist[seqlistidx].length = n;
1858       gcry_free (buffer);
1859       buffer = NULL;
1860       if (!seqlist[seqlistidx].buffer)
1861         goto failure;
1862       seqlistidx++;
1863     }
1864
1865   seqlist[seqlistidx].buffer = NULL;
1866   seqlist[seqlistidx].length = 0;
1867
1868   buffer = create_final (seqlist, pw, &buflen);
1869
1870  failure:
1871   for ( ; seqlistidx; seqlistidx--)
1872     gcry_free (seqlist[seqlistidx].buffer);
1873
1874   *r_length = buffer? buflen : 0;
1875   return buffer;
1876 }
1877
1878
1879 #ifdef TEST
1880
1881 static void 
1882 cert_cb (void *opaque, const unsigned char *cert, size_t certlen)
1883 {
1884   printf ("got a certificate of %u bytes length\n", certlen);
1885 }
1886
1887 int
1888 main (int argc, char **argv)
1889 {
1890   FILE *fp;
1891   struct stat st;
1892   unsigned char *buf;
1893   size_t buflen;
1894   gcry_mpi_t *result;
1895
1896   if (argc != 3)
1897     {
1898       fprintf (stderr, "usage: testp12 file passphrase\n");
1899       return 1;
1900     }
1901
1902   gcry_control (GCRYCTL_DISABLE_SECMEM, NULL);
1903   gcry_control (GCRYCTL_INITIALIZATION_FINISHED, NULL);
1904
1905   fp = fopen (argv[1], "rb");
1906   if (!fp)
1907     {
1908       fprintf (stderr, "can't open `%s': %s\n", argv[1], strerror (errno));
1909       return 1;
1910     }
1911   
1912   if (fstat (fileno(fp), &st))
1913     {
1914       fprintf (stderr, "can't stat `%s': %s\n", argv[1], strerror (errno));
1915       return 1;
1916     }
1917
1918   buflen = st.st_size;
1919   buf = gcry_malloc (buflen+1);
1920   if (!buf || fread (buf, buflen, 1, fp) != 1)
1921     {
1922       fprintf (stderr, "error reading `%s': %s\n", argv[1], strerror (errno));
1923       return 1;
1924     }
1925   fclose (fp);
1926
1927   result = p12_parse (buf, buflen, argv[2], cert_cb, NULL);
1928   if (result)
1929     {
1930       int i, rc;
1931       unsigned char *tmpbuf;
1932
1933       for (i=0; result[i]; i++)
1934         {
1935           rc = gcry_mpi_aprint (GCRYMPI_FMT_HEX, &tmpbuf,
1936                                 NULL, result[i]);
1937           if (rc)
1938             printf ("%d: [error printing number: %s]\n",
1939                     i, gpg_strerror (rc));
1940           else
1941             {
1942               printf ("%d: %s\n", i, tmpbuf);
1943               gcry_free (tmpbuf);
1944             }
1945         }
1946     }
1947
1948   return 0;
1949
1950 }
1951
1952 /*
1953 Local Variables:
1954 compile-command: "gcc -Wall -O -g -DTEST=1 -o minip12 minip12.c ../jnlib/libjnlib.a -L /usr/local/lib -lgcrypt -lgpg-error"
1955 End:
1956 */
1957 #endif /* TEST */