summaryrefslogtreecommitdiff
path: root/sshkey.c
diff options
context:
space:
mode:
Diffstat (limited to 'sshkey.c')
-rw-r--r--sshkey.c415
1 files changed, 250 insertions, 165 deletions
diff --git a/sshkey.c b/sshkey.c
index fdd0c8a89..476879033 100644
--- a/sshkey.c
+++ b/sshkey.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: sshkey.c,v 1.3 2014/07/03 01:45:38 djm Exp $ */ 1/* $OpenBSD: sshkey.c,v 1.15 2015/03/06 01:40:56 djm Exp $ */
2/* 2/*
3 * Copyright (c) 2000, 2001 Markus Friedl. All rights reserved. 3 * Copyright (c) 2000, 2001 Markus Friedl. All rights reserved.
4 * Copyright (c) 2008 Alexander von Gernler. All rights reserved. 4 * Copyright (c) 2008 Alexander von Gernler. All rights reserved.
@@ -27,18 +27,23 @@
27 27
28#include "includes.h" 28#include "includes.h"
29 29
30#include <sys/param.h> 30#include <sys/param.h> /* MIN MAX */
31#include <sys/types.h> 31#include <sys/types.h>
32#include <netinet/in.h>
32 33
34#ifdef WITH_OPENSSL
33#include <openssl/evp.h> 35#include <openssl/evp.h>
34#include <openssl/err.h> 36#include <openssl/err.h>
35#include <openssl/pem.h> 37#include <openssl/pem.h>
38#endif
36 39
37#include "crypto_api.h" 40#include "crypto_api.h"
38 41
39#include <errno.h> 42#include <errno.h>
43#include <limits.h>
40#include <stdio.h> 44#include <stdio.h>
41#include <string.h> 45#include <string.h>
46#include <resolv.h>
42#ifdef HAVE_UTIL_H 47#ifdef HAVE_UTIL_H
43#include <util.h> 48#include <util.h>
44#endif /* HAVE_UTIL_H */ 49#endif /* HAVE_UTIL_H */
@@ -52,6 +57,7 @@
52#include "digest.h" 57#include "digest.h"
53#define SSHKEY_INTERNAL 58#define SSHKEY_INTERNAL
54#include "sshkey.h" 59#include "sshkey.h"
60#include "match.h"
55 61
56/* openssh private key file format */ 62/* openssh private key file format */
57#define MARK_BEGIN "-----BEGIN OPENSSH PRIVATE KEY-----\n" 63#define MARK_BEGIN "-----BEGIN OPENSSH PRIVATE KEY-----\n"
@@ -67,7 +73,7 @@
67/* Version identification string for SSH v1 identity files. */ 73/* Version identification string for SSH v1 identity files. */
68#define LEGACY_BEGIN "SSH PRIVATE KEY FILE FORMAT 1.1\n" 74#define LEGACY_BEGIN "SSH PRIVATE KEY FILE FORMAT 1.1\n"
69 75
70static int sshkey_from_blob_internal(const u_char *blob, size_t blen, 76static int sshkey_from_blob_internal(struct sshbuf *buf,
71 struct sshkey **keyp, int allow_cert); 77 struct sshkey **keyp, int allow_cert);
72 78
73/* Supported key types */ 79/* Supported key types */
@@ -181,12 +187,12 @@ sshkey_ecdsa_nid_from_name(const char *name)
181{ 187{
182 const struct keytype *kt; 188 const struct keytype *kt;
183 189
184 for (kt = keytypes; kt->type != -1; kt++) { 190 for (kt = keytypes; kt->type != -1; kt++) {
185 if (kt->type != KEY_ECDSA && kt->type != KEY_ECDSA_CERT) 191 if (kt->type != KEY_ECDSA && kt->type != KEY_ECDSA_CERT)
186 continue; 192 continue;
187 if (kt->name != NULL && strcmp(name, kt->name) == 0) 193 if (kt->name != NULL && strcmp(name, kt->name) == 0)
188 return kt->nid; 194 return kt->nid;
189 } 195 }
190 return -1; 196 return -1;
191} 197}
192 198
@@ -217,9 +223,11 @@ key_alg_list(int certs_only, int plain_only)
217} 223}
218 224
219int 225int
220sshkey_names_valid2(const char *names) 226sshkey_names_valid2(const char *names, int allow_wildcard)
221{ 227{
222 char *s, *cp, *p; 228 char *s, *cp, *p;
229 const struct keytype *kt;
230 int type;
223 231
224 if (names == NULL || strcmp(names, "") == 0) 232 if (names == NULL || strcmp(names, "") == 0)
225 return 0; 233 return 0;
@@ -227,9 +235,28 @@ sshkey_names_valid2(const char *names)
227 return 0; 235 return 0;
228 for ((p = strsep(&cp, ",")); p && *p != '\0'; 236 for ((p = strsep(&cp, ",")); p && *p != '\0';
229 (p = strsep(&cp, ","))) { 237 (p = strsep(&cp, ","))) {
230 switch (sshkey_type_from_name(p)) { 238 type = sshkey_type_from_name(p);
231 case KEY_RSA1: 239 if (type == KEY_RSA1) {
232 case KEY_UNSPEC: 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, strlen(p), 0) != 0)
255 break;
256 }
257 if (kt->type != -1)
258 continue;
259 }
233 free(s); 260 free(s);
234 return 0; 261 return 0;
235 } 262 }
@@ -797,13 +824,28 @@ to_blob_buf(const struct sshkey *key, struct sshbuf *b, int force_plain)
797} 824}
798 825
799int 826int
800sshkey_to_blob_buf(const struct sshkey *key, struct sshbuf *b) 827sshkey_putb(const struct sshkey *key, struct sshbuf *b)
801{ 828{
802 return to_blob_buf(key, b, 0); 829 return to_blob_buf(key, b, 0);
803} 830}
804 831
805int 832int
806sshkey_plain_to_blob_buf(const struct sshkey *key, struct sshbuf *b) 833sshkey_puts(const struct sshkey *key, struct sshbuf *b)
834{
835 struct sshbuf *tmp;
836 int r;
837
838 if ((tmp = sshbuf_new()) == NULL)
839 return SSH_ERR_ALLOC_FAIL;
840 r = to_blob_buf(key, tmp, 0);
841 if (r == 0)
842 r = sshbuf_put_stringb(b, tmp);
843 sshbuf_free(tmp);
844 return r;
845}
846
847int
848sshkey_putb_plain(const struct sshkey *key, struct sshbuf *b)
807{ 849{
808 return to_blob_buf(key, b, 1); 850 return to_blob_buf(key, b, 1);
809} 851}
@@ -852,29 +894,18 @@ sshkey_plain_to_blob(const struct sshkey *key, u_char **blobp, size_t *lenp)
852} 894}
853 895
854int 896int
855sshkey_fingerprint_raw(const struct sshkey *k, enum sshkey_fp_type dgst_type, 897sshkey_fingerprint_raw(const struct sshkey *k, int dgst_alg,
856 u_char **retp, size_t *lenp) 898 u_char **retp, size_t *lenp)
857{ 899{
858 u_char *blob = NULL, *ret = NULL; 900 u_char *blob = NULL, *ret = NULL;
859 size_t blob_len = 0; 901 size_t blob_len = 0;
860 int hash_alg = -1, r = SSH_ERR_INTERNAL_ERROR; 902 int r = SSH_ERR_INTERNAL_ERROR;
861 903
862 if (retp != NULL) 904 if (retp != NULL)
863 *retp = NULL; 905 *retp = NULL;
864 if (lenp != NULL) 906 if (lenp != NULL)
865 *lenp = 0; 907 *lenp = 0;
866 908 if (ssh_digest_bytes(dgst_alg) == 0) {
867 switch (dgst_type) {
868 case SSH_FP_MD5:
869 hash_alg = SSH_DIGEST_MD5;
870 break;
871 case SSH_FP_SHA1:
872 hash_alg = SSH_DIGEST_SHA1;
873 break;
874 case SSH_FP_SHA256:
875 hash_alg = SSH_DIGEST_SHA256;
876 break;
877 default:
878 r = SSH_ERR_INVALID_ARGUMENT; 909 r = SSH_ERR_INVALID_ARGUMENT;
879 goto out; 910 goto out;
880 } 911 }
@@ -899,7 +930,7 @@ sshkey_fingerprint_raw(const struct sshkey *k, enum sshkey_fp_type dgst_type,
899 r = SSH_ERR_ALLOC_FAIL; 930 r = SSH_ERR_ALLOC_FAIL;
900 goto out; 931 goto out;
901 } 932 }
902 if ((r = ssh_digest_memory(hash_alg, blob, blob_len, 933 if ((r = ssh_digest_memory(dgst_alg, blob, blob_len,
903 ret, SSH_DIGEST_MAX_LENGTH)) != 0) 934 ret, SSH_DIGEST_MAX_LENGTH)) != 0)
904 goto out; 935 goto out;
905 /* success */ 936 /* success */
@@ -908,7 +939,7 @@ sshkey_fingerprint_raw(const struct sshkey *k, enum sshkey_fp_type dgst_type,
908 ret = NULL; 939 ret = NULL;
909 } 940 }
910 if (lenp != NULL) 941 if (lenp != NULL)
911 *lenp = ssh_digest_bytes(hash_alg); 942 *lenp = ssh_digest_bytes(dgst_alg);
912 r = 0; 943 r = 0;
913 out: 944 out:
914 free(ret); 945 free(ret);
@@ -920,21 +951,45 @@ sshkey_fingerprint_raw(const struct sshkey *k, enum sshkey_fp_type dgst_type,
920} 951}
921 952
922static char * 953static char *
923fingerprint_hex(u_char *dgst_raw, size_t dgst_raw_len) 954fingerprint_b64(const char *alg, u_char *dgst_raw, size_t dgst_raw_len)
924{ 955{
925 char *retval; 956 char *ret;
926 size_t i; 957 size_t plen = strlen(alg) + 1;
958 size_t rlen = ((dgst_raw_len + 2) / 3) * 4 + plen + 1;
959 int r;
927 960
928 if ((retval = calloc(1, dgst_raw_len * 3 + 1)) == NULL) 961 if (dgst_raw_len > 65536 || (ret = calloc(1, rlen)) == NULL)
962 return NULL;
963 strlcpy(ret, alg, rlen);
964 strlcat(ret, ":", rlen);
965 if (dgst_raw_len == 0)
966 return ret;
967 if ((r = b64_ntop(dgst_raw, dgst_raw_len,
968 ret + plen, rlen - plen)) == -1) {
969 explicit_bzero(ret, rlen);
970 free(ret);
929 return NULL; 971 return NULL;
930 for (i = 0; i < dgst_raw_len; i++) {
931 char hex[4];
932 snprintf(hex, sizeof(hex), "%02x:", dgst_raw[i]);
933 strlcat(retval, hex, dgst_raw_len * 3 + 1);
934 } 972 }
973 /* Trim padding characters from end */
974 ret[strcspn(ret, "=")] = '\0';
975 return ret;
976}
977
978static char *
979fingerprint_hex(const char *alg, u_char *dgst_raw, size_t dgst_raw_len)
980{
981 char *retval, hex[5];
982 size_t i, rlen = dgst_raw_len * 3 + strlen(alg) + 2;
935 983
936 /* Remove the trailing ':' character */ 984 if (dgst_raw_len > 65536 || (retval = calloc(1, rlen)) == NULL)
937 retval[(dgst_raw_len * 3) - 1] = '\0'; 985 return NULL;
986 strlcpy(retval, alg, rlen);
987 strlcat(retval, ":", rlen);
988 for (i = 0; i < dgst_raw_len; i++) {
989 snprintf(hex, sizeof(hex), "%s%02x",
990 i > 0 ? ":" : "", dgst_raw[i]);
991 strlcat(retval, hex, rlen);
992 }
938 return retval; 993 return retval;
939} 994}
940 995
@@ -1020,7 +1075,7 @@ fingerprint_bubblebabble(u_char *dgst_raw, size_t dgst_raw_len)
1020#define FLDSIZE_Y (FLDBASE + 1) 1075#define FLDSIZE_Y (FLDBASE + 1)
1021#define FLDSIZE_X (FLDBASE * 2 + 1) 1076#define FLDSIZE_X (FLDBASE * 2 + 1)
1022static char * 1077static char *
1023fingerprint_randomart(u_char *dgst_raw, size_t dgst_raw_len, 1078fingerprint_randomart(const char *alg, u_char *dgst_raw, size_t dgst_raw_len,
1024 const struct sshkey *k) 1079 const struct sshkey *k)
1025{ 1080{
1026 /* 1081 /*
@@ -1028,9 +1083,9 @@ fingerprint_randomart(u_char *dgst_raw, size_t dgst_raw_len,
1028 * intersects with itself. Matter of taste. 1083 * intersects with itself. Matter of taste.
1029 */ 1084 */
1030 char *augmentation_string = " .o+=*BOX@%&#/^SE"; 1085 char *augmentation_string = " .o+=*BOX@%&#/^SE";
1031 char *retval, *p, title[FLDSIZE_X]; 1086 char *retval, *p, title[FLDSIZE_X], hash[FLDSIZE_X];
1032 u_char field[FLDSIZE_X][FLDSIZE_Y]; 1087 u_char field[FLDSIZE_X][FLDSIZE_Y];
1033 size_t i, tlen; 1088 size_t i, tlen, hlen;
1034 u_int b; 1089 u_int b;
1035 int x, y, r; 1090 int x, y, r;
1036 size_t len = strlen(augmentation_string) - 1; 1091 size_t len = strlen(augmentation_string) - 1;
@@ -1075,8 +1130,12 @@ fingerprint_randomart(u_char *dgst_raw, size_t dgst_raw_len,
1075 sshkey_type(k), sshkey_size(k)); 1130 sshkey_type(k), sshkey_size(k));
1076 /* If [type size] won't fit, then try [type]; fits "[ED25519-CERT]" */ 1131 /* If [type size] won't fit, then try [type]; fits "[ED25519-CERT]" */
1077 if (r < 0 || r > (int)sizeof(title)) 1132 if (r < 0 || r > (int)sizeof(title))
1078 snprintf(title, sizeof(title), "[%s]", sshkey_type(k)); 1133 r = snprintf(title, sizeof(title), "[%s]", sshkey_type(k));
1079 tlen = strlen(title); 1134 tlen = (r <= 0) ? 0 : strlen(title);
1135
1136 /* assemble hash ID. */
1137 r = snprintf(hash, sizeof(hash), "[%s]", alg);
1138 hlen = (r <= 0) ? 0 : strlen(hash);
1080 1139
1081 /* output upper border */ 1140 /* output upper border */
1082 p = retval; 1141 p = retval;
@@ -1085,7 +1144,7 @@ fingerprint_randomart(u_char *dgst_raw, size_t dgst_raw_len,
1085 *p++ = '-'; 1144 *p++ = '-';
1086 memcpy(p, title, tlen); 1145 memcpy(p, title, tlen);
1087 p += tlen; 1146 p += tlen;
1088 for (i = p - retval - 1; i < FLDSIZE_X; i++) 1147 for (i += tlen; i < FLDSIZE_X; i++)
1089 *p++ = '-'; 1148 *p++ = '-';
1090 *p++ = '+'; 1149 *p++ = '+';
1091 *p++ = '\n'; 1150 *p++ = '\n';
@@ -1101,7 +1160,11 @@ fingerprint_randomart(u_char *dgst_raw, size_t dgst_raw_len,
1101 1160
1102 /* output lower border */ 1161 /* output lower border */
1103 *p++ = '+'; 1162 *p++ = '+';
1104 for (i = 0; i < FLDSIZE_X; i++) 1163 for (i = 0; i < (FLDSIZE_X - hlen) / 2; i++)
1164 *p++ = '-';
1165 memcpy(p, hash, hlen);
1166 p += hlen;
1167 for (i += hlen; i < FLDSIZE_X; i++)
1105 *p++ = '-'; 1168 *p++ = '-';
1106 *p++ = '+'; 1169 *p++ = '+';
1107 1170
@@ -1109,24 +1172,39 @@ fingerprint_randomart(u_char *dgst_raw, size_t dgst_raw_len,
1109} 1172}
1110 1173
1111char * 1174char *
1112sshkey_fingerprint(const struct sshkey *k, enum sshkey_fp_type dgst_type, 1175sshkey_fingerprint(const struct sshkey *k, int dgst_alg,
1113 enum sshkey_fp_rep dgst_rep) 1176 enum sshkey_fp_rep dgst_rep)
1114{ 1177{
1115 char *retval = NULL; 1178 char *retval = NULL;
1116 u_char *dgst_raw; 1179 u_char *dgst_raw;
1117 size_t dgst_raw_len; 1180 size_t dgst_raw_len;
1118 1181
1119 if (sshkey_fingerprint_raw(k, dgst_type, &dgst_raw, &dgst_raw_len) != 0) 1182 if (sshkey_fingerprint_raw(k, dgst_alg, &dgst_raw, &dgst_raw_len) != 0)
1120 return NULL; 1183 return NULL;
1121 switch (dgst_rep) { 1184 switch (dgst_rep) {
1185 case SSH_FP_DEFAULT:
1186 if (dgst_alg == SSH_DIGEST_MD5) {
1187 retval = fingerprint_hex(ssh_digest_alg_name(dgst_alg),
1188 dgst_raw, dgst_raw_len);
1189 } else {
1190 retval = fingerprint_b64(ssh_digest_alg_name(dgst_alg),
1191 dgst_raw, dgst_raw_len);
1192 }
1193 break;
1122 case SSH_FP_HEX: 1194 case SSH_FP_HEX:
1123 retval = fingerprint_hex(dgst_raw, dgst_raw_len); 1195 retval = fingerprint_hex(ssh_digest_alg_name(dgst_alg),
1196 dgst_raw, dgst_raw_len);
1197 break;
1198 case SSH_FP_BASE64:
1199 retval = fingerprint_b64(ssh_digest_alg_name(dgst_alg),
1200 dgst_raw, dgst_raw_len);
1124 break; 1201 break;
1125 case SSH_FP_BUBBLEBABBLE: 1202 case SSH_FP_BUBBLEBABBLE:
1126 retval = fingerprint_bubblebabble(dgst_raw, dgst_raw_len); 1203 retval = fingerprint_bubblebabble(dgst_raw, dgst_raw_len);
1127 break; 1204 break;
1128 case SSH_FP_RANDOMART: 1205 case SSH_FP_RANDOMART:
1129 retval = fingerprint_randomart(dgst_raw, dgst_raw_len, k); 1206 retval = fingerprint_randomart(ssh_digest_alg_name(dgst_alg),
1207 dgst_raw, dgst_raw_len, k);
1130 break; 1208 break;
1131 default: 1209 default:
1132 explicit_bzero(dgst_raw, dgst_raw_len); 1210 explicit_bzero(dgst_raw, dgst_raw_len);
@@ -1233,16 +1311,20 @@ sshkey_read(struct sshkey *ret, char **cpp)
1233 cp = space+1; 1311 cp = space+1;
1234 if (*cp == '\0') 1312 if (*cp == '\0')
1235 return SSH_ERR_INVALID_FORMAT; 1313 return SSH_ERR_INVALID_FORMAT;
1236 if (ret->type == KEY_UNSPEC) { 1314 if (ret->type != KEY_UNSPEC && ret->type != type)
1237 ret->type = type;
1238 } else if (ret->type != type)
1239 return SSH_ERR_KEY_TYPE_MISMATCH; 1315 return SSH_ERR_KEY_TYPE_MISMATCH;
1240 if ((blob = sshbuf_new()) == NULL) 1316 if ((blob = sshbuf_new()) == NULL)
1241 return SSH_ERR_ALLOC_FAIL; 1317 return SSH_ERR_ALLOC_FAIL;
1242 /* trim comment */ 1318 /* trim comment */
1243 space = strchr(cp, ' '); 1319 space = strchr(cp, ' ');
1244 if (space) 1320 if (space) {
1245 *space = '\0'; 1321 /* advance 'space': skip whitespace */
1322 *space++ = '\0';
1323 while (*space == ' ' || *space == '\t')
1324 space++;
1325 *cpp = space;
1326 } else
1327 *cpp = cp + strlen(cp);
1246 if ((r = sshbuf_b64tod(blob, cp)) != 0) { 1328 if ((r = sshbuf_b64tod(blob, cp)) != 0) {
1247 sshbuf_free(blob); 1329 sshbuf_free(blob);
1248 return r; 1330 return r;
@@ -1262,7 +1344,7 @@ sshkey_read(struct sshkey *ret, char **cpp)
1262 sshkey_free(k); 1344 sshkey_free(k);
1263 return SSH_ERR_EC_CURVE_MISMATCH; 1345 return SSH_ERR_EC_CURVE_MISMATCH;
1264 } 1346 }
1265/*XXXX*/ 1347 ret->type = type;
1266 if (sshkey_is_cert(ret)) { 1348 if (sshkey_is_cert(ret)) {
1267 if (!sshkey_is_cert(k)) { 1349 if (!sshkey_is_cert(k)) {
1268 sshkey_free(k); 1350 sshkey_free(k);
@@ -1319,12 +1401,6 @@ sshkey_read(struct sshkey *ret, char **cpp)
1319 sshkey_free(k); 1401 sshkey_free(k);
1320 if (retval != 0) 1402 if (retval != 0)
1321 break; 1403 break;
1322 /* advance cp: skip whitespace and data */
1323 while (*cp == ' ' || *cp == '\t')
1324 cp++;
1325 while (*cp != '\0' && *cp != ' ' && *cp != '\t')
1326 cp++;
1327 *cpp = cp;
1328 break; 1404 break;
1329 default: 1405 default:
1330 return SSH_ERR_INVALID_ARGUMENT; 1406 return SSH_ERR_INVALID_ARGUMENT;
@@ -1389,7 +1465,7 @@ sshkey_write(const struct sshkey *key, FILE *f)
1389 ret = SSH_ERR_ALLOC_FAIL; 1465 ret = SSH_ERR_ALLOC_FAIL;
1390 goto out; 1466 goto out;
1391 } 1467 }
1392 if ((ret = sshkey_to_blob_buf(key, bb)) != 0) 1468 if ((ret = sshkey_putb(key, bb)) != 0)
1393 goto out; 1469 goto out;
1394 if ((uu = sshbuf_dtob64(bb)) == NULL) { 1470 if ((uu = sshbuf_dtob64(bb)) == NULL) {
1395 ret = SSH_ERR_ALLOC_FAIL; 1471 ret = SSH_ERR_ALLOC_FAIL;
@@ -1766,38 +1842,30 @@ sshkey_from_private(const struct sshkey *k, struct sshkey **pkp)
1766} 1842}
1767 1843
1768static int 1844static int
1769cert_parse(struct sshbuf *b, struct sshkey *key, const u_char *blob, 1845cert_parse(struct sshbuf *b, struct sshkey *key, struct sshbuf *certbuf)
1770 size_t blen)
1771{ 1846{
1772 u_char *principals = NULL, *critical = NULL, *exts = NULL; 1847 struct sshbuf *principals = NULL, *crit = NULL;
1773 u_char *sig_key = NULL, *sig = NULL; 1848 struct sshbuf *exts = NULL, *ca = NULL;
1774 size_t signed_len, plen, clen, sklen, slen, kidlen, elen; 1849 u_char *sig = NULL;
1775 struct sshbuf *tmp; 1850 size_t signed_len = 0, slen = 0, kidlen = 0;
1776 char *principal;
1777 int ret = SSH_ERR_INTERNAL_ERROR; 1851 int ret = SSH_ERR_INTERNAL_ERROR;
1778 int v00 = sshkey_cert_is_legacy(key); 1852 int v00 = sshkey_cert_is_legacy(key);
1779 char **oprincipals;
1780
1781 if ((tmp = sshbuf_new()) == NULL)
1782 return SSH_ERR_ALLOC_FAIL;
1783 1853
1784 /* Copy the entire key blob for verification and later serialisation */ 1854 /* Copy the entire key blob for verification and later serialisation */
1785 if ((ret = sshbuf_put(key->cert->certblob, blob, blen)) != 0) 1855 if ((ret = sshbuf_putb(key->cert->certblob, certbuf)) != 0)
1786 return ret; 1856 return ret;
1787 1857
1788 elen = 0; /* Not touched for v00 certs */
1789 principals = exts = critical = sig_key = sig = NULL;
1790 if ((!v00 && (ret = sshbuf_get_u64(b, &key->cert->serial)) != 0) || 1858 if ((!v00 && (ret = sshbuf_get_u64(b, &key->cert->serial)) != 0) ||
1791 (ret = sshbuf_get_u32(b, &key->cert->type)) != 0 || 1859 (ret = sshbuf_get_u32(b, &key->cert->type)) != 0 ||
1792 (ret = sshbuf_get_cstring(b, &key->cert->key_id, &kidlen)) != 0 || 1860 (ret = sshbuf_get_cstring(b, &key->cert->key_id, &kidlen)) != 0 ||
1793 (ret = sshbuf_get_string(b, &principals, &plen)) != 0 || 1861 (ret = sshbuf_froms(b, &principals)) != 0 ||
1794 (ret = sshbuf_get_u64(b, &key->cert->valid_after)) != 0 || 1862 (ret = sshbuf_get_u64(b, &key->cert->valid_after)) != 0 ||
1795 (ret = sshbuf_get_u64(b, &key->cert->valid_before)) != 0 || 1863 (ret = sshbuf_get_u64(b, &key->cert->valid_before)) != 0 ||
1796 (ret = sshbuf_get_string(b, &critical, &clen)) != 0 || 1864 (ret = sshbuf_froms(b, &crit)) != 0 ||
1797 (!v00 && (ret = sshbuf_get_string(b, &exts, &elen)) != 0) || 1865 (!v00 && (ret = sshbuf_froms(b, &exts)) != 0) ||
1798 (v00 && (ret = sshbuf_get_string_direct(b, NULL, NULL)) != 0) || 1866 (v00 && (ret = sshbuf_get_string_direct(b, NULL, NULL)) != 0) ||
1799 (ret = sshbuf_get_string_direct(b, NULL, NULL)) != 0 || 1867 (ret = sshbuf_get_string_direct(b, NULL, NULL)) != 0 ||
1800 (ret = sshbuf_get_string(b, &sig_key, &sklen)) != 0) { 1868 (ret = sshbuf_froms(b, &ca)) != 0) {
1801 /* XXX debug print error for ret */ 1869 /* XXX debug print error for ret */
1802 ret = SSH_ERR_INVALID_FORMAT; 1870 ret = SSH_ERR_INVALID_FORMAT;
1803 goto out; 1871 goto out;
@@ -1817,14 +1885,17 @@ cert_parse(struct sshbuf *b, struct sshkey *key, const u_char *blob,
1817 goto out; 1885 goto out;
1818 } 1886 }
1819 1887
1820 if ((ret = sshbuf_put(tmp, principals, plen)) != 0) 1888 /* Parse principals section */
1821 goto out; 1889 while (sshbuf_len(principals) > 0) {
1822 while (sshbuf_len(tmp) > 0) { 1890 char *principal = NULL;
1891 char **oprincipals = NULL;
1892
1823 if (key->cert->nprincipals >= SSHKEY_CERT_MAX_PRINCIPALS) { 1893 if (key->cert->nprincipals >= SSHKEY_CERT_MAX_PRINCIPALS) {
1824 ret = SSH_ERR_INVALID_FORMAT; 1894 ret = SSH_ERR_INVALID_FORMAT;
1825 goto out; 1895 goto out;
1826 } 1896 }
1827 if ((ret = sshbuf_get_cstring(tmp, &principal, &plen)) != 0) { 1897 if ((ret = sshbuf_get_cstring(principals, &principal,
1898 NULL)) != 0) {
1828 ret = SSH_ERR_INVALID_FORMAT; 1899 ret = SSH_ERR_INVALID_FORMAT;
1829 goto out; 1900 goto out;
1830 } 1901 }
@@ -1841,38 +1912,38 @@ cert_parse(struct sshbuf *b, struct sshkey *key, const u_char *blob,
1841 key->cert->principals[key->cert->nprincipals++] = principal; 1912 key->cert->principals[key->cert->nprincipals++] = principal;
1842 } 1913 }
1843 1914
1844 sshbuf_reset(tmp); 1915 /*
1845 1916 * Stash a copies of the critical options and extensions sections
1846 if ((ret = sshbuf_put(key->cert->critical, critical, clen)) != 0 || 1917 * for later use.
1847 (ret = sshbuf_put(tmp, critical, clen)) != 0) 1918 */
1919 if ((ret = sshbuf_putb(key->cert->critical, crit)) != 0 ||
1920 (exts != NULL &&
1921 (ret = sshbuf_putb(key->cert->extensions, exts)) != 0))
1848 goto out; 1922 goto out;
1849 1923
1850 /* validate structure */ 1924 /*
1851 while (sshbuf_len(tmp) != 0) { 1925 * Validate critical options and extensions sections format.
1852 if ((ret = sshbuf_get_string_direct(tmp, NULL, NULL)) != 0 || 1926 * NB. extensions are not present in v00 certs.
1853 (ret = sshbuf_get_string_direct(tmp, NULL, NULL)) != 0) { 1927 */
1928 while (sshbuf_len(crit) != 0) {
1929 if ((ret = sshbuf_get_string_direct(crit, NULL, NULL)) != 0 ||
1930 (ret = sshbuf_get_string_direct(crit, NULL, NULL)) != 0) {
1931 sshbuf_reset(key->cert->critical);
1854 ret = SSH_ERR_INVALID_FORMAT; 1932 ret = SSH_ERR_INVALID_FORMAT;
1855 goto out; 1933 goto out;
1856 } 1934 }
1857 } 1935 }
1858 sshbuf_reset(tmp); 1936 while (exts != NULL && sshbuf_len(exts) != 0) {
1859 1937 if ((ret = sshbuf_get_string_direct(exts, NULL, NULL)) != 0 ||
1860 if ((ret = sshbuf_put(key->cert->extensions, exts, elen)) != 0 || 1938 (ret = sshbuf_get_string_direct(exts, NULL, NULL)) != 0) {
1861 (ret = sshbuf_put(tmp, exts, elen)) != 0) 1939 sshbuf_reset(key->cert->extensions);
1862 goto out;
1863
1864 /* validate structure */
1865 while (sshbuf_len(tmp) != 0) {
1866 if ((ret = sshbuf_get_string_direct(tmp, NULL, NULL)) != 0 ||
1867 (ret = sshbuf_get_string_direct(tmp, NULL, NULL)) != 0) {
1868 ret = SSH_ERR_INVALID_FORMAT; 1940 ret = SSH_ERR_INVALID_FORMAT;
1869 goto out; 1941 goto out;
1870 } 1942 }
1871 } 1943 }
1872 sshbuf_reset(tmp);
1873 1944
1874 if (sshkey_from_blob_internal(sig_key, sklen, 1945 /* Parse CA key and check signature */
1875 &key->cert->signature_key, 0) != 0) { 1946 if (sshkey_from_blob_internal(ca, &key->cert->signature_key, 0) != 0) {
1876 ret = SSH_ERR_KEY_CERT_INVALID_SIGN_KEY; 1947 ret = SSH_ERR_KEY_CERT_INVALID_SIGN_KEY;
1877 goto out; 1948 goto out;
1878 } 1949 }
@@ -1880,50 +1951,49 @@ cert_parse(struct sshbuf *b, struct sshkey *key, const u_char *blob,
1880 ret = SSH_ERR_KEY_CERT_INVALID_SIGN_KEY; 1951 ret = SSH_ERR_KEY_CERT_INVALID_SIGN_KEY;
1881 goto out; 1952 goto out;
1882 } 1953 }
1883
1884 if ((ret = sshkey_verify(key->cert->signature_key, sig, slen, 1954 if ((ret = sshkey_verify(key->cert->signature_key, sig, slen,
1885 sshbuf_ptr(key->cert->certblob), signed_len, 0)) != 0) 1955 sshbuf_ptr(key->cert->certblob), signed_len, 0)) != 0)
1886 goto out; 1956 goto out;
1887 ret = 0;
1888 1957
1958 /* Success */
1959 ret = 0;
1889 out: 1960 out:
1890 sshbuf_free(tmp); 1961 sshbuf_free(ca);
1891 free(principals); 1962 sshbuf_free(crit);
1892 free(critical); 1963 sshbuf_free(exts);
1893 free(exts); 1964 sshbuf_free(principals);
1894 free(sig_key);
1895 free(sig); 1965 free(sig);
1896 return ret; 1966 return ret;
1897} 1967}
1898 1968
1899static int 1969static int
1900sshkey_from_blob_internal(const u_char *blob, size_t blen, 1970sshkey_from_blob_internal(struct sshbuf *b, struct sshkey **keyp,
1901 struct sshkey **keyp, int allow_cert) 1971 int allow_cert)
1902{ 1972{
1903 struct sshbuf *b = NULL; 1973 int type, ret = SSH_ERR_INTERNAL_ERROR;
1904 int type, nid = -1, ret = SSH_ERR_INTERNAL_ERROR;
1905 char *ktype = NULL, *curve = NULL; 1974 char *ktype = NULL, *curve = NULL;
1906 struct sshkey *key = NULL; 1975 struct sshkey *key = NULL;
1907 size_t len; 1976 size_t len;
1908 u_char *pk = NULL; 1977 u_char *pk = NULL;
1978 struct sshbuf *copy;
1909#if defined(WITH_OPENSSL) && defined(OPENSSL_HAS_ECC) 1979#if defined(WITH_OPENSSL) && defined(OPENSSL_HAS_ECC)
1910 EC_POINT *q = NULL; 1980 EC_POINT *q = NULL;
1911#endif /* WITH_OPENSSL && OPENSSL_HAS_ECC */ 1981#endif /* WITH_OPENSSL && OPENSSL_HAS_ECC */
1912 1982
1913#ifdef DEBUG_PK /* XXX */ 1983#ifdef DEBUG_PK /* XXX */
1914 dump_base64(stderr, blob, blen); 1984 sshbuf_dump(b, stderr);
1915#endif 1985#endif
1916 *keyp = NULL; 1986 *keyp = NULL;
1917 if ((b = sshbuf_from(blob, blen)) == NULL) 1987 if ((copy = sshbuf_fromb(b)) == NULL) {
1918 return SSH_ERR_ALLOC_FAIL; 1988 ret = SSH_ERR_ALLOC_FAIL;
1989 goto out;
1990 }
1919 if (sshbuf_get_cstring(b, &ktype, NULL) != 0) { 1991 if (sshbuf_get_cstring(b, &ktype, NULL) != 0) {
1920 ret = SSH_ERR_INVALID_FORMAT; 1992 ret = SSH_ERR_INVALID_FORMAT;
1921 goto out; 1993 goto out;
1922 } 1994 }
1923 1995
1924 type = sshkey_type_from_name(ktype); 1996 type = sshkey_type_from_name(ktype);
1925 if (sshkey_type_plain(type) == KEY_ECDSA)
1926 nid = sshkey_ecdsa_nid_from_name(ktype);
1927 if (!allow_cert && sshkey_type_is_cert(type)) { 1997 if (!allow_cert && sshkey_type_is_cert(type)) {
1928 ret = SSH_ERR_KEY_CERT_INVALID_SIGN_KEY; 1998 ret = SSH_ERR_KEY_CERT_INVALID_SIGN_KEY;
1929 goto out; 1999 goto out;
@@ -1931,6 +2001,7 @@ sshkey_from_blob_internal(const u_char *blob, size_t blen,
1931 switch (type) { 2001 switch (type) {
1932#ifdef WITH_OPENSSL 2002#ifdef WITH_OPENSSL
1933 case KEY_RSA_CERT: 2003 case KEY_RSA_CERT:
2004 /* Skip nonce */
1934 if (sshbuf_get_string_direct(b, NULL, NULL) != 0) { 2005 if (sshbuf_get_string_direct(b, NULL, NULL) != 0) {
1935 ret = SSH_ERR_INVALID_FORMAT; 2006 ret = SSH_ERR_INVALID_FORMAT;
1936 goto out; 2007 goto out;
@@ -1952,6 +2023,7 @@ sshkey_from_blob_internal(const u_char *blob, size_t blen,
1952#endif 2023#endif
1953 break; 2024 break;
1954 case KEY_DSA_CERT: 2025 case KEY_DSA_CERT:
2026 /* Skip nonce */
1955 if (sshbuf_get_string_direct(b, NULL, NULL) != 0) { 2027 if (sshbuf_get_string_direct(b, NULL, NULL) != 0) {
1956 ret = SSH_ERR_INVALID_FORMAT; 2028 ret = SSH_ERR_INVALID_FORMAT;
1957 goto out; 2029 goto out;
@@ -1975,6 +2047,7 @@ sshkey_from_blob_internal(const u_char *blob, size_t blen,
1975#endif 2047#endif
1976 break; 2048 break;
1977 case KEY_ECDSA_CERT: 2049 case KEY_ECDSA_CERT:
2050 /* Skip nonce */
1978 if (sshbuf_get_string_direct(b, NULL, NULL) != 0) { 2051 if (sshbuf_get_string_direct(b, NULL, NULL) != 0) {
1979 ret = SSH_ERR_INVALID_FORMAT; 2052 ret = SSH_ERR_INVALID_FORMAT;
1980 goto out; 2053 goto out;
@@ -1986,7 +2059,7 @@ sshkey_from_blob_internal(const u_char *blob, size_t blen,
1986 ret = SSH_ERR_ALLOC_FAIL; 2059 ret = SSH_ERR_ALLOC_FAIL;
1987 goto out; 2060 goto out;
1988 } 2061 }
1989 key->ecdsa_nid = nid; 2062 key->ecdsa_nid = sshkey_ecdsa_nid_from_name(ktype);
1990 if (sshbuf_get_cstring(b, &curve, NULL) != 0) { 2063 if (sshbuf_get_cstring(b, &curve, NULL) != 0) {
1991 ret = SSH_ERR_INVALID_FORMAT; 2064 ret = SSH_ERR_INVALID_FORMAT;
1992 goto out; 2065 goto out;
@@ -2027,6 +2100,7 @@ sshkey_from_blob_internal(const u_char *blob, size_t blen,
2027# endif /* OPENSSL_HAS_ECC */ 2100# endif /* OPENSSL_HAS_ECC */
2028#endif /* WITH_OPENSSL */ 2101#endif /* WITH_OPENSSL */
2029 case KEY_ED25519_CERT: 2102 case KEY_ED25519_CERT:
2103 /* Skip nonce */
2030 if (sshbuf_get_string_direct(b, NULL, NULL) != 0) { 2104 if (sshbuf_get_string_direct(b, NULL, NULL) != 0) {
2031 ret = SSH_ERR_INVALID_FORMAT; 2105 ret = SSH_ERR_INVALID_FORMAT;
2032 goto out; 2106 goto out;
@@ -2058,8 +2132,7 @@ sshkey_from_blob_internal(const u_char *blob, size_t blen,
2058 } 2132 }
2059 2133
2060 /* Parse certificate potion */ 2134 /* Parse certificate potion */
2061 if (sshkey_is_cert(key) && 2135 if (sshkey_is_cert(key) && (ret = cert_parse(b, key, copy)) != 0)
2062 (ret = cert_parse(b, key, blob, blen)) != 0)
2063 goto out; 2136 goto out;
2064 2137
2065 if (key != NULL && sshbuf_len(b) != 0) { 2138 if (key != NULL && sshbuf_len(b) != 0) {
@@ -2070,7 +2143,7 @@ sshkey_from_blob_internal(const u_char *blob, size_t blen,
2070 *keyp = key; 2143 *keyp = key;
2071 key = NULL; 2144 key = NULL;
2072 out: 2145 out:
2073 sshbuf_free(b); 2146 sshbuf_free(copy);
2074 sshkey_free(key); 2147 sshkey_free(key);
2075 free(ktype); 2148 free(ktype);
2076 free(curve); 2149 free(curve);
@@ -2085,7 +2158,33 @@ sshkey_from_blob_internal(const u_char *blob, size_t blen,
2085int 2158int
2086sshkey_from_blob(const u_char *blob, size_t blen, struct sshkey **keyp) 2159sshkey_from_blob(const u_char *blob, size_t blen, struct sshkey **keyp)
2087{ 2160{
2088 return sshkey_from_blob_internal(blob, blen, keyp, 1); 2161 struct sshbuf *b;
2162 int r;
2163
2164 if ((b = sshbuf_from(blob, blen)) == NULL)
2165 return SSH_ERR_ALLOC_FAIL;
2166 r = sshkey_from_blob_internal(b, keyp, 1);
2167 sshbuf_free(b);
2168 return r;
2169}
2170
2171int
2172sshkey_fromb(struct sshbuf *b, struct sshkey **keyp)
2173{
2174 return sshkey_from_blob_internal(b, keyp, 1);
2175}
2176
2177int
2178sshkey_froms(struct sshbuf *buf, struct sshkey **keyp)
2179{
2180 struct sshbuf *b;
2181 int r;
2182
2183 if ((r = sshbuf_froms(buf, &b)) != 0)
2184 return r;
2185 r = sshkey_from_blob_internal(b, keyp, 1);
2186 sshbuf_free(b);
2187 return r;
2089} 2188}
2090 2189
2091int 2190int
@@ -2131,10 +2230,7 @@ sshkey_verify(const struct sshkey *key,
2131 const u_char *sig, size_t siglen, 2230 const u_char *sig, size_t siglen,
2132 const u_char *data, size_t dlen, u_int compat) 2231 const u_char *data, size_t dlen, u_int compat)
2133{ 2232{
2134 if (siglen == 0) 2233 if (siglen == 0 || dlen > SSH_KEY_MAX_SIGN_DATA_SIZE)
2135 return -1;
2136
2137 if (dlen > SSH_KEY_MAX_SIGN_DATA_SIZE)
2138 return SSH_ERR_INVALID_ARGUMENT; 2234 return SSH_ERR_INVALID_ARGUMENT;
2139 switch (key->type) { 2235 switch (key->type) {
2140#ifdef WITH_OPENSSL 2236#ifdef WITH_OPENSSL
@@ -2368,6 +2464,7 @@ sshkey_certify(struct sshkey *k, struct sshkey *ca)
2368 break; 2464 break;
2369 default: 2465 default:
2370 ret = SSH_ERR_INVALID_ARGUMENT; 2466 ret = SSH_ERR_INVALID_ARGUMENT;
2467 goto out;
2371 } 2468 }
2372 2469
2373 /* -v01 certs have a serial number next */ 2470 /* -v01 certs have a serial number next */
@@ -2593,8 +2690,7 @@ sshkey_private_deserialize(struct sshbuf *buf, struct sshkey **kp)
2593{ 2690{
2594 char *tname = NULL, *curve = NULL; 2691 char *tname = NULL, *curve = NULL;
2595 struct sshkey *k = NULL; 2692 struct sshkey *k = NULL;
2596 const u_char *cert; 2693 size_t pklen = 0, sklen = 0;
2597 size_t len, pklen = 0, sklen = 0;
2598 int type, r = SSH_ERR_INTERNAL_ERROR; 2694 int type, r = SSH_ERR_INTERNAL_ERROR;
2599 u_char *ed25519_pk = NULL, *ed25519_sk = NULL; 2695 u_char *ed25519_pk = NULL, *ed25519_sk = NULL;
2600#ifdef WITH_OPENSSL 2696#ifdef WITH_OPENSSL
@@ -2622,8 +2718,7 @@ sshkey_private_deserialize(struct sshbuf *buf, struct sshkey **kp)
2622 break; 2718 break;
2623 case KEY_DSA_CERT_V00: 2719 case KEY_DSA_CERT_V00:
2624 case KEY_DSA_CERT: 2720 case KEY_DSA_CERT:
2625 if ((r = sshbuf_get_string_direct(buf, &cert, &len)) != 0 || 2721 if ((r = sshkey_froms(buf, &k)) != 0 ||
2626 (r = sshkey_from_blob(cert, len, &k)) != 0 ||
2627 (r = sshkey_add_private(k)) != 0 || 2722 (r = sshkey_add_private(k)) != 0 ||
2628 (r = sshbuf_get_bignum2(buf, k->dsa->priv_key)) != 0) 2723 (r = sshbuf_get_bignum2(buf, k->dsa->priv_key)) != 0)
2629 goto out; 2724 goto out;
@@ -2666,8 +2761,7 @@ sshkey_private_deserialize(struct sshbuf *buf, struct sshkey **kp)
2666 r = SSH_ERR_LIBCRYPTO_ERROR; 2761 r = SSH_ERR_LIBCRYPTO_ERROR;
2667 goto out; 2762 goto out;
2668 } 2763 }
2669 if ((r = sshbuf_get_string_direct(buf, &cert, &len)) != 0 || 2764 if ((r = sshkey_froms(buf, &k)) != 0 ||
2670 (r = sshkey_from_blob(cert, len, &k)) != 0 ||
2671 (r = sshkey_add_private(k)) != 0 || 2765 (r = sshkey_add_private(k)) != 0 ||
2672 (r = sshbuf_get_bignum2(buf, exponent)) != 0) 2766 (r = sshbuf_get_bignum2(buf, exponent)) != 0)
2673 goto out; 2767 goto out;
@@ -2697,8 +2791,7 @@ sshkey_private_deserialize(struct sshbuf *buf, struct sshkey **kp)
2697 break; 2791 break;
2698 case KEY_RSA_CERT_V00: 2792 case KEY_RSA_CERT_V00:
2699 case KEY_RSA_CERT: 2793 case KEY_RSA_CERT:
2700 if ((r = sshbuf_get_string_direct(buf, &cert, &len)) != 0 || 2794 if ((r = sshkey_froms(buf, &k)) != 0 ||
2701 (r = sshkey_from_blob(cert, len, &k)) != 0 ||
2702 (r = sshkey_add_private(k)) != 0 || 2795 (r = sshkey_add_private(k)) != 0 ||
2703 (r = sshbuf_get_bignum2(buf, k->rsa->d) != 0) || 2796 (r = sshbuf_get_bignum2(buf, k->rsa->d) != 0) ||
2704 (r = sshbuf_get_bignum2(buf, k->rsa->iqmp) != 0) || 2797 (r = sshbuf_get_bignum2(buf, k->rsa->iqmp) != 0) ||
@@ -2725,8 +2818,7 @@ sshkey_private_deserialize(struct sshbuf *buf, struct sshkey **kp)
2725 ed25519_pk = ed25519_sk = NULL; 2818 ed25519_pk = ed25519_sk = NULL;
2726 break; 2819 break;
2727 case KEY_ED25519_CERT: 2820 case KEY_ED25519_CERT:
2728 if ((r = sshbuf_get_string_direct(buf, &cert, &len)) != 0 || 2821 if ((r = sshkey_froms(buf, &k)) != 0 ||
2729 (r = sshkey_from_blob(cert, len, &k)) != 0 ||
2730 (r = sshkey_add_private(k)) != 0 || 2822 (r = sshkey_add_private(k)) != 0 ||
2731 (r = sshbuf_get_string(buf, &ed25519_pk, &pklen)) != 0 || 2823 (r = sshbuf_get_string(buf, &ed25519_pk, &pklen)) != 0 ||
2732 (r = sshbuf_get_string(buf, &ed25519_sk, &sklen)) != 0) 2824 (r = sshbuf_get_string(buf, &ed25519_sk, &sklen)) != 0)
@@ -2952,8 +3044,9 @@ sshkey_private_to_blob2(const struct sshkey *prv, struct sshbuf *blob,
2952 const char *passphrase, const char *comment, const char *ciphername, 3044 const char *passphrase, const char *comment, const char *ciphername,
2953 int rounds) 3045 int rounds)
2954{ 3046{
2955 u_char *cp, *b64 = NULL, *key = NULL, *pubkeyblob = NULL; 3047 u_char *cp, *key = NULL, *pubkeyblob = NULL;
2956 u_char salt[SALT_LEN]; 3048 u_char salt[SALT_LEN];
3049 char *b64 = NULL;
2957 size_t i, pubkeylen, keylen, ivlen, blocksize, authlen; 3050 size_t i, pubkeylen, keylen, ivlen, blocksize, authlen;
2958 u_int check; 3051 u_int check;
2959 int r = SSH_ERR_INTERNAL_ERROR; 3052 int r = SSH_ERR_INTERNAL_ERROR;
@@ -3165,7 +3258,7 @@ sshkey_parse_private2(struct sshbuf *blob, int type, const char *passphrase,
3165 } 3258 }
3166 3259
3167 /* decode base64 */ 3260 /* decode base64 */
3168 if ((r = sshbuf_b64tod(decoded, sshbuf_ptr(encoded))) != 0) 3261 if ((r = sshbuf_b64tod(decoded, (char *)sshbuf_ptr(encoded))) != 0)
3169 goto out; 3262 goto out;
3170 3263
3171 /* check magic */ 3264 /* check magic */
@@ -3481,10 +3574,12 @@ sshkey_private_to_fileblob(struct sshkey *key, struct sshbuf *blob,
3481 int force_new_format, const char *new_format_cipher, int new_format_rounds) 3574 int force_new_format, const char *new_format_cipher, int new_format_rounds)
3482{ 3575{
3483 switch (key->type) { 3576 switch (key->type) {
3484#ifdef WITH_OPENSSL 3577#ifdef WITH_SSH1
3485 case KEY_RSA1: 3578 case KEY_RSA1:
3486 return sshkey_private_rsa1_to_blob(key, blob, 3579 return sshkey_private_rsa1_to_blob(key, blob,
3487 passphrase, comment); 3580 passphrase, comment);
3581#endif /* WITH_SSH1 */
3582#ifdef WITH_OPENSSL
3488 case KEY_DSA: 3583 case KEY_DSA:
3489 case KEY_ECDSA: 3584 case KEY_ECDSA:
3490 case KEY_RSA: 3585 case KEY_RSA:
@@ -3690,20 +3785,16 @@ sshkey_parse_private_rsa1(struct sshbuf *blob, const char *passphrase,
3690#endif /* WITH_SSH1 */ 3785#endif /* WITH_SSH1 */
3691 3786
3692#ifdef WITH_OPENSSL 3787#ifdef WITH_OPENSSL
3693/* XXX make private once ssh-keysign.c fixed */ 3788static int
3694int
3695sshkey_parse_private_pem_fileblob(struct sshbuf *blob, int type, 3789sshkey_parse_private_pem_fileblob(struct sshbuf *blob, int type,
3696 const char *passphrase, struct sshkey **keyp, char **commentp) 3790 const char *passphrase, struct sshkey **keyp)
3697{ 3791{
3698 EVP_PKEY *pk = NULL; 3792 EVP_PKEY *pk = NULL;
3699 struct sshkey *prv = NULL; 3793 struct sshkey *prv = NULL;
3700 char *name = "<no key>";
3701 BIO *bio = NULL; 3794 BIO *bio = NULL;
3702 int r; 3795 int r;
3703 3796
3704 *keyp = NULL; 3797 *keyp = NULL;
3705 if (commentp != NULL)
3706 *commentp = NULL;
3707 3798
3708 if ((bio = BIO_new(BIO_s_mem())) == NULL || sshbuf_len(blob) > INT_MAX) 3799 if ((bio = BIO_new(BIO_s_mem())) == NULL || sshbuf_len(blob) > INT_MAX)
3709 return SSH_ERR_ALLOC_FAIL; 3800 return SSH_ERR_ALLOC_FAIL;
@@ -3726,7 +3817,6 @@ sshkey_parse_private_pem_fileblob(struct sshbuf *blob, int type,
3726 } 3817 }
3727 prv->rsa = EVP_PKEY_get1_RSA(pk); 3818 prv->rsa = EVP_PKEY_get1_RSA(pk);
3728 prv->type = KEY_RSA; 3819 prv->type = KEY_RSA;
3729 name = "rsa w/o comment";
3730#ifdef DEBUG_PK 3820#ifdef DEBUG_PK
3731 RSA_print_fp(stderr, prv->rsa, 8); 3821 RSA_print_fp(stderr, prv->rsa, 8);
3732#endif 3822#endif
@@ -3742,7 +3832,6 @@ sshkey_parse_private_pem_fileblob(struct sshbuf *blob, int type,
3742 } 3832 }
3743 prv->dsa = EVP_PKEY_get1_DSA(pk); 3833 prv->dsa = EVP_PKEY_get1_DSA(pk);
3744 prv->type = KEY_DSA; 3834 prv->type = KEY_DSA;
3745 name = "dsa w/o comment";
3746#ifdef DEBUG_PK 3835#ifdef DEBUG_PK
3747 DSA_print_fp(stderr, prv->dsa, 8); 3836 DSA_print_fp(stderr, prv->dsa, 8);
3748#endif 3837#endif
@@ -3764,7 +3853,6 @@ sshkey_parse_private_pem_fileblob(struct sshbuf *blob, int type,
3764 r = SSH_ERR_INVALID_FORMAT; 3853 r = SSH_ERR_INVALID_FORMAT;
3765 goto out; 3854 goto out;
3766 } 3855 }
3767 name = "ecdsa w/o comment";
3768# ifdef DEBUG_PK 3856# ifdef DEBUG_PK
3769 if (prv != NULL && prv->ecdsa != NULL) 3857 if (prv != NULL && prv->ecdsa != NULL)
3770 sshkey_dump_ec_key(prv->ecdsa); 3858 sshkey_dump_ec_key(prv->ecdsa);
@@ -3774,11 +3862,6 @@ sshkey_parse_private_pem_fileblob(struct sshbuf *blob, int type,
3774 r = SSH_ERR_INVALID_FORMAT; 3862 r = SSH_ERR_INVALID_FORMAT;
3775 goto out; 3863 goto out;
3776 } 3864 }
3777 if (commentp != NULL &&
3778 (*commentp = strdup(name)) == NULL) {
3779 r = SSH_ERR_ALLOC_FAIL;
3780 goto out;
3781 }
3782 r = 0; 3865 r = 0;
3783 *keyp = prv; 3866 *keyp = prv;
3784 prv = NULL; 3867 prv = NULL;
@@ -3803,15 +3886,17 @@ sshkey_parse_private_fileblob_type(struct sshbuf *blob, int type,
3803 *commentp = NULL; 3886 *commentp = NULL;
3804 3887
3805 switch (type) { 3888 switch (type) {
3806#ifdef WITH_OPENSSL 3889#ifdef WITH_SSH1
3807 case KEY_RSA1: 3890 case KEY_RSA1:
3808 return sshkey_parse_private_rsa1(blob, passphrase, 3891 return sshkey_parse_private_rsa1(blob, passphrase,
3809 keyp, commentp); 3892 keyp, commentp);
3893#endif /* WITH_SSH1 */
3894#ifdef WITH_OPENSSL
3810 case KEY_DSA: 3895 case KEY_DSA:
3811 case KEY_ECDSA: 3896 case KEY_ECDSA:
3812 case KEY_RSA: 3897 case KEY_RSA:
3813 return sshkey_parse_private_pem_fileblob(blob, type, passphrase, 3898 return sshkey_parse_private_pem_fileblob(blob, type,
3814 keyp, commentp); 3899 passphrase, keyp);
3815#endif /* WITH_OPENSSL */ 3900#endif /* WITH_OPENSSL */
3816 case KEY_ED25519: 3901 case KEY_ED25519:
3817 return sshkey_parse_private2(blob, type, passphrase, 3902 return sshkey_parse_private2(blob, type, passphrase,
@@ -3821,8 +3906,8 @@ sshkey_parse_private_fileblob_type(struct sshbuf *blob, int type,
3821 commentp)) == 0) 3906 commentp)) == 0)
3822 return 0; 3907 return 0;
3823#ifdef WITH_OPENSSL 3908#ifdef WITH_OPENSSL
3824 return sshkey_parse_private_pem_fileblob(blob, type, passphrase, 3909 return sshkey_parse_private_pem_fileblob(blob, type,
3825 keyp, commentp); 3910 passphrase, keyp);
3826#else 3911#else
3827 return SSH_ERR_INVALID_FORMAT; 3912 return SSH_ERR_INVALID_FORMAT;
3828#endif /* WITH_OPENSSL */ 3913#endif /* WITH_OPENSSL */