summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authordjm@openbsd.org <djm@openbsd.org>2016-08-03 05:41:57 +0000
committerDarren Tucker <dtucker@zip.com.au>2016-08-09 09:06:52 +1000
commit4706c1d8c15cd5565b59512853c2da9bd4ca26c9 (patch)
tree81ff9de3bdf3627b382bb4b808cf0e0612f4424f
parente600348a7afd6325cc5cd783cb424065cbc20434 (diff)
upstream commit
small refactor of cipher.c: make ciphercontext opaque to callers feedback and ok markus@ Upstream-ID: 094849f8be68c3bdad2c0f3dee551ecf7be87f6f
-rw-r--r--cipher-chachapoly.c5
-rw-r--r--cipher.c165
-rw-r--r--cipher.h23
-rw-r--r--packet.c88
-rw-r--r--sshkey.c37
5 files changed, 179 insertions, 139 deletions
diff --git a/cipher-chachapoly.c b/cipher-chachapoly.c
index 7f31ff4ce..0899c5ad5 100644
--- a/cipher-chachapoly.c
+++ b/cipher-chachapoly.c
@@ -14,7 +14,7 @@
14 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
15 */ 15 */
16 16
17/* $OpenBSD: cipher-chachapoly.c,v 1.7 2015/01/14 10:24:42 markus Exp $ */ 17/* $OpenBSD: cipher-chachapoly.c,v 1.8 2016/08/03 05:41:57 djm Exp $ */
18 18
19#include "includes.h" 19#include "includes.h"
20 20
@@ -28,7 +28,8 @@
28#include "ssherr.h" 28#include "ssherr.h"
29#include "cipher-chachapoly.h" 29#include "cipher-chachapoly.h"
30 30
31int chachapoly_init(struct chachapoly_ctx *ctx, 31int
32chachapoly_init(struct chachapoly_ctx *ctx,
32 const u_char *key, u_int keylen) 33 const u_char *key, u_int keylen)
33{ 34{
34 if (keylen != (32 + 32)) /* 2 x 256 bit keys */ 35 if (keylen != (32 + 32)) /* 2 x 256 bit keys */
diff --git a/cipher.c b/cipher.c
index 031bda9ec..747b59bf0 100644
--- a/cipher.c
+++ b/cipher.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: cipher.c,v 1.101 2015/12/10 17:08:40 mmcc Exp $ */ 1/* $OpenBSD: cipher.c,v 1.102 2016/08/03 05:41:57 djm Exp $ */
2/* 2/*
3 * Author: Tatu Ylonen <ylo@cs.hut.fi> 3 * Author: Tatu Ylonen <ylo@cs.hut.fi>
4 * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland 4 * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland
@@ -57,6 +57,15 @@ extern const EVP_CIPHER *evp_ssh1_3des(void);
57extern int ssh1_3des_iv(EVP_CIPHER_CTX *, int, u_char *, int); 57extern int ssh1_3des_iv(EVP_CIPHER_CTX *, int, u_char *, int);
58#endif 58#endif
59 59
60struct sshcipher_ctx {
61 int plaintext;
62 int encrypt;
63 EVP_CIPHER_CTX *evp;
64 struct chachapoly_ctx cp_ctx; /* XXX union with evp? */
65 struct aesctr_ctx ac_ctx; /* XXX union with evp? */
66 const struct sshcipher *cipher;
67};
68
60struct sshcipher { 69struct sshcipher {
61 char *name; 70 char *name;
62 int number; /* for ssh1 only */ 71 int number; /* for ssh1 only */
@@ -206,6 +215,18 @@ cipher_is_cbc(const struct sshcipher *c)
206} 215}
207 216
208u_int 217u_int
218cipher_ctx_is_plaintext(struct sshcipher_ctx *cc)
219{
220 return cc->plaintext;
221}
222
223u_int
224cipher_ctx_get_number(struct sshcipher_ctx *cc)
225{
226 return cc->cipher->number;
227}
228
229u_int
209cipher_mask_ssh1(int client) 230cipher_mask_ssh1(int client)
210{ 231{
211 u_int mask = 0; 232 u_int mask = 0;
@@ -297,65 +318,81 @@ cipher_warning_message(const struct sshcipher_ctx *cc)
297} 318}
298 319
299int 320int
300cipher_init(struct sshcipher_ctx *cc, const struct sshcipher *cipher, 321cipher_init(struct sshcipher_ctx **ccp, const struct sshcipher *cipher,
301 const u_char *key, u_int keylen, const u_char *iv, u_int ivlen, 322 const u_char *key, u_int keylen, const u_char *iv, u_int ivlen,
302 int do_encrypt) 323 int do_encrypt)
303{ 324{
304#ifdef WITH_OPENSSL 325 struct sshcipher_ctx *cc = NULL;
305 int ret = SSH_ERR_INTERNAL_ERROR; 326 int ret = SSH_ERR_INTERNAL_ERROR;
327#ifdef WITH_OPENSSL
306 const EVP_CIPHER *type; 328 const EVP_CIPHER *type;
307 int klen; 329 int klen;
308 u_char *junk, *discard; 330 u_char *junk, *discard;
331#endif
332
333 *ccp = NULL;
334 if ((cc = calloc(sizeof(*cc), 1)) == NULL)
335 return SSH_ERR_ALLOC_FAIL;
309 336
310 if (cipher->number == SSH_CIPHER_DES) { 337 if (cipher->number == SSH_CIPHER_DES) {
311 if (keylen > 8) 338 if (keylen > 8)
312 keylen = 8; 339 keylen = 8;
313 } 340 }
314#endif 341
315 cc->plaintext = (cipher->number == SSH_CIPHER_NONE); 342 cc->plaintext = (cipher->number == SSH_CIPHER_NONE);
316 cc->encrypt = do_encrypt; 343 cc->encrypt = do_encrypt;
317 344
318 if (keylen < cipher->key_len || 345 if (keylen < cipher->key_len ||
319 (iv != NULL && ivlen < cipher_ivlen(cipher))) 346 (iv != NULL && ivlen < cipher_ivlen(cipher))) {
320 return SSH_ERR_INVALID_ARGUMENT; 347 ret = SSH_ERR_INVALID_ARGUMENT;
348 goto out;
349 }
321 350
322 cc->cipher = cipher; 351 cc->cipher = cipher;
323 if ((cc->cipher->flags & CFLAG_CHACHAPOLY) != 0) { 352 if ((cc->cipher->flags & CFLAG_CHACHAPOLY) != 0) {
324 return chachapoly_init(&cc->cp_ctx, key, keylen); 353 ret = chachapoly_init(&cc->cp_ctx, key, keylen);
354 goto out;
325 } 355 }
326#ifndef WITH_OPENSSL 356#ifndef WITH_OPENSSL
327 if ((cc->cipher->flags & CFLAG_AESCTR) != 0) { 357 if ((cc->cipher->flags & CFLAG_AESCTR) != 0) {
328 aesctr_keysetup(&cc->ac_ctx, key, 8 * keylen, 8 * ivlen); 358 aesctr_keysetup(&cc->ac_ctx, key, 8 * keylen, 8 * ivlen);
329 aesctr_ivsetup(&cc->ac_ctx, iv); 359 aesctr_ivsetup(&cc->ac_ctx, iv);
330 return 0; 360 ret = 0;
361 goto out;
331 } 362 }
332 if ((cc->cipher->flags & CFLAG_NONE) != 0) 363 if ((cc->cipher->flags & CFLAG_NONE) != 0) {
333 return 0; 364 ret = 0;
334 return SSH_ERR_INVALID_ARGUMENT; 365 goto out;
335#else 366 }
367 ret = SSH_ERR_INVALID_ARGUMENT;
368 goto out;
369#else /* WITH_OPENSSL */
336 type = (*cipher->evptype)(); 370 type = (*cipher->evptype)();
337 EVP_CIPHER_CTX_init(&cc->evp); 371 if ((cc->evp = EVP_CIPHER_CTX_new()) == NULL) {
338 if (EVP_CipherInit(&cc->evp, type, NULL, (u_char *)iv, 372 ret = SSH_ERR_ALLOC_FAIL;
373 goto out;
374 }
375 if (EVP_CipherInit(cc->evp, type, NULL, (u_char *)iv,
339 (do_encrypt == CIPHER_ENCRYPT)) == 0) { 376 (do_encrypt == CIPHER_ENCRYPT)) == 0) {
340 ret = SSH_ERR_LIBCRYPTO_ERROR; 377 ret = SSH_ERR_LIBCRYPTO_ERROR;
341 goto bad; 378 goto out;
342 } 379 }
343 if (cipher_authlen(cipher) && 380 if (cipher_authlen(cipher) &&
344 !EVP_CIPHER_CTX_ctrl(&cc->evp, EVP_CTRL_GCM_SET_IV_FIXED, 381 !EVP_CIPHER_CTX_ctrl(cc->evp, EVP_CTRL_GCM_SET_IV_FIXED,
345 -1, (u_char *)iv)) { 382 -1, (u_char *)iv)) {
346 ret = SSH_ERR_LIBCRYPTO_ERROR; 383 ret = SSH_ERR_LIBCRYPTO_ERROR;
347 goto bad; 384 goto out;
348 } 385 }
349 klen = EVP_CIPHER_CTX_key_length(&cc->evp); 386 klen = EVP_CIPHER_CTX_key_length(cc->evp);
350 if (klen > 0 && keylen != (u_int)klen) { 387 if (klen > 0 && keylen != (u_int)klen) {
351 if (EVP_CIPHER_CTX_set_key_length(&cc->evp, keylen) == 0) { 388 if (EVP_CIPHER_CTX_set_key_length(cc->evp, keylen) == 0) {
352 ret = SSH_ERR_LIBCRYPTO_ERROR; 389 ret = SSH_ERR_LIBCRYPTO_ERROR;
353 goto bad; 390 goto out;
354 } 391 }
355 } 392 }
356 if (EVP_CipherInit(&cc->evp, NULL, (u_char *)key, NULL, -1) == 0) { 393 if (EVP_CipherInit(cc->evp, NULL, (u_char *)key, NULL, -1) == 0) {
357 ret = SSH_ERR_LIBCRYPTO_ERROR; 394 ret = SSH_ERR_LIBCRYPTO_ERROR;
358 goto bad; 395 goto out;
359 } 396 }
360 397
361 if (cipher->discard_len > 0) { 398 if (cipher->discard_len > 0) {
@@ -363,21 +400,34 @@ cipher_init(struct sshcipher_ctx *cc, const struct sshcipher *cipher,
363 (discard = malloc(cipher->discard_len)) == NULL) { 400 (discard = malloc(cipher->discard_len)) == NULL) {
364 free(junk); 401 free(junk);
365 ret = SSH_ERR_ALLOC_FAIL; 402 ret = SSH_ERR_ALLOC_FAIL;
366 goto bad; 403 goto out;
367 } 404 }
368 ret = EVP_Cipher(&cc->evp, discard, junk, cipher->discard_len); 405 ret = EVP_Cipher(cc->evp, discard, junk, cipher->discard_len);
369 explicit_bzero(discard, cipher->discard_len); 406 explicit_bzero(discard, cipher->discard_len);
370 free(junk); 407 free(junk);
371 free(discard); 408 free(discard);
372 if (ret != 1) { 409 if (ret != 1) {
373 ret = SSH_ERR_LIBCRYPTO_ERROR; 410 ret = SSH_ERR_LIBCRYPTO_ERROR;
374 bad: 411 goto out;
375 EVP_CIPHER_CTX_cleanup(&cc->evp);
376 return ret;
377 } 412 }
378 } 413 }
379#endif 414 ret = 0;
380 return 0; 415#endif /* WITH_OPENSSL */
416 out:
417 if (ret == 0) {
418 /* success */
419 *ccp = cc;
420 } else {
421 if (cc != NULL) {
422#ifdef WITH_OPENSSL
423 if (cc->evp != NULL)
424 EVP_CIPHER_CTX_free(cc->evp);
425#endif /* WITH_OPENSSL */
426 explicit_bzero(cc, sizeof(*cc));
427 free(cc);
428 }
429 }
430 return ret;
381} 431}
382 432
383/* 433/*
@@ -418,33 +468,33 @@ cipher_crypt(struct sshcipher_ctx *cc, u_int seqnr, u_char *dest,
418 if (authlen != cipher_authlen(cc->cipher)) 468 if (authlen != cipher_authlen(cc->cipher))
419 return SSH_ERR_INVALID_ARGUMENT; 469 return SSH_ERR_INVALID_ARGUMENT;
420 /* increment IV */ 470 /* increment IV */
421 if (!EVP_CIPHER_CTX_ctrl(&cc->evp, EVP_CTRL_GCM_IV_GEN, 471 if (!EVP_CIPHER_CTX_ctrl(cc->evp, EVP_CTRL_GCM_IV_GEN,
422 1, lastiv)) 472 1, lastiv))
423 return SSH_ERR_LIBCRYPTO_ERROR; 473 return SSH_ERR_LIBCRYPTO_ERROR;
424 /* set tag on decyption */ 474 /* set tag on decyption */
425 if (!cc->encrypt && 475 if (!cc->encrypt &&
426 !EVP_CIPHER_CTX_ctrl(&cc->evp, EVP_CTRL_GCM_SET_TAG, 476 !EVP_CIPHER_CTX_ctrl(cc->evp, EVP_CTRL_GCM_SET_TAG,
427 authlen, (u_char *)src + aadlen + len)) 477 authlen, (u_char *)src + aadlen + len))
428 return SSH_ERR_LIBCRYPTO_ERROR; 478 return SSH_ERR_LIBCRYPTO_ERROR;
429 } 479 }
430 if (aadlen) { 480 if (aadlen) {
431 if (authlen && 481 if (authlen &&
432 EVP_Cipher(&cc->evp, NULL, (u_char *)src, aadlen) < 0) 482 EVP_Cipher(cc->evp, NULL, (u_char *)src, aadlen) < 0)
433 return SSH_ERR_LIBCRYPTO_ERROR; 483 return SSH_ERR_LIBCRYPTO_ERROR;
434 memcpy(dest, src, aadlen); 484 memcpy(dest, src, aadlen);
435 } 485 }
436 if (len % cc->cipher->block_size) 486 if (len % cc->cipher->block_size)
437 return SSH_ERR_INVALID_ARGUMENT; 487 return SSH_ERR_INVALID_ARGUMENT;
438 if (EVP_Cipher(&cc->evp, dest + aadlen, (u_char *)src + aadlen, 488 if (EVP_Cipher(cc->evp, dest + aadlen, (u_char *)src + aadlen,
439 len) < 0) 489 len) < 0)
440 return SSH_ERR_LIBCRYPTO_ERROR; 490 return SSH_ERR_LIBCRYPTO_ERROR;
441 if (authlen) { 491 if (authlen) {
442 /* compute tag (on encrypt) or verify tag (on decrypt) */ 492 /* compute tag (on encrypt) or verify tag (on decrypt) */
443 if (EVP_Cipher(&cc->evp, NULL, NULL, 0) < 0) 493 if (EVP_Cipher(cc->evp, NULL, NULL, 0) < 0)
444 return cc->encrypt ? 494 return cc->encrypt ?
445 SSH_ERR_LIBCRYPTO_ERROR : SSH_ERR_MAC_INVALID; 495 SSH_ERR_LIBCRYPTO_ERROR : SSH_ERR_MAC_INVALID;
446 if (cc->encrypt && 496 if (cc->encrypt &&
447 !EVP_CIPHER_CTX_ctrl(&cc->evp, EVP_CTRL_GCM_GET_TAG, 497 !EVP_CIPHER_CTX_ctrl(cc->evp, EVP_CTRL_GCM_GET_TAG,
448 authlen, dest + aadlen + len)) 498 authlen, dest + aadlen + len))
449 return SSH_ERR_LIBCRYPTO_ERROR; 499 return SSH_ERR_LIBCRYPTO_ERROR;
450 } 500 }
@@ -466,20 +516,23 @@ cipher_get_length(struct sshcipher_ctx *cc, u_int *plenp, u_int seqnr,
466 return 0; 516 return 0;
467} 517}
468 518
469int 519void
470cipher_cleanup(struct sshcipher_ctx *cc) 520cipher_free(struct sshcipher_ctx *cc)
471{ 521{
472 if (cc == NULL || cc->cipher == NULL) 522 if (cc == NULL)
473 return 0; 523 return;
474 if ((cc->cipher->flags & CFLAG_CHACHAPOLY) != 0) 524 if ((cc->cipher->flags & CFLAG_CHACHAPOLY) != 0)
475 explicit_bzero(&cc->cp_ctx, sizeof(cc->cp_ctx)); 525 explicit_bzero(&cc->cp_ctx, sizeof(cc->cp_ctx));
476 else if ((cc->cipher->flags & CFLAG_AESCTR) != 0) 526 else if ((cc->cipher->flags & CFLAG_AESCTR) != 0)
477 explicit_bzero(&cc->ac_ctx, sizeof(cc->ac_ctx)); 527 explicit_bzero(&cc->ac_ctx, sizeof(cc->ac_ctx));
478#ifdef WITH_OPENSSL 528#ifdef WITH_OPENSSL
479 else if (EVP_CIPHER_CTX_cleanup(&cc->evp) == 0) 529 if (cc->evp != NULL) {
480 return SSH_ERR_LIBCRYPTO_ERROR; 530 EVP_CIPHER_CTX_free(cc->evp);
531 cc->evp = NULL;
532 }
481#endif 533#endif
482 return 0; 534 explicit_bzero(cc, sizeof(*cc));
535 free(cc);
483} 536}
484 537
485/* 538/*
@@ -487,8 +540,8 @@ cipher_cleanup(struct sshcipher_ctx *cc)
487 * passphrase and using the resulting 16 bytes as the key. 540 * passphrase and using the resulting 16 bytes as the key.
488 */ 541 */
489int 542int
490cipher_set_key_string(struct sshcipher_ctx *cc, const struct sshcipher *cipher, 543cipher_set_key_string(struct sshcipher_ctx **ccp,
491 const char *passphrase, int do_encrypt) 544 const struct sshcipher *cipher, const char *passphrase, int do_encrypt)
492{ 545{
493 u_char digest[16]; 546 u_char digest[16];
494 int r = SSH_ERR_INTERNAL_ERROR; 547 int r = SSH_ERR_INTERNAL_ERROR;
@@ -498,7 +551,7 @@ cipher_set_key_string(struct sshcipher_ctx *cc, const struct sshcipher *cipher,
498 digest, sizeof(digest))) != 0) 551 digest, sizeof(digest))) != 0)
499 goto out; 552 goto out;
500 553
501 r = cipher_init(cc, cipher, digest, 16, NULL, 0, do_encrypt); 554 r = cipher_init(ccp, cipher, digest, 16, NULL, 0, do_encrypt);
502 out: 555 out:
503 explicit_bzero(digest, sizeof(digest)); 556 explicit_bzero(digest, sizeof(digest));
504 return r; 557 return r;
@@ -523,7 +576,7 @@ cipher_get_keyiv_len(const struct sshcipher_ctx *cc)
523 ivlen = sizeof(cc->ac_ctx.ctr); 576 ivlen = sizeof(cc->ac_ctx.ctr);
524#ifdef WITH_OPENSSL 577#ifdef WITH_OPENSSL
525 else 578 else
526 ivlen = EVP_CIPHER_CTX_iv_length(&cc->evp); 579 ivlen = EVP_CIPHER_CTX_iv_length(cc->evp);
527#endif /* WITH_OPENSSL */ 580#endif /* WITH_OPENSSL */
528 return (ivlen); 581 return (ivlen);
529} 582}
@@ -555,7 +608,7 @@ cipher_get_keyiv(struct sshcipher_ctx *cc, u_char *iv, u_int len)
555 case SSH_CIPHER_SSH2: 608 case SSH_CIPHER_SSH2:
556 case SSH_CIPHER_DES: 609 case SSH_CIPHER_DES:
557 case SSH_CIPHER_BLOWFISH: 610 case SSH_CIPHER_BLOWFISH:
558 evplen = EVP_CIPHER_CTX_iv_length(&cc->evp); 611 evplen = EVP_CIPHER_CTX_iv_length(cc->evp);
559 if (evplen == 0) 612 if (evplen == 0)
560 return 0; 613 return 0;
561 else if (evplen < 0) 614 else if (evplen < 0)
@@ -568,16 +621,16 @@ cipher_get_keyiv(struct sshcipher_ctx *cc, u_char *iv, u_int len)
568 else 621 else
569#endif 622#endif
570 if (cipher_authlen(c)) { 623 if (cipher_authlen(c)) {
571 if (!EVP_CIPHER_CTX_ctrl(&cc->evp, EVP_CTRL_GCM_IV_GEN, 624 if (!EVP_CIPHER_CTX_ctrl(cc->evp, EVP_CTRL_GCM_IV_GEN,
572 len, iv)) 625 len, iv))
573 return SSH_ERR_LIBCRYPTO_ERROR; 626 return SSH_ERR_LIBCRYPTO_ERROR;
574 } else 627 } else
575 memcpy(iv, cc->evp.iv, len); 628 memcpy(iv, cc->evp->iv, len);
576 break; 629 break;
577#endif 630#endif
578#ifdef WITH_SSH1 631#ifdef WITH_SSH1
579 case SSH_CIPHER_3DES: 632 case SSH_CIPHER_3DES:
580 return ssh1_3des_iv(&cc->evp, 0, iv, 24); 633 return ssh1_3des_iv(cc->evp, 0, iv, 24);
581#endif 634#endif
582 default: 635 default:
583 return SSH_ERR_INVALID_ARGUMENT; 636 return SSH_ERR_INVALID_ARGUMENT;
@@ -603,21 +656,21 @@ cipher_set_keyiv(struct sshcipher_ctx *cc, const u_char *iv)
603 case SSH_CIPHER_SSH2: 656 case SSH_CIPHER_SSH2:
604 case SSH_CIPHER_DES: 657 case SSH_CIPHER_DES:
605 case SSH_CIPHER_BLOWFISH: 658 case SSH_CIPHER_BLOWFISH:
606 evplen = EVP_CIPHER_CTX_iv_length(&cc->evp); 659 evplen = EVP_CIPHER_CTX_iv_length(cc->evp);
607 if (evplen <= 0) 660 if (evplen <= 0)
608 return SSH_ERR_LIBCRYPTO_ERROR; 661 return SSH_ERR_LIBCRYPTO_ERROR;
609 if (cipher_authlen(c)) { 662 if (cipher_authlen(c)) {
610 /* XXX iv arg is const, but EVP_CIPHER_CTX_ctrl isn't */ 663 /* XXX iv arg is const, but EVP_CIPHER_CTX_ctrl isn't */
611 if (!EVP_CIPHER_CTX_ctrl(&cc->evp, 664 if (!EVP_CIPHER_CTX_ctrl(cc->evp,
612 EVP_CTRL_GCM_SET_IV_FIXED, -1, (void *)iv)) 665 EVP_CTRL_GCM_SET_IV_FIXED, -1, (void *)iv))
613 return SSH_ERR_LIBCRYPTO_ERROR; 666 return SSH_ERR_LIBCRYPTO_ERROR;
614 } else 667 } else
615 memcpy(cc->evp.iv, iv, evplen); 668 memcpy(cc->evp->iv, iv, evplen);
616 break; 669 break;
617#endif 670#endif
618#ifdef WITH_SSH1 671#ifdef WITH_SSH1
619 case SSH_CIPHER_3DES: 672 case SSH_CIPHER_3DES:
620 return ssh1_3des_iv(&cc->evp, 1, (u_char *)iv, 24); 673 return ssh1_3des_iv(cc->evp, 1, (u_char *)iv, 24);
621#endif 674#endif
622 default: 675 default:
623 return SSH_ERR_INVALID_ARGUMENT; 676 return SSH_ERR_INVALID_ARGUMENT;
@@ -626,8 +679,8 @@ cipher_set_keyiv(struct sshcipher_ctx *cc, const u_char *iv)
626} 679}
627 680
628#ifdef WITH_OPENSSL 681#ifdef WITH_OPENSSL
629#define EVP_X_STATE(evp) (evp).cipher_data 682#define EVP_X_STATE(evp) (evp)->cipher_data
630#define EVP_X_STATE_LEN(evp) (evp).cipher->ctx_size 683#define EVP_X_STATE_LEN(evp) (evp)->cipher->ctx_size
631#endif 684#endif
632 685
633int 686int
diff --git a/cipher.h b/cipher.h
index 06d4be4d7..f4bca6285 100644
--- a/cipher.h
+++ b/cipher.h
@@ -1,4 +1,4 @@
1/* $OpenBSD: cipher.h,v 1.48 2015/07/08 19:09:25 markus Exp $ */ 1/* $OpenBSD: cipher.h,v 1.49 2016/08/03 05:41:57 djm Exp $ */
2 2
3/* 3/*
4 * Author: Tatu Ylonen <ylo@cs.hut.fi> 4 * Author: Tatu Ylonen <ylo@cs.hut.fi>
@@ -63,14 +63,7 @@
63#define CIPHER_DECRYPT 0 63#define CIPHER_DECRYPT 0
64 64
65struct sshcipher; 65struct sshcipher;
66struct sshcipher_ctx { 66struct sshcipher_ctx;
67 int plaintext;
68 int encrypt;
69 EVP_CIPHER_CTX evp;
70 struct chachapoly_ctx cp_ctx; /* XXX union with evp? */
71 struct aesctr_ctx ac_ctx; /* XXX union with evp? */
72 const struct sshcipher *cipher;
73};
74 67
75u_int cipher_mask_ssh1(int); 68u_int cipher_mask_ssh1(int);
76const struct sshcipher *cipher_by_name(const char *); 69const struct sshcipher *cipher_by_name(const char *);
@@ -80,15 +73,15 @@ char *cipher_name(int);
80const char *cipher_warning_message(const struct sshcipher_ctx *); 73const char *cipher_warning_message(const struct sshcipher_ctx *);
81int ciphers_valid(const char *); 74int ciphers_valid(const char *);
82char *cipher_alg_list(char, int); 75char *cipher_alg_list(char, int);
83int cipher_init(struct sshcipher_ctx *, const struct sshcipher *, 76int cipher_init(struct sshcipher_ctx **, const struct sshcipher *,
84 const u_char *, u_int, const u_char *, u_int, int); 77 const u_char *, u_int, const u_char *, u_int, int);
85int cipher_crypt(struct sshcipher_ctx *, u_int, u_char *, const u_char *, 78int cipher_crypt(struct sshcipher_ctx *, u_int, u_char *, const u_char *,
86 u_int, u_int, u_int); 79 u_int, u_int, u_int);
87int cipher_get_length(struct sshcipher_ctx *, u_int *, u_int, 80int cipher_get_length(struct sshcipher_ctx *, u_int *, u_int,
88 const u_char *, u_int); 81 const u_char *, u_int);
89int cipher_cleanup(struct sshcipher_ctx *); 82void cipher_free(struct sshcipher_ctx *);
90int cipher_set_key_string(struct sshcipher_ctx *, const struct sshcipher *, 83int cipher_set_key_string(struct sshcipher_ctx **,
91 const char *, int); 84 const struct sshcipher *, const char *, int);
92u_int cipher_blocksize(const struct sshcipher *); 85u_int cipher_blocksize(const struct sshcipher *);
93u_int cipher_keylen(const struct sshcipher *); 86u_int cipher_keylen(const struct sshcipher *);
94u_int cipher_seclen(const struct sshcipher *); 87u_int cipher_seclen(const struct sshcipher *);
@@ -96,10 +89,14 @@ u_int cipher_authlen(const struct sshcipher *);
96u_int cipher_ivlen(const struct sshcipher *); 89u_int cipher_ivlen(const struct sshcipher *);
97u_int cipher_is_cbc(const struct sshcipher *); 90u_int cipher_is_cbc(const struct sshcipher *);
98 91
92u_int cipher_ctx_is_plaintext(struct sshcipher_ctx *);
93u_int cipher_ctx_get_number(struct sshcipher_ctx *);
94
99u_int cipher_get_number(const struct sshcipher *); 95u_int cipher_get_number(const struct sshcipher *);
100int cipher_get_keyiv(struct sshcipher_ctx *, u_char *, u_int); 96int cipher_get_keyiv(struct sshcipher_ctx *, u_char *, u_int);
101int cipher_set_keyiv(struct sshcipher_ctx *, const u_char *); 97int cipher_set_keyiv(struct sshcipher_ctx *, const u_char *);
102int cipher_get_keyiv_len(const struct sshcipher_ctx *); 98int cipher_get_keyiv_len(const struct sshcipher_ctx *);
103int cipher_get_keycontext(const struct sshcipher_ctx *, u_char *); 99int cipher_get_keycontext(const struct sshcipher_ctx *, u_char *);
104void cipher_set_keycontext(struct sshcipher_ctx *, const u_char *); 100void cipher_set_keycontext(struct sshcipher_ctx *, const u_char *);
101
105#endif /* CIPHER_H */ 102#endif /* CIPHER_H */
diff --git a/packet.c b/packet.c
index d6dad2da6..d4221d12a 100644
--- a/packet.c
+++ b/packet.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: packet.c,v 1.234 2016/07/18 11:35:33 markus Exp $ */ 1/* $OpenBSD: packet.c,v 1.235 2016/08/03 05:41:57 djm Exp $ */
2/* 2/*
3 * Author: Tatu Ylonen <ylo@cs.hut.fi> 3 * Author: Tatu Ylonen <ylo@cs.hut.fi>
4 * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland 4 * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland
@@ -122,10 +122,10 @@ struct session_state {
122 u_int remote_protocol_flags; 122 u_int remote_protocol_flags;
123 123
124 /* Encryption context for receiving data. Only used for decryption. */ 124 /* Encryption context for receiving data. Only used for decryption. */
125 struct sshcipher_ctx receive_context; 125 struct sshcipher_ctx *receive_context;
126 126
127 /* Encryption context for sending data. Only used for encryption. */ 127 /* Encryption context for sending data. Only used for encryption. */
128 struct sshcipher_ctx send_context; 128 struct sshcipher_ctx *send_context;
129 129
130 /* Buffer for raw input data from the socket. */ 130 /* Buffer for raw input data from the socket. */
131 struct sshbuf *input; 131 struct sshbuf *input;
@@ -529,7 +529,6 @@ void
529ssh_packet_close(struct ssh *ssh) 529ssh_packet_close(struct ssh *ssh)
530{ 530{
531 struct session_state *state = ssh->state; 531 struct session_state *state = ssh->state;
532 int r;
533 u_int mode; 532 u_int mode;
534 533
535 if (!state->initialized) 534 if (!state->initialized)
@@ -573,10 +572,9 @@ ssh_packet_close(struct ssh *ssh)
573 inflateEnd(stream); 572 inflateEnd(stream);
574 } 573 }
575 } 574 }
576 if ((r = cipher_cleanup(&state->send_context)) != 0) 575 cipher_free(state->send_context);
577 error("%s: cipher_cleanup failed: %s", __func__, ssh_err(r)); 576 cipher_free(state->receive_context);
578 if ((r = cipher_cleanup(&state->receive_context)) != 0) 577 state->send_context = state->receive_context = NULL;
579 error("%s: cipher_cleanup failed: %s", __func__, ssh_err(r));
580 free(ssh->remote_ipaddr); 578 free(ssh->remote_ipaddr);
581 ssh->remote_ipaddr = NULL; 579 ssh->remote_ipaddr = NULL;
582 free(ssh->state); 580 free(ssh->state);
@@ -870,8 +868,8 @@ ssh_packet_set_encryption_key(struct ssh *ssh, const u_char *key, u_int keylen,
870 NULL, 0, CIPHER_DECRYPT) != 0)) 868 NULL, 0, CIPHER_DECRYPT) != 0))
871 fatal("%s: cipher_init failed: %s", __func__, ssh_err(r)); 869 fatal("%s: cipher_init failed: %s", __func__, ssh_err(r));
872 if (!state->cipher_warning_done && 870 if (!state->cipher_warning_done &&
873 ((wmsg = cipher_warning_message(&state->send_context)) != NULL || 871 ((wmsg = cipher_warning_message(state->send_context)) != NULL ||
874 (wmsg = cipher_warning_message(&state->send_context)) != NULL)) { 872 (wmsg = cipher_warning_message(state->send_context)) != NULL)) {
875 error("Warning: %s", wmsg); 873 error("Warning: %s", wmsg);
876 state->cipher_warning_done = 1; 874 state->cipher_warning_done = 1;
877 } 875 }
@@ -917,7 +915,7 @@ ssh_packet_send1(struct ssh *ssh)
917 915
918 /* Insert padding. Initialized to zero in packet_start1() */ 916 /* Insert padding. Initialized to zero in packet_start1() */
919 padding = 8 - len % 8; 917 padding = 8 - len % 8;
920 if (!state->send_context.plaintext) { 918 if (!cipher_ctx_is_plaintext(state->send_context)) {
921 cp = sshbuf_mutable_ptr(state->outgoing_packet); 919 cp = sshbuf_mutable_ptr(state->outgoing_packet);
922 if (cp == NULL) { 920 if (cp == NULL) {
923 r = SSH_ERR_INTERNAL_ERROR; 921 r = SSH_ERR_INTERNAL_ERROR;
@@ -947,7 +945,7 @@ ssh_packet_send1(struct ssh *ssh)
947 if ((r = sshbuf_reserve(state->output, 945 if ((r = sshbuf_reserve(state->output,
948 sshbuf_len(state->outgoing_packet), &cp)) != 0) 946 sshbuf_len(state->outgoing_packet), &cp)) != 0)
949 goto out; 947 goto out;
950 if ((r = cipher_crypt(&state->send_context, 0, cp, 948 if ((r = cipher_crypt(state->send_context, 0, cp,
951 sshbuf_ptr(state->outgoing_packet), 949 sshbuf_ptr(state->outgoing_packet),
952 sshbuf_len(state->outgoing_packet), 0, 0)) != 0) 950 sshbuf_len(state->outgoing_packet), 0, 0)) != 0)
953 goto out; 951 goto out;
@@ -978,7 +976,7 @@ ssh_set_newkeys(struct ssh *ssh, int mode)
978 struct sshenc *enc; 976 struct sshenc *enc;
979 struct sshmac *mac; 977 struct sshmac *mac;
980 struct sshcomp *comp; 978 struct sshcomp *comp;
981 struct sshcipher_ctx *cc; 979 struct sshcipher_ctx **ccp;
982 u_int64_t *max_blocks; 980 u_int64_t *max_blocks;
983 const char *wmsg; 981 const char *wmsg;
984 int r, crypt_type; 982 int r, crypt_type;
@@ -986,12 +984,12 @@ ssh_set_newkeys(struct ssh *ssh, int mode)
986 debug2("set_newkeys: mode %d", mode); 984 debug2("set_newkeys: mode %d", mode);
987 985
988 if (mode == MODE_OUT) { 986 if (mode == MODE_OUT) {
989 cc = &state->send_context; 987 ccp = &state->send_context;
990 crypt_type = CIPHER_ENCRYPT; 988 crypt_type = CIPHER_ENCRYPT;
991 state->p_send.packets = state->p_send.blocks = 0; 989 state->p_send.packets = state->p_send.blocks = 0;
992 max_blocks = &state->max_blocks_out; 990 max_blocks = &state->max_blocks_out;
993 } else { 991 } else {
994 cc = &state->receive_context; 992 ccp = &state->receive_context;
995 crypt_type = CIPHER_DECRYPT; 993 crypt_type = CIPHER_DECRYPT;
996 state->p_read.packets = state->p_read.blocks = 0; 994 state->p_read.packets = state->p_read.blocks = 0;
997 max_blocks = &state->max_blocks_in; 995 max_blocks = &state->max_blocks_in;
@@ -1003,8 +1001,8 @@ ssh_set_newkeys(struct ssh *ssh, int mode)
1003 (unsigned long long)state->p_read.blocks, 1001 (unsigned long long)state->p_read.blocks,
1004 (unsigned long long)state->p_send.bytes, 1002 (unsigned long long)state->p_send.bytes,
1005 (unsigned long long)state->p_send.blocks); 1003 (unsigned long long)state->p_send.blocks);
1006 if ((r = cipher_cleanup(cc)) != 0) 1004 cipher_free(*ccp);
1007 return r; 1005 *ccp = NULL;
1008 enc = &state->newkeys[mode]->enc; 1006 enc = &state->newkeys[mode]->enc;
1009 mac = &state->newkeys[mode]->mac; 1007 mac = &state->newkeys[mode]->mac;
1010 comp = &state->newkeys[mode]->comp; 1008 comp = &state->newkeys[mode]->comp;
@@ -1033,11 +1031,11 @@ ssh_set_newkeys(struct ssh *ssh, int mode)
1033 } 1031 }
1034 mac->enabled = 1; 1032 mac->enabled = 1;
1035 DBG(debug("cipher_init_context: %d", mode)); 1033 DBG(debug("cipher_init_context: %d", mode));
1036 if ((r = cipher_init(cc, enc->cipher, enc->key, enc->key_len, 1034 if ((r = cipher_init(ccp, enc->cipher, enc->key, enc->key_len,
1037 enc->iv, enc->iv_len, crypt_type)) != 0) 1035 enc->iv, enc->iv_len, crypt_type)) != 0)
1038 return r; 1036 return r;
1039 if (!state->cipher_warning_done && 1037 if (!state->cipher_warning_done &&
1040 (wmsg = cipher_warning_message(cc)) != NULL) { 1038 (wmsg = cipher_warning_message(*ccp)) != NULL) {
1041 error("Warning: %s", wmsg); 1039 error("Warning: %s", wmsg);
1042 state->cipher_warning_done = 1; 1040 state->cipher_warning_done = 1;
1043 } 1041 }
@@ -1259,7 +1257,7 @@ ssh_packet_send2_wrapped(struct ssh *ssh)
1259 } 1257 }
1260 if ((r = sshbuf_reserve(state->outgoing_packet, padlen, &cp)) != 0) 1258 if ((r = sshbuf_reserve(state->outgoing_packet, padlen, &cp)) != 0)
1261 goto out; 1259 goto out;
1262 if (enc && !state->send_context.plaintext) { 1260 if (enc && !cipher_ctx_is_plaintext(state->send_context)) {
1263 /* random padding */ 1261 /* random padding */
1264 arc4random_buf(cp, padlen); 1262 arc4random_buf(cp, padlen);
1265 } else { 1263 } else {
@@ -1291,7 +1289,7 @@ ssh_packet_send2_wrapped(struct ssh *ssh)
1291 if ((r = sshbuf_reserve(state->output, 1289 if ((r = sshbuf_reserve(state->output,
1292 sshbuf_len(state->outgoing_packet) + authlen, &cp)) != 0) 1290 sshbuf_len(state->outgoing_packet) + authlen, &cp)) != 0)
1293 goto out; 1291 goto out;
1294 if ((r = cipher_crypt(&state->send_context, state->p_send.seqnr, cp, 1292 if ((r = cipher_crypt(state->send_context, state->p_send.seqnr, cp,
1295 sshbuf_ptr(state->outgoing_packet), 1293 sshbuf_ptr(state->outgoing_packet),
1296 len - aadlen, aadlen, authlen)) != 0) 1294 len - aadlen, aadlen, authlen)) != 0)
1297 goto out; 1295 goto out;
@@ -1606,7 +1604,7 @@ ssh_packet_read_poll1(struct ssh *ssh, u_char *typep)
1606 * (C)1998 CORE-SDI, Buenos Aires Argentina 1604 * (C)1998 CORE-SDI, Buenos Aires Argentina
1607 * Ariel Futoransky(futo@core-sdi.com) 1605 * Ariel Futoransky(futo@core-sdi.com)
1608 */ 1606 */
1609 if (!state->receive_context.plaintext) { 1607 if (!cipher_ctx_is_plaintext(state->receive_context)) {
1610 emsg = NULL; 1608 emsg = NULL;
1611 switch (detect_attack(&state->deattack, 1609 switch (detect_attack(&state->deattack,
1612 sshbuf_ptr(state->input), padded_len)) { 1610 sshbuf_ptr(state->input), padded_len)) {
@@ -1635,7 +1633,7 @@ ssh_packet_read_poll1(struct ssh *ssh, u_char *typep)
1635 sshbuf_reset(state->incoming_packet); 1633 sshbuf_reset(state->incoming_packet);
1636 if ((r = sshbuf_reserve(state->incoming_packet, padded_len, &p)) != 0) 1634 if ((r = sshbuf_reserve(state->incoming_packet, padded_len, &p)) != 0)
1637 goto out; 1635 goto out;
1638 if ((r = cipher_crypt(&state->receive_context, 0, p, 1636 if ((r = cipher_crypt(state->receive_context, 0, p,
1639 sshbuf_ptr(state->input), padded_len, 0, 0)) != 0) 1637 sshbuf_ptr(state->input), padded_len, 0, 0)) != 0)
1640 goto out; 1638 goto out;
1641 1639
@@ -1733,7 +1731,7 @@ ssh_packet_read_poll2(struct ssh *ssh, u_char *typep, u_int32_t *seqnr_p)
1733 aadlen = (mac && mac->enabled && mac->etm) || authlen ? 4 : 0; 1731 aadlen = (mac && mac->enabled && mac->etm) || authlen ? 4 : 0;
1734 1732
1735 if (aadlen && state->packlen == 0) { 1733 if (aadlen && state->packlen == 0) {
1736 if (cipher_get_length(&state->receive_context, 1734 if (cipher_get_length(state->receive_context,
1737 &state->packlen, state->p_read.seqnr, 1735 &state->packlen, state->p_read.seqnr,
1738 sshbuf_ptr(state->input), sshbuf_len(state->input)) != 0) 1736 sshbuf_ptr(state->input), sshbuf_len(state->input)) != 0)
1739 return 0; 1737 return 0;
@@ -1759,7 +1757,7 @@ ssh_packet_read_poll2(struct ssh *ssh, u_char *typep, u_int32_t *seqnr_p)
1759 if ((r = sshbuf_reserve(state->incoming_packet, block_size, 1757 if ((r = sshbuf_reserve(state->incoming_packet, block_size,
1760 &cp)) != 0) 1758 &cp)) != 0)
1761 goto out; 1759 goto out;
1762 if ((r = cipher_crypt(&state->receive_context, 1760 if ((r = cipher_crypt(state->receive_context,
1763 state->p_send.seqnr, cp, sshbuf_ptr(state->input), 1761 state->p_send.seqnr, cp, sshbuf_ptr(state->input),
1764 block_size, 0, 0)) != 0) 1762 block_size, 0, 0)) != 0)
1765 goto out; 1763 goto out;
@@ -1827,7 +1825,7 @@ ssh_packet_read_poll2(struct ssh *ssh, u_char *typep, u_int32_t *seqnr_p)
1827 if ((r = sshbuf_reserve(state->incoming_packet, aadlen + need, 1825 if ((r = sshbuf_reserve(state->incoming_packet, aadlen + need,
1828 &cp)) != 0) 1826 &cp)) != 0)
1829 goto out; 1827 goto out;
1830 if ((r = cipher_crypt(&state->receive_context, state->p_read.seqnr, cp, 1828 if ((r = cipher_crypt(state->receive_context, state->p_read.seqnr, cp,
1831 sshbuf_ptr(state->input), need, aadlen, authlen)) != 0) 1829 sshbuf_ptr(state->input), need, aadlen, authlen)) != 0)
1832 goto out; 1830 goto out;
1833 if ((r = sshbuf_consume(state->input, aadlen + need + authlen)) != 0) 1831 if ((r = sshbuf_consume(state->input, aadlen + need + authlen)) != 0)
@@ -2509,8 +2507,8 @@ newkeys_to_blob(struct sshbuf *m, struct ssh *ssh, int mode)
2509 enc = &newkey->enc; 2507 enc = &newkey->enc;
2510 mac = &newkey->mac; 2508 mac = &newkey->mac;
2511 comp = &newkey->comp; 2509 comp = &newkey->comp;
2512 cc = (mode == MODE_OUT) ? &ssh->state->send_context : 2510 cc = (mode == MODE_OUT) ? ssh->state->send_context :
2513 &ssh->state->receive_context; 2511 ssh->state->receive_context;
2514 if ((r = cipher_get_keyiv(cc, enc->iv, enc->iv_len)) != 0) 2512 if ((r = cipher_get_keyiv(cc, enc->iv, enc->iv_len)) != 0)
2515 return r; 2513 return r;
2516 if ((b = sshbuf_new()) == NULL) 2514 if ((b = sshbuf_new()) == NULL)
@@ -2549,18 +2547,18 @@ ssh_packet_get_state(struct ssh *ssh, struct sshbuf *m)
2549 int r, ssh1cipher; 2547 int r, ssh1cipher;
2550 2548
2551 if (!compat20) { 2549 if (!compat20) {
2552 ssh1cipher = cipher_get_number(state->receive_context.cipher); 2550 ssh1cipher = cipher_ctx_get_number(state->receive_context);
2553 slen = cipher_get_keyiv_len(&state->send_context); 2551 slen = cipher_get_keyiv_len(state->send_context);
2554 rlen = cipher_get_keyiv_len(&state->receive_context); 2552 rlen = cipher_get_keyiv_len(state->receive_context);
2555 if ((r = sshbuf_put_u32(m, state->remote_protocol_flags)) != 0 || 2553 if ((r = sshbuf_put_u32(m, state->remote_protocol_flags)) != 0 ||
2556 (r = sshbuf_put_u32(m, ssh1cipher)) != 0 || 2554 (r = sshbuf_put_u32(m, ssh1cipher)) != 0 ||
2557 (r = sshbuf_put_string(m, state->ssh1_key, state->ssh1_keylen)) != 0 || 2555 (r = sshbuf_put_string(m, state->ssh1_key, state->ssh1_keylen)) != 0 ||
2558 (r = sshbuf_put_u32(m, slen)) != 0 || 2556 (r = sshbuf_put_u32(m, slen)) != 0 ||
2559 (r = sshbuf_reserve(m, slen, &p)) != 0 || 2557 (r = sshbuf_reserve(m, slen, &p)) != 0 ||
2560 (r = cipher_get_keyiv(&state->send_context, p, slen)) != 0 || 2558 (r = cipher_get_keyiv(state->send_context, p, slen)) != 0 ||
2561 (r = sshbuf_put_u32(m, rlen)) != 0 || 2559 (r = sshbuf_put_u32(m, rlen)) != 0 ||
2562 (r = sshbuf_reserve(m, rlen, &p)) != 0 || 2560 (r = sshbuf_reserve(m, rlen, &p)) != 0 ||
2563 (r = cipher_get_keyiv(&state->receive_context, p, rlen)) != 0) 2561 (r = cipher_get_keyiv(state->receive_context, p, rlen)) != 0)
2564 return r; 2562 return r;
2565 } else { 2563 } else {
2566 if ((r = kex_to_blob(m, ssh->kex)) != 0 || 2564 if ((r = kex_to_blob(m, ssh->kex)) != 0 ||
@@ -2579,17 +2577,17 @@ ssh_packet_get_state(struct ssh *ssh, struct sshbuf *m)
2579 return r; 2577 return r;
2580 } 2578 }
2581 2579
2582 slen = cipher_get_keycontext(&state->send_context, NULL); 2580 slen = cipher_get_keycontext(state->send_context, NULL);
2583 rlen = cipher_get_keycontext(&state->receive_context, NULL); 2581 rlen = cipher_get_keycontext(state->receive_context, NULL);
2584 if ((r = sshbuf_put_u32(m, slen)) != 0 || 2582 if ((r = sshbuf_put_u32(m, slen)) != 0 ||
2585 (r = sshbuf_reserve(m, slen, &p)) != 0) 2583 (r = sshbuf_reserve(m, slen, &p)) != 0)
2586 return r; 2584 return r;
2587 if (cipher_get_keycontext(&state->send_context, p) != (int)slen) 2585 if (cipher_get_keycontext(state->send_context, p) != (int)slen)
2588 return SSH_ERR_INTERNAL_ERROR; 2586 return SSH_ERR_INTERNAL_ERROR;
2589 if ((r = sshbuf_put_u32(m, rlen)) != 0 || 2587 if ((r = sshbuf_put_u32(m, rlen)) != 0 ||
2590 (r = sshbuf_reserve(m, rlen, &p)) != 0) 2588 (r = sshbuf_reserve(m, rlen, &p)) != 0)
2591 return r; 2589 return r;
2592 if (cipher_get_keycontext(&state->receive_context, p) != (int)rlen) 2590 if (cipher_get_keycontext(state->receive_context, p) != (int)rlen)
2593 return SSH_ERR_INTERNAL_ERROR; 2591 return SSH_ERR_INTERNAL_ERROR;
2594 2592
2595 if ((r = ssh_packet_get_compress_state(m, ssh)) != 0 || 2593 if ((r = ssh_packet_get_compress_state(m, ssh)) != 0 ||
@@ -2735,11 +2733,11 @@ ssh_packet_set_state(struct ssh *ssh, struct sshbuf *m)
2735 return SSH_ERR_KEY_UNKNOWN_CIPHER; 2733 return SSH_ERR_KEY_UNKNOWN_CIPHER;
2736 ssh_packet_set_encryption_key(ssh, ssh1key, ssh1keylen, 2734 ssh_packet_set_encryption_key(ssh, ssh1key, ssh1keylen,
2737 (int)ssh1cipher); 2735 (int)ssh1cipher);
2738 if (cipher_get_keyiv_len(&state->send_context) != (int)slen || 2736 if (cipher_get_keyiv_len(state->send_context) != (int)slen ||
2739 cipher_get_keyiv_len(&state->receive_context) != (int)rlen) 2737 cipher_get_keyiv_len(state->receive_context) != (int)rlen)
2740 return SSH_ERR_INVALID_FORMAT; 2738 return SSH_ERR_INVALID_FORMAT;
2741 if ((r = cipher_set_keyiv(&state->send_context, ivout)) != 0 || 2739 if ((r = cipher_set_keyiv(state->send_context, ivout)) != 0 ||
2742 (r = cipher_set_keyiv(&state->receive_context, ivin)) != 0) 2740 (r = cipher_set_keyiv(state->receive_context, ivin)) != 0)
2743 return r; 2741 return r;
2744 } else { 2742 } else {
2745 if ((r = kex_from_blob(m, &ssh->kex)) != 0 || 2743 if ((r = kex_from_blob(m, &ssh->kex)) != 0 ||
@@ -2769,11 +2767,11 @@ ssh_packet_set_state(struct ssh *ssh, struct sshbuf *m)
2769 if ((r = sshbuf_get_string_direct(m, &keyout, &slen)) != 0 || 2767 if ((r = sshbuf_get_string_direct(m, &keyout, &slen)) != 0 ||
2770 (r = sshbuf_get_string_direct(m, &keyin, &rlen)) != 0) 2768 (r = sshbuf_get_string_direct(m, &keyin, &rlen)) != 0)
2771 return r; 2769 return r;
2772 if (cipher_get_keycontext(&state->send_context, NULL) != (int)slen || 2770 if (cipher_get_keycontext(state->send_context, NULL) != (int)slen ||
2773 cipher_get_keycontext(&state->receive_context, NULL) != (int)rlen) 2771 cipher_get_keycontext(state->receive_context, NULL) != (int)rlen)
2774 return SSH_ERR_INVALID_FORMAT; 2772 return SSH_ERR_INVALID_FORMAT;
2775 cipher_set_keycontext(&state->send_context, keyout); 2773 cipher_set_keycontext(state->send_context, keyout);
2776 cipher_set_keycontext(&state->receive_context, keyin); 2774 cipher_set_keycontext(state->receive_context, keyin);
2777 2775
2778 if ((r = ssh_packet_set_compress_state(ssh, m)) != 0 || 2776 if ((r = ssh_packet_set_compress_state(ssh, m)) != 0 ||
2779 (r = ssh_packet_set_postauth(ssh)) != 0) 2777 (r = ssh_packet_set_postauth(ssh)) != 0)
diff --git a/sshkey.c b/sshkey.c
index c9f04cd67..166ac714d 100644
--- a/sshkey.c
+++ b/sshkey.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: sshkey.c,v 1.35 2016/06/19 07:48:02 djm Exp $ */ 1/* $OpenBSD: sshkey.c,v 1.36 2016/08/03 05:41:57 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.
@@ -3029,13 +3029,11 @@ sshkey_private_to_blob2(const struct sshkey *prv, struct sshbuf *blob,
3029 size_t i, pubkeylen, keylen, ivlen, blocksize, authlen; 3029 size_t i, pubkeylen, keylen, ivlen, blocksize, authlen;
3030 u_int check; 3030 u_int check;
3031 int r = SSH_ERR_INTERNAL_ERROR; 3031 int r = SSH_ERR_INTERNAL_ERROR;
3032 struct sshcipher_ctx ciphercontext; 3032 struct sshcipher_ctx *ciphercontext = NULL;
3033 const struct sshcipher *cipher; 3033 const struct sshcipher *cipher;
3034 const char *kdfname = KDFNAME; 3034 const char *kdfname = KDFNAME;
3035 struct sshbuf *encoded = NULL, *encrypted = NULL, *kdf = NULL; 3035 struct sshbuf *encoded = NULL, *encrypted = NULL, *kdf = NULL;
3036 3036
3037 memset(&ciphercontext, 0, sizeof(ciphercontext));
3038
3039 if (rounds <= 0) 3037 if (rounds <= 0)
3040 rounds = DEFAULT_ROUNDS; 3038 rounds = DEFAULT_ROUNDS;
3041 if (passphrase == NULL || !strlen(passphrase)) { 3039 if (passphrase == NULL || !strlen(passphrase)) {
@@ -3122,7 +3120,7 @@ sshkey_private_to_blob2(const struct sshkey *prv, struct sshbuf *blob,
3122 if ((r = sshbuf_reserve(encoded, 3120 if ((r = sshbuf_reserve(encoded,
3123 sshbuf_len(encrypted) + authlen, &cp)) != 0) 3121 sshbuf_len(encrypted) + authlen, &cp)) != 0)
3124 goto out; 3122 goto out;
3125 if ((r = cipher_crypt(&ciphercontext, 0, cp, 3123 if ((r = cipher_crypt(ciphercontext, 0, cp,
3126 sshbuf_ptr(encrypted), sshbuf_len(encrypted), 0, authlen)) != 0) 3124 sshbuf_ptr(encrypted), sshbuf_len(encrypted), 0, authlen)) != 0)
3127 goto out; 3125 goto out;
3128 3126
@@ -3154,7 +3152,7 @@ sshkey_private_to_blob2(const struct sshkey *prv, struct sshbuf *blob,
3154 sshbuf_free(kdf); 3152 sshbuf_free(kdf);
3155 sshbuf_free(encoded); 3153 sshbuf_free(encoded);
3156 sshbuf_free(encrypted); 3154 sshbuf_free(encrypted);
3157 cipher_cleanup(&ciphercontext); 3155 cipher_free(ciphercontext);
3158 explicit_bzero(salt, sizeof(salt)); 3156 explicit_bzero(salt, sizeof(salt));
3159 if (key != NULL) { 3157 if (key != NULL) {
3160 explicit_bzero(key, keylen + ivlen); 3158 explicit_bzero(key, keylen + ivlen);
@@ -3183,12 +3181,11 @@ sshkey_parse_private2(struct sshbuf *blob, int type, const char *passphrase,
3183 size_t i, keylen = 0, ivlen = 0, authlen = 0, slen = 0; 3181 size_t i, keylen = 0, ivlen = 0, authlen = 0, slen = 0;
3184 struct sshbuf *encoded = NULL, *decoded = NULL; 3182 struct sshbuf *encoded = NULL, *decoded = NULL;
3185 struct sshbuf *kdf = NULL, *decrypted = NULL; 3183 struct sshbuf *kdf = NULL, *decrypted = NULL;
3186 struct sshcipher_ctx ciphercontext; 3184 struct sshcipher_ctx *ciphercontext = NULL;
3187 struct sshkey *k = NULL; 3185 struct sshkey *k = NULL;
3188 u_char *key = NULL, *salt = NULL, *dp, pad, last; 3186 u_char *key = NULL, *salt = NULL, *dp, pad, last;
3189 u_int blocksize, rounds, nkeys, encrypted_len, check1, check2; 3187 u_int blocksize, rounds, nkeys, encrypted_len, check1, check2;
3190 3188
3191 memset(&ciphercontext, 0, sizeof(ciphercontext));
3192 if (keyp != NULL) 3189 if (keyp != NULL)
3193 *keyp = NULL; 3190 *keyp = NULL;
3194 if (commentp != NULL) 3191 if (commentp != NULL)
@@ -3317,7 +3314,7 @@ sshkey_parse_private2(struct sshbuf *blob, int type, const char *passphrase,
3317 (r = cipher_init(&ciphercontext, cipher, key, keylen, 3314 (r = cipher_init(&ciphercontext, cipher, key, keylen,
3318 key + keylen, ivlen, 0)) != 0) 3315 key + keylen, ivlen, 0)) != 0)
3319 goto out; 3316 goto out;
3320 if ((r = cipher_crypt(&ciphercontext, 0, dp, sshbuf_ptr(decoded), 3317 if ((r = cipher_crypt(ciphercontext, 0, dp, sshbuf_ptr(decoded),
3321 encrypted_len, 0, authlen)) != 0) { 3318 encrypted_len, 0, authlen)) != 0) {
3322 /* an integrity error here indicates an incorrect passphrase */ 3319 /* an integrity error here indicates an incorrect passphrase */
3323 if (r == SSH_ERR_MAC_INVALID) 3320 if (r == SSH_ERR_MAC_INVALID)
@@ -3371,7 +3368,7 @@ sshkey_parse_private2(struct sshbuf *blob, int type, const char *passphrase,
3371 } 3368 }
3372 out: 3369 out:
3373 pad = 0; 3370 pad = 0;
3374 cipher_cleanup(&ciphercontext); 3371 cipher_free(ciphercontext);
3375 free(ciphername); 3372 free(ciphername);
3376 free(kdfname); 3373 free(kdfname);
3377 free(comment); 3374 free(comment);
@@ -3405,7 +3402,7 @@ sshkey_private_rsa1_to_blob(struct sshkey *key, struct sshbuf *blob,
3405 struct sshbuf *buffer = NULL, *encrypted = NULL; 3402 struct sshbuf *buffer = NULL, *encrypted = NULL;
3406 u_char buf[8]; 3403 u_char buf[8];
3407 int r, cipher_num; 3404 int r, cipher_num;
3408 struct sshcipher_ctx ciphercontext; 3405 struct sshcipher_ctx *ciphercontext = NULL;
3409 const struct sshcipher *cipher; 3406 const struct sshcipher *cipher;
3410 u_char *cp; 3407 u_char *cp;
3411 3408
@@ -3475,16 +3472,14 @@ sshkey_private_rsa1_to_blob(struct sshkey *key, struct sshbuf *blob,
3475 if ((r = cipher_set_key_string(&ciphercontext, cipher, passphrase, 3472 if ((r = cipher_set_key_string(&ciphercontext, cipher, passphrase,
3476 CIPHER_ENCRYPT)) != 0) 3473 CIPHER_ENCRYPT)) != 0)
3477 goto out; 3474 goto out;
3478 if ((r = cipher_crypt(&ciphercontext, 0, cp, 3475 if ((r = cipher_crypt(ciphercontext, 0, cp,
3479 sshbuf_ptr(buffer), sshbuf_len(buffer), 0, 0)) != 0) 3476 sshbuf_ptr(buffer), sshbuf_len(buffer), 0, 0)) != 0)
3480 goto out; 3477 goto out;
3481 if ((r = cipher_cleanup(&ciphercontext)) != 0)
3482 goto out;
3483 3478
3484 r = sshbuf_putb(blob, encrypted); 3479 r = sshbuf_putb(blob, encrypted);
3485 3480
3486 out: 3481 out:
3487 explicit_bzero(&ciphercontext, sizeof(ciphercontext)); 3482 cipher_free(ciphercontext);
3488 explicit_bzero(buf, sizeof(buf)); 3483 explicit_bzero(buf, sizeof(buf));
3489 sshbuf_free(buffer); 3484 sshbuf_free(buffer);
3490 sshbuf_free(encrypted); 3485 sshbuf_free(encrypted);
@@ -3654,7 +3649,7 @@ sshkey_parse_private_rsa1(struct sshbuf *blob, const char *passphrase,
3654 struct sshbuf *decrypted = NULL, *copy = NULL; 3649 struct sshbuf *decrypted = NULL, *copy = NULL;
3655 u_char *cp; 3650 u_char *cp;
3656 char *comment = NULL; 3651 char *comment = NULL;
3657 struct sshcipher_ctx ciphercontext; 3652 struct sshcipher_ctx *ciphercontext = NULL;
3658 const struct sshcipher *cipher; 3653 const struct sshcipher *cipher;
3659 struct sshkey *prv = NULL; 3654 struct sshkey *prv = NULL;
3660 3655
@@ -3712,12 +3707,8 @@ sshkey_parse_private_rsa1(struct sshbuf *blob, const char *passphrase,
3712 if ((r = cipher_set_key_string(&ciphercontext, cipher, passphrase, 3707 if ((r = cipher_set_key_string(&ciphercontext, cipher, passphrase,
3713 CIPHER_DECRYPT)) != 0) 3708 CIPHER_DECRYPT)) != 0)
3714 goto out; 3709 goto out;
3715 if ((r = cipher_crypt(&ciphercontext, 0, cp, 3710 if ((r = cipher_crypt(ciphercontext, 0, cp,
3716 sshbuf_ptr(copy), sshbuf_len(copy), 0, 0)) != 0) { 3711 sshbuf_ptr(copy), sshbuf_len(copy), 0, 0)) != 0)
3717 cipher_cleanup(&ciphercontext);
3718 goto out;
3719 }
3720 if ((r = cipher_cleanup(&ciphercontext)) != 0)
3721 goto out; 3712 goto out;
3722 3713
3723 if ((r = sshbuf_get_u16(decrypted, &check1)) != 0 || 3714 if ((r = sshbuf_get_u16(decrypted, &check1)) != 0 ||
@@ -3754,7 +3745,7 @@ sshkey_parse_private_rsa1(struct sshbuf *blob, const char *passphrase,
3754 comment = NULL; 3745 comment = NULL;
3755 } 3746 }
3756 out: 3747 out:
3757 explicit_bzero(&ciphercontext, sizeof(ciphercontext)); 3748 cipher_free(ciphercontext);
3758 free(comment); 3749 free(comment);
3759 sshkey_free(prv); 3750 sshkey_free(prv);
3760 sshbuf_free(copy); 3751 sshbuf_free(copy);