Annotation of src/usr.bin/ssh/nchan.c, Revision 1.38
1.7 markus 1: /*
1.30 markus 2: * Copyright (c) 1999, 2000, 2001 Markus Friedl. All rights reserved.
1.7 markus 3: *
4: * Redistribution and use in source and binary forms, with or without
5: * modification, are permitted provided that the following conditions
6: * are met:
7: * 1. Redistributions of source code must retain the above copyright
8: * notice, this list of conditions and the following disclaimer.
9: * 2. Redistributions in binary form must reproduce the above copyright
10: * notice, this list of conditions and the following disclaimer in the
11: * documentation and/or other materials provided with the distribution.
12: *
13: * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
14: * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
15: * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
16: * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
17: * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
18: * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
19: * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
20: * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
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.
23: */
24:
1.1 markus 25: #include "includes.h"
1.38 ! markus 26: RCSID("$OpenBSD: nchan.c,v 1.37 2002/01/13 21:31:20 markus Exp $");
1.1 markus 27:
1.22 markus 28: #include "ssh1.h"
29: #include "ssh2.h"
1.1 markus 30: #include "buffer.h"
1.3 markus 31: #include "packet.h"
1.1 markus 32: #include "channels.h"
1.13 markus 33: #include "compat.h"
1.22 markus 34: #include "log.h"
1.3 markus 35:
1.28 markus 36: /*
37: * SSH Protocol 1.5 aka New Channel Protocol
38: * Thanks to Martina, Axel and everyone who left Erlangen, leaving me bored.
39: * Written by Markus Friedl in October 1999
40: *
41: * Protocol versions 1.3 and 1.5 differ in the handshake protocol used for the
42: * tear down of channels:
43: *
44: * 1.3: strict request-ack-protocol:
45: * CLOSE ->
46: * <- CLOSE_CONFIRM
47: *
48: * 1.5: uses variations of:
49: * IEOF ->
50: * <- OCLOSE
51: * <- IEOF
52: * OCLOSE ->
53: * i.e. both sides have to close the channel
54: *
55: * 2.0: the EOF messages are optional
56: *
57: * See the debugging output from 'ssh -v' and 'sshd -d' of
58: * ssh-1.2.27 as an example.
59: *
60: */
61:
1.13 markus 62: /* functions manipulating channel states */
1.3 markus 63: /*
1.6 markus 64: * EVENTS update channel input/output states execute ACTIONS
1.3 markus 65: */
1.13 markus 66: /* events concerning the INPUT from socket for channel (istate) */
67: chan_event_fn *chan_rcvd_oclose = NULL;
68: chan_event_fn *chan_read_failed = NULL;
69: chan_event_fn *chan_ibuf_empty = NULL;
70: /* events concerning the OUTPUT from channel for socket (ostate) */
71: chan_event_fn *chan_rcvd_ieof = NULL;
72: chan_event_fn *chan_write_failed = NULL;
73: chan_event_fn *chan_obuf_empty = NULL;
74: /*
75: * ACTIONS: should never update the channel states
76: */
1.29 itojun 77: static void chan_send_ieof1(Channel *);
78: static void chan_send_oclose1(Channel *);
79: static void chan_send_close2(Channel *);
80: static void chan_send_eof2(Channel *);
1.13 markus 81:
82: /* helper */
1.29 itojun 83: static void chan_shutdown_write(Channel *);
84: static void chan_shutdown_read(Channel *);
1.13 markus 85:
1.37 markus 86: static char *ostates[] = { "open", "drain", "wait_ieof", "closed" };
87: static char *istates[] = { "open", "drain", "wait_oclose", "closed" };
88:
89: static void
90: chan_set_istate(Channel *c, u_int next)
91: {
92: if (c->istate > CHAN_INPUT_CLOSED || next > CHAN_INPUT_CLOSED)
93: fatal("chan_set_istate: bad state %d -> %d", c->istate, next);
94: debug("channel %d: input %s -> %s", c->self, istates[c->istate],
95: istates[next]);
96: c->istate = next;
97: }
98: static void
99: chan_set_ostate(Channel *c, u_int next)
100: {
101: if (c->ostate > CHAN_OUTPUT_CLOSED || next > CHAN_OUTPUT_CLOSED)
102: fatal("chan_set_ostate: bad state %d -> %d", c->ostate, next);
103: debug("channel %d: output %s -> %s", c->self, ostates[c->ostate],
104: ostates[next]);
105: c->ostate = next;
106: }
107:
1.13 markus 108: /*
109: * SSH1 specific implementation of event functions
110: */
1.6 markus 111:
1.13 markus 112: static void
113: chan_rcvd_oclose1(Channel *c)
1.6 markus 114: {
1.13 markus 115: debug("channel %d: rcvd oclose", c->self);
1.6 markus 116: switch (c->istate) {
1.3 markus 117: case CHAN_INPUT_WAIT_OCLOSE:
1.37 markus 118: chan_set_istate(c, CHAN_INPUT_CLOSED);
1.3 markus 119: break;
120: case CHAN_INPUT_OPEN:
121: chan_shutdown_read(c);
1.13 markus 122: chan_send_ieof1(c);
1.37 markus 123: chan_set_istate(c, CHAN_INPUT_CLOSED);
1.10 markus 124: break;
125: case CHAN_INPUT_WAIT_DRAIN:
126: /* both local read_failed and remote write_failed */
1.13 markus 127: chan_send_ieof1(c);
1.37 markus 128: chan_set_istate(c, CHAN_INPUT_CLOSED);
1.3 markus 129: break;
130: default:
1.28 markus 131: error("channel %d: protocol error: rcvd_oclose for istate %d",
1.13 markus 132: c->self, c->istate);
1.10 markus 133: return;
1.3 markus 134: }
1.1 markus 135: }
1.13 markus 136: static void
137: chan_read_failed_12(Channel *c)
1.6 markus 138: {
1.13 markus 139: debug("channel %d: read failed", c->self);
1.6 markus 140: switch (c->istate) {
1.3 markus 141: case CHAN_INPUT_OPEN:
142: chan_shutdown_read(c);
1.37 markus 143: chan_set_istate(c, CHAN_INPUT_WAIT_DRAIN);
1.3 markus 144: break;
145: default:
1.28 markus 146: error("channel %d: chan_read_failed for istate %d",
1.13 markus 147: c->self, c->istate);
1.3 markus 148: break;
1.1 markus 149: }
150: }
1.13 markus 151: static void
152: chan_ibuf_empty1(Channel *c)
1.6 markus 153: {
1.13 markus 154: debug("channel %d: ibuf empty", c->self);
1.6 markus 155: if (buffer_len(&c->input)) {
1.28 markus 156: error("channel %d: chan_ibuf_empty for non empty buffer",
1.13 markus 157: c->self);
1.3 markus 158: return;
159: }
1.6 markus 160: switch (c->istate) {
1.3 markus 161: case CHAN_INPUT_WAIT_DRAIN:
1.13 markus 162: chan_send_ieof1(c);
1.37 markus 163: chan_set_istate(c, CHAN_INPUT_WAIT_OCLOSE);
1.3 markus 164: break;
165: default:
1.28 markus 166: error("channel %d: chan_ibuf_empty for istate %d",
1.13 markus 167: c->self, c->istate);
1.3 markus 168: break;
1.1 markus 169: }
170: }
1.13 markus 171: static void
172: chan_rcvd_ieof1(Channel *c)
1.6 markus 173: {
1.13 markus 174: debug("channel %d: rcvd ieof", c->self);
1.6 markus 175: switch (c->ostate) {
1.3 markus 176: case CHAN_OUTPUT_OPEN:
1.37 markus 177: chan_set_ostate(c, CHAN_OUTPUT_WAIT_DRAIN);
1.3 markus 178: break;
179: case CHAN_OUTPUT_WAIT_IEOF:
1.37 markus 180: chan_set_ostate(c, CHAN_OUTPUT_CLOSED);
1.3 markus 181: break;
182: default:
1.28 markus 183: error("channel %d: protocol error: rcvd_ieof for ostate %d",
1.13 markus 184: c->self, c->ostate);
1.3 markus 185: break;
186: }
187: }
1.13 markus 188: static void
189: chan_write_failed1(Channel *c)
1.6 markus 190: {
1.13 markus 191: debug("channel %d: write failed", c->self);
1.6 markus 192: switch (c->ostate) {
1.3 markus 193: case CHAN_OUTPUT_OPEN:
1.38 ! markus 194: chan_shutdown_write(c);
1.13 markus 195: chan_send_oclose1(c);
1.37 markus 196: chan_set_ostate(c, CHAN_OUTPUT_WAIT_IEOF);
1.3 markus 197: break;
198: case CHAN_OUTPUT_WAIT_DRAIN:
1.38 ! markus 199: chan_shutdown_write(c);
1.13 markus 200: chan_send_oclose1(c);
1.37 markus 201: chan_set_ostate(c, CHAN_OUTPUT_CLOSED);
1.3 markus 202: break;
203: default:
1.28 markus 204: error("channel %d: chan_write_failed for ostate %d",
1.13 markus 205: c->self, c->ostate);
1.3 markus 206: break;
207: }
208: }
1.13 markus 209: static void
210: chan_obuf_empty1(Channel *c)
1.6 markus 211: {
1.13 markus 212: debug("channel %d: obuf empty", c->self);
1.6 markus 213: if (buffer_len(&c->output)) {
1.28 markus 214: error("channel %d: chan_obuf_empty for non empty buffer",
1.13 markus 215: c->self);
1.3 markus 216: return;
217: }
1.6 markus 218: switch (c->ostate) {
1.3 markus 219: case CHAN_OUTPUT_WAIT_DRAIN:
1.38 ! markus 220: chan_shutdown_write(c);
1.13 markus 221: chan_send_oclose1(c);
1.37 markus 222: chan_set_ostate(c, CHAN_OUTPUT_CLOSED);
1.3 markus 223: break;
224: default:
1.28 markus 225: error("channel %d: internal error: obuf_empty for ostate %d",
1.13 markus 226: c->self, c->ostate);
1.3 markus 227: break;
228: }
229: }
230: static void
1.13 markus 231: chan_send_ieof1(Channel *c)
1.6 markus 232: {
1.13 markus 233: debug("channel %d: send ieof", c->self);
1.6 markus 234: switch (c->istate) {
1.3 markus 235: case CHAN_INPUT_OPEN:
236: case CHAN_INPUT_WAIT_DRAIN:
237: packet_start(SSH_MSG_CHANNEL_INPUT_EOF);
238: packet_put_int(c->remote_id);
239: packet_send();
240: break;
241: default:
1.28 markus 242: error("channel %d: cannot send ieof for istate %d",
1.13 markus 243: c->self, c->istate);
1.3 markus 244: break;
1.1 markus 245: }
246: }
1.3 markus 247: static void
1.13 markus 248: chan_send_oclose1(Channel *c)
1.6 markus 249: {
1.13 markus 250: debug("channel %d: send oclose", c->self);
1.6 markus 251: switch (c->ostate) {
1.3 markus 252: case CHAN_OUTPUT_OPEN:
253: case CHAN_OUTPUT_WAIT_DRAIN:
1.34 markus 254: buffer_clear(&c->output);
1.3 markus 255: packet_start(SSH_MSG_CHANNEL_OUTPUT_CLOSE);
256: packet_put_int(c->remote_id);
257: packet_send();
258: break;
259: default:
1.28 markus 260: error("channel %d: cannot send oclose for ostate %d",
1.33 deraadt 261: c->self, c->ostate);
1.3 markus 262: break;
1.1 markus 263: }
264: }
1.6 markus 265:
1.13 markus 266: /*
267: * the same for SSH2
268: */
269: static void
270: chan_rcvd_oclose2(Channel *c)
271: {
272: debug("channel %d: rcvd close", c->self);
273: if (c->flags & CHAN_CLOSE_RCVD)
274: error("channel %d: protocol error: close rcvd twice", c->self);
275: c->flags |= CHAN_CLOSE_RCVD;
276: if (c->type == SSH_CHANNEL_LARVAL) {
277: /* tear down larval channels immediately */
1.37 markus 278: chan_set_ostate(c, CHAN_OUTPUT_CLOSED);
279: chan_set_istate(c, CHAN_INPUT_CLOSED);
1.13 markus 280: return;
281: }
282: switch (c->ostate) {
283: case CHAN_OUTPUT_OPEN:
1.28 markus 284: /*
285: * wait until a data from the channel is consumed if a CLOSE
286: * is received
287: */
1.37 markus 288: chan_set_ostate(c, CHAN_OUTPUT_WAIT_DRAIN);
1.13 markus 289: break;
290: }
291: switch (c->istate) {
292: case CHAN_INPUT_OPEN:
293: chan_shutdown_read(c);
294: break;
295: case CHAN_INPUT_WAIT_DRAIN:
296: chan_send_eof2(c);
297: break;
298: }
1.37 markus 299: chan_set_istate(c, CHAN_INPUT_CLOSED);
1.13 markus 300: }
301: static void
302: chan_ibuf_empty2(Channel *c)
303: {
304: debug("channel %d: ibuf empty", c->self);
305: if (buffer_len(&c->input)) {
1.28 markus 306: error("channel %d: chan_ibuf_empty for non empty buffer",
1.33 deraadt 307: c->self);
1.13 markus 308: return;
309: }
310: switch (c->istate) {
311: case CHAN_INPUT_WAIT_DRAIN:
312: if (!(c->flags & CHAN_CLOSE_SENT))
313: chan_send_eof2(c);
1.37 markus 314: chan_set_istate(c, CHAN_INPUT_CLOSED);
1.13 markus 315: break;
316: default:
1.28 markus 317: error("channel %d: chan_ibuf_empty for istate %d",
1.33 deraadt 318: c->self, c->istate);
1.13 markus 319: break;
320: }
321: }
322: static void
323: chan_rcvd_ieof2(Channel *c)
324: {
325: debug("channel %d: rcvd eof", c->self);
1.37 markus 326: if (c->ostate == CHAN_OUTPUT_OPEN)
327: chan_set_ostate(c, CHAN_OUTPUT_WAIT_DRAIN);
1.13 markus 328: }
329: static void
330: chan_write_failed2(Channel *c)
331: {
332: debug("channel %d: write failed", c->self);
333: switch (c->ostate) {
334: case CHAN_OUTPUT_OPEN:
1.15 markus 335: chan_shutdown_write(c); /* ?? */
1.37 markus 336: chan_set_ostate(c, CHAN_OUTPUT_CLOSED);
1.13 markus 337: break;
338: case CHAN_OUTPUT_WAIT_DRAIN:
339: chan_shutdown_write(c);
1.37 markus 340: chan_set_ostate(c, CHAN_OUTPUT_CLOSED);
1.13 markus 341: break;
342: default:
1.28 markus 343: error("channel %d: chan_write_failed for ostate %d",
1.13 markus 344: c->self, c->ostate);
345: break;
346: }
347: }
348: static void
349: chan_obuf_empty2(Channel *c)
350: {
351: debug("channel %d: obuf empty", c->self);
352: if (buffer_len(&c->output)) {
1.28 markus 353: error("channel %d: chan_obuf_empty for non empty buffer",
1.13 markus 354: c->self);
355: return;
356: }
357: switch (c->ostate) {
358: case CHAN_OUTPUT_WAIT_DRAIN:
359: chan_shutdown_write(c);
1.37 markus 360: chan_set_ostate(c, CHAN_OUTPUT_CLOSED);
1.13 markus 361: break;
362: default:
1.28 markus 363: error("channel %d: chan_obuf_empty for ostate %d",
1.13 markus 364: c->self, c->ostate);
365: break;
366: }
367: }
1.3 markus 368: static void
1.13 markus 369: chan_send_eof2(Channel *c)
1.6 markus 370: {
1.13 markus 371: debug("channel %d: send eof", c->self);
372: switch (c->istate) {
373: case CHAN_INPUT_WAIT_DRAIN:
374: packet_start(SSH2_MSG_CHANNEL_EOF);
375: packet_put_int(c->remote_id);
376: packet_send();
377: break;
378: default:
1.28 markus 379: error("channel %d: cannot send eof for istate %d",
1.13 markus 380: c->self, c->istate);
381: break;
382: }
1.1 markus 383: }
1.3 markus 384: static void
1.13 markus 385: chan_send_close2(Channel *c)
1.6 markus 386: {
1.13 markus 387: debug("channel %d: send close", c->self);
388: if (c->ostate != CHAN_OUTPUT_CLOSED ||
389: c->istate != CHAN_INPUT_CLOSED) {
1.28 markus 390: error("channel %d: cannot send close for istate/ostate %d/%d",
1.13 markus 391: c->self, c->istate, c->ostate);
392: } else if (c->flags & CHAN_CLOSE_SENT) {
1.28 markus 393: error("channel %d: already sent close", c->self);
1.13 markus 394: } else {
395: packet_start(SSH2_MSG_CHANNEL_CLOSE);
396: packet_put_int(c->remote_id);
397: packet_send();
398: c->flags |= CHAN_CLOSE_SENT;
399: }
1.1 markus 400: }
1.23 markus 401:
402: /* shared */
403:
1.24 markus 404: void
405: chan_mark_dead(Channel *c)
406: {
1.26 markus 407: c->type = SSH_CHANNEL_ZOMBIE;
1.24 markus 408: }
409:
1.23 markus 410: int
1.32 markus 411: chan_is_dead(Channel *c, int send)
1.6 markus 412: {
1.26 markus 413: if (c->type == SSH_CHANNEL_ZOMBIE) {
414: debug("channel %d: zombie", c->self);
1.24 markus 415: return 1;
1.26 markus 416: }
1.23 markus 417: if (c->istate != CHAN_INPUT_CLOSED || c->ostate != CHAN_OUTPUT_CLOSED)
418: return 0;
419: if (!compat20) {
420: debug("channel %d: is dead", c->self);
421: return 1;
422: }
423: /*
424: * we have to delay the close message if the efd (for stderr) is
425: * still active
426: */
427: if (((c->extended_usage != CHAN_EXTENDED_IGNORE) &&
428: buffer_len(&c->extended) > 0)
429: #if 0
430: || ((c->extended_usage == CHAN_EXTENDED_READ) &&
431: c->efd != -1)
432: #endif
433: ) {
434: debug2("channel %d: active efd: %d len %d type %s",
435: c->self, c->efd, buffer_len(&c->extended),
436: c->extended_usage==CHAN_EXTENDED_READ ?
1.33 deraadt 437: "read": "write");
1.23 markus 438: } else {
1.13 markus 439: if (!(c->flags & CHAN_CLOSE_SENT)) {
1.32 markus 440: if (send) {
441: chan_send_close2(c);
442: } else {
443: /* channel would be dead if we sent a close */
444: if (c->flags & CHAN_CLOSE_RCVD) {
445: debug("channel %d: almost dead",
446: c->self);
447: return 1;
448: }
449: }
1.13 markus 450: }
1.14 markus 451: if ((c->flags & CHAN_CLOSE_SENT) &&
1.13 markus 452: (c->flags & CHAN_CLOSE_RCVD)) {
1.23 markus 453: debug("channel %d: is dead", c->self);
454: return 1;
1.14 markus 455: }
1.1 markus 456: }
1.23 markus 457: return 0;
1.3 markus 458: }
1.13 markus 459:
1.3 markus 460: void
1.6 markus 461: chan_init_iostates(Channel *c)
462: {
463: c->ostate = CHAN_OUTPUT_OPEN;
464: c->istate = CHAN_INPUT_OPEN;
1.13 markus 465: c->flags = 0;
466: }
467:
468: /* init */
469: void
470: chan_init(void)
471: {
472: if (compat20) {
473: chan_rcvd_oclose = chan_rcvd_oclose2;
474: chan_read_failed = chan_read_failed_12;
475: chan_ibuf_empty = chan_ibuf_empty2;
476:
477: chan_rcvd_ieof = chan_rcvd_ieof2;
478: chan_write_failed = chan_write_failed2;
479: chan_obuf_empty = chan_obuf_empty2;
480: } else {
481: chan_rcvd_oclose = chan_rcvd_oclose1;
482: chan_read_failed = chan_read_failed_12;
483: chan_ibuf_empty = chan_ibuf_empty1;
484:
485: chan_rcvd_ieof = chan_rcvd_ieof1;
486: chan_write_failed = chan_write_failed1;
487: chan_obuf_empty = chan_obuf_empty1;
488: }
489: }
490:
491: /* helper */
492: static void
493: chan_shutdown_write(Channel *c)
494: {
1.34 markus 495: buffer_clear(&c->output);
1.13 markus 496: if (compat20 && c->type == SSH_CHANNEL_LARVAL)
497: return;
498: /* shutdown failure is allowed if write failed already */
499: debug("channel %d: close_write", c->self);
500: if (c->sock != -1) {
501: if (shutdown(c->sock, SHUT_WR) < 0)
1.28 markus 502: debug("channel %d: chan_shutdown_write: "
503: "shutdown() failed for fd%d: %.100s",
1.13 markus 504: c->self, c->sock, strerror(errno));
505: } else {
1.31 markus 506: if (channel_close_fd(&c->wfd) < 0)
1.28 markus 507: log("channel %d: chan_shutdown_write: "
508: "close() failed for fd%d: %.100s",
1.13 markus 509: c->self, c->wfd, strerror(errno));
510: }
511: }
512: static void
513: chan_shutdown_read(Channel *c)
514: {
515: if (compat20 && c->type == SSH_CHANNEL_LARVAL)
516: return;
517: debug("channel %d: close_read", c->self);
518: if (c->sock != -1) {
519: if (shutdown(c->sock, SHUT_RD) < 0)
1.28 markus 520: error("channel %d: chan_shutdown_read: "
521: "shutdown() failed for fd%d [i%d o%d]: %.100s",
522: c->self, c->sock, c->istate, c->ostate,
523: strerror(errno));
1.13 markus 524: } else {
1.31 markus 525: if (channel_close_fd(&c->rfd) < 0)
1.28 markus 526: log("channel %d: chan_shutdown_read: "
527: "close() failed for fd%d: %.100s",
1.13 markus 528: c->self, c->rfd, strerror(errno));
529: }
1.1 markus 530: }