revamping code to appropriately handle FP condition code and conversion ops.
authorKorey Sewell <ksewell@umich.edu>
Wed, 10 May 2006 20:52:27 +0000 (16:52 -0400)
committerKorey Sewell <ksewell@umich.edu>
Wed, 10 May 2006 20:52:27 +0000 (16:52 -0400)
There still needs to be a work around to handle the paired singles operations ...

arch/mips/isa/decoder.isa:
    More revamping of the floating point ops in decoder.isa. Change all of the
    "convert and round" functions to fpConvert. Also, the utility functions
    roundFP, truncFP, and unorderedFP are in place everywhere. Things
    have been set up to appropriately use the FP condition codes in the decoder.isa
    The fp.isa format file and the isa_traits.cc file now needed to be updated
    to implement the appropriate "backend" operations/functionality...
arch/mips/isa_traits.hh:
    Remove convert & round functions
    Add roundFP, truncFP,unorderedFP, and the get/setFPconditionCode
    functions
arch/mips/isa_traits.cc:
    Add utility functions

--HG--
extra : convert_revision : 3d6708388abae5b432467f528d52e6343afecd9c

arch/mips/isa/decoder.isa
arch/mips/isa_traits.cc
arch/mips/isa_traits.hh

index 6f1081daba9900dcb6dc8b5673c18544ac78bf8c..285ac21ae69c714e359cfd94e6b162d96e30a603 100644 (file)
@@ -1,4 +1,4 @@
-// -*- mode:c++ -*-
+ // -*- mode:c++ -*-
 
 ////////////////////////////////////////////////////////////////////
 //
@@ -20,8 +20,8 @@ decode OPCODE_HI default Unknown::unknown() {
             0x0: decode FUNCTION_LO {
                 0x1: decode MOVCI {
                     format BasicOp {
-                        0: movf({{ if (xc->readMiscReg(FPCR) != CC) Rd = Rs}});
-                        1: movt({{ if (xc->readMiscReg(FPCR) == CC) Rd = Rs}});
+                        0: movf({{ if (getFPConditionCode(CC) == 0) Rd = Rs}});
+                        1: movt({{ if (getFPConditionCode(CC) == 1) Rd = Rs}});
                     }
                 }
 
@@ -476,15 +476,15 @@ decode OPCODE_HI default Unknown::unknown() {
                 0x1: decode ND {
                     0x0: decode TF {
                         format Branch {
-                            0x0: bc1f({{ cond = (xc->readMiscReg(FPCR) == 0); }});
-                            0x1: bc1t({{ cond = (xc->readMiscReg(FPCR) == 1); }});
+                            0x0: bc1f({{ cond = (getFPConditionCode(CC) == 0); }});
+                            0x1: bc1t({{ cond = (getFPConditionCode(CC) == 1); }});
                         }
                     }
 
                     0x1: decode TF {
                         format BranchLikely {
-                            0x0: bc1fl({{ cond = (xc->readMiscReg(FPCR) == 0); }});
-                            0x1: bc1tl({{ cond = (xc->readMiscReg(FPCR) == 1); }});
+                            0x0: bc1fl({{ cond = (getFPConditionCode(CC) == 0); }});
+                            0x1: bc1tl({{ cond = (getFPConditionCode(CC) == 1); }});
                         }
                     }
                 }
@@ -701,51 +701,51 @@ decode OPCODE_HI default Unknown::unknown() {
                     0x1: decode FUNCTION_HI {
                         0x0: decode FUNCTION_LO {
                             format FloatOp {
-                                0x0: addd({{ Fd.df = Fs.df + Ft.df;}});
-                                0x1: subd({{ Fd.df = Fs.df - Ft.df;}});
-                                0x2: muld({{ Fd.df = Fs.df * Ft.df;}});
-                                0x3: divd({{ Fd.df = Fs.df / Ft.df;}});
-                                0x4: sqrtd({{ Fd.df = sqrt(Fs.df);}});
-                                0x5: absd({{ Fd.df = fabs(Fs.df);}});
-                                0x6: movd({{ Fd.ud = Fs.ud;}});
-                                0x7: negd({{ Fd.df = -1 * Fs.df;}});
+                                0x0: add_d({{ Fd.df = Fs.df + Ft.df;}});
+                                0x1: sub_d({{ Fd.df = Fs.df - Ft.df;}});
+                                0x2: mul_d({{ Fd.df = Fs.df * Ft.df;}});
+                                0x3: div_d({{ Fd.df = Fs.df / Ft.df;}});
+                                0x4: sqrt_d({{ Fd.df = sqrt(Fs.df);}});
+                                0x5: abs_d({{ Fd.df = fabs(Fs.df);}});
+                                0x6: mov_d({{ Fd.ud = Fs.ud;}});
+                                0x7: neg_d({{ Fd.df = -1 * Fs.df;}});
                             }
                         }
 
                         0x1: decode FUNCTION_LO {
-                            format Float64Op {
+                            format FloatOp {
                                 0x0: round_l_d({{
-                                    Fd.ud = convert_and_round(Fs.ud, DOUBLE_TO_LONG, RND_NEAREST);
+                                    Fd.ud = fpConvert(roundFP(Fs.ud), DOUBLE_TO_LONG);
                                 }});
 
                                 0x1: trunc_l_d({{
-                                    Fd.ud = convert_and_round(Fs.ud, DOUBLE_TO_LONG, RND_ZERO);
+                                    Fd.ud = fpConvert(truncFP(Fs.ud), DOUBLE_TO_LONG);
                                 }});
 
                                 0x2: ceil_l_d({{
-                                    Fd.ud = convert_and_round(Fs.ud, DOUBLE_TO_LONG, RND_UP);
+                                    Fd.ud = fpConvert(ceil(Fs.ud), DOUBLE_TO_LONG);
                                 }});
 
                                 0x3: floor_l_d({{
-                                    Fd.ud = convert_and_round(Fs.ud, DOUBLE_TO_LONG, RND_DOWN);
+                                    Fd.ud = fpConvert(floor(Fs.ud), DOUBLE_TO_LONG);
                                 }});
                             }
 
                             format FloatOp {
                                 0x4: round_w_d({{
-                                    Fd.uw = convert_and_round(Fs.ud, DOUBLE_TO_WORD, RND_NEAREST);
+                                    Fd.uw = fpConvert(roundFP(Fs.ud), DOUBLE_TO_WORD);
                                 }});
 
                                 0x5: trunc_w_d({{
-                                    Fd.uw = convert_and_round(Fs.ud, DOUBLE_TO_WORD, RND_ZERO);
+                                    Fd.uw = fpConvert(truncFP(Fs.ud), DOUBLE_TO_WORD);
                                 }});
 
                                 0x6: ceil_w_d({{
-                                    Fd.uw = convert_and_round(Fs.ud, DOUBLE_TO_WORD, RND_UP);
+                                    Fd.uw = fpConvert(ceil(Fs.ud), DOUBLE_TO_WORD);
                                 }});
 
                                 0x7: floor_w_d({{
-                                    Fd.uw = convert_and_round(Fs.ud, DOUBLE_TO_WORD, RND_DOWN);
+                                    Fd.uw = fpConvert(floor(Fs.ud), DOUBLE_TO_WORD);
                                 }});
                             }
                         }
@@ -753,40 +753,34 @@ decode OPCODE_HI default Unknown::unknown() {
                         0x2: decode FUNCTION_LO {
                             0x1: decode MOVCF {
                                 format FloatOp {
-                                    0x0: movfd({{if (xc->readMiscReg(FPCR) != CC) Fd.df = Fs.df; }});
-                                    0x1: movtd({{if (xc->readMiscReg(FPCR) == CC) Fd.df = Fs.df; }});
+                                    0x0: movf_d({{if (getFPConditionCode(CC) == 0) Fd.df = Fs.df; }});
+                                    0x1: movt_d({{if (getFPConditionCode(CC) == 1) Fd.df = Fs.df; }});
                                 }
                             }
 
                             format BasicOp {
-                                0x2: movzd({{ if (Rt == 0) Fd.df = Fs.df; }});
-                                0x3: movnd({{ if (Rt != 0) Fd.df = Fs.df; }});
+                                0x2: movz_d({{ if (Rt == 0) Fd.df = Fs.df; }});
+                                0x3: movn_d({{ if (Rt != 0) Fd.df = Fs.df; }});
                             }
 
-                            format Float64Op {
-                                0x5: recipd({{ Fd.df = 1 / Fs.df}});
-                                0x6: rsqrtd({{ Fd.df = 1 / sqrt(Fs.df) }});
+                            format FloatOp {
+                                0x5: recip_d({{ Fd.df = 1 / Fs.df}});
+                                0x6: rsqrt_d({{ Fd.df = 1 / sqrt(Fs.df) }});
                             }
                         }
 
                         0x4: decode FUNCTION_LO {
                             format FloatOp {
                                 0x0: cvt_s_d({{
-                                    int rnd_mode = xc->readMiscReg(FCSR) & 0x03;
-                                    Fd.uw = convert_and_round(Fs.ud, DOUBLE_TO_SINGLE, rnd_mode);
+                                    Fd.uw = fpConvert(Fs.ud, DOUBLE_TO_SINGLE);
                                 }});
 
                                 0x4: cvt_w_d({{
-                                    int rnd_mode = xc->readMiscReg(FCSR) & 0x03;
-                                    Fd.uw = convert_and_round(Fs.ud, DOUBLE_TO_WORD, rnd_mode);
+                                    Fd.uw = fpConvert(Fs.ud, DOUBLE_TO_WORD);
                                 }});
-                            }
 
-                            //only legal for 64 bit
-                            format Float64Op {
                                 0x5: cvt_l_d({{
-                                    int rnd_mode = xc->readMiscReg(FCSR) & 0x03;
-                                    Fd.ud = convert_and_round(Fs.ud, DOUBLE_TO_LONG, rnd_mode);
+                                    Fd.ud = fpConvert(Fs.ud, DOUBLE_TO_LONG);
                                 }});
                             }
                         }
@@ -904,15 +898,19 @@ decode OPCODE_HI default Unknown::unknown() {
 
                     //Table A-16 MIPS32 COP1 Encoding of Function Field When rs=W
                     0x4: decode FUNCTION {
-                        format FloatOp {
+                        format FloatConvertOp {
                             0x20: cvt_s_w({{
-                                int rnd_mode = xc->readMiscReg(FCSR) & 0x03;
-                                Fd.uw = convert_and_round(Fs.sf, WORD_TO_SINGLE, rnd_mode);
+                                Fd.uw = fpConvert(Fs.sf, WORD_TO_SINGLE);
                             }});
 
                             0x21: cvt_d_w({{
-                                int rnd_mode = xc->readMiscReg(FCSR) & 0x03;
-                                Fd.ud = convert_and_round(Fs.sf, WORD_TO_DOUBLE, rnd_mode);
+                                Fd.ud = fpConvert(Fs.sf, WORD_TO_DOUBLE);
+                            }});
+                        }
+
+                        format Float64ConvertOp {
+                            0x26: cvt_ps_pw({{
+                                Fd.ud = fpConvert(Fs.ud, WORD_TO_PS);
                             }});
                         }
                     }
@@ -921,15 +919,17 @@ decode OPCODE_HI default Unknown::unknown() {
                     //Note: "1. Format type L is legal only if 64-bit floating point operations
                     //are enabled."
                     0x5: decode FUNCTION_HI {
-                        format Float64Op {
-                            0x10: cvt_s_l({{
-                                int rnd_mode = xc->readMiscReg(FCSR) & 0x03;
-                                Fd.uw = convert_and_round(Fs.ud, LONG_TO_SINGLE, rnd_mode);
+                        format Float64ConvertOp {
+                            0x20: cvt_s_l({{
+                                Fd.uw = fpConvert(Fs.ud, LONG_TO_SINGLE);
+                            }});
+
+                            0x21: cvt_d_l({{
+                                Fd.ud = fpConvert(Fs.ud, LONG_TO_DOUBLE);
                             }});
 
-                            0x11: cvt_d_l({{
-                                int rnd_mode = xc->readMiscReg(FCSR) & 0x03;
-                                Fd.ud = convert_and_round(Fs.ud, LONG_TO_DOUBLE, rnd_mode);
+                            0x26: cvt_ps_l({{
+                                Fd.ud = fpConvert(Fs.ud, LONG_TO_PS);
                             }});
                         }
                     }
@@ -940,33 +940,27 @@ decode OPCODE_HI default Unknown::unknown() {
                     0x6: decode FUNCTION_HI {
                         0x0: decode FUNCTION_LO {
                             format Float64Op {
-                                0x0: addps({{ //Must Check for Exception Here... Supposed to Operate on Upper and
-                                    //Lower Halves Independently but we take simulator shortcut
+                                0x0: add_ps({{
                                     Fd.df = Fs.df + Ft.df;
                                 }});
 
-                                0x1: subps({{ //Must Check for Exception Here... Supposed to Operate on Upper and
-                                    //Lower Halves Independently but we take simulator shortcut
+                                0x1: sub_ps({{
                                     Fd.df = Fs.df - Ft.df;
                                 }});
 
-                                0x2: mulps({{ //Must Check for Exception Here... Supposed to Operate on Upper and
-                                    //Lower Halves Independently but we take simulator shortcut
+                                0x2: mul_ps({{
                                     Fd.df = Fs.df * Ft.df;
                                 }});
 
-                                0x5: absps({{ //Must Check for Exception Here... Supposed to Operate on Upper and
-                                    //Lower Halves Independently but we take simulator shortcut
+                                0x5: abs_ps({{
                                     Fd.df = fabs(Fs.df);
                                 }});
 
-                                0x6: movps({{ //Must Check for Exception Here... Supposed to Operate on Upper and
-                                    //Lower Halves Independently but we take simulator shortcut
-                                    //Fd.df = Fs<31:0> |  Ft<31:0>;
+                                0x6: mov_ps({{
+                                    Fd.df = Fs |  Ft;
                                 }});
 
-                                0x7: negps({{ //Must Check for Exception Here... Supposed to Operate on Upper and
-                                    //Lower Halves Independently but we take simulator shortcut
+                                0x7: neg_ps({{
                                     Fd.df = -1 * Fs.df;
                                 }});
                             }
@@ -975,31 +969,28 @@ decode OPCODE_HI default Unknown::unknown() {
                         0x2: decode FUNCTION_LO {
                             0x1: decode MOVCF {
                                 format Float64Op {
-                                    0x0: movfps({{if (xc->readMiscReg(FPCR) != CC) Fd = Fs;}});
-                                    0x1: movtps({{if (xc->readMiscReg(FPCR) == CC) Fd = Fs;}});
+                                    0x0: movf_ps({{if (getFPConditionCode(CC) == 0) Fd = Fs;}});
+                                    0x1: movt_ps({{if (getFPConditionCode(CC) == 1) Fd = Fs;}});
                                 }
                             }
 
-                            format BasicOp {
-                                0x2: movzps({{if (xc->readMiscReg(FPCR) != CC) Fd = Fs; }});
-                                0x3: movnps({{if (xc->readMiscReg(FPCR) == CC) Fd = Fs; }});
+                            format Float64Op {
+                                0x2: movz_ps({{if (getFPConditionCode(CC) == 0) Fd = Fs; }});
+                                0x3: movn_ps({{if (getFPConditionCode(CC) == 1) Fd = Fs; }});
                             }
 
                         }
 
                         0x4: decode FUNCTION_LO {
                             0x0: Float64Op::cvt_s_pu({{
-                                int rnd_mode = xc->readMiscReg(FCSR) & 0x03;
-                                Fd.uw = convert_and_round(Fs.ud, PUPPER_TO_SINGLE, rnd_mode);
+                                Fd.uw = fpConvert(Fs.ud, PU_TO_SINGLE);
                             }});
                         }
 
                         0x5: decode FUNCTION_LO {
                             format Float64Op {
                                 0x0: cvt_s_pl({{
-                                    int rnd_mode = xc->readMiscReg(FCSR) & 0x03;
-                                    Fd.uw = convert_and_round(Fs.ud, PLOWER_TO_SINGLE,
-                                                           rnd_mode);
+                                    Fd.uw = fpConvert(Fs.ud, PL_TO_SINGLE);
                                 }});
 
                                 0x4: pll({{ Fd.ud = Fs.ud<31:0>  << 32 | Ft.ud<31:0>; }});
@@ -1102,8 +1093,6 @@ decode OPCODE_HI default Unknown::unknown() {
                         0x0: madd_s({{ Fd.sf = (Fs.sf * Fs.sf) + Fr.sf; }});
                         0x1: madd_d({{ Fd.df = (Fs.df * Fs.df) + Fr.df; }});
                         0x6: madd_ps({{
-                            //Must Check for Exception Here... Supposed to Operate on Upper and
-                            //Lower Halves Independently but we take simulator shortcut
                             Fd.df = (Fs.df * Fs.df) + Fr.df;
                         }});
                     }
@@ -1112,8 +1101,6 @@ decode OPCODE_HI default Unknown::unknown() {
                         0x0: msub_s({{ Fd.sf = (Fs.sf * Fs.sf) - Fr.sf; }});
                         0x1: msub_d({{ Fd.df = (Fs.df * Fs.df) - Fr.df; }});
                         0x6: msub_ps({{
-                            //Must Check for Exception Here... Supposed to Operate on Upper and
-                            //Lower Halves Independently but we take simulator shortcut
                             Fd.df = (Fs.df * Fs.df) - Fr.df;
                         }});
                     }
@@ -1122,8 +1109,6 @@ decode OPCODE_HI default Unknown::unknown() {
                         0x0: nmadd_s({{ Fd.sf = (-1 * Fs.sf * Fs.sf) - Fr.sf; }});
                         0x1: nmadd_d({{ Fd.df = (-1 * Fs.df * Fs.df) + Fr.df; }});
                         0x6: nmadd_ps({{
-                            //Must Check for Exception Here... Supposed to Operate on Upper and
-                            //Lower Halves Independently but we take simulator shortcut
                             Fd.df = (-1 * Fs.df * Fs.df) + Fr.df;
                         }});
                     }
@@ -1132,8 +1117,6 @@ decode OPCODE_HI default Unknown::unknown() {
                         0x0: nmsub_s({{ Fd.sf = (-1 * Fs.sf * Fs.sf) - Fr.sf; }});
                         0x1: nmsub_d({{ Fd.df = (-1 * Fs.df * Fs.df) - Fr.df; }});
                         0x6: nmsub_ps({{
-                            //Must Check for Exception Here... Supposed to Operate on Upper and
-                            //Lower Halves Independently but we take simulator shortcut
                             Fd.df = (-1 * Fs.df * Fs.df) + Fr.df;
                         }});
                     }
@@ -1141,7 +1124,6 @@ decode OPCODE_HI default Unknown::unknown() {
             }
         }
 
-        //MIPS obsolete instructions
         format BranchLikely {
             0x4: beql({{ cond = (Rs.sw == 0); }});
             0x5: bnel({{ cond = (Rs.sw != 0); }});
index 2260cdc35f4a59ce348cf47e1604a0f3415a9308..4eb14c66d8137e76e38e725a66adfdcd9a89a83f 100644 (file)
@@ -155,6 +155,80 @@ MipsISA::convert_and_round(double fp_val, ConvertType cvt_type, int rnd_mode)
     }
 }
 
+uint64_t
+MipsISA::fpConvert(double fp_val, ConvertType cvt_type)
+{
+
+    switch (cvt_type)
+    {
+      case SINGLE_TO_DOUBLE:
+        double sdouble_val = fp_val;
+        void  *sdouble_ptr = &sdouble_val;
+        uint64_t sdp_bits  = *(uint64_t *) sdouble_ptr;
+        return sdp_bits;
+
+      case SINGLE_TO_WORD:
+        int32_t sword_val  = (int32_t) fp_val;
+        void  *sword_ptr   = &sword_val;
+        uint64_t sword_bits= *(uint32_t *) sword_ptr;
+        return sword_bits;
+
+      case WORD_TO_SINGLE:
+        float wfloat_val   = fp_val;
+        void  *wfloat_ptr  = &wfloat_val;
+        uint64_t wfloat_bits = *(uint32_t *) wfloat_ptr;
+        return wfloat_bits;
+
+      case WORD_TO_DOUBLE:
+        double wdouble_val = fp_val;
+        void  *wdouble_ptr = &wdouble_val;
+        uint64_t wdp_bits  = *(uint64_t *) wdouble_ptr;
+        return wdp_bits;
+
+      default:
+        panic("Invalid Floating Point Conversion Type (%d). See \"types.hh\" for List of Conversions\n",cvt_type);
+        return 0;
+    }
+}
+
+double
+MipsISA::roundFP(double val)
+{
+    double trunc_val = trunc(val);
+    double fraction = val - trunc_val;
+
+    if (fraction < 0.5)
+        return val;
+    else
+        return val + 1;
+}
+
+inline double
+MipsISA::truncFP(double val)
+{
+    int trunc_val = (int) val;
+    return (double) trunc_val;
+}
+
+bool
+MipsISA::unorderedFP(uint32_t val)
+{
+}
+
+bool
+MipsISA::unorderedFP(uint64_t val)
+{
+}
+
+bool
+MipsISA::getConditionCode(int cc)
+{
+}
+
+void
+MipsISA::setConditionCode(int num, bool val)
+{
+}
 
 #if FULL_SYSTEM
 
index 33c490dcc1d944fa90290f3eaf670bc184bb72cd..d009bbea53cfb4a5f8ecb8d25ad0fa8b9c8a0bbc 100644 (file)
@@ -137,9 +137,13 @@ namespace MipsISA
 
     void copyRegs(ExecContext *src, ExecContext *dest);
 
-    uint64_t convert_and_round(uint32_t fp_val, ConvertType cvt_type, int rnd_mode = 0);
-    uint64_t convert_and_round(uint64_t fp_val, ConvertType cvt_type, int rnd_mode = 0);
-    uint64_t convert_and_round(double fp_val, ConvertType cvt_type, int rnd_mode = 0);
+    uint64_t fpConvert(double fp_val, ConvertType cvt_type);
+    double roundFP(double val);
+    inline double truncFP(double val);
+    bool unorderedFP(uint32_t val);
+    bool unorderedFP(uint64_t val);
+    bool getConditionCode(int cc);
+    void setConditionCode(int num, bool val);
 
     // Machine operations