Skip to main content
Vulnerability Database/CVE-2026-19575

CVE-2026-19575: Zephyr RTOS Device Deinit RCE Vulnerability

CVE-2026-19575 is a remote code execution flaw in Zephyr RTOS that allows unprivileged threads to execute arbitrary kernel code by exploiting improper validation in device_deinit. This post covers technical details, affected versions, impact, and mitigation.

Published:

CVE-2026-19575 Overview

CVE-2026-19575 is a type confusion vulnerability [CWE-843] in the Zephyr RTOS kernel. The user-mode verification handler z_vrfy_device_deinit() in kernel/device.c validates its dev argument with K_SYSCALL_OBJ_INIT(dev, K_OBJ_ANY). Because k_object_validate() short-circuits type comparisons when the requested type is K_OBJ_ANY, the handler accepts any kernel object the calling thread holds a permission on. A local unprivileged thread can pass a user-writable thread stack object as a fake struct device, causing the kernel to execute an attacker-controlled function pointer in supervisor mode.

Critical Impact

A local user-mode thread achieves full kernel code execution, defeating the CONFIG_USERSPACE isolation boundary entirely.

Affected Products

  • Zephyr RTOS v4.2.x (all CONFIG_USERSPACE builds; CONFIG_DEVICE_DEINIT_SUPPORT defaults to y; no backport available)
  • Zephyr RTOS v4.3.x (all CONFIG_USERSPACE builds; CONFIG_DEVICE_DEINIT_SUPPORT defaults to y)
  • Zephyr RTOS v4.4.x (only builds that explicitly enable CONFIG_DEVICE_DEINIT_SUPPORT alongside CONFIG_USERSPACE)

Discovery Timeline

  • 2026-10-09 - CVE-2026-19575 published to NVD
  • 2026-10-09 - Last updated in NVD database

Technical Details for CVE-2026-19575

Vulnerability Analysis

The defect lives in Zephyr's user-mode syscall boundary for device de-initialization. z_vrfy_device_deinit() was intended to verify that the caller-supplied dev pointer referenced a legitimate struct device. Instead, it used the K_OBJ_ANY sentinel, which bypasses both the kernel-object type check and the initialization-state check inside k_object_validate(). The sibling handlers z_vrfy_device_init() and z_vrfy_device_is_ready() already used K_OBJ_DRIVER_ANY and were unaffected.

Once the pointer passes validation, z_impl_device_deinit() dereferences the state pointer read from the object, invokes the function pointer stored in ops.deinit, and writes back through state on success. When the attacker supplies a user-writable backing object, every field is attacker-controlled.

Root Cause

The root cause is misuse of the K_OBJ_ANY sentinel in a type check that must constrain the argument to driver objects. K_OBJ_DRIVER_ANY limits the pointer to the linker-placed range K_OBJ_DRIVER_FIRST..K_OBJ_DRIVER_LAST, where state and ops.deinit are kernel-controlled.

Attack Vector

A local user-mode thread allocates a stack object via k_thread_stack_alloc() or receives a granted K_THREAD_STACK for spawning a child thread. The thread writes a crafted struct device layout into that user-writable memory, pointing ops.deinit at an arbitrary kernel address. Invoking the device_deinit() syscall with that pointer yields an indirect call executed in supervisor mode, plus an arbitrary kernel read and a single-byte kernel write. A less precise attempt produces a supervisor-mode fault and system crash.

c
#ifdef CONFIG_USERSPACE
static inline int z_vrfy_device_deinit(const struct device *dev)
{
-	K_OOPS(K_SYSCALL_OBJ_INIT(dev, K_OBJ_ANY));
+	K_OOPS(K_SYSCALL_OBJ_INIT(dev, K_OBJ_DRIVER_ANY));

 	return z_impl_device_deinit(dev);
}

Source: Zephyr commit 1036694889ab. The patch replaces the overly permissive K_OBJ_ANY sentinel with K_OBJ_DRIVER_ANY, restoring the intended driver-object constraint.

Stop Remote Code Execution Before It Runs

Singularity™ Endpoint detects and blocks exploit attempts at machine speed, including zero-days and novel attack techniques.

Stop Exploit Attempts

Detection Methods for CVE-2026-19575

Indicators of Compromise

  • Unexpected supervisor-mode faults or kernel oops events originating from z_impl_device_deinit() call paths.
  • User threads invoking the device_deinit() syscall with pointers that resolve outside the driver object linker range.
  • Allocation of a K_THREAD_STACK followed by an immediate device_deinit() syscall referencing stack-adjacent memory.

Detection Strategies

  • Audit Zephyr build configurations for the simultaneous presence of CONFIG_USERSPACE=y and CONFIG_DEVICE_DEINIT_SUPPORT=y.
  • Review firmware images and syscall tables to confirm z_vrfy_device_deinit() uses K_OBJ_DRIVER_ANY rather than K_OBJ_ANY.
  • Instrument the syscall boundary in debug builds to log every device_deinit() invocation and the resolved object type.

Monitoring Recommendations

  • Collect kernel panic traces from fielded devices and alert on faults attributed to the device de-initialization code path.
  • Track firmware release metadata to identify builds carrying the vulnerable Zephyr versions v4.2.x, v4.3.x, or v4.4.x without the patch.
  • Correlate crash telemetry with recent firmware deployments to isolate exploitation attempts from benign regressions.

How to Mitigate CVE-2026-19575

Immediate Actions Required

  • Rebuild and reflash affected devices with the patched Zephyr commit 1036694889ab applied to kernel/device.c.
  • For v4.3.x and v4.4.x deployments, upgrade to the fixed release line published by the Zephyr Project.
  • For v4.2.x deployments, migrate off the unmaintained branch, since no backport is provided.

Patch Information

The upstream fix is documented in Zephyr commit 1036694889ab and advisory GHSA-j9m4-fr5f-49wm. The patch tightens the object check in z_vrfy_device_deinit() to K_OBJ_DRIVER_ANY, restricting the syscall argument to the linker-generated driver object range.

Workarounds

  • Disable CONFIG_DEVICE_DEINIT_SUPPORT in the Kconfig for the firmware build; z_impl_device_deinit() then returns -ENOTSUP without dereferencing the pointer.
  • Disable CONFIG_USERSPACE where the application model does not require user-mode isolation, removing reachability of the syscall handler.
  • Restrict kernel-object permission grants so untrusted threads cannot obtain thread stack objects usable as fake struct device instances.
bash
# Kconfig fragment to remove exposure on v4.3.x and v4.4.x builds
CONFIG_DEVICE_DEINIT_SUPPORT=n

Disclaimer: This content was generated using AI. While we strive for accuracy, please verify critical information with official sources.

Experience the Most Advanced Cybersecurity Platform

See how the world’s most intelligent, autonomous cybersecurity platform can protect your organization today and into the future.