summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ChangeLog6
-rw-r--r--compat.c12
-rw-r--r--compat.h3
-rw-r--r--dh.c19
-rw-r--r--dh.h7
-rw-r--r--ssh2.h5
-rw-r--r--sshconnect2.c35
-rw-r--r--sshd.c34
-rw-r--r--version.h6
9 files changed, 97 insertions, 30 deletions
diff --git a/ChangeLog b/ChangeLog
index c892bd0d8..88c0af3ef 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -16,6 +16,10 @@
16 [compat.c compat.h ssh-rsa.c] 16 [compat.c compat.h ssh-rsa.c]
17 some older systems use NID_md5 instead of NID_sha1 for RSASSA-PKCS1-v1_5 17 some older systems use NID_md5 instead of NID_sha1 for RSASSA-PKCS1-v1_5
18 signatures in SSH protocol 2, ok djm@ 18 signatures in SSH protocol 2, ok djm@
19 - provos@cvs.openbsd.org 2001/03/27 17:46:50
20 [compat.c compat.h dh.c dh.h ssh2.h sshconnect2.c sshd.c version.h]
21 make dh group exchange more flexible, allow min and max group size,
22 okay markus@, deraadt@
19 23
2020010328 2420010328
21 - (djm) Reorder tests and library inclusion for Krb4/AFS to try to 25 - (djm) Reorder tests and library inclusion for Krb4/AFS to try to
@@ -4754,4 +4758,4 @@
4754 - Wrote replacements for strlcpy and mkdtemp 4758 - Wrote replacements for strlcpy and mkdtemp
4755 - Released 1.0pre1 4759 - Released 1.0pre1
4756 4760
4757$Id: ChangeLog,v 1.1030 2001/03/29 00:32:56 mouring Exp $ 4761$Id: ChangeLog,v 1.1031 2001/03/29 00:36:16 mouring Exp $
diff --git a/compat.c b/compat.c
index 98372e202..686016f82 100644
--- a/compat.c
+++ b/compat.c
@@ -23,7 +23,7 @@
23 */ 23 */
24 24
25#include "includes.h" 25#include "includes.h"
26RCSID("$OpenBSD: compat.c,v 1.41 2001/03/27 10:57:00 markus Exp $"); 26RCSID("$OpenBSD: compat.c,v 1.42 2001/03/27 17:46:49 provos Exp $");
27 27
28#ifdef HAVE_LIBPCRE 28#ifdef HAVE_LIBPCRE
29# include <pcreposix.h> 29# include <pcreposix.h>
@@ -68,10 +68,14 @@ compat_datafellows(const char *version)
68 int bugs; 68 int bugs;
69 } check[] = { 69 } check[] = {
70 { "^OpenSSH[-_]2\\.[012]", 70 { "^OpenSSH[-_]2\\.[012]",
71 SSH_OLD_SESSIONID|SSH_BUG_BANNER }, 71 SSH_OLD_SESSIONID|SSH_BUG_BANNER|
72 { "^OpenSSH_2\\.3\\.0", SSH_BUG_BANNER|SSH_BUG_BIGENDIANAES }, 72 SSH_OLD_DHGEX },
73 { "^OpenSSH_2\\.3\\.0", SSH_BUG_BANNER|SSH_BUG_BIGENDIANAES|
74 SSH_OLD_DHGEX},
73 { "^OpenSSH_2\\.5\\.[01]p1", 75 { "^OpenSSH_2\\.5\\.[01]p1",
74 SSH_BUG_BIGENDIANAES }, 76 SSH_BUG_BIGENDIANAES|SSH_OLD_DHGEX },
77 { "^OpenSSH_2\\.5\\.[012]",
78 SSH_OLD_DHGEX },
75 { "^OpenSSH", 0 }, 79 { "^OpenSSH", 0 },
76 { "MindTerm", 0 }, 80 { "MindTerm", 0 },
77 { "^2\\.1\\.0", SSH_BUG_SIGBLOB|SSH_BUG_HMAC| 81 { "^2\\.1\\.0", SSH_BUG_SIGBLOB|SSH_BUG_HMAC|
diff --git a/compat.h b/compat.h
index 03f236117..e4ca5c1bc 100644
--- a/compat.h
+++ b/compat.h
@@ -21,7 +21,7 @@
21 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 21 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
22 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 22 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
23 */ 23 */
24/* RCSID("$OpenBSD: compat.h,v 1.20 2001/03/27 10:57:00 markus Exp $"); */ 24/* RCSID("$OpenBSD: compat.h,v 1.21 2001/03/27 17:46:49 provos Exp $"); */
25 25
26#ifndef COMPAT_H 26#ifndef COMPAT_H
27#define COMPAT_H 27#define COMPAT_H
@@ -45,6 +45,7 @@
45#define SSH_BUG_SCANNER 0x0800 45#define SSH_BUG_SCANNER 0x0800
46#define SSH_BUG_BIGENDIANAES 0x1000 46#define SSH_BUG_BIGENDIANAES 0x1000
47#define SSH_BUG_RSASIGMD5 0x2000 47#define SSH_BUG_RSASIGMD5 0x2000
48#define SSH_OLD_DHGEX 0x4000
48 49
49void enable_compat13(void); 50void enable_compat13(void);
50void enable_compat20(void); 51void enable_compat20(void);
diff --git a/dh.c b/dh.c
index ac73f8400..5f441ee1c 100644
--- a/dh.c
+++ b/dh.c
@@ -23,7 +23,7 @@
23 */ 23 */
24 24
25#include "includes.h" 25#include "includes.h"
26RCSID("$OpenBSD: dh.c,v 1.8 2001/03/05 17:58:22 stevesk Exp $"); 26RCSID("$OpenBSD: dh.c,v 1.9 2001/03/27 17:46:49 provos Exp $");
27 27
28#include "xmalloc.h" 28#include "xmalloc.h"
29 29
@@ -69,6 +69,8 @@ parse_prime(int linenum, char *line, struct dhgroup *dhg)
69 if (cp == NULL || *strsize == '\0' || 69 if (cp == NULL || *strsize == '\0' ||
70 (dhg->size = atoi(strsize)) == 0) 70 (dhg->size = atoi(strsize)) == 0)
71 goto fail; 71 goto fail;
72 /* The whole group is one bit larger */
73 dhg->size++;
72 gen = strsep(&cp, " "); /* gen */ 74 gen = strsep(&cp, " "); /* gen */
73 if (cp == NULL || *gen == '\0') 75 if (cp == NULL || *gen == '\0')
74 goto fail; 76 goto fail;
@@ -95,7 +97,7 @@ parse_prime(int linenum, char *line, struct dhgroup *dhg)
95} 97}
96 98
97DH * 99DH *
98choose_dh(int minbits) 100choose_dh(int min, int wantbits, int max)
99{ 101{
100 FILE *f; 102 FILE *f;
101 char line[1024]; 103 char line[1024];
@@ -118,8 +120,11 @@ choose_dh(int minbits)
118 BN_free(dhg.g); 120 BN_free(dhg.g);
119 BN_free(dhg.p); 121 BN_free(dhg.p);
120 122
121 if ((dhg.size > minbits && dhg.size < best) || 123 if (dhg.size > max || dhg.size < min)
122 (dhg.size > best && best < minbits)) { 124 continue;
125
126 if ((dhg.size > wantbits && dhg.size < best) ||
127 (dhg.size > best && best < wantbits)) {
123 best = dhg.size; 128 best = dhg.size;
124 bestcount = 0; 129 bestcount = 0;
125 } 130 }
@@ -129,8 +134,8 @@ choose_dh(int minbits)
129 fclose (f); 134 fclose (f);
130 135
131 if (bestcount == 0) { 136 if (bestcount == 0) {
132 log("WARNING: no primes in %s, using old prime", _PATH_DH_PRIMES); 137 log("WARNING: no suitable primes in %s", _PATH_DH_PRIMES);
133 return (dh_new_group1()); 138 return (NULL);
134 } 139 }
135 140
136 f = fopen(_PATH_DH_PRIMES, "r"); 141 f = fopen(_PATH_DH_PRIMES, "r");
@@ -143,6 +148,8 @@ choose_dh(int minbits)
143 while (fgets(line, sizeof(line), f)) { 148 while (fgets(line, sizeof(line), f)) {
144 if (!parse_prime(linenum, line, &dhg)) 149 if (!parse_prime(linenum, line, &dhg))
145 continue; 150 continue;
151 if (dhg.size > max || dhg.size < min)
152 continue;
146 if (dhg.size != best) 153 if (dhg.size != best)
147 continue; 154 continue;
148 if (linenum++ != which) { 155 if (linenum++ != which) {
diff --git a/dh.h b/dh.h
index f08d70e3f..70b326e9f 100644
--- a/dh.h
+++ b/dh.h
@@ -1,4 +1,4 @@
1/* $OpenBSD: dh.h,v 1.2 2001/01/29 01:58:15 niklas Exp $ */ 1/* $OpenBSD: dh.h,v 1.3 2001/03/27 17:46:49 provos Exp $ */
2 2
3/* 3/*
4 * Copyright (c) 2000 Niels Provos. All rights reserved. 4 * Copyright (c) 2000 Niels Provos. All rights reserved.
@@ -32,6 +32,9 @@ struct dhgroup {
32 BIGNUM *p; 32 BIGNUM *p;
33}; 33};
34 34
35DH *choose_dh(int minbits); 35DH *choose_dh(int min, int nbits, int max);
36
37#define DH_GRP_MIN 1024
38#define DH_GRP_MAX 8192
36 39
37#endif 40#endif
diff --git a/ssh2.h b/ssh2.h
index fe0146cbd..e45aef275 100644
--- a/ssh2.h
+++ b/ssh2.h
@@ -52,7 +52,7 @@
52 * 52 *
53 * 192-255 Local extensions 53 * 192-255 Local extensions
54 */ 54 */
55/* RCSID("$OpenBSD: ssh2.h,v 1.5 2000/10/11 04:02:17 provos Exp $"); */ 55/* RCSID("$OpenBSD: ssh2.h,v 1.6 2001/03/27 17:46:49 provos Exp $"); */
56 56
57/* transport layer: generic */ 57/* transport layer: generic */
58 58
@@ -74,10 +74,11 @@
74#define SSH2_MSG_KEXDH_REPLY 31 74#define SSH2_MSG_KEXDH_REPLY 31
75 75
76/* dh-group-exchange */ 76/* dh-group-exchange */
77#define SSH2_MSG_KEX_DH_GEX_REQUEST 30 77#define SSH2_MSG_KEX_DH_GEX_REQUEST_OLD 30
78#define SSH2_MSG_KEX_DH_GEX_GROUP 31 78#define SSH2_MSG_KEX_DH_GEX_GROUP 31
79#define SSH2_MSG_KEX_DH_GEX_INIT 32 79#define SSH2_MSG_KEX_DH_GEX_INIT 32
80#define SSH2_MSG_KEX_DH_GEX_REPLY 33 80#define SSH2_MSG_KEX_DH_GEX_REPLY 33
81#define SSH2_MSG_KEX_DH_GEX_REQUEST 34
81 82
82/* user authentication: generic */ 83/* user authentication: generic */
83 84
diff --git a/sshconnect2.c b/sshconnect2.c
index f636fb3d9..da8c8229c 100644
--- a/sshconnect2.c
+++ b/sshconnect2.c
@@ -23,7 +23,7 @@
23 */ 23 */
24 24
25#include "includes.h" 25#include "includes.h"
26RCSID("$OpenBSD: sshconnect2.c,v 1.56 2001/03/26 08:07:09 markus Exp $"); 26RCSID("$OpenBSD: sshconnect2.c,v 1.57 2001/03/27 17:46:49 provos Exp $");
27 27
28#include <openssl/bn.h> 28#include <openssl/bn.h>
29#include <openssl/md5.h> 29#include <openssl/md5.h>
@@ -46,6 +46,7 @@ RCSID("$OpenBSD: sshconnect2.c,v 1.56 2001/03/26 08:07:09 markus Exp $");
46#include "sshconnect.h" 46#include "sshconnect.h"
47#include "authfile.h" 47#include "authfile.h"
48#include "cli.h" 48#include "cli.h"
49#include "dh.h"
49#include "dispatch.h" 50#include "dispatch.h"
50#include "authfd.h" 51#include "authfd.h"
51#include "log.h" 52#include "log.h"
@@ -309,7 +310,7 @@ ssh_dhgex_client(Kex *kex, char *host, struct sockaddr *hostaddr,
309 int plen, dlen; 310 int plen, dlen;
310 u_int klen, kout; 311 u_int klen, kout;
311 char *signature = NULL; 312 char *signature = NULL;
312 u_int slen, nbits; 313 u_int slen, nbits, min, max;
313 char *server_host_key_blob = NULL; 314 char *server_host_key_blob = NULL;
314 Key *server_host_key; 315 Key *server_host_key;
315 u_int sbloblen; 316 u_int sbloblen;
@@ -322,14 +323,31 @@ ssh_dhgex_client(Kex *kex, char *host, struct sockaddr *hostaddr,
322 323
323 nbits = dh_estimate(kex->we_need * 8); 324 nbits = dh_estimate(kex->we_need * 8);
324 325
325 debug("Sending SSH2_MSG_KEX_DH_GEX_REQUEST."); 326 if (datafellows & SSH_OLD_DHGEX) {
326 packet_start(SSH2_MSG_KEX_DH_GEX_REQUEST); 327 debug("Sending SSH2_MSG_KEX_DH_GEX_REQUEST_OLD.");
327 packet_put_int(nbits); 328
329 /* Old GEX request */
330 packet_start(SSH2_MSG_KEX_DH_GEX_REQUEST_OLD);
331 packet_put_int(nbits);
332 min = DH_GRP_MIN;
333 max = DH_GRP_MAX;
334 } else {
335 debug("Sending SSH2_MSG_KEX_DH_GEX_REQUEST.");
336
337 /* New GEX request */
338 min = DH_GRP_MIN;
339 max = MIN(DH_GRP_MAX, nbits * 1.25);
340
341 packet_start(SSH2_MSG_KEX_DH_GEX_REQUEST);
342 packet_put_int(min);
343 packet_put_int(nbits);
344 packet_put_int(max);
345 }
328 packet_send(); 346 packet_send();
329 packet_write_wait(); 347 packet_write_wait();
330 348
331#ifdef DEBUG_KEXDH 349#ifdef DEBUG_KEXDH
332 fprintf(stderr, "\nnbits = %d", nbits); 350 fprintf(stderr, "\nmin = %d, nbits = %d, max = %d", min, nbits, max);
333#endif 351#endif
334 352
335 debug("Wait SSH2_MSG_KEX_DH_GEX_GROUP."); 353 debug("Wait SSH2_MSG_KEX_DH_GEX_GROUP.");
@@ -344,6 +362,11 @@ ssh_dhgex_client(Kex *kex, char *host, struct sockaddr *hostaddr,
344 if ((g = BN_new()) == NULL) 362 if ((g = BN_new()) == NULL)
345 fatal("BN_new"); 363 fatal("BN_new");
346 packet_get_bignum2(g, &dlen); 364 packet_get_bignum2(g, &dlen);
365
366 if (BN_num_bits(p) < min || BN_num_bits(p) > max)
367 fatal("DH_GEX group out of range: %d !< %d !< %d",
368 min, BN_num_bits(p), max);
369
347 dh = dh_new_group(g, p); 370 dh = dh_new_group(g, p);
348 371
349 dh_gen_key(dh, kex->we_need * 8); 372 dh_gen_key(dh, kex->we_need * 8);
diff --git a/sshd.c b/sshd.c
index 961aeeaa0..65cb832d4 100644
--- a/sshd.c
+++ b/sshd.c
@@ -40,7 +40,7 @@
40 */ 40 */
41 41
42#include "includes.h" 42#include "includes.h"
43RCSID("$OpenBSD: sshd.c,v 1.180 2001/03/27 10:34:08 markus Exp $"); 43RCSID("$OpenBSD: sshd.c,v 1.181 2001/03/27 17:46:49 provos Exp $");
44 44
45#include <openssl/dh.h> 45#include <openssl/dh.h>
46#include <openssl/bn.h> 46#include <openssl/bn.h>
@@ -1614,7 +1614,7 @@ ssh_dhgex_server(Kex *kex, Buffer *client_kexinit, Buffer *server_kexinit)
1614 int i; 1614 int i;
1615#endif 1615#endif
1616 int payload_len, dlen; 1616 int payload_len, dlen;
1617 int slen, nbits; 1617 int slen, nbits, type, min, max;
1618 u_char *signature = NULL; 1618 u_char *signature = NULL;
1619 u_char *server_host_key_blob = NULL; 1619 u_char *server_host_key_blob = NULL;
1620 u_int sbloblen; 1620 u_int sbloblen;
@@ -1632,9 +1632,33 @@ ssh_dhgex_server(Kex *kex, Buffer *client_kexinit, Buffer *server_kexinit)
1632 1632
1633/* KEXDHGEX */ 1633/* KEXDHGEX */
1634 debug("Wait SSH2_MSG_KEX_DH_GEX_REQUEST."); 1634 debug("Wait SSH2_MSG_KEX_DH_GEX_REQUEST.");
1635 packet_read_expect(&payload_len, SSH2_MSG_KEX_DH_GEX_REQUEST); 1635 type = packet_read(&payload_len);
1636 nbits = packet_get_int(); 1636 if (type != SSH2_MSG_KEX_DH_GEX_REQUEST_OLD &&
1637 dh = choose_dh(nbits); 1637 type != SSH2_MSG_KEX_DH_GEX_REQUEST)
1638 packet_disconnect("Protocol error: expected type %d or %d, got %d",
1639 SSH2_MSG_KEX_DH_GEX_REQUEST_OLD,
1640 SSH2_MSG_KEX_DH_GEX_REQUEST,
1641 type);
1642 if (type == SSH2_MSG_KEX_DH_GEX_REQUEST_OLD) {
1643 nbits = packet_get_int();
1644 min = DH_GRP_MIN;
1645 max = DH_GRP_MAX;
1646 } else {
1647 min = packet_get_int();
1648 nbits = packet_get_int();
1649 max = packet_get_int();
1650
1651 min = MAX(DH_GRP_MIN, min);
1652 max = MIN(DH_GRP_MAX, max);
1653 }
1654
1655 if (max < min || nbits < min || max < nbits)
1656 fatal("DH_GEX_REQUEST, bad parameters: %d !< %d !< %d",
1657 min, nbits, max);
1658
1659 dh = choose_dh(min, nbits, max);
1660 if (dh == NULL)
1661 packet_disconnect("Protocol error: no matching DH grp found");
1638 1662
1639 debug("Sending SSH2_MSG_KEX_DH_GEX_GROUP."); 1663 debug("Sending SSH2_MSG_KEX_DH_GEX_GROUP.");
1640 packet_start(SSH2_MSG_KEX_DH_GEX_GROUP); 1664 packet_start(SSH2_MSG_KEX_DH_GEX_GROUP);
diff --git a/version.h b/version.h
index 8ece8d0e3..bdf8c1d2d 100644
--- a/version.h
+++ b/version.h
@@ -1,3 +1,3 @@
1/* $OpenBSD: version.h,v 1.20 2001/03/19 17:12:10 markus Exp $ */ 1/* $OpenBSD: version.h,v 1.21 2001/03/27 17:46:50 provos Exp $ */
2 2
3#define SSH_VERSION "OpenSSH_2.5.2p1" 3#define SSH_VERSION "OpenSSH_2.5.3p1"