Imported Upstream version 2.1.8
[platform/upstream/gpg2.git] / agent / cvt-openpgp.c
1 /* cvt-openpgp.c - Convert an OpenPGP key to our internal format.
2  * Copyright (C) 1998-2002, 2006, 2009, 2010 Free Software Foundation, Inc.
3  * Copyright (C) 2013, 2014 Werner Koch
4  *
5  * This file is part of GnuPG.
6  *
7  * GnuPG is free software; you can redistribute it and/or modify
8  * it under the terms of the GNU General Public License as published by
9  * the Free Software Foundation; either version 3 of the License, or
10  * (at your option) any later version.
11  *
12  * GnuPG is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program; if not, see <http://www.gnu.org/licenses/>.
19  */
20
21 #include <config.h>
22 #include <stdio.h>
23 #include <stdlib.h>
24 #include <string.h>
25 #include <assert.h>
26
27 #include "agent.h"
28 #include "i18n.h"
29 #include "cvt-openpgp.h"
30 #include "host2net.h"
31
32
33 /* Helper to pass data via the callback to do_unprotect. */
34 struct try_do_unprotect_arg_s
35 {
36   int  is_v4;
37   int  is_protected;
38   int  pubkey_algo;
39   const char *curve;
40   int  protect_algo;
41   char *iv;
42   int  ivlen;
43   int  s2k_mode;
44   int  s2k_algo;
45   byte *s2k_salt;
46   u32  s2k_count;
47   u16 desired_csum;
48   gcry_mpi_t *skey;
49   size_t skeysize;
50   int skeyidx;
51   gcry_sexp_t *r_key;
52 };
53
54
55
56 /* Compute the keygrip from the public key and store it at GRIP.  */
57 static gpg_error_t
58 get_keygrip (int pubkey_algo, const char *curve, gcry_mpi_t *pkey,
59              unsigned char *grip)
60 {
61   gpg_error_t err;
62   gcry_sexp_t s_pkey = NULL;
63
64   switch (pubkey_algo)
65     {
66     case GCRY_PK_DSA:
67       err = gcry_sexp_build (&s_pkey, NULL,
68                              "(public-key(dsa(p%m)(q%m)(g%m)(y%m)))",
69                              pkey[0], pkey[1], pkey[2], pkey[3]);
70       break;
71
72     case GCRY_PK_ELG:
73       err = gcry_sexp_build (&s_pkey, NULL,
74                              "(public-key(elg(p%m)(g%m)(y%m)))",
75                              pkey[0], pkey[1], pkey[2]);
76       break;
77
78     case GCRY_PK_RSA:
79       err = gcry_sexp_build (&s_pkey, NULL,
80                              "(public-key(rsa(n%m)(e%m)))", pkey[0], pkey[1]);
81       break;
82
83     case GCRY_PK_ECC:
84       if (!curve)
85         err = gpg_error (GPG_ERR_BAD_SECKEY);
86       else
87         {
88           const char *format;
89
90           if (!strcmp (curve, "Ed25519"))
91             format = "(public-key(ecc(curve %s)(flags eddsa)(q%m)))";
92           else if (!strcmp (curve, "Curve25519"))
93             format = "(public-key(ecc(curve %s)(flags djb-tweak)(q%m)))";
94           else
95             format = "(public-key(ecc(curve %s)(q%m)))";
96
97           err = gcry_sexp_build (&s_pkey, NULL, format, curve, pkey[0]);
98         }
99       break;
100
101     default:
102       err = gpg_error (GPG_ERR_PUBKEY_ALGO);
103       break;
104     }
105
106   if (!err && !gcry_pk_get_keygrip (s_pkey, grip))
107     err = gpg_error (GPG_ERR_INTERNAL);
108
109   gcry_sexp_release (s_pkey);
110   return err;
111 }
112
113
114 /* Convert a secret key given as algorithm id and an array of key
115    parameters into our s-expression based format.  Note that
116    PUBKEY_ALGO has an gcrypt algorithm number. */
117 static gpg_error_t
118 convert_secret_key (gcry_sexp_t *r_key, int pubkey_algo, gcry_mpi_t *skey,
119                     const char *curve)
120 {
121   gpg_error_t err;
122   gcry_sexp_t s_skey = NULL;
123
124   *r_key = NULL;
125
126   switch (pubkey_algo)
127     {
128     case GCRY_PK_DSA:
129       err = gcry_sexp_build (&s_skey, NULL,
130                              "(private-key(dsa(p%m)(q%m)(g%m)(y%m)(x%m)))",
131                              skey[0], skey[1], skey[2], skey[3], skey[4]);
132       break;
133
134     case GCRY_PK_ELG:
135     case GCRY_PK_ELG_E:
136       err = gcry_sexp_build (&s_skey, NULL,
137                              "(private-key(elg(p%m)(g%m)(y%m)(x%m)))",
138                              skey[0], skey[1], skey[2], skey[3]);
139       break;
140
141
142     case GCRY_PK_RSA:
143     case GCRY_PK_RSA_E:
144     case GCRY_PK_RSA_S:
145       err = gcry_sexp_build (&s_skey, NULL,
146                              "(private-key(rsa(n%m)(e%m)(d%m)(p%m)(q%m)(u%m)))",
147                              skey[0], skey[1], skey[2], skey[3], skey[4],
148                              skey[5]);
149       break;
150
151     case GCRY_PK_ECC:
152       if (!curve)
153         err = gpg_error (GPG_ERR_BAD_SECKEY);
154       else
155         {
156           const char *format;
157
158           if (!strcmp (curve, "Ed25519"))
159             /* Do not store the OID as name but the real name and the
160                EdDSA flag.  */
161             format = "(private-key(ecc(curve %s)(flags eddsa)(q%m)(d%m)))";
162           else if (!strcmp (curve, "Curve25519"))
163             format = "(private-key(ecc(curve %s)(flags djb-tweak)(q%m)(d%m)))";
164           else
165             format = "(private-key(ecc(curve %s)(q%m)(d%m)))";
166
167           err = gcry_sexp_build (&s_skey, NULL, format, curve, skey[0], skey[1]);
168         }
169       break;
170
171     default:
172       err = gpg_error (GPG_ERR_PUBKEY_ALGO);
173       break;
174     }
175
176   if (!err)
177     *r_key = s_skey;
178   return err;
179 }
180
181
182 /* Convert a secret key given as algorithm id, an array of key
183    parameters, and an S-expression of the original OpenPGP transfer
184    key into our s-expression based format.  This is a variant of
185    convert_secret_key which is used for the openpgp-native protection
186    mode.  Note that PUBKEY_ALGO has an gcrypt algorithm number. */
187 static gpg_error_t
188 convert_transfer_key (gcry_sexp_t *r_key, int pubkey_algo, gcry_mpi_t *skey,
189                       const char *curve, gcry_sexp_t transfer_key)
190 {
191   gpg_error_t err;
192   gcry_sexp_t s_skey = NULL;
193
194   *r_key = NULL;
195
196   switch (pubkey_algo)
197     {
198     case GCRY_PK_DSA:
199       err = gcry_sexp_build
200         (&s_skey, NULL,
201          "(protected-private-key(dsa(p%m)(q%m)(g%m)(y%m)"
202          "(protected openpgp-native%S)))",
203          skey[0], skey[1], skey[2], skey[3], transfer_key);
204       break;
205
206     case GCRY_PK_ELG:
207       err = gcry_sexp_build
208         (&s_skey, NULL,
209          "(protected-private-key(elg(p%m)(g%m)(y%m)"
210          "(protected openpgp-native%S)))",
211          skey[0], skey[1], skey[2], transfer_key);
212       break;
213
214
215     case GCRY_PK_RSA:
216       err = gcry_sexp_build
217         (&s_skey, NULL,
218          "(protected-private-key(rsa(n%m)(e%m)"
219          "(protected openpgp-native%S)))",
220          skey[0], skey[1], transfer_key );
221       break;
222
223     case GCRY_PK_ECC:
224       if (!curve)
225         err = gpg_error (GPG_ERR_BAD_SECKEY);
226       else
227         {
228           const char *format;
229
230           if (!strcmp (curve, "Ed25519"))
231             /* Do not store the OID as name but the real name and the
232                EdDSA flag.  */
233             format = "(protected-private-key(ecc(curve %s)(flags eddsa)(q%m)"
234               "(protected openpgp-native%S)))";
235           else if (!strcmp (curve, "Curve25519"))
236             format = "(protected-private-key(ecc(curve %s)(flags djb-tweak)(q%m)"
237               "(protected openpgp-native%S)))";
238           else
239             format = "(protected-private-key(ecc(curve %s)(q%m)"
240               "(protected openpgp-native%S)))";
241
242           err = gcry_sexp_build (&s_skey, NULL, format, curve, skey[0], transfer_key);
243         }
244       break;
245
246     default:
247       err = gpg_error (GPG_ERR_PUBKEY_ALGO);
248       break;
249     }
250
251   if (!err)
252     *r_key = s_skey;
253   return err;
254 }
255
256
257 /* Hash the passphrase and set the key. */
258 static gpg_error_t
259 hash_passphrase_and_set_key (const char *passphrase,
260                              gcry_cipher_hd_t hd, int protect_algo,
261                              int s2k_mode, int s2k_algo,
262                              byte *s2k_salt, u32 s2k_count)
263 {
264   gpg_error_t err;
265   unsigned char *key;
266   size_t keylen;
267
268   keylen = gcry_cipher_get_algo_keylen (protect_algo);
269   if (!keylen)
270     return gpg_error (GPG_ERR_INTERNAL);
271
272   key = xtrymalloc_secure (keylen);
273   if (!key)
274     return gpg_error_from_syserror ();
275
276   err = s2k_hash_passphrase (passphrase,
277                              s2k_algo, s2k_mode, s2k_salt, s2k_count,
278                              key, keylen);
279   if (!err)
280     err = gcry_cipher_setkey (hd, key, keylen);
281
282   xfree (key);
283   return err;
284 }
285
286
287 static u16
288 checksum (const unsigned char *p, unsigned int n)
289 {
290   u16 a;
291
292   for (a=0; n; n-- )
293     a += *p++;
294   return a;
295 }
296
297
298 /* Return the number of expected key parameters.  */
299 static void
300 get_npkey_nskey (int pubkey_algo, size_t *npkey, size_t *nskey)
301 {
302   switch (pubkey_algo)
303     {
304     case GCRY_PK_RSA:   *npkey = 2; *nskey = 6; break;
305     case GCRY_PK_ELG:   *npkey = 3; *nskey = 4; break;
306     case GCRY_PK_ELG_E: *npkey = 3; *nskey = 4; break;
307     case GCRY_PK_DSA:   *npkey = 4; *nskey = 5; break;
308     case GCRY_PK_ECC:   *npkey = 1; *nskey = 2; break;
309     default:            *npkey = 0; *nskey = 0; break;
310     }
311 }
312
313
314 /* Helper for do_unprotect.  PUBKEY_ALOGO is the gcrypt algo number.
315    On success R_NPKEY and R_NSKEY receive the number or parameters for
316    the algorithm PUBKEY_ALGO and R_SKEYLEN the used length of
317    SKEY.  */
318 static int
319 prepare_unprotect (int pubkey_algo, gcry_mpi_t *skey, size_t skeysize,
320                    int s2k_mode,
321                    unsigned int *r_npkey, unsigned int *r_nskey,
322                    unsigned int *r_skeylen)
323 {
324   size_t npkey, nskey, skeylen;
325   int i;
326
327   /* Count the actual number of MPIs is in the array and set the
328      remainder to NULL for easier processing later on.  */
329   for (skeylen = 0; skey[skeylen]; skeylen++)
330     ;
331   for (i=skeylen; i < skeysize; i++)
332     skey[i] = NULL;
333
334   /* Check some args.  */
335   if (s2k_mode == 1001)
336     {
337       /* Stub key.  */
338       log_info (_("secret key parts are not available\n"));
339       return gpg_error (GPG_ERR_UNUSABLE_SECKEY);
340     }
341
342   if (gcry_pk_test_algo (pubkey_algo))
343     {
344       log_info (_("public key algorithm %d (%s) is not supported\n"),
345                 pubkey_algo, gcry_pk_algo_name (pubkey_algo));
346       return gpg_error (GPG_ERR_PUBKEY_ALGO);
347     }
348
349   /* Get properties of the public key algorithm and do some
350      consistency checks.  Note that we need at least NPKEY+1 elements
351      in the SKEY array. */
352   get_npkey_nskey (pubkey_algo, &npkey, &nskey);
353   if (!npkey || !nskey || npkey >= nskey)
354     return gpg_error (GPG_ERR_INTERNAL);
355   if (skeylen <= npkey)
356     return gpg_error (GPG_ERR_MISSING_VALUE);
357   if (nskey+1 >= skeysize)
358     return gpg_error (GPG_ERR_BUFFER_TOO_SHORT);
359
360   /* Check that the public key parameters are all available and not
361      encrypted.  */
362   for (i=0; i < npkey; i++)
363     {
364       if (!skey[i] || gcry_mpi_get_flag (skey[i], GCRYMPI_FLAG_USER1))
365         return gpg_error (GPG_ERR_BAD_SECKEY);
366     }
367
368   if (r_npkey)
369     *r_npkey = npkey;
370   if (r_nskey)
371     *r_nskey = nskey;
372   if (r_skeylen)
373     *r_skeylen = skeylen;
374   return 0;
375 }
376
377
378 /* Note that this function modifies SKEY.  SKEYSIZE is the allocated
379    size of the array including the NULL item; this is used for a
380    bounds check.  On success a converted key is stored at R_KEY.  */
381 static int
382 do_unprotect (const char *passphrase,
383               int pkt_version, int pubkey_algo, int is_protected,
384               const char *curve, gcry_mpi_t *skey, size_t skeysize,
385               int protect_algo, void *protect_iv, size_t protect_ivlen,
386               int s2k_mode, int s2k_algo, byte *s2k_salt, u32 s2k_count,
387               u16 desired_csum, gcry_sexp_t *r_key)
388 {
389   gpg_error_t err;
390   unsigned int npkey, nskey, skeylen;
391   gcry_cipher_hd_t cipher_hd = NULL;
392   u16 actual_csum;
393   size_t nbytes;
394   int i;
395   gcry_mpi_t tmpmpi;
396
397   *r_key = NULL;
398
399   err = prepare_unprotect (pubkey_algo, skey, skeysize, s2k_mode,
400                            &npkey, &nskey, &skeylen);
401   if (err)
402     return err;
403
404   /* Check whether SKEY is at all protected.  If it is not protected
405      merely verify the checksum.  */
406   if (!is_protected)
407     {
408       actual_csum = 0;
409       for (i=npkey; i < nskey; i++)
410         {
411           if (!skey[i] || gcry_mpi_get_flag (skey[i], GCRYMPI_FLAG_USER1))
412             return gpg_error (GPG_ERR_BAD_SECKEY);
413
414           if (gcry_mpi_get_flag (skey[i], GCRYMPI_FLAG_OPAQUE))
415             {
416               unsigned int nbits;
417               const unsigned char *buffer;
418               buffer = gcry_mpi_get_opaque (skey[i], &nbits);
419               nbytes = (nbits+7)/8;
420               actual_csum += checksum (buffer, nbytes);
421             }
422           else
423             {
424               unsigned char *buffer;
425
426               err = gcry_mpi_aprint (GCRYMPI_FMT_PGP, &buffer, &nbytes,
427                                      skey[i]);
428               if (!err)
429                 actual_csum += checksum (buffer, nbytes);
430               xfree (buffer);
431             }
432           if (err)
433             return err;
434         }
435
436       if (actual_csum != desired_csum)
437         return gpg_error (GPG_ERR_CHECKSUM);
438
439       goto do_convert;
440     }
441
442
443   if (gcry_cipher_test_algo (protect_algo))
444     {
445       /* The algorithm numbers are Libgcrypt numbers but fortunately
446          the OpenPGP algorithm numbers map one-to-one to the Libgcrypt
447          numbers.  */
448       log_info (_("protection algorithm %d (%s) is not supported\n"),
449                 protect_algo, gnupg_cipher_algo_name (protect_algo));
450       return gpg_error (GPG_ERR_CIPHER_ALGO);
451     }
452
453   if (gcry_md_test_algo (s2k_algo))
454     {
455       log_info (_("protection hash algorithm %d (%s) is not supported\n"),
456                 s2k_algo, gcry_md_algo_name (s2k_algo));
457       return gpg_error (GPG_ERR_DIGEST_ALGO);
458     }
459
460   err = gcry_cipher_open (&cipher_hd, protect_algo,
461                           GCRY_CIPHER_MODE_CFB,
462                           (GCRY_CIPHER_SECURE
463                            | (protect_algo >= 100 ?
464                               0 : GCRY_CIPHER_ENABLE_SYNC)));
465   if (err)
466     {
467       log_error ("failed to open cipher_algo %d: %s\n",
468                  protect_algo, gpg_strerror (err));
469       return err;
470     }
471
472   err = hash_passphrase_and_set_key (passphrase, cipher_hd, protect_algo,
473                                      s2k_mode, s2k_algo, s2k_salt, s2k_count);
474   if (err)
475     {
476       gcry_cipher_close (cipher_hd);
477       return err;
478     }
479
480   gcry_cipher_setiv (cipher_hd, protect_iv, protect_ivlen);
481
482   actual_csum = 0;
483   if (pkt_version >= 4)
484     {
485       int ndata;
486       unsigned int ndatabits;
487       const unsigned char *p;
488       unsigned char *data;
489       u16 csum_pgp7 = 0;
490
491       if (!gcry_mpi_get_flag (skey[npkey], GCRYMPI_FLAG_OPAQUE ))
492         {
493           gcry_cipher_close (cipher_hd);
494           return gpg_error (GPG_ERR_BAD_SECKEY);
495         }
496       p = gcry_mpi_get_opaque (skey[npkey], &ndatabits);
497       ndata = (ndatabits+7)/8;
498
499       if (ndata > 1)
500         csum_pgp7 = buf16_to_u16 (p+ndata-2);
501       data = xtrymalloc_secure (ndata);
502       if (!data)
503         {
504           err = gpg_error_from_syserror ();
505           gcry_cipher_close (cipher_hd);
506           return err;
507         }
508       gcry_cipher_decrypt (cipher_hd, data, ndata, p, ndata);
509
510       p = data;
511       if (is_protected == 2)
512         {
513           /* This is the new SHA1 checksum method to detect tampering
514              with the key as used by the Klima/Rosa attack.  */
515           desired_csum = 0;
516           actual_csum = 1;  /* Default to bad checksum.  */
517
518           if (ndata < 20)
519             log_error ("not enough bytes for SHA-1 checksum\n");
520           else
521             {
522               gcry_md_hd_t h;
523
524               if (gcry_md_open (&h, GCRY_MD_SHA1, 1))
525                 BUG(); /* Algo not available. */
526               gcry_md_write (h, data, ndata - 20);
527               gcry_md_final (h);
528               if (!memcmp (gcry_md_read (h, GCRY_MD_SHA1), data+ndata-20, 20))
529                 actual_csum = 0; /* Digest does match.  */
530               gcry_md_close (h);
531             }
532         }
533       else
534         {
535           /* Old 16 bit checksum method.  */
536           if (ndata < 2)
537             {
538               log_error ("not enough bytes for checksum\n");
539               desired_csum = 0;
540               actual_csum = 1;  /* Mark checksum bad.  */
541             }
542           else
543             {
544               desired_csum = buf16_to_u16 (data+ndata-2);
545               actual_csum = checksum (data, ndata-2);
546               if (desired_csum != actual_csum)
547                 {
548                   /* This is a PGP 7.0.0 workaround */
549                   desired_csum = csum_pgp7; /* Take the encrypted one.  */
550                 }
551             }
552         }
553
554       /* Better check it here.  Otherwise the gcry_mpi_scan would fail
555          because the length may have an arbitrary value.  */
556       if (desired_csum == actual_csum)
557         {
558           for (i=npkey; i < nskey; i++ )
559             {
560               if (gcry_mpi_scan (&tmpmpi, GCRYMPI_FMT_PGP, p, ndata, &nbytes))
561                 {
562                   /* Checksum was okay, but not correctly decrypted.  */
563                   desired_csum = 0;
564                   actual_csum = 1;   /* Mark checksum bad.  */
565                   break;
566                 }
567               gcry_mpi_release (skey[i]);
568               skey[i] = tmpmpi;
569               ndata -= nbytes;
570               p += nbytes;
571             }
572           skey[i] = NULL;
573           skeylen = i;
574           assert (skeylen <= skeysize);
575
576           /* Note: at this point NDATA should be 2 for a simple
577              checksum or 20 for the sha1 digest.  */
578         }
579       xfree(data);
580     }
581   else /* Packet version <= 3.  */
582     {
583       unsigned char *buffer;
584
585       for (i = npkey; i < nskey; i++)
586         {
587           const unsigned char *p;
588           size_t ndata;
589           unsigned int ndatabits;
590
591           if (!skey[i] || !gcry_mpi_get_flag (skey[i], GCRYMPI_FLAG_OPAQUE))
592             {
593               gcry_cipher_close (cipher_hd);
594               return gpg_error (GPG_ERR_BAD_SECKEY);
595             }
596           p = gcry_mpi_get_opaque (skey[i], &ndatabits);
597           ndata = (ndatabits+7)/8;
598
599           if (!(ndata >= 2) || !(ndata == (buf16_to_ushort (p) + 7)/8 + 2))
600             {
601               gcry_cipher_close (cipher_hd);
602               return gpg_error (GPG_ERR_BAD_SECKEY);
603             }
604
605           buffer = xtrymalloc_secure (ndata);
606           if (!buffer)
607             {
608               err = gpg_error_from_syserror ();
609               gcry_cipher_close (cipher_hd);
610               return err;
611             }
612
613           gcry_cipher_sync (cipher_hd);
614           buffer[0] = p[0];
615           buffer[1] = p[1];
616           gcry_cipher_decrypt (cipher_hd, buffer+2, ndata-2, p+2, ndata-2);
617           actual_csum += checksum (buffer, ndata);
618           err = gcry_mpi_scan (&tmpmpi, GCRYMPI_FMT_PGP, buffer, ndata, &ndata);
619           xfree (buffer);
620           if (err)
621             {
622               /* Checksum was okay, but not correctly decrypted.  */
623               desired_csum = 0;
624               actual_csum = 1;   /* Mark checksum bad.  */
625               break;
626             }
627           gcry_mpi_release (skey[i]);
628           skey[i] = tmpmpi;
629         }
630     }
631   gcry_cipher_close (cipher_hd);
632
633   /* Now let's see whether we have used the correct passphrase. */
634   if (actual_csum != desired_csum)
635     return gpg_error (GPG_ERR_BAD_PASSPHRASE);
636
637  do_convert:
638   if (nskey != skeylen)
639     err = gpg_error (GPG_ERR_BAD_SECKEY);
640   else
641     err = convert_secret_key (r_key, pubkey_algo, skey, curve);
642   if (err)
643     return err;
644
645   /* The checksum may fail, thus we also check the key itself.  */
646   err = gcry_pk_testkey (*r_key);
647   if (err)
648     {
649       gcry_sexp_release (*r_key);
650       *r_key = NULL;
651       return gpg_error (GPG_ERR_BAD_PASSPHRASE);
652     }
653
654   return 0;
655 }
656
657
658 /* Callback function to try the unprotection from the passphrase query
659    code.  */
660 static int
661 try_do_unprotect_cb (struct pin_entry_info_s *pi)
662 {
663   gpg_error_t err;
664   struct try_do_unprotect_arg_s *arg = pi->check_cb_arg;
665
666   err = do_unprotect (pi->pin,
667                       arg->is_v4? 4:3,
668                       arg->pubkey_algo, arg->is_protected,
669                       arg->curve,
670                       arg->skey, arg->skeysize,
671                       arg->protect_algo, arg->iv, arg->ivlen,
672                       arg->s2k_mode, arg->s2k_algo,
673                       arg->s2k_salt, arg->s2k_count,
674                       arg->desired_csum, arg->r_key);
675   /* SKEY may be modified now, thus we need to re-compute SKEYIDX.  */
676   for (arg->skeyidx = 0; (arg->skeyidx < arg->skeysize
677                           && arg->skey[arg->skeyidx]); arg->skeyidx++)
678     ;
679   return err;
680 }
681
682
683 /* See convert_from_openpgp for the core of the description.  This
684    function adds an optional PASSPHRASE argument and uses this to
685    silently decrypt the key; CACHE_NONCE and R_PASSPHRASE must both be
686    NULL in this mode.  */
687 static gpg_error_t
688 convert_from_openpgp_main (ctrl_t ctrl, gcry_sexp_t s_pgp,
689                            unsigned char *grip, const char *prompt,
690                            const char *cache_nonce, const char *passphrase,
691                            unsigned char **r_key, char **r_passphrase)
692 {
693   gpg_error_t err;
694   int unattended;
695   int from_native;
696   gcry_sexp_t top_list;
697   gcry_sexp_t list = NULL;
698   const char *value;
699   size_t valuelen;
700   char *string;
701   int  idx;
702   int  is_v4, is_protected;
703   int  pubkey_algo;
704   int  protect_algo = 0;
705   char iv[16];
706   int  ivlen = 0;
707   int  s2k_mode = 0;
708   int  s2k_algo = 0;
709   byte s2k_salt[8];
710   u32  s2k_count = 0;
711   size_t npkey, nskey;
712   gcry_mpi_t skey[10];  /* We support up to 9 parameters.  */
713   char *curve = NULL;
714   u16 desired_csum;
715   int skeyidx = 0;
716   gcry_sexp_t s_skey = NULL;
717
718   *r_key = NULL;
719   if (r_passphrase)
720     *r_passphrase = NULL;
721   unattended = !r_passphrase;
722   from_native = (!cache_nonce && passphrase && !r_passphrase);
723
724   top_list = gcry_sexp_find_token (s_pgp, "openpgp-private-key", 0);
725   if (!top_list)
726     goto bad_seckey;
727
728   list = gcry_sexp_find_token (top_list, "version", 0);
729   if (!list)
730     goto bad_seckey;
731   value = gcry_sexp_nth_data (list, 1, &valuelen);
732   if (!value || valuelen != 1 || !(value[0] == '3' || value[0] == '4'))
733     goto bad_seckey;
734   is_v4 = (value[0] == '4');
735
736   gcry_sexp_release (list);
737   list = gcry_sexp_find_token (top_list, "protection", 0);
738   if (!list)
739     goto bad_seckey;
740   value = gcry_sexp_nth_data (list, 1, &valuelen);
741   if (!value)
742     goto bad_seckey;
743   if (valuelen == 4 && !memcmp (value, "sha1", 4))
744     is_protected = 2;
745   else if (valuelen == 3 && !memcmp (value, "sum", 3))
746     is_protected = 1;
747   else if (valuelen == 4 && !memcmp (value, "none", 4))
748     is_protected = 0;
749   else
750     goto bad_seckey;
751
752   if (is_protected)
753     {
754       string = gcry_sexp_nth_string (list, 2);
755       if (!string)
756         goto bad_seckey;
757       protect_algo = gcry_cipher_map_name (string);
758       xfree (string);
759
760       value = gcry_sexp_nth_data (list, 3, &valuelen);
761       if (!value || !valuelen || valuelen > sizeof iv)
762         goto bad_seckey;
763       memcpy (iv, value, valuelen);
764       ivlen = valuelen;
765
766       string = gcry_sexp_nth_string (list, 4);
767       if (!string)
768         goto bad_seckey;
769       s2k_mode = strtol (string, NULL, 10);
770       xfree (string);
771
772       string = gcry_sexp_nth_string (list, 5);
773       if (!string)
774         goto bad_seckey;
775       s2k_algo = gcry_md_map_name (string);
776       xfree (string);
777
778       value = gcry_sexp_nth_data (list, 6, &valuelen);
779       if (!value || !valuelen || valuelen > sizeof s2k_salt)
780         goto bad_seckey;
781       memcpy (s2k_salt, value, valuelen);
782
783       string = gcry_sexp_nth_string (list, 7);
784       if (!string)
785         goto bad_seckey;
786       s2k_count = strtoul (string, NULL, 10);
787       xfree (string);
788     }
789
790   gcry_sexp_release (list);
791   list = gcry_sexp_find_token (top_list, "algo", 0);
792   if (!list)
793     goto bad_seckey;
794   string = gcry_sexp_nth_string (list, 1);
795   if (!string)
796     goto bad_seckey;
797   pubkey_algo = gcry_pk_map_name (string);
798   xfree (string);
799
800   get_npkey_nskey (pubkey_algo, &npkey, &nskey);
801   if (!npkey || !nskey || npkey >= nskey)
802     goto bad_seckey;
803
804   if (npkey == 1) /* This is ECC */
805     {
806       gcry_sexp_release (list);
807       list = gcry_sexp_find_token (top_list, "curve", 0);
808       if (!list)
809         goto bad_seckey;
810       curve = gcry_sexp_nth_string (list, 1);
811       if (!curve)
812         goto bad_seckey;
813     }
814
815   gcry_sexp_release (list);
816   list = gcry_sexp_find_token (top_list, "skey", 0);
817   if (!list)
818     goto bad_seckey;
819   for (idx=0;;)
820     {
821       int is_enc;
822
823       value = gcry_sexp_nth_data (list, ++idx, &valuelen);
824       if (!value && skeyidx >= npkey)
825         break;  /* Ready.  */
826
827       /* Check for too many parameters.  Note that depending on the
828          protection mode and version number we may see less than NSKEY
829          (but at least NPKEY+1) parameters.  */
830       if (idx >= 2*nskey)
831         goto bad_seckey;
832       if (skeyidx >= DIM (skey)-1)
833         goto bad_seckey;
834
835       if (!value || valuelen != 1 || !(value[0] == '_' || value[0] == 'e'))
836         goto bad_seckey;
837       is_enc = (value[0] == 'e');
838       value = gcry_sexp_nth_data (list, ++idx, &valuelen);
839       if (!value || !valuelen)
840         goto bad_seckey;
841       if (is_enc || curve)
842         {
843           /* Encrypted parameters and ECC parameters need or can be
844              stored as opaque.  */
845           skey[skeyidx] = gcry_mpi_set_opaque_copy (NULL, value, valuelen*8);
846           if (!skey[skeyidx])
847             goto outofmem;
848           if (is_enc)
849             gcry_mpi_set_flag (skey[skeyidx], GCRYMPI_FLAG_USER1);
850         }
851       else
852         {
853           if (gcry_mpi_scan (skey + skeyidx, GCRYMPI_FMT_STD,
854                              value, valuelen, NULL))
855             goto bad_seckey;
856         }
857       skeyidx++;
858     }
859   skey[skeyidx++] = NULL;
860
861   gcry_sexp_release (list);
862   list = gcry_sexp_find_token (top_list, "csum", 0);
863   if (list)
864     {
865       string = gcry_sexp_nth_string (list, 1);
866       if (!string)
867         goto bad_seckey;
868       desired_csum = strtoul (string, NULL, 10);
869       xfree (string);
870     }
871   else
872     desired_csum = 0;
873
874
875   gcry_sexp_release (list); list = NULL;
876   gcry_sexp_release (top_list); top_list = NULL;
877
878 #if 0
879   log_debug ("XXX is_v4=%d\n", is_v4);
880   log_debug ("XXX pubkey_algo=%d\n", pubkey_algo);
881   log_debug ("XXX is_protected=%d\n", is_protected);
882   log_debug ("XXX protect_algo=%d\n", protect_algo);
883   log_printhex ("XXX iv", iv, ivlen);
884   log_debug ("XXX ivlen=%d\n", ivlen);
885   log_debug ("XXX s2k_mode=%d\n", s2k_mode);
886   log_debug ("XXX s2k_algo=%d\n", s2k_algo);
887   log_printhex ("XXX s2k_salt", s2k_salt, sizeof s2k_salt);
888   log_debug ("XXX s2k_count=%lu\n", (unsigned long)s2k_count);
889   log_debug ("XXX curve='%s'\n", curve);
890   for (idx=0; skey[idx]; idx++)
891     gcry_log_debugmpi (gcry_mpi_get_flag (skey[idx], GCRYMPI_FLAG_USER1)
892                        ? "skey(e)" : "skey(_)", skey[idx]);
893 #endif /*0*/
894
895   err = get_keygrip (pubkey_algo, curve, skey, grip);
896   if (err)
897     goto leave;
898
899   if (!from_native && !agent_key_available (grip))
900     {
901       err = gpg_error (GPG_ERR_EEXIST);
902       goto leave;
903     }
904
905   if (unattended && !from_native)
906     {
907       err = prepare_unprotect (pubkey_algo, skey, DIM(skey), s2k_mode,
908                                NULL, NULL, NULL);
909       if (err)
910         goto leave;
911
912       err = convert_transfer_key (&s_skey, pubkey_algo, skey, curve, s_pgp);
913       if (err)
914         goto leave;
915     }
916   else
917     {
918       struct pin_entry_info_s *pi;
919       struct try_do_unprotect_arg_s pi_arg;
920
921       pi = xtrycalloc_secure (1, sizeof (*pi) + MAX_PASSPHRASE_LEN + 1);
922       if (!pi)
923         return gpg_error_from_syserror ();
924       pi->max_length = MAX_PASSPHRASE_LEN + 1;
925       pi->min_digits = 0;  /* We want a real passphrase.  */
926       pi->max_digits = 16;
927       pi->max_tries = 3;
928       pi->check_cb = try_do_unprotect_cb;
929       pi->check_cb_arg = &pi_arg;
930       pi_arg.is_v4 = is_v4;
931       pi_arg.is_protected = is_protected;
932       pi_arg.pubkey_algo = pubkey_algo;
933       pi_arg.curve = curve;
934       pi_arg.protect_algo = protect_algo;
935       pi_arg.iv = iv;
936       pi_arg.ivlen = ivlen;
937       pi_arg.s2k_mode = s2k_mode;
938       pi_arg.s2k_algo = s2k_algo;
939       pi_arg.s2k_salt = s2k_salt;
940       pi_arg.s2k_count = s2k_count;
941       pi_arg.desired_csum = desired_csum;
942       pi_arg.skey = skey;
943       pi_arg.skeysize = DIM (skey);
944       pi_arg.skeyidx = skeyidx;
945       pi_arg.r_key = &s_skey;
946
947       err = gpg_error (GPG_ERR_BAD_PASSPHRASE);
948       if (!is_protected)
949         {
950           err = try_do_unprotect_cb (pi);
951         }
952       else if (cache_nonce)
953         {
954           char *cache_value;
955
956           cache_value = agent_get_cache (cache_nonce, CACHE_MODE_NONCE);
957           if (cache_value)
958             {
959               if (strlen (cache_value) < pi->max_length)
960                 strcpy (pi->pin, cache_value);
961               xfree (cache_value);
962             }
963           if (*pi->pin)
964             err = try_do_unprotect_cb (pi);
965         }
966       else if (from_native)
967         {
968           if (strlen (passphrase) < pi->max_length)
969             strcpy (pi->pin, passphrase);
970           err = try_do_unprotect_cb (pi);
971         }
972       if (gpg_err_code (err) == GPG_ERR_BAD_PASSPHRASE && !from_native)
973         err = agent_askpin (ctrl, prompt, NULL, NULL, pi, NULL, 0);
974       skeyidx = pi_arg.skeyidx;
975       if (!err && r_passphrase && is_protected)
976         {
977           *r_passphrase = xtrystrdup (pi->pin);
978           if (!*r_passphrase)
979             err = gpg_error_from_syserror ();
980         }
981       xfree (pi);
982       if (err)
983         goto leave;
984     }
985
986   /* Save some memory and get rid of the SKEY array now.  */
987   for (idx=0; idx < skeyidx; idx++)
988     gcry_mpi_release (skey[idx]);
989   skeyidx = 0;
990
991   /* Note that the padding is not required - we use it only because
992      that function allows us to create the result in secure memory.  */
993   err = make_canon_sexp_pad (s_skey, 1, r_key, NULL);
994
995  leave:
996   xfree (curve);
997   gcry_sexp_release (s_skey);
998   gcry_sexp_release (list);
999   gcry_sexp_release (top_list);
1000   for (idx=0; idx < skeyidx; idx++)
1001     gcry_mpi_release (skey[idx]);
1002   if (err && r_passphrase)
1003     {
1004       xfree (*r_passphrase);
1005       *r_passphrase = NULL;
1006     }
1007   return err;
1008
1009  bad_seckey:
1010   err = gpg_error (GPG_ERR_BAD_SECKEY);
1011   goto leave;
1012
1013  outofmem:
1014   err = gpg_error (GPG_ERR_ENOMEM);
1015   goto leave;
1016
1017 }
1018
1019
1020 /* Convert an OpenPGP transfer key into our internal format.  Before
1021    asking for a passphrase we check whether the key already exists in
1022    our key storage.  S_PGP is the OpenPGP key in transfer format.  If
1023    CACHE_NONCE is given the passphrase will be looked up in the cache.
1024    On success R_KEY will receive a canonical encoded S-expression with
1025    the unprotected key in our internal format; the caller needs to
1026    release that memory.  The passphrase used to decrypt the OpenPGP
1027    key will be returned at R_PASSPHRASE; the caller must release this
1028    passphrase.  If R_PASSPHRASE is NULL the unattended conversion mode
1029    will be used which uses the openpgp-native protection format for
1030    the key.  The keygrip will be stored at the 20 byte buffer pointed
1031    to by GRIP.  On error NULL is stored at all return arguments.  */
1032 gpg_error_t
1033 convert_from_openpgp (ctrl_t ctrl, gcry_sexp_t s_pgp,
1034                       unsigned char *grip, const char *prompt,
1035                       const char *cache_nonce,
1036                       unsigned char **r_key, char **r_passphrase)
1037 {
1038   return convert_from_openpgp_main (ctrl, s_pgp, grip, prompt,
1039                                     cache_nonce, NULL,
1040                                     r_key, r_passphrase);
1041 }
1042
1043 /* This function is called by agent_unprotect to re-protect an
1044    openpgp-native protected private-key into the standard private-key
1045    protection format.  */
1046 gpg_error_t
1047 convert_from_openpgp_native (ctrl_t ctrl,
1048                              gcry_sexp_t s_pgp, const char *passphrase,
1049                              unsigned char **r_key)
1050 {
1051   gpg_error_t err;
1052   unsigned char grip[20];
1053
1054   if (!passphrase)
1055     return gpg_error (GPG_ERR_INTERNAL);
1056
1057   err = convert_from_openpgp_main (ctrl, s_pgp, grip, NULL,
1058                                    NULL, passphrase,
1059                                    r_key, NULL);
1060
1061   /* On success try to re-write the key.  */
1062   if (!err)
1063     {
1064       if (*passphrase)
1065         {
1066           unsigned char *protectedkey = NULL;
1067           size_t protectedkeylen;
1068
1069           if (!agent_protect (*r_key, passphrase,
1070                               &protectedkey, &protectedkeylen,
1071                               ctrl->s2k_count))
1072             agent_write_private_key (grip, protectedkey, protectedkeylen, 1);
1073           xfree (protectedkey);
1074         }
1075       else
1076         {
1077           /* Empty passphrase: write key without protection.  */
1078           agent_write_private_key (grip,
1079                                    *r_key,
1080                                    gcry_sexp_canon_len (*r_key, 0, NULL,NULL),
1081                                    1);
1082         }
1083     }
1084
1085   return err;
1086 }
1087
1088
1089 /* Given an ARRAY of mpis with the key parameters, protect the secret
1090    parameters in that array and replace them by one opaque encoded
1091    mpi.  NPKEY is the number of public key parameters and NSKEY is
1092    the number of secret key parameters (including the public ones).
1093    On success the array will have NPKEY+1 elements.  */
1094 static gpg_error_t
1095 apply_protection (gcry_mpi_t *array, int npkey, int nskey,
1096                   const char *passphrase,
1097                   int protect_algo, void *protect_iv, size_t protect_ivlen,
1098                   int s2k_mode, int s2k_algo, byte *s2k_salt, u32 s2k_count)
1099 {
1100   gpg_error_t err;
1101   int i, j;
1102   gcry_cipher_hd_t cipherhd;
1103   unsigned char *bufarr[10];
1104   size_t narr[10];
1105   unsigned int nbits[10];
1106   int ndata;
1107   unsigned char *p, *data;
1108
1109   assert (npkey < nskey);
1110   assert (nskey < DIM (bufarr));
1111
1112   /* Collect only the secret key parameters into BUFARR et al and
1113      compute the required size of the data buffer.  */
1114   ndata = 20; /* Space for the SHA-1 checksum.  */
1115   for (i = npkey, j = 0; i < nskey; i++, j++ )
1116     {
1117       if (gcry_mpi_get_flag (array[i], GCRYMPI_FLAG_OPAQUE))
1118         {
1119           const unsigned char *s;
1120           unsigned int n;
1121
1122           s = gcry_mpi_get_opaque (array[i], &n);
1123           if (!s)
1124             {
1125               s = "";
1126               n = 0;
1127             }
1128           /* Strip leading zero bits.  */
1129           for (; n >= 8 && !*s; s++, n -= 8)
1130             ;
1131           if (n >= 8 && !(*s & 0x80))
1132             if (--n >= 7 && !(*s & 0x40))
1133               if (--n >= 6 && !(*s & 0x20))
1134                 if (--n >= 5 && !(*s & 0x10))
1135                   if (--n >= 4 && !(*s & 0x08))
1136                     if (--n >= 3 && !(*s & 0x04))
1137                       if (--n >= 2 && !(*s & 0x02))
1138                         if (--n >= 1 && !(*s & 0x01))
1139                           --n;
1140
1141           nbits[j] = n;
1142           n = (n+7)/8;
1143           narr[j] = n;
1144           bufarr[j] = (gcry_is_secure (s)? xtrymalloc_secure (n?n:1)
1145                        /* */             : xtrymalloc (n?n:1));
1146           if (!bufarr[j])
1147             {
1148               err = gpg_error_from_syserror ();
1149               for (i = 0; i < j; i++)
1150                 xfree (bufarr[i]);
1151               return err;
1152             }
1153           memcpy (bufarr[j], s, n);
1154         }
1155       else
1156         {
1157           err = gcry_mpi_aprint (GCRYMPI_FMT_USG, bufarr+j, narr+j, array[i]);
1158           if (err)
1159             {
1160               for (i = 0; i < j; i++)
1161                 xfree (bufarr[i]);
1162               return err;
1163             }
1164           nbits[j] = gcry_mpi_get_nbits (array[i]);
1165         }
1166       ndata += 2 + narr[j];
1167     }
1168
1169   /* Allocate data buffer and stuff it with the secret key parameters.  */
1170   data = xtrymalloc_secure (ndata);
1171   if (!data)
1172     {
1173       err = gpg_error_from_syserror ();
1174       for (i = 0; i < (nskey-npkey); i++ )
1175         xfree (bufarr[i]);
1176       return err;
1177     }
1178   p = data;
1179   for (i = 0; i < (nskey-npkey); i++ )
1180     {
1181       *p++ = nbits[i] >> 8 ;
1182       *p++ = nbits[i];
1183       memcpy (p, bufarr[i], narr[i]);
1184       p += narr[i];
1185       xfree (bufarr[i]);
1186       bufarr[i] = NULL;
1187     }
1188   assert (p == data + ndata - 20);
1189
1190   /* Append a hash of the secret key parameters.  */
1191   gcry_md_hash_buffer (GCRY_MD_SHA1, p, data, ndata - 20);
1192
1193   /* Encrypt it.  */
1194   err = gcry_cipher_open (&cipherhd, protect_algo,
1195                           GCRY_CIPHER_MODE_CFB, GCRY_CIPHER_SECURE);
1196   if (!err)
1197     err = hash_passphrase_and_set_key (passphrase, cipherhd, protect_algo,
1198                                        s2k_mode, s2k_algo, s2k_salt, s2k_count);
1199   if (!err)
1200     err = gcry_cipher_setiv (cipherhd, protect_iv, protect_ivlen);
1201   if (!err)
1202     err = gcry_cipher_encrypt (cipherhd, data, ndata, NULL, 0);
1203   gcry_cipher_close (cipherhd);
1204   if (err)
1205     {
1206       xfree (data);
1207       return err;
1208     }
1209
1210   /* Replace the secret key parameters in the array by one opaque value.  */
1211   for (i = npkey; i < nskey; i++ )
1212     {
1213       gcry_mpi_release (array[i]);
1214       array[i] = NULL;
1215     }
1216   array[npkey] = gcry_mpi_set_opaque (NULL, data, ndata*8);
1217   return 0;
1218 }
1219
1220
1221 /*
1222  * Examining S_KEY in S-Expression and extract data.
1223  * When REQ_PRIVATE_KEY_DATA == 1, S_KEY's CAR should be 'private-key',
1224  * but it also allows shadowed or protected versions.
1225  * On success, it returns 0, otherwise error number.
1226  * R_ALGONAME is static string which is no need to free by caller.
1227  * R_NPKEY is pointer to number of public key data.
1228  * R_NSKEY is pointer to number of private key data.
1229  * R_ELEMS is static string which is no need to free by caller.
1230  * ARRAY contains public and private key data.
1231  * ARRAYSIZE is the allocated size of the array for cross-checking.
1232  * R_CURVE is pointer to S-Expression of the curve (can be NULL).
1233  * R_FLAGS is pointer to S-Expression of the flags (can be NULL).
1234  */
1235 gpg_error_t
1236 extract_private_key (gcry_sexp_t s_key, int req_private_key_data,
1237                      const char **r_algoname, int *r_npkey, int *r_nskey,
1238                      const char **r_elems,
1239                      gcry_mpi_t *array, int arraysize,
1240                      gcry_sexp_t *r_curve, gcry_sexp_t *r_flags)
1241 {
1242   gpg_error_t err;
1243   gcry_sexp_t list, l2;
1244   char *name;
1245   const char *algoname, *format;
1246   int npkey, nskey;
1247   gcry_sexp_t curve = NULL;
1248   gcry_sexp_t flags = NULL;
1249
1250   *r_curve = NULL;
1251   *r_flags = NULL;
1252
1253   if (!req_private_key_data)
1254     {
1255       list = gcry_sexp_find_token (s_key, "shadowed-private-key", 0 );
1256       if (!list)
1257         list = gcry_sexp_find_token (s_key, "protected-private-key", 0 );
1258       if (!list)
1259         list = gcry_sexp_find_token (s_key, "private-key", 0 );
1260     }
1261   else
1262     list = gcry_sexp_find_token (s_key, "private-key", 0);
1263
1264   if (!list)
1265     {
1266       log_error ("invalid private key format\n");
1267       return gpg_error (GPG_ERR_BAD_SECKEY);
1268     }
1269
1270   l2 = gcry_sexp_cadr (list);
1271   gcry_sexp_release (list);
1272   list = l2;
1273   name = gcry_sexp_nth_string (list, 0);
1274   if (!name)
1275     {
1276       gcry_sexp_release (list);
1277       return gpg_error (GPG_ERR_INV_OBJ); /* Invalid structure of object. */
1278     }
1279
1280   if (arraysize < 7)
1281     BUG ();
1282
1283   /* Map NAME to a name as used by Libgcrypt.  We do not use the
1284      Libgcrypt function here because we need a lowercase name and
1285      require special treatment for some algorithms.  */
1286   strlwr (name);
1287   if (!strcmp (name, "rsa"))
1288     {
1289       algoname = "rsa";
1290       format = "ned?p?q?u?";
1291       npkey = 2;
1292       nskey = 6;
1293       err = gcry_sexp_extract_param (list, NULL, format,
1294                                      array+0, array+1, array+2, array+3,
1295                                      array+4, array+5, NULL);
1296     }
1297   else if (!strcmp (name, "elg"))
1298     {
1299       algoname = "elg";
1300       format = "pgyx?";
1301       npkey = 3;
1302       nskey = 4;
1303       err = gcry_sexp_extract_param (list, NULL, format,
1304                                      array+0, array+1, array+2, array+3,
1305                                      NULL);
1306     }
1307   else if (!strcmp (name, "dsa"))
1308     {
1309       algoname = "dsa";
1310       format = "pqgyx?";
1311       npkey = 4;
1312       nskey = 5;
1313       err = gcry_sexp_extract_param (list, NULL, format,
1314                                      array+0, array+1, array+2, array+3,
1315                                      array+4, NULL);
1316     }
1317   else if (!strcmp (name, "ecc"))
1318     {
1319       algoname = "ecc";
1320       format = "/qd?";
1321       npkey = 1;
1322       nskey = 2;
1323       curve = gcry_sexp_find_token (list, "curve", 0);
1324       flags = gcry_sexp_find_token (list, "flags", 0);
1325       err = gcry_sexp_extract_param (list, NULL, format,
1326                                      array+0, array+1, NULL);
1327       if (flags)
1328         {
1329           gcry_sexp_t param = gcry_sexp_find_token (flags, "param", 0);
1330           if (param)
1331             {
1332               gcry_sexp_release (param);
1333               array[6] = array[0];
1334               array[7] = array[1];
1335               err = gcry_sexp_extract_param (list, NULL, "pabgnh?",
1336                                              array+0, array+1, array+2, array+3,
1337                                              array+4, array+5, NULL);
1338               if (array[5] == NULL)
1339                 {
1340                   array[5] = GCRYMPI_CONST_ONE;
1341                   npkey += 6;
1342                   nskey += 6;
1343                 }
1344               format = "pabgnhqd?";
1345             }
1346         }
1347     }
1348   else if (!strcmp (name, "ecdsa"))
1349     {
1350       algoname = "ecdsa";
1351       format = "pabgnqd?";
1352       npkey = 6;
1353       nskey = 7;
1354       err = gcry_sexp_extract_param (list, NULL, format,
1355                                      array+0, array+1, array+2, array+3,
1356                                      array+4, array+5, array+6, NULL);
1357     }
1358   else if (!strcmp (name, "ecdh"))
1359     {
1360       algoname = "ecdh";
1361       format = "pabgnqd?";
1362       npkey = 6;
1363       nskey= 7;
1364       err = gcry_sexp_extract_param (list, NULL, format,
1365                                      array+0, array+1, array+2, array+3,
1366                                      array+4, array+5, array+6, NULL);
1367     }
1368   else
1369     {
1370       err = gpg_error (GPG_ERR_PUBKEY_ALGO);
1371     }
1372   xfree (name);
1373   gcry_sexp_release (list);
1374   if (err)
1375     {
1376       gcry_sexp_release (curve);
1377       gcry_sexp_release (flags);
1378       return err;
1379     }
1380   else
1381     {
1382       *r_algoname = algoname;
1383       if (r_elems)
1384         {
1385           if (format[0] == '/') /* It is opaque data qualifier, skip it.  */
1386             *r_elems = format+1;
1387           else
1388             *r_elems = format;
1389         }
1390       *r_npkey = npkey;
1391       if (r_nskey)
1392         *r_nskey = nskey;
1393       *r_curve = curve;
1394       *r_flags = flags;
1395
1396       return 0;
1397     }
1398 }
1399
1400 /* Convert our key S_KEY into an OpenPGP key transfer format.  On
1401    success a canonical encoded S-expression is stored at R_TRANSFERKEY
1402    and its length at R_TRANSFERKEYLEN; this S-expression is also
1403    padded to a multiple of 64 bits.  */
1404 gpg_error_t
1405 convert_to_openpgp (ctrl_t ctrl, gcry_sexp_t s_key, const char *passphrase,
1406                     unsigned char **r_transferkey, size_t *r_transferkeylen)
1407 {
1408   gpg_error_t err;
1409   const char *algoname;
1410   int npkey, nskey;
1411   gcry_mpi_t array[10];
1412   gcry_sexp_t curve = NULL;
1413   gcry_sexp_t flags = NULL;
1414   char protect_iv[16];
1415   char salt[8];
1416   unsigned long s2k_count;
1417   int i, j;
1418
1419   (void)ctrl;
1420
1421   *r_transferkey = NULL;
1422
1423   for (i=0; i < DIM (array); i++)
1424     array[i] = NULL;
1425
1426   err = extract_private_key (s_key, 1, &algoname, &npkey, &nskey, NULL,
1427                              array, DIM (array), &curve, &flags);
1428   if (err)
1429     return err;
1430
1431   gcry_create_nonce (protect_iv, sizeof protect_iv);
1432   gcry_create_nonce (salt, sizeof salt);
1433   /* We need to use the encoded S2k count.  It is not possible to
1434      encode it after it has been used because the encoding procedure
1435      may round the value up.  */
1436   s2k_count = get_standard_s2k_count_rfc4880 ();
1437   err = apply_protection (array, npkey, nskey, passphrase,
1438                           GCRY_CIPHER_AES, protect_iv, sizeof protect_iv,
1439                           3, GCRY_MD_SHA1, salt, s2k_count);
1440   /* Turn it into the transfer key S-expression.  Note that we always
1441      return a protected key.  */
1442   if (!err)
1443     {
1444       char countbuf[35];
1445       membuf_t mbuf;
1446       void *format_args[10+2];
1447       gcry_sexp_t tmpkey;
1448       gcry_sexp_t tmpsexp = NULL;
1449
1450       snprintf (countbuf, sizeof countbuf, "%lu", s2k_count);
1451
1452       init_membuf (&mbuf, 50);
1453       put_membuf_str (&mbuf, "(skey");
1454       for (i=j=0; i < npkey; i++)
1455         {
1456           put_membuf_str (&mbuf, " _ %m");
1457           format_args[j++] = array + i;
1458         }
1459       put_membuf_str (&mbuf, " e %m");
1460       format_args[j++] = array + npkey;
1461       put_membuf_str (&mbuf, ")\n");
1462       put_membuf (&mbuf, "", 1);
1463
1464       tmpkey = NULL;
1465       {
1466         char *format = get_membuf (&mbuf, NULL);
1467         if (!format)
1468           err = gpg_error_from_syserror ();
1469         else
1470           err = gcry_sexp_build_array (&tmpkey, NULL, format, format_args);
1471         xfree (format);
1472       }
1473       if (!err)
1474         err = gcry_sexp_build (&tmpsexp, NULL,
1475                                "(openpgp-private-key\n"
1476                                " (version 1:4)\n"
1477                                " (algo %s)\n"
1478                                " %S%S\n"
1479                                " (protection sha1 aes %b 1:3 sha1 %b %s))\n",
1480                                algoname,
1481                                curve,
1482                                tmpkey,
1483                                (int)sizeof protect_iv, protect_iv,
1484                                (int)sizeof salt, salt,
1485                                countbuf);
1486       gcry_sexp_release (tmpkey);
1487       if (!err)
1488         err = make_canon_sexp_pad (tmpsexp, 0, r_transferkey, r_transferkeylen);
1489       gcry_sexp_release (tmpsexp);
1490     }
1491
1492   for (i=0; i < DIM (array); i++)
1493     gcry_mpi_release (array[i]);
1494   gcry_sexp_release (curve);
1495   gcry_sexp_release (flags);
1496
1497   return err;
1498 }