bool WatchpointMap::triggerWatchpoint(JSContext *cx, HandleObject obj, HandleId id, MutableHandleValue vp) { Map::Ptr p = map.lookup(WatchKey(obj, id)); if (!p || p->value.held) return true; AutoEntryHolder holder(cx, map, p); /* Copy the entry, since GC would invalidate p. */ JSWatchPointHandler handler = p->value.handler; RootedObject closure(cx, p->value.closure); /* Determine the property's old value. */ Value old; old.setUndefined(); if (obj->isNative()) { if (RawShape shape = obj->nativeLookup(cx, id)) { if (shape->hasSlot()) old = obj->nativeGetSlot(shape->slot()); } } // Read barrier to prevent an incorrectly gray closure from escaping the // watchpoint. See the comment before UnmarkGrayChildren in gc/Marking.cpp ExposeGCThingToActiveJS(closure, JSTRACE_OBJECT); /* Call the handler. */ return handler(cx, obj, id, old, vp.address(), closure); }
bool WatchpointMap::triggerWatchpoint(JSContext *cx, HandleObject obj, HandleId id, Value *vp) { Map::Ptr p = map.lookup(WatchKey(obj, id)); if (!p || p->value.held) return true; AutoEntryHolder holder(cx, map, p); /* Copy the entry, since GC would invalidate p. */ JSWatchPointHandler handler = p->value.handler; RootedObject closure(cx, p->value.closure); /* Determine the property's old value. */ Value old; old.setUndefined(); if (obj->isNative()) { if (const Shape *shape = obj->nativeLookup(cx, id)) { if (shape->hasSlot()) old = obj->nativeGetSlot(shape->slot()); } } /* Call the handler. */ return handler(cx, obj, id, old, vp, closure); }