static void PatchGetFallback(VMFrame &f, ic::GetGlobalNameIC *ic) { Repatcher repatch(f.chunk()); JSC::FunctionPtr fptr(JS_FUNC_TO_DATA_PTR(void *, stubs::Name)); repatch.relink(ic->slowPathCall, fptr); }
static LookupStatus UpdateSetGlobalName(VMFrame &f, ic::SetGlobalNameIC *ic, JSObject *obj, Shape *shape) { /* Give globals a chance to appear. */ if (!shape) return Lookup_Uncacheable; if (!shape->hasDefaultSetter() || !shape->writable() || !shape->hasSlot() || obj->watched()) { /* Disable the IC for weird shape attributes and watchpoints. */ PatchSetFallback(f, ic); return Lookup_Uncacheable; } /* Object is not branded, so we can use the inline path. */ Repatcher repatcher(f.chunk()); ic->patchInlineShapeGuard(repatcher, obj->lastProperty()); uint32_t index = obj->dynamicSlotIndex(shape->slot()); JSC::CodeLocationLabel label = ic->fastPathStart.labelAtOffset(ic->loadStoreOffset); repatcher.patchAddressOffsetForValueStore(label, index * sizeof(Value), ic->vr.isTypeKnown()); return Lookup_Cacheable; }
static void PatchSetFallback(VMFrame &f, ic::SetGlobalNameIC *ic) { Repatcher repatch(f.chunk()); VoidStubSetGlobal stub = STRICT_VARIANT(f.script(), DisabledSetGlobal); JSC::FunctionPtr fptr(JS_FUNC_TO_DATA_PTR(void *, stub)); repatch.relink(ic->slowPathCall, fptr); }
void JS_FASTCALL ic::GetGlobalName(VMFrame &f, ic::GetGlobalNameIC *ic) { AssertCanGC(); RootedObject obj(f.cx, &f.fp()->global()); PropertyName *name = f.script()->getName(GET_UINT32_INDEX(f.pc())); RecompilationMonitor monitor(f.cx); uint32_t slot; { RootedShape shape(f.cx, obj->nativeLookup(f.cx, NameToId(name))); if (monitor.recompiled()) { stubs::Name(f); return; } if (!shape || !shape->hasDefaultGetter() || !shape->hasSlot()) { if (shape) PatchGetFallback(f, ic); stubs::Name(f); return; } slot = shape->slot(); /* Patch shape guard. */ Repatcher repatcher(f.chunk()); repatcher.repatch(ic->fastPathStart.dataLabelPtrAtOffset(ic->shapeOffset), obj->lastProperty()); /* Patch loads. */ uint32_t index = obj->dynamicSlotIndex(slot); JSC::CodeLocationLabel label = ic->fastPathStart.labelAtOffset(ic->loadStoreOffset); repatcher.patchAddressOffsetForValueLoad(label, index * sizeof(Value)); } /* Do load anyway... this time. */ stubs::Name(f); }
void JS_FASTCALL ic::GetGlobalName(VMFrame &f, ic::GetGlobalNameIC *ic) { JSObject &obj = f.fp()->scopeChain().global(); PropertyName *name = f.script()->getName(GET_UINT32_INDEX(f.pc())); RecompilationMonitor monitor(f.cx); const Shape *shape = obj.nativeLookup(f.cx, js_CheckForStringIndex(ATOM_TO_JSID(name))); if (monitor.recompiled()) { stubs::Name(f); return; } if (!shape || !shape->hasDefaultGetter() || !shape->hasSlot()) { if (shape) PatchGetFallback(f, ic); stubs::Name(f); return; } uint32_t slot = shape->slot(); /* Patch shape guard. */ Repatcher repatcher(f.chunk()); repatcher.repatch(ic->fastPathStart.dataLabelPtrAtOffset(ic->shapeOffset), obj.lastProperty()); /* Patch loads. */ uint32_t index = obj.dynamicSlotIndex(slot); JSC::CodeLocationLabel label = ic->fastPathStart.labelAtOffset(ic->loadStoreOffset); repatcher.patchAddressOffsetForValueLoad(label, index * sizeof(Value)); /* Do load anyway... this time. */ stubs::Name(f); }