Test only low 8 bits for bool return values (bug 733248, r=pierron).
authorDavid Anderson <danderson@mozilla.com>
Mon, 12 Mar 2012 16:46:18 -0700
changeset 89960 1052d3eb7a7849a1bb15520982704bba4cedebee
parent 89959 79b5d9b66d9a68117abbda7f3a8ed87fb99d52ce
child 89961 76e469f863aed3bc776e4865977aab92c50889c9
push id712
push userdanderson@mozilla.com
push dateMon, 12 Mar 2012 23:50:57 +0000
reviewerspierron
bugs733248
milestone13.0a1
Test only low 8 bits for bool return values (bug 733248, r=pierron).
js/src/assembler/assembler/X86Assembler.h
js/src/ion/shared/Assembler-x86-shared.h
js/src/ion/x64/Trampoline-x64.cpp
js/src/ion/x86/Trampoline-x86.cpp
--- a/js/src/assembler/assembler/X86Assembler.h
+++ b/js/src/assembler/assembler/X86Assembler.h
@@ -221,16 +221,17 @@ private:
 #endif
         PRE_OPERAND_SIZE                = 0x66,
         PRE_SSE_66                      = 0x66,
         OP_PUSH_Iz                      = 0x68,
         OP_IMUL_GvEvIz                  = 0x69,
         OP_GROUP1_EbIb                  = 0x80,
         OP_GROUP1_EvIz                  = 0x81,
         OP_GROUP1_EvIb                  = 0x83,
+        OP_TEST_EbGb                    = 0x84,
         OP_TEST_EvGv                    = 0x85,
         OP_XCHG_EvGv                    = 0x87,
         OP_MOV_EbGv                     = 0x88,
         OP_MOV_EvGv                     = 0x89,
         OP_MOV_GvEv                     = 0x8B,
         OP_LEA                          = 0x8D,
         OP_GROUP1A_Ev                   = 0x8F,
         OP_NOP                          = 0x90,
@@ -1266,16 +1267,24 @@ public:
 
     void testl_rr(RegisterID src, RegisterID dst)
     {
         js::JaegerSpew(js::JSpew_Insns,
                        IPFX "testl      %s, %s\n", MAYBE_PAD,
                        nameIReg(4,src), nameIReg(4,dst));
         m_formatter.oneByteOp(OP_TEST_EvGv, src, dst);
     }
+
+    void testb_rr(RegisterID src, RegisterID dst)
+    {
+        js::JaegerSpew(js::JSpew_Insns,
+                       IPFX "testb      %s, %s\n", MAYBE_PAD,
+                       nameIReg(1,src), nameIReg(1,dst));
+        m_formatter.oneByteOp(OP_TEST_EbGb, src, dst);
+    }
     
     void testl_i32r(int imm, RegisterID dst)
     {
         js::JaegerSpew(js::JSpew_Insns,
                        IPFX "testl      $0x%x, %s\n", MAYBE_PAD,
                        imm, nameIReg(dst));
         m_formatter.oneByteOp(OP_GROUP3_EvIz, GROUP3_OP_TEST, dst);
         m_formatter.immediate32(imm);
--- a/js/src/ion/shared/Assembler-x86-shared.h
+++ b/js/src/ion/shared/Assembler-x86-shared.h
@@ -496,16 +496,21 @@ class AssemblerX86Shared
             break;
           default:
             JS_NOT_REACHED("unexpected operand kind");
         }
     }
     void setCC(Condition cond, const Register &r) {
         masm.setCC_r(static_cast<JSC::X86Assembler::Condition>(cond), r.code());
     }
+    void testb(const Register &lhs, const Register &rhs) {
+        JS_ASSERT(GeneralRegisterSet(Registers::SingleByteRegs).has(lhs));
+        JS_ASSERT(GeneralRegisterSet(Registers::SingleByteRegs).has(rhs));
+        masm.testb_rr(rhs.code(), lhs.code());
+    }
     void testl(const Register &lhs, const Register &rhs) {
         masm.testl_rr(rhs.code(), lhs.code());
     }
     void testl(const Register &lhs, Imm32 rhs) {
         masm.testl_i32r(rhs.value, lhs.code());
     }
     void testl(const Operand &lhs, Imm32 rhs) {
         switch (lhs.kind()) {
--- a/js/src/ion/x64/Trampoline-x64.cpp
+++ b/js/src/ion/x64/Trampoline-x64.cpp
@@ -564,17 +564,18 @@ IonCompartment::generateVMWrapper(JSCont
     // Test for failure.
     Label exception;
     switch (f.failType()) {
       case Type_Object:
         masm.testq(rax, rax);
         masm.j(Assembler::Zero, &exception);
         break;
       case Type_Bool:
-        masm.branchTest32(Assembler::Zero, eax, eax, &exception);
+        masm.testb(rax, rax);
+        masm.j(Assembler::Zero, &exception);
         break;
       default:
         JS_NOT_REACHED("unknown failure kind");
         break;
     }
 
     // Load the outparam and free any allocated stack.
     switch (f.outParam) {
--- a/js/src/ion/x86/Trampoline-x86.cpp
+++ b/js/src/ion/x86/Trampoline-x86.cpp
@@ -583,17 +583,29 @@ IonCompartment::generateVMWrapper(JSCont
     // Copy the implicit outparam, if any.
     if (outReg != InvalidReg)
         masm.passABIArg(outReg);
 
     masm.callWithABI(f.wrapped);
 
     // Test for failure.
     Label exception;
-    masm.branchTest32(Assembler::Zero, eax, eax, &exception);
+    switch (f.failType()) {
+      case Type_Object:
+        masm.testl(eax, eax);
+        masm.j(Assembler::Zero, &exception);
+        break;
+      case Type_Bool:
+        masm.testb(eax, eax);
+        masm.j(Assembler::Zero, &exception);
+        break;
+      default:
+        JS_NOT_REACHED("unknown failure kind");
+        break;
+    }
 
     // Load the outparam and free any allocated stack.
     switch (f.outParam) {
       case Type_Value:
         masm.loadValue(Address(esp, 0), JSReturnOperand);
         masm.freeStack(sizeof(Value));
         break;