CVE-2026-87039 (GCVE-0-2026-87039)
Vulnerability from cvelistv5 – Published: 2026-11-04 06:09 – Updated: 2026-11-09 21:25
VLAI
EPSS
VEX
Title
I2S configure syscall handler passes an unvalidated user-supplied kernel object pointer to drivers
Summary
The user-mode syscall verifier z_vrfy_i2s_configure() in drivers/i2s/i2s_handlers.c copies the caller's struct i2s_config in from user memory and then, when cfg->frame_clk_freq is 0 (the API's "unconfigure the stream" request), jumps straight to z_impl_i2s_configure() without performing the K_SYSCALL_OBJ(config.mem_slab, K_OBJ_MEM_SLAB) ownership/type check or the block_size sanity check. The mem_slab field is a struct k_mem_slab *, so on that path a completely unvalidated, user-chosen pointer reaches driver code that is entitled to trust it as a real kernel object.
Any thread running under CONFIG_USERSPACE that has access to an I2S device object can trigger this with a single i2s_configure() call. Most in-tree drivers special-case frame_clk_freq == 0 and never store the caller's structure, but drivers/i2s/i2s_litex.c does not: i2s_litex_configure() only logs a warning for a mismatched frame clock, then memcpy()s the caller's config into stream->cfg and marks the stream I2S_STATE_READY. A subsequent i2s_trigger() with I2S_TRIGGER_START enables the FIFO interrupt, and the interrupt handlers i2s_litex_isr_rx() / i2s_litex_isr_tx() then call k_mem_slab_alloc() and k_mem_slab_free() on the attacker-supplied pointer in supervisor context.
The result is an arbitrary-pointer read/write primitive executed by the kernel on behalf of an unprivileged thread — k_mem_slab_alloc() takes a spinlock at slab->lock and reads and writes slab->free_list and the link word inside the returned "block" — which defeats the CONFIG_USERSPACE isolation boundary entirely. The same missing validation is a hazard for out-of-tree I2S drivers that retain the configuration on the unconfigure path. Builds without CONFIG_USERSPACE are unaffected, since the verifier is not used.
The fix zeroes config.mem_slab and config.block_size on the unconfigure path so the driver can never receive an unvalidated pointer, while still allowing a stream to be unconfigured by a caller that does not own a memory slab, as the API documents.
Severity
7.8 (High)
SSVC
Exploitation: none
Automatable: no
Technical Impact: total
CISA Coordinator · CISA-ADP (v2.0.3)
Decision recorded 2026-11-09 21:25 UTC
CWE
- CWE-787 - memory-safety
Assigner
zephyr
CNA
References
2 references
Impacted products
1 product
| Vendor | Product | Version | |
|---|---|---|---|
| zephyrproject | zephyr |
Affected:
4.4.0 , < 4.5.0
(semver)
|
{
"containers": {
"adp": [
{
"metrics": [
{
"other": {
"content": {
"id": "CVE-2026-87039",
"options": [
{
"Exploitation": "none"
},
{
"Automatable": "no"
},
{
"Technical Impact": "total"
}
],
"role": "CISA Coordinator",
"timestamp": "2026-11-09T21:25:28.661011Z",
"version": "2.0.3"
},
"type": "ssvc"
}
}
],
"providerMetadata": {
"dateUpdated": "2026-11-09T21:25:43.928Z",
"orgId": "134c704f-9b21-4f2e-91b3-4a467353bcc0",
"shortName": "CISA-ADP"
},
"title": "CISA ADP Vulnrichment"
}
],
"cna": {
"affected": [
{
"collectionURL": "https://github.com/zephyrproject-rtos/zephyr",
"defaultStatus": "unaffected",
"packageName": "zephyr",
"product": "zephyr",
"programFiles": [
"drivers/i2s/i2s_handlers.c",
"drivers/i2s/i2s_litex.c"
],
"programRoutines": [
{
"name": "i2s_litex_configure"
},
{
"name": "i2s_litex_isr_rx"
},
{
"name": "z_vrfy_i2s_configure"
}
],
"vendor": "zephyrproject",
"versions": [
{
"lessThan": "4.5.0",
"status": "affected",
"version": "4.4.0",
"versionType": "semver"
}
]
}
],
"descriptions": [
{
"lang": "en",
"value": "The user-mode syscall verifier z_vrfy_i2s_configure() in drivers/i2s/i2s_handlers.c copies the caller\u0027s struct i2s_config in from user memory and then, when cfg-\u003eframe_clk_freq is 0 (the API\u0027s \"unconfigure the stream\" request), jumps straight to z_impl_i2s_configure() without performing the K_SYSCALL_OBJ(config.mem_slab, K_OBJ_MEM_SLAB) ownership/type check or the block_size sanity check. The mem_slab field is a struct k_mem_slab *, so on that path a completely unvalidated, user-chosen pointer reaches driver code that is entitled to trust it as a real kernel object.\n\nAny thread running under CONFIG_USERSPACE that has access to an I2S device object can trigger this with a single i2s_configure() call. Most in-tree drivers special-case frame_clk_freq == 0 and never store the caller\u0027s structure, but drivers/i2s/i2s_litex.c does not: i2s_litex_configure() only logs a warning for a mismatched frame clock, then memcpy()s the caller\u0027s config into stream-\u003ecfg and marks the stream I2S_STATE_READY. A subsequent i2s_trigger() with I2S_TRIGGER_START enables the FIFO interrupt, and the interrupt handlers i2s_litex_isr_rx() / i2s_litex_isr_tx() then call k_mem_slab_alloc() and k_mem_slab_free() on the attacker-supplied pointer in supervisor context.\n\nThe result is an arbitrary-pointer read/write primitive executed by the kernel on behalf of an unprivileged thread \u2014 k_mem_slab_alloc() takes a spinlock at slab-\u003elock and reads and writes slab-\u003efree_list and the link word inside the returned \"block\" \u2014 which defeats the CONFIG_USERSPACE isolation boundary entirely. The same missing validation is a hazard for out-of-tree I2S drivers that retain the configuration on the unconfigure path. Builds without CONFIG_USERSPACE are unaffected, since the verifier is not used.\n\nThe fix zeroes config.mem_slab and config.block_size on the unconfigure path so the driver can never receive an unvalidated pointer, while still allowing a stream to be unconfigured by a caller that does not own a memory slab, as the API documents."
}
],
"metrics": [
{
"cvssV3_1": {
"baseScore": 7.8,
"baseSeverity": "HIGH",
"vectorString": "CVSS:3.1/AV:L/AC:H/PR:L/UI:N/S:C/C:H/I:H/A:H",
"version": "3.1"
},
"format": "CVSS"
}
],
"problemTypes": [
{
"descriptions": [
{
"cweId": "CWE-787",
"description": "memory-safety",
"lang": "en",
"type": "CWE"
}
]
}
],
"providerMetadata": {
"dateUpdated": "2026-11-04T06:09:04.926Z",
"orgId": "e2e69745-5e70-4e92-8431-deb5529a81ad",
"shortName": "zephyr"
},
"references": [
{
"name": "Fix commit",
"tags": [
"patch"
],
"url": "https://github.com/zephyrproject-rtos/zephyr/commit/e9898c4d22f69575d9b5f297b3df130ceaff1b8f"
},
{
"name": "GHSA-g43m-x6vj-5cg2",
"url": "https://github.com/zephyrproject-rtos/zephyr/security/advisories/GHSA-g43m-x6vj-5cg2"
}
],
"title": "I2S configure syscall handler passes an unvalidated user-supplied kernel object pointer to drivers",
"x_generator": {
"engine": "cvelib 1.8.0"
}
}
},
"cveMetadata": {
"assignerOrgId": "e2e69745-5e70-4e92-8431-deb5529a81ad",
"assignerShortName": "zephyr",
"cveId": "CVE-2026-87039",
"datePublished": "2026-11-04T06:09:04.926Z",
"dateReserved": "2026-09-08T18:40:40.197Z",
"dateUpdated": "2026-11-09T21:25:43.928Z",
"state": "PUBLISHED"
},
"dataType": "CVE_RECORD",
"dataVersion": "5.2"
}
Loading…
Loading…
Drag nodes to arrange them. Double-click a related vulnerability to open it, or a source to visit its link. The Physics button on the left tunes the layout and the simulation; the legend at the bottom left hides or shows nodes by kind and by sighting type.
Experimental. This forecast is provided for visualization only and may change without notice. Do not use it for operational decisions.
Forecast uses a logistic model when the trend is rising, or an exponential decay model when the trend is falling. Fitted via linearized least squares.
Sightings
| Author | Source | Type | Date | Other |
|---|
Nomenclature
- Seen: The vulnerability was mentioned, discussed, or observed by the user.
- Confirmed: The vulnerability has been validated from an analyst's perspective.
- Published Proof of Concept: A public proof of concept is available for this vulnerability.
- Exploited: The vulnerability was observed as exploited by the user who reported the sighting.
- Patched: The vulnerability was observed as successfully patched by the user who reported the sighting.
- Not exploited: The vulnerability was not observed as exploited by the user who reported the sighting.
- Not confirmed: The user expressed doubt about the validity of the vulnerability.
- Not patched: The vulnerability was not observed as successfully patched by the user who reported the sighting.
Vulnerability timeline
Sightings and recorded dates, grouped by day · UTC
Loading timeline…
Loading…
Loading…
The MITRE ATT&CK techniques below are AI-generated suggestions, inferred from the description of the
vulnerability by the CIRCL/vulnerability-attack-technique-classification-roberta-base
model, served locally by ML-Gateway.
They have not been verified by an analyst and are provided for guidance only.
The approach is described in our paper Mapping CVEs to MITRE ATT&CK Techniques: A Curated Gold-Set Classifier and the Limits of LLM-Assisted Label Expansion.
Browse all ATT&CK techniques and the vulnerabilities related to each.
The approach is described in our paper Mapping CVEs to MITRE ATT&CK Techniques: A Curated Gold-Set Classifier and the Limits of LLM-Assisted Label Expansion.
Browse all ATT&CK techniques and the vulnerabilities related to each.
Loading…
Related by attack behaviour
Vulnerabilities whose description is nearest to this one in the vector space of the CIRCL/vulnerability-attack-technique-biencoder model. This is a similarity search over the bi-encoder space (plain cosine), not a classification, and it has no measured accuracy.