mirror of
https://gitlab.winehq.org/wine/wine-gecko.git
synced 2024-09-13 09:24:08 -07:00
Bug 1245767 - Allow combining different gczeal modes. r=terrence
This commit is contained in:
parent
a2988de8a0
commit
fc1572a57e
@ -624,10 +624,10 @@ ScheduleGC(JSContext* cx, unsigned argc, Value* vp)
|
||||
PrepareZoneForGC(args[0].toString()->zone());
|
||||
}
|
||||
|
||||
uint8_t zeal;
|
||||
uint32_t zealBits;
|
||||
uint32_t freq;
|
||||
uint32_t next;
|
||||
JS_GetGCZeal(cx, &zeal, &freq, &next);
|
||||
JS_GetGCZealBits(cx, &zealBits, &freq, &next);
|
||||
args.rval().setInt32(next);
|
||||
return true;
|
||||
}
|
||||
|
@ -580,7 +580,8 @@ class GCRuntime
|
||||
void finishRoots();
|
||||
void finish();
|
||||
|
||||
inline int zeal();
|
||||
inline bool hasZealMode(ZealMode mode);
|
||||
inline void clearZealMode(ZealMode mode);
|
||||
inline bool upcomingZealousGC();
|
||||
inline bool needZealousGC();
|
||||
|
||||
@ -636,8 +637,8 @@ class GCRuntime
|
||||
void onOutOfMallocMemory(const AutoLockGC& lock);
|
||||
|
||||
#ifdef JS_GC_ZEAL
|
||||
const void* addressOfZealMode() { return &zealMode; }
|
||||
void getZeal(uint8_t* zeal, uint32_t* frequency, uint32_t* nextScheduled);
|
||||
const void* addressOfZealModeBits() { return &zealModeBits; }
|
||||
void getZealBits(uint32_t* zealBits, uint32_t* frequency, uint32_t* nextScheduled);
|
||||
void setZeal(uint8_t zeal, uint32_t frequency);
|
||||
bool parseAndSetZeal(const char* str);
|
||||
void setNextScheduled(uint32_t count);
|
||||
@ -1259,7 +1260,7 @@ class GCRuntime
|
||||
* zeal_ value 14 performs periodic shrinking collections.
|
||||
*/
|
||||
#ifdef JS_GC_ZEAL
|
||||
int zealMode;
|
||||
uint32_t zealModeBits;
|
||||
int zealFrequency;
|
||||
int nextScheduled;
|
||||
bool deterministicOnly;
|
||||
@ -1347,9 +1348,20 @@ class MOZ_RAII AutoEnterIteration {
|
||||
};
|
||||
|
||||
#ifdef JS_GC_ZEAL
|
||||
inline int
|
||||
GCRuntime::zeal() {
|
||||
return zealMode;
|
||||
|
||||
inline bool
|
||||
GCRuntime::hasZealMode(ZealMode mode)
|
||||
{
|
||||
static_assert(size_t(ZealMode::Limit) < sizeof(zealModeBits) * 8,
|
||||
"Zeal modes must fit in zealModeBits");
|
||||
return zealModeBits & (1 << uint32_t(mode));
|
||||
}
|
||||
|
||||
inline void
|
||||
GCRuntime::clearZealMode(ZealMode mode)
|
||||
{
|
||||
zealModeBits &= ~(1 << uint32_t(mode));
|
||||
MOZ_ASSERT(!hasZealMode(mode));
|
||||
}
|
||||
|
||||
inline bool
|
||||
@ -1360,11 +1372,12 @@ GCRuntime::upcomingZealousGC() {
|
||||
inline bool
|
||||
GCRuntime::needZealousGC() {
|
||||
if (nextScheduled > 0 && --nextScheduled == 0) {
|
||||
if (zealMode == ZealAllocValue ||
|
||||
zealMode == ZealGenerationalGCValue ||
|
||||
(zealMode >= ZealIncrementalRootsThenFinish &&
|
||||
zealMode <= ZealIncrementalMultipleSlices) ||
|
||||
zealMode == ZealCompactValue)
|
||||
if (hasZealMode(ZealMode::Alloc) ||
|
||||
hasZealMode(ZealMode::GenerationalGC) ||
|
||||
hasZealMode(ZealMode::IncrementalRootsThenFinish) ||
|
||||
hasZealMode(ZealMode::IncrementalMarkAllThenFinish) ||
|
||||
hasZealMode(ZealMode::IncrementalMultipleSlices) ||
|
||||
hasZealMode(ZealMode::Compact))
|
||||
{
|
||||
nextScheduled = zealFrequency;
|
||||
}
|
||||
@ -1373,7 +1386,8 @@ GCRuntime::needZealousGC() {
|
||||
return false;
|
||||
}
|
||||
#else
|
||||
inline int GCRuntime::zeal() { return 0; }
|
||||
inline bool GCRuntime::hasZealMode(ZealMode mode) { return false; }
|
||||
inline void GCRuntime::clearZealMode(ZealMode mode) { }
|
||||
inline bool GCRuntime::upcomingZealousGC() { return false; }
|
||||
inline bool GCRuntime::needZealousGC() { return false; }
|
||||
#endif
|
||||
|
@ -139,7 +139,7 @@ js::Nursery::enable()
|
||||
setCurrentChunk(0);
|
||||
currentStart_ = position();
|
||||
#ifdef JS_GC_ZEAL
|
||||
if (runtime()->gcZeal() == ZealGenerationalGCValue)
|
||||
if (runtime()->hasZealMode(ZealMode::GenerationalGC))
|
||||
enterZealMode();
|
||||
#endif
|
||||
}
|
||||
@ -161,7 +161,7 @@ js::Nursery::isEmpty() const
|
||||
MOZ_ASSERT(runtime_);
|
||||
if (!isEnabled())
|
||||
return true;
|
||||
MOZ_ASSERT_IF(runtime_->gcZeal() != ZealGenerationalGCValue, currentStart_ == start());
|
||||
MOZ_ASSERT_IF(!runtime_->hasZealMode(ZealMode::GenerationalGC), currentStart_ == start());
|
||||
return position() == currentStart_;
|
||||
}
|
||||
|
||||
@ -516,7 +516,7 @@ js::Nursery::collect(JSRuntime* rt, JS::gcreason::Reason reason, ObjectGroupList
|
||||
// Make sure hashtables have been updated after the collection.
|
||||
TIME_START(checkHashTables);
|
||||
#ifdef JS_GC_ZEAL
|
||||
if (rt->gcZeal() == ZealCheckHashTablesOnMinorGC)
|
||||
if (rt->hasZealMode(ZealMode::CheckHashTablesOnMinorGC))
|
||||
CheckHashTablesAfterMovingGC(rt);
|
||||
#endif
|
||||
TIME_END(checkHashTables);
|
||||
@ -678,7 +678,7 @@ js::Nursery::sweep()
|
||||
for (int i = 0; i < numNurseryChunks_; ++i)
|
||||
initChunk(i);
|
||||
|
||||
if (runtime()->gcZeal() == ZealGenerationalGCValue) {
|
||||
if (runtime()->hasZealMode(ZealMode::GenerationalGC)) {
|
||||
MOZ_ASSERT(numActiveChunks_ == numNurseryChunks_);
|
||||
|
||||
/* Only reset the alloc point when we are close to the end. */
|
||||
@ -704,7 +704,7 @@ void
|
||||
js::Nursery::growAllocableSpace()
|
||||
{
|
||||
#ifdef JS_GC_ZEAL
|
||||
MOZ_ASSERT_IF(runtime()->gcZeal() == ZealGenerationalGCValue,
|
||||
MOZ_ASSERT_IF(runtime()->hasZealMode(ZealMode::GenerationalGC),
|
||||
numActiveChunks_ == numNurseryChunks_);
|
||||
#endif
|
||||
numActiveChunks_ = Min(numActiveChunks_ * 2, numNurseryChunks_);
|
||||
@ -714,7 +714,7 @@ void
|
||||
js::Nursery::shrinkAllocableSpace()
|
||||
{
|
||||
#ifdef JS_GC_ZEAL
|
||||
if (runtime()->gcZeal() == ZealGenerationalGCValue)
|
||||
if (runtime()->hasZealMode(ZealMode::GenerationalGC))
|
||||
return;
|
||||
#endif
|
||||
numActiveChunks_ = Max(numActiveChunks_ - 1, 1);
|
||||
|
@ -381,7 +381,7 @@ gc::VerifyBarriers(JSRuntime* rt, VerifierType type)
|
||||
void
|
||||
gc::GCRuntime::maybeVerifyPreBarriers(bool always)
|
||||
{
|
||||
if (zealMode != ZealVerifierPreValue)
|
||||
if (!hasZealMode(ZealMode::VerifierPre))
|
||||
return;
|
||||
|
||||
if (rt->mainThread.suppressGC)
|
||||
|
@ -233,7 +233,7 @@ struct Zone : public JS::shadow::Zone,
|
||||
bool compileBarriers() const { return compileBarriers(needsIncrementalBarrier()); }
|
||||
bool compileBarriers(bool needsIncrementalBarrier) const {
|
||||
return needsIncrementalBarrier ||
|
||||
runtimeFromMainThread()->gcZeal() == js::gc::ZealVerifierPreValue;
|
||||
runtimeFromMainThread()->hasZealMode(js::gc::ZealMode::VerifierPre);
|
||||
}
|
||||
|
||||
enum ShouldUpdateJit { DontUpdateJit, UpdateJit };
|
||||
|
@ -78,9 +78,9 @@ CompileRuntime::addressOfLastCachedNativeIterator()
|
||||
|
||||
#ifdef JS_GC_ZEAL
|
||||
const void*
|
||||
CompileRuntime::addressOfGCZeal()
|
||||
CompileRuntime::addressOfGCZealModeBits()
|
||||
{
|
||||
return runtime()->gc.addressOfZealMode();
|
||||
return runtime()->gc.addressOfZealModeBits();
|
||||
}
|
||||
#endif
|
||||
|
||||
|
@ -53,7 +53,7 @@ class CompileRuntime
|
||||
const void* addressOfLastCachedNativeIterator();
|
||||
|
||||
#ifdef JS_GC_ZEAL
|
||||
const void* addressOfGCZeal();
|
||||
const void* addressOfGCZealModeBits();
|
||||
#endif
|
||||
|
||||
const void* addressOfInterruptUint32();
|
||||
|
@ -718,12 +718,12 @@ MacroAssembler::checkAllocatorState(Label* fail)
|
||||
if (js::gc::TraceEnabled() || MemProfiler::enabled())
|
||||
jump(fail);
|
||||
|
||||
# ifdef JS_GC_ZEAL
|
||||
#ifdef JS_GC_ZEAL
|
||||
// Don't execute the inline path if gc zeal or tracing are active.
|
||||
branch32(Assembler::NotEqual,
|
||||
AbsoluteAddress(GetJitContext()->runtime->addressOfGCZeal()), Imm32(0),
|
||||
AbsoluteAddress(GetJitContext()->runtime->addressOfGCZealModeBits()), Imm32(0),
|
||||
fail);
|
||||
# endif
|
||||
#endif
|
||||
|
||||
// Don't execute the inline path if the compartment has an object metadata callback,
|
||||
// as the metadata to use for the object may vary between executions of the op.
|
||||
|
@ -625,7 +625,7 @@ PostWriteElementBarrier(JSRuntime* rt, JSObject* obj, size_t index)
|
||||
if (obj->is<NativeObject>() &&
|
||||
(obj->as<NativeObject>().getDenseInitializedLength() > MAX_WHOLE_CELL_BUFFER_SIZE
|
||||
#ifdef JS_GC_ZEAL
|
||||
|| rt->gcZeal() == gc::ZealElementsBarrier
|
||||
|| rt->hasZealMode(gc::ZealMode::ElementsBarrier)
|
||||
#endif
|
||||
))
|
||||
{
|
||||
|
@ -424,19 +424,29 @@ class TestJSPrincipals : public JSPrincipals
|
||||
class AutoLeaveZeal
|
||||
{
|
||||
JSContext* cx_;
|
||||
uint8_t zeal_;
|
||||
uint32_t zealBits_;
|
||||
uint32_t frequency_;
|
||||
|
||||
public:
|
||||
explicit AutoLeaveZeal(JSContext* cx) : cx_(cx) {
|
||||
uint32_t dummy;
|
||||
JS_GetGCZeal(cx_, &zeal_, &frequency_, &dummy);
|
||||
JS_GetGCZealBits(cx_, &zealBits_, &frequency_, &dummy);
|
||||
JS_SetGCZeal(cx_, 0, 0);
|
||||
JS::PrepareForFullGC(JS_GetRuntime(cx_));
|
||||
JS::GCForReason(JS_GetRuntime(cx_), GC_SHRINK, JS::gcreason::DEBUG_GC);
|
||||
}
|
||||
~AutoLeaveZeal() {
|
||||
JS_SetGCZeal(cx_, zeal_, frequency_);
|
||||
for (size_t i = 0; i < sizeof(zealBits_) * 8; i++) {
|
||||
if (zealBits_ & (1 << i))
|
||||
JS_SetGCZeal(cx_, i, frequency_);
|
||||
}
|
||||
|
||||
#ifdef DEBUG
|
||||
uint32_t zealBitsAfter, frequencyAfter, dummy;
|
||||
JS_GetGCZealBits(cx_, &zealBitsAfter, &frequencyAfter, &dummy);
|
||||
MOZ_ASSERT(zealBitsAfter == zealBits_);
|
||||
MOZ_ASSERT(frequencyAfter == frequency_);
|
||||
#endif
|
||||
}
|
||||
};
|
||||
#endif /* JS_GC_ZEAL */
|
||||
|
@ -5753,9 +5753,9 @@ JS_AbortIfWrongThread(JSRuntime* rt)
|
||||
|
||||
#ifdef JS_GC_ZEAL
|
||||
JS_PUBLIC_API(void)
|
||||
JS_GetGCZeal(JSContext* cx, uint8_t* zeal, uint32_t* frequency, uint32_t* nextScheduled)
|
||||
JS_GetGCZealBits(JSContext* cx, uint32_t* zealBits, uint32_t* frequency, uint32_t* nextScheduled)
|
||||
{
|
||||
cx->runtime()->gc.getZeal(zeal, frequency, nextScheduled);
|
||||
cx->runtime()->gc.getZealBits(zealBits, frequency, nextScheduled);
|
||||
}
|
||||
|
||||
JS_PUBLIC_API(void)
|
||||
|
@ -5239,7 +5239,7 @@ JS_NewObjectForConstructor(JSContext* cx, const JSClass* clasp, const JS::CallAr
|
||||
#define JS_DEFAULT_ZEAL_FREQ 100
|
||||
|
||||
extern JS_PUBLIC_API(void)
|
||||
JS_GetGCZeal(JSContext* cx, uint8_t* zeal, uint32_t* frequency, uint32_t* nextScheduled);
|
||||
JS_GetGCZealBits(JSContext* cx, uint32_t* zealBits, uint32_t* frequency, uint32_t* nextScheduled);
|
||||
|
||||
extern JS_PUBLIC_API(void)
|
||||
JS_SetGCZeal(JSContext* cx, uint8_t zeal, uint32_t frequency);
|
||||
|
@ -1164,7 +1164,7 @@ GCRuntime::GCRuntime(JSRuntime* rt) :
|
||||
objectsMarkedInDeadZones(0),
|
||||
poked(false),
|
||||
#ifdef JS_GC_ZEAL
|
||||
zealMode(0),
|
||||
zealModeBits(0),
|
||||
zealFrequency(0),
|
||||
nextScheduled(0),
|
||||
deterministicOnly(false),
|
||||
@ -1188,16 +1188,20 @@ GCRuntime::GCRuntime(JSRuntime* rt) :
|
||||
#ifdef JS_GC_ZEAL
|
||||
|
||||
void
|
||||
GCRuntime::getZeal(uint8_t* zeal, uint32_t* frequency, uint32_t* scheduled)
|
||||
GCRuntime::getZealBits(uint32_t* zealBits, uint32_t* frequency, uint32_t* scheduled)
|
||||
{
|
||||
*zeal = zealMode;
|
||||
*zealBits = zealModeBits;
|
||||
*frequency = zealFrequency;
|
||||
*scheduled = nextScheduled;
|
||||
}
|
||||
|
||||
const char* gc::ZealModeHelpText =
|
||||
" Specifies how zealous the garbage collector should be. Values for level:\n"
|
||||
" 0: Normal amount of collection\n"
|
||||
" Specifies how zealous the garbage collector should be. Some of these modes can\n"
|
||||
" be set simultaneously, e.g. in the shell, gczeal(2); gczeal(4); will activate\n"
|
||||
" both modes 2 and 4.\n"
|
||||
" \n"
|
||||
" Values:\n"
|
||||
" 0: Normal amount of collection (resets all modes)\n"
|
||||
" 1: Collect when roots are added or removed\n"
|
||||
" 2: Collect when every N allocations (default: 100)\n"
|
||||
" 3: Collect when the window paints (browser only)\n"
|
||||
@ -1216,19 +1220,35 @@ const char* gc::ZealModeHelpText =
|
||||
void
|
||||
GCRuntime::setZeal(uint8_t zeal, uint32_t frequency)
|
||||
{
|
||||
MOZ_ASSERT(zeal <= unsigned(ZealMode::Limit));
|
||||
|
||||
if (verifyPreData)
|
||||
VerifyBarriers(rt, PreBarrierVerifier);
|
||||
|
||||
if (zealMode == ZealGenerationalGCValue) {
|
||||
if (zeal == 0 && hasZealMode(ZealMode::GenerationalGC)) {
|
||||
evictNursery(JS::gcreason::DEBUG_GC);
|
||||
nursery.leaveZealMode();
|
||||
}
|
||||
|
||||
if (zeal == ZealGenerationalGCValue)
|
||||
ZealMode zealMode = ZealMode(zeal);
|
||||
if (zealMode == ZealMode::GenerationalGC)
|
||||
nursery.enterZealMode();
|
||||
|
||||
bool schedule = zeal >= js::gc::ZealAllocValue;
|
||||
zealMode = zeal;
|
||||
// Zeal modes 8-10 are mutually exclusive. If we're setting one of those,
|
||||
// we first reset all of them.
|
||||
if (zealMode >= ZealMode::IncrementalRootsThenFinish &&
|
||||
zealMode <= ZealMode::IncrementalMultipleSlices)
|
||||
{
|
||||
clearZealMode(ZealMode::IncrementalRootsThenFinish);
|
||||
clearZealMode(ZealMode::IncrementalMarkAllThenFinish);
|
||||
clearZealMode(ZealMode::IncrementalMultipleSlices);
|
||||
}
|
||||
|
||||
bool schedule = zealMode >= ZealMode::Alloc;
|
||||
if (zeal != 0)
|
||||
zealModeBits |= 1 << unsigned(zeal);
|
||||
else
|
||||
zealModeBits = 0;
|
||||
zealFrequency = frequency;
|
||||
nextScheduled = schedule ? frequency : 0;
|
||||
}
|
||||
@ -1255,7 +1275,7 @@ GCRuntime::parseAndSetZeal(const char* str)
|
||||
frequency = atoi(p + 1);
|
||||
}
|
||||
|
||||
if (zeal < 0 || zeal > ZealLimit || frequency <= 0) {
|
||||
if (zeal < 0 || zeal > int(ZealMode::Limit) || frequency <= 0) {
|
||||
fprintf(stderr, "Format: JS_GC_ZEAL=level[,N]\n");
|
||||
fputs(ZealModeHelpText, stderr);
|
||||
return false;
|
||||
@ -3251,7 +3271,7 @@ GCRuntime::triggerZoneGC(Zone* zone, JS::gcreason::Reason reason)
|
||||
return false;
|
||||
|
||||
#ifdef JS_GC_ZEAL
|
||||
if (zealMode == ZealAllocValue) {
|
||||
if (hasZealMode(ZealMode::Alloc)) {
|
||||
triggerGC(reason);
|
||||
return true;
|
||||
}
|
||||
@ -3280,7 +3300,7 @@ GCRuntime::maybeGC(Zone* zone)
|
||||
MOZ_ASSERT(CurrentThreadCanAccessRuntime(rt));
|
||||
|
||||
#ifdef JS_GC_ZEAL
|
||||
if (zealMode == ZealAllocValue || zealMode == ZealPokeValue) {
|
||||
if (hasZealMode(ZealMode::Alloc) || hasZealMode(ZealMode::Poke)) {
|
||||
JS::PrepareForFullGC(rt);
|
||||
gc(GC_NORMAL, JS::gcreason::DEBUG_GC);
|
||||
return true;
|
||||
@ -3680,7 +3700,7 @@ GCRuntime::shouldReleaseObservedTypes()
|
||||
bool releaseTypes = false;
|
||||
|
||||
#ifdef JS_GC_ZEAL
|
||||
if (zealMode != 0)
|
||||
if (zealModeBits != 0)
|
||||
releaseTypes = true;
|
||||
#endif
|
||||
|
||||
@ -4504,7 +4524,7 @@ GCRuntime::computeNonIncrementalMarkingForValidation()
|
||||
{
|
||||
#ifdef JS_GC_ZEAL
|
||||
MOZ_ASSERT(!markingValidator);
|
||||
if (isIncremental && zeal() == ZealIncrementalMarkingValidator)
|
||||
if (isIncremental && hasZealMode(ZealMode::IncrementalMarkingValidator))
|
||||
markingValidator = js_new<MarkingValidator>(this);
|
||||
if (markingValidator)
|
||||
markingValidator->nonIncrementalMark();
|
||||
@ -6033,7 +6053,7 @@ GCRuntime::incrementalCollectSlice(SliceBudget& budget, JS::gcreason::Reason rea
|
||||
|
||||
gc::State initialState = incrementalState;
|
||||
|
||||
int zeal = 0;
|
||||
bool useZeal = false;
|
||||
#ifdef JS_GC_ZEAL
|
||||
if (reason == JS::gcreason::DEBUG_GC && !budget.isUnlimited()) {
|
||||
/*
|
||||
@ -6041,14 +6061,16 @@ GCRuntime::incrementalCollectSlice(SliceBudget& budget, JS::gcreason::Reason rea
|
||||
* collection was triggered by runDebugGC() and incremental GC has not
|
||||
* been cancelled by resetIncrementalGC().
|
||||
*/
|
||||
zeal = zealMode;
|
||||
useZeal = true;
|
||||
}
|
||||
#endif
|
||||
|
||||
MOZ_ASSERT_IF(isIncrementalGCInProgress(), isIncremental);
|
||||
isIncremental = !budget.isUnlimited();
|
||||
|
||||
if (zeal == ZealIncrementalRootsThenFinish || zeal == ZealIncrementalMarkAllThenFinish) {
|
||||
if (useZeal && (hasZealMode(ZealMode::IncrementalRootsThenFinish) ||
|
||||
hasZealMode(ZealMode::IncrementalMarkAllThenFinish)))
|
||||
{
|
||||
/*
|
||||
* Yields between slices occurs at predetermined points in these modes;
|
||||
* the budget is not used.
|
||||
@ -6078,7 +6100,7 @@ GCRuntime::incrementalCollectSlice(SliceBudget& budget, JS::gcreason::Reason rea
|
||||
|
||||
incrementalState = MARK;
|
||||
|
||||
if (isIncremental && zeal == ZealIncrementalRootsThenFinish)
|
||||
if (isIncremental && useZeal && hasZealMode(ZealMode::IncrementalRootsThenFinish))
|
||||
break;
|
||||
|
||||
MOZ_FALLTHROUGH;
|
||||
@ -6097,9 +6119,9 @@ GCRuntime::incrementalCollectSlice(SliceBudget& budget, JS::gcreason::Reason rea
|
||||
|
||||
MOZ_ASSERT(marker.isDrained());
|
||||
|
||||
if (!lastMarkSlice && isIncremental &&
|
||||
((initialState == MARK && zeal != ZealIncrementalRootsThenFinish) ||
|
||||
zeal == ZealIncrementalMarkAllThenFinish))
|
||||
if (!lastMarkSlice && isIncremental && useZeal &&
|
||||
((initialState == MARK && !hasZealMode(ZealMode::IncrementalRootsThenFinish)) ||
|
||||
hasZealMode(ZealMode::IncrementalMarkAllThenFinish)))
|
||||
{
|
||||
/*
|
||||
* Yield with the aim of starting the sweep in the next
|
||||
@ -6124,7 +6146,7 @@ GCRuntime::incrementalCollectSlice(SliceBudget& budget, JS::gcreason::Reason rea
|
||||
* Always yield here when running in incremental multi-slice zeal
|
||||
* mode, so RunDebugGC can reset the slice buget.
|
||||
*/
|
||||
if (isIncremental && zeal == ZealIncrementalMultipleSlices)
|
||||
if (isIncremental && useZeal && hasZealMode(ZealMode::IncrementalMultipleSlices))
|
||||
break;
|
||||
|
||||
MOZ_FALLTHROUGH;
|
||||
@ -6550,12 +6572,10 @@ GCRuntime::notifyDidPaint()
|
||||
MOZ_ASSERT(CurrentThreadCanAccessRuntime(rt));
|
||||
|
||||
#ifdef JS_GC_ZEAL
|
||||
if (zealMode == ZealFrameVerifierPreValue) {
|
||||
if (hasZealMode(ZealMode::FrameVerifierPre))
|
||||
verifyPreBarriers();
|
||||
return;
|
||||
}
|
||||
|
||||
if (zealMode == ZealFrameGCValue) {
|
||||
if (hasZealMode(ZealMode::FrameGC)) {
|
||||
JS::PrepareForFullGC(rt);
|
||||
gc(GC_NORMAL, JS::gcreason::REFRESH_FRAME);
|
||||
return;
|
||||
@ -6929,23 +6949,21 @@ void
|
||||
GCRuntime::runDebugGC()
|
||||
{
|
||||
#ifdef JS_GC_ZEAL
|
||||
int type = zealMode;
|
||||
|
||||
if (rt->mainThread.suppressGC)
|
||||
return;
|
||||
|
||||
if (type == js::gc::ZealGenerationalGCValue)
|
||||
if (hasZealMode(ZealMode::GenerationalGC))
|
||||
return minorGC(JS::gcreason::DEBUG_GC);
|
||||
|
||||
PrepareForDebugGC(rt);
|
||||
|
||||
auto budget = SliceBudget::unlimited();
|
||||
if (type == ZealIncrementalRootsThenFinish ||
|
||||
type == ZealIncrementalMarkAllThenFinish ||
|
||||
type == ZealIncrementalMultipleSlices)
|
||||
if (hasZealMode(ZealMode::IncrementalRootsThenFinish) ||
|
||||
hasZealMode(ZealMode::IncrementalMarkAllThenFinish) ||
|
||||
hasZealMode(ZealMode::IncrementalMultipleSlices))
|
||||
{
|
||||
js::gc::State initialState = incrementalState;
|
||||
if (type == ZealIncrementalMultipleSlices) {
|
||||
if (hasZealMode(ZealMode::IncrementalMultipleSlices)) {
|
||||
/*
|
||||
* Start with a small slice limit and double it every slice. This
|
||||
* ensure that we get multiple slices, and collection runs to
|
||||
@ -6969,14 +6987,14 @@ GCRuntime::runDebugGC()
|
||||
* For multi-slice zeal, reset the slice size when we get to the sweep
|
||||
* or compact phases.
|
||||
*/
|
||||
if (type == ZealIncrementalMultipleSlices) {
|
||||
if (hasZealMode(ZealMode::IncrementalMultipleSlices)) {
|
||||
if ((initialState == MARK && incrementalState == SWEEP) ||
|
||||
(initialState == SWEEP && incrementalState == COMPACT))
|
||||
{
|
||||
incrementalLimit = zealFrequency / 2;
|
||||
}
|
||||
}
|
||||
} else if (type == ZealCompactValue) {
|
||||
} else if (hasZealMode(ZealMode::Compact)) {
|
||||
gc(GC_SHRINK, JS::gcreason::DEBUG_GC);
|
||||
} else {
|
||||
gc(GC_NORMAL, JS::gcreason::DEBUG_GC);
|
||||
|
@ -1251,21 +1251,23 @@ CheckValueAfterMovingGC(const JS::Value& value)
|
||||
|
||||
#endif // JSGC_HASH_TABLE_CHECKS
|
||||
|
||||
const int ZealPokeValue = 1;
|
||||
const int ZealAllocValue = 2;
|
||||
const int ZealFrameGCValue = 3;
|
||||
const int ZealVerifierPreValue = 4;
|
||||
const int ZealFrameVerifierPreValue = 5;
|
||||
const int ZealStackRootingValue = 6;
|
||||
const int ZealGenerationalGCValue = 7;
|
||||
const int ZealIncrementalRootsThenFinish = 8;
|
||||
const int ZealIncrementalMarkAllThenFinish = 9;
|
||||
const int ZealIncrementalMultipleSlices = 10;
|
||||
const int ZealIncrementalMarkingValidator = 11;
|
||||
const int ZealElementsBarrier = 12;
|
||||
const int ZealCheckHashTablesOnMinorGC = 13;
|
||||
const int ZealCompactValue = 14;
|
||||
const int ZealLimit = 14;
|
||||
enum class ZealMode {
|
||||
Poke = 1,
|
||||
Alloc = 2,
|
||||
FrameGC = 3,
|
||||
VerifierPre = 4,
|
||||
FrameVerifierPre = 5,
|
||||
StackRooting = 6,
|
||||
GenerationalGC = 7,
|
||||
IncrementalRootsThenFinish = 8,
|
||||
IncrementalMarkAllThenFinish = 9,
|
||||
IncrementalMultipleSlices = 10,
|
||||
IncrementalMarkingValidator = 11,
|
||||
ElementsBarrier = 12,
|
||||
CheckHashTablesOnMinorGC = 13,
|
||||
Compact = 14,
|
||||
Limit = 14
|
||||
};
|
||||
|
||||
enum VerifierType {
|
||||
PreBarrierVerifier
|
||||
|
@ -33,7 +33,7 @@ GCRuntime::poke()
|
||||
|
||||
#ifdef JS_GC_ZEAL
|
||||
/* Schedule a GC to happen "soon" after a GC poke. */
|
||||
if (zealMode == ZealPokeValue)
|
||||
if (hasZealMode(ZealMode::Poke))
|
||||
nextScheduled = 1;
|
||||
#endif
|
||||
}
|
||||
|
@ -1092,7 +1092,7 @@ struct JSRuntime : public JS::shadow::Runtime,
|
||||
/* Garbage collector state has been successfully initialized. */
|
||||
bool gcInitialized;
|
||||
|
||||
int gcZeal() { return gc.zeal(); }
|
||||
bool hasZealMode(js::gc::ZealMode mode) { return gc.hasZealMode(mode); }
|
||||
|
||||
void lockGC() {
|
||||
assertCanLock(js::GCLock);
|
||||
|
Loading…
Reference in New Issue
Block a user