GHSA-8qf6-hjvf-g68f: VIDEO class descriptor walk consumes device-controlled wTotalLength as its bound
GHSA ID |
|
|---|---|
CVE ID |
CVE‑2026‑96406 |
Severity |
Medium |
CVSS score |
4.9 ( |
CWE |
|
Published |
2026‑10‑02 |
Last updated |
2026‑10‑02 |
Description
Summary
A VideoStreaming interface reports the size of its whole class-specific descriptor block in the wTotalLength field of its input header. The USBX host recorded that figure and used it as the budget for walking the format, frame and frame-interval descriptors, without holding it against the configuration descriptor actually received.
A device that reports a wTotalLength larger than the descriptors it supplies therefore had its own claim believed. Once the real bytes ran out the walk kept going, dereferencing the cursor past the end of the configuration buffer, in the host’s context, whenever the application queried format or frame data.
Details
_ux_host_class_video_input_format_get assigned input_header_descriptor.wTotalLength straight into video → ux_host_class_video_length_formats. _ux_host_class_video_activate set the same field from the packed entity descriptor.
The walks in _ux_host_class_video_format_data_get, _ux_host_class_video_frame_data_get and _ux_host_class_video_frame_interval_get then took total_descriptor_length from that field and looped while it remained non-zero. Their two guards — a descriptor shorter than three bytes, and a descriptor longer than the claimed remaining total — measure one descriptor against the device’s own claim. Neither measures the cursor against the end of the buffer the descriptors were read into.
With a six-byte block holding two three-byte descriptors and a reported length of 100, the cursor reaches offset 6 with 94 bytes still claimed, and the next iteration reads past the region.
The separate bLength == 0 non-advance case is already refused with UX_DESCRIPTOR_CORRUPTED by the three-byte guard. The defect here is the disagreement between the reported length and the bytes present.
Impact
A malicious or malfunctioning UVC device causes the host to read beyond its configuration descriptor buffer. What that discloses depends on the heap layout behind the buffer; where the following page is not mapped, the read faults instead. The device must be attached and enumerated, and the application must query format or frame data, which is ordinary use of the class.
Affected configurations
Builds including the USBX host VIDEO class. Products that do not build it are unaffected.
⇐ 6.5.1.202602.
Severity
CVSS v3.1 base score 4.9 (Medium)
CVSS:3.1/AV:P/AC:L/PR:N/UI:R/S:U/C:L/I:N/A:H
Physical access is required to attach the device, and a user action to connect it. The disclosure is bounded by what happens to follow the buffer and is not aimed by the attacker, while a fault in the host’s descriptor parsing stops the class.
Patches
Fixed in USBX 6.5.2.202603.
The budget for the walks is now the part of the class-specific block that lies behind the selected format, rather than the whole block measured from the input header, and it is still held against the configuration buffer so a device cannot enlarge it by over-reporting. This distinction matters: the frame queries start their walk at the selected format rather than at the header, so measuring from the header left the cursor able to run past the block, while clamping the header’s figure against the configuration buffer and then starting further in refused any device whose streaming descriptors happen to reach the end of its configuration. The clamps where wTotalLength is first recorded are unchanged.
A regression test drives a two-format MJPEG block that ends with the configuration, which fails against the previous bound, and covers an over-reported wTotalLength and a format sitting past the reported block.