Make testing traces easier

We would like to add unit tests to make sure important trace events, that are
used in benchmarks, like the ones recently introduced in crrev/c/861389, are not
accidentally deleted.

This patch cleans up existing similar unit tests and makes writing new tests
easier.

TBR=oysteine@chromium.org,jam@chromium.org,hjd@chromium.org,skyostil@chromium.org,tdresser@chromium.org

BUG=none

Change-Id: Ieda04b3e5470b1b31b4140c2c9a6c51ea6e56202
Reviewed-on: https://chromium-review.googlesource.com/919144
Commit-Queue: Ehsan Chiniforooshan <chiniforooshan@chromium.org>
Reviewed-by: Ehsan Chiniforooshan <chiniforooshan@chromium.org>
Reviewed-by: Timothy Dresser <tdresser@chromium.org>
Reviewed-by: danakj <danakj@chromium.org>
Cr-Commit-Position: refs/heads/master@{#536814}

CrOS-Libchrome-Original-Commit: b53a9c2f3acb0405b1b26f15fca5d059e8fd98ce
diff --git a/base/test/trace_event_analyzer.cc b/base/test/trace_event_analyzer.cc
index 5d6d081..a822aee 100644
--- a/base/test/trace_event_analyzer.cc
+++ b/base/test/trace_event_analyzer.cc
@@ -7,13 +7,29 @@
 #include <math.h>
 
 #include <algorithm>
-#include <memory>
 #include <set>
 
 #include "base/json/json_reader.h"
+#include "base/memory/ptr_util.h"
+#include "base/memory/ref_counted_memory.h"
+#include "base/run_loop.h"
 #include "base/strings/pattern.h"
+#include "base/trace_event/trace_buffer.h"
+#include "base/trace_event/trace_config.h"
+#include "base/trace_event/trace_log.h"
 #include "base/values.h"
 
+namespace {
+void OnTraceDataCollected(base::OnceClosure quit_closure,
+                          base::trace_event::TraceResultBuffer* buffer,
+                          const scoped_refptr<base::RefCountedString>& json,
+                          bool has_more_events) {
+  buffer->AddFragment(json->data());
+  if (!has_more_events)
+    std::move(quit_closure).Run();
+}
+}  // namespace
+
 namespace trace_analyzer {
 
 // TraceEvent
@@ -874,6 +890,34 @@
   }
 }
 
+// Utility functions for collecting process-local traces and creating a
+// |TraceAnalyzer| from the result.
+
+void Start(const std::string& category_filter_string) {
+  DCHECK(!base::trace_event::TraceLog::GetInstance()->IsEnabled());
+  base::trace_event::TraceLog::GetInstance()->SetEnabled(
+      base::trace_event::TraceConfig(category_filter_string, ""),
+      base::trace_event::TraceLog::RECORDING_MODE);
+}
+
+std::unique_ptr<TraceAnalyzer> Stop() {
+  DCHECK(base::trace_event::TraceLog::GetInstance()->IsEnabled());
+  base::trace_event::TraceLog::GetInstance()->SetDisabled();
+
+  base::trace_event::TraceResultBuffer buffer;
+  base::trace_event::TraceResultBuffer::SimpleOutput trace_output;
+  buffer.SetOutputCallback(trace_output.GetCallback());
+  base::RunLoop run_loop;
+  buffer.Start();
+  base::trace_event::TraceLog::GetInstance()->Flush(
+      base::BindRepeating(&OnTraceDataCollected, run_loop.QuitClosure(),
+                          base::Unretained(&buffer)));
+  run_loop.Run();
+  buffer.Finish();
+
+  return base::WrapUnique(TraceAnalyzer::Create(trace_output.json_output));
+}
+
 // TraceEventVector utility functions.
 
 bool GetRateStats(const TraceEventVector& events,
diff --git a/base/test/trace_event_analyzer.h b/base/test/trace_event_analyzer.h
index 4e1d09d..ea716bc 100644
--- a/base/test/trace_event_analyzer.h
+++ b/base/test/trace_event_analyzer.h
@@ -71,7 +71,21 @@
 //     EXPECT_TRUE(events[i].GetAbsTimeToOtherEvent(&duration));
 //     EXPECT_LT(duration, 1000000.0/60.0); // expect less than 1/60 second.
 //   }
-
+//
+// There are two helper functions, Start(category_filter_string) and Stop(), for
+// facilitating the collection of process-local traces and building a
+// TraceAnalyzer from them. A typical test, that uses the helper functions,
+// looks like the following:
+//
+// TEST_F(...) {
+//   Start("*");
+//   [Invoke the functions you want to test their traces]
+//   auto analyzer = Stop();
+//
+//   [Use the analyzer to verify produced traces, as explained above]
+// }
+//
+// Note: The Stop() function needs a SingleThreadTaskRunner.
 
 #ifndef BASE_TEST_TRACE_EVENT_ANALYZER_H_
 #define BASE_TEST_TRACE_EVENT_ANALYZER_H_
@@ -80,6 +94,9 @@
 #include <stdint.h>
 
 #include <map>
+#include <memory>
+#include <string>
+#include <vector>
 
 #include "base/macros.h"
 #include "base/memory/ref_counted.h"
@@ -743,6 +760,13 @@
   DISALLOW_COPY_AND_ASSIGN(TraceAnalyzer);
 };
 
+// Utility functions for collecting process-local traces and creating a
+// |TraceAnalyzer| from the result. Please see comments in trace_config.h to
+// understand how the |category_filter_string| works. Use "*" to enable all
+// default categories.
+void Start(const std::string& category_filter_string);
+std::unique_ptr<TraceAnalyzer> Stop();
+
 // Utility functions for TraceEventVector.
 
 struct RateStats {
diff --git a/base/trace_event/blame_context_unittest.cc b/base/trace_event/blame_context_unittest.cc
index bd999aa..12e7857 100644
--- a/base/trace_event/blame_context_unittest.cc
+++ b/base/trace_event/blame_context_unittest.cc
@@ -5,12 +5,8 @@
 #include "base/trace_event/blame_context.h"
 
 #include "base/json/json_writer.h"
-#include "base/memory/ptr_util.h"
-#include "base/memory/ref_counted_memory.h"
 #include "base/message_loop/message_loop.h"
-#include "base/run_loop.h"
 #include "base/test/trace_event_analyzer.h"
-#include "base/trace_event/trace_buffer.h"
 #include "base/trace_event/trace_event_argument.h"
 #include "testing/gtest/include/gtest/gtest.h"
 
@@ -60,61 +56,21 @@
                      nullptr) {}
 };
 
-void OnTraceDataCollected(Closure quit_closure,
-                          trace_event::TraceResultBuffer* buffer,
-                          const scoped_refptr<RefCountedString>& json,
-                          bool has_more_events) {
-  buffer->AddFragment(json->data());
-  if (!has_more_events)
-    quit_closure.Run();
-}
-
 class BlameContextTest : public testing::Test {
- public:
-  void StartTracing();
-  void StopTracing();
-  std::unique_ptr<trace_analyzer::TraceAnalyzer> CreateTraceAnalyzer();
  protected:
   MessageLoop loop_;
 };
 
-void BlameContextTest::StartTracing() {
-  trace_event::TraceLog::GetInstance()->SetEnabled(
-      trace_event::TraceConfig("*"), trace_event::TraceLog::RECORDING_MODE);
-}
-
-void BlameContextTest::StopTracing() {
-  trace_event::TraceLog::GetInstance()->SetDisabled();
-}
-
-std::unique_ptr<trace_analyzer::TraceAnalyzer>
-BlameContextTest::CreateTraceAnalyzer() {
-  trace_event::TraceResultBuffer buffer;
-  trace_event::TraceResultBuffer::SimpleOutput trace_output;
-  buffer.SetOutputCallback(trace_output.GetCallback());
-  RunLoop run_loop;
-  buffer.Start();
-  trace_event::TraceLog::GetInstance()->Flush(
-      Bind(&OnTraceDataCollected, run_loop.QuitClosure(), Unretained(&buffer)));
-  run_loop.Run();
-  buffer.Finish();
-
-  return WrapUnique(
-      trace_analyzer::TraceAnalyzer::Create(trace_output.json_output));
-}
-
 TEST_F(BlameContextTest, EnterAndLeave) {
   using trace_analyzer::Query;
-  StartTracing();
+  trace_analyzer::Start("*");
   {
     TestBlameContext blame_context(0x1234);
     blame_context.Initialize();
     blame_context.Enter();
     blame_context.Leave();
   }
-  StopTracing();
-  std::unique_ptr<trace_analyzer::TraceAnalyzer> analyzer =
-      CreateTraceAnalyzer();
+  auto analyzer = trace_analyzer::Stop();
 
   trace_analyzer::TraceEventVector events;
   Query q = Query::EventPhaseIs(TRACE_EVENT_PHASE_ENTER_CONTEXT) ||
@@ -136,7 +92,7 @@
   // Ensure there is no cross talk between blame contexts from different
   // categories.
   using trace_analyzer::Query;
-  StartTracing();
+  trace_analyzer::Start("*");
   {
     TestBlameContext blame_context(0x1234);
     DisabledTestBlameContext disabled_blame_context(0x5678);
@@ -147,9 +103,7 @@
     disabled_blame_context.Enter();
     disabled_blame_context.Leave();
   }
-  StopTracing();
-  std::unique_ptr<trace_analyzer::TraceAnalyzer> analyzer =
-      CreateTraceAnalyzer();
+  auto analyzer = trace_analyzer::Stop();
 
   trace_analyzer::TraceEventVector events;
   Query q = Query::EventPhaseIs(TRACE_EVENT_PHASE_ENTER_CONTEXT) ||
@@ -170,7 +124,7 @@
 
 TEST_F(BlameContextTest, TakeSnapshot) {
   using trace_analyzer::Query;
-  StartTracing();
+  trace_analyzer::Start("*");
   {
     TestBlameContext parent_blame_context(0x5678);
     TestBlameContext blame_context(0x1234, parent_blame_context);
@@ -178,9 +132,7 @@
     blame_context.Initialize();
     blame_context.TakeSnapshot();
   }
-  StopTracing();
-  std::unique_ptr<trace_analyzer::TraceAnalyzer> analyzer =
-      CreateTraceAnalyzer();
+  auto analyzer = trace_analyzer::Stop();
 
   trace_analyzer::TraceEventVector events;
   Query q = Query::EventPhaseIs(TRACE_EVENT_PHASE_SNAPSHOT_OBJECT);