On 6/27/19 7:24 PM, Mark Cave-Ayland wrote: > For the TCG_TYPE_V128 case we have ret = TCG_REG_V2 but (ret & 31) masks > off the top bit which converts this to TCG_REG_R2 and that's why > tcg_out_mem_long() starts using r2 to calculate offsets.
Oh geez. Ok, I see it now. > case TCG_TYPE_V128: > tcg_debug_assert(ret >= 32); > assert((offset & 15) == 0); > - tcg_out_mem_long(s, 0, LVX, ret & 31, base, offset); > + tcg_out_mem_long(s, 0, LVX, TCG_REG_TMP1, base, offset); No, here ret is the register into which we are loading. Same for the rest. The error is in tcg_out_mem_long in trying to reuse the output register as a scratch. > Presumably the reason this didn't break on your Power 9 box is because > the 64-bit ABI doesn't mark r2 as reserved? Correct. That and the fact that V0 and V1 get reserved as temporaries, so I didn't attempt to use r1 (i.e. sp) as a temporary. Please try the following patch on top and if it works I'll split it back into the patch set properly. r~
diff --git a/target/m68k/translate.c b/target/m68k/translate.c index 2ae537461f..b61c7ea0f1 100644 --- a/target/m68k/translate.c +++ b/target/m68k/translate.c @@ -6124,27 +6124,34 @@ static void m68k_tr_tb_stop(DisasContextBase *dcbase, CPUState *cpu) { DisasContext *dc = container_of(dcbase, DisasContext, base); - if (dc->base.is_jmp == DISAS_NORETURN) { - return; - } - if (dc->base.singlestep_enabled) { - gen_helper_raise_exception(cpu_env, tcg_const_i32(EXCP_DEBUG)); - return; - } - switch (dc->base.is_jmp) { + case DISAS_NORETURN: + break; case DISAS_TOO_MANY: update_cc_op(dc); - gen_jmp_tb(dc, 0, dc->pc); + if (dc->base.singlestep_enabled) { + tcg_gen_movi_i32(QREG_PC, dc->pc); + gen_helper_raise_exception(cpu_env, tcg_const_i32(EXCP_DEBUG)); + } else { + gen_jmp_tb(dc, 0, dc->pc); + } break; case DISAS_JUMP: /* We updated CC_OP and PC in gen_jmp/gen_jmp_im. */ - tcg_gen_lookup_and_goto_ptr(); + if (dc->base.singlestep_enabled) { + gen_helper_raise_exception(cpu_env, tcg_const_i32(EXCP_DEBUG)); + } else { + tcg_gen_lookup_and_goto_ptr(); + } break; case DISAS_EXIT: /* We updated CC_OP and PC in gen_exit_tb, but also modified other state that may require returning to the main loop. */ - tcg_gen_exit_tb(NULL, 0); + if (dc->base.singlestep_enabled) { + gen_helper_raise_exception(cpu_env, tcg_const_i32(EXCP_DEBUG)); + } else { + tcg_gen_exit_tb(NULL, 0); + } break; default: g_assert_not_reached();