Commit c40f4152 authored by Ulan Degenbaev's avatar Ulan Degenbaev Committed by Commit Bot

[heap] Introduce incremental marking trigger flags for experiments

--incremental-marking-soft-trigger is a percentage of (limit - size)
at which incremental marking starts via a task.

--incremental-marking-hard-trigger is a percentage of (limit - size)
at which incremental marking starts immediately.

E.g. --incremental-marking-soft-trigger=50 and
--incremental-marking-soft-trigger=100 will start a task half-way to
the limit and start incremental marking at the limit.

Change-Id: I14be992c8552dc47de401b376b815f693564cb74
Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/2144069Reviewed-by: 's avatarMichael Lippautz <mlippautz@chromium.org>
Commit-Queue: Ulan Degenbaev <ulan@chromium.org>
Cr-Commit-Position: refs/heads/master@{#67140}
parent a50ee0e3
......@@ -893,6 +893,12 @@ DEFINE_BOOL(incremental_marking, true, "use incremental marking")
DEFINE_BOOL(incremental_marking_wrappers, true,
"use incremental marking for marking wrappers")
DEFINE_BOOL(incremental_marking_task, true, "use tasks for incremental marking")
DEFINE_INT(incremental_marking_soft_trigger, 0,
"threshold for starting incremental marking via a task in percent "
"of available space: limit - size")
DEFINE_INT(incremental_marking_hard_trigger, 0,
"threshold for starting incremental marking immediately in percent "
"of available space: limit - size")
DEFINE_BOOL(trace_unmapper, false, "Trace the unmapping")
DEFINE_BOOL(parallel_scavenge, true, "parallel scavenge")
DEFINE_BOOL(scavenge_task, true, "schedule scavenge tasks")
......
......@@ -2034,6 +2034,7 @@ bool Heap::PerformGarbageCollection(
old_generation_allocation_counter_at_last_gc_ +=
static_cast<size_t>(promoted_objects_size_);
old_generation_size_at_last_gc_ = OldGenerationSizeOfObjects();
global_memory_at_last_gc_ = GlobalSizeOfObjects();
break;
case MINOR_MARK_COMPACTOR:
MinorMarkCompact();
......@@ -4912,6 +4913,22 @@ size_t Heap::GlobalMemoryAvailable() {
: new_space_->Capacity() + 1;
}
double Heap::PercentToOldGenerationLimit() {
double size_at_gc = old_generation_size_at_last_gc_;
double size_now = OldGenerationObjectsAndPromotedExternalMemorySize();
double current_bytes = size_now - size_at_gc;
double total_bytes = old_generation_allocation_limit_ - size_at_gc;
return total_bytes > 0 ? (current_bytes / total_bytes) * 100.0 : 0;
}
double Heap::PercentToGlobalMemoryLimit() {
double size_at_gc = old_generation_size_at_last_gc_;
double size_now = OldGenerationObjectsAndPromotedExternalMemorySize();
double current_bytes = size_now - size_at_gc;
double total_bytes = old_generation_allocation_limit_ - size_at_gc;
return total_bytes > 0 ? (current_bytes / total_bytes) * 100.0 : 0;
}
// This function returns either kNoLimit, kSoftLimit, or kHardLimit.
// The kNoLimit means that either incremental marking is disabled or it is too
// early to start incremental marking.
......@@ -4939,37 +4956,42 @@ Heap::IncrementalMarkingLimit Heap::IncrementalMarkingLimitReached() {
}
if (FLAG_stress_marking > 0) {
double gained_since_last_gc =
PromotedSinceLastGC() +
(isolate()->isolate_data()->external_memory_ -
isolate()->isolate_data()->external_memory_low_since_mark_compact_);
double size_before_gc =
OldGenerationObjectsAndPromotedExternalMemorySize() -
gained_since_last_gc;
double bytes_to_limit = old_generation_allocation_limit_ - size_before_gc;
if (bytes_to_limit > 0) {
double current_percent = (gained_since_last_gc / bytes_to_limit) * 100.0;
int current_percent = static_cast<int>(
std::max(PercentToOldGenerationLimit(), PercentToGlobalMemoryLimit()));
if (current_percent > 0) {
if (FLAG_trace_stress_marking) {
isolate()->PrintWithTimestamp(
"[IncrementalMarking] %.2lf%% of the memory limit reached\n",
"[IncrementalMarking] %d%% of the memory limit reached\n",
current_percent);
}
if (FLAG_fuzzer_gc_analysis) {
// Skips values >=100% since they already trigger marking.
if (current_percent < 100.0) {
if (current_percent < 100) {
max_marking_limit_reached_ =
std::max(max_marking_limit_reached_, current_percent);
std::max<double>(max_marking_limit_reached_, current_percent);
}
} else if (static_cast<int>(current_percent) >=
stress_marking_percentage_) {
} else if (current_percent >= stress_marking_percentage_) {
stress_marking_percentage_ = NextStressMarkingLimit();
return IncrementalMarkingLimit::kHardLimit;
}
}
}
if (FLAG_incremental_marking_soft_trigger > 0 ||
FLAG_incremental_marking_hard_trigger > 0) {
int current_percent = static_cast<int>(
std::max(PercentToOldGenerationLimit(), PercentToGlobalMemoryLimit()));
if (current_percent > FLAG_incremental_marking_hard_trigger &&
FLAG_incremental_marking_hard_trigger > 0) {
return IncrementalMarkingLimit::kHardLimit;
}
if (current_percent > FLAG_incremental_marking_soft_trigger &&
FLAG_incremental_marking_soft_trigger > 0) {
return IncrementalMarkingLimit::kSoftLimit;
}
return IncrementalMarkingLimit::kNoLimit;
}
size_t old_generation_space_available = OldGenerationSpaceAvailable();
const size_t global_memory_available = GlobalMemoryAvailable();
......
......@@ -1816,6 +1816,8 @@ class Heap {
HeapGrowingMode CurrentHeapGrowingMode();
double PercentToOldGenerationLimit();
double PercentToGlobalMemoryLimit();
enum class IncrementalMarkingLimit { kNoLimit, kSoftLimit, kHardLimit };
IncrementalMarkingLimit IncrementalMarkingLimitReached();
......@@ -2136,6 +2138,9 @@ class Heap {
// The size of objects in old generation after the last MarkCompact GC.
size_t old_generation_size_at_last_gc_ = 0;
// The size of global memory after the last MarkCompact GC.
size_t global_memory_at_last_gc_ = 0;
// The feedback storage is used to store allocation sites (keys) and how often
// they have been visited (values) by finding a memento behind an object. The
// storage is only alive temporary during a GC. The invariant is that all
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment