Reviewed-by:  Xianglai Li <[email protected]>

For atomic instructions and LL/SC instruction pairs, the accessed
address must be aligned to the access size. Otherwise, an EXCCODE_ALE
exception is raised.

Add support for unaligned address accesses for these instructions.

Signed-off-by: Bibo Mao <[email protected]>
---
  target/loongarch/tcg/tcg_cpu.c       |  2 ++
  target/loongarch/tcg/tcg_loongarch.h |  4 ++++
  target/loongarch/tcg/tlb_helper.c    | 16 ++++++++++++++++
  3 files changed, 22 insertions(+)

diff --git a/target/loongarch/tcg/tcg_cpu.c b/target/loongarch/tcg/tcg_cpu.c
index cbf0e12c81..0549506035 100644
--- a/target/loongarch/tcg/tcg_cpu.c
+++ b/target/loongarch/tcg/tcg_cpu.c
@@ -92,6 +92,7 @@ static void loongarch_cpu_do_interrupt(CPUState *cs)
      case EXCCODE_PME:
      case EXCCODE_PNR:
      case EXCCODE_PPI:
+    case EXCCODE_ALE:
          cause = cs->exception_index;
          break;
      default:
@@ -289,5 +290,6 @@ const TCGCPUOps loongarch_tcg_ops = {
      .cpu_exec_reset = cpu_reset,
      .do_interrupt = loongarch_cpu_do_interrupt,
      .do_transaction_failed = loongarch_cpu_do_transaction_failed,
+    .do_unaligned_access = loongarch_cpu_do_unaligned_access,
  #endif
  };
diff --git a/target/loongarch/tcg/tcg_loongarch.h 
b/target/loongarch/tcg/tcg_loongarch.h
index 7fb627f2d6..9c8627972f 100644
--- a/target/loongarch/tcg/tcg_loongarch.h
+++ b/target/loongarch/tcg/tcg_loongarch.h
@@ -15,6 +15,10 @@ void loongarch_csr_translate_init(void);
  bool loongarch_cpu_tlb_fill(CPUState *cs, vaddr address, int size,
                              MMUAccessType access_type, int mmu_idx,
                              bool probe, uintptr_t retaddr);
+G_NORETURN void loongarch_cpu_do_unaligned_access(CPUState *cs, vaddr vaddr,
+                                                  MMUAccessType access_type,
+                                                  int mmu_idx,
+                                                  uintptr_t retaddr);
TLBRet loongarch_get_addr_from_tlb(CPULoongArchState *env,
                                     MMUContext *context,
diff --git a/target/loongarch/tcg/tlb_helper.c 
b/target/loongarch/tcg/tlb_helper.c
index a707de9876..5662b2c49a 100644
--- a/target/loongarch/tcg/tlb_helper.c
+++ b/target/loongarch/tcg/tlb_helper.c
@@ -706,6 +706,22 @@ bool loongarch_cpu_tlb_fill(CPUState *cs, vaddr address, 
int size,
      cpu_loop_exit_restore(cs, retaddr);
  }
+G_NORETURN void loongarch_cpu_do_unaligned_access(CPUState *cs, vaddr vaddr,
+                                                  MMUAccessType access_type,
+                                                  int mmu_idx,
+                                                  uintptr_t retaddr)
+{
+    CPULoongArchState *env = cpu_env(cs);
+    CPUSysState *sys = env_sys(env);
+
+    /*
+     * Unaligned accesses are currently triggered by atomic instructions
+     * that impose alignment requirements on memory operands.
+     */
+    sys->CSR_BADV = vaddr;
+    do_raise_exception(env, EXCCODE_ALE, retaddr);
+}
+
  static inline uint64_t loongarch_sanitize_hw_pte(CPULoongArchState *env,
                                                   uint64_t pte)
  {

base-commit: 73294d096cc591e122fde9e63db4739de6d84f2b


Reply via email to