Ibland så behöver man ha möjlighet att komma åt sin server som sitter bakom någon typ av brandvägg. Har man åtkomsten till konfigureringen av brandväggen så är det egentligen inte ett problem men ibland så har man inte kontroll över filtreringen. T.ex om man har en dator uppkopplad via 3G så blockerar leverantören åtkomsten då maskinen sitter bakom leverantörens brandvägg och ibland även på ett NAT-nät. Normalt har man öppen åtkomst ut från maskinen och detta öppnar för en annan typ av lösning som är en punkt-till-punkt anslutning via ssh så trafiken är krypterad. Ett exempel är en maskin som sitter i någon sommarstuga och har åtkomst till nätet via en 3G-dongle som man vill ha möjlighet att komma åt.
Vad man gör är att öppna en ssh mellan server och en maskin som du har nätåtkomst till, därefter startas en tunnel inne i sshkopplet i andra riktningen så att man kan via den få åtkomst till servern bakom brandväggen.
Ett exempel, jag vill ha möjlighet att komma åt ssh (port 22) på server1 från klient1, där server1 är maskinen bakom brandvägg och klient1 är den du har åtkomst till.
- en ssh anslutning skapas från server1 till klient1
- via shh anslutningen skapas en tunnel mellan port 2222 på klient1 till port 22 på server1
- på klient1 startas en ssh mot localhost port 2222
- tunneln skickar anropet som den får på port 2222 till port 22 på server1
- server1 hantera anropet på port 22 som en inlogging på server1
- om du angav rätt användare och lösenord så är du nu inloggad via en ssh på klient1 på server1
För att lösa detta finns två problem
- Hur loggar jag in från servern till klienten utan ha ha blankt lösenord?
- Hur håller jag tunneln öppen om förbindelsen går ner då jag inte kan logga in på servern och starta om tunneln.
Då vi kommer att arbeta med två datorer i denna artikel så kommer jag att använda namnet server för den dator som finns bakom brandväggen och namnet klient på den dator som du har tillgång till.
Att logga in utan lösenord har varit löst ganska länge på Unix/Linux system. Genom att använda en privat och en publik ssh-nyckel kan man logga in utan lösenord. Den privata ska den som ska initiera inloggningen (den som startar ssh anslutningen) ha och den publika behöver mottagaren för att verifiera att du är du. Den privata nyckel kan förses med ett lösenord för att skapa en extra nivå av säkerhet. I detta fall så kommer vi att köra utan lösenord på nycken annars är vi tillbaka till ruta ett, hur kan vi logga in utan att mata in lösenordet men nu behöver vi inte lämna mottagarsidan öppen. Man generera en unik nyckel med kommandot ssh-keygen, observera att man genererar en ny nyckel varje gång man kör kommandot så om du kör det igen får du upprepa proceduren att flytta över den publika nyckeln till klienten. Dessa kryptonycklar sparas i hemmakatalogen i en gömd katalog som heter .ssh, vi börjar med att generera nycklarna, viktigt är att man kör det som användaren som ska initiera ssh uppkopplingen då den måste ha tillgång till nycklarna.
Följande kommandon ska utföras på server om det inte står något annat.
Det först vi behöver göra är att generera nycklarna som ska användas, viktigt är att ange blank “passphrase” annars kommer den inte att fungera, kör ssh-keygen
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 |
pi@rpi ~ $ ssh-keygen Generating public/private rsa key pair. Enter file in which to save the key (/home/pi/.ssh/id_rsa): Enter passphrase (empty for no passphrase): Enter same passphrase again: Your identification has been saved in /home/pi/.ssh/id_rsa. Your public key has been saved in /home/pi/.ssh/id_rsa.pub. The key fingerprint is: 94:92:05:ca:d6:05:6d:01:4c:6a:9c:d9:c2:b0:09:b6 pi@rpi The key's randomart image is: +--[ RSA 2048]----+ |... o==+. | |...B B.+o. | | Eo % =.o | | o . o | | S | | | | | | | | | +-----------------+ |
Nu finns 2 filer i .ssh katalogen
- id_rsa – din privata nyckel, den lämnar man aldrig ut
- id_rsa_pub – din publika nyckel, används på mottagande sida för att identifiera dig
Nu ska vi kopiera den publika nyckeln till klientmaskinen, man hade kunna fyttat över den manuellt och lagt till den men som tur är finns ett kommando som gär allt-i-ett, ssh-copy-id, pi@klient.nimmis.se är användarnamn och adress till datorn klient precis som när man loggar in normalt med ssh
1 2 3 4 5 6 7 |
pi@rpi ~ $ ssh-copy-id -i .ssh/id_rsa.pub pi@klient.nimmis.se pi@klient.nimmis.se's password: Now try logging into the machine, with "ssh 'pi@klient.nimmis.se'", and check in: ~/.ssh/authorized_keys to make sure we haven't added extra keys that you weren't expecting. |
Pröva att logga in på klienten igen
1 |
ssh pi@klient.nimmis.se |
denna gång ska du inte få någon fråga om lösenord utan du ska komma in direkt
1 2 3 4 5 6 7 8 9 10 11 12 13 |
pi@rpi ~ $ ssh pi@klient.nimmis.se Linux shellbox 3.18.11+ #781 PREEMPT Tue Apr 21 18:02:18 BST 2015 armv6l The programs included with the Debian GNU/Linux system are free software; the exact distribution terms for each program are described in the individual files in /usr/share/doc/*/copyright. Debian GNU/Linux comes with ABSOLUTELY NO WARRANTY, to the extent permitted by applicable law. Last login: Thu Jul 23 20:34:29 2015 from host-95-197-66-112.mobileonline.telia.com pi@shellbox ~ $ exit logout Connection to klient.nimmis.se closed. |
Nu har vi löst problem 1, dax för problem 2, som tur var finns det redan en lösning för att hantera uppkopplingar som kan gå ner som heter autossh (http://www.harding.motd.ca/autossh/). Programmet övervakar uppkopplingen och om länken gått ner, startar om uppkopplingen helt automatiskt. Så då installerar vi det
1 |
sudo apt-get install autossh |
Kommandosyntaxen för tunneln är något som nedan
autossh -M 20000 -o “PubkeyAuthentication=yes” -o “PasswordAuthentication=no” -i /home/pi/.ssh/id_rsa -R 2222:localhost:22 pi@klient.nimmis.se
- -M 20000 är en monitor port, valfri men välj ett som inte används och över 1000 om du in kör det som root
- -o “PubkeyAuthentication=yes” använd ssh nyckeln för inloggning
- -o “PasswordAuthentication=no” använd aldrig lösenord, förhindrar att något hänger sig och väntar på input
- -i /home/pi/.ssh/id_rsa anger vart ssh-nyckeln finns, använd alltid fullständig sökväg om du skulle starta den som root
- -R 2222:localhost:22 anger klient port 2222 och server port
- pi@klient.nimmis.se inloggninguppgifterna för användarn som vi satte upp publika nyckeln för
Då kan vi testa om det verkar fungera
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
pi@rpi2 ~ $ autossh -M 20000 -o "PubkeyAuthentication=yes" -o "PasswordAuthentication=no" -i /home/pi/.ssh/id_rsa -R 2222:localhost:22 pi@klient.nimmis.se Linux shellbox 3.18.11+ #781 PREEMPT Tue Apr 21 18:02:18 BST 2015 armv6l The programs included with the Debian GNU/Linux system are free software; the exact distribution terms for each program are described in the individual files in /usr/share/doc/*/copyright. Debian GNU/Linux comes with ABSOLUTELY NO WARRANTY, to the extent permitted by applicable law. Last login: Sat Aug 8 10:48:25 2015 from host-78-78-21-247.mobileonline.telia.com pi@shellbox ~ $ netstat -an | grep LIST tcp 0 0 0.0.0.0:1723 0.0.0.0:* LISTEN tcp 0 0 127.0.0.1:20000 0.0.0.0:* LISTEN tcp 0 0 127.0.0.1:2222 0.0.0.0:* LISTEN tcp 0 0 0.0.0.0:22 0.0.0.0:* LISTEN tcp6 0 0 ::1:20000 :::* LISTEN tcp6 0 0 ::1:2222 :::* LISTEN |
Här kan man se att klientmaskinen lyssnar på port 2222, så alla som kan komma åt port 2222 på den maskinen kan använda tunneln, man behöver inte var lokalt inloggad på den för att det ska fungera.
Logga in på klientmaskinen och kör följande kommando, använd en användare på server och motsvarande lösenord, i exemplet loggar jag in på användare pi på server.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
kjell@shellbox ~ $ ssh pi@localhost -p 2222 The authenticity of host '[localhost]:2222 ([::1]:2222)' can't be established. ECDSA key fingerprint is b5:e9:fa:c5:ee:9f:ea:32:0d:62:92:4b:b7:54:87:0d. Are you sure you want to continue connecting (yes/no)? yes Warning: Permanently added '[localhost]:2222' (ECDSA) to the list of known hosts. pi@localhost's password: Linux rpi2 3.18.11-v7+ #781 SMP PREEMPT Tue Apr 21 18:07:59 BST 2015 armv7l The programs included with the Debian GNU/Linux system are free software; the exact distribution terms for each program are described in the individual files in /usr/share/doc/*/copyright. Debian GNU/Linux comes with ABSOLUTELY NO WARRANTY, to the extent permitted by applicable law. Last login: Sat Aug 8 10:49:10 2015 from localhost pi@rpi2 ~ $ |
Som du ser kom vi inte på server via tunnelen klient:2222<->server:22, logga ut från klienten och skriv exit i fönstret på server så att du kommer tillbaka till kommandopromten.
Nu är det dax att sätta upp autossh så att den startar upp automatiskt. Öppna filen /etc/init.d/autossh
1 |
sudo nano /etc/init.d/autossh |
och klistra in följande
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 |
#!/bin/sh ### BEGIN INIT INFO # Provides: autossh # Required-Start: $remote_fs $syslog # Required-Stop: $remote_fs $syslog # Default-Start: 2 3 4 5 # Default-Stop: 0 1 6 # chkconfig: 345 50 50 # Description: autossh init script ### END INIT INFO # # # generic start script # # (c) 2015 nimmis <kjell.havneskold@gmail.com> # SRV_USER=pi # User name running theserver SSH_MPORT=20000 # monitor port SSH_KEY=/home/pi/.ssh/id_rsa # path to private ssh key SSH_DPORT=22 # destination port on server SSH_CPORT=2222 # source port on klient SSH_DEST=pi@klient.nimmis.se # <user>@<host> for klient server SRV_OPTS="-M $SSH_MPORT -f -N -o 'PubkeyAuthentication=yes' -o 'PasswordAuthentication=no' -i $SSH_KEY -R $SSH_CPORT:localhost:$SSH_DPORT $SSH_DEST" # Options SRV_PROC=autossh # Name of the process SRV_PATH=/usr/lib/autossh # path to service no trailing slash USAGE=$(cat <<EOF Usage: $0 <option> Options: start Start theserver. stop Stop theserver. restart Restart the server. status Give the status of the server EOF ) # # get the PID for the server pocess # getPID() { local PID PID=$( ps -f -u $SRV_USER | grep "$SRV_PATH/$SRV_PROC"| grep -v grep | awk '{print $2}' ) printf "%d\n" $PID } # # return 1 if the server is running othervise 0 # isRunning() { if [ $(getPID) -eq 0 ] ; then echo 0 else echo 1 fi } # execute command as minecraft user execCMD() { # if running as root, switch to defined user if [ $(id -u) -eq 0 ]; then su -s /bin/sh -c "$1" $SRV_USER $2 >> /var/log/$SRV_PROC.deamon.log else sh -c "$1" $2 fi } # # start the server # start() { echo -n "Starting $SRV_PROC server as user $SRV_USER..." # be in right working directory when starting cd $SRV_PATH execCMD "$SRV_PATH/$SRV_PROC $SRV_OPTS" # check if the command wait OK if [ $? -ne 0 ]; then echo "Could not start $SRV_PATH/$SRV_PROC\n" exit 1 fi # wait 2 seconds to see if the process survived sleep 2 if [ $(isRunning) -eq 1 ] ; then echo "Started" else echo "stopped again" exit 1 fi } stop() { echo -n "Stopping $SRV_PROC server..." kill $(getPID) # give it time to die sleep 2 # do it harder if [ $(isRunning) -eq 1 ] ; then kill -9 $(getPID) sleep 2 fi if [ $(isRunning) -eq 1 ] ; then echo "Could not stop it" exit 1 else echo "Stopped" fi } case "$1" in start) if [ $(isRunning) -eq 1 ] ; then echo -n "$SRV_PROC is already running with PID " getPID exit 1 fi start ;; stop) if [ $(isRunning) -eq 1 ] ; then stop else echo "$SRV_PROC is not running" fi ;; restart) stop start ;; status) if [ $(isRunning) -eq 1 ] ; then echo -n "$SRV_PROC is running with PID " getPID else echo "$SRV_PROC is not running" fi ;; *) printf "$USAGE\n" exit 1 ;; esac exit 0 |
Ändra på SSH_ variablarna så att de stämmer överens med dina inställningar och spara filen
Gör sendan filen exekverbar
1 |
sudo chmod +x /etc/init.d/autossh |
Sätt upp autossh så att den startar upp automatiskt
1 |
sudo update-rc.d autossh defaults |
Boota om för att kontrollera att allt verkar fungera
Recent Comments