Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2017 The Chromium Authors. All rights reserved. | 1 // Copyright 2017 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #if !defined(ADDRESS_SANITIZER) | |
|
Primiano Tucci (use gerrit)
2017/05/15 03:48:09
any reason why we are not using the MAYBE_ pattern
erikchen
2017/05/15 17:29:15
I wrapped the only relevant call in a "!defined(AD
| |
| 6 | |
| 5 #include "chrome/browser/metrics/process_memory_metrics_emitter.h" | 7 #include "chrome/browser/metrics/process_memory_metrics_emitter.h" |
| 6 | 8 |
| 9 #include "base/memory/ref_counted.h" | |
| 7 #include "base/message_loop/message_loop.h" | 10 #include "base/message_loop/message_loop.h" |
| 11 #include "base/test/histogram_tester.h" | |
| 12 #include "base/trace_event/memory_dump_manager.h" | |
| 13 #include "base/trace_event/trace_config_memory_test_util.h" | |
| 8 #include "chrome/test/base/in_process_browser_test.h" | 14 #include "chrome/test/base/in_process_browser_test.h" |
| 15 #include "chrome/test/base/tracing.h" | |
| 16 #include "chrome/test/base/ui_test_utils.h" | |
| 9 #include "content/public/test/test_utils.h" | 17 #include "content/public/test/test_utils.h" |
| 18 #include "url/gurl.h" | |
| 10 | 19 |
| 11 namespace { | 20 namespace { |
| 12 | 21 |
| 22 using base::trace_event::MemoryDumpType; | |
| 23 | |
| 24 void RequestGlobalDumpCallback(base::Closure quit_closure, | |
| 25 uint64_t, | |
| 26 bool success) { | |
| 27 base::ThreadTaskRunnerHandle::Get()->PostTask(FROM_HERE, quit_closure); | |
| 28 ASSERT_TRUE(success); | |
| 29 } | |
| 30 | |
| 31 void OnStartTracingDoneCallback( | |
| 32 base::trace_event::MemoryDumpLevelOfDetail explicit_dump_type, | |
| 33 base::Closure quit_closure) { | |
| 34 base::trace_event::MemoryDumpManager::GetInstance()->RequestGlobalDump( | |
| 35 MemoryDumpType::EXPLICITLY_TRIGGERED, explicit_dump_type, | |
| 36 Bind(&RequestGlobalDumpCallback, quit_closure)); | |
| 37 } | |
| 38 | |
| 13 class ProcessMemoryMetricsEmitterFake : public ProcessMemoryMetricsEmitter { | 39 class ProcessMemoryMetricsEmitterFake : public ProcessMemoryMetricsEmitter { |
| 14 public: | 40 public: |
| 15 ProcessMemoryMetricsEmitterFake() {} | 41 explicit ProcessMemoryMetricsEmitterFake(base::RunLoop* run_loop) |
| 42 : run_loop_(run_loop) {} | |
| 16 | 43 |
| 17 private: | 44 private: |
| 18 ~ProcessMemoryMetricsEmitterFake() override {} | 45 ~ProcessMemoryMetricsEmitterFake() override {} |
| 19 | 46 |
| 20 void ReceivedMemoryDump( | 47 void ReceivedMemoryDump( |
| 21 uint64_t dump_guid, | 48 uint64_t dump_guid, |
| 22 bool success, | 49 bool success, |
| 23 memory_instrumentation::mojom::GlobalMemoryDumpPtr ptr) override { | 50 memory_instrumentation::mojom::GlobalMemoryDumpPtr ptr) override { |
| 24 EXPECT_TRUE(success); | 51 EXPECT_TRUE(success); |
| 25 base::MessageLoop::current()->QuitWhenIdle(); | 52 ProcessMemoryMetricsEmitter::ReceivedMemoryDump(dump_guid, success, |
| 53 std::move(ptr)); | |
| 54 if (run_loop_) | |
| 55 run_loop_->Quit(); | |
| 26 } | 56 } |
| 27 | 57 |
| 58 base::RunLoop* run_loop_; | |
| 59 | |
| 28 DISALLOW_COPY_AND_ASSIGN(ProcessMemoryMetricsEmitterFake); | 60 DISALLOW_COPY_AND_ASSIGN(ProcessMemoryMetricsEmitterFake); |
| 29 }; | 61 }; |
| 30 | 62 |
| 63 void CheckMemoryMetric(const std::string& name, | |
| 64 const base::HistogramTester& histogram_tester, | |
| 65 int count) { | |
| 66 histogram_tester.ExpectTotalCount(name, count); | |
| 67 std::unique_ptr<base::HistogramSamples> samples( | |
| 68 histogram_tester.GetHistogramSamplesSinceCreation(name)); | |
| 69 ASSERT_TRUE(samples); | |
| 70 EXPECT_GT(samples->sum(), 0u) << name; | |
| 71 | |
| 72 // As a sanity check, no memory stat should exceed 1 GB. | |
| 73 int64_t maximum_expected_size = 1ll << 30; | |
| 74 EXPECT_LT(samples->sum(), maximum_expected_size) << name; | |
| 75 } | |
| 76 | |
| 77 void CheckAllMemoryMetrics(const base::HistogramTester& histogram_tester, | |
| 78 int count) { | |
| 79 CheckMemoryMetric("Memory.Experimental.Browser2.Malloc", histogram_tester, | |
| 80 count); | |
| 81 CheckMemoryMetric("Memory.Experimental.Browser2.Resident", histogram_tester, | |
| 82 count); | |
| 83 CheckMemoryMetric("Memory.Experimental.Renderer2.Malloc", histogram_tester, | |
| 84 count); | |
| 85 CheckMemoryMetric("Memory.Experimental.Renderer2.Resident", histogram_tester, | |
| 86 count); | |
| 87 CheckMemoryMetric("Memory.Experimental.Renderer2.BlinkGC", histogram_tester, | |
| 88 count); | |
| 89 CheckMemoryMetric("Memory.Experimental.Renderer2.V8", histogram_tester, | |
| 90 count); | |
| 91 } | |
| 92 | |
| 31 } // namespace | 93 } // namespace |
| 32 | 94 |
| 33 class ProcessMemoryMetricsEmitterTest : public InProcessBrowserTest { | 95 class ProcessMemoryMetricsEmitterTest : public InProcessBrowserTest { |
| 34 public: | 96 public: |
| 35 ProcessMemoryMetricsEmitterTest() {} | 97 ProcessMemoryMetricsEmitterTest() {} |
| 36 ~ProcessMemoryMetricsEmitterTest() override {} | 98 ~ProcessMemoryMetricsEmitterTest() override {} |
| 37 | 99 |
| 38 private: | 100 private: |
| 39 DISALLOW_COPY_AND_ASSIGN(ProcessMemoryMetricsEmitterTest); | 101 DISALLOW_COPY_AND_ASSIGN(ProcessMemoryMetricsEmitterTest); |
| 40 }; | 102 }; |
| 41 | 103 |
| 42 IN_PROC_BROWSER_TEST_F(ProcessMemoryMetricsEmitterTest, FetchAndEmitMetrics) { | 104 IN_PROC_BROWSER_TEST_F(ProcessMemoryMetricsEmitterTest, FetchAndEmitMetrics) { |
| 105 base::HistogramTester histogram_tester; | |
| 106 base::RunLoop run_loop; | |
| 107 | |
| 43 // Intentionally let emitter leave scope to check that it correctly keeps | 108 // Intentionally let emitter leave scope to check that it correctly keeps |
| 44 // itself alive. | 109 // itself alive. |
| 45 { | 110 { |
| 46 scoped_refptr<ProcessMemoryMetricsEmitterFake> emitter( | 111 scoped_refptr<ProcessMemoryMetricsEmitterFake> emitter( |
| 47 new ProcessMemoryMetricsEmitterFake); | 112 new ProcessMemoryMetricsEmitterFake(&run_loop)); |
| 48 emitter->FetchAndEmitProcessMemoryMetrics(); | 113 emitter->FetchAndEmitProcessMemoryMetrics(); |
| 49 } | 114 } |
| 50 | 115 |
| 51 content::RunMessageLoop(); | 116 run_loop.Run(); |
| 117 | |
| 118 CheckAllMemoryMetrics(histogram_tester, 1); | |
| 52 } | 119 } |
| 120 | |
| 121 IN_PROC_BROWSER_TEST_F(ProcessMemoryMetricsEmitterTest, FetchDuringTrace) { | |
| 122 base::HistogramTester histogram_tester; | |
| 123 base::RunLoop run_loop; | |
| 124 | |
| 125 base::trace_event::TraceConfig trace_config( | |
| 126 base::trace_event::TraceConfigMemoryTestUtil:: | |
| 127 GetTraceConfig_EmptyTriggers()); | |
| 128 ASSERT_TRUE(tracing::BeginTracingWithTraceConfig( | |
| 129 trace_config, Bind(&OnStartTracingDoneCallback, | |
| 130 base::trace_event::MemoryDumpLevelOfDetail::DETAILED, | |
| 131 run_loop.QuitClosure()))); | |
| 132 | |
| 133 // Intentionally let emitter leave scope to check that it correctly keeps | |
| 134 // itself alive. | |
| 135 { | |
| 136 scoped_refptr<ProcessMemoryMetricsEmitterFake> emitter( | |
| 137 new ProcessMemoryMetricsEmitterFake(&run_loop)); | |
| 138 emitter->FetchAndEmitProcessMemoryMetrics(); | |
| 139 } | |
| 140 | |
| 141 GURL url1("about:blank"); | |
| 142 ui_test_utils::NavigateToURLWithDisposition( | |
| 143 browser(), url1, WindowOpenDisposition::NEW_FOREGROUND_TAB, | |
| 144 ui_test_utils::BROWSER_TEST_WAIT_FOR_NAVIGATION); | |
| 145 run_loop.Run(); | |
| 146 | |
| 147 std::string json_events; | |
| 148 ASSERT_TRUE(tracing::EndTracing(&json_events)); | |
| 149 EXPECT_NE(0u, json_events.length()); | |
|
Primiano Tucci (use gerrit)
2017/05/15 03:48:09
this one won't guarantee that the dump is in the t
erikchen
2017/05/15 17:29:15
Done.
| |
| 150 | |
| 151 CheckAllMemoryMetrics(histogram_tester, 1); | |
| 152 } | |
| 153 | |
| 154 IN_PROC_BROWSER_TEST_F(ProcessMemoryMetricsEmitterTest, FetchThreeTimes) { | |
| 155 base::HistogramTester histogram_tester; | |
| 156 base::RunLoop run_loop; | |
| 157 | |
| 158 int count = 3; | |
| 159 for (int i = 0; i < count; ++i) { | |
| 160 // Only the last emitter should stop the run loop. | |
| 161 auto emitter = base::MakeShared<ProcessMemoryMetricsEmitterFake>( | |
| 162 (i == count - 1) ? &run_loop : nullptr); | |
| 163 emitter->FetchAndEmitProcessMemoryMetrics(); | |
| 164 } | |
| 165 | |
| 166 run_loop.Run(); | |
| 167 | |
| 168 CheckAllMemoryMetrics(histogram_tester, count); | |
| 169 } | |
| 170 #endif // !defined(ADDRESS_SANITIZER) | |
| OLD | NEW |