fcnet_types/lib.rs
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91
#[cfg(all(not(feature = "simple"), not(feature = "namespaced")))]
compile_error!("Either \"simple\" or \"namespaced\" networking feature flags must be enabled");
use std::net::IpAddr;
use cidr::IpInet;
/// A configuration for a Firecracker microVM network.
#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
pub struct FirecrackerNetwork {
/// The optional explicit path to "nft" to use when invoking it.
#[cfg_attr(feature = "serde", serde(default))]
pub nft_path: Option<String>,
/// The IP stack to use.
#[cfg_attr(feature = "serde", serde(default))]
pub ip_stack: FirecrackerIpStack,
/// The name of the host network interface that handles real connectivity (i.e. via Ethernet or Wi-Fi).
pub iface_name: String,
/// The name of the tap device to direct Firecracker to use.
pub tap_name: String,
/// The IP of the tap device to direct Firecracker to use.
pub tap_ip: IpInet,
/// The IP of the guest.
pub guest_ip: IpInet,
/// The type of network to create, the available options depend on the feature flags enabled.
pub network_type: FirecrackerNetworkType,
}
/// The IP stack to use for networking.
#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash, Default)]
#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
pub enum FirecrackerIpStack {
/// IPv4, translated to "ip" chains in nftables.
#[default]
V4,
/// IPv6, translated to "ip6" chains in nftables.
V6,
/// Both IPv4 and IPv6, translated to "inet" chains in nftables.
Dual,
}
/// The type of Firecracker network to work with.
#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
#[cfg_attr(feature = "serde", serde(tag = "type"))]
pub enum FirecrackerNetworkType {
/// A "simple" network configuration, with a tap device bound to the host interface via 1 set of forwarding rules.
/// The most optimal and performant choice for the majority of use-cases.
#[cfg(feature = "simple")]
Simple,
/// A namespaced network configuration, with the tap device residing in a separate network namespace and being
/// bound to the host interface via 2 sets of forwarding rules.
/// The better choice exclusively for multiple running microVM sharing the same snapshot data (i.e. so-called "clones").
#[cfg(feature = "namespaced")]
Namespaced {
netns_name: String,
veth1_name: String,
veth2_name: String,
veth1_ip: IpInet,
veth2_ip: IpInet,
#[cfg_attr(feature = "serde", serde(default))]
forwarded_guest_ip: Option<IpAddr>,
},
}
impl FirecrackerNetwork {
/// Format a kernel boot argument that can be added so that all routing setup in the guest is performed
/// by the kernel automatically with iproute2 not needed in the guest.
pub fn guest_ip_boot_arg(&self, guest_iface_name: impl AsRef<str>) -> String {
format!(
"ip={}::{}:{}::{}:off",
self.guest_ip.address().to_string(),
self.tap_ip.address().to_string(),
self.guest_ip.mask().to_string(),
guest_iface_name.as_ref()
)
}
}
/// An operation that can be made with a FirecrackerNetwork.
#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)]
#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
pub enum FirecrackerNetworkOperation {
/// Add this network to the host.
Add,
/// Check that this network already exists on the host.
Check,
/// Delete this network from the host.
Delete,
}