Share
## https://sploitus.com/exploit?id=E476ED22-8DC0-58CC-A1BC-415DA7A57BBE
# CVE-2026-31431 / GHSA-2274-3hgr-wxv6 โ€” algif_aead Remediator

**Severity:** High (CVSS 7.8 โ€” `CVSS:3.1/AV:L/AC:L/PR:L/UI:N/S:U/C:H/I:H/A:H`)

## Background

[CVE-2026-31431](https://github.com/advisories/GHSA-2274-3hgr-wxv6) is a local privilege escalation vulnerability in the Linux kernel's `algif_aead` module (AF_ALG AEAD crypto socket interface). A low-privileged local user can exploit incorrect in-place buffer operations to gain full root access. All AKS node pools running Linux kernels prior to the upstream patch are potentially affected.

The `algif_aead` module is not required for normal Kubernetes or AKS workloads. Blacklisting it eliminates the attack surface entirely.

---

## What this DaemonSet does

One pod runs on every Linux node. On start-up and then every 60 seconds each pod:

1. **Writes** `/etc/modprobe.d/modprobe-CIS.conf` on the host with:
   ```
   install algif_aead /bin/false
   blacklist algif_aead
   ```
   This prevents the module from loading on reboot or via `modprobe`.

2. **Checks** `/proc/modules` (the live host kernel module list โ€” shared with all containers) for `algif_aead`.

3. **Labels** the Kubernetes node with the result so you can query across the cluster:
   | Label value | Meaning |
   |---|---|
   | `mitigated` | Module not loaded; blacklist config applied |
   | `module-loaded` | Module is currently loaded โ€” investigate immediately |

---

## Files

| File | Purpose |
|---|---|
| `rbac.yaml` | Namespace, ServiceAccount, ClusterRole (`get`/`patch` nodes), ClusterRoleBinding |
| `configmap.yaml` | Shell remediation script mounted into every pod |
| `daemonset.yaml` | DaemonSet definition โ€” one pod per Linux node |

---

## Prerequisites

- `kubectl` configured against the target AKS cluster
- Cluster-admin permissions (required to create a ClusterRole and a privileged namespace)

---

## Deploy

Apply the manifests in order:

```sh
kubectl apply -f rbac.yaml
kubectl apply -f configmap.yaml
kubectl apply -f daemonset.yaml
```

Wait for the rollout to complete on all nodes:

```sh
kubectl -n security-remediation rollout status daemonset/cve-2026-31431-remediator
```

---

## Verify

### Check node remediation status at a glance

```sh
kubectl get nodes -L vulnerability.aks.io/CVE-2026-31431
```

Expected output on a clean cluster:

```
NAME                                STATUS   ROLES    AGE   VERSION   CVE-2026-31431
aks-nodepool1-xxxxx-vmss000000      Ready       4d    v1.33.7   mitigated
aks-nodepool1-xxxxx-vmss000001      Ready       4d    v1.33.7   mitigated
```

### Check logs on a specific pod

```sh
# List pods and their assigned nodes
kubectl -n security-remediation get pods -o wide

# Tail a specific pod's logs
kubectl -n security-remediation logs  -f
```

Expected log output:

```
2026-05-01T01:33:36Z [INFO    ] CVE-2026-31431 remediator starting on node: aks-nodepool1-...
2026-05-01T01:33:36Z [INFO    ] Blacklist config written โ†’ /host/etc/modprobe.d/modprobe-CIS.conf
2026-05-01T01:33:36Z [INFO    ] Node aks-nodepool1-...: 'algif_aead' is NOT loaded โ€” blacklist config applied, node is mitigated.
2026-05-01T01:33:36Z [INFO    ] Labeled node aks-nodepool1-...: vulnerability.aks.io/CVE-2026-31431=mitigated
2026-05-01T01:33:36Z [INFO    ] Entering monitoring loop (interval: 60s)
```

### Verify the modprobe config was written to the host

```sh
kubectl -n security-remediation exec  -- cat /host/etc/modprobe.d/modprobe-CIS.conf
```

Expected content:

```
# CIS hardening โ€“ mitigate CVE-2026-31431 (GHSA-2274-3hgr-wxv6)
# Prevents algif_aead (AF_ALG AEAD) LPE from being loaded or exploited.
install algif_aead /bin/false
blacklist algif_aead
```

### Alert: module-loaded nodes

If a node shows `module-loaded`, the kernel module is currently active and the node may already be compromised. Cordon and drain the node immediately for forensic analysis:

```sh
# Find affected nodes
kubectl get nodes -l vulnerability.aks.io/CVE-2026-31431=module-loaded

# Cordon and drain for investigation
kubectl cordon 
kubectl drain  --ignore-daemonsets --delete-emptydir-data
```

---

## Uninstall

> **Note:** Removing the DaemonSet does **not** remove the `/etc/modprobe.d/modprobe-CIS.conf` file from host nodes. That file is intentionally left in place as a persistent kernel hardening measure.

### Remove Kubernetes resources

```sh
kubectl delete -f daemonset.yaml
kubectl delete -f configmap.yaml
kubectl delete -f rbac.yaml
```

This deletes the DaemonSet, all its pods, the ConfigMap, the ServiceAccount, the ClusterRole, the ClusterRoleBinding, and the namespace.

### Remove node labels (optional)

```sh
kubectl label nodes --all vulnerability.aks.io/CVE-2026-31431-
```

### Remove the modprobe config from nodes (not recommended)

Only do this if you have an alternative mitigation (patched kernel). Run on each node or via a privileged pod:

```sh
rm -f /etc/modprobe.d/modprobe-CIS.conf
```

---

## Security notes

- The pod runs as **root** (`runAsUser: 0`) โ€” required to write to `/etc/modprobe.d/` on the host.
- All Linux capabilities are **dropped** (`capabilities.drop: ["ALL"]`). No kernel capabilities are needed.
- The main container runs with **`readOnlyRootFilesystem: true`**. Only the mounted `hostPath` and `emptyDir` volumes are writable.
- Only `/etc/modprobe.d/` is bind-mounted from the host โ€” not `/etc`, `/proc`, or any broader path.
- The `curl` binary and its shared libraries are staged by the init container into an `emptyDir` (`/tools`) so the main container can call the Kubernetes API without needing write access to rootfs.
- The service account has the minimum RBAC permissions needed: `get` and `patch` on `nodes` only.