Module Name:    src
Committed By:   matt
Date:           Thu Feb 20 23:24:55 UTC 2014

Modified Files:
        src/sys/arch/arm/arm: cpufunc.c
        src/sys/arch/arm/arm32: cpu.c
        src/sys/arch/arm/include: cpufunc.h

Log Message:
Keep track of what each cache is (VIVT/VIPT/PIPT).

cpu0: 32KB/32B 2-way L1 VIPT Instruction cache
cpu0: 32KB/64B 4-way write-back-locking-C L1 PIPT Data cache
cpu0: 256KB/64B 8-way write-through L2 PIPT Unified cache


To generate a diff of this commit:
cvs rdiff -u -r1.138 -r1.139 src/sys/arch/arm/arm/cpufunc.c
cvs rdiff -u -r1.99 -r1.100 src/sys/arch/arm/arm32/cpu.c
cvs rdiff -u -r1.66 -r1.67 src/sys/arch/arm/include/cpufunc.h

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: src/sys/arch/arm/arm/cpufunc.c
diff -u src/sys/arch/arm/arm/cpufunc.c:1.138 src/sys/arch/arm/arm/cpufunc.c:1.139
--- src/sys/arch/arm/arm/cpufunc.c:1.138	Thu Feb 20 17:38:42 2014
+++ src/sys/arch/arm/arm/cpufunc.c	Thu Feb 20 23:24:55 2014
@@ -1,4 +1,4 @@
-/*	$NetBSD: cpufunc.c,v 1.138 2014/02/20 17:38:42 matt Exp $	*/
+/*	$NetBSD: cpufunc.c,v 1.139 2014/02/20 23:24:55 matt 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.138 2014/02/20 17:38:42 matt Exp $");
+__KERNEL_RCSID(0, "$NetBSD: cpufunc.c,v 1.139 2014/02/20 23:24:55 matt Exp $");
 
 #include "opt_compat_netbsd.h"
 #include "opt_cpuoptions.h"
@@ -1509,7 +1509,7 @@ get_cacheinfo_clidr(struct arm_cache_inf
 	u_int nsets;
 
 	if (clidr & 6) {
-		csid = get_cachesize_cp15(level << 1); /* select L1 dcache values */
+		csid = get_cachesize_cp15(level << 1); /* select dcache values */
 		nsets = CPU_CSID_NUMSETS(csid) + 1;
 		info->dcache_ways = CPU_CSID_ASSOC(csid) + 1;
 		info->dcache_line_size = 1U << (CPU_CSID_LEN(csid) + 4);
@@ -1518,22 +1518,32 @@ get_cacheinfo_clidr(struct arm_cache_inf
 		if (level == 0) {
 			arm_dcache_log2_assoc = CPU_CSID_ASSOC(csid) + 1;
 			arm_dcache_log2_linesize = CPU_CSID_LEN(csid) + 4;
-			arm_dcache_log2_nsets = 31 - __builtin_clz(nsets);
+			arm_dcache_log2_nsets = 31 - __builtin_clz(nsets*2-1);
 		}
 	}
 
 	info->cache_unified = (clidr == 4);
 
-	if (clidr & 1) {
-		csid = get_cachesize_cp15((level << 1)|CPU_CSSR_InD); /* select L1 icache values */
+	if (level > 0) {
+		info->dcache_type = CACHE_TYPE_PIPT;
+		info->icache_type = CACHE_TYPE_PIPT;
+	}
+
+	if (info->cache_unified) {
+		info->icache_ways = info->dcache_ways;
+		info->icache_line_size = info->dcache_line_size;
+		info->icache_size = info->dcache_size;
+	} else {
+		csid = get_cachesize_cp15((level << 1)|CPU_CSSR_InD); /* select icache values */
 		nsets = CPU_CSID_NUMSETS(csid) + 1;
 		info->icache_ways = CPU_CSID_ASSOC(csid) + 1;
 		info->icache_line_size = 1U << (CPU_CSID_LEN(csid) + 4);
 		info->icache_size = info->icache_line_size * info->icache_ways * nsets;
-	} else {
-		info->icache_ways = info->dcache_ways;
-		info->icache_line_size = info->dcache_line_size;
-		info->icache_size = info->dcache_size;
+	}
+	if (level == 0
+	    && info->dcache_size / info->dcache_ways <= PAGE_SIZE
+	    && info->icache_size / info->icache_ways <= PAGE_SIZE) {
+		arm_cache_prefer_mask = 0;
 	}
 }
 #endif /* (ARM_MMU_V6 + ARM_MMU_V7) > 0 */
@@ -1561,9 +1571,20 @@ get_cachetype_cp15(void)
 	if (CPU_CT_FORMAT(ctype) == 4) {
 		u_int clidr = armreg_clidr_read();
 
-		if (CPU_CT4_L1IPOLICY(ctype) != CPU_CT4_L1_PIPT) {
+		if (CPU_CT4_L1IPOLICY(ctype) == CPU_CT4_L1_PIPT) {
+			arm_pcache.icache_type = CACHE_TYPE_PIPT;
+		} else {
+			arm_pcache.icache_type = CACHE_TYPE_VIPT;
 			arm_cache_prefer_mask = PAGE_SIZE;
 		}
+#ifdef CPU_CORTEX
+		if (CPU_ID_CORTEX_P(cpu_id())) {
+			arm_pcache.dcache_type = CACHE_TYPE_PIPT;
+		} else
+#endif
+		{
+			arm_pcache.dcache_type = CACHE_TYPE_VIPT;
+		}
 		arm_pcache.cache_type = CPU_CT_CTYPE_WB14;
 
 		get_cacheinfo_clidr(&arm_pcache, 0, clidr & 7);
@@ -1574,6 +1595,9 @@ get_cachetype_cp15(void)
 			if (arm_scache.dcache_line_size < arm_dcache_align)
 				arm_dcache_align = arm_scache.dcache_line_size;
 		}
+		if (arm_pcache.dcache_type == CACHE_TYPE_PIPT) {
+			arm_cache_prefer_mask = 0;
+		}
 		goto out;
 	}
 #endif /* ARM_MMU_V6 + ARM_MMU_V7 > 0 */
@@ -1600,6 +1624,7 @@ get_cachetype_cp15(void)
 			arm_pcache.icache_ways = multiplier <<
 			    (CPU_CT_xSIZE_ASSOC(isize) - 1);
 #if (ARM_MMU_V6 + ARM_MMU_V7) > 0
+			arm_pcache.icache_type = CACHE_TYPE_VIPT;
 			if (CPU_CT_xSIZE_P & isize)
 				arm_cache_prefer_mask |=
 				    __BIT(9 + CPU_CT_xSIZE_SIZE(isize)
@@ -1621,11 +1646,14 @@ get_cachetype_cp15(void)
 	} else {
 		arm_pcache.dcache_ways = multiplier <<
 		    (CPU_CT_xSIZE_ASSOC(dsize) - 1);
-#if (ARM_MMU_V6 + ARM_MMU_V7) > 0
-		if (CPU_CT_xSIZE_P & dsize)
+#if (ARM_MMU_V6) > 0
+		arm_pcache.dcache_type = CACHE_TYPE_VIPT;
+		if ((CPU_CT_xSIZE_P & dsize)
+		    && CPU_ID_ARM11_P(curcpu()->ci_arm_cpuid)) {
 			arm_cache_prefer_mask |=
 			    __BIT(9 + CPU_CT_xSIZE_SIZE(dsize)
 				  - CPU_CT_xSIZE_ASSOC(dsize)) - PAGE_SIZE;
+		}
 #endif
 	}
 	arm_pcache.dcache_size = multiplier << (CPU_CT_xSIZE_SIZE(dsize) + 8);
@@ -1638,6 +1666,9 @@ get_cachetype_cp15(void)
 	    CPU_CT_xSIZE_ASSOC(dsize) - CPU_CT_xSIZE_LEN(dsize);
 
  out:
+	KASSERTMSG(arm_dcache_align <= CACHE_LINE_SIZE,
+	    "arm_dcache_align=%u CACHE_LINE_SIZE=%u",
+	    arm_dcache_align, CACHE_LINE_SIZE);
 	arm_dcache_align_mask = arm_dcache_align - 1;
 }
 #endif /* ARM7TDMI || ARM8 || ARM9 || XSCALE */

Index: src/sys/arch/arm/arm32/cpu.c
diff -u src/sys/arch/arm/arm32/cpu.c:1.99 src/sys/arch/arm/arm32/cpu.c:1.100
--- src/sys/arch/arm/arm32/cpu.c:1.99	Sat Sep  7 23:10:02 2013
+++ src/sys/arch/arm/arm32/cpu.c	Thu Feb 20 23:24:55 2014
@@ -1,4 +1,4 @@
-/*	$NetBSD: cpu.c,v 1.99 2013/09/07 23:10:02 matt Exp $	*/
+/*	$NetBSD: cpu.c,v 1.100 2014/02/20 23:24:55 matt Exp $	*/
 
 /*
  * Copyright (c) 1995 Mark Brinicombe.
@@ -46,7 +46,7 @@
 
 #include <sys/param.h>
 
-__KERNEL_RCSID(0, "$NetBSD: cpu.c,v 1.99 2013/09/07 23:10:02 matt Exp $");
+__KERNEL_RCSID(0, "$NetBSD: cpu.c,v 1.100 2014/02/20 23:24:55 matt Exp $");
 
 #include <sys/systm.h>
 #include <sys/conf.h>
@@ -565,18 +565,24 @@ static void
 print_cache_info(device_t dv, struct arm_cache_info *info, u_int level)
 {
 	if (info->cache_unified) {
-		aprint_normal_dev(dv, "%dKB/%dB %d-way %s L%u Unified cache\n",
+		aprint_normal_dev(dv, "%dKB/%dB %d-way %s L%u %cI%cT Unified cache\n",
 		    info->dcache_size / 1024,
 		    info->dcache_line_size, info->dcache_ways,
-		    wtnames[info->cache_type], level + 1);
+		    wtnames[info->cache_type], level + 1,
+		    info->dcache_type & CACHE_TYPE_PIxx ? 'P' : 'V',
+		    info->dcache_type & CACHE_TYPE_xxPT ? 'P' : 'V');
 	} else {
-		aprint_normal_dev(dv, "%dKB/%dB %d-way L%u Instruction cache\n",
+		aprint_normal_dev(dv, "%dKB/%dB %d-way L%u %cI%cT Instruction cache\n",
 		    info->icache_size / 1024,
-		    info->icache_line_size, info->icache_ways, level + 1);
-		aprint_normal_dev(dv, "%dKB/%dB %d-way %s L%u Data cache\n",
+		    info->icache_line_size, info->icache_ways, level + 1,
+		    info->icache_type & CACHE_TYPE_PIxx ? 'P' : 'V',
+		    info->icache_type & CACHE_TYPE_xxPT ? 'P' : 'V');
+		aprint_normal_dev(dv, "%dKB/%dB %d-way %s L%u %cI%cT Data cache\n",
 		    info->dcache_size / 1024, 
 		    info->dcache_line_size, info->dcache_ways,
-		    wtnames[info->cache_type], level + 1);
+		    wtnames[info->cache_type], level + 1,
+		    info->dcache_type & CACHE_TYPE_PIxx ? 'P' : 'V',
+		    info->dcache_type & CACHE_TYPE_xxPT ? 'P' : 'V');
 	}
 }
 

Index: src/sys/arch/arm/include/cpufunc.h
diff -u src/sys/arch/arm/include/cpufunc.h:1.66 src/sys/arch/arm/include/cpufunc.h:1.67
--- src/sys/arch/arm/include/cpufunc.h:1.66	Thu Feb 20 17:19:55 2014
+++ src/sys/arch/arm/include/cpufunc.h	Thu Feb 20 23:24:54 2014
@@ -744,6 +744,11 @@ void cpu_reset		(void) __dead;
 /*
  * Cache info variables.
  */
+#define	CACHE_TYPE_VIVT		0
+#define	CACHE_TYPE_xxPT		1
+#define	CACHE_TYPE_VIPT		1
+#define	CACHE_TYPE_PIxx		2
+#define	CACHE_TYPE_PIPT		3
 
 /* PRIMARY CACHE VARIABLES */
 struct arm_cache_info {
@@ -759,6 +764,8 @@ struct arm_cache_info {
 
 	u_int cache_type;
 	bool cache_unified;
+	uint8_t icache_type;
+	uint8_t dcache_type;
 };
 
 extern u_int arm_cache_prefer_mask;

Reply via email to