| OLD | NEW |
| 1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 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 #include "base/trace_event/heap_profiler_stack_frame_deduplicator.h" |
| 6 |
| 5 #include <iterator> | 7 #include <iterator> |
| 8 #include <memory> |
| 6 | 9 |
| 7 #include "base/macros.h" | 10 #include "base/macros.h" |
| 8 #include "base/memory/scoped_ptr.h" | |
| 9 #include "base/trace_event/heap_profiler_allocation_context.h" | 11 #include "base/trace_event/heap_profiler_allocation_context.h" |
| 10 #include "base/trace_event/heap_profiler_stack_frame_deduplicator.h" | |
| 11 #include "testing/gtest/include/gtest/gtest.h" | 12 #include "testing/gtest/include/gtest/gtest.h" |
| 12 | 13 |
| 13 namespace base { | 14 namespace base { |
| 14 namespace trace_event { | 15 namespace trace_event { |
| 15 | 16 |
| 16 // Define all strings once, because the deduplicator requires pointer equality, | 17 // Define all strings once, because the deduplicator requires pointer equality, |
| 17 // and string interning is unreliable. | 18 // and string interning is unreliable. |
| 18 const char kBrowserMain[] = "BrowserMain"; | 19 const char kBrowserMain[] = "BrowserMain"; |
| 19 const char kRendererMain[] = "RendererMain"; | 20 const char kRendererMain[] = "RendererMain"; |
| 20 const char kCreateWidget[] = "CreateWidget"; | 21 const char kCreateWidget[] = "CreateWidget"; |
| 21 const char kInitialize[] = "Initialize"; | 22 const char kInitialize[] = "Initialize"; |
| 22 const char kMalloc[] = "malloc"; | 23 const char kMalloc[] = "malloc"; |
| 23 | 24 |
| 24 TEST(StackFrameDeduplicatorTest, SingleBacktrace) { | 25 TEST(StackFrameDeduplicatorTest, SingleBacktrace) { |
| 25 StackFrame bt[] = {kBrowserMain, kCreateWidget, kMalloc}; | 26 StackFrame bt[] = {kBrowserMain, kCreateWidget, kMalloc}; |
| 26 | 27 |
| 27 // The call tree should look like this (index in brackets). | 28 // The call tree should look like this (index in brackets). |
| 28 // | 29 // |
| 29 // BrowserMain [0] | 30 // BrowserMain [0] |
| 30 // CreateWidget [1] | 31 // CreateWidget [1] |
| 31 // malloc [2] | 32 // malloc [2] |
| 32 | 33 |
| 33 scoped_ptr<StackFrameDeduplicator> dedup(new StackFrameDeduplicator); | 34 std::unique_ptr<StackFrameDeduplicator> dedup(new StackFrameDeduplicator); |
| 34 ASSERT_EQ(2, dedup->Insert(std::begin(bt), std::end(bt))); | 35 ASSERT_EQ(2, dedup->Insert(std::begin(bt), std::end(bt))); |
| 35 | 36 |
| 36 auto iter = dedup->begin(); | 37 auto iter = dedup->begin(); |
| 37 ASSERT_EQ(kBrowserMain, (iter + 0)->frame); | 38 ASSERT_EQ(kBrowserMain, (iter + 0)->frame); |
| 38 ASSERT_EQ(-1, (iter + 0)->parent_frame_index); | 39 ASSERT_EQ(-1, (iter + 0)->parent_frame_index); |
| 39 | 40 |
| 40 ASSERT_EQ(kCreateWidget, (iter + 1)->frame); | 41 ASSERT_EQ(kCreateWidget, (iter + 1)->frame); |
| 41 ASSERT_EQ(0, (iter + 1)->parent_frame_index); | 42 ASSERT_EQ(0, (iter + 1)->parent_frame_index); |
| 42 | 43 |
| 43 ASSERT_EQ(kMalloc, (iter + 2)->frame); | 44 ASSERT_EQ(kMalloc, (iter + 2)->frame); |
| (...skipping 12 matching lines...) Expand all Loading... |
| 56 // The call tree should look like this (index in brackets). | 57 // The call tree should look like this (index in brackets). |
| 57 // | 58 // |
| 58 // BrowserMain [0] | 59 // BrowserMain [0] |
| 59 // CreateWidget [1] | 60 // CreateWidget [1] |
| 60 // RendererMain [2] | 61 // RendererMain [2] |
| 61 // CreateWidget [3] | 62 // CreateWidget [3] |
| 62 // | 63 // |
| 63 // Note that there will be two instances of CreateWidget, | 64 // Note that there will be two instances of CreateWidget, |
| 64 // with different parents. | 65 // with different parents. |
| 65 | 66 |
| 66 scoped_ptr<StackFrameDeduplicator> dedup(new StackFrameDeduplicator); | 67 std::unique_ptr<StackFrameDeduplicator> dedup(new StackFrameDeduplicator); |
| 67 ASSERT_EQ(1, dedup->Insert(std::begin(bt0), std::end(bt0))); | 68 ASSERT_EQ(1, dedup->Insert(std::begin(bt0), std::end(bt0))); |
| 68 ASSERT_EQ(3, dedup->Insert(std::begin(bt1), std::end(bt1))); | 69 ASSERT_EQ(3, dedup->Insert(std::begin(bt1), std::end(bt1))); |
| 69 | 70 |
| 70 auto iter = dedup->begin(); | 71 auto iter = dedup->begin(); |
| 71 ASSERT_EQ(kBrowserMain, (iter + 0)->frame); | 72 ASSERT_EQ(kBrowserMain, (iter + 0)->frame); |
| 72 ASSERT_EQ(-1, (iter + 0)->parent_frame_index); | 73 ASSERT_EQ(-1, (iter + 0)->parent_frame_index); |
| 73 | 74 |
| 74 ASSERT_EQ(kCreateWidget, (iter + 1)->frame); | 75 ASSERT_EQ(kCreateWidget, (iter + 1)->frame); |
| 75 ASSERT_EQ(0, (iter + 1)->parent_frame_index); | 76 ASSERT_EQ(0, (iter + 1)->parent_frame_index); |
| 76 | 77 |
| (...skipping 11 matching lines...) Expand all Loading... |
| 88 StackFrame bt1[] = {kBrowserMain, kInitialize}; | 89 StackFrame bt1[] = {kBrowserMain, kInitialize}; |
| 89 | 90 |
| 90 // The call tree should look like this (index in brackets). | 91 // The call tree should look like this (index in brackets). |
| 91 // | 92 // |
| 92 // BrowserMain [0] | 93 // BrowserMain [0] |
| 93 // CreateWidget [1] | 94 // CreateWidget [1] |
| 94 // Initialize [2] | 95 // Initialize [2] |
| 95 // | 96 // |
| 96 // Note that BrowserMain will be re-used. | 97 // Note that BrowserMain will be re-used. |
| 97 | 98 |
| 98 scoped_ptr<StackFrameDeduplicator> dedup(new StackFrameDeduplicator); | 99 std::unique_ptr<StackFrameDeduplicator> dedup(new StackFrameDeduplicator); |
| 99 ASSERT_EQ(1, dedup->Insert(std::begin(bt0), std::end(bt0))); | 100 ASSERT_EQ(1, dedup->Insert(std::begin(bt0), std::end(bt0))); |
| 100 ASSERT_EQ(2, dedup->Insert(std::begin(bt1), std::end(bt1))); | 101 ASSERT_EQ(2, dedup->Insert(std::begin(bt1), std::end(bt1))); |
| 101 | 102 |
| 102 auto iter = dedup->begin(); | 103 auto iter = dedup->begin(); |
| 103 ASSERT_EQ(kBrowserMain, (iter + 0)->frame); | 104 ASSERT_EQ(kBrowserMain, (iter + 0)->frame); |
| 104 ASSERT_EQ(-1, (iter + 0)->parent_frame_index); | 105 ASSERT_EQ(-1, (iter + 0)->parent_frame_index); |
| 105 | 106 |
| 106 ASSERT_EQ(kCreateWidget, (iter + 1)->frame); | 107 ASSERT_EQ(kCreateWidget, (iter + 1)->frame); |
| 107 ASSERT_EQ(0, (iter + 1)->parent_frame_index); | 108 ASSERT_EQ(0, (iter + 1)->parent_frame_index); |
| 108 | 109 |
| 109 ASSERT_EQ(kInitialize, (iter + 2)->frame); | 110 ASSERT_EQ(kInitialize, (iter + 2)->frame); |
| 110 ASSERT_EQ(0, (iter + 2)->parent_frame_index); | 111 ASSERT_EQ(0, (iter + 2)->parent_frame_index); |
| 111 | 112 |
| 112 ASSERT_EQ(iter + 3, dedup->end()); | 113 ASSERT_EQ(iter + 3, dedup->end()); |
| 113 | 114 |
| 114 // Inserting the same backtrace again should return the index of the existing | 115 // Inserting the same backtrace again should return the index of the existing |
| 115 // node. | 116 // node. |
| 116 ASSERT_EQ(1, dedup->Insert(std::begin(bt0), std::end(bt0))); | 117 ASSERT_EQ(1, dedup->Insert(std::begin(bt0), std::end(bt0))); |
| 117 ASSERT_EQ(2, dedup->Insert(std::begin(bt1), std::end(bt1))); | 118 ASSERT_EQ(2, dedup->Insert(std::begin(bt1), std::end(bt1))); |
| 118 ASSERT_EQ(dedup->begin() + 3, dedup->end()); | 119 ASSERT_EQ(dedup->begin() + 3, dedup->end()); |
| 119 } | 120 } |
| 120 | 121 |
| 121 TEST(StackFrameDeduplicatorTest, NullPaddingIsRemoved) { | 122 TEST(StackFrameDeduplicatorTest, NullPaddingIsRemoved) { |
| 122 StackFrame bt0[] = {kBrowserMain, nullptr, nullptr, nullptr}; | 123 StackFrame bt0[] = {kBrowserMain, nullptr, nullptr, nullptr}; |
| 123 | 124 |
| 124 scoped_ptr<StackFrameDeduplicator> dedup(new StackFrameDeduplicator); | 125 std::unique_ptr<StackFrameDeduplicator> dedup(new StackFrameDeduplicator); |
| 125 | 126 |
| 126 // There are four frames in the backtrace, but the null pointers should be | 127 // There are four frames in the backtrace, but the null pointers should be |
| 127 // skipped, so only one frame is inserted, which will have index 0. | 128 // skipped, so only one frame is inserted, which will have index 0. |
| 128 ASSERT_EQ(4u, arraysize(bt0)); | 129 ASSERT_EQ(4u, arraysize(bt0)); |
| 129 ASSERT_EQ(0, dedup->Insert(std::begin(bt0), std::end(bt0))); | 130 ASSERT_EQ(0, dedup->Insert(std::begin(bt0), std::end(bt0))); |
| 130 ASSERT_EQ(dedup->begin() + 1, dedup->end()); | 131 ASSERT_EQ(dedup->begin() + 1, dedup->end()); |
| 131 } | 132 } |
| 132 | 133 |
| 133 } // namespace trace_event | 134 } // namespace trace_event |
| 134 } // namespace base | 135 } // namespace base |
| OLD | NEW |