DISCLAIMER: This has been written for educational purposes of learning about routing net traffic. I am not responsible for how you use this information. The title is clickbait only.
Avoiding geofencing can be done using a VPN. When using streaming services, however, it is often useful not to have that extra layer of encryption a VPN imposes for speed purposes. A SOCKS5 proxy allows us to forward traffic through another machine using only ssh
.
This article will outline the steps to set up a SOCKS5
proxy over ssh
on an Amazon Web Services instance in the US. The instance will be used to forward internet traffic from a machine with a foreign IP address to the host machine.
When we’re done here, running the command socks-XXX
in a terminal will launch a browser, where “what’s my ip” will return a US address.
The service can be run at zero cost providing
The basic steps, assuming a Linux/Mac host machine, are outlined below
16.04
was the LTS at the time of writing~/.ssh/config
filessh
tunnel using the proxy instancessh
tunnelYou’ll then be able to confirm the physical location of the IP address through “what’s my IP”. Note that a bug in Chrome means that to launch a Chrome session using the proxy, no other Chrome sessions can be open.
AWS have servers in several different countries for several reasons, i.e., so applications can route traffic more effectively. We’re going to exploit this by borrowing an IP address from a different country.
This means that any service sending web traffic to our borrowed IP address, sends it to a US address. Thus the traffic is geofenced to the US. From our home country, we can then read the data off the foreign machine, i.e., we ‘forward’ the traffic to the UK.
AWS is fairly generous with marking out exactly which options are free. Now, if you’re familiar with ssh
keys, feel free to continue on to the next section
SSH
keys.pem
key to set the instance up with and download itssh
into the AWS instance
ssh
command syntax is ssh -i /path/to/pem user@host
host
refers to the public IP address of the machine. This is found by clicking the instance in the AWS console and finding ‘Public IP’ in the detailsuser
is ubuntu
ssh -i ~/Downloads/key.pem ubuntu@54.192.170.23
~/.ssh/authorized_keys
on the instance.pem
to login, which is minorly more convienient to me.We add an ssh
alias for ease of using ssh
. Instead of the lengthy command that
was necessary previously, after adding an alias, we can log on to our remote
machine through ssh
simply by typing ssh <alias>
. Aliases are added by
adding new hosts (and configuring them) to the ~/.ssh/config
file. Copy and paste
the below block into the host terminal, with the URL you chose for your remote
machine through the DDNS.
# Add an ssh alias on host
# XXX should be a country code of the jumpbox's location
# The public IP address should be in the form xx.xx.xxx.xxx or similar
cat <<EOF>> ~/.ssh/config
Host XXX-Jumpbox
Hostname public-ip-address
User ubuntu
IdentityFile /path/to/public/key
EOF
This will set up an ssh
alias such that ssh XXX-Jumpbox
is all that is needed to open an ssh
pipe to the jumpbox. The alias will also work with tab completion.
NOTE: If your host machine isn’t running linux, 1) wot r u doin, 2) please refer to the link in the references to crack these last steps on other OSes
We now need a way to set up our ssh
tunnel to the proxy server, and launch a browser which is configured to connect to the web through the proxy server.
I added some functions to my ~/.bashrc
file to achieve this.
# Kill a process running on a port by name
port-kill () {
# Find offending process's port
{
# Truthy hack to handle error if no process with that name is found
ps -C $1 -o pid= &> /dev/null && port=$(ps -C $1 -o pid=)
} || {
echo "No process found with name $1"
return
}
# Get process name by port ID
process_name=$(ps -p ${port} -o comm=)
# Option to kill found process
read -r -p "Are you sure you want to kill ${process_name}? [y/N] " response
response=${response,,} # tolower
if [[ $response =~ ^(yes|y)$ ]]
then
kill ${port}
fi
}
# Access the web via a proxy server
#
# Must not have a google-chrome session open.
# Seems to be a bug in chrome that you can't force start with a new session
alias socks-XXX="ssh -D 1089 -f -C -q -N XXX-Jumpbox && google-chrome --proxy-server='socks5://localhost:1089'"
Breaking down the final aliases, socks-XXX
is composed of two statements.
ssh -D 1089 -f -C -q -N XXX-Jumpbox
We already know what ssh US-Jumpbox
does. Explaining the other flags
-D 1089
sets up [D]ynamic port forwarding on the local port 1089
through
ssh
-f
[f]orks the process and runs it in the background-C
[C]ompresses the data before sending it through the ssh
pipe-q
sends all STDOUT
and STDERR
messages to /dev/null
, i.e. it is
[q]uiet-N
[N]egates remote commands, which is good for just port forwarding (according to the ssh
manual)The final command is
google-chrome --proxy-server='socks5://localhost:1089'"
This command simply starts google chrome, however specifies that it connects to the web through a proxy server. We specify the SOCKS5
endpoint as localhost
at port 1089
, which we know is dynamically routing our web traffic through some other country.
Now all you have to do to is to run the command socks-XXX
in the terminal to launch a web browser, geofenced to another country. When done, tear down the tunnel using port-kill ssh
, or simply leave it running.
Thanks for reading,
Akhil
Unfortunately there seems to be a small bug in google-chrome
, where you cannot force the browser to run in a new session, so for the routing to work, chrome
cannot already be open. To get around this, use one browser reading traffic through the proxy, and other for general surfing.