On Fri, Aug 14, 2026 at 04:01:30PM +0000, [email protected] wrote:
> Thank you for your contribution! Sashiko AI review found 1 potential issue(s)
> to consider:
> - [High] The local variable `spare_size` is left uninitialized via `goto
> read;` in `tracing_buffers_read()`, resulting in a kernel memory leak to
> userspace.
> --
>
> --- Patch [1]: [PATCH v6 1/2] tracing: Fix subbuf resize races with
> trace_pipe_raw readers ---
> commit bdc760fe7b1aa6eb8c8a8b8c38e9fd02d25051b6
> Author: Vincent Donnefort <[email protected]>
>
> tracing: Fix subbuf resize races with trace_pipe_raw readers
>
> Concurrent subbuffer resizes may crash trace_pipe_raw readers or leak
> uninitialized memory to userspace due to stale size values. This commit
> modifies ring_buffer_alloc_read_page() to handle resizing and introduces
> ring_buffer_read_page_size().
>
> > diff --git a/kernel/trace/trace.c b/kernel/trace/trace.c
> > index 395238b2b715c..355278083b3fb 100644
> > --- a/kernel/trace/trace.c
> > +++ b/kernel/trace/trace.c
> [ ... ]
> > @@ -7091,36 +7091,21 @@ ssize_t tracing_buffers_read(struct file *filp,
> > char __user *ubuf,
> > if (iter->snapshot && tracer_uses_snapshot(iter->tr->current_trace))
> > return -EBUSY;
> >
> > - page_size = ring_buffer_subbuf_size_get(iter->array_buffer->buffer);
> > -
> > - /* Make sure the spare matches the current sub buffer size */
> > - if (info->spare) {
> > - if (page_size != info->spare_size) {
> > - ring_buffer_free_read_page(iter->array_buffer->buffer,
> > - info->spare_cpu,
> > info->spare);
> > - info->spare = NULL;
> > - }
> > - }
> > +again:
> > + /* Do we have previous read data to read? */
> > + if (info->spare && (info->read <
> > ring_buffer_read_page_size(info->spare)))
> > + goto read;
> >
> > - if (!info->spare) {
> > - info->spare =
> > ring_buffer_alloc_read_page(iter->array_buffer->buffer,
> > - iter->cpu_file);
> > - if (IS_ERR(info->spare)) {
> > - ret = PTR_ERR(info->spare);
> > - info->spare = NULL;
> > - } else {
> > - info->spare_cpu = iter->cpu_file;
> > - info->spare_size = page_size;
> > - }
> > - }
> > - if (!info->spare)
> > + /* Make sure the read page order is aligned with the current buffer
> > subbuf order */
> > + ret = ring_buffer_alloc_read_page(iter->array_buffer->buffer,
> > iter->cpu_file,
> > + &info->spare);
> > + if (ret < 0)
> > return ret;
> >
> > - /* Do we have previous read data to read? */
> > - if (info->read < page_size)
> > - goto read;
> > + spare_size = ring_buffer_read_page_size(info->spare);
> > + info->read = spare_size;
> > + info->spare_cpu = iter->cpu_file;
> >
> > - again:
> > trace_access_lock(iter->cpu_file);
> > ret = ring_buffer_read_page(iter->array_buffer->buffer,
> > info->spare,
> [ ... ]
> > @@ -7146,8 +7133,9 @@ ssize_t tracing_buffers_read(struct file *filp, char
> > __user *ubuf,
> > }
> >
> > info->read = 0;
> > +
> > read:
> > - size = page_size - info->read;
> > + size = spare_size - info->read;
>
> [Severity: High]
> Can this regression leak uninitialized stack memory to userspace?
>
> If a userspace process does a partial read (consuming fewer bytes than a full
> subbuffer page), the next read syscall will take the goto read; branch at the
> top of tracing_buffers_read().
>
> When that branch is taken, spare_size is completely uninitialized stack
> memory.
>
> Could size end up being a large garbage value (or underflow if spare_size <
> info->read), causing copy_to_user() below to read beyond the bounds of
> info->spare and leak arbitrary kernel memory?
sigh... I hope I will eventually get this right!
again:
- /* Do we have previous read data to read? */
- if (info->spare && (info->read <
ring_buffer_read_page_size(info->spare)))
- goto read;
+ if (info->spare) {
+ spare_size = ring_buffer_read_page_size(info->spare);
+ /* Do we have previous read data to read? */
+ if (info->read < spare_size)
+ goto read;
+ }
This should do.
>
> > if (size > count)
> > size = count;
> > trace_data = ring_buffer_read_page_data(info->spare);
> > ret = copy_to_user(ubuf, trace_data + info->read, size);
>
> --
> Sashiko AI review ยท
> https://sashiko.dev/#/patchset/[email protected]?part=1
--
Vincent