1#!/bin/bash 2# SPDX-License-Identifier: GPL-2.0 3# 4# Copyright (C) 2015-2019 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved. 5# 6# This script tests the below topology: 7# 8# ┌─────────────────────┐ ┌──────────────────────────────────┐ ┌─────────────────────┐ 9# │ $ns1 namespace │ │ $ns0 namespace │ │ $ns2 namespace │ 10# │ │ │ │ │ │ 11# │┌────────┐ │ │ ┌────────┐ │ │ ┌────────┐│ 12# ││ wg0 │───────────┼───┼────────────│ lo │────────────┼───┼───────────│ wg0 ││ 13# │├────────┴──────────┐│ │ ┌───────┴────────┴────────┐ │ │┌──────────┴────────┤│ 14# ││192.168.241.1/24 ││ │ │(ns1) (ns2) │ │ ││192.168.241.2/24 ││ 15# ││fd00::1/24 ││ │ │127.0.0.1:1 127.0.0.1:2│ │ ││fd00::2/24 ││ 16# │└───────────────────┘│ │ │[::]:1 [::]:2 │ │ │└───────────────────┘│ 17# └─────────────────────┘ │ └─────────────────────────┘ │ └─────────────────────┘ 18# └──────────────────────────────────┘ 19# 20# After the topology is prepared we run a series of TCP/UDP iperf3 tests between the 21# wireguard peers in $ns1 and $ns2. Note that $ns0 is the endpoint for the wg0 22# interfaces in $ns1 and $ns2. See https://www.wireguard.com/netns/ for further 23# details on how this is accomplished. 24set -e 25 26exec 3>&1 27export LANG=C 28export WG_HIDE_KEYS=never 29netns0="wg-test-$$-0" 30netns1="wg-test-$$-1" 31netns2="wg-test-$$-2" 32pretty() { echo -e "\x1b[32m\x1b[1m[+] ${1:+NS$1: }${2}\x1b[0m" >&3; } 33pp() { pretty "" "$*"; "$@"; } 34maybe_exec() { if [[ $BASHPID -eq $$ ]]; then "$@"; else exec "$@"; fi; } 35n0() { pretty 0 "$*"; maybe_exec ip netns exec $netns0 "$@"; } 36n1() { pretty 1 "$*"; maybe_exec ip netns exec $netns1 "$@"; } 37n2() { pretty 2 "$*"; maybe_exec ip netns exec $netns2 "$@"; } 38ip0() { pretty 0 "ip $*"; ip -n $netns0 "$@"; } 39ip1() { pretty 1 "ip $*"; ip -n $netns1 "$@"; } 40ip2() { pretty 2 "ip $*"; ip -n $netns2 "$@"; } 41sleep() { read -t "$1" -N 1 || true; } 42waitiperf() { pretty "${1//*-}" "wait for iperf:5201 pid $2"; while [[ $(ss -N "$1" -tlpH 'sport = 5201') != *\"iperf3\",pid=$2,fd=* ]]; do sleep 0.1; done; } 43waitncatudp() { pretty "${1//*-}" "wait for udp:1111 pid $2"; while [[ $(ss -N "$1" -ulpH 'sport = 1111') != *\"ncat\",pid=$2,fd=* ]]; do sleep 0.1; done; } 44waitiface() { pretty "${1//*-}" "wait for $2 to come up"; ip netns exec "$1" bash -c "while [[ \$(< \"/sys/class/net/$2/operstate\") != up ]]; do read -t .1 -N 0 || true; done;"; } 45 46cleanup() { 47 set +e 48 exec 2>/dev/null 49 printf "$orig_message_cost" > /proc/sys/net/core/message_cost 50 ip0 link del dev wg0 51 ip1 link del dev wg0 52 ip2 link del dev wg0 53 local to_kill="$(ip netns pids $netns0) $(ip netns pids $netns1) $(ip netns pids $netns2)" 54 [[ -n $to_kill ]] && kill $to_kill 55 pp ip netns del $netns1 56 pp ip netns del $netns2 57 pp ip netns del $netns0 58 exit 59} 60 61orig_message_cost="$(< /proc/sys/net/core/message_cost)" 62trap cleanup EXIT 63printf 0 > /proc/sys/net/core/message_cost 64 65ip netns del $netns0 2>/dev/null || true 66ip netns del $netns1 2>/dev/null || true 67ip netns del $netns2 2>/dev/null || true 68pp ip netns add $netns0 69pp ip netns add $netns1 70pp ip netns add $netns2 71ip0 link set up dev lo 72 73ip0 link add dev wg0 type wireguard 74ip0 link set wg0 netns $netns1 75ip0 link add dev wg0 type wireguard 76ip0 link set wg0 netns $netns2 77key1="$(pp wg genkey)" 78key2="$(pp wg genkey)" 79key3="$(pp wg genkey)" 80pub1="$(pp wg pubkey <<<"$key1")" 81pub2="$(pp wg pubkey <<<"$key2")" 82pub3="$(pp wg pubkey <<<"$key3")" 83psk="$(pp wg genpsk)" 84[[ -n $key1 && -n $key2 && -n $psk ]] 85 86configure_peers() { 87 ip1 addr add 192.168.241.1/24 dev wg0 88 ip1 addr add fd00::1/24 dev wg0 89 90 ip2 addr add 192.168.241.2/24 dev wg0 91 ip2 addr add fd00::2/24 dev wg0 92 93 n1 wg set wg0 \ 94 private-key <(echo "$key1") \ 95 listen-port 1 \ 96 peer "$pub2" \ 97 preshared-key <(echo "$psk") \ 98 allowed-ips 192.168.241.2/32,fd00::2/128 99 n2 wg set wg0 \ 100 private-key <(echo "$key2") \ 101 listen-port 2 \ 102 peer "$pub1" \ 103 preshared-key <(echo "$psk") \ 104 allowed-ips 192.168.241.1/32,fd00::1/128 105 106 ip1 link set up dev wg0 107 ip2 link set up dev wg0 108} 109configure_peers 110 111tests() { 112 # Ping over IPv4 113 n2 ping -c 10 -f -W 1 192.168.241.1 114 n1 ping -c 10 -f -W 1 192.168.241.2 115 116 # Ping over IPv6 117 n2 ping6 -c 10 -f -W 1 fd00::1 118 n1 ping6 -c 10 -f -W 1 fd00::2 119 120 # TCP over IPv4 121 n2 iperf3 -s -1 -B 192.168.241.2 & 122 waitiperf $netns2 $! 123 n1 iperf3 -Z -t 3 -c 192.168.241.2 124 125 # TCP over IPv6 126 n1 iperf3 -s -1 -B fd00::1 & 127 waitiperf $netns1 $! 128 n2 iperf3 -Z -t 3 -c fd00::1 129 130 # UDP over IPv4 131 n1 iperf3 -s -1 -B 192.168.241.1 & 132 waitiperf $netns1 $! 133 n2 iperf3 -Z -t 3 -b 0 -u -c 192.168.241.1 134 135 # UDP over IPv6 136 n2 iperf3 -s -1 -B fd00::2 & 137 waitiperf $netns2 $! 138 n1 iperf3 -Z -t 3 -b 0 -u -c fd00::2 139} 140 141[[ $(ip1 link show dev wg0) =~ mtu\ ([0-9]+) ]] && orig_mtu="${BASH_REMATCH[1]}" 142big_mtu=$(( 34816 - 1500 + $orig_mtu )) 143 144# Test using IPv4 as outer transport 145n1 wg set wg0 peer "$pub2" endpoint 127.0.0.1:2 146n2 wg set wg0 peer "$pub1" endpoint 127.0.0.1:1 147# Before calling tests, we first make sure that the stats counters and timestamper are working 148n2 ping -c 10 -f -W 1 192.168.241.1 149{ read _; read _; read _; read rx_bytes _; read _; read tx_bytes _; } < <(ip2 -stats link show dev wg0) 150(( rx_bytes == 1372 && (tx_bytes == 1428 || tx_bytes == 1460) )) 151{ read _; read _; read _; read rx_bytes _; read _; read tx_bytes _; } < <(ip1 -stats link show dev wg0) 152(( tx_bytes == 1372 && (rx_bytes == 1428 || rx_bytes == 1460) )) 153read _ rx_bytes tx_bytes < <(n2 wg show wg0 transfer) 154(( rx_bytes == 1372 && (tx_bytes == 1428 || tx_bytes == 1460) )) 155read _ rx_bytes tx_bytes < <(n1 wg show wg0 transfer) 156(( tx_bytes == 1372 && (rx_bytes == 1428 || rx_bytes == 1460) )) 157read _ timestamp < <(n1 wg show wg0 latest-handshakes) 158(( timestamp != 0 )) 159 160tests 161ip1 link set wg0 mtu $big_mtu 162ip2 link set wg0 mtu $big_mtu 163tests 164 165ip1 link set wg0 mtu $orig_mtu 166ip2 link set wg0 mtu $orig_mtu 167 168# Test using IPv6 as outer transport 169n1 wg set wg0 peer "$pub2" endpoint [::1]:2 170n2 wg set wg0 peer "$pub1" endpoint [::1]:1 171tests 172ip1 link set wg0 mtu $big_mtu 173ip2 link set wg0 mtu $big_mtu 174tests 175 176# Test that route MTUs work with the padding 177ip1 link set wg0 mtu 1300 178ip2 link set wg0 mtu 1300 179n1 wg set wg0 peer "$pub2" endpoint 127.0.0.1:2 180n2 wg set wg0 peer "$pub1" endpoint 127.0.0.1:1 181n0 iptables -A INPUT -m length --length 1360 -j DROP 182n1 ip route add 192.168.241.2/32 dev wg0 mtu 1299 183n2 ip route add 192.168.241.1/32 dev wg0 mtu 1299 184n2 ping -c 1 -W 1 -s 1269 192.168.241.1 185n2 ip route delete 192.168.241.1/32 dev wg0 mtu 1299 186n1 ip route delete 192.168.241.2/32 dev wg0 mtu 1299 187n0 iptables -F INPUT 188 189ip1 link set wg0 mtu $orig_mtu 190ip2 link set wg0 mtu $orig_mtu 191 192# Test using IPv4 that roaming works 193ip0 -4 addr del 127.0.0.1/8 dev lo 194ip0 -4 addr add 127.212.121.99/8 dev lo 195n1 wg set wg0 listen-port 9999 196n1 wg set wg0 peer "$pub2" endpoint 127.0.0.1:2 197n1 ping6 -W 1 -c 1 fd00::2 198[[ $(n2 wg show wg0 endpoints) == "$pub1 127.212.121.99:9999" ]] 199 200# Test using IPv6 that roaming works 201n1 wg set wg0 listen-port 9998 202n1 wg set wg0 peer "$pub2" endpoint [::1]:2 203n1 ping -W 1 -c 1 192.168.241.2 204[[ $(n2 wg show wg0 endpoints) == "$pub1 [::1]:9998" ]] 205 206# Test that crypto-RP filter works 207n1 wg set wg0 peer "$pub2" allowed-ips 192.168.241.0/24 208exec 4< <(n1 ncat -l -u -p 1111) 209ncat_pid=$! 210waitncatudp $netns1 $ncat_pid 211n2 ncat -u 192.168.241.1 1111 <<<"X" 212read -r -N 1 -t 1 out <&4 && [[ $out == "X" ]] 213kill $ncat_pid 214more_specific_key="$(pp wg genkey | pp wg pubkey)" 215n1 wg set wg0 peer "$more_specific_key" allowed-ips 192.168.241.2/32 216n2 wg set wg0 listen-port 9997 217exec 4< <(n1 ncat -l -u -p 1111) 218ncat_pid=$! 219waitncatudp $netns1 $ncat_pid 220n2 ncat -u 192.168.241.1 1111 <<<"X" 221! read -r -N 1 -t 1 out <&4 || false 222kill $ncat_pid 223n1 wg set wg0 peer "$more_specific_key" remove 224[[ $(n1 wg show wg0 endpoints) == "$pub2 [::1]:9997" ]] 225 226# Test that we can change private keys keys and immediately handshake 227n1 wg set wg0 private-key <(echo "$key1") peer "$pub2" preshared-key <(echo "$psk") allowed-ips 192.168.241.2/32 endpoint 127.0.0.1:2 228n2 wg set wg0 private-key <(echo "$key2") listen-port 2 peer "$pub1" preshared-key <(echo "$psk") allowed-ips 192.168.241.1/32 229n1 ping -W 1 -c 1 192.168.241.2 230n1 wg set wg0 private-key <(echo "$key3") 231n2 wg set wg0 peer "$pub3" preshared-key <(echo "$psk") allowed-ips 192.168.241.1/32 peer "$pub1" remove 232n1 ping -W 1 -c 1 192.168.241.2 233 234ip1 link del wg0 235ip2 link del wg0 236 237# Test using NAT. We now change the topology to this: 238# ┌────────────────────────────────────────┐ ┌────────────────────────────────────────────────┐ ┌────────────────────────────────────────┐ 239# │ $ns1 namespace │ │ $ns0 namespace │ │ $ns2 namespace │ 240# │ │ │ │ │ │ 241# │ ┌─────┐ ┌─────┐ │ │ ┌──────┐ ┌──────┐ │ │ ┌─────┐ ┌─────┐ │ 242# │ │ wg0 │─────────────│vethc│───────────┼────┼────│vethrc│ │vethrs│──────────────┼─────┼──│veths│────────────│ wg0 │ │ 243# │ ├─────┴──────────┐ ├─────┴──────────┐│ │ ├──────┴─────────┐ ├──────┴────────────┐ │ │ ├─────┴──────────┐ ├─────┴──────────┐ │ 244# │ │192.168.241.1/24│ │192.168.1.100/24││ │ │192.168.1.1/24 │ │10.0.0.1/24 │ │ │ │10.0.0.100/24 │ │192.168.241.2/24│ │ 245# │ │fd00::1/24 │ │ ││ │ │ │ │SNAT:192.168.1.0/24│ │ │ │ │ │fd00::2/24 │ │ 246# │ └────────────────┘ └────────────────┘│ │ └────────────────┘ └───────────────────┘ │ │ └────────────────┘ └────────────────┘ │ 247# └────────────────────────────────────────┘ └────────────────────────────────────────────────┘ └────────────────────────────────────────┘ 248 249ip1 link add dev wg0 type wireguard 250ip2 link add dev wg0 type wireguard 251configure_peers 252 253ip0 link add vethrc type veth peer name vethc 254ip0 link add vethrs type veth peer name veths 255ip0 link set vethc netns $netns1 256ip0 link set veths netns $netns2 257ip0 link set vethrc up 258ip0 link set vethrs up 259ip0 addr add 192.168.1.1/24 dev vethrc 260ip0 addr add 10.0.0.1/24 dev vethrs 261ip1 addr add 192.168.1.100/24 dev vethc 262ip1 link set vethc up 263ip1 route add default via 192.168.1.1 264ip2 addr add 10.0.0.100/24 dev veths 265ip2 link set veths up 266waitiface $netns0 vethrc 267waitiface $netns0 vethrs 268waitiface $netns1 vethc 269waitiface $netns2 veths 270 271n0 bash -c 'printf 1 > /proc/sys/net/ipv4/ip_forward' 272n0 bash -c 'printf 2 > /proc/sys/net/netfilter/nf_conntrack_udp_timeout' 273n0 bash -c 'printf 2 > /proc/sys/net/netfilter/nf_conntrack_udp_timeout_stream' 274n0 iptables -t nat -A POSTROUTING -s 192.168.1.0/24 -d 10.0.0.0/24 -j SNAT --to 10.0.0.1 275 276n1 wg set wg0 peer "$pub2" endpoint 10.0.0.100:2 persistent-keepalive 1 277n1 ping -W 1 -c 1 192.168.241.2 278n2 ping -W 1 -c 1 192.168.241.1 279[[ $(n2 wg show wg0 endpoints) == "$pub1 10.0.0.1:1" ]] 280# Demonstrate n2 can still send packets to n1, since persistent-keepalive will prevent connection tracking entry from expiring (to see entries: `n0 conntrack -L`). 281pp sleep 3 282n2 ping -W 1 -c 1 192.168.241.1 283n1 wg set wg0 peer "$pub2" persistent-keepalive 0 284 285# Do a wg-quick(8)-style policy routing for the default route, making sure vethc has a v6 address to tease out bugs. 286ip1 -6 addr add fc00::9/96 dev vethc 287ip1 -6 route add default via fc00::1 288ip2 -4 addr add 192.168.99.7/32 dev wg0 289ip2 -6 addr add abab::1111/128 dev wg0 290n1 wg set wg0 fwmark 51820 peer "$pub2" allowed-ips 192.168.99.7,abab::1111 291ip1 -6 route add default dev wg0 table 51820 292ip1 -6 rule add not fwmark 51820 table 51820 293ip1 -6 rule add table main suppress_prefixlength 0 294ip1 -4 route add default dev wg0 table 51820 295ip1 -4 rule add not fwmark 51820 table 51820 296ip1 -4 rule add table main suppress_prefixlength 0 297# Flood the pings instead of sending just one, to trigger routing table reference counting bugs. 298n1 ping -W 1 -c 100 -f 192.168.99.7 299n1 ping -W 1 -c 100 -f abab::1111 300 301# Have ns2 NAT into wg0 packets from ns0, but return an icmp error along the right route. 302n2 iptables -t nat -A POSTROUTING -s 10.0.0.0/24 -d 192.168.241.0/24 -j SNAT --to 192.168.241.2 303n0 iptables -t filter -A INPUT \! -s 10.0.0.0/24 -i vethrs -j DROP # Manual rpfilter just to be explicit. 304n2 bash -c 'printf 1 > /proc/sys/net/ipv4/ip_forward' 305ip0 -4 route add 192.168.241.1 via 10.0.0.100 306n2 wg set wg0 peer "$pub1" remove 307[[ $(! n0 ping -W 1 -c 1 192.168.241.1 || false) == *"From 10.0.0.100 icmp_seq=1 Destination Host Unreachable"* ]] 308 309n0 iptables -t nat -F 310n0 iptables -t filter -F 311n2 iptables -t nat -F 312ip0 link del vethrc 313ip0 link del vethrs 314ip1 link del wg0 315ip2 link del wg0 316 317# Test that saddr routing is sticky but not too sticky, changing to this topology: 318# ┌────────────────────────────────────────┐ ┌────────────────────────────────────────┐ 319# │ $ns1 namespace │ │ $ns2 namespace │ 320# │ │ │ │ 321# │ ┌─────┐ ┌─────┐ │ │ ┌─────┐ ┌─────┐ │ 322# │ │ wg0 │─────────────│veth1│───────────┼────┼──│veth2│────────────│ wg0 │ │ 323# │ ├─────┴──────────┐ ├─────┴──────────┐│ │ ├─────┴──────────┐ ├─────┴──────────┐ │ 324# │ │192.168.241.1/24│ │10.0.0.1/24 ││ │ │10.0.0.2/24 │ │192.168.241.2/24│ │ 325# │ │fd00::1/24 │ │fd00:aa::1/96 ││ │ │fd00:aa::2/96 │ │fd00::2/24 │ │ 326# │ └────────────────┘ └────────────────┘│ │ └────────────────┘ └────────────────┘ │ 327# └────────────────────────────────────────┘ └────────────────────────────────────────┘ 328 329ip1 link add dev wg0 type wireguard 330ip2 link add dev wg0 type wireguard 331configure_peers 332ip1 link add veth1 type veth peer name veth2 333ip1 link set veth2 netns $netns2 334n1 bash -c 'printf 0 > /proc/sys/net/ipv6/conf/all/accept_dad' 335n2 bash -c 'printf 0 > /proc/sys/net/ipv6/conf/all/accept_dad' 336n1 bash -c 'printf 0 > /proc/sys/net/ipv6/conf/veth1/accept_dad' 337n2 bash -c 'printf 0 > /proc/sys/net/ipv6/conf/veth2/accept_dad' 338n1 bash -c 'printf 1 > /proc/sys/net/ipv4/conf/veth1/promote_secondaries' 339 340# First we check that we aren't overly sticky and can fall over to new IPs when old ones are removed 341ip1 addr add 10.0.0.1/24 dev veth1 342ip1 addr add fd00:aa::1/96 dev veth1 343ip2 addr add 10.0.0.2/24 dev veth2 344ip2 addr add fd00:aa::2/96 dev veth2 345ip1 link set veth1 up 346ip2 link set veth2 up 347waitiface $netns1 veth1 348waitiface $netns2 veth2 349n1 wg set wg0 peer "$pub2" endpoint 10.0.0.2:2 350n1 ping -W 1 -c 1 192.168.241.2 351ip1 addr add 10.0.0.10/24 dev veth1 352ip1 addr del 10.0.0.1/24 dev veth1 353n1 ping -W 1 -c 1 192.168.241.2 354n1 wg set wg0 peer "$pub2" endpoint [fd00:aa::2]:2 355n1 ping -W 1 -c 1 192.168.241.2 356ip1 addr add fd00:aa::10/96 dev veth1 357ip1 addr del fd00:aa::1/96 dev veth1 358n1 ping -W 1 -c 1 192.168.241.2 359 360# Now we show that we can successfully do reply to sender routing 361ip1 link set veth1 down 362ip2 link set veth2 down 363ip1 addr flush dev veth1 364ip2 addr flush dev veth2 365ip1 addr add 10.0.0.1/24 dev veth1 366ip1 addr add 10.0.0.2/24 dev veth1 367ip1 addr add fd00:aa::1/96 dev veth1 368ip1 addr add fd00:aa::2/96 dev veth1 369ip2 addr add 10.0.0.3/24 dev veth2 370ip2 addr add fd00:aa::3/96 dev veth2 371ip1 link set veth1 up 372ip2 link set veth2 up 373waitiface $netns1 veth1 374waitiface $netns2 veth2 375n2 wg set wg0 peer "$pub1" endpoint 10.0.0.1:1 376n2 ping -W 1 -c 1 192.168.241.1 377[[ $(n2 wg show wg0 endpoints) == "$pub1 10.0.0.1:1" ]] 378n2 wg set wg0 peer "$pub1" endpoint [fd00:aa::1]:1 379n2 ping -W 1 -c 1 192.168.241.1 380[[ $(n2 wg show wg0 endpoints) == "$pub1 [fd00:aa::1]:1" ]] 381n2 wg set wg0 peer "$pub1" endpoint 10.0.0.2:1 382n2 ping -W 1 -c 1 192.168.241.1 383[[ $(n2 wg show wg0 endpoints) == "$pub1 10.0.0.2:1" ]] 384n2 wg set wg0 peer "$pub1" endpoint [fd00:aa::2]:1 385n2 ping -W 1 -c 1 192.168.241.1 386[[ $(n2 wg show wg0 endpoints) == "$pub1 [fd00:aa::2]:1" ]] 387 388# What happens if the inbound destination address belongs to a different interface as the default route? 389ip1 link add dummy0 type dummy 390ip1 addr add 10.50.0.1/24 dev dummy0 391ip1 link set dummy0 up 392ip2 route add 10.50.0.0/24 dev veth2 393n2 wg set wg0 peer "$pub1" endpoint 10.50.0.1:1 394n2 ping -W 1 -c 1 192.168.241.1 395[[ $(n2 wg show wg0 endpoints) == "$pub1 10.50.0.1:1" ]] 396 397ip1 link del dummy0 398ip1 addr flush dev veth1 399ip2 addr flush dev veth2 400ip1 route flush dev veth1 401ip2 route flush dev veth2 402 403# Now we see what happens if another interface route takes precedence over an ongoing one 404ip1 link add veth3 type veth peer name veth4 405ip1 link set veth4 netns $netns2 406ip1 addr add 10.0.0.1/24 dev veth1 407ip2 addr add 10.0.0.2/24 dev veth2 408ip1 addr add 10.0.0.3/24 dev veth3 409ip1 link set veth1 up 410ip2 link set veth2 up 411ip1 link set veth3 up 412ip2 link set veth4 up 413waitiface $netns1 veth1 414waitiface $netns2 veth2 415waitiface $netns1 veth3 416waitiface $netns2 veth4 417ip1 route flush dev veth1 418ip1 route flush dev veth3 419ip1 route add 10.0.0.0/24 dev veth1 src 10.0.0.1 metric 2 420n1 wg set wg0 peer "$pub2" endpoint 10.0.0.2:2 421n1 ping -W 1 -c 1 192.168.241.2 422[[ $(n2 wg show wg0 endpoints) == "$pub1 10.0.0.1:1" ]] 423ip1 route add 10.0.0.0/24 dev veth3 src 10.0.0.3 metric 1 424n1 bash -c 'printf 0 > /proc/sys/net/ipv4/conf/veth1/rp_filter' 425n2 bash -c 'printf 0 > /proc/sys/net/ipv4/conf/veth4/rp_filter' 426n1 bash -c 'printf 0 > /proc/sys/net/ipv4/conf/all/rp_filter' 427n2 bash -c 'printf 0 > /proc/sys/net/ipv4/conf/all/rp_filter' 428n1 ping -W 1 -c 1 192.168.241.2 429[[ $(n2 wg show wg0 endpoints) == "$pub1 10.0.0.3:1" ]] 430 431ip1 link del veth1 432ip1 link del veth3 433ip1 link del wg0 434ip2 link del wg0 435 436# We test that Netlink/IPC is working properly by doing things that usually cause split responses 437ip0 link add dev wg0 type wireguard 438config=( "[Interface]" "PrivateKey=$(wg genkey)" "[Peer]" "PublicKey=$(wg genkey)" ) 439for a in {1..255}; do 440 for b in {0..255}; do 441 config+=( "AllowedIPs=$a.$b.0.0/16,$a::$b/128" ) 442 done 443done 444n0 wg setconf wg0 <(printf '%s\n' "${config[@]}") 445i=0 446for ip in $(n0 wg show wg0 allowed-ips); do 447 ((++i)) 448done 449((i == 255*256*2+1)) 450ip0 link del wg0 451ip0 link add dev wg0 type wireguard 452config=( "[Interface]" "PrivateKey=$(wg genkey)" ) 453for a in {1..40}; do 454 config+=( "[Peer]" "PublicKey=$(wg genkey)" ) 455 for b in {1..52}; do 456 config+=( "AllowedIPs=$a.$b.0.0/16" ) 457 done 458done 459n0 wg setconf wg0 <(printf '%s\n' "${config[@]}") 460i=0 461while read -r line; do 462 j=0 463 for ip in $line; do 464 ((++j)) 465 done 466 ((j == 53)) 467 ((++i)) 468done < <(n0 wg show wg0 allowed-ips) 469((i == 40)) 470ip0 link del wg0 471ip0 link add wg0 type wireguard 472config=( ) 473for i in {1..29}; do 474 config+=( "[Peer]" "PublicKey=$(wg genkey)" ) 475done 476config+=( "[Peer]" "PublicKey=$(wg genkey)" "AllowedIPs=255.2.3.4/32,abcd::255/128" ) 477n0 wg setconf wg0 <(printf '%s\n' "${config[@]}") 478n0 wg showconf wg0 > /dev/null 479ip0 link del wg0 480 481allowedips=( ) 482for i in {1..197}; do 483 allowedips+=( abcd::$i ) 484done 485saved_ifs="$IFS" 486IFS=, 487allowedips="${allowedips[*]}" 488IFS="$saved_ifs" 489ip0 link add wg0 type wireguard 490n0 wg set wg0 peer "$pub1" 491n0 wg set wg0 peer "$pub2" allowed-ips "$allowedips" 492{ 493 read -r pub allowedips 494 [[ $pub == "$pub1" && $allowedips == "(none)" ]] 495 read -r pub allowedips 496 [[ $pub == "$pub2" ]] 497 i=0 498 for _ in $allowedips; do 499 ((++i)) 500 done 501 ((i == 197)) 502} < <(n0 wg show wg0 allowed-ips) 503ip0 link del wg0 504 505! n0 wg show doesnotexist || false 506 507ip0 link add wg0 type wireguard 508n0 wg set wg0 private-key <(echo "$key1") peer "$pub2" preshared-key <(echo "$psk") 509[[ $(n0 wg show wg0 private-key) == "$key1" ]] 510[[ $(n0 wg show wg0 preshared-keys) == "$pub2 $psk" ]] 511n0 wg set wg0 private-key /dev/null peer "$pub2" preshared-key /dev/null 512[[ $(n0 wg show wg0 private-key) == "(none)" ]] 513[[ $(n0 wg show wg0 preshared-keys) == "$pub2 (none)" ]] 514n0 wg set wg0 peer "$pub2" 515n0 wg set wg0 private-key <(echo "$key2") 516[[ $(n0 wg show wg0 public-key) == "$pub2" ]] 517[[ -z $(n0 wg show wg0 peers) ]] 518n0 wg set wg0 peer "$pub2" 519[[ -z $(n0 wg show wg0 peers) ]] 520n0 wg set wg0 private-key <(echo "$key1") 521n0 wg set wg0 peer "$pub2" 522[[ $(n0 wg show wg0 peers) == "$pub2" ]] 523n0 wg set wg0 private-key <(echo "/${key1:1}") 524[[ $(n0 wg show wg0 private-key) == "+${key1:1}" ]] 525n0 wg set wg0 peer "$pub2" allowed-ips 0.0.0.0/0,10.0.0.0/8,100.0.0.0/10,172.16.0.0/12,192.168.0.0/16 526n0 wg set wg0 peer "$pub2" allowed-ips 0.0.0.0/0 527n0 wg set wg0 peer "$pub2" allowed-ips ::/0,1700::/111,5000::/4,e000::/37,9000::/75 528n0 wg set wg0 peer "$pub2" allowed-ips ::/0 529n0 wg set wg0 peer "$pub2" remove 530for low_order_point in AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA= AQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA= 4Ot6fDtBuK4WVuP68Z/EatoJjeucMrH9hmIFFl9JuAA= X5yVvKNQjCSx0LFVnIPvWwREXMRYHI6G2CJO3dCfEVc= 7P///////////////////////////////////////38= 7f///////////////////////////////////////38= 7v///////////////////////////////////////38=; do 531 n0 wg set wg0 peer "$low_order_point" persistent-keepalive 1 endpoint 127.0.0.1:1111 532done 533[[ -n $(n0 wg show wg0 peers) ]] 534exec 4< <(n0 ncat -l -u -p 1111) 535ncat_pid=$! 536waitncatudp $netns0 $ncat_pid 537ip0 link set wg0 up 538! read -r -n 1 -t 2 <&4 || false 539kill $ncat_pid 540ip0 link del wg0 541 542declare -A objects 543while read -t 0.1 -r line 2>/dev/null || [[ $? -ne 142 ]]; do 544 [[ $line =~ .*(wg[0-9]+:\ [A-Z][a-z]+\ [0-9]+)\ .*(created|destroyed).* ]] || continue 545 objects["${BASH_REMATCH[1]}"]+="${BASH_REMATCH[2]}" 546done < /dev/kmsg 547alldeleted=1 548for object in "${!objects[@]}"; do 549 if [[ ${objects["$object"]} != *createddestroyed ]]; then 550 echo "Error: $object: merely ${objects["$object"]}" >&3 551 alldeleted=0 552 fi 553done 554[[ $alldeleted -eq 1 ]] 555pretty "" "Objects that were created were also destroyed." 556