@@ -92,6 +92,13 @@ void cpu_loop(CPURISCVState *env)
sigcode = TARGET_SEGV_MAPERR;
sigaddr = env->badaddr;
break;
+ case RISCV_EXCP_INST_ADDR_MIS:
+ case RISCV_EXCP_LOAD_ADDR_MIS:
+ case RISCV_EXCP_STORE_AMO_ADDR_MIS:
+ signum = TARGET_SIGBUS;
+ sigcode = TARGET_BUS_ADRALN;
+ sigaddr = env->badaddr;
+ break;
case RISCV_EXCP_SEMIHOST:
env->gpr[xA0] = do_common_semihosting(cs);
env->pc += 4;
@@ -644,11 +644,11 @@ static const struct TCGCPUOps riscv_tcg_ops = {
.synchronize_from_tb = riscv_cpu_synchronize_from_tb,
.cpu_exec_interrupt = riscv_cpu_exec_interrupt,
.tlb_fill = riscv_cpu_tlb_fill,
+ .do_unaligned_access = riscv_cpu_do_unaligned_access,
#ifndef CONFIG_USER_ONLY
.do_interrupt = riscv_cpu_do_interrupt,
.do_transaction_failed = riscv_cpu_do_transaction_failed,
- .do_unaligned_access = riscv_cpu_do_unaligned_access,
#endif /* !CONFIG_USER_ONLY */
};
@@ -727,6 +727,7 @@ void riscv_cpu_do_transaction_failed(CPUState *cs, hwaddr physaddr,
riscv_cpu_two_stage_lookup(mmu_idx);
riscv_raise_exception(&cpu->env, cs->exception_index, retaddr);
}
+#endif /* !CONFIG_USER_ONLY */
void riscv_cpu_do_unaligned_access(CPUState *cs, vaddr addr,
MMUAccessType access_type, int mmu_idx,
@@ -734,6 +735,7 @@ void riscv_cpu_do_unaligned_access(CPUState *cs, vaddr addr,
{
RISCVCPU *cpu = RISCV_CPU(cs);
CPURISCVState *env = &cpu->env;
+
switch (access_type) {
case MMU_INST_FETCH:
cs->exception_index = RISCV_EXCP_INST_ADDR_MIS;
@@ -748,11 +750,15 @@ void riscv_cpu_do_unaligned_access(CPUState *cs, vaddr addr,
g_assert_not_reached();
}
env->badaddr = addr;
+
+#ifdef CONFIG_USER_ONLY
+ cpu_loop_exit_restore(cs, retaddr);
+#else
env->two_stage_lookup = riscv_cpu_virt_enabled(env) ||
riscv_cpu_two_stage_lookup(mmu_idx);
riscv_raise_exception(env, cs->exception_index, retaddr);
+#endif
}
-#endif /* !CONFIG_USER_ONLY */
bool riscv_cpu_tlb_fill(CPUState *cs, vaddr address, int size,
MMUAccessType access_type, int mmu_idx,