static void MarkIonActivation(JSTracer *trc, const IonActivationIterator &activations) { for (IonFrameIterator frames(activations); !frames.done(); ++frames) { switch (frames.type()) { case IonFrame_Exit: MarkIonExitFrame(trc, frames); break; case IonFrame_JS: MarkIonJSFrame(trc, frames); break; case IonFrame_Bailed_JS: JS_NOT_REACHED("invalid"); break; case IonFrame_Rectifier: case IonFrame_Bailed_Rectifier: { IonCompartment *ionCompartment = activations.activation()->compartment()->ionCompartment(); MarkIonCodeRoot(trc, ionCompartment->getArgumentsRectifierAddr(), "Arguments Rectifier"); break; } case IonFrame_Osr: // The callee token will be marked by the callee JS frame; // otherwise, it does not need to be marked, since the frame is // dead. break; default: JS_NOT_REACHED("unexpected frame type"); break; } } }
IonBailoutIterator::IonBailoutIterator(const IonActivationIterator &activations, BailoutStack *bailout) : IonFrameIterator(activations), machine_(bailout->machine()) { uint8_t *sp = bailout->parentStackPointer(); uint8_t *fp = sp + bailout->frameSize(); current_ = fp; type_ = IonFrame_OptimizedJS; topFrameSize_ = current_ - sp; topIonScript_ = script()->ion; if (bailout->frameClass() == FrameSizeClass::None()) { snapshotOffset_ = bailout->snapshotOffset(); return; } // Compute the snapshot offset from the bailout ID. IonActivation *activation = activations.activation(); JSCompartment *jsCompartment = activation->compartment(); IonCompartment *ionCompartment = jsCompartment->ionCompartment(); IonCode *code = ionCompartment->getBailoutTable(bailout->frameClass()); uintptr_t tableOffset = bailout->tableOffset(); uintptr_t tableStart = reinterpret_cast<uintptr_t>(code->raw()); JS_ASSERT(tableOffset >= tableStart && tableOffset < tableStart + code->instructionsSize()); JS_ASSERT((tableOffset - tableStart) % BAILOUT_TABLE_ENTRY_SIZE == 0); uint32_t bailoutId = ((tableOffset - tableStart) / BAILOUT_TABLE_ENTRY_SIZE) - 1; JS_ASSERT(bailoutId < BAILOUT_TABLE_SIZE); snapshotOffset_ = topIonScript_->bailoutToSnapshot(bailoutId); }
IonFrameIterator::IonFrameIterator(const IonActivationIterator &activations) : current_(activations.top()), type_(IonFrame_Exit), returnAddressToFp_(NULL), frameSize_(0), cachedSafepointIndex_(NULL), activation_(activations.activation()) { }