Branch data Line data Source code
1 : : /* $OpenBSD: kexdhc.c,v 1.15 2014/02/02 03:44:31 djm Exp $ */
2 : : /*
3 : : * Copyright (c) 2001 Markus Friedl. All rights reserved.
4 : : *
5 : : * Redistribution and use in source and binary forms, with or without
6 : : * modification, are permitted provided that the following conditions
7 : : * are met:
8 : : * 1. Redistributions of source code must retain the above copyright
9 : : * notice, this list of conditions and the following disclaimer.
10 : : * 2. Redistributions in binary form must reproduce the above copyright
11 : : * notice, this list of conditions and the following disclaimer in the
12 : : * documentation and/or other materials provided with the distribution.
13 : : *
14 : : * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
15 : : * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
16 : : * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
17 : : * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
18 : : * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
19 : : * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
20 : : * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
21 : : * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22 : : * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
23 : : * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24 : : */
25 : :
26 : : #include "includes.h"
27 : :
28 : : #include <sys/types.h>
29 : :
30 : : #include <openssl/dh.h>
31 : :
32 : : #include <stdarg.h>
33 : : #include <stdio.h>
34 : : #include <string.h>
35 : : #include <signal.h>
36 : :
37 : : #include "xmalloc.h"
38 : : #include "buffer.h"
39 : : #include "key.h"
40 : : #include "cipher.h"
41 : : #include "kex.h"
42 : : #include "log.h"
43 : : #include "packet.h"
44 : : #include "dh.h"
45 : : #include "ssh2.h"
46 : :
47 : : void
48 : 72 : kexdh_client(Kex *kex)
49 : : {
50 : 72 : BIGNUM *dh_server_pub = NULL, *shared_secret = NULL;
51 : : DH *dh;
52 : : Key *server_host_key;
53 : 72 : u_char *server_host_key_blob = NULL, *signature = NULL;
54 : : u_char *kbuf, *hash;
55 : : u_int klen, slen, sbloblen, hashlen;
56 : : int kout;
57 : :
58 : : /* generate and send 'e', client DH public key */
59 [ + + - ]: 72 : switch (kex->kex_type) {
60 : : case KEX_DH_GRP1_SHA1:
61 : 48 : dh = dh_new_group1();
62 : 48 : break;
63 : : case KEX_DH_GRP14_SHA1:
64 : 24 : dh = dh_new_group14();
65 : 24 : break;
66 : : default:
67 : 0 : fatal("%s: Unexpected KEX type %d", __func__, kex->kex_type);
68 : : }
69 : 72 : dh_gen_key(dh, kex->we_need * 8);
70 : 72 : packet_start(SSH2_MSG_KEXDH_INIT);
71 : 72 : packet_put_bignum2(dh->pub_key);
72 : 72 : packet_send();
73 : :
74 : 72 : debug("sending SSH2_MSG_KEXDH_INIT");
75 : : #ifdef DEBUG_KEXDH
76 : : DHparams_print_fp(stderr, dh);
77 : : fprintf(stderr, "pub= ");
78 : : BN_print_fp(stderr, dh->pub_key);
79 : : fprintf(stderr, "\n");
80 : : #endif
81 : :
82 : 72 : debug("expecting SSH2_MSG_KEXDH_REPLY");
83 : 72 : packet_read_expect(SSH2_MSG_KEXDH_REPLY);
84 : :
85 : : /* key, cert */
86 : 72 : server_host_key_blob = packet_get_string(&sbloblen);
87 : 72 : server_host_key = key_from_blob(server_host_key_blob, sbloblen);
88 [ - + ]: 72 : if (server_host_key == NULL)
89 : 0 : fatal("cannot decode server_host_key_blob");
90 [ - + ]: 72 : if (server_host_key->type != kex->hostkey_type)
91 : 0 : fatal("type mismatch for decoded server_host_key_blob");
92 [ - + ]: 72 : if (kex->verify_host_key == NULL)
93 : 0 : fatal("cannot verify server_host_key");
94 [ - + ]: 72 : if (kex->verify_host_key(server_host_key) == -1)
95 : 0 : fatal("server_host_key verification failed");
96 : :
97 : : /* DH parameter f, server public DH key */
98 [ - + ]: 72 : if ((dh_server_pub = BN_new()) == NULL)
99 : 0 : fatal("dh_server_pub == NULL");
100 : 72 : packet_get_bignum2(dh_server_pub);
101 : :
102 : : #ifdef DEBUG_KEXDH
103 : : fprintf(stderr, "dh_server_pub= ");
104 : : BN_print_fp(stderr, dh_server_pub);
105 : : fprintf(stderr, "\n");
106 : : debug("bits %d", BN_num_bits(dh_server_pub));
107 : : #endif
108 : :
109 : : /* signed H */
110 : 72 : signature = packet_get_string(&slen);
111 [ - + ]: 72 : packet_check_eom();
112 : :
113 [ - + ]: 72 : if (!dh_pub_is_valid(dh, dh_server_pub))
114 : 0 : packet_disconnect("bad server public DH value");
115 : :
116 : 72 : klen = DH_size(dh);
117 : 72 : kbuf = xmalloc(klen);
118 [ - + ]: 72 : if ((kout = DH_compute_key(kbuf, dh_server_pub, dh)) < 0)
119 : 0 : fatal("DH_compute_key: failed");
120 : : #ifdef DEBUG_KEXDH
121 : : dump_digest("shared secret", kbuf, kout);
122 : : #endif
123 [ - + ]: 72 : if ((shared_secret = BN_new()) == NULL)
124 : 0 : fatal("kexdh_client: BN_new failed");
125 [ - + ]: 72 : if (BN_bin2bn(kbuf, kout, shared_secret) == NULL)
126 : 0 : fatal("kexdh_client: BN_bin2bn failed");
127 : 72 : explicit_bzero(kbuf, klen);
128 : 72 : free(kbuf);
129 : :
130 : : /* calc and verify H */
131 : 72 : kex_dh_hash(
132 : : kex->client_version_string,
133 : : kex->server_version_string,
134 : 72 : buffer_ptr(&kex->my), buffer_len(&kex->my),
135 : 72 : buffer_ptr(&kex->peer), buffer_len(&kex->peer),
136 : : server_host_key_blob, sbloblen,
137 : : dh->pub_key,
138 : : dh_server_pub,
139 : : shared_secret,
140 : : &hash, &hashlen
141 : : );
142 : 72 : free(server_host_key_blob);
143 : 72 : BN_clear_free(dh_server_pub);
144 : 72 : DH_free(dh);
145 : :
146 [ - + ]: 72 : if (key_verify(server_host_key, signature, slen, hash, hashlen) != 1)
147 : 0 : fatal("key_verify failed for server_host_key");
148 : 72 : key_free(server_host_key);
149 : 72 : free(signature);
150 : :
151 : : /* save session id */
152 [ + + ]: 72 : if (kex->session_id == NULL) {
153 : 24 : kex->session_id_len = hashlen;
154 : 24 : kex->session_id = xmalloc(kex->session_id_len);
155 : 24 : memcpy(kex->session_id, hash, kex->session_id_len);
156 : : }
157 : :
158 : 72 : kex_derive_keys_bn(kex, hash, hashlen, shared_secret);
159 : 72 : BN_clear_free(shared_secret);
160 : 72 : kex_finish(kex);
161 : 72 : }
|