diff options
Diffstat (limited to 'sshconnect2.c')
-rw-r--r-- | sshconnect2.c | 99 |
1 files changed, 46 insertions, 53 deletions
diff --git a/sshconnect2.c b/sshconnect2.c index c22477f59..83562c688 100644 --- a/sshconnect2.c +++ b/sshconnect2.c | |||
@@ -1,4 +1,4 @@ | |||
1 | /* $OpenBSD: sshconnect2.c,v 1.266 2017/08/27 00:38:41 dtucker Exp $ */ | 1 | /* $OpenBSD: sshconnect2.c,v 1.270 2018/03/24 19:28:43 markus Exp $ */ |
2 | /* | 2 | /* |
3 | * Copyright (c) 2000 Markus Friedl. All rights reserved. | 3 | * Copyright (c) 2000 Markus Friedl. All rights reserved. |
4 | * Copyright (c) 2008 Damien Miller. All rights reserved. | 4 | * Copyright (c) 2008 Damien Miller. All rights reserved. |
@@ -644,7 +644,6 @@ input_userauth_pk_ok(int type, u_int32_t seq, struct ssh *ssh) | |||
644 | Authctxt *authctxt = ssh->authctxt; | 644 | Authctxt *authctxt = ssh->authctxt; |
645 | struct sshkey *key = NULL; | 645 | struct sshkey *key = NULL; |
646 | Identity *id = NULL; | 646 | Identity *id = NULL; |
647 | Buffer b; | ||
648 | int pktype, sent = 0; | 647 | int pktype, sent = 0; |
649 | u_int alen, blen; | 648 | u_int alen, blen; |
650 | char *pkalg, *fp; | 649 | char *pkalg, *fp; |
@@ -652,18 +651,9 @@ input_userauth_pk_ok(int type, u_int32_t seq, struct ssh *ssh) | |||
652 | 651 | ||
653 | if (authctxt == NULL) | 652 | if (authctxt == NULL) |
654 | fatal("input_userauth_pk_ok: no authentication context"); | 653 | fatal("input_userauth_pk_ok: no authentication context"); |
655 | if (datafellows & SSH_BUG_PKOK) { | 654 | |
656 | /* this is similar to SSH_BUG_PKAUTH */ | 655 | pkalg = packet_get_string(&alen); |
657 | debug2("input_userauth_pk_ok: SSH_BUG_PKOK"); | 656 | pkblob = packet_get_string(&blen); |
658 | pkblob = packet_get_string(&blen); | ||
659 | buffer_init(&b); | ||
660 | buffer_append(&b, pkblob, blen); | ||
661 | pkalg = buffer_get_string(&b, &alen); | ||
662 | buffer_free(&b); | ||
663 | } else { | ||
664 | pkalg = packet_get_string(&alen); | ||
665 | pkblob = packet_get_string(&blen); | ||
666 | } | ||
667 | packet_check_eom(); | 657 | packet_check_eom(); |
668 | 658 | ||
669 | debug("Server accepts key: pkalg %s blen %u", pkalg, blen); | 659 | debug("Server accepts key: pkalg %s blen %u", pkalg, blen); |
@@ -700,8 +690,7 @@ input_userauth_pk_ok(int type, u_int32_t seq, struct ssh *ssh) | |||
700 | } | 690 | } |
701 | } | 691 | } |
702 | done: | 692 | done: |
703 | if (key != NULL) | 693 | key_free(key); |
704 | key_free(key); | ||
705 | free(pkalg); | 694 | free(pkalg); |
706 | free(pkblob); | 695 | free(pkblob); |
707 | 696 | ||
@@ -1136,17 +1125,46 @@ key_sign_encode(const struct sshkey *key) | |||
1136 | return key_ssh_name(key); | 1125 | return key_ssh_name(key); |
1137 | } | 1126 | } |
1138 | 1127 | ||
1128 | /* | ||
1129 | * Some agents will return ssh-rsa signatures when asked to make a | ||
1130 | * rsa-sha2-* signature. Check what they actually gave back and warn the | ||
1131 | * user if the agent has returned an unexpected type. | ||
1132 | */ | ||
1133 | static int | ||
1134 | check_sigtype(const struct sshkey *key, const u_char *sig, size_t len) | ||
1135 | { | ||
1136 | int r; | ||
1137 | char *sigtype = NULL; | ||
1138 | const char *alg = key_sign_encode(key); | ||
1139 | |||
1140 | if (sshkey_is_cert(key)) | ||
1141 | return 0; | ||
1142 | if ((r = sshkey_sigtype(sig, len, &sigtype)) != 0) | ||
1143 | return r; | ||
1144 | if (strcmp(sigtype, alg) != 0) { | ||
1145 | logit("warning: agent returned different signature type %s " | ||
1146 | "(expected %s)", sigtype, alg); | ||
1147 | } | ||
1148 | free(sigtype); | ||
1149 | /* Incorrect signature types aren't an error ... yet */ | ||
1150 | return 0; | ||
1151 | } | ||
1152 | |||
1139 | static int | 1153 | static int |
1140 | identity_sign(struct identity *id, u_char **sigp, size_t *lenp, | 1154 | identity_sign(struct identity *id, u_char **sigp, size_t *lenp, |
1141 | const u_char *data, size_t datalen, u_int compat) | 1155 | const u_char *data, size_t datalen, u_int compat) |
1142 | { | 1156 | { |
1143 | struct sshkey *prv; | 1157 | struct sshkey *prv; |
1144 | int ret; | 1158 | int r; |
1145 | 1159 | ||
1146 | /* the agent supports this key */ | 1160 | /* the agent supports this key */ |
1147 | if (id->key != NULL && id->agent_fd != -1) | 1161 | if (id->key != NULL && id->agent_fd != -1) { |
1148 | return ssh_agent_sign(id->agent_fd, id->key, sigp, lenp, | 1162 | if ((r = ssh_agent_sign(id->agent_fd, id->key, sigp, lenp, |
1149 | data, datalen, key_sign_encode(id->key), compat); | 1163 | data, datalen, key_sign_encode(id->key), compat)) != 0 || |
1164 | (r = check_sigtype(id->key, *sigp, *lenp)) != 0) | ||
1165 | return r; | ||
1166 | return 0; | ||
1167 | } | ||
1150 | 1168 | ||
1151 | /* | 1169 | /* |
1152 | * we have already loaded the private key or | 1170 | * we have already loaded the private key or |
@@ -1165,10 +1183,10 @@ identity_sign(struct identity *id, u_char **sigp, size_t *lenp, | |||
1165 | __func__, id->filename); | 1183 | __func__, id->filename); |
1166 | return SSH_ERR_KEY_NOT_FOUND; | 1184 | return SSH_ERR_KEY_NOT_FOUND; |
1167 | } | 1185 | } |
1168 | ret = sshkey_sign(prv, sigp, lenp, data, datalen, | 1186 | r = sshkey_sign(prv, sigp, lenp, data, datalen, |
1169 | key_sign_encode(prv), compat); | 1187 | key_sign_encode(prv), compat); |
1170 | sshkey_free(prv); | 1188 | sshkey_free(prv); |
1171 | return (ret); | 1189 | return r; |
1172 | } | 1190 | } |
1173 | 1191 | ||
1174 | static int | 1192 | static int |
@@ -1223,17 +1241,10 @@ sign_and_send_pubkey(Authctxt *authctxt, Identity *id) | |||
1223 | } | 1241 | } |
1224 | buffer_put_char(&b, SSH2_MSG_USERAUTH_REQUEST); | 1242 | buffer_put_char(&b, SSH2_MSG_USERAUTH_REQUEST); |
1225 | buffer_put_cstring(&b, authctxt->server_user); | 1243 | buffer_put_cstring(&b, authctxt->server_user); |
1226 | buffer_put_cstring(&b, | 1244 | buffer_put_cstring(&b, authctxt->service); |
1227 | datafellows & SSH_BUG_PKSERVICE ? | 1245 | buffer_put_cstring(&b, authctxt->method->name); |
1228 | "ssh-userauth" : | 1246 | buffer_put_char(&b, have_sig); |
1229 | authctxt->service); | 1247 | buffer_put_cstring(&b, key_sign_encode(id->key)); |
1230 | if (datafellows & SSH_BUG_PKAUTH) { | ||
1231 | buffer_put_char(&b, have_sig); | ||
1232 | } else { | ||
1233 | buffer_put_cstring(&b, authctxt->method->name); | ||
1234 | buffer_put_char(&b, have_sig); | ||
1235 | buffer_put_cstring(&b, key_sign_encode(id->key)); | ||
1236 | } | ||
1237 | buffer_put_string(&b, blob, bloblen); | 1248 | buffer_put_string(&b, blob, bloblen); |
1238 | 1249 | ||
1239 | /* | 1250 | /* |
@@ -1293,19 +1304,6 @@ sign_and_send_pubkey(Authctxt *authctxt, Identity *id) | |||
1293 | #ifdef DEBUG_PK | 1304 | #ifdef DEBUG_PK |
1294 | buffer_dump(&b); | 1305 | buffer_dump(&b); |
1295 | #endif | 1306 | #endif |
1296 | if (datafellows & SSH_BUG_PKSERVICE) { | ||
1297 | buffer_clear(&b); | ||
1298 | buffer_append(&b, session_id2, session_id2_len); | ||
1299 | skip = session_id2_len; | ||
1300 | buffer_put_char(&b, SSH2_MSG_USERAUTH_REQUEST); | ||
1301 | buffer_put_cstring(&b, authctxt->server_user); | ||
1302 | buffer_put_cstring(&b, authctxt->service); | ||
1303 | buffer_put_cstring(&b, authctxt->method->name); | ||
1304 | buffer_put_char(&b, have_sig); | ||
1305 | if (!(datafellows & SSH_BUG_PKAUTH)) | ||
1306 | buffer_put_cstring(&b, key_ssh_name(id->key)); | ||
1307 | buffer_put_string(&b, blob, bloblen); | ||
1308 | } | ||
1309 | free(blob); | 1307 | free(blob); |
1310 | 1308 | ||
1311 | /* append signature */ | 1309 | /* append signature */ |
@@ -1347,8 +1345,7 @@ send_pubkey_test(Authctxt *authctxt, Identity *id) | |||
1347 | packet_put_cstring(authctxt->service); | 1345 | packet_put_cstring(authctxt->service); |
1348 | packet_put_cstring(authctxt->method->name); | 1346 | packet_put_cstring(authctxt->method->name); |
1349 | packet_put_char(have_sig); | 1347 | packet_put_char(have_sig); |
1350 | if (!(datafellows & SSH_BUG_PKAUTH)) | 1348 | packet_put_cstring(key_sign_encode(id->key)); |
1351 | packet_put_cstring(key_sign_encode(id->key)); | ||
1352 | packet_put_string(blob, bloblen); | 1349 | packet_put_string(blob, bloblen); |
1353 | free(blob); | 1350 | free(blob); |
1354 | packet_send(); | 1351 | packet_send(); |
@@ -1864,7 +1861,6 @@ userauth_hostbased(Authctxt *authctxt) | |||
1864 | struct ssh *ssh = active_state; | 1861 | struct ssh *ssh = active_state; |
1865 | struct sshkey *private = NULL; | 1862 | struct sshkey *private = NULL; |
1866 | struct sshbuf *b = NULL; | 1863 | struct sshbuf *b = NULL; |
1867 | const char *service; | ||
1868 | u_char *sig = NULL, *keyblob = NULL; | 1864 | u_char *sig = NULL, *keyblob = NULL; |
1869 | char *fp = NULL, *chost = NULL, *lname = NULL; | 1865 | char *fp = NULL, *chost = NULL, *lname = NULL; |
1870 | size_t siglen = 0, keylen = 0; | 1866 | size_t siglen = 0, keylen = 0; |
@@ -1935,9 +1931,6 @@ userauth_hostbased(Authctxt *authctxt) | |||
1935 | xasprintf(&chost, "%s.", lname); | 1931 | xasprintf(&chost, "%s.", lname); |
1936 | debug2("%s: chost %s", __func__, chost); | 1932 | debug2("%s: chost %s", __func__, chost); |
1937 | 1933 | ||
1938 | service = datafellows & SSH_BUG_HBSERVICE ? "ssh-userauth" : | ||
1939 | authctxt->service; | ||
1940 | |||
1941 | /* construct data */ | 1934 | /* construct data */ |
1942 | if ((b = sshbuf_new()) == NULL) { | 1935 | if ((b = sshbuf_new()) == NULL) { |
1943 | error("%s: sshbuf_new failed", __func__); | 1936 | error("%s: sshbuf_new failed", __func__); |
@@ -1950,7 +1943,7 @@ userauth_hostbased(Authctxt *authctxt) | |||
1950 | if ((r = sshbuf_put_string(b, session_id2, session_id2_len)) != 0 || | 1943 | if ((r = sshbuf_put_string(b, session_id2, session_id2_len)) != 0 || |
1951 | (r = sshbuf_put_u8(b, SSH2_MSG_USERAUTH_REQUEST)) != 0 || | 1944 | (r = sshbuf_put_u8(b, SSH2_MSG_USERAUTH_REQUEST)) != 0 || |
1952 | (r = sshbuf_put_cstring(b, authctxt->server_user)) != 0 || | 1945 | (r = sshbuf_put_cstring(b, authctxt->server_user)) != 0 || |
1953 | (r = sshbuf_put_cstring(b, service)) != 0 || | 1946 | (r = sshbuf_put_cstring(b, authctxt->service)) != 0 || |
1954 | (r = sshbuf_put_cstring(b, authctxt->method->name)) != 0 || | 1947 | (r = sshbuf_put_cstring(b, authctxt->method->name)) != 0 || |
1955 | (r = sshbuf_put_cstring(b, key_ssh_name(private))) != 0 || | 1948 | (r = sshbuf_put_cstring(b, key_ssh_name(private))) != 0 || |
1956 | (r = sshbuf_put_string(b, keyblob, keylen)) != 0 || | 1949 | (r = sshbuf_put_string(b, keyblob, keylen)) != 0 || |