From: Andrew Morton <akpm@linux-foundation.org>
To: Shashank Mohan Jain <jain.sm@gmail.com>
Cc: Masami Hiramatsu <mhiramat@kernel.org>,
Matt Wu <wuqiang.matt@bytedance.com>,
linux-trace-kernel@vger.kernel.org, linux-kernel@vger.kernel.org
Subject: Re: [PATCH 1/2] objpool: keep objpool_push() correct when a push from NMI nests in it
Date: Mon, 28 Sep 2026 15:44:05 -0700 [thread overview]
Message-ID: <20260928154405.fc2e650ef162f53d9d8e4d0a@linux-foundation.org> (raw)
In-Reply-To: <20260928084125.67104-2-jain.sm@gmail.com>
On Mon, 28 Sep 2026 14:11:24 +0530 Shashank Mohan Jain <jain.sm@gmail.com> wrote:
> objpool_push() adds an object to the slot of the local CPU with
> interrupts disabled. It reserves an entry with a cmpxchg() on
> slot->tail, writes the entry, and publishes it with
> smp_store_release(&slot->last, tail + 1).
>
> A push from NMI context can still interrupt it and push to the same
> slot. kretprobes may run in NMI context since commit e03b4a084ea6
> ("kprobes: Remove NMI context check"). At the time, kretprobe instances
> came from a CAS-based lockless freelist, which tolerates that. Commit
> 4bbd93455659 ("kprobes: kretprobe scalability improvement") moved
> kretprobes and rethook to objpool.
>
> With rethook, rethook_trampoline_handler() recycles instances with
> objpool_push() after the user handler has run, when no kprobe is marked
> running anymore; rethook_flush_task() does the same. An NMI that arrives
> during such a push and runs a function probed by the same kretprobe takes
> an instance in pre_handler_kretprobe(), and when the function returns
> inside the NMI, pushes it back to the same slot. This needs a kretprobe
> on a function that runs both in NMI context and outside it, for instance
> one that perf calls from the PMU NMI handler on x86. Before v6.14, fprobe
> also used rethook and could push from NMI the same way, with one pool
> shared by all functions of an fprobe.
>
> ...
>
> Publish the entries in order instead:
Thanks.
> --- a/include/linux/objpool.h
> +++ b/include/linux/objpool.h
> @@ -193,19 +193,40 @@ __objpool_try_add_slot(void *obj, struct objpool_head *pool, int cpu)
> struct objpool_slot *slot = pool->cpu_slots[cpu];
> uint32_t head, tail;
>
> - /* loading tail and head as a local snapshot, tail first */
> + /*
> + * Only the local CPU pushes to its slot, with irqs disabled, but a
> + * push from NMI context (a kretprobe'd function returning in NMI)
> + * can interrupt this one at any point.
> + */
> tail = READ_ONCE(slot->tail);
> + while (!try_cmpxchg_acquire(&slot->tail, &tail, tail + 1))
> + ;
>
> - do {
> - head = READ_ONCE(slot->head);
> - /* fault caught: something must be wrong */
> - WARN_ON_ONCE(tail - head > pool->nr_objs);
> - } while (!try_cmpxchg_acquire(&slot->tail, &tail, tail + 1));
> + /*
> + * fault caught: something must be wrong. Read head only after the
> + * reservation: a nested push and a pop on another CPU could have
> + * moved head past an older snapshot of tail.
> + */
> + head = READ_ONCE(slot->head);
> + WARN_ON_ONCE(tail - head > pool->nr_objs);
This code can run in NMI?
Calling WARN_ON from NMI sounds quite sketchy - the warning handler
does all sorts of stuff. I see this is pre-existing but perhaps this
is a chance to address it.
Sashiko liked [1/2] but had a lot to say about the test module:
https://sashiko.dev/#/patchset/20260928084125.67104-1-jain.sm@gmail.com
next prev parent reply other threads:[~2026-09-28 22:44 UTC|newest]
Thread overview: 6+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-09-28 8:41 [PATCH 0/2] objpool: fix nested pushes from NMI context Shashank Mohan Jain
2026-09-28 8:41 ` [PATCH 1/2] objpool: keep objpool_push() correct when a push from NMI nests in it Shashank Mohan Jain
2026-09-28 22:44 ` Andrew Morton [this message]
2026-09-29 1:20 ` shashank Jain
2026-09-28 8:41 ` [PATCH 2/2] lib/tests: add KUnit test for nested objpool pushes Shashank Mohan Jain
2026-09-28 8:54 ` sashiko-bot
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20260928154405.fc2e650ef162f53d9d8e4d0a@linux-foundation.org \
--to=akpm@linux-foundation.org \
--cc=jain.sm@gmail.com \
--cc=linux-kernel@vger.kernel.org \
--cc=linux-trace-kernel@vger.kernel.org \
--cc=mhiramat@kernel.org \
--cc=wuqiang.matt@bytedance.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.