SSH Tunneling

Arjen de Vries

Sometimes you find yourself stuck behind a firewall or proxy when trying to connect to a remote desktop session of a user or a remote machine.

In this short tutorial I’ll show you how to ‘tunnel’ your way out.

An SSH tunnel is an encrypted tunnel created through an SSH protocol connection. Users may set up SSH tunnels to transfer unencrypted traffic over a network through an encrypted channel. For instance, if you would like to connect to a unencrypted vnc session through the internet or another untrusted network you could create a tunnel and connect to your vnc session via the encrypted tunnel.

First the basics: We would like to setup a encrypted tunnel from “” to “” on port 3389

To do this we’ll use the following ssh line on

$ssh -L 1234:localhost:5901

the command above explained:

-L localport:host:remoteport

localport = port on the machine we are connecting from (should be above 1024 or you should be a privileged user) in this example 1234 is an unused port.

host = the host we want to be the endpoint of our tunnel. This can be the localhost (which is the host we are connecting to) or a machine which is reachable from the host we are connecting from.

remoteport = the port we want our localport data to be forwarded to. In this example port 5901 (a vnc session).

If everything works as intended you can add the following options to make the tunnel go to the background:

-f = go into the background just before executing the command. This allows for asking for password etc. before going to the background.

– N = Do not execute a remote command.

After successfully setting up the tunnel you can connect to your remote vnc session via the encrypted tunnel with the following command:

$vncviewer localhost:1234

That’s it, the very basics of tunnelling.
But what happens when you are on and the other host is in a different location which is only reachable via the internet through a jumphost called
In this case the tunnelling line changes a bit:

ssh -L

In this situation we are forwarding port 1234 to port 5901 on via

Sometimes it’s not possible to directly connect from to because of firewall restrictions. If is allowed to connect to directly but not the other way round, you can setup a remote port forward.
Of course you need a way to connect to via either a jumphost or local access etc.
Remote port forward (specified with “-R”) specifies that the given port on the remote host ( is to be forwarded to the given host and port on the local side (

On the remote host (

ssh -R 1234:localhost:5901

Now it’s possible on to connect to port 1234 and you will be forwarded to port 5901

vncviewer localhost:1234

You could even enable the Gatewayports option in sshd_config so that you can connect to the forwarded port on Use this with caution: it could mean that you open up a unwanted “hole” in the firewall, especially if the isn’t firewalled. Also when creating tunnels, keep in mind that other local users on can also connect on your local port.

In the last example we’ll make it a bit more complicated: needs to connect to is on a firewalled network only able to connect to the internet via a proxy. can only connect to via the jumpserver (also via the proxy).

A simple overview: -> -> ->

The jumphost has a ssh client listening on port 443. (so that the proxy allows the connection)

To connect trough the proxy you could use corkscrew:

After installing corkscrew on add the following to your .ssh/config:

$vi .ssh/config
Host hostc
     ProxyCommand /home/exampleuser/bin/corkscrew 8080 %h %p

Now we can create the tunnel like this:

hosta$ ssh -L user@hostc -p 443

Now you can connect to your vnc session on from

hosta$ vncviewer localhost:1234

These are the most common ways to tunnel via ssh, there are of course a lot more possibilities. For more info check the ssh man pages or google.


you might also like