madbeer
01-17-2008, 10:43 PM
Hi everyone!
I know a lot of you already know this, but I thought it would be a good idea to have a thread on ssh tunneling -- something I find very useful. I will start with simple tunneling and get into more advanced techniques as time passes. Before we start its worth mentioning some definitions of terms that are thrown around a lot when people talk about tunneling:
===DEFINITIONS===
Tunnel: to encapsulate specified traffic into an existing connection. You can think of it like this: Lets say you want to send letter (regular mail not EMAIL) to your mailmans wife, but you donnt want him to know that you are doing this :naughty:. Normally you would just adress the envlope to the mailmans wife, but he could simply look at the letter and know it was from you destined for his wife. What I could do (in this contrived example) is have an outer envelope, that was addressed to a third person, and put inside of it my envelope destined for the mailman's wife. This third party would get the letter, open it, take out our original letter destined for the mailmans wife, and send it to her from HIS house. (I hope this example helps)
Proxy: something that acts on behalf of you. example: if you are too shy to hit on a girl, so you have your friend go up to her and speak for you. He is your proxy
Socket: something your operating system provides for communication. The OS handles the lower level things we dont care about now(ARP, IP, TCP). When you want to open google.com, your web browser (amongst other things) has to open a socket so it can send/receive (sockets are full duplex iirc) information to www.google.com. You can think of your cellphone as being a socket. you punch your friends number into it and it connects you to him, and you both speak and hear things through it.
Port: a virtual 'address' that sockets bind to. Some ports require super user privileges (1-1025) and the rest any user of the OS can use (1025-65535). For instance. Your ssh server will listen on port 22 by default. However, there is nothing preventing you from configuring ssh to listen on a different port. You cannot have 2 programs listening on the same port.
SOCKS: an abbreviation for SOCKetS. It is a protocol that allows an external computer to access internal sockets, effectively making the SOCKS server a proxy.
Shell: the command interpreter used on operating systems. When you open up command.com in windows or /bin/bash on *nix, you are interfacing with a shell. You type commands and it gives you output.
SSH (secure Shell): a protocol that allows for secure remote shell access (and much more)
====END DEFINITIONS====
So why would anyone want to proxy socket connections? Well let me give you 2 simple reasons (many better ones exist):
1) your network has a restrictive browsing policy. they wont let you access miniclip.com or facebook.com at work. those bastards!
2) your ISP interferes with your p2p communications. those bastards!
So now you are wondering how can I set this "tunneling" shit up?!?
=====Configuration=====
This is where things get hairy, so Im not really going to talk about port forwarding/firewalling or installing services. You just need a machine (either at home or a friends house or another country) that is running sshd. Linux usually comes with an SSH server installed by defualt. what you will want to do on your SSH server is the following:
log in to the linux machine (or other *nix) as root (or use sudo if you have it set up), and run:
#echo "1" > /proc/sys/net/ipv4/ip_forward
this allows your machine to forward traffic on behalf of other machines
then you need to edit your sshd configuration file (/etc/ssh/sshd_config), and make sure these you have these lines in there:
AllowTcpForwarding yes
GatewayPorts yes
then after modifying the file, you need to restart ssh:
#/etc/init.d/sshd restart
===END CONFIGURATION====
So now that you have your ssh server set up, you need to access it from your ssh client. For windows I recommend PuTTy and for *nix/osx I use the command line openssh client (built-in most likely)
===TUNNELING===
So now the good stuff. in the first example, I am trying to browse to web sites that are blocked at work. What I will do is use my SSH server as a SOCKS proxy and forward all my web traffic to my SSH server.
### first example###
start ssh like this:
$ ssh -2 -D 1234 [email protected] -p 22
where user is the username you have setup and host.com is the domain name or IP address of your ssh server.
the -2 options forces ssh to use version 2 of the protocol (version 1 has vulnerabilities)
the -D 1234 option forces the ssh server to set up 'D'ynamic application-level port forwarding. from the Manual: "Whenever a connection is made to this port, the connection is forwarded over the secure channel, and the application protocol is then used to determine where to connect to from the remote machine. Currently the SOCKS4 and SOCKS5 protocols are supported, and ssh will act as a SOCKS server."
the -p option allows us to specify what port our ssh server is listening on.
after issuing this command, your local machine will open a socket that is listening on port 1234. We then instruct our web browser to use 127.0.0.1 as a SOCKS proxy, with a port of 1234. This forces all web traffic to go over the ssh tunnel, so all websites you visit think you are browsing from your tunnel endpoint.
###second example###
lets say your ISP is messing with your traffic, and they are preventing you from seeding (who would do such a thing!), or you want to host a webserver at your house but your ISP is preventing you from doing so. For this example however, I will detail how to set up Azureus to use a proxy
you would execute the following ssh command:
$ ssh -2 -R 50000:localhost:50000 -D 1234 [email protected] -p 22
the only thing different here in comparison with our first example is:
-R 50000:localhost:50000
and this does the following:
"Specifies that the given port on the remote (server) host is to be forwarded to the given host and port on the local side. This works by allocating a socket to listen to port on the remote side, and whenever a connection is made to this port, the connection is forwarded over the secure channel, and a connection is made to host port hostport from the local machine."
This makes our SSH server listen on port 50000, and forward all traffic to port 50000 on our local machine.
So now we set up azurerus as following:
Under Options-> Connection, set your TCP listen port to 50000
then under Options-> Connection->proxy options, click Enable proxying of tracker communications, and click "I have a socks proxy", and enter 127.0.0.1 for the host, and the port is 1234. Leave the username and password field blank.
you can also proxy peer communications (outgoing only :( )
====END TUNNELING====
I tried to be as clear as poosible, but since this is a rough draft I will be making changes regularly. I hope this was of help to some people!
I am open for any critisisms and/or suggestions.
Happy Tunneling!
bEER
I know a lot of you already know this, but I thought it would be a good idea to have a thread on ssh tunneling -- something I find very useful. I will start with simple tunneling and get into more advanced techniques as time passes. Before we start its worth mentioning some definitions of terms that are thrown around a lot when people talk about tunneling:
===DEFINITIONS===
Tunnel: to encapsulate specified traffic into an existing connection. You can think of it like this: Lets say you want to send letter (regular mail not EMAIL) to your mailmans wife, but you donnt want him to know that you are doing this :naughty:. Normally you would just adress the envlope to the mailmans wife, but he could simply look at the letter and know it was from you destined for his wife. What I could do (in this contrived example) is have an outer envelope, that was addressed to a third person, and put inside of it my envelope destined for the mailman's wife. This third party would get the letter, open it, take out our original letter destined for the mailmans wife, and send it to her from HIS house. (I hope this example helps)
Proxy: something that acts on behalf of you. example: if you are too shy to hit on a girl, so you have your friend go up to her and speak for you. He is your proxy
Socket: something your operating system provides for communication. The OS handles the lower level things we dont care about now(ARP, IP, TCP). When you want to open google.com, your web browser (amongst other things) has to open a socket so it can send/receive (sockets are full duplex iirc) information to www.google.com. You can think of your cellphone as being a socket. you punch your friends number into it and it connects you to him, and you both speak and hear things through it.
Port: a virtual 'address' that sockets bind to. Some ports require super user privileges (1-1025) and the rest any user of the OS can use (1025-65535). For instance. Your ssh server will listen on port 22 by default. However, there is nothing preventing you from configuring ssh to listen on a different port. You cannot have 2 programs listening on the same port.
SOCKS: an abbreviation for SOCKetS. It is a protocol that allows an external computer to access internal sockets, effectively making the SOCKS server a proxy.
Shell: the command interpreter used on operating systems. When you open up command.com in windows or /bin/bash on *nix, you are interfacing with a shell. You type commands and it gives you output.
SSH (secure Shell): a protocol that allows for secure remote shell access (and much more)
====END DEFINITIONS====
So why would anyone want to proxy socket connections? Well let me give you 2 simple reasons (many better ones exist):
1) your network has a restrictive browsing policy. they wont let you access miniclip.com or facebook.com at work. those bastards!
2) your ISP interferes with your p2p communications. those bastards!
So now you are wondering how can I set this "tunneling" shit up?!?
=====Configuration=====
This is where things get hairy, so Im not really going to talk about port forwarding/firewalling or installing services. You just need a machine (either at home or a friends house or another country) that is running sshd. Linux usually comes with an SSH server installed by defualt. what you will want to do on your SSH server is the following:
log in to the linux machine (or other *nix) as root (or use sudo if you have it set up), and run:
#echo "1" > /proc/sys/net/ipv4/ip_forward
this allows your machine to forward traffic on behalf of other machines
then you need to edit your sshd configuration file (/etc/ssh/sshd_config), and make sure these you have these lines in there:
AllowTcpForwarding yes
GatewayPorts yes
then after modifying the file, you need to restart ssh:
#/etc/init.d/sshd restart
===END CONFIGURATION====
So now that you have your ssh server set up, you need to access it from your ssh client. For windows I recommend PuTTy and for *nix/osx I use the command line openssh client (built-in most likely)
===TUNNELING===
So now the good stuff. in the first example, I am trying to browse to web sites that are blocked at work. What I will do is use my SSH server as a SOCKS proxy and forward all my web traffic to my SSH server.
### first example###
start ssh like this:
$ ssh -2 -D 1234 [email protected] -p 22
where user is the username you have setup and host.com is the domain name or IP address of your ssh server.
the -2 options forces ssh to use version 2 of the protocol (version 1 has vulnerabilities)
the -D 1234 option forces the ssh server to set up 'D'ynamic application-level port forwarding. from the Manual: "Whenever a connection is made to this port, the connection is forwarded over the secure channel, and the application protocol is then used to determine where to connect to from the remote machine. Currently the SOCKS4 and SOCKS5 protocols are supported, and ssh will act as a SOCKS server."
the -p option allows us to specify what port our ssh server is listening on.
after issuing this command, your local machine will open a socket that is listening on port 1234. We then instruct our web browser to use 127.0.0.1 as a SOCKS proxy, with a port of 1234. This forces all web traffic to go over the ssh tunnel, so all websites you visit think you are browsing from your tunnel endpoint.
###second example###
lets say your ISP is messing with your traffic, and they are preventing you from seeding (who would do such a thing!), or you want to host a webserver at your house but your ISP is preventing you from doing so. For this example however, I will detail how to set up Azureus to use a proxy
you would execute the following ssh command:
$ ssh -2 -R 50000:localhost:50000 -D 1234 [email protected] -p 22
the only thing different here in comparison with our first example is:
-R 50000:localhost:50000
and this does the following:
"Specifies that the given port on the remote (server) host is to be forwarded to the given host and port on the local side. This works by allocating a socket to listen to port on the remote side, and whenever a connection is made to this port, the connection is forwarded over the secure channel, and a connection is made to host port hostport from the local machine."
This makes our SSH server listen on port 50000, and forward all traffic to port 50000 on our local machine.
So now we set up azurerus as following:
Under Options-> Connection, set your TCP listen port to 50000
then under Options-> Connection->proxy options, click Enable proxying of tracker communications, and click "I have a socks proxy", and enter 127.0.0.1 for the host, and the port is 1234. Leave the username and password field blank.
you can also proxy peer communications (outgoing only :( )
====END TUNNELING====
I tried to be as clear as poosible, but since this is a rough draft I will be making changes regularly. I hope this was of help to some people!
I am open for any critisisms and/or suggestions.
Happy Tunneling!
bEER