Detect cyclic __proto__ values ourselves because the JS engine gets confused by the wrappers. bug 390626, r=brendan sr=jst

This commit is contained in:
mrbkap@gmail.com 2007-08-02 16:38:11 -07:00
Родитель f9a815e445
Коммит 15893bcdca
3 изменённых файлов: 30 добавлений и 0 удалений

Просмотреть файл

@ -576,6 +576,13 @@ XPC_XOW_GetOrSetProperty(JSContext *cx, JSObject *obj, jsval id, jsval *vp,
return XPC_XOW_RewrapIfNeeded(cx, obj, vp);
}
JSObject *proto = nsnull; // Initialize this to quiet GCC.
JSBool checkProto =
(isSet && id == GetRTStringByIndex(cx, XPCJSRuntime::IDX_PROTO));
if (checkProto) {
proto = JS_GetPrototype(cx, wrappedObj);
}
// Same origin, pass this request along as though nothing interesting
// happened.
jsid asId;
@ -591,6 +598,27 @@ XPC_XOW_GetOrSetProperty(JSContext *cx, JSObject *obj, jsval id, jsval *vp,
return JS_FALSE;
}
if (checkProto && JS_GetPrototype(cx, wrappedObj) != proto) {
// Ensure that this __proto__ setting didn't create a cycle. The JS
// engine tries to do this, but XOWs confuse it. So here we deal with
// them by unwrapping each step up the prototype chain.
JSObject *oldProto = proto;
proto = wrappedObj;
while ((proto = JS_GetPrototype(cx, proto)) != nsnull) {
JSObject *unwrapped = GetWrappedObject(cx, proto);
if (unwrapped) {
proto = unwrapped;
}
if (proto == wrappedObj) {
JS_SetPrototype(cx, wrappedObj, oldProto);
JS_ReportError(cx, "cyclic __proto__ value");
return JS_FALSE;
}
}
}
// Don't call XPC_XOW_RewrapIfNeeded for same origin properties. We only
// need to wrap window, document and location.
if (JSVAL_IS_PRIMITIVE(*vp)) {

Просмотреть файл

@ -64,6 +64,7 @@ const char* XPCJSRuntime::mStrings[] = {
, "COMObject" // IDX_COMOBJECT
, "supports" // IDX_ACTIVEX_SUPPORTS
#endif
, "__proto__" // IDX_PROTO
};
/***************************************************************************/

Просмотреть файл

@ -650,6 +650,7 @@ public:
IDX_COM_OBJECT ,
IDX_ACTIVEX_SUPPORTS ,
#endif
IDX_PROTO ,
IDX_TOTAL_COUNT // just a count of the above
};