>[!quote] In a Nutshell
>Open source software to build [[VPN - Virtual Private Network|VPN]] via encrypted connection. WireGuard is directly implemented in the [[- Linux -|(Linux)]] kernel and therefore faster than e.g. OpenVPN (but only transports via [[UDP - User Datagram Protocol|UDP]]).
WireGuard securely encapsulates [[IP Packets|IP packets]] over UDP. You add a WireGuard interface, configure it with your private key and your peers' public keys, and then you send packets across it.
---
#### How it works
WireGuard works by adding a network interface (or multiple), like `eth0` or `wlan0`, called `wg0` (or `wg1`, `wg2`, `wg3`, etc). This network interface can then be configured normally using `ifconfig(8)` or `ip-address(8)`, with routes for it added and removed using `route(8)` or `ip-route(8)`, and so on with all the ordinary networking utilities. The specific WireGuard aspects of the interface are configured using the [`wg(8)`](https://git.zx2c4.com/wireguard-tools/about/src/man/wg.8) tool. This interface acts as a tunnel interface.
WireGuard associates tunnel IP addresses with public keys and remote endpoints. When the interface sends a packet to a peer, it does the following:
1. This packet is meant for 192.168.30.8. Which peer is that? Let me look... Okay, it's for peer `ABCDEFGH`. (Or if it's not for any configured peer, drop the packet.)
2. Encrypt entire IP packet using peer `ABCDEFGH`'s public key.
3. What is the remote endpoint of peer `ABCDEFGH`? Let me look... Okay, the endpoint is UDP port 53133 on host 216.58.211.110.
4. Send encrypted bytes from step 2 over the Internet to 216.58.211.110:53133 using UDP.
When the interface receives a packet, this happens:
1. I just got a packet from UDP port 7361 on host 98.139.183.24. Let's decrypt it!
2. It decrypted and authenticated properly for peer `LMNOPQRS`. Okay, let's remember that peer `LMNOPQRS`'s most recent Internet endpoint is 98.139.183.24:7361 using UDP.
3. Once decrypted, the plain-text packet is from 192.168.43.89. Is peer `LMNOPQRS` allowed to be sending us packets as 192.168.43.89?
4. If so, accept the packet on the interface. If not, drop it.
---
#### How to set it up
```bash
wg genkey | tee server-private.key | wg pubkey > server-public.key
```
Pick a name for the keys and move them e.g. in the `/etc/wireguard` dir.
Find out [[IP Address, IPv4, IPv6, ULA and Subnet Mask|public IPv6]] network prefix for your home network via [[ip - Configure and View Network Interfaces|ip command]]
```bash
ip -6 address
```
**Server**
Add new virtual interface (name here is `wg0`) of type wireguard
```bash
ip link add dev wg0 type wireguard
```
Then create a `wg0.conf` in the same directory and create a minimal file
```bash
[Interface]
PrivateKey = ... # local
Address = ... # ! see below
ListenPort = 51820 # default
[Peer]
PublicKey = ... # from client
AllowedIPs = ...
```
In the `Address` line either use your home prefix to expose your network (**firewall required**) or use IPv4 (free to choose number, just have to be unique and within the same [[IP Address, IPv4, IPv6, ULA and Subnet Mask|subnet]]).
See if the interface is up and running with [[ip - Configure and View Network Interfaces|ip command]], if not double check the config and enable / disable
```bash
sudo wg-quick up wg0
sudo wg-quick down wg0
```
**Clients**
Add new virtual interface (name here is `wg0`) of type wireguard
```bash
ip link add dev wg0 type wireguard
```
Then create a `wg0.conf` in the same directory and create a minimal file
```bash
[Interface]
PrivateKey = ... # local
ListenPort = 21841
[Peer]
PublicKey = ... # from server
Endpoint = ... # IP:Port (Address:ListenPort Server)
AllowedIPs = ...
```
See if the interface is up and running with [[ip - Configure and View Network Interfaces|ip command]], if not double check the config and enable / disable
```bash
sudo wg-quick up wg0
sudo wg-quick down wg0
```
>[!brainwaves] Private Network with Access from Everywhere
>- Come up with [[IP Address, IPv4, IPv6, ULA and Subnet Mask|ULA IPs]] for your server and all clients, set them for Address and allowed IPs
>- Only the Endpoint field on every client needs to be the public ISP-provided IP of your home network (or [[DNS and DDNS - (Dynamic) Domain Name System|DDNS]] custom domain)
>- Adapt Firewall to allow UDP traffic through the chosen port (here default) and ssh.
>- For more information on which IPs to use, see [[IP Address, IPv4, IPv6, ULA and Subnet Mask]] note