Reverse Tunneling

Introduction
You sometimes visit a campus lab, internet cafe ... and you want your computer (notebook) there to connect to your ssh daemon at your home, dorm ... (destination), but the destination is behind NAT (Network Address Translation, IP masquerade) or firewall, blocking connections to your destination machine.

Fortunately you somehow happened to be able to initiate a TCP connection to some other computer (the middle) from both computers (notebook and destination) where you have UNIX accounts.

Preconditions

 * the notebook can connect to port 10000 (or any other) on the middle
 * the middle is running an ssh daemon willing to do port-forwarding (enabled by default in OpenSSH) and the GatewayPorts feature is enabled
 * you have an account on the middle
 * you can open an ssh connection from destination to the middle in advance (and leave it open) or you have someone do it on your behalf
 * the SSH daemon is running on destination on port 22. In fact the port can be arbitrary and the daemon does not have to allow port forwarding. You can even establish your own (not root) ssh daemon.

You do not need root privileges on any of these machines.

If you need to use port <1024 on the middle, you would need to be root there.

Creating the Tunnel
All you have to do is create a tunnel from the middle to destination.

On destination, using an ssh client, login to middle and open a tunnel from port 10000 on middle to port 22 on destination.

or

This will open port 10000 for listening and forward all future connections to port 22 at destination.


 * Do not close this session and make sure it will not close itself due to inactivity (see /etc/ssh/sshd_config below)
 * Go wherever you want with your notebook and point your ssh client to port 10000 on middle. Use the user/password pair on destination.


 * You are now logged in the destination. Enjoy.

Turn on -X or -Y for X-Forwarding, and you can run X apps on your local machine through the tunnel!

Avoiding Timeouts with keep-alive
We must make sure that we can hold an SSH session without timing out. This way, when we leave home, we know that the connection won't just die. So, edit the (destination) file on the server as shown:

Enabling GatewayPorts
If you want to use the above given example, the SSH daemon running on middle must be set to allow the GatewayPorts feature. To make this possible, edit the as follows. Don't forget to restart the ssh server after making these changes!

This makes it possible that forwarded ports on middle can be reached from another host. If you do not have the necessary privileges to make these changes, you can still log on to middle directly and then reach destination by opening a ssh connection to localhost -p 10000. That means, instead of:

You have to call:

Use the user/password pair on middle.

and then:

Use the user/password pair on destination.

Alternatives

 * app-shells/rrs: Reverse Remote Shell. Supports Encryption. Another way to do things, rrs has the advantage that when you close down a connection from your computer (say by accident) it will start trying to connect to you again. This behaviour can be emulated with ssh by putting it in a script or in crontab.
 * autossh is a program to start a copy of ssh and monitor it, restarting it as necessary. See autossh.
 * harms is a 4-port-forwarding application that's doing exactly the same
 * sshto: multihop ssh wrapper using UUCP-style host1!host2!host3 notation