Bug 1227263 part 1 - Rename frame thisValue methods to thisArgument. r=shu
authorJan de Mooij <jdemooij@mozilla.com>
Thu, 26 Nov 2015 12:00:04 +0100
changeset 308465 b5ecca6e060ce1464a58bbb87bbc872573af4914
parent 308464 20fe83d4949d5a5be9d91c319fe86b4f7ac993b7
child 308466 cc18f42e01686b6b7d608ea91406f09a20e624dc
push id5513
push userraliiev@mozilla.com
push dateMon, 25 Jan 2016 13:55:34 +0000
treeherdermozilla-beta@5ee97dd05b5c [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersshu
bugs1227263
milestone45.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1227263 part 1 - Rename frame thisValue methods to thisArgument. r=shu
js/src/jit/BaselineBailouts.cpp
js/src/jit/BaselineFrame.cpp
js/src/jit/BaselineFrame.h
js/src/jit/BaselineJIT.cpp
js/src/jit/IonBuilder.cpp
js/src/jit/JitFrameIterator.h
js/src/jit/RematerializedFrame.cpp
js/src/jit/RematerializedFrame.h
js/src/jsobj.cpp
js/src/vm/GeneratorObject.cpp
js/src/vm/Interpreter.cpp
js/src/vm/ScopeObject.cpp
js/src/vm/Stack-inl.h
js/src/vm/Stack.cpp
js/src/vm/Stack.h
js/src/vm/TypeInference.cpp
--- a/js/src/jit/BaselineBailouts.cpp
+++ b/js/src/jit/BaselineBailouts.cpp
@@ -1715,17 +1715,19 @@ CopyFromRematerializedFrame(JSContext* c
     // Debugger.Frame for it.
     if (!rematFrame)
         return true;
 
     MOZ_ASSERT(rematFrame->script() == frame->script());
     MOZ_ASSERT(rematFrame->numActualArgs() == frame->numActualArgs());
 
     frame->setScopeChain(rematFrame->scopeChain());
-    frame->thisValue() = rematFrame->thisValue();
+
+    if (frame->isNonEvalFunctionFrame())
+        frame->thisArgument() = rematFrame->thisArgument();
 
     for (unsigned i = 0; i < frame->numActualArgs(); i++)
         frame->argv()[i] = rematFrame->argv()[i];
 
     for (size_t i = 0; i < frame->script()->nfixed(); i++)
         *frame->valueSlot(i) = rematFrame->locals()[i];
 
     if (rematFrame->hasCachedSavedFrame())
--- a/js/src/jit/BaselineFrame.cpp
+++ b/js/src/jit/BaselineFrame.cpp
@@ -27,20 +27,20 @@ MarkLocals(BaselineFrame* frame, JSTrace
     }
 }
 
 void
 BaselineFrame::trace(JSTracer* trc, JitFrameIterator& frameIterator)
 {
     replaceCalleeToken(MarkCalleeToken(trc, calleeToken()));
 
-    TraceRoot(trc, &thisValue(), "baseline-this");
+    // Mark |this|, actual and formal args.
+    if (isNonEvalFunctionFrame()) {
+        TraceRoot(trc, &thisArgument(), "baseline-this");
 
-    // Mark actual and formal args.
-    if (isNonEvalFunctionFrame()) {
         unsigned numArgs = js::Max(numActualArgs(), numFormalArgs());
         TraceRootRange(trc, numArgs + isConstructing(), argv(), "baseline-args");
     }
 
     // Mark scope chain, if it exists.
     if (scopeChain_)
         TraceRoot(trc, &scopeChain_, "baseline-scopechain");
 
--- a/js/src/jit/BaselineFrame.h
+++ b/js/src/jit/BaselineFrame.h
@@ -206,17 +206,18 @@ class BaselineFrame
     unsigned numActualArgs() const {
         return *(size_t*)(reinterpret_cast<const uint8_t*>(this) +
                              BaselineFrame::Size() +
                              offsetOfNumActualArgs());
     }
     unsigned numFormalArgs() const {
         return script()->functionNonDelazifying()->nargs();
     }
-    Value& thisValue() const {
+    Value& thisArgument() const {
+        MOZ_ASSERT(isNonEvalFunctionFrame());
         return *(Value*)(reinterpret_cast<const uint8_t*>(this) +
                          BaselineFrame::Size() +
                          offsetOfThis());
     }
     Value* argv() const {
         return (Value*)(reinterpret_cast<const uint8_t*>(this) +
                          BaselineFrame::Size() +
                          offsetOfArg(0));
--- a/js/src/jit/BaselineJIT.cpp
+++ b/js/src/jit/BaselineJIT.cpp
@@ -193,17 +193,17 @@ jit::EnterBaselineAtBranch(JSContext* cx
     if (fp->isNonEvalFunctionFrame()) {
         data.constructing = fp->isConstructing();
         data.numActualArgs = fp->numActualArgs();
         data.maxArgc = Max(fp->numActualArgs(), fp->numFormalArgs()) + 1; // +1 = include |this|
         data.maxArgv = fp->argv() - 1; // -1 = include |this|
         data.scopeChain = nullptr;
         data.calleeToken = CalleeToToken(&fp->callee(), data.constructing);
     } else {
-        thisv = fp->thisValue();
+        thisv.setUndefined();
         data.constructing = false;
         data.numActualArgs = 0;
         data.maxArgc = 1;
         data.maxArgv = thisv.address();
         data.scopeChain = fp->scopeChain();
 
         // For eval function frames, set the callee token to the enclosing function.
         if (fp->isFunctionFrame())
--- a/js/src/jit/IonBuilder.cpp
+++ b/js/src/jit/IonBuilder.cpp
@@ -70,17 +70,18 @@ jit::NewBaselineFrameInspector(TempAlloc
     BaselineFrameInspector* inspector = temp->lifoAlloc()->new_<BaselineFrameInspector>(temp);
     if (!inspector)
         return nullptr;
 
     // Note: copying the actual values into a temporary structure for use
     // during compilation could capture nursery pointers, so the values' types
     // are recorded instead.
 
-    inspector->thisType = TypeSet::GetMaybeUntrackedValueType(frame->thisValue());
+    if (frame->isNonEvalFunctionFrame())
+        inspector->thisType = TypeSet::GetMaybeUntrackedValueType(frame->thisArgument());
 
     if (frame->scopeChain()->isSingleton())
         inspector->singletonScopeChain = frame->scopeChain();
 
     JSScript* script = frame->script();
 
     if (script->functionNonDelazifying()) {
         if (!inspector->argTypes.reserve(frame->numFormalArgs()))
--- a/js/src/jit/JitFrameIterator.h
+++ b/js/src/jit/JitFrameIterator.h
@@ -817,18 +817,17 @@ class InlineFrameIterator
     JSObject* scopeChain(MaybeReadFallback& fallback) const {
         SnapshotIterator s(si_);
 
         // scopeChain
         Value v = s.maybeRead(fallback);
         return computeScopeChain(v, fallback);
     }
 
-    Value thisValue(MaybeReadFallback& fallback) const {
-        // MOZ_ASSERT(isConstructing(...));
+    Value thisArgument(MaybeReadFallback& fallback) const {
         SnapshotIterator s(si_);
 
         // scopeChain
         s.skip();
 
         // return value
         s.skip();
 
--- a/js/src/jit/RematerializedFrame.cpp
+++ b/js/src/jit/RematerializedFrame.cpp
@@ -46,17 +46,17 @@ RematerializedFrame::RematerializedFrame
 {
     if (iter.isFunctionFrame())
         callee_ = iter.callee(fallback);
     else
         callee_ = nullptr;
 
     CopyValueToRematerializedFrame op(slots_);
     iter.readFrameArgsAndLocals(cx, op, op, &scopeChain_, &hasCallObj_, &returnValue_,
-                                &argsObj_, &thisValue_, ReadFrame_Actuals,
+                                &argsObj_, &thisArgument_, ReadFrame_Actuals,
                                 fallback);
 }
 
 /* static */ RematerializedFrame*
 RematerializedFrame::New(JSContext* cx, uint8_t* top, InlineFrameIterator& iter,
                          MaybeReadFallback& fallback)
 {
     unsigned numFormals = iter.isFunctionFrame() ? iter.calleeTemplate()->nargs() : 0;
@@ -157,17 +157,17 @@ RematerializedFrame::mark(JSTracer* trc)
 {
     TraceRoot(trc, &script_, "remat ion frame script");
     TraceRoot(trc, &scopeChain_, "remat ion frame scope chain");
     if (callee_)
         TraceRoot(trc, &callee_, "remat ion frame callee");
     if (argsObj_)
         TraceRoot(trc, &argsObj_, "remat ion frame argsobj");
     TraceRoot(trc, &returnValue_, "remat ion frame return value");
-    TraceRoot(trc, &thisValue_, "remat ion frame this");
+    TraceRoot(trc, &thisArgument_, "remat ion frame this");
     TraceRootRange(trc, numActualArgs_ + isConstructing_ + script_->nfixed(),
                    slots_, "remat ion frame stack");
 }
 
 void
 RematerializedFrame::dump()
 {
     fprintf(stderr, " Rematerialized Ion Frame%s\n", inlined() ? " (inlined)" : "");
@@ -202,17 +202,17 @@ RematerializedFrame::dump()
             DumpValue(ObjectValue(argsObj()));
 #else
             fprintf(stderr, "?\n");
 #endif
         }
 
         fprintf(stderr, "  this: ");
 #ifdef DEBUG
-        DumpValue(thisValue());
+        DumpValue(thisArgument());
 #else
         fprintf(stderr, "?\n");
 #endif
 
         for (unsigned i = 0; i < numActualArgs(); i++) {
             if (i < numFormalArgs())
                 fprintf(stderr, "  formal (arg %d): ", i);
             else
--- a/js/src/jit/RematerializedFrame.h
+++ b/js/src/jit/RematerializedFrame.h
@@ -50,17 +50,17 @@ class RematerializedFrame
     unsigned numActualArgs_;
 
     JSScript* script_;
     JSObject* scopeChain_;
     JSFunction* callee_;
     ArgumentsObject* argsObj_;
 
     Value returnValue_;
-    Value thisValue_;
+    Value thisArgument_;
     Value slots_[1];
 
     RematerializedFrame(JSContext* cx, uint8_t* top, unsigned numActualArgs,
                         InlineFrameIterator& iter, MaybeReadFallback& fallback);
 
   public:
     static RematerializedFrame* New(JSContext* cx, uint8_t* top, InlineFrameIterator& iter,
                                     MaybeReadFallback& fallback);
@@ -164,18 +164,18 @@ class RematerializedFrame
     }
     JSFunction* callee() const {
         MOZ_ASSERT(isFunctionFrame());
         return callee_;
     }
     Value calleev() const {
         return ObjectValue(*callee());
     }
-    Value& thisValue() {
-        return thisValue_;
+    Value& thisArgument() {
+        return thisArgument_;
     }
 
     bool isConstructing() const {
         return isConstructing_;
     }
 
     bool hasCachedSavedFrame() const {
         return hasCachedSavedFrame_;
--- a/js/src/jsobj.cpp
+++ b/js/src/jsobj.cpp
@@ -3477,17 +3477,17 @@ js::DumpInterpreterFrame(JSContext* cx, 
                 i.script()->filename(), i.script()->lineno());
 
         if (jsbytecode* pc = i.pc()) {
             fprintf(stderr, "  pc = %p\n", pc);
             fprintf(stderr, "  current op: %s\n", js_CodeName[*pc]);
             MaybeDumpObject("staticScope", i.script()->getStaticBlockScope(pc));
         }
         if (i.isNonEvalFunctionFrame())
-            MaybeDumpValue("this", i.originalFunctionThis(cx));
+            MaybeDumpValue("this", i.thisArgument(cx));
         if (!i.isJit()) {
             fprintf(stderr, "  rval: ");
             dumpValue(i.interpFrame()->returnValue());
             fputc('\n', stderr);
         }
 
         fprintf(stderr, "  flags:");
         if (i.isConstructing())
--- a/js/src/vm/GeneratorObject.cpp
+++ b/js/src/vm/GeneratorObject.cpp
@@ -43,17 +43,17 @@ GeneratorObject::create(JSContext* cx, A
             return nullptr;
         obj = NewNativeObjectWithGivenProto(cx, &LegacyGeneratorObject::class_, proto);
     }
     if (!obj)
         return nullptr;
 
     GeneratorObject* genObj = &obj->as<GeneratorObject>();
     genObj->setCallee(*frame.callee());
-    genObj->setThisValue(frame.thisValue());
+    genObj->setThisValue(frame.thisArgument());
     genObj->setNewTarget(frame.newTarget());
     genObj->setScopeChain(*frame.scopeChain());
     if (frame.script()->needsArgsObj())
         genObj->setArgsObj(frame.argsObj());
     genObj->clearExpressionStack();
 
     return obj;
 }
--- a/js/src/vm/Interpreter.cpp
+++ b/js/src/vm/Interpreter.cpp
@@ -136,25 +136,25 @@ js::BoxNonStrictThis(JSContext* cx, cons
 }
 
 bool
 js::GetFunctionThis(JSContext* cx, AbstractFramePtr frame, MutableHandleValue res)
 {
     MOZ_ASSERT(frame.isNonEvalFunctionFrame());
     MOZ_ASSERT(!frame.fun()->isArrow());
 
-    if (frame.thisValue().isObject() ||
+    if (frame.thisArgument().isObject() ||
         frame.fun()->strict() ||
         frame.fun()->isSelfHostedBuiltin())
     {
-        res.set(frame.thisValue());
+        res.set(frame.thisArgument());
         return true;
     }
 
-    RootedValue thisv(cx, frame.thisValue());
+    RootedValue thisv(cx, frame.thisArgument());
     return BoxNonStrictThis(cx, thisv, res);
 }
 
 bool
 js::GetNonSyntacticGlobalThis(JSContext* cx, HandleObject scopeChain, MutableHandleValue res)
 {
     RootedObject scope(cx, scopeChain);
     while (true) {
--- a/js/src/vm/ScopeObject.cpp
+++ b/js/src/vm/ScopeObject.cpp
@@ -3106,18 +3106,18 @@ js::GetThisValueForDebuggerMaybeOptimize
         RootedScript script(cx, si.fun().nonLazyScript());
 
         if (!script->functionHasThisBinding()) {
             MOZ_ASSERT(!script->isDerivedClassConstructor(),
                        "Derived class constructors always have a this-binding");
 
             // If we're still inside `frame`, we can use the this-value passed
             // to it, if it does not require boxing.
-            if (si.withinInitialFrame() && (frame.thisValue().isObject() || script->strict()))
-                res.set(frame.thisValue());
+            if (si.withinInitialFrame() && (frame.thisArgument().isObject() || script->strict()))
+                res.set(frame.thisArgument());
             else
                 res.setMagic(JS_OPTIMIZED_OUT);
             return true;
         }
 
         BindingIter bi = Bindings::thisBinding(cx, script);
 
         if (script->bindingIsAliased(bi)) {
--- a/js/src/vm/Stack-inl.h
+++ b/js/src/vm/Stack-inl.h
@@ -844,23 +844,23 @@ AbstractFramePtr::unsetPrevUpToDate() co
     if (isBaselineFrame()) {
         asBaselineFrame()->unsetPrevUpToDate();
         return;
     }
     asRematerializedFrame()->unsetPrevUpToDate();
 }
 
 inline Value&
-AbstractFramePtr::thisValue() const
+AbstractFramePtr::thisArgument() const
 {
     if (isInterpreterFrame())
-        return asInterpreterFrame()->thisValue();
+        return asInterpreterFrame()->thisArgument();
     if (isBaselineFrame())
-        return asBaselineFrame()->thisValue();
-    return asRematerializedFrame()->thisValue();
+        return asBaselineFrame()->thisArgument();
+    return asRematerializedFrame()->thisArgument();
 }
 
 inline Value
 AbstractFramePtr::newTarget() const
 {
     if (isInterpreterFrame())
         return asInterpreterFrame()->newTarget();
     if (isBaselineFrame())
--- a/js/src/vm/Stack.cpp
+++ b/js/src/vm/Stack.cpp
@@ -254,25 +254,25 @@ InterpreterFrame::prologue(JSContext* cx
 
     MOZ_ASSERT(isNonEvalFunctionFrame());
     if (fun()->needsCallObject() && !initFunctionScopeObjects(cx))
         return false;
 
     if (isConstructing()) {
         if (script->isDerivedClassConstructor()) {
             MOZ_ASSERT(callee().isClassConstructor());
-            functionThis() = MagicValue(JS_UNINITIALIZED_LEXICAL);
-        } else if (functionThis().isPrimitive()) {
+            thisArgument() = MagicValue(JS_UNINITIALIZED_LEXICAL);
+        } else if (thisArgument().isPrimitive()) {
             RootedObject callee(cx, &this->callee());
             RootedObject newTarget(cx, &this->newTarget().toObject());
             JSObject* obj = CreateThisForFunction(cx, callee, newTarget,
                                                   createSingleton() ? SingletonObject : GenericObject);
             if (!obj)
                 return false;
-            functionThis() = ObjectValue(*obj);
+            thisArgument() = ObjectValue(*obj);
         }
     }
 
     return probes::EnterScript(cx, script, script->functionNonDelazifying(), this);
 }
 
 void
 InterpreterFrame::epilogue(JSContext* cx)
@@ -311,18 +311,23 @@ InterpreterFrame::epilogue(JSContext* cx
                       scopeChain()->as<CallObject>().callee().nonLazyScript() == script);
     } else {
         AssertDynamicScopeMatchesStaticScope(cx, script, scopeChain());
     }
 
     if (MOZ_UNLIKELY(cx->compartment()->isDebuggee()))
         DebugScopes::onPopCall(this, cx);
 
-    if (!fun()->isGenerator() && isConstructing() && thisValue().isObject() && returnValue().isPrimitive())
-        setReturnValue(ObjectValue(constructorThis()));
+    if (!fun()->isGenerator() &&
+        isConstructing() &&
+        thisArgument().isObject() &&
+        returnValue().isPrimitive())
+    {
+        setReturnValue(thisArgument());
+    }
 }
 
 bool
 InterpreterFrame::checkReturn(JSContext* cx, HandleValue thisv)
 {
     MOZ_ASSERT(script()->isDerivedClassConstructor());
     MOZ_ASSERT(isFunctionFrame());
     MOZ_ASSERT(callee().isClassConstructor());
@@ -1288,32 +1293,32 @@ FrameIter::hasArgsObj() const
 ArgumentsObject&
 FrameIter::argsObj() const
 {
     MOZ_ASSERT(hasArgsObj());
     return abstractFramePtr().argsObj();
 }
 
 Value
-FrameIter::originalFunctionThis(JSContext* cx) const
+FrameIter::thisArgument(JSContext* cx) const
 {
     MOZ_ASSERT(isNonEvalFunctionFrame());
 
     switch (data_.state_) {
       case DONE:
       case ASMJS:
         break;
       case JIT:
         if (data_.jitFrames_.isIonScripted()) {
             jit::MaybeReadFallback recover(cx, activation()->asJit(), &data_.jitFrames_);
-            return ionInlineFrames_.thisValue(recover);
+            return ionInlineFrames_.thisArgument(recover);
         }
-        return data_.jitFrames_.baselineFrame()->thisValue();
+        return data_.jitFrames_.baselineFrame()->thisArgument();
       case INTERP:
-        return interpFrame()->thisValue();
+        return interpFrame()->thisArgument();
     }
     MOZ_CRASH("Unexpected state");
 }
 
 Value
 FrameIter::newTarget() const
 {
     switch (data_.state_) {
--- a/js/src/vm/Stack.h
+++ b/js/src/vm/Stack.h
@@ -211,17 +211,17 @@ class AbstractFramePtr
     inline bool hasCachedSavedFrame() const;
     inline void setHasCachedSavedFrame();
 
     inline JSScript* script() const;
     inline JSFunction* fun() const;
     inline JSFunction* maybeFun() const;
     inline JSFunction* callee() const;
     inline Value calleev() const;
-    inline Value& thisValue() const;
+    inline Value& thisArgument() const;
 
     inline Value newTarget() const;
 
     inline bool isNonEvalFunctionFrame() const;
     inline bool isNonStrictDirectEvalFrame() const;
     inline bool isStrictEvalFrame() const;
 
     inline unsigned numActualArgs() const;
@@ -706,43 +706,23 @@ class InterpreterFrame
         return exec.module;
     }
 
     ModuleObject* maybeModule() const {
         return isModuleFrame() ? module() : nullptr;
     }
 
     /*
-     * This value
-     *
-     * Every frame has a this value although, until 'this' is computed, the
-     * value may not be the semantically-correct 'this' value.
-     *
-     * The 'this' value is stored before the formal arguments for function
-     * frames and directly before the frame for global frames. The *Args
-     * members assert !isEvalFrame(), so we implement specialized inline
-     * methods for accessing 'this'. When the caller has static knowledge that
-     * a frame is a function, 'functionThis' allows more efficient access.
+     * Return the 'this' argument passed to a non-eval function frame. This is
+     * not necessarily the frame's this-binding, for instance non-strict
+     * functions will box primitive 'this' values and thisArgument() will
+     * return the original, unboxed Value.
      */
-
-    Value& functionThis() const {
-        MOZ_ASSERT(isFunctionFrame());
-        if (isEvalFrame())
-            return ((Value*)this)[-1];
-        return argv()[-1];
-    }
-
-    JSObject& constructorThis() const {
-        MOZ_ASSERT(hasArgs());
-        return argv()[-1].toObject();
-    }
-
-    Value& thisValue() const {
-        if (flags_ & (EVAL | GLOBAL | MODULE))
-            return ((Value*)this)[-1];
+    Value& thisArgument() const {
+        MOZ_ASSERT(isNonEvalFunctionFrame());
         return argv()[-1];
     }
 
     /*
      * Callee
      *
      * Only function frames have a callee. An eval frame in a function has the
      * same callee as its containing function frame. maybeCalleev can be used
@@ -2001,17 +1981,17 @@ class FrameIter
 
     bool        hasArgsObj() const;
     ArgumentsObject& argsObj() const;
 
     // Get the original |this| value passed to this function. May not be the
     // actual this-binding (for instance, derived class constructors will
     // change their this-value later and non-strict functions will box
     // primitives).
-    Value       originalFunctionThis(JSContext* cx) const;
+    Value       thisArgument(JSContext* cx) const;
 
     Value       newTarget() const;
 
     Value       returnValue() const;
     void        setReturnValue(const Value& v);
 
     // These are only valid for the top frame.
     size_t      numFrameSlots() const;
--- a/js/src/vm/TypeInference.cpp
+++ b/js/src/vm/TypeInference.cpp
@@ -3876,17 +3876,17 @@ TypeNewScript::rollbackPartiallyInitiali
 
         if (!iter.isConstructing() || !iter.matchCallee(cx, function))
             continue;
 
         // Derived class constructors initialize their this-binding later and
         // we shouldn't run the definite properties analysis on them.
         MOZ_ASSERT(!iter.script()->isDerivedClassConstructor());
 
-        Value thisv = iter.originalFunctionThis(cx);
+        Value thisv = iter.thisArgument(cx);
         if (!thisv.isObject() ||
             thisv.toObject().hasLazyGroup() ||
             thisv.toObject().group() != group)
         {
             continue;
         }
 
         if (thisv.toObject().is<UnboxedPlainObject>()) {