Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys/arch add synchronization barrier for AURORA_IO_CACHE_COH...
details: https://anonhg.NetBSD.org/src/rev/eda823bba54f
branches: trunk
changeset: 338200:eda823bba54f
user: hsuenaga <hsuenaga%NetBSD.org@localhost>
date: Thu May 14 05:39:32 2015 +0000
description:
add synchronization barrier for AURORA_IO_CACHE_COHERENCY.
cleanup MARVELL L2 cache code.
diffstat:
sys/arch/arm/arm/cpufunc.c | 52 +++++++---
sys/arch/arm/arm/cpufunc_asm_pj4b.S | 26 +++++-
sys/arch/arm/include/cpufunc_proto.h | 4 +
sys/arch/arm/marvell/armadaxp.c | 136 +++++++++++++++++++++--------
sys/arch/arm/marvell/armadaxpreg.h | 44 ++++++++-
sys/arch/arm/marvell/mvsocreg.h | 20 +++-
sys/arch/evbarm/marvell/marvell_machdep.c | 11 +-
7 files changed, 219 insertions(+), 74 deletions(-)
diffs (truncated from 508 to 300 lines):
diff -r 68668b88b401 -r eda823bba54f sys/arch/arm/arm/cpufunc.c
--- a/sys/arch/arm/arm/cpufunc.c Thu May 14 02:43:33 2015 +0000
+++ b/sys/arch/arm/arm/cpufunc.c Thu May 14 05:39:32 2015 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: cpufunc.c,v 1.153 2015/04/17 13:39:01 hsuenaga Exp $ */
+/* $NetBSD: cpufunc.c,v 1.154 2015/05/14 05:39:32 hsuenaga Exp $ */
/*
* arm7tdmi support code Copyright (c) 2001 John Fremlin
@@ -49,7 +49,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: cpufunc.c,v 1.153 2015/04/17 13:39:01 hsuenaga Exp $");
+__KERNEL_RCSID(0, "$NetBSD: cpufunc.c,v 1.154 2015/05/14 05:39:32 hsuenaga Exp $");
#include "opt_compat_netbsd.h"
#include "opt_cpuoptions.h"
@@ -1371,8 +1371,7 @@
.cf_tlb_flushD = armv7_tlb_flushID,
.cf_tlb_flushD_SE = armv7_tlb_flushID_SE,
- /* Cache operations */
-
+ /* Cache operations (see also pj4bv7_setup) */
.cf_icache_sync_all = armv7_idcache_wbinv_all,
.cf_icache_sync_range = armv7_icache_sync_range,
@@ -1381,18 +1380,6 @@
.cf_dcache_inv_range = armv7_dcache_inv_range,
.cf_dcache_wb_range = armv7_dcache_wb_range,
-#if defined(L2CACHE_ENABLE) && \
- !defined(AURORA_IO_CACHE_COHERENCY) && \
- defined(ARMADAXP)
- .cf_sdcache_wbinv_range = armadaxp_sdcache_wbinv_range,
- .cf_sdcache_inv_range = armadaxp_sdcache_inv_range,
- .cf_sdcache_wb_range = armadaxp_sdcache_wb_range,
-#else
- .cf_sdcache_wbinv_range = (void *)cpufunc_nullop,
- .cf_sdcache_inv_range = (void *)cpufunc_nullop,
- .cf_sdcache_wb_range = (void *)cpufunc_nullop,
-#endif
-
.cf_idcache_wbinv_all = armv7_idcache_wbinv_all,
.cf_idcache_wbinv_range = armv7_idcache_wbinv_range,
@@ -3096,6 +3083,36 @@
cpuctrl |= CPU_CONTROL_VECRELOC;
#endif
+#ifdef L2CACHE_ENABLE
+ /* Setup L2 cache */
+ arm_scache.cache_type = CPU_CT_CTYPE_WT;
+ arm_scache.cache_unified = 1;
+ arm_scache.dcache_type = arm_scache.icache_type = CACHE_TYPE_PIPT;
+ arm_scache.dcache_size = arm_scache.icache_size = ARMADAXP_L2_SIZE;
+ arm_scache.dcache_ways = arm_scache.icache_ways = ARMADAXP_L2_WAYS;
+ arm_scache.dcache_way_size = arm_scache.icache_way_size =
+ ARMADAXP_L2_WAY_SIZE;
+ arm_scache.dcache_line_size = arm_scache.icache_line_size =
+ ARMADAXP_L2_LINE_SIZE;
+ arm_scache.dcache_sets = arm_scache.icache_sets =
+ ARMADAXP_L2_SETS;
+
+ cpufuncs.cf_sdcache_wbinv_range = armadaxp_sdcache_wbinv_range;
+ cpufuncs.cf_sdcache_inv_range = armadaxp_sdcache_inv_range;
+ cpufuncs.cf_sdcache_wb_range = armadaxp_sdcache_wb_range;
+#endif
+
+#ifdef AURORA_IO_CACHE_COHERENCY
+ /* use AMBA and I/O Coherency Fabric to maintain cache */
+ cpufuncs.cf_dcache_wbinv_range = pj4b_dcache_cfu_wbinv_range;
+ cpufuncs.cf_dcache_inv_range = pj4b_dcache_cfu_inv_range;
+ cpufuncs.cf_dcache_wb_range = pj4b_dcache_cfu_wb_range;
+
+ cpufuncs.cf_sdcache_wbinv_range = (void *)cpufunc_nullop;
+ cpufuncs.cf_sdcache_inv_range = (void *)cpufunc_nullop;
+ cpufuncs.cf_sdcache_wb_range = (void *)cpufunc_nullop;
+#endif
+
/* Clear out the cache */
cpu_idcache_wbinv_all();
@@ -3104,6 +3121,9 @@
/* And again. */
cpu_idcache_wbinv_all();
+#ifdef L2CACHE_ENABLE
+ armadaxp_sdcache_wbinv_all();
+#endif
curcpu()->ci_ctrl = cpuctrl;
}
diff -r 68668b88b401 -r eda823bba54f sys/arch/arm/arm/cpufunc_asm_pj4b.S
--- a/sys/arch/arm/arm/cpufunc_asm_pj4b.S Thu May 14 02:43:33 2015 +0000
+++ b/sys/arch/arm/arm/cpufunc_asm_pj4b.S Thu May 14 05:39:32 2015 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: cpufunc_asm_pj4b.S,v 1.7 2015/04/15 10:52:18 hsuenaga Exp $ */
+/* $NetBSD: cpufunc_asm_pj4b.S,v 1.8 2015/05/14 05:39:32 hsuenaga Exp $ */
/*******************************************************************************
Copyright (C) Marvell International Ltd. and its affiliates
@@ -41,9 +41,10 @@
#include <arm/asm.h>
#include <arm/locore.h>
-.Lpj4b_cache_line_size:
- .word _C_LABEL(arm_dcache_align)
+.Lpj4b_l2_barrier_reg:
+ .word _C_LABEL(armadaxp_l2_barrier_reg)
+/* LINTSTUB: void pj4b_cpu_sleep(int); */
ENTRY(pj4b_cpu_sleep)
dsb
wfi @ wait for an interrupt
@@ -51,6 +52,7 @@
b irq_idle_entry @ assume we got an interrupt
END(pj4b_cpu_sleep)
+/* LINTSTUB: void pj4b_config(void); */
ENTRY(pj4b_config)
/* Set Auxiliary Debug Modes Control 0 register */
mrc p15, 1, r0, c15, c1, 0
@@ -87,3 +89,21 @@
RET
END(pj4b_config)
+
+/* LINTSTUB: void pj4b_io_coherency_barrier(vaddr_t, paddr_t, vsize_t); */
+ENTRY_NP(pj4b_io_coherency_barrier)
+ ldr r0, .Lpj4b_l2_barrier_reg
+ ldr r0, [r0] @ MVSOC_MLMB_CIB_BARRIER
+ mov r1, #1 @ MVSOC_MLMB_CIB_BARRIER_TRIGGER
+ str r1, [r0]
+1:
+ ldr r1, [r0]
+ tst r1, #1
+ beq 1b
+ dsb
+ RET
+END(pj4b_io_coherency_barrier)
+
+STRONG_ALIAS(pj4b_dcache_cfu_wbinv_range, pj4b_io_coherency_barrier)
+STRONG_ALIAS(pj4b_dcache_cfu_inv_range, pj4b_io_coherency_barrier)
+STRONG_ALIAS(pj4b_dcache_cfu_wb_range, pj4b_io_coherency_barrier)
diff -r 68668b88b401 -r eda823bba54f sys/arch/arm/include/cpufunc_proto.h
--- a/sys/arch/arm/include/cpufunc_proto.h Thu May 14 02:43:33 2015 +0000
+++ b/sys/arch/arm/include/cpufunc_proto.h Thu May 14 05:39:32 2015 +0000
@@ -326,6 +326,10 @@
void pj4b_cpu_sleep(int);
void pj4bv7_setup(char *string);
void pj4b_config(void);
+void pj4b_io_coherency_barrier(vaddr_t, paddr_t, vsize_t);
+void pj4b_dcache_cfu_inv_range(vaddr_t, vsize_t);
+void pj4b_dcache_cfu_wb_range(vaddr_t, vsize_t);
+void pj4b_dcache_cfu_wbinv_range(vaddr_t, vsize_t);
#endif /* CPU_PJ4B */
#if defined(CPU_ARM1136) || defined(CPU_ARM1176)
diff -r 68668b88b401 -r eda823bba54f sys/arch/arm/marvell/armadaxp.c
--- a/sys/arch/arm/marvell/armadaxp.c Thu May 14 02:43:33 2015 +0000
+++ b/sys/arch/arm/marvell/armadaxp.c Thu May 14 05:39:32 2015 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: armadaxp.c,v 1.12 2015/05/03 06:29:31 hsuenaga Exp $ */
+/* $NetBSD: armadaxp.c,v 1.13 2015/05/14 05:39:32 hsuenaga Exp $ */
/*******************************************************************************
Copyright (C) Marvell International Ltd. and its affiliates
@@ -37,7 +37,7 @@
*******************************************************************************/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: armadaxp.c,v 1.12 2015/05/03 06:29:31 hsuenaga Exp $");
+__KERNEL_RCSID(0, "$NetBSD: armadaxp.c,v 1.13 2015/05/14 05:39:32 hsuenaga Exp $");
#define _INTR_PRIVATE
@@ -89,6 +89,7 @@
int iocc_state = 0;
#define read_miscreg(r) (*(volatile uint32_t *)(misc_base + (r)))
vaddr_t misc_base;
+vaddr_t armadaxp_l2_barrier_reg;
extern void (*mvsoc_intr_init)(void);
static void armadaxp_intr_init(void);
@@ -432,11 +433,18 @@
return (-1);
}
+ /* Variables for cpufunc_asm_pj4b.S */
+ armadaxp_l2_barrier_reg = mlmb_base + MVSOC_MLMB_CIB_BARRIER_TRIGGER;
+
/* Set L2 policy */
reg = L2_READ(ARMADAXP_L2_AUX_CTRL);
- reg &= ~(L2_WBWT_MODE_MASK);
- reg &= ~(L2_REP_STRAT_MASK);
- reg |= L2_REP_STRAT_SEMIPLRU;
+ reg &= ~(L2_AUX_WBWT_MODE_MASK);
+ reg &= ~(L2_AUX_REP_STRAT_MASK);
+ reg |= L2_AUX_WBWT_MODE_WB;
+ reg |= L2_AUX_ECC_ENABLE;
+ reg |= L2_AUX_PARITY_ENABLE;
+ reg |= L2_AUX_FORCE_WA;
+ reg |= L2_AUX_REP_STRAT_SEMIPLRU;
L2_WRITE(ARMADAXP_L2_AUX_CTRL, reg);
/* Invalidate L2 cache */
@@ -460,7 +468,7 @@
/* Enable L2 cache */
reg = L2_READ(ARMADAXP_L2_CTRL);
- L2_WRITE(ARMADAXP_L2_CTRL, reg | L2_ENABLE);
+ L2_WRITE(ARMADAXP_L2_CTRL, reg | L2_CTRL_ENABLE);
/* Mark as enabled */
l2cache_state = 1;
@@ -497,39 +505,88 @@
__asm__ __volatile__("dsb");
}
+static paddr_t
+armadaxp_sdcache_wbalign_base(vaddr_t va, paddr_t pa, psize_t sz)
+{
+ paddr_t line_start = pa & ~ARMADAXP_L2_ALIGN;
+ vaddr_t save_start;
+ uint8_t save_buf[ARMADAXP_L2_LINE_SIZE];
+ size_t unalign;
+
+ unalign = va & ARMADAXP_L2_ALIGN;
+ if (unalign == 0)
+ return line_start; /* request is aligned to cache line size */
+
+ /* save data that is not intended to invalidate */
+ save_start = va & ~ARMADAXP_L2_ALIGN;
+ memcpy(save_buf, (void *)save_start, unalign);
+
+ /* invalidate include saved data */
+ L2_WRITE(ARMADAXP_L2_INV_PHYS, line_start);
+
+ /* write back saved data */
+ memcpy((void *)save_start, save_buf, unalign);
+ L2_WRITE(ARMADAXP_L2_WB_PHYS, line_start);
+ L2_WRITE(ARMADAXP_L2_SYNC, 0);
+ __asm__ __volatile__("dsb");
+
+ return line_start;
+}
+
+static paddr_t
+armadaxp_sdcache_wbalign_end(vaddr_t va, paddr_t pa, psize_t sz)
+{
+ paddr_t line_start = (pa + sz - 1) & ~ARMADAXP_L2_ALIGN;
+ vaddr_t save_start = va + sz;
+ uint8_t save_buf[ARMADAXP_L2_LINE_SIZE];
+ size_t save_len;
+ size_t unalign;
+
+ unalign = save_start & ARMADAXP_L2_ALIGN;
+ if (unalign == 0)
+ return line_start; /* request is aligned to cache line size */
+
+ /* save data that is not intended to invalidate */
+ save_len = ARMADAXP_L2_LINE_SIZE - unalign;
+ memcpy(save_buf, (void *)save_start, save_len);
+
+ /* invalidate include saved data */
+ L2_WRITE(ARMADAXP_L2_INV_PHYS, line_start);
+
+ /* write back saved data */
+ memcpy((void *)save_start, save_buf, save_len);
+ L2_WRITE(ARMADAXP_L2_WB_PHYS, line_start);
+ __asm__ __volatile__("dsb");
+
+ return line_start;
+}
+
void
armadaxp_sdcache_inv_range(vaddr_t va, paddr_t pa, psize_t sz)
{
- paddr_t pa_base = pa;
- paddr_t pa_end = pa + sz - 1;
+ paddr_t pa_base;
+ paddr_t pa_end;
- /* need write back if boundary is not aligned */
- if (pa_base & 0x1f)
- L2_WRITE(ARMADAXP_L2_WB_PHYS, (pa_base & ~0x1f));
- if (pa_end & 0x1f)
- L2_WRITE(ARMADAXP_L2_WB_PHYS, (pa_end & ~0x1f));
- L2_WRITE(ARMADAXP_L2_SYNC, 0);
- __asm__ __volatile__("dsb");
+ /* align and write-back the boundary */
+ pa_base = armadaxp_sdcache_wbalign_base(va, pa, sz);
+ pa_end = armadaxp_sdcache_wbalign_end(va, pa, sz);
/* invalidate other cache */
- pa_base &= ~0x1f;
- pa_end &= ~0x1f;
- if (pa_base == pa_end)
Home |
Main Index |
Thread Index |
Old Index