blob: e91870be9dae87279ea1bafcdb0e183b3dfc9a33 [file] [log] [blame]
// Copyright 2020 the V8 project authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "src/heap/cppgc/incremental-marking-schedule.h"
#include "src/base/platform/time.h"
#include "src/heap/cppgc/globals.h"
#include "src/heap/cppgc/stats-collector.h"
#include "testing/gtest/include/gtest/gtest.h"
namespace cppgc {
namespace internal {
namespace {
class IncrementalMarkingScheduleTest : public testing::Test {
public:
static const size_t kObjectSize;
};
const size_t IncrementalMarkingScheduleTest::kObjectSize =
100 * IncrementalMarkingSchedule::kMinimumMarkedBytesPerIncrementalStep;
} // namespace
TEST_F(IncrementalMarkingScheduleTest, FirstStepReturnsDefaultDuration) {
IncrementalMarkingSchedule schedule;
schedule.NotifyIncrementalMarkingStart();
schedule.SetElapsedTimeForTesting(0);
EXPECT_EQ(IncrementalMarkingSchedule::kMinimumMarkedBytesPerIncrementalStep,
schedule.GetNextIncrementalStepDuration(kObjectSize));
}
// If marking is not behind schedule and very small time passed between steps
// the oracle should return the minimum step duration.
TEST_F(IncrementalMarkingScheduleTest, NoTimePassedReturnsMinimumDuration) {
IncrementalMarkingSchedule schedule;
schedule.NotifyIncrementalMarkingStart();
// Add incrementally marked bytes to tell oracle this is not the first step.
schedule.UpdateIncrementalMarkedBytes(
IncrementalMarkingSchedule::kMinimumMarkedBytesPerIncrementalStep);
schedule.SetElapsedTimeForTesting(0);
EXPECT_EQ(IncrementalMarkingSchedule::kMinimumMarkedBytesPerIncrementalStep,
schedule.GetNextIncrementalStepDuration(kObjectSize));
}
TEST_F(IncrementalMarkingScheduleTest, OracleDoesntExccedMaximumStepDuration) {
IncrementalMarkingSchedule schedule;
schedule.NotifyIncrementalMarkingStart();
// Add incrementally marked bytes to tell oracle this is not the first step.
static constexpr size_t kMarkedBytes = 1;
schedule.UpdateIncrementalMarkedBytes(kMarkedBytes);
schedule.SetElapsedTimeForTesting(
IncrementalMarkingSchedule::kEstimatedMarkingTimeMs);
EXPECT_EQ(kObjectSize - kMarkedBytes,
schedule.GetNextIncrementalStepDuration(kObjectSize));
}
TEST_F(IncrementalMarkingScheduleTest, AheadOfScheduleReturnsMinimumDuration) {
IncrementalMarkingSchedule schedule;
schedule.NotifyIncrementalMarkingStart();
// Add incrementally marked bytes to tell oracle this is not the first step.
schedule.UpdateIncrementalMarkedBytes(
IncrementalMarkingSchedule::kMinimumMarkedBytesPerIncrementalStep);
schedule.AddConcurrentlyMarkedBytes(0.6 * kObjectSize);
schedule.SetElapsedTimeForTesting(
0.5 * IncrementalMarkingSchedule::kEstimatedMarkingTimeMs);
EXPECT_EQ(IncrementalMarkingSchedule::kMinimumMarkedBytesPerIncrementalStep,
schedule.GetNextIncrementalStepDuration(kObjectSize));
}
TEST_F(IncrementalMarkingScheduleTest, BehindScheduleReturnsCorrectDuration) {
IncrementalMarkingSchedule schedule;
schedule.NotifyIncrementalMarkingStart();
schedule.UpdateIncrementalMarkedBytes(0.1 * kObjectSize);
schedule.AddConcurrentlyMarkedBytes(0.25 * kObjectSize);
schedule.SetElapsedTimeForTesting(
0.5 * IncrementalMarkingSchedule::kEstimatedMarkingTimeMs);
EXPECT_EQ(0.15 * kObjectSize,
schedule.GetNextIncrementalStepDuration(kObjectSize));
schedule.AddConcurrentlyMarkedBytes(0.05 * kObjectSize);
schedule.SetElapsedTimeForTesting(
0.5 * IncrementalMarkingSchedule::kEstimatedMarkingTimeMs);
EXPECT_EQ(0.1 * kObjectSize,
schedule.GetNextIncrementalStepDuration(kObjectSize));
schedule.AddConcurrentlyMarkedBytes(0.05 * kObjectSize);
schedule.SetElapsedTimeForTesting(
0.5 * IncrementalMarkingSchedule::kEstimatedMarkingTimeMs);
EXPECT_EQ(0.05 * kObjectSize,
schedule.GetNextIncrementalStepDuration(kObjectSize));
}
} // namespace internal
} // namespace cppgc