cgroup Memory Pressure Monitoring (memory.events / PSI)
Description
Monitors cgroups v2 memory pressure signals — memory.events (oom_kill, high, max counters) and Pressure Stall Information (PSI) via /proc/pressure/memory — to detect resource leaks before they exhaust system memory. When a cgroup approaches its memory limit due to a resource leak, these interfaces provide deterministic signals (memory.high threshold crossings, oom_kill increments, PSI stall percentages) that monitoring systems consume to trigger alerts and automated remediation. Complements cgroup memory limits (CME-704) which contain the leak by adding detection of when containment is being stressed. The memory.events counters are monotonically increasing and per-cgroup, enabling precise attribution of pressure to the leaking workload.
CVSS Vector Impacts
| Metric | Transition | Rationale |
|---|---|---|
| Attack Complexity (AC) | L → H | Compensating control: cgroup memory pressure events (memory.events oom_kill/high counters and PSI stall metrics) provide deterministic early warning of resource leaks before system-wide exhaustion occurs, enabling operators to identify and remediate leaking processes within the monitoring interval — the attacker must exhaust resources faster than the monitoring and response cycle to achieve sustained denial of service. |
CWE Relationships
Verification
Check that cgroup memory.events is accessible and PSI is enabled in the kernel
# Expected: Non-zero counters if pressure has occurred; file existence confirms cgroup v2 memory accounting is active
# Expected: PSI metrics present (some/full avg10/avg60/avg300 values); confirms CONFIG_PSI=y
# Expected: 1
Remediation
printf '#!/bin/bash\nTHRESHOLD=${1:-25}\nwhile true; do\n PRESSURE=$(awk "/^some/ {split(\$2,a,\"=\"); printf \"%%d\", a[2]}" /proc/pressure/memory)\n if [ "$PRESSURE" -ge "$THRESHOLD" ] 2>/dev/null; then\n echo "ALERT: memory pressure avg10=${PRESSURE}%% exceeds threshold ${THRESHOLD}%%" | systemd-cat -t cme-1010-psi -p warning\n fi\n sleep 10\ndone\n' > /usr/local/bin/cme-1010-psi-monitor.sh && chmod +x /usr/local/bin/cme-1010-psi-monitor.sh
printf '[Unit]\nDescription=CME-1010 cgroup memory pressure monitor (PSI)\nAfter=sysinit.target\n\n[Service]\nType=simple\nExecStart=/usr/local/bin/cme-1010-psi-monitor.sh 25\nRestart=on-failure\nRestartSec=10s\n\n[Install]\nWantedBy=multi-user.target\n' > /etc/systemd/system/cme-1010-psi-monitor.service
systemctl daemon-reload && systemctl enable --now cme-1010-psi-monitor.service
printf '#!/bin/bash\nSVC=${1:?"Usage: $0 <service-name>"}\nCG=/sys/fs/cgroup/system.slice/${SVC}.service/memory.events\ntest -f "$CG" || { echo "No cgroup at $CG"; exit 1; }\nPREV_OOM=$(awk "/oom_kill/ {print \$2}" "$CG")\nwhile true; do\n CUR_OOM=$(awk "/oom_kill/ {print \$2}" "$CG")\n if [ "$CUR_OOM" -gt "$PREV_OOM" ] 2>/dev/null; then\n echo "ALERT: ${SVC} oom_kill count increased ${PREV_OOM}->${CUR_OOM}" | systemd-cat -t cme-1010-oom -p err\n PREV_OOM=$CUR_OOM\n fi\n sleep 5\ndone\n' > /usr/local/bin/cme-1010-oom-watch.sh && chmod +x /usr/local/bin/cme-1010-oom-watch.sh
printf '[Unit]\nDescription=CME-1010 cgroup memory.events oom_kill watcher for %%i\nAfter=sysinit.target %s\n\n[Service]\nType=simple\nExecStart=/usr/local/bin/cme-1010-oom-watch.sh %%i\nRestart=on-failure\nRestartSec=10s\n\n[Install]\nWantedBy=multi-user.target\n' > /etc/systemd/system/cme-1010-oom-watch@.service
systemctl daemon-reload && systemctl enable --now cme-1010-oom-watch@<service>.service