xref: /openbsd-src/usr.bin/ssh/nchan.c (revision daf88648c0e349d5c02e1504293082072c981640)
1 /* $OpenBSD: nchan.c,v 1.57 2006/08/03 03:34:42 deraadt Exp $ */
2 /*
3  * Copyright (c) 1999, 2000, 2001, 2002 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 <sys/types.h>
27 #include <sys/socket.h>
28 
29 #include <errno.h>
30 #include <string.h>
31 #include <stdarg.h>
32 
33 #include "ssh1.h"
34 #include "ssh2.h"
35 #include "buffer.h"
36 #include "packet.h"
37 #include "channels.h"
38 #include "compat.h"
39 #include "log.h"
40 
41 /*
42  * SSH Protocol 1.5 aka New Channel Protocol
43  * Thanks to Martina, Axel and everyone who left Erlangen, leaving me bored.
44  * Written by Markus Friedl in October 1999
45  *
46  * Protocol versions 1.3 and 1.5 differ in the handshake protocol used for the
47  * tear down of channels:
48  *
49  * 1.3:	strict request-ack-protocol:
50  *	CLOSE	->
51  *		<-  CLOSE_CONFIRM
52  *
53  * 1.5:	uses variations of:
54  *	IEOF	->
55  *		<-  OCLOSE
56  *		<-  IEOF
57  *	OCLOSE	->
58  *	i.e. both sides have to close the channel
59  *
60  * 2.0: the EOF messages are optional
61  *
62  * See the debugging output from 'ssh -v' and 'sshd -d' of
63  * ssh-1.2.27 as an example.
64  *
65  */
66 
67 /* functions manipulating channel states */
68 /*
69  * EVENTS update channel input/output states execute ACTIONS
70  */
71 /*
72  * ACTIONS: should never update the channel states
73  */
74 static void	chan_send_ieof1(Channel *);
75 static void	chan_send_oclose1(Channel *);
76 static void	chan_send_close2(Channel *);
77 static void	chan_send_eof2(Channel *);
78 
79 /* helper */
80 static void	chan_shutdown_write(Channel *);
81 static void	chan_shutdown_read(Channel *);
82 
83 static char *ostates[] = { "open", "drain", "wait_ieof", "closed" };
84 static char *istates[] = { "open", "drain", "wait_oclose", "closed" };
85 
86 static void
87 chan_set_istate(Channel *c, u_int next)
88 {
89 	if (c->istate > CHAN_INPUT_CLOSED || next > CHAN_INPUT_CLOSED)
90 		fatal("chan_set_istate: bad state %d -> %d", c->istate, next);
91 	debug2("channel %d: input %s -> %s", c->self, istates[c->istate],
92 	    istates[next]);
93 	c->istate = next;
94 }
95 static void
96 chan_set_ostate(Channel *c, u_int next)
97 {
98 	if (c->ostate > CHAN_OUTPUT_CLOSED || next > CHAN_OUTPUT_CLOSED)
99 		fatal("chan_set_ostate: bad state %d -> %d", c->ostate, next);
100 	debug2("channel %d: output %s -> %s", c->self, ostates[c->ostate],
101 	    ostates[next]);
102 	c->ostate = next;
103 }
104 
105 /*
106  * SSH1 specific implementation of event functions
107  */
108 
109 static void
110 chan_rcvd_oclose1(Channel *c)
111 {
112 	debug2("channel %d: rcvd oclose", c->self);
113 	switch (c->istate) {
114 	case CHAN_INPUT_WAIT_OCLOSE:
115 		chan_set_istate(c, CHAN_INPUT_CLOSED);
116 		break;
117 	case CHAN_INPUT_OPEN:
118 		chan_shutdown_read(c);
119 		chan_send_ieof1(c);
120 		chan_set_istate(c, CHAN_INPUT_CLOSED);
121 		break;
122 	case CHAN_INPUT_WAIT_DRAIN:
123 		/* both local read_failed and remote write_failed  */
124 		chan_send_ieof1(c);
125 		chan_set_istate(c, CHAN_INPUT_CLOSED);
126 		break;
127 	default:
128 		error("channel %d: protocol error: rcvd_oclose for istate %d",
129 		    c->self, c->istate);
130 		return;
131 	}
132 }
133 void
134 chan_read_failed(Channel *c)
135 {
136 	debug2("channel %d: read failed", c->self);
137 	switch (c->istate) {
138 	case CHAN_INPUT_OPEN:
139 		chan_shutdown_read(c);
140 		chan_set_istate(c, CHAN_INPUT_WAIT_DRAIN);
141 		break;
142 	default:
143 		error("channel %d: chan_read_failed for istate %d",
144 		    c->self, c->istate);
145 		break;
146 	}
147 }
148 void
149 chan_ibuf_empty(Channel *c)
150 {
151 	debug2("channel %d: ibuf empty", c->self);
152 	if (buffer_len(&c->input)) {
153 		error("channel %d: chan_ibuf_empty for non empty buffer",
154 		    c->self);
155 		return;
156 	}
157 	switch (c->istate) {
158 	case CHAN_INPUT_WAIT_DRAIN:
159 		if (compat20) {
160 			if (!(c->flags & CHAN_CLOSE_SENT))
161 				chan_send_eof2(c);
162 			chan_set_istate(c, CHAN_INPUT_CLOSED);
163 		} else {
164 			chan_send_ieof1(c);
165 			chan_set_istate(c, CHAN_INPUT_WAIT_OCLOSE);
166 		}
167 		break;
168 	default:
169 		error("channel %d: chan_ibuf_empty for istate %d",
170 		    c->self, c->istate);
171 		break;
172 	}
173 }
174 static void
175 chan_rcvd_ieof1(Channel *c)
176 {
177 	debug2("channel %d: rcvd ieof", c->self);
178 	switch (c->ostate) {
179 	case CHAN_OUTPUT_OPEN:
180 		chan_set_ostate(c, CHAN_OUTPUT_WAIT_DRAIN);
181 		break;
182 	case CHAN_OUTPUT_WAIT_IEOF:
183 		chan_set_ostate(c, CHAN_OUTPUT_CLOSED);
184 		break;
185 	default:
186 		error("channel %d: protocol error: rcvd_ieof for ostate %d",
187 		    c->self, c->ostate);
188 		break;
189 	}
190 }
191 static void
192 chan_write_failed1(Channel *c)
193 {
194 	debug2("channel %d: write failed", c->self);
195 	switch (c->ostate) {
196 	case CHAN_OUTPUT_OPEN:
197 		chan_shutdown_write(c);
198 		chan_send_oclose1(c);
199 		chan_set_ostate(c, CHAN_OUTPUT_WAIT_IEOF);
200 		break;
201 	case CHAN_OUTPUT_WAIT_DRAIN:
202 		chan_shutdown_write(c);
203 		chan_send_oclose1(c);
204 		chan_set_ostate(c, CHAN_OUTPUT_CLOSED);
205 		break;
206 	default:
207 		error("channel %d: chan_write_failed for ostate %d",
208 		    c->self, c->ostate);
209 		break;
210 	}
211 }
212 void
213 chan_obuf_empty(Channel *c)
214 {
215 	debug2("channel %d: obuf empty", c->self);
216 	if (buffer_len(&c->output)) {
217 		error("channel %d: chan_obuf_empty for non empty buffer",
218 		    c->self);
219 		return;
220 	}
221 	switch (c->ostate) {
222 	case CHAN_OUTPUT_WAIT_DRAIN:
223 		chan_shutdown_write(c);
224 		if (!compat20)
225 			chan_send_oclose1(c);
226 		chan_set_ostate(c, CHAN_OUTPUT_CLOSED);
227 		break;
228 	default:
229 		error("channel %d: internal error: obuf_empty for ostate %d",
230 		    c->self, c->ostate);
231 		break;
232 	}
233 }
234 static void
235 chan_send_ieof1(Channel *c)
236 {
237 	debug2("channel %d: send ieof", c->self);
238 	switch (c->istate) {
239 	case CHAN_INPUT_OPEN:
240 	case CHAN_INPUT_WAIT_DRAIN:
241 		packet_start(SSH_MSG_CHANNEL_INPUT_EOF);
242 		packet_put_int(c->remote_id);
243 		packet_send();
244 		break;
245 	default:
246 		error("channel %d: cannot send ieof for istate %d",
247 		    c->self, c->istate);
248 		break;
249 	}
250 }
251 static void
252 chan_send_oclose1(Channel *c)
253 {
254 	debug2("channel %d: send oclose", c->self);
255 	switch (c->ostate) {
256 	case CHAN_OUTPUT_OPEN:
257 	case CHAN_OUTPUT_WAIT_DRAIN:
258 		buffer_clear(&c->output);
259 		packet_start(SSH_MSG_CHANNEL_OUTPUT_CLOSE);
260 		packet_put_int(c->remote_id);
261 		packet_send();
262 		break;
263 	default:
264 		error("channel %d: cannot send oclose for ostate %d",
265 		    c->self, c->ostate);
266 		break;
267 	}
268 }
269 
270 /*
271  * the same for SSH2
272  */
273 static void
274 chan_rcvd_close2(Channel *c)
275 {
276 	debug2("channel %d: rcvd close", c->self);
277 	if (c->flags & CHAN_CLOSE_RCVD)
278 		error("channel %d: protocol error: close rcvd twice", c->self);
279 	c->flags |= CHAN_CLOSE_RCVD;
280 	if (c->type == SSH_CHANNEL_LARVAL) {
281 		/* tear down larval channels immediately */
282 		chan_set_ostate(c, CHAN_OUTPUT_CLOSED);
283 		chan_set_istate(c, CHAN_INPUT_CLOSED);
284 		return;
285 	}
286 	switch (c->ostate) {
287 	case CHAN_OUTPUT_OPEN:
288 		/*
289 		 * wait until a data from the channel is consumed if a CLOSE
290 		 * is received
291 		 */
292 		chan_set_ostate(c, CHAN_OUTPUT_WAIT_DRAIN);
293 		break;
294 	}
295 	switch (c->istate) {
296 	case CHAN_INPUT_OPEN:
297 		chan_shutdown_read(c);
298 		chan_set_istate(c, CHAN_INPUT_CLOSED);
299 		break;
300 	case CHAN_INPUT_WAIT_DRAIN:
301 		chan_send_eof2(c);
302 		chan_set_istate(c, CHAN_INPUT_CLOSED);
303 		break;
304 	}
305 }
306 static void
307 chan_rcvd_eof2(Channel *c)
308 {
309 	debug2("channel %d: rcvd eof", c->self);
310 	c->flags |= CHAN_EOF_RCVD;
311 	if (c->ostate == CHAN_OUTPUT_OPEN)
312 		chan_set_ostate(c, CHAN_OUTPUT_WAIT_DRAIN);
313 }
314 static void
315 chan_write_failed2(Channel *c)
316 {
317 	debug2("channel %d: write failed", c->self);
318 	switch (c->ostate) {
319 	case CHAN_OUTPUT_OPEN:
320 	case CHAN_OUTPUT_WAIT_DRAIN:
321 		chan_shutdown_write(c);
322 		chan_set_ostate(c, CHAN_OUTPUT_CLOSED);
323 		break;
324 	default:
325 		error("channel %d: chan_write_failed for ostate %d",
326 		    c->self, c->ostate);
327 		break;
328 	}
329 }
330 static void
331 chan_send_eof2(Channel *c)
332 {
333 	debug2("channel %d: send eof", c->self);
334 	switch (c->istate) {
335 	case CHAN_INPUT_WAIT_DRAIN:
336 		packet_start(SSH2_MSG_CHANNEL_EOF);
337 		packet_put_int(c->remote_id);
338 		packet_send();
339 		c->flags |= CHAN_EOF_SENT;
340 		break;
341 	default:
342 		error("channel %d: cannot send eof for istate %d",
343 		    c->self, c->istate);
344 		break;
345 	}
346 }
347 static void
348 chan_send_close2(Channel *c)
349 {
350 	debug2("channel %d: send close", c->self);
351 	if (c->ostate != CHAN_OUTPUT_CLOSED ||
352 	    c->istate != CHAN_INPUT_CLOSED) {
353 		error("channel %d: cannot send close for istate/ostate %d/%d",
354 		    c->self, c->istate, c->ostate);
355 	} else if (c->flags & CHAN_CLOSE_SENT) {
356 		error("channel %d: already sent close", c->self);
357 	} else {
358 		packet_start(SSH2_MSG_CHANNEL_CLOSE);
359 		packet_put_int(c->remote_id);
360 		packet_send();
361 		c->flags |= CHAN_CLOSE_SENT;
362 	}
363 }
364 
365 /* shared */
366 
367 void
368 chan_rcvd_ieof(Channel *c)
369 {
370 	if (compat20)
371 		chan_rcvd_eof2(c);
372 	else
373 		chan_rcvd_ieof1(c);
374 	if (c->ostate == CHAN_OUTPUT_WAIT_DRAIN &&
375 	    buffer_len(&c->output) == 0 &&
376 	    !CHANNEL_EFD_OUTPUT_ACTIVE(c))
377 		chan_obuf_empty(c);
378 }
379 void
380 chan_rcvd_oclose(Channel *c)
381 {
382 	if (compat20)
383 		chan_rcvd_close2(c);
384 	else
385 		chan_rcvd_oclose1(c);
386 }
387 void
388 chan_write_failed(Channel *c)
389 {
390 	if (compat20)
391 		chan_write_failed2(c);
392 	else
393 		chan_write_failed1(c);
394 }
395 
396 void
397 chan_mark_dead(Channel *c)
398 {
399 	c->type = SSH_CHANNEL_ZOMBIE;
400 }
401 
402 int
403 chan_is_dead(Channel *c, int do_send)
404 {
405 	if (c->type == SSH_CHANNEL_ZOMBIE) {
406 		debug2("channel %d: zombie", c->self);
407 		return 1;
408 	}
409 	if (c->istate != CHAN_INPUT_CLOSED || c->ostate != CHAN_OUTPUT_CLOSED)
410 		return 0;
411 	if (!compat20) {
412 		debug2("channel %d: is dead", c->self);
413 		return 1;
414 	}
415 	if ((datafellows & SSH_BUG_EXTEOF) &&
416 	    c->extended_usage == CHAN_EXTENDED_WRITE &&
417 	    c->efd != -1 &&
418 	    buffer_len(&c->extended) > 0) {
419 		debug2("channel %d: active efd: %d len %d",
420 		    c->self, c->efd, buffer_len(&c->extended));
421 		return 0;
422 	}
423 	if (!(c->flags & CHAN_CLOSE_SENT)) {
424 		if (do_send) {
425 			chan_send_close2(c);
426 		} else {
427 			/* channel would be dead if we sent a close */
428 			if (c->flags & CHAN_CLOSE_RCVD) {
429 				debug2("channel %d: almost dead",
430 				    c->self);
431 				return 1;
432 			}
433 		}
434 	}
435 	if ((c->flags & CHAN_CLOSE_SENT) &&
436 	    (c->flags & CHAN_CLOSE_RCVD)) {
437 		debug2("channel %d: is dead", c->self);
438 		return 1;
439 	}
440 	return 0;
441 }
442 
443 /* helper */
444 static void
445 chan_shutdown_write(Channel *c)
446 {
447 	buffer_clear(&c->output);
448 	if (compat20 && c->type == SSH_CHANNEL_LARVAL)
449 		return;
450 	/* shutdown failure is allowed if write failed already */
451 	debug2("channel %d: close_write", c->self);
452 	if (c->sock != -1) {
453 		if (shutdown(c->sock, SHUT_WR) < 0)
454 			debug2("channel %d: chan_shutdown_write: "
455 			    "shutdown() failed for fd%d: %.100s",
456 			    c->self, c->sock, strerror(errno));
457 	} else {
458 		if (channel_close_fd(&c->wfd) < 0)
459 			logit("channel %d: chan_shutdown_write: "
460 			    "close() failed for fd%d: %.100s",
461 			    c->self, c->wfd, strerror(errno));
462 	}
463 }
464 static void
465 chan_shutdown_read(Channel *c)
466 {
467 	if (compat20 && c->type == SSH_CHANNEL_LARVAL)
468 		return;
469 	debug2("channel %d: close_read", c->self);
470 	if (c->sock != -1) {
471 		if (shutdown(c->sock, SHUT_RD) < 0)
472 			error("channel %d: chan_shutdown_read: "
473 			    "shutdown() failed for fd%d [i%d o%d]: %.100s",
474 			    c->self, c->sock, c->istate, c->ostate,
475 			    strerror(errno));
476 	} else {
477 		if (channel_close_fd(&c->rfd) < 0)
478 			logit("channel %d: chan_shutdown_read: "
479 			    "close() failed for fd%d: %.100s",
480 			    c->self, c->rfd, strerror(errno));
481 	}
482 }
483