Ensure Etcd Data Directory Ownership Is Etcd
More Info:
Ensure that the etcd data directory ownership is set to etcd:etcd
Risk Level
Medium
Address
Security
Compliance Standards
- CIS Kubernetes
Triage and Remediation
- Remediation
Remediation
Manual Steps
-
On every control plane node, determine the etcd data directory:
ps -ef | grep '[e]tcd' | grep -- --data-dirFrom the output, note the value of
--data-dir(for example/var/lib/etcdor/var/lib/etcd/default.etcd). -
On the same control plane node, confirm that directory exists (substitute the actual path you found):
ls -ld /var/lib/etcdIf the directory is different, replace
/var/lib/etcdin the command above with your actual data directory path. -
On the same control plane node, change ownership of the etcd data directory to
etcd:etcd(substitute the actual path you found):sudo chown -R etcd:etcd /var/lib/etcd -
If your etcd data directory is not explicitly set via
--data-dirand does not exist, create the default directory and set ownership:sudo mkdir -p /var/lib/etcd/default.etcdsudo chown -R etcd:etcd /var/lib/etcd/default.etcd -
On the same control plane node, verify ownership using a command derived from the audit:
DATA_DIR=''for d in $(ps -ef | grep etcd | grep -- --data-dir | sed 's%.*data-dir[= ]\([^ ]*\).*%\1%'); doif test -d "$d"; then DATA_DIR="$d"; fidoneif ! test -d "$DATA_DIR"; then DATA_DIR=/var/lib/etcd/default.etcd; fistat -c %U:%G "$DATA_DIR"Ensure the output is:
etcd:etcd
Using kubectl
kubectl cannot modify ownership of the etcd data directory or edit /etc/kubernetes/manifests/etcd.yaml, because these are host-level files managed directly on each control plane node. To remediate this finding, follow the instructions in the Manual Steps section on every control plane node.
Automation
#!/usr/bin/env bash
#
# Remediation: Ensure the etcd data directory ownership is set to etcd:etcd
# Scope: Run on every control plane node
# Usage: sudo bash fix-etcd-data-dir-ownership.sh
set -euo pipefail
echo "[INFO] Detecting etcd data directory..."
DATA_DIR=''
# Discover the etcd --data-dir from the running process
for d in $(ps -ef | grep '[e]tcd' | grep -- --data-dir | sed 's%.*data-dir[= ]\([^ ]*\).*%\1%'); do
if [ -d "$d" ]; then
DATA_DIR="$d"
fi
done
# Fallback used by the audit command if no directory could be discovered
if [ -z "${DATA_DIR}" ]; then
DATA_DIR="/var/lib/etcd/default.etcd"
fi
if [ ! -d "${DATA_DIR}" ]; then
echo "[ERROR] Detected etcd data directory '${DATA_DIR}' does not exist."
echo "[ERROR] Check the etcd manifest at /etc/kubernetes/manifests/etcd.yaml for the correct --data-dir value."
exit 1
fi
echo "[INFO] Etcd data directory resolved to: ${DATA_DIR}"
# Ensure etcd user and group exist
if ! id etcd >/dev/null 2>&1; then
echo "[ERROR] User 'etcd' does not exist on this node. Create it before running this script."
exit 1
fi
if ! getent group etcd >/dev/null 2>&1; then
echo "[ERROR] Group 'etcd' does not exist on this node. Create it before running this script."
exit 1
fi
CURRENT_OWNER="$(stat -c '%U:%G' "${DATA_DIR}")"
echo "[INFO] Current ownership of ${DATA_DIR}: ${CURRENT_OWNER}"
if [ "${CURRENT_OWNER}" = "etcd:etcd" ]; then
echo "[INFO] Ownership already set to etcd:etcd. No change needed."
else
echo "[INFO] Updating ownership of ${DATA_DIR} to etcd:etcd (recursive)..."
chown -R etcd:etcd "${DATA_DIR}"
fi
echo "[INFO] Verifying ownership after remediation..."
FINAL_OWNER="$(stat -c '%U:%G' "${DATA_DIR}")"
echo "[INFO] Final ownership of ${DATA_DIR}: ${FINAL_OWNER}"
if [ "${FINAL_OWNER}" != "etcd:etcd" ]; then
echo "[ERROR] Ownership is still not etcd:etcd. Manual investigation required."
exit 1
fi
echo "[INFO] Verification successful. Etcd data directory ownership is correctly set to etcd:etcd."
exit 0