From 2f6501ba37d77ec8dec67b5e3b5ee10da0c91662 Mon Sep 17 00:00:00 2001 From: blackdragoon26 Date: Tue, 12 Aug 2025 01:02:19 +0530 Subject: [PATCH] base files Signed-off-by: blackdragoon26 --- src/network/bridge.rs | 14 +++++++++++ src/network/netlink.rs | 55 ++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 69 insertions(+) diff --git a/src/network/bridge.rs b/src/network/bridge.rs index 0a4ef72fc..b08fc4259 100644 --- a/src/network/bridge.rs +++ b/src/network/bridge.rs @@ -85,6 +85,7 @@ impl<'a> Bridge<'a> { } } + impl driver::NetworkDriver for Bridge<'_> { fn network_name(&self) -> String { self.info.network.name.clone() @@ -583,6 +584,19 @@ fn create_interfaces( } if let BridgeMode::Unmanaged = data.mode { + if let Some(vlan_id) = data.vlan { + log::info!( + "Configuring VLAN {} filtering rules for unmanaged bridge {}", + vlan_id, + data.bridge_interface_name + ); + + + crate::utils::netlink::allow_dhcp_on_vlan( + &data.bridge_interface_name, + vlan_id, + )?; + } return Err(err) .wrap("in unmanaged mode, the bridge must already exist on the host"); } diff --git a/src/network/netlink.rs b/src/network/netlink.rs index 67ceef9fd..60297afa9 100644 --- a/src/network/netlink.rs +++ b/src/network/netlink.rs @@ -3,6 +3,7 @@ use std::{ os::fd::{AsFd, AsRawFd, BorrowedFd}, }; + use crate::{ error::{ErrorWrap, NetavarkError, NetavarkResult}, network::constants, @@ -612,3 +613,57 @@ pub fn parse_create_link_options(msg: &mut LinkMessage, options: CreateLinkOptio .push(LinkAttribute::NetNsFd(netns.as_raw_fd())); } } + + +use log::{info, warn}; +use rtnetlink::{new_connection, Error}; +use futures::stream::TryStreamExt; + + +pub fn allow_dhcp_on_vlan(bridge_name: &str, vlan_id: u16) -> Result<(), Error> { + info!( + "Applying DHCP allow rule on VLAN {} for bridge {}", + vlan_id, bridge_name + ); + + // Build VLAN subinterface name (e.g., br0.100) + let vlan_iface = format!("{}.{}", bridge_name, vlan_id); + + // Create netlink connection + let (connection, handle, _) = new_connection()?; + tokio::spawn(connection); + + // Lookup VLAN interface by name + let mut rt = tokio::runtime::Runtime::new().unwrap(); + let mut links = rt.block_on( + handle + .link() + .get() + .match_name(vlan_iface.clone()) + .execute() + ); + + match rt.block_on(links.try_next()) { + Ok(Some(_link)) => { + info!( + "Found VLAN interface {}, would configure bridge VLAN filtering to allow DHCP (UDP 67/68)", + vlan_iface + ); + // TODO: implement actual VLAN filtering adjustment here + } + Ok(None) => { + warn!( + "VLAN interface {} not found, skipping DHCP allow rule", + vlan_iface + ); + } + Err(e) => { + warn!( + "Error looking up VLAN interface {}: {}", + vlan_iface, e + ); + } + } + + Ok(()) +}