Reverse SSH connection

— 577 words — 3 min


Table of Contents
  1. Generating SSH key pairs
  2. Raspberry Pi
  3. SSH configuration

I have a raspberry pi which is running pihole and some other things and I want to be able to connect to it from wherever I am without exposing it directly to the internet. So, I thought I could make this possible with an SSH connection form my raspberry pi to my VPS and, at the same time, forwarding the SSH port. Then I can use my VPS as a jumphost by connecting to the VPS and then to the forwarded SSH port from pi.

Generating SSH key pairs🔗

First, let’s generate the needed key pairs for the vps and the raspberry pi. I like to create folders in .ssh to keep my keys sorted.

I use Curve 25519 for pubkey authentication.

ssh-keygen -t ed25519

Generate two keys. My directory structure looks like this

-- .ssh/
  |- config
  |- pihole/
    |- id_ed25519
  |- vps/
    |- id_ed25519

with the following SSH config

Host vps
    HostName VPS_IP
    Port PORT
    IdentityFile ~/.ssh/vps/id_ed25519

Host pihole
    HostName LOCAL_IP
    user USERNAME
    IdentityFile ~/.ssh/pihole/id_ed25519

Great, now I can connect to my vps with ssh vps and to my raspberry pi with ssh pihole.

Raspberry Pi🔗

I want to make sure that my raspberry pi is always connecting to my vps, e.g. if SSH crashed or if I restarted my pi. I use a systemd service and SSH public key authentication to accomplish this.

Go to /etc/systemd/system/ and create a ssh-reverse.service file with the following content:

Description=Reverse SSH connection

ExecStart=/usr/bin/ssh -vvv -g -N -T -o "ServerAliveInterval 10" -o "ExitOnForwardFailure yes" -R 22221:localhost:22 -l USERNAME -p PORT -i /home/USERNAME/.ssh/id_ed25519 VPS_IP


Replace USERNAME, PORT, VPS_IP and the path to the IdentityFile (-i) with your values.

A few important options (more info: man ssh_config)

If this unit is not running, we try restarting the connection every 5 seconds. Make sure, that you already accepted the public key of your VPS on the raspberry pi by connecting to it manually. Otherwise the systemd unit will fail over and over again.

Then enable the service

sudo systemctl start ssh-reverse.service
sudo systemctl enable ssh-reverse.service

SSH configuration🔗

Let’s write the SSH configuration to connect to the raspberry pi via the VPS.

The configuration for the connection to the VPS is already in place and, in my case, it’s called vps. So, if I do ssh vps I will be connected to my VPS. Great. Now let’s use the VPS as jump host.

Write a new Host configuration in ~/.ssh/config. I called it pihole-remote so that I can still connect to my raspberry pi via ssh pihole in my LAN when I’m home.

Host pihole-remote
    ProxyJump vps
    HostName localhost
    user PI_USER
    Port 22221
    IdentityFile ~/.ssh/pihole/id_ed25519
    LocalForward 8888 localhost:80

Now I can connect to my raspberry pi by using my VPS as a jump host. I’m also fowarding localhost:80 to 8888, so that I can access my pihole webinterface in my browser whenever I am connected to my pi with SSH.

Articles from blogs I follow around the net

Status update, May 2024

Hi! Sadly, I need to start this status update with bad news: SourceHut has decided to terminate my contract. At this time, I’m still in the process of figuring out what I’ll do next. I’ve marked some SourceHut-specific projects as unmaintained, such as…

via emersion May 21, 2024

How and why to make a /now page on your site

Background I used to wonder what my friend Benny Lewis was doing. He has a website and social media accounts, but neither gave an overview of what he’s doing now. Then I realized some people might wonder the same about me. So in 2015, I made a /now page on my…

via Derek Sivers blog May 18, 2024

Email DNS Records Cheatsheet

A quick summary of the SMTP related DNS records together with brief examples.

via Signs of Triviality April 12, 2024

Generated by openring