usb-mtp: outlaw slashes in filenames
[qemu/ar7.git] / target / riscv / cpu.c
bloba025a0a3baacb356aa83814ea2d30e1cd54bfcbb
1 /*
2 * QEMU RISC-V CPU
4 * Copyright (c) 2016-2017 Sagar Karandikar, sagark@eecs.berkeley.edu
5 * Copyright (c) 2017-2018 SiFive, Inc.
7 * This program is free software; you can redistribute it and/or modify it
8 * under the terms and conditions of the GNU General Public License,
9 * version 2 or later, as published by the Free Software Foundation.
11 * This program is distributed in the hope it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
14 * more details.
16 * You should have received a copy of the GNU General Public License along with
17 * this program. If not, see <http://www.gnu.org/licenses/>.
20 #include "qemu/osdep.h"
21 #include "qemu/log.h"
22 #include "cpu.h"
23 #include "exec/exec-all.h"
24 #include "qapi/error.h"
25 #include "migration/vmstate.h"
27 /* RISC-V CPU definitions */
29 static const char riscv_exts[26] = "IEMAFDQCLBJTPVNSUHKORWXYZG";
31 const char * const riscv_int_regnames[] = {
32 "zero", "ra ", "sp ", "gp ", "tp ", "t0 ", "t1 ", "t2 ",
33 "s0 ", "s1 ", "a0 ", "a1 ", "a2 ", "a3 ", "a4 ", "a5 ",
34 "a6 ", "a7 ", "s2 ", "s3 ", "s4 ", "s5 ", "s6 ", "s7 ",
35 "s8 ", "s9 ", "s10 ", "s11 ", "t3 ", "t4 ", "t5 ", "t6 "
38 const char * const riscv_fpr_regnames[] = {
39 "ft0 ", "ft1 ", "ft2 ", "ft3 ", "ft4 ", "ft5 ", "ft6 ", "ft7 ",
40 "fs0 ", "fs1 ", "fa0 ", "fa1 ", "fa2 ", "fa3 ", "fa4 ", "fa5 ",
41 "fa6 ", "fa7 ", "fs2 ", "fs3 ", "fs4 ", "fs5 ", "fs6 ", "fs7 ",
42 "fs8 ", "fs9 ", "fs10", "fs11", "ft8 ", "ft9 ", "ft10", "ft11"
45 const char * const riscv_excp_names[] = {
46 "misaligned_fetch",
47 "fault_fetch",
48 "illegal_instruction",
49 "breakpoint",
50 "misaligned_load",
51 "fault_load",
52 "misaligned_store",
53 "fault_store",
54 "user_ecall",
55 "supervisor_ecall",
56 "hypervisor_ecall",
57 "machine_ecall",
58 "exec_page_fault",
59 "load_page_fault",
60 "reserved",
61 "store_page_fault"
64 const char * const riscv_intr_names[] = {
65 "u_software",
66 "s_software",
67 "h_software",
68 "m_software",
69 "u_timer",
70 "s_timer",
71 "h_timer",
72 "m_timer",
73 "u_external",
74 "s_external",
75 "h_external",
76 "m_external",
77 "reserved",
78 "reserved",
79 "reserved",
80 "reserved"
83 typedef struct RISCVCPUInfo {
84 const int bit_widths;
85 const char *name;
86 void (*initfn)(Object *obj);
87 } RISCVCPUInfo;
89 static void set_misa(CPURISCVState *env, target_ulong misa)
91 env->misa = misa;
94 static void set_versions(CPURISCVState *env, int user_ver, int priv_ver)
96 env->user_ver = user_ver;
97 env->priv_ver = priv_ver;
100 static void set_feature(CPURISCVState *env, int feature)
102 env->features |= (1ULL << feature);
105 static void set_resetvec(CPURISCVState *env, int resetvec)
107 #ifndef CONFIG_USER_ONLY
108 env->resetvec = resetvec;
109 #endif
112 static void riscv_any_cpu_init(Object *obj)
114 CPURISCVState *env = &RISCV_CPU(obj)->env;
115 set_misa(env, RVXLEN | RVI | RVM | RVA | RVF | RVD | RVC | RVU);
116 set_versions(env, USER_VERSION_2_02_0, PRIV_VERSION_1_10_0);
117 set_resetvec(env, DEFAULT_RSTVEC);
120 #if defined(TARGET_RISCV32)
122 static void rv32gcsu_priv1_09_1_cpu_init(Object *obj)
124 CPURISCVState *env = &RISCV_CPU(obj)->env;
125 set_misa(env, RV32 | RVI | RVM | RVA | RVF | RVD | RVC | RVS | RVU);
126 set_versions(env, USER_VERSION_2_02_0, PRIV_VERSION_1_09_1);
127 set_resetvec(env, DEFAULT_RSTVEC);
128 set_feature(env, RISCV_FEATURE_MMU);
131 static void rv32gcsu_priv1_10_0_cpu_init(Object *obj)
133 CPURISCVState *env = &RISCV_CPU(obj)->env;
134 set_misa(env, RV32 | RVI | RVM | RVA | RVF | RVD | RVC | RVS | RVU);
135 set_versions(env, USER_VERSION_2_02_0, PRIV_VERSION_1_10_0);
136 set_resetvec(env, DEFAULT_RSTVEC);
137 set_feature(env, RISCV_FEATURE_MMU);
140 static void rv32imacu_nommu_cpu_init(Object *obj)
142 CPURISCVState *env = &RISCV_CPU(obj)->env;
143 set_misa(env, RV32 | RVI | RVM | RVA | RVC | RVU);
144 set_versions(env, USER_VERSION_2_02_0, PRIV_VERSION_1_10_0);
145 set_resetvec(env, DEFAULT_RSTVEC);
148 #elif defined(TARGET_RISCV64)
150 static void rv64gcsu_priv1_09_1_cpu_init(Object *obj)
152 CPURISCVState *env = &RISCV_CPU(obj)->env;
153 set_misa(env, RV64 | RVI | RVM | RVA | RVF | RVD | RVC | RVS | RVU);
154 set_versions(env, USER_VERSION_2_02_0, PRIV_VERSION_1_09_1);
155 set_resetvec(env, DEFAULT_RSTVEC);
156 set_feature(env, RISCV_FEATURE_MMU);
159 static void rv64gcsu_priv1_10_0_cpu_init(Object *obj)
161 CPURISCVState *env = &RISCV_CPU(obj)->env;
162 set_misa(env, RV64 | RVI | RVM | RVA | RVF | RVD | RVC | RVS | RVU);
163 set_versions(env, USER_VERSION_2_02_0, PRIV_VERSION_1_10_0);
164 set_resetvec(env, DEFAULT_RSTVEC);
165 set_feature(env, RISCV_FEATURE_MMU);
168 static void rv64imacu_nommu_cpu_init(Object *obj)
170 CPURISCVState *env = &RISCV_CPU(obj)->env;
171 set_misa(env, RV64 | RVI | RVM | RVA | RVC | RVU);
172 set_versions(env, USER_VERSION_2_02_0, PRIV_VERSION_1_10_0);
173 set_resetvec(env, DEFAULT_RSTVEC);
176 #endif
178 static ObjectClass *riscv_cpu_class_by_name(const char *cpu_model)
180 ObjectClass *oc;
181 char *typename;
182 char **cpuname;
184 cpuname = g_strsplit(cpu_model, ",", 1);
185 typename = g_strdup_printf(RISCV_CPU_TYPE_NAME("%s"), cpuname[0]);
186 oc = object_class_by_name(typename);
187 g_strfreev(cpuname);
188 g_free(typename);
189 if (!oc || !object_class_dynamic_cast(oc, TYPE_RISCV_CPU) ||
190 object_class_is_abstract(oc)) {
191 return NULL;
193 return oc;
196 static void riscv_cpu_dump_state(CPUState *cs, FILE *f,
197 fprintf_function cpu_fprintf, int flags)
199 RISCVCPU *cpu = RISCV_CPU(cs);
200 CPURISCVState *env = &cpu->env;
201 int i;
203 cpu_fprintf(f, " %s " TARGET_FMT_lx "\n", "pc ", env->pc);
204 #ifndef CONFIG_USER_ONLY
205 cpu_fprintf(f, " %s " TARGET_FMT_lx "\n", "mhartid ", env->mhartid);
206 cpu_fprintf(f, " %s " TARGET_FMT_lx "\n", "mstatus ", env->mstatus);
207 cpu_fprintf(f, " %s " TARGET_FMT_lx "\n", "mip ",
208 (target_ulong)atomic_read(&env->mip));
209 cpu_fprintf(f, " %s " TARGET_FMT_lx "\n", "mie ", env->mie);
210 cpu_fprintf(f, " %s " TARGET_FMT_lx "\n", "mideleg ", env->mideleg);
211 cpu_fprintf(f, " %s " TARGET_FMT_lx "\n", "medeleg ", env->medeleg);
212 cpu_fprintf(f, " %s " TARGET_FMT_lx "\n", "mtvec ", env->mtvec);
213 cpu_fprintf(f, " %s " TARGET_FMT_lx "\n", "mepc ", env->mepc);
214 cpu_fprintf(f, " %s " TARGET_FMT_lx "\n", "mcause ", env->mcause);
215 #endif
217 for (i = 0; i < 32; i++) {
218 cpu_fprintf(f, " %s " TARGET_FMT_lx,
219 riscv_int_regnames[i], env->gpr[i]);
220 if ((i & 3) == 3) {
221 cpu_fprintf(f, "\n");
224 if (flags & CPU_DUMP_FPU) {
225 for (i = 0; i < 32; i++) {
226 cpu_fprintf(f, " %s %016" PRIx64,
227 riscv_fpr_regnames[i], env->fpr[i]);
228 if ((i & 3) == 3) {
229 cpu_fprintf(f, "\n");
235 static void riscv_cpu_set_pc(CPUState *cs, vaddr value)
237 RISCVCPU *cpu = RISCV_CPU(cs);
238 CPURISCVState *env = &cpu->env;
239 env->pc = value;
242 static void riscv_cpu_synchronize_from_tb(CPUState *cs, TranslationBlock *tb)
244 RISCVCPU *cpu = RISCV_CPU(cs);
245 CPURISCVState *env = &cpu->env;
246 env->pc = tb->pc;
249 static bool riscv_cpu_has_work(CPUState *cs)
251 #ifndef CONFIG_USER_ONLY
252 RISCVCPU *cpu = RISCV_CPU(cs);
253 CPURISCVState *env = &cpu->env;
255 * Definition of the WFI instruction requires it to ignore the privilege
256 * mode and delegation registers, but respect individual enables
258 return (atomic_read(&env->mip) & env->mie) != 0;
259 #else
260 return true;
261 #endif
264 void restore_state_to_opc(CPURISCVState *env, TranslationBlock *tb,
265 target_ulong *data)
267 env->pc = data[0];
270 static void riscv_cpu_reset(CPUState *cs)
272 RISCVCPU *cpu = RISCV_CPU(cs);
273 RISCVCPUClass *mcc = RISCV_CPU_GET_CLASS(cpu);
274 CPURISCVState *env = &cpu->env;
276 mcc->parent_reset(cs);
277 #ifndef CONFIG_USER_ONLY
278 env->priv = PRV_M;
279 env->mstatus &= ~(MSTATUS_MIE | MSTATUS_MPRV);
280 env->mcause = 0;
281 env->pc = env->resetvec;
282 #endif
283 cs->exception_index = EXCP_NONE;
284 set_default_nan_mode(1, &env->fp_status);
287 static void riscv_cpu_disas_set_info(CPUState *s, disassemble_info *info)
289 #if defined(TARGET_RISCV32)
290 info->print_insn = print_insn_riscv32;
291 #elif defined(TARGET_RISCV64)
292 info->print_insn = print_insn_riscv64;
293 #endif
296 static void riscv_cpu_realize(DeviceState *dev, Error **errp)
298 CPUState *cs = CPU(dev);
299 RISCVCPUClass *mcc = RISCV_CPU_GET_CLASS(dev);
300 Error *local_err = NULL;
302 cpu_exec_realizefn(cs, &local_err);
303 if (local_err != NULL) {
304 error_propagate(errp, local_err);
305 return;
308 qemu_init_vcpu(cs);
309 cpu_reset(cs);
311 mcc->parent_realize(dev, errp);
314 static void riscv_cpu_init(Object *obj)
316 CPUState *cs = CPU(obj);
317 RISCVCPU *cpu = RISCV_CPU(obj);
319 cs->env_ptr = &cpu->env;
322 static const VMStateDescription vmstate_riscv_cpu = {
323 .name = "cpu",
324 .unmigratable = 1,
327 static void riscv_cpu_class_init(ObjectClass *c, void *data)
329 RISCVCPUClass *mcc = RISCV_CPU_CLASS(c);
330 CPUClass *cc = CPU_CLASS(c);
331 DeviceClass *dc = DEVICE_CLASS(c);
333 mcc->parent_realize = dc->realize;
334 dc->realize = riscv_cpu_realize;
336 mcc->parent_reset = cc->reset;
337 cc->reset = riscv_cpu_reset;
339 cc->class_by_name = riscv_cpu_class_by_name;
340 cc->has_work = riscv_cpu_has_work;
341 cc->do_interrupt = riscv_cpu_do_interrupt;
342 cc->cpu_exec_interrupt = riscv_cpu_exec_interrupt;
343 cc->dump_state = riscv_cpu_dump_state;
344 cc->set_pc = riscv_cpu_set_pc;
345 cc->synchronize_from_tb = riscv_cpu_synchronize_from_tb;
346 cc->gdb_read_register = riscv_cpu_gdb_read_register;
347 cc->gdb_write_register = riscv_cpu_gdb_write_register;
348 cc->gdb_num_core_regs = 65;
349 cc->gdb_stop_before_watchpoint = true;
350 cc->disas_set_info = riscv_cpu_disas_set_info;
351 #ifdef CONFIG_USER_ONLY
352 cc->handle_mmu_fault = riscv_cpu_handle_mmu_fault;
353 #else
354 cc->do_unaligned_access = riscv_cpu_do_unaligned_access;
355 cc->get_phys_page_debug = riscv_cpu_get_phys_page_debug;
356 #endif
357 #ifdef CONFIG_TCG
358 cc->tcg_initialize = riscv_translate_init;
359 #endif
360 /* For now, mark unmigratable: */
361 cc->vmsd = &vmstate_riscv_cpu;
364 char *riscv_isa_string(RISCVCPU *cpu)
366 int i;
367 const size_t maxlen = sizeof("rv128") + sizeof(riscv_exts) + 1;
368 char *isa_str = g_new(char, maxlen);
369 char *p = isa_str + snprintf(isa_str, maxlen, "rv%d", TARGET_LONG_BITS);
370 for (i = 0; i < sizeof(riscv_exts); i++) {
371 if (cpu->env.misa & RV(riscv_exts[i])) {
372 *p++ = qemu_tolower(riscv_exts[i]);
375 *p = '\0';
376 return isa_str;
379 typedef struct RISCVCPUListState {
380 fprintf_function cpu_fprintf;
381 FILE *file;
382 } RISCVCPUListState;
384 static gint riscv_cpu_list_compare(gconstpointer a, gconstpointer b)
386 ObjectClass *class_a = (ObjectClass *)a;
387 ObjectClass *class_b = (ObjectClass *)b;
388 const char *name_a, *name_b;
390 name_a = object_class_get_name(class_a);
391 name_b = object_class_get_name(class_b);
392 return strcmp(name_a, name_b);
395 static void riscv_cpu_list_entry(gpointer data, gpointer user_data)
397 RISCVCPUListState *s = user_data;
398 const char *typename = object_class_get_name(OBJECT_CLASS(data));
399 int len = strlen(typename) - strlen(RISCV_CPU_TYPE_SUFFIX);
401 (*s->cpu_fprintf)(s->file, "%.*s\n", len, typename);
404 void riscv_cpu_list(FILE *f, fprintf_function cpu_fprintf)
406 RISCVCPUListState s = {
407 .cpu_fprintf = cpu_fprintf,
408 .file = f,
410 GSList *list;
412 list = object_class_get_list(TYPE_RISCV_CPU, false);
413 list = g_slist_sort(list, riscv_cpu_list_compare);
414 g_slist_foreach(list, riscv_cpu_list_entry, &s);
415 g_slist_free(list);
418 #define DEFINE_CPU(type_name, initfn) \
420 .name = type_name, \
421 .parent = TYPE_RISCV_CPU, \
422 .instance_init = initfn \
425 static const TypeInfo riscv_cpu_type_infos[] = {
427 .name = TYPE_RISCV_CPU,
428 .parent = TYPE_CPU,
429 .instance_size = sizeof(RISCVCPU),
430 .instance_init = riscv_cpu_init,
431 .abstract = true,
432 .class_size = sizeof(RISCVCPUClass),
433 .class_init = riscv_cpu_class_init,
435 DEFINE_CPU(TYPE_RISCV_CPU_ANY, riscv_any_cpu_init),
436 #if defined(TARGET_RISCV32)
437 DEFINE_CPU(TYPE_RISCV_CPU_RV32GCSU_V1_09_1, rv32gcsu_priv1_09_1_cpu_init),
438 DEFINE_CPU(TYPE_RISCV_CPU_RV32GCSU_V1_10_0, rv32gcsu_priv1_10_0_cpu_init),
439 DEFINE_CPU(TYPE_RISCV_CPU_RV32IMACU_NOMMU, rv32imacu_nommu_cpu_init),
440 DEFINE_CPU(TYPE_RISCV_CPU_SIFIVE_E31, rv32imacu_nommu_cpu_init),
441 DEFINE_CPU(TYPE_RISCV_CPU_SIFIVE_U34, rv32gcsu_priv1_10_0_cpu_init)
442 #elif defined(TARGET_RISCV64)
443 DEFINE_CPU(TYPE_RISCV_CPU_RV64GCSU_V1_09_1, rv64gcsu_priv1_09_1_cpu_init),
444 DEFINE_CPU(TYPE_RISCV_CPU_RV64GCSU_V1_10_0, rv64gcsu_priv1_10_0_cpu_init),
445 DEFINE_CPU(TYPE_RISCV_CPU_RV64IMACU_NOMMU, rv64imacu_nommu_cpu_init),
446 DEFINE_CPU(TYPE_RISCV_CPU_SIFIVE_E51, rv64imacu_nommu_cpu_init),
447 DEFINE_CPU(TYPE_RISCV_CPU_SIFIVE_U54, rv64gcsu_priv1_10_0_cpu_init)
448 #endif
451 DEFINE_TYPES(riscv_cpu_type_infos)