Procházet zdrojové kódy

adding min max for F4

adding comments and test

test files

adding asmjs tests

moving tests into Bugs

removing noisy changes

simplifying flags

canonicalizing non-asmjs test

removing debugging output from tests

 removing unnecessary calls

fixing test opts

fixing test baseline
nikolayk před 10 roky
rodič
revize
fa531329b8

+ 1 - 0
lib/Backend/LowerMDShared.h

@@ -347,6 +347,7 @@ public:
     IR::Instr*          Simd128LowerLessThanOrEqual(IR::Instr* instr);
     IR::Instr*          Simd128LowerGreaterThanOrEqual(IR::Instr* instr);
     IR::Instr*          Simd128LowerMinMax(IR::Instr* instr);
+    IR::Instr*          Simd128LowerMinMax_F4(IR::Instr* instr);
     IR::Instr*          Simd128LowerMinMaxNum(IR::Instr* instr);
     IR::Instr*          Simd128LowerAnyTrue(IR::Instr* instr);
     IR::Instr*          Simd128LowerAllTrue(IR::Instr* instr);

+ 66 - 2
lib/Backend/LowerMDSharedSimd128.cpp

@@ -353,6 +353,10 @@ IR::Instr* LowererMD::Simd128LowerUnMappedInstruction(IR::Instr *instr)
     case Js::OpCode::Simd128_Max_U8:
         return Simd128LowerMinMax(instr);
 
+    case Js::OpCode::Simd128_Min_F4:
+    case Js::OpCode::Simd128_Max_F4:
+        return Simd128LowerMinMax_F4(instr);
+
     case Js::OpCode::Simd128_MinNum_F4:
     case Js::OpCode::Simd128_MaxNum_F4:
         return Simd128LowerMinMaxNum(instr);
@@ -2320,6 +2324,68 @@ IR::Instr* LowererMD::Simd128LowerMinMax(IR::Instr* instr)
     return pInstr;
 }
 
+IR::Instr* LowererMD::Simd128LowerMinMax_F4(IR::Instr* instr)
+{
+    IR::Instr *pInstr;
+    IR::Opnd* dst = instr->GetDst();
+    IR::Opnd* src1 = instr->GetSrc1();
+    IR::Opnd* src2 = instr->GetSrc2();
+    Assert(dst->IsRegOpnd() && dst->IsSimd128());
+    Assert(src1->IsRegOpnd() && src1->IsSimd128());
+    Assert(src2->IsRegOpnd() && src2->IsSimd128());
+    Assert(instr->m_opcode == Js::OpCode::Simd128_Min_F4 || instr->m_opcode == Js::OpCode::Simd128_Max_F4);
+    IR::RegOpnd* tmp1 = IR::RegOpnd::New(src1->GetType(), m_func);
+    IR::RegOpnd* tmp2 = IR::RegOpnd::New(src2->GetType(), m_func);
+
+    if (instr->m_opcode == Js::OpCode::Simd128_Min_F4)
+    {
+        pInstr = IR::Instr::New(Js::OpCode::MINPS, tmp1, src1, src2, m_func);
+        instr->InsertBefore(pInstr);
+        Legalize(pInstr);
+        //
+        pInstr = IR::Instr::New(Js::OpCode::MINPS, tmp2, src2, src1, m_func);
+        instr->InsertBefore(pInstr);
+        Legalize(pInstr);
+        //
+        pInstr = IR::Instr::New(Js::OpCode::ORPS, dst, tmp1, tmp2, m_func);
+        instr->InsertBefore(pInstr);
+        Legalize(pInstr);
+    }
+    else 
+    {
+
+        //This sequence closely mirrors SIMDFloat32x4Operation::OpMax except for
+        //the fact that tmp2 (tmpbValue) is reused to reduce the number of registers
+        //needed for this sequence. 
+
+        pInstr = IR::Instr::New(Js::OpCode::MAXPS, tmp1, src1, src2, m_func);
+        instr->InsertBefore(pInstr);
+        Legalize(pInstr);
+        //
+        pInstr = IR::Instr::New(Js::OpCode::MAXPS, tmp2, src2, src1, m_func);
+        instr->InsertBefore(pInstr);
+        Legalize(pInstr);
+        //
+        pInstr = IR::Instr::New(Js::OpCode::ANDPS, tmp1, tmp1, tmp2, m_func);
+        instr->InsertBefore(pInstr);
+        Legalize(pInstr);
+        //
+        pInstr = IR::Instr::New(Js::OpCode::CMPUNORDPS, tmp2, src1, src2, m_func);
+        instr->InsertBefore(pInstr);
+        Legalize(pInstr);
+        //
+        pInstr = IR::Instr::New(Js::OpCode::ORPS, dst, tmp1, tmp2, m_func);
+        instr->InsertBefore(pInstr);
+        Legalize(pInstr);
+    }
+
+    pInstr = instr->m_prev;
+    instr->Remove();
+    return pInstr;
+
+}
+
+
 IR::Instr* LowererMD::Simd128LowerMinMaxNum(IR::Instr* instr)
 {
     IR::Instr *pInstr;
@@ -3312,8 +3378,6 @@ void LowererMD::Simd128InitOpcodeMap()
     SET_SIMDOPCODE(Simd128_Sub_F4                , SUBPS);
     SET_SIMDOPCODE(Simd128_Mul_F4                , MULPS);
     SET_SIMDOPCODE(Simd128_Div_F4                , DIVPS);
-    SET_SIMDOPCODE(Simd128_Min_F4                , MINPS);
-    SET_SIMDOPCODE(Simd128_Max_F4                , MAXPS);
     SET_SIMDOPCODE(Simd128_Sqrt_F4               , SQRTPS);
     SET_SIMDOPCODE(Simd128_Lt_F4                 , CMPLTPS); // CMPLTPS
     SET_SIMDOPCODE(Simd128_LtEq_F4               , CMPLEPS); // CMPLEPS

+ 2 - 0
test/Bugs/b208.baseline

@@ -0,0 +1,2 @@
+testMin = SIMD.Float32x4(NaN, NaN, NaN, NaN)
+testMax = SIMD.Float32x4(NaN, NaN, NaN, NaN)

+ 28 - 0
test/Bugs/b208.js

@@ -0,0 +1,28 @@
+//-------------------------------------------------------------------------------------------------------
+// Copyright (C) Microsoft Corporation and contributors. All rights reserved.
+// Licensed under the MIT license. See LICENSE.txt file in the project root for full license information.
+//-------------------------------------------------------------------------------------------------------
+
+function testMax () {
+    var one = SIMD.Float32x4(NaN, 42, NaN, NaN)
+    var two = SIMD.Float32x4(NaN, NaN, NaN, 3.14)
+    var three = SIMD.Float32x4.max(one,two);
+    return three;
+}
+
+function testMin () {
+    var one = SIMD.Float32x4(NaN, 42, NaN, NaN)
+    var two = SIMD.Float32x4(NaN, NaN, NaN, 3.14)
+    var three = SIMD.Float32x4.min(one,two);
+    return three;
+}
+
+
+for (var i = 0; i < 3; i++) {
+    testMax();
+    testMin();
+}
+
+print("testMin = " + testMin());
+print("testMax = " + testMax());
+

+ 2 - 0
test/Bugs/b208_asmjs.baseline

@@ -0,0 +1,2 @@
+SIMD.Float32x4(NaN, NaN, NaN, NaN)
+SIMD.Float32x4(NaN, NaN, NaN, NaN)

+ 58 - 0
test/Bugs/b208_asmjs.js

@@ -0,0 +1,58 @@
+//-------------------------------------------------------------------------------------------------------
+// Copyright (C) Microsoft Corporation and contributors. All rights reserved.
+// Licensed under the MIT license. See LICENSE.txt file in the project root for full license information.
+//-------------------------------------------------------------------------------------------------------
+
+function asmModule(stdlib, imports) {
+    "use asm";
+    
+    var f4 = stdlib.SIMD.Float32x4; 
+    var f4check = f4.check;
+    
+    var f4min = f4.min;
+    var f4max = f4.max;
+    
+    var f4sqrt = f4.sqrt;
+
+    var fround = stdlib.Math.fround;
+
+    function func1()
+    {
+        var x = f4(-1.0,42.0,-1.0,-1.0);
+        var y = f4(-1.0,-1.0,-1.0,3.14);
+        var res = f4(0.0,0.0,0.0,0.0);
+        
+        x = f4sqrt(x); //generate nans in the right positions
+        y = f4sqrt(y);
+
+        res = f4max(x,y);
+
+        return f4check(res);
+    }
+    
+    function func2()
+    {
+        var x = f4(-1.0,42.0,-1.0,-1.0);
+        var y = f4(-1.0,-1.0,-1.0,3.14);
+        var res = f4(0.0,0.0,0.0,0.0);
+        
+        x = f4sqrt(x); //generate nans in the right positions
+        y = f4sqrt(y);
+
+        res = f4min(x,y);
+
+        return f4check(res);
+    }
+   
+    return {func1:func1, func2:func2};
+}
+
+var m = asmModule(this, {});
+
+m.func1();
+m.func2();
+
+print (m.func1());
+print (m.func2());
+
+

+ 23 - 0
test/Bugs/rlexe.xml

@@ -276,4 +276,27 @@
       <compile-flags>-nonative</compile-flags>
     </default>
   </test>
+  <test>
+    <default>
+      <files>b208.js</files>
+      <baseline>b208.baseline</baseline>
+      <compile-flags> -bgjit- -simdjs -simd128typespec -mic:1 -lic:1 -off:simplejit</compile-flags>
+    </default>
+  </test>
+  <test>
+    <default>
+      <files>b208_asmjs.js</files>
+      <baseline>b208_asmjs.baseline</baseline>
+      <tags>exclude_dynapogo,exclude_ship</tags>
+      <compile-flags>-simdjs -AsmJsStopOnError -maic:0</compile-flags>
+    </default>
+  </test> 
+  <test>
+    <default>
+      <files>b208_asmjs.js</files>
+      <baseline>b208_asmjs.baseline</baseline>
+      <tags>exclude_dynapogo,exclude_ship</tags>
+      <compile-flags> -bgjit- -simdjs -simd128typespec -asmjs- -mic:1 -lic:1 -off:simplejit</compile-flags>
+    </default>
+  </test>
 </regress-exe>