New Tag scheme, no SetObject silliness
This commit is contained in:
@@ -1105,7 +1105,7 @@ js_InitFunctionAndObjectClasses(JSContext *cx, JSObject *obj)
|
||||
goto out;
|
||||
}
|
||||
obj->defineProperty(cx, ATOM_TO_JSID(CLASS_ATOM(cx, Function)),
|
||||
FunObjValue(*ctor), 0, 0, 0);
|
||||
FunObjTag(*ctor), 0, 0, 0);
|
||||
}
|
||||
|
||||
/* Initialize the object class next so Object.prototype works. */
|
||||
@@ -1121,9 +1121,9 @@ js_InitFunctionAndObjectClasses(JSContext *cx, JSObject *obj)
|
||||
}
|
||||
|
||||
/* Function.prototype and the global object delegate to Object.prototype. */
|
||||
fun_proto->setProto(NonFunObjPtr(*obj_proto));
|
||||
fun_proto->setProto(NonFunObjTag(*obj_proto));
|
||||
if (!obj->getProto())
|
||||
obj->setProto(NonFunObjPtr(*obj_proto));
|
||||
obj->setProto(NonFunObjTag(*obj_proto));
|
||||
|
||||
out:
|
||||
/* If resolving, remove the other entry (Object or Function) from table. */
|
||||
@@ -2894,7 +2894,7 @@ JS_DefineObject(JSContext *cx, JSObject *obj, const char *name, JSClass *jsclasp
|
||||
JSObject *nobj = NewObject(cx, clasp, proto, obj);
|
||||
if (!nobj)
|
||||
return NULL;
|
||||
if (!DefineProperty(cx, obj, name, ToValue(nobj), NULL, NULL, attrs,
|
||||
if (!DefineProperty(cx, obj, name, ObjectTag(*nobj), NULL, NULL, attrs,
|
||||
0, 0)) {
|
||||
return NULL;
|
||||
}
|
||||
@@ -3064,7 +3064,7 @@ LookupResult(JSContext *cx, JSObject *obj, JSObject *obj2, JSProperty *prop,
|
||||
if (sprop->isMethod()) {
|
||||
AutoScopePropertyRooter root(cx, sprop);
|
||||
JS_UNLOCK_OBJ(cx, obj2);
|
||||
vp->copy(sprop->methodValue());
|
||||
vp->setFunObj(sprop->methodFunObj());
|
||||
return obj2->scope()->methodReadBarrier(cx, sprop, vp);
|
||||
}
|
||||
|
||||
@@ -3966,7 +3966,7 @@ JS_NextProperty(JSContext *cx, JSObject *iterobj, jsid *idp)
|
||||
*idp = JSID_VOID;
|
||||
} else {
|
||||
*idp = ida->vector[--i];
|
||||
iterobj->setSlot(JSSLOT_ITER_INDEX, Value(i));
|
||||
iterobj->setSlot(JSSLOT_ITER_INDEX, Int32Tag(i));
|
||||
}
|
||||
}
|
||||
return JS_TRUE;
|
||||
@@ -4081,7 +4081,7 @@ JS_CloneFunctionObject(JSContext *cx, JSObject *funobj, JSObject *parent)
|
||||
* idea, but we changed incompatibly to teach any abusers a lesson!).
|
||||
*/
|
||||
Value v;
|
||||
SetObject(&v, funobj);
|
||||
v.setObject(*funobj);
|
||||
js_ReportIsNotFunction(cx, &v, 0);
|
||||
return NULL;
|
||||
}
|
||||
@@ -4684,8 +4684,7 @@ JS_CompileUCFunctionForPrincipals(JSContext *cx, JSObject *obj,
|
||||
}
|
||||
|
||||
if (obj && funAtom &&
|
||||
!obj->defineProperty(cx, ATOM_TO_JSID(funAtom),
|
||||
FunObjValue(*FUN_OBJECT(fun)),
|
||||
!obj->defineProperty(cx, ATOM_TO_JSID(funAtom), fun->funObjVal(),
|
||||
NULL, NULL, JSPROP_ENUMERATE)) {
|
||||
fun = NULL;
|
||||
}
|
||||
@@ -4849,8 +4848,8 @@ JS_CallFunction(JSContext *cx, JSObject *obj, JSFunction *fun, uintN argc,
|
||||
JSBool ok;
|
||||
|
||||
CHECK_REQUEST(cx);
|
||||
ok = InternalCall(cx, obj, FunObjValue(*FUN_OBJECT(fun)), argc,
|
||||
Valueify(argv), Valueify(rval));
|
||||
ok = InternalCall(cx, obj, fun->funObjVal(), argc, Valueify(argv),
|
||||
Valueify(rval));
|
||||
LAST_FRAME_CHECKS(cx, ok);
|
||||
return ok;
|
||||
}
|
||||
@@ -4898,7 +4897,7 @@ JS_New(JSContext *cx, JSObject *ctor, uintN argc, jsval *argv)
|
||||
return NULL;
|
||||
|
||||
Value *vp = args.getvp();
|
||||
SetObject(&vp[0], ctor);
|
||||
vp[0].setObject(*ctor);
|
||||
vp[1].setNull();
|
||||
memcpy(vp + 2, argv, argc * sizeof(jsval));
|
||||
|
||||
|
||||
451
js/src/jsapi.h
451
js/src/jsapi.h
@@ -2950,6 +2950,59 @@ JS_END_EXTERN_C
|
||||
|
||||
namespace js {
|
||||
|
||||
struct NullTag {
|
||||
explicit NullTag() {}
|
||||
};
|
||||
|
||||
struct UndefinedTag {
|
||||
explicit UndefinedTag() {}
|
||||
};
|
||||
|
||||
struct Int32Tag {
|
||||
explicit Int32Tag(int32 i32) : i32(i32) {}
|
||||
int32 i32;
|
||||
};
|
||||
|
||||
struct FunObjTag {
|
||||
explicit FunObjTag(JSObject &obj) : obj(obj) {}
|
||||
JSObject &obj;
|
||||
};
|
||||
|
||||
struct FunObjOrNull {
|
||||
explicit FunObjOrNull(JSObject *obj) : obj(obj) {}
|
||||
JSObject *obj;
|
||||
};
|
||||
|
||||
struct FunObjOrUndefinedTag {
|
||||
explicit FunObjOrUndefinedTag(JSObject *obj) : obj(obj) {}
|
||||
JSObject *obj;
|
||||
};
|
||||
|
||||
struct NonFunObjTag {
|
||||
explicit NonFunObjTag(JSObject &o) : obj(obj) {}
|
||||
JSObject &obj;
|
||||
};
|
||||
|
||||
struct NonFunObjOrNull {
|
||||
explicit NonFunObjOrNull(JSObject *obj) : obj(obj) {}
|
||||
JSObject *obj;
|
||||
};
|
||||
|
||||
struct ObjectTag {
|
||||
explicit ObjectTag(JSObject &obj) : obj(obj) {}
|
||||
JSObject &obj;
|
||||
};
|
||||
|
||||
struct ObjectOrNullTag {
|
||||
explicit ObjectOrNullTag(JSObject *obj) : obj(obj) {}
|
||||
JSObject *obj;
|
||||
};
|
||||
|
||||
struct BooleanTag {
|
||||
explicit BooleanTag(bool boo) : boo(boo) {}
|
||||
bool boo;
|
||||
};
|
||||
|
||||
/*
|
||||
* An ObjPtr is a restriction of a Value (below) to the three types: null,
|
||||
* non-function object and function object. ObjPtr is useful when code
|
||||
@@ -2981,14 +3034,41 @@ class ObjPtr
|
||||
public:
|
||||
/* Constructors */
|
||||
|
||||
/* N.B. defualt construction yields a ObjPtr in an undefined state. */
|
||||
ObjPtr() {}
|
||||
ObjPtr() {
|
||||
/* N.B. mask and obj are undefined */
|
||||
}
|
||||
|
||||
/*
|
||||
* To construct a null pointer, use NullObjPtr. To construct pointers to
|
||||
* objects statically known to be, or not to be, function objects, use
|
||||
* FunObjPtr, NonFunObjPtr.
|
||||
*/
|
||||
ObjPtr(NullTag) {
|
||||
mask = NullMask;
|
||||
obj = NULL;
|
||||
}
|
||||
|
||||
ObjPtr(FunObjTag arg) {
|
||||
JS_ASSERT(JS_ObjectIsFunction(NULL, &arg.obj));
|
||||
mask = FunObjMask;
|
||||
obj = &arg.obj;
|
||||
}
|
||||
|
||||
ObjPtr(FunObjOrNull arg) {
|
||||
JS_ASSERT_IF(arg.obj, JS_ObjectIsFunction(NULL, arg.obj));
|
||||
mask = arg.obj ? FunObjMask : NullMask;
|
||||
obj = arg.obj;
|
||||
}
|
||||
|
||||
ObjPtr(NonFunObjTag arg) {
|
||||
JS_ASSERT(!JS_ObjectIsFunction(NULL, &arg.obj));
|
||||
mask = NonFunObjMask;
|
||||
obj = &arg.obj;
|
||||
}
|
||||
|
||||
ObjPtr(NonFunObjOrNull arg) {
|
||||
JS_ASSERT_IF(arg.obj, !JS_ObjectIsFunction(NULL, arg.obj));
|
||||
mask = arg.obj ? NonFunObjMask : NullMask;
|
||||
obj = arg.obj;
|
||||
}
|
||||
|
||||
inline ObjPtr(ObjectTag arg);
|
||||
inline ObjPtr(ObjectOrNullTag arg);
|
||||
|
||||
/* Accessors */
|
||||
|
||||
@@ -3040,28 +3120,32 @@ class ObjPtr
|
||||
obj = NULL;
|
||||
}
|
||||
|
||||
void setFunObj(JSObject &o) {
|
||||
JS_ASSERT(JS_ObjectIsFunction(NULL, &o));
|
||||
void setFunObj(JSObject &arg) {
|
||||
JS_ASSERT(JS_ObjectIsFunction(NULL, &arg));
|
||||
mask = FunObjMask;
|
||||
obj = &o;
|
||||
obj = &arg;
|
||||
}
|
||||
|
||||
void setNonFunObj(JSObject &o) {
|
||||
JS_ASSERT(!JS_ObjectIsFunction(NULL, &o));
|
||||
mask = NonFunObjMask;
|
||||
obj = &o;
|
||||
void setFunObjOrNull(JSObject *arg) {
|
||||
JS_ASSERT_IF(arg, JS_ObjectIsFunction(NULL, arg));
|
||||
mask = arg ? FunObjMask : NullMask;
|
||||
obj = arg;
|
||||
}
|
||||
|
||||
void setNonFunObjOrNull(JSObject *o) {
|
||||
if (o) {
|
||||
JS_ASSERT(!JS_ObjectIsFunction(NULL, o));
|
||||
void setNonFunObj(JSObject &arg) {
|
||||
JS_ASSERT(!JS_ObjectIsFunction(NULL, &arg));
|
||||
mask = NonFunObjMask;
|
||||
obj = o;
|
||||
} else {
|
||||
mask = NullMask;
|
||||
obj = o;
|
||||
obj = &arg;
|
||||
}
|
||||
|
||||
void setNonFunObjOrNull(JSObject *arg) {
|
||||
JS_ASSERT_IF(arg, !JS_ObjectIsFunction(NULL, arg));
|
||||
mask = arg ? NonFunObjMask : NullMask;
|
||||
obj = arg;
|
||||
}
|
||||
|
||||
inline void setObject(JSObject &arg);
|
||||
inline void setObjectOrNull(JSObject *arg);
|
||||
};
|
||||
|
||||
inline bool operator==(ObjPtr lhs, ObjPtr rhs) { return lhs == rhs; }
|
||||
@@ -3071,56 +3155,7 @@ inline bool operator!=(ObjPtr lhs, ObjPtr rhs) { return !(lhs == rhs); }
|
||||
inline bool operator!=(ObjPtr lhs, JSObject *rhs) { return !(lhs == rhs); }
|
||||
inline bool operator!=(JSObject *lhs, ObjPtr rhs) { return !(lhs == rhs); }
|
||||
|
||||
/*
|
||||
* These types are intended to be used like:
|
||||
*
|
||||
* ObjPtr p = NullObjPtr();
|
||||
* void f1(ObjPtr);
|
||||
* f1(FunObjPtr(funobj));
|
||||
*/
|
||||
|
||||
struct NullObjPtr : ObjPtr
|
||||
{
|
||||
explicit NullObjPtr() {
|
||||
mask = NullMask;
|
||||
obj = NULL;
|
||||
}
|
||||
};
|
||||
|
||||
struct FunObjPtr : ObjPtr
|
||||
{
|
||||
explicit FunObjPtr(JSObject &o) {
|
||||
JS_ASSERT(JS_ObjectIsFunction(NULL, &o));
|
||||
mask = FunObjMask;
|
||||
obj = &o;
|
||||
}
|
||||
};
|
||||
|
||||
struct NonFunObjPtr : ObjPtr
|
||||
{
|
||||
explicit NonFunObjPtr(JSObject &o) {
|
||||
JS_ASSERT(!JS_ObjectIsFunction(NULL, &o));
|
||||
mask = NonFunObjMask;
|
||||
obj = &o;
|
||||
}
|
||||
};
|
||||
|
||||
struct NonFunObjOrNullPtr : ObjPtr
|
||||
{
|
||||
explicit NonFunObjOrNullPtr(JSObject *o) {
|
||||
if (o) {
|
||||
JS_ASSERT(!JS_ObjectIsFunction(NULL, o));
|
||||
mask = NonFunObjMask;
|
||||
obj = o;
|
||||
} else {
|
||||
mask = NullMask;
|
||||
obj = NULL;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/* TODO: this can be removed when copying is implicit/public. */
|
||||
class ExplicitlyConstructedValue;
|
||||
class CopyableValue;
|
||||
|
||||
/*
|
||||
* While there is a single representation for values, there are two declared
|
||||
@@ -3195,65 +3230,90 @@ class Value
|
||||
Value &operator=(const Value &);
|
||||
|
||||
public:
|
||||
/* XXX: this can be removed when copying is public/implicit */
|
||||
inline Value(const ExplicitlyConstructedValue &v);
|
||||
/* Constructors */
|
||||
|
||||
/*
|
||||
* Constructors
|
||||
*
|
||||
* To construct a null value, use NullValue. To construct pointers to
|
||||
* objects statically known to be, or not to be, function objects, use
|
||||
* FunObjValue, NonFunObjValue.
|
||||
*/
|
||||
Value() {
|
||||
/* N.B. mask and data are undefined. */
|
||||
}
|
||||
|
||||
/* N.B. default construction yields a Value in an undefined state. */
|
||||
Value() {}
|
||||
Value(NullTag) {
|
||||
mask = NullMask;
|
||||
data.obj = NULL;
|
||||
}
|
||||
|
||||
Value(UndefinedTag) {
|
||||
mask = UndefinedMask;
|
||||
/* N.B. data is undefined */
|
||||
}
|
||||
|
||||
Value(Int32Tag arg) {
|
||||
mask = Int32Mask;
|
||||
data.i32 = arg.i32;
|
||||
}
|
||||
|
||||
Value(double arg) {
|
||||
mask = DoubleMask;
|
||||
data.dbl = arg;
|
||||
}
|
||||
|
||||
Value(JSString *arg) {
|
||||
mask = StringMask;
|
||||
data.str = arg;
|
||||
}
|
||||
|
||||
Value(FunObjTag arg) {
|
||||
JS_ASSERT(JS_ObjectIsFunction(NULL, &arg.obj));
|
||||
mask = FunObjMask;
|
||||
data.obj = &arg.obj;
|
||||
}
|
||||
|
||||
Value(FunObjOrNull arg) {
|
||||
JS_ASSERT_IF(arg.obj, JS_ObjectIsFunction(NULL, arg.obj));
|
||||
mask = arg.obj ? FunObjMask : NullMask;
|
||||
data.obj = arg.obj;
|
||||
}
|
||||
|
||||
Value(FunObjOrUndefinedTag arg) {
|
||||
JS_ASSERT_IF(arg.obj, JS_ObjectIsFunction(NULL, arg.obj));
|
||||
mask = arg.obj ? FunObjMask : UndefinedMask;
|
||||
data.obj = arg.obj;
|
||||
}
|
||||
|
||||
Value(NonFunObjTag arg) {
|
||||
JS_ASSERT(JS_ObjectIsFunction(NULL, &arg.obj));
|
||||
mask = NonFunObjMask;
|
||||
data.obj = &arg.obj;
|
||||
}
|
||||
|
||||
Value(NonFunObjOrNull arg) {
|
||||
JS_ASSERT_IF(arg.obj, !JS_ObjectIsFunction(NULL, arg.obj));
|
||||
mask = arg.obj ? NonFunObjMask : NullMask;
|
||||
data.obj = arg.obj;
|
||||
}
|
||||
|
||||
inline Value(ObjectTag arg);
|
||||
inline Value(ObjectOrNullTag arg);
|
||||
|
||||
Value(BooleanTag arg) {
|
||||
mask = BooleanMask;
|
||||
data.boo = arg.boo;
|
||||
}
|
||||
|
||||
Value(JSWhyMagic arg) {
|
||||
mask = MagicMask;
|
||||
#ifdef DEBUG
|
||||
data.why = arg;
|
||||
#endif
|
||||
}
|
||||
|
||||
/* XXX: 'explicit' can be removed when copying is public/implicit */
|
||||
|
||||
explicit Value(const Value &v)
|
||||
: mask(v.mask), data(v.data)
|
||||
{}
|
||||
|
||||
explicit Value(int32 i32) {
|
||||
mask = Int32Mask;
|
||||
data.i32 = i32;
|
||||
}
|
||||
|
||||
explicit Value(double dbl) {
|
||||
mask = DoubleMask;
|
||||
data.dbl = dbl;
|
||||
}
|
||||
|
||||
Value(JSString *str) {
|
||||
mask = StringMask;
|
||||
data.str = str;
|
||||
}
|
||||
|
||||
private:
|
||||
/*
|
||||
* This overload catches values constructed with unsupported T* types
|
||||
* before they are implicitly converted to bool.
|
||||
*/
|
||||
template <class T> explicit Value(T *); /* undefined */
|
||||
|
||||
public:
|
||||
|
||||
explicit Value(bool b) {
|
||||
mask = BooleanMask;
|
||||
data.boo = b;
|
||||
}
|
||||
|
||||
explicit Value(JSWhyMagic why) {
|
||||
mask = MagicMask;
|
||||
#ifdef DEBUG
|
||||
data.why = why;
|
||||
#endif
|
||||
}
|
||||
|
||||
Value(ObjPtr ptr) {
|
||||
mask = ptr.mask;
|
||||
data.obj = ptr.obj;
|
||||
}
|
||||
/* XXX: can be removed when copy is implicit */
|
||||
Value(const CopyableValue &);
|
||||
|
||||
/* Mutators */
|
||||
|
||||
@@ -3294,6 +3354,39 @@ class Value
|
||||
data.str = str;
|
||||
}
|
||||
|
||||
void setFunObj(JSObject &arg) {
|
||||
JS_ASSERT(JS_ObjectIsFunction(NULL, &arg));
|
||||
mask = FunObjMask;
|
||||
data.obj = &arg;
|
||||
}
|
||||
|
||||
void setFunObjOrNull(JSObject *arg) {
|
||||
JS_ASSERT_IF(arg, JS_ObjectIsFunction(NULL, arg));
|
||||
mask = arg ? FunObjMask : NullMask;
|
||||
data.obj = arg;
|
||||
}
|
||||
|
||||
void setFunObjOrUndefined(JSObject *arg) {
|
||||
JS_ASSERT_IF(arg, JS_ObjectIsFunction(NULL, arg));
|
||||
mask = arg ? FunObjMask : UndefinedMask;
|
||||
data.obj = arg;
|
||||
}
|
||||
|
||||
void setNonFunObj(JSObject &arg) {
|
||||
JS_ASSERT(!JS_ObjectIsFunction(NULL, &arg));
|
||||
mask = NonFunObjMask;
|
||||
data.obj = &arg;
|
||||
}
|
||||
|
||||
void setNonFunObjOrNull(JSObject *arg) {
|
||||
JS_ASSERT_IF(arg, !JS_ObjectIsFunction(NULL, arg));
|
||||
mask = arg ? NonFunObjMask : NullMask;
|
||||
data.obj = arg;
|
||||
}
|
||||
|
||||
inline void setObject(JSObject &arg);
|
||||
inline void setObjectOrNull(JSObject *arg);
|
||||
|
||||
void setBoolean(bool b) {
|
||||
mask = BooleanMask;
|
||||
data.boo = b;
|
||||
@@ -3306,28 +3399,6 @@ class Value
|
||||
#endif
|
||||
}
|
||||
|
||||
void setFunObj(JSObject &o) {
|
||||
JS_ASSERT(JS_ObjectIsFunction(NULL, &o));
|
||||
mask = FunObjMask;
|
||||
data.obj = &o;
|
||||
}
|
||||
|
||||
void setNonFunObj(JSObject &o) {
|
||||
JS_ASSERT(!JS_ObjectIsFunction(NULL, &o));
|
||||
mask = NonFunObjMask;
|
||||
data.obj = &o;
|
||||
}
|
||||
|
||||
void setNonFunObjOrNull(JSObject *o) {
|
||||
if (o) {
|
||||
mask = NonFunObjMask;
|
||||
data.obj = o;
|
||||
} else {
|
||||
mask = NullMask;
|
||||
data.obj = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
/* Mutators */
|
||||
|
||||
/* XXX: to be removed when copying is implicit/public */
|
||||
@@ -3496,7 +3567,7 @@ class Value
|
||||
* Private setters/getters allow the caller to read/write arbitrary types
|
||||
* that fit in the 64-bit payload. It is the caller's responsibility, after
|
||||
* storing to a value with setPrivateX to only read with getPrivateX.
|
||||
* Privates values are given a valid type of Int32 and are thus GC-safe.
|
||||
* Privates values are given a valid type of Int32Tag and are thus GC-safe.
|
||||
*/
|
||||
|
||||
void setPrivateVoidPtr(void *p) {
|
||||
@@ -3525,69 +3596,6 @@ class Value
|
||||
}
|
||||
};
|
||||
|
||||
/*
|
||||
* These types are intended to be used like:
|
||||
*
|
||||
* Value v = NullValue();
|
||||
* void f1(Value);
|
||||
* f1(FunObjValue(funobj));
|
||||
*/
|
||||
|
||||
/* TODO: this hackiness will be removed once copying is public/implicit */
|
||||
struct ExplicitlyConstructedValue : Value {};
|
||||
|
||||
JS_ALWAYS_INLINE
|
||||
Value::Value(const ExplicitlyConstructedValue &v)
|
||||
: mask(v.mask), data(v.data)
|
||||
{}
|
||||
|
||||
struct NullValue : ExplicitlyConstructedValue
|
||||
{
|
||||
explicit NullValue() {
|
||||
mask = NullMask;
|
||||
data.obj = NULL;
|
||||
}
|
||||
};
|
||||
|
||||
struct UndefinedValue : ExplicitlyConstructedValue
|
||||
{
|
||||
explicit UndefinedValue() {
|
||||
mask = UndefinedMask;
|
||||
}
|
||||
};
|
||||
|
||||
struct FunObjValue : ExplicitlyConstructedValue
|
||||
{
|
||||
explicit FunObjValue(JSObject &o) {
|
||||
JS_ASSERT(JS_ObjectIsFunction(NULL, &o));
|
||||
mask = FunObjMask;
|
||||
data.obj = &o;
|
||||
}
|
||||
};
|
||||
|
||||
struct NonFunObjValue : ExplicitlyConstructedValue
|
||||
{
|
||||
explicit NonFunObjValue(JSObject &o) {
|
||||
JS_ASSERT(JS_ObjectIsFunction(NULL, &o));
|
||||
mask = NonFunObjMask;
|
||||
data.obj = &o;
|
||||
}
|
||||
};
|
||||
|
||||
struct NonFunObjOrNullValue : ExplicitlyConstructedValue
|
||||
{
|
||||
explicit NonFunObjOrNullValue(JSObject *o) {
|
||||
if (o) {
|
||||
JS_ASSERT(JS_ObjectIsFunction(NULL, o));
|
||||
mask = NonFunObjMask;
|
||||
data.obj = o;
|
||||
} else {
|
||||
mask = NullMask;
|
||||
data.obj = NULL;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
struct AssertLayoutCompatible
|
||||
{
|
||||
JS_STATIC_ASSERT(sizeof(jsval) == 16);
|
||||
@@ -3601,12 +3609,31 @@ struct AssertLayoutCompatible
|
||||
JS_STATIC_ASSERT(sizeof(Value::MaskType) == sizeof(JSValueMaskType));
|
||||
JS_STATIC_ASSERT(sizeof(Value::MaskType) == sizeof(((jsval *)0)->mask));
|
||||
JS_STATIC_ASSERT(offsetof(Value, mask) == offsetof(jsval, mask));
|
||||
JS_STATIC_ASSERT(sizeof(NullValue) == sizeof(Value));
|
||||
JS_STATIC_ASSERT(sizeof(UndefinedValue) == sizeof(Value));
|
||||
JS_STATIC_ASSERT(sizeof(FunObjValue) == sizeof(Value));
|
||||
JS_STATIC_ASSERT(sizeof(NonFunObjValue) == sizeof(Value));
|
||||
};
|
||||
|
||||
/* XXX: this is a temporary hack until copying is implicit. */
|
||||
struct CopyableValue : Value
|
||||
{
|
||||
CopyableValue(NullTag arg) : Value(arg) {}
|
||||
CopyableValue(UndefinedTag arg) : Value(arg) {}
|
||||
CopyableValue(Int32Tag arg) : Value(arg) {}
|
||||
CopyableValue(double arg) : Value(arg) {}
|
||||
CopyableValue(JSString *arg) : Value(arg) {}
|
||||
CopyableValue(FunObjTag arg) : Value(arg) {}
|
||||
CopyableValue(NonFunObjTag arg) : Value(arg) {}
|
||||
CopyableValue(ObjectTag arg) : Value(arg) {}
|
||||
CopyableValue(BooleanTag arg) : Value(arg) {}
|
||||
CopyableValue(JSWhyMagic arg) : Value(arg) {}
|
||||
};
|
||||
|
||||
JS_ALWAYS_INLINE
|
||||
Value::Value(const CopyableValue &v) {
|
||||
mask = v.mask;
|
||||
data = v.data;
|
||||
}
|
||||
|
||||
JS_STATIC_ASSERT(sizeof(CopyableValue) == sizeof(Value));
|
||||
|
||||
/*
|
||||
* As asserted above, js::Value and jsval are layout equivalent. To provide
|
||||
* widespread casting, the following safe casts are provided.
|
||||
|
||||
@@ -241,7 +241,7 @@ js_GetLengthProperty(JSContext *cx, JSObject *obj, jsuint *lengthp)
|
||||
return true;
|
||||
}
|
||||
|
||||
AutoValueRooter tvr(cx, NullValue());
|
||||
AutoValueRooter tvr(cx);
|
||||
if (!obj->getProperty(cx, ATOM_TO_JSID(cx->runtime->atomState.lengthAtom), tvr.addr()))
|
||||
return false;
|
||||
|
||||
@@ -276,7 +276,7 @@ js_IndexToId(JSContext *cx, jsuint index, jsid *idp)
|
||||
str = js_NumberToString(cx, index);
|
||||
if (!str)
|
||||
return JS_FALSE;
|
||||
return js_ValueToStringId(cx, Value(str), idp);
|
||||
return js_ValueToStringId(cx, str, idp);
|
||||
}
|
||||
|
||||
static JSBool
|
||||
@@ -350,7 +350,7 @@ JSObject::resizeDenseArrayElements(JSContext *cx, uint32 oldcap, uint32 newcap,
|
||||
|
||||
if (initializeAllSlots) {
|
||||
for (uint32 i = oldcap; i < newcap; i++)
|
||||
setDenseArrayElement(i, Value(JS_ARRAY_HOLE));
|
||||
setDenseArrayElement(i, JS_ARRAY_HOLE);
|
||||
}
|
||||
|
||||
return true;
|
||||
@@ -405,7 +405,7 @@ JSObject::ensureDenseArrayElements(JSContext *cx, uint32 newcap, bool initialize
|
||||
* Initialize the slots caller didn't actually ask for.
|
||||
*/
|
||||
for (uint32 i = newcap; i < actualCapacity; i++) {
|
||||
setDenseArrayElement(i, Value(JS_ARRAY_HOLE));
|
||||
setDenseArrayElement(i, JS_ARRAY_HOLE);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -415,7 +415,7 @@ JSObject::ensureDenseArrayElements(JSContext *cx, uint32 newcap, bool initialize
|
||||
static bool
|
||||
ReallyBigIndexToId(JSContext* cx, jsdouble index, jsid* idp)
|
||||
{
|
||||
return js_ValueToStringId(cx, Value(index), idp);
|
||||
return js_ValueToStringId(cx, index, idp);
|
||||
}
|
||||
|
||||
static bool
|
||||
@@ -534,7 +534,7 @@ DeleteArrayElement(JSContext *cx, JSObject *obj, jsdouble index)
|
||||
if (!INDEX_TOO_SPARSE(obj, idx) && idx < obj->getDenseArrayCapacity()) {
|
||||
if (!obj->getDenseArrayElement(idx).isMagic(JS_ARRAY_HOLE))
|
||||
obj->decDenseArrayCountBy(1);
|
||||
obj->setDenseArrayElement(idx, Value(JS_ARRAY_HOLE));
|
||||
obj->setDenseArrayElement(idx, JS_ARRAY_HOLE);
|
||||
return JS_TRUE;
|
||||
}
|
||||
}
|
||||
@@ -582,7 +582,7 @@ JSBool
|
||||
js_HasLengthProperty(JSContext *cx, JSObject *obj, jsuint *lengthp)
|
||||
{
|
||||
JSErrorReporter older = JS_SetErrorReporter(cx, NULL);
|
||||
AutoValueRooter tvr(cx, NullValue());
|
||||
AutoValueRooter tvr(cx);
|
||||
jsid id = ATOM_TO_JSID(cx->runtime->atomState.lengthAtom);
|
||||
JSBool ok = obj->getProperty(cx, id, tvr.addr());
|
||||
JS_SetErrorReporter(cx, older);
|
||||
@@ -1050,7 +1050,7 @@ array_deleteProperty(JSContext *cx, JSObject *obj, jsid id, Value *rval)
|
||||
if (js_IdIsIndex(id, &i) && i < obj->getDenseArrayCapacity() &&
|
||||
!obj->getDenseArrayElement(i).isMagic(JS_ARRAY_HOLE)) {
|
||||
obj->decDenseArrayCountBy(1);
|
||||
obj->setDenseArrayElement(i, Value(JS_ARRAY_HOLE));
|
||||
obj->setDenseArrayElement(i, JS_ARRAY_HOLE);
|
||||
}
|
||||
|
||||
rval->setBoolean(true);
|
||||
@@ -1163,7 +1163,7 @@ js_MakeArraySlow(JSContext *cx, JSObject *obj)
|
||||
goto out_bad;
|
||||
|
||||
if (obj->getDenseArrayElement(i).isMagic(JS_ARRAY_HOLE)) {
|
||||
obj->setDenseArrayElement(i, UndefinedValue());
|
||||
obj->setDenseArrayElement(i, UndefinedTag());
|
||||
continue;
|
||||
}
|
||||
|
||||
@@ -1528,7 +1528,7 @@ InitArrayElements(JSContext *cx, JSObject *obj, jsuint start, jsuint count, Valu
|
||||
JS_ASSERT(start == MAXINDEX);
|
||||
AutoValueRooter tvr(cx);
|
||||
AutoIdRooter idr(cx);
|
||||
Value idval(double(MAXINDEX));
|
||||
Value idval(MAXINDEX);
|
||||
do {
|
||||
tvr.addr()->copy(*vector++);
|
||||
if (!js_ValueToStringId(cx, idval, idr.addr()) ||
|
||||
@@ -1601,7 +1601,7 @@ array_reverse(JSContext *cx, uintN argc, Value *vp)
|
||||
JSObject *obj = ComputeThisObjectFromVp(cx, vp);
|
||||
if (!obj || !js_GetLengthProperty(cx, obj, &len))
|
||||
return JS_FALSE;
|
||||
SetObject(vp, *obj);
|
||||
vp->setObject(*obj);
|
||||
|
||||
if (obj->isDenseArray() && !js_PrototypeHasIndexedProperties(cx, obj)) {
|
||||
/* An empty array or an array with no elements is already reversed. */
|
||||
@@ -1899,7 +1899,7 @@ array_sort(JSContext *cx, uintN argc, Value *vp)
|
||||
if (!obj || !js_GetLengthProperty(cx, obj, &len))
|
||||
return false;
|
||||
if (len == 0) {
|
||||
SetObject(vp, *obj);
|
||||
vp->setObject(*obj);
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -2110,7 +2110,7 @@ array_sort(JSContext *cx, uintN argc, Value *vp)
|
||||
if (!JS_CHECK_OPERATION_LIMIT(cx) || !DeleteArrayElement(cx, obj, --len))
|
||||
return JS_FALSE;
|
||||
}
|
||||
SetObject(vp, *obj);
|
||||
vp->setObject(*obj);
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -2273,7 +2273,7 @@ array_shift(JSContext *cx, uintN argc, Value *vp)
|
||||
obj->decDenseArrayCountBy(1);
|
||||
Value *elems = obj->getDenseArrayElements();
|
||||
memmove(elems, elems + 1, length * sizeof(jsval));
|
||||
obj->setDenseArrayElement(length, Value(JS_ARRAY_HOLE));
|
||||
obj->setDenseArrayElement(length, JS_ARRAY_HOLE);
|
||||
obj->setDenseArrayLength(length);
|
||||
return JS_TRUE;
|
||||
}
|
||||
@@ -2323,7 +2323,7 @@ array_unshift(JSContext *cx, uintN argc, Value *vp)
|
||||
Value *elems = obj->getDenseArrayElements();
|
||||
memmove(elems + argc, elems, length * sizeof(jsval));
|
||||
for (uint32 i = 0; i < argc; i++)
|
||||
obj->setDenseArrayElement(i, Value(JS_ARRAY_HOLE));
|
||||
obj->setDenseArrayElement(i, JS_ARRAY_HOLE);
|
||||
} else {
|
||||
last = length;
|
||||
jsdouble upperIndex = last + argc;
|
||||
@@ -2413,7 +2413,7 @@ array_splice(JSContext *cx, uintN argc, Value *vp)
|
||||
argv++;
|
||||
}
|
||||
|
||||
AutoValueRooter tvr(cx, NullValue());
|
||||
AutoValueRooter tvr(cx);
|
||||
|
||||
/* If there are elements to remove, put them into the return value. */
|
||||
if (count > 0) {
|
||||
@@ -2545,7 +2545,7 @@ array_concat(JSContext *cx, uintN argc, Value *vp)
|
||||
length = 0;
|
||||
}
|
||||
|
||||
AutoValueRooter tvr(cx, NullValue());
|
||||
AutoValueRooter tvr(cx);
|
||||
|
||||
/* Loop over [0, argc] to concat args into nobj, expanding all Arrays. */
|
||||
for (uintN i = 0; i <= argc; i++) {
|
||||
@@ -2874,9 +2874,9 @@ array_extra(JSContext *cx, ArrayExtraMode mode, uintN argc, Value *vp)
|
||||
Value *invokevp = args.getvp();
|
||||
|
||||
Value calleev, thisv, objv;
|
||||
SetObject(&calleev, callable);
|
||||
SetObject(&thisv, thisp);
|
||||
SetObject(&objv, obj);
|
||||
calleev.setObject(*callable);
|
||||
thisv.setObjectOrNull(thisp);
|
||||
objv.setObject(*obj);
|
||||
AutoValueRooter tvr(cx);
|
||||
for (jsint i = start; i != end; i += step) {
|
||||
JSBool hole;
|
||||
@@ -3098,7 +3098,7 @@ js_NewEmptyArray(JSContext* cx, JSObject* proto)
|
||||
/* Initialize all fields of JSObject. */
|
||||
obj->map = const_cast<JSObjectMap *>(&SharedArrayMap);
|
||||
|
||||
obj->init(&js_ArrayClass, NonFunObjPtr(*proto), proto->getParent(), NullValue());
|
||||
obj->init(&js_ArrayClass, NonFunObjTag(*proto), proto->getParent(), NullTag());
|
||||
obj->setDenseArrayLength(0);
|
||||
obj->setDenseArrayCount(0);
|
||||
return obj;
|
||||
|
||||
@@ -95,7 +95,7 @@ JS_STATIC_ASSERT((1 + 2) * sizeof(JSAtom *) ==
|
||||
const char *
|
||||
js_AtomToPrintableString(JSContext *cx, JSAtom *atom)
|
||||
{
|
||||
return js_ValueToPrintableString(cx, Value(ATOM_TO_STRING(atom)));
|
||||
return js_ValueToPrintableString(cx, ATOM_TO_STRING(atom));
|
||||
}
|
||||
|
||||
#define JS_PROTO(name,code,init) const char js_##name##_str[] = #name;
|
||||
@@ -1299,7 +1299,7 @@ js_InternNonIntElementIdSlow(JSContext *cx, JSObject *obj, const Value &idval,
|
||||
if (obj->isXML()) {
|
||||
JSObject &idobj = idval.asObject();
|
||||
*idp = OBJECT_TO_JSID(&idobj);
|
||||
SetObject(vp, idobj);
|
||||
vp->setObject(idobj);
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -1351,16 +1351,13 @@ ValueToId(JSContext *cx, const Value *vp, jsid *idp)
|
||||
Value
|
||||
IdToValue(jsid id)
|
||||
{
|
||||
ExplicitlyConstructedValue v;
|
||||
if (JSID_IS_INT(id))
|
||||
v.setInt32(JSID_TO_INT(id));
|
||||
return CopyableValue(Int32Tag(JSID_TO_INT(id)));
|
||||
else if (JSID_IS_ATOM(id))
|
||||
v.setString(ATOM_TO_STRING(JSID_TO_ATOM(id)));
|
||||
return CopyableValue(ATOM_TO_STRING(JSID_TO_ATOM(id)));
|
||||
else if (JSID_IS_NULL(id))
|
||||
v.setNull();
|
||||
else
|
||||
SetObject(&v, *JSID_TO_OBJECT(id));
|
||||
return v;
|
||||
return CopyableValue(NullTag());
|
||||
return CopyableValue(ObjectTag(*JSID_TO_OBJECT(id)));
|
||||
}
|
||||
|
||||
} /* namespace js */
|
||||
|
||||
@@ -98,7 +98,7 @@ js_Int32ToId(JSContext* cx, int32 index, jsid* id)
|
||||
JSString* str = js_NumberToString(cx, index);
|
||||
if (!str)
|
||||
return false;
|
||||
return js_ValueToStringId(cx, js::Value(str), id);
|
||||
return js_ValueToStringId(cx, str, id);
|
||||
}
|
||||
|
||||
inline bool
|
||||
|
||||
@@ -152,7 +152,7 @@ js_InitBooleanClass(JSContext *cx, JSObject *obj)
|
||||
NULL, boolean_methods, NULL, NULL);
|
||||
if (!proto)
|
||||
return NULL;
|
||||
proto->setPrimitiveThis(Value(false));
|
||||
proto->setPrimitiveThis(BooleanTag(false));
|
||||
return proto;
|
||||
}
|
||||
|
||||
|
||||
@@ -2242,7 +2242,7 @@ class AutoValueRooter : private AutoGCRooter
|
||||
public:
|
||||
explicit AutoValueRooter(JSContext *cx
|
||||
JS_GUARD_OBJECT_NOTIFIER_PARAM)
|
||||
: AutoGCRooter(cx, JSVAL), val(js::NullValue())
|
||||
: AutoGCRooter(cx, JSVAL), val(js::NullTag())
|
||||
{
|
||||
JS_GUARD_OBJECT_NOTIFIER_INIT;
|
||||
}
|
||||
@@ -2990,7 +2990,7 @@ class AutoValueVector : private AutoGCRooter
|
||||
size_t length() const { return vector.length(); }
|
||||
|
||||
bool append(const Value &v) { return vector.append(v); }
|
||||
bool append(JSString *str) { return append(Value(str)); }
|
||||
bool append(JSString *str) { return append(str); }
|
||||
|
||||
void popBack() { vector.popBack(); }
|
||||
|
||||
|
||||
@@ -679,7 +679,7 @@ js_watch_set(JSContext *cx, JSObject *obj, jsid id, Value *vp)
|
||||
/* Initialize slots/frame. */
|
||||
Value *vp = frame.getvp();
|
||||
PodZero(vp, vplen);
|
||||
SetObject(&vp[0], closure);
|
||||
vp[0].setObject(*closure);
|
||||
JSStackFrame *fp = frame.getFrame();
|
||||
PodZero(fp->slots(), nfixed);
|
||||
PodZero(fp);
|
||||
@@ -707,7 +707,7 @@ js_watch_set(JSContext *cx, JSObject *obj, jsid id, Value *vp)
|
||||
JSBool ok = !wp->setter ||
|
||||
(sprop->hasSetterValue()
|
||||
? InternalCall(cx, obj,
|
||||
ToValue(CastAsObject(wp->setter)),
|
||||
ObjectTag(*CastAsObject(wp->setter)),
|
||||
1, vp, vp)
|
||||
: wp->setter(cx, obj, userid, vp));
|
||||
|
||||
|
||||
@@ -53,6 +53,8 @@
|
||||
#include "jslibmath.h"
|
||||
#include "jscntxt.h"
|
||||
|
||||
#include "jsobjinlines.h"
|
||||
|
||||
#ifdef IS_LITTLE_ENDIAN
|
||||
#define IEEE_8087
|
||||
#else
|
||||
|
||||
@@ -285,7 +285,8 @@ InitExnPrivate(JSContext *cx, JSObject *exnObject, JSString *message,
|
||||
valueCount = 0;
|
||||
for (fp = js_GetTopStackFrame(cx); fp; fp = fp->down) {
|
||||
if (fp->fun && fp->argv) {
|
||||
NullValue v;
|
||||
Value v;
|
||||
v.setNull();
|
||||
if (checkAccess &&
|
||||
!checkAccess(cx, fp->callee(), callerid, JSACC_READ, &v)) {
|
||||
break;
|
||||
|
||||
@@ -176,8 +176,8 @@ NewArguments(JSContext *cx, JSObject *parent, uint32 argc, JSObject *callee)
|
||||
return NULL;
|
||||
|
||||
/* Init immediately to avoid GC seeing a half-init'ed object. */
|
||||
argsobj->init(&js_ArgumentsClass, NonFunObjPtr(*proto), parent, NullValue());
|
||||
argsobj->setArgsCallee(ToValue(callee));
|
||||
argsobj->init(&js_ArgumentsClass, NonFunObjTag(*proto), parent, NullTag());
|
||||
argsobj->setArgsCallee(ObjectOrNullTag(callee));
|
||||
argsobj->setArgsLength(argc);
|
||||
|
||||
argsobj->map = cx->runtime->emptyArgumentsScope;
|
||||
@@ -841,7 +841,7 @@ js_CreateCallObjectOnTrace(JSContext *cx, JSFunction *fun, JSObject *callee, JSO
|
||||
JSObject *callobj = NewCallObject(cx, fun, scopeChain);
|
||||
if (!callobj)
|
||||
return NULL;
|
||||
callobj->setSlot(JSSLOT_CALLEE, NonFunObjValue(*callee));
|
||||
callobj->setSlot(JSSLOT_CALLEE, NonFunObjTag(*callee));
|
||||
return callobj;
|
||||
}
|
||||
|
||||
@@ -877,7 +877,7 @@ js_PutCallObject(JSContext *cx, JSStackFrame *fp)
|
||||
/* Get the arguments object to snapshot fp's actual argument values. */
|
||||
if (fp->argsobj) {
|
||||
if (!(fp->flags & JSFRAME_OVERRIDE_ARGS))
|
||||
callobj->setSlot(JSSLOT_CALL_ARGUMENTS, NonFunObjValue(*fp->argsobj));
|
||||
callobj->setSlot(JSSLOT_CALL_ARGUMENTS, NonFunObjTag(*fp->argsobj));
|
||||
js_PutArgsObject(cx, fp);
|
||||
}
|
||||
|
||||
@@ -1723,7 +1723,7 @@ fun_hasInstance(JSContext *cx, JSObject *obj, const Value *v, JSBool *bp)
|
||||
* Throw a runtime error if instanceof is called on a function that
|
||||
* has a non-object as its .prototype value.
|
||||
*/
|
||||
js_ReportValueError(cx, JSMSG_BAD_PROTOTYPE, -1, ToValue(obj), NULL);
|
||||
js_ReportValueError(cx, JSMSG_BAD_PROTOTYPE, -1, ObjectTag(*obj), NULL);
|
||||
return JS_FALSE;
|
||||
}
|
||||
|
||||
@@ -2527,7 +2527,7 @@ js_DefineFunction(JSContext *cx, JSObject *obj, JSAtom *atom, Native native,
|
||||
fun = js_NewFunction(cx, NULL, native, nargs, attrs, obj, atom);
|
||||
if (!fun)
|
||||
return NULL;
|
||||
if (!obj->defineProperty(cx, ATOM_TO_JSID(atom), FunObjValue(*FUN_OBJECT(fun)),
|
||||
if (!obj->defineProperty(cx, ATOM_TO_JSID(atom), fun->funObjVal(),
|
||||
gsop, gsop, attrs & ~JSFUN_FLAGS_MASK)) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
@@ -199,6 +199,10 @@ struct JSFunction : public JSObject
|
||||
bool mightEscape() const {
|
||||
return FUN_INTERPRETED(this) && (FUN_FLAT_CLOSURE(this) || u.i.nupvars == 0);
|
||||
}
|
||||
|
||||
js::FunObjTag funObjVal() {
|
||||
return js::FunObjTag(*this);
|
||||
}
|
||||
};
|
||||
|
||||
/*
|
||||
@@ -309,8 +313,8 @@ extern void
|
||||
js_FinalizeFunction(JSContext *cx, JSFunction *fun);
|
||||
|
||||
extern JSObject *
|
||||
js_CloneFunctionObject(JSContext *cx, JSFunction *fun, const js::Value &parent,
|
||||
const js::Value &proto);
|
||||
js_CloneFunctionObject(JSContext *cx, JSFunction *fun, JSObject *parent,
|
||||
JSObject *proto);
|
||||
|
||||
inline JSObject *
|
||||
CloneFunctionObject(JSContext *cx, JSFunction *fun, JSObject *parent)
|
||||
@@ -319,8 +323,7 @@ CloneFunctionObject(JSContext *cx, JSFunction *fun, JSObject *parent)
|
||||
JSObject *proto;
|
||||
if (!js_GetClassPrototype(cx, parent, JSProto_Function, &proto))
|
||||
return NULL;
|
||||
return js_CloneFunctionObject(cx, fun, js::NonFunObjValue(*parent),
|
||||
js::FunObjValue(*proto));
|
||||
return js_CloneFunctionObject(cx, fun, parent, proto);
|
||||
}
|
||||
|
||||
extern JS_REQUIRES_STACK JSObject *
|
||||
|
||||
@@ -2343,7 +2343,7 @@ ProcessSetSlotRequest(JSContext *cx, JSSetSlotRequest *ssr)
|
||||
|
||||
pobj = ssr->pobj;
|
||||
if (slot == JSSLOT_PROTO) {
|
||||
obj->setProto(ToObjPtr(pobj));
|
||||
obj->setProto(ObjectOrNullTag(pobj));
|
||||
} else {
|
||||
JS_ASSERT(slot == JSSLOT_PARENT);
|
||||
obj->setParent(pobj);
|
||||
|
||||
@@ -273,7 +273,7 @@ ComputeGlobalThis(JSContext *cx, Value *argv)
|
||||
thisp = cx->globalObject;
|
||||
else
|
||||
thisp = argv[-2].asObject().getGlobal();
|
||||
return CallThisObjectHook(cx, NonFunObjPtr(*thisp), argv);
|
||||
return CallThisObjectHook(cx, NonFunObjTag(*thisp), argv);
|
||||
}
|
||||
|
||||
static bool
|
||||
@@ -482,7 +482,7 @@ Invoke(JSContext *cx, const InvokeArgsGuard &args, uintN flags)
|
||||
|
||||
if (JSFUN_BOUND_METHOD_TEST(fun->flags)) {
|
||||
/* Handle bound method special case. */
|
||||
SetObject(&vp[1], parent);
|
||||
vp[1].setObjectOrNull(parent);
|
||||
} else if (vp[1].isPrimitive()) {
|
||||
JS_ASSERT(!(flags & JSINVOKE_CONSTRUCT));
|
||||
if (PrimitiveThisTest(fun, vp[1]))
|
||||
@@ -667,7 +667,7 @@ InternalInvoke(JSContext *cx, JSObject *obj, const Value &fval, uintN flags,
|
||||
return JS_FALSE;
|
||||
|
||||
args.getvp()[0].copy(fval);
|
||||
SetObject(&args.getvp()[1], obj);
|
||||
args.getvp()[1].setObjectOrNull(obj);
|
||||
memcpy(args.getvp() + 2, argv, argc * sizeof(*argv));
|
||||
|
||||
if (!Invoke(cx, args, flags))
|
||||
@@ -792,7 +792,7 @@ Execute(JSContext *cx, JSObject *chain, JSScript *script,
|
||||
JSObject *thisp = chain->thisObject(cx);
|
||||
if (!thisp)
|
||||
return false;
|
||||
SetObject(&fp->thisv, *thisp);
|
||||
fp->thisv.setObject(*thisp);
|
||||
fp->flags = flags | JSFRAME_COMPUTED_THIS;
|
||||
fp->argc = 0;
|
||||
fp->argv = NULL;
|
||||
@@ -1105,7 +1105,7 @@ InvokeConstructor(JSContext *cx, const InvokeArgsGuard &args, JSBool clampReturn
|
||||
return JS_FALSE;
|
||||
|
||||
/* Now we have an object with a constructor method; call it. */
|
||||
SetObject(&vp[1], *obj);
|
||||
vp[1].setObject(*obj);
|
||||
if (!Invoke(cx, args, JSINVOKE_CONSTRUCT))
|
||||
return JS_FALSE;
|
||||
|
||||
@@ -1118,7 +1118,7 @@ InvokeConstructor(JSContext *cx, const InvokeArgsGuard &args, JSBool clampReturn
|
||||
js_ValueToPrintableString(cx, *vp));
|
||||
return JS_FALSE;
|
||||
}
|
||||
SetObject(vp, *obj);
|
||||
vp->setObject(*obj);
|
||||
}
|
||||
|
||||
JS_RUNTIME_METER(cx->runtime, constructs);
|
||||
@@ -1682,10 +1682,10 @@ namespace reprmeter {
|
||||
#define PUSH_BOOLEAN(b) regs.sp++->setBoolean(b)
|
||||
#define PUSH_INT32(i) regs.sp++->setInt32(i)
|
||||
#define PUSH_STRING(s) regs.sp++->setString(s)
|
||||
#define PUSH_NONFUNOBJ(o) regs.sp++->setNonFunObj(o)
|
||||
#define PUSH_FUNOBJ(o) regs.sp++->setFunObj(o)
|
||||
#define PUSH_OBJECT(o) SetObject(regs.sp++, o)
|
||||
#define PUSH_OBJECT_OR_NULL(o) SetObject(regs.sp++, o)
|
||||
#define PUSH_NONFUNOBJ(obj) regs.sp++->setNonFunObj(obj)
|
||||
#define PUSH_FUNOBJ(obj) regs.sp++->setFunObj(obj)
|
||||
#define PUSH_OBJECT(obj) regs.sp++->setObject(obj)
|
||||
#define PUSH_OBJECT_OR_NULL(obj) regs.sp++->setObject(obj)
|
||||
#define PUSH_HOLE() regs.sp++->setMagic(JS_ARRAY_HOLE)
|
||||
#define POP_COPY_TO(v) v.copy(*--regs.sp)
|
||||
|
||||
@@ -1859,7 +1859,7 @@ AssertValidPropertyCacheHit(JSContext *cx, JSScript *script, JSFrameRegs& regs,
|
||||
} else if (entry->vword.isSprop()) {
|
||||
JS_ASSERT(entry->vword.toSprop() == sprop);
|
||||
JS_ASSERT_IF(sprop->isMethod(),
|
||||
sprop->methodValue().isSame(pobj->lockedGetSlot(sprop->slot)));
|
||||
&sprop->methodFunObj() == &pobj->lockedGetSlot(sprop->slot).asFunObj());
|
||||
} else {
|
||||
Value v;
|
||||
JS_ASSERT(entry->vword.isFunObj());
|
||||
@@ -1872,7 +1872,7 @@ AssertValidPropertyCacheHit(JSContext *cx, JSScript *script, JSFrameRegs& regs,
|
||||
|
||||
if (sprop->isMethod()) {
|
||||
JS_ASSERT(js_CodeSpec[*regs.pc].format & JOF_CALLOP);
|
||||
JS_ASSERT(sprop->methodValue().isSame(v));
|
||||
JS_ASSERT(&sprop->methodFunObj() == &v.asFunObj());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -476,7 +476,7 @@ JSStackFrame::getThisObject(JSContext *cx)
|
||||
if (flags & JSFRAME_COMPUTED_THIS)
|
||||
return thisv.asObjPtr(); /* JSVAL_COMPUTED_THIS invariant */
|
||||
if (!js::ComputeThisFromArgv(cx, argv))
|
||||
return js::NullObjPtr();
|
||||
return js::NullTag();
|
||||
thisv.copy(argv[-1]);
|
||||
flags |= JSFRAME_COMPUTED_THIS;
|
||||
return thisv.asObjPtr();
|
||||
|
||||
@@ -103,9 +103,9 @@ ExtendedClass js_IteratorClass = {
|
||||
void
|
||||
NativeIterator::mark(JSTracer *trc)
|
||||
{
|
||||
for (jsval *vp = props_array; vp < props_end; ++vp) {
|
||||
for (Value *vp = props_array; vp < props_end; ++vp) {
|
||||
JS_SET_TRACING_INDEX(trc, "props", (vp - props_array));
|
||||
js_CallValueTracerIfGCThing(trc, *vp);
|
||||
CallGCMarkerIfGCThing(trc, *vp);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -164,7 +164,7 @@ obj_getProto(JSContext *cx, JSObject *obj, jsid id, Value *vp)
|
||||
pobj = thisObject(cx, pobj);
|
||||
if (!pobj)
|
||||
return JS_FALSE;
|
||||
SetObject(vp, *pobj);
|
||||
vp->setObject(*pobj);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -239,7 +239,7 @@ js_SetProtoOrParent(JSContext *cx, JSObject *obj, uint32 slot, JSObject *pobj,
|
||||
|
||||
if (!pobj || !checkForCycles) {
|
||||
if (slot == JSSLOT_PROTO)
|
||||
obj->setProto(ToObjPtr(pobj));
|
||||
obj->setProto(ObjectOrNullTag(pobj));
|
||||
else
|
||||
obj->setParent(pobj);
|
||||
} else {
|
||||
@@ -332,14 +332,14 @@ MarkSharpObjects(JSContext *cx, JSObject *obj, JSIdArray **idap)
|
||||
JSScopeProperty *sprop = (JSScopeProperty *) prop;
|
||||
val.setUndefined();
|
||||
if (attrs & JSPROP_GETTER)
|
||||
val.copy(sprop->getterValue());
|
||||
val.setFunObjOrUndefined(sprop->getterObject());
|
||||
if (attrs & JSPROP_SETTER) {
|
||||
if (!val.isUndefined()) {
|
||||
/* Mark the getter, then set val to setter. */
|
||||
ok = (MarkSharpObjects(cx, &val.asFunObj(), NULL)
|
||||
!= NULL);
|
||||
}
|
||||
val.copy(sprop->setterValue());
|
||||
val.setFunObjOrUndefined(sprop->setterObject());
|
||||
}
|
||||
} else {
|
||||
ok = obj->getProperty(cx, id, &val);
|
||||
@@ -575,7 +575,7 @@ obj_toSource(JSContext *cx, uintN argc, Value *vp)
|
||||
|
||||
JS_CHECK_RECURSION(cx, return JS_FALSE);
|
||||
|
||||
Value localroot[4] = {NullValue(), NullValue(), NullValue(), NullValue()};
|
||||
CopyableValue localroot[4] = { NullTag(), NullTag(), NullTag(), NullTag() };
|
||||
AutoArrayRooter tvr(cx, JS_ARRAY_LENGTH(localroot), localroot);
|
||||
|
||||
/* If outermost, we need parentheses to be an expression, not a block. */
|
||||
@@ -674,12 +674,12 @@ obj_toSource(JSContext *cx, uintN argc, Value *vp)
|
||||
if (obj2->isNative() && (attrs & (JSPROP_GETTER | JSPROP_SETTER))) {
|
||||
JSScopeProperty *sprop = (JSScopeProperty *) prop;
|
||||
if (attrs & JSPROP_GETTER) {
|
||||
val[valcnt].copy(sprop->getterValue());
|
||||
val[valcnt].setFunObjOrUndefined(sprop->getterObject());
|
||||
gsop[valcnt] = ATOM_TO_STRING(cx->runtime->atomState.getAtom);
|
||||
valcnt++;
|
||||
}
|
||||
if (attrs & JSPROP_SETTER) {
|
||||
val[valcnt].copy(sprop->setterValue());
|
||||
val[valcnt].setFunObjOrUndefined(sprop->setterObject());
|
||||
gsop[valcnt] = ATOM_TO_STRING(cx->runtime->atomState.setAtom);
|
||||
valcnt++;
|
||||
}
|
||||
@@ -1248,7 +1248,7 @@ obj_eval(JSContext *cx, uintN argc, Value *vp)
|
||||
|
||||
scopeobj = withGuard.obj;
|
||||
JS_ASSERT(argc >= 2);
|
||||
SetObject(&argv[1], *withGuard.obj);
|
||||
argv[1].setObject(*withGuard.obj);
|
||||
}
|
||||
|
||||
/* We're pretending that we're in global code. */
|
||||
@@ -1434,7 +1434,7 @@ obj_watch_handler(JSContext *cx, JSObject *obj, jsid id, const Value *old,
|
||||
argv[0].copy(IdToValue(id));
|
||||
argv[1].copy(*old);
|
||||
argv[2].copy(*nvp);
|
||||
ok = InternalCall(cx, obj, ToValue(callable), 3, argv, nvp);
|
||||
ok = InternalCall(cx, obj, ObjectOrNullTag(callable), 3, argv, nvp);
|
||||
js_StopResolving(cx, &key, JSRESFLAG_WATCH, entry, generation);
|
||||
return ok;
|
||||
}
|
||||
@@ -1729,7 +1729,7 @@ obj_lookupGetter(JSContext *cx, uintN argc, Value *vp)
|
||||
if (pobj->isNative()) {
|
||||
JSScopeProperty *sprop = (JSScopeProperty *) prop;
|
||||
if (sprop->hasGetterValue())
|
||||
vp->copy(sprop->getterValue());
|
||||
vp->setFunObjOrUndefined(sprop->getterObject());
|
||||
}
|
||||
pobj->dropProperty(cx, prop);
|
||||
}
|
||||
@@ -1752,7 +1752,7 @@ obj_lookupSetter(JSContext *cx, uintN argc, Value *vp)
|
||||
if (pobj->isNative()) {
|
||||
JSScopeProperty *sprop = (JSScopeProperty *) prop;
|
||||
if (sprop->hasSetterValue())
|
||||
vp->copy(sprop->setterValue());
|
||||
vp->setFunObjOrUndefined(sprop->setterObject());
|
||||
}
|
||||
pobj->dropProperty(cx, prop);
|
||||
}
|
||||
@@ -1802,15 +1802,15 @@ js_GetOwnPropertyDescriptor(JSContext *cx, JSObject *obj, jsid id, Value *vp)
|
||||
return false;
|
||||
}
|
||||
|
||||
Value roots[] = { UndefinedValue(), UndefinedValue() };
|
||||
CopyableValue roots[2] = { UndefinedTag(), UndefinedTag() };
|
||||
AutoArrayRooter tvr(cx, JS_ARRAY_LENGTH(roots), roots);
|
||||
if (attrs & (JSPROP_GETTER | JSPROP_SETTER)) {
|
||||
if (obj->isNative()) {
|
||||
JSScopeProperty *sprop = reinterpret_cast<JSScopeProperty *>(prop);
|
||||
if (attrs & JSPROP_GETTER)
|
||||
roots[0].copy(sprop->getterValue());
|
||||
roots[0].setFunObjOrUndefined(sprop->getterObject());
|
||||
if (attrs & JSPROP_SETTER)
|
||||
roots[1].copy(sprop->setterValue());
|
||||
roots[1].setFunObjOrUndefined(sprop->setterObject());
|
||||
}
|
||||
|
||||
pobj->dropProperty(cx, prop);
|
||||
@@ -1826,7 +1826,7 @@ js_GetOwnPropertyDescriptor(JSContext *cx, JSObject *obj, jsid id, Value *vp)
|
||||
JSObject *desc = NewObject(cx, &js_ObjectClass, NULL, NULL);
|
||||
if (!desc)
|
||||
return false;
|
||||
SetObject(vp, *desc); /* Root and return. */
|
||||
vp->setObject(*desc); /* Root and return. */
|
||||
|
||||
const JSAtomState &atomState = cx->runtime->atomState;
|
||||
if (attrs & (JSPROP_GETTER | JSPROP_SETTER)) {
|
||||
@@ -1934,9 +1934,9 @@ HasProperty(JSContext* cx, JSObject* obj, jsid id, Value* vp, JSBool* answerp)
|
||||
|
||||
PropertyDescriptor::PropertyDescriptor()
|
||||
: id(INT_TO_JSID(0)),
|
||||
value(UndefinedValue()),
|
||||
get(UndefinedValue()),
|
||||
set(UndefinedValue()),
|
||||
value(UndefinedTag()),
|
||||
get(UndefinedTag()),
|
||||
set(UndefinedTag()),
|
||||
attrs(0),
|
||||
hasGet(false),
|
||||
hasSet(false),
|
||||
@@ -2142,14 +2142,12 @@ DefinePropertyOnObject(JSContext *cx, JSObject *obj, const PropertyDescriptor &d
|
||||
break;
|
||||
|
||||
if (desc.hasGet &&
|
||||
!SameValue(cx, desc.getterValue(),
|
||||
sprop->hasGetterValue() ? sprop->getterValue() : UndefinedValue())) {
|
||||
!SameValue(cx, desc.getterValue(), sprop->getterOrUndefined())) {
|
||||
break;
|
||||
}
|
||||
|
||||
if (desc.hasSet &&
|
||||
!SameValue(cx, desc.setterValue(),
|
||||
sprop->hasSetterValue() ? sprop->setterValue() : UndefinedValue())) {
|
||||
!SameValue(cx, desc.setterValue(), sprop->setterOrUndefined())) {
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
@@ -2261,11 +2259,9 @@ DefinePropertyOnObject(JSContext *cx, JSObject *obj, const PropertyDescriptor &d
|
||||
JS_ASSERT(desc.isAccessorDescriptor() && sprop->isAccessorDescriptor());
|
||||
if (!sprop->configurable()) {
|
||||
if ((desc.hasSet &&
|
||||
!SameValue(cx, desc.setterValue(),
|
||||
sprop->hasSetterValue() ? sprop->setterValue() : UndefinedValue())) ||
|
||||
!SameValue(cx, desc.setterValue(), sprop->setterOrUndefined())) ||
|
||||
(desc.hasGet &&
|
||||
!SameValue(cx, desc.getterValue(),
|
||||
sprop->hasGetterValue() ? sprop->getterValue() : UndefinedValue()))) {
|
||||
!SameValue(cx, desc.getterValue(), sprop->getterOrUndefined()))) {
|
||||
return Reject(cx, obj2, current, JSMSG_CANT_REDEFINE_UNCONFIGURABLE_PROP,
|
||||
throwError, desc.id, rval);
|
||||
}
|
||||
@@ -3028,7 +3024,7 @@ js_CloneBlockObject(JSContext *cx, JSObject *proto, JSStackFrame *fp)
|
||||
/* The caller sets parent on its own. */
|
||||
Value priv;
|
||||
priv.setPrivateVoidPtr(js_FloatingFrameIfGenerator(cx, fp));
|
||||
clone->init(&js_BlockClass, NonFunObjPtr(*proto), NULL, priv);
|
||||
clone->init(&js_BlockClass, NonFunObjTag(*proto), NULL, priv);
|
||||
clone->fslots[JSSLOT_BLOCK_DEPTH].copy(proto->fslots[JSSLOT_BLOCK_DEPTH]);
|
||||
|
||||
JS_ASSERT(cx->runtime->emptyBlockScope->freeslot == JSSLOT_BLOCK_DEPTH + 1);
|
||||
@@ -3376,7 +3372,7 @@ js_InitClass(JSContext *cx, JSObject *obj, JSObject *parent_proto,
|
||||
key != JSProto_Null) {
|
||||
named = JS_FALSE;
|
||||
} else {
|
||||
named = obj->defineProperty(cx, ATOM_TO_JSID(atom), ToValue(proto),
|
||||
named = obj->defineProperty(cx, ATOM_TO_JSID(atom), ObjectOrNullTag(proto),
|
||||
PropertyStub, PropertyStub,
|
||||
(clasp->flags & JSCLASS_IS_ANONYMOUS)
|
||||
? JSPROP_READONLY | JSPROP_PERMANENT
|
||||
@@ -3410,7 +3406,7 @@ js_InitClass(JSContext *cx, JSObject *obj, JSObject *parent_proto,
|
||||
ctor = FUN_OBJECT(fun);
|
||||
if (clasp->flags & JSCLASS_CONSTRUCT_PROTOTYPE) {
|
||||
Value rval;
|
||||
if (!InternalConstruct(cx, proto, ToValue(ctor), 0, NULL, &rval))
|
||||
if (!InternalConstruct(cx, proto, ObjectOrNullTag(ctor), 0, NULL, &rval))
|
||||
goto bad;
|
||||
if (rval.isObject() && &rval.asObject() != proto)
|
||||
proto = &rval.asObject();
|
||||
@@ -3424,7 +3420,7 @@ js_InitClass(JSContext *cx, JSObject *obj, JSObject *parent_proto,
|
||||
|
||||
/* Bootstrap Function.prototype (see also JS_InitStandardClasses). */
|
||||
if (ctor->getClass() == clasp)
|
||||
ctor->setProto(ToObjPtr(proto));
|
||||
ctor->setProto(ObjectOrNullTag(proto));
|
||||
}
|
||||
|
||||
/* Add properties and methods to the prototype and the constructor. */
|
||||
@@ -3663,7 +3659,7 @@ js_SetClassObject(JSContext *cx, JSObject *obj, JSProtoKey key, JSObject *cobj)
|
||||
if (!(obj->getClass()->flags & JSCLASS_IS_GLOBAL))
|
||||
return JS_TRUE;
|
||||
|
||||
return js_SetReservedSlot(cx, obj, key, ToValue(cobj));
|
||||
return js_SetReservedSlot(cx, obj, key, ObjectOrNullTag(cobj));
|
||||
}
|
||||
|
||||
JSBool
|
||||
@@ -3709,7 +3705,7 @@ js_FindClassObject(JSContext *cx, JSObject *start, JSProtoKey protoKey,
|
||||
if (!js_GetClassObject(cx, obj, protoKey, &cobj))
|
||||
return JS_FALSE;
|
||||
if (cobj) {
|
||||
SetObject(vp, *cobj);
|
||||
vp->setObject(*cobj);
|
||||
return JS_TRUE;
|
||||
}
|
||||
id = ATOM_TO_JSID(cx->runtime->atomState.classAtoms[protoKey]);
|
||||
@@ -4588,7 +4584,7 @@ js_NativeGet(JSContext *cx, JSObject *obj, JSObject *pobj,
|
||||
return true;
|
||||
|
||||
if (JS_UNLIKELY(sprop->isMethod()) && (getHow & JSGET_NO_METHOD_BARRIER)) {
|
||||
JS_ASSERT(sprop->methodValue().isSame(*vp));
|
||||
JS_ASSERT(&sprop->methodFunObj() == &vp->asFunObj());
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -5204,7 +5200,7 @@ JSBool
|
||||
js_DefaultValue(JSContext *cx, JSObject *obj, JSType hint, Value *vp)
|
||||
{
|
||||
Value v;
|
||||
SetObject(&v, obj);
|
||||
v.setObject(*obj);
|
||||
if (hint == JSTYPE_STRING) {
|
||||
JS_ASSERT(hint != JSTYPE_OBJECT && hint != JSTYPE_FUNCTION);
|
||||
|
||||
@@ -5281,7 +5277,7 @@ js_DefaultValue(JSContext *cx, JSObject *obj, JSType hint, Value *vp)
|
||||
} else {
|
||||
str = NULL;
|
||||
}
|
||||
SetObject(vp, *obj);
|
||||
vp->setObject(*obj);
|
||||
js_ReportValueError2(cx, JSMSG_CANT_CONVERT_TO,
|
||||
JSDVG_SEARCH_STACK, *vp, str,
|
||||
(hint == JSTYPE_VOID)
|
||||
@@ -5556,7 +5552,7 @@ js_HasInstance(JSContext *cx, JSObject *obj, const Value *vp, JSBool *bp)
|
||||
}
|
||||
#endif
|
||||
js_ReportValueError(cx, JSMSG_BAD_INSTANCEOF_RHS,
|
||||
JSDVG_SEARCH_STACK, ToValue(*obj), NULL);
|
||||
JSDVG_SEARCH_STACK, ObjectTag(*obj), NULL);
|
||||
return JS_FALSE;
|
||||
}
|
||||
|
||||
@@ -5682,7 +5678,7 @@ js_SetClassPrototype(JSContext *cx, JSObject *ctor, JSObject *proto, uintN attrs
|
||||
* DontDelete.
|
||||
*/
|
||||
if (!ctor->defineProperty(cx, ATOM_TO_JSID(cx->runtime->atomState.classPrototypeAtom),
|
||||
ToValue(proto), PropertyStub, PropertyStub, attrs)) {
|
||||
ObjectOrNullTag(proto), PropertyStub, PropertyStub, attrs)) {
|
||||
return JS_FALSE;
|
||||
}
|
||||
|
||||
@@ -5691,7 +5687,7 @@ js_SetClassPrototype(JSContext *cx, JSObject *ctor, JSObject *proto, uintN attrs
|
||||
* for a user-defined function f, is DontEnum.
|
||||
*/
|
||||
return proto->defineProperty(cx, ATOM_TO_JSID(cx->runtime->atomState.constructorAtom),
|
||||
ToValue(ctor), CheckCtorGetAccess, CheckCtorSetAccess, 0);
|
||||
ObjectOrNullTag(ctor), CheckCtorGetAccess, CheckCtorSetAccess, 0);
|
||||
}
|
||||
|
||||
JSBool
|
||||
@@ -6375,11 +6371,11 @@ DumpObject(JSObject *obj)
|
||||
}
|
||||
|
||||
fprintf(stderr, "proto ");
|
||||
dumpValue(ToValue(obj->getProto()));
|
||||
dumpValue(obj->getProtoValue());
|
||||
fputc('\n', stderr);
|
||||
|
||||
fprintf(stderr, "parent ");
|
||||
dumpValue(ToValue(obj->getParent()));
|
||||
dumpValue(obj->getParentValue());
|
||||
fputc('\n', stderr);
|
||||
|
||||
i = JSSLOT_PRIVATE;
|
||||
@@ -6409,7 +6405,7 @@ MaybeDumpObject(const char *name, JSObject *obj)
|
||||
{
|
||||
if (obj) {
|
||||
fprintf(stderr, " %s: ", name);
|
||||
dumpValue(ToValue(*obj));
|
||||
dumpValue(ObjectTag(*obj));
|
||||
fputc('\n', stderr);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1292,21 +1292,4 @@ js_InferFlags(JSContext *cx, uintN defaultFlags);
|
||||
JSBool
|
||||
js_Object(JSContext *cx, JSObject *obj, uintN argc, js::Value *argv, js::Value *rval);
|
||||
|
||||
namespace js {
|
||||
|
||||
/*
|
||||
* Convenience functions for manipulating objects and values. To be inlined,
|
||||
* these functions need to be in jsobj.h, so they cannot be member functions.
|
||||
*/
|
||||
|
||||
JS_ALWAYS_INLINE ObjPtr ToObjPtr(JSObject *pobj);
|
||||
JS_ALWAYS_INLINE ObjPtr ToObjPtr(JSObject &obj);
|
||||
JS_ALWAYS_INLINE Value ToValue(JSObject *pobj);
|
||||
JS_ALWAYS_INLINE Value ToValue(JSObject &obj);
|
||||
JS_ALWAYS_INLINE void SetObject(ObjPtr *vp, JSObject *pobj);
|
||||
JS_ALWAYS_INLINE void SetObject(Value *vp, JSObject *pobj);
|
||||
JS_ALWAYS_INLINE void SetObject(ObjPtr *vp, JSObject &obj);
|
||||
JS_ALWAYS_INLINE void SetObject(Value *vp, JSObject &obj);
|
||||
|
||||
} /* namespace js */
|
||||
#endif /* jsobj_h___ */
|
||||
|
||||
@@ -470,10 +470,10 @@ inline js::ObjPtr
|
||||
JSObject::thisObject(JSContext *cx, js::ObjPtr obj)
|
||||
{
|
||||
if (JSObjectOp thisOp = obj->map->ops->thisObject) {
|
||||
JSObject *o = thisOp(cx, obj);
|
||||
if (!o)
|
||||
return js::NullObjPtr();
|
||||
SetObject(&obj, *o);
|
||||
JSObject *pobj = thisOp(cx, obj);
|
||||
if (!pobj)
|
||||
return js::NullTag();
|
||||
obj.setObject(*pobj);
|
||||
}
|
||||
return obj;
|
||||
}
|
||||
@@ -590,7 +590,7 @@ NewObjectWithGivenProto(JSContext *cx, js::Class *clasp, JSObject *proto,
|
||||
* the parent of the prototype's constructor.
|
||||
*/
|
||||
obj->init(clasp,
|
||||
ToObjPtr(proto),
|
||||
js::ObjectOrNullTag(proto),
|
||||
(!parent && proto) ? proto->getParent() : parent,
|
||||
JSObject::defaultPrivate(clasp));
|
||||
|
||||
@@ -650,80 +650,60 @@ NewObject(JSContext *cx, js::Class *clasp, JSObject *proto,
|
||||
return NewObjectWithGivenProto(cx, clasp, proto, parent, objectSize);
|
||||
}
|
||||
|
||||
JS_ALWAYS_INLINE ObjPtr
|
||||
ToObjPtr(JSObject *pobj)
|
||||
JS_ALWAYS_INLINE
|
||||
ObjPtr::ObjPtr(ObjectTag arg)
|
||||
{
|
||||
if (pobj)
|
||||
return NullObjPtr();
|
||||
if (pobj->isFunction())
|
||||
return FunObjPtr(*pobj);
|
||||
return NonFunObjPtr(*pobj);
|
||||
mask = arg.obj.isFunction() ? FunObjMask : NonFunObjMask;
|
||||
obj = &arg.obj;
|
||||
}
|
||||
|
||||
JS_ALWAYS_INLINE ObjPtr
|
||||
ToObjPtr(JSObject &obj)
|
||||
JS_ALWAYS_INLINE
|
||||
ObjPtr::ObjPtr(ObjectOrNullTag arg)
|
||||
{
|
||||
if (obj.isFunction())
|
||||
return FunObjPtr(obj);
|
||||
return NonFunObjPtr(obj);
|
||||
}
|
||||
|
||||
JS_ALWAYS_INLINE Value
|
||||
ToValue(JSObject *pobj)
|
||||
{
|
||||
if (pobj)
|
||||
return NullValue();
|
||||
if (pobj->isFunction())
|
||||
return FunObjValue(*pobj);
|
||||
return NonFunObjValue(*pobj);
|
||||
}
|
||||
|
||||
JS_ALWAYS_INLINE Value
|
||||
ToValue(JSObject &obj)
|
||||
{
|
||||
if (obj.isFunction())
|
||||
return FunObjValue(obj);
|
||||
return NonFunObjValue(obj);
|
||||
mask = arg.obj ? arg.obj->isFunction() ? FunObjMask : NonFunObjMask : NullMask;
|
||||
obj = arg.obj;
|
||||
}
|
||||
|
||||
JS_ALWAYS_INLINE void
|
||||
SetObject(ObjPtr *vp, JSObject *pobj)
|
||||
ObjPtr::setObject(JSObject &arg)
|
||||
{
|
||||
if (!pobj)
|
||||
vp->setNull();
|
||||
else if (pobj->isFunction())
|
||||
vp->setFunObj(*pobj);
|
||||
else
|
||||
vp->setNonFunObj(*pobj);
|
||||
mask = arg.isFunction() ? FunObjMask : NonFunObjMask;
|
||||
obj = &arg;
|
||||
}
|
||||
|
||||
JS_ALWAYS_INLINE void
|
||||
SetObject(Value *vp, JSObject *pobj)
|
||||
ObjPtr::setObjectOrNull(JSObject *arg)
|
||||
{
|
||||
if (!pobj)
|
||||
vp->setNull();
|
||||
if (pobj->isFunction())
|
||||
vp->setFunObj(*pobj);
|
||||
else
|
||||
vp->setNonFunObj(*pobj);
|
||||
mask = arg ? arg->isFunction() ? FunObjMask : NonFunObjMask : NullMask;
|
||||
obj = arg;
|
||||
}
|
||||
|
||||
JS_ALWAYS_INLINE
|
||||
Value::Value(ObjectTag arg)
|
||||
{
|
||||
mask = arg.obj.isFunction() ? FunObjMask : NonFunObjMask;
|
||||
data.obj = &arg.obj;
|
||||
}
|
||||
|
||||
JS_ALWAYS_INLINE
|
||||
Value::Value(ObjectOrNullTag arg)
|
||||
{
|
||||
mask = arg.obj ? arg.obj->isFunction() ? FunObjMask : NonFunObjMask : NullMask;
|
||||
data.obj = arg.obj;
|
||||
}
|
||||
|
||||
JS_ALWAYS_INLINE void
|
||||
SetObject(ObjPtr *vp, JSObject &obj)
|
||||
Value::setObject(JSObject &arg)
|
||||
{
|
||||
if (obj.isFunction())
|
||||
vp->setFunObj(obj);
|
||||
else
|
||||
vp->setNonFunObj(obj);
|
||||
mask = arg.isFunction() ? FunObjMask : NonFunObjMask;
|
||||
data.obj = &arg;
|
||||
}
|
||||
|
||||
JS_ALWAYS_INLINE void
|
||||
SetObject(Value *vp, JSObject &obj)
|
||||
Value::setObjectOrNull(JSObject *arg)
|
||||
{
|
||||
if (obj.isFunction())
|
||||
vp->setFunObj(obj);
|
||||
else
|
||||
vp->setNonFunObj(obj);
|
||||
mask = arg ? arg->isFunction() ? FunObjMask : NonFunObjMask : NullMask;
|
||||
data.obj = arg;
|
||||
}
|
||||
|
||||
} /* namespace js */
|
||||
|
||||
@@ -3151,7 +3151,8 @@ BEGIN_CASE(JSOP_DEFFUN)
|
||||
MUST_FLOW_THROUGH("restore_scope");
|
||||
fp->scopeChain = obj;
|
||||
|
||||
FunObjValue rval(*obj);
|
||||
Value rval;
|
||||
rval.setFunObj(*obj);
|
||||
|
||||
/*
|
||||
* ECMA requires functions defined when entering Eval code to be
|
||||
@@ -3250,7 +3251,9 @@ BEGIN_CASE(JSOP_DEFFUN_DBGFC)
|
||||
: js_NewDebuggableFlatClosure(cx, fun);
|
||||
if (!obj)
|
||||
goto error;
|
||||
FunObjValue rval(*obj);
|
||||
|
||||
Value rval;
|
||||
rval.setFunObj(*obj);
|
||||
|
||||
uintN attrs = (fp->flags & JSFRAME_EVAL)
|
||||
? JSPROP_ENUMERATE
|
||||
@@ -4044,7 +4047,7 @@ BEGIN_CASE(JSOP_QNAMECONST)
|
||||
JSObject *obj = js_ConstructXMLQNameObject(cx, lval, rval);
|
||||
if (!obj)
|
||||
goto error;
|
||||
SetObject(®s.sp[-1], *obj);
|
||||
regs.sp[-1].setObject(*obj);
|
||||
}
|
||||
END_CASE(JSOP_QNAMECONST)
|
||||
|
||||
@@ -4057,7 +4060,7 @@ BEGIN_CASE(JSOP_QNAME)
|
||||
if (!obj)
|
||||
goto error;
|
||||
regs.sp--;
|
||||
SetObject(®s.sp[-1], *obj);
|
||||
regs.sp[-1].setObject(*obj);
|
||||
}
|
||||
END_CASE(JSOP_QNAME)
|
||||
|
||||
@@ -4107,7 +4110,7 @@ BEGIN_CASE(JSOP_BINDXMLNAME)
|
||||
jsid id;
|
||||
if (!js_FindXMLProperty(cx, lval, &obj, &id))
|
||||
goto error;
|
||||
SetObject(®s.sp[-1], obj);
|
||||
regs.sp[-1].setObjectOrNull(obj);
|
||||
PUSH_COPY(IdToValue(id));
|
||||
}
|
||||
END_CASE(JSOP_BINDXMLNAME)
|
||||
@@ -4215,7 +4218,7 @@ BEGIN_CASE(JSOP_TOXML)
|
||||
JSObject *obj = js_ValueToXMLObject(cx, rval);
|
||||
if (!obj)
|
||||
goto error;
|
||||
SetObject(®s.sp[-1], *obj);
|
||||
regs.sp[-1].setObject(*obj);
|
||||
}
|
||||
END_CASE(JSOP_TOXML)
|
||||
|
||||
@@ -4226,7 +4229,7 @@ BEGIN_CASE(JSOP_TOXMLLIST)
|
||||
JSObject *obj = js_ValueToXMLListObject(cx, rval);
|
||||
if (!obj)
|
||||
goto error;
|
||||
SetObject(®s.sp[-1], *obj);
|
||||
regs.sp[-1].setObject(*obj);
|
||||
}
|
||||
END_CASE(JSOP_TOXMLLIST)
|
||||
|
||||
@@ -4305,7 +4308,7 @@ BEGIN_CASE(JSOP_XMLPI)
|
||||
JSObject *obj = js_NewXMLSpecialObject(cx, JSXML_CLASS_PROCESSING_INSTRUCTION, str, str2);
|
||||
if (!obj)
|
||||
goto error;
|
||||
SetObject(®s.sp[-1], *obj);
|
||||
regs.sp[-1].setObject(*obj);
|
||||
}
|
||||
END_CASE(JSOP_XMLPI)
|
||||
|
||||
|
||||
@@ -689,8 +689,7 @@ struct JSScopeProperty {
|
||||
bool hasShortID() const { return (flags & HAS_SHORTID) != 0; }
|
||||
bool isMethod() const { return (flags & METHOD) != 0; }
|
||||
|
||||
JSObject *methodObject() const { JS_ASSERT(isMethod()); return getterObj; }
|
||||
js::Value methodValue() const { return js::FunObjValue(*methodObject()); }
|
||||
JSObject &methodFunObj() const { JS_ASSERT(isMethod()); return *getterObj; }
|
||||
|
||||
js::PropertyOp getter() const { return rawGetter; }
|
||||
bool hasDefaultGetter() const { return !rawGetter; }
|
||||
@@ -698,11 +697,13 @@ struct JSScopeProperty {
|
||||
JSObject *getterObject() const { JS_ASSERT(hasGetterValue()); return getterObj; }
|
||||
|
||||
// Per ES5, decode null getterObj as the undefined value, which encodes as null.
|
||||
js::Value getterValue() const {
|
||||
js::FunObjOrUndefinedTag getterValue() const {
|
||||
JS_ASSERT(hasGetterValue());
|
||||
if (getterObj)
|
||||
return js::FunObjValue(*getterObj);
|
||||
return js::UndefinedValue();
|
||||
return js::FunObjOrUndefinedTag(getterObj);
|
||||
}
|
||||
|
||||
js::FunObjOrUndefinedTag getterOrUndefined() const {
|
||||
return js::FunObjOrUndefinedTag(hasGetterValue() ? getterObj : NULL);
|
||||
}
|
||||
|
||||
js::PropertyOp setter() const { return rawSetter; }
|
||||
@@ -711,11 +712,13 @@ struct JSScopeProperty {
|
||||
JSObject *setterObject() const { JS_ASSERT(hasSetterValue()); return setterObj; }
|
||||
|
||||
// Per ES5, decode null setterObj as the undefined value, which encodes as null.
|
||||
js::Value setterValue() const {
|
||||
js::FunObjOrUndefinedTag setterValue() const {
|
||||
JS_ASSERT(hasSetterValue());
|
||||
if (setterObj)
|
||||
return js::FunObjValue(*setterObj);
|
||||
return js::UndefinedValue();
|
||||
return js::FunObjOrUndefinedTag(setterObj);
|
||||
}
|
||||
|
||||
js::FunObjOrUndefinedTag setterOrUndefined() const {
|
||||
return js::FunObjOrUndefinedTag(hasSetterValue() ? setterObj : NULL);
|
||||
}
|
||||
|
||||
inline JSDHashNumber hash() const;
|
||||
@@ -964,7 +967,7 @@ JSScopeProperty::get(JSContext* cx, JSObject *obj, JSObject *pobj, js::Value* vp
|
||||
}
|
||||
|
||||
if (isMethod()) {
|
||||
vp->copy(methodValue());
|
||||
vp->setFunObj(methodFunObj());
|
||||
|
||||
JSScope *scope = pobj->scope();
|
||||
JS_ASSERT(scope->object == pobj);
|
||||
|
||||
@@ -119,7 +119,7 @@ JSScope::methodReadBarrier(JSContext *cx, JSScopeProperty *sprop, js::Value *vp)
|
||||
JS_ASSERT(hasMethodBarrier());
|
||||
JS_ASSERT(hasProperty(sprop));
|
||||
JS_ASSERT(sprop->isMethod());
|
||||
JS_ASSERT(sprop->methodValue().isSame(*vp));
|
||||
JS_ASSERT(&vp->asFunObj() == &sprop->methodFunObj());
|
||||
JS_ASSERT(object->getClass() == &js_ObjectClass);
|
||||
|
||||
JSObject *funobj = &vp->asFunObj();
|
||||
|
||||
Reference in New Issue
Block a user