]> git.ipfire.org Git - thirdparty/valgrind.git/commitdiff
More x86 tidying up following rounding changes.
authorJulian Seward <jseward@acm.org>
Sat, 4 Feb 2006 15:20:13 +0000 (15:20 +0000)
committerJulian Seward <jseward@acm.org>
Sat, 4 Feb 2006 15:20:13 +0000 (15:20 +0000)
git-svn-id: svn://svn.valgrind.org/vex/trunk@1565

VEX/priv/guest-x86/toIR.c
VEX/priv/host-x86/isel.c

index d9aa5cb2a8e7e3875fb9c087b0e3b670e7d20557..f8b22d937973f6bffcc26312e2a4dd1c7ec69322 100644 (file)
@@ -3973,9 +3973,16 @@ UInt dis_FPU ( Bool* decode_ok, UChar sorb, Int delta )
                   to get the C3210 flag values. */
                assign( a1, get_ST(0) );
                assign( a2, get_ST(1) );
-               put_ST_UNCHECKED(0, binop(Iop_PRem1F64,
-                                         mkexpr(a1), mkexpr(a2)));
-               put_C3210( binop(Iop_PRem1C3210F64, mkexpr(a1), mkexpr(a2)) );
+               put_ST_UNCHECKED(0, 
+                  triop(Iop_PRem1F64,
+                        get_FAKE_roundingmode(), /* XXXROUNDINGFIXME */
+                        mkexpr(a1), 
+                        mkexpr(a2)));
+               put_C3210(
+                  triop(Iop_PRem1C3210F64,
+                        get_FAKE_roundingmode(), /* XXXROUNDINGFIXME */
+                        mkexpr(a1), 
+                        mkexpr(a2)) );
                break;
             }
 
@@ -3992,9 +3999,16 @@ UInt dis_FPU ( Bool* decode_ok, UChar sorb, Int delta )
                   to get the C3210 flag values. */
                assign( a1, get_ST(0) );
                assign( a2, get_ST(1) );
-               put_ST_UNCHECKED(0, binop(Iop_PRemF64,
-                                         mkexpr(a1), mkexpr(a2)));
-               put_C3210( binop(Iop_PRemC3210F64, mkexpr(a1), mkexpr(a2)) );
+               put_ST_UNCHECKED(0, 
+                  triop(Iop_PRemF64,
+                        get_FAKE_roundingmode(), /* XXXROUNDINGFIXME */
+                        mkexpr(a1), 
+                        mkexpr(a2)));
+               put_C3210( 
+                  triop(Iop_PRemC3210F64,
+                        get_FAKE_roundingmode(), /* XXXROUNDINGFIXME */
+                        mkexpr(a1), 
+                        mkexpr(a2)) );
                break;
             }
 
index b30a215b35711a42cde4ecff051002d954fedc0f..0d55f30a31ff99c1b8c42bdabe158665eca3bc59 100644 (file)
@@ -760,6 +760,34 @@ static HReg iselIntExpr_R_wrk ( ISelEnv* env, IRExpr* e )
       break;
    }
 
+   /* --------- TERNARY OP --------- */
+   case Iex_Triop: {
+      /* C3210 flags following FPU partial remainder (fprem), both
+         IEEE compliant (PREM1) and non-IEEE compliant (PREM). */
+      if (e->Iex.Triop.op == Iop_PRemC3210F64
+          || e->Iex.Triop.op == Iop_PRem1C3210F64) {
+         HReg junk = newVRegF(env);
+         HReg dst  = newVRegI(env);
+         HReg srcL = iselDblExpr(env, e->Iex.Triop.arg2);
+         HReg srcR = iselDblExpr(env, e->Iex.Triop.arg3);
+         /* XXXROUNDINGFIXME */
+         /* set roundingmode here */
+         addInstr(env, X86Instr_FpBinary(
+                           e->Iex.Binop.op==Iop_PRemC3210F64 
+                              ? Xfp_PREM : Xfp_PREM1,
+                           srcL,srcR,junk
+                 ));
+         /* The previous pseudo-insn will have left the FPU's C3210
+            flags set correctly.  So bag them. */
+         addInstr(env, X86Instr_FpStSW_AX());
+         addInstr(env, mk_iMOVsd_RR(hregX86_EAX(), dst));
+         addInstr(env, X86Instr_Alu32R(Xalu_AND, X86RMI_Imm(0x4700), dst));
+         return dst;
+      }
+
+      break;
+   }
+
    /* --------- BINARY OP --------- */
    case Iex_Binop: {
       X86AluOp   aluOp;
@@ -972,27 +1000,6 @@ static HReg iselIntExpr_R_wrk ( ISelEnv* env, IRExpr* e )
          return dst;
       }
 
-      /* C3210 flags following FPU partial remainder (fprem), both
-         IEEE compliant (PREM1) and non-IEEE compliant (PREM). */
-      if (e->Iex.Binop.op == Iop_PRemC3210F64
-          || e->Iex.Binop.op == Iop_PRem1C3210F64) {
-         HReg junk = newVRegF(env);
-         HReg dst  = newVRegI(env);
-         HReg srcL = iselDblExpr(env, e->Iex.Binop.arg1);
-         HReg srcR = iselDblExpr(env, e->Iex.Binop.arg2);
-         addInstr(env, X86Instr_FpBinary(
-                           e->Iex.Binop.op==Iop_PRemC3210F64 
-                              ? Xfp_PREM : Xfp_PREM1,
-                           srcL,srcR,junk
-                 ));
-         /* The previous pseudo-insn will have left the FPU's C3210
-            flags set correctly.  So bag them. */
-         addInstr(env, X86Instr_FpStSW_AX());
-         addInstr(env, mk_iMOVsd_RR(hregX86_EAX(), dst));
-        addInstr(env, X86Instr_Alu32R(Xalu_AND, X86RMI_Imm(0x4700), dst));
-         return dst;
-      }
-
       break;
    }
 
@@ -2615,6 +2622,8 @@ static HReg iselDblExpr_wrk ( ISelEnv* env, IRExpr* e )
          case Iop_Yl2xF64:   fpop = Xfp_YL2X; break;
          case Iop_Yl2xp1F64: fpop = Xfp_YL2XP1; break;
          case Iop_AtanF64:   fpop = Xfp_ATAN; break;
+         case Iop_PRemF64:   fpop = Xfp_PREM; break;
+         case Iop_PRem1F64:  fpop = Xfp_PREM1; break;
          default: break;
       }
       if (fpop != Xfp_INVALID) {
@@ -2631,25 +2640,6 @@ static HReg iselDblExpr_wrk ( ISelEnv* env, IRExpr* e )
       }
    }
 
-   if (e->tag == Iex_Binop) {
-      X86FpOp fpop = Xfp_INVALID;
-      switch (e->Iex.Binop.op) {
-         case Iop_PRemF64:   fpop = Xfp_PREM; break;
-         case Iop_PRem1F64:  fpop = Xfp_PREM1; break;
-         default: break;
-      }
-      if (fpop != Xfp_INVALID) {
-         HReg res  = newVRegF(env);
-         HReg srcL = iselDblExpr(env, e->Iex.Binop.arg1);
-         HReg srcR = iselDblExpr(env, e->Iex.Binop.arg2);
-         addInstr(env, X86Instr_FpBinary(fpop,srcL,srcR,res));
-        if (fpop != Xfp_ADD && fpop != Xfp_SUB 
-            && fpop != Xfp_MUL && fpop != Xfp_DIV)
-            roundToF64(env, res);
-         return res;
-      }
-   }
-
    if (e->tag == Iex_Binop && e->Iex.Binop.op == Iop_RoundF64toInt) {
       HReg rf  = iselDblExpr(env, e->Iex.Binop.arg2);
       HReg dst = newVRegF(env);