Skip to content

Instantly share code, notes, and snippets.

@brettowe
Last active September 5, 2025 16:43
Show Gist options
  • Save brettowe/4d9d7b24baa5f974c998fa45fadd53a4 to your computer and use it in GitHub Desktop.
Save brettowe/4d9d7b24baa5f974c998fa45fadd53a4 to your computer and use it in GitHub Desktop.
wireguard namespace script, based off the script found here https://www.wireguard.com/netns/, made more automatic for pulling info from wg-quick configs and deal with a system using NetworkManager
#!/bin/bash
# based off the basic script idea found here: https://www.wireguard.com/netns/
set -ex
# namespace name
ns=physical
# ethernet type device list, seperated by spaces
physeth="enp1s0"
# wifi devices
physwifi="wlp2s0"
# list of phy devices that iw needs to touch
phywifi="phy0"
# wireguard device to use
wgdev=wg0
# assumes wg-quick style file
wgcfg=/etc/wireguard/wg0.conf
[[ $UID != 0 ]] && exec sudo -E "$(readlink -f "$0")" "$@"
up() {
wgip=$(grep Address ${wgcfg} | tr -d ' ' | cut -d '=' -f 2)
nsresolvconfdir="/etc/netns/${ns}"
nsresolvconf="${nsresolvconfdir}/resolv.conf"
wgresolvconf="/etc/resolv.conf"
wgip=$(grep Address ${wgcfg} | tr -d ' ' | cut -d '=' -f 2)
EPHN=$(grep Endpoint ${wgcfg} | tr -d ' ' | cut -d '=' -f 2 | cut -d ':' -f 1 | cut -d ' ' -f 1)
# use getent to resolve wireguard endpoint dns names to IP since wg will fail when it runs trying
# to resolve the dns since open dns requests are outside the namespace it attempts to connect with
EPIP=$(getent hosts ${EPHN} | tr -s ' ' | cut -d ' ' -f 1)
DNSIP=$(grep DNS ${wgcfg} | tr -d ' ' | cut -d '=' -f 2)
wgtmpcfg=$(mktemp)
if [ -d ${nsresolvconfdir} ]; then
mkdir -p ${nsresolvconfdir}
fi
# copy previous resolvconf into namespace conf space
# dhcp might overwrite it immediately but better than nothing existing
cp ${wgresolvconf} ${nsresolvconf}
# then modify previous copy for the namespace wg is in
sed --in-place -e "s/nameserver .*/nameserver ${DNSIP}/" ${wgresolvconf}
sed -e "/Address/d; /DNS/d; s/${EPHN}/${EPIP}/" ${wgcfg} > ${wgtmpcfg}
systemctl stop NetworkManager || true
ip netns add ${ns}
ip -n ${ns} link add ${wgdev} type wireguard
ip -n ${ns} link set ${wgdev} netns 1
wg setconf ${wgdev} ${wgtmpcfg}
ip addr add ${wgip} dev ${wgdev}
for pd in ${physeth}; do
ip link set ${pd} down
ip link set ${pd} netns ${ns}
done
for pd in ${physwifi}; do
ip link set ${pd} down
done
for pd in ${phywifi}; do
iw phy ${pd} set netns name ${ns}
done
# would like to just use network manager to manage the interfaces but it needs more than just itself
#ip netns exec ${ns} NetworkManager
ip link set ${wgdev} up
ip route add default dev ${wgdev}
rm ${wgtmpcfg}
}
down() {
#systemctl stop NetworkManager || true
#killall -KILL NetworkManager || true
killall -KILL dhcpcd || true
ip link del ${wgdev} || true
for pd in ${physeth}; do
ip -n ${ns} link set ${pd} down
ip -n ${ns} link set ${pd} netns 1
done
for pd in ${physwifi}; do
ip -n ${ns} link set ${pd} down
done
for pd in ${phywifi}; do
ip netns exec ${ns} iw phy ${pd} set netns 1
done
ip netns del ${ns}
systemctl start NetworkManager
}
execi() {
exec ip netns exec ${ns} sudo -E -u \#${SUDO_UID:-$(id -u)} -g \#${SUDO_GID:-$(id -g)} -- "$@"
}
command="$1"
shift
case "$command" in
up) up "$@" ;;
down) down "$@" ;;
exec) execi "$@" ;;
*) echo "Usage: $0 up|down|exec" >&2; exit 1 ;;
esac
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment