May 21, 2026·6 min read·27 visits
A race condition in the Linux kernel process exit sequence allows local unprivileged users to steal open file descriptors from SUID processes. By targeting binaries like ssh-keysign, attackers can read root-owned files such as SSH host keys.
CVE-2026-46333 is a high-severity race condition in the Linux kernel process management subsystem, specifically involving the get_dumpable() logic during process exit. Local attackers can exploit this timing window to hijack file descriptors belonging to privileged SUID/SGID processes, leading to the disclosure of sensitive files such as SSH private keys and shadow password hashes.
CVE-2026-46333, commonly tracked as "ssh-keysign-pwn", is an information disclosure vulnerability in the Linux kernel's process management subsystem. The vulnerability is classified as a race condition (CWE-362) occurring within the process exit sequence. It allows local, unprivileged attackers to bypass security restrictions and access resources held by privileged processes.
The Linux kernel utilizes a "dumpability" flag to determine if a process can generate a core dump. This flag also serves as an access control mechanism for system calls like ptrace and pidfd_getfd(2). The kernel references this flag to prevent unprivileged users from attaching to or reading the memory and file descriptors of SUID/SGID processes.
The flaw exists in how the kernel evaluates dumpability as a process terminates. An unprivileged attacker can exploit a timing window during the exit of a privileged process to bypass these checks. Successful exploitation yields access to file descriptors opened by the privileged process, directly exposing the contents of restricted files.
The root cause of CVE-2026-46333 is improper state synchronization between a process's memory management struct (mm_struct) and its file descriptor table during termination. In Linux, a process maintains an mm pointer that tracks its memory context, which historically included the dumpability flag.
During the process exit path, the kernel executes exit_mm(), which sets the process's mm pointer to NULL. This operation occurs before the process invokes exit_files(), which is responsible for closing the process's open file descriptors. This sequence creates a temporary state where a process has no memory context but retains open file handles.
The get_dumpable() function handles requests to determine a process's dumpability. Prior to the fix, the logic for evaluating dumpability when mm == NULL was flawed. It failed to accurately return the restrictive permissions that applied to the process before termination.
When an attacker calls ptrace_may_access() against a target in this intermediate state, the check incorrectly resolves in the attacker's favor. The kernel permits the access because it cannot correctly verify the dumpability restrictions of the now-NULL mm structure. This authorization failure extends to operations like pidfd_getfd(2), granting the attacker complete access to the target's open files.
The vulnerability stems from the kernel's inability to retain a process's security context once its mm_struct is detached. The patch, introduced in commit 93d4ba49d18e3d7fb41a9927c2d0cca5e9dfefd6, redesigns the get_dumpable() logic to cache the dumpability state.
// Pre-patch logic in get_dumpable()
int get_dumpable(struct mm_struct *mm)
{
if (!mm)
return 0; // Kernel threads and exiting tasks were treated incorrectly
return (mm->flags & MMF_DUMPABLE_MASK) >> MMF_DUMPABLE_SHIFT;
}The unpatched code fails to differentiate between a standard kernel thread (which never had an mm) and a privileged user thread that is in the process of exiting. The access control checks default to a permissive or inconsistent state when mm evaluates to NULL.
// Post-patch logic
int get_dumpable(struct task_struct *task, struct mm_struct *mm)
{
if (mm)
return (mm->flags & MMF_DUMPABLE_MASK) >> MMF_DUMPABLE_SHIFT;
// Check if the task is a kernel thread or a user task exiting
if (task->flags & PF_KTHREAD)
return 0;
// Fallback to a cached dumpability state stored in task_struct
return task->saved_dumpable;
}The patch introduces a saved_dumpable field within the task_struct. If the process drops its mm pointer during termination, the kernel falls back to this cached value. Furthermore, the kernel now explicitly requires CAP_SYS_PTRACE to override these checks, ensuring that transitioning to an mm == NULL state no longer downgrades the process's security posture.
Exploitation of CVE-2026-46333 relies on precise execution timing and abuse of the pidfd_getfd(2) system call. The attacker requires local access to the system and the ability to execute SUID binaries. The primary target for this exploit is /usr/lib/openssh/ssh-keysign, a SUID-root helper program used for host-based authentication.
The attacker spawns the ssh-keysign process and immediately sends a termination signal or provides invalid input to force a fast exit. Concurrently, an attacker-controlled process loops aggressively, attempting to acquire a file descriptor to the target process via pidfd_open(2).
Once the target process hits the vulnerable window (mm == NULL but file descriptors remain open), the attacker process calls pidfd_getfd(2). The kernel's ptrace_may_access() check evaluates to true due to the flaw, allowing the attacker to duplicate the file descriptor for the host's private key into their own process space. The attacker then reads the key material directly from the duplicated descriptor.
The impact of CVE-2026-46333 is constrained to the local system, requiring attackers to already possess a low-privileged shell. However, the severity of the information disclosure is extremely high. By targeting the ssh-keysign binary, an attacker successfully extracts the SSH host private keys.
Possession of the SSH host keys enables complete host impersonation. An attacker positioned on the network can perform man-in-the-middle attacks against subsequent SSH connections to the compromised server. This allows the attacker to intercept sessions, steal credentials, and hijack administrative access.
The vulnerability is not limited to SSH keys. Attackers can target other SUID binaries that process sensitive files. For example, exploiting the /usr/bin/chage binary yields a file descriptor to /etc/shadow. The attacker can read the system's password hashes and subject them to offline cracking, eventually escalating privileges to root.
The primary remediation for CVE-2026-46333 is upgrading the Linux kernel to a patched version. The fix has been integrated into mainline kernel 7.1-rc4 and backported to long-term stable branches. Administrators should deploy kernels 6.18.31, 6.12.89, 6.6.139, 6.1.173, 5.15.207, or 5.10.256 depending on their distribution's track.
If immediate reboot and kernel upgrade are infeasible, administrators must deploy a sysctl workaround. Modifying the Yama security module configuration to restrict ptrace usage effectively neutralizes the exploit vector. Running sysctl -w kernel.yama.ptrace_scope=2 forces the kernel to demand CAP_SYS_PTRACE for all ptrace and pidfd_getfd operations.
To persist this mitigation across reboots, administrators must write the configuration to /etc/sysctl.d/99-CVE-2026-46333.conf. Applying this workaround has operational side effects. Setting ptrace_scope to 2 prevents unprivileged users from attaching debuggers like gdb or using tools like strace on their own processes. Developers on affected systems will require elevated privileges to perform debugging tasks.
CVSS:3.1/AV:L/AC:L/PR:L/UI:N/S:U/C:H/I:H/A:N| Product | Affected Versions | Fixed Version |
|---|---|---|
Linux Kernel Mainline Linux Foundation | < 7.1-rc4 | 7.1-rc4 |
Linux Kernel Stable (6.18.x) Linux Foundation | < 6.18.31 | 6.18.31 |
Ubuntu Linux Canonical | 14.04 - 26.04 | TBD |
| Attribute | Detail |
|---|---|
| Vulnerability Class | Race Condition (CWE-362) |
| Attack Vector | Local (AV:L) |
| CVSS v3.1 Score | 7.1 (High) |
| EPSS Score | 0.01% (0.44th percentile) |
| Exploit Status | Weaponized PoC Available |
| CISA KEV | Not Listed |
| Primary Target | /usr/lib/openssh/ssh-keysign |
The system contains a race condition in the process exit path that allows an attacker to bypass access controls and access file descriptors of a privileged process.