Message ID | 1462466065-30212-5-git-send-email-julien.grall@arm.com |
---|---|
State | New |
Headers | show |
On 05/05/2016 17:34, Julien Grall wrote: > Flushing the icache will required when the support Xen patching will be > added. > > Also import the macro icache_line_size which is used by > flush_icache_range. > > Signed-off-by: Julien Grall <julien.grall@arm.com> Hmmm, I forgot to drop this patch from the series. Please ignore it. Cheers, > --- > xen/arch/arm/arm64/cache.S | 45 +++++++++++++++++++++++++++++++++++++++++++++ > xen/include/asm-arm/page.h | 2 ++ > 2 files changed, 47 insertions(+) > > diff --git a/xen/arch/arm/arm64/cache.S b/xen/arch/arm/arm64/cache.S > index eff4e16..bc5a8f7 100644 > --- a/xen/arch/arm/arm64/cache.S > +++ b/xen/arch/arm/arm64/cache.S > @@ -30,6 +30,51 @@ > .endm > > /* > + * icache_line_size - get the minimum I-cache line size from the CTR register. > + */ > + .macro icache_line_size, reg, tmp > + mrs \tmp, ctr_el0 // read CTR > + and \tmp, \tmp, #0xf // cache line size encoding > + mov \reg, #4 // bytes per word > + lsl \reg, \reg, \tmp // actual cache line size > + .endm > + > +/* > + * flush_icache_range(start,end) > + * > + * Ensure that the I and D caches are coherent within specified region. > + * This is typically used when code has been written to a memory region, > + * and will be executed. > + * > + * - start - virtual start address of region > + * - end - virtual end address of region > + */ > +ENTRY(flush_icache_range) > + dcache_line_size x2, x3 > + sub x3, x2, #1 > + bic x4, x0, x3 > +1: > + dc cvau, x4 // clean D line to PoU > + add x4, x4, x2 > + cmp x4, x1 > + b.lo 1b > + dsb ish > + > + icache_line_size x2, x3 > + sub x3, x2, #1 > + bic x4, x0, x3 > +1: > + ic ivau, x4 // invalidate I line PoU > + add x4, x4, x2 > + cmp x4, x1 > + b.lo 1b > + dsb ish > + isb > + mov x0, #0 > + ret > +ENDPROC(flush_icache_range) > + > +/* > * __flush_dcache_area(kaddr, size) > * > * Ensure that the data held in the page kaddr is written back to the > diff --git a/xen/include/asm-arm/page.h b/xen/include/asm-arm/page.h > index 05d9f82..a94e826 100644 > --- a/xen/include/asm-arm/page.h > +++ b/xen/include/asm-arm/page.h > @@ -328,6 +328,8 @@ static inline int clean_and_invalidate_dcache_va_range > return 0; > } > > +int flush_icache_range(unsigned long start, unsigned long end); > + > /* Macros for flushing a single small item. The predicate is always > * compile-time constant so this will compile down to 3 instructions in > * the common case. */ >
diff --git a/xen/arch/arm/arm64/cache.S b/xen/arch/arm/arm64/cache.S index eff4e16..bc5a8f7 100644 --- a/xen/arch/arm/arm64/cache.S +++ b/xen/arch/arm/arm64/cache.S @@ -30,6 +30,51 @@ .endm /* + * icache_line_size - get the minimum I-cache line size from the CTR register. + */ + .macro icache_line_size, reg, tmp + mrs \tmp, ctr_el0 // read CTR + and \tmp, \tmp, #0xf // cache line size encoding + mov \reg, #4 // bytes per word + lsl \reg, \reg, \tmp // actual cache line size + .endm + +/* + * flush_icache_range(start,end) + * + * Ensure that the I and D caches are coherent within specified region. + * This is typically used when code has been written to a memory region, + * and will be executed. + * + * - start - virtual start address of region + * - end - virtual end address of region + */ +ENTRY(flush_icache_range) + dcache_line_size x2, x3 + sub x3, x2, #1 + bic x4, x0, x3 +1: + dc cvau, x4 // clean D line to PoU + add x4, x4, x2 + cmp x4, x1 + b.lo 1b + dsb ish + + icache_line_size x2, x3 + sub x3, x2, #1 + bic x4, x0, x3 +1: + ic ivau, x4 // invalidate I line PoU + add x4, x4, x2 + cmp x4, x1 + b.lo 1b + dsb ish + isb + mov x0, #0 + ret +ENDPROC(flush_icache_range) + +/* * __flush_dcache_area(kaddr, size) * * Ensure that the data held in the page kaddr is written back to the diff --git a/xen/include/asm-arm/page.h b/xen/include/asm-arm/page.h index 05d9f82..a94e826 100644 --- a/xen/include/asm-arm/page.h +++ b/xen/include/asm-arm/page.h @@ -328,6 +328,8 @@ static inline int clean_and_invalidate_dcache_va_range return 0; } +int flush_icache_range(unsigned long start, unsigned long end); + /* Macros for flushing a single small item. The predicate is always * compile-time constant so this will compile down to 3 instructions in * the common case. */
Flushing the icache will required when the support Xen patching will be added. Also import the macro icache_line_size which is used by flush_icache_range. Signed-off-by: Julien Grall <julien.grall@arm.com> --- xen/arch/arm/arm64/cache.S | 45 +++++++++++++++++++++++++++++++++++++++++++++ xen/include/asm-arm/page.h | 2 ++ 2 files changed, 47 insertions(+)