Skip to main content

Ensure Make Iptables Util Chains Argument Is Enabled

More Info:​

Allow Kubelet to manage iptables.

Risk Level​

High

Address​

Security

Compliance Standards​

  • CIS Kubernetes

Triage and Remediation​

Remediation​

Manual Steps
  1. On every worker node, back up the existing kubelet config file and open it for editing:

    sudo cp /var/lib/kubelet/config.yaml /var/lib/kubelet/config.yaml.bak
    sudo vi /var/lib/kubelet/config.yaml
  2. In /var/lib/kubelet/config.yaml, ensure the following key is set (add it if missing) under the top-level config (align with existing indentation):

    makeIPTablesUtilChains: true

    Save and exit the editor.

  3. On every worker node using a systemd unit override, open the kubelet systemd drop-in file (if it exists):

    sudo vi /etc/systemd/system/kubelet.service.d/10-kubeadm.conf
  4. In /etc/systemd/system/kubelet.service.d/10-kubeadm.conf, remove any occurrence of the --make-iptables-util-chains= flag from the kubelet arguments (for example, from KUBELET_SYSTEM_PODS_ARGS or any other KUBELET_* variable). Save and exit the editor.

  5. On every worker node, reload systemd and restart kubelet to apply the changes:

    sudo systemctl daemon-reload
    sudo systemctl restart kubelet.service
  6. On every worker node, verify that kubelet is running without an overriding --make-iptables-util-chains flag and that the effective setting is taken from the config file:

    /bin/ps -fC kubelet

    Confirm in the output that there is no --make-iptables-util-chains= argument present for the kubelet process.

Using kubectl

kubectl cannot modify kubelet process flags or its config file, so this finding cannot be fixed via the Kubernetes API. The change must be made on every worker node’s host-level kubelet configuration (for example /var/lib/kubelet/config.yaml or the kubelet systemd unit), as described in the Manual Steps section.

Automation
#!/usr/bin/env bash
#
# Remediation: Ensure Kubelet makeIPTablesUtilChains is enabled (CIS 4.2.7)
# Target: EVERY WORKER NODE (run this script on each worker node as root)
#
# Behavior:
# - Ensures /var/lib/kubelet/config.yaml exists and has makeIPTablesUtilChains: true
# - Removes any explicit --make-iptables-util-chains flag from kubelet systemd drop-ins
# - Reloads systemd and restarts kubelet only if a change was made
# - Verifies that kubelet is running with makeIPTablesUtilChains enabled
#
# Safe to re-run: yes (idempotent)

set -euo pipefail

KUBELET_CONFIG="/var/lib/kubelet/config.yaml"
SYSTEMD_DIR="/etc/systemd/system"
CHANGED=0

echo "[INFO] Running on worker node: $(hostname)"

#############################################
# Step 1: Ensure Kubelet config file exists
#############################################
if [ ! -f "${KUBELET_CONFIG}" ]; then
echo "[INFO] ${KUBELET_CONFIG} not found, creating minimal config file"
install -m 600 -o root -g root /dev/null "${KUBELET_CONFIG}"
cat > "${KUBELET_CONFIG}" <<'EOF'
apiVersion: kubelet.config.k8s.io/v1beta1
kind: KubeletConfiguration
makeIPTablesUtilChains: true
EOF
CHANGED=1
else
echo "[INFO] ${KUBELET_CONFIG} exists, ensuring makeIPTablesUtilChains: true"

# If key is present, set to true; if absent, append.
if grep -Eq '^\s*makeIPTablesUtilChains\s*:' "${KUBELET_CONFIG}"; then
if ! grep -Eq '^\s*makeIPTablesUtilChains\s*:\s*true\s*($|#)' "${KUBELET_CONFIG}"; then
echo "[INFO] Updating existing makeIPTablesUtilChains entry to true"
# In-place edit: set any value to true
sed -Ei 's/^\s*makeIPTablesUtilChains\s*:.*/makeIPTablesUtilChains: true/' "${KUBELET_CONFIG}"
CHANGED=1
else
echo "[INFO] makeIPTablesUtilChains already set to true in config file"
fi
else
echo "[INFO] Adding makeIPTablesUtilChains: true to ${KUBELET_CONFIG}"
printf '\nmakeIPTablesUtilChains: true\n' >> "${KUBELET_CONFIG}"
CHANGED=1
fi
fi

#######################################################
# Step 2: Remove CLI flag --make-iptables-util-chains
#######################################################
echo "[INFO] Checking for CLI flags in systemd units"

# Process all kubelet-related systemd unit files and drop-ins
mapfile -t UNIT_FILES < <(grep -rl --exclude-dir='*.wants' 'kubelet' "${SYSTEMD_DIR}" 2>/dev/null | sort -u || true)

for f in "${UNIT_FILES[@]}"; do
if grep -q -- '--make-iptables-util-chains' "$f"; then
echo "[INFO] Removing --make-iptables-util-chains from ${f}"
# Remove occurrences of the flag safely, including optional value
sed -Ei 's/--make-iptables-util-chains(=[^[:space:]]*)?//g' "$f"
# Normalize multiple spaces
sed -Ei 's/[[:space:]]+/ /g' "$f"
CHANGED=1
fi
done

#############################################
# Step 3: Reload systemd and restart kubelet
#############################################
if [ "${CHANGED}" -eq 1 ]; then
echo "[INFO] Changes detected; reloading systemd and restarting kubelet"
systemctl daemon-reload
systemctl restart kubelet.service
else
echo "[INFO] No changes made; kubelet restart not required"
fi

#############################################
# Step 4: Verification
#############################################
echo "[INFO] Verifying kubelet process and configuration"

# Verify kubelet process is running
if ! /bin/ps -fC kubelet >/dev/null 2>&1; then
echo "[ERROR] kubelet process is not running after remediation"
exit 1
fi

# Show current kubelet command line for manual review
echo "[INFO] kubelet process command line:"
/bin/ps -fC kubelet || true

# Verify config file setting
if grep -Eq '^\s*makeIPTablesUtilChains\s*:\s*true\s*($|#)' "${KUBELET_CONFIG}"; then
echo "[INFO] Verified: ${KUBELET_CONFIG} has makeIPTablesUtilChains: true"
else
echo "[ERROR] Verification failed: ${KUBELET_CONFIG} does not have makeIPTablesUtilChains: true"
exit 1
fi

echo "[INFO] Remediation and verification for makeIPTablesUtilChains completed successfully"

Additional Reading:​