]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - sshkey.c
Vendor import of OpenSSH 6.9p1.
[FreeBSD/FreeBSD.git] / sshkey.c
1 /* $OpenBSD: sshkey.c,v 1.19 2015/05/21 04:55:51 djm Exp $ */
2 /*
3  * Copyright (c) 2000, 2001 Markus Friedl.  All rights reserved.
4  * Copyright (c) 2008 Alexander von Gernler.  All rights reserved.
5  * Copyright (c) 2010,2011 Damien Miller.  All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  * 1. Redistributions of source code must retain the above copyright
11  *    notice, this list of conditions and the following disclaimer.
12  * 2. Redistributions in binary form must reproduce the above copyright
13  *    notice, this list of conditions and the following disclaimer in the
14  *    documentation and/or other materials provided with the distribution.
15  *
16  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
17  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
18  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
19  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
20  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
21  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
22  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
23  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
25  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26  */
27
28 #include "includes.h"
29
30 #include <sys/param.h>  /* MIN MAX */
31 #include <sys/types.h>
32 #include <netinet/in.h>
33
34 #ifdef WITH_OPENSSL
35 #include <openssl/evp.h>
36 #include <openssl/err.h>
37 #include <openssl/pem.h>
38 #endif
39
40 #include "crypto_api.h"
41
42 #include <errno.h>
43 #include <limits.h>
44 #include <stdio.h>
45 #include <string.h>
46 #include <resolv.h>
47 #ifdef HAVE_UTIL_H
48 #include <util.h>
49 #endif /* HAVE_UTIL_H */
50
51 #include "ssh2.h"
52 #include "ssherr.h"
53 #include "misc.h"
54 #include "sshbuf.h"
55 #include "rsa.h"
56 #include "cipher.h"
57 #include "digest.h"
58 #define SSHKEY_INTERNAL
59 #include "sshkey.h"
60 #include "match.h"
61
62 /* openssh private key file format */
63 #define MARK_BEGIN              "-----BEGIN OPENSSH PRIVATE KEY-----\n"
64 #define MARK_END                "-----END OPENSSH PRIVATE KEY-----\n"
65 #define MARK_BEGIN_LEN          (sizeof(MARK_BEGIN) - 1)
66 #define MARK_END_LEN            (sizeof(MARK_END) - 1)
67 #define KDFNAME                 "bcrypt"
68 #define AUTH_MAGIC              "openssh-key-v1"
69 #define SALT_LEN                16
70 #define DEFAULT_CIPHERNAME      "aes256-cbc"
71 #define DEFAULT_ROUNDS          16
72
73 /* Version identification string for SSH v1 identity files. */
74 #define LEGACY_BEGIN            "SSH PRIVATE KEY FILE FORMAT 1.1\n"
75
76 static int sshkey_from_blob_internal(struct sshbuf *buf,
77     struct sshkey **keyp, int allow_cert);
78
79 /* Supported key types */
80 struct keytype {
81         const char *name;
82         const char *shortname;
83         int type;
84         int nid;
85         int cert;
86 };
87 static const struct keytype keytypes[] = {
88         { "ssh-ed25519", "ED25519", KEY_ED25519, 0, 0 },
89         { "ssh-ed25519-cert-v01@openssh.com", "ED25519-CERT",
90             KEY_ED25519_CERT, 0, 1 },
91 #ifdef WITH_OPENSSL
92         { NULL, "RSA1", KEY_RSA1, 0, 0 },
93         { "ssh-rsa", "RSA", KEY_RSA, 0, 0 },
94         { "ssh-dss", "DSA", KEY_DSA, 0, 0 },
95 # ifdef OPENSSL_HAS_ECC
96         { "ecdsa-sha2-nistp256", "ECDSA", KEY_ECDSA, NID_X9_62_prime256v1, 0 },
97         { "ecdsa-sha2-nistp384", "ECDSA", KEY_ECDSA, NID_secp384r1, 0 },
98 #  ifdef OPENSSL_HAS_NISTP521
99         { "ecdsa-sha2-nistp521", "ECDSA", KEY_ECDSA, NID_secp521r1, 0 },
100 #  endif /* OPENSSL_HAS_NISTP521 */
101 # endif /* OPENSSL_HAS_ECC */
102         { "ssh-rsa-cert-v01@openssh.com", "RSA-CERT", KEY_RSA_CERT, 0, 1 },
103         { "ssh-dss-cert-v01@openssh.com", "DSA-CERT", KEY_DSA_CERT, 0, 1 },
104 # ifdef OPENSSL_HAS_ECC
105         { "ecdsa-sha2-nistp256-cert-v01@openssh.com", "ECDSA-CERT",
106             KEY_ECDSA_CERT, NID_X9_62_prime256v1, 1 },
107         { "ecdsa-sha2-nistp384-cert-v01@openssh.com", "ECDSA-CERT",
108             KEY_ECDSA_CERT, NID_secp384r1, 1 },
109 #  ifdef OPENSSL_HAS_NISTP521
110         { "ecdsa-sha2-nistp521-cert-v01@openssh.com", "ECDSA-CERT",
111             KEY_ECDSA_CERT, NID_secp521r1, 1 },
112 #  endif /* OPENSSL_HAS_NISTP521 */
113 # endif /* OPENSSL_HAS_ECC */
114         { "ssh-rsa-cert-v00@openssh.com", "RSA-CERT-V00",
115             KEY_RSA_CERT_V00, 0, 1 },
116         { "ssh-dss-cert-v00@openssh.com", "DSA-CERT-V00",
117             KEY_DSA_CERT_V00, 0, 1 },
118 #endif /* WITH_OPENSSL */
119         { NULL, NULL, -1, -1, 0 }
120 };
121
122 const char *
123 sshkey_type(const struct sshkey *k)
124 {
125         const struct keytype *kt;
126
127         for (kt = keytypes; kt->type != -1; kt++) {
128                 if (kt->type == k->type)
129                         return kt->shortname;
130         }
131         return "unknown";
132 }
133
134 static const char *
135 sshkey_ssh_name_from_type_nid(int type, int nid)
136 {
137         const struct keytype *kt;
138
139         for (kt = keytypes; kt->type != -1; kt++) {
140                 if (kt->type == type && (kt->nid == 0 || kt->nid == nid))
141                         return kt->name;
142         }
143         return "ssh-unknown";
144 }
145
146 int
147 sshkey_type_is_cert(int type)
148 {
149         const struct keytype *kt;
150
151         for (kt = keytypes; kt->type != -1; kt++) {
152                 if (kt->type == type)
153                         return kt->cert;
154         }
155         return 0;
156 }
157
158 const char *
159 sshkey_ssh_name(const struct sshkey *k)
160 {
161         return sshkey_ssh_name_from_type_nid(k->type, k->ecdsa_nid);
162 }
163
164 const char *
165 sshkey_ssh_name_plain(const struct sshkey *k)
166 {
167         return sshkey_ssh_name_from_type_nid(sshkey_type_plain(k->type),
168             k->ecdsa_nid);
169 }
170
171 int
172 sshkey_type_from_name(const char *name)
173 {
174         const struct keytype *kt;
175
176         for (kt = keytypes; kt->type != -1; kt++) {
177                 /* Only allow shortname matches for plain key types */
178                 if ((kt->name != NULL && strcmp(name, kt->name) == 0) ||
179                     (!kt->cert && strcasecmp(kt->shortname, name) == 0))
180                         return kt->type;
181         }
182         return KEY_UNSPEC;
183 }
184
185 int
186 sshkey_ecdsa_nid_from_name(const char *name)
187 {
188         const struct keytype *kt;
189
190         for (kt = keytypes; kt->type != -1; kt++) {
191                 if (kt->type != KEY_ECDSA && kt->type != KEY_ECDSA_CERT)
192                         continue;
193                 if (kt->name != NULL && strcmp(name, kt->name) == 0)
194                         return kt->nid;
195         }
196         return -1;
197 }
198
199 char *
200 key_alg_list(int certs_only, int plain_only)
201 {
202         char *tmp, *ret = NULL;
203         size_t nlen, rlen = 0;
204         const struct keytype *kt;
205
206         for (kt = keytypes; kt->type != -1; kt++) {
207                 if (kt->name == NULL)
208                         continue;
209                 if ((certs_only && !kt->cert) || (plain_only && kt->cert))
210                         continue;
211                 if (ret != NULL)
212                         ret[rlen++] = '\n';
213                 nlen = strlen(kt->name);
214                 if ((tmp = realloc(ret, rlen + nlen + 2)) == NULL) {
215                         free(ret);
216                         return NULL;
217                 }
218                 ret = tmp;
219                 memcpy(ret + rlen, kt->name, nlen + 1);
220                 rlen += nlen;
221         }
222         return ret;
223 }
224
225 int
226 sshkey_names_valid2(const char *names, int allow_wildcard)
227 {
228         char *s, *cp, *p;
229         const struct keytype *kt;
230         int type;
231
232         if (names == NULL || strcmp(names, "") == 0)
233                 return 0;
234         if ((s = cp = strdup(names)) == NULL)
235                 return 0;
236         for ((p = strsep(&cp, ",")); p && *p != '\0';
237             (p = strsep(&cp, ","))) {
238                 type = sshkey_type_from_name(p);
239                 if (type == KEY_RSA1) {
240                         free(s);
241                         return 0;
242                 }
243                 if (type == KEY_UNSPEC) {
244                         if (allow_wildcard) {
245                                 /*
246                                  * Try matching key types against the string.
247                                  * If any has a positive or negative match then
248                                  * the component is accepted.
249                                  */
250                                 for (kt = keytypes; kt->type != -1; kt++) {
251                                         if (kt->type == KEY_RSA1)
252                                                 continue;
253                                         if (match_pattern_list(kt->name,
254                                             p, 0) != 0)
255                                                 break;
256                                 }
257                                 if (kt->type != -1)
258                                         continue;
259                         }
260                         free(s);
261                         return 0;
262                 }
263         }
264         free(s);
265         return 1;
266 }
267
268 u_int
269 sshkey_size(const struct sshkey *k)
270 {
271         switch (k->type) {
272 #ifdef WITH_OPENSSL
273         case KEY_RSA1:
274         case KEY_RSA:
275         case KEY_RSA_CERT_V00:
276         case KEY_RSA_CERT:
277                 return BN_num_bits(k->rsa->n);
278         case KEY_DSA:
279         case KEY_DSA_CERT_V00:
280         case KEY_DSA_CERT:
281                 return BN_num_bits(k->dsa->p);
282         case KEY_ECDSA:
283         case KEY_ECDSA_CERT:
284                 return sshkey_curve_nid_to_bits(k->ecdsa_nid);
285 #endif /* WITH_OPENSSL */
286         case KEY_ED25519:
287         case KEY_ED25519_CERT:
288                 return 256;     /* XXX */
289         }
290         return 0;
291 }
292
293 int
294 sshkey_cert_is_legacy(const struct sshkey *k)
295 {
296         switch (k->type) {
297         case KEY_DSA_CERT_V00:
298         case KEY_RSA_CERT_V00:
299                 return 1;
300         default:
301                 return 0;
302         }
303 }
304
305 static int
306 sshkey_type_is_valid_ca(int type)
307 {
308         switch (type) {
309         case KEY_RSA:
310         case KEY_DSA:
311         case KEY_ECDSA:
312         case KEY_ED25519:
313                 return 1;
314         default:
315                 return 0;
316         }
317 }
318
319 int
320 sshkey_is_cert(const struct sshkey *k)
321 {
322         if (k == NULL)
323                 return 0;
324         return sshkey_type_is_cert(k->type);
325 }
326
327 /* Return the cert-less equivalent to a certified key type */
328 int
329 sshkey_type_plain(int type)
330 {
331         switch (type) {
332         case KEY_RSA_CERT_V00:
333         case KEY_RSA_CERT:
334                 return KEY_RSA;
335         case KEY_DSA_CERT_V00:
336         case KEY_DSA_CERT:
337                 return KEY_DSA;
338         case KEY_ECDSA_CERT:
339                 return KEY_ECDSA;
340         case KEY_ED25519_CERT:
341                 return KEY_ED25519;
342         default:
343                 return type;
344         }
345 }
346
347 #ifdef WITH_OPENSSL
348 /* XXX: these are really begging for a table-driven approach */
349 int
350 sshkey_curve_name_to_nid(const char *name)
351 {
352         if (strcmp(name, "nistp256") == 0)
353                 return NID_X9_62_prime256v1;
354         else if (strcmp(name, "nistp384") == 0)
355                 return NID_secp384r1;
356 # ifdef OPENSSL_HAS_NISTP521
357         else if (strcmp(name, "nistp521") == 0)
358                 return NID_secp521r1;
359 # endif /* OPENSSL_HAS_NISTP521 */
360         else
361                 return -1;
362 }
363
364 u_int
365 sshkey_curve_nid_to_bits(int nid)
366 {
367         switch (nid) {
368         case NID_X9_62_prime256v1:
369                 return 256;
370         case NID_secp384r1:
371                 return 384;
372 # ifdef OPENSSL_HAS_NISTP521
373         case NID_secp521r1:
374                 return 521;
375 # endif /* OPENSSL_HAS_NISTP521 */
376         default:
377                 return 0;
378         }
379 }
380
381 int
382 sshkey_ecdsa_bits_to_nid(int bits)
383 {
384         switch (bits) {
385         case 256:
386                 return NID_X9_62_prime256v1;
387         case 384:
388                 return NID_secp384r1;
389 # ifdef OPENSSL_HAS_NISTP521
390         case 521:
391                 return NID_secp521r1;
392 # endif /* OPENSSL_HAS_NISTP521 */
393         default:
394                 return -1;
395         }
396 }
397
398 const char *
399 sshkey_curve_nid_to_name(int nid)
400 {
401         switch (nid) {
402         case NID_X9_62_prime256v1:
403                 return "nistp256";
404         case NID_secp384r1:
405                 return "nistp384";
406 # ifdef OPENSSL_HAS_NISTP521
407         case NID_secp521r1:
408                 return "nistp521";
409 # endif /* OPENSSL_HAS_NISTP521 */
410         default:
411                 return NULL;
412         }
413 }
414
415 int
416 sshkey_ec_nid_to_hash_alg(int nid)
417 {
418         int kbits = sshkey_curve_nid_to_bits(nid);
419
420         if (kbits <= 0)
421                 return -1;
422
423         /* RFC5656 section 6.2.1 */
424         if (kbits <= 256)
425                 return SSH_DIGEST_SHA256;
426         else if (kbits <= 384)
427                 return SSH_DIGEST_SHA384;
428         else
429                 return SSH_DIGEST_SHA512;
430 }
431 #endif /* WITH_OPENSSL */
432
433 static void
434 cert_free(struct sshkey_cert *cert)
435 {
436         u_int i;
437
438         if (cert == NULL)
439                 return;
440         if (cert->certblob != NULL)
441                 sshbuf_free(cert->certblob);
442         if (cert->critical != NULL)
443                 sshbuf_free(cert->critical);
444         if (cert->extensions != NULL)
445                 sshbuf_free(cert->extensions);
446         if (cert->key_id != NULL)
447                 free(cert->key_id);
448         for (i = 0; i < cert->nprincipals; i++)
449                 free(cert->principals[i]);
450         if (cert->principals != NULL)
451                 free(cert->principals);
452         if (cert->signature_key != NULL)
453                 sshkey_free(cert->signature_key);
454         explicit_bzero(cert, sizeof(*cert));
455         free(cert);
456 }
457
458 static struct sshkey_cert *
459 cert_new(void)
460 {
461         struct sshkey_cert *cert;
462
463         if ((cert = calloc(1, sizeof(*cert))) == NULL)
464                 return NULL;
465         if ((cert->certblob = sshbuf_new()) == NULL ||
466             (cert->critical = sshbuf_new()) == NULL ||
467             (cert->extensions = sshbuf_new()) == NULL) {
468                 cert_free(cert);
469                 return NULL;
470         }
471         cert->key_id = NULL;
472         cert->principals = NULL;
473         cert->signature_key = NULL;
474         return cert;
475 }
476
477 struct sshkey *
478 sshkey_new(int type)
479 {
480         struct sshkey *k;
481 #ifdef WITH_OPENSSL
482         RSA *rsa;
483         DSA *dsa;
484 #endif /* WITH_OPENSSL */
485
486         if ((k = calloc(1, sizeof(*k))) == NULL)
487                 return NULL;
488         k->type = type;
489         k->ecdsa = NULL;
490         k->ecdsa_nid = -1;
491         k->dsa = NULL;
492         k->rsa = NULL;
493         k->cert = NULL;
494         k->ed25519_sk = NULL;
495         k->ed25519_pk = NULL;
496         switch (k->type) {
497 #ifdef WITH_OPENSSL
498         case KEY_RSA1:
499         case KEY_RSA:
500         case KEY_RSA_CERT_V00:
501         case KEY_RSA_CERT:
502                 if ((rsa = RSA_new()) == NULL ||
503                     (rsa->n = BN_new()) == NULL ||
504                     (rsa->e = BN_new()) == NULL) {
505                         if (rsa != NULL)
506                                 RSA_free(rsa);
507                         free(k);
508                         return NULL;
509                 }
510                 k->rsa = rsa;
511                 break;
512         case KEY_DSA:
513         case KEY_DSA_CERT_V00:
514         case KEY_DSA_CERT:
515                 if ((dsa = DSA_new()) == NULL ||
516                     (dsa->p = BN_new()) == NULL ||
517                     (dsa->q = BN_new()) == NULL ||
518                     (dsa->g = BN_new()) == NULL ||
519                     (dsa->pub_key = BN_new()) == NULL) {
520                         if (dsa != NULL)
521                                 DSA_free(dsa);
522                         free(k);
523                         return NULL;
524                 }
525                 k->dsa = dsa;
526                 break;
527         case KEY_ECDSA:
528         case KEY_ECDSA_CERT:
529                 /* Cannot do anything until we know the group */
530                 break;
531 #endif /* WITH_OPENSSL */
532         case KEY_ED25519:
533         case KEY_ED25519_CERT:
534                 /* no need to prealloc */
535                 break;
536         case KEY_UNSPEC:
537                 break;
538         default:
539                 free(k);
540                 return NULL;
541                 break;
542         }
543
544         if (sshkey_is_cert(k)) {
545                 if ((k->cert = cert_new()) == NULL) {
546                         sshkey_free(k);
547                         return NULL;
548                 }
549         }
550
551         return k;
552 }
553
554 int
555 sshkey_add_private(struct sshkey *k)
556 {
557         switch (k->type) {
558 #ifdef WITH_OPENSSL
559         case KEY_RSA1:
560         case KEY_RSA:
561         case KEY_RSA_CERT_V00:
562         case KEY_RSA_CERT:
563 #define bn_maybe_alloc_failed(p) (p == NULL && (p = BN_new()) == NULL)
564                 if (bn_maybe_alloc_failed(k->rsa->d) ||
565                     bn_maybe_alloc_failed(k->rsa->iqmp) ||
566                     bn_maybe_alloc_failed(k->rsa->q) ||
567                     bn_maybe_alloc_failed(k->rsa->p) ||
568                     bn_maybe_alloc_failed(k->rsa->dmq1) ||
569                     bn_maybe_alloc_failed(k->rsa->dmp1))
570                         return SSH_ERR_ALLOC_FAIL;
571                 break;
572         case KEY_DSA:
573         case KEY_DSA_CERT_V00:
574         case KEY_DSA_CERT:
575                 if (bn_maybe_alloc_failed(k->dsa->priv_key))
576                         return SSH_ERR_ALLOC_FAIL;
577                 break;
578 #undef bn_maybe_alloc_failed
579         case KEY_ECDSA:
580         case KEY_ECDSA_CERT:
581                 /* Cannot do anything until we know the group */
582                 break;
583 #endif /* WITH_OPENSSL */
584         case KEY_ED25519:
585         case KEY_ED25519_CERT:
586                 /* no need to prealloc */
587                 break;
588         case KEY_UNSPEC:
589                 break;
590         default:
591                 return SSH_ERR_INVALID_ARGUMENT;
592         }
593         return 0;
594 }
595
596 struct sshkey *
597 sshkey_new_private(int type)
598 {
599         struct sshkey *k = sshkey_new(type);
600
601         if (k == NULL)
602                 return NULL;
603         if (sshkey_add_private(k) != 0) {
604                 sshkey_free(k);
605                 return NULL;
606         }
607         return k;
608 }
609
610 void
611 sshkey_free(struct sshkey *k)
612 {
613         if (k == NULL)
614                 return;
615         switch (k->type) {
616 #ifdef WITH_OPENSSL
617         case KEY_RSA1:
618         case KEY_RSA:
619         case KEY_RSA_CERT_V00:
620         case KEY_RSA_CERT:
621                 if (k->rsa != NULL)
622                         RSA_free(k->rsa);
623                 k->rsa = NULL;
624                 break;
625         case KEY_DSA:
626         case KEY_DSA_CERT_V00:
627         case KEY_DSA_CERT:
628                 if (k->dsa != NULL)
629                         DSA_free(k->dsa);
630                 k->dsa = NULL;
631                 break;
632 # ifdef OPENSSL_HAS_ECC
633         case KEY_ECDSA:
634         case KEY_ECDSA_CERT:
635                 if (k->ecdsa != NULL)
636                         EC_KEY_free(k->ecdsa);
637                 k->ecdsa = NULL;
638                 break;
639 # endif /* OPENSSL_HAS_ECC */
640 #endif /* WITH_OPENSSL */
641         case KEY_ED25519:
642         case KEY_ED25519_CERT:
643                 if (k->ed25519_pk) {
644                         explicit_bzero(k->ed25519_pk, ED25519_PK_SZ);
645                         free(k->ed25519_pk);
646                         k->ed25519_pk = NULL;
647                 }
648                 if (k->ed25519_sk) {
649                         explicit_bzero(k->ed25519_sk, ED25519_SK_SZ);
650                         free(k->ed25519_sk);
651                         k->ed25519_sk = NULL;
652                 }
653                 break;
654         case KEY_UNSPEC:
655                 break;
656         default:
657                 break;
658         }
659         if (sshkey_is_cert(k))
660                 cert_free(k->cert);
661         explicit_bzero(k, sizeof(*k));
662         free(k);
663 }
664
665 static int
666 cert_compare(struct sshkey_cert *a, struct sshkey_cert *b)
667 {
668         if (a == NULL && b == NULL)
669                 return 1;
670         if (a == NULL || b == NULL)
671                 return 0;
672         if (sshbuf_len(a->certblob) != sshbuf_len(b->certblob))
673                 return 0;
674         if (timingsafe_bcmp(sshbuf_ptr(a->certblob), sshbuf_ptr(b->certblob),
675             sshbuf_len(a->certblob)) != 0)
676                 return 0;
677         return 1;
678 }
679
680 /*
681  * Compare public portions of key only, allowing comparisons between
682  * certificates and plain keys too.
683  */
684 int
685 sshkey_equal_public(const struct sshkey *a, const struct sshkey *b)
686 {
687 #if defined(WITH_OPENSSL) && defined(OPENSSL_HAS_ECC)
688         BN_CTX *bnctx;
689 #endif /* WITH_OPENSSL && OPENSSL_HAS_ECC */
690
691         if (a == NULL || b == NULL ||
692             sshkey_type_plain(a->type) != sshkey_type_plain(b->type))
693                 return 0;
694
695         switch (a->type) {
696 #ifdef WITH_OPENSSL
697         case KEY_RSA1:
698         case KEY_RSA_CERT_V00:
699         case KEY_RSA_CERT:
700         case KEY_RSA:
701                 return a->rsa != NULL && b->rsa != NULL &&
702                     BN_cmp(a->rsa->e, b->rsa->e) == 0 &&
703                     BN_cmp(a->rsa->n, b->rsa->n) == 0;
704         case KEY_DSA_CERT_V00:
705         case KEY_DSA_CERT:
706         case KEY_DSA:
707                 return a->dsa != NULL && b->dsa != NULL &&
708                     BN_cmp(a->dsa->p, b->dsa->p) == 0 &&
709                     BN_cmp(a->dsa->q, b->dsa->q) == 0 &&
710                     BN_cmp(a->dsa->g, b->dsa->g) == 0 &&
711                     BN_cmp(a->dsa->pub_key, b->dsa->pub_key) == 0;
712 # ifdef OPENSSL_HAS_ECC
713         case KEY_ECDSA_CERT:
714         case KEY_ECDSA:
715                 if (a->ecdsa == NULL || b->ecdsa == NULL ||
716                     EC_KEY_get0_public_key(a->ecdsa) == NULL ||
717                     EC_KEY_get0_public_key(b->ecdsa) == NULL)
718                         return 0;
719                 if ((bnctx = BN_CTX_new()) == NULL)
720                         return 0;
721                 if (EC_GROUP_cmp(EC_KEY_get0_group(a->ecdsa),
722                     EC_KEY_get0_group(b->ecdsa), bnctx) != 0 ||
723                     EC_POINT_cmp(EC_KEY_get0_group(a->ecdsa),
724                     EC_KEY_get0_public_key(a->ecdsa),
725                     EC_KEY_get0_public_key(b->ecdsa), bnctx) != 0) {
726                         BN_CTX_free(bnctx);
727                         return 0;
728                 }
729                 BN_CTX_free(bnctx);
730                 return 1;
731 # endif /* OPENSSL_HAS_ECC */
732 #endif /* WITH_OPENSSL */
733         case KEY_ED25519:
734         case KEY_ED25519_CERT:
735                 return a->ed25519_pk != NULL && b->ed25519_pk != NULL &&
736                     memcmp(a->ed25519_pk, b->ed25519_pk, ED25519_PK_SZ) == 0;
737         default:
738                 return 0;
739         }
740         /* NOTREACHED */
741 }
742
743 int
744 sshkey_equal(const struct sshkey *a, const struct sshkey *b)
745 {
746         if (a == NULL || b == NULL || a->type != b->type)
747                 return 0;
748         if (sshkey_is_cert(a)) {
749                 if (!cert_compare(a->cert, b->cert))
750                         return 0;
751         }
752         return sshkey_equal_public(a, b);
753 }
754
755 static int
756 to_blob_buf(const struct sshkey *key, struct sshbuf *b, int force_plain)
757 {
758         int type, ret = SSH_ERR_INTERNAL_ERROR;
759         const char *typename;
760
761         if (key == NULL)
762                 return SSH_ERR_INVALID_ARGUMENT;
763
764         if (sshkey_is_cert(key)) {
765                 if (key->cert == NULL)
766                         return SSH_ERR_EXPECTED_CERT;
767                 if (sshbuf_len(key->cert->certblob) == 0)
768                         return SSH_ERR_KEY_LACKS_CERTBLOB;
769         }
770         type = force_plain ? sshkey_type_plain(key->type) : key->type;
771         typename = sshkey_ssh_name_from_type_nid(type, key->ecdsa_nid);
772
773         switch (type) {
774 #ifdef WITH_OPENSSL
775         case KEY_DSA_CERT_V00:
776         case KEY_RSA_CERT_V00:
777         case KEY_DSA_CERT:
778         case KEY_ECDSA_CERT:
779         case KEY_RSA_CERT:
780 #endif /* WITH_OPENSSL */
781         case KEY_ED25519_CERT:
782                 /* Use the existing blob */
783                 /* XXX modified flag? */
784                 if ((ret = sshbuf_putb(b, key->cert->certblob)) != 0)
785                         return ret;
786                 break;
787 #ifdef WITH_OPENSSL
788         case KEY_DSA:
789                 if (key->dsa == NULL)
790                         return SSH_ERR_INVALID_ARGUMENT;
791                 if ((ret = sshbuf_put_cstring(b, typename)) != 0 ||
792                     (ret = sshbuf_put_bignum2(b, key->dsa->p)) != 0 ||
793                     (ret = sshbuf_put_bignum2(b, key->dsa->q)) != 0 ||
794                     (ret = sshbuf_put_bignum2(b, key->dsa->g)) != 0 ||
795                     (ret = sshbuf_put_bignum2(b, key->dsa->pub_key)) != 0)
796                         return ret;
797                 break;
798 # ifdef OPENSSL_HAS_ECC
799         case KEY_ECDSA:
800                 if (key->ecdsa == NULL)
801                         return SSH_ERR_INVALID_ARGUMENT;
802                 if ((ret = sshbuf_put_cstring(b, typename)) != 0 ||
803                     (ret = sshbuf_put_cstring(b,
804                     sshkey_curve_nid_to_name(key->ecdsa_nid))) != 0 ||
805                     (ret = sshbuf_put_eckey(b, key->ecdsa)) != 0)
806                         return ret;
807                 break;
808 # endif
809         case KEY_RSA:
810                 if (key->rsa == NULL)
811                         return SSH_ERR_INVALID_ARGUMENT;
812                 if ((ret = sshbuf_put_cstring(b, typename)) != 0 ||
813                     (ret = sshbuf_put_bignum2(b, key->rsa->e)) != 0 ||
814                     (ret = sshbuf_put_bignum2(b, key->rsa->n)) != 0)
815                         return ret;
816                 break;
817 #endif /* WITH_OPENSSL */
818         case KEY_ED25519:
819                 if (key->ed25519_pk == NULL)
820                         return SSH_ERR_INVALID_ARGUMENT;
821                 if ((ret = sshbuf_put_cstring(b, typename)) != 0 ||
822                     (ret = sshbuf_put_string(b,
823                     key->ed25519_pk, ED25519_PK_SZ)) != 0)
824                         return ret;
825                 break;
826         default:
827                 return SSH_ERR_KEY_TYPE_UNKNOWN;
828         }
829         return 0;
830 }
831
832 int
833 sshkey_putb(const struct sshkey *key, struct sshbuf *b)
834 {
835         return to_blob_buf(key, b, 0);
836 }
837
838 int
839 sshkey_puts(const struct sshkey *key, struct sshbuf *b)
840 {
841         struct sshbuf *tmp;
842         int r;
843
844         if ((tmp = sshbuf_new()) == NULL)
845                 return SSH_ERR_ALLOC_FAIL;
846         r = to_blob_buf(key, tmp, 0);
847         if (r == 0)
848                 r = sshbuf_put_stringb(b, tmp);
849         sshbuf_free(tmp);
850         return r;
851 }
852
853 int
854 sshkey_putb_plain(const struct sshkey *key, struct sshbuf *b)
855 {
856         return to_blob_buf(key, b, 1);
857 }
858
859 static int
860 to_blob(const struct sshkey *key, u_char **blobp, size_t *lenp, int force_plain)
861 {
862         int ret = SSH_ERR_INTERNAL_ERROR;
863         size_t len;
864         struct sshbuf *b = NULL;
865
866         if (lenp != NULL)
867                 *lenp = 0;
868         if (blobp != NULL)
869                 *blobp = NULL;
870         if ((b = sshbuf_new()) == NULL)
871                 return SSH_ERR_ALLOC_FAIL;
872         if ((ret = to_blob_buf(key, b, force_plain)) != 0)
873                 goto out;
874         len = sshbuf_len(b);
875         if (lenp != NULL)
876                 *lenp = len;
877         if (blobp != NULL) {
878                 if ((*blobp = malloc(len)) == NULL) {
879                         ret = SSH_ERR_ALLOC_FAIL;
880                         goto out;
881                 }
882                 memcpy(*blobp, sshbuf_ptr(b), len);
883         }
884         ret = 0;
885  out:
886         sshbuf_free(b);
887         return ret;
888 }
889
890 int
891 sshkey_to_blob(const struct sshkey *key, u_char **blobp, size_t *lenp)
892 {
893         return to_blob(key, blobp, lenp, 0);
894 }
895
896 int
897 sshkey_plain_to_blob(const struct sshkey *key, u_char **blobp, size_t *lenp)
898 {
899         return to_blob(key, blobp, lenp, 1);
900 }
901
902 int
903 sshkey_fingerprint_raw(const struct sshkey *k, int dgst_alg,
904     u_char **retp, size_t *lenp)
905 {
906         u_char *blob = NULL, *ret = NULL;
907         size_t blob_len = 0;
908         int r = SSH_ERR_INTERNAL_ERROR;
909
910         if (retp != NULL)
911                 *retp = NULL;
912         if (lenp != NULL)
913                 *lenp = 0;
914         if (ssh_digest_bytes(dgst_alg) == 0) {
915                 r = SSH_ERR_INVALID_ARGUMENT;
916                 goto out;
917         }
918
919         if (k->type == KEY_RSA1) {
920 #ifdef WITH_OPENSSL
921                 int nlen = BN_num_bytes(k->rsa->n);
922                 int elen = BN_num_bytes(k->rsa->e);
923
924                 blob_len = nlen + elen;
925                 if (nlen >= INT_MAX - elen ||
926                     (blob = malloc(blob_len)) == NULL) {
927                         r = SSH_ERR_ALLOC_FAIL;
928                         goto out;
929                 }
930                 BN_bn2bin(k->rsa->n, blob);
931                 BN_bn2bin(k->rsa->e, blob + nlen);
932 #endif /* WITH_OPENSSL */
933         } else if ((r = to_blob(k, &blob, &blob_len, 1)) != 0)
934                 goto out;
935         if ((ret = calloc(1, SSH_DIGEST_MAX_LENGTH)) == NULL) {
936                 r = SSH_ERR_ALLOC_FAIL;
937                 goto out;
938         }
939         if ((r = ssh_digest_memory(dgst_alg, blob, blob_len,
940             ret, SSH_DIGEST_MAX_LENGTH)) != 0)
941                 goto out;
942         /* success */
943         if (retp != NULL) {
944                 *retp = ret;
945                 ret = NULL;
946         }
947         if (lenp != NULL)
948                 *lenp = ssh_digest_bytes(dgst_alg);
949         r = 0;
950  out:
951         free(ret);
952         if (blob != NULL) {
953                 explicit_bzero(blob, blob_len);
954                 free(blob);
955         }
956         return r;
957 }
958
959 static char *
960 fingerprint_b64(const char *alg, u_char *dgst_raw, size_t dgst_raw_len)
961 {
962         char *ret;
963         size_t plen = strlen(alg) + 1;
964         size_t rlen = ((dgst_raw_len + 2) / 3) * 4 + plen + 1;
965         int r;
966
967         if (dgst_raw_len > 65536 || (ret = calloc(1, rlen)) == NULL)
968                 return NULL;
969         strlcpy(ret, alg, rlen);
970         strlcat(ret, ":", rlen);
971         if (dgst_raw_len == 0)
972                 return ret;
973         if ((r = b64_ntop(dgst_raw, dgst_raw_len,
974             ret + plen, rlen - plen)) == -1) {
975                 explicit_bzero(ret, rlen);
976                 free(ret);
977                 return NULL;
978         }
979         /* Trim padding characters from end */
980         ret[strcspn(ret, "=")] = '\0';
981         return ret;
982 }
983
984 static char *
985 fingerprint_hex(const char *alg, u_char *dgst_raw, size_t dgst_raw_len)
986 {
987         char *retval, hex[5];
988         size_t i, rlen = dgst_raw_len * 3 + strlen(alg) + 2;
989
990         if (dgst_raw_len > 65536 || (retval = calloc(1, rlen)) == NULL)
991                 return NULL;
992         strlcpy(retval, alg, rlen);
993         strlcat(retval, ":", rlen);
994         for (i = 0; i < dgst_raw_len; i++) {
995                 snprintf(hex, sizeof(hex), "%s%02x",
996                     i > 0 ? ":" : "", dgst_raw[i]);
997                 strlcat(retval, hex, rlen);
998         }
999         return retval;
1000 }
1001
1002 static char *
1003 fingerprint_bubblebabble(u_char *dgst_raw, size_t dgst_raw_len)
1004 {
1005         char vowels[] = { 'a', 'e', 'i', 'o', 'u', 'y' };
1006         char consonants[] = { 'b', 'c', 'd', 'f', 'g', 'h', 'k', 'l', 'm',
1007             'n', 'p', 'r', 's', 't', 'v', 'z', 'x' };
1008         u_int i, j = 0, rounds, seed = 1;
1009         char *retval;
1010
1011         rounds = (dgst_raw_len / 2) + 1;
1012         if ((retval = calloc(rounds, 6)) == NULL)
1013                 return NULL;
1014         retval[j++] = 'x';
1015         for (i = 0; i < rounds; i++) {
1016                 u_int idx0, idx1, idx2, idx3, idx4;
1017                 if ((i + 1 < rounds) || (dgst_raw_len % 2 != 0)) {
1018                         idx0 = (((((u_int)(dgst_raw[2 * i])) >> 6) & 3) +
1019                             seed) % 6;
1020                         idx1 = (((u_int)(dgst_raw[2 * i])) >> 2) & 15;
1021                         idx2 = ((((u_int)(dgst_raw[2 * i])) & 3) +
1022                             (seed / 6)) % 6;
1023                         retval[j++] = vowels[idx0];
1024                         retval[j++] = consonants[idx1];
1025                         retval[j++] = vowels[idx2];
1026                         if ((i + 1) < rounds) {
1027                                 idx3 = (((u_int)(dgst_raw[(2 * i) + 1])) >> 4) & 15;
1028                                 idx4 = (((u_int)(dgst_raw[(2 * i) + 1]))) & 15;
1029                                 retval[j++] = consonants[idx3];
1030                                 retval[j++] = '-';
1031                                 retval[j++] = consonants[idx4];
1032                                 seed = ((seed * 5) +
1033                                     ((((u_int)(dgst_raw[2 * i])) * 7) +
1034                                     ((u_int)(dgst_raw[(2 * i) + 1])))) % 36;
1035                         }
1036                 } else {
1037                         idx0 = seed % 6;
1038                         idx1 = 16;
1039                         idx2 = seed / 6;
1040                         retval[j++] = vowels[idx0];
1041                         retval[j++] = consonants[idx1];
1042                         retval[j++] = vowels[idx2];
1043                 }
1044         }
1045         retval[j++] = 'x';
1046         retval[j++] = '\0';
1047         return retval;
1048 }
1049
1050 /*
1051  * Draw an ASCII-Art representing the fingerprint so human brain can
1052  * profit from its built-in pattern recognition ability.
1053  * This technique is called "random art" and can be found in some
1054  * scientific publications like this original paper:
1055  *
1056  * "Hash Visualization: a New Technique to improve Real-World Security",
1057  * Perrig A. and Song D., 1999, International Workshop on Cryptographic
1058  * Techniques and E-Commerce (CrypTEC '99)
1059  * sparrow.ece.cmu.edu/~adrian/projects/validation/validation.pdf
1060  *
1061  * The subject came up in a talk by Dan Kaminsky, too.
1062  *
1063  * If you see the picture is different, the key is different.
1064  * If the picture looks the same, you still know nothing.
1065  *
1066  * The algorithm used here is a worm crawling over a discrete plane,
1067  * leaving a trace (augmenting the field) everywhere it goes.
1068  * Movement is taken from dgst_raw 2bit-wise.  Bumping into walls
1069  * makes the respective movement vector be ignored for this turn.
1070  * Graphs are not unambiguous, because circles in graphs can be
1071  * walked in either direction.
1072  */
1073
1074 /*
1075  * Field sizes for the random art.  Have to be odd, so the starting point
1076  * can be in the exact middle of the picture, and FLDBASE should be >=8 .
1077  * Else pictures would be too dense, and drawing the frame would
1078  * fail, too, because the key type would not fit in anymore.
1079  */
1080 #define FLDBASE         8
1081 #define FLDSIZE_Y       (FLDBASE + 1)
1082 #define FLDSIZE_X       (FLDBASE * 2 + 1)
1083 static char *
1084 fingerprint_randomart(const char *alg, u_char *dgst_raw, size_t dgst_raw_len,
1085     const struct sshkey *k)
1086 {
1087         /*
1088          * Chars to be used after each other every time the worm
1089          * intersects with itself.  Matter of taste.
1090          */
1091         char    *augmentation_string = " .o+=*BOX@%&#/^SE";
1092         char    *retval, *p, title[FLDSIZE_X], hash[FLDSIZE_X];
1093         u_char   field[FLDSIZE_X][FLDSIZE_Y];
1094         size_t   i, tlen, hlen;
1095         u_int    b;
1096         int      x, y, r;
1097         size_t   len = strlen(augmentation_string) - 1;
1098
1099         if ((retval = calloc((FLDSIZE_X + 3), (FLDSIZE_Y + 2))) == NULL)
1100                 return NULL;
1101
1102         /* initialize field */
1103         memset(field, 0, FLDSIZE_X * FLDSIZE_Y * sizeof(char));
1104         x = FLDSIZE_X / 2;
1105         y = FLDSIZE_Y / 2;
1106
1107         /* process raw key */
1108         for (i = 0; i < dgst_raw_len; i++) {
1109                 int input;
1110                 /* each byte conveys four 2-bit move commands */
1111                 input = dgst_raw[i];
1112                 for (b = 0; b < 4; b++) {
1113                         /* evaluate 2 bit, rest is shifted later */
1114                         x += (input & 0x1) ? 1 : -1;
1115                         y += (input & 0x2) ? 1 : -1;
1116
1117                         /* assure we are still in bounds */
1118                         x = MAX(x, 0);
1119                         y = MAX(y, 0);
1120                         x = MIN(x, FLDSIZE_X - 1);
1121                         y = MIN(y, FLDSIZE_Y - 1);
1122
1123                         /* augment the field */
1124                         if (field[x][y] < len - 2)
1125                                 field[x][y]++;
1126                         input = input >> 2;
1127                 }
1128         }
1129
1130         /* mark starting point and end point*/
1131         field[FLDSIZE_X / 2][FLDSIZE_Y / 2] = len - 1;
1132         field[x][y] = len;
1133
1134         /* assemble title */
1135         r = snprintf(title, sizeof(title), "[%s %u]",
1136                 sshkey_type(k), sshkey_size(k));
1137         /* If [type size] won't fit, then try [type]; fits "[ED25519-CERT]" */
1138         if (r < 0 || r > (int)sizeof(title))
1139                 r = snprintf(title, sizeof(title), "[%s]", sshkey_type(k));
1140         tlen = (r <= 0) ? 0 : strlen(title);
1141
1142         /* assemble hash ID. */
1143         r = snprintf(hash, sizeof(hash), "[%s]", alg);
1144         hlen = (r <= 0) ? 0 : strlen(hash);
1145
1146         /* output upper border */
1147         p = retval;
1148         *p++ = '+';
1149         for (i = 0; i < (FLDSIZE_X - tlen) / 2; i++)
1150                 *p++ = '-';
1151         memcpy(p, title, tlen);
1152         p += tlen;
1153         for (i += tlen; i < FLDSIZE_X; i++)
1154                 *p++ = '-';
1155         *p++ = '+';
1156         *p++ = '\n';
1157
1158         /* output content */
1159         for (y = 0; y < FLDSIZE_Y; y++) {
1160                 *p++ = '|';
1161                 for (x = 0; x < FLDSIZE_X; x++)
1162                         *p++ = augmentation_string[MIN(field[x][y], len)];
1163                 *p++ = '|';
1164                 *p++ = '\n';
1165         }
1166
1167         /* output lower border */
1168         *p++ = '+';
1169         for (i = 0; i < (FLDSIZE_X - hlen) / 2; i++)
1170                 *p++ = '-';
1171         memcpy(p, hash, hlen);
1172         p += hlen;
1173         for (i += hlen; i < FLDSIZE_X; i++)
1174                 *p++ = '-';
1175         *p++ = '+';
1176
1177         return retval;
1178 }
1179
1180 char *
1181 sshkey_fingerprint(const struct sshkey *k, int dgst_alg,
1182     enum sshkey_fp_rep dgst_rep)
1183 {
1184         char *retval = NULL;
1185         u_char *dgst_raw;
1186         size_t dgst_raw_len;
1187
1188         if (sshkey_fingerprint_raw(k, dgst_alg, &dgst_raw, &dgst_raw_len) != 0)
1189                 return NULL;
1190         switch (dgst_rep) {
1191         case SSH_FP_DEFAULT:
1192                 if (dgst_alg == SSH_DIGEST_MD5) {
1193                         retval = fingerprint_hex(ssh_digest_alg_name(dgst_alg),
1194                             dgst_raw, dgst_raw_len);
1195                 } else {
1196                         retval = fingerprint_b64(ssh_digest_alg_name(dgst_alg),
1197                             dgst_raw, dgst_raw_len);
1198                 }
1199                 break;
1200         case SSH_FP_HEX:
1201                 retval = fingerprint_hex(ssh_digest_alg_name(dgst_alg),
1202                     dgst_raw, dgst_raw_len);
1203                 break;
1204         case SSH_FP_BASE64:
1205                 retval = fingerprint_b64(ssh_digest_alg_name(dgst_alg),
1206                     dgst_raw, dgst_raw_len);
1207                 break;
1208         case SSH_FP_BUBBLEBABBLE:
1209                 retval = fingerprint_bubblebabble(dgst_raw, dgst_raw_len);
1210                 break;
1211         case SSH_FP_RANDOMART:
1212                 retval = fingerprint_randomart(ssh_digest_alg_name(dgst_alg),
1213                     dgst_raw, dgst_raw_len, k);
1214                 break;
1215         default:
1216                 explicit_bzero(dgst_raw, dgst_raw_len);
1217                 free(dgst_raw);
1218                 return NULL;
1219         }
1220         explicit_bzero(dgst_raw, dgst_raw_len);
1221         free(dgst_raw);
1222         return retval;
1223 }
1224
1225 #ifdef WITH_SSH1
1226 /*
1227  * Reads a multiple-precision integer in decimal from the buffer, and advances
1228  * the pointer.  The integer must already be initialized.  This function is
1229  * permitted to modify the buffer.  This leaves *cpp to point just beyond the
1230  * last processed character.
1231  */
1232 static int
1233 read_decimal_bignum(char **cpp, BIGNUM *v)
1234 {
1235         char *cp;
1236         size_t e;
1237         int skip = 1;   /* skip white space */
1238
1239         cp = *cpp;
1240         while (*cp == ' ' || *cp == '\t')
1241                 cp++;
1242         e = strspn(cp, "0123456789");
1243         if (e == 0)
1244                 return SSH_ERR_INVALID_FORMAT;
1245         if (e > SSHBUF_MAX_BIGNUM * 3)
1246                 return SSH_ERR_BIGNUM_TOO_LARGE;
1247         if (cp[e] == '\0')
1248                 skip = 0;
1249         else if (index(" \t\r\n", cp[e]) == NULL)
1250                 return SSH_ERR_INVALID_FORMAT;
1251         cp[e] = '\0';
1252         if (BN_dec2bn(&v, cp) <= 0)
1253                 return SSH_ERR_INVALID_FORMAT;
1254         *cpp = cp + e + skip;
1255         return 0;
1256 }
1257 #endif /* WITH_SSH1 */
1258
1259 /* returns 0 ok, and < 0 error */
1260 int
1261 sshkey_read(struct sshkey *ret, char **cpp)
1262 {
1263         struct sshkey *k;
1264         int retval = SSH_ERR_INVALID_FORMAT;
1265         char *cp, *space;
1266         int r, type, curve_nid = -1;
1267         struct sshbuf *blob;
1268 #ifdef WITH_SSH1
1269         char *ep;
1270         u_long bits;
1271 #endif /* WITH_SSH1 */
1272
1273         cp = *cpp;
1274
1275         switch (ret->type) {
1276         case KEY_RSA1:
1277 #ifdef WITH_SSH1
1278                 /* Get number of bits. */
1279                 bits = strtoul(cp, &ep, 10);
1280                 if (*cp == '\0' || index(" \t\r\n", *ep) == NULL ||
1281                     bits == 0 || bits > SSHBUF_MAX_BIGNUM * 8)
1282                         return SSH_ERR_INVALID_FORMAT;  /* Bad bit count... */
1283                 /* Get public exponent, public modulus. */
1284                 if ((r = read_decimal_bignum(&ep, ret->rsa->e)) < 0)
1285                         return r;
1286                 if ((r = read_decimal_bignum(&ep, ret->rsa->n)) < 0)
1287                         return r;
1288                 *cpp = ep;
1289                 /* validate the claimed number of bits */
1290                 if (BN_num_bits(ret->rsa->n) != (int)bits)
1291                         return SSH_ERR_KEY_BITS_MISMATCH;
1292                 retval = 0;
1293 #endif /* WITH_SSH1 */
1294                 break;
1295         case KEY_UNSPEC:
1296         case KEY_RSA:
1297         case KEY_DSA:
1298         case KEY_ECDSA:
1299         case KEY_ED25519:
1300         case KEY_DSA_CERT_V00:
1301         case KEY_RSA_CERT_V00:
1302         case KEY_DSA_CERT:
1303         case KEY_ECDSA_CERT:
1304         case KEY_RSA_CERT:
1305         case KEY_ED25519_CERT:
1306                 space = strchr(cp, ' ');
1307                 if (space == NULL)
1308                         return SSH_ERR_INVALID_FORMAT;
1309                 *space = '\0';
1310                 type = sshkey_type_from_name(cp);
1311                 if (sshkey_type_plain(type) == KEY_ECDSA &&
1312                     (curve_nid = sshkey_ecdsa_nid_from_name(cp)) == -1)
1313                         return SSH_ERR_EC_CURVE_INVALID;
1314                 *space = ' ';
1315                 if (type == KEY_UNSPEC)
1316                         return SSH_ERR_INVALID_FORMAT;
1317                 cp = space+1;
1318                 if (*cp == '\0')
1319                         return SSH_ERR_INVALID_FORMAT;
1320                 if (ret->type != KEY_UNSPEC && ret->type != type)
1321                         return SSH_ERR_KEY_TYPE_MISMATCH;
1322                 if ((blob = sshbuf_new()) == NULL)
1323                         return SSH_ERR_ALLOC_FAIL;
1324                 /* trim comment */
1325                 space = strchr(cp, ' ');
1326                 if (space) {
1327                         /* advance 'space': skip whitespace */
1328                         *space++ = '\0';
1329                         while (*space == ' ' || *space == '\t')
1330                                 space++;
1331                         *cpp = space;
1332                 } else
1333                         *cpp = cp + strlen(cp);
1334                 if ((r = sshbuf_b64tod(blob, cp)) != 0) {
1335                         sshbuf_free(blob);
1336                         return r;
1337                 }
1338                 if ((r = sshkey_from_blob(sshbuf_ptr(blob),
1339                     sshbuf_len(blob), &k)) != 0) {
1340                         sshbuf_free(blob);
1341                         return r;
1342                 }
1343                 sshbuf_free(blob);
1344                 if (k->type != type) {
1345                         sshkey_free(k);
1346                         return SSH_ERR_KEY_TYPE_MISMATCH;
1347                 }
1348                 if (sshkey_type_plain(type) == KEY_ECDSA &&
1349                     curve_nid != k->ecdsa_nid) {
1350                         sshkey_free(k);
1351                         return SSH_ERR_EC_CURVE_MISMATCH;
1352                 }
1353                 ret->type = type;
1354                 if (sshkey_is_cert(ret)) {
1355                         if (!sshkey_is_cert(k)) {
1356                                 sshkey_free(k);
1357                                 return SSH_ERR_EXPECTED_CERT;
1358                         }
1359                         if (ret->cert != NULL)
1360                                 cert_free(ret->cert);
1361                         ret->cert = k->cert;
1362                         k->cert = NULL;
1363                 }
1364 #ifdef WITH_OPENSSL
1365                 if (sshkey_type_plain(ret->type) == KEY_RSA) {
1366                         if (ret->rsa != NULL)
1367                                 RSA_free(ret->rsa);
1368                         ret->rsa = k->rsa;
1369                         k->rsa = NULL;
1370 #ifdef DEBUG_PK
1371                         RSA_print_fp(stderr, ret->rsa, 8);
1372 #endif
1373                 }
1374                 if (sshkey_type_plain(ret->type) == KEY_DSA) {
1375                         if (ret->dsa != NULL)
1376                                 DSA_free(ret->dsa);
1377                         ret->dsa = k->dsa;
1378                         k->dsa = NULL;
1379 #ifdef DEBUG_PK
1380                         DSA_print_fp(stderr, ret->dsa, 8);
1381 #endif
1382                 }
1383 # ifdef OPENSSL_HAS_ECC
1384                 if (sshkey_type_plain(ret->type) == KEY_ECDSA) {
1385                         if (ret->ecdsa != NULL)
1386                                 EC_KEY_free(ret->ecdsa);
1387                         ret->ecdsa = k->ecdsa;
1388                         ret->ecdsa_nid = k->ecdsa_nid;
1389                         k->ecdsa = NULL;
1390                         k->ecdsa_nid = -1;
1391 #ifdef DEBUG_PK
1392                         sshkey_dump_ec_key(ret->ecdsa);
1393 #endif
1394                 }
1395 # endif /* OPENSSL_HAS_ECC */
1396 #endif /* WITH_OPENSSL */
1397                 if (sshkey_type_plain(ret->type) == KEY_ED25519) {
1398                         free(ret->ed25519_pk);
1399                         ret->ed25519_pk = k->ed25519_pk;
1400                         k->ed25519_pk = NULL;
1401 #ifdef DEBUG_PK
1402                         /* XXX */
1403 #endif
1404                 }
1405                 retval = 0;
1406 /*XXXX*/
1407                 sshkey_free(k);
1408                 if (retval != 0)
1409                         break;
1410                 break;
1411         default:
1412                 return SSH_ERR_INVALID_ARGUMENT;
1413         }
1414         return retval;
1415 }
1416
1417 int
1418 sshkey_to_base64(const struct sshkey *key, char **b64p)
1419 {
1420         int r = SSH_ERR_INTERNAL_ERROR;
1421         struct sshbuf *b = NULL;
1422         char *uu = NULL;
1423
1424         if (b64p != NULL)
1425                 *b64p = NULL;
1426         if ((b = sshbuf_new()) == NULL)
1427                 return SSH_ERR_ALLOC_FAIL;
1428         if ((r = sshkey_putb(key, b)) != 0)
1429                 goto out;
1430         if ((uu = sshbuf_dtob64(b)) == NULL) {
1431                 r = SSH_ERR_ALLOC_FAIL;
1432                 goto out;
1433         }
1434         /* Success */
1435         if (b64p != NULL) {
1436                 *b64p = uu;
1437                 uu = NULL;
1438         }
1439         r = 0;
1440  out:
1441         sshbuf_free(b);
1442         free(uu);
1443         return r;
1444 }
1445
1446 static int
1447 sshkey_format_rsa1(const struct sshkey *key, struct sshbuf *b)
1448 {
1449         int r = SSH_ERR_INTERNAL_ERROR;
1450 #ifdef WITH_SSH1
1451         u_int bits = 0;
1452         char *dec_e = NULL, *dec_n = NULL;
1453
1454         if (key->rsa == NULL || key->rsa->e == NULL ||
1455             key->rsa->n == NULL) {
1456                 r = SSH_ERR_INVALID_ARGUMENT;
1457                 goto out;
1458         }
1459         if ((dec_e = BN_bn2dec(key->rsa->e)) == NULL ||
1460             (dec_n = BN_bn2dec(key->rsa->n)) == NULL) {
1461                 r = SSH_ERR_ALLOC_FAIL;
1462                 goto out;
1463         }
1464         /* size of modulus 'n' */
1465         if ((bits = BN_num_bits(key->rsa->n)) <= 0) {
1466                 r = SSH_ERR_INVALID_ARGUMENT;
1467                 goto out;
1468         }
1469         if ((r = sshbuf_putf(b, "%u %s %s", bits, dec_e, dec_n)) != 0)
1470                 goto out;
1471
1472         /* Success */
1473         r = 0;
1474  out:
1475         if (dec_e != NULL)
1476                 OPENSSL_free(dec_e);
1477         if (dec_n != NULL)
1478                 OPENSSL_free(dec_n);
1479 #endif /* WITH_SSH1 */
1480
1481         return r;
1482 }
1483
1484 static int
1485 sshkey_format_text(const struct sshkey *key, struct sshbuf *b)
1486 {
1487         int r = SSH_ERR_INTERNAL_ERROR;
1488         char *uu = NULL;
1489
1490         if (key->type == KEY_RSA1) {
1491                 if ((r = sshkey_format_rsa1(key, b)) != 0)
1492                         goto out;
1493         } else {
1494                 /* Unsupported key types handled in sshkey_to_base64() */
1495                 if ((r = sshkey_to_base64(key, &uu)) != 0)
1496                         goto out;
1497                 if ((r = sshbuf_putf(b, "%s %s",
1498                     sshkey_ssh_name(key), uu)) != 0)
1499                         goto out;
1500         }
1501         r = 0;
1502  out:
1503         free(uu);
1504         return r;
1505 }
1506
1507 int
1508 sshkey_write(const struct sshkey *key, FILE *f)
1509 {
1510         struct sshbuf *b = NULL;
1511         int r = SSH_ERR_INTERNAL_ERROR;
1512
1513         if ((b = sshbuf_new()) == NULL)
1514                 return SSH_ERR_ALLOC_FAIL;
1515         if ((r = sshkey_format_text(key, b)) != 0)
1516                 goto out;
1517         if (fwrite(sshbuf_ptr(b), sshbuf_len(b), 1, f) != 1) {
1518                 if (feof(f))
1519                         errno = EPIPE;
1520                 r = SSH_ERR_SYSTEM_ERROR;
1521                 goto out;
1522         }
1523         /* Success */
1524         r = 0;
1525  out:
1526         sshbuf_free(b);
1527         return r;
1528 }
1529
1530 const char *
1531 sshkey_cert_type(const struct sshkey *k)
1532 {
1533         switch (k->cert->type) {
1534         case SSH2_CERT_TYPE_USER:
1535                 return "user";
1536         case SSH2_CERT_TYPE_HOST:
1537                 return "host";
1538         default:
1539                 return "unknown";
1540         }
1541 }
1542
1543 #ifdef WITH_OPENSSL
1544 static int
1545 rsa_generate_private_key(u_int bits, RSA **rsap)
1546 {
1547         RSA *private = NULL;
1548         BIGNUM *f4 = NULL;
1549         int ret = SSH_ERR_INTERNAL_ERROR;
1550
1551         if (rsap == NULL ||
1552             bits < SSH_RSA_MINIMUM_MODULUS_SIZE ||
1553             bits > SSHBUF_MAX_BIGNUM * 8)
1554                 return SSH_ERR_INVALID_ARGUMENT;
1555         *rsap = NULL;
1556         if ((private = RSA_new()) == NULL || (f4 = BN_new()) == NULL) {
1557                 ret = SSH_ERR_ALLOC_FAIL;
1558                 goto out;
1559         }
1560         if (!BN_set_word(f4, RSA_F4) ||
1561             !RSA_generate_key_ex(private, bits, f4, NULL)) {
1562                 ret = SSH_ERR_LIBCRYPTO_ERROR;
1563                 goto out;
1564         }
1565         *rsap = private;
1566         private = NULL;
1567         ret = 0;
1568  out:
1569         if (private != NULL)
1570                 RSA_free(private);
1571         if (f4 != NULL)
1572                 BN_free(f4);
1573         return ret;
1574 }
1575
1576 static int
1577 dsa_generate_private_key(u_int bits, DSA **dsap)
1578 {
1579         DSA *private;
1580         int ret = SSH_ERR_INTERNAL_ERROR;
1581
1582         if (dsap == NULL || bits != 1024)
1583                 return SSH_ERR_INVALID_ARGUMENT;
1584         if ((private = DSA_new()) == NULL) {
1585                 ret = SSH_ERR_ALLOC_FAIL;
1586                 goto out;
1587         }
1588         *dsap = NULL;
1589         if (!DSA_generate_parameters_ex(private, bits, NULL, 0, NULL,
1590             NULL, NULL) || !DSA_generate_key(private)) {
1591                 DSA_free(private);
1592                 ret = SSH_ERR_LIBCRYPTO_ERROR;
1593                 goto out;
1594         }
1595         *dsap = private;
1596         private = NULL;
1597         ret = 0;
1598  out:
1599         if (private != NULL)
1600                 DSA_free(private);
1601         return ret;
1602 }
1603
1604 # ifdef OPENSSL_HAS_ECC
1605 int
1606 sshkey_ecdsa_key_to_nid(EC_KEY *k)
1607 {
1608         EC_GROUP *eg;
1609         int nids[] = {
1610                 NID_X9_62_prime256v1,
1611                 NID_secp384r1,
1612 #  ifdef OPENSSL_HAS_NISTP521
1613                 NID_secp521r1,
1614 #  endif /* OPENSSL_HAS_NISTP521 */
1615                 -1
1616         };
1617         int nid;
1618         u_int i;
1619         BN_CTX *bnctx;
1620         const EC_GROUP *g = EC_KEY_get0_group(k);
1621
1622         /*
1623          * The group may be stored in a ASN.1 encoded private key in one of two
1624          * ways: as a "named group", which is reconstituted by ASN.1 object ID
1625          * or explicit group parameters encoded into the key blob. Only the
1626          * "named group" case sets the group NID for us, but we can figure
1627          * it out for the other case by comparing against all the groups that
1628          * are supported.
1629          */
1630         if ((nid = EC_GROUP_get_curve_name(g)) > 0)
1631                 return nid;
1632         if ((bnctx = BN_CTX_new()) == NULL)
1633                 return -1;
1634         for (i = 0; nids[i] != -1; i++) {
1635                 if ((eg = EC_GROUP_new_by_curve_name(nids[i])) == NULL) {
1636                         BN_CTX_free(bnctx);
1637                         return -1;
1638                 }
1639                 if (EC_GROUP_cmp(g, eg, bnctx) == 0)
1640                         break;
1641                 EC_GROUP_free(eg);
1642         }
1643         BN_CTX_free(bnctx);
1644         if (nids[i] != -1) {
1645                 /* Use the group with the NID attached */
1646                 EC_GROUP_set_asn1_flag(eg, OPENSSL_EC_NAMED_CURVE);
1647                 if (EC_KEY_set_group(k, eg) != 1) {
1648                         EC_GROUP_free(eg);
1649                         return -1;
1650                 }
1651         }
1652         return nids[i];
1653 }
1654
1655 static int
1656 ecdsa_generate_private_key(u_int bits, int *nid, EC_KEY **ecdsap)
1657 {
1658         EC_KEY *private;
1659         int ret = SSH_ERR_INTERNAL_ERROR;
1660
1661         if (nid == NULL || ecdsap == NULL ||
1662             (*nid = sshkey_ecdsa_bits_to_nid(bits)) == -1)
1663                 return SSH_ERR_INVALID_ARGUMENT;
1664         *ecdsap = NULL;
1665         if ((private = EC_KEY_new_by_curve_name(*nid)) == NULL) {
1666                 ret = SSH_ERR_ALLOC_FAIL;
1667                 goto out;
1668         }
1669         if (EC_KEY_generate_key(private) != 1) {
1670                 ret = SSH_ERR_LIBCRYPTO_ERROR;
1671                 goto out;
1672         }
1673         EC_KEY_set_asn1_flag(private, OPENSSL_EC_NAMED_CURVE);
1674         *ecdsap = private;
1675         private = NULL;
1676         ret = 0;
1677  out:
1678         if (private != NULL)
1679                 EC_KEY_free(private);
1680         return ret;
1681 }
1682 # endif /* OPENSSL_HAS_ECC */
1683 #endif /* WITH_OPENSSL */
1684
1685 int
1686 sshkey_generate(int type, u_int bits, struct sshkey **keyp)
1687 {
1688         struct sshkey *k;
1689         int ret = SSH_ERR_INTERNAL_ERROR;
1690
1691         if (keyp == NULL)
1692                 return SSH_ERR_INVALID_ARGUMENT;
1693         *keyp = NULL;
1694         if ((k = sshkey_new(KEY_UNSPEC)) == NULL)
1695                 return SSH_ERR_ALLOC_FAIL;
1696         switch (type) {
1697         case KEY_ED25519:
1698                 if ((k->ed25519_pk = malloc(ED25519_PK_SZ)) == NULL ||
1699                     (k->ed25519_sk = malloc(ED25519_SK_SZ)) == NULL) {
1700                         ret = SSH_ERR_ALLOC_FAIL;
1701                         break;
1702                 }
1703                 crypto_sign_ed25519_keypair(k->ed25519_pk, k->ed25519_sk);
1704                 ret = 0;
1705                 break;
1706 #ifdef WITH_OPENSSL
1707         case KEY_DSA:
1708                 ret = dsa_generate_private_key(bits, &k->dsa);
1709                 break;
1710 # ifdef OPENSSL_HAS_ECC
1711         case KEY_ECDSA:
1712                 ret = ecdsa_generate_private_key(bits, &k->ecdsa_nid,
1713                     &k->ecdsa);
1714                 break;
1715 # endif /* OPENSSL_HAS_ECC */
1716         case KEY_RSA:
1717         case KEY_RSA1:
1718                 ret = rsa_generate_private_key(bits, &k->rsa);
1719                 break;
1720 #endif /* WITH_OPENSSL */
1721         default:
1722                 ret = SSH_ERR_INVALID_ARGUMENT;
1723         }
1724         if (ret == 0) {
1725                 k->type = type;
1726                 *keyp = k;
1727         } else
1728                 sshkey_free(k);
1729         return ret;
1730 }
1731
1732 int
1733 sshkey_cert_copy(const struct sshkey *from_key, struct sshkey *to_key)
1734 {
1735         u_int i;
1736         const struct sshkey_cert *from;
1737         struct sshkey_cert *to;
1738         int ret = SSH_ERR_INTERNAL_ERROR;
1739
1740         if (to_key->cert != NULL) {
1741                 cert_free(to_key->cert);
1742                 to_key->cert = NULL;
1743         }
1744
1745         if ((from = from_key->cert) == NULL)
1746                 return SSH_ERR_INVALID_ARGUMENT;
1747
1748         if ((to = to_key->cert = cert_new()) == NULL)
1749                 return SSH_ERR_ALLOC_FAIL;
1750
1751         if ((ret = sshbuf_putb(to->certblob, from->certblob)) != 0 ||
1752             (ret = sshbuf_putb(to->critical, from->critical)) != 0 ||
1753             (ret = sshbuf_putb(to->extensions, from->extensions) != 0))
1754                 return ret;
1755
1756         to->serial = from->serial;
1757         to->type = from->type;
1758         if (from->key_id == NULL)
1759                 to->key_id = NULL;
1760         else if ((to->key_id = strdup(from->key_id)) == NULL)
1761                 return SSH_ERR_ALLOC_FAIL;
1762         to->valid_after = from->valid_after;
1763         to->valid_before = from->valid_before;
1764         if (from->signature_key == NULL)
1765                 to->signature_key = NULL;
1766         else if ((ret = sshkey_from_private(from->signature_key,
1767             &to->signature_key)) != 0)
1768                 return ret;
1769
1770         if (from->nprincipals > SSHKEY_CERT_MAX_PRINCIPALS)
1771                 return SSH_ERR_INVALID_ARGUMENT;
1772         if (from->nprincipals > 0) {
1773                 if ((to->principals = calloc(from->nprincipals,
1774                     sizeof(*to->principals))) == NULL)
1775                         return SSH_ERR_ALLOC_FAIL;
1776                 for (i = 0; i < from->nprincipals; i++) {
1777                         to->principals[i] = strdup(from->principals[i]);
1778                         if (to->principals[i] == NULL) {
1779                                 to->nprincipals = i;
1780                                 return SSH_ERR_ALLOC_FAIL;
1781                         }
1782                 }
1783         }
1784         to->nprincipals = from->nprincipals;
1785         return 0;
1786 }
1787
1788 int
1789 sshkey_from_private(const struct sshkey *k, struct sshkey **pkp)
1790 {
1791         struct sshkey *n = NULL;
1792         int ret = SSH_ERR_INTERNAL_ERROR;
1793
1794         if (pkp != NULL)
1795                 *pkp = NULL;
1796
1797         switch (k->type) {
1798 #ifdef WITH_OPENSSL
1799         case KEY_DSA:
1800         case KEY_DSA_CERT_V00:
1801         case KEY_DSA_CERT:
1802                 if ((n = sshkey_new(k->type)) == NULL)
1803                         return SSH_ERR_ALLOC_FAIL;
1804                 if ((BN_copy(n->dsa->p, k->dsa->p) == NULL) ||
1805                     (BN_copy(n->dsa->q, k->dsa->q) == NULL) ||
1806                     (BN_copy(n->dsa->g, k->dsa->g) == NULL) ||
1807                     (BN_copy(n->dsa->pub_key, k->dsa->pub_key) == NULL)) {
1808                         sshkey_free(n);
1809                         return SSH_ERR_ALLOC_FAIL;
1810                 }
1811                 break;
1812 # ifdef OPENSSL_HAS_ECC
1813         case KEY_ECDSA:
1814         case KEY_ECDSA_CERT:
1815                 if ((n = sshkey_new(k->type)) == NULL)
1816                         return SSH_ERR_ALLOC_FAIL;
1817                 n->ecdsa_nid = k->ecdsa_nid;
1818                 n->ecdsa = EC_KEY_new_by_curve_name(k->ecdsa_nid);
1819                 if (n->ecdsa == NULL) {
1820                         sshkey_free(n);
1821                         return SSH_ERR_ALLOC_FAIL;
1822                 }
1823                 if (EC_KEY_set_public_key(n->ecdsa,
1824                     EC_KEY_get0_public_key(k->ecdsa)) != 1) {
1825                         sshkey_free(n);
1826                         return SSH_ERR_LIBCRYPTO_ERROR;
1827                 }
1828                 break;
1829 # endif /* OPENSSL_HAS_ECC */
1830         case KEY_RSA:
1831         case KEY_RSA1:
1832         case KEY_RSA_CERT_V00:
1833         case KEY_RSA_CERT:
1834                 if ((n = sshkey_new(k->type)) == NULL)
1835                         return SSH_ERR_ALLOC_FAIL;
1836                 if ((BN_copy(n->rsa->n, k->rsa->n) == NULL) ||
1837                     (BN_copy(n->rsa->e, k->rsa->e) == NULL)) {
1838                         sshkey_free(n);
1839                         return SSH_ERR_ALLOC_FAIL;
1840                 }
1841                 break;
1842 #endif /* WITH_OPENSSL */
1843         case KEY_ED25519:
1844         case KEY_ED25519_CERT:
1845                 if ((n = sshkey_new(k->type)) == NULL)
1846                         return SSH_ERR_ALLOC_FAIL;
1847                 if (k->ed25519_pk != NULL) {
1848                         if ((n->ed25519_pk = malloc(ED25519_PK_SZ)) == NULL) {
1849                                 sshkey_free(n);
1850                                 return SSH_ERR_ALLOC_FAIL;
1851                         }
1852                         memcpy(n->ed25519_pk, k->ed25519_pk, ED25519_PK_SZ);
1853                 }
1854                 break;
1855         default:
1856                 return SSH_ERR_KEY_TYPE_UNKNOWN;
1857         }
1858         if (sshkey_is_cert(k)) {
1859                 if ((ret = sshkey_cert_copy(k, n)) != 0) {
1860                         sshkey_free(n);
1861                         return ret;
1862                 }
1863         }
1864         *pkp = n;
1865         return 0;
1866 }
1867
1868 static int
1869 cert_parse(struct sshbuf *b, struct sshkey *key, struct sshbuf *certbuf)
1870 {
1871         struct sshbuf *principals = NULL, *crit = NULL;
1872         struct sshbuf *exts = NULL, *ca = NULL;
1873         u_char *sig = NULL;
1874         size_t signed_len = 0, slen = 0, kidlen = 0;
1875         int ret = SSH_ERR_INTERNAL_ERROR;
1876         int v00 = sshkey_cert_is_legacy(key);
1877
1878         /* Copy the entire key blob for verification and later serialisation */
1879         if ((ret = sshbuf_putb(key->cert->certblob, certbuf)) != 0)
1880                 return ret;
1881
1882         if ((!v00 && (ret = sshbuf_get_u64(b, &key->cert->serial)) != 0) ||
1883             (ret = sshbuf_get_u32(b, &key->cert->type)) != 0 ||
1884             (ret = sshbuf_get_cstring(b, &key->cert->key_id, &kidlen)) != 0 ||
1885             (ret = sshbuf_froms(b, &principals)) != 0 ||
1886             (ret = sshbuf_get_u64(b, &key->cert->valid_after)) != 0 ||
1887             (ret = sshbuf_get_u64(b, &key->cert->valid_before)) != 0 ||
1888             (ret = sshbuf_froms(b, &crit)) != 0 ||
1889             (!v00 && (ret = sshbuf_froms(b, &exts)) != 0) ||
1890             (v00 && (ret = sshbuf_get_string_direct(b, NULL, NULL)) != 0) ||
1891             (ret = sshbuf_get_string_direct(b, NULL, NULL)) != 0 ||
1892             (ret = sshbuf_froms(b, &ca)) != 0) {
1893                 /* XXX debug print error for ret */
1894                 ret = SSH_ERR_INVALID_FORMAT;
1895                 goto out;
1896         }
1897
1898         /* Signature is left in the buffer so we can calculate this length */
1899         signed_len = sshbuf_len(key->cert->certblob) - sshbuf_len(b);
1900
1901         if ((ret = sshbuf_get_string(b, &sig, &slen)) != 0) {
1902                 ret = SSH_ERR_INVALID_FORMAT;
1903                 goto out;
1904         }
1905
1906         if (key->cert->type != SSH2_CERT_TYPE_USER &&
1907             key->cert->type != SSH2_CERT_TYPE_HOST) {
1908                 ret = SSH_ERR_KEY_CERT_UNKNOWN_TYPE;
1909                 goto out;
1910         }
1911
1912         /* Parse principals section */
1913         while (sshbuf_len(principals) > 0) {
1914                 char *principal = NULL;
1915                 char **oprincipals = NULL;
1916
1917                 if (key->cert->nprincipals >= SSHKEY_CERT_MAX_PRINCIPALS) {
1918                         ret = SSH_ERR_INVALID_FORMAT;
1919                         goto out;
1920                 }
1921                 if ((ret = sshbuf_get_cstring(principals, &principal,
1922                     NULL)) != 0) {
1923                         ret = SSH_ERR_INVALID_FORMAT;
1924                         goto out;
1925                 }
1926                 oprincipals = key->cert->principals;
1927                 key->cert->principals = realloc(key->cert->principals,
1928                     (key->cert->nprincipals + 1) *
1929                     sizeof(*key->cert->principals));
1930                 if (key->cert->principals == NULL) {
1931                         free(principal);
1932                         key->cert->principals = oprincipals;
1933                         ret = SSH_ERR_ALLOC_FAIL;
1934                         goto out;
1935                 }
1936                 key->cert->principals[key->cert->nprincipals++] = principal;
1937         }
1938
1939         /*
1940          * Stash a copies of the critical options and extensions sections
1941          * for later use.
1942          */
1943         if ((ret = sshbuf_putb(key->cert->critical, crit)) != 0 ||
1944             (exts != NULL &&
1945             (ret = sshbuf_putb(key->cert->extensions, exts)) != 0))
1946                 goto out;
1947
1948         /*
1949          * Validate critical options and extensions sections format.
1950          * NB. extensions are not present in v00 certs.
1951          */
1952         while (sshbuf_len(crit) != 0) {
1953                 if ((ret = sshbuf_get_string_direct(crit, NULL, NULL)) != 0 ||
1954                     (ret = sshbuf_get_string_direct(crit, NULL, NULL)) != 0) {
1955                         sshbuf_reset(key->cert->critical);
1956                         ret = SSH_ERR_INVALID_FORMAT;
1957                         goto out;
1958                 }
1959         }
1960         while (exts != NULL && sshbuf_len(exts) != 0) {
1961                 if ((ret = sshbuf_get_string_direct(exts, NULL, NULL)) != 0 ||
1962                     (ret = sshbuf_get_string_direct(exts, NULL, NULL)) != 0) {
1963                         sshbuf_reset(key->cert->extensions);
1964                         ret = SSH_ERR_INVALID_FORMAT;
1965                         goto out;
1966                 }
1967         }
1968
1969         /* Parse CA key and check signature */
1970         if (sshkey_from_blob_internal(ca, &key->cert->signature_key, 0) != 0) {
1971                 ret = SSH_ERR_KEY_CERT_INVALID_SIGN_KEY;
1972                 goto out;
1973         }
1974         if (!sshkey_type_is_valid_ca(key->cert->signature_key->type)) {
1975                 ret = SSH_ERR_KEY_CERT_INVALID_SIGN_KEY;
1976                 goto out;
1977         }
1978         if ((ret = sshkey_verify(key->cert->signature_key, sig, slen,
1979             sshbuf_ptr(key->cert->certblob), signed_len, 0)) != 0)
1980                 goto out;
1981
1982         /* Success */
1983         ret = 0;
1984  out:
1985         sshbuf_free(ca);
1986         sshbuf_free(crit);
1987         sshbuf_free(exts);
1988         sshbuf_free(principals);
1989         free(sig);
1990         return ret;
1991 }
1992
1993 static int
1994 sshkey_from_blob_internal(struct sshbuf *b, struct sshkey **keyp,
1995     int allow_cert)
1996 {
1997         int type, ret = SSH_ERR_INTERNAL_ERROR;
1998         char *ktype = NULL, *curve = NULL;
1999         struct sshkey *key = NULL;
2000         size_t len;
2001         u_char *pk = NULL;
2002         struct sshbuf *copy;
2003 #if defined(WITH_OPENSSL) && defined(OPENSSL_HAS_ECC)
2004         EC_POINT *q = NULL;
2005 #endif /* WITH_OPENSSL && OPENSSL_HAS_ECC */
2006
2007 #ifdef DEBUG_PK /* XXX */
2008         sshbuf_dump(b, stderr);
2009 #endif
2010         *keyp = NULL;
2011         if ((copy = sshbuf_fromb(b)) == NULL) {
2012                 ret = SSH_ERR_ALLOC_FAIL;
2013                 goto out;
2014         }
2015         if (sshbuf_get_cstring(b, &ktype, NULL) != 0) {
2016                 ret = SSH_ERR_INVALID_FORMAT;
2017                 goto out;
2018         }
2019
2020         type = sshkey_type_from_name(ktype);
2021         if (!allow_cert && sshkey_type_is_cert(type)) {
2022                 ret = SSH_ERR_KEY_CERT_INVALID_SIGN_KEY;
2023                 goto out;
2024         }
2025         switch (type) {
2026 #ifdef WITH_OPENSSL
2027         case KEY_RSA_CERT:
2028                 /* Skip nonce */
2029                 if (sshbuf_get_string_direct(b, NULL, NULL) != 0) {
2030                         ret = SSH_ERR_INVALID_FORMAT;
2031                         goto out;
2032                 }
2033                 /* FALLTHROUGH */
2034         case KEY_RSA:
2035         case KEY_RSA_CERT_V00:
2036                 if ((key = sshkey_new(type)) == NULL) {
2037                         ret = SSH_ERR_ALLOC_FAIL;
2038                         goto out;
2039                 }
2040                 if (sshbuf_get_bignum2(b, key->rsa->e) != 0 ||
2041                     sshbuf_get_bignum2(b, key->rsa->n) != 0) {
2042                         ret = SSH_ERR_INVALID_FORMAT;
2043                         goto out;
2044                 }
2045 #ifdef DEBUG_PK
2046                 RSA_print_fp(stderr, key->rsa, 8);
2047 #endif
2048                 break;
2049         case KEY_DSA_CERT:
2050                 /* Skip nonce */
2051                 if (sshbuf_get_string_direct(b, NULL, NULL) != 0) {
2052                         ret = SSH_ERR_INVALID_FORMAT;
2053                         goto out;
2054                 }
2055                 /* FALLTHROUGH */
2056         case KEY_DSA:
2057         case KEY_DSA_CERT_V00:
2058                 if ((key = sshkey_new(type)) == NULL) {
2059                         ret = SSH_ERR_ALLOC_FAIL;
2060                         goto out;
2061                 }
2062                 if (sshbuf_get_bignum2(b, key->dsa->p) != 0 ||
2063                     sshbuf_get_bignum2(b, key->dsa->q) != 0 ||
2064                     sshbuf_get_bignum2(b, key->dsa->g) != 0 ||
2065                     sshbuf_get_bignum2(b, key->dsa->pub_key) != 0) {
2066                         ret = SSH_ERR_INVALID_FORMAT;
2067                         goto out;
2068                 }
2069 #ifdef DEBUG_PK
2070                 DSA_print_fp(stderr, key->dsa, 8);
2071 #endif
2072                 break;
2073         case KEY_ECDSA_CERT:
2074                 /* Skip nonce */
2075                 if (sshbuf_get_string_direct(b, NULL, NULL) != 0) {
2076                         ret = SSH_ERR_INVALID_FORMAT;
2077                         goto out;
2078                 }
2079                 /* FALLTHROUGH */
2080 # ifdef OPENSSL_HAS_ECC
2081         case KEY_ECDSA:
2082                 if ((key = sshkey_new(type)) == NULL) {
2083                         ret = SSH_ERR_ALLOC_FAIL;
2084                         goto out;
2085                 }
2086                 key->ecdsa_nid = sshkey_ecdsa_nid_from_name(ktype);
2087                 if (sshbuf_get_cstring(b, &curve, NULL) != 0) {
2088                         ret = SSH_ERR_INVALID_FORMAT;
2089                         goto out;
2090                 }
2091                 if (key->ecdsa_nid != sshkey_curve_name_to_nid(curve)) {
2092                         ret = SSH_ERR_EC_CURVE_MISMATCH;
2093                         goto out;
2094                 }
2095                 if (key->ecdsa != NULL)
2096                         EC_KEY_free(key->ecdsa);
2097                 if ((key->ecdsa = EC_KEY_new_by_curve_name(key->ecdsa_nid))
2098                     == NULL) {
2099                         ret = SSH_ERR_EC_CURVE_INVALID;
2100                         goto out;
2101                 }
2102                 if ((q = EC_POINT_new(EC_KEY_get0_group(key->ecdsa))) == NULL) {
2103                         ret = SSH_ERR_ALLOC_FAIL;
2104                         goto out;
2105                 }
2106                 if (sshbuf_get_ec(b, q, EC_KEY_get0_group(key->ecdsa)) != 0) {
2107                         ret = SSH_ERR_INVALID_FORMAT;
2108                         goto out;
2109                 }
2110                 if (sshkey_ec_validate_public(EC_KEY_get0_group(key->ecdsa),
2111                     q) != 0) {
2112                         ret = SSH_ERR_KEY_INVALID_EC_VALUE;
2113                         goto out;
2114                 }
2115                 if (EC_KEY_set_public_key(key->ecdsa, q) != 1) {
2116                         /* XXX assume it is a allocation error */
2117                         ret = SSH_ERR_ALLOC_FAIL;
2118                         goto out;
2119                 }
2120 #ifdef DEBUG_PK
2121                 sshkey_dump_ec_point(EC_KEY_get0_group(key->ecdsa), q);
2122 #endif
2123                 break;
2124 # endif /* OPENSSL_HAS_ECC */
2125 #endif /* WITH_OPENSSL */
2126         case KEY_ED25519_CERT:
2127                 /* Skip nonce */
2128                 if (sshbuf_get_string_direct(b, NULL, NULL) != 0) {
2129                         ret = SSH_ERR_INVALID_FORMAT;
2130                         goto out;
2131                 }
2132                 /* FALLTHROUGH */
2133         case KEY_ED25519:
2134                 if ((ret = sshbuf_get_string(b, &pk, &len)) != 0)
2135                         goto out;
2136                 if (len != ED25519_PK_SZ) {
2137                         ret = SSH_ERR_INVALID_FORMAT;
2138                         goto out;
2139                 }
2140                 if ((key = sshkey_new(type)) == NULL) {
2141                         ret = SSH_ERR_ALLOC_FAIL;
2142                         goto out;
2143                 }
2144                 key->ed25519_pk = pk;
2145                 pk = NULL;
2146                 break;
2147         case KEY_UNSPEC:
2148                 if ((key = sshkey_new(type)) == NULL) {
2149                         ret = SSH_ERR_ALLOC_FAIL;
2150                         goto out;
2151                 }
2152                 break;
2153         default:
2154                 ret = SSH_ERR_KEY_TYPE_UNKNOWN;
2155                 goto out;
2156         }
2157
2158         /* Parse certificate potion */
2159         if (sshkey_is_cert(key) && (ret = cert_parse(b, key, copy)) != 0)
2160                 goto out;
2161
2162         if (key != NULL && sshbuf_len(b) != 0) {
2163                 ret = SSH_ERR_INVALID_FORMAT;
2164                 goto out;
2165         }
2166         ret = 0;
2167         *keyp = key;
2168         key = NULL;
2169  out:
2170         sshbuf_free(copy);
2171         sshkey_free(key);
2172         free(ktype);
2173         free(curve);
2174         free(pk);
2175 #if defined(WITH_OPENSSL) && defined(OPENSSL_HAS_ECC)
2176         if (q != NULL)
2177                 EC_POINT_free(q);
2178 #endif /* WITH_OPENSSL && OPENSSL_HAS_ECC */
2179         return ret;
2180 }
2181
2182 int
2183 sshkey_from_blob(const u_char *blob, size_t blen, struct sshkey **keyp)
2184 {
2185         struct sshbuf *b;
2186         int r;
2187
2188         if ((b = sshbuf_from(blob, blen)) == NULL)
2189                 return SSH_ERR_ALLOC_FAIL;
2190         r = sshkey_from_blob_internal(b, keyp, 1);
2191         sshbuf_free(b);
2192         return r;
2193 }
2194
2195 int
2196 sshkey_fromb(struct sshbuf *b, struct sshkey **keyp)
2197 {
2198         return sshkey_from_blob_internal(b, keyp, 1);
2199 }
2200
2201 int
2202 sshkey_froms(struct sshbuf *buf, struct sshkey **keyp)
2203 {
2204         struct sshbuf *b;
2205         int r;
2206
2207         if ((r = sshbuf_froms(buf, &b)) != 0)
2208                 return r;
2209         r = sshkey_from_blob_internal(b, keyp, 1);
2210         sshbuf_free(b);
2211         return r;
2212 }
2213
2214 int
2215 sshkey_sign(const struct sshkey *key,
2216     u_char **sigp, size_t *lenp,
2217     const u_char *data, size_t datalen, u_int compat)
2218 {
2219         if (sigp != NULL)
2220                 *sigp = NULL;
2221         if (lenp != NULL)
2222                 *lenp = 0;
2223         if (datalen > SSH_KEY_MAX_SIGN_DATA_SIZE)
2224                 return SSH_ERR_INVALID_ARGUMENT;
2225         switch (key->type) {
2226 #ifdef WITH_OPENSSL
2227         case KEY_DSA_CERT_V00:
2228         case KEY_DSA_CERT:
2229         case KEY_DSA:
2230                 return ssh_dss_sign(key, sigp, lenp, data, datalen, compat);
2231 # ifdef OPENSSL_HAS_ECC
2232         case KEY_ECDSA_CERT:
2233         case KEY_ECDSA:
2234                 return ssh_ecdsa_sign(key, sigp, lenp, data, datalen, compat);
2235 # endif /* OPENSSL_HAS_ECC */
2236         case KEY_RSA_CERT_V00:
2237         case KEY_RSA_CERT:
2238         case KEY_RSA:
2239                 return ssh_rsa_sign(key, sigp, lenp, data, datalen, compat);
2240 #endif /* WITH_OPENSSL */
2241         case KEY_ED25519:
2242         case KEY_ED25519_CERT:
2243                 return ssh_ed25519_sign(key, sigp, lenp, data, datalen, compat);
2244         default:
2245                 return SSH_ERR_KEY_TYPE_UNKNOWN;
2246         }
2247 }
2248
2249 /*
2250  * ssh_key_verify returns 0 for a correct signature  and < 0 on error.
2251  */
2252 int
2253 sshkey_verify(const struct sshkey *key,
2254     const u_char *sig, size_t siglen,
2255     const u_char *data, size_t dlen, u_int compat)
2256 {
2257         if (siglen == 0 || dlen > SSH_KEY_MAX_SIGN_DATA_SIZE)
2258                 return SSH_ERR_INVALID_ARGUMENT;
2259         switch (key->type) {
2260 #ifdef WITH_OPENSSL
2261         case KEY_DSA_CERT_V00:
2262         case KEY_DSA_CERT:
2263         case KEY_DSA:
2264                 return ssh_dss_verify(key, sig, siglen, data, dlen, compat);
2265 # ifdef OPENSSL_HAS_ECC
2266         case KEY_ECDSA_CERT:
2267         case KEY_ECDSA:
2268                 return ssh_ecdsa_verify(key, sig, siglen, data, dlen, compat);
2269 # endif /* OPENSSL_HAS_ECC */
2270         case KEY_RSA_CERT_V00:
2271         case KEY_RSA_CERT:
2272         case KEY_RSA:
2273                 return ssh_rsa_verify(key, sig, siglen, data, dlen, compat);
2274 #endif /* WITH_OPENSSL */
2275         case KEY_ED25519:
2276         case KEY_ED25519_CERT:
2277                 return ssh_ed25519_verify(key, sig, siglen, data, dlen, compat);
2278         default:
2279                 return SSH_ERR_KEY_TYPE_UNKNOWN;
2280         }
2281 }
2282
2283 /* Converts a private to a public key */
2284 int
2285 sshkey_demote(const struct sshkey *k, struct sshkey **dkp)
2286 {
2287         struct sshkey *pk;
2288         int ret = SSH_ERR_INTERNAL_ERROR;
2289
2290         if (dkp != NULL)
2291                 *dkp = NULL;
2292
2293         if ((pk = calloc(1, sizeof(*pk))) == NULL)
2294                 return SSH_ERR_ALLOC_FAIL;
2295         pk->type = k->type;
2296         pk->flags = k->flags;
2297         pk->ecdsa_nid = k->ecdsa_nid;
2298         pk->dsa = NULL;
2299         pk->ecdsa = NULL;
2300         pk->rsa = NULL;
2301         pk->ed25519_pk = NULL;
2302         pk->ed25519_sk = NULL;
2303
2304         switch (k->type) {
2305 #ifdef WITH_OPENSSL
2306         case KEY_RSA_CERT_V00:
2307         case KEY_RSA_CERT:
2308                 if ((ret = sshkey_cert_copy(k, pk)) != 0)
2309                         goto fail;
2310                 /* FALLTHROUGH */
2311         case KEY_RSA1:
2312         case KEY_RSA:
2313                 if ((pk->rsa = RSA_new()) == NULL ||
2314                     (pk->rsa->e = BN_dup(k->rsa->e)) == NULL ||
2315                     (pk->rsa->n = BN_dup(k->rsa->n)) == NULL) {
2316                         ret = SSH_ERR_ALLOC_FAIL;
2317                         goto fail;
2318                         }
2319                 break;
2320         case KEY_DSA_CERT_V00:
2321         case KEY_DSA_CERT:
2322                 if ((ret = sshkey_cert_copy(k, pk)) != 0)
2323                         goto fail;
2324                 /* FALLTHROUGH */
2325         case KEY_DSA:
2326                 if ((pk->dsa = DSA_new()) == NULL ||
2327                     (pk->dsa->p = BN_dup(k->dsa->p)) == NULL ||
2328                     (pk->dsa->q = BN_dup(k->dsa->q)) == NULL ||
2329                     (pk->dsa->g = BN_dup(k->dsa->g)) == NULL ||
2330                     (pk->dsa->pub_key = BN_dup(k->dsa->pub_key)) == NULL) {
2331                         ret = SSH_ERR_ALLOC_FAIL;
2332                         goto fail;
2333                 }
2334                 break;
2335         case KEY_ECDSA_CERT:
2336                 if ((ret = sshkey_cert_copy(k, pk)) != 0)
2337                         goto fail;
2338                 /* FALLTHROUGH */
2339 # ifdef OPENSSL_HAS_ECC
2340         case KEY_ECDSA:
2341                 pk->ecdsa = EC_KEY_new_by_curve_name(pk->ecdsa_nid);
2342                 if (pk->ecdsa == NULL) {
2343                         ret = SSH_ERR_ALLOC_FAIL;
2344                         goto fail;
2345                 }
2346                 if (EC_KEY_set_public_key(pk->ecdsa,
2347                     EC_KEY_get0_public_key(k->ecdsa)) != 1) {
2348                         ret = SSH_ERR_LIBCRYPTO_ERROR;
2349                         goto fail;
2350                 }
2351                 break;
2352 # endif /* OPENSSL_HAS_ECC */
2353 #endif /* WITH_OPENSSL */
2354         case KEY_ED25519_CERT:
2355                 if ((ret = sshkey_cert_copy(k, pk)) != 0)
2356                         goto fail;
2357                 /* FALLTHROUGH */
2358         case KEY_ED25519:
2359                 if (k->ed25519_pk != NULL) {
2360                         if ((pk->ed25519_pk = malloc(ED25519_PK_SZ)) == NULL) {
2361                                 ret = SSH_ERR_ALLOC_FAIL;
2362                                 goto fail;
2363                         }
2364                         memcpy(pk->ed25519_pk, k->ed25519_pk, ED25519_PK_SZ);
2365                 }
2366                 break;
2367         default:
2368                 ret = SSH_ERR_KEY_TYPE_UNKNOWN;
2369  fail:
2370                 sshkey_free(pk);
2371                 return ret;
2372         }
2373         *dkp = pk;
2374         return 0;
2375 }
2376
2377 /* Convert a plain key to their _CERT equivalent */
2378 int
2379 sshkey_to_certified(struct sshkey *k, int legacy)
2380 {
2381         int newtype;
2382
2383         switch (k->type) {
2384 #ifdef WITH_OPENSSL
2385         case KEY_RSA:
2386                 newtype = legacy ? KEY_RSA_CERT_V00 : KEY_RSA_CERT;
2387                 break;
2388         case KEY_DSA:
2389                 newtype = legacy ? KEY_DSA_CERT_V00 : KEY_DSA_CERT;
2390                 break;
2391         case KEY_ECDSA:
2392                 if (legacy)
2393                         return SSH_ERR_INVALID_ARGUMENT;
2394                 newtype = KEY_ECDSA_CERT;
2395                 break;
2396 #endif /* WITH_OPENSSL */
2397         case KEY_ED25519:
2398                 if (legacy)
2399                         return SSH_ERR_INVALID_ARGUMENT;
2400                 newtype = KEY_ED25519_CERT;
2401                 break;
2402         default:
2403                 return SSH_ERR_INVALID_ARGUMENT;
2404         }
2405         if ((k->cert = cert_new()) == NULL)
2406                 return SSH_ERR_ALLOC_FAIL;
2407         k->type = newtype;
2408         return 0;
2409 }
2410
2411 /* Convert a certificate to its raw key equivalent */
2412 int
2413 sshkey_drop_cert(struct sshkey *k)
2414 {
2415         if (!sshkey_type_is_cert(k->type))
2416                 return SSH_ERR_KEY_TYPE_UNKNOWN;
2417         cert_free(k->cert);
2418         k->cert = NULL;
2419         k->type = sshkey_type_plain(k->type);
2420         return 0;
2421 }
2422
2423 /* Sign a certified key, (re-)generating the signed certblob. */
2424 int
2425 sshkey_certify(struct sshkey *k, struct sshkey *ca)
2426 {
2427         struct sshbuf *principals = NULL;
2428         u_char *ca_blob = NULL, *sig_blob = NULL, nonce[32];
2429         size_t i, ca_len, sig_len;
2430         int ret = SSH_ERR_INTERNAL_ERROR;
2431         struct sshbuf *cert;
2432
2433         if (k == NULL || k->cert == NULL ||
2434             k->cert->certblob == NULL || ca == NULL)
2435                 return SSH_ERR_INVALID_ARGUMENT;
2436         if (!sshkey_is_cert(k))
2437                 return SSH_ERR_KEY_TYPE_UNKNOWN;
2438         if (!sshkey_type_is_valid_ca(ca->type))
2439                 return SSH_ERR_KEY_CERT_INVALID_SIGN_KEY;
2440
2441         if ((ret = sshkey_to_blob(ca, &ca_blob, &ca_len)) != 0)
2442                 return SSH_ERR_KEY_CERT_INVALID_SIGN_KEY;
2443
2444         cert = k->cert->certblob; /* for readability */
2445         sshbuf_reset(cert);
2446         if ((ret = sshbuf_put_cstring(cert, sshkey_ssh_name(k))) != 0)
2447                 goto out;
2448
2449         /* -v01 certs put nonce first */
2450         arc4random_buf(&nonce, sizeof(nonce));
2451         if (!sshkey_cert_is_legacy(k)) {
2452                 if ((ret = sshbuf_put_string(cert, nonce, sizeof(nonce))) != 0)
2453                         goto out;
2454         }
2455
2456         /* XXX this substantially duplicates to_blob(); refactor */
2457         switch (k->type) {
2458 #ifdef WITH_OPENSSL
2459         case KEY_DSA_CERT_V00:
2460         case KEY_DSA_CERT:
2461                 if ((ret = sshbuf_put_bignum2(cert, k->dsa->p)) != 0 ||
2462                     (ret = sshbuf_put_bignum2(cert, k->dsa->q)) != 0 ||
2463                     (ret = sshbuf_put_bignum2(cert, k->dsa->g)) != 0 ||
2464                     (ret = sshbuf_put_bignum2(cert, k->dsa->pub_key)) != 0)
2465                         goto out;
2466                 break;
2467 # ifdef OPENSSL_HAS_ECC
2468         case KEY_ECDSA_CERT:
2469                 if ((ret = sshbuf_put_cstring(cert,
2470                     sshkey_curve_nid_to_name(k->ecdsa_nid))) != 0 ||
2471                     (ret = sshbuf_put_ec(cert,
2472                     EC_KEY_get0_public_key(k->ecdsa),
2473                     EC_KEY_get0_group(k->ecdsa))) != 0)
2474                         goto out;
2475                 break;
2476 # endif /* OPENSSL_HAS_ECC */
2477         case KEY_RSA_CERT_V00:
2478         case KEY_RSA_CERT:
2479                 if ((ret = sshbuf_put_bignum2(cert, k->rsa->e)) != 0 ||
2480                     (ret = sshbuf_put_bignum2(cert, k->rsa->n)) != 0)
2481                         goto out;
2482                 break;
2483 #endif /* WITH_OPENSSL */
2484         case KEY_ED25519_CERT:
2485                 if ((ret = sshbuf_put_string(cert,
2486                     k->ed25519_pk, ED25519_PK_SZ)) != 0)
2487                         goto out;
2488                 break;
2489         default:
2490                 ret = SSH_ERR_INVALID_ARGUMENT;
2491                 goto out;
2492         }
2493
2494         /* -v01 certs have a serial number next */
2495         if (!sshkey_cert_is_legacy(k)) {
2496                 if ((ret = sshbuf_put_u64(cert, k->cert->serial)) != 0)
2497                         goto out;
2498         }
2499
2500         if ((ret = sshbuf_put_u32(cert, k->cert->type)) != 0 ||
2501             (ret = sshbuf_put_cstring(cert, k->cert->key_id)) != 0)
2502                 goto out;
2503
2504         if ((principals = sshbuf_new()) == NULL) {
2505                 ret = SSH_ERR_ALLOC_FAIL;
2506                 goto out;
2507         }
2508         for (i = 0; i < k->cert->nprincipals; i++) {
2509                 if ((ret = sshbuf_put_cstring(principals,
2510                     k->cert->principals[i])) != 0)
2511                         goto out;
2512         }
2513         if ((ret = sshbuf_put_stringb(cert, principals)) != 0 ||
2514             (ret = sshbuf_put_u64(cert, k->cert->valid_after)) != 0 ||
2515             (ret = sshbuf_put_u64(cert, k->cert->valid_before)) != 0 ||
2516             (ret = sshbuf_put_stringb(cert, k->cert->critical)) != 0)
2517                 goto out;
2518
2519         /* -v01 certs have non-critical options here */
2520         if (!sshkey_cert_is_legacy(k)) {
2521                 if ((ret = sshbuf_put_stringb(cert, k->cert->extensions)) != 0)
2522                         goto out;
2523         }
2524
2525         /* -v00 certs put the nonce at the end */
2526         if (sshkey_cert_is_legacy(k)) {
2527                 if ((ret = sshbuf_put_string(cert, nonce, sizeof(nonce))) != 0)
2528                         goto out;
2529         }
2530
2531         if ((ret = sshbuf_put_string(cert, NULL, 0)) != 0 || /* Reserved */
2532             (ret = sshbuf_put_string(cert, ca_blob, ca_len)) != 0)
2533                 goto out;
2534
2535         /* Sign the whole mess */
2536         if ((ret = sshkey_sign(ca, &sig_blob, &sig_len, sshbuf_ptr(cert),
2537             sshbuf_len(cert), 0)) != 0)
2538                 goto out;
2539
2540         /* Append signature and we are done */
2541         if ((ret = sshbuf_put_string(cert, sig_blob, sig_len)) != 0)
2542                 goto out;
2543         ret = 0;
2544  out:
2545         if (ret != 0)
2546                 sshbuf_reset(cert);
2547         if (sig_blob != NULL)
2548                 free(sig_blob);
2549         if (ca_blob != NULL)
2550                 free(ca_blob);
2551         if (principals != NULL)
2552                 sshbuf_free(principals);
2553         return ret;
2554 }
2555
2556 int
2557 sshkey_cert_check_authority(const struct sshkey *k,
2558     int want_host, int require_principal,
2559     const char *name, const char **reason)
2560 {
2561         u_int i, principal_matches;
2562         time_t now = time(NULL);
2563
2564         if (reason != NULL)
2565                 *reason = NULL;
2566
2567         if (want_host) {
2568                 if (k->cert->type != SSH2_CERT_TYPE_HOST) {
2569                         *reason = "Certificate invalid: not a host certificate";
2570                         return SSH_ERR_KEY_CERT_INVALID;
2571                 }
2572         } else {
2573                 if (k->cert->type != SSH2_CERT_TYPE_USER) {
2574                         *reason = "Certificate invalid: not a user certificate";
2575                         return SSH_ERR_KEY_CERT_INVALID;
2576                 }
2577         }
2578         if (now < 0) {
2579                 /* yikes - system clock before epoch! */
2580                 *reason = "Certificate invalid: not yet valid";
2581                 return SSH_ERR_KEY_CERT_INVALID;
2582         }
2583         if ((u_int64_t)now < k->cert->valid_after) {
2584                 *reason = "Certificate invalid: not yet valid";
2585                 return SSH_ERR_KEY_CERT_INVALID;
2586         }
2587         if ((u_int64_t)now >= k->cert->valid_before) {
2588                 *reason = "Certificate invalid: expired";
2589                 return SSH_ERR_KEY_CERT_INVALID;
2590         }
2591         if (k->cert->nprincipals == 0) {
2592                 if (require_principal) {
2593                         *reason = "Certificate lacks principal list";
2594                         return SSH_ERR_KEY_CERT_INVALID;
2595                 }
2596         } else if (name != NULL) {
2597                 principal_matches = 0;
2598                 for (i = 0; i < k->cert->nprincipals; i++) {
2599                         if (strcmp(name, k->cert->principals[i]) == 0) {
2600                                 principal_matches = 1;
2601                                 break;
2602                         }
2603                 }
2604                 if (!principal_matches) {
2605                         *reason = "Certificate invalid: name is not a listed "
2606                             "principal";
2607                         return SSH_ERR_KEY_CERT_INVALID;
2608                 }
2609         }
2610         return 0;
2611 }
2612
2613 int
2614 sshkey_private_serialize(const struct sshkey *key, struct sshbuf *b)
2615 {
2616         int r = SSH_ERR_INTERNAL_ERROR;
2617
2618         if ((r = sshbuf_put_cstring(b, sshkey_ssh_name(key))) != 0)
2619                 goto out;
2620         switch (key->type) {
2621 #ifdef WITH_OPENSSL
2622         case KEY_RSA:
2623                 if ((r = sshbuf_put_bignum2(b, key->rsa->n)) != 0 ||
2624                     (r = sshbuf_put_bignum2(b, key->rsa->e)) != 0 ||
2625                     (r = sshbuf_put_bignum2(b, key->rsa->d)) != 0 ||
2626                     (r = sshbuf_put_bignum2(b, key->rsa->iqmp)) != 0 ||
2627                     (r = sshbuf_put_bignum2(b, key->rsa->p)) != 0 ||
2628                     (r = sshbuf_put_bignum2(b, key->rsa->q)) != 0)
2629                         goto out;
2630                 break;
2631         case KEY_RSA_CERT_V00:
2632         case KEY_RSA_CERT:
2633                 if (key->cert == NULL || sshbuf_len(key->cert->certblob) == 0) {
2634                         r = SSH_ERR_INVALID_ARGUMENT;
2635                         goto out;
2636                 }
2637                 if ((r = sshbuf_put_stringb(b, key->cert->certblob)) != 0 ||
2638                     (r = sshbuf_put_bignum2(b, key->rsa->d)) != 0 ||
2639                     (r = sshbuf_put_bignum2(b, key->rsa->iqmp)) != 0 ||
2640                     (r = sshbuf_put_bignum2(b, key->rsa->p)) != 0 ||
2641                     (r = sshbuf_put_bignum2(b, key->rsa->q)) != 0)
2642                         goto out;
2643                 break;
2644         case KEY_DSA:
2645                 if ((r = sshbuf_put_bignum2(b, key->dsa->p)) != 0 ||
2646                     (r = sshbuf_put_bignum2(b, key->dsa->q)) != 0 ||
2647                     (r = sshbuf_put_bignum2(b, key->dsa->g)) != 0 ||
2648                     (r = sshbuf_put_bignum2(b, key->dsa->pub_key)) != 0 ||
2649                     (r = sshbuf_put_bignum2(b, key->dsa->priv_key)) != 0)
2650                         goto out;
2651                 break;
2652         case KEY_DSA_CERT_V00:
2653         case KEY_DSA_CERT:
2654                 if (key->cert == NULL || sshbuf_len(key->cert->certblob) == 0) {
2655                         r = SSH_ERR_INVALID_ARGUMENT;
2656                         goto out;
2657                 }
2658                 if ((r = sshbuf_put_stringb(b, key->cert->certblob)) != 0 ||
2659                     (r = sshbuf_put_bignum2(b, key->dsa->priv_key)) != 0)
2660                         goto out;
2661                 break;
2662 # ifdef OPENSSL_HAS_ECC
2663         case KEY_ECDSA:
2664                 if ((r = sshbuf_put_cstring(b,
2665                     sshkey_curve_nid_to_name(key->ecdsa_nid))) != 0 ||
2666                     (r = sshbuf_put_eckey(b, key->ecdsa)) != 0 ||
2667                     (r = sshbuf_put_bignum2(b,
2668                     EC_KEY_get0_private_key(key->ecdsa))) != 0)
2669                         goto out;
2670                 break;
2671         case KEY_ECDSA_CERT:
2672                 if (key->cert == NULL || sshbuf_len(key->cert->certblob) == 0) {
2673                         r = SSH_ERR_INVALID_ARGUMENT;
2674                         goto out;
2675                 }
2676                 if ((r = sshbuf_put_stringb(b, key->cert->certblob)) != 0 ||
2677                     (r = sshbuf_put_bignum2(b,
2678                     EC_KEY_get0_private_key(key->ecdsa))) != 0)
2679                         goto out;
2680                 break;
2681 # endif /* OPENSSL_HAS_ECC */
2682 #endif /* WITH_OPENSSL */
2683         case KEY_ED25519:
2684                 if ((r = sshbuf_put_string(b, key->ed25519_pk,
2685                     ED25519_PK_SZ)) != 0 ||
2686                     (r = sshbuf_put_string(b, key->ed25519_sk,
2687                     ED25519_SK_SZ)) != 0)
2688                         goto out;
2689                 break;
2690         case KEY_ED25519_CERT:
2691                 if (key->cert == NULL || sshbuf_len(key->cert->certblob) == 0) {
2692                         r = SSH_ERR_INVALID_ARGUMENT;
2693                         goto out;
2694                 }
2695                 if ((r = sshbuf_put_stringb(b, key->cert->certblob)) != 0 ||
2696                     (r = sshbuf_put_string(b, key->ed25519_pk,
2697                     ED25519_PK_SZ)) != 0 ||
2698                     (r = sshbuf_put_string(b, key->ed25519_sk,
2699                     ED25519_SK_SZ)) != 0)
2700                         goto out;
2701                 break;
2702         default:
2703                 r = SSH_ERR_INVALID_ARGUMENT;
2704                 goto out;
2705         }
2706         /* success */
2707         r = 0;
2708  out:
2709         return r;
2710 }
2711
2712 int
2713 sshkey_private_deserialize(struct sshbuf *buf, struct sshkey **kp)
2714 {
2715         char *tname = NULL, *curve = NULL;
2716         struct sshkey *k = NULL;
2717         size_t pklen = 0, sklen = 0;
2718         int type, r = SSH_ERR_INTERNAL_ERROR;
2719         u_char *ed25519_pk = NULL, *ed25519_sk = NULL;
2720 #ifdef WITH_OPENSSL
2721         BIGNUM *exponent = NULL;
2722 #endif /* WITH_OPENSSL */
2723
2724         if (kp != NULL)
2725                 *kp = NULL;
2726         if ((r = sshbuf_get_cstring(buf, &tname, NULL)) != 0)
2727                 goto out;
2728         type = sshkey_type_from_name(tname);
2729         switch (type) {
2730 #ifdef WITH_OPENSSL
2731         case KEY_DSA:
2732                 if ((k = sshkey_new_private(type)) == NULL) {
2733                         r = SSH_ERR_ALLOC_FAIL;
2734                         goto out;
2735                 }
2736                 if ((r = sshbuf_get_bignum2(buf, k->dsa->p)) != 0 ||
2737                     (r = sshbuf_get_bignum2(buf, k->dsa->q)) != 0 ||
2738                     (r = sshbuf_get_bignum2(buf, k->dsa->g)) != 0 ||
2739                     (r = sshbuf_get_bignum2(buf, k->dsa->pub_key)) != 0 ||
2740                     (r = sshbuf_get_bignum2(buf, k->dsa->priv_key)) != 0)
2741                         goto out;
2742                 break;
2743         case KEY_DSA_CERT_V00:
2744         case KEY_DSA_CERT:
2745                 if ((r = sshkey_froms(buf, &k)) != 0 ||
2746                     (r = sshkey_add_private(k)) != 0 ||
2747                     (r = sshbuf_get_bignum2(buf, k->dsa->priv_key)) != 0)
2748                         goto out;
2749                 break;
2750 # ifdef OPENSSL_HAS_ECC
2751         case KEY_ECDSA:
2752                 if ((k = sshkey_new_private(type)) == NULL) {
2753                         r = SSH_ERR_ALLOC_FAIL;
2754                         goto out;
2755                 }
2756                 if ((k->ecdsa_nid = sshkey_ecdsa_nid_from_name(tname)) == -1) {
2757                         r = SSH_ERR_INVALID_ARGUMENT;
2758                         goto out;
2759                 }
2760                 if ((r = sshbuf_get_cstring(buf, &curve, NULL)) != 0)
2761                         goto out;
2762                 if (k->ecdsa_nid != sshkey_curve_name_to_nid(curve)) {
2763                         r = SSH_ERR_EC_CURVE_MISMATCH;
2764                         goto out;
2765                 }
2766                 k->ecdsa = EC_KEY_new_by_curve_name(k->ecdsa_nid);
2767                 if (k->ecdsa  == NULL || (exponent = BN_new()) == NULL) {
2768                         r = SSH_ERR_LIBCRYPTO_ERROR;
2769                         goto out;
2770                 }
2771                 if ((r = sshbuf_get_eckey(buf, k->ecdsa)) != 0 ||
2772                     (r = sshbuf_get_bignum2(buf, exponent)))
2773                         goto out;
2774                 if (EC_KEY_set_private_key(k->ecdsa, exponent) != 1) {
2775                         r = SSH_ERR_LIBCRYPTO_ERROR;
2776                         goto out;
2777                 }
2778                 if ((r = sshkey_ec_validate_public(EC_KEY_get0_group(k->ecdsa),
2779                     EC_KEY_get0_public_key(k->ecdsa)) != 0) ||
2780                     (r = sshkey_ec_validate_private(k->ecdsa)) != 0)
2781                         goto out;
2782                 break;
2783         case KEY_ECDSA_CERT:
2784                 if ((exponent = BN_new()) == NULL) {
2785                         r = SSH_ERR_LIBCRYPTO_ERROR;
2786                         goto out;
2787                 }
2788                 if ((r = sshkey_froms(buf, &k)) != 0 ||
2789                     (r = sshkey_add_private(k)) != 0 ||
2790                     (r = sshbuf_get_bignum2(buf, exponent)) != 0)
2791                         goto out;
2792                 if (EC_KEY_set_private_key(k->ecdsa, exponent) != 1) {
2793                         r = SSH_ERR_LIBCRYPTO_ERROR;
2794                         goto out;
2795                 }
2796                 if ((r = sshkey_ec_validate_public(EC_KEY_get0_group(k->ecdsa),
2797                     EC_KEY_get0_public_key(k->ecdsa)) != 0) ||
2798                     (r = sshkey_ec_validate_private(k->ecdsa)) != 0)
2799                         goto out;
2800                 break;
2801 # endif /* OPENSSL_HAS_ECC */
2802         case KEY_RSA:
2803                 if ((k = sshkey_new_private(type)) == NULL) {
2804                         r = SSH_ERR_ALLOC_FAIL;
2805                         goto out;
2806                 }
2807                 if ((r = sshbuf_get_bignum2(buf, k->rsa->n)) != 0 ||
2808                     (r = sshbuf_get_bignum2(buf, k->rsa->e)) != 0 ||
2809                     (r = sshbuf_get_bignum2(buf, k->rsa->d)) != 0 ||
2810                     (r = sshbuf_get_bignum2(buf, k->rsa->iqmp)) != 0 ||
2811                     (r = sshbuf_get_bignum2(buf, k->rsa->p)) != 0 ||
2812                     (r = sshbuf_get_bignum2(buf, k->rsa->q)) != 0 ||
2813                     (r = rsa_generate_additional_parameters(k->rsa)) != 0)
2814                         goto out;
2815                 break;
2816         case KEY_RSA_CERT_V00:
2817         case KEY_RSA_CERT:
2818                 if ((r = sshkey_froms(buf, &k)) != 0 ||
2819                     (r = sshkey_add_private(k)) != 0 ||
2820                     (r = sshbuf_get_bignum2(buf, k->rsa->d) != 0) ||
2821                     (r = sshbuf_get_bignum2(buf, k->rsa->iqmp) != 0) ||
2822                     (r = sshbuf_get_bignum2(buf, k->rsa->p) != 0) ||
2823                     (r = sshbuf_get_bignum2(buf, k->rsa->q) != 0) ||
2824                     (r = rsa_generate_additional_parameters(k->rsa)) != 0)
2825                         goto out;
2826                 break;
2827 #endif /* WITH_OPENSSL */
2828         case KEY_ED25519:
2829                 if ((k = sshkey_new_private(type)) == NULL) {
2830                         r = SSH_ERR_ALLOC_FAIL;
2831                         goto out;
2832                 }
2833                 if ((r = sshbuf_get_string(buf, &ed25519_pk, &pklen)) != 0 ||
2834                     (r = sshbuf_get_string(buf, &ed25519_sk, &sklen)) != 0)
2835                         goto out;
2836                 if (pklen != ED25519_PK_SZ || sklen != ED25519_SK_SZ) {
2837                         r = SSH_ERR_INVALID_FORMAT;
2838                         goto out;
2839                 }
2840                 k->ed25519_pk = ed25519_pk;
2841                 k->ed25519_sk = ed25519_sk;
2842                 ed25519_pk = ed25519_sk = NULL;
2843                 break;
2844         case KEY_ED25519_CERT:
2845                 if ((r = sshkey_froms(buf, &k)) != 0 ||
2846                     (r = sshkey_add_private(k)) != 0 ||
2847                     (r = sshbuf_get_string(buf, &ed25519_pk, &pklen)) != 0 ||
2848                     (r = sshbuf_get_string(buf, &ed25519_sk, &sklen)) != 0)
2849                         goto out;
2850                 if (pklen != ED25519_PK_SZ || sklen != ED25519_SK_SZ) {
2851                         r = SSH_ERR_INVALID_FORMAT;
2852                         goto out;
2853                 }
2854                 k->ed25519_pk = ed25519_pk;
2855                 k->ed25519_sk = ed25519_sk;
2856                 ed25519_pk = ed25519_sk = NULL;
2857                 break;
2858         default:
2859                 r = SSH_ERR_KEY_TYPE_UNKNOWN;
2860                 goto out;
2861         }
2862 #ifdef WITH_OPENSSL
2863         /* enable blinding */
2864         switch (k->type) {
2865         case KEY_RSA:
2866         case KEY_RSA_CERT_V00:
2867         case KEY_RSA_CERT:
2868         case KEY_RSA1:
2869                 if (RSA_blinding_on(k->rsa, NULL) != 1) {
2870                         r = SSH_ERR_LIBCRYPTO_ERROR;
2871                         goto out;
2872                 }
2873                 break;
2874         }
2875 #endif /* WITH_OPENSSL */
2876         /* success */
2877         r = 0;
2878         if (kp != NULL) {
2879                 *kp = k;
2880                 k = NULL;
2881         }
2882  out:
2883         free(tname);
2884         free(curve);
2885 #ifdef WITH_OPENSSL
2886         if (exponent != NULL)
2887                 BN_clear_free(exponent);
2888 #endif /* WITH_OPENSSL */
2889         sshkey_free(k);
2890         if (ed25519_pk != NULL) {
2891                 explicit_bzero(ed25519_pk, pklen);
2892                 free(ed25519_pk);
2893         }
2894         if (ed25519_sk != NULL) {
2895                 explicit_bzero(ed25519_sk, sklen);
2896                 free(ed25519_sk);
2897         }
2898         return r;
2899 }
2900
2901 #if defined(WITH_OPENSSL) && defined(OPENSSL_HAS_ECC)
2902 int
2903 sshkey_ec_validate_public(const EC_GROUP *group, const EC_POINT *public)
2904 {
2905         BN_CTX *bnctx;
2906         EC_POINT *nq = NULL;
2907         BIGNUM *order, *x, *y, *tmp;
2908         int ret = SSH_ERR_KEY_INVALID_EC_VALUE;
2909
2910         if ((bnctx = BN_CTX_new()) == NULL)
2911                 return SSH_ERR_ALLOC_FAIL;
2912         BN_CTX_start(bnctx);
2913
2914         /*
2915          * We shouldn't ever hit this case because bignum_get_ecpoint()
2916          * refuses to load GF2m points.
2917          */
2918         if (EC_METHOD_get_field_type(EC_GROUP_method_of(group)) !=
2919             NID_X9_62_prime_field)
2920                 goto out;
2921
2922         /* Q != infinity */
2923         if (EC_POINT_is_at_infinity(group, public))
2924                 goto out;
2925
2926         if ((x = BN_CTX_get(bnctx)) == NULL ||
2927             (y = BN_CTX_get(bnctx)) == NULL ||
2928             (order = BN_CTX_get(bnctx)) == NULL ||
2929             (tmp = BN_CTX_get(bnctx)) == NULL) {
2930                 ret = SSH_ERR_ALLOC_FAIL;
2931                 goto out;
2932         }
2933
2934         /* log2(x) > log2(order)/2, log2(y) > log2(order)/2 */
2935         if (EC_GROUP_get_order(group, order, bnctx) != 1 ||
2936             EC_POINT_get_affine_coordinates_GFp(group, public,
2937             x, y, bnctx) != 1) {
2938                 ret = SSH_ERR_LIBCRYPTO_ERROR;
2939                 goto out;
2940         }
2941         if (BN_num_bits(x) <= BN_num_bits(order) / 2 ||
2942             BN_num_bits(y) <= BN_num_bits(order) / 2)
2943                 goto out;
2944
2945         /* nQ == infinity (n == order of subgroup) */
2946         if ((nq = EC_POINT_new(group)) == NULL) {
2947                 ret = SSH_ERR_ALLOC_FAIL;
2948                 goto out;
2949         }
2950         if (EC_POINT_mul(group, nq, NULL, public, order, bnctx) != 1) {
2951                 ret = SSH_ERR_LIBCRYPTO_ERROR;
2952                 goto out;
2953         }
2954         if (EC_POINT_is_at_infinity(group, nq) != 1)
2955                 goto out;
2956
2957         /* x < order - 1, y < order - 1 */
2958         if (!BN_sub(tmp, order, BN_value_one())) {
2959                 ret = SSH_ERR_LIBCRYPTO_ERROR;
2960                 goto out;
2961         }
2962         if (BN_cmp(x, tmp) >= 0 || BN_cmp(y, tmp) >= 0)
2963                 goto out;
2964         ret = 0;
2965  out:
2966         BN_CTX_free(bnctx);
2967         if (nq != NULL)
2968                 EC_POINT_free(nq);
2969         return ret;
2970 }
2971
2972 int
2973 sshkey_ec_validate_private(const EC_KEY *key)
2974 {
2975         BN_CTX *bnctx;
2976         BIGNUM *order, *tmp;
2977         int ret = SSH_ERR_KEY_INVALID_EC_VALUE;
2978
2979         if ((bnctx = BN_CTX_new()) == NULL)
2980                 return SSH_ERR_ALLOC_FAIL;
2981         BN_CTX_start(bnctx);
2982
2983         if ((order = BN_CTX_get(bnctx)) == NULL ||
2984             (tmp = BN_CTX_get(bnctx)) == NULL) {
2985                 ret = SSH_ERR_ALLOC_FAIL;
2986                 goto out;
2987         }
2988
2989         /* log2(private) > log2(order)/2 */
2990         if (EC_GROUP_get_order(EC_KEY_get0_group(key), order, bnctx) != 1) {
2991                 ret = SSH_ERR_LIBCRYPTO_ERROR;
2992                 goto out;
2993         }
2994         if (BN_num_bits(EC_KEY_get0_private_key(key)) <=
2995             BN_num_bits(order) / 2)
2996                 goto out;
2997
2998         /* private < order - 1 */
2999         if (!BN_sub(tmp, order, BN_value_one())) {
3000                 ret = SSH_ERR_LIBCRYPTO_ERROR;
3001                 goto out;
3002         }
3003         if (BN_cmp(EC_KEY_get0_private_key(key), tmp) >= 0)
3004                 goto out;
3005         ret = 0;
3006  out:
3007         BN_CTX_free(bnctx);
3008         return ret;
3009 }
3010
3011 void
3012 sshkey_dump_ec_point(const EC_GROUP *group, const EC_POINT *point)
3013 {
3014         BIGNUM *x, *y;
3015         BN_CTX *bnctx;
3016
3017         if (point == NULL) {
3018                 fputs("point=(NULL)\n", stderr);
3019                 return;
3020         }
3021         if ((bnctx = BN_CTX_new()) == NULL) {
3022                 fprintf(stderr, "%s: BN_CTX_new failed\n", __func__);
3023                 return;
3024         }
3025         BN_CTX_start(bnctx);
3026         if ((x = BN_CTX_get(bnctx)) == NULL ||
3027             (y = BN_CTX_get(bnctx)) == NULL) {
3028                 fprintf(stderr, "%s: BN_CTX_get failed\n", __func__);
3029                 return;
3030         }
3031         if (EC_METHOD_get_field_type(EC_GROUP_method_of(group)) !=
3032             NID_X9_62_prime_field) {
3033                 fprintf(stderr, "%s: group is not a prime field\n", __func__);
3034                 return;
3035         }
3036         if (EC_POINT_get_affine_coordinates_GFp(group, point, x, y,
3037             bnctx) != 1) {
3038                 fprintf(stderr, "%s: EC_POINT_get_affine_coordinates_GFp\n",
3039                     __func__);
3040                 return;
3041         }
3042         fputs("x=", stderr);
3043         BN_print_fp(stderr, x);
3044         fputs("\ny=", stderr);
3045         BN_print_fp(stderr, y);
3046         fputs("\n", stderr);
3047         BN_CTX_free(bnctx);
3048 }
3049
3050 void
3051 sshkey_dump_ec_key(const EC_KEY *key)
3052 {
3053         const BIGNUM *exponent;
3054
3055         sshkey_dump_ec_point(EC_KEY_get0_group(key),
3056             EC_KEY_get0_public_key(key));
3057         fputs("exponent=", stderr);
3058         if ((exponent = EC_KEY_get0_private_key(key)) == NULL)
3059                 fputs("(NULL)", stderr);
3060         else
3061                 BN_print_fp(stderr, EC_KEY_get0_private_key(key));
3062         fputs("\n", stderr);
3063 }
3064 #endif /* WITH_OPENSSL && OPENSSL_HAS_ECC */
3065
3066 static int
3067 sshkey_private_to_blob2(const struct sshkey *prv, struct sshbuf *blob,
3068     const char *passphrase, const char *comment, const char *ciphername,
3069     int rounds)
3070 {
3071         u_char *cp, *key = NULL, *pubkeyblob = NULL;
3072         u_char salt[SALT_LEN];
3073         char *b64 = NULL;
3074         size_t i, pubkeylen, keylen, ivlen, blocksize, authlen;
3075         u_int check;
3076         int r = SSH_ERR_INTERNAL_ERROR;
3077         struct sshcipher_ctx ciphercontext;
3078         const struct sshcipher *cipher;
3079         const char *kdfname = KDFNAME;
3080         struct sshbuf *encoded = NULL, *encrypted = NULL, *kdf = NULL;
3081
3082         memset(&ciphercontext, 0, sizeof(ciphercontext));
3083
3084         if (rounds <= 0)
3085                 rounds = DEFAULT_ROUNDS;
3086         if (passphrase == NULL || !strlen(passphrase)) {
3087                 ciphername = "none";
3088                 kdfname = "none";
3089         } else if (ciphername == NULL)
3090                 ciphername = DEFAULT_CIPHERNAME;
3091         else if (cipher_number(ciphername) != SSH_CIPHER_SSH2) {
3092                 r = SSH_ERR_INVALID_ARGUMENT;
3093                 goto out;
3094         }
3095         if ((cipher = cipher_by_name(ciphername)) == NULL) {
3096                 r = SSH_ERR_INTERNAL_ERROR;
3097                 goto out;
3098         }
3099
3100         if ((kdf = sshbuf_new()) == NULL ||
3101             (encoded = sshbuf_new()) == NULL ||
3102             (encrypted = sshbuf_new()) == NULL) {
3103                 r = SSH_ERR_ALLOC_FAIL;
3104                 goto out;
3105         }
3106         blocksize = cipher_blocksize(cipher);
3107         keylen = cipher_keylen(cipher);
3108         ivlen = cipher_ivlen(cipher);
3109         authlen = cipher_authlen(cipher);
3110         if ((key = calloc(1, keylen + ivlen)) == NULL) {
3111                 r = SSH_ERR_ALLOC_FAIL;
3112                 goto out;
3113         }
3114         if (strcmp(kdfname, "bcrypt") == 0) {
3115                 arc4random_buf(salt, SALT_LEN);
3116                 if (bcrypt_pbkdf(passphrase, strlen(passphrase),
3117                     salt, SALT_LEN, key, keylen + ivlen, rounds) < 0) {
3118                         r = SSH_ERR_INVALID_ARGUMENT;
3119                         goto out;
3120                 }
3121                 if ((r = sshbuf_put_string(kdf, salt, SALT_LEN)) != 0 ||
3122                     (r = sshbuf_put_u32(kdf, rounds)) != 0)
3123                         goto out;
3124         } else if (strcmp(kdfname, "none") != 0) {
3125                 /* Unsupported KDF type */
3126                 r = SSH_ERR_KEY_UNKNOWN_CIPHER;
3127                 goto out;
3128         }
3129         if ((r = cipher_init(&ciphercontext, cipher, key, keylen,
3130             key + keylen, ivlen, 1)) != 0)
3131                 goto out;
3132
3133         if ((r = sshbuf_put(encoded, AUTH_MAGIC, sizeof(AUTH_MAGIC))) != 0 ||
3134             (r = sshbuf_put_cstring(encoded, ciphername)) != 0 ||
3135             (r = sshbuf_put_cstring(encoded, kdfname)) != 0 ||
3136             (r = sshbuf_put_stringb(encoded, kdf)) != 0 ||
3137             (r = sshbuf_put_u32(encoded, 1)) != 0 ||    /* number of keys */
3138             (r = sshkey_to_blob(prv, &pubkeyblob, &pubkeylen)) != 0 ||
3139             (r = sshbuf_put_string(encoded, pubkeyblob, pubkeylen)) != 0)
3140                 goto out;
3141
3142         /* set up the buffer that will be encrypted */
3143
3144         /* Random check bytes */
3145         check = arc4random();
3146         if ((r = sshbuf_put_u32(encrypted, check)) != 0 ||
3147             (r = sshbuf_put_u32(encrypted, check)) != 0)
3148                 goto out;
3149
3150         /* append private key and comment*/
3151         if ((r = sshkey_private_serialize(prv, encrypted)) != 0 ||
3152             (r = sshbuf_put_cstring(encrypted, comment)) != 0)
3153                 goto out;
3154
3155         /* padding */
3156         i = 0;
3157         while (sshbuf_len(encrypted) % blocksize) {
3158                 if ((r = sshbuf_put_u8(encrypted, ++i & 0xff)) != 0)
3159                         goto out;
3160         }
3161
3162         /* length in destination buffer */
3163         if ((r = sshbuf_put_u32(encoded, sshbuf_len(encrypted))) != 0)
3164                 goto out;
3165
3166         /* encrypt */
3167         if ((r = sshbuf_reserve(encoded,
3168             sshbuf_len(encrypted) + authlen, &cp)) != 0)
3169                 goto out;
3170         if ((r = cipher_crypt(&ciphercontext, 0, cp,
3171             sshbuf_ptr(encrypted), sshbuf_len(encrypted), 0, authlen)) != 0)
3172                 goto out;
3173
3174         /* uuencode */
3175         if ((b64 = sshbuf_dtob64(encoded)) == NULL) {
3176                 r = SSH_ERR_ALLOC_FAIL;
3177                 goto out;
3178         }
3179
3180         sshbuf_reset(blob);
3181         if ((r = sshbuf_put(blob, MARK_BEGIN, MARK_BEGIN_LEN)) != 0)
3182                 goto out;
3183         for (i = 0; i < strlen(b64); i++) {
3184                 if ((r = sshbuf_put_u8(blob, b64[i])) != 0)
3185                         goto out;
3186                 /* insert line breaks */
3187                 if (i % 70 == 69 && (r = sshbuf_put_u8(blob, '\n')) != 0)
3188                         goto out;
3189         }
3190         if (i % 70 != 69 && (r = sshbuf_put_u8(blob, '\n')) != 0)
3191                 goto out;
3192         if ((r = sshbuf_put(blob, MARK_END, MARK_END_LEN)) != 0)
3193                 goto out;
3194
3195         /* success */
3196         r = 0;
3197
3198  out:
3199         sshbuf_free(kdf);
3200         sshbuf_free(encoded);
3201         sshbuf_free(encrypted);
3202         cipher_cleanup(&ciphercontext);
3203         explicit_bzero(salt, sizeof(salt));
3204         if (key != NULL) {
3205                 explicit_bzero(key, keylen + ivlen);
3206                 free(key);
3207         }
3208         if (pubkeyblob != NULL) {
3209                 explicit_bzero(pubkeyblob, pubkeylen);
3210                 free(pubkeyblob);
3211         }
3212         if (b64 != NULL) {
3213                 explicit_bzero(b64, strlen(b64));
3214                 free(b64);
3215         }
3216         return r;
3217 }
3218
3219 static int
3220 sshkey_parse_private2(struct sshbuf *blob, int type, const char *passphrase,
3221     struct sshkey **keyp, char **commentp)
3222 {
3223         char *comment = NULL, *ciphername = NULL, *kdfname = NULL;
3224         const struct sshcipher *cipher = NULL;
3225         const u_char *cp;
3226         int r = SSH_ERR_INTERNAL_ERROR;
3227         size_t encoded_len;
3228         size_t i, keylen = 0, ivlen = 0, authlen = 0, slen = 0;
3229         struct sshbuf *encoded = NULL, *decoded = NULL;
3230         struct sshbuf *kdf = NULL, *decrypted = NULL;
3231         struct sshcipher_ctx ciphercontext;
3232         struct sshkey *k = NULL;
3233         u_char *key = NULL, *salt = NULL, *dp, pad, last;
3234         u_int blocksize, rounds, nkeys, encrypted_len, check1, check2;
3235
3236         memset(&ciphercontext, 0, sizeof(ciphercontext));
3237         if (keyp != NULL)
3238                 *keyp = NULL;
3239         if (commentp != NULL)
3240                 *commentp = NULL;
3241
3242         if ((encoded = sshbuf_new()) == NULL ||
3243             (decoded = sshbuf_new()) == NULL ||
3244             (decrypted = sshbuf_new()) == NULL) {
3245                 r = SSH_ERR_ALLOC_FAIL;
3246                 goto out;
3247         }
3248
3249         /* check preamble */
3250         cp = sshbuf_ptr(blob);
3251         encoded_len = sshbuf_len(blob);
3252         if (encoded_len < (MARK_BEGIN_LEN + MARK_END_LEN) ||
3253             memcmp(cp, MARK_BEGIN, MARK_BEGIN_LEN) != 0) {
3254                 r = SSH_ERR_INVALID_FORMAT;
3255                 goto out;
3256         }
3257         cp += MARK_BEGIN_LEN;
3258         encoded_len -= MARK_BEGIN_LEN;
3259
3260         /* Look for end marker, removing whitespace as we go */
3261         while (encoded_len > 0) {
3262                 if (*cp != '\n' && *cp != '\r') {
3263                         if ((r = sshbuf_put_u8(encoded, *cp)) != 0)
3264                                 goto out;
3265                 }
3266                 last = *cp;
3267                 encoded_len--;
3268                 cp++;
3269                 if (last == '\n') {
3270                         if (encoded_len >= MARK_END_LEN &&
3271                             memcmp(cp, MARK_END, MARK_END_LEN) == 0) {
3272                                 /* \0 terminate */
3273                                 if ((r = sshbuf_put_u8(encoded, 0)) != 0)
3274                                         goto out;
3275                                 break;
3276                         }
3277                 }
3278         }
3279         if (encoded_len == 0) {
3280                 r = SSH_ERR_INVALID_FORMAT;
3281                 goto out;
3282         }
3283
3284         /* decode base64 */
3285         if ((r = sshbuf_b64tod(decoded, (char *)sshbuf_ptr(encoded))) != 0)
3286                 goto out;
3287
3288         /* check magic */
3289         if (sshbuf_len(decoded) < sizeof(AUTH_MAGIC) ||
3290             memcmp(sshbuf_ptr(decoded), AUTH_MAGIC, sizeof(AUTH_MAGIC))) {
3291                 r = SSH_ERR_INVALID_FORMAT;
3292                 goto out;
3293         }
3294         /* parse public portion of key */
3295         if ((r = sshbuf_consume(decoded, sizeof(AUTH_MAGIC))) != 0 ||
3296             (r = sshbuf_get_cstring(decoded, &ciphername, NULL)) != 0 ||
3297             (r = sshbuf_get_cstring(decoded, &kdfname, NULL)) != 0 ||
3298             (r = sshbuf_froms(decoded, &kdf)) != 0 ||
3299             (r = sshbuf_get_u32(decoded, &nkeys)) != 0 ||
3300             (r = sshbuf_skip_string(decoded)) != 0 || /* pubkey */
3301             (r = sshbuf_get_u32(decoded, &encrypted_len)) != 0)
3302                 goto out;
3303
3304         if ((cipher = cipher_by_name(ciphername)) == NULL) {
3305                 r = SSH_ERR_KEY_UNKNOWN_CIPHER;
3306                 goto out;
3307         }
3308         if ((passphrase == NULL || strlen(passphrase) == 0) &&
3309             strcmp(ciphername, "none") != 0) {
3310                 /* passphrase required */
3311                 r = SSH_ERR_KEY_WRONG_PASSPHRASE;
3312                 goto out;
3313         }
3314         if (strcmp(kdfname, "none") != 0 && strcmp(kdfname, "bcrypt") != 0) {
3315                 r = SSH_ERR_KEY_UNKNOWN_CIPHER;
3316                 goto out;
3317         }
3318         if (!strcmp(kdfname, "none") && strcmp(ciphername, "none") != 0) {
3319                 r = SSH_ERR_INVALID_FORMAT;
3320                 goto out;
3321         }
3322         if (nkeys != 1) {
3323                 /* XXX only one key supported */
3324                 r = SSH_ERR_INVALID_FORMAT;
3325                 goto out;
3326         }
3327
3328         /* check size of encrypted key blob */
3329         blocksize = cipher_blocksize(cipher);
3330         if (encrypted_len < blocksize || (encrypted_len % blocksize) != 0) {
3331                 r = SSH_ERR_INVALID_FORMAT;
3332                 goto out;
3333         }
3334
3335         /* setup key */
3336         keylen = cipher_keylen(cipher);
3337         ivlen = cipher_ivlen(cipher);
3338         authlen = cipher_authlen(cipher);
3339         if ((key = calloc(1, keylen + ivlen)) == NULL) {
3340                 r = SSH_ERR_ALLOC_FAIL;
3341                 goto out;
3342         }
3343         if (strcmp(kdfname, "bcrypt") == 0) {
3344                 if ((r = sshbuf_get_string(kdf, &salt, &slen)) != 0 ||
3345                     (r = sshbuf_get_u32(kdf, &rounds)) != 0)
3346                         goto out;
3347                 if (bcrypt_pbkdf(passphrase, strlen(passphrase), salt, slen,
3348                     key, keylen + ivlen, rounds) < 0) {
3349                         r = SSH_ERR_INVALID_FORMAT;
3350                         goto out;
3351                 }
3352         }
3353
3354         /* check that an appropriate amount of auth data is present */
3355         if (sshbuf_len(decoded) < encrypted_len + authlen) {
3356                 r = SSH_ERR_INVALID_FORMAT;
3357                 goto out;
3358         }
3359
3360         /* decrypt private portion of key */
3361         if ((r = sshbuf_reserve(decrypted, encrypted_len, &dp)) != 0 ||
3362             (r = cipher_init(&ciphercontext, cipher, key, keylen,
3363             key + keylen, ivlen, 0)) != 0)
3364                 goto out;
3365         if ((r = cipher_crypt(&ciphercontext, 0, dp, sshbuf_ptr(decoded),
3366             encrypted_len, 0, authlen)) != 0) {
3367                 /* an integrity error here indicates an incorrect passphrase */
3368                 if (r == SSH_ERR_MAC_INVALID)
3369                         r = SSH_ERR_KEY_WRONG_PASSPHRASE;
3370                 goto out;
3371         }
3372         if ((r = sshbuf_consume(decoded, encrypted_len + authlen)) != 0)
3373                 goto out;
3374         /* there should be no trailing data */
3375         if (sshbuf_len(decoded) != 0) {
3376                 r = SSH_ERR_INVALID_FORMAT;
3377                 goto out;
3378         }
3379
3380         /* check check bytes */
3381         if ((r = sshbuf_get_u32(decrypted, &check1)) != 0 ||
3382             (r = sshbuf_get_u32(decrypted, &check2)) != 0)
3383                 goto out;
3384         if (check1 != check2) {
3385                 r = SSH_ERR_KEY_WRONG_PASSPHRASE;
3386                 goto out;
3387         }
3388
3389         /* Load the private key and comment */
3390         if ((r = sshkey_private_deserialize(decrypted, &k)) != 0 ||
3391             (r = sshbuf_get_cstring(decrypted, &comment, NULL)) != 0)
3392                 goto out;
3393
3394         /* Check deterministic padding */
3395         i = 0;
3396         while (sshbuf_len(decrypted)) {
3397                 if ((r = sshbuf_get_u8(decrypted, &pad)) != 0)
3398                         goto out;
3399                 if (pad != (++i & 0xff)) {
3400                         r = SSH_ERR_INVALID_FORMAT;
3401                         goto out;
3402                 }
3403         }
3404
3405         /* XXX decode pubkey and check against private */
3406
3407         /* success */
3408         r = 0;
3409         if (keyp != NULL) {
3410                 *keyp = k;
3411                 k = NULL;
3412         }
3413         if (commentp != NULL) {
3414                 *commentp = comment;
3415                 comment = NULL;
3416         }
3417  out:
3418         pad = 0;
3419         cipher_cleanup(&ciphercontext);
3420         free(ciphername);
3421         free(kdfname);
3422         free(comment);
3423         if (salt != NULL) {
3424                 explicit_bzero(salt, slen);
3425                 free(salt);
3426         }
3427         if (key != NULL) {
3428                 explicit_bzero(key, keylen + ivlen);
3429                 free(key);
3430         }
3431         sshbuf_free(encoded);
3432         sshbuf_free(decoded);
3433         sshbuf_free(kdf);
3434         sshbuf_free(decrypted);
3435         sshkey_free(k);
3436         return r;
3437 }
3438
3439 #if WITH_SSH1
3440 /*
3441  * Serialises the authentication (private) key to a blob, encrypting it with
3442  * passphrase.  The identification of the blob (lowest 64 bits of n) will
3443  * precede the key to provide identification of the key without needing a
3444  * passphrase.
3445  */
3446 static int
3447 sshkey_private_rsa1_to_blob(struct sshkey *key, struct sshbuf *blob,
3448     const char *passphrase, const char *comment)
3449 {
3450         struct sshbuf *buffer = NULL, *encrypted = NULL;
3451         u_char buf[8];
3452         int r, cipher_num;
3453         struct sshcipher_ctx ciphercontext;
3454         const struct sshcipher *cipher;
3455         u_char *cp;
3456
3457         /*
3458          * If the passphrase is empty, use SSH_CIPHER_NONE to ease converting
3459          * to another cipher; otherwise use SSH_AUTHFILE_CIPHER.
3460          */
3461         cipher_num = (strcmp(passphrase, "") == 0) ?
3462             SSH_CIPHER_NONE : SSH_CIPHER_3DES;
3463         if ((cipher = cipher_by_number(cipher_num)) == NULL)
3464                 return SSH_ERR_INTERNAL_ERROR;
3465
3466         /* This buffer is used to build the secret part of the private key. */
3467         if ((buffer = sshbuf_new()) == NULL)
3468                 return SSH_ERR_ALLOC_FAIL;
3469
3470         /* Put checkbytes for checking passphrase validity. */
3471         if ((r = sshbuf_reserve(buffer, 4, &cp)) != 0)
3472                 goto out;
3473         arc4random_buf(cp, 2);
3474         memcpy(cp + 2, cp, 2);
3475
3476         /*
3477          * Store the private key (n and e will not be stored because they
3478          * will be stored in plain text, and storing them also in encrypted
3479          * format would just give known plaintext).
3480          * Note: q and p are stored in reverse order to SSL.
3481          */
3482         if ((r = sshbuf_put_bignum1(buffer, key->rsa->d)) != 0 ||
3483             (r = sshbuf_put_bignum1(buffer, key->rsa->iqmp)) != 0 ||
3484             (r = sshbuf_put_bignum1(buffer, key->rsa->q)) != 0 ||
3485             (r = sshbuf_put_bignum1(buffer, key->rsa->p)) != 0)
3486                 goto out;
3487
3488         /* Pad the part to be encrypted to a size that is a multiple of 8. */
3489         explicit_bzero(buf, 8);
3490         if ((r = sshbuf_put(buffer, buf, 8 - (sshbuf_len(buffer) % 8))) != 0)
3491                 goto out;
3492
3493         /* This buffer will be used to contain the data in the file. */
3494         if ((encrypted = sshbuf_new()) == NULL) {
3495                 r = SSH_ERR_ALLOC_FAIL;
3496                 goto out;
3497         }
3498
3499         /* First store keyfile id string. */
3500         if ((r = sshbuf_put(encrypted, LEGACY_BEGIN,
3501             sizeof(LEGACY_BEGIN))) != 0)
3502                 goto out;
3503
3504         /* Store cipher type and "reserved" field. */
3505         if ((r = sshbuf_put_u8(encrypted, cipher_num)) != 0 ||
3506             (r = sshbuf_put_u32(encrypted, 0)) != 0)
3507                 goto out;
3508
3509         /* Store public key.  This will be in plain text. */
3510         if ((r = sshbuf_put_u32(encrypted, BN_num_bits(key->rsa->n))) != 0 ||
3511             (r = sshbuf_put_bignum1(encrypted, key->rsa->n) != 0) ||
3512             (r = sshbuf_put_bignum1(encrypted, key->rsa->e) != 0) ||
3513             (r = sshbuf_put_cstring(encrypted, comment) != 0))
3514                 goto out;
3515
3516         /* Allocate space for the private part of the key in the buffer. */
3517         if ((r = sshbuf_reserve(encrypted, sshbuf_len(buffer), &cp)) != 0)
3518                 goto out;
3519
3520         if ((r = cipher_set_key_string(&ciphercontext, cipher, passphrase,
3521             CIPHER_ENCRYPT)) != 0)
3522                 goto out;
3523         if ((r = cipher_crypt(&ciphercontext, 0, cp,
3524             sshbuf_ptr(buffer), sshbuf_len(buffer), 0, 0)) != 0)
3525                 goto out;
3526         if ((r = cipher_cleanup(&ciphercontext)) != 0)
3527                 goto out;
3528
3529         r = sshbuf_putb(blob, encrypted);
3530
3531  out:
3532         explicit_bzero(&ciphercontext, sizeof(ciphercontext));
3533         explicit_bzero(buf, sizeof(buf));
3534         if (buffer != NULL)
3535                 sshbuf_free(buffer);
3536         if (encrypted != NULL)
3537                 sshbuf_free(encrypted);
3538
3539         return r;
3540 }
3541 #endif /* WITH_SSH1 */
3542
3543 #ifdef WITH_OPENSSL
3544 /* convert SSH v2 key in OpenSSL PEM format */
3545 static int
3546 sshkey_private_pem_to_blob(struct sshkey *key, struct sshbuf *blob,
3547     const char *_passphrase, const char *comment)
3548 {
3549         int success, r;
3550         int blen, len = strlen(_passphrase);
3551         u_char *passphrase = (len > 0) ? (u_char *)_passphrase : NULL;
3552 #if (OPENSSL_VERSION_NUMBER < 0x00907000L)
3553         const EVP_CIPHER *cipher = (len > 0) ? EVP_des_ede3_cbc() : NULL;
3554 #else
3555         const EVP_CIPHER *cipher = (len > 0) ? EVP_aes_128_cbc() : NULL;
3556 #endif
3557         const u_char *bptr;
3558         BIO *bio = NULL;
3559
3560         if (len > 0 && len <= 4)
3561                 return SSH_ERR_PASSPHRASE_TOO_SHORT;
3562         if ((bio = BIO_new(BIO_s_mem())) == NULL)
3563                 return SSH_ERR_ALLOC_FAIL;
3564
3565         switch (key->type) {
3566         case KEY_DSA:
3567                 success = PEM_write_bio_DSAPrivateKey(bio, key->dsa,
3568                     cipher, passphrase, len, NULL, NULL);
3569                 break;
3570 #ifdef OPENSSL_HAS_ECC
3571         case KEY_ECDSA:
3572                 success = PEM_write_bio_ECPrivateKey(bio, key->ecdsa,
3573                     cipher, passphrase, len, NULL, NULL);
3574                 break;
3575 #endif
3576         case KEY_RSA:
3577                 success = PEM_write_bio_RSAPrivateKey(bio, key->rsa,
3578                     cipher, passphrase, len, NULL, NULL);
3579                 break;
3580         default:
3581                 success = 0;
3582                 break;
3583         }
3584         if (success == 0) {
3585                 r = SSH_ERR_LIBCRYPTO_ERROR;
3586                 goto out;
3587         }
3588         if ((blen = BIO_get_mem_data(bio, &bptr)) <= 0) {
3589                 r = SSH_ERR_INTERNAL_ERROR;
3590                 goto out;
3591         }
3592         if ((r = sshbuf_put(blob, bptr, blen)) != 0)
3593                 goto out;
3594         r = 0;
3595  out:
3596         BIO_free(bio);
3597         return r;
3598 }
3599 #endif /* WITH_OPENSSL */
3600
3601 /* Serialise "key" to buffer "blob" */
3602 int
3603 sshkey_private_to_fileblob(struct sshkey *key, struct sshbuf *blob,
3604     const char *passphrase, const char *comment,
3605     int force_new_format, const char *new_format_cipher, int new_format_rounds)
3606 {
3607         switch (key->type) {
3608 #ifdef WITH_SSH1
3609         case KEY_RSA1:
3610                 return sshkey_private_rsa1_to_blob(key, blob,
3611                     passphrase, comment);
3612 #endif /* WITH_SSH1 */
3613 #ifdef WITH_OPENSSL
3614         case KEY_DSA:
3615         case KEY_ECDSA:
3616         case KEY_RSA:
3617                 if (force_new_format) {
3618                         return sshkey_private_to_blob2(key, blob, passphrase,
3619                             comment, new_format_cipher, new_format_rounds);
3620                 }
3621                 return sshkey_private_pem_to_blob(key, blob,
3622                     passphrase, comment);
3623 #endif /* WITH_OPENSSL */
3624         case KEY_ED25519:
3625                 return sshkey_private_to_blob2(key, blob, passphrase,
3626                     comment, new_format_cipher, new_format_rounds);
3627         default:
3628                 return SSH_ERR_KEY_TYPE_UNKNOWN;
3629         }
3630 }
3631
3632 #ifdef WITH_SSH1
3633 /*
3634  * Parse the public, unencrypted portion of a RSA1 key.
3635  */
3636 int
3637 sshkey_parse_public_rsa1_fileblob(struct sshbuf *blob,
3638     struct sshkey **keyp, char **commentp)
3639 {
3640         int r;
3641         struct sshkey *pub = NULL;
3642         struct sshbuf *copy = NULL;
3643
3644         if (keyp != NULL)
3645                 *keyp = NULL;
3646         if (commentp != NULL)
3647                 *commentp = NULL;
3648
3649         /* Check that it is at least big enough to contain the ID string. */
3650         if (sshbuf_len(blob) < sizeof(LEGACY_BEGIN))
3651                 return SSH_ERR_INVALID_FORMAT;
3652
3653         /*
3654          * Make sure it begins with the id string.  Consume the id string
3655          * from the buffer.
3656          */
3657         if (memcmp(sshbuf_ptr(blob), LEGACY_BEGIN, sizeof(LEGACY_BEGIN)) != 0)
3658                 return SSH_ERR_INVALID_FORMAT;
3659         /* Make a working copy of the keyblob and skip past the magic */
3660         if ((copy = sshbuf_fromb(blob)) == NULL)
3661                 return SSH_ERR_ALLOC_FAIL;
3662         if ((r = sshbuf_consume(copy, sizeof(LEGACY_BEGIN))) != 0)
3663                 goto out;
3664
3665         /* Skip cipher type, reserved data and key bits. */
3666         if ((r = sshbuf_get_u8(copy, NULL)) != 0 ||     /* cipher type */
3667             (r = sshbuf_get_u32(copy, NULL)) != 0 ||    /* reserved */
3668             (r = sshbuf_get_u32(copy, NULL)) != 0)      /* key bits */
3669                 goto out;
3670
3671         /* Read the public key from the buffer. */
3672         if ((pub = sshkey_new(KEY_RSA1)) == NULL ||
3673             (r = sshbuf_get_bignum1(copy, pub->rsa->n)) != 0 ||
3674             (r = sshbuf_get_bignum1(copy, pub->rsa->e)) != 0)
3675                 goto out;
3676
3677         /* Finally, the comment */
3678         if ((r = sshbuf_get_string(copy, (u_char**)commentp, NULL)) != 0)
3679                 goto out;
3680
3681         /* The encrypted private part is not parsed by this function. */
3682
3683         r = 0;
3684         if (keyp != NULL)
3685                 *keyp = pub;
3686         else
3687                 sshkey_free(pub);
3688         pub = NULL;
3689
3690  out:
3691         if (copy != NULL)
3692                 sshbuf_free(copy);
3693         if (pub != NULL)
3694                 sshkey_free(pub);
3695         return r;
3696 }
3697
3698 static int
3699 sshkey_parse_private_rsa1(struct sshbuf *blob, const char *passphrase,
3700     struct sshkey **keyp, char **commentp)
3701 {
3702         int r;
3703         u_int16_t check1, check2;
3704         u_int8_t cipher_type;
3705         struct sshbuf *decrypted = NULL, *copy = NULL;
3706         u_char *cp;
3707         char *comment = NULL;
3708         struct sshcipher_ctx ciphercontext;
3709         const struct sshcipher *cipher;
3710         struct sshkey *prv = NULL;
3711
3712         *keyp = NULL;
3713         if (commentp != NULL)
3714                 *commentp = NULL;
3715
3716         /* Check that it is at least big enough to contain the ID string. */
3717         if (sshbuf_len(blob) < sizeof(LEGACY_BEGIN))
3718                 return SSH_ERR_INVALID_FORMAT;
3719
3720         /*
3721          * Make sure it begins with the id string.  Consume the id string
3722          * from the buffer.
3723          */
3724         if (memcmp(sshbuf_ptr(blob), LEGACY_BEGIN, sizeof(LEGACY_BEGIN)) != 0)
3725                 return SSH_ERR_INVALID_FORMAT;
3726
3727         if ((prv = sshkey_new_private(KEY_RSA1)) == NULL) {
3728                 r = SSH_ERR_ALLOC_FAIL;
3729                 goto out;
3730         }
3731         if ((copy = sshbuf_fromb(blob)) == NULL ||
3732             (decrypted = sshbuf_new()) == NULL) {
3733                 r = SSH_ERR_ALLOC_FAIL;
3734                 goto out;
3735         }
3736         if ((r = sshbuf_consume(copy, sizeof(LEGACY_BEGIN))) != 0)
3737                 goto out;
3738
3739         /* Read cipher type. */
3740         if ((r = sshbuf_get_u8(copy, &cipher_type)) != 0 ||
3741             (r = sshbuf_get_u32(copy, NULL)) != 0)      /* reserved */
3742                 goto out;
3743
3744         /* Read the public key and comment from the buffer. */
3745         if ((r = sshbuf_get_u32(copy, NULL)) != 0 ||    /* key bits */
3746             (r = sshbuf_get_bignum1(copy, prv->rsa->n)) != 0 ||
3747             (r = sshbuf_get_bignum1(copy, prv->rsa->e)) != 0 ||
3748             (r = sshbuf_get_cstring(copy, &comment, NULL)) != 0)
3749                 goto out;
3750
3751         /* Check that it is a supported cipher. */
3752         cipher = cipher_by_number(cipher_type);
3753         if (cipher == NULL) {
3754                 r = SSH_ERR_KEY_UNKNOWN_CIPHER;
3755                 goto out;
3756         }
3757         /* Initialize space for decrypted data. */
3758         if ((r = sshbuf_reserve(decrypted, sshbuf_len(copy), &cp)) != 0)
3759                 goto out;
3760
3761         /* Rest of the buffer is encrypted.  Decrypt it using the passphrase. */
3762         if ((r = cipher_set_key_string(&ciphercontext, cipher, passphrase,
3763             CIPHER_DECRYPT)) != 0)
3764                 goto out;
3765         if ((r = cipher_crypt(&ciphercontext, 0, cp,
3766             sshbuf_ptr(copy), sshbuf_len(copy), 0, 0)) != 0) {
3767                 cipher_cleanup(&ciphercontext);
3768                 goto out;
3769         }
3770         if ((r = cipher_cleanup(&ciphercontext)) != 0)
3771                 goto out;
3772
3773         if ((r = sshbuf_get_u16(decrypted, &check1)) != 0 ||
3774             (r = sshbuf_get_u16(decrypted, &check2)) != 0)
3775                 goto out;
3776         if (check1 != check2) {
3777                 r = SSH_ERR_KEY_WRONG_PASSPHRASE;
3778                 goto out;
3779         }
3780
3781         /* Read the rest of the private key. */
3782         if ((r = sshbuf_get_bignum1(decrypted, prv->rsa->d)) != 0 ||
3783             (r = sshbuf_get_bignum1(decrypted, prv->rsa->iqmp)) != 0 ||
3784             (r = sshbuf_get_bignum1(decrypted, prv->rsa->q)) != 0 ||
3785             (r = sshbuf_get_bignum1(decrypted, prv->rsa->p)) != 0)
3786                 goto out;
3787
3788         /* calculate p-1 and q-1 */
3789         if ((r = rsa_generate_additional_parameters(prv->rsa)) != 0)
3790                 goto out;
3791
3792         /* enable blinding */
3793         if (RSA_blinding_on(prv->rsa, NULL) != 1) {
3794                 r = SSH_ERR_LIBCRYPTO_ERROR;
3795                 goto out;
3796         }
3797         r = 0;
3798         *keyp = prv;
3799         prv = NULL;
3800         if (commentp != NULL) {
3801                 *commentp = comment;
3802                 comment = NULL;
3803         }
3804  out:
3805         explicit_bzero(&ciphercontext, sizeof(ciphercontext));
3806         if (comment != NULL)
3807                 free(comment);
3808         if (prv != NULL)
3809                 sshkey_free(prv);
3810         if (copy != NULL)
3811                 sshbuf_free(copy);
3812         if (decrypted != NULL)
3813                 sshbuf_free(decrypted);
3814         return r;
3815 }
3816 #endif /* WITH_SSH1 */
3817
3818 #ifdef WITH_OPENSSL
3819 static int
3820 sshkey_parse_private_pem_fileblob(struct sshbuf *blob, int type,
3821     const char *passphrase, struct sshkey **keyp)
3822 {
3823         EVP_PKEY *pk = NULL;
3824         struct sshkey *prv = NULL;
3825         BIO *bio = NULL;
3826         int r;
3827
3828         *keyp = NULL;
3829
3830         if ((bio = BIO_new(BIO_s_mem())) == NULL || sshbuf_len(blob) > INT_MAX)
3831                 return SSH_ERR_ALLOC_FAIL;
3832         if (BIO_write(bio, sshbuf_ptr(blob), sshbuf_len(blob)) !=
3833             (int)sshbuf_len(blob)) {
3834                 r = SSH_ERR_ALLOC_FAIL;
3835                 goto out;
3836         }
3837
3838         if ((pk = PEM_read_bio_PrivateKey(bio, NULL, NULL,
3839             (char *)passphrase)) == NULL) {
3840                 r = SSH_ERR_KEY_WRONG_PASSPHRASE;
3841                 goto out;
3842         }
3843         if (pk->type == EVP_PKEY_RSA &&
3844             (type == KEY_UNSPEC || type == KEY_RSA)) {
3845                 if ((prv = sshkey_new(KEY_UNSPEC)) == NULL) {
3846                         r = SSH_ERR_ALLOC_FAIL;
3847                         goto out;
3848                 }
3849                 prv->rsa = EVP_PKEY_get1_RSA(pk);
3850                 prv->type = KEY_RSA;
3851 #ifdef DEBUG_PK
3852                 RSA_print_fp(stderr, prv->rsa, 8);
3853 #endif
3854                 if (RSA_blinding_on(prv->rsa, NULL) != 1) {
3855                         r = SSH_ERR_LIBCRYPTO_ERROR;
3856                         goto out;
3857                 }
3858         } else if (pk->type == EVP_PKEY_DSA &&
3859             (type == KEY_UNSPEC || type == KEY_DSA)) {
3860                 if ((prv = sshkey_new(KEY_UNSPEC)) == NULL) {
3861                         r = SSH_ERR_ALLOC_FAIL;
3862                         goto out;
3863                 }
3864                 prv->dsa = EVP_PKEY_get1_DSA(pk);
3865                 prv->type = KEY_DSA;
3866 #ifdef DEBUG_PK
3867                 DSA_print_fp(stderr, prv->dsa, 8);
3868 #endif
3869 #ifdef OPENSSL_HAS_ECC
3870         } else if (pk->type == EVP_PKEY_EC &&
3871             (type == KEY_UNSPEC || type == KEY_ECDSA)) {
3872                 if ((prv = sshkey_new(KEY_UNSPEC)) == NULL) {
3873                         r = SSH_ERR_ALLOC_FAIL;
3874                         goto out;
3875                 }
3876                 prv->ecdsa = EVP_PKEY_get1_EC_KEY(pk);
3877                 prv->type = KEY_ECDSA;
3878                 prv->ecdsa_nid = sshkey_ecdsa_key_to_nid(prv->ecdsa);
3879                 if (prv->ecdsa_nid == -1 ||
3880                     sshkey_curve_nid_to_name(prv->ecdsa_nid) == NULL ||
3881                     sshkey_ec_validate_public(EC_KEY_get0_group(prv->ecdsa),
3882                     EC_KEY_get0_public_key(prv->ecdsa)) != 0 ||
3883                     sshkey_ec_validate_private(prv->ecdsa) != 0) {
3884                         r = SSH_ERR_INVALID_FORMAT;
3885                         goto out;
3886                 }
3887 # ifdef DEBUG_PK
3888                 if (prv != NULL && prv->ecdsa != NULL)
3889                         sshkey_dump_ec_key(prv->ecdsa);
3890 # endif
3891 #endif /* OPENSSL_HAS_ECC */
3892         } else {
3893                 r = SSH_ERR_INVALID_FORMAT;
3894                 goto out;
3895         }
3896         r = 0;
3897         *keyp = prv;
3898         prv = NULL;
3899  out:
3900         BIO_free(bio);
3901         if (pk != NULL)
3902                 EVP_PKEY_free(pk);
3903         if (prv != NULL)
3904                 sshkey_free(prv);
3905         return r;
3906 }
3907 #endif /* WITH_OPENSSL */
3908
3909 int
3910 sshkey_parse_private_fileblob_type(struct sshbuf *blob, int type,
3911     const char *passphrase, struct sshkey **keyp, char **commentp)
3912 {
3913         int r;
3914
3915         *keyp = NULL;
3916         if (commentp != NULL)
3917                 *commentp = NULL;
3918
3919         switch (type) {
3920 #ifdef WITH_SSH1
3921         case KEY_RSA1:
3922                 return sshkey_parse_private_rsa1(blob, passphrase,
3923                     keyp, commentp);
3924 #endif /* WITH_SSH1 */
3925 #ifdef WITH_OPENSSL
3926         case KEY_DSA:
3927         case KEY_ECDSA:
3928         case KEY_RSA:
3929                 return sshkey_parse_private_pem_fileblob(blob, type,
3930                     passphrase, keyp);
3931 #endif /* WITH_OPENSSL */
3932         case KEY_ED25519:
3933                 return sshkey_parse_private2(blob, type, passphrase,
3934                     keyp, commentp);
3935         case KEY_UNSPEC:
3936                 if ((r = sshkey_parse_private2(blob, type, passphrase, keyp,
3937                     commentp)) == 0)
3938                         return 0;
3939 #ifdef WITH_OPENSSL
3940                 return sshkey_parse_private_pem_fileblob(blob, type,
3941                     passphrase, keyp);
3942 #else
3943                 return SSH_ERR_INVALID_FORMAT;
3944 #endif /* WITH_OPENSSL */
3945         default:
3946                 return SSH_ERR_KEY_TYPE_UNKNOWN;
3947         }
3948 }
3949
3950 int
3951 sshkey_parse_private_fileblob(struct sshbuf *buffer, const char *passphrase,
3952     const char *filename, struct sshkey **keyp, char **commentp)
3953 {
3954         int r;
3955
3956         if (keyp != NULL)
3957                 *keyp = NULL;
3958         if (commentp != NULL)
3959                 *commentp = NULL;
3960
3961 #ifdef WITH_SSH1
3962         /* it's a SSH v1 key if the public key part is readable */
3963         if ((r = sshkey_parse_public_rsa1_fileblob(buffer, NULL, NULL)) == 0) {
3964                 return sshkey_parse_private_fileblob_type(buffer, KEY_RSA1,
3965                     passphrase, keyp, commentp);
3966         }
3967 #endif /* WITH_SSH1 */
3968         if ((r = sshkey_parse_private_fileblob_type(buffer, KEY_UNSPEC,
3969             passphrase, keyp, commentp)) == 0)
3970                 return 0;
3971         return r;
3972 }