Score:1

Best way to have a network bridge with both my LAN and WAN (not AP) interfaces attached?

us flag

I have this configuration to put my LAN and WAN (not AP) network interfaces on the same bridge but I'm wondering if there is a better way to do it? Has anyone done this in a better way? Thanks.

I've only tested it on Ubuntu 22.10 with Network Manager disabled and systemd-networkd enabled. I did that part like this:

sudo systemctl disable --now NetworkManager-dispatcher.service NetworkManager-wait-online.service NetworkManager.service
sudo systemctl enable --now systemd-networkd.service

Install some packages, you definitely need iw while bridge-utils and ebtables are optional but good to have for troubleshooting, etc.

sudo apt install bridge-utils ebtables iw

In the netplan yaml file below:

  • Replace eth0 with the name of your LAN network interface.
  • Replace wlan0 with the name of your LAN network interface. For network interface names, see the output of running these commands: ip a and ip l

Create: /etc/netplan/02-bridge.yaml

Contents:

network:
  version: 2
  renderer: networkd
  ethernets:
    eth0:
      dhcp4: no
  wifis:
    wlan0:
      dhcp4: no
      access-points:
        "<your SSID>":
          password: "<your password>"
  bridges:
    br0:
      dhcp4: yes
      interfaces:
        - eth0
        - wlan0

Copy the systemd-networkd.service unit file to the directory where administrators can override unit files. It is not safe to edit a unit file under /lib/systemd/system because a package update can overwrite your modifications. This is by design.

sudo cp /lib/systemd/system/systemd-networkd.service /etc/systemd/system/systemd-networkd.service

Then edit /etc/systemd/system/systemd-networkd.service, adding an ExecStartPre above the existing ExecStart.

$ diff -u /lib/systemd/system/systemd-networkd.service /etc/systemd/system/systemd-networkd.service
--- /lib/systemd/system/systemd-networkd.service    2022-09-20 11:19:06.000000000 -0400
+++ /etc/systemd/system/systemd-networkd.service    2022-10-09 20:48:35.657885031 -0400
@@ -23,6 +23,7 @@
 BusName=org.freedesktop.network1
 CapabilityBoundingSet=CAP_NET_ADMIN CAP_NET_BIND_SERVICE CAP_NET_BROADCAST CAP_NET_RAW
 DeviceAllow=char-* rw
+ExecStartPre=-/sbin/iw dev wlan0 set 4addr on
 ExecStart=!!/lib/systemd/systemd-networkd
 ExecReload=networkctl reload
 LockPersonality=yes

I do that because the iw ... 4addr, which turns on WDS mode has to happen before the wlan0 interfaces is added to the br0 bridge or you get:

Oct 09 14:14:34 wookums systemd-networkd[2006]: wlan0: Failed to set master interface: Device does not allow enslaving to a bridge. Operation not supported

Once WDS ("4addr") mode is enabled that error no longer happens.

I tried to use networkd-dispatcher to set WDS ("4addr") mode but it is started after systemd-networkd attempts to put wlan0 into the br0 bridge and fails because WDS has not yet been enabled.

It seems really gross to have to cram something into systemd-networkd.service just to have one line of code be run before something goes wrong because it wasn't run in time.

Aside from the obvious improvement of using a systemd unit file drop-in instead of copying all of systemd-networkd.service into /etc/systemd/system, is there any way to this better?

UPDATE:

  • wpa_supplicant connects to the AP using DHCP; the AP is a DHCP server and the wlan0 is a client. However, the IP address of wlan0 (acquired via DHCP) does not appear to be visible because bridge slaves do not have IP addresses assigned, only the bridge itself has one. The br0 and wlan0 interfaces will not have the same IP address; the wlan0 interface will not be usable even though brctl show and ip a, etc. will look OK.

Thanks KES

Tilman avatar
cn flag
Please explain what you are trying to achieve. Bridging two intentionally separate networks (as implied by the labels "LAN" and "WAN") generally doesn't make sense.
us flag
Bridges are exactly for connecting two different networks. But I don't understand what the submitter is looking for in terms of a "better" way.
Acceptable Name avatar
us flag
@Tilman KVM/Qemu/libvirt needs bridged networking in order for the VM guests to be on my LAN. My router is short on wired LAN ports. If I need to move a cable to another physical computer I want my bridge to stay up. In the past I was using a SolidRun Marvell Clearfog Pro with five LAN ports, running Arch Linux ARM. It died of contradictory constraints, specifically it is a 32-bit armv7 box while Arch Linux ARM is always providing the latest versions of package but developers are not testing their software on 32-bit systems much anymore. I switched to my 4-port backup router running OpenWRT.
Acceptable Name avatar
us flag
@slangasek I mean better approach, better coding, a better way to bridge LAN and WiFi.
Acceptable Name avatar
us flag
One of the issues that I'm having is that I only got the netplan configuration in my OP to work inside a Kinetic VM guest. My Ubuntu 22.04 VM host still needs a bit of clean up, probably due to being munged from a lot of stuff like being disto-updated repeatedly from 18.04. I'm sure I'll get there in time, netplan is already able to bring up a bridge with one LAN interface. One of the issues I ran into was that "netplan --debug try" doesn't warn about typos in NIC names so I opened a question on launchpad about that. https://answers.launchpad.net/ubuntu/+source/netplan.io/+question/703423
Acceptable Name avatar
us flag
@Tilman one more thing, I've been working on rebuilding the Clearfog Pro on Armbian, but I can't get to it much because I'm short on LAN cables and it's often unplugged from the LAN. The last thing I remember doing is selecting ufw as the firewall and starting to configure it. I'm an old man who's been using computers for 45 years and my memory isn't what it was. But I still remember finding a TCP/IP to Chaosnet protocol converter and using it to get to AI.AI.MIT.EDU which was necessary because the IMP had been removed from that KS10. I've been around the block a couple of times.
Acceptable Name avatar
us flag
Did I mention that I was in the Honeywell building on I-495 shoulder surfing Eagle Scouts while they used Multics? Did I mention bought my first computer in 1980 after bumming time of as many computers as I could in the 70s? Did I mention that my first UNIX-like system was David Beckemeyer's Micro-RTX and his MT-Cshell? I was using levee, a very small vi clone. Later after I started using real vi on System V2 on PDP-11 and then went back to levee I couldn't use it anymore because I had learned too many vi commands that it didn't implement.
Acceptable Name avatar
us flag
The moral of the story is don't as a blabber-mouth like me why he is doing something. ;)
Tilman avatar
cn flag
Ok, that's a lot to digest, and I'm not convinced it is all necessary in order to understand, and eventually answer, your question. Could you edit your question to include just the relevant parts? I guess your brush with Multics isn't, while the presence of KVM in your configuration certainly is. An overview of your network structure would also help to understand what you are trying to achieve.
Acceptable Name avatar
us flag
@Tilman Sorry, I over-reacted. I'm so used to asking a question on a forum only to have non-useful comments like "why do you want to do that?" that I must of misinterpreted you.
Acceptable Name avatar
us flag
@Tilman I've almost given up on this network configuration except for two things. (1) Debian has a page on using proxy ARP to do this instead of bridging but the author's configuration appears to involve the bridge as a separate computer between two networks. (2) It might be a better approach to use bonding instead of bridging for this.
Tilman avatar
cn flag
After re-reading your question I noticed one source for my confusion: The abbreviation "WAN" usually stands for "Wide Area Network", but you are apparently using it to mean "Wireless LAN". Also it seems that at least in the sentence "Replace wlan0 with the name of your LAN network interface", you used "LAN" to mean "Wireless LAN". It would really help if you always stuck to the customary abbreviation "WLAN" for that.
Tilman avatar
cn flag
Re your last comment, I do not think that either proxy ARP or bonding would work in your scenario. Bridging is indeed the way to go.
us flag
Ok not sure if the question has been changed or if I just missed the point before. But the other way to set the dev mode (and not racy, unlike starting it in systemd-networkd, which is!), is to write this as a udev rule that starts when your wlan0 device is available. (Which is covered by the answer below)
Score:0
cn flag

Linux offers several ways of configuring network interfaces. Each one has its own advantages and drawbacks. Each is geared towards a set of usecases and tends to become unwieldy when applied to a usecase outside what its creators had in mind.

The old sys5init up/down scripts were the most flexible solution since you could write into the scripts exactly what you needed. They were however error-prone and complicated for non-experts to handle and therefore fell out of favor. At the other end of the spectrum is NetworkManager which tries to automate everything so that the user doesn't have to think about it, thereby making it very hard for those who know exactly which settings they want to actually get them. Netplan is in the middle ground, accomodating a pretty wide range of setups easily, but there are scenarios like yours (setting RDS/4-address-mode on a wireless interface) which are not in its repertoire so you have to resort to scripting.

That said, there is an alternative to creating a custom systemd-networkd.service script. That is, create a udev rule as described in https://superuser.com/questions/1601099/how-to-automatically-enable-wifi-4addr-wds-mode-before-connecting-to-specific over on SuperUser. The limitation mentioned there (not being able to connect to non-RDS WLANs anymore) will probably not hurt you.

A note on DHCP:

Bridging is a layer 2 mechanism. The two bridged networks (LAN and WLAN) become a single broadcast domain, so a single DHCP server will cover them both. You should disable the DHCP server in your AP since your LAN DHCP server will also provide IP addresses to the WLAN once the bridge is up.

By the same reason, the member interfaces of the bridge cannot have and do not need individual layer 3 configurations such as IP addresses. Only the bridge as a whole has a layer 3 configuration. You enable the member interfaces eth0 and wlan0 and connect wlan0 to the AP via wpa_supplicant on layer 2 only, without assigning an IP address, by virtue of the dhcp*: no lines in your netplan configuration. Then you join them to the bridge. Only once that's done you run DHCP through the bridge interface to get one IP address from the (one) DHCP server serving your combined LAN/WLAN network segment.

(You could in theory run DHCP with only one interface in the bridge and the other one would then share the acquired IP address upon joining, but I recommend against it.)

Acceptable Name avatar
us flag
My example in the OP has "dhcp4: no" for the wlan0 already. (nitpick: IFAICT, "dhcp: no" is not valid netplan syntax, only "dhcp4" and "dhcp6" is.) I'm going to try to do this with individual commands instead of abstraction frameworks like netplan, Network Manager, ifupdown, etc. That will help me decide if it can be done at all.
mangohost

Post an answer

Most people don’t grasp that asking a lot of questions unlocks learning and improves interpersonal bonding. In Alison’s studies, for example, though people could accurately recall how many questions had been asked in their conversations, they didn’t intuit the link between questions and liking. Across four studies, in which participants were engaged in conversations themselves or read transcripts of others’ conversations, people tended not to realize that question asking would influence—or had influenced—the level of amity between the conversationalists.