diff --git a/qemu/target/arm/translate-a64.c b/qemu/target/arm/translate-a64.c index a83c78d4..dd6a0c83 100644 --- a/qemu/target/arm/translate-a64.c +++ b/qemu/target/arm/translate-a64.c @@ -647,6 +647,15 @@ static TCGv_i32 read_fp_sreg(DisasContext *s, int reg) return v; } +static TCGv_i32 read_fp_hreg(DisasContext *s, int reg) +{ + TCGContext *tcg_ctx = s->uc->tcg_ctx; + TCGv_i32 v = tcg_temp_new_i32(tcg_ctx); + + tcg_gen_ld16u_i32(tcg_ctx, v, tcg_ctx->cpu_env, fp_reg_offset(s, reg, MO_16)); + return v; +} + /* Clear the bits above an N-bit vector, for N = (is_q ? 128 : 64). * If SVE is not enabled, then there are only 128 bits in the vector. */ @@ -4973,11 +4982,9 @@ static void handle_fp_1src_half(DisasContext *s, int opcode, int rd, int rn) { TCGContext *tcg_ctx = s->uc->tcg_ctx; TCGv_ptr fpst = NULL; - TCGv_i32 tcg_op = tcg_temp_new_i32(tcg_ctx); + TCGv_i32 tcg_op = read_fp_hreg(s, rn); TCGv_i32 tcg_res = tcg_temp_new_i32(tcg_ctx); - read_vec_element_i32(s, tcg_op, rn, 0, MO_16); - switch (opcode) { case 0x0: /* FMOV */ tcg_gen_mov_i32(tcg_ctx, tcg_res, tcg_op); @@ -7908,13 +7915,10 @@ static void disas_simd_scalar_three_reg_diff(DisasContext *s, uint32_t insn) tcg_temp_free_i64(tcg_ctx, tcg_op2); tcg_temp_free_i64(tcg_ctx, tcg_res); } else { - TCGv_i32 tcg_op1 = tcg_temp_new_i32(tcg_ctx); - TCGv_i32 tcg_op2 = tcg_temp_new_i32(tcg_ctx); + TCGv_i32 tcg_op1 = read_fp_hreg(s, rn); + TCGv_i32 tcg_op2 = read_fp_hreg(s, rm); TCGv_i64 tcg_res = tcg_temp_new_i64(tcg_ctx); - read_vec_element_i32(s, tcg_op1, rn, 0, MO_16); - read_vec_element_i32(s, tcg_op2, rm, 0, MO_16); - gen_helper_neon_mull_s16(tcg_ctx, tcg_res, tcg_op1, tcg_op2); gen_helper_neon_addl_saturate_s32(tcg_ctx, tcg_res, tcg_ctx->cpu_env, tcg_res, tcg_res); @@ -8459,13 +8463,10 @@ static void disas_simd_scalar_three_reg_same_fp16(DisasContext *s, fpst = get_fpstatus_ptr(tcg_ctx, true); - tcg_op1 = tcg_temp_new_i32(tcg_ctx); - tcg_op2 = tcg_temp_new_i32(tcg_ctx); + tcg_op1 = read_fp_hreg(s, rn); + tcg_op2 = read_fp_hreg(s, rm); tcg_res = tcg_temp_new_i32(tcg_ctx); - read_vec_element_i32(s, tcg_op1, rn, 0, MO_16); - read_vec_element_i32(s, tcg_op2, rm, 0, MO_16); - switch (fpopcode) { case 0x03: /* FMULX */ gen_helper_advsimd_mulxh(tcg_ctx, tcg_res, tcg_op1, tcg_op2, fpst); @@ -12389,11 +12390,9 @@ static void disas_simd_two_reg_misc_fp16(DisasContext *s, uint32_t insn) } if (is_scalar) { - TCGv_i32 tcg_op = tcg_temp_new_i32(tcg_ctx); + TCGv_i32 tcg_op = read_fp_hreg(s, rn); TCGv_i32 tcg_res = tcg_temp_new_i32(tcg_ctx); - read_vec_element_i32(s, tcg_op, rn, 0, MO_16); - switch (fpop) { case 0x1a: /* FCVTNS */ case 0x1b: /* FCVTMS */