From 5159250118c6f58a469fc9185ea4227f852e51d0 Mon Sep 17 00:00:00 2001
From: Samuel Holland <samuel@sholland.org>
Date: Sun, 5 Feb 2023 09:44:05 -0600
Subject: [PATCH 04/68] riscv: cpu: thead: Initialize extension CSRs

Enable the T-HEAD ISA extensions, as these are required to use the cache
maintenance instructions. Enable the branch predictor and BTB to improve
performance. Some bits are only available on specific CPU models, so
provide Kconfig symbols for selecting the right model.

Signed-off-by: Samuel Holland <samuel@sholland.org>
---
 arch/riscv/Kconfig           |  1 +
 arch/riscv/cpu/thead/Kconfig |  7 +++++++
 arch/riscv/cpu/thead/cpu.c   | 21 +++++++++++++++++++++
 3 files changed, 29 insertions(+)
 create mode 100644 arch/riscv/cpu/thead/Kconfig

--- a/arch/riscv/Kconfig
+++ b/arch/riscv/Kconfig
@@ -89,6 +89,7 @@ source "arch/riscv/cpu/fu540/Kconfig"
 source "arch/riscv/cpu/fu740/Kconfig"
 source "arch/riscv/cpu/generic/Kconfig"
 source "arch/riscv/cpu/jh7110/Kconfig"
+source "arch/riscv/cpu/thead/Kconfig"
 
 # architecture-specific options below
 
--- /dev/null
+++ b/arch/riscv/cpu/thead/Kconfig
@@ -0,0 +1,7 @@
+# SPDX-License-Identifier: GPL-2.0+
+
+config THEAD_C906
+	bool
+
+config THEAD_E906
+	bool
--- a/arch/riscv/cpu/thead/cpu.c
+++ b/arch/riscv/cpu/thead/cpu.c
@@ -5,6 +5,10 @@
 
 #include <irq_func.h>
 #include <asm/cache.h>
+#include <asm/csr.h>
+#include <linux/bitops.h>
+
+#include "thead_csr.h"
 
 /*
  * cleanup_before_linux() is called just before we call linux
@@ -20,3 +24,20 @@ int cleanup_before_linux(void)
 
 	return 0;
 }
+
+void harts_early_init(void)
+{
+	if (!CONFIG_IS_ENABLED(RISCV_MMODE))
+		return;
+
+	csr_set(CSR_MXSTATUS, MXSTATUS_THEADISAEE | MXSTATUS_MM);
+	if (IS_ENABLED(THEAD_C906)) {
+		csr_set(CSR_MHCR,
+			MHCR_BTB_C906 | MHCR_BPE | MHCR_RS | MHCR_WB | MHCR_WA);
+		csr_set(CSR_MHINT, MHINT_IWPE | MHINT_IPLD | MHINT_IPLD);
+	}
+	if (IS_ENABLED(THEAD_E906)) {
+		csr_set(CSR_MHCR,
+			MHCR_BTB_E906 | MHCR_BPE | MHCR_RS | MHCR_WB | MHCR_WA);
+	}
+}
