зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1491313. Add some MOZ_CRASH instrumentation to help figure out why ClearDocumentDependentSlots hits its MOZ_CRASH case. r=mccr8
We need the isDOMClass() checks in the Compartment code to pass tests, because some of the jsapi tests explicitly test those failure codepaths. But not with DOM objects, which is what we're interested in here. Differential Revision: https://phabricator.services.mozilla.com/D6047 --HG-- extra : moz-landing-system : lando
This commit is contained in:
Родитель
6d56c9b541
Коммит
8e04fc97a0
|
@ -44,6 +44,7 @@
|
|||
|
||||
class nsGenericHTMLElement;
|
||||
class nsIJSID;
|
||||
class nsIDocument;
|
||||
|
||||
namespace mozilla {
|
||||
|
||||
|
@ -53,6 +54,7 @@ namespace dom {
|
|||
class CustomElementReactionsStack;
|
||||
class MessageManagerGlobal;
|
||||
template<typename KeyType, typename ValueType> class Record;
|
||||
class Location;
|
||||
|
||||
nsresult
|
||||
UnwrapArgImpl(JSContext* cx, JS::Handle<JSObject*> src, const nsIID& iid,
|
||||
|
@ -1060,8 +1062,30 @@ struct CheckWrapperCacheTracing<T, true>
|
|||
void
|
||||
AssertReflectorHasGivenProto(JSContext* aCx, JSObject* aReflector,
|
||||
JS::Handle<JSObject*> aGivenProto);
|
||||
|
||||
#endif // DEBUG
|
||||
|
||||
template <class T>
|
||||
MOZ_ALWAYS_INLINE void
|
||||
CrashIfDocumentOrLocationWrapFailed()
|
||||
{
|
||||
// Do nothing.
|
||||
}
|
||||
|
||||
template<>
|
||||
MOZ_ALWAYS_INLINE void
|
||||
CrashIfDocumentOrLocationWrapFailed<nsIDocument>()
|
||||
{
|
||||
MOZ_CRASH("Looks like bug 1488480/1405521, with WrapObject() on nsIDocument throwing");
|
||||
}
|
||||
|
||||
template<>
|
||||
MOZ_ALWAYS_INLINE void
|
||||
CrashIfDocumentOrLocationWrapFailed<Location>()
|
||||
{
|
||||
MOZ_CRASH("Looks like bug 1488480/1405521, with WrapObject() on Location throwing");
|
||||
}
|
||||
|
||||
template <class T, GetOrCreateReflectorWrapBehavior wrapBehavior>
|
||||
MOZ_ALWAYS_INLINE bool
|
||||
DoGetOrCreateDOMReflector(JSContext* cx, T* value,
|
||||
|
@ -1084,6 +1108,7 @@ DoGetOrCreateDOMReflector(JSContext* cx, T* value,
|
|||
// At this point, obj is null, so just return false.
|
||||
// Callers seem to be testing JS_IsExceptionPending(cx) to
|
||||
// figure out whether WrapObject() threw.
|
||||
CrashIfDocumentOrLocationWrapFailed<T>();
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -1113,19 +1138,35 @@ DoGetOrCreateDOMReflector(JSContext* cx, T* value,
|
|||
rval.set(JS::ObjectValue(*obj));
|
||||
|
||||
if (js::GetObjectCompartment(obj) == js::GetContextCompartment(cx)) {
|
||||
return TypeNeedsOuterization<T>::value ? TryToOuterize(rval) : true;
|
||||
if (!TypeNeedsOuterization<T>::value) {
|
||||
return true;
|
||||
}
|
||||
if (TryToOuterize(rval)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
if (wrapBehavior == eDontWrapIntoContextCompartment) {
|
||||
if (TypeNeedsOuterization<T>::value) {
|
||||
JSAutoRealm ar(cx, obj);
|
||||
return TryToOuterize(rval);
|
||||
if (TryToOuterize(rval)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
return JS_WrapValue(cx, rval);
|
||||
if (JS_WrapValue(cx, rval)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
MOZ_CRASH("Looks like bug 1488480/1405521, with JS_WrapValue failing");
|
||||
return false;
|
||||
}
|
||||
|
||||
} // namespace binding_detail
|
||||
|
|
|
@ -4015,6 +4015,14 @@ class CGClearCachedValueMethod(CGAbstractMethod):
|
|||
saveMember = (
|
||||
"JS::Rooted<JS::Value> oldValue(aCx, js::GetReservedSlot(obj, %s));\n" %
|
||||
slotIndex)
|
||||
if self.descriptor.name == "Document" or self.descriptor.name == "Location":
|
||||
maybeCrash = dedent(
|
||||
"""
|
||||
MOZ_CRASH("Looks like bug 1488480/1405521, with the getter failing");
|
||||
""")
|
||||
else:
|
||||
maybeCrash = ""
|
||||
|
||||
regetMember = fill(
|
||||
"""
|
||||
JS::Rooted<JS::Value> temp(aCx);
|
||||
|
@ -4022,12 +4030,14 @@ class CGClearCachedValueMethod(CGAbstractMethod):
|
|||
JSAutoRealm ar(aCx, obj);
|
||||
if (!get_${name}(aCx, obj, aObject, args)) {
|
||||
js::SetReservedSlot(obj, ${slotIndex}, oldValue);
|
||||
$*{maybeCrash}
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
""",
|
||||
name=self.member.identifier.name,
|
||||
slotIndex=slotIndex)
|
||||
slotIndex=slotIndex,
|
||||
maybeCrash=maybeCrash)
|
||||
else:
|
||||
declObj = "JSObject* obj;\n"
|
||||
noopRetval = ""
|
||||
|
@ -6681,6 +6691,11 @@ def getWrapTemplateForType(type, descriptorProvider, result, successCode,
|
|||
# threw an exception.
|
||||
failed = ("MOZ_ASSERT(JS_IsExceptionPending(cx));\n" +
|
||||
exceptionCode)
|
||||
|
||||
if descriptor.name == "Document" or descriptor.name == "Location":
|
||||
failed = (
|
||||
'MOZ_CRASH("Looks like bug 1488480/1405521, with getting the reflector failing");\n' +
|
||||
failed)
|
||||
else:
|
||||
if descriptor.notflattened:
|
||||
getIID = "&NS_GET_IID(%s), " % descriptor.nativeType
|
||||
|
@ -7836,6 +7851,14 @@ class CGPerSignatureCall(CGThing):
|
|||
"args.rval().isObject()")
|
||||
postConversionSteps += freezeValue.define()
|
||||
|
||||
if self.descriptor.name == "Window":
|
||||
maybeCrash = dedent(
|
||||
"""
|
||||
MOZ_CRASH("Looks like bug 1488480/1405521, with the other MaybeWrap failing");
|
||||
""")
|
||||
else:
|
||||
maybeCrash = ""
|
||||
|
||||
# slotStorageSteps are steps that run once we have entered the
|
||||
# slotStorage compartment.
|
||||
slotStorageSteps= fill(
|
||||
|
@ -7843,11 +7866,13 @@ class CGPerSignatureCall(CGThing):
|
|||
// Make a copy so that we don't do unnecessary wrapping on args.rval().
|
||||
JS::Rooted<JS::Value> storedVal(cx, args.rval());
|
||||
if (!${maybeWrap}(cx, &storedVal)) {
|
||||
$*{maybeCrash}
|
||||
return false;
|
||||
}
|
||||
js::SetReservedSlot(slotStorage, slotIndex, storedVal);
|
||||
""",
|
||||
maybeWrap=getMaybeWrapValueFuncForType(self.idlNode.type))
|
||||
maybeWrap=getMaybeWrapValueFuncForType(self.idlNode.type),
|
||||
maybeCrash=maybeCrash)
|
||||
|
||||
checkForXray = mayUseXrayExpandoSlots(self.descriptor, self.idlNode)
|
||||
|
||||
|
@ -7885,6 +7910,14 @@ class CGPerSignatureCall(CGThing):
|
|||
else:
|
||||
conversionScope = "slotStorage"
|
||||
|
||||
if self.descriptor.name == "Window":
|
||||
maybeCrash = dedent(
|
||||
"""
|
||||
MOZ_CRASH("Looks like bug 1488480/1405521, with the third MaybeWrap failing");
|
||||
""")
|
||||
else:
|
||||
maybeCrash = ""
|
||||
|
||||
wrapCode = fill(
|
||||
"""
|
||||
{
|
||||
|
@ -7900,13 +7933,18 @@ class CGPerSignatureCall(CGThing):
|
|||
$*{slotStorageSteps}
|
||||
}
|
||||
// And now make sure args.rval() is in the caller realm.
|
||||
return ${maybeWrap}(cx, args.rval());
|
||||
if (${maybeWrap}(cx, args.rval())) {
|
||||
return true;
|
||||
}
|
||||
$*{maybeCrash}
|
||||
return false;
|
||||
""",
|
||||
conversionScope=conversionScope,
|
||||
wrapCode=wrapCode,
|
||||
postConversionSteps=postConversionSteps,
|
||||
slotStorageSteps=slotStorageSteps,
|
||||
maybeWrap=getMaybeWrapValueFuncForType(self.idlNode.type))
|
||||
maybeWrap=getMaybeWrapValueFuncForType(self.idlNode.type),
|
||||
maybeCrash=maybeCrash)
|
||||
return wrapCode
|
||||
|
||||
def define(self):
|
||||
|
@ -8938,6 +8976,14 @@ class CGSpecializedGetter(CGAbstractStaticMethod):
|
|||
""",
|
||||
slotIndex=memberReservedSlot(self.attr, self.descriptor))
|
||||
|
||||
if self.descriptor.name == "Window":
|
||||
maybeCrash = dedent(
|
||||
"""
|
||||
MOZ_CRASH("Looks like bug 1488480/1405521, with cached value wrapping failing");
|
||||
""")
|
||||
else:
|
||||
maybeCrash = ""
|
||||
|
||||
prefix += fill(
|
||||
"""
|
||||
MOZ_ASSERT(JSCLASS_RESERVED_SLOTS(js::GetObjectClass(slotStorage)) > slotIndex);
|
||||
|
@ -8948,12 +8994,17 @@ class CGSpecializedGetter(CGAbstractStaticMethod):
|
|||
args.rval().set(cachedVal);
|
||||
// The cached value is in the compartment of slotStorage,
|
||||
// so wrap into the caller compartment as needed.
|
||||
return ${maybeWrap}(cx, args.rval());
|
||||
if (${maybeWrap}(cx, args.rval())) {
|
||||
return true;
|
||||
}
|
||||
$*{maybeCrash}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
""",
|
||||
maybeWrap=getMaybeWrapValueFuncForType(self.attr.type))
|
||||
maybeWrap=getMaybeWrapValueFuncForType(self.attr.type),
|
||||
maybeCrash=maybeCrash)
|
||||
else:
|
||||
prefix = ""
|
||||
|
||||
|
|
|
@ -92,6 +92,9 @@ JS::Compartment::wrap(JSContext* cx, JS::MutableHandleValue vp)
|
|||
|
||||
JS::RootedObject obj(cx, &vp.toObject());
|
||||
if (!wrap(cx, &obj)) {
|
||||
if (js::UncheckedUnwrap(&vp.toObject())->getClass()->isDOMClass()) {
|
||||
MOZ_CRASH("Looks like bug 1488480/1405521, with the object version of Compartment::wrap failing");
|
||||
}
|
||||
return false;
|
||||
}
|
||||
vp.setObject(*obj);
|
||||
|
|
|
@ -237,11 +237,17 @@ Compartment::getNonWrapperObjectForCurrentCompartment(JSContext* cx, MutableHand
|
|||
// see bug 809295.
|
||||
auto preWrap = cx->runtime()->wrapObjectCallbacks->preWrap;
|
||||
if (!CheckSystemRecursionLimit(cx)) {
|
||||
if (obj->getClass()->isDOMClass()) {
|
||||
MOZ_CRASH("Looks like bug 1488480/1405521, with system recursion limit failing in getNonWrapperObjectForCurrentCompartment");
|
||||
}
|
||||
return false;
|
||||
}
|
||||
if (preWrap) {
|
||||
preWrap(cx, cx->global(), obj, objectPassedToWrap, obj);
|
||||
if (!obj) {
|
||||
if (UncheckedUnwrap(objectPassedToWrap)->getClass()->isDOMClass()) {
|
||||
MOZ_CRASH("Looks like bug 1488480/1405521, with preWrap failing in getNonWrapperObjectForCurrentCompartment");
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
@ -269,6 +275,9 @@ Compartment::getOrCreateWrapper(JSContext* cx, HandleObject existing, MutableHan
|
|||
auto wrap = cx->runtime()->wrapObjectCallbacks->wrap;
|
||||
RootedObject wrapper(cx, wrap(cx, existing, obj));
|
||||
if (!wrapper) {
|
||||
if (key.toObject().getClass()->isDOMClass()) {
|
||||
MOZ_CRASH("Looks like bug 1488480/1405521, with wrap() call failing in Compartment::getOrCreateWrapper");
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -285,6 +294,9 @@ Compartment::getOrCreateWrapper(JSContext* cx, HandleObject existing, MutableHan
|
|||
if (wrapper->is<CrossCompartmentWrapperObject>()) {
|
||||
NukeCrossCompartmentWrapper(cx, wrapper);
|
||||
}
|
||||
if (obj->getClass()->isDOMClass()) {
|
||||
MOZ_CRASH("Looks like bug 1488480/1405521, with hashtable ops failing in Compartment::getOrCreateWrapper");
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
|
|
Загрузка…
Ссылка в новой задаче