Annotation of src/usr.bin/ssh/mux.c, Revision 1.13
1.13 ! djm 1: /* $OpenBSD: mux.c,v 1.12 2010/01/27 13:26:17 djm Exp $ */
1.1 djm 2: /*
3: * Copyright (c) 2002-2008 Damien Miller <djm@openbsd.org>
4: *
5: * Permission to use, copy, modify, and distribute this software for any
6: * purpose with or without fee is hereby granted, provided that the above
7: * copyright notice and this permission notice appear in all copies.
8: *
9: * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
10: * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
11: * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
12: * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
13: * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
14: * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
15: * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
16: */
17:
18: /* ssh session multiplexing support */
19:
1.2 djm 20: /*
21: * TODO:
1.10 djm 22: * - Better signalling from master to slave, especially passing of
1.2 djm 23: * error messages
1.10 djm 24: * - Better fall-back from mux slave error to new connection.
25: * - ExitOnForwardingFailure
26: * - Maybe extension mechanisms for multi-X11/multi-agent forwarding
27: * - Support ~^Z in mux slaves.
28: * - Inspect or control sessions in master.
29: * - If we ever support the "signal" channel request, send signals on
30: * sessions in master.
1.2 djm 31: */
32:
1.1 djm 33: #include <sys/types.h>
34: #include <sys/param.h>
35: #include <sys/queue.h>
36: #include <sys/stat.h>
37: #include <sys/socket.h>
38: #include <sys/un.h>
39:
40: #include <errno.h>
41: #include <fcntl.h>
1.10 djm 42: #include <poll.h>
1.1 djm 43: #include <signal.h>
44: #include <stdarg.h>
45: #include <stddef.h>
46: #include <stdlib.h>
47: #include <stdio.h>
48: #include <string.h>
49: #include <unistd.h>
50: #include <util.h>
51: #include <paths.h>
52:
1.10 djm 53: #include "atomicio.h"
1.1 djm 54: #include "xmalloc.h"
55: #include "log.h"
56: #include "ssh.h"
57: #include "pathnames.h"
58: #include "misc.h"
59: #include "match.h"
60: #include "buffer.h"
61: #include "channels.h"
62: #include "msg.h"
63: #include "packet.h"
64: #include "monitor_fdpass.h"
65: #include "sshpty.h"
66: #include "key.h"
67: #include "readconf.h"
68: #include "clientloop.h"
69:
70: /* from ssh.c */
71: extern int tty_flag;
1.9 djm 72: extern int force_tty_flag;
1.1 djm 73: extern Options options;
74: extern int stdin_null_flag;
75: extern char *host;
1.8 dtucker 76: extern int subsystem_flag;
1.1 djm 77: extern Buffer command;
1.10 djm 78: extern volatile sig_atomic_t quit_pending;
79: extern char *stdio_forward_host;
80: extern int stdio_forward_port;
1.1 djm 81:
1.2 djm 82: /* Context for session open confirmation callback */
83: struct mux_session_confirm_ctx {
1.10 djm 84: u_int want_tty;
85: u_int want_subsys;
86: u_int want_x_fwd;
87: u_int want_agent_fwd;
1.2 djm 88: Buffer cmd;
89: char *term;
90: struct termios tio;
91: char **env;
92: };
93:
1.1 djm 94: /* fd to control socket */
95: int muxserver_sock = -1;
96:
1.10 djm 97: /* client request id */
98: u_int muxclient_request_id = 0;
99:
1.1 djm 100: /* Multiplexing control command */
101: u_int muxclient_command = 0;
102:
103: /* Set when signalled. */
104: static volatile sig_atomic_t muxclient_terminate = 0;
105:
106: /* PID of multiplex server */
107: static u_int muxserver_pid = 0;
108:
1.10 djm 109: static Channel *mux_listener_channel = NULL;
110:
111: struct mux_master_state {
112: int hello_rcvd;
113: };
1.1 djm 114:
1.10 djm 115: /* mux protocol messages */
116: #define MUX_MSG_HELLO 0x00000001
117: #define MUX_C_NEW_SESSION 0x10000002
118: #define MUX_C_ALIVE_CHECK 0x10000004
119: #define MUX_C_TERMINATE 0x10000005
120: #define MUX_C_OPEN_FWD 0x10000006
121: #define MUX_C_CLOSE_FWD 0x10000007
122: #define MUX_C_NEW_STDIO_FWD 0x10000008
123: #define MUX_S_OK 0x80000001
124: #define MUX_S_PERMISSION_DENIED 0x80000002
125: #define MUX_S_FAILURE 0x80000003
126: #define MUX_S_EXIT_MESSAGE 0x80000004
127: #define MUX_S_ALIVE 0x80000005
128: #define MUX_S_SESSION_OPENED 0x80000006
129:
130: /* type codes for MUX_C_OPEN_FWD and MUX_C_CLOSE_FWD */
131: #define MUX_FWD_LOCAL 1
132: #define MUX_FWD_REMOTE 2
133: #define MUX_FWD_DYNAMIC 3
134:
135: static void mux_session_confirm(int, void *);
136:
137: static int process_mux_master_hello(u_int, Channel *, Buffer *, Buffer *);
138: static int process_mux_new_session(u_int, Channel *, Buffer *, Buffer *);
139: static int process_mux_alive_check(u_int, Channel *, Buffer *, Buffer *);
140: static int process_mux_terminate(u_int, Channel *, Buffer *, Buffer *);
141: static int process_mux_open_fwd(u_int, Channel *, Buffer *, Buffer *);
142: static int process_mux_close_fwd(u_int, Channel *, Buffer *, Buffer *);
143: static int process_mux_stdio_fwd(u_int, Channel *, Buffer *, Buffer *);
144:
145: static const struct {
146: u_int type;
147: int (*handler)(u_int, Channel *, Buffer *, Buffer *);
148: } mux_master_handlers[] = {
149: { MUX_MSG_HELLO, process_mux_master_hello },
150: { MUX_C_NEW_SESSION, process_mux_new_session },
151: { MUX_C_ALIVE_CHECK, process_mux_alive_check },
152: { MUX_C_TERMINATE, process_mux_terminate },
153: { MUX_C_OPEN_FWD, process_mux_open_fwd },
154: { MUX_C_CLOSE_FWD, process_mux_close_fwd },
155: { MUX_C_NEW_STDIO_FWD, process_mux_stdio_fwd },
156: { 0, NULL }
157: };
1.1 djm 158:
1.10 djm 159: /* Cleanup callback fired on closure of mux slave _session_ channel */
160: /* ARGSUSED */
161: static void
162: mux_master_session_cleanup_cb(int cid, void *unused)
1.1 djm 163: {
1.10 djm 164: Channel *cc, *c = channel_by_id(cid);
1.1 djm 165:
1.10 djm 166: debug3("%s: entering for channel %d", __func__, cid);
167: if (c == NULL)
168: fatal("%s: channel_by_id(%i) == NULL", __func__, cid);
169: if (c->ctl_chan != -1) {
170: if ((cc = channel_by_id(c->ctl_chan)) == NULL)
171: fatal("%s: channel %d missing control channel %d",
172: __func__, c->self, c->ctl_chan);
173: c->ctl_chan = -1;
174: cc->remote_id = -1;
175: chan_rcvd_oclose(cc);
1.1 djm 176: }
1.10 djm 177: channel_cancel_cleanup(c->self);
1.1 djm 178: }
179:
1.10 djm 180: /* Cleanup callback fired on closure of mux slave _control_ channel */
181: /* ARGSUSED */
1.1 djm 182: static void
1.10 djm 183: mux_master_control_cleanup_cb(int cid, void *unused)
1.1 djm 184: {
1.10 djm 185: Channel *sc, *c = channel_by_id(cid);
1.1 djm 186:
1.10 djm 187: debug3("%s: entering for channel %d", __func__, cid);
188: if (c == NULL)
189: fatal("%s: channel_by_id(%i) == NULL", __func__, cid);
190: if (c->remote_id != -1) {
191: if ((sc = channel_by_id(c->remote_id)) == NULL)
192: debug2("%s: channel %d n session channel %d",
193: __func__, c->self, c->remote_id);
194: c->remote_id = -1;
195: sc->ctl_chan = -1;
1.12 djm 196: if (sc->type != SSH_CHANNEL_OPEN) {
197: debug2("%s: channel %d: not open", __func__, sc->self);
1.13 ! djm 198: chan_mark_dead(sc);
1.12 djm 199: } else {
200: chan_read_failed(sc);
201: chan_write_failed(sc);
202: }
1.1 djm 203: }
1.10 djm 204: channel_cancel_cleanup(c->self);
1.1 djm 205: }
206:
1.10 djm 207: /* Check mux client environment variables before passing them to mux master. */
208: static int
209: env_permitted(char *env)
1.1 djm 210: {
1.10 djm 211: int i, ret;
212: char name[1024], *cp;
1.1 djm 213:
1.10 djm 214: if ((cp = strchr(env, '=')) == NULL || cp == env)
1.1 djm 215: return 0;
1.10 djm 216: ret = snprintf(name, sizeof(name), "%.*s", (int)(cp - env), env);
217: if (ret <= 0 || (size_t)ret >= sizeof(name)) {
218: error("env_permitted: name '%.100s...' too long", env);
1.1 djm 219: return 0;
220: }
221:
1.10 djm 222: for (i = 0; i < options.num_send_env; i++)
223: if (match_pattern(name, options.send_env[i]))
224: return 1;
1.1 djm 225:
1.10 djm 226: return 0;
227: }
1.1 djm 228:
1.10 djm 229: /* Mux master protocol message handlers */
1.1 djm 230:
1.10 djm 231: static int
232: process_mux_master_hello(u_int rid, Channel *c, Buffer *m, Buffer *r)
233: {
234: u_int ver;
235: struct mux_master_state *state = (struct mux_master_state *)c->mux_ctx;
1.1 djm 236:
1.10 djm 237: if (state == NULL)
238: fatal("%s: channel %d: c->mux_ctx == NULL", __func__, c->self);
239: if (state->hello_rcvd) {
240: error("%s: HELLO received twice", __func__);
241: return -1;
242: }
243: if (buffer_get_int_ret(&ver, m) != 0) {
244: malf:
245: error("%s: malformed message", __func__);
246: return -1;
247: }
248: if (ver != SSHMUX_VER) {
249: error("Unsupported multiplexing protocol version %d "
250: "(expected %d)", ver, SSHMUX_VER);
251: return -1;
252: }
253: debug2("%s: channel %d slave version %u", __func__, c->self, ver);
254:
255: /* No extensions are presently defined */
256: while (buffer_len(m) > 0) {
257: char *name = buffer_get_string_ret(m, NULL);
258: char *value = buffer_get_string_ret(m, NULL);
259:
260: if (name == NULL || value == NULL) {
261: if (name != NULL)
262: xfree(name);
263: goto malf;
1.1 djm 264: }
1.10 djm 265: debug2("Unrecognised slave extension \"%s\"", name);
266: xfree(name);
267: xfree(value);
1.1 djm 268: }
1.10 djm 269: state->hello_rcvd = 1;
270: return 0;
271: }
272:
273: static int
274: process_mux_new_session(u_int rid, Channel *c, Buffer *m, Buffer *r)
275: {
276: Channel *nc;
277: struct mux_session_confirm_ctx *cctx;
278: char *reserved, *cmd, *cp;
279: u_int i, j, len, env_len, escape_char, window, packetmax;
280: int new_fd[3];
1.1 djm 281:
282: /* Reply for SSHMUX_COMMAND_OPEN */
1.10 djm 283: cctx = xcalloc(1, sizeof(*cctx));
284: cctx->term = NULL;
1.11 djm 285: cmd = reserved = NULL;
1.10 djm 286: if ((reserved = buffer_get_string_ret(m, NULL)) == NULL ||
287: buffer_get_int_ret(&cctx->want_tty, m) != 0 ||
288: buffer_get_int_ret(&cctx->want_x_fwd, m) != 0 ||
289: buffer_get_int_ret(&cctx->want_agent_fwd, m) != 0 ||
290: buffer_get_int_ret(&cctx->want_subsys, m) != 0 ||
291: buffer_get_int_ret(&escape_char, m) != 0 ||
292: (cctx->term = buffer_get_string_ret(m, &len)) == NULL ||
293: (cmd = buffer_get_string_ret(m, &len)) == NULL) {
294: malf:
1.11 djm 295: if (cmd != NULL)
296: xfree(cmd);
297: if (reserved != NULL)
298: xfree(reserved);
1.10 djm 299: if (cctx->term != NULL)
300: xfree(cctx->term);
301: error("%s: malformed message", __func__);
302: return -1;
1.1 djm 303: }
1.10 djm 304: xfree(reserved);
1.11 djm 305: reserved = NULL;
1.1 djm 306:
1.10 djm 307: cctx->env = NULL;
308: env_len = 0;
309: while (buffer_len(m) > 0) {
310: #define MUX_MAX_ENV_VARS 4096
311: if ((cp = buffer_get_string_ret(m, &len)) == NULL) {
312: xfree(cmd);
313: goto malf;
314: }
315: if (!env_permitted(cp)) {
316: xfree(cp);
317: continue;
318: }
319: cctx->env = xrealloc(cctx->env, env_len + 2,
320: sizeof(*cctx->env));
321: cctx->env[env_len++] = cp;
322: cctx->env[env_len] = NULL;
323: if (env_len > MUX_MAX_ENV_VARS) {
324: error(">%d environment variables received, ignoring "
325: "additional", MUX_MAX_ENV_VARS);
326: break;
327: }
1.1 djm 328: }
329:
1.10 djm 330: debug2("%s: channel %d: request tty %d, X %d, agent %d, subsys %d, "
331: "term \"%s\", cmd \"%s\", env %u", __func__, c->self,
332: cctx->want_tty, cctx->want_x_fwd, cctx->want_agent_fwd,
333: cctx->want_subsys, cctx->term, cmd, env_len);
1.1 djm 334:
335: buffer_init(&cctx->cmd);
336: buffer_append(&cctx->cmd, cmd, strlen(cmd));
337: xfree(cmd);
1.11 djm 338: cmd = NULL;
1.1 djm 339:
340: /* Gather fds from client */
341: for(i = 0; i < 3; i++) {
1.10 djm 342: if ((new_fd[i] = mm_receive_fd(c->sock)) == -1) {
1.1 djm 343: error("%s: failed to receive fd %d from slave",
344: __func__, i);
345: for (j = 0; j < i; j++)
346: close(new_fd[j]);
347: for (j = 0; j < env_len; j++)
348: xfree(cctx->env[j]);
349: if (env_len > 0)
350: xfree(cctx->env);
351: xfree(cctx->term);
352: buffer_free(&cctx->cmd);
353: xfree(cctx);
1.10 djm 354:
355: /* prepare reply */
356: buffer_put_int(r, MUX_S_FAILURE);
357: buffer_put_int(r, rid);
358: buffer_put_cstring(r,
359: "did not receive file descriptors");
360: return -1;
1.1 djm 361: }
362: }
363:
1.10 djm 364: debug3("%s: got fds stdin %d, stdout %d, stderr %d", __func__,
1.1 djm 365: new_fd[0], new_fd[1], new_fd[2]);
366:
1.10 djm 367: /* XXX support multiple child sessions in future */
368: if (c->remote_id != -1) {
369: debug2("%s: session already open", __func__);
370: /* prepare reply */
371: buffer_put_int(r, MUX_S_FAILURE);
372: buffer_put_int(r, rid);
373: buffer_put_cstring(r, "Multiple sessions not supported");
374: cleanup:
1.1 djm 375: close(new_fd[0]);
376: close(new_fd[1]);
377: close(new_fd[2]);
378: xfree(cctx->term);
379: if (env_len != 0) {
380: for (i = 0; i < env_len; i++)
381: xfree(cctx->env[i]);
382: xfree(cctx->env);
383: }
1.10 djm 384: buffer_free(&cctx->cmd);
1.1 djm 385: return 0;
386: }
1.10 djm 387:
388: if (options.control_master == SSHCTL_MASTER_ASK ||
389: options.control_master == SSHCTL_MASTER_AUTO_ASK) {
390: if (!ask_permission("Allow shared connection to %s? ", host)) {
391: debug2("%s: session refused by user", __func__);
392: /* prepare reply */
393: buffer_put_int(r, MUX_S_PERMISSION_DENIED);
394: buffer_put_int(r, rid);
395: buffer_put_cstring(r, "Permission denied");
396: goto cleanup;
397: }
398: }
399:
400: /* Try to pick up ttymodes from client before it goes raw */
401: if (cctx->want_tty && tcgetattr(new_fd[0], &cctx->tio) == -1)
402: error("%s: tcgetattr: %s", __func__, strerror(errno));
1.1 djm 403:
404: /* enable nonblocking unless tty */
405: if (!isatty(new_fd[0]))
406: set_nonblock(new_fd[0]);
407: if (!isatty(new_fd[1]))
408: set_nonblock(new_fd[1]);
409: if (!isatty(new_fd[2]))
410: set_nonblock(new_fd[2]);
411:
412: window = CHAN_SES_WINDOW_DEFAULT;
413: packetmax = CHAN_SES_PACKET_DEFAULT;
414: if (cctx->want_tty) {
415: window >>= 1;
416: packetmax >>= 1;
417: }
1.10 djm 418:
419: nc = channel_new("session", SSH_CHANNEL_OPENING,
1.1 djm 420: new_fd[0], new_fd[1], new_fd[2], window, packetmax,
421: CHAN_EXTENDED_WRITE, "client-session", /*nonblock*/0);
422:
1.10 djm 423: nc->ctl_chan = c->self; /* link session -> control channel */
424: c->remote_id = nc->self; /* link control -> session channel */
425:
1.2 djm 426: if (cctx->want_tty && escape_char != 0xffffffff) {
1.10 djm 427: channel_register_filter(nc->self,
1.2 djm 428: client_simple_escape_filter, NULL,
1.4 djm 429: client_filter_cleanup,
1.2 djm 430: client_new_escape_filter_ctx((int)escape_char));
431: }
1.1 djm 432:
1.10 djm 433: debug2("%s: channel_new: %d linked to control channel %d",
434: __func__, nc->self, nc->ctl_chan);
435:
436: channel_send_open(nc->self);
437: channel_register_open_confirm(nc->self, mux_session_confirm, cctx);
438: channel_register_cleanup(nc->self, mux_master_session_cleanup_cb, 0);
439:
440: /* prepare reply */
441: /* XXX defer until mux_session_confirm() fires */
442: buffer_put_int(r, MUX_S_SESSION_OPENED);
443: buffer_put_int(r, rid);
444: buffer_put_int(r, nc->self);
1.1 djm 445:
446: return 0;
447: }
448:
1.10 djm 449: static int
450: process_mux_alive_check(u_int rid, Channel *c, Buffer *m, Buffer *r)
1.1 djm 451: {
1.10 djm 452: debug2("%s: channel %d: alive check", __func__, c->self);
1.1 djm 453:
1.10 djm 454: /* prepare reply */
455: buffer_put_int(r, MUX_S_ALIVE);
456: buffer_put_int(r, rid);
457: buffer_put_int(r, (u_int)getpid());
1.1 djm 458:
1.10 djm 459: return 0;
1.1 djm 460: }
461:
462: static int
1.10 djm 463: process_mux_terminate(u_int rid, Channel *c, Buffer *m, Buffer *r)
1.1 djm 464: {
1.10 djm 465: debug2("%s: channel %d: terminate request", __func__, c->self);
1.1 djm 466:
1.10 djm 467: if (options.control_master == SSHCTL_MASTER_ASK ||
468: options.control_master == SSHCTL_MASTER_AUTO_ASK) {
469: if (!ask_permission("Terminate shared connection to %s? ",
470: host)) {
471: debug2("%s: termination refused by user", __func__);
472: buffer_put_int(r, MUX_S_PERMISSION_DENIED);
473: buffer_put_int(r, rid);
474: buffer_put_cstring(r, "Permission denied");
475: return 0;
476: }
477: }
1.1 djm 478:
1.10 djm 479: quit_pending = 1;
480: buffer_put_int(r, MUX_S_OK);
481: buffer_put_int(r, rid);
482: /* XXX exit happens too soon - message never makes it to client */
483: return 0;
1.1 djm 484: }
485:
1.10 djm 486: static char *
487: format_forward(u_int ftype, Forward *fwd)
1.1 djm 488: {
1.10 djm 489: char *ret;
1.1 djm 490:
1.10 djm 491: switch (ftype) {
492: case MUX_FWD_LOCAL:
493: xasprintf(&ret, "local forward %.200s:%d -> %.200s:%d",
494: (fwd->listen_host == NULL) ?
495: (options.gateway_ports ? "*" : "LOCALHOST") :
496: fwd->listen_host, fwd->listen_port,
497: fwd->connect_host, fwd->connect_port);
498: break;
499: case MUX_FWD_DYNAMIC:
500: xasprintf(&ret, "dynamic forward %.200s:%d -> *",
501: (fwd->listen_host == NULL) ?
502: (options.gateway_ports ? "*" : "LOCALHOST") :
503: fwd->listen_host, fwd->listen_port);
504: break;
505: case MUX_FWD_REMOTE:
506: xasprintf(&ret, "remote forward %.200s:%d -> %.200s:%d",
507: (fwd->listen_host == NULL) ?
508: "LOCALHOST" : fwd->listen_host,
509: fwd->listen_port,
510: fwd->connect_host, fwd->connect_port);
1.1 djm 511: break;
512: default:
1.10 djm 513: fatal("%s: unknown forward type %u", __func__, ftype);
1.1 djm 514: }
1.10 djm 515: return ret;
516: }
1.1 djm 517:
1.10 djm 518: static int
519: compare_host(const char *a, const char *b)
520: {
521: if (a == NULL && b == NULL)
522: return 1;
523: if (a == NULL || b == NULL)
524: return 0;
525: return strcmp(a, b) == 0;
526: }
1.1 djm 527:
1.10 djm 528: static int
529: compare_forward(Forward *a, Forward *b)
530: {
531: if (!compare_host(a->listen_host, b->listen_host))
532: return 0;
533: if (a->listen_port != b->listen_port)
534: return 0;
535: if (!compare_host(a->connect_host, b->connect_host))
536: return 0;
537: if (a->connect_port != b->connect_port)
538: return 0;
1.1 djm 539:
1.10 djm 540: return 1;
541: }
1.1 djm 542:
1.10 djm 543: static int
544: process_mux_open_fwd(u_int rid, Channel *c, Buffer *m, Buffer *r)
545: {
546: Forward fwd;
547: char *fwd_desc = NULL;
548: u_int ftype;
549: int i, ret = 0, freefwd = 1;
550:
551: fwd.listen_host = fwd.connect_host = NULL;
552: if (buffer_get_int_ret(&ftype, m) != 0 ||
553: (fwd.listen_host = buffer_get_string_ret(m, NULL)) == NULL ||
554: buffer_get_int_ret(&fwd.listen_port, m) != 0 ||
555: (fwd.connect_host = buffer_get_string_ret(m, NULL)) == NULL ||
556: buffer_get_int_ret(&fwd.connect_port, m) != 0) {
557: error("%s: malformed message", __func__);
558: ret = -1;
559: goto out;
560: }
561:
562: if (*fwd.listen_host == '\0') {
563: xfree(fwd.listen_host);
564: fwd.listen_host = NULL;
565: }
566: if (*fwd.connect_host == '\0') {
567: xfree(fwd.connect_host);
568: fwd.connect_host = NULL;
569: }
570:
571: debug2("%s: channel %d: request %s", __func__, c->self,
572: (fwd_desc = format_forward(ftype, &fwd)));
573:
574: if (ftype != MUX_FWD_LOCAL && ftype != MUX_FWD_REMOTE &&
575: ftype != MUX_FWD_DYNAMIC) {
576: logit("%s: invalid forwarding type %u", __func__, ftype);
577: invalid:
578: xfree(fwd.listen_host);
579: xfree(fwd.connect_host);
580: buffer_put_int(r, MUX_S_FAILURE);
581: buffer_put_int(r, rid);
582: buffer_put_cstring(r, "Invalid forwarding request");
583: return 0;
584: }
585: /* XXX support rport0 forwarding with reply of port assigned */
586: if (fwd.listen_port == 0 || fwd.listen_port >= 65536) {
587: logit("%s: invalid listen port %u", __func__,
588: fwd.listen_port);
589: goto invalid;
590: }
591: if (fwd.connect_port >= 65536 || (ftype != MUX_FWD_DYNAMIC &&
592: ftype != MUX_FWD_REMOTE && fwd.connect_port == 0)) {
593: logit("%s: invalid connect port %u", __func__,
594: fwd.connect_port);
595: goto invalid;
596: }
597: if (ftype != MUX_FWD_DYNAMIC && fwd.connect_host == NULL) {
598: logit("%s: missing connect host", __func__);
599: goto invalid;
600: }
601:
602: /* Skip forwards that have already been requested */
603: switch (ftype) {
604: case MUX_FWD_LOCAL:
605: case MUX_FWD_DYNAMIC:
606: for (i = 0; i < options.num_local_forwards; i++) {
607: if (compare_forward(&fwd,
608: options.local_forwards + i)) {
609: exists:
610: debug2("%s: found existing forwarding",
611: __func__);
612: buffer_put_int(r, MUX_S_OK);
613: buffer_put_int(r, rid);
614: goto out;
615: }
616: }
617: break;
618: case MUX_FWD_REMOTE:
619: for (i = 0; i < options.num_remote_forwards; i++) {
620: if (compare_forward(&fwd,
621: options.remote_forwards + i))
622: goto exists;
623: }
624: break;
625: }
626:
627: if (options.control_master == SSHCTL_MASTER_ASK ||
628: options.control_master == SSHCTL_MASTER_AUTO_ASK) {
629: if (!ask_permission("Open %s on %s?", fwd_desc, host)) {
630: debug2("%s: forwarding refused by user", __func__);
631: buffer_put_int(r, MUX_S_PERMISSION_DENIED);
632: buffer_put_int(r, rid);
633: buffer_put_cstring(r, "Permission denied");
634: goto out;
635: }
636: }
637:
638: if (ftype == MUX_FWD_LOCAL || ftype == MUX_FWD_DYNAMIC) {
639: if (options.num_local_forwards + 1 >=
640: SSH_MAX_FORWARDS_PER_DIRECTION ||
641: channel_setup_local_fwd_listener(fwd.listen_host,
642: fwd.listen_port, fwd.connect_host, fwd.connect_port,
643: options.gateway_ports) < 0) {
644: fail:
645: logit("slave-requested %s failed", fwd_desc);
646: buffer_put_int(r, MUX_S_FAILURE);
647: buffer_put_int(r, rid);
648: buffer_put_cstring(r, "Port forwarding failed");
649: goto out;
650: }
651: add_local_forward(&options, &fwd);
652: freefwd = 0;
653: } else {
654: /* XXX wait for remote to confirm */
655: if (options.num_remote_forwards + 1 >=
656: SSH_MAX_FORWARDS_PER_DIRECTION ||
657: channel_request_remote_forwarding(fwd.listen_host,
658: fwd.listen_port, fwd.connect_host, fwd.connect_port) < 0)
659: goto fail;
660: add_remote_forward(&options, &fwd);
661: freefwd = 0;
662: }
663: buffer_put_int(r, MUX_S_OK);
664: buffer_put_int(r, rid);
665: out:
666: if (fwd_desc != NULL)
667: xfree(fwd_desc);
668: if (freefwd) {
669: if (fwd.listen_host != NULL)
670: xfree(fwd.listen_host);
671: if (fwd.connect_host != NULL)
672: xfree(fwd.connect_host);
673: }
674: return ret;
675: }
676:
677: static int
678: process_mux_close_fwd(u_int rid, Channel *c, Buffer *m, Buffer *r)
679: {
680: Forward fwd;
681: char *fwd_desc = NULL;
682: u_int ftype;
683: int ret = 0;
684:
685: fwd.listen_host = fwd.connect_host = NULL;
686: if (buffer_get_int_ret(&ftype, m) != 0 ||
687: (fwd.listen_host = buffer_get_string_ret(m, NULL)) == NULL ||
688: buffer_get_int_ret(&fwd.listen_port, m) != 0 ||
689: (fwd.connect_host = buffer_get_string_ret(m, NULL)) == NULL ||
690: buffer_get_int_ret(&fwd.connect_port, m) != 0) {
691: error("%s: malformed message", __func__);
692: ret = -1;
693: goto out;
694: }
695:
696: if (*fwd.listen_host == '\0') {
697: xfree(fwd.listen_host);
698: fwd.listen_host = NULL;
699: }
700: if (*fwd.connect_host == '\0') {
701: xfree(fwd.connect_host);
702: fwd.connect_host = NULL;
703: }
704:
705: debug2("%s: channel %d: request %s", __func__, c->self,
706: (fwd_desc = format_forward(ftype, &fwd)));
707:
708: /* XXX implement this */
709: buffer_put_int(r, MUX_S_FAILURE);
710: buffer_put_int(r, rid);
711: buffer_put_cstring(r, "unimplemented");
712:
713: out:
714: if (fwd_desc != NULL)
715: xfree(fwd_desc);
716: if (fwd.listen_host != NULL)
717: xfree(fwd.listen_host);
718: if (fwd.connect_host != NULL)
719: xfree(fwd.connect_host);
720:
721: return ret;
722: }
723:
724: static int
725: process_mux_stdio_fwd(u_int rid, Channel *c, Buffer *m, Buffer *r)
726: {
727: Channel *nc;
728: char *reserved, *chost;
729: u_int cport, i, j;
730: int new_fd[2];
731:
1.11 djm 732: chost = reserved = NULL;
1.10 djm 733: if ((reserved = buffer_get_string_ret(m, NULL)) == NULL ||
734: (chost = buffer_get_string_ret(m, NULL)) == NULL ||
735: buffer_get_int_ret(&cport, m) != 0) {
1.11 djm 736: if (reserved != NULL)
737: xfree(reserved);
1.10 djm 738: if (chost != NULL)
739: xfree(chost);
740: error("%s: malformed message", __func__);
741: return -1;
742: }
743: xfree(reserved);
744:
745: debug2("%s: channel %d: request stdio fwd to %s:%u",
746: __func__, c->self, chost, cport);
747:
748: /* Gather fds from client */
749: for(i = 0; i < 2; i++) {
750: if ((new_fd[i] = mm_receive_fd(c->sock)) == -1) {
751: error("%s: failed to receive fd %d from slave",
752: __func__, i);
753: for (j = 0; j < i; j++)
754: close(new_fd[j]);
755: xfree(chost);
756:
757: /* prepare reply */
758: buffer_put_int(r, MUX_S_FAILURE);
759: buffer_put_int(r, rid);
760: buffer_put_cstring(r,
761: "did not receive file descriptors");
762: return -1;
763: }
764: }
765:
766: debug3("%s: got fds stdin %d, stdout %d", __func__,
767: new_fd[0], new_fd[1]);
768:
769: /* XXX support multiple child sessions in future */
770: if (c->remote_id != -1) {
771: debug2("%s: session already open", __func__);
772: /* prepare reply */
773: buffer_put_int(r, MUX_S_FAILURE);
774: buffer_put_int(r, rid);
775: buffer_put_cstring(r, "Multiple sessions not supported");
776: cleanup:
777: close(new_fd[0]);
778: close(new_fd[1]);
779: xfree(chost);
780: return 0;
781: }
782:
783: if (options.control_master == SSHCTL_MASTER_ASK ||
784: options.control_master == SSHCTL_MASTER_AUTO_ASK) {
785: if (!ask_permission("Allow forward to to %s:%u? ",
786: chost, cport)) {
787: debug2("%s: stdio fwd refused by user", __func__);
788: /* prepare reply */
789: buffer_put_int(r, MUX_S_PERMISSION_DENIED);
790: buffer_put_int(r, rid);
791: buffer_put_cstring(r, "Permission denied");
792: goto cleanup;
793: }
794: }
795:
796: /* enable nonblocking unless tty */
797: if (!isatty(new_fd[0]))
798: set_nonblock(new_fd[0]);
799: if (!isatty(new_fd[1]))
800: set_nonblock(new_fd[1]);
801:
802: nc = channel_connect_stdio_fwd(chost, cport, new_fd[0], new_fd[1]);
803:
804: nc->ctl_chan = c->self; /* link session -> control channel */
805: c->remote_id = nc->self; /* link control -> session channel */
806:
807: debug2("%s: channel_new: %d linked to control channel %d",
808: __func__, nc->self, nc->ctl_chan);
809:
810: channel_register_cleanup(nc->self, mux_master_session_cleanup_cb, 0);
811:
812: /* prepare reply */
813: /* XXX defer until channel confirmed */
814: buffer_put_int(r, MUX_S_SESSION_OPENED);
815: buffer_put_int(r, rid);
816: buffer_put_int(r, nc->self);
817:
818: return 0;
819: }
820:
821: /* Channel callbacks fired on read/write from mux slave fd */
822: static int
823: mux_master_read_cb(Channel *c)
824: {
825: struct mux_master_state *state = (struct mux_master_state *)c->mux_ctx;
826: Buffer in, out;
827: void *ptr;
828: u_int type, rid, have, i;
829: int ret = -1;
830:
831: /* Setup ctx and */
832: if (c->mux_ctx == NULL) {
833: state = xcalloc(1, sizeof(state));
834: c->mux_ctx = state;
835: channel_register_cleanup(c->self,
836: mux_master_control_cleanup_cb, 0);
837:
838: /* Send hello */
839: buffer_init(&out);
840: buffer_put_int(&out, MUX_MSG_HELLO);
841: buffer_put_int(&out, SSHMUX_VER);
842: /* no extensions */
843: buffer_put_string(&c->output, buffer_ptr(&out),
844: buffer_len(&out));
845: buffer_free(&out);
846: debug3("%s: channel %d: hello sent", __func__, c->self);
847: return 0;
848: }
849:
850: buffer_init(&in);
851: buffer_init(&out);
852:
853: /* Channel code ensures that we receive whole packets */
854: if ((ptr = buffer_get_string_ptr_ret(&c->input, &have)) == NULL) {
855: malf:
856: error("%s: malformed message", __func__);
857: goto out;
858: }
859: buffer_append(&in, ptr, have);
860:
861: if (buffer_get_int_ret(&type, &in) != 0)
862: goto malf;
863: debug3("%s: channel %d packet type 0x%08x len %u",
864: __func__, c->self, type, buffer_len(&in));
865:
866: if (type == MUX_MSG_HELLO)
867: rid = 0;
868: else {
869: if (!state->hello_rcvd) {
870: error("%s: expected MUX_MSG_HELLO(0x%08x), "
871: "received 0x%08x", __func__, MUX_MSG_HELLO, type);
872: goto out;
1.1 djm 873: }
1.10 djm 874: if (buffer_get_int_ret(&rid, &in) != 0)
875: goto malf;
876: }
877:
878: for (i = 0; mux_master_handlers[i].handler != NULL; i++) {
879: if (type == mux_master_handlers[i].type) {
880: ret = mux_master_handlers[i].handler(rid, c, &in, &out);
881: break;
1.1 djm 882: }
1.10 djm 883: }
884: if (mux_master_handlers[i].handler == NULL) {
885: error("%s: unsupported mux message 0x%08x", __func__, type);
886: buffer_put_int(&out, MUX_S_FAILURE);
887: buffer_put_int(&out, rid);
888: buffer_put_cstring(&out, "unsupported request");
889: ret = 0;
890: }
891: /* Enqueue reply packet */
892: if (buffer_len(&out) != 0) {
893: buffer_put_string(&c->output, buffer_ptr(&out),
894: buffer_len(&out));
895: }
896: out:
897: buffer_free(&in);
898: buffer_free(&out);
899: return ret;
900: }
901:
902: void
903: mux_exit_message(Channel *c, int exitval)
904: {
905: Buffer m;
906: Channel *mux_chan;
907:
908: debug3("%s: channel %d: exit message, evitval %d", __func__, c->self,
909: exitval);
910:
911: if ((mux_chan = channel_by_id(c->ctl_chan)) == NULL)
912: fatal("%s: channel %d missing mux channel %d",
913: __func__, c->self, c->ctl_chan);
914:
915: /* Append exit message packet to control socket output queue */
916: buffer_init(&m);
917: buffer_put_int(&m, MUX_S_EXIT_MESSAGE);
918: buffer_put_int(&m, c->self);
919: buffer_put_int(&m, exitval);
920:
921: buffer_put_string(&mux_chan->output, buffer_ptr(&m), buffer_len(&m));
922: buffer_free(&m);
923: }
924:
925: /* Prepare a mux master to listen on a Unix domain socket. */
926: void
927: muxserver_listen(void)
928: {
929: struct sockaddr_un addr;
930: mode_t old_umask;
931:
932: if (options.control_path == NULL ||
933: options.control_master == SSHCTL_MASTER_NO)
1.1 djm 934: return;
1.10 djm 935:
936: debug("setting up multiplex master socket");
937:
938: memset(&addr, '\0', sizeof(addr));
939: addr.sun_family = AF_UNIX;
940: addr.sun_len = offsetof(struct sockaddr_un, sun_path) +
941: strlen(options.control_path) + 1;
942:
943: if (strlcpy(addr.sun_path, options.control_path,
944: sizeof(addr.sun_path)) >= sizeof(addr.sun_path))
945: fatal("ControlPath too long");
946:
947: if ((muxserver_sock = socket(PF_UNIX, SOCK_STREAM, 0)) < 0)
948: fatal("%s socket(): %s", __func__, strerror(errno));
949:
950: old_umask = umask(0177);
951: if (bind(muxserver_sock, (struct sockaddr *)&addr, addr.sun_len) == -1) {
952: muxserver_sock = -1;
953: if (errno == EINVAL || errno == EADDRINUSE) {
954: error("ControlSocket %s already exists, "
955: "disabling multiplexing", options.control_path);
956: close(muxserver_sock);
957: muxserver_sock = -1;
958: xfree(options.control_path);
959: options.control_path = NULL;
960: options.control_master = SSHCTL_MASTER_NO;
961: return;
962: } else
963: fatal("%s bind(): %s", __func__, strerror(errno));
964: }
965: umask(old_umask);
966:
967: if (listen(muxserver_sock, 64) == -1)
968: fatal("%s listen(): %s", __func__, strerror(errno));
969:
970: set_nonblock(muxserver_sock);
971:
972: mux_listener_channel = channel_new("mux listener",
973: SSH_CHANNEL_MUX_LISTENER, muxserver_sock, muxserver_sock, -1,
974: CHAN_TCP_WINDOW_DEFAULT, CHAN_TCP_PACKET_DEFAULT,
975: 0, addr.sun_path, 1);
976: mux_listener_channel->mux_rcb = mux_master_read_cb;
977: debug3("%s: mux listener channel %d fd %d", __func__,
978: mux_listener_channel->self, mux_listener_channel->sock);
979: }
980:
981: /* Callback on open confirmation in mux master for a mux client session. */
982: static void
983: mux_session_confirm(int id, void *arg)
984: {
985: struct mux_session_confirm_ctx *cctx = arg;
986: const char *display;
987: Channel *c;
988: int i;
989:
990: if (cctx == NULL)
991: fatal("%s: cctx == NULL", __func__);
992: if ((c = channel_by_id(id)) == NULL)
993: fatal("%s: no channel for id %d", __func__, id);
994:
995: display = getenv("DISPLAY");
996: if (cctx->want_x_fwd && options.forward_x11 && display != NULL) {
997: char *proto, *data;
998: /* Get reasonable local authentication information. */
999: client_x11_get_proto(display, options.xauth_location,
1000: options.forward_x11_trusted, &proto, &data);
1001: /* Request forwarding with authentication spoofing. */
1002: debug("Requesting X11 forwarding with authentication spoofing.");
1003: x11_request_forwarding_with_spoofing(id, display, proto, data);
1004: /* XXX wait for reply */
1005: }
1006:
1007: if (cctx->want_agent_fwd && options.forward_agent) {
1008: debug("Requesting authentication agent forwarding.");
1009: channel_request_start(id, "auth-agent-req@openssh.com", 0);
1010: packet_send();
1011: }
1012:
1013: client_session2_setup(id, cctx->want_tty, cctx->want_subsys,
1014: cctx->term, &cctx->tio, c->rfd, &cctx->cmd, cctx->env);
1015:
1016: c->open_confirm_ctx = NULL;
1017: buffer_free(&cctx->cmd);
1018: xfree(cctx->term);
1019: if (cctx->env != NULL) {
1020: for (i = 0; cctx->env[i] != NULL; i++)
1021: xfree(cctx->env[i]);
1022: xfree(cctx->env);
1.1 djm 1023: }
1.10 djm 1024: xfree(cctx);
1025: }
1026:
1027: /* ** Multiplexing client support */
1028:
1029: /* Exit signal handler */
1030: static void
1031: control_client_sighandler(int signo)
1032: {
1033: muxclient_terminate = signo;
1034: }
1035:
1036: /*
1037: * Relay signal handler - used to pass some signals from mux client to
1038: * mux master.
1039: */
1040: static void
1041: control_client_sigrelay(int signo)
1042: {
1043: int save_errno = errno;
1044:
1045: if (muxserver_pid > 1)
1046: kill(muxserver_pid, signo);
1047:
1048: errno = save_errno;
1049: }
1.1 djm 1050:
1.10 djm 1051: static int
1052: mux_client_read(int fd, Buffer *b, u_int need)
1053: {
1054: u_int have;
1055: ssize_t len;
1056: u_char *p;
1057: struct pollfd pfd;
1058:
1059: pfd.fd = fd;
1060: pfd.events = POLLIN;
1061: p = buffer_append_space(b, need);
1062: for (have = 0; have < need; ) {
1063: if (muxclient_terminate) {
1064: errno = EINTR;
1065: return -1;
1066: }
1067: len = read(fd, p + have, need - have);
1068: if (len < 0) {
1069: switch (errno) {
1070: case EAGAIN:
1071: (void)poll(&pfd, 1, -1);
1072: /* FALLTHROUGH */
1073: case EINTR:
1074: continue;
1075: default:
1076: return -1;
1077: }
1078: }
1079: if (len == 0) {
1080: errno = EPIPE;
1081: return -1;
1082: }
1083: have += (u_int)len;
1.1 djm 1084: }
1.10 djm 1085: return 0;
1086: }
1.1 djm 1087:
1.10 djm 1088: static int
1089: mux_client_write_packet(int fd, Buffer *m)
1090: {
1091: Buffer queue;
1092: u_int have, need;
1093: int oerrno, len;
1094: u_char *ptr;
1095: struct pollfd pfd;
1096:
1097: pfd.fd = fd;
1098: pfd.events = POLLOUT;
1099: buffer_init(&queue);
1100: buffer_put_string(&queue, buffer_ptr(m), buffer_len(m));
1101:
1102: need = buffer_len(&queue);
1103: ptr = buffer_ptr(&queue);
1104:
1105: for (have = 0; have < need; ) {
1106: if (muxclient_terminate) {
1107: buffer_free(&queue);
1108: errno = EINTR;
1109: return -1;
1110: }
1111: len = write(fd, ptr + have, need - have);
1112: if (len < 0) {
1113: switch (errno) {
1114: case EAGAIN:
1115: (void)poll(&pfd, 1, -1);
1116: /* FALLTHROUGH */
1117: case EINTR:
1118: continue;
1119: default:
1120: oerrno = errno;
1121: buffer_free(&queue);
1122: errno = oerrno;
1123: return -1;
1124: }
1125: }
1126: if (len == 0) {
1127: buffer_free(&queue);
1128: errno = EPIPE;
1129: return -1;
1130: }
1131: have += (u_int)len;
1132: }
1133: buffer_free(&queue);
1134: return 0;
1135: }
1.1 djm 1136:
1.10 djm 1137: static int
1138: mux_client_read_packet(int fd, Buffer *m)
1139: {
1140: Buffer queue;
1141: u_int need, have;
1142: void *ptr;
1143: int oerrno;
1144:
1145: buffer_init(&queue);
1146: if (mux_client_read(fd, &queue, 4) != 0) {
1147: if ((oerrno = errno) == EPIPE)
1148: debug3("%s: read header failed: %s", __func__, strerror(errno));
1149: errno = oerrno;
1150: return -1;
1151: }
1152: need = get_u32(buffer_ptr(&queue));
1153: if (mux_client_read(fd, &queue, need) != 0) {
1154: oerrno = errno;
1155: debug3("%s: read body failed: %s", __func__, strerror(errno));
1156: errno = oerrno;
1157: return -1;
1158: }
1159: ptr = buffer_get_string_ptr(&queue, &have);
1160: buffer_append(m, ptr, have);
1161: buffer_free(&queue);
1162: return 0;
1163: }
1.1 djm 1164:
1.10 djm 1165: static int
1166: mux_client_hello_exchange(int fd)
1167: {
1168: Buffer m;
1169: u_int type, ver;
1.1 djm 1170:
1171: buffer_init(&m);
1.10 djm 1172: buffer_put_int(&m, MUX_MSG_HELLO);
1173: buffer_put_int(&m, SSHMUX_VER);
1174: /* no extensions */
1175:
1176: if (mux_client_write_packet(fd, &m) != 0)
1177: fatal("%s: write packet: %s", __func__, strerror(errno));
1.1 djm 1178:
1.10 djm 1179: buffer_clear(&m);
1180:
1181: /* Read their HELLO */
1182: if (mux_client_read_packet(fd, &m) != 0) {
1.5 djm 1183: buffer_free(&m);
1.10 djm 1184: return -1;
1185: }
1186:
1187: type = buffer_get_int(&m);
1188: if (type != MUX_MSG_HELLO)
1189: fatal("%s: expected HELLO (%u) received %u",
1190: __func__, MUX_MSG_HELLO, type);
1191: ver = buffer_get_int(&m);
1192: if (ver != SSHMUX_VER)
1193: fatal("Unsupported multiplexing protocol version %d "
1194: "(expected %d)", ver, SSHMUX_VER);
1195: debug2("%s: master version %u", __func__, ver);
1196: /* No extensions are presently defined */
1197: while (buffer_len(&m) > 0) {
1198: char *name = buffer_get_string(&m, NULL);
1199: char *value = buffer_get_string(&m, NULL);
1200:
1201: debug2("Unrecognised master extension \"%s\"", name);
1202: xfree(name);
1203: xfree(value);
1.5 djm 1204: }
1.10 djm 1205: buffer_free(&m);
1206: return 0;
1207: }
1208:
1209: static u_int
1210: mux_client_request_alive(int fd)
1211: {
1212: Buffer m;
1213: char *e;
1214: u_int pid, type, rid;
1215:
1216: debug3("%s: entering", __func__);
1217:
1218: buffer_init(&m);
1219: buffer_put_int(&m, MUX_C_ALIVE_CHECK);
1220: buffer_put_int(&m, muxclient_request_id);
1221:
1222: if (mux_client_write_packet(fd, &m) != 0)
1223: fatal("%s: write packet: %s", __func__, strerror(errno));
1224:
1.1 djm 1225: buffer_clear(&m);
1226:
1.10 djm 1227: /* Read their reply */
1228: if (mux_client_read_packet(fd, &m) != 0) {
1229: buffer_free(&m);
1230: return 0;
1231: }
1232:
1233: type = buffer_get_int(&m);
1234: if (type != MUX_S_ALIVE) {
1235: e = buffer_get_string(&m, NULL);
1236: fatal("%s: master returned error: %s", __func__, e);
1.5 djm 1237: }
1.10 djm 1238:
1239: if ((rid = buffer_get_int(&m)) != muxclient_request_id)
1240: fatal("%s: out of sequence reply: my id %u theirs %u",
1241: __func__, muxclient_request_id, rid);
1242: pid = buffer_get_int(&m);
1243: buffer_free(&m);
1244:
1245: debug3("%s: done pid = %u", __func__, pid);
1246:
1247: muxclient_request_id++;
1248:
1249: return pid;
1250: }
1251:
1252: static void
1253: mux_client_request_terminate(int fd)
1254: {
1255: Buffer m;
1256: char *e;
1257: u_int type, rid;
1258:
1259: debug3("%s: entering", __func__);
1260:
1261: buffer_init(&m);
1262: buffer_put_int(&m, MUX_C_TERMINATE);
1263: buffer_put_int(&m, muxclient_request_id);
1264:
1265: if (mux_client_write_packet(fd, &m) != 0)
1266: fatal("%s: write packet: %s", __func__, strerror(errno));
1.1 djm 1267:
1268: buffer_clear(&m);
1269:
1.10 djm 1270: /* Read their reply */
1271: if (mux_client_read_packet(fd, &m) != 0) {
1272: /* Remote end exited already */
1273: if (errno == EPIPE) {
1274: buffer_free(&m);
1275: return;
1.2 djm 1276: }
1.10 djm 1277: fatal("%s: read from master failed: %s",
1278: __func__, strerror(errno));
1279: }
1280:
1281: type = buffer_get_int(&m);
1282: if ((rid = buffer_get_int(&m)) != muxclient_request_id)
1283: fatal("%s: out of sequence reply: my id %u theirs %u",
1284: __func__, muxclient_request_id, rid);
1285: switch (type) {
1286: case MUX_S_OK:
1287: break;
1288: case MUX_S_PERMISSION_DENIED:
1289: e = buffer_get_string(&m, NULL);
1290: fatal("Master refused termination request: %s", e);
1291: case MUX_S_FAILURE:
1292: e = buffer_get_string(&m, NULL);
1293: fatal("%s: termination request failed: %s", __func__, e);
1294: default:
1295: fatal("%s: unexpected response from master 0x%08x",
1296: __func__, type);
1297: }
1298: buffer_free(&m);
1299: muxclient_request_id++;
1300: }
1301:
1302: static int
1303: mux_client_request_forward(int fd, u_int ftype, Forward *fwd)
1304: {
1305: Buffer m;
1306: char *e, *fwd_desc;
1307: u_int type, rid;
1308:
1309: fwd_desc = format_forward(ftype, fwd);
1310: debug("Requesting %s", fwd_desc);
1311: xfree(fwd_desc);
1312:
1313: buffer_init(&m);
1314: buffer_put_int(&m, MUX_C_OPEN_FWD);
1315: buffer_put_int(&m, muxclient_request_id);
1316: buffer_put_int(&m, ftype);
1317: buffer_put_cstring(&m,
1318: fwd->listen_host == NULL ? "" : fwd->listen_host);
1319: buffer_put_int(&m, fwd->listen_port);
1320: buffer_put_cstring(&m,
1321: fwd->connect_host == NULL ? "" : fwd->connect_host);
1322: buffer_put_int(&m, fwd->connect_port);
1323:
1324: if (mux_client_write_packet(fd, &m) != 0)
1325: fatal("%s: write packet: %s", __func__, strerror(errno));
1326:
1327: buffer_clear(&m);
1328:
1329: /* Read their reply */
1330: if (mux_client_read_packet(fd, &m) != 0) {
1331: buffer_free(&m);
1332: return -1;
1333: }
1334:
1335: type = buffer_get_int(&m);
1336: if ((rid = buffer_get_int(&m)) != muxclient_request_id)
1337: fatal("%s: out of sequence reply: my id %u theirs %u",
1338: __func__, muxclient_request_id, rid);
1339: switch (type) {
1340: case MUX_S_OK:
1.1 djm 1341: break;
1.10 djm 1342: case MUX_S_PERMISSION_DENIED:
1343: e = buffer_get_string(&m, NULL);
1344: buffer_free(&m);
1345: error("Master refused forwarding request: %s", e);
1346: return -1;
1347: case MUX_S_FAILURE:
1348: e = buffer_get_string(&m, NULL);
1349: buffer_free(&m);
1350: error("%s: session request failed: %s", __func__, e);
1351: return -1;
1.1 djm 1352: default:
1.10 djm 1353: fatal("%s: unexpected response from master 0x%08x",
1354: __func__, type);
1355: }
1356: buffer_free(&m);
1357:
1358: muxclient_request_id++;
1359: return 0;
1360: }
1361:
1362: static int
1363: mux_client_request_forwards(int fd)
1364: {
1365: int i;
1366:
1367: debug3("%s: requesting forwardings: %d local, %d remote", __func__,
1368: options.num_local_forwards, options.num_remote_forwards);
1369:
1370: /* XXX ExitOnForwardingFailure */
1371: for (i = 0; i < options.num_local_forwards; i++) {
1372: if (mux_client_request_forward(fd,
1373: options.local_forwards[i].connect_port == 0 ?
1374: MUX_FWD_DYNAMIC : MUX_FWD_LOCAL,
1375: options.local_forwards + i) != 0)
1376: return -1;
1377: }
1378: for (i = 0; i < options.num_remote_forwards; i++) {
1379: if (mux_client_request_forward(fd, MUX_FWD_REMOTE,
1380: options.remote_forwards + i) != 0)
1381: return -1;
1382: }
1383: return 0;
1384: }
1385:
1386: static int
1387: mux_client_request_session(int fd)
1388: {
1389: Buffer m;
1390: char *e, *term;
1391: u_int i, rid, sid, esid, exitval, type, exitval_seen;
1392: extern char **environ;
1393: int devnull;
1394:
1395: debug3("%s: entering", __func__);
1396:
1397: if ((muxserver_pid = mux_client_request_alive(fd)) == 0) {
1398: error("%s: master alive request failed", __func__);
1399: return -1;
1.1 djm 1400: }
1401:
1.10 djm 1402: signal(SIGPIPE, SIG_IGN);
1403:
1404: if (stdin_null_flag) {
1405: if ((devnull = open(_PATH_DEVNULL, O_RDONLY)) == -1)
1406: fatal("open(/dev/null): %s", strerror(errno));
1407: if (dup2(devnull, STDIN_FILENO) == -1)
1408: fatal("dup2: %s", strerror(errno));
1409: if (devnull > STDERR_FILENO)
1410: close(devnull);
1.5 djm 1411: }
1.1 djm 1412:
1.10 djm 1413: term = getenv("TERM");
1414:
1415: buffer_init(&m);
1416: buffer_put_int(&m, MUX_C_NEW_SESSION);
1417: buffer_put_int(&m, muxclient_request_id);
1418: buffer_put_cstring(&m, ""); /* reserved */
1419: buffer_put_int(&m, tty_flag);
1420: buffer_put_int(&m, options.forward_x11);
1421: buffer_put_int(&m, options.forward_agent);
1422: buffer_put_int(&m, subsystem_flag);
1423: buffer_put_int(&m, options.escape_char == SSH_ESCAPECHAR_NONE ?
1424: 0xffffffff : (u_int)options.escape_char);
1425: buffer_put_cstring(&m, term == NULL ? "" : term);
1426: buffer_put_string(&m, buffer_ptr(&command), buffer_len(&command));
1427:
1428: if (options.num_send_env > 0 && environ != NULL) {
1429: /* Pass environment */
1430: for (i = 0; environ[i] != NULL; i++) {
1431: if (env_permitted(environ[i])) {
1432: buffer_put_cstring(&m, environ[i]);
1433: }
1434: }
1.5 djm 1435: }
1436:
1.10 djm 1437: if (mux_client_write_packet(fd, &m) != 0)
1438: fatal("%s: write packet: %s", __func__, strerror(errno));
1439:
1440: /* Send the stdio file descriptors */
1441: if (mm_send_fd(fd, STDIN_FILENO) == -1 ||
1442: mm_send_fd(fd, STDOUT_FILENO) == -1 ||
1443: mm_send_fd(fd, STDERR_FILENO) == -1)
1444: fatal("%s: send fds failed", __func__);
1445:
1446: debug3("%s: session request sent", __func__);
1.1 djm 1447:
1.10 djm 1448: /* Read their reply */
1.1 djm 1449: buffer_clear(&m);
1.10 djm 1450: if (mux_client_read_packet(fd, &m) != 0) {
1451: error("%s: read from master failed: %s",
1452: __func__, strerror(errno));
1453: buffer_free(&m);
1454: return -1;
1455: }
1456:
1457: type = buffer_get_int(&m);
1458: if ((rid = buffer_get_int(&m)) != muxclient_request_id)
1459: fatal("%s: out of sequence reply: my id %u theirs %u",
1460: __func__, muxclient_request_id, rid);
1461: switch (type) {
1462: case MUX_S_SESSION_OPENED:
1463: sid = buffer_get_int(&m);
1464: debug("%s: master session id: %u", __func__, sid);
1465: break;
1466: case MUX_S_PERMISSION_DENIED:
1467: e = buffer_get_string(&m, NULL);
1468: buffer_free(&m);
1469: error("Master refused forwarding request: %s", e);
1470: return -1;
1471: case MUX_S_FAILURE:
1472: e = buffer_get_string(&m, NULL);
1473: buffer_free(&m);
1474: error("%s: forwarding request failed: %s", __func__, e);
1475: return -1;
1476: default:
1477: buffer_free(&m);
1478: error("%s: unexpected response from master 0x%08x",
1479: __func__, type);
1480: return -1;
1481: }
1482: muxclient_request_id++;
1.1 djm 1483:
1484: signal(SIGHUP, control_client_sighandler);
1485: signal(SIGINT, control_client_sighandler);
1486: signal(SIGTERM, control_client_sighandler);
1487: signal(SIGWINCH, control_client_sigrelay);
1488:
1489: if (tty_flag)
1.9 djm 1490: enter_raw_mode(force_tty_flag);
1.1 djm 1491:
1492: /*
1493: * Stick around until the controlee closes the client_fd.
1.10 djm 1494: * Before it does, it is expected to write an exit message.
1495: * This process must read the value and wait for the closure of
1496: * the client_fd; if this one closes early, the multiplex master will
1497: * terminate early too (possibly losing data).
1.1 djm 1498: */
1.10 djm 1499: for (exitval = 255, exitval_seen = 0;;) {
1500: buffer_clear(&m);
1501: if (mux_client_read_packet(fd, &m) != 0)
1.1 djm 1502: break;
1.10 djm 1503: type = buffer_get_int(&m);
1504: if (type != MUX_S_EXIT_MESSAGE) {
1505: e = buffer_get_string(&m, NULL);
1506: fatal("%s: master returned error: %s", __func__, e);
1.1 djm 1507: }
1.10 djm 1508: if ((esid = buffer_get_int(&m)) != sid)
1509: fatal("%s: exit on unknown session: my id %u theirs %u",
1510: __func__, sid, esid);
1511: debug("%s: master session id: %u", __func__, sid);
1512: if (exitval_seen)
1513: fatal("%s: exitval sent twice", __func__);
1514: exitval = buffer_get_int(&m);
1515: exitval_seen = 1;
1.1 djm 1516: }
1517:
1.10 djm 1518: close(fd);
1.9 djm 1519: leave_raw_mode(force_tty_flag);
1.10 djm 1520:
1.1 djm 1521: if (muxclient_terminate) {
1522: debug2("Exiting on signal %d", muxclient_terminate);
1.10 djm 1523: exitval = 255;
1524: } else if (!exitval_seen) {
1.1 djm 1525: debug2("Control master terminated unexpectedly");
1.10 djm 1526: exitval = 255;
1.1 djm 1527: } else
1.10 djm 1528: debug2("Received exit status from master %d", exitval);
1.1 djm 1529:
1530: if (tty_flag && options.log_level != SYSLOG_LEVEL_QUIET)
1531: fprintf(stderr, "Shared connection to %s closed.\r\n", host);
1532:
1.10 djm 1533: exit(exitval);
1534: }
1535:
1536: static int
1537: mux_client_request_stdio_fwd(int fd)
1538: {
1539: Buffer m;
1540: char *e;
1541: u_int type, rid, sid;
1542: int devnull;
1543:
1544: debug3("%s: entering", __func__);
1545:
1546: if ((muxserver_pid = mux_client_request_alive(fd)) == 0) {
1547: error("%s: master alive request failed", __func__);
1548: return -1;
1549: }
1550:
1551: signal(SIGPIPE, SIG_IGN);
1552:
1553: if (stdin_null_flag) {
1554: if ((devnull = open(_PATH_DEVNULL, O_RDONLY)) == -1)
1555: fatal("open(/dev/null): %s", strerror(errno));
1556: if (dup2(devnull, STDIN_FILENO) == -1)
1557: fatal("dup2: %s", strerror(errno));
1558: if (devnull > STDERR_FILENO)
1559: close(devnull);
1560: }
1561:
1562: buffer_init(&m);
1563: buffer_put_int(&m, MUX_C_NEW_STDIO_FWD);
1564: buffer_put_int(&m, muxclient_request_id);
1565: buffer_put_cstring(&m, ""); /* reserved */
1566: buffer_put_cstring(&m, stdio_forward_host);
1567: buffer_put_int(&m, stdio_forward_port);
1568:
1569: if (mux_client_write_packet(fd, &m) != 0)
1570: fatal("%s: write packet: %s", __func__, strerror(errno));
1571:
1572: /* Send the stdio file descriptors */
1573: if (mm_send_fd(fd, STDIN_FILENO) == -1 ||
1574: mm_send_fd(fd, STDOUT_FILENO) == -1)
1575: fatal("%s: send fds failed", __func__);
1576:
1577: debug3("%s: stdio forward request sent", __func__);
1578:
1579: /* Read their reply */
1580: buffer_clear(&m);
1581:
1582: if (mux_client_read_packet(fd, &m) != 0) {
1583: error("%s: read from master failed: %s",
1584: __func__, strerror(errno));
1585: buffer_free(&m);
1586: return -1;
1587: }
1588:
1589: type = buffer_get_int(&m);
1590: if ((rid = buffer_get_int(&m)) != muxclient_request_id)
1591: fatal("%s: out of sequence reply: my id %u theirs %u",
1592: __func__, muxclient_request_id, rid);
1593: switch (type) {
1594: case MUX_S_SESSION_OPENED:
1595: sid = buffer_get_int(&m);
1596: debug("%s: master session id: %u", __func__, sid);
1597: break;
1598: case MUX_S_PERMISSION_DENIED:
1599: e = buffer_get_string(&m, NULL);
1600: buffer_free(&m);
1601: fatal("Master refused forwarding request: %s", e);
1602: case MUX_S_FAILURE:
1603: e = buffer_get_string(&m, NULL);
1604: buffer_free(&m);
1605: fatal("%s: stdio forwarding request failed: %s", __func__, e);
1606: default:
1607: buffer_free(&m);
1608: error("%s: unexpected response from master 0x%08x",
1609: __func__, type);
1610: return -1;
1611: }
1612: muxclient_request_id++;
1613:
1614: signal(SIGHUP, control_client_sighandler);
1615: signal(SIGINT, control_client_sighandler);
1616: signal(SIGTERM, control_client_sighandler);
1617: signal(SIGWINCH, control_client_sigrelay);
1618:
1619: /*
1620: * Stick around until the controlee closes the client_fd.
1621: */
1622: buffer_clear(&m);
1623: if (mux_client_read_packet(fd, &m) != 0) {
1624: if (errno == EPIPE ||
1625: (errno == EINTR && muxclient_terminate != 0))
1626: return 0;
1627: fatal("%s: mux_client_read_packet: %s",
1628: __func__, strerror(errno));
1629: }
1630: fatal("%s: master returned unexpected message %u", __func__, type);
1631: }
1632:
1633: /* Multiplex client main loop. */
1634: void
1635: muxclient(const char *path)
1636: {
1637: struct sockaddr_un addr;
1638: int sock;
1639: u_int pid;
1640:
1641: if (muxclient_command == 0) {
1642: if (stdio_forward_host != NULL)
1643: muxclient_command = SSHMUX_COMMAND_STDIO_FWD;
1644: else
1645: muxclient_command = SSHMUX_COMMAND_OPEN;
1646: }
1647:
1648: switch (options.control_master) {
1649: case SSHCTL_MASTER_AUTO:
1650: case SSHCTL_MASTER_AUTO_ASK:
1651: debug("auto-mux: Trying existing master");
1652: /* FALLTHROUGH */
1653: case SSHCTL_MASTER_NO:
1654: break;
1655: default:
1656: return;
1657: }
1658:
1659: memset(&addr, '\0', sizeof(addr));
1660: addr.sun_family = AF_UNIX;
1661: addr.sun_len = offsetof(struct sockaddr_un, sun_path) +
1662: strlen(path) + 1;
1663:
1664: if (strlcpy(addr.sun_path, path,
1665: sizeof(addr.sun_path)) >= sizeof(addr.sun_path))
1666: fatal("ControlPath too long");
1667:
1668: if ((sock = socket(PF_UNIX, SOCK_STREAM, 0)) < 0)
1669: fatal("%s socket(): %s", __func__, strerror(errno));
1670:
1671: if (connect(sock, (struct sockaddr *)&addr, addr.sun_len) == -1) {
1672: switch (muxclient_command) {
1673: case SSHMUX_COMMAND_OPEN:
1674: case SSHMUX_COMMAND_STDIO_FWD:
1675: break;
1676: default:
1677: fatal("Control socket connect(%.100s): %s", path,
1678: strerror(errno));
1679: }
1680: if (errno == ENOENT)
1681: debug("Control socket \"%.100s\" does not exist", path);
1682: else {
1683: error("Control socket connect(%.100s): %s", path,
1684: strerror(errno));
1685: }
1686: close(sock);
1687: return;
1688: }
1689: set_nonblock(sock);
1690:
1691: if (mux_client_hello_exchange(sock) != 0) {
1692: error("%s: master hello exchange failed", __func__);
1693: close(sock);
1694: return;
1695: }
1696:
1697: switch (muxclient_command) {
1698: case SSHMUX_COMMAND_ALIVE_CHECK:
1699: if ((pid = mux_client_request_alive(sock)) == 0)
1700: fatal("%s: master alive check failed", __func__);
1701: fprintf(stderr, "Master running (pid=%d)\r\n", pid);
1702: exit(0);
1703: case SSHMUX_COMMAND_TERMINATE:
1704: mux_client_request_terminate(sock);
1705: fprintf(stderr, "Exit request sent.\r\n");
1706: exit(0);
1707: case SSHMUX_COMMAND_OPEN:
1708: if (mux_client_request_forwards(sock) != 0) {
1709: error("%s: master forward request failed", __func__);
1710: return;
1711: }
1712: mux_client_request_session(sock);
1713: return;
1714: case SSHMUX_COMMAND_STDIO_FWD:
1715: mux_client_request_stdio_fwd(sock);
1716: exit(0);
1717: default:
1718: fatal("unrecognised muxclient_command %d", muxclient_command);
1719: }
1.1 djm 1720: }