From 3cc6b5251ebba8c26f44c6747b641bdb2181d6f7 Mon Sep 17 00:00:00 2001 From: Aurelien Jarno Date: Wed, 14 Feb 2018 17:04:29 -0500 Subject: [PATCH] target-mips: fix page fault address for LWL/LWR/LDL/LDR When a LWL, LWR, LDL or LDR instruction triggers a page fault, QEMU currently reports the aligned address in CP0 BadVAddr, while the Windows NT kernel expects the unaligned address. This patch adds a byte access with the unaligned address at the beginning of the LWL/LWR/LDL/LDR instructions to possibly trigger a page fault and fill the QEMU TLB. Backports commit 908680c6441ac468f4871d513f42be396ea0d264 from qemu --- qemu/target-mips/translate.c | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/qemu/target-mips/translate.c b/qemu/target-mips/translate.c index eb6f47b6..536144b6 100644 --- a/qemu/target-mips/translate.c +++ b/qemu/target-mips/translate.c @@ -2149,6 +2149,9 @@ static void gen_ld(DisasContext *ctx, uint32_t opc, break; case OPC_LDL: t1 = tcg_temp_new(tcg_ctx); + /* Do a byte access to possibly trigger a page + fault with the unaligned address. */ + tcg_gen_qemu_ld_tl(ctx->uc, t1, t0, ctx->mem_idx, MO_UB); tcg_gen_andi_tl(tcg_ctx, t1, t0, 7); #ifndef TARGET_WORDS_BIGENDIAN tcg_gen_xori_tl(tcg_ctx, t1, t1, 7); @@ -2170,6 +2173,9 @@ static void gen_ld(DisasContext *ctx, uint32_t opc, break; case OPC_LDR: t1 = tcg_temp_new(tcg_ctx); + /* Do a byte access to possibly trigger a page + fault with the unaligned address. */ + tcg_gen_qemu_ld_tl(ctx->uc, t1, t0, ctx->mem_idx, MO_UB); tcg_gen_andi_tl(tcg_ctx, t1, t0, 7); #ifdef TARGET_WORDS_BIGENDIAN tcg_gen_xori_tl(tcg_ctx, t1, t1, 7); @@ -2236,6 +2242,9 @@ static void gen_ld(DisasContext *ctx, uint32_t opc, break; case OPC_LWL: t1 = tcg_temp_new(tcg_ctx); + /* Do a byte access to possibly trigger a page + fault with the unaligned address. */ + tcg_gen_qemu_ld_tl(ctx->uc, t1, t0, ctx->mem_idx, MO_UB); tcg_gen_andi_tl(tcg_ctx, t1, t0, 3); #ifndef TARGET_WORDS_BIGENDIAN tcg_gen_xori_tl(tcg_ctx, t1, t1, 3); @@ -2258,6 +2267,9 @@ static void gen_ld(DisasContext *ctx, uint32_t opc, break; case OPC_LWR: t1 = tcg_temp_new(tcg_ctx); + /* Do a byte access to possibly trigger a page + fault with the unaligned address. */ + tcg_gen_qemu_ld_tl(ctx->uc, t1, t0, ctx->mem_idx, MO_UB); tcg_gen_andi_tl(tcg_ctx, t1, t0, 3); #ifdef TARGET_WORDS_BIGENDIAN tcg_gen_xori_tl(tcg_ctx, t1, t1, 3);