View | Details | Raw Unified | Return to bug 49349
Collapse All | Expand All

(-)a/cli-session.c (+11 lines)
Lines 46-51 static void cli_finished(void) ATTRIB_NORETURN; Link Here
46
static void recv_msg_service_accept(void);
46
static void recv_msg_service_accept(void);
47
static void cli_session_cleanup(void);
47
static void cli_session_cleanup(void);
48
static void recv_msg_global_request_cli(void);
48
static void recv_msg_global_request_cli(void);
49
static void cli_algos_initialise(void);
49
50
50
struct clientsession cli_ses; /* GLOBAL */
51
struct clientsession cli_ses; /* GLOBAL */
51
52
Lines 117-122 void cli_session(int sock_in, int sock_out, struct dropbear_progress_connection Link Here
117
	}
118
	}
118
119
119
	chaninitialise(cli_chantypes);
120
	chaninitialise(cli_chantypes);
121
	cli_algos_initialise();
120
122
121
	/* Set up cli_ses vars */
123
	/* Set up cli_ses vars */
122
	cli_session_init(proxy_cmd_pid);
124
	cli_session_init(proxy_cmd_pid);
Lines 487-489 void cli_dropbear_log(int priority, const char* format, va_list param) { Link Here
487
	fflush(stderr);
489
	fflush(stderr);
488
}
490
}
489
491
492
static void cli_algos_initialise(void) {
493
	algo_type *algo;
494
	for (algo = sshkex; algo->name; algo++) {
495
		if (strcmp(algo->name, SSH_STRICT_KEX_S) == 0) {
496
			algo->usable = 0;
497
		}
498
	}
499
}
500
(-)a/common-algo.c (+6 lines)
Lines 307-312 algo_type sshkex[] = { Link Here
307
	/* Set unusable by svr_algos_initialise() */
307
	/* Set unusable by svr_algos_initialise() */
308
	{SSH_EXT_INFO_C, 0, NULL, 1, NULL},
308
	{SSH_EXT_INFO_C, 0, NULL, 1, NULL},
309
#endif
309
#endif
310
#endif
311
#if DROPBEAR_CLIENT
312
	{SSH_STRICT_KEX_C, 0, NULL, 1, NULL},
313
#endif
314
#if DROPBEAR_SERVER
315
	{SSH_STRICT_KEX_S, 0, NULL, 1, NULL},
310
#endif
316
#endif
311
	{NULL, 0, NULL, 0, NULL}
317
	{NULL, 0, NULL, 0, NULL}
312
};
318
};
(-)a/common-kex.c (-1 / +25 lines)
Lines 183-188 void send_msg_newkeys() { Link Here
183
	gen_new_keys();
183
	gen_new_keys();
184
	switch_keys();
184
	switch_keys();
185
185
186
	if (ses.kexstate.strict_kex) {
187
		ses.transseq = 0;
188
	}
189
186
	TRACE(("leave send_msg_newkeys"))
190
	TRACE(("leave send_msg_newkeys"))
187
}
191
}
188
192
Lines 193-199 void recv_msg_newkeys() { Link Here
193
197
194
	ses.kexstate.recvnewkeys = 1;
198
	ses.kexstate.recvnewkeys = 1;
195
	switch_keys();
199
	switch_keys();
196
	
200
201
	if (ses.kexstate.strict_kex) {
202
		ses.recvseq = 0;
203
	}
204
197
	TRACE(("leave recv_msg_newkeys"))
205
	TRACE(("leave recv_msg_newkeys"))
198
}
206
}
199
207
Lines 550-555 void recv_msg_kexinit() { Link Here
550
558
551
	ses.kexstate.recvkexinit = 1;
559
	ses.kexstate.recvkexinit = 1;
552
560
561
	if (ses.kexstate.strict_kex && !ses.kexstate.donefirstkex && ses.recvseq != 1) {
562
		dropbear_exit("First packet wasn't kexinit");
563
	}
564
553
	TRACE(("leave recv_msg_kexinit"))
565
	TRACE(("leave recv_msg_kexinit"))
554
}
566
}
555
567
Lines 859-864 static void read_kex_algos() { Link Here
859
	}
871
	}
860
#endif
872
#endif
861
873
874
	if (!ses.kexstate.donefirstkex) {
875
		const char* strict_name;
876
		if (IS_DROPBEAR_CLIENT) {
877
			strict_name = SSH_STRICT_KEX_S;
878
		} else {
879
			strict_name = SSH_STRICT_KEX_C;
880
		}
881
		if (buf_has_algo(ses.payload, strict_name) == DROPBEAR_SUCCESS) {
882
			ses.kexstate.strict_kex = 1;
883
		}
884
	}
885
862
	algo = buf_match_algo(ses.payload, sshkex, kexguess2, &goodguess);
886
	algo = buf_match_algo(ses.payload, sshkex, kexguess2, &goodguess);
863
	allgood &= goodguess;
887
	allgood &= goodguess;
864
	if (algo == NULL || algo->data == NULL) {
888
	if (algo == NULL || algo->data == NULL) {
(-)a/kex.h (+3 lines)
Lines 83-88 struct KEXState { Link Here
83
83
84
	unsigned our_first_follows_matches : 1;
84
	unsigned our_first_follows_matches : 1;
85
85
86
	/* Boolean indicating that strict kex mode is in use */
87
	unsigned int strict_kex;
88
86
	time_t lastkextime; /* time of the last kex */
89
	time_t lastkextime; /* time of the last kex */
87
	unsigned int datatrans; /* data transmitted since last kex */
90
	unsigned int datatrans; /* data transmitted since last kex */
88
	unsigned int datarecv; /* data received since last kex */
91
	unsigned int datarecv; /* data received since last kex */
(-)a/process-packet.c (-15 / +19 lines)
Lines 44-49 void process_packet() { Link Here
44
44
45
	unsigned char type;
45
	unsigned char type;
46
	unsigned int i;
46
	unsigned int i;
47
	unsigned int first_strict_kex = ses.kexstate.strict_kex && !ses.kexstate.donefirstkex;
47
	time_t now;
48
	time_t now;
48
49
49
	TRACE2(("enter process_packet"))
50
	TRACE2(("enter process_packet"))
Lines 54-75 void process_packet() { Link Here
54
	now = monotonic_now();
55
	now = monotonic_now();
55
	ses.last_packet_time_keepalive_recv = now;
56
	ses.last_packet_time_keepalive_recv = now;
56
57
57
	/* These packets we can receive at any time */
58
	switch(type) {
59
58
60
		case SSH_MSG_IGNORE:
59
	if (type == SSH_MSG_DISCONNECT) {
61
			goto out;
60
		/* Allowed at any time */
62
		case SSH_MSG_DEBUG:
61
		dropbear_close("Disconnect received");
63
			goto out;
62
	}
64
63
65
		case SSH_MSG_UNIMPLEMENTED:
64
	/* These packets may be received at any time,
66
			/* debugging XXX */
65
	   except during first kex with strict kex */
67
			TRACE(("SSH_MSG_UNIMPLEMENTED"))
66
	if (!first_strict_kex) {
68
			goto out;
67
		switch(type) {
69
			
68
			case SSH_MSG_IGNORE:
70
		case SSH_MSG_DISCONNECT:
69
				goto out;
71
			/* TODO cleanup? */
70
			case SSH_MSG_DEBUG:
72
			dropbear_close("Disconnect received");
71
				goto out;
72
			case SSH_MSG_UNIMPLEMENTED:
73
				TRACE(("SSH_MSG_UNIMPLEMENTED"))
74
				goto out;
75
		}
73
	}
76
	}
74
77
75
	/* Ignore these packet types so that keepalives don't interfere with
78
	/* Ignore these packet types so that keepalives don't interfere with
Lines 98-104 void process_packet() { Link Here
98
			if (type >= 1 && type <= 49
101
			if (type >= 1 && type <= 49
99
				&& type != SSH_MSG_SERVICE_REQUEST
102
				&& type != SSH_MSG_SERVICE_REQUEST
100
				&& type != SSH_MSG_SERVICE_ACCEPT
103
				&& type != SSH_MSG_SERVICE_ACCEPT
101
				&& type != SSH_MSG_KEXINIT)
104
				&& type != SSH_MSG_KEXINIT
105
				&& !first_strict_kex)
102
			{
106
			{
103
				TRACE(("unknown allowed packet during kexinit"))
107
				TRACE(("unknown allowed packet during kexinit"))
104
				recv_unimplemented();
108
				recv_unimplemented();
(-)a/ssh.h (+4 lines)
Lines 100-105 Link Here
100
#define SSH_EXT_INFO_C "ext-info-c"
100
#define SSH_EXT_INFO_C "ext-info-c"
101
#define SSH_SERVER_SIG_ALGS "server-sig-algs"
101
#define SSH_SERVER_SIG_ALGS "server-sig-algs"
102
102
103
/* OpenSSH strict KEX feature */
104
#define SSH_STRICT_KEX_S "kex-strict-s-v00@openssh.com"
105
#define SSH_STRICT_KEX_C "kex-strict-c-v00@openssh.com"
106
103
/* service types */
107
/* service types */
104
#define SSH_SERVICE_USERAUTH "ssh-userauth"
108
#define SSH_SERVICE_USERAUTH "ssh-userauth"
105
#define SSH_SERVICE_USERAUTH_LEN 12
109
#define SSH_SERVICE_USERAUTH_LEN 12
(-)a/svr-session.c (+3 lines)
Lines 370-375 static void svr_algos_initialise(void) { Link Here
370
			algo->usable = 0;
370
			algo->usable = 0;
371
		}
371
		}
372
#endif
372
#endif
373
		if (strcmp(algo->name, SSH_STRICT_KEX_C) == 0) {
374
			algo->usable = 0;
375
		}
373
	}
376
	}
374
}
377
}
375
378

Return to bug 49349