mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-11-26 06:11:37 +00:00
Bug 930414 - Replace |thisObject| object op with |thisValue| and use if for modules r=shu r=smaug
This commit is contained in:
parent
59f519ac6f
commit
59be23d316
@ -3168,5 +3168,13 @@ DeprecationWarning(JSContext* aCx, JSObject* aObject,
|
||||
}
|
||||
}
|
||||
|
||||
bool
|
||||
ObjectToOuterObjectValue(JSContext* cx, JS::Handle<JSObject*> obj, JS::MutableHandle<JS::Value> vp)
|
||||
{
|
||||
JSObject* outer = JS_ObjectToOuterObject(cx, obj);
|
||||
vp.setObject(*outer);
|
||||
return true;
|
||||
}
|
||||
|
||||
} // namespace dom
|
||||
} // namespace mozilla
|
||||
|
@ -789,6 +789,9 @@ TryToOuterize(JSContext* cx, JS::MutableHandle<JS::Value> rval)
|
||||
return true;
|
||||
}
|
||||
|
||||
bool
|
||||
ObjectToOuterObjectValue(JSContext* cx, JS::Handle<JSObject*> obj, JS::MutableHandle<JS::Value> vp);
|
||||
|
||||
// Make sure to wrap the given string value into the right compartment, as
|
||||
// needed.
|
||||
MOZ_ALWAYS_INLINE
|
||||
|
@ -453,7 +453,7 @@ class CGDOMJSClass(CGThing):
|
||||
nullptr, /* unwatch */
|
||||
nullptr, /* getElements */
|
||||
nullptr, /* enumerate */
|
||||
JS_ObjectToOuterObject /* thisObject */
|
||||
mozilla::dom::ObjectToOuterObjectValue /* thisValue */
|
||||
}
|
||||
""",
|
||||
objectMoved=objectMovedHook)
|
||||
|
@ -427,6 +427,9 @@ typedef bool
|
||||
typedef bool
|
||||
(* UnwatchOp)(JSContext* cx, JS::HandleObject obj, JS::HandleId id);
|
||||
|
||||
typedef bool
|
||||
(* ThisValueOp)(JSContext* cx, JS::HandleObject obj, JS::MutableHandleValue vp);
|
||||
|
||||
class JS_FRIEND_API(ElementAdder)
|
||||
{
|
||||
public:
|
||||
@ -646,7 +649,7 @@ struct ObjectOps
|
||||
UnwatchOp unwatch;
|
||||
GetElementsOp getElements;
|
||||
JSNewEnumerateOp enumerate;
|
||||
ObjectOp thisObject;
|
||||
ThisValueOp thisValue;
|
||||
};
|
||||
|
||||
#define JS_NULL_OBJECT_OPS \
|
||||
|
@ -274,10 +274,8 @@ EvalKernel(JSContext* cx, const CallArgs& args, EvalType evalType, AbstractFrame
|
||||
MOZ_ASSERT(args.callee().global() == scopeobj->as<ClonedBlockObject>().global());
|
||||
|
||||
// Use the global as 'this', modulo outerization.
|
||||
JSObject* thisobj = GetThisObject(cx, scopeobj);
|
||||
if (!thisobj)
|
||||
if (!GetThisValue(cx, scopeobj, &thisv))
|
||||
return false;
|
||||
thisv = ObjectValue(*thisobj);
|
||||
}
|
||||
|
||||
RootedLinearString linearStr(cx, str->ensureLinear(cx));
|
||||
@ -441,10 +439,8 @@ js::DirectEvalStringFromIon(JSContext* cx,
|
||||
// value as necessary while it executes.
|
||||
RootedValue nthisValue(cx, thisValue);
|
||||
if (!callerScript->strict() && esg.script()->strict() && !thisValue.isObject()) {
|
||||
JSObject* obj = BoxNonStrictThis(cx, thisValue);
|
||||
if (!obj)
|
||||
if (!BoxNonStrictThis(cx, thisValue, &nthisValue))
|
||||
return false;
|
||||
nthisValue = ObjectValue(*obj);
|
||||
}
|
||||
|
||||
return ExecuteKernel(cx, esg.script(), *scopeobj, nthisValue, newTargetValue,
|
||||
@ -520,11 +516,10 @@ js::ExecuteInGlobalAndReturnScope(JSContext* cx, HandleObject global, HandleScri
|
||||
if (!scope)
|
||||
return false;
|
||||
|
||||
JSObject* thisobj = GetThisObject(cx, global);
|
||||
if (!thisobj)
|
||||
RootedValue thisv(cx);
|
||||
if (!GetThisValue(cx, global, &thisv))
|
||||
return false;
|
||||
|
||||
RootedValue thisv(cx, ObjectValue(*thisobj));
|
||||
RootedValue rval(cx);
|
||||
if (!ExecuteKernel(cx, script, *scope, thisv, UndefinedValue(), EXECUTE_GLOBAL,
|
||||
NullFramePtr() /* evalInFrame */, rval.address()))
|
||||
|
@ -943,13 +943,7 @@ static bool
|
||||
DoThisFallback(JSContext* cx, ICThis_Fallback* stub, HandleValue thisv, MutableHandleValue ret)
|
||||
{
|
||||
FallbackICSpew(cx, stub, "This");
|
||||
|
||||
JSObject* thisObj = BoxNonStrictThis(cx, thisv);
|
||||
if (!thisObj)
|
||||
return false;
|
||||
|
||||
ret.setObject(*thisObj);
|
||||
return true;
|
||||
return BoxNonStrictThis(cx, thisv, ret);
|
||||
}
|
||||
|
||||
typedef bool (*DoThisFallbackFn)(JSContext*, ICThis_Fallback*, HandleValue, MutableHandleValue);
|
||||
|
@ -5089,7 +5089,7 @@ CodeGenerator::visitReturnFromCtor(LReturnFromCtor* lir)
|
||||
masm.bind(&end);
|
||||
}
|
||||
|
||||
typedef JSObject* (*BoxNonStrictThisFn)(JSContext*, HandleValue);
|
||||
typedef bool (*BoxNonStrictThisFn)(JSContext*, HandleValue, MutableHandleValue);
|
||||
static const VMFunction BoxNonStrictThisInfo = FunctionInfo<BoxNonStrictThisFn>(BoxNonStrictThis);
|
||||
|
||||
void
|
||||
@ -5098,13 +5098,11 @@ CodeGenerator::visitComputeThis(LComputeThis* lir)
|
||||
ValueOperand value = ToValue(lir, LComputeThis::ValueIndex);
|
||||
Register output = ToRegister(lir->output());
|
||||
|
||||
OutOfLineCode* ool = oolCallVM(BoxNonStrictThisInfo, lir, ArgList(value),
|
||||
StoreRegisterTo(output));
|
||||
OutOfLineCode* ool = oolCallVM(BoxNonStrictThisInfo, lir, ArgList(value), StoreValueTo(value));
|
||||
|
||||
masm.branchTestObject(Assembler::NotEqual, value, ool->entry());
|
||||
masm.unboxObject(value, output);
|
||||
|
||||
masm.bind(ool->rejoin());
|
||||
masm.unboxObject(value, output);
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -1038,7 +1038,7 @@ GetObjectClassName(JSContext* cx, HandleObject obj);
|
||||
/*
|
||||
* Inner and outer objects
|
||||
*
|
||||
* GetInnerObject and GetOuterObject (and also GetThisObject, somewhat) have to
|
||||
* GetInnerObject and GetOuterObject (and also GetThisValue, somewhat) have to
|
||||
* do with Windows and WindowProxies. There's a screwy invariant that actual
|
||||
* Window objects (the global objects of web pages) are never directly exposed
|
||||
* to script. Instead we often substitute a WindowProxy.
|
||||
@ -1078,7 +1078,7 @@ GetInnerObject(JSObject* obj)
|
||||
*
|
||||
* This must be called before passing an object to script, if the object might
|
||||
* be a Window. (But usually those cases involve scope objects, and for those,
|
||||
* it is better to call GetThisObject instead.)
|
||||
* it is better to call GetThisValue instead.)
|
||||
*/
|
||||
inline JSObject*
|
||||
GetOuterObject(JSContext* cx, HandleObject obj)
|
||||
@ -1095,16 +1095,18 @@ GetOuterObject(JSContext* cx, HandleObject obj)
|
||||
* Some JSObjects shouldn't be exposed directly to script. This includes (at
|
||||
* least) DynamicWithObjects and Window objects. However, since both of those
|
||||
* can be on scope chains, we sometimes would expose those as `this` if we
|
||||
* were not so vigilant about calling GetThisObject where appropriate.
|
||||
* were not so vigilant about calling GetThisValue where appropriate.
|
||||
*
|
||||
* See comments at ComputeImplicitThis.
|
||||
*/
|
||||
inline JSObject*
|
||||
GetThisObject(JSContext* cx, HandleObject obj)
|
||||
inline bool
|
||||
GetThisValue(JSContext* cx, HandleObject obj, MutableHandleValue vp)
|
||||
{
|
||||
if (ObjectOp op = obj->getOps()->thisObject)
|
||||
return op(cx, obj);
|
||||
return obj;
|
||||
if (ThisValueOp op = obj->getOps()->thisValue)
|
||||
return op(cx, obj, vp);
|
||||
|
||||
vp.setObject(*obj);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
|
@ -6715,10 +6715,8 @@ DebuggerGenericEval(JSContext* cx, const char* fullMethodName, const Value& code
|
||||
* object, it should have a thisObject hook that returns the
|
||||
* appropriate outer object.
|
||||
*/
|
||||
JSObject* thisObj = GetThisObject(cx, scope);
|
||||
if (!thisObj)
|
||||
if (!GetThisValue(cx, scope, &thisv))
|
||||
return false;
|
||||
thisv = ObjectValue(*thisObj);
|
||||
env = scope;
|
||||
}
|
||||
|
||||
|
@ -63,11 +63,11 @@ ComputeThis(JSContext* cx, AbstractFramePtr frame)
|
||||
MOZ_ASSERT_IF(frame.isEvalFrame(), thisv.isUndefined() || thisv.isNull());
|
||||
}
|
||||
|
||||
JSObject* thisObj = BoxNonStrictThis(cx, thisv);
|
||||
if (!thisObj)
|
||||
RootedValue result(cx);
|
||||
if (!BoxNonStrictThis(cx, thisv, &result))
|
||||
return false;
|
||||
|
||||
frame.thisValue().setObject(*thisObj);
|
||||
frame.thisValue() = result;
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -84,8 +84,8 @@ LooseEqualityOp(JSContext* cx, InterpreterRegs& regs)
|
||||
return true;
|
||||
}
|
||||
|
||||
JSObject*
|
||||
js::BoxNonStrictThis(JSContext* cx, HandleValue thisv)
|
||||
bool
|
||||
js::BoxNonStrictThis(JSContext* cx, HandleValue thisv, MutableHandleValue vp)
|
||||
{
|
||||
/*
|
||||
* Check for SynthesizeFrame poisoning and fast constructors which
|
||||
@ -95,13 +95,16 @@ js::BoxNonStrictThis(JSContext* cx, HandleValue thisv)
|
||||
|
||||
if (thisv.isNullOrUndefined()) {
|
||||
Rooted<GlobalObject*> global(cx, cx->global());
|
||||
return GetThisObject(cx, global);
|
||||
return GetThisValue(cx, global, vp);
|
||||
}
|
||||
|
||||
if (thisv.isObject())
|
||||
return &thisv.toObject();
|
||||
if (thisv.isObject()) {
|
||||
vp.set(thisv);
|
||||
return true;
|
||||
}
|
||||
|
||||
return PrimitiveToObject(cx, thisv);
|
||||
vp.setObject(*PrimitiveToObject(cx, thisv));
|
||||
return true;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -133,12 +136,7 @@ js::BoxNonStrictThis(JSContext* cx, const CallReceiver& call)
|
||||
MOZ_ASSERT_IF(fun && fun->isInterpreted(), !fun->strict());
|
||||
#endif
|
||||
|
||||
JSObject* thisObj = BoxNonStrictThis(cx, call.thisv());
|
||||
if (!thisObj)
|
||||
return false;
|
||||
|
||||
call.setThis(ObjectValue(*thisObj));
|
||||
return true;
|
||||
return BoxNonStrictThis(cx, call.thisv(), call.mutableThisv());
|
||||
}
|
||||
|
||||
#if JS_HAS_NO_SUCH_METHOD
|
||||
@ -829,10 +827,8 @@ js::Invoke(JSContext* cx, const Value& thisv, const Value& fval, unsigned argc,
|
||||
fval.toObject().as<JSFunction>().jitInfo()->needsOuterizedThisObject())
|
||||
{
|
||||
RootedObject thisObj(cx, &args.thisv().toObject());
|
||||
JSObject* thisp = GetThisObject(cx, thisObj);
|
||||
if (!thisp)
|
||||
if (!GetThisValue(cx, thisObj, args.mutableThisv()))
|
||||
return false;
|
||||
args.setThis(ObjectValue(*thisp));
|
||||
}
|
||||
}
|
||||
|
||||
@ -1029,20 +1025,11 @@ js::Execute(JSContext* cx, HandleScript script, JSObject& scopeChainArg, Value*
|
||||
} while ((s = s->enclosingScope()));
|
||||
#endif
|
||||
|
||||
ExecuteType type;
|
||||
Value thisv;
|
||||
if (script->module()) {
|
||||
type = EXECUTE_MODULE;
|
||||
thisv = UndefinedValue();
|
||||
} else {
|
||||
type = EXECUTE_GLOBAL;
|
||||
ExecuteType type = script->module() ? EXECUTE_MODULE : EXECUTE_GLOBAL;
|
||||
|
||||
/* Use the scope chain as 'this', modulo outerization. */
|
||||
JSObject* thisObj = GetThisObject(cx, scopeChain);
|
||||
if (!thisObj)
|
||||
return false;
|
||||
thisv = ObjectValue(*thisObj);
|
||||
}
|
||||
RootedValue thisv(cx);
|
||||
if (!GetThisValue(cx, scopeChain, &thisv))
|
||||
return false;
|
||||
|
||||
return ExecuteKernel(cx, script, *scopeChain, thisv, NullValue(), type,
|
||||
NullFramePtr() /* evalInFrame */, rval);
|
||||
@ -1609,7 +1596,7 @@ JS_STATIC_ASSERT(JSOP_IFNE == JSOP_IFEQ + 1);
|
||||
* is what IsCacheableNonGlobalScope tests). Such objects-as-scopes must be
|
||||
* censored with undefined.
|
||||
*
|
||||
* Otherwise, we bind |this| to GetThisObject(cx, obj). Only names inside
|
||||
* Otherwise, we bind |this| to the result of GetThisValue(). Only names inside
|
||||
* |with| statements and embedding-specific scope objects fall into this
|
||||
* category.
|
||||
*
|
||||
@ -1632,12 +1619,7 @@ ComputeImplicitThis(JSContext* cx, HandleObject obj, MutableHandleValue vp)
|
||||
if (IsCacheableNonGlobalScope(obj))
|
||||
return true;
|
||||
|
||||
JSObject* nobj = GetThisObject(cx, obj);
|
||||
if (!nobj)
|
||||
return false;
|
||||
|
||||
vp.setObject(*nobj);
|
||||
return true;
|
||||
return GetThisValue(cx, obj, vp);
|
||||
}
|
||||
|
||||
static MOZ_ALWAYS_INLINE bool
|
||||
|
@ -31,8 +31,8 @@ class ScopeIter;
|
||||
extern bool
|
||||
BoxNonStrictThis(JSContext* cx, const CallReceiver& call);
|
||||
|
||||
extern JSObject*
|
||||
BoxNonStrictThis(JSContext* cx, HandleValue thisv);
|
||||
extern bool
|
||||
BoxNonStrictThis(JSContext* cx, HandleValue thisv, MutableHandleValue vp);
|
||||
|
||||
/*
|
||||
* Ensure that fp->thisValue() is the correct value of |this| for the scripted
|
||||
|
@ -344,7 +344,7 @@ const Class ModuleEnvironmentObject::class_ = {
|
||||
nullptr, nullptr, /* watch/unwatch */
|
||||
nullptr, /* getElements */
|
||||
ModuleEnvironmentObject::enumerate,
|
||||
nullptr /* thisObject */
|
||||
ModuleEnvironmentObject::thisValue
|
||||
}
|
||||
};
|
||||
|
||||
@ -519,6 +519,13 @@ ModuleEnvironmentObject::enumerate(JSContext* cx, HandleObject obj, AutoIdVector
|
||||
return true;
|
||||
}
|
||||
|
||||
/* static */ bool
|
||||
ModuleEnvironmentObject::thisValue(JSContext* cx, HandleObject obj, MutableHandleValue vp)
|
||||
{
|
||||
vp.setUndefined();
|
||||
return true;
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
||||
const Class DeclEnvObject::class_ = {
|
||||
@ -626,13 +633,13 @@ DynamicWithObject::create(JSContext* cx, HandleObject object, HandleObject enclo
|
||||
if (!obj)
|
||||
return nullptr;
|
||||
|
||||
JSObject* thisp = GetThisObject(cx, object);
|
||||
if (!thisp)
|
||||
RootedValue thisv(cx);
|
||||
if (!GetThisValue(cx, object, &thisv))
|
||||
return nullptr;
|
||||
|
||||
obj->setEnclosingScope(enclosing);
|
||||
obj->setFixedSlot(OBJECT_SLOT, ObjectValue(*object));
|
||||
obj->setFixedSlot(THIS_SLOT, ObjectValue(*thisp));
|
||||
obj->setFixedSlot(THIS_SLOT, thisv);
|
||||
obj->setFixedSlot(KIND_SLOT, Int32Value(kind));
|
||||
|
||||
return obj;
|
||||
@ -698,10 +705,11 @@ with_DeleteProperty(JSContext* cx, HandleObject obj, HandleId id, ObjectOpResult
|
||||
return DeleteProperty(cx, actual, id, result);
|
||||
}
|
||||
|
||||
static JSObject*
|
||||
with_ThisObject(JSContext* cx, HandleObject obj)
|
||||
static bool
|
||||
with_ThisValue(JSContext* cx, HandleObject obj, MutableHandleValue vp)
|
||||
{
|
||||
return &obj->as<DynamicWithObject>().withThis();
|
||||
vp.set(obj->as<DynamicWithObject>().withThis());
|
||||
return true;
|
||||
}
|
||||
|
||||
const Class StaticWithObject::class_ = {
|
||||
@ -739,7 +747,7 @@ const Class DynamicWithObject::class_ = {
|
||||
nullptr, nullptr, /* watch/unwatch */
|
||||
nullptr, /* getElements */
|
||||
nullptr, /* enumerate (native enumeration of target doesn't work) */
|
||||
with_ThisObject,
|
||||
with_ThisValue,
|
||||
}
|
||||
};
|
||||
|
||||
@ -1005,8 +1013,8 @@ StaticBlockObject::addVar(ExclusiveContext* cx, Handle<StaticBlockObject*> block
|
||||
/* allowDictionary = */ false);
|
||||
}
|
||||
|
||||
static JSObject*
|
||||
block_ThisObject(JSContext* cx, HandleObject obj)
|
||||
static bool
|
||||
block_ThisValue(JSContext* cx, HandleObject obj, MutableHandleValue vp)
|
||||
{
|
||||
// No other block objects should ever get passed to the 'this' object
|
||||
// hook except the global lexical scope and non-syntactic ones.
|
||||
@ -1015,7 +1023,7 @@ block_ThisObject(JSContext* cx, HandleObject obj)
|
||||
MOZ_ASSERT_IF(obj->as<ClonedBlockObject>().isGlobal(),
|
||||
obj->enclosingScope() == cx->global());
|
||||
RootedObject enclosing(cx, obj->enclosingScope());
|
||||
return GetThisObject(cx, enclosing);
|
||||
return GetThisValue(cx, enclosing, vp);
|
||||
}
|
||||
|
||||
const Class BlockObject::class_ = {
|
||||
@ -1047,7 +1055,7 @@ const Class BlockObject::class_ = {
|
||||
nullptr, nullptr, /* watch/unwatch */
|
||||
nullptr, /* getElements */
|
||||
nullptr, /* enumerate (native enumeration of target doesn't work) */
|
||||
block_ThisObject,
|
||||
block_ThisValue,
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -403,6 +403,7 @@ class ModuleEnvironmentObject : public CallObject
|
||||
ObjectOpResult& result);
|
||||
static bool enumerate(JSContext* cx, HandleObject obj, AutoIdVector& properties,
|
||||
bool enumerableOnly);
|
||||
static bool thisValue(JSContext* cx, HandleObject obj, MutableHandleValue vp);
|
||||
};
|
||||
|
||||
typedef Rooted<ModuleEnvironmentObject*> RootedModuleEnvironmentObject;
|
||||
@ -676,8 +677,10 @@ class DynamicWithObject : public NestedScopeObject
|
||||
}
|
||||
|
||||
/* Return object for the 'this' class hook. */
|
||||
JSObject& withThis() const {
|
||||
return getReservedSlot(THIS_SLOT).toObject();
|
||||
Value withThis() const {
|
||||
Value thisValue = getReservedSlot(THIS_SLOT);
|
||||
MOZ_ASSERT(thisValue.isObject());
|
||||
return thisValue;
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -665,7 +665,7 @@ const XPCWrappedNativeJSClass XPC_WN_NoHelper_JSClass = {
|
||||
nullptr, nullptr, // watch/unwatch
|
||||
nullptr, // getElements
|
||||
nullptr, // enumerate
|
||||
XPC_WN_JSOp_ThisObject,
|
||||
XPC_WN_JSOp_ThisValue,
|
||||
}
|
||||
}
|
||||
};
|
||||
@ -927,10 +927,10 @@ XPC_WN_JSOp_Enumerate(JSContext* cx, HandleObject obj, AutoIdVector& properties,
|
||||
return retval;
|
||||
}
|
||||
|
||||
JSObject*
|
||||
XPC_WN_JSOp_ThisObject(JSContext* cx, HandleObject obj)
|
||||
bool
|
||||
XPC_WN_JSOp_ThisValue(JSContext* cx, HandleObject obj, MutableHandleValue vp)
|
||||
{
|
||||
return JS_ObjectToOuterObject(cx, obj);
|
||||
return mozilla::dom::ObjectToOuterObjectValue(cx, obj, vp);
|
||||
}
|
||||
|
||||
/***************************************************************************/
|
||||
@ -1036,7 +1036,7 @@ XPCNativeScriptableShared::PopulateJSClass()
|
||||
js::ObjectOps* ops = &mJSClass.base.ops;
|
||||
if (mFlags.WantNewEnumerate())
|
||||
ops->enumerate = XPC_WN_JSOp_Enumerate;
|
||||
ops->thisObject = XPC_WN_JSOp_ThisObject;
|
||||
ops->thisValue = XPC_WN_JSOp_ThisValue;
|
||||
|
||||
|
||||
if (mFlags.WantCall())
|
||||
|
@ -944,8 +944,8 @@ XPC_WN_CallMethod(JSContext* cx, unsigned argc, JS::Value* vp);
|
||||
extern bool
|
||||
XPC_WN_GetterSetter(JSContext* cx, unsigned argc, JS::Value* vp);
|
||||
|
||||
extern JSObject*
|
||||
XPC_WN_JSOp_ThisObject(JSContext* cx, JS::HandleObject obj);
|
||||
extern bool
|
||||
XPC_WN_JSOp_ThisValue(JSContext* cx, JS::HandleObject obj, JS::MutableHandleValue vp);
|
||||
|
||||
// Macros to initialize Object or Function like XPC_WN classes
|
||||
#define XPC_WN_WithCall_ObjectOps \
|
||||
@ -960,7 +960,7 @@ XPC_WN_JSOp_ThisObject(JSContext* cx, JS::HandleObject obj);
|
||||
nullptr, nullptr, /* watch/unwatch */ \
|
||||
nullptr, /* getElements */ \
|
||||
nullptr, /* enumerate */ \
|
||||
XPC_WN_JSOp_ThisObject, \
|
||||
XPC_WN_JSOp_ThisValue, \
|
||||
}
|
||||
|
||||
#define XPC_WN_NoCall_ObjectOps \
|
||||
@ -975,7 +975,7 @@ XPC_WN_JSOp_ThisObject(JSContext* cx, JS::HandleObject obj);
|
||||
nullptr, nullptr, /* watch/unwatch */ \
|
||||
nullptr, /* getElements */ \
|
||||
nullptr, /* enumerate */ \
|
||||
XPC_WN_JSOp_ThisObject, \
|
||||
XPC_WN_JSOp_ThisValue, \
|
||||
}
|
||||
|
||||
// Maybe this macro should check for class->enumerate ==
|
||||
|
Loading…
Reference in New Issue
Block a user