[PATCH 3/6] irqchip: gic: use writel instead of dsb + writel_relaxed
Will Deacon
will.deacon at arm.com
Thu Feb 6 08:26:44 EST 2014
On Thu, Feb 06, 2014 at 12:23:40PM +0000, Catalin Marinas wrote:
> On Thu, Feb 06, 2014 at 12:13:50PM +0000, Will Deacon wrote:
> > Ok, so if we assume that a dsb(ishst) is sufficient because the CPU we're
> > talking to is either (a) coherent in the inner-shareable domain or (b)
> > incoherent, and we flushed everything to PoC, then why wouldn't a dmb(ishst)
> > work?
>
> Because you want to guarantee the ordering between a store to Normal
> Cacheable memory vs store to Device for the IPI (see the mailbox example
> in the Barrier Litmus section ;)). The second is just a slave access, DMB
> guarantees observability from the master access perspective.
Ok, my reasoning is as follows:
- CPU0 tries to message CPU1. It writes to a location in normal memory,
then writes to the GICD to send the SGI
- We need to ensure that CPU1 observes the write to normal memory before
the write to GICD reaches the distributor. This is *not* about end-point
ordering (the usual non-coherent DMA example).
- A dmb ishst ensures that the two writes are observed in order by CPU1
(and, in fact, the inner-shareable domain containing CPU0).
so the only way this can break is if the GICD write reaches the distributor
before being observed by CPU1 (otherwise, we know the mailbox write was
observed by CPU1). I dread to think how you would build such a beast
(dual-ported GICD with no serialisation to the same locations?)...
Furthermore, if we decide that device writes can reach their endpoints
before being observed by other inner-shareable observers, then doesn't that
pose a potential problem for spinlocks? If I take a lock and write to a
device, the write can hit the device before the lock appears to be taken.
That doesn't sound right to me.
Using a dsb(ishst) will ensure that we don't issue the GICD write until the
mailbox is visible to CPU1, but may be overkill.
Will
More information about the linux-arm-kernel
mailing list