On Thu, Jul 17, 2026 at 05:13:00PM +0000, Greg Kroah-Hartman wrote:
How was this found, and tested?
Found by manual code audit of the topology parsing path in drivers/staging/greybus/audio_topology.c.
The pattern that caught my attention was in gb_audio_gb_get_topology(): it reads a u16 size from the module, allocates and fills a buffer of that size, but then discards the size and never passes it to the parsing functions. The parser then walks the buffer using lengths and counts taken from inside the buffer itself (size_dais, size_controls, size_widgets, num_controls, num_widgets, num_routes, names_length, items) with no bounds checks against the actual allocation size, so every one of those walks is an unchecked trust of wire data.
gb_generate_enum_strings() in particular has an unbounded while (*data != '\0') scan with no end pointer, which is the most straightforward out-of-bounds read.
Testing: I verified the patch builds cleanly with make M=drivers/staging/greybus on x86_64 (allyesconfig with CONFIG_STAGING=y and CONFIG_GREYBUS=m). I do not have Greybus hardware, so runtime testing was limited to build verification and manual review of the bounds logic.
I confirmed that: - All four block offsets (dai, control, widget, route) are validated as ordered and within the buffer in gbaudio_tplg_process_header(). - Each per-element walk in _process_kcontrols(), _process_widgets(), and _process_routes() checks that the element fits before dereferencing. - gb_generate_enum_strings() now has an explicit end pointer and rejects items > names_length. - The gbaudio_control_size() helper centralises the variable-length control size calculation and validates it before use.
Thanks, Muhammad Bilal