SSH via Tor onion service zonder open poorten
Beheer uw VPS zonder open inkomende poorten door SSH achter een Tor onion service te plaatsen. Leer de juiste configuratie, v3 client authenticatie en voorkom buitensluiting.
Wat SSH via een Tor onion service verandert
SSH via een Tor onion service stelt u in staat een VPS te beheren die geen inkomende verbindingen op welke poort dan ook accepteert. De server maakt verbinding met het Tor-netwerk en houdt deze verbinding open. Uw SSH-sessie verloopt via dit kanaal, waardoor er niets op het publieke IP-adres hoeft te luisteren.
Het effect op de logs is direct merkbaar. Een server met een publieke SSH-poort verzamelt dagelijks duizenden mislukte inlogpogingen van scanners. Verplaats sshd achter een onion service en blokkeer inkomend verkeer bij de firewall; /var/log/auth.log registreert daarna alleen nog de sessies die u zelf bent gestart.
Het nadeel is dat tor zich in het pad van elke beheersessie bevindt. Het is een userspace-daemon die na elke reboot moet opstarten en verbinding moet maken voordat u kunt inloggen. Houd hier rekening mee voordat u de poort sluit, want het risico is dat u de toegang verliest tot een machine die u fysiek niet kunt bereiken.
Zorg voor een achterdeur voordat u wijzigingen aanbrengt
Begin niet voordat u beschikt over een herstelmethode die geen gebruikmaakt van SSH.
Open nu de console van uw provider, de VNC- of seriële console in het configuratiescherm, en log hiermee in. Als het root-wachtwoord onbekend is, reset dan eerst het root-wachtwoord via het configuratiescherm en controleer of dit werkt. Een console die u nooit heeft getest, is geen betrouwbare herstelmethode.
De onderstaande volgorde is van belang. Elke stap wordt geverifieerd voordat de volgende wordt uitgevoerd, en poort 22 blijft open totdat de onion-route werkt.
- Installeer tor en bevestig dat het opstart.
- Definieer de onion-service en lees het adres uit.
- Maak verbinding via de onion-service terwijl poort 22 nog open staat.
- Voeg client-autorisatie toe en maak vervolgens opnieuw verbinding.
- Bind
sshdaan loopback en sluit poort 22. - Start opnieuw op en maak daarna opnieuw verbinding via de onion-service.
Houd uw huidige SSH-sessie gedurende het gehele proces open. Een actieve sessie blijft bestaan na een firewallwijziging die een nieuwe verbinding zou blokkeren; dit is daarom uw eerste redmiddel.
Tor installeren op de server
Ubuntu levert Tor in zijn eigen repository, maar die versie loopt vaak achter. De repository van The Tor Project bevat de versie die in hun documentatie wordt beschreven. Voeg deze toe met de commando's uit hun apt repository guide.
sudo apt update
sudo apt install -y apt-transport-https wget gpg
wget -qO- https://deb.torproject.org/torproject.org/A3C4F0F979CAA22CDBA8F512EE8CBC9E886DDD89.asc | gpg --dearmor | sudo tee /usr/share/keyrings/deb.torproject.org-keyring.gpg >/dev/nullSchrijf /etc/apt/sources.list.d/tor.sources. Suites gebruikt uw release-codename, die lsb_release -cs weergeeft (noble op Ubuntu 24.04).
Types: deb deb-src
URIs: https://deb.torproject.org/torproject.org/
Suites: noble
Components: main
Signed-By: /usr/share/keyrings/deb.torproject.org-keyring.gpgsudo apt update
sudo apt install -y tor deb.torproject.org-keyring
sudo journalctl -u tor@default -n 20 --no-pagerHet logbestand moet eindigen met Bootstrapped 100% (done). Als het proces daaronder blijft hangen, kan Tor het netwerk niet bereiken; dit wordt bijna altijd veroorzaakt door een uitgaande firewallregel of een onjuiste systeemklok.
De unit-naam is een valstrik. systemctl status tor rapporteert Active: active (exited), zelfs als alles correct functioneert. Dit komt doordat Debian en Ubuntu Tor verpakken als een multi-instance master-unit, waarvan de enige taak is om de daadwerkelijke instantie te laden. De daemon zelf draait als tor@default.service. Gebruik die naam voor status en voor journalctl. Start-, stop- en reload-commando's voor tor bereiken de instantie wel, dus sudo systemctl reload tor werkt zoals u verwacht.
Definieer de onion service voor poort 22
Voeg twee regels toe aan /etc/tor/torrc.
HiddenServiceDir /var/lib/tor/ssh/
HiddenServicePort 22 127.0.0.1:22De tweede regel instrueert tor om virtuele poort 22 op het onion-adres te accepteren en verbinding te maken met 127.0.0.1:22 op de server. Tor bereikt sshd via loopback; dit is precies de reden waarom sshd later kan stoppen met luisteren op het publieke adres.
sudo systemctl reload tor
sudo cat /var/lib/tor/ssh/hostnameDit print 56 base32-tekens gevolgd door .onion. Deze tekens vormen de publieke sleutel van de service in gecodeerde vorm. Er is geen certificaatautoriteit en er vindt nergens een naamregistratie plaats.
Laat tor /var/lib/tor/ssh/ zelf aanmaken. Maak deze handmatig aan met de verkeerde eigenaar of met rechten die ruimer zijn dan 0700, en tor zal weigeren deze te gebruiken; het logboek zal rapporteren dat de directory te toegankelijk is. De bestanden in deze map vormen de identiteit van de service: hs_ed25519_secret_key is het adres. Maak een back-up van deze directory met modus 600 en bewaar de kopie buiten de server, aangezien verlies ervan betekent dat u een nieuw adres krijgt en de configuratie op elke client moet aanpassen.
Verbinding maken vanaf uw werkstation
Uw werkstation heeft een Tor-client nodig, waarvoor geen enkele configuratie vereist is. Op Debian of Ubuntu is dit sudo apt install -y tor netcat-openbsd. Tor luistert vervolgens op 127.0.0.1:9050 als een SOCKS5-proxy. SOCKS is een generiek proxyprotocol, en versie 5 kan een hostnaam in plaats van een IP-adres doorgeven; dit is het cruciale onderdeel in deze context.
OpenSSH beschikt niet over een eigen SOCKS-client, dus wordt er een hulpprogramma gebruikt om de verbinding tot stand te brengen. Voeg het volgende toe aan ~/.ssh/config.
Host myvps
HostName xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.onion
User admin
ProxyCommand /usr/bin/nc -X 5 -x 127.0.0.1:9050 %h %p
ServerAliveInterval 30-X 5 selecteert SOCKS5 en -x 127.0.0.1:9050 wijst naar de lokale Tor-instantie. %h geeft de onion-naam door aan Tor als een naam, zodat Tor deze binnen het netwerk kan resolven. Dit moet de OpenBSD-versie van netcat zijn. GNU netcat beschikt niet over de -X-optie en stopt met nc: invalid option -- 'X'.
ssh myvpsDe eerste verbinding verloopt traag, omdat Tor eerst een circuit moet opbouwen voordat er iets anders gebeurt. Accepteer de host key fingerprint zoals u dat overal elders zou doen. Vanaf dit punt is de gebruikelijke SSH-sleutelafhandeling ongewijzigd van toepassing. Het transport is verplaatst, maar de authenticatie niet.
Voor een eenmalige actie kunt u de configuratie-ingang overslaan: torsocks ssh admin@xxxxx.onion voert dezelfde taak uit.
Clientautorisatie voor v3 toevoegen
Op dit moment kan iedereen die het adres achterhaalt uw SSH-banner bereiken en beginnen met gokken. Onion-adressen kunnen niet worden opgevraagd via het directory-systeem, waardoor het adres als een geheim fungeert. Het lekt echter op gebruikelijke manieren: via shell-geschiedenis en configuratiebestanden die in een git-repository zijn geplaatst. Clientautorisatie dicht dit gat. De service publiceert de descriptor versleuteld met een clientsleutel, waardoor iemand die wel het adres heeft, maar niet de sleutel, de service niet eens kan lokaliseren.
Genereer een x25519-sleutelpaar op de client. Dit is de pipeline uit de handleiding voor clientautorisatie van het Tor Project, met één wijziging.
openssl genpkey -algorithm x25519 -out /tmp/k1.prv.pem
grep -v " PRIVATE KEY" /tmp/k1.prv.pem | base64 -d | tail --bytes=32 | base32 | sed 's/=//g' > /tmp/k1.prv.key
openssl pkey -in /tmp/k1.prv.pem -pubout | grep -v " PUBLIC KEY" | base64 -d | tail --bytes=32 | base32 | sed 's/=//g' > /tmp/k1.pub.keyDe gepubliceerde versie van deze regels gebruikt base64pem -d, wat een standaard Ubuntu-installatie niet bevat. Het commando stopt dan met base64pem: command not found. GNU base64 -d decodeert hetzelfde PEM-bestand, dus gebruik dat in plaats daarvan.
Installeer de publieke sleutel op de server.
sudo install -d -m 700 -o debian-tor -g debian-tor /var/lib/tor/ssh/authorized_clients
echo "descriptor:x25519:PASTE_PUBLIC_KEY_HERE" | sudo tee /var/lib/tor/ssh/authorized_clients/laptop.auth >/dev/null
sudo chown debian-tor:debian-tor /var/lib/tor/ssh/authorized_clients/laptop.auth
sudo systemctl reload torAlleen bestanden die eindigen op .auth worden gelezen. Slaat u het op als laptop.auth.txt, dan negeert tor het bestand zonder foutmelding en blijft de service stilletjes openstaan voor iedereen met het adres.
Installeer de private sleutel op de client. Op Ubuntu draait de tor-daemon als de gebruiker debian-tor en kan deze geen bestanden in uw home-directory lezen; bewaar de directory dus op een locatie die toegankelijk is voor die gebruiker.
sudo install -d -m 700 -o debian-tor -g debian-tor /var/lib/tor/onion_auth
echo "ADDRESS_WITHOUT_DOT_ONION:descriptor:x25519:PASTE_PRIVATE_KEY_HERE" | sudo tee /var/lib/tor/onion_auth/myvps.auth_private >/dev/null
sudo chown debian-tor:debian-tor /var/lib/tor/onion_auth/myvps.auth_private
sudo chmod 600 /var/lib/tor/onion_auth/myvps.auth_privateVoeg ClientOnionAuthDir /var/lib/tor/onion_auth toe aan het bestand /etc/tor/torrc van de client en herlaad tor. Als u tor als uw eigen gebruiker draait, bijvoorbeeld de Homebrew-build op macOS, wijs ClientOnionAuthDir dan naar ~/.tor/onion_auth met modus 0700.
Het adres in dat bestand bestaat uit de 56 tekens zonder het achtervoegsel .onion. Verwijder /tmp/k1.prv.pem en /tmp/k1.prv.key zodra u klaar bent.
Test nu beide richtingen. ssh myvps zou nog steeds verbinding moeten maken. Vanaf een machine zonder sleutel zou hetzelfde adres moeten falen. Dat falen is uw bewijs dat de autorisatie actief is.
Poort 22 sluiten, in deze volgorde
Stel eerst een vangnet in. Dit commando draait beide onderstaande wijzigingen na vijftien minuten terug als u uzelf buitensluit.
sudo systemd-run --on-active=15m --unit=ssh-rescue \
/bin/sh -c 'ufw allow 22/tcp; rm -f /etc/systemd/system/ssh.socket.d/override.conf; systemctl daemon-reload; systemctl restart ssh.socket'Annuleer dit met sudo systemctl stop ssh-rescue.timer zodra u heeft bevestigd dat de onion-route nog steeds werkt.
Stop vervolgens het luisteren van sshd op het publieke adres. Ubuntu 24.04 activeert ssh via een socket-unit, waardoor ListenAddress in sshd_config wordt genegeerd: ssh.socket beheert de luisterende socket, niet sshd. Controleer in welke situatie u zich bevindt.
systemctl is-enabled ssh.socketAls dit enabled weergeeft, voer dan sudo systemctl edit ssh.socket uit en voeg dit toe.
[Socket]
ListenStream=
ListenStream=127.0.0.1:22De lege ListenStream= wist de waarde die is overgenomen van de meegeleverde unit. Laat die regel weg en u voegt een tweede listener toe terwijl de publieke actief blijft; dit is de meest voorkomende manier waarop deze stap ongemerkt mislukt.
sudo systemctl daemon-reload
sudo systemctl restart ssh.socket
ss -tlnp | grep ':22'ss hoort 127.0.0.1:22 te tonen en niets op 0.0.0.0:22. Als ssh.socket was uitgeschakeld, plaats dan ListenAddress 127.0.0.1 in /etc/ssh/sshd_config.d/10-onion.conf, voer sudo systemctl restart ssh uit en controleer daarna met dezelfde ss-regel. Die uitvoer is in beide gevallen het bewijs.
Vervolgens de firewall, wat standaard ufw-regelbeheer op een VPS is. Voer eerst sudo ufw status numbered uit en verwijder de SSH-regel die daar wordt vermeld.
sudo ufw status numbered
sudo ufw delete allow OpenSSH
sudo ufw default allow outgoing
sudo ufw default deny incoming
sudo ufw status verboseLaat uitgaand verkeer toegestaan. Tor maakt verbinding met relays op poorten zoals 443 en 9001; een default-deny beleid voor uitgaand verkeer stopt dus het opstarten van Tor en verwijdert tegelijkertijd uw enige overgebleven toegangsweg. De meeste providers beheren ook een afzonderlijke netwerkfirewall in het configuratiescherm. Sluit poort 22 daar ook, anders blijft de poort bereikbaar, ongeacht wat ufw rapporteert.
Als Docker op deze machine draait, controleer dan de gepubliceerde poorten voordat u het werk als voltooid beschouwt. Docker schrijft zijn eigen regels naar dezelfde tabellen en publiceert containerpoorten direct langs ufw heen, waardoor een ufw deny-beleid geen volledig beeld geeft.
Herstart voordat u het vertrouwt
systemctl is-enabled tor@default
sudo rebootAls het eerste commando niet aangeeft dat de service is ingeschakeld, voer dan sudo systemctl enable tor@default uit voordat u de server herstart. Wacht twee minuten en voer daarna ssh myvps uit. Tor moet na het opstarten initialiseren, waardoor het onion-adres pas enige tijd nadat de machine zelf actief is, reageert.
Als de service niet terugkeert, open dan de console en lees sudo journalctl -u tor@default -b. Een syntaxfout in torrc of een probleem met maprechten wordt daar weergegeven. U kunt een bewerking in torrc ook controleren voordat u deze toepast.
sudo -u debian-tor tor --verify-configWat dit kost in vergelijking met een WireGuard-tunnel
In vergelijking met een WireGuard VPN op uw eigen VPS, is een onion service trager en minder voorspelbaar. Wees eerlijk tegen uzelf over de afweging voordat u zich hieraan verbindt.
Latentie. Een client-circuit bestaat uit drie relays en de service-kant voegt er nog eens drie toe, waardoor uw toetsaanslagen ongeveer zes willekeurig gekozen machines over de hele wereld passeren. Interactief typen heeft een merkbare vertraging en het kopiëren van bestanden verloopt traag. WireGuard voegt slechts één hop toe. Meet uw eigen situatie met time ssh myvps 'echo ok', omdat het cijfer afhangt van het circuit dat tor op dat moment heeft opgebouwd en dit verandert zodra tor een nieuw circuit opbouwt.
Een userspace-daemon in het kritieke pad. WireGuard bevindt zich in de kernel en komt tegelijk met het netwerk op. Tor is een proces dat moet opstarten, bootstrappen en een guard-relay moet bereiken voordat er iets werkt. Wanneer dit faalt, bent u aangewezen op de console van de provider.
Kloknauwkeurigheid. Onion service-descriptors worden gepubliceerd op basis van tijdsperioden, dus een onjuiste klokinstelling zorgt ervoor dat adresopzoeking faalt zonder duidelijke foutmelding. timedatectl hoort System clock synchronized: yes te rapporteren.
Wat u ervoor terugkrijgt, is een blootstelling die niet langer afhankelijk is van een correcte firewallregel. Er is geen poort om te scannen en geen banner om uit te lezen, en het adres is zelf een publieke sleutel, waardoor het eindpunt zijn identiteit bewijst nog voordat SSH überhaupt start.
Het praktische antwoord is meestal beide. Gebruik WireGuard als het dagelijkse pad en houd de onion service aan als de route die nog steeds werkt wanneer de WireGuard-configuratie onjuist is. Dat laat één UDP-poort open in plaats van een publieke SSH-poort. Niets hiervan vervangt het beveiligen van sshd zelf: authenticatie via sleutels en een login die niet als root plaatsvindt, blijven van belang, omdat een onion service alleen het netwerkpad beschermt en niets daarbuiten.
Foutmodi en de foutmeldingen die u zult zien
Tor passeert Bootstrapped 0% nooit. Uitgaand verkeer wordt geblokkeerd of de klok loopt ver achter. Controleer het uitgaande beleid met sudo ufw status verbose en voer vervolgens timedatectl uit.
systemctl status tor zegt active (exited). Dit is normaal op Debian en Ubuntu. Lees in plaats daarvan tor@default.
De descriptor kan niet worden gevonden. Tor retourneert SOCKS extended error F0, "Onion Service Descriptor Can Not be Found". Ofwel de descriptor is nog niet gepubliceerd, wat na een herlaadactie even duurt, of tor op de server draait niet.
F4, "Onion Service Missing Client Authorization". De client heeft geen overeenkomende .auth_private die tor kan gebruiken. Controleer of ClientOnionAuthDir in torrc staat, of de directory de modus 0700 heeft, of de bestandsnaam eindigt op .auth_private en of debian-tor het bestand kan lezen.
F5, "Onion Service Wrong Client Authorization". De privésleutel komt niet overeen met het .auth-bestand op de server. Een afsluitende = of een onbedoelde nieuwe regel in de base32-string veroorzaakt dit.
nc: invalid option -- 'X'. GNU netcat is geïnstalleerd in plaats van de OpenBSD-versie. Voer sudo apt install -y netcat-openbsd uit.
Could not resolve hostname. ssh probeerde gewone DNS, wat geen antwoord heeft voor .onion, waardoor ProxyCommand nooit werd uitgevoerd. Het Host-patroon in ~/.ssh/config komt niet overeen met de naam die u heeft getypt.
Permission denied (publickey). De tunnel werkte en tor is klaar. Behandel dit als een gewoon permission denied publickey-probleem en laat tor buiten beschouwing.
FAQ
Betekent een onion service echt dat er geen open poorten op mijn VPS zijn?
Ja, zodra sshd is gebonden aan 127.0.0.1 en de firewall inkomend verkeer blokkeert. Tor maakt een uitgaande TCP-verbinding met een relay en uw sessie loopt daar via een omweg terug, waardoor er op de server niets is dat verbindingen op het publieke adres accepteert. Controleer dit met ss -tlnp op de server en een poortscan vanaf een andere locatie. Vergeet niet de netwerkfirewall van de provider in het configuratiescherm; dit is een aparte instelling naast ufw die eveneens moet worden gesloten.
Is het .onion-adres op zichzelf voldoende beveiliging voor SSH?
Nee. Het adres bestaat uit 56 tekens en kan niet worden geraden of opgevraagd via het directory-systeem, waardoor het als een geheim fungeert, maar het lekt via shell-geschiedenis en configuratiebestanden. Voeg v3 client-autorisatie toe. Hiermee wordt de service-descriptor versleuteld met uw clientsleutel, zodat iemand die alleen het adres heeft, de uitgebreide foutmelding F4 krijgt en sshd nooit bereikt.
Wat gebeurt er als tor na een herstart niet opstart?
U verliest de SSH-toegang volledig, omdat het onion-adres dan de enige ingang is. Daarom moet de console van de provider worden getest voordat u poort 22 sluit. Tor heeft bovendien tijd nodig om na het opstarten te bootstrappen, waardoor het adres pas reageert nadat de machine al op ping antwoordt. Als er nooit antwoord komt, log dan in via de console en lees sudo journalctl -u tor@default -b; hierin staat een eventuele torrc-syntaxfout of een probleem met de rechten op /var/lib/tor/ssh vermeld.
Is SSH over Tor trager dan WireGuard?
Ja, aanzienlijk. Een verbinding met een onion service loopt via ongeveer zes willekeurig gekozen relays, terwijl WireGuard één versleutelde hop direct naar uw server is. Typen voelt vertraagd aan en bestandsoverdrachten zijn traag. Een gebruikelijke opzet is WireGuard voor dagelijks gebruik, waarbij de onion service dient als noodroute die blijft werken bij een defecte VPN-configuratie.