[PATCH] ARM: V6 MPCore v6_dma_inv_range and v6_dma_flush_range RWFO fix
Catalin Marinas
catalin.marinas at arm.com
Fri Dec 10 04:50:16 EST 2010
On Fri, 2010-12-10 at 05:26 +0000, George G. Davis wrote:
> On Wed, Nov 24, 2010 at 09:39:36PM +0300, Valentine Barshak wrote:
> > Updated according to the comments to avoid r/w outside the buffer and
> > used byte r/w for the possible unaligned data. Seems to work fine.
> >
> > Cache ownership must be acqired by reading/writing data from the
> > cache line to make cache operation have the desired effect on the
> > SMP MPCore CPU. However, the ownership is never aquired in the
> > v6_dma_inv_range function when cleaning the first line and
> > flushing the last one, in case the address is not aligned
> > to D_CACHE_LINE_SIZE boundary.
> > Fix this by reading/writing data if needed, before performing
> > cache operations.
> > While at it, fix v6_dma_flush_range to prevent RWFO outside
> > the buffer.
> >
> > Signed-off-by: Valentine Barshak <vbarshak at mvista.com>
> > Signed-off-by: George G. Davis <gdavis at mvista.com>
> > ---
> > arch/arm/mm/cache-v6.S | 40 ++++++++++++++++++++++++++--------------
> > 1 files changed, 26 insertions(+), 14 deletions(-)
> >
> > diff --git a/arch/arm/mm/cache-v6.S b/arch/arm/mm/cache-v6.S
> > index 99fa688..622f8a1 100644
> > --- a/arch/arm/mm/cache-v6.S
> > +++ b/arch/arm/mm/cache-v6.S
> > @@ -203,25 +203,29 @@ ENTRY(v6_flush_kern_dcache_area)
> > * - end - virtual end address of region
> > */
> > v6_dma_inv_range:
> > - tst r0, #D_CACHE_LINE_SIZE - 1
> > - bic r0, r0, #D_CACHE_LINE_SIZE - 1
> > -#ifdef HARVARD_CACHE
> > - mcrne p15, 0, r0, c7, c10, 1 @ clean D line
> > -#else
> > - mcrne p15, 0, r0, c7, c11, 1 @ clean unified line
> > -#endif
> > tst r1, #D_CACHE_LINE_SIZE - 1
> > +#ifdef CONFIG_DMA_CACHE_RWFO
> > + ldrneb r2, [r1, #-1] @ read for ownership
> > + strneb r2, [r1, #-1] @ write for ownership
> > +#endif
> > bic r1, r1, #D_CACHE_LINE_SIZE - 1
> > #ifdef HARVARD_CACHE
> > mcrne p15, 0, r1, c7, c14, 1 @ clean & invalidate D line
> > #else
> > mcrne p15, 0, r1, c7, c15, 1 @ clean & invalidate unified line
> > #endif
> > -1:
> > #ifdef CONFIG_DMA_CACHE_RWFO
> > - ldr r2, [r0] @ read for ownership
> > - str r2, [r0] @ write for ownership
> > + ldrb r2, [r0] @ read for ownership
> > + strb r2, [r0] @ write for ownership
> > +#endif
> > + tst r0, #D_CACHE_LINE_SIZE - 1
> > + bic r0, r0, #D_CACHE_LINE_SIZE - 1
> > +#ifdef HARVARD_CACHE
> > + mcrne p15, 0, r0, c7, c10, 1 @ clean D line
> > +#else
> > + mcrne p15, 0, r0, c7, c11, 1 @ clean unified line
> > #endif
> > +1:
> > #ifdef HARVARD_CACHE
> > mcr p15, 0, r0, c7, c6, 1 @ invalidate D line
> > #else
> > @@ -229,6 +233,10 @@ v6_dma_inv_range:
> > #endif
> > add r0, r0, #D_CACHE_LINE_SIZE
> > cmp r0, r1
> > +#ifdef CONFIG_DMA_CACHE_RWFO
> > + ldrlo r2, [r0] @ read for ownership
> > + strlo r2, [r0] @ write for ownership
> > +#endif
> > blo 1b
> > mov r0, #0
> > mcr p15, 0, r0, c7, c10, 4 @ drain write buffer
>
> Just a minor nit...
>
> Any reason for rearranging the order of 'start'/'end' parameters in the
> above changes? It's not clear that there is any performance benefit by
> rearranging those parameters and it obfuscates the changes, e.g. this
> is equivalent to your change above and also much clearer:
I've been wondering about this as well. But I was too lazy to rewrite it
and see whether there is a performance benefit in the original patch. I
agree that yours looks cleaner.
--
Catalin
More information about the linux-arm-kernel
mailing list