Hi Emmanuel,

I have been looking into what appears to be the same NULL dereference in
nouveau_fence_sync(), and I found a path that may explain how prev->cli
ends up NULL.

In the failure I traced, nouveau_fence_no_signaling() removes the fence
from the pending list, but leaves fence->channel pointing to the channel.
The fence itself can remain alive through a BO reservation. After the
channel is torn down, the same fence can later be encountered again in
nouveau_fence_sync() through that stale channel association.

The normal nouveau_fence_signal() path clears fence->channel when removing
the fence from the pending list, so the no-signaling path appears
asymmetric here.

I also did not find a normal path that explicitly sets channel->cli to
NULL while keeping the channel valid. If this is the path leading to the
crash, checking prev->cli here would prevent the dereference, but the stale
fence->channel association would still remain.

The existing fence/channel lifetime handling seems to rely on clearing
fence->channel once the fence is detached from the channel. If that is the
intended invariant, preserving it in the no-signaling path seems preferable
to allowing a non-NULL fence->channel to refer to a torn-down channel.

I sent a separate patch that clears fence->channel in
nouveau_fence_no_signaling():

  [PATCH] drm/nouveau: Clear fence channel in no-signaling path
  https://lore.kernel.org/r/[email protected]

Thanks,
Beomseok

Reply via email to