From 9e8d31d31f4f7a18244c6195fea87ecad4428833 Mon Sep 17 00:00:00 2001
From: Salvador Fandino <sfandino@yahoo.com>
Date: Tue, 23 Jun 2015 15:34:31 +0200
Subject: [PATCH] Allow forwarding of stdio to streamlocal end points.
Later versions of OpenSSH allow the user to forward connections also to/from Unix sockets.
This patch allows to use Unix sockets as the target when forwarding the local stdio using the -W feature.
---
channels.c | 15 ++++++++++-----
channels.h | 2 +-
mux.c | 6 +++---
ssh.c | 21 +++++++++++++--------
4 files changed, 27 insertions(+), 17 deletions(-)
diff --git a/channels.c b/channels.c
index 45e1f9f..d4bf467 100644
--- a/channels.c
+++ b/channels.c
@@ -1269,25 +1269,30 @@ channel_decode_socks5(Channel *c, fd_set *readset, fd_set *writeset)
}
Channel *
-channel_connect_stdio_fwd(const char *host_to_connect, u_short port_to_connect,
+channel_connect_stdio_fwd(const char *path_to_connect, u_int port_to_connect,
int in, int out)
{
Channel *c;
- debug("channel_connect_stdio_fwd %s:%d", host_to_connect,
- port_to_connect);
+ if (port_to_connect == (u_int)PORT_STREAMLOCAL)
+ debug("channel_connect_stdio_fwd stream local %s", path_to_connect);
+ else
+ debug("channel_connect_stdio_fwd %s:%d", path_to_connect,
+ port_to_connect);
c = channel_new("stdio-forward", SSH_CHANNEL_OPENING, in, out,
-1, CHAN_TCP_WINDOW_DEFAULT, CHAN_TCP_PACKET_DEFAULT,
0, "stdio-forward", /*nonblock*/0);
- c->path = xstrdup(host_to_connect);
+ c->path = xstrdup(path_to_connect);
c->host_port = port_to_connect;
c->listening_port = 0;
c->force_drain = 1;
channel_register_fds(c, in, out, -1, 0, 1, 0);
- port_open_helper(c, "direct-tcpip");
+ port_open_helper(c, ((port_to_connect == (u_int)PORT_STREAMLOCAL)
+ ? "direct-streamlocal@openssh.com"
+ : "direct-tcpip"));
return c;
}
diff --git a/channels.h b/channels.h
index b9b4860..937e9b3 100644
--- a/channels.h
+++ b/channels.h
@@ -270,7 +270,7 @@ void channel_print_adm_permitted_opens(void);
int channel_input_port_forward_request(int, struct ForwardOptions *);
Channel *channel_connect_to_port(const char *, u_short, char *, char *);
Channel *channel_connect_to_path(const char *, char *, char *);
-Channel *channel_connect_stdio_fwd(const char*, u_short, int, int);
+Channel *channel_connect_stdio_fwd(const char*, u_int, int, int);
Channel *channel_connect_by_listen_address(const char *, u_short,
char *, char *);
Channel *channel_connect_by_listen_path(const char *, char *, char *);
diff --git a/mux.c b/mux.c
index cdc01bd..dd448e9 100644
--- a/mux.c
+++ b/mux.c
@@ -88,7 +88,7 @@ extern char *host;
extern int subsystem_flag;
extern Buffer command;
extern volatile sig_atomic_t quit_pending;
-extern char *stdio_forward_host;
+extern char *stdio_forward_path;
extern int stdio_forward_port;
/* Context for session open confirmation callback */
@@ -1981,7 +1981,7 @@ mux_client_request_stdio_fwd(int fd)
buffer_put_int(&m, MUX_C_NEW_STDIO_FWD);
buffer_put_int(&m, muxclient_request_id);
buffer_put_cstring(&m, ""); /* reserved */
- buffer_put_cstring(&m, stdio_forward_host);
+ buffer_put_cstring(&m, stdio_forward_path);
buffer_put_int(&m, stdio_forward_port);
if (mux_client_write_packet(fd, &m) != 0)
@@ -2102,7 +2102,7 @@ muxclient(const char *path)
u_int pid;
if (muxclient_command == 0) {
- if (stdio_forward_host != NULL)
+ if (stdio_forward_path != NULL)
muxclient_command = SSHMUX_COMMAND_STDIO_FWD;
else
muxclient_command = SSHMUX_COMMAND_OPEN;
diff --git a/ssh.c b/ssh.c
index 3fd5a94..60f86be 100644
--- a/ssh.c
+++ b/ssh.c
@@ -151,8 +151,8 @@ int ostdin_null_flag, ono_shell_flag, otty_flag, orequest_tty;
*/
int fork_after_authentication_flag = 0;
-/* forward stdio to remote host and port */
-char *stdio_forward_host = NULL;
+/* forward stdio to remote host and port or unix socket */
+char *stdio_forward_path = NULL;
int stdio_forward_port = 0;
/*
@@ -639,7 +639,7 @@ main(int ac, char **av)
options.fwd_opts.gateway_ports = 1;
break;
case 'O':
- if (stdio_forward_host != NULL)
+ if (stdio_forward_path != NULL)
fatal("Cannot specify multiplexing "
"command with -W");
else if (muxclient_command != 0)
@@ -756,12 +756,14 @@ main(int ac, char **av)
}
break;
case 'W':
- if (stdio_forward_host != NULL)
+ if (stdio_forward_path != NULL)
fatal("stdio forward already specified");
if (muxclient_command != 0)
fatal("Cannot specify stdio forward with -O");
if (parse_forward(&fwd, optarg, 1, 0)) {
- stdio_forward_host = fwd.listen_host;
+ stdio_forward_path = ((fwd.listen_port == PORT_STREAMLOCAL)
+ ? fwd.listen_path
+ : fwd.listen_host);
stdio_forward_port = fwd.listen_port;
free(fwd.connect_host);
} else {
@@ -1493,17 +1495,20 @@ ssh_init_stdio_forwarding(void)
Channel *c;
int in, out;
- if (stdio_forward_host == NULL)
+ if (stdio_forward_path == NULL)
return;
if (!compat20)
fatal("stdio forwarding require Protocol 2");
- debug3("%s: %s:%d", __func__, stdio_forward_host, stdio_forward_port);
+ if (stdio_forward_port == PORT_STREAMLOCAL)
+ debug3("%s: stream local %s", __func__, stdio_forward_path);
+ else
+ debug3("%s: %s:%d", __func__, stdio_forward_path, stdio_forward_port);
if ((in = dup(STDIN_FILENO)) < 0 ||
(out = dup(STDOUT_FILENO)) < 0)
fatal("channel_connect_stdio_fwd: dup() in/out failed");
- if ((c = channel_connect_stdio_fwd(stdio_forward_host,
+ if ((c = channel_connect_stdio_fwd(stdio_forward_path,
stdio_forward_port, in, out)) == NULL)
fatal("%s: channel_connect_stdio_fwd failed", __func__);
channel_register_cleanup(c->self, client_cleanup_stdio_fwd, 0);
--
2.1.4