Bug 1460895: Deduplicate MegamorphicLoadSlotResult using EmitLoadStubField r=jandem
authorMatthew Gaudet <mgaudet@mozilla.com>
Tue, 30 Jan 2018 14:35:30 -0500
changeset 794957 9eb850fd168812a2a8f427814335fdd93ab64ae5
parent 794956 5d368658145949915eaaa095275cc20a6fa76748
child 794958 0f5b9cd3d7107aa8d744036247d56dc9576e1dcf
push id109827
push usermozilla@noorenberghe.ca
push dateMon, 14 May 2018 20:13:54 +0000
reviewersjandem
bugs1460895
milestone62.0a1
Bug 1460895: Deduplicate MegamorphicLoadSlotResult using EmitLoadStubField r=jandem Also rename helper method to match pre-existing spidermonkey style.
js/src/jit/BaselineCacheIRCompiler.cpp
js/src/jit/CacheIRCompiler.cpp
js/src/jit/CacheIRCompiler.h
js/src/jit/IonCacheIRCompiler.cpp
--- a/js/src/jit/BaselineCacheIRCompiler.cpp
+++ b/js/src/jit/BaselineCacheIRCompiler.cpp
@@ -539,68 +539,16 @@ BaselineCacheIRCompiler::emitLoadDynamic
 
     masm.load32(stubAddress(reader.stubOffset()), scratch);
     masm.loadPtr(Address(obj, NativeObject::offsetOfSlots()), scratch2);
     masm.loadValue(BaseIndex(scratch2, scratch, TimesOne), output.valueReg());
     return true;
 }
 
 bool
-BaselineCacheIRCompiler::emitMegamorphicLoadSlotResult()
-{
-    AutoOutputRegister output(*this);
-
-    Register obj = allocator.useRegister(masm, reader.objOperandId());
-    Address nameAddr = stubAddress(reader.stubOffset());
-    bool handleMissing = reader.readBool();
-
-    AutoScratchRegisterMaybeOutput scratch1(allocator, masm, output);
-    AutoScratchRegister scratch2(allocator, masm);
-    AutoScratchRegister scratch3(allocator, masm);
-
-    FailurePath* failure;
-    if (!addFailurePath(&failure))
-        return false;
-
-    // The object must be Native.
-    masm.branchIfNonNativeObj(obj, scratch3, failure->label());
-
-    masm.Push(UndefinedValue());
-    masm.moveStackPtrTo(scratch3.get());
-
-    LiveRegisterSet volatileRegs(GeneralRegisterSet::Volatile(), liveVolatileFloatRegs());
-    volatileRegs.takeUnchecked(scratch1);
-    volatileRegs.takeUnchecked(scratch2);
-    volatileRegs.takeUnchecked(scratch3);
-    masm.PushRegsInMask(volatileRegs);
-
-    masm.setupUnalignedABICall(scratch1);
-    masm.loadJSContext(scratch1);
-    masm.passABIArg(scratch1);
-    masm.passABIArg(obj);
-    masm.loadPtr(nameAddr, scratch2);
-    masm.passABIArg(scratch2);
-    masm.passABIArg(scratch3);
-    if (handleMissing)
-        masm.callWithABI(JS_FUNC_TO_DATA_PTR(void*, (GetNativeDataProperty<true>)));
-    else
-        masm.callWithABI(JS_FUNC_TO_DATA_PTR(void*, (GetNativeDataProperty<false>)));
-    masm.mov(ReturnReg, scratch2);
-    masm.PopRegsInMask(volatileRegs);
-
-    masm.loadTypedOrValue(Address(masm.getStackPointer(), 0), output);
-    masm.adjustStack(sizeof(Value));
-
-    masm.branchIfFalseBool(scratch2, failure->label());
-    if (JitOptions.spectreJitToCxxCalls)
-        masm.speculationBarrier();
-    return true;
-}
-
-bool
 BaselineCacheIRCompiler::emitMegamorphicStoreSlot()
 {
     Register obj = allocator.useRegister(masm, reader.objOperandId());
     Address nameAddr = stubAddress(reader.stubOffset());
     ValueOperand val = allocator.useValueRegister(masm, reader.valOperandId());
     bool needsTypeBarrier = reader.readBool();
 
     AutoScratchRegister scratch1(allocator, masm);
--- a/js/src/jit/CacheIRCompiler.cpp
+++ b/js/src/jit/CacheIRCompiler.cpp
@@ -2932,17 +2932,17 @@ CacheIRCompiler::emitCallObjectHasSparse
     masm.loadTypedOrValue(Address(masm.getStackPointer(), 0), output);
     masm.adjustStack(sizeof(Value));
     return true;
 }
 
 /*
  * Move a constant value into register dest.
  */
-void CacheIRCompiler::EmitLoadStubFieldConstant(StubFieldOffset val, Register dest) {
+void CacheIRCompiler::emitLoadStubFieldConstant(StubFieldOffset val, Register dest) {
     MOZ_ASSERT(mode_ == Mode::Ion);
     switch (val.getStubFieldType()) {
       case StubField::Type::Shape:
         masm.movePtr(ImmGCPtr(shapeStubField(val.getOffset())),dest);
         break;
       case StubField::Type::String:
         masm.movePtr(ImmGCPtr(stringStubField(val.getOffset())), dest);
         break;
@@ -2954,19 +2954,19 @@ void CacheIRCompiler::EmitLoadStubFieldC
 /*
  * After this is done executing, dest contains the value; either through a constant load
  * or through the load from the stub data.
  *
  * The current policy is that Baseline will use loads from the stub data (to allow IC
  * sharing), where as Ion doesn't share ICs, and so we can safely use constants in the
  * IC.
  */
-void CacheIRCompiler::EmitLoadStubField(StubFieldOffset val, Register dest) {
+void CacheIRCompiler::emitLoadStubField(StubFieldOffset val, Register dest) {
     if (stubFieldPolicy_ == StubFieldPolicy::Constant) {
-        EmitLoadStubFieldConstant(val, dest);
+        emitLoadStubFieldConstant(val, dest);
     } else {
         Address load(ICStubReg, stubDataOffset_ + val.getOffset());
         masm.loadPtr(load, dest);
     }
 }
 
 bool
 CacheIRCompiler::emitLoadInstanceOfObjectResult()
@@ -3009,8 +3009,61 @@ CacheIRCompiler::emitLoadInstanceOfObjec
     masm.jump(&done);
 
     masm.bind(&returnTrue);
     EmitStoreBoolean(masm, true, output);
     //fallthrough
     masm.bind(&done);
     return true;
 }
+
+bool
+CacheIRCompiler::emitMegamorphicLoadSlotResult()
+{
+    AutoOutputRegister output(*this);
+
+    Register obj = allocator.useRegister(masm, reader.objOperandId());
+    StubFieldOffset name(reader.stubOffset(), StubField::Type::String);
+    bool handleMissing = reader.readBool();
+
+    AutoScratchRegisterMaybeOutput scratch1(allocator, masm, output);
+    AutoScratchRegister scratch2(allocator, masm);
+    AutoScratchRegister scratch3(allocator, masm);
+
+    FailurePath* failure;
+    if (!addFailurePath(&failure))
+        return false;
+
+    // The object must be Native.
+    masm.branchIfNonNativeObj(obj, scratch3, failure->label());
+
+    masm.Push(UndefinedValue());
+    masm.moveStackPtrTo(scratch3.get());
+
+    LiveRegisterSet volatileRegs(GeneralRegisterSet::Volatile(), liveVolatileFloatRegs());
+    volatileRegs.takeUnchecked(scratch1);
+    volatileRegs.takeUnchecked(scratch2);
+    volatileRegs.takeUnchecked(scratch3);
+    masm.PushRegsInMask(volatileRegs);
+
+    masm.setupUnalignedABICall(scratch1);
+    masm.loadJSContext(scratch1);
+    masm.passABIArg(scratch1);
+    masm.passABIArg(obj);
+    emitLoadStubField(name, scratch2);
+    masm.passABIArg(scratch2);
+    masm.passABIArg(scratch3);
+    if (handleMissing)
+        masm.callWithABI(JS_FUNC_TO_DATA_PTR(void*, (GetNativeDataProperty<true>)));
+    else
+        masm.callWithABI(JS_FUNC_TO_DATA_PTR(void*, (GetNativeDataProperty<false>)));
+    masm.mov(ReturnReg, scratch2);
+    masm.PopRegsInMask(volatileRegs);
+
+    masm.loadTypedOrValue(Address(masm.getStackPointer(), 0), output);
+    masm.adjustStack(sizeof(Value));
+
+    masm.branchIfFalseBool(scratch2, failure->label());
+    if (JitOptions.spectreJitToCxxCalls)
+        masm.speculationBarrier();
+
+    return true;
+}
\ No newline at end of file
--- a/js/src/jit/CacheIRCompiler.h
+++ b/js/src/jit/CacheIRCompiler.h
@@ -72,16 +72,17 @@ namespace jit {
     _(LoadStringTruthyResult)             \
     _(LoadObjectTruthyResult)             \
     _(CompareStringResult)                \
     _(CompareObjectResult)                \
     _(CompareSymbolResult)                \
     _(ArrayJoinResult)                    \
     _(CallPrintString)                    \
     _(Breakpoint)                         \
+    _(MegamorphicLoadSlotResult)          \
     _(MegamorphicLoadSlotByValueResult)   \
     _(MegamorphicHasPropResult)           \
     _(CallObjectHasSparseElementResult)   \
     _(WrapResult)
 
 // Represents a Value on the Baseline frame's expression stack. Slot 0 is the
 // value on top of the stack (the most recently pushed value), slot 1 is the
 // value pushed before that, etc.
@@ -654,18 +655,18 @@ class MOZ_RAII CacheIRCompiler
     }
 
     bool emitComparePointerResultShared(bool symbol);
 
 #define DEFINE_SHARED_OP(op) MOZ_MUST_USE bool emit##op();
     CACHE_IR_SHARED_OPS(DEFINE_SHARED_OP)
 #undef DEFINE_SHARED_OP
 
-    void EmitLoadStubField(StubFieldOffset val, Register dest);
-    void EmitLoadStubFieldConstant(StubFieldOffset val, Register dest);
+    void emitLoadStubField(StubFieldOffset val, Register dest);
+    void emitLoadStubFieldConstant(StubFieldOffset val, Register dest);
 
     uintptr_t readStubWord(uint32_t offset, StubField::Type type) {
         MOZ_ASSERT(stubFieldPolicy_ == StubFieldPolicy::Constant);
         MOZ_ASSERT((offset % sizeof(uintptr_t)) == 0);
         // We use nextStubField_ to access the data as it's stored in an as-of-yet
         // unpacked vector, and so using the offset can be incorrect where the index
         // would change as a result of packing.
         return writer_.readStubFieldForIon(nextStubField_++, type).asWord();
--- a/js/src/jit/IonCacheIRCompiler.cpp
+++ b/js/src/jit/IonCacheIRCompiler.cpp
@@ -926,68 +926,16 @@ IonCacheIRCompiler::emitLoadDynamicSlotR
 
     AutoScratchRegisterMaybeOutput scratch(allocator, masm, output);
     masm.loadPtr(Address(obj, NativeObject::offsetOfSlots()), scratch);
     masm.loadTypedOrValue(Address(scratch, offset), output);
     return true;
 }
 
 bool
-IonCacheIRCompiler::emitMegamorphicLoadSlotResult()
-{
-    AutoOutputRegister output(*this);
-
-    Register obj = allocator.useRegister(masm, reader.objOperandId());
-    PropertyName* name = stringStubField(reader.stubOffset())->asAtom().asPropertyName();
-    bool handleMissing = reader.readBool();
-
-    AutoScratchRegisterMaybeOutput scratch1(allocator, masm, output);
-    AutoScratchRegister scratch2(allocator, masm);
-    AutoScratchRegister scratch3(allocator, masm);
-
-    FailurePath* failure;
-    if (!addFailurePath(&failure))
-        return false;
-
-    // The object must be Native.
-    masm.branchIfNonNativeObj(obj, scratch3, failure->label());
-
-    masm.Push(UndefinedValue());
-    masm.moveStackPtrTo(scratch3.get());
-
-    LiveRegisterSet volatileRegs(GeneralRegisterSet::Volatile(), liveVolatileFloatRegs());
-    volatileRegs.takeUnchecked(scratch1);
-    volatileRegs.takeUnchecked(scratch2);
-    volatileRegs.takeUnchecked(scratch3);
-    masm.PushRegsInMask(volatileRegs);
-
-    masm.setupUnalignedABICall(scratch1);
-    masm.loadJSContext(scratch1);
-    masm.passABIArg(scratch1);
-    masm.passABIArg(obj);
-    masm.movePtr(ImmGCPtr(name), scratch2);
-    masm.passABIArg(scratch2);
-    masm.passABIArg(scratch3);
-    if (handleMissing)
-        masm.callWithABI(JS_FUNC_TO_DATA_PTR(void*, (GetNativeDataProperty<true>)));
-    else
-        masm.callWithABI(JS_FUNC_TO_DATA_PTR(void*, (GetNativeDataProperty<false>)));
-    masm.mov(ReturnReg, scratch2);
-    masm.PopRegsInMask(volatileRegs);
-
-    masm.loadTypedOrValue(Address(masm.getStackPointer(), 0), output);
-    masm.adjustStack(sizeof(Value));
-
-    masm.branchIfFalseBool(scratch2, failure->label());
-    if (JitOptions.spectreJitToCxxCalls)
-        masm.speculationBarrier();
-    return true;
-}
-
-bool
 IonCacheIRCompiler::emitMegamorphicStoreSlot()
 {
     Register obj = allocator.useRegister(masm, reader.objOperandId());
     PropertyName* name = stringStubField(reader.stubOffset())->asAtom().asPropertyName();
     ValueOperand val = allocator.useValueRegister(masm, reader.valOperandId());
     bool needsTypeBarrier = reader.readBool();
 
     AutoScratchRegister scratch1(allocator, masm);