Forward all traffic from a VLAN to wireguard interface (outbound)

Hello everyone!

I'm building the following setup:

  • Multiple, seperated VLANs (lan,gast,iot,nl,wan)
  • "Router on a stick" with a Raspberry Pi5 openwrt as the main router
  • Connected to a managed switch with several access ports for client devices
  • Internet access over existing ISP Router (vlan1000/wan) also connected to the switch
  • Traffic from clients connected to the nl VLAN should go through the wg0 wireguard tunnel and mainly to internet from there.

Basic config for the VLANs including the switch is working. Clients in lan/gast/iot get DHCP addresses and DNS info from the router and can successfully reach the web via wan.

The wireguard also seems to work, handshake is successful with the peer. When connecting to the same peer (same config file used) with the official wireguard client software from a client, I can reach the web via the endpoint.

What I can't get to work is to route all the traffic from the nl VLAN to the wireguard interface. I have set up a dedicated wireguard zone, identical to the wan zone. Then a zone for the nl VLAN which forwards to the wireguard zone.

Any help would be greatyl appreciated! And please bear with me, I'm very new to openwrt.

BusyBox v1.36.1 (2025-02-03 23:09:37 UTC) built-in shell (ash)

  _______                     ________        __
 |       |.-----.-----.-----.|  |  |  |.----.|  |_
 |   -   ||  _  |  -__|     ||  |  |  ||   _||   _|
 |_______||   __|_____|__|__||________||__|  |____|
          |__| W I R E L E S S   F R E E D O M
 -----------------------------------------------------
 OpenWrt 24.10.0, r28427-6df0e3d02a
 -----------------------------------------------------
root@PiWrt:~# cat /etc/config/network

config interface 'loopback'
        option device 'lo'
        option proto 'static'
        option ipaddr '127.0.0.1'
        option netmask '255.0.0.0'

config globals 'globals'
        option ula_prefix 'fd83:b4c2:2e4a::/48'
        option packet_steering '1'

config device
        option name 'br-lan'
        option type 'bridge'
        list ports 'eth0'

config interface 'lan'
        option device 'br-lan.10'
        option proto 'static'
        option ipaddr '192.168.10.1'
        option netmask '255.255.255.0'
        option ip6assign '60'
        option defaultroute '0'

config bridge-vlan
        option device 'br-lan'
        option vlan '1000'
        list ports 'eth0:t'

config bridge-vlan
        option device 'br-lan'
        option vlan '20'
        list ports 'eth0:t'

config interface 'wan'
        option proto 'dhcp'
        option device 'br-lan.1000'

config bridge-vlan
        option device 'br-lan'
        option vlan '10'
        list ports 'eth0:t'

config bridge-vlan
        option device 'br-lan'
        option vlan '30'
        list ports 'eth0:t'

config bridge-vlan
        option device 'br-lan'
        option vlan '40'
        list ports 'eth0:t'

config interface 'gast'
        option proto 'static'
        option device 'br-lan.20'
        option ipaddr '192.168.20.1'
        option netmask '255.255.255.0'
        option defaultroute '0'

config interface 'iot'
        option proto 'static'
        option device 'br-lan.30'
        option ipaddr '192.168.30.1'
        option netmask '255.255.255.0'
        option defaultroute '0'

config interface 'nl'
        option proto 'static'
        option device 'br-lan.40'
        option ipaddr '192.168.40.1'
        option netmask '255.255.255.0'
        option defaultroute '0'

config interface 'wg0'
        option proto 'wireguard'
        option private_key 'REDACTED'
        list addresses '10.100.0.3/32'
        list addresses 'fd08:4711::3/128'
        list dns 'REDACTED'
        option defaultroute '0'

config wireguard_wg0
        option description 'Imported peer configuration'
        option public_key 'REDACTED'
        option preshared_key 'REDACTED'
        list allowed_ips '0.0.0.0/0'
        list allowed_ips '::/0'
        option persistent_keepalive '25'
        option endpoint_host 'REDACTED'
        option endpoint_port 'REDACTED'
root@PiWrt:~# cat /etc/config/firewall

config defaults
        option input 'REJECT'
        option output 'ACCEPT'
        option forward 'REJECT'
        option synflood_protect '1'
        option drop_invalid '1'

config zone
        option name 'lan'
        list network 'lan'
        option input 'ACCEPT'
        option output 'ACCEPT'
        option forward 'ACCEPT'

config zone
        option name 'wan'
        option input 'DROP'
        option output 'ACCEPT'
        option forward 'DROP'
        option masq '1'
        option mtu_fix '1'
        list network 'wan'

config forwarding
        option src 'lan'
        option dest 'wan'

config rule
        option name 'Allow-DHCP-Renew'
        option src 'wan'
        option proto 'udp'
        option dest_port '68'
        option target 'ACCEPT'
        option family 'ipv4'

config rule
        option name 'Allow-Ping'
        option src 'wan'
        option proto 'icmp'
        option icmp_type 'echo-request'
        option family 'ipv4'
        option target 'ACCEPT'

config rule
        option name 'Allow-IGMP'
        option src 'wan'
        option proto 'igmp'
        option family 'ipv4'
        option target 'ACCEPT'

config rule
        option name 'Allow-DHCPv6'
        option src 'wan'
        option proto 'udp'
        option dest_port '546'
        option family 'ipv6'
        option target 'ACCEPT'

config rule
        option name 'Allow-MLD'
        option src 'wan'
        option proto 'icmp'
        option src_ip 'fe80::/10'
        list icmp_type '130/0'
        list icmp_type '131/0'
        list icmp_type '132/0'
        list icmp_type '143/0'
        option family 'ipv6'
        option target 'ACCEPT'

config rule
        option name 'Allow-ICMPv6-Input'
        option src 'wan'
        option proto 'icmp'
        list icmp_type 'echo-request'
        list icmp_type 'echo-reply'
        list icmp_type 'destination-unreachable'
        list icmp_type 'packet-too-big'
        list icmp_type 'time-exceeded'
        list icmp_type 'bad-header'
        list icmp_type 'unknown-header-type'
        list icmp_type 'router-solicitation'
        list icmp_type 'neighbour-solicitation'
        list icmp_type 'router-advertisement'
        list icmp_type 'neighbour-advertisement'
        option limit '1000/sec'
        option family 'ipv6'
        option target 'ACCEPT'

config rule
        option name 'Allow-ICMPv6-Forward'
        option src 'wan'
        option dest '*'
        option proto 'icmp'
        list icmp_type 'echo-request'
        list icmp_type 'echo-reply'
        list icmp_type 'destination-unreachable'
        list icmp_type 'packet-too-big'
        list icmp_type 'time-exceeded'
        list icmp_type 'bad-header'
        list icmp_type 'unknown-header-type'
        option limit '1000/sec'
        option family 'ipv6'
        option target 'ACCEPT'

config rule
        option name 'Allow-IPSec-ESP'
        option src 'wan'
        option dest 'lan'
        option proto 'esp'
        option target 'ACCEPT'

config rule
        option name 'Allow-ISAKMP'
        option src 'wan'
        option dest 'lan'
        option dest_port '500'
        option proto 'udp'
        option target 'ACCEPT'

config zone
        option name 'wg0'
        option input 'DROP'
        option output 'ACCEPT'
        option forward 'DROP'
        list network 'wg0'

config zone
        option name 'gast'
        option input 'DROP'
        option output 'ACCEPT'
        option forward 'DROP'
        list device 'br-lan.20'

config forwarding
        option src 'gast'
        option dest 'wan'

config rule
        option src 'gast'
        option dest_port '67 68'
        option target 'ACCEPT'
        option name 'gast-DHCP'

config rule
        option name 'gast-DNS'
        option src 'gast'
        option dest_port '53'
        option target 'ACCEPT'

config zone
        option name 'iot'
        option input 'DROP'
        option output 'ACCEPT'
        option forward 'DROP'
        list device 'br-lan.30'

config forwarding
        option src 'iot'
        option dest 'wan'

config rule
        option name 'iot-DHCP'
        option src 'iot'
        option dest_port '67 68'
        option target 'ACCEPT'

config rule
        option name 'iot-DNS'
        option src 'iot'
        option dest_port '53'
        option target 'ACCEPT'

config rule
        option name 'nl-DHCP'
        option src 'nl'
        option dest_port '67 68'
        option target 'ACCEPT'

config rule
        option name 'nl-DNS'
        option src 'nl'
        option dest_port '53'
        option target 'ACCEPT'

config zone
        option name 'nl'
        option input 'DROP'
        option output 'ACCEPT'
        option forward 'DROP'
        list device 'br-lan.40'

config forwarding
        option src 'nl'
        option dest 'wg0'

Enable Route Allowed IPs on the WireGuard peer

Ok, tried that. Still no luck, unfortunately.

Since you've set the interface (actually all of them) to not use the default route...

You need to select one of the following options:

  • remove that line so that the interfaces use the new default route via the WG tunnel (this is established with the route_allowed_ips option in WG).
  • Use Policy Based Routing to setup the desired policies and routes.
  • Build your own routing table manually

Setting the default route by removing the "option defaultroute '0'" didn't work.

But I made it work with Policy Based Routing. Installed luci-app-pbr and set a policy according to https://openwrt.org/docs/guide-user/network/routing/pbr_app#route_lan_to_vpn
I also had to set a DNS policy, to prevent DNS leak.

Have to play around with it a bit more for fine-tuning, but I am glad that it works at all!
Thanks a ton!

This topic was automatically closed 10 days after the last reply. New replies are no longer allowed.