The poor man's anonymizing VPN tunnel using SSH and pppd

by Rudd-O published 2007/05/15 02:37:55 GMT+0, last modified 2013-06-26T03:24:19+00:00

Want to create a quick 'n dirty secure tunnel between your computer and a remote SSH server? Now you can.

/usr/sbin/pppd pty "ssh -t -e none -o 'Batchmode yes' \
/usr/sbin/pppd" local nodetach silent \

This is all you need to create a secure tunnel between your computer and a computer that has the SSH running (in the example, on the Internet.

Once you run this command, both your local and your remote computers will have new PPP network interfaces:

  • Local: interface ppp0, IP address
  • Remote: interface ppp0, IP address

But a few quick and easy preparations are needed in order to run and take advantage of this kind of tunnel.

The SSH server installed on the server, pppd on both machines

This should be self-explanatory. Use your Linux distribution's package management tools to install them -- should take less than 1 minute.

The right pppd configuration

You use the /etc/ppp/options file to configure it. Most options, once set in the configuration file, cannot be overriden in the command line.

On the server's /etc/ppp/options file


On the client's /etc/ppp/options file


The right security configuration

[ #] /usr/sbin/groupadd -r ppp
...(add your SSH login user name to the ppp group in /etc/group)...
chown root.ppp /usr/sbin/pppd
chmod 750 /usr/sbin/pppd
chmod +s /usr/sbin/pppd

Now only members of the ppp group (namely, you) can join the fun.

SSH public key authentication enabled

  • Put PubkeyAuthentication yes in the server's /etc/ssh/sshd_options.
  • Generate an SSH key pair in your computer.
  • Upload the public key of the generated pair to your server's ~/.ssh/authorized_keys2 file. Don't forget to chmod 600 that file, or else SSH won't even look at it.

That's it!

Now run the following command on your computer:

/usr/sbin/pppd pty "ssh -t -e none -o 'Batchmode yes' \
/usr/sbin/pppd" local nodetach silent \

What this command basically does is start pppd locally, tell it to connect via SSH in batch mode (using the public key, so it doesn't ask for your password), start pppd on the remote server, and use the SSH connection as their conversation path.

Wait a few seconds. pppd will utter a few things:

Using interface ppp0
Connect: ppp0 <--> /dev/pts/7

You will have to confirm that the PPP interface is up:

[youruser@yourcomputer $] /sbin/ifconfig ppp0
ppp0      Link encap:Point-to-Point Protocol
          inet addr:  P-t-P:  Mask:
          RX packets:5 errors:0 dropped:0 overruns:0 frame:0
          TX packets:5 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:3
          RX bytes:75 (75.0 b)  TX bytes:69 (69.0 b)

Now you can ping If pinging fails, check the firewall rules on both the server and your computer.

To interrupt the tunnel, hit Ctrl+C on the terminal that holds the running pppd command.

What next?

Bringing the tunnel up is actually one part of the deal. If you're like me, perhaps you'll want to actually carry all of your network traffic across the tunnel.

Set up the remote server to route traffic for you

This is easy. On the server, either:

  • set firewall rules that will do NAT between the PPP interface and the Internet; or
  • replace noproxyarp with proxyarp in the (server's) /etc/ppp/options file; then set aside an extra IP address in the (server's) local network; then use it as the remote endpoint in the pppd command. If your server has IP address, then provision and use it instead of

Set the default route to be the tunnel's remote endpoint

If you want to route all of your network traffic through your newly created PPP link, you need to do two steps in this order:

  1. Manually add a route to your server, so the SSH traffic knows the physical route it should follow. If the IP address of your current default route is, then run route add gw
  2. Replace the default route. Run route add default gw dev ppp0

Before you suggest the pppd's defaultroute option: no, it won't work, because it'll disrupt the only communication route between your computer and the remote SSH server.

Perhaps you'd like to add manual, shorter routes to your DNS servers -- otherwise Web browsing may get a little slow. You know, due to the latency of the tunnel and stuff...

After doing this:

  • your computer will send all (SSH) traffic to through your regular default route, so the tunnel keeps working fine;
  • the rest of the traffic will go through the PPP interface (notice we named the remote IP address in the default route command?)

Combine this with the proxyarp option on the server, and you have a recipe to make your computer appear as a completely different computer on the Internet. Perfect for anonymizing your real computer!