chromium/base/threading/thread_perftest.cc

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

#include <stddef.h>

#include <memory>
#include <vector>

#include "base/base_switches.h"
#include "base/command_line.h"
#include "base/functional/bind.h"
#include "base/location.h"
#include "base/memory/ptr_util.h"
#include "base/synchronization/condition_variable.h"
#include "base/synchronization/lock.h"
#include "base/synchronization/waitable_event.h"
#include "base/task/current_thread.h"
#include "base/task/single_thread_task_runner.h"
#include "base/task/task_observer.h"
#include "base/threading/thread.h"
#include "base/time/time.h"
#include "build/build_config.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "testing/perf/perf_result_reporter.h"

#if BUILDFLAG(IS_POSIX)
#include <pthread.h>
#endif

namespace base {

namespace {

const int kNumRuns =;

constexpr char kMetricPrefixThread[] =;
constexpr char kMetricClockTimePerHop[] =;
constexpr char kMetricCpuTimePerHop[] =;
constexpr char kStoryBaseTask[] =;
constexpr char kStoryBaseTaskWithObserver[] =;
constexpr char kStoryBaseWaitableEvent[] =;
constexpr char kStoryBaseCondVar[] =;
constexpr char kStorySuffixOneThread[] =;
constexpr char kStorySuffixFourThreads[] =;

#if BUILDFLAG(IS_POSIX)
constexpr char kStoryBasePthreadCondVar[] =;
#endif  // BUILDFLAG(IS_POSIX)

perf_test::PerfResultReporter SetUpReporter(const std::string& story_name) {}

// Base class for a threading perf-test. This sets up some threads for the
// test and measures the clock-time in addition to time spent on each thread.
class ThreadPerfTest : public testing::Test {};

// Class to test task performance by posting empty tasks back and forth.
class TaskPerfTest : public ThreadPerfTest {};

// This tries to test the 'best-case' as well as the 'worst-case' task posting
// performance. The best-case keeps one thread alive such that it never yeilds,
// while the worse-case forces a context switch for every task. Four threads are
// used to ensure the threads do yeild (with just two it might be possible for
// both threads to stay awake if they can signal each other fast enough).
TEST_F(TaskPerfTest, TaskPingPong) {}


// Same as above, but add observers to test their perf impact.
class MessageLoopObserver : public base::TaskObserver {};
MessageLoopObserver message_loop_observer;

class TaskObserverPerfTest : public TaskPerfTest {};

TEST_F(TaskObserverPerfTest, TaskPingPong) {}

// Class to test our WaitableEvent performance by signaling back and fort.
// WaitableEvent is templated so we can also compare with other versions.
template <typename WaitableEventType>
class EventPerfTest : public ThreadPerfTest {};

// Similar to the task posting test, this just tests similar functionality
// using WaitableEvents. We only test four threads (worst-case), but we
// might want to craft a way to test the best-case (where the thread doesn't
// end up blocking because the event is already signalled).
WaitableEventThreadPerfTest;
TEST_F(WaitableEventThreadPerfTest, EventPingPong) {}

// Build a minimal event using ConditionVariable.
class ConditionVariableEvent {};

// This is meant to test the absolute minimal context switching time
// using our own base synchronization code.
ConditionVariablePerfTest;
TEST_F(ConditionVariablePerfTest, EventPingPong) {}
#if BUILDFLAG(IS_POSIX)

// Absolutely 100% minimal posix waitable event. If there is a better/faster
// way to force a context switch, we should use that instead.
class PthreadEvent {};

// This is meant to test the absolute minimal context switching time.
// If there is any faster way to do this we should substitute it in.
PthreadEventPerfTest;
TEST_F(PthreadEventPerfTest, EventPingPong) {}

#endif

}  // namespace

}  // namespace base