mirror of https://github.com/xemu-project/xemu.git
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. Cc: Leon Alrae <leon.alrae@imgtec.com> Reported-by: Hervé Poussineau <hpoussin@reactos.org> Tested-by: Hervé Poussineau <hpoussin@reactos.org> Signed-off-by: Aurelien Jarno <aurelien@aurel32.net> Signed-off-by: Leon Alrae <leon.alrae@imgtec.com>
This commit is contained in:
parent
f01a361bfc
commit
908680c644
|
@ -2142,6 +2142,9 @@ static void gen_ld(DisasContext *ctx, uint32_t opc,
|
|||
break;
|
||||
case OPC_LDL:
|
||||
t1 = tcg_temp_new();
|
||||
/* Do a byte access to possibly trigger a page
|
||||
fault with the unaligned address. */
|
||||
tcg_gen_qemu_ld_tl(t1, t0, ctx->mem_idx, MO_UB);
|
||||
tcg_gen_andi_tl(t1, t0, 7);
|
||||
#ifndef TARGET_WORDS_BIGENDIAN
|
||||
tcg_gen_xori_tl(t1, t1, 7);
|
||||
|
@ -2163,6 +2166,9 @@ static void gen_ld(DisasContext *ctx, uint32_t opc,
|
|||
break;
|
||||
case OPC_LDR:
|
||||
t1 = tcg_temp_new();
|
||||
/* Do a byte access to possibly trigger a page
|
||||
fault with the unaligned address. */
|
||||
tcg_gen_qemu_ld_tl(t1, t0, ctx->mem_idx, MO_UB);
|
||||
tcg_gen_andi_tl(t1, t0, 7);
|
||||
#ifdef TARGET_WORDS_BIGENDIAN
|
||||
tcg_gen_xori_tl(t1, t1, 7);
|
||||
|
@ -2229,6 +2235,9 @@ static void gen_ld(DisasContext *ctx, uint32_t opc,
|
|||
break;
|
||||
case OPC_LWL:
|
||||
t1 = tcg_temp_new();
|
||||
/* Do a byte access to possibly trigger a page
|
||||
fault with the unaligned address. */
|
||||
tcg_gen_qemu_ld_tl(t1, t0, ctx->mem_idx, MO_UB);
|
||||
tcg_gen_andi_tl(t1, t0, 3);
|
||||
#ifndef TARGET_WORDS_BIGENDIAN
|
||||
tcg_gen_xori_tl(t1, t1, 3);
|
||||
|
@ -2251,6 +2260,9 @@ static void gen_ld(DisasContext *ctx, uint32_t opc,
|
|||
break;
|
||||
case OPC_LWR:
|
||||
t1 = tcg_temp_new();
|
||||
/* Do a byte access to possibly trigger a page
|
||||
fault with the unaligned address. */
|
||||
tcg_gen_qemu_ld_tl(t1, t0, ctx->mem_idx, MO_UB);
|
||||
tcg_gen_andi_tl(t1, t0, 3);
|
||||
#ifdef TARGET_WORDS_BIGENDIAN
|
||||
tcg_gen_xori_tl(t1, t1, 3);
|
||||
|
|
Loading…
Reference in New Issue