Tuesday, June 5, 2012

Bypassing Firewalls - Reverse SSH Tunneling

Have you ever found yourself in the situation where you need remote access to internal resources but don’t have the time (or maybe authority) to make changes to the network firewall?  If so, you are in luck!

This tutorial shows how SSH can be used to connect to machines that are not accessible via the internet without 1-to-1 NAT, firewall exceptions, etc...  With this you can bypass NAT and incoming FIREWALL restrictions.  Examples of when this would be used include: getting a remote shell on a firewall’d server (see diagram below), establishing VNC or RDP sessions to NAT’d servers (see guide below), etc...



Essentially, this can be used to remotely connect to any locally listening ports and to communicate with the services that run on them.  Lets get started...

Command

ssh -f -N -R [bind_address:]port:host:hostport user@rhost -p 22

-f        SSH to go to background just before command execution.
Note: If ExitOnForwardFailure = yes in /etc/ssh/ssh_config, then SSH will go into the background just after establishing the connection.

-N      Do not execute remote command.             

-R      Specifies that the given port on the remote (server) host is to be forwarded to the 
          given host and port on the local side.

                             port         Port to be opened on remote machine

                             host         IP or hostname of remote machine

                             hostport   Local port target for remote machine opened port traffic

-p      Remote SSH port

Example

The following command should be run on Server A (the one that is not publicly accessible). 
Note: VNC server should be running on Server A, listening locally on port 5000.

ssh -f -N -R 31337:localhost:5000 user@remote.example.com -p 22
  1. Server A is running VNC - on filtered port 5000 (privately accessible)
  2. Server B is running SSH - on open port 22 (publicly accessible)
  3. Server A establishes remote SSH connection to Server B via port 22
  4. Server B opens specified port - in this case we are opening 1337
  5. Server B will now forward all traffic destined for port 1337 to port 22
  6. Server B will now continue to forward the traffic through the original tunnel
  7. Server A will now forward all incoming traffic from the original tunnel to port 5000
  8. Server B is now ready to connect to the remote VNC session.
  9. Server B connects using tightvnc - vncviewer localhost:1337 
Simple Script

#-------------------------------------------------------------------------------------------------------------------
#!/bin/bash
#
#Reverse SSH Script
echo ------------Reverse SSH Connection---------------
echo establishes a reverse connection to THIS machine
echo -n Remote User: 
read ruser
echo -n Remote Host: 
read rhost
echo -n Remote SSH Port: 
read rssh
echo -n Port to Open on Remote Host: 
read rport
echo -n Local User:
read luser
echo -n Local Port: 
read lport
echo COMMAND OUTPUT: ssh -f -N -R $rport:localhost:$lport $ruser@$rhost -p $rssh
echo ACCESS COMMAND on $rhost: ssh $luser@localhost -p $rport
ssh -f -N -R $rport:localhost:$lport $ruser@$rhost -p $rssh
echo DONE!
exit
#-------------------------------------------------------------------------------------------------------------------