'ControlMaster auto'
David Woodhouse
dwmw2 at infradead.org
Sun Jun 12 23:18:11 EST 2005
On Sun, 2005-06-12 at 09:59 +0100, David Woodhouse wrote:
> This allows me to set 'ControlPath ~/.ssh/sockets/%h.%p.%u' for example.
... and this one complements it by adding 'ControlMaster auto'. I should
probably use #defines for the ControlMaster settings now that they're
more complicated than just 0, 1 or 2, -- but I'll do that in the next
patch, which will add 'persist' and 'autopersist' to the available
options.
--- openssh-4.1p1/readconf.c 2005-03-14 12:08:12.000000000 +0000
+++ openssh-4.1p1-auto/readconf.c 2005-06-12 11:18:05.000000000 +0100
@@ -793,7 +793,26 @@ parse_int:
case oControlMaster:
intptr = &options->control_master;
- goto parse_yesnoask;
+ arg = strdelim(&s);
+ if (!arg || *arg == '\0')
+ fatal("%.200s line %d: Missing ControlMaster argument.",
+ filename, linenum);
+ value = 0; /* To avoid compiler warning... */
+ if (strcmp(arg, "yes") == 0 || strcmp(arg, "true") == 0)
+ value = 1;
+ else if (strcmp(arg, "no") == 0 || strcmp(arg, "false") == 0)
+ value = 0;
+ else if (strcmp(arg, "ask") == 0)
+ value = 2;
+ else if (strcmp(arg, "auto") == 0)
+ value = 3;
+ else if (strcmp(arg, "autoask") == 0)
+ value = 4;
+ else
+ fatal("%.200s line %d: Bad ControlMaster argument.", filename, linenum);
+ if (*activep && *intptr == -1)
+ *intptr = value;
+ break;
case oHashKnownHosts:
intptr = &options->hash_known_hosts;
--- openssh-4.1p1/ssh.c 2005-06-12 13:56:53.000000000 +0100
+++ openssh-4.1p1-auto/ssh.c 2005-06-12 13:55:32.000000000 +0100
@@ -659,8 +659,13 @@ again:
options.control_path = xstrdup(buffer_ptr(&path));
}
}
- if (options.control_path != NULL && options.control_master == 0)
- control_client(options.control_path); /* This doesn't return */
+ if (options.control_path != NULL &&
+ (options.control_master == 0 || options.control_master == 3 ||
+ options.control_master == 4)) {
+ /* This only returns in the 'ask' cases, if we should
+ become a master */
+ control_client(options.control_path);
+ }
/* Open a connection to the remote host. */
if (ssh_connect(host, &hostaddr, options.port,
@@ -1337,15 +1342,6 @@ control_client(const char *path)
extern char **environ;
u_int flags;
- if (stdin_null_flag) {
- if ((fd = open(_PATH_DEVNULL, O_RDONLY)) == -1)
- fatal("open(/dev/null): %s", strerror(errno));
- if (dup2(fd, STDIN_FILENO) == -1)
- fatal("dup2: %s", strerror(errno));
- if (fd > STDERR_FILENO)
- close(fd);
- }
-
memset(&addr, '\0', sizeof(addr));
addr.sun_family = AF_UNIX;
addr_len = offsetof(struct sockaddr_un, sun_path) +
@@ -1358,8 +1354,25 @@ control_client(const char *path)
if ((sock = socket(PF_UNIX, SOCK_STREAM, 0)) < 0)
fatal("%s socket(): %s", __func__, strerror(errno));
- if (connect(sock, (struct sockaddr*)&addr, addr_len) == -1)
+ if (connect(sock, (struct sockaddr*)&addr, addr_len) == -1) {
+ if (options.control_master >= 2) {
+ debug("Couldn't connect to %s: %s", path, strerror(errno));
+ /* Automatic mode; return and become a master */
+ options.control_master -= 2;
+ close(sock);
+ return;
+ }
fatal("Couldn't connect to %s: %s", path, strerror(errno));
+ }
+
+ if (stdin_null_flag) {
+ if ((fd = open(_PATH_DEVNULL, O_RDONLY)) == -1)
+ fatal("open(/dev/null): %s", strerror(errno));
+ if (dup2(fd, STDIN_FILENO) == -1)
+ fatal("dup2: %s", strerror(errno));
+ if (fd > STDERR_FILENO)
+ close(fd);
+ }
if ((term = getenv("TERM")) == NULL)
term = "";
--
dwmw2
More information about the openssh-unix-dev
mailing list