chromium/content/browser/scheduler/responsiveness/calculator_unittest.cc

// Copyright 2018 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "content/browser/scheduler/responsiveness/calculator.h"

#include <optional>

#include "base/test/metrics/histogram_tester.h"
#include "base/time/time.h"
#include "build/build_config.h"
#include "content/public/browser/responsiveness_calculator_delegate.h"
#include "content/public/test/browser_task_environment.h"
#include "testing/gmock/include/gmock/gmock.h"
#include "testing/gtest/include/gtest/gtest.h"

namespace content {
namespace responsiveness {

CongestionType;
StartupStage;
_;

namespace {
// Copied from calculator.cc.
constexpr int kMeasurementIntervalInMs =;
constexpr int kCongestionThresholdInMs =;

class FakeCalculator : public Calculator {};

}  // namespace

class MockDelegate : public ResponsivenessCalculatorDelegate {};

class ResponsivenessCalculatorTest : public testing::Test {};

#define EXPECT_EXECUTION_CONGESTED_SLICES(num_slices, phase)
#define EXPECT_CONGESTED_SLICES(num_slices, phase)

// A single event executing slightly longer than kCongestionThresholdInMs.
TEST_F(ResponsivenessCalculatorTest, ShortExecutionCongestion) {}

// A single event queued slightly longer than kCongestionThresholdInMs.
TEST_F(ResponsivenessCalculatorTest, ShortQueueCongestion) {}

// A single event whose queuing and execution time together take longer than
// kCongestionThresholdInMs.
TEST_F(ResponsivenessCalculatorTest, ShortCombinedQueueAndExecutionCongestion) {}

// A single event executing slightly longer than 10 * kCongestionThresholdInMs.
TEST_F(ResponsivenessCalculatorTest, LongExecutionCongestion) {}

// A single event executing slightly longer than 10 * kCongestionThresholdInMs.
TEST_F(ResponsivenessCalculatorTest, LongQueueCongestion) {}

// Events that execute in less than 100ms are not congested, regardless of start
// time.
TEST_F(ResponsivenessCalculatorTest, NoExecutionCongestion) {}

// Events that are queued and execute in less than 100ms are not congested,
// regardless of start time.
TEST_F(ResponsivenessCalculatorTest, NoQueueCongestion) {}

// 10 execution congestion events, but very closely overlapping. Time slices are
// discretized and fixed, e.g. [0 100] [100 200] [200 300]. In this test, the
// events all start in the [0 100] slice and end in the [100 200] slice. All of
// them end up marking the [100 200] slice as congested.
TEST_F(ResponsivenessCalculatorTest, OverlappingExecutionCongestion) {}

// 10 queue congestion events, but very closely overlapping. Time slices are
// discretized and fixed, e.g. [0 100] [100 200] [200 300]. In this test, the
// events are all queued in the [0 100] slice and start executing in the [100
// 200] slice. All of them end up marking the [100 200] slice as congested.
TEST_F(ResponsivenessCalculatorTest, OverlappingQueueCongestion) {}

// UI thread has 3 execution congestion events on slices 1, 2, 3
// IO thread has 3 execution congestion events on slices 3, 4, 5,
// There should be a total of 5 congestion events.
TEST_F(ResponsivenessCalculatorTest,
       OverlappingExecutionCongestionMultipleThreads) {}

// UI thread has 3 queue congestion events on slices 1, 2, 3
// IO thread has 3 queue congestion events on slices 3, 4, 5,
// There should be a total of 5 congestion events.
TEST_F(ResponsivenessCalculatorTest,
       OverlappingQueueCongestionMultipleThreads) {}

// Three execution congestions, each of length 2, separated by some shorter
// events.
TEST_F(ResponsivenessCalculatorTest, SeparatedExecutionCongestions) {}

// Three queue congestions, each of length 2, separated by some shorter events.
TEST_F(ResponsivenessCalculatorTest, SeparatedQueueCongestions) {}

TEST_F(ResponsivenessCalculatorTest, MultipleTrigger) {}

// A long delay means that the machine likely went to sleep.
TEST_F(ResponsivenessCalculatorTest, LongDelay) {}

// A long event means that the machine likely went to sleep.
TEST_F(ResponsivenessCalculatorTest, LongEvent) {}

#if BUILDFLAG(IS_ANDROID)
// Metric should not be recorded when application is in background.
TEST_F(ResponsivenessCalculatorTest, ApplicationInBackground) {
  constexpr int kQueueTime = 35;
  constexpr int kStartTime = 40;
  constexpr int kFinishTime = kStartTime + kCongestionThresholdInMs + 5;
  AddEventUI(kQueueTime, kStartTime, kFinishTime);

  base::android::ApplicationStatusListener::NotifyApplicationStateChange(
      base::android::APPLICATION_STATE_HAS_STOPPED_ACTIVITIES);
  base::RunLoop().RunUntilIdle();

  AddEventUI(kQueueTime, kStartTime + 1, kFinishTime + 1);
  EXPECT_CALL(*calculator_, EmitResponsivenessMock(_, _, _)).Times(0);
  TriggerCalculation();
}
#endif

TEST_F(ResponsivenessCalculatorTest, StartupStages) {}

TEST_F(ResponsivenessCalculatorTest, FastStartupStages) {}

// An event execution that crosses a measurement interval boundary should count
// towards both measurement intervals.
TEST_F(ResponsivenessCalculatorTest, ExecutionCrossesBoundary) {}

// An event queuing that crosses a measurement interval boundary should count
// towards both measurement intervals.
TEST_F(ResponsivenessCalculatorTest, QueuingCrossesBoundary) {}

// Events may not be ordered by start or end time.
TEST_F(ResponsivenessCalculatorTest, UnorderedEvents) {}

TEST_F(ResponsivenessCalculatorTest, EmitResponsivenessTraceEventsEmpty) {}

TEST_F(ResponsivenessCalculatorTest, EmitResponsivenessTraceEventsWrongMetric) {}

TEST_F(ResponsivenessCalculatorTest, EmitResponsivenessTraceEvents) {}

TEST_F(ResponsivenessCalculatorTest, Delegate) {}

}  // namespace responsiveness
}  // namespace content