CVE-2026-31413 Overview
A critical vulnerability has been identified in the Linux kernel's BPF (Berkeley Packet Filter) verifier subsystem. The flaw resides in the maybe_fork_scalars() function, which incorrectly handles scalar forking when processing BPF_OR operations with constant source operands. When the destination register has a signed range of [-1, 0], the verifier forks state incorrectly, leading to a verifier/runtime divergence that can be exploited for out-of-bounds map access.
Critical Impact
This vulnerability creates an exploitable divergence between BPF verifier analysis and runtime execution, allowing attackers to bypass kernel security checks and perform out-of-bounds memory access on BPF maps.
Affected Products
- Linux kernel (versions containing vulnerable BPF verifier code)
- Systems with BPF subsystem enabled
- Container and cloud environments utilizing eBPF for security monitoring
Discovery Timeline
- 2026-04-12 - CVE CVE-2026-31413 published to NVD
- 2026-04-13 - Last updated in NVD database
Technical Details for CVE-2026-31413
Vulnerability Analysis
The vulnerability stems from a logical error in the BPF verifier's state forking mechanism when handling BPF_OR ALU operations. The maybe_fork_scalars() function is designed to optimize verifier analysis by forking execution paths when certain conditions are met. When the destination operand (dst) has a signed range of [-1, 0] and the source operand is a constant, the verifier creates two execution paths: one where dst = 0 (pushed path) and one where dst = -1 (current path).
For BPF_AND operations, this forking is mathematically sound because 0 & K == 0 for any constant K. However, for BPF_OR operations, the logic breaks down: 0 | K == K, not 0. This means the pushed path incorrectly tracks the destination as 0 when the actual runtime value would be K, creating a dangerous discrepancy between what the verifier believes and what actually executes.
This verifier/runtime divergence is a severe class of vulnerability because the BPF verifier serves as a critical security boundary, ensuring that BPF programs cannot perform unsafe memory operations. When the verifier's model diverges from runtime reality, attackers can craft BPF programs that pass verification but perform out-of-bounds memory accesses during execution.
Root Cause
The root cause is an incorrect argument passed to push_stack() within the maybe_fork_scalars() function. The function passes env->insn_idx + 1 to push_stack(), causing the pushed path to skip re-execution of the ALU instruction. This means the pushed path proceeds with the assumption that dst = 0 without computing the actual result of the BPF_OR operation (0 | K = K).
The fix involves passing env->insn_idx (instead of env->insn_idx + 1) to push_stack(), ensuring the pushed path re-executes the ALU instruction with dst = 0 and correctly computes the result for any opcode, including BPF_OR.
Attack Vector
An attacker with the ability to load BPF programs (requiring CAP_BPF capability or unprivileged BPF access if enabled) can exploit this vulnerability by crafting a malicious BPF program that:
- Sets up a register with a signed range of [-1, 0]
- Performs a BPF_OR operation with a carefully chosen constant
- Uses the resulting register (which the verifier incorrectly tracks as 0) to calculate map access indices
- Performs out-of-bounds reads or writes on BPF maps, potentially leading to information disclosure or arbitrary kernel memory corruption
The vulnerability mechanism involves the verifier incorrectly tracking register values during BPF_OR operations. When a register has a signed range of [-1, 0] and is OR'ed with a constant K, the verifier forks state and tracks one path with the register set to 0. However, the runtime value would be K (since 0 | K == K), creating a discrepancy that allows out-of-bounds map access. For full technical details and the patch implementation, see the kernel git commits.
Detection Methods for CVE-2026-31413
Indicators of Compromise
- Unusual BPF program loading activity, particularly programs with complex ALU operations involving BPF_OR
- Unexpected out-of-bounds access patterns in kernel logs related to BPF map operations
- Anomalous BPF verifier behavior or increased verifier rejection rates
Detection Strategies
- Monitor bpf() system calls for suspicious program loading patterns
- Enable BPF audit logging to track program loads and identify potentially malicious programs
- Deploy kernel security modules that can inspect BPF programs before execution
Monitoring Recommendations
- Enable enhanced BPF logging via /sys/kernel/debug/tracing/events/bpf/
- Monitor for unexpected privilege escalation attempts following BPF program execution
- Implement runtime BPF program monitoring to detect anomalous memory access patterns
How to Mitigate CVE-2026-31413
Immediate Actions Required
- Apply the kernel patches from the official kernel git repository immediately
- If patching is not immediately possible, consider disabling unprivileged BPF access via sysctl kernel.unprivileged_bpf_disabled=1
- Audit existing BPF programs for suspicious patterns involving scalar forking operations
- Restrict CAP_BPF capability to trusted processes only
Patch Information
The Linux kernel maintainers have released patches to address this vulnerability. The fix modifies the maybe_fork_scalars() function to pass env->insn_idx (instead of env->insn_idx + 1) to push_stack(), ensuring correct re-execution of ALU instructions on forked paths. Patches are available through the official kernel git repository:
- Kernel Git Commit 342aa1e
- Kernel Git Commit 58bd87d
- Kernel Git Commit c845894
- Kernel Git Commit d13281a
Workarounds
- Disable unprivileged BPF access if not required by applications
- Implement strict CAP_BPF capability restrictions using Linux Security Modules
- Consider using Seccomp filters to restrict bpf() system call access for untrusted processes
# Disable unprivileged BPF access as a temporary workaround
sysctl -w kernel.unprivileged_bpf_disabled=1
# Make the setting persistent across reboots
echo "kernel.unprivileged_bpf_disabled=1" >> /etc/sysctl.conf
Disclaimer: This content was generated using AI. While we strive for accuracy, please verify critical information with official sources.

