Skip to content

Flannel Reference

Scope

Look-up facts for Flannel v0.28.x: net-conf.json keys, backend matrix and options, flanneld flags and environment variables, node annotations, files and ports, K3s flags, Helm values, release history, performance estimates, and a hardening checklist. For why things work this way see Explanation; for step-by-step tasks see How-to Guides.

Version and Support Facts

Item Value Source
Latest release v0.28.9 (2026-08-07) GitHub releases, Chart.yaml
0.28 line started v0.28.0 (2026-01-06) GitHub releases
Release cadence (2026) Patch releases roughly every 2-6 weeks (v0.28.0 to v0.28.9 in about 7 months) GitHub releases
Supported versions Latest release only; older releases are not patched SECURITY.md
Vulnerability reporting GitHub private vulnerability reporting; acknowledgement within 7 days, fix target 90 days SECURITY.md
Container images ghcr.io/flannel-io/flannel:v0.28.9, ghcr.io/flannel-io/flannel-cni-plugin:v1.9.1-flannel3 kube-flannel.yml
Helm repo https://flannel-io.github.io/flannel/ (chart flannel/flannel, since v0.21.4) upgrade.md
Manifest Kubernetes minimum v1.17+ for the current kube-flannel.yml README
Build toolchain Go 1.26 (go.mod) go.mod
License Apache-2.0 LICENSE
Maintainers Manuel Buil, Michael Fritch, Roberto Bonafiglia, Thomas Ferrandiz (all SUSE) GOVERNANCE.md

Release History (selected)

Version Date Notable change
v0.28.9 2026-08-07 /healthz (liveness) and /readyz (readiness) endpoints, wired into manifest and chart on port 8081. etcd single-subnet watch recovers from compaction. Dependency CVE fixes (CVE-2026-46600, CVE-2026-56852).
v0.28.8 2026-07-22 Atomic write of subnet.env
v0.28.6 / v0.28.7 2026-07-07 New install-conf command used by the install-cni init container
v0.28.5 2026-06-04 VXLAN IPv4-only guard fix, zombie-process handling, k8s client libraries v0.33.11
v0.28.3 2026-04-15 GOVERNANCE.md added, VXLAN IPv6 route deletion fix
v0.28.2 2026-03-27 Fix for CVE-2026-32241 (extension backend RCE); build hardening
v0.28.0 2026-01-06 Go and k8s dependency upgrade, nftables pre-check, better primary-address selection
v0.26.0 2024-10-23 Multiple nodes behind a single public IP
v0.25.5 2024-07-17 kube-network-policies controller option in the Helm chart (netpol.enabled)
v0.25.0 2024-04-08 nftables implementation (EnableNFTables, experimental)
v0.24.0 2023-12-19 riscv64 support

Dates for v0.25.x and v0.26.0 come from the GitHub releases pages. Cross-check against newreleases.io if exact dates matter.

net-conf.json Keys

In kube mode Flannel reads /etc/kube-flannel/net-conf.json (the net-conf.json key of ConfigMap kube-flannel-cfg). In etcd mode it reads /coreos.com/network/config.

Key Type Default Notes
Network string (CIDR) none IPv4 cluster pod CIDR. Required if EnableIPv4. Upstream manifest uses 10.244.0.0/16; K3s uses 10.42.0.0/16.
IPv6Network string (CIDR) none Required if EnableIPv6
EnableIPv4 bool true Set false for IPv6-only
EnableIPv6 bool false Dual-stack or IPv6-only
EnableNFTables bool false EXPERIMENTAL. Use nftables instead of iptables for masquerade and forward rules (since v0.25.0).
SubnetLen int 24 If Network is smaller than /22, defaults to network prefix + 2. Ignored in kube mode (node podCIDR wins).
SubnetMin / SubnetMax string (IP) 2nd / last subnet Allocation range (etcd mode)
IPv6SubnetLen int 64 If IPv6Network is smaller than /62, defaults to network prefix + 2
IPv6SubnetMin / IPv6SubnetMax string (IP) 2nd / last subnet IPv6 allocation range
Backend object {"Type": "vxlan"} See backend tables below

Backend Matrix

Backend Type Upstream status Encapsulation MTU overhead Port / protocol Device Encrypted Dual-stack Windows
vxlan Recommended (default) VXLAN (L2 in UDP) 50 B UDP 8472 (Linux), 4789 (Windows) flannel.<VNI>, flannel-v6.<VNI> No Yes Yes
host-gw Recommended (needs L2 adjacency) None 0 none none (routes only) No Yes (Linux) Yes
wireguard Recommended WireGuard 80 B UDP 51820 (v4), 51821 (v6) flannel-wg, flannel-wg-v6 Yes Yes No
udp Debugging only, linux/amd64 only UDP via userspace TUN proxy 28 B UDP 8285 flannel0 No No No
ipip Experimental IP-in-IP 20 B IP protocol 4 flannel.ipip (plus kernel tunl0) No No (IPv4 unicast only) No
ipsec Experimental ESP (strongSwan IKEv2) TBD (not documented upstream) ESP (IP 50), UDP 500, UDP 4500 XFRM policies Yes TBD No
alloc Experimental None (allocation only) 0 none none No n/a No
extension Experimental, prototyping User scripts user-defined user-defined user-defined n/a Yes (IPv6 vars) No
tencent-vpc Experimental Tencent Cloud VPC routes 0 none none No TBD No

MTU overheads come from the encapOverhead/overhead constants in each backend's source. "Dual-stack: Yes" follows configuration.md: only vxlan, wireguard and host-gw (Linux) support it. Windows support follows the Windows notes in backends.md and hostgw_windows.go / vxlan_windows.go.

VXLAN Options

Option Type Default Notes
VNI number 1 (Linux) Windows needs >= 4096
Port number kernel default 8472 Windows must use 4789
GBP bool false VXLAN Group Based Policy; not on Windows
DirectRouting bool false host-gw routes for same-subnet peers; not on Windows
Learning bool false Kernel MAC learning on the VXLAN link (Linux)
MTU number external interface MTU Linux only
MacPrefix string 0E-2A Windows only
Name string flannel.<VNI> Windows only

WireGuard Options

Option Type Default Notes
PSK string none Generate with wg genpsk
ListenPort int 51820 IPv4 tunnel
ListenPortV6 int 51821 IPv6 tunnel
MTU number external interface MTU
Mode string separate separate, auto, ipv4, ipv6
PersistentKeepaliveInterval int (seconds) 0 (off) Use for NAT traversal
env WIREGUARD_KEY_FILE path /run/flannel/wgkey Private key location

Other Backend Options

Backend Option Default Notes
udp Port 8285
ipip DirectRouting false
ipsec PSK required At least 96 characters
ipsec UDPEncap false Force UDP encapsulation (NAT)
ipsec ESPProposal aes128gcm16-sha256-prfsha256-ecp256
extension PreStartupCommand, PostStartupCommand, SubnetAddCommand, SubnetRemoveCommand none Run through sh with daemon privileges
tencent-vpc AccessKeyID, AccessKeySecret env ACCESS_KEY_ID / ACCESS_KEY_SECRET 50 routes per route table

flanneld Flags

Flag Default Purpose
--kube-subnet-mgr false Use the Kubernetes API instead of etcd
--kube-api-url, --kubeconfig-file in-cluster API access when not running in a pod
--kube-annotation-prefix flannel.alpha.coreos.com Node annotation prefix
--net-config-path /etc/kube-flannel/net-conf.json Network config file (kube mode)
--etcd-endpoints http://127.0.0.1:4001,http://127.0.0.1:2379 etcd mode
--etcd-prefix /coreos.com/network etcd mode
--etcd-keyfile, --etcd-certfile, --etcd-cafile empty etcd mTLS
--etcd-username, --etcd-password empty etcd basic auth
--iface (repeatable) default-route interface Interface name or IP for inter-host traffic
--iface-regex (repeatable) none Checked after --iface
--iface-can-reach none Pick the interface that ip route get <ip> would use
--public-ip, --public-ipv6 interface IP Address advertised to peers
--ip-masq false (manifest sets it) Masquerade pod traffic leaving the overlay
--ip-masq-fully-random-disable false Disable --random-fully on MASQUERADE
--iptables-forward-rules true ACCEPT rules in FORWARD
--iptables-resync 5 (seconds) Rule resync period
--ip-blackhole-route false Blackhole route for the local podCIDR
--set-node-network-unavailable true Set the node's NetworkUnavailable condition once Flannel is ready
--subnet-file /run/flannel/subnet.env Where subnet and MTU are written
--subnet-lease-renew-margin 60 (minutes, 1-1439) Lease renewal margin (etcd mode)
--healthz-ip / --healthz-port 0.0.0.0 / 0 (disabled) /healthz and /readyz; manifest uses 8081
-v 0 Log verbosity (-v=10 for most detail)
--version Print version

Every flag also works as an environment variable: prefix FLANNELD_, uppercase, dashes to underscores (for example FLANNELD_ETCD_ENDPOINTS).

Other Environment Variables

Variable Default Purpose
EVENT_QUEUE_DEPTH 5000 Node informer queue depth; raise for very large clusters
CONT_WHEN_CACHE_NOT_READY false Continue startup before the node cache fully syncs
WIREGUARD_KEY_FILE /run/flannel/wgkey WireGuard private key path

Node Annotations

Prefix: flannel.alpha.coreos.com/ (configurable).

Annotation Written by Meaning
backend-type flanneld Backend in use
backend-data, backend-v6-data flanneld Backend peer data (VTEP MAC, WireGuard public key, and so on)
public-ip, public-ipv6 flanneld Address peers should tunnel to
kube-subnet-manager flanneld Marks the node as managed in kube mode
node-public-ip, node-public-ipv6 Operator Choose which local IP to use (same as --public-ip)
public-ip-overwrite, public-ipv6-overwrite Operator Advertise an IP not configured on the node (behind NAT)

Files, Interfaces and Paths

Path / object Purpose
/run/flannel/subnet.env FLANNEL_NETWORK, FLANNEL_SUBNET, FLANNEL_IPV6_NETWORK, FLANNEL_IPV6_SUBNET, FLANNEL_MTU, FLANNEL_IPMASQ
/etc/cni/net.d/10-flannel.conflist CNI config (flannel + portmap, cniVersion 1.0.0)
/opt/cni/bin/flannel Flannel CNI plugin; also needs bridge, host-local, portmap
/etc/kube-flannel/net-conf.json, cni-conf.json Mounted from ConfigMap kube-flannel-cfg
/run/xtables.lock Shared iptables lock (hostPath)
cni0 Per-node Linux bridge created by the bridge plugin
Namespace kube-flannel Pod Security privileged; DaemonSet kube-flannel-ds, ServiceAccount flannel, ClusterRole/Binding flannel
iptables chains FLANNEL-POSTRTG (nat), FLANNEL-FWD (filter)
nftables tables flannel-ipv4, flannel-ipv6
Kernel modules br_netfilter (required; kubeadm >= 1.30 no longer checks it), vxlan, wireguard (kernel < 5.6 needs package)

Ports

Protocol Port Needed for
UDP 8472 VXLAN (Linux)
UDP 4789 VXLAN (Windows)
UDP 51820 WireGuard IPv4
UDP 51821 WireGuard IPv6
UDP 8285 UDP backend
IP proto 50, UDP 500, UDP 4500 IPsec backend
IP proto 4 IPIP backend
TCP 8081 /healthz and /readyz (manifest default, node-local)

Open these only between node IPs. K3s docs warn that exposing 8472 publicly "opens up your cluster network to be accessed by anyone".

K3s Flannel Flags

Flag Where Notes
--flannel-backend servers vxlan (default), host-gw, wireguard-native, none. ipsec and wireguard are deprecated; the current --help lists only the first four.
--flannel-ipv6-masq servers Masquerade IPv6 pod traffic (dual-stack or IPv6-only)
--flannel-external-ip servers Tunnel to node external IPs (needs --node-external-ip)
--flannel-iface each node Override interface
--flannel-conf, --flannel-cni-conf each node Override Flannel or CNI config file
--cluster-cidr servers Default 10.42.0.0/16; dual-stack example 10.42.0.0/16,2001:db8:42::/56
--disable-network-policy servers Turn off the embedded kube-router netpol controller

Flannel options must be identical on all K3s servers. Dual-stack must be set when the cluster is created (K3s basic network options).

Helm Chart Values (flannel/flannel v0.28.9)

Value Default
podCidr / podCidrv6 10.244.0.0/16 / empty
flannel.image.repository / tag ghcr.io/flannel-io/flannel / v0.28.9
flannel.backend vxlan
flannel.backendPort, mtu, vni, GBP, directRouting, macPrefix unset (backend defaults)
flannel.backendPortv6, psk, tunnelMode, keepaliveInterval unset (WireGuard)
flannel.enableNFTables false
flannel.args --ip-masq, --kube-subnet-mgr
flannel.skipCNIConfigInstallation false
flannel.resources.requests cpu: 100m, memory: 50Mi
flannel.healthz.port 8081
netpol.enabled false
netpol.image registry.k8s.io/networking/kube-network-policies:v1.0.0

Performance Estimates

Unverified estimates, not benchmarks

Earlier versions of this note carried the figures below without test conditions or a source. Upstream publishes no benchmark suite yet (it is a ROADMAP item). Treat these as order-of-magnitude guidance only and measure on your own hardware, NICs, kernel and MTU.

Backend Throughput on 10GbE (estimate) Added latency (estimate)
host-gw ~9.5+ Gbps ~10-20 us
VXLAN ~8-9 Gbps ~80-100 us
WireGuard ~7-8 Gbps ~100-200 us
UDP ~5-6 Gbps ~200-500 us

The order host-gw > VXLAN > UDP matches upstream's qualitative guidance. The absolute numbers are TBD (no sourced benchmark).

Resource Value Source
Requested CPU / memory per node 100m / 50Mi Upstream manifest and chart
Typical idle usage TBD (earlier note claimed < 10m CPU, 30-50Mi; unverified) none
Node informer queue 5000 nodes before EVENT_QUEUE_DEPTH tuning configuration.md
Pods per node Bounded by the node subnet (/24 gives 254 IPs) and kubelet maxPods (default 110) Kubernetes defaults

Hardening Checklist

Item Action
Version Run the latest patch release; only it receives security fixes
Encryption Use wireguard (K3s: wireguard-native) when the underlay is untrusted
Firewall Allow backend ports only between node IPs; never expose 8472 to the internet
NetworkPolicy Enable netpol.enabled, the K3s embedded controller, Canal or Cilium chaining
Pod Security Keep kube-flannel namespace restricted to admins; apply restricted PSS elsewhere (drops NET_RAW)
RBAC Limit who can patch Node annotations (flannel.alpha.coreos.com/*)
Backends Avoid extension in production; if used, run v0.28.2 or later
etcd mode Enable etcd mTLS and a dedicated user limited to /coreos.com/network/
Health Keep --healthz-port enabled so /readyz gates pod scheduling readiness
Egress Enable --ip-masq unless pod CIDRs are routed upstream
External filtering Use cloud security groups or host firewalls for north-south traffic; Flannel does not filter it
Monitoring Flannel has no flow telemetry; use node-exporter, packet capture, or a policy engine with visibility
Node hardening Restrict SSH, limit privileged workloads, keep kernels patched (VXLAN and WireGuard are in-kernel)

Sources