summaryrefslogtreecommitdiff
path: root/kex.c
diff options
context:
space:
mode:
Diffstat (limited to 'kex.c')
-rw-r--r--kex.c54
1 files changed, 40 insertions, 14 deletions
diff --git a/kex.c b/kex.c
index 47983f8d9..5f9b1dc40 100644
--- a/kex.c
+++ b/kex.c
@@ -1,3 +1,4 @@
1/* $OpenBSD: kex.c,v 1.77 2007/01/21 01:41:54 stevesk Exp $ */
1/* 2/*
2 * Copyright (c) 2000, 2001 Markus Friedl. All rights reserved. 3 * Copyright (c) 2000, 2001 Markus Friedl. All rights reserved.
3 * 4 *
@@ -23,19 +24,25 @@
23 */ 24 */
24 25
25#include "includes.h" 26#include "includes.h"
26RCSID("$OpenBSD: kex.c,v 1.65 2005/11/04 05:15:59 djm Exp $"); 27
28#include <sys/param.h>
29
30#include <signal.h>
31#include <stdarg.h>
32#include <stdio.h>
33#include <stdlib.h>
34#include <string.h>
27 35
28#include <openssl/crypto.h> 36#include <openssl/crypto.h>
29 37
30#include "ssh2.h"
31#include "xmalloc.h" 38#include "xmalloc.h"
39#include "ssh2.h"
32#include "buffer.h" 40#include "buffer.h"
33#include "bufaux.h"
34#include "packet.h" 41#include "packet.h"
35#include "compat.h" 42#include "compat.h"
36#include "cipher.h" 43#include "cipher.h"
37#include "kex.h"
38#include "key.h" 44#include "key.h"
45#include "kex.h"
39#include "log.h" 46#include "log.h"
40#include "mac.h" 47#include "mac.h"
41#include "match.h" 48#include "match.h"
@@ -48,6 +55,14 @@ RCSID("$OpenBSD: kex.c,v 1.65 2005/11/04 05:15:59 djm Exp $");
48 55
49#define KEX_COOKIE_LEN 16 56#define KEX_COOKIE_LEN 16
50 57
58#if OPENSSL_VERSION_NUMBER >= 0x00907000L
59# if defined(HAVE_EVP_SHA256)
60# define evp_ssh_sha256 EVP_sha256
61# else
62extern const EVP_MD *evp_ssh_sha256(void);
63# endif
64#endif
65
51/* prototype */ 66/* prototype */
52static void kex_kexinit_finish(Kex *); 67static void kex_kexinit_finish(Kex *);
53static void kex_choose_conf(Kex *); 68static void kex_choose_conf(Kex *);
@@ -79,7 +94,7 @@ kex_buf2prop(Buffer *raw, int *first_kex_follows)
79 int i; 94 int i;
80 char **proposal; 95 char **proposal;
81 96
82 proposal = xmalloc(PROPOSAL_MAX * sizeof(char *)); 97 proposal = xcalloc(PROPOSAL_MAX, sizeof(char *));
83 98
84 buffer_init(&b); 99 buffer_init(&b);
85 buffer_append(&b, buffer_ptr(raw), buffer_len(raw)); 100 buffer_append(&b, buffer_ptr(raw), buffer_len(raw));
@@ -214,8 +229,7 @@ kex_setup(char *proposal[PROPOSAL_MAX])
214{ 229{
215 Kex *kex; 230 Kex *kex;
216 231
217 kex = xmalloc(sizeof(*kex)); 232 kex = xcalloc(1, sizeof(*kex));
218 memset(kex, 0, sizeof(*kex));
219 buffer_init(&kex->peer); 233 buffer_init(&kex->peer);
220 buffer_init(&kex->my); 234 buffer_init(&kex->my);
221 kex_prop2buf(&kex->my, proposal); 235 kex_prop2buf(&kex->my, proposal);
@@ -258,6 +272,7 @@ choose_enc(Enc *enc, char *client, char *server)
258 enc->key_len = cipher_keylen(enc->cipher); 272 enc->key_len = cipher_keylen(enc->cipher);
259 enc->block_size = cipher_blocksize(enc->cipher); 273 enc->block_size = cipher_blocksize(enc->cipher);
260} 274}
275
261static void 276static void
262choose_mac(Mac *mac, char *client, char *server) 277choose_mac(Mac *mac, char *client, char *server)
263{ 278{
@@ -273,6 +288,7 @@ choose_mac(Mac *mac, char *client, char *server)
273 mac->key = NULL; 288 mac->key = NULL;
274 mac->enabled = 0; 289 mac->enabled = 0;
275} 290}
291
276static void 292static void
277choose_comp(Comp *comp, char *client, char *server) 293choose_comp(Comp *comp, char *client, char *server)
278{ 294{
@@ -290,6 +306,7 @@ choose_comp(Comp *comp, char *client, char *server)
290 } 306 }
291 comp->name = name; 307 comp->name = name;
292} 308}
309
293static void 310static void
294choose_kex(Kex *k, char *client, char *server) 311choose_kex(Kex *k, char *client, char *server)
295{ 312{
@@ -305,15 +322,24 @@ choose_kex(Kex *k, char *client, char *server)
305 } else if (strcmp(k->name, KEX_DHGEX_SHA1) == 0) { 322 } else if (strcmp(k->name, KEX_DHGEX_SHA1) == 0) {
306 k->kex_type = KEX_DH_GEX_SHA1; 323 k->kex_type = KEX_DH_GEX_SHA1;
307 k->evp_md = EVP_sha1(); 324 k->evp_md = EVP_sha1();
325#if OPENSSL_VERSION_NUMBER >= 0x00907000L
326 } else if (strcmp(k->name, KEX_DHGEX_SHA256) == 0) {
327 k->kex_type = KEX_DH_GEX_SHA256;
328 k->evp_md = evp_ssh_sha256();
329#endif
308#ifdef GSSAPI 330#ifdef GSSAPI
309 } else if (strncmp(k->name, KEX_GSS_GEX_SHA1_ID, 331 } else if (strncmp(k->name, KEX_GSS_GEX_SHA1_ID,
310 sizeof(KEX_GSS_GEX_SHA1_ID)-1) == 0) { 332 sizeof(KEX_GSS_GEX_SHA1_ID) - 1) == 0) {
311 k->kex_type = KEX_GSS_GEX_SHA1; 333 k->kex_type = KEX_GSS_GEX_SHA1;
312 k->evp_md = EVP_sha1(); 334 k->evp_md = EVP_sha1();
313 } else if (strncmp(k->name, KEX_GSS_GRP1_SHA1_ID, 335 } else if (strncmp(k->name, KEX_GSS_GRP1_SHA1_ID,
314 sizeof(KEX_GSS_GRP1_SHA1_ID)-1) == 0) { 336 sizeof(KEX_GSS_GRP1_SHA1_ID) - 1) == 0) {
315 k->kex_type = KEX_GSS_GRP1_SHA1; 337 k->kex_type = KEX_GSS_GRP1_SHA1;
316 k->evp_md = EVP_sha1(); 338 k->evp_md = EVP_sha1();
339 } else if (strncmp(k->name, KEX_GSS_GRP14_SHA1_ID,
340 sizeof(KEX_GSS_GRP14_SHA1_ID) - 1) == 0) {
341 k->kex_type = KEX_GSS_GRP14_SHA1;
342 k->evp_md = EVP_sha1();
317#endif 343#endif
318 } else 344 } else
319 fatal("bad kex alg %s", k->name); 345 fatal("bad kex alg %s", k->name);
@@ -378,8 +404,7 @@ kex_choose_conf(Kex *kex)
378 404
379 /* Algorithm Negotiation */ 405 /* Algorithm Negotiation */
380 for (mode = 0; mode < MODE_MAX; mode++) { 406 for (mode = 0; mode < MODE_MAX; mode++) {
381 newkeys = xmalloc(sizeof(*newkeys)); 407 newkeys = xcalloc(1, sizeof(*newkeys));
382 memset(newkeys, 0, sizeof(*newkeys));
383 kex->newkeys[mode] = newkeys; 408 kex->newkeys[mode] = newkeys;
384 ctos = (!kex->server && mode == MODE_OUT) || (kex->server && mode == MODE_IN); 409 ctos = (!kex->server && mode == MODE_OUT) || (kex->server && mode == MODE_IN);
385 nenc = ctos ? PROPOSAL_ENC_ALGS_CTOS : PROPOSAL_ENC_ALGS_STOC; 410 nenc = ctos ? PROPOSAL_ENC_ALGS_CTOS : PROPOSAL_ENC_ALGS_STOC;
@@ -434,7 +459,7 @@ derive_key(Kex *kex, int id, u_int need, u_char *hash, u_int hashlen,
434 459
435 if ((mdsz = EVP_MD_size(kex->evp_md)) <= 0) 460 if ((mdsz = EVP_MD_size(kex->evp_md)) <= 0)
436 fatal("bad kex md size %d", mdsz); 461 fatal("bad kex md size %d", mdsz);
437 digest = xmalloc(roundup(need, mdsz)); 462 digest = xmalloc(roundup(need, mdsz));
438 463
439 buffer_init(&b); 464 buffer_init(&b);
440 buffer_put_bignum2(&b, shared_secret); 465 buffer_put_bignum2(&b, shared_secret);
@@ -487,7 +512,8 @@ kex_derive_keys(Kex *kex, u_char *hash, u_int hashlen, BIGNUM *shared_secret)
487 for (mode = 0; mode < MODE_MAX; mode++) { 512 for (mode = 0; mode < MODE_MAX; mode++) {
488 current_keys[mode] = kex->newkeys[mode]; 513 current_keys[mode] = kex->newkeys[mode];
489 kex->newkeys[mode] = NULL; 514 kex->newkeys[mode] = NULL;
490 ctos = (!kex->server && mode == MODE_OUT) || (kex->server && mode == MODE_IN); 515 ctos = (!kex->server && mode == MODE_OUT) ||
516 (kex->server && mode == MODE_IN);
491 current_keys[mode]->enc.iv = keys[ctos ? 0 : 1]; 517 current_keys[mode]->enc.iv = keys[ctos ? 0 : 1];
492 current_keys[mode]->enc.key = keys[ctos ? 2 : 3]; 518 current_keys[mode]->enc.key = keys[ctos ? 2 : 3];
493 current_keys[mode]->mac.key = keys[ctos ? 4 : 5]; 519 current_keys[mode]->mac.key = keys[ctos ? 4 : 5];
@@ -544,7 +570,7 @@ dump_digest(char *msg, u_char *digest, int len)
544 u_int i; 570 u_int i;
545 571
546 fprintf(stderr, "%s\n", msg); 572 fprintf(stderr, "%s\n", msg);
547 for (i = 0; i< len; i++) { 573 for (i = 0; i < len; i++) {
548 fprintf(stderr, "%02x", digest[i]); 574 fprintf(stderr, "%02x", digest[i]);
549 if (i%32 == 31) 575 if (i%32 == 31)
550 fprintf(stderr, "\n"); 576 fprintf(stderr, "\n");