From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from mailman by lists.gnu.org with tmda-scanned (Exim 4.43) id 1NnrGy-0007Wr-Gg for qemu-devel@nongnu.org; Sat, 06 Mar 2010 05:30:16 -0500 Received: from [199.232.76.173] (port=37832 helo=monty-python.gnu.org) by lists.gnu.org with esmtp (Exim 4.43) id 1NnrGx-0007WT-HR for qemu-devel@nongnu.org; Sat, 06 Mar 2010 05:30:15 -0500 Received: from Debian-exim by monty-python.gnu.org with spam-scanned (Exim 4.60) (envelope-from ) id 1NnrGt-00045L-V0 for qemu-devel@nongnu.org; Sat, 06 Mar 2010 05:30:15 -0500 Received: from hall.aurel32.net ([88.191.82.174]:56898) by monty-python.gnu.org with esmtps (TLS-1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.60) (envelope-from ) id 1NnrGs-00044j-St for qemu-devel@nongnu.org; Sat, 06 Mar 2010 05:30:11 -0500 Date: Sat, 6 Mar 2010 11:30:05 +0100 From: Aurelien Jarno Subject: Re: [Qemu-devel] [PATCH] tcg: add div/rem 32-bit helpers Message-ID: <20100306103005.GD5860@hall.aurel32.net> References: <1267738597-26248-1-git-send-email-aurelien@aurel32.net> MIME-Version: 1.0 Content-Type: text/plain; charset=iso-8859-15 Content-Disposition: inline In-Reply-To: Sender: Aurelien Jarno List-Id: qemu-devel.nongnu.org List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: Blue Swirl Cc: Andrzej Zaborowski , qemu-devel@nongnu.org On Sat, Mar 06, 2010 at 09:15:38AM +0200, Blue Swirl wrote: > On 3/4/10, Aurelien Jarno wrote: > > Some targets like ARM would benefit to use 32-bit helpers for > > div/rem/divu/remu. > > > > Create a #define for div2 so that targets can select between > > div, div2 and helper implementation. Use the helper version if none > > of the #define are present. > > > > Signed-off-by: Aurelien Jarno > > --- > > tcg-runtime.c | 24 +++++++++++++++++++ > > tcg/arm/tcg-target.h | 1 + > > tcg/hppa/tcg-target.h | 1 + > > tcg/i386/tcg-target.h | 1 + > > tcg/tcg-op.h | 57 +++++++++++++++++++++++++++++++++++++++++++++- > > tcg/tcg-runtime.h | 5 ++++ > > tcg/x86_64/tcg-target.h | 2 + > > 7 files changed, 89 insertions(+), 2 deletions(-) > > > > diff --git a/tcg-runtime.c b/tcg-runtime.c > > index 219cade..abfc364 100644 > > --- a/tcg-runtime.c > > +++ b/tcg-runtime.c > > @@ -25,6 +25,30 @@ > > > > #include "tcg/tcg-runtime.h" > > > > +/* 32-bit helpers */ > > + > > +int32_t tcg_helper_div_i32(int32_t arg1, int32_t arg2) > > +{ > > + return arg1 / arg2; > > +} > > + > > +int32_t tcg_helper_rem_i32(int32_t arg1, int32_t arg2) > > +{ > > + return arg1 % arg2; > > +} > > + > > +uint32_t tcg_helper_divu_i32(uint32_t arg1, uint32_t arg2) > > +{ > > + return arg1 / arg2; > > +} > > + > > +uint32_t tcg_helper_remu_i32(uint32_t arg1, uint32_t arg2) > > +{ > > + return arg1 % arg2; > > +} > > + > > +/* 64-bit helpers */ > > + > > int64_t tcg_helper_shl_i64(int64_t arg1, int64_t arg2) > > { > > return arg1 << arg2; > > diff --git a/tcg/arm/tcg-target.h b/tcg/arm/tcg-target.h > > index 4cad967..4b2b0be 100644 > > --- a/tcg/arm/tcg-target.h > > +++ b/tcg/arm/tcg-target.h > > @@ -56,6 +56,7 @@ enum { > > #define TCG_TARGET_CALL_STACK_OFFSET 0 > > > > /* optional instructions */ > > +#define TCG_TARGET_HAS_div2_i32 > > Please also add commented out #defines for targets that do not > implement div2 yet. I don't really see the point. The targets should implement either div/rem or div2, depending on their instruction set. Implementing div2 on a targets which have separate instructions to compute div and rem will impact the performances negatively. > > #define TCG_TARGET_HAS_ext8s_i32 > > #define TCG_TARGET_HAS_ext16s_i32 > > // #define TCG_TARGET_HAS_ext8u_i32 > > diff --git a/tcg/hppa/tcg-target.h b/tcg/hppa/tcg-target.h > > index 7ab6f0c..fa39bfc 100644 > > --- a/tcg/hppa/tcg-target.h > > +++ b/tcg/hppa/tcg-target.h > > @@ -75,6 +75,7 @@ enum { > > #define TCG_TARGET_STACK_GROWSUP > > > > /* optional instructions */ > > +#define TCG_TARGET_HAS_div2_i32 > > //#define TCG_TARGET_HAS_ext8s_i32 > > //#define TCG_TARGET_HAS_ext16s_i32 > > //#define TCG_TARGET_HAS_bswap16_i32 > > diff --git a/tcg/i386/tcg-target.h b/tcg/i386/tcg-target.h > > index f97034c..e994fd5 100644 > > --- a/tcg/i386/tcg-target.h > > +++ b/tcg/i386/tcg-target.h > > @@ -45,6 +45,7 @@ enum { > > #define TCG_TARGET_CALL_STACK_OFFSET 0 > > > > /* optional instructions */ > > +#define TCG_TARGET_HAS_div2_i32 > > #define TCG_TARGET_HAS_rot_i32 > > #define TCG_TARGET_HAS_ext8s_i32 > > #define TCG_TARGET_HAS_ext16s_i32 > > diff --git a/tcg/tcg-op.h b/tcg/tcg-op.h > > index 6ae1760..c71e1a8 100644 > > --- a/tcg/tcg-op.h > > +++ b/tcg/tcg-op.h > > @@ -365,6 +365,19 @@ static inline void tcg_gen_helperN(void *func, int flags, int sizemask, > > } > > > > /* FIXME: Should this be pure? */ > > +static inline void tcg_gen_helper32(void *func, TCGv_i32 ret, > > + TCGv_i32 a, TCGv_i32 b) > > +{ > > + TCGv_ptr fn; > > + TCGArg args[2]; > > + fn = tcg_const_ptr((tcg_target_long)func); > > + args[0] = GET_TCGV_I32(a); > > + args[1] = GET_TCGV_I32(b); > > + tcg_gen_callN(&tcg_ctx, fn, 0, 0, GET_TCGV_I32(ret), 2, args); > > + tcg_temp_free_ptr(fn); > > +} > > + > > +/* FIXME: Should this be pure? */ > > static inline void tcg_gen_helper64(void *func, TCGv_i64 ret, > > TCGv_i64 a, TCGv_i64 b) > > { > > @@ -635,7 +648,7 @@ static inline void tcg_gen_remu_i32(TCGv_i32 ret, TCGv_i32 arg1, TCGv_i32 arg2) > > { > > tcg_gen_op3_i32(INDEX_op_remu_i32, ret, arg1, arg2); > > } > > -#else > > +#elif defined(TCG_TARGET_HAS_div2_i32) > > static inline void tcg_gen_div_i32(TCGv_i32 ret, TCGv_i32 arg1, TCGv_i32 arg2) > > { > > TCGv_i32 t0; > > @@ -671,6 +684,26 @@ static inline void tcg_gen_remu_i32(TCGv_i32 ret, TCGv_i32 arg1, TCGv_i32 arg2) > > tcg_gen_op5_i32(INDEX_op_divu2_i32, t0, ret, arg1, t0, arg2); > > tcg_temp_free_i32(t0); > > } > > +#else > > +static inline void tcg_gen_div_i32(TCGv_i32 ret, TCGv_i32 arg1, TCGv_i32 arg2) > > +{ > > + tcg_gen_helper32(tcg_helper_div_i32, ret, arg1, arg2); > > +} > > + > > +static inline void tcg_gen_rem_i32(TCGv_i32 ret, TCGv_i32 arg1, TCGv_i32 arg2) > > +{ > > + tcg_gen_helper32(tcg_helper_rem_i32, ret, arg1, arg2); > > +} > > + > > +static inline void tcg_gen_divu_i32(TCGv_i32 ret, TCGv_i32 arg1, TCGv_i32 arg2) > > +{ > > + tcg_gen_helper32(tcg_helper_divu_i32, ret, arg1, arg2); > > +} > > + > > +static inline void tcg_gen_remu_i32(TCGv_i32 ret, TCGv_i32 arg1, TCGv_i32 arg2) > > +{ > > + tcg_gen_helper32(tcg_helper_remu_i32, ret, arg1, arg2); > > +} > > #endif > > > > #if TCG_TARGET_REG_BITS == 32 > > @@ -1135,7 +1168,7 @@ static inline void tcg_gen_remu_i64(TCGv_i64 ret, TCGv_i64 arg1, TCGv_i64 arg2) > > { > > tcg_gen_op3_i64(INDEX_op_remu_i64, ret, arg1, arg2); > > } > > -#else > > +#elif defined(TCG_TARGET_HAS_div2_i64) > > static inline void tcg_gen_div_i64(TCGv_i64 ret, TCGv_i64 arg1, TCGv_i64 arg2) > > { > > TCGv_i64 t0; > > @@ -1171,6 +1204,26 @@ static inline void tcg_gen_remu_i64(TCGv_i64 ret, TCGv_i64 arg1, TCGv_i64 arg2) > > tcg_gen_op5_i64(INDEX_op_divu2_i64, t0, ret, arg1, t0, arg2); > > tcg_temp_free_i64(t0); > > } > > +#else > > +static inline void tcg_gen_div_i64(TCGv_i64 ret, TCGv_i64 arg1, TCGv_i64 arg2) > > +{ > > + tcg_gen_helper64(tcg_helper_div_i64, ret, arg1, arg2); > > +} > > + > > +static inline void tcg_gen_rem_i64(TCGv_i64 ret, TCGv_i64 arg1, TCGv_i64 arg2) > > +{ > > + tcg_gen_helper64(tcg_helper_rem_i64, ret, arg1, arg2); > > +} > > + > > +static inline void tcg_gen_divu_i64(TCGv_i64 ret, TCGv_i64 arg1, TCGv_i64 arg2) > > +{ > > + tcg_gen_helper64(tcg_helper_divu_i64, ret, arg1, arg2); > > +} > > + > > +static inline void tcg_gen_remu_i64(TCGv_i64 ret, TCGv_i64 arg1, TCGv_i64 arg2) > > +{ > > + tcg_gen_helper64(tcg_helper_remu_i64, ret, arg1, arg2); > > +} > > #endif > > > > #endif > > diff --git a/tcg/tcg-runtime.h b/tcg/tcg-runtime.h > > index e750cc1..5615b13 100644 > > --- a/tcg/tcg-runtime.h > > +++ b/tcg/tcg-runtime.h > > @@ -2,6 +2,11 @@ > > #define TCG_RUNTIME_H > > > > /* tcg-runtime.c */ > > +int32_t tcg_helper_div_i32(int32_t arg1, int32_t arg2); > > +int32_t tcg_helper_rem_i32(int32_t arg1, int32_t arg2); > > +uint32_t tcg_helper_divu_i32(uint32_t arg1, uint32_t arg2); > > +uint32_t tcg_helper_remu_i32(uint32_t arg1, uint32_t arg2); > > + > > int64_t tcg_helper_shl_i64(int64_t arg1, int64_t arg2); > > int64_t tcg_helper_shr_i64(int64_t arg1, int64_t arg2); > > int64_t tcg_helper_sar_i64(int64_t arg1, int64_t arg2); > > diff --git a/tcg/x86_64/tcg-target.h b/tcg/x86_64/tcg-target.h > > index 765f0b4..d1e8b9e 100644 > > --- a/tcg/x86_64/tcg-target.h > > +++ b/tcg/x86_64/tcg-target.h > > @@ -56,6 +56,8 @@ enum { > > #define TCG_TARGET_CALL_STACK_OFFSET 0 > > > > /* optional instructions */ > > +#define TCG_TARGET_HAS_div2_i32 > > +#define TCG_TARGET_HAS_div2_i64 > > #define TCG_TARGET_HAS_bswap16_i32 > > #define TCG_TARGET_HAS_bswap16_i64 > > #define TCG_TARGET_HAS_bswap32_i32 > > > > -- > > 1.7.0 > > > > > > > > > > > -- Aurelien Jarno GPG: 1024D/F1BCDB73 aurelien@aurel32.net http://www.aurel32.net