[PATCH V2 06/14] i3c: mipi-i3c-hci: Fix race in DMA ring dequeue
Frank Li
Frank.li at nxp.com
Thu Mar 5 07:52:27 PST 2026
On Thu, Mar 05, 2026 at 12:13:43PM +0200, Adrian Hunter wrote:
> On 04/03/2026 22:00, Frank Li wrote:
> > On Wed, Mar 04, 2026 at 08:16:57PM +0200, Adrian Hunter wrote:
> >> The HCI DMA dequeue path (hci_dma_dequeue_xfer()) may be invoked for
> >> multiple transfers that timeout around the same time. However, the
> >> function is not serialized and can race with itself.
> >>
> >> When a timeout occurs, hci_dma_dequeue_xfer() stops the ring, processes
> >> incomplete transfers, and then restarts the ring. If another timeout
> >> triggers a parallel call into the same function, the two instances may
> >> interfere with each other - stopping or restarting the ring at unexpected
> >> times.
> >>
> >> Add a mutex so that hci_dma_dequeue_xfer() is serialized with respect to
> >> itself.
> >>
> >> Fixes: 9ad9a52cce282 ("i3c/master: introduce the mipi-i3c-hci driver")
> >> Cc: stable at vger.kernel.org
> >> Signed-off-by: Adrian Hunter <adrian.hunter at intel.com>
> >> ---
> >>
> >>
> >> Changes in V2:
> >>
> >> Mutex now defined in struct i3c_hci instead of struct hci_rh_data
> >>
> >>
> >> drivers/i3c/master/mipi-i3c-hci/core.c | 1 +
> >> drivers/i3c/master/mipi-i3c-hci/dma.c | 2 ++
> >> drivers/i3c/master/mipi-i3c-hci/hci.h | 1 +
> >> 3 files changed, 4 insertions(+)
> >>
> >> diff --git a/drivers/i3c/master/mipi-i3c-hci/core.c b/drivers/i3c/master/mipi-i3c-hci/core.c
> >> index faf5eae2409f..061e84a5c412 100644
> >> --- a/drivers/i3c/master/mipi-i3c-hci/core.c
> >> +++ b/drivers/i3c/master/mipi-i3c-hci/core.c
> >> @@ -927,6 +927,7 @@ static int i3c_hci_probe(struct platform_device *pdev)
> >> return -ENOMEM;
> >>
> >> spin_lock_init(&hci->lock);
> >> + mutex_init(&hci->control_mutex);
> >>
> >> /*
> >> * Multi-bus instances share the same MMIO address range, but not
> >> diff --git a/drivers/i3c/master/mipi-i3c-hci/dma.c b/drivers/i3c/master/mipi-i3c-hci/dma.c
> >> index 74b255ad6d0f..f7d411e5e11f 100644
> >> --- a/drivers/i3c/master/mipi-i3c-hci/dma.c
> >> +++ b/drivers/i3c/master/mipi-i3c-hci/dma.c
> >> @@ -547,6 +547,8 @@ static bool hci_dma_dequeue_xfer(struct i3c_hci *hci,
> >> unsigned int i;
> >> bool did_unqueue = false;
> >>
> >> + guard(mutex)(&hci->control_mutex);
> >> +
> >
> > if dequeue use mutex, equeue also need use the same mutex protect to make
> > sure no equeue happen during dequeue. Or you can guaratee equeue never
> > happen when dequeue.
>
> There are several other issues in this area, and they will be
> addressed in later patch sets.
>
> For this specific case, the enqueue path is already protected
> by the existing spinlock, and we want to keep that path as lightweight
> as possible. Adding a mutex there would unnecessarily penalize the
> common fast path, so it's not the right trade‑off.
>
> Also, the ABORT handling is only relevant when a timeout occurs
> while the ring is still running. That situation only arises when the
> timeout value is too aggressive or the controller ends up stuck - both
> of which are rare. Compared to ordinary error conditions (e.g. a NACK)
> that stop the ring immediately, this race is lower priority.
>
> This patch set is already quite large, so it makes sense to defer
> broader coordination changes to a follow‑up series.
Make sense.
Reviewed-by: Frank Li <Frank.Li at nxp.com>
>
>
> --
> linux-i3c mailing list
> linux-i3c at lists.infradead.org
> http://lists.infradead.org/mailman/listinfo/linux-i3c
More information about the linux-i3c
mailing list