FlyingBullets n00b
Joined: 19 Mar 2024 Posts: 5
|
Posted: Thu Aug 08, 2024 5:37 pm Post subject: WireGuard can't send/receive network packets [SOLVED] |
|
|
I am trying to set up WireGuard (WG) on my laptop so that I can connect to my home network. The endpoint is my router running OpenWRT ready to receive the request. I tested the WG connection with my Android phone using the official WG app. I'm able to keep a reliable connection between my phone and router. When I setup WG on Gentoo following the guide (no wg-quick), WG is able to connect (even OpenWRT detects it), but is unable to send/receive any traffic. WG *seems* to work for a few seconds right after startup, but eventually fails.
NOTE: /etc/resolv.conf stays the same after starting net.wg0.
Code: | user $ ping gnu.org
ping: gnu.org: Temporary failure in name resolution |
Code: | user $ ping 1.1.1.1
(100% packet loss) |
I then tried using my laptop's WG config file, /etc/wireguard/wg0.conf, on my phone to see if it would still work (after adding the 'DNS =' and 'Address =' lines). The result was it did work.
The only custom thing I changed from the wiki was a line in the postup() function, changing 'ip' to 'inet' to account for both IPv4 and IPv6. I'm also using the Gentoo example workstation nftable rule.
/etc/wireguard/wg0.conf:
Code: | # /etc/wireguard/wg0.conf
[Interface]
PrivateKey = INTERFACE_PRIVATE_KEY_PLACEHOLDER
# 'Address' is not recognized by netifrc; put addresses in 'config_wg0'.
#Address =
# 'DNS' is not recognized by netifrc; put dns addresses in 'dns_servers_wg0'.
#DNS =
[Peer]
PublicKey = PEER_PUBLIC_KEY_PLACEHOLDER
PresharedKey = PRESHARED_KEY_PLACEHOLDER
AllowedIPs = 0.0.0.0/0, ::/0
Endpoint = IP_ADDRESS_OR_DOMAIN_PLACEHOLDER:51820
# This can help keep the connection alive when this machine is behind a NAT.
PersistentKeepAlive = 25 |
/var/lib/nftables/rules-save:
Code: | #!/sbin/nft -f
# NOTE:
# * Location of this file is NFTABLES_SAVE in /etc/conf.d/nftables.
#
# * The following rule set was gotten at:
# https://wiki.gentoo.org/wiki/Nftables/Examples
flush ruleset
table inet filter {
chain input {
type filter hook input priority 0; policy drop;
ct state invalid counter drop comment "early drop of invalid packets"
ct state {established, related} counter accept comment "accept all connections related to connections made by us"
iif lo accept comment "accept loopback"
iif != lo ip daddr 127.0.0.1/8 counter drop comment "drop connections to loopback not coming from loopback"
iif != lo ip6 daddr ::1/128 counter drop comment "drop connections to loopback not coming from loopback"
ip protocol icmp counter accept comment "accept all ICMP types"
meta l4proto ipv6-icmp counter accept comment "accept all ICMP types"
tcp dport 22 counter accept comment "accept SSH"
counter comment "count dropped packets"
}
chain forward {
type filter hook forward priority 0; policy drop;
counter comment "count dropped packets"
}
# If we're not counting packets, this chain can be omitted.
chain output {
type filter hook output priority 0; policy accept;
counter comment "count accepted packets"
}
} |
/etc/conf.d/net:
Code: | #!/bin/bash
# /etc/conf.d/net
# NOTE:
# * Not all rules can be global.
#
# * Default behavior is used if a rule is empty ("") or missing (commented out).
#
# * Interface-specific rules do not carry over global rules.
# Example:
# If
# - modules="!wireless"
# - modules_wwan0="wpa_supplicant"
# then, modules_wwan0="wpa_supplicant", not "!wireless wpa_supplicant".
#
# * If two or more mutually exclusive rules are used, the result is undefined.
# Example:
# ...="!wireless wpa_supplicant"
# and
# ...="wpa_supplicant !wireless"
# both result in no wireless capabilities.
#
# * Consider the following:
# - Interface A has DNS server/domain A1 via 'dns_*_A="A1"'
# - Interface B has DNS server/domain B1 via 'dns_*_B="B1"'
# If interface A starts, then B, then the current DNS server is B1. If B stops, then the current DNS server is still B1.
#
# * ifplugd works as long as the interface stays connected to the machine. For example, if using a USB-to-ethernet adapter, ifplugd will reconnect if the
# ethernet side was disconnected (the USB side is still connected to the machine, thus the machine still sees the interface), but not if the
# USB side was disconnected (the machine lost sight of the interface).
# Set which modules to use.
declare -r MY_GLOBAL_MODULES="dhcpcd iproute2 ifplugd"
# 'dhcp'
# Dynamically set IP address, DNS server, etc.
declare -r MY_GLOBAL_CONFIG="dhcp"
# A route is a rule set in the kernel that is used to determine which physical network interface or gateway is needed in order to reach a particular network
# (or single host).
# https://wiki.gentoo.org/wiki/Static_routing
declare -r MY_GLOBAL_ROUTES=""
# 'nodns'
# Do not let dhcp set the DNS server; this rule is required to set a specific DNS server here. If this is not set, then dhcp and netifrc will
# fight over /etc/resolv.conf! If we want dhcp to set the DNS server, remove 'nodns' and the specified DNS server.
declare -r MY_GLOBAL_DHCP="nodns"
# Set the DNS server (IP address).
#
# NOTE:
# * Not all places support IPv6. Phones might not support IPv6 through hotspot.
#
# * OpenDNS: 208.67.220.220 208.67.222.222 2620:0:ccc::2 2620:0:ccd::2
#
# * Quad9: 9.9.9.9 2620:fe::fe
#
# * Mullvad (no content filtering): 194.242.2.2 2a07:e340::2
declare -r MY_GLOBAL_DNS_SERVERS="208.67.220.220 208.67.222.222 2620:0:ccc::2 2620:0:ccd::2"
# Set the DNS server (domain).
#
# NOTE:
# * Mullvad (no content filtering): dns.mullvad.net
declare -r MY_GLOBAL_DNS_SEARCH=""
# Set the maximum transfer unit.
declare -r MY_GLOBAL_MTU=""
# Set the MAC address.
declare -r MY_GLOBAL_MAC="random-samekind"
# Set the priority (lower number = higher priority).
declare -r MY_GLOBAL_METRIC=""
# Set dependencies.
declare -r MY_GLOBAL_RC_NET_NEED=""
# Global rules
##############
#modules=""
#config=""
#...
# WireGuard rules
#################
wireguard_wg0="/etc/wireguard/wg0.conf"
modules_wg0="$MY_GLOBAL_MODULES !wireless"
config_wg0="$MY_GLOBAL_CONFIG"
routes_wg0="$MY_GLOBAL_ROUTES"
dhcp_wg0="$MY_GLOBAL_DHCP"
# Stopping WireGuard will not change the DNS back to what it was before starting this interface; that must be done in postup() and predown().
# We set it to nothing here because we are going to use the same DNS anyway.
dns_servers_wg0=""
dns_search_wg0=""
mtu_wg0="$MY_GLOBAL_MTU"
# WireGuard does not use MAC addresses.
mac_wg0=""
metric_wg0="0"
rc_net_wg0_need="$MY_GLOBAL_RC_NET_NEED"
# Wifi rules
############
modules_wlan0="$MY_GLOBAL_MODULES wpa_supplicant"
config_wlan0="$MY_GLOBAL_CONFIG"
routes_wlan0="$MY_GLOBAL_ROUTES"
dhcp_wlan0="$MY_GLOBAL_DHCP"
dns_servers_wlan0="$MY_GLOBAL_DNS_SERVERS"
dns_search_wlan0="$MY_GLOBAL_DNS_SEARCH"
mtu_wlan0="$MY_GLOBAL_MTU"
mac_wlan0="$MY_GLOBAL_MAC"
metric_wlan0="2"
rc_net_wlan0_need="$MY_GLOBAL_RC_NET_NEED dbus"
postup()
{
# After the wg0 interface is up, we add routing and firewall rules,
# which prevent packets from going through the normal routes, which are
# for "plaintext" packets.
# routing rules taken from: https://www.wireguard.com/netns/
# firewall rules taken from: man wg-quick
#
# If the connection to the VPN goes down, the firewall rule makes sure
# no other connections can be open, until you remove the interface
# using: rc-service net.wg0 stop
#
# For the nftables firewall rule to work, make sure you set:
# SAVE_ON_STOP="no"
# in: /etc/conf.d/nftables
if [[ "${IFACE}" == "wg0" ]]; then
# Set a firewall mark for all wireguard packets.
wg set wg0 fwmark 334455 || exit 1
# Route all packets to the wg0 interface in table 2468.
ip route add default dev wg0 table 2468 || exit 1
# If packet doesn't have the wireguard firewall mark, send it to table 2468.
ip rule add not fwmark 334455 table 2468 || exit 1
# If packet isn't going out the wg0 interface, doesn't have the wireguard firewall mark and isn't broadcast or multicast reject it
# (don't drop it like there's no connection).
#
# NOTE:
# * We use 'inet' for IPv4 and IPv6.
#
# * Shell scripts break atomicity when applying the ruleset unless using nftables native scripting environment.
# https://wiki.nftables.org/wiki-nftables/index.php/Scripting
#
# It's fine here because we're only using one command.
nft insert rule inet filter output oifname!="wg0" mark!=334455 fib daddr type!=local counter reject || exit 1
# Make sure only DNS server is the one from your provider or
# a custom one fitting your needs!
# If there is one, otherwise you can remove this line.
#echo "nameserver 9.10.11.12" > /etc/resolv.conf || exit 1
fi
return 0
}
predown()
{
# Prevent bringing down interface in case there's a NFS root.
# taken from: https://github.com/gentoo/netifrc/blob/4bd8be5f43d07a9e92b73174c7fbef8b989aaa55/doc/net.example.Linux.in
if is_net_fs /; then
eerror "root filesystem is network mounted -- can't stop ${IFACE}"
return 1
fi
# When bringing down the interface using rc-service, make sure that all
# rules specific to isolating the wireguard connections are gone, so
# that normal connections can work again.
# Change the DNS values for your setup!
if [[ "${IFACE}" == "wg0" ]]; then
# Bringing back default nftables rules.
rc-service nftables reload || exit 1
# Removing wireguard specific routing rules.
ip route del default dev wg0 table 2468 || exit 1
ip rule del not fwmark 334455 table 2468 || exit 1
# Bringing back your own DNS settings, in case they were
# changed in postup()
#echo "nameserver 1.2.3.4" > /etc/resolv.conf || exit 1
#echo "nameserver 123.12.21.1" >> /etc/resolv.conf || exit 1
fi
return 0
} |
Last edited by FlyingBullets on Mon Oct 07, 2024 3:41 pm; edited 1 time in total |
|