CVE-2026-15924 Overview
CVE-2026-15924 is a use-after-free vulnerability [CWE-416] in the Zephyr real-time operating system's TLS socket layer, located in subsys/net/lib/sockets/sockets_tls.c. The flaw stems from unsynchronized access to a process-global client_cache array shared by every TLS socket context. Concurrent client sockets can race on the same cache slot, producing a use-after-free read or a double-free that corrupts the mbedTLS heap. Exploitation requires an application that opts into per-socket client session caching via the TLS_SESSION_CACHE socket option and runs concurrent TLS client connections across multiple threads. A malicious or compromised server can widen the race window by increasing TLS 1.3 session-ticket frequency.
Critical Impact
Concurrent TLS client sockets can trigger heap corruption in mbedTLS, leading to crashes or denial of service on affected Zephyr devices.
Affected Products
- Zephyr RTOS TLS socket subsystem (subsys/net/lib/sockets/sockets_tls.c)
- Applications enabling CONFIG_NET_SOCKETS_TLS with the TLS_SESSION_CACHE socket option
- Deployments using CONFIG_NET_SOCKETS_TLS_MAX_CLIENT_SESSION_COUNT (default value 1)
Discovery Timeline
- 2026-09-14 - CVE CVE-2026-15924 published to NVD
- 2026-09-14 - Last updated in NVD database
Technical Details for CVE-2026-15924
Vulnerability Analysis
The Zephyr TLS socket layer maintains a single process-global array, client_cache, of cached client sessions shared by every TLS socket context. The functions tls_session_save(), tls_session_get(), tls_session_cache_reset(), and the settings restore handler allocate, free, and dereference each entry's heap buffer entry->session. Before the fix, these accesses were serialized only by the per-socket context mutex ctx->lock assigned in ctx_set_lock(). The per-socket mutex provides no mutual exclusion between different sockets touching the shared cache.
Because CONFIG_NET_SOCKETS_TLS_MAX_CLIENT_SESSION_COUNT defaults to 1, any two concurrent client sockets contend for the same slot. A thread in tls_session_get() reading entry->session inside mbedtls_ssl_session_load() can run concurrently with another thread in tls_session_save() that selects the same entry for reuse. The second thread executes mbedtls_free(entry->session) before reallocating, producing a use-after-free read. Two concurrent saves evicting the same entry produce a double-free. Both outcomes corrupt the mbedTLS heap.
Root Cause
The root cause is missing mutual exclusion on a shared data structure. The client_cache array is process-global but was guarded only by per-socket locks, which cannot serialize operations initiated from different socket contexts.
Attack Vector
The cache is reached on ordinary TLS client paths. At connect time it is entered via tls_session_store() and tls_session_restore(). On main it is entered whenever a TLS 1.3 session ticket arrives during recv() or poll() via tls_session_store_current(). A remote peer influences the timing that opens the race window. A malicious or compromised server can raise session-ticket frequency to widen the race and increase the likelihood of heap corruption.
static struct tls_session_cache client_cache[CONFIG_NET_SOCKETS_TLS_MAX_CLIENT_SESSION_COUNT];
+/* A mutex for protecting access to the client session cache. */
+static K_MUTEX_DEFINE(session_cache_lock);
+
#if defined(MBEDTLS_SSL_CACHE_C)
static mbedtls_ssl_cache_context server_cache;
#endif
Source: Zephyr commit 7f9d8ee32ba9. The patch introduces a dedicated session_cache_lock mutex taken across every accessor of client_cache, serializing all reads and frees.
Detection Methods for CVE-2026-15924
Indicators of Compromise
- Unexpected crashes or reboots on Zephyr devices during concurrent TLS client sessions
- mbedTLS heap assertion failures or memory allocator faults logged in device diagnostics
- Repeated TLS handshake failures shortly after receiving TLS 1.3 session tickets
Detection Strategies
- Audit application source for calls to setsockopt() with the TLS_SESSION_CACHE option and confirm whether concurrent TLS clients share the cache
- Enable Zephyr memory debugging features and heap sanity checks to surface double-free events during testing
- Instrument builds with stress tests that open multiple concurrent TLS client sockets against a server issuing frequent session tickets
Monitoring Recommendations
- Collect and centralize device crash logs and mbedTLS error codes for anomaly review
- Monitor upstream TLS servers for abnormal session-ticket issuance patterns that could indicate abuse
- Track deployed firmware versions against the fixed Zephyr commit to identify unpatched devices
How to Mitigate CVE-2026-15924
Immediate Actions Required
- Apply the upstream Zephyr patch that introduces session_cache_lock in subsys/net/lib/sockets/sockets_tls.c
- Rebuild and redeploy firmware for all devices that enable TLS client session caching
- Inventory applications that set the TLS_SESSION_CACHE socket option and prioritize their remediation
Patch Information
The fix is available in Zephyr commit 7f9d8ee32ba9a93fc1dbb192ca2a591ac0853bdc, which adds a dedicated K_MUTEX_DEFINE(session_cache_lock) mutex taken across every accessor of client_cache. Reference the Zephyr Security Advisory GHSA-wcgm-pq6x-v2gf for the full advisory.
Workarounds
- Disable per-socket client session caching by not setting the TLS_SESSION_CACHE socket option on client sockets
- Restrict TLS client operations to a single thread to avoid concurrent access to client_cache
- Limit connections to trusted TLS servers to reduce the probability of adversarial session-ticket flooding
# Configuration example: disable client session caching in application code
# Ensure TLS_SESSION_CACHE is not enabled on client sockets
int cache_disabled = TLS_SESSION_CACHE_DISABLED;
setsockopt(sock, SOL_TLS, TLS_SESSION_CACHE, &cache_disabled, sizeof(cache_disabled));
Disclaimer: This content was generated using AI. While we strive for accuracy, please verify critical information with official sources.

