Message ID | 20171004184325.24157-8-richard.henderson@linaro.org |
---|---|
State | Superseded |
Headers | show |
Series | ARM v8.1 simd + v8.3 complex insns | expand |
Richard Henderson <richard.henderson@linaro.org> writes: > Signed-off-by: Richard Henderson <richard.henderson@linaro.org> > --- > target/arm/translate.c | 36 ++++++++++++++++++++++++++++++++++-- > 1 file changed, 34 insertions(+), 2 deletions(-) > > diff --git a/target/arm/translate.c b/target/arm/translate.c > index 0cd58710b3..ee1e364fb5 100644 > --- a/target/arm/translate.c > +++ b/target/arm/translate.c > @@ -6941,10 +6941,42 @@ static int disas_neon_data_insn(DisasContext *s, uint32_t insn) > } > neon_store_reg64(cpu_V0, rd + pass); > } > + break; > + case 14: /* VQRDMLAH scalar */ > + case 15: /* VQRDMLSH scalar */ > + if (!arm_dc_feature(s, ARM_FEATURE_V8_1_SIMD)) { > + return 1; > + } > + if (u && ((rd | rn) & 1)) { > + return 1; > + } > + tmp2 = neon_get_scalar(size, rm); > + for (pass = 0; pass < (u ? 4 : 2); pass++) { > + void (*fn)(TCGv_i32, TCGv_env, TCGv_i32, > + TCGv_i32, TCGv_i32); > > - > + tmp = neon_load_reg(rn, pass); > + tmp3 = neon_load_reg(rd, pass); > + if (op == 14) { > + if (size == 1) { > + fn = gen_helper_neon_qrdmlah_s16; > + } else { > + fn = gen_helper_neon_qrdmlah_s32; > + } > + } else { > + if (size == 1) { > + fn = gen_helper_neon_qrdmlsh_s16; > + } else { > + fn = gen_helper_neon_qrdmlsh_s32; > + } > + } > + fn(tmp, cpu_env, tmp, tmp2, tmp3); > + tcg_temp_free_i32(tmp3); > + neon_store_reg(rd, pass, tmp); > + } > + tcg_temp_free_i32(tmp2); > break; > - default: /* 14 and 15 are RESERVED */ > + default: > return 1; I think this should now be g_assert_not_reached() as we decode the whole op space. That said it's tricky to follow in the mega function that extracts op with old-school shifts 5 different ways :-/ > } > } -- Alex Bennée
On 11/13/2017 06:05 PM, Alex Bennée wrote: >> - default: /* 14 and 15 are RESERVED */ >> + default: >> return 1; > > I think this should now be g_assert_not_reached() as we decode the whole > op space. That said it's tricky to follow in the mega function that > extracts op with old-school shifts 5 different ways :-/ You're right. Thanks. r~
diff --git a/target/arm/translate.c b/target/arm/translate.c index 0cd58710b3..ee1e364fb5 100644 --- a/target/arm/translate.c +++ b/target/arm/translate.c @@ -6941,10 +6941,42 @@ static int disas_neon_data_insn(DisasContext *s, uint32_t insn) } neon_store_reg64(cpu_V0, rd + pass); } + break; + case 14: /* VQRDMLAH scalar */ + case 15: /* VQRDMLSH scalar */ + if (!arm_dc_feature(s, ARM_FEATURE_V8_1_SIMD)) { + return 1; + } + if (u && ((rd | rn) & 1)) { + return 1; + } + tmp2 = neon_get_scalar(size, rm); + for (pass = 0; pass < (u ? 4 : 2); pass++) { + void (*fn)(TCGv_i32, TCGv_env, TCGv_i32, + TCGv_i32, TCGv_i32); - + tmp = neon_load_reg(rn, pass); + tmp3 = neon_load_reg(rd, pass); + if (op == 14) { + if (size == 1) { + fn = gen_helper_neon_qrdmlah_s16; + } else { + fn = gen_helper_neon_qrdmlah_s32; + } + } else { + if (size == 1) { + fn = gen_helper_neon_qrdmlsh_s16; + } else { + fn = gen_helper_neon_qrdmlsh_s32; + } + } + fn(tmp, cpu_env, tmp, tmp2, tmp3); + tcg_temp_free_i32(tmp3); + neon_store_reg(rd, pass, tmp); + } + tcg_temp_free_i32(tmp2); break; - default: /* 14 and 15 are RESERVED */ + default: return 1; } }
Signed-off-by: Richard Henderson <richard.henderson@linaro.org> --- target/arm/translate.c | 36 ++++++++++++++++++++++++++++++++++-- 1 file changed, 34 insertions(+), 2 deletions(-) -- 2.13.6