Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

❓ Setup a wireguard server instead of a client #12

Open
AlexOnFOSS opened this issue Nov 21, 2023 · 3 comments
Open

❓ Setup a wireguard server instead of a client #12

AlexOnFOSS opened this issue Nov 21, 2023 · 3 comments
Assignees
Labels
question Further information is requested wontfix This will not be worked on

Comments

@AlexOnFOSS
Copy link

Hi there,

thanks a lot for sharing this. Running wireguard in initramfs is excatly what I want since I am using full disk encryption on my homeserver. The only problem I have with your code / config file is: I don't understand how to setup a wireguard server instead of a wireguard client.

After a reboot of my homeserver, i want it to wait for a wireguard client to connect to it. After successful connection the client will create the ssh connection and unlock the encrypted drive.

So instead of connecting to the outside from my server I want the opposite: connect into my server from the outside.

Is there a way to setup the /etc/wireguard-initramfs/config file for that or is that use case not implemented yet?

Thank u and best wishes,
Alex.

@r-pufky
Copy link
Owner

r-pufky commented Nov 22, 2023

Hi Alex,

I'll try to answer your question here, however this utility is only for providing wireguard services on boot; configuration and support of wireguard itself is outside the scope of this project.

Bastion host

A bastion is basically a heavily restricted / monitored host that is exposed publicly that generally enables proxies and jumps to another network through it.

Client/Server Monikers

These used were to clarify mental models for folks setting it up. Both machines are wireguard clients connecting to each other or through a bastion host. In the documented instructions, the homeserver is a wg client that connects to a bastion host on boot; and you can use another machine to connect to the bastion host; once these connections are established, both machines would be able to send traffic to each other over wireguard (if configured properly). Both are wg clients; the bastion host is a wg client as well, but acts as a traditional vpn endpoint in this case (server).

This model enables the bastion to essentially be anywhere on a well-known (e.g. public IP or DNS space) for the clients to connect to; inside or outside of your internal network.

Direct Connections

The alternative method for setting it up is directly connecting both WG clients to each other; which in your case would require exposing the WG port through your firewall so that another client (e.g. your machine connecting externally) can route traffic to it. The clients would be directly connecting to each other. In this model (which you are talking about) the homeserver is essentially the vpn endpoint, so the WG port would need to be exposed publically so your machine could connect to it outside of your home network.

Wireguard Gotchas

Wireguard is a bit heavy to wrap your head around if you are new to it or don't come from a networking background. I highly, highly recommend setting up wireguard and verifying everything is working the way you intend it to before setting up wireguard-initramfs -- this tool checks for static errors but will not fix broken or incorrect wireguard configs; so you have to know it is working before you use it.

Some good documentation:

Reporting issues

Both cases should be supported with the current configuration. However, if you find that it is not, please file a bug with details including both configurations to validate the bug.

Hopefully this helps you out. Feel free to ask more questions, but please post your configurations with secrets obfuscated. Always test your configuration with clients before moving to the configuring wireguard-initramfs tool

@r-pufky r-pufky added question Further information is requested wontfix This will not be worked on labels Nov 22, 2023
@r-pufky r-pufky self-assigned this Nov 22, 2023
@AlexOnFOSS
Copy link
Author

AlexOnFOSS commented Nov 24, 2023

Hey there, thank you very much for your long answer.

I have been using WireGuard for several years now, so I am familiar with it. I also watched the presentation from Donenfeld and was especially impressed by its non-chatty behavior, so that a port scan will not reveal that there is a WireGuard server listening for connections. I am using it only at home for my home server as an endpoint. Clients connect to it. The server is fully encrypted and I want to be able to reboot the server and then decrypt it from the outside.

My problem is, I don’t know how to set up your config file to achieve this. I did set up a minimal Debian 12 VM for testing and I am able to connect from my VM to an endpoint. But I don’t know how to set up your config file to run the VM as the endpoint.

In the end, I tried to “hack” some code to run the VM as the endpoint into the init-premount script and added a port variable in the config file. So in case the endpoint variable is empty and the port variable is set, the WG-server should be up and running and waiting for clients to connect to it to decrypt the server but that didn’t work as intended. My code worked, but not automatically on startup. I don’t know why, but for sure, because I am a total noob in coding. XD

When I am back at my laptop I can show you the modifications I did and how my config file looks like.

@AlexOnFOSS
Copy link
Author

AlexOnFOSS commented Nov 24, 2023

This is my config file:

cat /etc/wireguard-initramfs/config 
# Wireguard initramfs configuration.
#
# NOTE: As most systems do not encrypt /boot, private key material is exposed
#       and compromised/untrusted. Boot wireguard network should be
#       **different** & untrusted; versus the network used after booting.
#       Always restrict ports and access on the wireguard server.
#
# Be sure to test wireguard config with a running system before setting
# options. See: https://manpages.debian.org/unstable/wireguard-tools/wg.8.en.html
#
# Restricting dropbear connections to **only** wireguard:
# * Confirm wireguard/dropbear work without restriction first.
# * Set dropbear listen address to only wireguard client interface address.
#
#   /etc/dropbear-initramfs/config
#     DROPBEAR_OPTIONS='... -p 172.31.255.10:22 ...'
#

# Wireguard interface name.
INTERFACE=wgserver

# CIDR wireguard interface address.
INTERFACE_ADDR=172.31.25.100/32

# Peer public key (server's public key).
PEER_PUBLIC_KEY=bpmsfOXbzH7zvx/2gPcI3BahU03qJi9WI0XSJqYxdyI=

# Pre shared key (optional: leave blank to disable).
#PRE_SHARED_KEY=/etc/wireguard-initramfs/pre_shared_key

# IP:PORT of the peer (server); any reachable IP/DNS.
#PEER_ENDPOINT=192.168.122.1:51820

# Client Private key. Specify location of file containing only the private key.
CLIENT_PRIVATE_KEYFILE=/etc/wireguard-initramfs/private_key

# Persistent Keepalive. Required to ensure connection for non-exposed ports.
#PERSISTENT_KEEPALIVES=25

# Allowed IP's (CIDR) on wireguard; for boot this should be the peer (server).
ALLOWED_IPS=172.31.25.1/32

# Input Port
PORT=518200`

and here the modified premount script:

cat /etc/initramfs-tools/scripts/init-premount/wireguard 
#!/bin/sh

PREREQ="udev"

prereqs() {
  echo "${PREREQ}"
}

case "${1}" in
  prereqs)
    prereqs
    exit 0
  ;;
esac

. /scripts/functions

if [ ! -e /sbin/wg ]; then
  log_failure_msg 'Wireguard binary not found; skipping start'
  exit 0
fi
if [ ! -e /etc/wireguard/config ]; then
  log_failure_msg 'Wireguard config not found; skipping start'
  exit 0
fi
if [ ! -e /etc/wireguard/private_key ]; then
  log_failure_msg 'Wireguard client private keyfile not found, skipping start'
  exit 0
fi

log_begin_msg 'Loading wireguard config'
. /etc/wireguard/config

if [ -z ${INTERFACE} ]; then
  log_failure_msg 'Interface name is not defined'
  return 1
fi

if [ -z ${INTERFACE_ADDR} ]; then
  log_failure_msg 'Interface address is not defined'
  return 1
fi

if [ -z ${PEER_PUBLIC_KEY} ]; then
  log_failure_msg 'Peer public key is not defined'
  return 1
fi

if [ ! -z ${PRE_SHARED_KEY} ] && [ ! -s "/etc/wireguard/pre_shared_key" ]; then
  log_failure_msg 'Pre shared key is not defined'
  return 1
fi

if [ -z ${PEER_ENDPOINT} ]; then
  log_failure_msg 'Peer endpoint is not defined'
  return 1
fi

if [ -z ${PERSISTENT_KEEPALIVES} ]; then
  log_failure_msg 'Persistent keepalive is not defined'
  return 1
fi

if [ -z ${ALLOWED_IPS} ]; then
  log_failure_msg 'Allowed IPs is not defined'
  return 1
fi
log_end_msg

log_begin_msg 'Starting wireguard'
# Ensure networking is started (idempotent) and setup DNS.
configure_networking
touch /etc/resolv.conf
for adapter in /run/net-*.conf; do
  . "${adapter}"
  if [ ! -z "${IPV4DNS0}" ]; then
    echo nameserver "${IPV4DNS0}" >> /etc/resolv.conf
    echo nameserver "${IPV4DNS1}" >> /etc/resolv.conf
  fi
  if [ ! -z "${IPV6DNS0}" ]; then
    echo nameserver "${IPV6DNS0}" >> /etc/resolv.conf
  fi
done

ip link add dev ${INTERFACE} type wireguard

if [ -z ${PEER_ENDPOINT} ]; then
/sbin/wg set ${INTERFACE} \
    listen-port ${PORT} \
    private-key /etc/wireguard/private_key \
    peer ${PEER_PUBLIC_KEY} \
    allowed-ips ${ALLOWED_IPS} 
elif [ -z ${PRE_SHARED_KEY} ]; then
/sbin/wg set ${INTERFACE} \
    private-key /etc/wireguard/private_key \
    peer ${PEER_PUBLIC_KEY} \
    endpoint ${PEER_ENDPOINT} \
    persistent-keepalive ${PERSISTENT_KEEPALIVES} \
    allowed-ips ${ALLOWED_IPS}
else
/sbin/wg set ${INTERFACE} \
    private-key /etc/wireguard/private_key \
    peer ${PEER_PUBLIC_KEY} \
    preshared-key /etc/wireguard/pre_shared_key \
    endpoint ${PEER_ENDPOINT} \
    persistent-keepalive ${PERSISTENT_KEEPALIVES} \
    allowed-ips ${ALLOWED_IPS}
fi
ip addr add ${INTERFACE_ADDR} dev ${INTERFACE}
ip link set ${INTERFACE} up
ip route add ${ALLOWED_IPS} dev ${INTERFACE}
log_end_msg

Dont be scared because of my keys posted, it is all in a test environment locally on ma laptop and a vm

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
question Further information is requested wontfix This will not be worked on
Projects
None yet
Development

No branches or pull requests

2 participants