CVSROOT: /sources/qemu Module name: qemu Changes by: Fabrice Bellard <bellard> 06/06/21 18:37:05
Modified files: . : configure target-sparc : cpu.h op.c op_helper.c Log message: soft floats for SPARC (Blue Swirl) CVSWeb URLs: http://cvs.savannah.gnu.org/viewcvs/qemu/configure?cvsroot=qemu&r1=1.108&r2=1.109 http://cvs.savannah.gnu.org/viewcvs/qemu/target-sparc/cpu.h?cvsroot=qemu&r1=1.21&r2=1.22 http://cvs.savannah.gnu.org/viewcvs/qemu/target-sparc/op.c?cvsroot=qemu&r1=1.19&r2=1.20 http://cvs.savannah.gnu.org/viewcvs/qemu/target-sparc/op_helper.c?cvsroot=qemu&r1=1.19&r2=1.20 Patches: Index: configure =================================================================== RCS file: /sources/qemu/qemu/configure,v retrieving revision 1.108 retrieving revision 1.109 diff -u -b -r1.108 -r1.109 --- configure 18 Jun 2006 19:16:53 -0000 1.108 +++ configure 21 Jun 2006 18:37:05 -0000 1.109 @@ -850,7 +850,7 @@ echo "#define CONFIG_USER_ONLY 1" >> $config_h fi -if test "$target_cpu" = "arm" -o "$target_cpu" = "armeb" ; then +if test "$target_cpu" = "arm" -o "$target_cpu" = "armeb" -o "$target_cpu" = "sparc" -o "$target_cpu" = "sparc64"; then echo "CONFIG_SOFTFLOAT=yes" >> $config_mak echo "#define CONFIG_SOFTFLOAT 1" >> $config_h fi Index: target-sparc/cpu.h =================================================================== RCS file: /sources/qemu/qemu/target-sparc/cpu.h,v retrieving revision 1.21 retrieving revision 1.22 diff -u -b -r1.21 -r1.22 --- target-sparc/cpu.h 5 Dec 2005 20:31:52 -0000 1.21 +++ target-sparc/cpu.h 21 Jun 2006 18:37:05 -0000 1.22 @@ -12,7 +12,7 @@ #define TARGET_FPREGS 64 #define TARGET_PAGE_BITS 12 /* XXX */ #endif -#define TARGET_FPREG_T float +#define TARGET_FPREG_T float32 #include "cpu-defs.h" @@ -146,7 +146,7 @@ typedef struct CPUSPARCState { target_ulong gregs[8]; /* general registers */ target_ulong *regwptr; /* pointer to current register window */ - TARGET_FPREG_T fpr[TARGET_FPREGS]; /* floating point registers */ + float32 fpr[TARGET_FPREGS]; /* floating point registers */ target_ulong pc; /* program counter */ target_ulong npc; /* next program counter */ target_ulong y; /* multiply/divide register */ @@ -187,8 +187,8 @@ uint32_t mmuregs[16]; #endif /* temporary float registers */ - float ft0, ft1; - double dt0, dt1; + float32 ft0, ft1; + float64 dt0, dt1; float_status fp_status; #if defined(TARGET_SPARC64) #define MAXTL 4 @@ -236,8 +236,6 @@ CPUSPARCState *cpu_sparc_init(void); int cpu_sparc_exec(CPUSPARCState *s); int cpu_sparc_close(CPUSPARCState *s); -void cpu_get_fp64(uint64_t *pmant, uint16_t *pexp, double f); -double cpu_put_fp64(uint64_t mant, uint16_t exp); /* Fake impl 0, version 4 */ #define GET_PSR(env) ((0 << 28) | (4 << 24) | (env->psr & PSR_ICC) | \ Index: target-sparc/op.c =================================================================== RCS file: /sources/qemu/qemu/target-sparc/op.c,v retrieving revision 1.19 retrieving revision 1.20 diff -u -b -r1.19 -r1.20 --- target-sparc/op.c 23 Apr 2006 21:33:48 -0000 1.19 +++ target-sparc/op.c 21 Jun 2006 18:37:05 -0000 1.20 @@ -1339,94 +1339,66 @@ helper_flush(T0); } -void OPPROTO op_fnegs(void) -{ - FT0 = -FT1; -} - -void OPPROTO op_fabss(void) -{ - do_fabss(); -} +#define F_OP(name, p) void OPPROTO op_f##name##p(void) -#ifdef TARGET_SPARC64 -void OPPROTO op_fnegd(void) -{ - DT0 = -DT1; -} - -void OPPROTO op_fabsd(void) -{ - do_fabsd(); -} -#endif - -void OPPROTO op_fsqrts(void) -{ - do_fsqrts(); -} - -void OPPROTO op_fsqrtd(void) -{ - do_fsqrtd(); -} - -void OPPROTO op_fmuls(void) -{ - FT0 *= FT1; -} +#define F_BINOP(name) \ + F_OP(name, s) \ + { \ + FT0 = float32_ ## name (FT0, FT1, &env->fp_status); \ + } \ + F_OP(name, d) \ + { \ + DT0 = float64_ ## name (DT0, DT1, &env->fp_status); \ + } -void OPPROTO op_fmuld(void) -{ - DT0 *= DT1; -} +F_BINOP(add); +F_BINOP(sub); +F_BINOP(mul); +F_BINOP(div); +#undef F_BINOP void OPPROTO op_fsmuld(void) { - DT0 = FT0 * FT1; -} - -void OPPROTO op_fadds(void) -{ - FT0 += FT1; + DT0 = float64_mul(float32_to_float64(FT0, &env->fp_status), + float32_to_float64(FT1, &env->fp_status), + &env->fp_status); } -void OPPROTO op_faddd(void) -{ - DT0 += DT1; -} +#define F_HELPER(name) \ + F_OP(name, s) \ + { \ + do_f##name##s(); \ + } \ + F_OP(name, d) \ + { \ + do_f##name##d(); \ + } -void OPPROTO op_fsubs(void) -{ - FT0 -= FT1; -} +F_HELPER(sqrt); -void OPPROTO op_fsubd(void) +F_OP(neg, s) { - DT0 -= DT1; + FT0 = float32_chs(FT1); } -void OPPROTO op_fdivs(void) +F_OP(abs, s) { - FT0 /= FT1; + do_fabss(); } -void OPPROTO op_fdivd(void) -{ - DT0 /= DT1; -} +F_HELPER(cmp); -void OPPROTO op_fcmps(void) +#ifdef TARGET_SPARC64 +F_OP(neg, d) { - do_fcmps(); + DT0 = float64_chs(DT1); } -void OPPROTO op_fcmpd(void) +F_OP(abs, d) { - do_fcmpd(); + do_fabsd(); } -#ifdef TARGET_SPARC64 void OPPROTO op_fcmps_fcc1(void) { do_fcmps_fcc1(); @@ -1458,69 +1430,65 @@ } #endif +/* Integer to float conversion. */ #ifdef USE_INT_TO_FLOAT_HELPERS -void OPPROTO op_fitos(void) -{ - do_fitos(); -} - -void OPPROTO op_fitod(void) -{ - do_fitod(); -} +F_HELPER(ito); #else -void OPPROTO op_fitos(void) +F_OP(ito, s) { - FT0 = (float) *((int32_t *)&FT1); + FT0 = int32_to_float32(*((int32_t *)&FT1), &env->fp_status); } -void OPPROTO op_fitod(void) +F_OP(ito, d) { - DT0 = (double) *((int32_t *)&FT1); + DT0 = int32_to_float64(*((int32_t *)&FT1), &env->fp_status); } #ifdef TARGET_SPARC64 -void OPPROTO op_fxtos(void) +F_OP(xto, s) { - FT0 = (float) *((int64_t *)&DT1); + FT0 = int64_to_float32(*((int64_t *)&DT1), &env->fp_status); } -void OPPROTO op_fxtod(void) +F_OP(xto, d) { - DT0 = (double) *((int64_t *)&DT1); + DT0 = int64_to_float64(*((int64_t *)&DT1), &env->fp_status); } #endif #endif +#undef F_HELPER +/* floating point conversion */ void OPPROTO op_fdtos(void) { - FT0 = (float) DT1; + FT0 = float64_to_float32(DT1, &env->fp_status); } void OPPROTO op_fstod(void) { - DT0 = (double) FT1; + DT0 = float32_to_float64(FT1, &env->fp_status); } +/* Float to integer conversion. */ void OPPROTO op_fstoi(void) { - *((int32_t *)&FT0) = (int32_t) FT1; + *((int32_t *)&FT0) = float32_to_int32(FT1, &env->fp_status); } void OPPROTO op_fdtoi(void) { - *((int32_t *)&FT0) = (int32_t) DT1; + *((int32_t *)&FT0) = float64_to_int32(DT1, &env->fp_status); } #ifdef TARGET_SPARC64 void OPPROTO op_fstox(void) { - *((int64_t *)&DT0) = (int64_t) FT1; + *((int64_t *)&DT0) = float32_to_int64(FT1, &env->fp_status); } void OPPROTO op_fdtox(void) { - *((int64_t *)&DT0) = (int64_t) DT1; + *((int64_t *)&DT0) = float64_to_int64(DT1, &env->fp_status); } void OPPROTO op_fmovs_cc(void) Index: target-sparc/op_helper.c =================================================================== RCS file: /sources/qemu/qemu/target-sparc/op_helper.c,v retrieving revision 1.19 retrieving revision 1.20 diff -u -b -r1.19 -r1.20 --- target-sparc/op_helper.c 21 Nov 2005 23:32:42 -0000 1.19 +++ target-sparc/op_helper.c 21 Jun 2006 18:37:05 -0000 1.20 @@ -12,12 +12,12 @@ #ifdef USE_INT_TO_FLOAT_HELPERS void do_fitos(void) { - FT0 = (float) *((int32_t *)&FT1); + FT0 = int32_to_float32(*((int32_t *)&FT1)); } void do_fitod(void) { - DT0 = (double) *((int32_t *)&FT1); + DT0 = int32_to_float64(*((int32_t *)&FT1)); } #endif @@ -43,182 +43,45 @@ DT0 = float64_sqrt(DT1, &env->fp_status); } -#define FS 0 -void do_fcmps (void) -{ - env->fsr &= ~((FSR_FCC1 | FSR_FCC0) << FS); - if (isnan(FT0) || isnan(FT1)) { - T0 = (FSR_FCC1 | FSR_FCC0) << FS; - if (env->fsr & FSR_NVM) { - env->fsr |= T0; - raise_exception(TT_FP_EXCP); - } else { - env->fsr |= FSR_NVA; - } - } else if (FT0 < FT1) { - T0 = FSR_FCC0 << FS; - } else if (FT0 > FT1) { - T0 = FSR_FCC1 << FS; - } else { - T0 = 0; +#define GEN_FCMP(name, size, reg1, reg2, FS) \ + void glue(do_, name) (void) \ + { \ + env->fsr &= ~((FSR_FCC1 | FSR_FCC0) << FS); \ + switch (glue(size, _compare) (reg1, reg2, &env->fp_status)) { \ + case float_relation_unordered: \ + T0 = (FSR_FCC1 | FSR_FCC0) << FS; \ + if (env->fsr & FSR_NVM) { \ + env->fsr |= T0; \ + raise_exception(TT_FP_EXCP); \ + } else { \ + env->fsr |= FSR_NVA; \ + } \ + break; \ + case float_relation_less: \ + T0 = FSR_FCC0 << FS; \ + break; \ + case float_relation_greater: \ + T0 = FSR_FCC1 << FS; \ + break; \ + default: \ + T0 = 0; \ + break; \ + } \ + env->fsr |= T0; \ } - env->fsr |= T0; -} -void do_fcmpd (void) -{ - env->fsr &= ~((FSR_FCC1 | FSR_FCC0) << FS); - if (isnan(DT0) || isnan(DT1)) { - T0 = (FSR_FCC1 | FSR_FCC0) << FS; - if (env->fsr & FSR_NVM) { - env->fsr |= T0; - raise_exception(TT_FP_EXCP); - } else { - env->fsr |= FSR_NVA; - } - } else if (DT0 < DT1) { - T0 = FSR_FCC0 << FS; - } else if (DT0 > DT1) { - T0 = FSR_FCC1 << FS; - } else { - T0 = 0; - } - env->fsr |= T0; -} +GEN_FCMP(fcmps, float32, FT0, FT1, 0); +GEN_FCMP(fcmpd, float64, DT0, DT1, 0); #ifdef TARGET_SPARC64 -#undef FS -#define FS 22 -void do_fcmps_fcc1 (void) -{ - env->fsr &= ~((FSR_FCC1 | FSR_FCC0) << FS); - if (isnan(FT0) || isnan(FT1)) { - T0 = (FSR_FCC1 | FSR_FCC0) << FS; - if (env->fsr & FSR_NVM) { - env->fsr |= T0; - raise_exception(TT_FP_EXCP); - } else { - env->fsr |= FSR_NVA; - } - } else if (FT0 < FT1) { - T0 = FSR_FCC0 << FS; - } else if (FT0 > FT1) { - T0 = FSR_FCC1 << FS; - } else { - T0 = 0; - } - env->fsr |= T0; -} - -void do_fcmpd_fcc1 (void) -{ - env->fsr &= ~((FSR_FCC1 | FSR_FCC0) << FS); - if (isnan(DT0) || isnan(DT1)) { - T0 = (FSR_FCC1 | FSR_FCC0) << FS; - if (env->fsr & FSR_NVM) { - env->fsr |= T0; - raise_exception(TT_FP_EXCP); - } else { - env->fsr |= FSR_NVA; - } - } else if (DT0 < DT1) { - T0 = FSR_FCC0 << FS; - } else if (DT0 > DT1) { - T0 = FSR_FCC1 << FS; - } else { - T0 = 0; - } - env->fsr |= T0; -} - -#undef FS -#define FS 24 -void do_fcmps_fcc2 (void) -{ - env->fsr &= ~((FSR_FCC1 | FSR_FCC0) << FS); - if (isnan(FT0) || isnan(FT1)) { - T0 = (FSR_FCC1 | FSR_FCC0) << FS; - if (env->fsr & FSR_NVM) { - env->fsr |= T0; - raise_exception(TT_FP_EXCP); - } else { - env->fsr |= FSR_NVA; - } - } else if (FT0 < FT1) { - T0 = FSR_FCC0 << FS; - } else if (FT0 > FT1) { - T0 = FSR_FCC1 << FS; - } else { - T0 = 0; - } - env->fsr |= T0; -} - -void do_fcmpd_fcc2 (void) -{ - env->fsr &= ~((FSR_FCC1 | FSR_FCC0) << FS); - if (isnan(DT0) || isnan(DT1)) { - T0 = (FSR_FCC1 | FSR_FCC0) << FS; - if (env->fsr & FSR_NVM) { - env->fsr |= T0; - raise_exception(TT_FP_EXCP); - } else { - env->fsr |= FSR_NVA; - } - } else if (DT0 < DT1) { - T0 = FSR_FCC0 << FS; - } else if (DT0 > DT1) { - T0 = FSR_FCC1 << FS; - } else { - T0 = 0; - } - env->fsr |= T0; -} +GEN_FCMP(fcmps_fcc1, float32, FT0, FT1, 22); +GEN_FCMP(fcmpd_fcc1, float64, DT0, DT1, 22); -#undef FS -#define FS 26 -void do_fcmps_fcc3 (void) -{ - env->fsr &= ~((FSR_FCC1 | FSR_FCC0) << FS); - if (isnan(FT0) || isnan(FT1)) { - T0 = (FSR_FCC1 | FSR_FCC0) << FS; - if (env->fsr & FSR_NVM) { - env->fsr |= T0; - raise_exception(TT_FP_EXCP); - } else { - env->fsr |= FSR_NVA; - } - } else if (FT0 < FT1) { - T0 = FSR_FCC0 << FS; - } else if (FT0 > FT1) { - T0 = FSR_FCC1 << FS; - } else { - T0 = 0; - } - env->fsr |= T0; -} +GEN_FCMP(fcmps_fcc2, float32, FT0, FT1, 24); +GEN_FCMP(fcmpd_fcc2, float64, DT0, DT1, 24); -void do_fcmpd_fcc3 (void) -{ - env->fsr &= ~((FSR_FCC1 | FSR_FCC0) << FS); - if (isnan(DT0) || isnan(DT1)) { - T0 = (FSR_FCC1 | FSR_FCC0) << FS; - if (env->fsr & FSR_NVM) { - env->fsr |= T0; - raise_exception(TT_FP_EXCP); - } else { - env->fsr |= FSR_NVA; - } - } else if (DT0 < DT1) { - T0 = FSR_FCC0 << FS; - } else if (DT0 > DT1) { - T0 = FSR_FCC1 << FS; - } else { - T0 = 0; - } - env->fsr |= T0; -} -#undef FS +GEN_FCMP(fcmps_fcc3, float32, FT0, FT1, 26); +GEN_FCMP(fcmpd_fcc3, float64, DT0, DT1, 26); #endif #if defined(CONFIG_USER_ONLY) @@ -783,19 +646,6 @@ set_float_rounding_mode(rnd_mode, &env->fp_status); } -void cpu_get_fp64(uint64_t *pmant, uint16_t *pexp, double f) -{ - int exptemp; - - *pmant = ldexp(frexp(f, &exptemp), 53); - *pexp = exptemp; -} - -double cpu_put_fp64(uint64_t mant, uint16_t exp) -{ - return ldexp((double) mant, exp - 53); -} - void helper_debug() { env->exception_index = EXCP_DEBUG; _______________________________________________ Qemu-devel mailing list Qemu-devel@nongnu.org http://lists.nongnu.org/mailman/listinfo/qemu-devel