* Re: [PATCH 2/2] RDMA/nldev: Guard against NULL ucontext in resource dumps
[not found] ` <6a7affdd.5c752b50.b00e6.7ed7SMTPIN_ADDED_BROKEN@mx.google.com>
@ 2026-08-11 14:19 ` Jason Gunthorpe
2026-08-12 12:32 ` Yili Zhang
0 siblings, 1 reply; 3+ messages in thread
From: Jason Gunthorpe @ 2026-08-11 14:19 UTC (permalink / raw)
To: Yili Zhang; +Cc: leon, linux-rdma, linux-kernel
On Tue, Aug 11, 2026 at 06:56:23PM +0800, Yili Zhang wrote:
> + /*
> + * The uobject's context is cleared by uverbs_destroy_uobject() during
> + * the RDMA_REMOVE_DRIVER_FAILURE fallback path, while the CQ itself is
> + * leaked in the restrack xarray (its destroy failed, so neither the HW
> + * CQ nor the restrack entry can be torn down). A concurrent dump must
> + * not oops when it stumbles onto such a half-destroyed user CQ.
> + */
> + if (!rdma_is_kernel_res(res)) {
> + struct ib_ucontext *ctx =
> + READ_ONCE(cq->uobject->uevent.uobject.context);
> +
> + if (ctx && nla_put_u32(msg, RDMA_NLDEV_ATTR_RES_CTXN,
> + ctx->res.id))
> + return -EMSGSIZE;
> + }
It is missing locking right? This needs to run under the disassociate
srcu probably
Jason
^ permalink raw reply [flat|nested] 3+ messages in thread
* Re: [PATCH 2/2] RDMA/nldev: Guard against NULL ucontext in resource dumps
2026-08-11 14:19 ` [PATCH 2/2] RDMA/nldev: Guard against NULL ucontext in resource dumps Jason Gunthorpe
@ 2026-08-12 12:32 ` Yili Zhang
2026-08-13 0:04 ` Jason Gunthorpe
0 siblings, 1 reply; 3+ messages in thread
From: Yili Zhang @ 2026-08-12 12:32 UTC (permalink / raw)
To: jgg; +Cc: leon, linux-kernel, linux-rdma, zhangyili01
Hi Jason,
Thanks for the review. After re-reading your feedback and re-examining
the crash log, I think I mis-characterized the root cause in my original
patches. Let me lay out what the log actually shows, because I'd like
to get the fix on the right track.
The crash is a three-stage sequence, all from the same host
(6.1.52 + MLNX_OFED 24.10):
Stage 1 - a create_qp failure:
[24805924.400] mlx5_3: create_qp:3323:(pid 2758615): Create QP type 2 failed
Stage 2 - on process exit, ib_uverbs_close() could not tear down the
process's CQs and fell into the DRIVER_FAILURE fallback:
[24805924.747] WARNING: ... rdma_core.c:945 uverbs_destroy_ufile_hw
Call Trace:
uverbs_destroy_ufile_hw
ib_uverbs_close
__fput
Stage 3 - 23s later, an unrelated `rdma res show cq` tripped over the
leaked CQ:
[24805947.514] BUG: kernel NULL pointer dereference, address: 0x58
RIP: fill_res_cq_entry+0x15e/0x180
Call Trace: res_get_common_dumpit ... netlink_dump
So the dereference is not a disassociation-time race: teardown ran to
completion (the WARNING fired, uobj->context was cleared to NULL by the
DRIVER_FAILURE fallback in uverbs_destroy_uobject()), and only 23s later
did the dump read it. The leaked CQ sits in restrack with
context == NULL as a committed state, not a transient window.
To be concrete about why it persists: under the current code, once the
DRIVER_FAILURE fallback runs, the leaked object's restrack entry is
never actively removed. The CQ case:
- First pass (RDMA_REMOVE_CLOSE): uverbs_destroy_uobject() enters the
destroy_hw branch because uobj->object is non-NULL; destroy_hw_idr
calls ib_destroy_cq_user(), whose driver destroy_cq fails and
returns before rdma_restrack_del(&cq->res). Entry stays.
- Second pass (RDMA_REMOVE_DRIVER_FAILURE): __uverbs_cleanup_ufile()
pre-sets obj->object = NULL before calling uverbs_destroy_uobject(),
so the "else if (uobj->object)" branch is skipped entirely -
destroy_hw, and thus ib_destroy_cq_user() / rdma_restrack_del(), is
never reached. uobj->context is then cleared to NULL, and the
object is removed only from ufile->idr (remove_handle is not called
either, as reason != DESTROY), not from the restrack xarray.
So the restrack entry is removed only by rdma_restrack_clean() ->
xa_destroy() at ib_dealloc_device() time. For the entire lifetime of
the device after a failed fd-close teardown, the leaked CQ sits in the
restrack xarray with context == NULL. That is exactly the window the
crash log shows: 23s between the close-time WARNING and the dump oops,
same device still registered.
On your two points:
Patch 1 (move rdma_restrack_del before destroy): you're right that
this breaks the legitimate case where destroy is allowed to fail -
withdrawing the object from restrack while it still exists is wrong.
I'll drop it.
Patch 2 (NULL guard): you're right that it's missing locking against
a concurrent disassociation teardown. But the crash above is not
that race; it's a fd-close path where context is already NULL. A
NULL check would stop this particular oops, but I understand that's
not the synchronization you're asking for.
Which leaves me unsure where the dump-side fix should live. Two
questions:
1. For the disassociation race you pointed at, I can hold a
disassociate srcu around fill_func() in res_get_common_doit/
dumpit (it would have to live on struct ib_device, since nldev in
ib_core cannot reach ib_uverbs_device). Does that match what you
had in mind? This closes the concurrent-UAF case but does not
touch the fd-close NULL case above.
2. For the fd-close path - where a driver destroy fails and the
DRIVER_FAILURE fallback leaves a leaked restrack entry with a
NULL context - is the correct fix entirely on the driver side
(destroy must not fail on transient HW error; wait for FLR),
as you said on patch 1? I.e. should the core/nldev side not
defend against this at all, or is a NULL-skip in the dump still
wanted as a defense-in-depth? A driver that never fails destroy
would prevent the leak from happening in the first place, but
would not help with objects already leaked before such a fix is
deployed, or with any other future path that leaves a restrack
entry behind with a cleared context.
Thanks,
Yili
^ permalink raw reply [flat|nested] 3+ messages in thread
* Re: [PATCH 2/2] RDMA/nldev: Guard against NULL ucontext in resource dumps
2026-08-12 12:32 ` Yili Zhang
@ 2026-08-13 0:04 ` Jason Gunthorpe
0 siblings, 0 replies; 3+ messages in thread
From: Jason Gunthorpe @ 2026-08-13 0:04 UTC (permalink / raw)
To: Yili Zhang; +Cc: leon, linux-kernel, linux-rdma
On Wed, Aug 12, 2026 at 08:32:49PM +0800, Yili Zhang wrote:
> Hi Jason,
>
> Thanks for the review. After re-reading your feedback and re-examining
> the crash log, I think I mis-characterized the root cause in my original
> patches. Let me lay out what the log actually shows, because I'd like
> to get the fix on the right track.
>
> The crash is a three-stage sequence, all from the same host
> (6.1.52 + MLNX_OFED 24.10):
You have to provide an analyis from top of tree upstream kernel if you
want help from this mailing list.
> Stage 1 - a create_qp failure:
> [24805924.400] mlx5_3: create_qp:3323:(pid 2758615): Create QP type 2 failed
>
> Stage 2 - on process exit, ib_uverbs_close() could not tear down the
> process's CQs and fell into the DRIVER_FAILURE fallback:
> [24805924.747] WARNING: ... rdma_core.c:945 uverbs_destroy_ufile_hw
> Call Trace:
> uverbs_destroy_ufile_hw
> ib_uverbs_close
> __fput
That's not supposed to happen.
> To be concrete about why it persists: under the current code, once the
> DRIVER_FAILURE fallback runs, the leaked object's restrack entry is
> never actively removed. The CQ case:
And I think this was just fixed recently.
Jason
^ permalink raw reply [flat|nested] 3+ messages in thread
end of thread, other threads:[~2026-08-13 0:04 UTC | newest]
Thread overview: 3+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
[not found] <20260811105623.48633-1-xVq3SwEoxhQs281bogBL>
[not found] ` <6a7affdd.5c752b50.b00e6.7ed7SMTPIN_ADDED_BROKEN@mx.google.com>
2026-08-11 14:19 ` [PATCH 2/2] RDMA/nldev: Guard against NULL ucontext in resource dumps Jason Gunthorpe
2026-08-12 12:32 ` Yili Zhang
2026-08-13 0:04 ` Jason Gunthorpe
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox