зеркало из https://github.com/mozilla/gecko-dev.git
Backed out changeset aa3c5d257b1e (bug 1490042) for causing topcrash bug 1491530.
This commit is contained in:
Родитель
4d3821f569
Коммит
7dfaaa045e
|
@ -975,23 +975,6 @@ GCPreserveCode(JSContext* cx, unsigned argc, Value* vp)
|
|||
|
||||
#ifdef JS_GC_ZEAL
|
||||
|
||||
static bool
|
||||
ParseGCZealMode(JSContext* cx, const CallArgs& args, uint8_t* zeal)
|
||||
{
|
||||
uint32_t value;
|
||||
if (!ToUint32(cx, args.get(0), &value)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (value > uint32_t(gc::ZealMode::Limit)) {
|
||||
JS_ReportErrorASCII(cx, "gczeal argument out of range");
|
||||
return false;
|
||||
}
|
||||
|
||||
*zeal = static_cast<uint8_t>(value);
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool
|
||||
GCZeal(JSContext* cx, unsigned argc, Value* vp)
|
||||
{
|
||||
|
@ -1003,8 +986,13 @@ GCZeal(JSContext* cx, unsigned argc, Value* vp)
|
|||
return false;
|
||||
}
|
||||
|
||||
uint8_t zeal;
|
||||
if (!ParseGCZealMode(cx, args, &zeal)) {
|
||||
uint32_t zeal;
|
||||
if (!ToUint32(cx, args.get(0), &zeal)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (zeal > uint32_t(gc::ZealMode::Limit)) {
|
||||
JS_ReportErrorASCII(cx, "gczeal argument out of range");
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -1015,28 +1003,7 @@ GCZeal(JSContext* cx, unsigned argc, Value* vp)
|
|||
}
|
||||
}
|
||||
|
||||
JS_SetGCZeal(cx, zeal, frequency);
|
||||
args.rval().setUndefined();
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool
|
||||
UnsetGCZeal(JSContext* cx, unsigned argc, Value* vp)
|
||||
{
|
||||
CallArgs args = CallArgsFromVp(argc, vp);
|
||||
|
||||
if (args.length() > 1) {
|
||||
RootedObject callee(cx, &args.callee());
|
||||
ReportUsageErrorASCII(cx, callee, "Too many arguments");
|
||||
return false;
|
||||
}
|
||||
|
||||
uint8_t zeal;
|
||||
if (!ParseGCZealMode(cx, args, &zeal)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
JS_UnsetGCZeal(cx, zeal);
|
||||
JS_SetGCZeal(cx, (uint8_t)zeal, frequency);
|
||||
args.rval().setUndefined();
|
||||
return true;
|
||||
}
|
||||
|
@ -5713,14 +5680,9 @@ JS_FN_HELP("streamsAreEnabled", StreamsAreEnabled, 0, 0,
|
|||
|
||||
#ifdef JS_GC_ZEAL
|
||||
JS_FN_HELP("gczeal", GCZeal, 2, 0,
|
||||
"gczeal(mode, [frequency])",
|
||||
"gczeal(level, [N])",
|
||||
gc::ZealModeHelpText),
|
||||
|
||||
JS_FN_HELP("unsetgczeal", UnsetGCZeal, 2, 0,
|
||||
"unsetgczeal(mode)",
|
||||
" Turn off a single zeal mode set with gczeal() and don't finish any ongoing\n"
|
||||
" collection that may be happening."),
|
||||
|
||||
JS_FN_HELP("schedulegc", ScheduleGC, 1, 0,
|
||||
"schedulegc([num | obj | string])",
|
||||
" If num is given, schedule a GC after num allocations.\n"
|
||||
|
|
|
@ -1149,41 +1149,6 @@ GCRuntime::setZeal(uint8_t zeal, uint32_t frequency)
|
|||
nextScheduled = schedule ? frequency : 0;
|
||||
}
|
||||
|
||||
void
|
||||
GCRuntime::unsetZeal(uint8_t zeal)
|
||||
{
|
||||
MOZ_ASSERT(zeal <= unsigned(ZealMode::Limit));
|
||||
ZealMode zealMode = ZealMode(zeal);
|
||||
|
||||
if (temporaryAbortIfWasmGc(rt->mainContextFromOwnThread())) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!hasZealMode(zealMode)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (verifyPreData) {
|
||||
VerifyBarriers(rt, PreBarrierVerifier);
|
||||
}
|
||||
|
||||
if (zealMode == ZealMode::GenerationalGC) {
|
||||
evictNursery(JS::gcreason::DEBUG_GC);
|
||||
nursery().leaveZealMode();
|
||||
}
|
||||
|
||||
clearZealMode(zealMode);
|
||||
|
||||
if (zealModeBits == 0) {
|
||||
if (isIncrementalGCInProgress()) {
|
||||
finishGC(JS::gcreason::DEBUG_GC);
|
||||
}
|
||||
|
||||
zealFrequency = 0;
|
||||
nextScheduled = 0;
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
GCRuntime::setNextScheduled(uint32_t count)
|
||||
{
|
||||
|
@ -2651,10 +2616,10 @@ GCRuntime::sweepTypesAfterCompacting(Zone* zone)
|
|||
AutoClearTypeInferenceStateOnOOM oom(zone);
|
||||
|
||||
for (auto script = zone->cellIter<JSScript>(); !script.done(); script.next()) {
|
||||
AutoSweepTypeScript sweep(script, oom);
|
||||
AutoSweepTypeScript sweep(script, &oom);
|
||||
}
|
||||
for (auto group = zone->cellIter<ObjectGroup>(); !group.done(); group.next()) {
|
||||
AutoSweepObjectGroup sweep(group, oom);
|
||||
AutoSweepObjectGroup sweep(group, &oom);
|
||||
}
|
||||
|
||||
zone->types.endSweep(rt);
|
||||
|
@ -6274,24 +6239,24 @@ SweepThing(Shape* shape)
|
|||
}
|
||||
|
||||
static void
|
||||
SweepThing(JSScript* script, AutoClearTypeInferenceStateOnOOM& oom)
|
||||
SweepThing(JSScript* script, AutoClearTypeInferenceStateOnOOM* oom)
|
||||
{
|
||||
AutoSweepTypeScript sweep(script, oom);
|
||||
}
|
||||
|
||||
static void
|
||||
SweepThing(ObjectGroup* group, AutoClearTypeInferenceStateOnOOM& oom)
|
||||
SweepThing(ObjectGroup* group, AutoClearTypeInferenceStateOnOOM* oom)
|
||||
{
|
||||
AutoSweepObjectGroup sweep(group, oom);
|
||||
}
|
||||
|
||||
template <typename T, typename... Args>
|
||||
static bool
|
||||
SweepArenaList(Arena** arenasToSweep, SliceBudget& sliceBudget, Args&&... args)
|
||||
SweepArenaList(Arena** arenasToSweep, SliceBudget& sliceBudget, Args... args)
|
||||
{
|
||||
while (Arena* arena = *arenasToSweep) {
|
||||
for (ArenaCellIterUnderGC i(arena); !i.done(); i.next()) {
|
||||
SweepThing(i.get<T>(), std::forward<Args>(args)...);
|
||||
SweepThing(i.get<T>(), args...);
|
||||
}
|
||||
|
||||
*arenasToSweep = (*arenasToSweep)->next;
|
||||
|
@ -6323,11 +6288,11 @@ GCRuntime::sweepTypeInformation(FreeOp* fop, SliceBudget& budget, Zone* zone)
|
|||
|
||||
AutoClearTypeInferenceStateOnOOM oom(zone);
|
||||
|
||||
if (!SweepArenaList<JSScript>(&al.gcScriptArenasToUpdate.ref(), budget, oom)) {
|
||||
if (!SweepArenaList<JSScript>(&al.gcScriptArenasToUpdate.ref(), budget, &oom)) {
|
||||
return NotFinished;
|
||||
}
|
||||
|
||||
if (!SweepArenaList<ObjectGroup>(&al.gcObjectGroupArenasToUpdate.ref(), budget, oom)) {
|
||||
if (!SweepArenaList<ObjectGroup>(&al.gcObjectGroupArenasToUpdate.ref(), budget, &oom)) {
|
||||
return NotFinished;
|
||||
}
|
||||
|
||||
|
@ -8104,7 +8069,8 @@ GCRuntime::collect(bool nonincrementalByAPI, SliceBudget budget, JS::gcreason::R
|
|||
return;
|
||||
}
|
||||
|
||||
stats().writeLogMessage("GC starting in state %s", StateName(incrementalState));
|
||||
stats().writeLogMessage("GC starting in state %s",
|
||||
StateName(incrementalState));
|
||||
|
||||
AutoTraceLog logGC(TraceLoggerForCurrentThread(), TraceLogger_GC);
|
||||
AutoStopVerifyingBarriers av(rt, IsShutdownGC(reason));
|
||||
|
@ -8161,7 +8127,7 @@ GCRuntime::collect(bool nonincrementalByAPI, SliceBudget budget, JS::gcreason::R
|
|||
MOZ_RELEASE_ASSERT(CheckGrayMarkingState(rt));
|
||||
}
|
||||
#endif
|
||||
stats().writeLogMessage("GC ending in state %s", StateName(incrementalState));
|
||||
stats().writeLogMessage("GC ending");
|
||||
}
|
||||
|
||||
js::AutoEnqueuePendingParseTasksAfterGC::~AutoEnqueuePendingParseTasksAfterGC()
|
||||
|
|
|
@ -299,7 +299,6 @@ class GCRuntime
|
|||
}
|
||||
void getZealBits(uint32_t* zealBits, uint32_t* frequency, uint32_t* nextScheduled);
|
||||
void setZeal(uint8_t zeal, uint32_t frequency);
|
||||
void unsetZeal(uint8_t zeal);
|
||||
bool parseAndSetZeal(const char* str);
|
||||
void setNextScheduled(uint32_t count);
|
||||
void verifyPreBarriers();
|
||||
|
|
|
@ -1,34 +0,0 @@
|
|||
// |jit-test| --no-ion; --no-baseline
|
||||
|
||||
if (!("gcstate" in this))
|
||||
quit();
|
||||
|
||||
gczeal(0);
|
||||
|
||||
// Create a bunch of ObjectGroups with TypeNewScript attached.
|
||||
const count = 1000;
|
||||
let c = [];
|
||||
let a = [];
|
||||
for (let i = 0; i < count; i++) {
|
||||
c[i] = function() { this.a = 1; this.b = 0; this.c = 2; };
|
||||
a[i] = new c[i];
|
||||
}
|
||||
|
||||
// Start an incremental GC and run until we're about to sweep type information.
|
||||
assertEq(gcstate(), "NotActive");
|
||||
gczeal(20);
|
||||
startgc(1);
|
||||
|
||||
// Run incremental slices with simulated OOM set up to provoke OOM when sweeping
|
||||
// types.
|
||||
assertEq(gcstate(), "Sweep");
|
||||
gczeal(10);
|
||||
unsetgczeal(20);
|
||||
while (gcstate() == "Sweep") {
|
||||
oomAfterAllocations(2);
|
||||
gcslice(1);
|
||||
resetOOMFailure();
|
||||
}
|
||||
|
||||
// Ensure our type information stays alive.
|
||||
let x = c.length + a.length;
|
|
@ -6411,12 +6411,6 @@ JS_SetGCZeal(JSContext* cx, uint8_t zeal, uint32_t frequency)
|
|||
cx->runtime()->gc.setZeal(zeal, frequency);
|
||||
}
|
||||
|
||||
JS_PUBLIC_API(void)
|
||||
JS_UnsetGCZeal(JSContext* cx, uint8_t zeal)
|
||||
{
|
||||
cx->runtime()->gc.unsetZeal(zeal);
|
||||
}
|
||||
|
||||
JS_PUBLIC_API(void)
|
||||
JS_ScheduleGC(JSContext* cx, uint32_t count)
|
||||
{
|
||||
|
|
|
@ -4383,9 +4383,6 @@ JS_GetGCZealBits(JSContext* cx, uint32_t* zealBits, uint32_t* frequency, uint32_
|
|||
extern JS_PUBLIC_API(void)
|
||||
JS_SetGCZeal(JSContext* cx, uint8_t zeal, uint32_t frequency);
|
||||
|
||||
extern JS_PUBLIC_API(void)
|
||||
JS_UnsetGCZeal(JSContext* cx, uint8_t zeal);
|
||||
|
||||
extern JS_PUBLIC_API(void)
|
||||
JS_ScheduleGC(JSContext* cx, uint32_t count);
|
||||
#endif
|
||||
|
|
|
@ -1798,7 +1798,7 @@ class JSScript : public js::gc::TenuredCell
|
|||
inline bool typesNeedsSweep() const;
|
||||
|
||||
void sweepTypes(const js::AutoSweepTypeScript& sweep,
|
||||
js::AutoClearTypeInferenceStateOnOOM& oom);
|
||||
js::AutoClearTypeInferenceStateOnOOM* oom);
|
||||
|
||||
inline js::GlobalObject& global() const;
|
||||
js::GlobalObject& uninlinedGlobal() const;
|
||||
|
|
|
@ -284,8 +284,7 @@ class ObjectGroup : public gc::TenuredCell
|
|||
}
|
||||
|
||||
TypeNewScript* anyNewScript(const AutoSweepObjectGroup& sweep);
|
||||
void detachNewScript(bool writeBarrier, ObjectGroup* replacement,
|
||||
AutoClearTypeInferenceStateOnOOM& oom);
|
||||
void detachNewScript(bool writeBarrier, ObjectGroup* replacement);
|
||||
|
||||
ObjectGroupFlags flagsDontCheckGeneration() const {
|
||||
return flags_;
|
||||
|
@ -470,7 +469,7 @@ class ObjectGroup : public gc::TenuredCell
|
|||
void markStateChange(const AutoSweepObjectGroup& sweep, JSContext* cx);
|
||||
void setFlags(const AutoSweepObjectGroup& sweep, JSContext* cx, ObjectGroupFlags flags);
|
||||
void markUnknown(const AutoSweepObjectGroup& sweep, JSContext* cx);
|
||||
void maybeClearNewScriptOnOOM(AutoClearTypeInferenceStateOnOOM& oom);
|
||||
void maybeClearNewScriptOnOOM();
|
||||
void clearNewScript(JSContext* cx, ObjectGroup* replacement = nullptr);
|
||||
|
||||
void print(const AutoSweepObjectGroup& sweep);
|
||||
|
@ -479,7 +478,7 @@ class ObjectGroup : public gc::TenuredCell
|
|||
void traceChildren(JSTracer* trc);
|
||||
|
||||
inline bool needsSweep();
|
||||
void sweep(const AutoSweepObjectGroup& sweep, AutoClearTypeInferenceStateOnOOM& oom);
|
||||
void sweep(const AutoSweepObjectGroup& sweep, AutoClearTypeInferenceStateOnOOM* oom);
|
||||
|
||||
private:
|
||||
uint32_t generation() {
|
||||
|
|
|
@ -446,6 +446,9 @@ struct AutoEnterAnalysis
|
|||
// Prevent GC activity in the middle of analysis.
|
||||
gc::AutoSuppressGC suppressGC;
|
||||
|
||||
// Allow clearing inference info on OOM during incremental sweeping.
|
||||
mozilla::Maybe<AutoClearTypeInferenceStateOnOOM> oom;
|
||||
|
||||
// Pending recompilations to perform before execution of JIT code can resume.
|
||||
RecompileInfoVector pendingRecompiles;
|
||||
|
||||
|
@ -1438,21 +1441,9 @@ ObjectGroup::getProperty(const AutoSweepObjectGroup& sweep, unsigned i)
|
|||
return result;
|
||||
}
|
||||
|
||||
inline
|
||||
AutoSweepObjectGroup::AutoSweepObjectGroup(ObjectGroup* group)
|
||||
#ifdef DEBUG
|
||||
: group_(group)
|
||||
#endif
|
||||
{
|
||||
if (group->needsSweep()) {
|
||||
AutoClearTypeInferenceStateOnOOM oom(group->zone());
|
||||
group->sweep(*this, oom);
|
||||
}
|
||||
}
|
||||
|
||||
inline
|
||||
AutoSweepObjectGroup::AutoSweepObjectGroup(ObjectGroup* group,
|
||||
AutoClearTypeInferenceStateOnOOM& oom)
|
||||
AutoClearTypeInferenceStateOnOOM* oom)
|
||||
#ifdef DEBUG
|
||||
: group_(group)
|
||||
#endif
|
||||
|
@ -1472,19 +1463,8 @@ AutoSweepObjectGroup::~AutoSweepObjectGroup()
|
|||
#endif
|
||||
|
||||
inline
|
||||
AutoSweepTypeScript::AutoSweepTypeScript(JSScript* script)
|
||||
#ifdef DEBUG
|
||||
: script_(script)
|
||||
#endif
|
||||
{
|
||||
if (script->typesNeedsSweep()) {
|
||||
AutoClearTypeInferenceStateOnOOM oom(script->zone());
|
||||
script->sweepTypes(*this, oom);
|
||||
}
|
||||
}
|
||||
|
||||
inline
|
||||
AutoSweepTypeScript::AutoSweepTypeScript(JSScript* script, AutoClearTypeInferenceStateOnOOM& oom)
|
||||
AutoSweepTypeScript::AutoSweepTypeScript(JSScript* script,
|
||||
AutoClearTypeInferenceStateOnOOM* oom)
|
||||
#ifdef DEBUG
|
||||
: script_(script)
|
||||
#endif
|
||||
|
|
|
@ -3302,14 +3302,13 @@ ObjectGroup::anyNewScript(const AutoSweepObjectGroup& sweep)
|
|||
}
|
||||
|
||||
void
|
||||
ObjectGroup::detachNewScript(bool writeBarrier, ObjectGroup* replacement,
|
||||
AutoClearTypeInferenceStateOnOOM& oom)
|
||||
ObjectGroup::detachNewScript(bool writeBarrier, ObjectGroup* replacement)
|
||||
{
|
||||
// Clear the TypeNewScript from this ObjectGroup and, if it has been
|
||||
// analyzed, remove it from the newObjectGroups table so that it will not be
|
||||
// produced by calling 'new' on the associated function anymore.
|
||||
// The TypeNewScript is not actually destroyed.
|
||||
AutoSweepObjectGroup sweep(this, oom);
|
||||
AutoSweepObjectGroup sweep(this);
|
||||
TypeNewScript* newScript = anyNewScript(sweep);
|
||||
MOZ_ASSERT(newScript);
|
||||
|
||||
|
@ -3321,7 +3320,7 @@ ObjectGroup::detachNewScript(bool writeBarrier, ObjectGroup* replacement,
|
|||
}
|
||||
JSObject* associated = MaybeForwarded(newScript->function());
|
||||
if (replacement) {
|
||||
AutoSweepObjectGroup sweepReplacement(replacement, oom);
|
||||
AutoSweepObjectGroup sweepReplacement(replacement);
|
||||
MOZ_ASSERT(replacement->newScript(sweepReplacement)->function() == newScript->function());
|
||||
objectGroups.replaceDefaultNewGroup(nullptr, proto, associated, replacement);
|
||||
} else {
|
||||
|
@ -3339,7 +3338,7 @@ ObjectGroup::detachNewScript(bool writeBarrier, ObjectGroup* replacement,
|
|||
}
|
||||
|
||||
void
|
||||
ObjectGroup::maybeClearNewScriptOnOOM(AutoClearTypeInferenceStateOnOOM& oom)
|
||||
ObjectGroup::maybeClearNewScriptOnOOM()
|
||||
{
|
||||
MOZ_ASSERT(zone()->isGCSweepingOrCompacting());
|
||||
|
||||
|
@ -3347,7 +3346,7 @@ ObjectGroup::maybeClearNewScriptOnOOM(AutoClearTypeInferenceStateOnOOM& oom)
|
|||
return;
|
||||
}
|
||||
|
||||
AutoSweepObjectGroup sweep(this, oom);
|
||||
AutoSweepObjectGroup sweep(this);
|
||||
TypeNewScript* newScript = anyNewScript(sweep);
|
||||
if (!newScript) {
|
||||
return;
|
||||
|
@ -3356,7 +3355,7 @@ ObjectGroup::maybeClearNewScriptOnOOM(AutoClearTypeInferenceStateOnOOM& oom)
|
|||
addFlags(sweep, OBJECT_FLAG_NEW_SCRIPT_CLEARED);
|
||||
|
||||
// This method is called during GC sweeping, so don't trigger pre barriers.
|
||||
detachNewScript(/* writeBarrier = */ false, nullptr, oom);
|
||||
detachNewScript(/* writeBarrier = */ false, nullptr);
|
||||
|
||||
js_delete(newScript);
|
||||
}
|
||||
|
@ -3364,8 +3363,7 @@ ObjectGroup::maybeClearNewScriptOnOOM(AutoClearTypeInferenceStateOnOOM& oom)
|
|||
void
|
||||
ObjectGroup::clearNewScript(JSContext* cx, ObjectGroup* replacement /* = nullptr*/)
|
||||
{
|
||||
AutoClearTypeInferenceStateOnOOM oom(zone());
|
||||
AutoSweepObjectGroup sweep(this, oom);
|
||||
AutoSweepObjectGroup sweep(this);
|
||||
TypeNewScript* newScript = anyNewScript(sweep);
|
||||
if (!newScript) {
|
||||
return;
|
||||
|
@ -3382,7 +3380,7 @@ ObjectGroup::clearNewScript(JSContext* cx, ObjectGroup* replacement /* = nullptr
|
|||
newScript->function()->setNewScriptCleared();
|
||||
}
|
||||
|
||||
detachNewScript(/* writeBarrier = */ true, replacement, oom);
|
||||
detachNewScript(/* writeBarrier = */ true, replacement);
|
||||
|
||||
if (!cx->helperThread()) {
|
||||
bool found = newScript->rollbackPartiallyInitializedObjects(cx, this);
|
||||
|
@ -4746,6 +4744,23 @@ ObjectGroup::clearProperties(const AutoSweepObjectGroup& sweep)
|
|||
propertySet = nullptr;
|
||||
}
|
||||
|
||||
static void
|
||||
EnsureHasAutoClearTypeInferenceStateOnOOM(AutoClearTypeInferenceStateOnOOM*& oom, Zone* zone,
|
||||
Maybe<AutoClearTypeInferenceStateOnOOM>& fallback)
|
||||
{
|
||||
if (!oom) {
|
||||
if (AutoEnterAnalysis* analysis = zone->types.activeAnalysis) {
|
||||
if (analysis->oom.isNothing()) {
|
||||
analysis->oom.emplace(zone);
|
||||
}
|
||||
oom = analysis->oom.ptr();
|
||||
} else {
|
||||
fallback.emplace(zone);
|
||||
oom = &fallback.ref();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Before sweeping the arenas themselves, scan all groups in a compartment to
|
||||
* fixup weak references: property type sets referencing dead JS and type
|
||||
|
@ -4754,13 +4769,16 @@ ObjectGroup::clearProperties(const AutoSweepObjectGroup& sweep)
|
|||
* objects are accessed before their contents have been swept.
|
||||
*/
|
||||
void
|
||||
ObjectGroup::sweep(const AutoSweepObjectGroup& sweep, AutoClearTypeInferenceStateOnOOM& oom)
|
||||
ObjectGroup::sweep(const AutoSweepObjectGroup& sweep, AutoClearTypeInferenceStateOnOOM* oom)
|
||||
{
|
||||
MOZ_ASSERT(generation() != zoneFromAnyThread()->types.generation);
|
||||
setGeneration(zone()->types.generation);
|
||||
|
||||
AssertGCStateForSweep(zone());
|
||||
|
||||
Maybe<AutoClearTypeInferenceStateOnOOM> fallbackOOM;
|
||||
EnsureHasAutoClearTypeInferenceStateOnOOM(oom, zone(), fallbackOOM);
|
||||
|
||||
AutoTouchingGrayThings tgt;
|
||||
|
||||
if (auto* layout = maybeUnboxedLayout(sweep)) {
|
||||
|
@ -4835,12 +4853,12 @@ ObjectGroup::sweep(const AutoSweepObjectGroup& sweep, AutoClearTypeInferenceStat
|
|||
(typeLifoAlloc, propertySet, propertyCount, newProp->id);
|
||||
if (pentry) {
|
||||
*pentry = newProp;
|
||||
newProp->types.sweep(sweep, zone(), oom);
|
||||
newProp->types.sweep(sweep, zone(), *oom);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
oom.setOOM();
|
||||
oom->setOOM();
|
||||
addFlags(sweep, OBJECT_FLAG_DYNAMIC_MASK | OBJECT_FLAG_UNKNOWN_PROPERTIES);
|
||||
clearProperties(sweep);
|
||||
return;
|
||||
|
@ -4863,9 +4881,9 @@ ObjectGroup::sweep(const AutoSweepObjectGroup& sweep, AutoClearTypeInferenceStat
|
|||
JS_POISON(prop, JS_SWEPT_TI_PATTERN, sizeof(Property), MemCheckKind::MakeUndefined);
|
||||
if (newProp) {
|
||||
propertySet = (Property**) newProp;
|
||||
newProp->types.sweep(sweep, zone(), oom);
|
||||
newProp->types.sweep(sweep, zone(), *oom);
|
||||
} else {
|
||||
oom.setOOM();
|
||||
oom->setOOM();
|
||||
addFlags(sweep, OBJECT_FLAG_DYNAMIC_MASK | OBJECT_FLAG_UNKNOWN_PROPERTIES);
|
||||
clearProperties(sweep);
|
||||
return;
|
||||
|
@ -4877,13 +4895,16 @@ ObjectGroup::sweep(const AutoSweepObjectGroup& sweep, AutoClearTypeInferenceStat
|
|||
}
|
||||
|
||||
/* static */ void
|
||||
JSScript::sweepTypes(const js::AutoSweepTypeScript& sweep, AutoClearTypeInferenceStateOnOOM& oom)
|
||||
JSScript::sweepTypes(const js::AutoSweepTypeScript& sweep, AutoClearTypeInferenceStateOnOOM* oom)
|
||||
{
|
||||
MOZ_ASSERT(typesGeneration() != zone()->types.generation);
|
||||
setTypesGeneration(zone()->types.generation);
|
||||
|
||||
AssertGCStateForSweep(zone());
|
||||
|
||||
Maybe<AutoClearTypeInferenceStateOnOOM> fallbackOOM;
|
||||
EnsureHasAutoClearTypeInferenceStateOnOOM(oom, zone(), fallbackOOM);
|
||||
|
||||
TypeZone& types = zone()->types;
|
||||
|
||||
// Sweep the inlinedCompilations Vector.
|
||||
|
@ -4923,10 +4944,10 @@ JSScript::sweepTypes(const js::AutoSweepTypeScript& sweep, AutoClearTypeInferenc
|
|||
|
||||
// Remove constraints and references to dead objects from stack type sets.
|
||||
for (unsigned i = 0; i < num; i++) {
|
||||
typeArray[i].sweep(sweep, zone(), oom);
|
||||
typeArray[i].sweep(sweep, zone(), *oom);
|
||||
}
|
||||
|
||||
if (oom.hadOOM()) {
|
||||
if (oom->hadOOM()) {
|
||||
// It's possible we OOM'd while copying freeze constraints, so they
|
||||
// need to be regenerated.
|
||||
bitFields_.hasFreezeConstraints_ = false;
|
||||
|
@ -5014,12 +5035,12 @@ TypeZone::endSweep(JSRuntime* rt)
|
|||
}
|
||||
|
||||
void
|
||||
TypeZone::clearAllNewScriptsOnOOM(AutoClearTypeInferenceStateOnOOM& oom)
|
||||
TypeZone::clearAllNewScriptsOnOOM()
|
||||
{
|
||||
for (auto iter = zone()->cellIter<ObjectGroup>(); !iter.done(); iter.next()) {
|
||||
ObjectGroup* group = iter;
|
||||
if (!IsAboutToBeFinalizedUnbarriered(&group)) {
|
||||
group->maybeClearNewScriptOnOOM(oom);
|
||||
group->maybeClearNewScriptOnOOM();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -5034,15 +5055,15 @@ AutoClearTypeInferenceStateOnOOM::AutoClearTypeInferenceStateOnOOM(Zone* zone)
|
|||
|
||||
AutoClearTypeInferenceStateOnOOM::~AutoClearTypeInferenceStateOnOOM()
|
||||
{
|
||||
zone->types.setSweepingTypes(false);
|
||||
|
||||
if (oom) {
|
||||
JSRuntime* rt = zone->runtimeFromMainThread();
|
||||
js::CancelOffThreadIonCompile(rt);
|
||||
zone->setPreservingCode(false);
|
||||
zone->discardJitCode(rt->defaultFreeOp(), /* discardBaselineCode = */ false);
|
||||
zone->types.clearAllNewScriptsOnOOM(*this);
|
||||
zone->types.clearAllNewScriptsOnOOM();
|
||||
}
|
||||
|
||||
zone->types.setSweepingTypes(false);
|
||||
}
|
||||
|
||||
#ifdef DEBUG
|
||||
|
|
|
@ -84,8 +84,8 @@ class MOZ_RAII AutoSweepObjectGroup : public AutoSweepBase
|
|||
#endif
|
||||
|
||||
public:
|
||||
inline explicit AutoSweepObjectGroup(ObjectGroup* group);
|
||||
inline AutoSweepObjectGroup(ObjectGroup* group, AutoClearTypeInferenceStateOnOOM& oom);
|
||||
inline explicit AutoSweepObjectGroup(ObjectGroup* group,
|
||||
AutoClearTypeInferenceStateOnOOM* oom = nullptr);
|
||||
#ifdef DEBUG
|
||||
inline ~AutoSweepObjectGroup();
|
||||
|
||||
|
@ -104,8 +104,8 @@ class MOZ_RAII AutoSweepTypeScript : public AutoSweepBase
|
|||
#endif
|
||||
|
||||
public:
|
||||
inline explicit AutoSweepTypeScript(JSScript* script);
|
||||
inline AutoSweepTypeScript(JSScript* script, AutoClearTypeInferenceStateOnOOM& oom);
|
||||
inline explicit AutoSweepTypeScript(JSScript* script,
|
||||
AutoClearTypeInferenceStateOnOOM* oom = nullptr);
|
||||
#ifdef DEBUG
|
||||
inline ~AutoSweepTypeScript();
|
||||
|
||||
|
@ -414,7 +414,7 @@ class TypeZone
|
|||
|
||||
void beginSweep(bool releaseTypes);
|
||||
void endSweep(JSRuntime* rt);
|
||||
void clearAllNewScriptsOnOOM(AutoClearTypeInferenceStateOnOOM& oom);
|
||||
void clearAllNewScriptsOnOOM();
|
||||
|
||||
/* Mark a script as needing recompilation once inference has finished. */
|
||||
void addPendingRecompile(JSContext* cx, const RecompileInfo& info);
|
||||
|
|
Загрузка…
Ссылка в новой задаче