Bug 1342012 - Store a CCW to the introuction script's script source object r=jandem

This commit is contained in:
Jon Coppeard 2019-01-03 10:06:00 +00:00
parent bdfdf72d44
commit 4f6ab86fcf
3 changed files with 31 additions and 11 deletions

View File

@ -3365,15 +3365,17 @@ ModuleObject* js::GetModuleObjectForScript(JSScript* script) {
}
Value js::FindScriptOrModulePrivateForScript(JSScript* script) {
while (script) {
ScriptSourceObject* sso = script->sourceObject();
MOZ_ASSERT(script);
ScriptSourceObject* sso = script->sourceObject();
while (sso) {
Value value = sso->canonicalPrivate();
if (!value.isUndefined()) {
return value;
}
MOZ_ASSERT(sso->unwrappedIntroductionScript() != script);
script = sso->unwrappedIntroductionScript();
ScriptSourceObject* parent = sso->unwrappedIntroductionSourceObject();
MOZ_ASSERT(parent != sso);
sso = parent;
}
return UndefinedValue();

View File

@ -1382,6 +1382,7 @@ ScriptSourceObject* ScriptSourceObject::createInternal(JSContext* cx,
obj->initReservedSlot(ELEMENT_SLOT, MagicValue(JS_GENERIC_MAGIC));
obj->initReservedSlot(ELEMENT_PROPERTY_SLOT, MagicValue(JS_GENERIC_MAGIC));
obj->initReservedSlot(INTRODUCTION_SCRIPT_SLOT, MagicValue(JS_GENERIC_MAGIC));
obj->initReservedSlot(INTRODUCTION_SOURCE_OBJECT_SLOT, MagicValue(JS_GENERIC_MAGIC));
return obj;
}
@ -1420,6 +1421,8 @@ ScriptSourceObject* ScriptSourceObject::unwrappedCanonical() const {
source->getReservedSlot(ELEMENT_PROPERTY_SLOT).isMagic(JS_GENERIC_MAGIC));
MOZ_ASSERT(source->getReservedSlot(INTRODUCTION_SCRIPT_SLOT)
.isMagic(JS_GENERIC_MAGIC));
MOZ_ASSERT(source->getReservedSlot(INTRODUCTION_SOURCE_OBJECT_SLOT)
.isMagic(JS_GENERIC_MAGIC));
RootedObject element(cx, options.element());
RootedString elementAttributeName(cx, options.elementAttributeName());
@ -1430,14 +1433,20 @@ ScriptSourceObject* ScriptSourceObject::unwrappedCanonical() const {
// There is no equivalent of cross-compartment wrappers for scripts. If the
// introduction script and ScriptSourceObject are in different compartments,
// we would be creating a cross-compartment script reference, which is
// forbidden. In that case, simply don't bother to retain the introduction
// script.
Value introductionScript = UndefinedValue();
if (options.introductionScript() &&
options.introductionScript()->compartment() == cx->compartment()) {
introductionScript.setPrivateGCThing(options.introductionScript());
// forbidden. We can still store a CCW to the script source object though.
RootedValue introdutionScript(cx);
RootedValue introdutionSource(cx);
if (options.introductionScript()) {
if (options.introductionScript()->compartment() == cx->compartment()) {
introdutionScript.setPrivateGCThing(options.introductionScript());
}
introdutionSource.setObject(*options.introductionScript()->sourceObject());
if (!cx->compartment()->wrap(cx, &introdutionSource)) {
return false;
}
}
source->setReservedSlot(INTRODUCTION_SCRIPT_SLOT, introductionScript);
source->setReservedSlot(INTRODUCTION_SCRIPT_SLOT, introdutionScript);
source->setReservedSlot(INTRODUCTION_SOURCE_OBJECT_SLOT, introdutionSource);
return true;
}

View File

@ -1170,6 +1170,14 @@ class ScriptSourceObject : public NativeObject {
}
return value.toGCThing()->as<JSScript>();
}
ScriptSourceObject* unwrappedIntroductionSourceObject() const {
Value value =
unwrappedCanonical()->getReservedSlot(INTRODUCTION_SOURCE_OBJECT_SLOT);
if (value.isUndefined()) {
return nullptr;
}
return &UncheckedUnwrap(&value.toObject())->as<ScriptSourceObject>();
}
void setPrivate(const Value& value) {
MOZ_ASSERT(isCanonical());
@ -1189,6 +1197,7 @@ class ScriptSourceObject : public NativeObject {
ELEMENT_SLOT,
ELEMENT_PROPERTY_SLOT,
INTRODUCTION_SCRIPT_SLOT,
INTRODUCTION_SOURCE_OBJECT_SLOT,
PRIVATE_SLOT,
RESERVED_SLOTS
};