Message ID | 20250415192515.232910-103-richard.henderson@linaro.org |
---|---|
State | New |
Headers | show |
Series | tcg: Convert to TCGOutOp structures | expand |
On 4/15/25 12:24, Richard Henderson wrote: > Use ANDI for deposit 0 into a register. > Use UBFIZ, aka UBFM, for deposit register into 0. > > Signed-off-by: Richard Henderson <richard.henderson@linaro.org> > --- > tcg/aarch64/tcg-target-con-set.h | 2 +- > tcg/aarch64/tcg-target.c.inc | 29 ++++++++++++++++++++++++++++- > 2 files changed, 29 insertions(+), 2 deletions(-) > > diff --git a/tcg/aarch64/tcg-target-con-set.h b/tcg/aarch64/tcg-target-con-set.h > index 1281e5efc0..2eda499cd3 100644 > --- a/tcg/aarch64/tcg-target-con-set.h > +++ b/tcg/aarch64/tcg-target-con-set.h > @@ -18,7 +18,6 @@ C_O1_I1(r, r) > C_O1_I1(w, r) > C_O1_I1(w, w) > C_O1_I1(w, wr) > -C_O1_I2(r, 0, rz) > C_O1_I2(r, r, r) > C_O1_I2(r, r, rA) > C_O1_I2(r, r, rAL) > @@ -26,6 +25,7 @@ C_O1_I2(r, r, rC) > C_O1_I2(r, r, ri) > C_O1_I2(r, r, rL) > C_O1_I2(r, rz, rz) > +C_O1_I2(r, rZ, rZ) > C_O1_I2(w, 0, w) > C_O1_I2(w, w, w) > C_O1_I2(w, w, wN) > diff --git a/tcg/aarch64/tcg-target.c.inc b/tcg/aarch64/tcg-target.c.inc > index 62b045c222..dee4afcce1 100644 > --- a/tcg/aarch64/tcg-target.c.inc > +++ b/tcg/aarch64/tcg-target.c.inc > @@ -2572,12 +2572,39 @@ static void tgen_deposit(TCGContext *s, TCGType type, TCGReg a0, TCGReg a1, > TCGReg a2, unsigned ofs, unsigned len) > { > unsigned mask = type == TCG_TYPE_I32 ? 31 : 63; > + > + /* > + * Since we can't support "0Z" as a constraint, we allow a1 in > + * any register. Fix things up as if a matching constraint. > + */ > + if (a0 != a1) { > + if (a0 == a2) { > + tcg_out_mov(s, type, TCG_REG_TMP0, a2); > + a2 = TCG_REG_TMP0; > + } > + tcg_out_mov(s, type, a0, a1); > + } > tcg_out_bfm(s, type, a0, a2, -ofs & mask, len - 1); > } > > +static void tgen_depositi(TCGContext *s, TCGType type, TCGReg a0, TCGReg a1, > + tcg_target_long a2, unsigned ofs, unsigned len) > +{ > + tgen_andi(s, type, a0, a1, ~MAKE_64BIT_MASK(ofs, len)); > +} > + > +static void tgen_depositz(TCGContext *s, TCGType type, TCGReg a0, TCGReg a2, > + unsigned ofs, unsigned len) > +{ > + int max = type == TCG_TYPE_I32 ? 31 : 63; > + tcg_out_ubfm(s, type, a0, a2, -ofs & max, len - 1); > +} > + > static const TCGOutOpDeposit outop_deposit = { > - .base.static_constraint = C_O1_I2(r, 0, rz), > + .base.static_constraint = C_O1_I2(r, rZ, rZ), > .out_rrr = tgen_deposit, > + .out_rri = tgen_depositi, > + .out_rzr = tgen_depositz, > }; > > static void tgen_extract(TCGContext *s, TCGType type, TCGReg a0, TCGReg a1, Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>
diff --git a/tcg/aarch64/tcg-target-con-set.h b/tcg/aarch64/tcg-target-con-set.h index 1281e5efc0..2eda499cd3 100644 --- a/tcg/aarch64/tcg-target-con-set.h +++ b/tcg/aarch64/tcg-target-con-set.h @@ -18,7 +18,6 @@ C_O1_I1(r, r) C_O1_I1(w, r) C_O1_I1(w, w) C_O1_I1(w, wr) -C_O1_I2(r, 0, rz) C_O1_I2(r, r, r) C_O1_I2(r, r, rA) C_O1_I2(r, r, rAL) @@ -26,6 +25,7 @@ C_O1_I2(r, r, rC) C_O1_I2(r, r, ri) C_O1_I2(r, r, rL) C_O1_I2(r, rz, rz) +C_O1_I2(r, rZ, rZ) C_O1_I2(w, 0, w) C_O1_I2(w, w, w) C_O1_I2(w, w, wN) diff --git a/tcg/aarch64/tcg-target.c.inc b/tcg/aarch64/tcg-target.c.inc index 62b045c222..dee4afcce1 100644 --- a/tcg/aarch64/tcg-target.c.inc +++ b/tcg/aarch64/tcg-target.c.inc @@ -2572,12 +2572,39 @@ static void tgen_deposit(TCGContext *s, TCGType type, TCGReg a0, TCGReg a1, TCGReg a2, unsigned ofs, unsigned len) { unsigned mask = type == TCG_TYPE_I32 ? 31 : 63; + + /* + * Since we can't support "0Z" as a constraint, we allow a1 in + * any register. Fix things up as if a matching constraint. + */ + if (a0 != a1) { + if (a0 == a2) { + tcg_out_mov(s, type, TCG_REG_TMP0, a2); + a2 = TCG_REG_TMP0; + } + tcg_out_mov(s, type, a0, a1); + } tcg_out_bfm(s, type, a0, a2, -ofs & mask, len - 1); } +static void tgen_depositi(TCGContext *s, TCGType type, TCGReg a0, TCGReg a1, + tcg_target_long a2, unsigned ofs, unsigned len) +{ + tgen_andi(s, type, a0, a1, ~MAKE_64BIT_MASK(ofs, len)); +} + +static void tgen_depositz(TCGContext *s, TCGType type, TCGReg a0, TCGReg a2, + unsigned ofs, unsigned len) +{ + int max = type == TCG_TYPE_I32 ? 31 : 63; + tcg_out_ubfm(s, type, a0, a2, -ofs & max, len - 1); +} + static const TCGOutOpDeposit outop_deposit = { - .base.static_constraint = C_O1_I2(r, 0, rz), + .base.static_constraint = C_O1_I2(r, rZ, rZ), .out_rrr = tgen_deposit, + .out_rri = tgen_depositi, + .out_rzr = tgen_depositz, }; static void tgen_extract(TCGContext *s, TCGType type, TCGReg a0, TCGReg a1,
Use ANDI for deposit 0 into a register. Use UBFIZ, aka UBFM, for deposit register into 0. Signed-off-by: Richard Henderson <richard.henderson@linaro.org> --- tcg/aarch64/tcg-target-con-set.h | 2 +- tcg/aarch64/tcg-target.c.inc | 29 ++++++++++++++++++++++++++++- 2 files changed, 29 insertions(+), 2 deletions(-)