--- a/js/src/ion/Bailouts.cpp
+++ b/js/src/ion/Bailouts.cpp
@@ -256,17 +256,17 @@ ConvertFrames(JSContext *cx, IonActivati
return BAILOUT_RETURN_FATAL_ERROR;
activation->setBailout(br);
StackFrame *fp;
if (it.isEntryJSFrame() && cx->fp()->runningInIon() && activation->entryfp()) {
// Avoid creating duplicate interpreter frames. This is necessary to
// avoid blowing out the interpreter stack, and must be used in
// conjunction with inline-OSR from within bailouts (since each Ion
- // activation must be tied to a unique JSStackFrame for StackIter to
+ // activation must be tied to a unique StackFrame for ScriptFrameIter to
// work).
//
// Note: If the entry frame is a placeholder (a stub frame pushed for
// JM -> Ion calls), then we cannot re-use it as it does not have
// enough slots.
JS_ASSERT(cx->fp() == activation->entryfp());
fp = cx->fp();
cx->regs().sp = fp->base();
@@ -662,17 +662,17 @@ ion::ThunkToInterpreter(Value *vp)
PCToLineNumber(cx->fp()->script(), cx->regs().pc));
// We want to OSR again. We need to avoid the problem where frequent
// bailouts cause recursive nestings of Interpret and EnterIon. The
// interpreter therefore shortcuts out, and now we're responsible for
// completing the OSR inline.
//
// Note that we set runningInIon so that if we re-enter C++ from within
- // the inlined OSR, StackIter will know to traverse these frames.
+ // the inlined OSR, ScriptFrameIter will know to traverse these frames.
StackFrame *fp = cx->fp();
fp->setRunningInIon();
vp->setPrivate(fp);
js_delete(br);
return Interpret_OSR;
}
--- a/js/src/ion/IonCompartment.h
+++ b/js/src/ion/IonCompartment.h
@@ -319,17 +319,17 @@ class IonActivation
JSCompartment *compartment_;
IonActivation *prev_;
StackFrame *entryfp_;
BailoutClosure *bailout_;
uint8_t *prevIonTop_;
JSContext *prevIonJSContext_;
// When creating an activation without a StackFrame, this field is used
- // to communicate the calling pc for StackIter.
+ // to communicate the calling pc for ScriptFrameIter.
jsbytecode *prevpc_;
public:
IonActivation(JSContext *cx, StackFrame *fp);
~IonActivation();
StackFrame *entryfp() const {
return entryfp_;
--- a/js/src/ion/IonFrames.cpp
+++ b/js/src/ion/IonFrames.cpp
@@ -514,18 +514,18 @@ HandleException(ResumeFromException *rfe
IonJSFrameLayout *current = iter.isScripted() ? iter.jsFrame() : NULL;
++iter;
if (current) {
// Unwind the frame by updating ionTop. This is necessary so that
// (1) debugger exception unwind and leave frame hooks don't see this
- // frame when they use StackIter, and (2) StackIter does not crash
- // when accessing an IonScript that's destroyed by the
+ // frame when they use ScriptFrameIter, and (2) ScriptFrameIter does
+ // not crash when accessing an IonScript that's destroyed by the
// ionScript->decref call.
EnsureExitFrame(current);
cx->mainThread().ionTop = (uint8_t *)current;
}
}
rfe->stackPointer = iter.fp();
}
--- a/js/src/jsdbgapi.cpp
+++ b/js/src/jsdbgapi.cpp
@@ -1365,48 +1365,48 @@ JSAbstractFramePtr::evaluateUCInStackFra
JSBrokenFrameIterator::JSBrokenFrameIterator(JSContext *cx)
{
NonBuiltinScriptFrameIter iter(cx);
data_ = iter.copyData();
}
JSBrokenFrameIterator::~JSBrokenFrameIterator()
{
- js_free((StackIter::Data *)data_);
+ js_free((ScriptFrameIter::Data *)data_);
}
bool
JSBrokenFrameIterator::done() const
{
- NonBuiltinScriptFrameIter iter(*(StackIter::Data *)data_);
+ NonBuiltinScriptFrameIter iter(*(ScriptFrameIter::Data *)data_);
return iter.done();
}
JSBrokenFrameIterator &
JSBrokenFrameIterator::operator++()
{
- StackIter::Data *data = (StackIter::Data *)data_;
+ ScriptFrameIter::Data *data = (ScriptFrameIter::Data *)data_;
NonBuiltinScriptFrameIter iter(*data);
++iter;
*data = iter.data_;
return *this;
}
JSAbstractFramePtr
JSBrokenFrameIterator::abstractFramePtr() const
{
- NonBuiltinScriptFrameIter iter(*(StackIter::Data *)data_);
+ NonBuiltinScriptFrameIter iter(*(ScriptFrameIter::Data *)data_);
return Jsvalify(iter.abstractFramePtr());
}
jsbytecode *
JSBrokenFrameIterator::pc() const
{
- NonBuiltinScriptFrameIter iter(*(StackIter::Data *)data_);
+ NonBuiltinScriptFrameIter iter(*(ScriptFrameIter::Data *)data_);
return iter.pc();
}
bool
JSBrokenFrameIterator::isConstructing() const
{
- NonBuiltinScriptFrameIter iter(*(StackIter::Data *)data_);
+ NonBuiltinScriptFrameIter iter(*(ScriptFrameIter::Data *)data_);
return iter.isConstructing();
}
--- a/js/src/jsfun.cpp
+++ b/js/src/jsfun.cpp
@@ -914,19 +914,19 @@ js_fun_apply(JSContext *cx, unsigned arg
* function and read actuals out of the frame.
*
* N.B. Changes here need to be propagated to stubs::SplatApplyArgs.
*/
/* Steps 4-6. */
StackFrame *fp = cx->fp();
#ifdef JS_ION
- // We do not want to use StackIter to abstract here because this is
- // supposed to be a fast path as opposed to StackIter which is doing
- // complex logic to settle on the next frame twice.
+ // We do not want to use ScriptFrameIter to abstract here because this
+ // is supposed to be a fast path as opposed to ScriptFrameIter which is
+ // doing complex logic to settle on the next frame twice.
if (fp->beginsIonActivation()) {
ion::IonActivationIterator activations(cx);
ion::IonFrameIterator frame(activations);
if (frame.isNative()) {
// Stop on the next Ion JS Frame.
++frame;
if (frame.isOptimizedJS()) {
ion::InlineFrameIterator iter(cx, &frame);
--- a/js/src/jsinterp.cpp
+++ b/js/src/jsinterp.cpp
@@ -303,17 +303,17 @@ js::RunScript(JSContext *cx, StackFrame
#endif
JS_CHECK_RECURSION(cx, return false);
// Check to see if useNewType flag should be set for this frame.
if (fp->isFunctionFrame() && fp->isConstructing() && !fp->isGeneratorFrame() &&
cx->typeInferenceEnabled())
{
- StackIter iter(cx);
+ ScriptFrameIter iter(cx);
if (!iter.done()) {
++iter;
JSScript *script = iter.script();
jsbytecode *pc = iter.pc();
if (UseNewType(cx, script, pc))
fp->setUseNewType();
}
}
--- a/js/src/jsobj.cpp
+++ b/js/src/jsobj.cpp
@@ -5199,17 +5199,17 @@ MaybeDumpValue(const char *name, const V
fputc('\n', stderr);
}
}
JS_FRIEND_API(void)
js_DumpStackFrame(JSContext *cx, StackFrame *start)
{
/* This should only called during live debugging. */
- ScriptFrameIter i(cx, StackIter::GO_THROUGH_SAVED);
+ ScriptFrameIter i(cx, ScriptFrameIter::GO_THROUGH_SAVED);
if (!start) {
if (i.done()) {
fprintf(stderr, "no stack for cx = %p\n", (void*) cx);
return;
}
} else {
while (!i.done() && !i.isIon() && i.interpFrame() != start)
++i;
@@ -5273,17 +5273,17 @@ js_DumpStackFrame(JSContext *cx, StackFr
#endif /* DEBUG */
JS_FRIEND_API(void)
js_DumpBacktrace(JSContext *cx)
{
Sprinter sprinter(cx);
sprinter.init();
size_t depth = 0;
- for (StackIter i(cx); !i.done(); ++i, ++depth) {
+ for (ScriptFrameIter i(cx); !i.done(); ++i, ++depth) {
const char *filename = JS_GetScriptFilename(cx, i.script());
unsigned line = JS_PCToLineNumber(cx, i.script(), i.pc());
JSScript *script = i.script();
sprinter.printf("#%d %14p %s:%d (%p @ %d)\n",
depth, (i.isIon() ? 0 : i.interpFrame()), filename, line,
script, i.pc() - script->code);
}
fprintf(stdout, "%s", sprinter.string());
--- a/js/src/jsopcode.cpp
+++ b/js/src/jsopcode.cpp
@@ -1622,17 +1622,17 @@ DecompileArgumentFromStack(JSContext *cx
/* See note in DecompileExpressionFromStack. */
return true;
#endif
/*
* Settle on the nearest script frame, which should be the builtin that
* called the intrinsic.
*/
- StackIter frameIter(cx);
+ ScriptFrameIter frameIter(cx);
JS_ASSERT(!frameIter.done());
/*
* Get the second-to-top frame, the caller of the builtin that called the
* intrinsic.
*/
++frameIter;
if (frameIter.done())
--- a/js/src/jsscript.cpp
+++ b/js/src/jsscript.cpp
@@ -2815,17 +2815,17 @@ JSScript::argumentsOptimizationFailed(JS
for (AllFramesIter i(cx->runtime); !i.done(); ++i) {
/*
* We cannot reliably create an arguments object for Ion activations of
* this script. To maintain the invariant that "script->needsArgsObj
* implies fp->hasArgsObj", the Ion bail mechanism will create an
* arguments object right after restoring the StackFrame and before
* entering the interpreter (in ion::ThunkToInterpreter). This delay is
* safe since the engine avoids any observation of a StackFrame when it
- * beginsIonActivation (see StackIter::interpFrame comment).
+ * beginsIonActivation (see ScriptFrameIter::interpFrame comment).
*/
if (i.isIonOptimizedJS())
continue;
AbstractFramePtr frame = i.abstractFramePtr();
if (frame.isFunctionFrame() && frame.script() == script) {
ArgumentsObject *argsobj = ArgumentsObject::createExpected(cx, frame);
if (!argsobj) {
/*
--- a/js/src/vm/ArgumentsObject.cpp
+++ b/js/src/vm/ArgumentsObject.cpp
@@ -136,21 +136,21 @@ struct CopyIonJSFrameArgs
* call object is the canonical location for formals.
*/
void maybeForwardToCallObject(JSObject *obj, ArgumentsData *data) {
ArgumentsObject::MaybeForwardToCallObject(frame_, callObj_, obj, data);
}
};
#endif
-struct CopyStackIterArgs
+struct CopyScriptFrameIterArgs
{
- StackIter &iter_;
+ ScriptFrameIter &iter_;
- CopyStackIterArgs(StackIter &iter)
+ CopyScriptFrameIterArgs(ScriptFrameIter &iter)
: iter_(iter)
{ }
void copyArgs(JSContext *cx, HeapValue *dstBase, unsigned totalArgs) const {
if (!iter_.isIon()) {
CopyStackFrameArguments(iter_.abstractFramePtr(), dstBase, totalArgs);
return;
}
@@ -255,21 +255,21 @@ ArgumentsObject::createExpected(JSContex
if (!argsobj)
return NULL;
frame.initArgsObj(*argsobj);
return argsobj;
}
ArgumentsObject *
-ArgumentsObject::createUnexpected(JSContext *cx, StackIter &iter)
+ArgumentsObject::createUnexpected(JSContext *cx, ScriptFrameIter &iter)
{
RootedScript script(cx, iter.script());
RootedFunction callee(cx, iter.callee());
- CopyStackIterArgs copy(iter);
+ CopyScriptFrameIterArgs copy(iter);
return create(cx, script, callee, iter.numActualArgs(), copy);
}
ArgumentsObject *
ArgumentsObject::createUnexpected(JSContext *cx, AbstractFramePtr frame)
{
RootedScript script(cx, frame.script());
RootedFunction callee(cx, frame.callee());
--- a/js/src/vm/ArgumentsObject.h
+++ b/js/src/vm/ArgumentsObject.h
@@ -118,17 +118,17 @@ class ArgumentsObject : public JSObject
static ArgumentsObject *createExpected(JSContext *cx, AbstractFramePtr frame);
/*
* Purposefully disconnect the returned arguments object from the frame
* by always creating a new copy that does not alias formal parameters.
* This allows function-local analysis to determine that formals are
* not aliased and generally simplifies arguments objects.
*/
- static ArgumentsObject *createUnexpected(JSContext *cx, StackIter &iter);
+ static ArgumentsObject *createUnexpected(JSContext *cx, ScriptFrameIter &iter);
static ArgumentsObject *createUnexpected(JSContext *cx, AbstractFramePtr frame);
#if defined(JS_ION)
static ArgumentsObject *createForIon(JSContext *cx, ion::IonJSFrameLayout *frame,
HandleObject scopeChain);
#endif
/*
* Return the initial length of the arguments. This may differ from the
--- a/js/src/vm/Debugger.cpp
+++ b/js/src/vm/Debugger.cpp
@@ -425,17 +425,17 @@ Debugger::getScriptFrame(JSContext *cx,
FrameMap::AddPtr p = frames.lookupForAdd(iter.abstractFramePtr());
if (!p) {
/* Create and populate the Debugger.Frame object. */
JSObject *proto = &object->getReservedSlot(JSSLOT_DEBUG_FRAME_PROTO).toObject();
JSObject *frameobj =
NewObjectWithGivenProto(cx, &DebuggerFrame_class, proto, NULL);
if (!frameobj)
return false;
- StackIter::Data *data = iter.copyData();
+ ScriptFrameIter::Data *data = iter.copyData();
if (!data)
return false;
frameobj->setPrivate(data);
frameobj->setReservedSlot(JSSLOT_DEBUGFRAME_OWNER, ObjectValue(*object));
if (!frames.add(p, iter.abstractFramePtr(), frameobj)) {
js_ReportOutOfMemory(cx);
return false;
@@ -508,17 +508,17 @@ Debugger::slowPathOnEnterFrame(JSContext
return status;
}
}
return JSTRAP_CONTINUE;
}
static void
-DebuggerFrame_freeStackIterData(FreeOp *fop, JSObject *obj);
+DebuggerFrame_freeScriptFrameIterData(FreeOp *fop, JSObject *obj);
/*
* Handle leaving a frame with debuggers watching. |frameOk| indicates whether
* the frame is exiting normally or abruptly. Set |cx|'s exception and/or
* |cx->fp()|'s return value, and return a new success value.
*/
bool
Debugger::slowPathOnLeaveFrame(JSContext *cx, AbstractFramePtr frame, bool frameOk)
@@ -584,17 +584,17 @@ Debugger::slowPathOnLeaveFrame(JSContext
* debugger's onPop handler could have caused another debugger to create its
* own Debugger.Frame instance.
*/
for (FrameRange r(frame, global); !r.empty(); r.popFront()) {
RootedObject frameobj(cx, r.frontFrame());
Debugger *dbg = r.frontDebugger();
JS_ASSERT(dbg == Debugger::fromChildJSObject(frameobj));
- DebuggerFrame_freeStackIterData(cx->runtime->defaultFreeOp(), frameobj);
+ DebuggerFrame_freeScriptFrameIterData(cx->runtime->defaultFreeOp(), frameobj);
/* If this frame had an onStep handler, adjust the script's count. */
if (!frameobj->getReservedSlot(JSSLOT_DEBUGFRAME_ONSTEP_HANDLER).isUndefined() &&
!frame.script()->changeStepModeCount(cx, -1))
{
status = JSTRAP_ERROR;
/* Don't exit the loop; we must mark all frames as dead. */
}
@@ -2029,17 +2029,17 @@ Debugger::getNewestFrame(JSContext *cx,
for (AllFramesIter i(cx->runtime); !i.done(); ++i) {
/*
* Debug-mode currently disables Ion compilation in the compartment of
* the debuggee.
*/
if (i.isIonOptimizedJS())
continue;
if (dbg->observesFrame(i.abstractFramePtr())) {
- ScriptFrameIter iter(i.seg()->cx(), StackIter::GO_THROUGH_SAVED);
+ ScriptFrameIter iter(i.seg()->cx(), ScriptFrameIter::GO_THROUGH_SAVED);
while (iter.isIonOptimizedJS() || iter.abstractFramePtr() != i.abstractFramePtr())
++iter;
return dbg->getScriptFrame(cx, iter, args.rval());
}
}
args.rval().setNull();
return true;
}
@@ -2221,17 +2221,17 @@ Debugger::removeDebuggeeGlobal(FreeOp *f
* have live Frame objects. So we take the easy way out and kill them here.
* This is a bug, since it's observable and contrary to the spec. One
* possible fix would be to put such objects into a compartment-wide bag
* which slowPathOnLeaveFrame would have to examine.
*/
for (FrameMap::Enum e(frames); !e.empty(); e.popFront()) {
AbstractFramePtr frame = e.front().key;
if (&frame.script()->global() == global) {
- DebuggerFrame_freeStackIterData(fop, e.front().value);
+ DebuggerFrame_freeScriptFrameIterData(fop, e.front().value);
e.removeFront();
}
}
GlobalObject::DebuggerVector *v = global->getDebuggers();
Debugger **p;
for (p = v->begin(); p != v->end(); p++) {
if (*p == this)
@@ -3328,19 +3328,19 @@ Debugger::handleBaselineOsr(JSContext *c
ScriptFrameIter iter(cx);
JS_ASSERT(iter.abstractFramePtr() == to);
for (FrameRange r(from); !r.empty(); r.popFront()) {
RootedObject frameobj(cx, r.frontFrame());
Debugger *dbg = r.frontDebugger();
JS_ASSERT(dbg == Debugger::fromChildJSObject(frameobj));
- // Update frame object's StackIter::data pointer.
- DebuggerFrame_freeStackIterData(cx->runtime->defaultFreeOp(), frameobj);
- StackIter::Data *data = iter.copyData();
+ // Update frame object's ScriptFrameIter::data pointer.
+ DebuggerFrame_freeScriptFrameIterData(cx->runtime->defaultFreeOp(), frameobj);
+ ScriptFrameIter::Data *data = iter.copyData();
if (!data)
return false;
frameobj->setPrivate(data);
// Add the frame object with |to| as key.
if (!dbg->frames.putNew(to, frameobj)) {
js_ReportOutOfMemory(cx);
return false;
@@ -3477,26 +3477,26 @@ static const JSFunctionSpec DebuggerScri
JS_FN("clearAllBreakpoints", DebuggerScript_clearAllBreakpoints, 0, 0),
JS_FS_END
};
/*** Debugger.Frame ******************************************************************************/
static void
-DebuggerFrame_freeStackIterData(FreeOp *fop, JSObject *obj)
-{
- fop->delete_((StackIter::Data *)obj->getPrivate());
+DebuggerFrame_freeScriptFrameIterData(FreeOp *fop, JSObject *obj)
+{
+ fop->delete_((ScriptFrameIter::Data *)obj->getPrivate());
obj->setPrivate(NULL);
}
static void
DebuggerFrame_finalize(FreeOp *fop, JSObject *obj)
{
- DebuggerFrame_freeStackIterData(fop, obj);
+ DebuggerFrame_freeScriptFrameIterData(fop, obj);
}
Class DebuggerFrame_class = {
"Frame", JSCLASS_HAS_PRIVATE | JSCLASS_HAS_RESERVED_SLOTS(JSSLOT_DEBUGFRAME_COUNT),
JS_PropertyStub, JS_DeletePropertyStub, JS_PropertyStub, JS_StrictPropertyStub,
JS_EnumerateStub, JS_ResolveStub, JS_ConvertStub, DebuggerFrame_finalize
};
@@ -3535,17 +3535,17 @@ CheckThisFrame(JSContext *cx, const Call
return thisobj;
}
#define THIS_FRAME(cx, argc, vp, fnname, args, thisobj, iter) \
CallArgs args = CallArgsFromVp(argc, vp); \
RootedObject thisobj(cx, CheckThisFrame(cx, args, fnname, true)); \
if (!thisobj) \
return false; \
- ScriptFrameIter iter(*(StackIter::Data *)thisobj->getPrivate());
+ ScriptFrameIter iter(*(ScriptFrameIter::Data *)thisobj->getPrivate());
#define THIS_FRAME_OWNER(cx, argc, vp, fnname, args, thisobj, iter, dbg) \
THIS_FRAME(cx, argc, vp, fnname, args, thisobj, iter); \
Debugger *dbg = Debugger::fromChildJSObject(thisobj)
static JSBool
DebuggerFrame_getType(JSContext *cx, unsigned argc, Value *vp)
{
--- a/js/src/vm/Stack-inl.h
+++ b/js/src/vm/Stack-inl.h
@@ -557,17 +557,17 @@ ContextStack::currentScript(jsbytecode *
inline HandleObject
ContextStack::currentScriptedScopeChain() const
{
return fp()->scopeChain();
}
template <class Op>
inline void
-StackIter::ionForEachCanonicalActualArg(JSContext *cx, Op op)
+ScriptFrameIter::ionForEachCanonicalActualArg(JSContext *cx, Op op)
{
JS_ASSERT(isIon());
#ifdef JS_ION
if (data_.ionFrames_.isOptimizedJS()) {
ionInlineFrames_.forEachCanonicalActualArg(cx, op, 0, -1);
} else {
JS_ASSERT(data_.ionFrames_.isBaselineJS());
data_.ionFrames_.forEachCanonicalActualArg(op, 0, -1);
--- a/js/src/vm/Stack.cpp
+++ b/js/src/vm/Stack.cpp
@@ -1029,17 +1029,17 @@ ContextStack::pushExecuteFrame(JSContext
/* First, find the right segment. */
AllFramesIter frameIter(cx->runtime);
while (frameIter.isIonOptimizedJS() || frameIter.abstractFramePtr() != evalInFrame)
++frameIter;
JS_ASSERT(frameIter.abstractFramePtr() == evalInFrame);
StackSegment &seg = *frameIter.seg();
- StackIter iter(cx->runtime, seg);
+ ScriptFrameIter iter(cx->runtime, seg);
/* Debug-mode currently disables Ion compilation. */
JS_ASSERT_IF(evalInFrame.isStackFrame(), !evalInFrame.asStackFrame()->runningInIon());
JS_ASSERT_IF(evalInFrame.compartment() == iter.compartment(), !iter.isIonOptimizedJS());
while (iter.isIonOptimizedJS() || iter.abstractFramePtr() != evalInFrame) {
++iter;
JS_ASSERT_IF(evalInFrame.compartment() == iter.compartment(), !iter.isIonOptimizedJS());
}
JS_ASSERT(iter.abstractFramePtr() == evalInFrame);
@@ -1207,74 +1207,74 @@ ContextStack::restoreFrameChain()
JS_ASSERT(seg_->isEmpty());
popSegment();
}
/*****************************************************************************/
void
-StackIter::poisonRegs()
+ScriptFrameIter::poisonRegs()
{
data_.pc_ = (jsbytecode *)0xbad;
}
void
-StackIter::popFrame()
+ScriptFrameIter::popFrame()
{
StackFrame *oldfp = data_.fp_;
JS_ASSERT(data_.seg_->contains(oldfp));
data_.fp_ = data_.fp_->prev();
if (data_.seg_->contains(data_.fp_)) {
InlinedSite *inline_;
data_.pc_ = oldfp->prevpc(&inline_);
JS_ASSERT(!inline_);
} else {
poisonRegs();
}
}
void
-StackIter::settleOnNewSegment()
+ScriptFrameIter::settleOnNewSegment()
{
if (FrameRegs *regs = data_.seg_->maybeRegs())
data_.pc_ = regs->pc;
else
poisonRegs();
}
void
-StackIter::startOnSegment(StackSegment *seg)
+ScriptFrameIter::startOnSegment(StackSegment *seg)
{
data_.seg_ = seg;
data_.fp_ = data_.seg_->maybefp();
settleOnNewSegment();
}
/*
* Given the iterator's current value of fp_ (initialized on construction or
* after operator++ popped the previous call), "settle" the iterator on a new
- * StackIter::State value. The goal is to present the client a simple linear
- * sequence of scripted calls while covering up unpleasant stack implementation
- * details:
+ * ScriptFrameIter::State value. The goal is to present the client a simple
+ * linear sequence of scripted calls while covering up unpleasant stack
+ * implementation details:
* - The frame chain can be "saved" and "restored" (see JS_SaveFrameChain).
- * This artificially cuts the call chain and the StackIter client may want
- * to continue through this cut to the previous frame by passing
+ * This artificially cuts the call chain and the ScriptFrameIter client may
+ * want to continue through this cut to the previous frame by passing
* GO_THROUGH_SAVED.
* - fp->prev can be in a different contiguous segment from fp. In this case,
* the current values of sp/pc after calling popFrame are incorrect and
* should be recovered from fp->prev's segment.
*/
/* PGO causes xpcshell startup crashes with VS2010. */
#if defined(_MSC_VER)
# pragma optimize("g", off)
#endif
void
-StackIter::settleOnNewState()
+ScriptFrameIter::settleOnNewState()
{
/*
* There are elements of the fp_ chain that we want to skip over so iterate
* until we settle on one or until there are no more.
*/
while (true) {
if (!data_.fp_) {
if (data_.savedOption_ == GO_THROUGH_SAVED && data_.seg_->prevInContext()) {
@@ -1290,17 +1290,17 @@ StackIter::settleOnNewState()
while (!containsFrame) {
/* Eval-in-frame can cross contexts, so use prevInMemory. */
data_.seg_ = data_.seg_->prevInMemory();
containsFrame = data_.seg_->contains(data_.fp_);
/* Eval-in-frame allows jumping into the middle of a segment. */
if (containsFrame && data_.seg_->fp() != data_.fp_) {
/* Avoid duplicating logic; seg_ contains fp_, so no iloop. */
- StackIter tmp = *this;
+ ScriptFrameIter tmp = *this;
tmp.startOnSegment(data_.seg_);
tmp.settleOnNewState();
while (tmp.data_.fp_ != data_.fp_)
++tmp;
JS_ASSERT(!tmp.done() &&
tmp.data_.seg_ == data_.seg_ &&
tmp.data_.fp_ == data_.fp_);
*this = tmp;
@@ -1350,54 +1350,54 @@ StackIter::settleOnNewState()
data_.state_ = SCRIPTED;
return;
}
}
#if defined(_MSC_VER)
# pragma optimize("", on)
#endif
-StackIter::Data::Data(JSContext *cx, PerThreadData *perThread, SavedOption savedOption)
+ScriptFrameIter::Data::Data(JSContext *cx, PerThreadData *perThread, SavedOption savedOption)
: perThread_(perThread),
cx_(cx),
savedOption_(savedOption)
#ifdef JS_ION
, ionActivations_(cx),
ionFrames_((uint8_t *)NULL)
#endif
{
}
-StackIter::Data::Data(JSContext *cx, JSRuntime *rt, StackSegment *seg)
+ScriptFrameIter::Data::Data(JSContext *cx, JSRuntime *rt, StackSegment *seg)
: perThread_(&rt->mainThread),
cx_(cx),
savedOption_(STOP_AT_SAVED)
#ifdef JS_ION
, ionActivations_(rt),
ionFrames_((uint8_t *)NULL)
#endif
{
}
-StackIter::Data::Data(const StackIter::Data &other)
+ScriptFrameIter::Data::Data(const ScriptFrameIter::Data &other)
: perThread_(other.perThread_),
cx_(other.cx_),
savedOption_(other.savedOption_),
state_(other.state_),
fp_(other.fp_),
seg_(other.seg_),
pc_(other.pc_)
#ifdef JS_ION
, ionActivations_(other.ionActivations_),
ionFrames_(other.ionFrames_)
#endif
{
}
-StackIter::StackIter(JSContext *cx, SavedOption savedOption)
+ScriptFrameIter::ScriptFrameIter(JSContext *cx, SavedOption savedOption)
: data_(cx, &cx->runtime->mainThread, savedOption)
#ifdef JS_ION
, ionInlineFrames_(cx, (js::ion::IonFrameIterator*) NULL)
#endif
{
#ifdef JS_METHODJIT
for (ZonesIter zone(cx->runtime); !zone.done(); zone.next())
mjit::ExpandInlineFrames(zone);
@@ -1406,63 +1406,63 @@ StackIter::StackIter(JSContext *cx, Save
if (StackSegment *seg = cx->stack.seg_) {
startOnSegment(seg);
settleOnNewState();
} else {
data_.state_ = DONE;
}
}
-StackIter::StackIter(JSRuntime *rt, StackSegment &seg)
+ScriptFrameIter::ScriptFrameIter(JSRuntime *rt, StackSegment &seg)
: data_(seg.cx(), rt, &seg)
#ifdef JS_ION
, ionInlineFrames_(seg.cx(), (js::ion::IonFrameIterator*) NULL)
#endif
{
#ifdef JS_METHODJIT
for (ZonesIter zone(rt); !zone.done(); zone.next())
mjit::ExpandInlineFrames(zone);
#endif
startOnSegment(&seg);
settleOnNewState();
}
-StackIter::StackIter(const StackIter &other)
+ScriptFrameIter::ScriptFrameIter(const ScriptFrameIter &other)
: data_(other.data_)
#ifdef JS_ION
, ionInlineFrames_(other.data_.seg_->cx(),
data_.ionFrames_.isScripted() ? &other.ionInlineFrames_ : NULL)
#endif
{
}
-StackIter::StackIter(const Data &data)
+ScriptFrameIter::ScriptFrameIter(const Data &data)
: data_(data)
#ifdef JS_ION
, ionInlineFrames_(data.cx_, data_.ionFrames_.isOptimizedJS() ? &data_.ionFrames_ : NULL)
#endif
{
JS_ASSERT(data.cx_);
}
#ifdef JS_ION
void
-StackIter::nextIonFrame()
+ScriptFrameIter::nextIonFrame()
{
if (data_.ionFrames_.isOptimizedJS()) {
ionInlineFrames_.resetOn(&data_.ionFrames_);
data_.pc_ = ionInlineFrames_.pc();
} else {
JS_ASSERT(data_.ionFrames_.isBaselineJS());
data_.ionFrames_.baselineScriptAndPc(NULL, &data_.pc_);
}
}
void
-StackIter::popIonFrame()
+ScriptFrameIter::popIonFrame()
{
// Keep fp which describes all ion frames.
poisonRegs();
if (data_.ionFrames_.isOptimizedJS() && ionInlineFrames_.more()) {
++ionInlineFrames_;
data_.pc_ = ionInlineFrames_.pc();
} else {
++data_.ionFrames_;
@@ -1494,31 +1494,31 @@ StackIter::popIonFrame()
data_.state_ = SCRIPTED;
data_.pc_ = data_.ionActivations_.activation()->prevpc();
++data_.ionActivations_;
}
}
}
void
-StackIter::popBaselineDebuggerFrame()
+ScriptFrameIter::popBaselineDebuggerFrame()
{
ion::BaselineFrame *prevBaseline = data_.fp_->prevBaselineFrame();
popFrame();
settleOnNewState();
JS_ASSERT(data_.state_ == ION);
while (!data_.ionFrames_.isBaselineJS() || data_.ionFrames_.baselineFrame() != prevBaseline)
popIonFrame();
}
#endif
-StackIter &
-StackIter::operator++()
+ScriptFrameIter &
+ScriptFrameIter::operator++()
{
switch (data_.state_) {
case DONE:
JS_NOT_REACHED("Unexpected state");
case SCRIPTED:
#ifdef JS_ION
if (data_.fp_->isDebuggerFrame() && data_.fp_->prevBaselineFrame()) {
/* Eval-in-frame with a baseline JIT frame. */
@@ -1536,37 +1536,37 @@ StackIter::operator++()
#else
JS_NOT_REACHED("Unexpected state");
#endif
}
return *this;
}
bool
-StackIter::operator==(const StackIter &rhs) const
+ScriptFrameIter::operator==(const ScriptFrameIter &rhs) const
{
return done() == rhs.done() &&
(done() || data_.fp_ == rhs.data_.fp_);
}
-StackIter::Data *
-StackIter::copyData() const
+ScriptFrameIter::Data *
+ScriptFrameIter::copyData() const
{
#ifdef JS_ION
/*
* This doesn't work for optimized Ion frames since ionInlineFrames_ is
* not copied.
*/
JS_ASSERT(data_.ionFrames_.type() != ion::IonFrame_OptimizedJS);
#endif
return data_.cx_->new_<Data>(data_);
}
JSCompartment *
-StackIter::compartment() const
+ScriptFrameIter::compartment() const
{
switch (data_.state_) {
case DONE:
break;
case SCRIPTED:
return data_.fp_->compartment();
case ION:
#ifdef JS_ION
@@ -1575,17 +1575,17 @@ StackIter::compartment() const
break;
#endif
}
JS_NOT_REACHED("Unexpected state");
return NULL;
}
bool
-StackIter::isFunctionFrame() const
+ScriptFrameIter::isFunctionFrame() const
{
switch (data_.state_) {
case DONE:
break;
case SCRIPTED:
return interpFrame()->isFunctionFrame();
case ION:
#ifdef JS_ION
@@ -1597,17 +1597,17 @@ StackIter::isFunctionFrame() const
break;
#endif
}
JS_NOT_REACHED("Unexpected state");
return false;
}
bool
-StackIter::isGlobalFrame() const
+ScriptFrameIter::isGlobalFrame() const
{
switch (data_.state_) {
case DONE:
break;
case SCRIPTED:
return interpFrame()->isGlobalFrame();
case ION:
#ifdef JS_ION
@@ -1619,17 +1619,17 @@ StackIter::isGlobalFrame() const
break;
#endif
}
JS_NOT_REACHED("Unexpected state");
return false;
}
bool
-StackIter::isEvalFrame() const
+ScriptFrameIter::isEvalFrame() const
{
switch (data_.state_) {
case DONE:
break;
case SCRIPTED:
return interpFrame()->isEvalFrame();
case ION:
#ifdef JS_ION
@@ -1641,48 +1641,48 @@ StackIter::isEvalFrame() const
break;
#endif
}
JS_NOT_REACHED("Unexpected state");
return false;
}
bool
-StackIter::isNonEvalFunctionFrame() const
+ScriptFrameIter::isNonEvalFunctionFrame() const
{
JS_ASSERT(!done());
switch (data_.state_) {
case DONE:
break;
case SCRIPTED:
return interpFrame()->isNonEvalFunctionFrame();
case ION:
return !isEvalFrame() && isFunctionFrame();
}
JS_NOT_REACHED("Unexpected state");
return false;
}
bool
-StackIter::isGeneratorFrame() const
+ScriptFrameIter::isGeneratorFrame() const
{
switch (data_.state_) {
case DONE:
break;
case SCRIPTED:
return interpFrame()->isGeneratorFrame();
case ION:
return false;
}
JS_NOT_REACHED("Unexpected state");
return false;
}
bool
-StackIter::isConstructing() const
+ScriptFrameIter::isConstructing() const
{
switch (data_.state_) {
case DONE:
break;
case ION:
#ifdef JS_ION
if (data_.ionFrames_.isOptimizedJS())
return ionInlineFrames_.isConstructing();
@@ -1694,17 +1694,17 @@ StackIter::isConstructing() const
case SCRIPTED:
return interpFrame()->isConstructing();
}
JS_NOT_REACHED("Unexpected state");
return false;
}
AbstractFramePtr
-StackIter::abstractFramePtr() const
+ScriptFrameIter::abstractFramePtr() const
{
switch (data_.state_) {
case DONE:
break;
case ION:
#ifdef JS_ION
if (data_.ionFrames_.isBaselineJS())
return data_.ionFrames_.baselineFrame();
@@ -1714,17 +1714,17 @@ StackIter::abstractFramePtr() const
JS_ASSERT(interpFrame());
return AbstractFramePtr(interpFrame());
}
JS_NOT_REACHED("Unexpected state");
return NullFramePtr();
}
void
-StackIter::updatePcQuadratic()
+ScriptFrameIter::updatePcQuadratic()
{
switch (data_.state_) {
case DONE:
break;
case SCRIPTED:
data_.pc_ = interpFrame()->pcQuadratic(data_.cx_);
return;
case ION:
@@ -1751,17 +1751,17 @@ StackIter::updatePcQuadratic()
}
#endif
break;
}
JS_NOT_REACHED("Unexpected state");
}
JSFunction *
-StackIter::callee() const
+ScriptFrameIter::callee() const
{
switch (data_.state_) {
case DONE:
break;
case SCRIPTED:
JS_ASSERT(isFunctionFrame());
return &interpFrame()->callee();
case ION:
@@ -1774,17 +1774,17 @@ StackIter::callee() const
break;
#endif
}
JS_NOT_REACHED("Unexpected state");
return NULL;
}
Value
-StackIter::calleev() const
+ScriptFrameIter::calleev() const
{
switch (data_.state_) {
case DONE:
break;
case SCRIPTED:
JS_ASSERT(isFunctionFrame());
return interpFrame()->calleev();
case ION:
@@ -1794,17 +1794,17 @@ StackIter::calleev() const
break;
#endif
}
JS_NOT_REACHED("Unexpected state");
return Value();
}
unsigned
-StackIter::numActualArgs() const
+ScriptFrameIter::numActualArgs() const
{
switch (data_.state_) {
case DONE:
break;
case SCRIPTED:
JS_ASSERT(isFunctionFrame());
return interpFrame()->numActualArgs();
case ION:
@@ -1818,17 +1818,17 @@ StackIter::numActualArgs() const
break;
#endif
}
JS_NOT_REACHED("Unexpected state");
return 0;
}
Value
-StackIter::unaliasedActual(unsigned i, MaybeCheckAliasing checkAliasing) const
+ScriptFrameIter::unaliasedActual(unsigned i, MaybeCheckAliasing checkAliasing) const
{
switch (data_.state_) {
case DONE:
break;
case SCRIPTED:
return interpFrame()->unaliasedActual(i, checkAliasing);
case ION:
#ifdef JS_ION
@@ -1838,17 +1838,17 @@ StackIter::unaliasedActual(unsigned i, M
break;
#endif
}
JS_NOT_REACHED("Unexpected state");
return NullValue();
}
JSObject *
-StackIter::scopeChain() const
+ScriptFrameIter::scopeChain() const
{
switch (data_.state_) {
case DONE:
break;
case ION:
#ifdef JS_ION
if (data_.ionFrames_.isOptimizedJS())
return ionInlineFrames_.scopeChain();
@@ -1859,28 +1859,28 @@ StackIter::scopeChain() const
case SCRIPTED:
return interpFrame()->scopeChain();
}
JS_NOT_REACHED("Unexpected state");
return NULL;
}
CallObject &
-StackIter::callObj() const
+ScriptFrameIter::callObj() const
{
JS_ASSERT(callee()->isHeavyweight());
JSObject *pobj = scopeChain();
while (!pobj->isCall())
pobj = pobj->enclosingScope();
return pobj->asCall();
}
bool
-StackIter::hasArgsObj() const
+ScriptFrameIter::hasArgsObj() const
{
switch (data_.state_) {
case DONE:
break;
case SCRIPTED:
return interpFrame()->hasArgsObj();
case ION:
#ifdef JS_ION
@@ -1890,17 +1890,17 @@ StackIter::hasArgsObj() const
break;
#endif
}
JS_NOT_REACHED("Unexpected state");
return false;
}
ArgumentsObject &
-StackIter::argsObj() const
+ScriptFrameIter::argsObj() const
{
JS_ASSERT(hasArgsObj());
switch (data_.state_) {
case DONE:
break;
case ION:
#ifdef JS_ION
@@ -1912,28 +1912,28 @@ StackIter::argsObj() const
case SCRIPTED:
return interpFrame()->argsObj();
}
JS_NOT_REACHED("Unexpected state");
return interpFrame()->argsObj();
}
bool
-StackIter::computeThis() const
+ScriptFrameIter::computeThis() const
{
JS_ASSERT(!done());
if (!isIonOptimizedJS()) {
JS_ASSERT(data_.cx_);
return ComputeThis(data_.cx_, abstractFramePtr());
}
return true;
}
Value
-StackIter::thisv() const
+ScriptFrameIter::thisv() const
{
switch (data_.state_) {
case DONE:
break;
case ION:
#ifdef JS_ION
if (data_.ionFrames_.isOptimizedJS())
return ObjectValue(*ionInlineFrames_.thisObject());
@@ -1944,17 +1944,17 @@ StackIter::thisv() const
case SCRIPTED:
return interpFrame()->thisValue();
}
JS_NOT_REACHED("Unexpected state");
return NullValue();
}
Value
-StackIter::returnValue() const
+ScriptFrameIter::returnValue() const
{
switch (data_.state_) {
case DONE:
break;
case ION:
#ifdef JS_ION
if (data_.ionFrames_.isBaselineJS())
return *data_.ionFrames_.baselineFrame()->returnValue();
@@ -1963,17 +1963,17 @@ StackIter::returnValue() const
case SCRIPTED:
return interpFrame()->returnValue();
}
JS_NOT_REACHED("Unexpected state");
return NullValue();
}
void
-StackIter::setReturnValue(const Value &v)
+ScriptFrameIter::setReturnValue(const Value &v)
{
switch (data_.state_) {
case DONE:
break;
case ION:
#ifdef JS_ION
if (data_.ionFrames_.isBaselineJS()) {
data_.ionFrames_.baselineFrame()->setReturnValue(v);
@@ -1984,17 +1984,17 @@ StackIter::setReturnValue(const Value &v
case SCRIPTED:
interpFrame()->setReturnValue(v);
return;
}
JS_NOT_REACHED("Unexpected state");
}
size_t
-StackIter::numFrameSlots() const
+ScriptFrameIter::numFrameSlots() const
{
switch (data_.state_) {
case DONE:
break;
case ION: {
#ifdef JS_ION
if (data_.ionFrames_.isOptimizedJS())
return ionInlineFrames_.snapshotIterator().slots() - ionInlineFrames_.script()->nfixed;
@@ -2009,17 +2009,17 @@ StackIter::numFrameSlots() const
JS_ASSERT(data_.cx_->regs().spForStackDepth(0) == interpFrame()->base());
return data_.cx_->regs().sp - interpFrame()->base();
}
JS_NOT_REACHED("Unexpected state");
return 0;
}
Value
-StackIter::frameSlotValue(size_t index) const
+ScriptFrameIter::frameSlotValue(size_t index) const
{
switch (data_.state_) {
case DONE:
break;
case ION:
#ifdef JS_ION
if (data_.ionFrames_.isOptimizedJS()) {
ion::SnapshotIterator si(ionInlineFrames_.snapshotIterator());
@@ -2157,17 +2157,17 @@ JSObject *
AbstractFramePtr::evalPrevScopeChain(JSRuntime *rt) const
{
/* Find the stack segment containing this frame. */
AllFramesIter alliter(rt);
while (alliter.isIonOptimizedJS() || alliter.abstractFramePtr() != *this)
++alliter;
/* Eval frames are not compiled by Ion, though their caller might be. */
- StackIter iter(rt, *alliter.seg());
+ ScriptFrameIter iter(rt, *alliter.seg());
while (iter.isIonOptimizedJS() || iter.abstractFramePtr() != *this)
++iter;
++iter;
return iter.scopeChain();
}
#ifdef DEBUG
void
--- a/js/src/vm/Stack.h
+++ b/js/src/vm/Stack.h
@@ -392,17 +392,17 @@ class StackFrame
Value *formals() const { return (Value *)this - fun()->nargs; }
Value *actuals() const { return formals() - (flags_ & OVERFLOW_ARGS ? 2 + u.nactual : 0); }
unsigned nactual() const { return u.nactual; }
private:
friend class FrameRegs;
friend class ContextStack;
friend class StackSpace;
- friend class StackIter;
+ friend class ScriptFrameIter;
friend class CallObject;
friend class ClonedBlockObject;
friend class ArgumentsObject;
#ifdef JS_METHODJIT
friend class mjit::CallCompiler;
friend class mjit::GetPropCompiler;
friend struct mjit::ic::GetElementIC;
#endif
@@ -532,18 +532,18 @@ class StackFrame
StackFrame *prev() const {
return prev_;
}
#ifdef JS_ION
/*
* To handle eval-in-frame with a baseline JIT frame, |prev_| points to the
* entry frame and prevBaselineFrame_ to the actual BaselineFrame. This is
- * done so that StackIter can skip JIT frames pushed on top of the baseline
- * frame (these frames should not appear in stack traces).
+ * done so that ScriptFrameIter can skip JIT frames pushed on top of the
+ * baseline frame (these frames should not appear in stack traces).
*/
ion::BaselineFrame *prevBaselineFrame() const {
JS_ASSERT(isEvalFrame());
return prevBaselineFrame_;
}
#endif
inline void resetGeneratorPrev(JSContext *cx);
@@ -1580,17 +1580,17 @@ class ContextStack
void popSegment();
friend class InvokeArgsGuard;
void popInvokeArgs(const InvokeArgsGuard &iag);
friend class FrameGuard;
void popFrame(const FrameGuard &fg);
friend class GeneratorFrameGuard;
void popGeneratorFrame(const GeneratorFrameGuard &gfg);
- friend class StackIter;
+ friend class ScriptFrameIter;
public:
ContextStack(JSContext *cx);
~ContextStack();
/*** Stack accessors ***/
/*
@@ -1796,25 +1796,25 @@ struct DefaultHasher<AbstractFramePtr> {
* JS_ASSERT(i.isNativeCall());
* ... i.args();
* }
* }
*
* The SavedOption parameter additionally lets the iterator continue through
* breaks in the callstack (from JS_SaveFrameChain). The default is to stop.
*/
-class StackIter
+class ScriptFrameIter
{
public:
enum SavedOption { STOP_AT_SAVED, GO_THROUGH_SAVED };
enum State { DONE, SCRIPTED, ION };
/*
- * Unlike StackIter itself, StackIter::Data can be allocated on the heap,
- * so this structure should not contain any GC things.
+ * Unlike ScriptFrameIter itself, ScriptFrameIter::Data can be allocated on
+ * the heap, so this structure should not contain any GC things.
*/
struct Data
{
PerThreadData *perThread_;
JSContext *cx_;
SavedOption savedOption_;
State state_;
@@ -1849,28 +1849,28 @@ class StackIter
void popIonFrame();
void popBaselineDebuggerFrame();
#endif
void settleOnNewSegment();
void settleOnNewState();
void startOnSegment(StackSegment *seg);
public:
- StackIter(JSContext *cx, SavedOption = STOP_AT_SAVED);
- StackIter(JSRuntime *rt, StackSegment &seg);
- StackIter(const StackIter &iter);
- StackIter(const Data &data);
+ ScriptFrameIter(JSContext *cx, SavedOption = STOP_AT_SAVED);
+ ScriptFrameIter(JSRuntime *rt, StackSegment &seg);
+ ScriptFrameIter(const ScriptFrameIter &iter);
+ ScriptFrameIter(const Data &data);
bool done() const { return data_.state_ == DONE; }
- StackIter &operator++();
+ ScriptFrameIter &operator++();
Data *copyData() const;
- bool operator==(const StackIter &rhs) const;
- bool operator!=(const StackIter &rhs) const { return !(*this == rhs); }
+ bool operator==(const ScriptFrameIter &rhs) const;
+ bool operator!=(const ScriptFrameIter &rhs) const { return !(*this == rhs); }
JSCompartment *compartment() const;
JSScript *script() const {
JS_ASSERT(!done());
if (data_.state_ == SCRIPTED)
return interpFrame()->script();
#ifdef JS_ION
@@ -1950,45 +1950,33 @@ class StackIter
// These are only valid for the top frame.
size_t numFrameSlots() const;
Value frameSlotValue(size_t index) const;
template <class Op>
inline void ionForEachCanonicalActualArg(JSContext *cx, Op op);
};
-/* A filtering of the StackIter to only stop at scripts. */
-class ScriptFrameIter : public StackIter
-{
- public:
- ScriptFrameIter(JSContext *cx, StackIter::SavedOption opt = StackIter::STOP_AT_SAVED)
- : StackIter(cx, opt) { }
-
- ScriptFrameIter(const StackIter::Data &data)
- : StackIter(data)
- {}
-};
-
-/* A filtering of the StackIter to only stop at non-self-hosted scripts. */
-class NonBuiltinScriptFrameIter : public StackIter
+/* A filtering of the ScriptFrameIter to only stop at non-self-hosted scripts. */
+class NonBuiltinScriptFrameIter : public ScriptFrameIter
{
void settle() {
while (!done() && script()->selfHosted)
- StackIter::operator++();
+ ScriptFrameIter::operator++();
}
public:
- NonBuiltinScriptFrameIter(JSContext *cx, StackIter::SavedOption opt = StackIter::STOP_AT_SAVED)
- : StackIter(cx, opt) { settle(); }
+ NonBuiltinScriptFrameIter(JSContext *cx, ScriptFrameIter::SavedOption opt = ScriptFrameIter::STOP_AT_SAVED)
+ : ScriptFrameIter(cx, opt) { settle(); }
- NonBuiltinScriptFrameIter(const StackIter::Data &data)
- : StackIter(data)
+ NonBuiltinScriptFrameIter(const ScriptFrameIter::Data &data)
+ : ScriptFrameIter(data)
{}
- NonBuiltinScriptFrameIter &operator++() { StackIter::operator++(); settle(); return *this; }
+ NonBuiltinScriptFrameIter &operator++() { ScriptFrameIter::operator++(); settle(); return *this; }
};
/*****************************************************************************/
/*
* Blindly iterate over all frames in the current thread's stack. These frames
* can be from different contexts and compartments, so beware. Iterates over
* Ion frames, but does not handle inlined frames.