SSH als VPN Tunnel einrichten Ubuntu

Aus Howtos und Gedankenstuetzen

Wechseln zu: Navigation, Suche

Inhaltsverzeichnis

Einrichtung Client zu Server

Server

Auf dem Server brauchen wir einen fertigkonfigurierten ssh-daemon, desweiteren muss das Kernelmodul "ppp" bzw. "ppp_generic" geladen sein.

# server:~$ modprobe ppp_generic
# server:~$ lsmod |grep ppp
ppp_generic         19476 0
slhc                6784 1 ppp_generic

Anlegen des "Tunnel Users"

Es ist erforderlich einen User und eine Gruppe auf dem Server anzulegen, der Name spielt dabei keine Rolle. Ich werde den User und die Gruppe einfach mal "tunnel" nennen.

# server:~$ groupadd tunnel
# server:~$ useradd -g tunnel tunnel


Setzen sie ein password für ihren tunnel User.

# server:~$ passwd tunnel
Enter new UNIX password: 
Retype new UNIX password: 
passwd: password updated successfully

Einloggen

Jetzt sollte man sich von dem Client aus einmal auf dem Server einloggen, damit man in die ~./ssh/known_hosts aufgenommen wird.

# client:~$ ssh server.exampel.com -l tunnel
tunnel@server password: 
Linux server 2.6.7-rc3 #1 Tue Jun 15 10:12:48 CEST 2004 i686 unknown No mail.
tunnel@server:~$

RSA Schlüssel generieren

So, jetzt werden wir nurnoch dafür sorgen, dass diese Password-Eingabe nicht mehr notwendig ist.
Note: Der RSA Schlüssen wird auf dem Client als user "root" angelegt.

client:~# ssh-keygen -b 768 -t rsa
Generating public/private rsa key pair.
Enter file in which to save the key (/root/.ssh/id_rsa):
An dieser Stelle geben sie den folgenden Pfad ein "/root/.ssh/identity"

Note: Bei der "passphrase" Abfrage drücke sie nur die Eingabetaste.

Enter file in which to save the key (/root/.ssh/id_rsa): /root/.ssh/identity
Enter passphrase (empty for no passphrase):
Enter same passphrase again:
Your identification has been saved in /root/.ssh/identity.
Your public key has been saved in /root/.ssh/identity.pub.
The key fingerprint is:
8f:f3:25:0b:e9:a2:41:33:ff:38:c9:51:21:a0:84:32 root@client
client:~#

Kopieren des Schlüssels

So, jetzt kopieren wir den Schlüssel (identity.pub) auf den Server, in das .ssh Verzeichnis des Users tunnel.

server:~# cd ~tunnel
server:~# mkdir .ssh
server:~# chown root.tunnel .ssh
server:~# chmod 755 .ssh
server:~# cd .ssh

Den Schlüssel "/root/.ssh/identity.pub" (auf dem Client) müssen sie jetzt nach "~tunnel/.ssh/authorized_keys" auf dem Server kopieren.
Sollte die Datei authorized_keys bereits vorhanden sein, dann fügen sie die Schlüsselzeile, die sich in der identity.pub Datei befindet, hinzu.

Note: Sie können beliebig viele Schlüssel in die .ssh/authorized_keys hinzufügen

Das tunnel-scriptes

ssh-tunnel.sh

#!/bin/sh

# Hier tragen sie den Auflösbaren Namen des Servers ein.
SERVER_HOSTNAME=server.example.com

# Hier tragen sie bitte den Tunnel user ein.
SERVER_USERNAME=tunnel

# Das wird die Tunnel-IP des Servers sein:
SERVER_IFIPADDR=192.168.100.2

# und die des Clients:
CLIENT_IFIPADDR=192.168.100.1

# Hier können sie dem ssh noch einige optionale Optionen übergeben.
LOCAL_SSH_OPTS="-i /home/tunnel/.ssh/id_rsa -P"


############ Ab Hier! bitte nichts mehr verändern! ###############

PATH=/usr/local/sbin:/sbin:/bin:/usr/sbin:/usr/bin:/usr/bin/X11/:

# Notwendige Anwendungen:

PPPD=/usr/sbin/pppd
SSH=/usr/bin/ssh

if ! test -f $PPPD  ; then echo "can't find $PPPD";  exit 3; fi
if ! test -f $SSH   ; then echo "can't find $SSH";   exit 4; fi


case "$1" in
  start)
    # echo -n "Starting vpn to $SERVER_HOSTNAME: "
    ${PPPD} updetach noauth passive pty "${SSH} ${LOCAL_SSH_OPTS} ${SERVER_HOSTNAME} -l${SERVER_USERNAME} -o Batchmode=yes sudo ${PPPD} nodetach notty noauth" ipparam vpn ${CLIENT_IFIPADDR}:${SERVER_IFIPADDR}
    # echo "connected."
    ;;

  stop)
        # echo -n "Stopping vpn to $SERVER_HOSTNAME: "
        PID=`ps ax | grep "${SSH} ${LOCAL_SSH_OPTS} ${SERVER_HOSTNAME} -l${SERVER_USERNAME} -o" | grep -v ' passive ' | grep -v 'grep ' | awk '{print $1}'`
        if [ "${PID}" != "" ]; then
          kill $PID
          echo "disconnected."
        else
          echo "Failed to find PID for the connection"
        fi
    ;;

  config)
    echo "SERVER_HOSTNAME=$SERVER_HOSTNAME"
    echo "SERVER_USERNAME=$SERVER_USERNAME"
    echo "SERVER_IFIPADDR=$SERVER_IFIPADDR"
    echo "CLIENT_IFIPADDR=$CLIENT_IFIPADDR"
  ;;

  *)
    echo "Usage: VPN {start|stop|config}"
    exit 1
    ;;
esac

exit 0

Sie sollten das script an eine Stelle kopieren die in $PATH liegt, z.B.: "/usr/local/bin".

Anpassen des tunnel-scriptes

Die Datei kann mit einem beliebigen Editor deiner Wahl angepasst werden.

SERVER_HOSTNAME=server.example.com
SERVER_USERNAME=tunnel
SERVER_IFIPADDR=192.168.100.2
CLIENT_IFIPADDR=192.168.100.1

Tunnel aufbauen

Nun können sie von ihrem Client aus das script ausführen.

Client:~$ ssh-tunnel.sh start
Using interface ppp0
Connect: ppp0 <--> /dev/pts/3
local  IP address 192.168.100.1
remote IP address 192.168.100.2

Bei Problemen

Wenn sie die Verbindung nicht aufgebaut bekommen, ist meist die firewall dran schuld. Das lässt sich am einfachsten mit "tcpdump -i <interface_name_ihrer_internet_Verbindung>" anzeigen. Sie sollten daher zusehen, dass die Pakete mit dem vom script verwendeten interface (entweder ppp0 oder ppp1...) nicht von der Firewall geblockt werden. Sollte ihr Server sich hinter einem router befinden, dann ist es zusätzlich erforderlich eine Port-Weiterleitung auf dem router zu aktivieren. Der router soll alle Anfragen die auf Port 22 eintreffen an ihren Server Port 22 weiterleiten.

Es kann aber auch zu Problemen führen, da sie in der Regel nicht die ausreichenden Rechte besitzen. Siehe sudo.

SUDO

sudo einrichten

Wenn man nun das Script startet bekommt man eine Fehlermeldung von sudo. Das liegt daran das nur root oder ein priveligierter Benutzer diese Befehle ausführen darf. Um nun denoch als user tunnel das Script ausführen zu können braucht es noch folgendes:

Server

als root

nano /etc/sudoers

Cmnd_Alias VPN=/usr/sbin/pppd
vpn ALL=NOPASSWD: VPN

Client

als root

ln /home/tunnel/tunnel.sh VPN

Wenn sie nun den VPN Tunnel mit

VPN start

aufrufen sehen sie das die Fehlermeldung nicht mehr auftaucht und das Script wird zu Ende ausgeführt. Dies liegt daran, dass wir bei dem Eintrag in die Sudoers Datei auf dem Server einen Command Alias eingetragen haben. (siehe oben). Da wir nun das Script über den SimLink VPN aufrufen greift auch der zweite Eintrag in /etc/sudoers und lässt uns das Script fehlerfrei zu Ende ausführen.

Starten beim booten

Entweder kopiert man das Script oder besser man erzeugt einen SimLink nach /etc/init.d/

cp /home/tunnel/tunnel.sh /etc/init.d
ln /home/tunnel/tunnel.sh /etc/init.d/VPN

Wenn man die echo Zeilen in der Start/Stop Anweisung auskommentiert sieht man im Bootvorgang auch die Starting bzw. done Nachrichten. Schreibe > /dev/null 2>&1 hinter die Zeile welche mit ${PPPD} beginnen. Dies verhindert das pppd mit verbose messages den Bootscreen zumüllt. Man kann ebenso hingehen und die Nachrichten in ein Logfile schreiben lassen (hilfreich fürs Troubleshooting).

Nun kann man das Script einfach mit allen 6 Runleveln verlinken.

ln -s /etc/init.d/vpn-pppssh /etc/rc0.d/K10vpn-pppssh
ln -s /etc/init.d/vpn-pppssh /etc/rc1.d/K10vpn-pppssh
ln -s /etc/init.d/vpn-pppssh /etc/rc2.d/S99vpn-pppssh
ln -s /etc/init.d/vpn-pppssh /etc/rc3.d/S99vpn-pppssh
ln -s /etc/init.d/vpn-pppssh /etc/rc4.d/S99vpn-pppssh
ln -s /etc/init.d/vpn-pppssh /etc/rc5.d/S99vpn-pppssh
ln -s /etc/init.d/vpn-pppssh /etc/rc6.d/K10vpn-pppssh

Wenn nun dein PC neu bootet sollte die VPN-verbindung aufgebaut werden (ziemlich am Ende des Boot Prozesses). Der Bootvorgang wird erst weiter abgearbeitet wenn die VPN-verbindung steht. Das kann evtl. zu Problemen führen wenn sich die Verbindung nicht aufbauen lässt (timeout). Wenn das stört kann man ein eigens /etc/init.d/VPN Script bauen welches das Script in /usr/local/bin/VPN im Hintergrund aufruft. Dieser Link wird erst aufgerufen bzw. die Verbindung aufgebaut, wenn der PC fertig gebootet hat.

Einrichtung Netz zu Netz

Forwarding

Als erstes muss man sich versichern, dass das Forwarden über das Interface erlaubt ist

echo 1 > /proc/sys/net/ipv4/ip_forward
echo 1 > /proc/sys/net/ipv4/conf/ppp1(1) /forwarding

Natürlich muss ppp1 mit dem gültigen Wert des VPN Interfaces getauscht werden. jeweils auf Client und Server mittels ifconfig.

Wenn man das Routing im Script mit übergeben will muss man es um folgende Einträge ergänzen:

# Hier tragen sie den Auflösbaren Namen des Servers ein.
SERVER_HOSTNAME=chaosfield.org

# Hier tragen sie bitte den Tunnel user ein.
SERVER_USERNAME=root

# Das wird die Tunnel-IP des Servers sein:
SERVER_IFIPADDR=192.168.100.2

# und die des Clients:
CLIENT_IFIPADDR=192.168.100.1
  
# Hier können sie dem ssh noch einige optionale Optionen übergeben.
 LOCAL_SSH_OPTS="-P -i /home/tunnel/.ssh/id_rsa"
  
#Netz zu Netz Verbindung --Routing
NET2=10.16.0.0
MASK=255.255.255.0
case "$1" in
 start)
   # echo -n "Starting vpn to $SERVER_HOSTNAME: "
   ${PPPD} updetach noauth passive pty "${SSH} ${LOCAL_SSH_OPTS} ${SERVER_HOST$
   route add -net ${NET2} netmask ${MASK} gw ${CLIENT_IFIPADDR}

   # echo "connected."
   ;;