6

Is there a more direct way to exit an OpenSSH control master process and delete its socket file than with the help of the programs lsof or fuser and without knowing the destination host (connection details) as suggested by the accepted answer of this question? I thought of something like this along the lines of:

$ ssh -O exit -S ~/.ssh/7eb92b0827f3e8e1e8591fb3d1a5cd1b94b758cb.socket

I'm asking because I'm looking for a scriptable way to exit every open control master connection each time when I log out of my user account. Not doing so causes my sytemd-powered openSUSE computer to wait for a timeout of two minutes until it forcefully terminates the still open control master connection powering off eventually.

Unfortunately OpenSSH's client program ssh requires the destination host and the ControlPath file name pattern in order to deduce the actual file path to the socket file. I on the contrary thought of the more direct method of providing the concrete socket file via the program's -S ctl_path option.

In the global section of my system-wide OpenSSH client config file I configured OpenSSH's connection multiplexing feature as follows:

ControlMaster auto      
ControlPath ~/.ssh/%C.socket
ControlPersist 30m

Please note that I want to keep the file name pattern for socket files, i.e. hashing the token string %l%h%p%r with the token %C.

Any ideas?

  • @slm: I was already aware of the answer unix.stackexchange.com/questions/24005/… but it doesn't suffice my needs. I therefore chose a very specific title for this question. Basically how to accomplish closing an OpenSSH control master connection without lsof or fuser. Maybe I should have further restricted it to without knowing the destination host (connection details). – Tim Friske Jul 30 '18 at 20:49
  • I think I figured out the issue, see A'er. – slm Jul 30 '18 at 23:21
6

This works for me using just the socket file for the control master:

$ ssh -o ControlPath=~/.ssh/<controlfile> -O check <bogus arg>

NOTE: You can also use ssh -S ~/.ssh/<controlfile> ... as well, which is a bit shorter form of the above.

Example

Here's an example where I've already established a connection to a remote server:

$ ssh -S ~/.ssh/master-57db26a0499dfd881986e23a2e4dd5c5c63e26c2 -O check blah
Master running (pid=89228)
$

And with it disconnected:

$ ssh -S ~/.ssh/master-66496a62823573e4760469df70e57ce4c15afd74 -O check blah
Control socket connect(/Users/user1/.ssh/master-66496a62823573e4760469df70e57ce4c15afd74): No such file or directory
$

If it were still connected, this would force it to exit immediately:

$ ssh -S ~/.ssh/master-66496a62823573e4760469df70e57ce4c15afd74 -O exit blah
Exit request sent.
$

It's unclear to me, but it would appear to potentially be a bug in ssh that it requires an additional argument at the end, even though blah is meaningless in the context of the switches I'm using.

Without it gives me this:

$ ssh -S ~/.ssh/master-57db26a0499dfd881986e23a2e4dd5c5c63e26c2 -O check
usage: ssh [-1246AaCfGgKkMNnqsTtVvXxYy] [-b bind_address] [-c cipher_spec]
           [-D [bind_address:]port] [-E log_file] [-e escape_char]
           [-F configfile] [-I pkcs11] [-i identity_file]
           [-L [bind_address:]port:host:hostport] [-l login_name] [-m mac_spec]
           [-O ctl_cmd] [-o option] [-p port]
           [-Q cipher | cipher-auth | mac | kex | key]
           [-R [bind_address:]port:host:hostport] [-S ctl_path] [-W host:port]
           [-w local_tun[:remote_tun]] [user@]hostname [command]

Version info

OSX
$ ssh -V
OpenSSH_6.9p1, LibreSSL 2.1.8
CentOS 7.x
$ ssh -V
OpenSSH_7.4p1, OpenSSL 1.0.2k-fips  26 Jan 2017

I confirmed that on both of these versions, the need for the additional bogus argument was required.

UPDATE #1

I raised this as a potential bug to the OpenSSH upstream and they replied as follows:

Yes - this is intentional.

ControlPath may contain %-expansions that need a hostname to expand fully.

We could conceivably check to see whether ControlPath actually needs this and make the hostname optional but 1) ControlPaths that use %h are common and 2) I'd rather not make the argument parsing code more of a maze than it already is.

References

  • The host argument at the end tells ssh what ControlMaster socket to remove if the ControlMaster is set up in a .ssh/config file. I could do ssh myhost (which sets of a ControlMaster socket) and later ssh -O exit myhost while still having other sockets active for other hosts in my configuration file. – Kusalananda Aug 10 '18 at 19:51
  • Right, that's was the feedback I received and what was described in the scenario form the upstream. – slm Aug 10 '18 at 19:52
0

I wrote a utility that eases management of SSH ControlMaster connections. It's called cmc: TimidRobot/cmc: ControlMaster Controller - Eases management of SSH ControlMaster connections.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.