SSH tunnels are very useful in server administration and development, and change SSH from being just a remote shell to being a tool that can overcome what might, from the point of view of a developer, be otherwise insurmountable networking challenges.

Basic Tunnels

Probably the simplest type of SSH tunnel is that which forwards a connection from a local port to a remote one. The example below opens port 9999 on the local machine and forwards it to port 443 on the remote machine.

ssh -L9999:localhost:443 user@server.example.com

This is useful for testing a service that the local machine might not have direct access to without changing firewall rules around or exposing ports any more widely than needed.

It is not necessary to stick to just connections local to the remote machine. For example, the following will forward connections from local port 9998 to web.example.com on port 443, with the connection originating from server.example.com.

ssh -L9998:web.example.com:443 user@server.example.com

Reverse Tunnels

Similarly useful is the ability to expose ports remotely and have them connect back to the local machine. The example below will accept local connections on the remote machine on port 3306 and forward them back to the originating machine. This is often useful to allow remote applications to connect back to development services running locally.

ssh -R3306:localhost:3306 user@server.example.com

It’s worth pointing out that by default the listening port is only bound to the local interface of the remote server.

Dynamic Tunnels and SOCKS

OpenSSH has a built-in SOCKS proxy, which can be insanely useful in some scenarios. Essentially, this allows a process running locally to access the network as if it is running on the remote server.

It’s probably most commonly used with by web browsers, but plenty of different software has the ability to use a SOCKS proxy to access network resources.

ssh -D8080 user@server.example.com

The command above opens an SSH connection to server.example.com, and starts listening to port 8080 on the local machine for SOCKS clients.

If you then configure your browser to use a SOCKS proxy of localhost:8080 then you can browse as if the browser were running on the remote server. This can be useful for all sorts of things, such as interacting with administration GUIs that would otherwise be inaccessible or appearing that you’re browsing from a different location.

Running SSH tunnels in the background

If the connection is just used simply to tunnel network traffic and there’s no need for an interactive session, then adding the -N switch to the command will make it a non-interactive session, and adding -f will cause it to run in the background after the connection is made.

ssh -Nf -L9999:localhost:443 user@server.example.com

Obviously this will then leave a process running in the background that will need to be killed in order to end the SSH connection.

Turning off SSH tunnels

The sheer flexibility of SSH tunnels means they can be used to circumvent network security controls and the like. Additionally, the flexible nature of them can make it hard to reason about exactly what impact leaving them enabled might have. If there’s no specific use for them in an environment, disabling the ability to set up SSH tunnels in the first place should be strongly considered.

Luckily, this is pretty easy, and is done in the sshd_config file.

AllowTcpForwarding no
AllowStreamLocalForwarding no
GatewayPorts no
PermitTunnel no

Remember, however, this can restrict the ability of your administrators to work around problems in a crisis. Like all security, it’s about striking the right balance for your organisation.

Key-based Authentication and ssh-agent

Given how useful SSH tunnels can be, it’s well worth spending the time to configure key based authentication and ssh-agent. This removes the requirement to repeatedly type passwords over and over again, and can significantly improve security when password authentication is turned off entirely.

And much, much more

Of course, this is only scratching the surface of what’s possible with SSH tunneling, and the manual pages are well worth reading.