An independent re-analysis by Goldberg Security Research of a publicly disclosed vulnerability: our breakdown of root cause, exploitation, and defence. Discovery credit belongs to the original researchers (see references).

Summary

The kernel's UVC driver — what handles ordinary USB webcams — miscounts the frames it will later parse from a device's descriptors. A malformed or malicious USB device that advertises UVC_VS_UNDEFINED frame types triggers a heap out-of-bounds write in kernel space, enabling privilege escalation, code execution, or a crash. It's been exploited in the wild and is especially relevant to Android and any physical-access scenario.

Root cause

A classic size-computation vs. parse-time mismatch. When sizing the frames buffer, uvc_parse_format() skips UVC_VS_UNDEFINED frames — so they aren't counted. But uvc_parse_streaming() later does parse them and writes their entries into that buffer. The device gets the driver to allocate for N frames and then write N+ — straight past the end of the allocation.

// Conceptual: the count and the parse disagree.
// uvc_parse_format()  -> ignores UVC_VS_UNDEFINED when computing nframes (buffer size)
// uvc_parse_streaming() -> still parses UVC_VS_UNDEFINED frames into that buffer
//   => writes beyond the allocation when a device supplies such frames

Exploitability

A crafted USB descriptor — a programmable "BadUSB"-style device, or a compromised peripheral — triggers the overflow during enumeration. Whoever can plug in (or emulate) USB hardware can reach the bug; with heap grooming it becomes a kernel write primitive.

Impact

Local privilege escalation / kernel code execution with physical or emulated USB access; at minimum a denial of service.

Remediation

  • Patch the kernel to a fixed stable release (4.19.324 / 5.4.286 / 5.10.230 / newer).
  • Restrict USB device classes with USBGuard on sensitive endpoints; lock screens disable new USB on many platforms.
  • Unload uvcvideo on systems with no camera need.

Takeaway

When one function counts objects and a different function parses them, the two must agree exactly — count precisely what you will later write. USB descriptor parsers are a recurring source of these mismatches because the device fully controls the input.

References