Bug 1301400: Baseline Wasm Compiler: Part 20: Don't fully generalize when functions are not yet available on every platform, r=lth
authorh4writer <hv1989@gmail.com>
Thu, 29 Sep 2016 22:33:23 +0200
changeset 315920 9643bfae6b315489c3fbafc7fac15d5e241ca585
parent 315919 ef4dbc8dc886d39bea1bb5042694501c0f5d2263
child 315921 8b70b53f6f27a27716706ed305ff69cb17b59606
push id20634
push usercbook@mozilla.com
push dateFri, 30 Sep 2016 10:10:13 +0000
treeherderfx-team@afe79b010d13 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewerslth
bugs1301400
milestone52.0a1
Bug 1301400: Baseline Wasm Compiler: Part 20: Don't fully generalize when functions are not yet available on every platform, r=lth
js/src/asmjs/WasmBaselineCompile.cpp
--- a/js/src/asmjs/WasmBaselineCompile.cpp
+++ b/js/src/asmjs/WasmBaselineCompile.cpp
@@ -2117,24 +2117,26 @@ class BaseCompiler
                 loadI32(argLoc.gpr(), arg);
             }
             break;
           }
           case ValType::I64: {
             ABIArg argLoc = call.abi_.next(MIRType::Int64);
             if (argLoc.kind() == ABIArg::Stack) {
                 ScratchI32 scratch(*this);
-#ifdef JS_PUNBOX64
+#if defined(JS_CODEGEN_X64)
                 loadI64(Register64(scratch), arg);
                 masm.movq(scratch, Operand(StackPointer, argLoc.offsetFromArgBase()));
-#else
+#elif defined(JS_CODEGEN_X86)
                 loadI64Low(scratch, arg);
                 masm.move32(scratch, Operand(StackPointer, argLoc.offsetFromArgBase() + INT64LOW_OFFSET));
                 loadI64High(scratch, arg);
                 masm.move32(scratch, Operand(StackPointer, argLoc.offsetFromArgBase() + INT64HIGH_OFFSET));
+#else
+                MOZ_CRASH("BaseCompiler platform hook: passArg I64");
 #endif
             } else {
                 loadI64(argLoc.gpr64(), arg);
             }
             break;
           }
           case ValType::F64: {
             ABIArg argLoc = call.abi_.next(MIRType::Double);
@@ -2364,25 +2366,33 @@ class BaseCompiler
 
     void returnF32(RegF32 r) {
         moveF32(r, RegF32(ReturnFloat32Reg));
         popStackBeforeBranch(ctl_[0].framePushed);
         masm.jump(&returnLabel_);
     }
 
     void subtractI64(RegI64 rhs, RegI64 srcDest) {
+#if defined(JS_CODEGEN_X64) || defined(JS_CODEGEN_X86)
         masm.sub64(rhs.reg, srcDest.reg);
+#else
+        MOZ_CRASH("BaseCompiler platform hook: subtractI64");
+#endif
     }
 
     void multiplyI64(RegI64 rhs, RegI64 srcDest, RegI32 temp) {
 #if defined(JS_CODEGEN_X64)
         MOZ_ASSERT(srcDest.reg.reg == rax);
         MOZ_ASSERT(isAvailable(rdx));
+        masm.mul64(rhs.reg, srcDest.reg, temp.reg);
+#elif defined(JS_CODEGEN_X86)
+        masm.mul64(rhs.reg, srcDest.reg, temp.reg);
+#else
+        MOZ_CRASH("BaseCompiler platform hook: multiplyI64");
 #endif
-        masm.mul64(rhs.reg, srcDest.reg, temp.reg);
     }
 
     void checkDivideByZeroI32(RegI32 rhs, RegI32 srcDest, Label* done) {
         if (isCompilingAsmJS()) {
             // Truncated division by zero is zero (Infinity|0 == 0)
             Label notDivByZero;
             masm.branchTest32(Assembler::NonZero, rhs.reg, rhs.reg, &notDivByZero);
             masm.move32(Imm32(0), srcDest.reg);
@@ -2393,22 +2403,24 @@ class BaseCompiler
         }
     }
 
     void checkDivideByZeroI64(RegI64 rhs, RegI64 srcDest, Label* done) {
         MOZ_ASSERT(!isCompilingAsmJS());
 #ifdef JS_CODEGEN_X64
         masm.testq(rhs.reg.reg, rhs.reg.reg);
         masm.j(Assembler::Zero, wasm::JumpTarget::IntegerDivideByZero);
-#else
+#elif defined(JS_CODEGEN_X86)
         Label nonZero;
         masm.branchTest32(Assembler::NonZero, rhs.reg.low, rhs.reg.low, &nonZero);
         masm.branchTest32(Assembler::Zero, rhs.reg.high, rhs.reg.high,
                           wasm::JumpTarget::IntegerDivideByZero);
         masm.bind(&nonZero);
+#else
+        MOZ_CRASH("BaseCompiler platform hook: checkDivideByZeroI64");
 #endif
     }
 
     void checkDivideSignedOverflowI32(RegI32 rhs, RegI32 srcDest, Label* done, bool zeroOnOverflow) {
         Label notMin;
         masm.branch32(Assembler::NotEqual, srcDest.reg, Imm32(INT32_MIN), &notMin);
         if (zeroOnOverflow) {
             masm.branch32(Assembler::NotEqual, rhs.reg, Imm32(-1), &notMin);
@@ -2419,26 +2431,30 @@ class BaseCompiler
             masm.branch32(Assembler::Equal, rhs.reg, Imm32(-1), done);
         } else {
             masm.branch32(Assembler::Equal, rhs.reg, Imm32(-1), wasm::JumpTarget::IntegerOverflow);
         }
         masm.bind(&notMin);
     }
 
     void checkDivideSignedOverflowI64(RegI64 rhs, RegI64 srcDest, Label* done, bool zeroOnOverflow) {
+#if defined(JS_CODEGEN_X64) || defined(JS_CODEGEN_X86)
         MOZ_ASSERT(!isCompilingAsmJS());
         Label notmin;
         masm.branch64(Assembler::NotEqual, srcDest.reg, Imm64(INT64_MIN), &notmin);
         masm.branch64(Assembler::NotEqual, rhs.reg, Imm64(-1), &notmin);
         if (zeroOnOverflow)
             masm.xor64(srcDest.reg, srcDest.reg);
         else
             masm.jump(wasm::JumpTarget::IntegerOverflow);
         masm.jump(done);
         masm.bind(&notmin);
+#else
+        MOZ_CRASH("BaseCompiler platform hook: checkDivideSignedOverflowI64");
+#endif
     }
 
     void quotientI64(RegI64 rhs, RegI64 srcDest, IsUnsigned isUnsigned) {
         // This follows quotientI32, above.
         Label done;
 
         checkDivideByZeroI64(rhs, srcDest, &done);
 
@@ -2489,78 +2505,96 @@ class BaseCompiler
         masm.bind(&done);
     }
 
     void orI64(RegI64 rhs, RegI64 srcDest) {
         masm.or64(rhs.reg, srcDest.reg);
     }
 
     void andI64(RegI64 rhs, RegI64 srcDest) {
+#if defined(JS_CODEGEN_X64) || defined(JS_CODEGEN_X86) || defined(JS_CODEGEN_ARM)
         masm.and64(rhs.reg, srcDest.reg);
+#else
+        MOZ_CRASH("BaseCompiler platform hook: andI64");
+#endif
     }
 
     void xorI64(RegI64 rhs, RegI64 srcDest) {
         masm.xor64(rhs.reg, srcDest.reg);
     }
 
     void lshiftI64(RegI64 shift, RegI64 srcDest) {
-#ifdef JS_PUNBOX64
+#if defined(JS_CODEGEN_X64)
         masm.lshift64(shift.reg.reg, srcDest.reg);
+#elif defined(JS_CODEGEN_X86) || defined(JS_CODEGEN_ARM)
+        masm.lshift64(shift.reg.low, srcDest.reg);
 #else
-        masm.lshift64(shift.reg.low, srcDest.reg);
+        MOZ_CRASH("BaseCompiler platform hook: lshiftI64");
 #endif
     }
 
     void rshiftI64(RegI64 shift, RegI64 srcDest) {
-#ifdef JS_PUNBOX64
+#if defined(JS_CODEGEN_X64)
         masm.rshift64Arithmetic(shift.reg.reg, srcDest.reg);
+#elif defined(JS_CODEGEN_X86) || defined(JS_CODEGEN_ARM)
+        masm.rshift64Arithmetic(shift.reg.low, srcDest.reg);
 #else
-        masm.rshift64Arithmetic(shift.reg.low, srcDest.reg);
+        MOZ_CRASH("BaseCompiler platform hook: rshiftI64");
 #endif
     }
 
     void rshiftU64(RegI64 shift, RegI64 srcDest) {
-#ifdef JS_PUNBOX64
+#if defined(JS_CODEGEN_X64)
         masm.rshift64(shift.reg.reg, srcDest.reg);
+#elif defined(JS_CODEGEN_X86) || defined(JS_CODEGEN_ARM)
+        masm.rshift64(shift.reg.low, srcDest.reg);
 #else
-        masm.rshift64(shift.reg.low, srcDest.reg);
+        MOZ_CRASH("BaseCompiler platform hook: rshiftU64");
 #endif
     }
 
     void rotateRightI64(RegI64 shift, RegI64 srcDest) {
-#ifdef JS_PUNBOX64
+#if defined(JS_CODEGEN_X64)
         masm.rotateRight64(shift.reg.reg, srcDest.reg, srcDest.reg, Register::Invalid());
+#elif defined(JS_CODEGEN_X86) || defined(JS_CODEGEN_ARM)
+        masm.rotateRight64(shift.reg.low, srcDest.reg, srcDest.reg, shift.reg.high);
 #else
-        masm.rotateRight64(shift.reg.low, srcDest.reg, srcDest.reg, shift.reg.high);
+        MOZ_CRASH("BaseCompiler platform hook: rotateRightI64");
 #endif
     }
 
     void rotateLeftI64(RegI64 shift, RegI64 srcDest) {
-#ifdef JS_PUNBOX64
+#if defined(JS_CODEGEN_X64)
         masm.rotateLeft64(shift.reg.reg, srcDest.reg, srcDest.reg, Register::Invalid());
+#elif defined(JS_CODEGEN_X86) || defined(JS_CODEGEN_ARM)
+        masm.rotateLeft64(shift.reg.low, srcDest.reg, srcDest.reg, shift.reg.high);
 #else
-        masm.rotateLeft64(shift.reg.low, srcDest.reg, srcDest.reg, shift.reg.high);
+        MOZ_CRASH("BaseCompiler platform hook: rotateLeftI64");
 #endif
     }
 
     void clzI64(RegI64 srcDest) {
-#ifdef JS_PUNBOX64
+#if defined(JS_CODEGEN_X64)
         masm.clz64(srcDest.reg, srcDest.reg.reg);
-#else
+#elif defined(JS_CODEGEN_X86) || defined(JS_CODEGEN_ARM)
         masm.clz64(srcDest.reg, srcDest.reg.low);
         masm.move32(Imm32(0), srcDest.reg.high);
+#else
+        MOZ_CRASH("BaseCompiler platform hook: clzI64");
 #endif
     }
 
     void ctzI64(RegI64 srcDest) {
-#ifdef JS_PUNBOX64
+#if defined(JS_CODEGEN_X64)
         masm.ctz64(srcDest.reg, srcDest.reg.reg);
-#else
+#elif defined(JS_CODEGEN_X86) || defined(JS_CODEGEN_ARM)
         masm.ctz64(srcDest.reg, srcDest.reg.low);
         masm.move32(Imm32(0), srcDest.reg.high);
+#else
+        MOZ_CRASH("BaseCompiler platform hook: ctzI64");
 #endif
     }
 
     bool popcnt32NeedsTemp() const {
 #if defined(JS_CODEGEN_X86) || defined(JS_CODEGEN_X64)
         return !AssemblerX86Shared::HasPOPCNT();
 #else
         MOZ_CRASH("BaseCompiler platform hook: popcnt32NeedsTemp");
@@ -2579,17 +2613,21 @@ class BaseCompiler
 #if defined(JS_CODEGEN_X86) || defined(JS_CODEGEN_X64)
         return !AssemblerX86Shared::HasPOPCNT();
 #else
         MOZ_CRASH("BaseCompiler platform hook: popcnt64NeedsTemp");
 #endif
     }
 
     void popcntI64(RegI64 srcDest, RegI32 tmp) {
+#if defined(JS_CODEGEN_X86) || defined(JS_CODEGEN_X64) || defined(JS_CODEGEN_ARM)
         masm.popcnt64(srcDest.reg, srcDest.reg, tmp.reg);
+#else
+        MOZ_CRASH("BaseCompiler platform hook: popcntI64");
+#endif
     }
 
     void reinterpretI64AsF64(RegI64 src, RegF64 dest) {
 #if defined(JS_CODEGEN_X64)
         masm.vmovq(src.reg.reg, dest.reg);
 #elif defined(JS_CODEGEN_X86)
         masm.Push(src.reg.high);
         masm.Push(src.reg.low);
@@ -2875,24 +2913,26 @@ class BaseCompiler
         masm.append(GlobalAccess(label, globalDataOffset));
 #else
         MOZ_CRASH("BaseCompiler platform hook: loadGlobalVarI32");
 #endif
     }
 
     void loadGlobalVarI64(unsigned globalDataOffset, RegI64 r)
     {
-#if defined(JS_PUNBOX64)
+#if defined(JS_CODEGEN_X64)
         CodeOffset label = masm.loadRipRelativeInt64(r.reg.reg);
         masm.append(GlobalAccess(label, globalDataOffset));
-#else
+#elif defined(JS_CODEGEN_X86)
         CodeOffset labelLow = masm.movlWithPatch(PatchedAbsoluteAddress(), r.reg.low);
         masm.append(GlobalAccess(labelLow, globalDataOffset + INT64LOW_OFFSET));
         CodeOffset labelHigh = masm.movlWithPatch(PatchedAbsoluteAddress(), r.reg.high);
         masm.append(GlobalAccess(labelHigh, globalDataOffset + INT64HIGH_OFFSET));
+#else
+        MOZ_CRASH("BaseCompiler platform hook: loadGlobalVarI64");
 #endif
     }
 
     void loadGlobalVarF32(unsigned globalDataOffset, RegF32 r)
     {
 #if defined(JS_CODEGEN_X64)
         CodeOffset label = masm.loadRipRelativeFloat32(r.reg);
         masm.append(GlobalAccess(label, globalDataOffset));
@@ -3610,43 +3650,43 @@ BaseCompiler::emitQuotientI64()
 #endif
 }
 
 void
 BaseCompiler::emitQuotientU64()
 {
 #ifdef JS_PUNBOX64
     RegI64 r0, r1;
- #ifdef JS_CODEGEN_X64
+# ifdef JS_CODEGEN_X64
     // srcDest must be rax, and rdx will be clobbered.
     need2xI64(specific_rax, specific_rdx);
     r1 = popI64();
     r0 = popI64ToSpecific(specific_rax);
     freeI64(specific_rdx);
- #else
+# else
     pop2xI64(&r0, &r1);
- #endif
+# endif
     quotientI64(r1, r0, IsUnsigned(true));
     freeI64(r1);
     pushI64(r0);
 #else
- #if defined(JS_CODEGEN_X86)
+# if defined(JS_CODEGEN_X86)
     RegI64 r0, r1;
     RegI32 temp;
     needI64(abiReturnRegI64);
     temp = needI32();
     r1 = popI64();
     r0 = popI64ToSpecific(abiReturnRegI64);
     emitDivOrModI64BuiltinCall(SymbolicAddress::UDivI64, r1, r0, temp);
     freeI32(temp);
     freeI64(r1);
     pushI64(r0);
- #else
+# else
     MOZ_CRASH("BaseCompiler platform hook: emitQuotientU64");
- #endif
+# endif
 #endif
 }
 
 void
 BaseCompiler::emitRemainderI32()
 {
     // TODO / OPTIMIZE: Fast case if lhs >= 0 and rhs is power of two.
     RegI32 r0, r1;
@@ -3694,76 +3734,76 @@ BaseCompiler::emitRemainderU32()
     pushI32(r0);
 }
 
 void
 BaseCompiler::emitRemainderI64()
 {
 #ifdef JS_PUNBOX64
     RegI64 r0, r1;
- #ifdef JS_CODEGEN_X64
+# ifdef JS_CODEGEN_X64
     need2xI64(specific_rax, specific_rdx);
     r1 = popI64();
     r0 = popI64ToSpecific(specific_rax);
     freeI64(specific_rdx);
- #else
+# else
     pop2xI64(&r0, &r1);
- #endif
+# endif
     remainderI64(r1, r0, IsUnsigned(false));
     freeI64(r1);
     pushI64(r0);
 #else
- #if defined(JS_CODEGEN_X86)
+# if defined(JS_CODEGEN_X86)
     RegI64 r0, r1;
     RegI32 temp;
     needI64(abiReturnRegI64);
     temp = needI32();
     r1 = popI64();
     r0 = popI64ToSpecific(abiReturnRegI64);
     emitDivOrModI64BuiltinCall(SymbolicAddress::ModI64, r1, r0, temp);
     freeI32(temp);
     freeI64(r1);
     pushI64(r0);
- #else
+# else
     MOZ_CRASH("BaseCompiler platform hook: emitRemainderI64");
- #endif
+# endif
 #endif
 }
 
 void
 BaseCompiler::emitRemainderU64()
 {
 #ifdef JS_PUNBOX64
     RegI64 r0, r1;
- #ifdef JS_CODEGEN_X64
+# ifdef JS_CODEGEN_X64
     need2xI64(specific_rax, specific_rdx);
     r1 = popI64();
     r0 = popI64ToSpecific(specific_rax);
     freeI64(specific_rdx);
- #else
+# else
     pop2xI64(&r0, &r1);
- #endif
+# endif
     remainderI64(r1, r0, IsUnsigned(true));
     freeI64(r1);
     pushI64(r0);
 #else
- #if defined(JS_CODEGEN_X86)
+# if defined(JS_CODEGEN_X86)
     RegI64 r0, r1;
     RegI32 temp;
     needI64(abiReturnRegI64);
     temp = needI32();
     r1 = popI64();
     r0 = popI64ToSpecific(abiReturnRegI64);
     emitDivOrModI64BuiltinCall(SymbolicAddress::UModI64, r1, r0, temp);
     freeI32(temp);
     freeI64(r1);
     pushI64(r0);
- #else
+# else
     MOZ_CRASH("BaseCompiler platform hook: emitRemainderU64");
- #endif
+# endif
 #endif
 }
 
 void
 BaseCompiler::emitDivideF32()
 {
     RegF32 r0, r1;
     pop2xF32(&r0, &r1);