diff options
Diffstat (limited to 'key.c')
-rw-r--r-- | key.c | 182 |
1 files changed, 149 insertions, 33 deletions
@@ -1,4 +1,4 @@ | |||
1 | /* $OpenBSD: key.c,v 1.86 2010/03/15 19:40:02 stevesk Exp $ */ | 1 | /* $OpenBSD: key.c,v 1.90 2010/07/13 23:13:16 djm Exp $ */ |
2 | /* | 2 | /* |
3 | * read_bignum(): | 3 | * read_bignum(): |
4 | * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland | 4 | * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland |
@@ -52,6 +52,7 @@ | |||
52 | #include "uuencode.h" | 52 | #include "uuencode.h" |
53 | #include "buffer.h" | 53 | #include "buffer.h" |
54 | #include "log.h" | 54 | #include "log.h" |
55 | #include "misc.h" | ||
55 | #include "ssh2.h" | 56 | #include "ssh2.h" |
56 | 57 | ||
57 | static struct KeyCert * | 58 | static struct KeyCert * |
@@ -61,7 +62,8 @@ cert_new(void) | |||
61 | 62 | ||
62 | cert = xcalloc(1, sizeof(*cert)); | 63 | cert = xcalloc(1, sizeof(*cert)); |
63 | buffer_init(&cert->certblob); | 64 | buffer_init(&cert->certblob); |
64 | buffer_init(&cert->constraints); | 65 | buffer_init(&cert->critical); |
66 | buffer_init(&cert->extensions); | ||
65 | cert->key_id = NULL; | 67 | cert->key_id = NULL; |
66 | cert->principals = NULL; | 68 | cert->principals = NULL; |
67 | cert->signature_key = NULL; | 69 | cert->signature_key = NULL; |
@@ -82,6 +84,7 @@ key_new(int type) | |||
82 | switch (k->type) { | 84 | switch (k->type) { |
83 | case KEY_RSA1: | 85 | case KEY_RSA1: |
84 | case KEY_RSA: | 86 | case KEY_RSA: |
87 | case KEY_RSA_CERT_V00: | ||
85 | case KEY_RSA_CERT: | 88 | case KEY_RSA_CERT: |
86 | if ((rsa = RSA_new()) == NULL) | 89 | if ((rsa = RSA_new()) == NULL) |
87 | fatal("key_new: RSA_new failed"); | 90 | fatal("key_new: RSA_new failed"); |
@@ -92,6 +95,7 @@ key_new(int type) | |||
92 | k->rsa = rsa; | 95 | k->rsa = rsa; |
93 | break; | 96 | break; |
94 | case KEY_DSA: | 97 | case KEY_DSA: |
98 | case KEY_DSA_CERT_V00: | ||
95 | case KEY_DSA_CERT: | 99 | case KEY_DSA_CERT: |
96 | if ((dsa = DSA_new()) == NULL) | 100 | if ((dsa = DSA_new()) == NULL) |
97 | fatal("key_new: DSA_new failed"); | 101 | fatal("key_new: DSA_new failed"); |
@@ -124,6 +128,7 @@ key_add_private(Key *k) | |||
124 | switch (k->type) { | 128 | switch (k->type) { |
125 | case KEY_RSA1: | 129 | case KEY_RSA1: |
126 | case KEY_RSA: | 130 | case KEY_RSA: |
131 | case KEY_RSA_CERT_V00: | ||
127 | case KEY_RSA_CERT: | 132 | case KEY_RSA_CERT: |
128 | if ((k->rsa->d = BN_new()) == NULL) | 133 | if ((k->rsa->d = BN_new()) == NULL) |
129 | fatal("key_new_private: BN_new failed"); | 134 | fatal("key_new_private: BN_new failed"); |
@@ -139,6 +144,7 @@ key_add_private(Key *k) | |||
139 | fatal("key_new_private: BN_new failed"); | 144 | fatal("key_new_private: BN_new failed"); |
140 | break; | 145 | break; |
141 | case KEY_DSA: | 146 | case KEY_DSA: |
147 | case KEY_DSA_CERT_V00: | ||
142 | case KEY_DSA_CERT: | 148 | case KEY_DSA_CERT: |
143 | if ((k->dsa->priv_key = BN_new()) == NULL) | 149 | if ((k->dsa->priv_key = BN_new()) == NULL) |
144 | fatal("key_new_private: BN_new failed"); | 150 | fatal("key_new_private: BN_new failed"); |
@@ -165,7 +171,8 @@ cert_free(struct KeyCert *cert) | |||
165 | u_int i; | 171 | u_int i; |
166 | 172 | ||
167 | buffer_free(&cert->certblob); | 173 | buffer_free(&cert->certblob); |
168 | buffer_free(&cert->constraints); | 174 | buffer_free(&cert->critical); |
175 | buffer_free(&cert->extensions); | ||
169 | if (cert->key_id != NULL) | 176 | if (cert->key_id != NULL) |
170 | xfree(cert->key_id); | 177 | xfree(cert->key_id); |
171 | for (i = 0; i < cert->nprincipals; i++) | 178 | for (i = 0; i < cert->nprincipals; i++) |
@@ -184,12 +191,14 @@ key_free(Key *k) | |||
184 | switch (k->type) { | 191 | switch (k->type) { |
185 | case KEY_RSA1: | 192 | case KEY_RSA1: |
186 | case KEY_RSA: | 193 | case KEY_RSA: |
194 | case KEY_RSA_CERT_V00: | ||
187 | case KEY_RSA_CERT: | 195 | case KEY_RSA_CERT: |
188 | if (k->rsa != NULL) | 196 | if (k->rsa != NULL) |
189 | RSA_free(k->rsa); | 197 | RSA_free(k->rsa); |
190 | k->rsa = NULL; | 198 | k->rsa = NULL; |
191 | break; | 199 | break; |
192 | case KEY_DSA: | 200 | case KEY_DSA: |
201 | case KEY_DSA_CERT_V00: | ||
193 | case KEY_DSA_CERT: | 202 | case KEY_DSA_CERT: |
194 | if (k->dsa != NULL) | 203 | if (k->dsa != NULL) |
195 | DSA_free(k->dsa); | 204 | DSA_free(k->dsa); |
@@ -219,7 +228,7 @@ cert_compare(struct KeyCert *a, struct KeyCert *b) | |||
219 | return 0; | 228 | return 0; |
220 | if (buffer_len(&a->certblob) != buffer_len(&b->certblob)) | 229 | if (buffer_len(&a->certblob) != buffer_len(&b->certblob)) |
221 | return 0; | 230 | return 0; |
222 | if (memcmp(buffer_ptr(&a->certblob), buffer_ptr(&b->certblob), | 231 | if (timingsafe_bcmp(buffer_ptr(&a->certblob), buffer_ptr(&b->certblob), |
223 | buffer_len(&a->certblob)) != 0) | 232 | buffer_len(&a->certblob)) != 0) |
224 | return 0; | 233 | return 0; |
225 | return 1; | 234 | return 1; |
@@ -238,11 +247,13 @@ key_equal_public(const Key *a, const Key *b) | |||
238 | 247 | ||
239 | switch (a->type) { | 248 | switch (a->type) { |
240 | case KEY_RSA1: | 249 | case KEY_RSA1: |
250 | case KEY_RSA_CERT_V00: | ||
241 | case KEY_RSA_CERT: | 251 | case KEY_RSA_CERT: |
242 | case KEY_RSA: | 252 | case KEY_RSA: |
243 | return a->rsa != NULL && b->rsa != NULL && | 253 | return a->rsa != NULL && b->rsa != NULL && |
244 | BN_cmp(a->rsa->e, b->rsa->e) == 0 && | 254 | BN_cmp(a->rsa->e, b->rsa->e) == 0 && |
245 | BN_cmp(a->rsa->n, b->rsa->n) == 0; | 255 | BN_cmp(a->rsa->n, b->rsa->n) == 0; |
256 | case KEY_DSA_CERT_V00: | ||
246 | case KEY_DSA_CERT: | 257 | case KEY_DSA_CERT: |
247 | case KEY_DSA: | 258 | case KEY_DSA: |
248 | return a->dsa != NULL && b->dsa != NULL && | 259 | return a->dsa != NULL && b->dsa != NULL && |
@@ -304,6 +315,8 @@ key_fingerprint_raw(Key *k, enum fp_type dgst_type, u_int *dgst_raw_length) | |||
304 | case KEY_RSA: | 315 | case KEY_RSA: |
305 | key_to_blob(k, &blob, &len); | 316 | key_to_blob(k, &blob, &len); |
306 | break; | 317 | break; |
318 | case KEY_DSA_CERT_V00: | ||
319 | case KEY_RSA_CERT_V00: | ||
307 | case KEY_DSA_CERT: | 320 | case KEY_DSA_CERT: |
308 | case KEY_RSA_CERT: | 321 | case KEY_RSA_CERT: |
309 | /* We want a fingerprint of the _key_ not of the cert */ | 322 | /* We want a fingerprint of the _key_ not of the cert */ |
@@ -631,6 +644,8 @@ key_read(Key *ret, char **cpp) | |||
631 | case KEY_UNSPEC: | 644 | case KEY_UNSPEC: |
632 | case KEY_RSA: | 645 | case KEY_RSA: |
633 | case KEY_DSA: | 646 | case KEY_DSA: |
647 | case KEY_DSA_CERT_V00: | ||
648 | case KEY_RSA_CERT_V00: | ||
634 | case KEY_DSA_CERT: | 649 | case KEY_DSA_CERT: |
635 | case KEY_RSA_CERT: | 650 | case KEY_RSA_CERT: |
636 | space = strchr(cp, ' '); | 651 | space = strchr(cp, ' '); |
@@ -757,11 +772,13 @@ key_write(const Key *key, FILE *f) | |||
757 | error("key_write: failed for RSA key"); | 772 | error("key_write: failed for RSA key"); |
758 | return 0; | 773 | return 0; |
759 | case KEY_DSA: | 774 | case KEY_DSA: |
775 | case KEY_DSA_CERT_V00: | ||
760 | case KEY_DSA_CERT: | 776 | case KEY_DSA_CERT: |
761 | if (key->dsa == NULL) | 777 | if (key->dsa == NULL) |
762 | return 0; | 778 | return 0; |
763 | break; | 779 | break; |
764 | case KEY_RSA: | 780 | case KEY_RSA: |
781 | case KEY_RSA_CERT_V00: | ||
765 | case KEY_RSA_CERT: | 782 | case KEY_RSA_CERT: |
766 | if (key->rsa == NULL) | 783 | if (key->rsa == NULL) |
767 | return 0; | 784 | return 0; |
@@ -793,6 +810,10 @@ key_type(const Key *k) | |||
793 | return "RSA"; | 810 | return "RSA"; |
794 | case KEY_DSA: | 811 | case KEY_DSA: |
795 | return "DSA"; | 812 | return "DSA"; |
813 | case KEY_RSA_CERT_V00: | ||
814 | return "RSA-CERT-V00"; | ||
815 | case KEY_DSA_CERT_V00: | ||
816 | return "DSA-CERT-V00"; | ||
796 | case KEY_RSA_CERT: | 817 | case KEY_RSA_CERT: |
797 | return "RSA-CERT"; | 818 | return "RSA-CERT"; |
798 | case KEY_DSA_CERT: | 819 | case KEY_DSA_CERT: |
@@ -822,10 +843,14 @@ key_ssh_name(const Key *k) | |||
822 | return "ssh-rsa"; | 843 | return "ssh-rsa"; |
823 | case KEY_DSA: | 844 | case KEY_DSA: |
824 | return "ssh-dss"; | 845 | return "ssh-dss"; |
825 | case KEY_RSA_CERT: | 846 | case KEY_RSA_CERT_V00: |
826 | return "ssh-rsa-cert-v00@openssh.com"; | 847 | return "ssh-rsa-cert-v00@openssh.com"; |
827 | case KEY_DSA_CERT: | 848 | case KEY_DSA_CERT_V00: |
828 | return "ssh-dss-cert-v00@openssh.com"; | 849 | return "ssh-dss-cert-v00@openssh.com"; |
850 | case KEY_RSA_CERT: | ||
851 | return "ssh-rsa-cert-v01@openssh.com"; | ||
852 | case KEY_DSA_CERT: | ||
853 | return "ssh-dss-cert-v01@openssh.com"; | ||
829 | } | 854 | } |
830 | return "ssh-unknown"; | 855 | return "ssh-unknown"; |
831 | } | 856 | } |
@@ -836,9 +861,11 @@ key_size(const Key *k) | |||
836 | switch (k->type) { | 861 | switch (k->type) { |
837 | case KEY_RSA1: | 862 | case KEY_RSA1: |
838 | case KEY_RSA: | 863 | case KEY_RSA: |
864 | case KEY_RSA_CERT_V00: | ||
839 | case KEY_RSA_CERT: | 865 | case KEY_RSA_CERT: |
840 | return BN_num_bits(k->rsa->n); | 866 | return BN_num_bits(k->rsa->n); |
841 | case KEY_DSA: | 867 | case KEY_DSA: |
868 | case KEY_DSA_CERT_V00: | ||
842 | case KEY_DSA_CERT: | 869 | case KEY_DSA_CERT: |
843 | return BN_num_bits(k->dsa->p); | 870 | return BN_num_bits(k->dsa->p); |
844 | } | 871 | } |
@@ -882,6 +909,8 @@ key_generate(int type, u_int bits) | |||
882 | case KEY_RSA1: | 909 | case KEY_RSA1: |
883 | k->rsa = rsa_generate_private_key(bits); | 910 | k->rsa = rsa_generate_private_key(bits); |
884 | break; | 911 | break; |
912 | case KEY_RSA_CERT_V00: | ||
913 | case KEY_DSA_CERT_V00: | ||
885 | case KEY_RSA_CERT: | 914 | case KEY_RSA_CERT: |
886 | case KEY_DSA_CERT: | 915 | case KEY_DSA_CERT: |
887 | fatal("key_generate: cert keys cannot be generated directly"); | 916 | fatal("key_generate: cert keys cannot be generated directly"); |
@@ -912,9 +941,12 @@ key_cert_copy(const Key *from_key, struct Key *to_key) | |||
912 | buffer_append(&to->certblob, buffer_ptr(&from->certblob), | 941 | buffer_append(&to->certblob, buffer_ptr(&from->certblob), |
913 | buffer_len(&from->certblob)); | 942 | buffer_len(&from->certblob)); |
914 | 943 | ||
915 | buffer_append(&to->constraints, buffer_ptr(&from->constraints), | 944 | buffer_append(&to->critical, |
916 | buffer_len(&from->constraints)); | 945 | buffer_ptr(&from->critical), buffer_len(&from->critical)); |
946 | buffer_append(&to->extensions, | ||
947 | buffer_ptr(&from->extensions), buffer_len(&from->extensions)); | ||
917 | 948 | ||
949 | to->serial = from->serial; | ||
918 | to->type = from->type; | 950 | to->type = from->type; |
919 | to->key_id = from->key_id == NULL ? NULL : xstrdup(from->key_id); | 951 | to->key_id = from->key_id == NULL ? NULL : xstrdup(from->key_id); |
920 | to->valid_after = from->valid_after; | 952 | to->valid_after = from->valid_after; |
@@ -940,6 +972,7 @@ key_from_private(const Key *k) | |||
940 | Key *n = NULL; | 972 | Key *n = NULL; |
941 | switch (k->type) { | 973 | switch (k->type) { |
942 | case KEY_DSA: | 974 | case KEY_DSA: |
975 | case KEY_DSA_CERT_V00: | ||
943 | case KEY_DSA_CERT: | 976 | case KEY_DSA_CERT: |
944 | n = key_new(k->type); | 977 | n = key_new(k->type); |
945 | if ((BN_copy(n->dsa->p, k->dsa->p) == NULL) || | 978 | if ((BN_copy(n->dsa->p, k->dsa->p) == NULL) || |
@@ -950,6 +983,7 @@ key_from_private(const Key *k) | |||
950 | break; | 983 | break; |
951 | case KEY_RSA: | 984 | case KEY_RSA: |
952 | case KEY_RSA1: | 985 | case KEY_RSA1: |
986 | case KEY_RSA_CERT_V00: | ||
953 | case KEY_RSA_CERT: | 987 | case KEY_RSA_CERT: |
954 | n = key_new(k->type); | 988 | n = key_new(k->type); |
955 | if ((BN_copy(n->rsa->n, k->rsa->n) == NULL) || | 989 | if ((BN_copy(n->rsa->n, k->rsa->n) == NULL) || |
@@ -979,8 +1013,12 @@ key_type_from_name(char *name) | |||
979 | } else if (strcmp(name, "ssh-dss") == 0) { | 1013 | } else if (strcmp(name, "ssh-dss") == 0) { |
980 | return KEY_DSA; | 1014 | return KEY_DSA; |
981 | } else if (strcmp(name, "ssh-rsa-cert-v00@openssh.com") == 0) { | 1015 | } else if (strcmp(name, "ssh-rsa-cert-v00@openssh.com") == 0) { |
982 | return KEY_RSA_CERT; | 1016 | return KEY_RSA_CERT_V00; |
983 | } else if (strcmp(name, "ssh-dss-cert-v00@openssh.com") == 0) { | 1017 | } else if (strcmp(name, "ssh-dss-cert-v00@openssh.com") == 0) { |
1018 | return KEY_DSA_CERT_V00; | ||
1019 | } else if (strcmp(name, "ssh-rsa-cert-v01@openssh.com") == 0) { | ||
1020 | return KEY_RSA_CERT; | ||
1021 | } else if (strcmp(name, "ssh-dss-cert-v01@openssh.com") == 0) { | ||
984 | return KEY_DSA_CERT; | 1022 | return KEY_DSA_CERT; |
985 | } | 1023 | } |
986 | debug2("key_type_from_name: unknown key type '%s'", name); | 1024 | debug2("key_type_from_name: unknown key type '%s'", name); |
@@ -1012,26 +1050,31 @@ key_names_valid2(const char *names) | |||
1012 | static int | 1050 | static int |
1013 | cert_parse(Buffer *b, Key *key, const u_char *blob, u_int blen) | 1051 | cert_parse(Buffer *b, Key *key, const u_char *blob, u_int blen) |
1014 | { | 1052 | { |
1015 | u_char *principals, *constraints, *sig_key, *sig; | 1053 | u_char *principals, *critical, *exts, *sig_key, *sig; |
1016 | u_int signed_len, plen, clen, sklen, slen, kidlen; | 1054 | u_int signed_len, plen, clen, sklen, slen, kidlen, elen; |
1017 | Buffer tmp; | 1055 | Buffer tmp; |
1018 | char *principal; | 1056 | char *principal; |
1019 | int ret = -1; | 1057 | int ret = -1; |
1058 | int v00 = key->type == KEY_DSA_CERT_V00 || | ||
1059 | key->type == KEY_RSA_CERT_V00; | ||
1020 | 1060 | ||
1021 | buffer_init(&tmp); | 1061 | buffer_init(&tmp); |
1022 | 1062 | ||
1023 | /* Copy the entire key blob for verification and later serialisation */ | 1063 | /* Copy the entire key blob for verification and later serialisation */ |
1024 | buffer_append(&key->cert->certblob, blob, blen); | 1064 | buffer_append(&key->cert->certblob, blob, blen); |
1025 | 1065 | ||
1026 | principals = constraints = sig_key = sig = NULL; | 1066 | elen = 0; /* Not touched for v00 certs */ |
1027 | if (buffer_get_int_ret(&key->cert->type, b) != 0 || | 1067 | principals = exts = critical = sig_key = sig = NULL; |
1068 | if ((!v00 && buffer_get_int64_ret(&key->cert->serial, b) != 0) || | ||
1069 | buffer_get_int_ret(&key->cert->type, b) != 0 || | ||
1028 | (key->cert->key_id = buffer_get_string_ret(b, &kidlen)) == NULL || | 1070 | (key->cert->key_id = buffer_get_string_ret(b, &kidlen)) == NULL || |
1029 | (principals = buffer_get_string_ret(b, &plen)) == NULL || | 1071 | (principals = buffer_get_string_ret(b, &plen)) == NULL || |
1030 | buffer_get_int64_ret(&key->cert->valid_after, b) != 0 || | 1072 | buffer_get_int64_ret(&key->cert->valid_after, b) != 0 || |
1031 | buffer_get_int64_ret(&key->cert->valid_before, b) != 0 || | 1073 | buffer_get_int64_ret(&key->cert->valid_before, b) != 0 || |
1032 | (constraints = buffer_get_string_ret(b, &clen)) == NULL || | 1074 | (critical = buffer_get_string_ret(b, &clen)) == NULL || |
1033 | /* skip nonce */ buffer_get_string_ptr_ret(b, NULL) == NULL || | 1075 | (!v00 && (exts = buffer_get_string_ret(b, &elen)) == NULL) || |
1034 | /* skip reserved */ buffer_get_string_ptr_ret(b, NULL) == NULL || | 1076 | (v00 && buffer_get_string_ptr_ret(b, NULL) == NULL) || /* nonce */ |
1077 | buffer_get_string_ptr_ret(b, NULL) == NULL || /* reserved */ | ||
1035 | (sig_key = buffer_get_string_ret(b, &sklen)) == NULL) { | 1078 | (sig_key = buffer_get_string_ret(b, &sklen)) == NULL) { |
1036 | error("%s: parse error", __func__); | 1079 | error("%s: parse error", __func__); |
1037 | goto out; | 1080 | goto out; |
@@ -1078,13 +1121,25 @@ cert_parse(Buffer *b, Key *key, const u_char *blob, u_int blen) | |||
1078 | 1121 | ||
1079 | buffer_clear(&tmp); | 1122 | buffer_clear(&tmp); |
1080 | 1123 | ||
1081 | buffer_append(&key->cert->constraints, constraints, clen); | 1124 | buffer_append(&key->cert->critical, critical, clen); |
1082 | buffer_append(&tmp, constraints, clen); | 1125 | buffer_append(&tmp, critical, clen); |
1083 | /* validate structure */ | 1126 | /* validate structure */ |
1084 | while (buffer_len(&tmp) != 0) { | 1127 | while (buffer_len(&tmp) != 0) { |
1085 | if (buffer_get_string_ptr_ret(&tmp, NULL) == NULL || | 1128 | if (buffer_get_string_ptr_ret(&tmp, NULL) == NULL || |
1086 | buffer_get_string_ptr_ret(&tmp, NULL) == NULL) { | 1129 | buffer_get_string_ptr_ret(&tmp, NULL) == NULL) { |
1087 | error("%s: Constraints data invalid", __func__); | 1130 | error("%s: critical option data invalid", __func__); |
1131 | goto out; | ||
1132 | } | ||
1133 | } | ||
1134 | buffer_clear(&tmp); | ||
1135 | |||
1136 | buffer_append(&key->cert->extensions, exts, elen); | ||
1137 | buffer_append(&tmp, exts, elen); | ||
1138 | /* validate structure */ | ||
1139 | while (buffer_len(&tmp) != 0) { | ||
1140 | if (buffer_get_string_ptr_ret(&tmp, NULL) == NULL || | ||
1141 | buffer_get_string_ptr_ret(&tmp, NULL) == NULL) { | ||
1142 | error("%s: extension data invalid", __func__); | ||
1088 | goto out; | 1143 | goto out; |
1089 | } | 1144 | } |
1090 | } | 1145 | } |
@@ -1121,8 +1176,10 @@ cert_parse(Buffer *b, Key *key, const u_char *blob, u_int blen) | |||
1121 | buffer_free(&tmp); | 1176 | buffer_free(&tmp); |
1122 | if (principals != NULL) | 1177 | if (principals != NULL) |
1123 | xfree(principals); | 1178 | xfree(principals); |
1124 | if (constraints != NULL) | 1179 | if (critical != NULL) |
1125 | xfree(constraints); | 1180 | xfree(critical); |
1181 | if (exts != NULL) | ||
1182 | xfree(exts); | ||
1126 | if (sig_key != NULL) | 1183 | if (sig_key != NULL) |
1127 | xfree(sig_key); | 1184 | xfree(sig_key); |
1128 | if (sig != NULL) | 1185 | if (sig != NULL) |
@@ -1151,8 +1208,11 @@ key_from_blob(const u_char *blob, u_int blen) | |||
1151 | type = key_type_from_name(ktype); | 1208 | type = key_type_from_name(ktype); |
1152 | 1209 | ||
1153 | switch (type) { | 1210 | switch (type) { |
1154 | case KEY_RSA: | ||
1155 | case KEY_RSA_CERT: | 1211 | case KEY_RSA_CERT: |
1212 | (void)buffer_get_string_ptr_ret(&b, NULL); /* Skip nonce */ | ||
1213 | /* FALLTHROUGH */ | ||
1214 | case KEY_RSA: | ||
1215 | case KEY_RSA_CERT_V00: | ||
1156 | key = key_new(type); | 1216 | key = key_new(type); |
1157 | if (buffer_get_bignum2_ret(&b, key->rsa->e) == -1 || | 1217 | if (buffer_get_bignum2_ret(&b, key->rsa->e) == -1 || |
1158 | buffer_get_bignum2_ret(&b, key->rsa->n) == -1) { | 1218 | buffer_get_bignum2_ret(&b, key->rsa->n) == -1) { |
@@ -1166,8 +1226,11 @@ key_from_blob(const u_char *blob, u_int blen) | |||
1166 | RSA_print_fp(stderr, key->rsa, 8); | 1226 | RSA_print_fp(stderr, key->rsa, 8); |
1167 | #endif | 1227 | #endif |
1168 | break; | 1228 | break; |
1169 | case KEY_DSA: | ||
1170 | case KEY_DSA_CERT: | 1229 | case KEY_DSA_CERT: |
1230 | (void)buffer_get_string_ptr_ret(&b, NULL); /* Skip nonce */ | ||
1231 | /* FALLTHROUGH */ | ||
1232 | case KEY_DSA: | ||
1233 | case KEY_DSA_CERT_V00: | ||
1171 | key = key_new(type); | 1234 | key = key_new(type); |
1172 | if (buffer_get_bignum2_ret(&b, key->dsa->p) == -1 || | 1235 | if (buffer_get_bignum2_ret(&b, key->dsa->p) == -1 || |
1173 | buffer_get_bignum2_ret(&b, key->dsa->q) == -1 || | 1236 | buffer_get_bignum2_ret(&b, key->dsa->q) == -1 || |
@@ -1213,6 +1276,8 @@ key_to_blob(const Key *key, u_char **blobp, u_int *lenp) | |||
1213 | } | 1276 | } |
1214 | buffer_init(&b); | 1277 | buffer_init(&b); |
1215 | switch (key->type) { | 1278 | switch (key->type) { |
1279 | case KEY_DSA_CERT_V00: | ||
1280 | case KEY_RSA_CERT_V00: | ||
1216 | case KEY_DSA_CERT: | 1281 | case KEY_DSA_CERT: |
1217 | case KEY_RSA_CERT: | 1282 | case KEY_RSA_CERT: |
1218 | /* Use the existing blob */ | 1283 | /* Use the existing blob */ |
@@ -1255,9 +1320,11 @@ key_sign( | |||
1255 | const u_char *data, u_int datalen) | 1320 | const u_char *data, u_int datalen) |
1256 | { | 1321 | { |
1257 | switch (key->type) { | 1322 | switch (key->type) { |
1323 | case KEY_DSA_CERT_V00: | ||
1258 | case KEY_DSA_CERT: | 1324 | case KEY_DSA_CERT: |
1259 | case KEY_DSA: | 1325 | case KEY_DSA: |
1260 | return ssh_dss_sign(key, sigp, lenp, data, datalen); | 1326 | return ssh_dss_sign(key, sigp, lenp, data, datalen); |
1327 | case KEY_RSA_CERT_V00: | ||
1261 | case KEY_RSA_CERT: | 1328 | case KEY_RSA_CERT: |
1262 | case KEY_RSA: | 1329 | case KEY_RSA: |
1263 | return ssh_rsa_sign(key, sigp, lenp, data, datalen); | 1330 | return ssh_rsa_sign(key, sigp, lenp, data, datalen); |
@@ -1281,9 +1348,11 @@ key_verify( | |||
1281 | return -1; | 1348 | return -1; |
1282 | 1349 | ||
1283 | switch (key->type) { | 1350 | switch (key->type) { |
1351 | case KEY_DSA_CERT_V00: | ||
1284 | case KEY_DSA_CERT: | 1352 | case KEY_DSA_CERT: |
1285 | case KEY_DSA: | 1353 | case KEY_DSA: |
1286 | return ssh_dss_verify(key, signature, signaturelen, data, datalen); | 1354 | return ssh_dss_verify(key, signature, signaturelen, data, datalen); |
1355 | case KEY_RSA_CERT_V00: | ||
1287 | case KEY_RSA_CERT: | 1356 | case KEY_RSA_CERT: |
1288 | case KEY_RSA: | 1357 | case KEY_RSA: |
1289 | return ssh_rsa_verify(key, signature, signaturelen, data, datalen); | 1358 | return ssh_rsa_verify(key, signature, signaturelen, data, datalen); |
@@ -1306,6 +1375,7 @@ key_demote(const Key *k) | |||
1306 | pk->rsa = NULL; | 1375 | pk->rsa = NULL; |
1307 | 1376 | ||
1308 | switch (k->type) { | 1377 | switch (k->type) { |
1378 | case KEY_RSA_CERT_V00: | ||
1309 | case KEY_RSA_CERT: | 1379 | case KEY_RSA_CERT: |
1310 | key_cert_copy(k, pk); | 1380 | key_cert_copy(k, pk); |
1311 | /* FALLTHROUGH */ | 1381 | /* FALLTHROUGH */ |
@@ -1318,6 +1388,7 @@ key_demote(const Key *k) | |||
1318 | if ((pk->rsa->n = BN_dup(k->rsa->n)) == NULL) | 1388 | if ((pk->rsa->n = BN_dup(k->rsa->n)) == NULL) |
1319 | fatal("key_demote: BN_dup failed"); | 1389 | fatal("key_demote: BN_dup failed"); |
1320 | break; | 1390 | break; |
1391 | case KEY_DSA_CERT_V00: | ||
1321 | case KEY_DSA_CERT: | 1392 | case KEY_DSA_CERT: |
1322 | key_cert_copy(k, pk); | 1393 | key_cert_copy(k, pk); |
1323 | /* FALLTHROUGH */ | 1394 | /* FALLTHROUGH */ |
@@ -1344,8 +1415,17 @@ key_demote(const Key *k) | |||
1344 | int | 1415 | int |
1345 | key_is_cert(const Key *k) | 1416 | key_is_cert(const Key *k) |
1346 | { | 1417 | { |
1347 | return k != NULL && | 1418 | if (k == NULL) |
1348 | (k->type == KEY_RSA_CERT || k->type == KEY_DSA_CERT); | 1419 | return 0; |
1420 | switch (k->type) { | ||
1421 | case KEY_RSA_CERT_V00: | ||
1422 | case KEY_DSA_CERT_V00: | ||
1423 | case KEY_RSA_CERT: | ||
1424 | case KEY_DSA_CERT: | ||
1425 | return 1; | ||
1426 | default: | ||
1427 | return 0; | ||
1428 | } | ||
1349 | } | 1429 | } |
1350 | 1430 | ||
1351 | /* Return the cert-less equivalent to a certified key type */ | 1431 | /* Return the cert-less equivalent to a certified key type */ |
@@ -1353,8 +1433,10 @@ int | |||
1353 | key_type_plain(int type) | 1433 | key_type_plain(int type) |
1354 | { | 1434 | { |
1355 | switch (type) { | 1435 | switch (type) { |
1436 | case KEY_RSA_CERT_V00: | ||
1356 | case KEY_RSA_CERT: | 1437 | case KEY_RSA_CERT: |
1357 | return KEY_RSA; | 1438 | return KEY_RSA; |
1439 | case KEY_DSA_CERT_V00: | ||
1358 | case KEY_DSA_CERT: | 1440 | case KEY_DSA_CERT: |
1359 | return KEY_DSA; | 1441 | return KEY_DSA; |
1360 | default: | 1442 | default: |
@@ -1364,16 +1446,16 @@ key_type_plain(int type) | |||
1364 | 1446 | ||
1365 | /* Convert a KEY_RSA or KEY_DSA to their _CERT equivalent */ | 1447 | /* Convert a KEY_RSA or KEY_DSA to their _CERT equivalent */ |
1366 | int | 1448 | int |
1367 | key_to_certified(Key *k) | 1449 | key_to_certified(Key *k, int legacy) |
1368 | { | 1450 | { |
1369 | switch (k->type) { | 1451 | switch (k->type) { |
1370 | case KEY_RSA: | 1452 | case KEY_RSA: |
1371 | k->cert = cert_new(); | 1453 | k->cert = cert_new(); |
1372 | k->type = KEY_RSA_CERT; | 1454 | k->type = legacy ? KEY_RSA_CERT_V00 : KEY_RSA_CERT; |
1373 | return 0; | 1455 | return 0; |
1374 | case KEY_DSA: | 1456 | case KEY_DSA: |
1375 | k->cert = cert_new(); | 1457 | k->cert = cert_new(); |
1376 | k->type = KEY_DSA_CERT; | 1458 | k->type = legacy ? KEY_DSA_CERT_V00 : KEY_DSA_CERT; |
1377 | return 0; | 1459 | return 0; |
1378 | default: | 1460 | default: |
1379 | error("%s: key has incorrect type %s", __func__, key_type(k)); | 1461 | error("%s: key has incorrect type %s", __func__, key_type(k)); |
@@ -1386,10 +1468,12 @@ int | |||
1386 | key_drop_cert(Key *k) | 1468 | key_drop_cert(Key *k) |
1387 | { | 1469 | { |
1388 | switch (k->type) { | 1470 | switch (k->type) { |
1471 | case KEY_RSA_CERT_V00: | ||
1389 | case KEY_RSA_CERT: | 1472 | case KEY_RSA_CERT: |
1390 | cert_free(k->cert); | 1473 | cert_free(k->cert); |
1391 | k->type = KEY_RSA; | 1474 | k->type = KEY_RSA; |
1392 | return 0; | 1475 | return 0; |
1476 | case KEY_DSA_CERT_V00: | ||
1393 | case KEY_DSA_CERT: | 1477 | case KEY_DSA_CERT: |
1394 | cert_free(k->cert); | 1478 | cert_free(k->cert); |
1395 | k->type = KEY_DSA; | 1479 | k->type = KEY_DSA; |
@@ -1430,13 +1514,21 @@ key_certify(Key *k, Key *ca) | |||
1430 | buffer_clear(&k->cert->certblob); | 1514 | buffer_clear(&k->cert->certblob); |
1431 | buffer_put_cstring(&k->cert->certblob, key_ssh_name(k)); | 1515 | buffer_put_cstring(&k->cert->certblob, key_ssh_name(k)); |
1432 | 1516 | ||
1517 | /* -v01 certs put nonce first */ | ||
1518 | if (k->type == KEY_DSA_CERT || k->type == KEY_RSA_CERT) { | ||
1519 | arc4random_buf(&nonce, sizeof(nonce)); | ||
1520 | buffer_put_string(&k->cert->certblob, nonce, sizeof(nonce)); | ||
1521 | } | ||
1522 | |||
1433 | switch (k->type) { | 1523 | switch (k->type) { |
1524 | case KEY_DSA_CERT_V00: | ||
1434 | case KEY_DSA_CERT: | 1525 | case KEY_DSA_CERT: |
1435 | buffer_put_bignum2(&k->cert->certblob, k->dsa->p); | 1526 | buffer_put_bignum2(&k->cert->certblob, k->dsa->p); |
1436 | buffer_put_bignum2(&k->cert->certblob, k->dsa->q); | 1527 | buffer_put_bignum2(&k->cert->certblob, k->dsa->q); |
1437 | buffer_put_bignum2(&k->cert->certblob, k->dsa->g); | 1528 | buffer_put_bignum2(&k->cert->certblob, k->dsa->g); |
1438 | buffer_put_bignum2(&k->cert->certblob, k->dsa->pub_key); | 1529 | buffer_put_bignum2(&k->cert->certblob, k->dsa->pub_key); |
1439 | break; | 1530 | break; |
1531 | case KEY_RSA_CERT_V00: | ||
1440 | case KEY_RSA_CERT: | 1532 | case KEY_RSA_CERT: |
1441 | buffer_put_bignum2(&k->cert->certblob, k->rsa->e); | 1533 | buffer_put_bignum2(&k->cert->certblob, k->rsa->e); |
1442 | buffer_put_bignum2(&k->cert->certblob, k->rsa->n); | 1534 | buffer_put_bignum2(&k->cert->certblob, k->rsa->n); |
@@ -1448,6 +1540,10 @@ key_certify(Key *k, Key *ca) | |||
1448 | return -1; | 1540 | return -1; |
1449 | } | 1541 | } |
1450 | 1542 | ||
1543 | /* -v01 certs have a serial number next */ | ||
1544 | if (k->type == KEY_DSA_CERT || k->type == KEY_RSA_CERT) | ||
1545 | buffer_put_int64(&k->cert->certblob, k->cert->serial); | ||
1546 | |||
1451 | buffer_put_int(&k->cert->certblob, k->cert->type); | 1547 | buffer_put_int(&k->cert->certblob, k->cert->type); |
1452 | buffer_put_cstring(&k->cert->certblob, k->cert->key_id); | 1548 | buffer_put_cstring(&k->cert->certblob, k->cert->key_id); |
1453 | 1549 | ||
@@ -1461,11 +1557,19 @@ key_certify(Key *k, Key *ca) | |||
1461 | buffer_put_int64(&k->cert->certblob, k->cert->valid_after); | 1557 | buffer_put_int64(&k->cert->certblob, k->cert->valid_after); |
1462 | buffer_put_int64(&k->cert->certblob, k->cert->valid_before); | 1558 | buffer_put_int64(&k->cert->certblob, k->cert->valid_before); |
1463 | buffer_put_string(&k->cert->certblob, | 1559 | buffer_put_string(&k->cert->certblob, |
1464 | buffer_ptr(&k->cert->constraints), | 1560 | buffer_ptr(&k->cert->critical), buffer_len(&k->cert->critical)); |
1465 | buffer_len(&k->cert->constraints)); | 1561 | |
1562 | /* -v01 certs have non-critical options here */ | ||
1563 | if (k->type == KEY_DSA_CERT || k->type == KEY_RSA_CERT) { | ||
1564 | buffer_put_string(&k->cert->certblob, | ||
1565 | buffer_ptr(&k->cert->extensions), | ||
1566 | buffer_len(&k->cert->extensions)); | ||
1567 | } | ||
1568 | |||
1569 | /* -v00 certs put the nonce at the end */ | ||
1570 | if (k->type == KEY_DSA_CERT_V00 || k->type == KEY_RSA_CERT_V00) | ||
1571 | buffer_put_string(&k->cert->certblob, nonce, sizeof(nonce)); | ||
1466 | 1572 | ||
1467 | arc4random_buf(&nonce, sizeof(nonce)); | ||
1468 | buffer_put_string(&k->cert->certblob, nonce, sizeof(nonce)); | ||
1469 | buffer_put_string(&k->cert->certblob, NULL, 0); /* reserved */ | 1573 | buffer_put_string(&k->cert->certblob, NULL, 0); /* reserved */ |
1470 | buffer_put_string(&k->cert->certblob, ca_blob, ca_len); | 1574 | buffer_put_string(&k->cert->certblob, ca_blob, ca_len); |
1471 | xfree(ca_blob); | 1575 | xfree(ca_blob); |
@@ -1520,7 +1624,7 @@ key_cert_check_authority(const Key *k, int want_host, int require_principal, | |||
1520 | *reason = "Certificate lacks principal list"; | 1624 | *reason = "Certificate lacks principal list"; |
1521 | return -1; | 1625 | return -1; |
1522 | } | 1626 | } |
1523 | } else { | 1627 | } else if (name != NULL) { |
1524 | principal_matches = 0; | 1628 | principal_matches = 0; |
1525 | for (i = 0; i < k->cert->nprincipals; i++) { | 1629 | for (i = 0; i < k->cert->nprincipals; i++) { |
1526 | if (strcmp(name, k->cert->principals[i]) == 0) { | 1630 | if (strcmp(name, k->cert->principals[i]) == 0) { |
@@ -1536,3 +1640,15 @@ key_cert_check_authority(const Key *k, int want_host, int require_principal, | |||
1536 | } | 1640 | } |
1537 | return 0; | 1641 | return 0; |
1538 | } | 1642 | } |
1643 | |||
1644 | int | ||
1645 | key_cert_is_legacy(Key *k) | ||
1646 | { | ||
1647 | switch (k->type) { | ||
1648 | case KEY_DSA_CERT_V00: | ||
1649 | case KEY_RSA_CERT_V00: | ||
1650 | return 1; | ||
1651 | default: | ||
1652 | return 0; | ||
1653 | } | ||
1654 | } | ||