aboutsummaryrefslogtreecommitdiff
path: root/target
diff options
context:
space:
mode:
authorSong Gao <gaosong@loongson.cn>2023-10-20 16:49:24 +0800
committerSong Gao <gaosong@loongson.cn>2023-11-03 14:13:02 +0800
commit464136ceb65ddebbd60fecd486628cc82fd722ab (patch)
treee4e1c2403356169ecbe007ba25b7c77be0f861c0 /target
parentd6f077321ae3f9508d3e066455ae1278ab3213e5 (diff)
target/loongarch: Allow user enable/disable LSX/LASX features
Some users may not need LSX/LASX, this patch allows the user enable/disable LSX/LASX features. e.g '-cpu max,lsx=on,lasx=on' (default); '-cpu max,lsx=on,lasx=off' (enabled LSX); '-cpu max,lsx=off,lasx=on' (enabled LASX, LSX); '-cpu max,lsx=off' (disable LSX and LASX). Signed-off-by: Song Gao <gaosong@loongson.cn> Reviewed-by: Richard Henderson <richard.henderson@linaro.org> Message-Id: <20231020084925.3457084-3-gaosong@loongson.cn>
Diffstat (limited to 'target')
-rw-r--r--target/loongarch/cpu.c67
-rw-r--r--target/loongarch/cpu.h2
2 files changed, 69 insertions, 0 deletions
diff --git a/target/loongarch/cpu.c b/target/loongarch/cpu.c
index ef6922e812..a60d07acd5 100644
--- a/target/loongarch/cpu.c
+++ b/target/loongarch/cpu.c
@@ -443,6 +443,7 @@ static void loongarch_la464_initfn(Object *obj)
env->cpucfg[20] = data;
env->CSR_ASID = FIELD_DP64(0, CSR_ASID, ASIDBITS, 0xa);
+ loongarch_cpu_post_init(obj);
}
static void loongarch_la132_initfn(Object *obj)
@@ -622,6 +623,72 @@ static const MemoryRegionOps loongarch_qemu_ops = {
};
#endif
+static bool loongarch_get_lsx(Object *obj, Error **errp)
+{
+ LoongArchCPU *cpu = LOONGARCH_CPU(obj);
+ bool ret;
+
+ if (FIELD_EX32(cpu->env.cpucfg[2], CPUCFG2, LSX)) {
+ ret = true;
+ } else {
+ ret = false;
+ }
+ return ret;
+}
+
+static void loongarch_set_lsx(Object *obj, bool value, Error **errp)
+{
+ LoongArchCPU *cpu = LOONGARCH_CPU(obj);
+
+ if (value) {
+ cpu->env.cpucfg[2] = FIELD_DP32(cpu->env.cpucfg[2], CPUCFG2, LSX, 1);
+ } else {
+ cpu->env.cpucfg[2] = FIELD_DP32(cpu->env.cpucfg[2], CPUCFG2, LSX, 0);
+ cpu->env.cpucfg[2] = FIELD_DP32(cpu->env.cpucfg[2], CPUCFG2, LASX, 0);
+ }
+}
+
+static bool loongarch_get_lasx(Object *obj, Error **errp)
+{
+ LoongArchCPU *cpu = LOONGARCH_CPU(obj);
+ bool ret;
+
+ if (FIELD_EX32(cpu->env.cpucfg[2], CPUCFG2, LASX)) {
+ ret = true;
+ } else {
+ ret = false;
+ }
+ return ret;
+}
+
+static void loongarch_set_lasx(Object *obj, bool value, Error **errp)
+{
+ LoongArchCPU *cpu = LOONGARCH_CPU(obj);
+
+ if (value) {
+ if (!FIELD_EX32(cpu->env.cpucfg[2], CPUCFG2, LSX)) {
+ cpu->env.cpucfg[2] = FIELD_DP32(cpu->env.cpucfg[2], CPUCFG2, LSX, 1);
+ }
+ cpu->env.cpucfg[2] = FIELD_DP32(cpu->env.cpucfg[2], CPUCFG2, LASX, 1);
+ } else {
+ cpu->env.cpucfg[2] = FIELD_DP32(cpu->env.cpucfg[2], CPUCFG2, LASX, 0);
+ }
+}
+
+void loongarch_cpu_post_init(Object *obj)
+{
+ LoongArchCPU *cpu = LOONGARCH_CPU(obj);
+
+ if (FIELD_EX32(cpu->env.cpucfg[2], CPUCFG2, LSX)) {
+ object_property_add_bool(obj, "lsx", loongarch_get_lsx,
+ loongarch_set_lsx);
+ }
+ if (FIELD_EX32(cpu->env.cpucfg[2], CPUCFG2, LASX)) {
+ object_property_add_bool(obj, "lasx", loongarch_get_lasx,
+ loongarch_set_lasx);
+ }
+}
+
static void loongarch_cpu_init(Object *obj)
{
#ifndef CONFIG_USER_ONLY
diff --git a/target/loongarch/cpu.h b/target/loongarch/cpu.h
index 8b54cf109c..9d0f79f814 100644
--- a/target/loongarch/cpu.h
+++ b/target/loongarch/cpu.h
@@ -486,4 +486,6 @@ void loongarch_cpu_list(void);
#define LOONGARCH_CPU_TYPE_NAME(model) model LOONGARCH_CPU_TYPE_SUFFIX
#define CPU_RESOLVING_TYPE TYPE_LOONGARCH_CPU
+void loongarch_cpu_post_init(Object *obj);
+
#endif /* LOONGARCH_CPU_H */