Skip to content

Commit

Permalink
macvlan: add bclim option
Browse files Browse the repository at this point in the history
Expose the netlink IFLA_MACVLAN_BC_CUTOFF option as bclim like the ip
command does. We still need c/common and podman patches to allow this
option for podman network create.

Also I created a PR[1] upstream in the netlink lib to allow setting
these options directly instead of using the DefaultNla work around as I
do here.

TODO: Add a test but for now this option is not in a released version of
iproute so there is no way to check for it right now.

[1] rust-netlink/netlink-packet-route#32

This is needed for https://bugzilla.redhat.com/show_bug.cgi?id=2183896

Signed-off-by: Paul Holzinger <[email protected]>
  • Loading branch information
Luap99 committed May 24, 2023
1 parent 3d3563b commit e4e78f0
Show file tree
Hide file tree
Showing 4 changed files with 38 additions and 10 deletions.
1 change: 1 addition & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,7 @@ zbus = { version = "3.12.0" }
nix = "0.26.2"
rand = "0.8.5"
sha2 = "0.10.6"
netlink-packet-utils = "0.5"
netlink-packet-route = "0.15"
netlink-packet-core = "0.5"
fs2 = "0.4.3"
Expand Down
1 change: 1 addition & 0 deletions src/network/constants.rs
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ pub const OPTION_MTU: &str = "mtu";
pub const OPTION_MODE: &str = "mode";
pub const OPTION_METRIC: &str = "metric";
pub const OPTION_NO_DEFAULT_ROUTE: &str = "no_default_route";
pub const OPTION_BCLIM: &str = "bclim";

/// 100 is the default metric for most Linux networking tools.
pub const DEFAULT_METRIC: u32 = 100;
Expand Down
45 changes: 35 additions & 10 deletions src/network/vlan.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ use log::{debug, error};
use std::{collections::HashMap, net::IpAddr, os::unix::prelude::RawFd};

use netlink_packet_route::nlas::link::{InfoData, InfoIpVlan, InfoKind, InfoMacVlan, Nla};
use netlink_packet_utils::nla::DefaultNla;
use rand::distributions::{Alphanumeric, DistString};

use crate::network::macvlan_dhcp::{get_dhcp_lease, release_dhcp_lease};
Expand All @@ -14,7 +15,7 @@ use crate::{

use super::{
constants::{
NO_CONTAINER_INTERFACE_ERROR, OPTION_METRIC, OPTION_MODE, OPTION_MTU,
NO_CONTAINER_INTERFACE_ERROR, OPTION_BCLIM, OPTION_METRIC, OPTION_MODE, OPTION_MTU,
OPTION_NO_DEFAULT_ROUTE,
},
core_utils::{self, get_ipam_addresses, parse_option, CoreUtils},
Expand All @@ -30,6 +31,9 @@ enum KindData {
mac_address: Option<Vec<u8>>,
/// macvlan mode
mode: u32,

// IFLA_MACVLAN_BC_CUTOFF option if set
bclim: Option<i32>,
},
IpVlan {
/// ipvlan mode
Expand Down Expand Up @@ -117,13 +121,17 @@ impl driver::NetworkDriver for Vlan<'_> {
super::constants::DRIVER_IPVLAN => KindData::IpVlan {
mode: CoreUtils::get_ipvlan_mode_from_string(mode.as_deref())?,
},
super::constants::DRIVER_MACVLAN => KindData::MacVlan {
mode: CoreUtils::get_macvlan_mode_from_string(mode.as_deref())?,
mac_address: match &self.info.per_network_opts.static_mac {
Some(mac) => Some(CoreUtils::decode_address_from_hex(mac)?),
None => None,
},
},
super::constants::DRIVER_MACVLAN => {
let bclim = parse_option(&self.info.network.options, OPTION_BCLIM)?;
KindData::MacVlan {
mode: CoreUtils::get_macvlan_mode_from_string(mode.as_deref())?,
mac_address: match &self.info.per_network_opts.static_mac {
Some(mac) => Some(CoreUtils::decode_address_from_hex(mac)?),
None => None,
},
bclim,
}
}
other => {
return Err(NetavarkError::msg(format!(
"unsupported VLAN type {}",
Expand Down Expand Up @@ -268,13 +276,30 @@ fn setup(
opts.info_data = Some(InfoData::IpVlan(vec![InfoIpVlan::Mode(*mode)]));
opts
}
KindData::MacVlan { mode, mac_address } => {
KindData::MacVlan {
mode,
mac_address,
bclim,
} => {
let mut opts = CreateLinkOptions::new(if_name.to_string(), InfoKind::MacVlan);
opts.mac = mac_address.clone().unwrap_or_default();
opts.mtu = data.mtu;
opts.netns = netns_fd;
opts.link = link.header.index;
opts.info_data = Some(InfoData::MacVlan(vec![InfoMacVlan::Mode(*mode)]));

let mut mv_opts = vec![InfoMacVlan::Mode(*mode)];
if let Some(bclim) = bclim {
debug!("setting macvlan bclim to {bclim}");
// TODO: change this to use the upstream const when available
// https://github.com/rust-netlink/netlink-packet-route/pull/32
// IFLA_MACVLAN_BC_CUTOFF const in the kernel is 9
mv_opts.push(InfoMacVlan::Other(DefaultNla::new(
9,
bclim.to_ne_bytes().to_vec(),
)))
}

opts.info_data = Some(InfoData::MacVlan(mv_opts));
opts
}
};
Expand Down

0 comments on commit e4e78f0

Please sign in to comment.