Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 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 // Test of classes in the tracked_objects.h classes. | 5 // Test of classes in the tracked_objects.h classes. |
| 6 | 6 |
| 7 #include "base/tracked_objects.h" | 7 #include "base/tracked_objects.h" |
| 8 | 8 |
| 9 #include "base/json/json_writer.h" | 9 #include "base/json/json_writer.h" |
| 10 #include "base/memory/scoped_ptr.h" | 10 #include "base/memory/scoped_ptr.h" |
| (...skipping 27 matching lines...) Expand all Loading... | |
| 38 if (!ThreadData::InitializeAndSetTrackingStatus(true)) | 38 if (!ThreadData::InitializeAndSetTrackingStatus(true)) |
| 39 return; | 39 return; |
| 40 | 40 |
| 41 EXPECT_FALSE(ThreadData::first()); // No activity even on this thread. | 41 EXPECT_FALSE(ThreadData::first()); // No activity even on this thread. |
| 42 ThreadData* data = ThreadData::Get(); | 42 ThreadData* data = ThreadData::Get(); |
| 43 EXPECT_TRUE(ThreadData::first()); // Now class was constructed. | 43 EXPECT_TRUE(ThreadData::first()); // Now class was constructed. |
| 44 EXPECT_TRUE(data); | 44 EXPECT_TRUE(data); |
| 45 EXPECT_TRUE(!data->next()); | 45 EXPECT_TRUE(!data->next()); |
| 46 EXPECT_EQ(data, ThreadData::Get()); | 46 EXPECT_EQ(data, ThreadData::Get()); |
| 47 ThreadData::BirthMap birth_map; | 47 ThreadData::BirthMap birth_map; |
| 48 data->SnapshotBirthMap(&birth_map); | 48 ThreadData::DeathMap death_map; |
| 49 data->SnapshotMaps(false, &birth_map, &death_map); | |
| 49 EXPECT_EQ(0u, birth_map.size()); | 50 EXPECT_EQ(0u, birth_map.size()); |
| 50 ThreadData::DeathMap death_map; | |
| 51 data->SnapshotDeathMap(&death_map); | |
| 52 EXPECT_EQ(0u, death_map.size()); | 51 EXPECT_EQ(0u, death_map.size()); |
| 53 // Cleanup with no leaking. | 52 // Cleanup with no leaking. |
| 54 ShutdownSingleThreadedCleanup(false); | 53 ShutdownSingleThreadedCleanup(false); |
| 55 | 54 |
| 56 // Do it again, just to be sure we reset state completely. | 55 // Do it again, just to be sure we reset state completely. |
| 57 ThreadData::InitializeAndSetTrackingStatus(true); | 56 ThreadData::InitializeAndSetTrackingStatus(true); |
| 58 EXPECT_FALSE(ThreadData::first()); // No activity even on this thread. | 57 EXPECT_FALSE(ThreadData::first()); // No activity even on this thread. |
| 59 data = ThreadData::Get(); | 58 data = ThreadData::Get(); |
| 60 EXPECT_TRUE(ThreadData::first()); // Now class was constructed. | 59 EXPECT_TRUE(ThreadData::first()); // Now class was constructed. |
| 61 EXPECT_TRUE(data); | 60 EXPECT_TRUE(data); |
| 62 EXPECT_TRUE(!data->next()); | 61 EXPECT_TRUE(!data->next()); |
| 63 EXPECT_EQ(data, ThreadData::Get()); | 62 EXPECT_EQ(data, ThreadData::Get()); |
| 64 birth_map.clear(); | 63 birth_map.clear(); |
| 65 data->SnapshotBirthMap(&birth_map); | 64 death_map.clear(); |
| 65 data->SnapshotMaps(false, &birth_map, &death_map); | |
| 66 EXPECT_EQ(0u, birth_map.size()); | 66 EXPECT_EQ(0u, birth_map.size()); |
| 67 death_map.clear(); | |
| 68 data->SnapshotDeathMap(&death_map); | |
| 69 EXPECT_EQ(0u, death_map.size()); | 67 EXPECT_EQ(0u, death_map.size()); |
| 70 } | 68 } |
| 71 | 69 |
| 72 TEST_F(TrackedObjectsTest, TinyStartupShutdown) { | 70 TEST_F(TrackedObjectsTest, TinyStartupShutdown) { |
| 73 if (!ThreadData::InitializeAndSetTrackingStatus(true)) | 71 if (!ThreadData::InitializeAndSetTrackingStatus(true)) |
| 74 return; | 72 return; |
| 75 | 73 |
| 76 // Instigate tracking on a single tracked object, on our thread. | 74 // Instigate tracking on a single tracked object, on our thread. |
| 77 const Location& location = FROM_HERE; | 75 const Location& location = FROM_HERE; |
| 78 ThreadData::TallyABirthIfActive(location); | 76 ThreadData::TallyABirthIfActive(location); |
| 79 | 77 |
| 80 const ThreadData* data = ThreadData::first(); | 78 ThreadData* data = ThreadData::first(); |
| 81 ASSERT_TRUE(data); | 79 ASSERT_TRUE(data); |
| 82 EXPECT_TRUE(!data->next()); | 80 EXPECT_TRUE(!data->next()); |
| 83 EXPECT_EQ(data, ThreadData::Get()); | 81 EXPECT_EQ(data, ThreadData::Get()); |
| 84 ThreadData::BirthMap birth_map; | 82 ThreadData::BirthMap birth_map; |
| 85 data->SnapshotBirthMap(&birth_map); | 83 ThreadData::DeathMap death_map; |
| 84 data->SnapshotMaps(false, &birth_map, &death_map); | |
| 86 EXPECT_EQ(1u, birth_map.size()); // 1 birth location. | 85 EXPECT_EQ(1u, birth_map.size()); // 1 birth location. |
| 87 EXPECT_EQ(1, birth_map.begin()->second->birth_count()); // 1 birth. | 86 EXPECT_EQ(1, birth_map.begin()->second->birth_count()); // 1 birth. |
| 88 ThreadData::DeathMap death_map; | |
| 89 data->SnapshotDeathMap(&death_map); | |
| 90 EXPECT_EQ(0u, death_map.size()); // No deaths. | 87 EXPECT_EQ(0u, death_map.size()); // No deaths. |
| 91 | 88 |
| 92 | 89 |
| 93 // Now instigate another birth, and a first death at the same location. | 90 // Now instigate another birth, and a first death at the same location. |
| 94 // TrackingInfo will call TallyABirth() during construction. | 91 // TrackingInfo will call TallyABirth() during construction. |
| 95 base::TimeTicks kBogusStartTime; | 92 base::TimeTicks kBogusStartTime; |
| 96 base::TrackingInfo pending_task(location, kBogusStartTime); | 93 base::TrackingInfo pending_task(location, kBogusStartTime); |
| 97 TrackedTime kBogusStartRunTime; | 94 TrackedTime kBogusStartRunTime; |
| 98 TrackedTime kBogusEndRunTime; | 95 TrackedTime kBogusEndRunTime; |
| 99 ThreadData::TallyRunOnNamedThreadIfTracking(pending_task, kBogusStartRunTime, | 96 ThreadData::TallyRunOnNamedThreadIfTracking(pending_task, kBogusStartRunTime, |
| 100 kBogusEndRunTime); | 97 kBogusEndRunTime); |
| 101 | 98 |
| 102 birth_map.clear(); | 99 birth_map.clear(); |
| 103 data->SnapshotBirthMap(&birth_map); | 100 death_map.clear(); |
| 101 data->SnapshotMaps(false, &birth_map, &death_map); | |
| 104 EXPECT_EQ(1u, birth_map.size()); // 1 birth location. | 102 EXPECT_EQ(1u, birth_map.size()); // 1 birth location. |
| 105 EXPECT_EQ(2, birth_map.begin()->second->birth_count()); // 2 births. | 103 EXPECT_EQ(2, birth_map.begin()->second->birth_count()); // 2 births. |
| 106 death_map.clear(); | |
| 107 data->SnapshotDeathMap(&death_map); | |
| 108 EXPECT_EQ(1u, death_map.size()); // 1 location. | 104 EXPECT_EQ(1u, death_map.size()); // 1 location. |
| 109 EXPECT_EQ(1, death_map.begin()->second.count()); // 1 death. | 105 EXPECT_EQ(1, death_map.begin()->second.count()); // 1 death. |
| 110 | 106 |
| 111 // The births were at the same location as the one known death. | 107 // The births were at the same location as the one known death. |
| 112 EXPECT_EQ(birth_map.begin()->second, death_map.begin()->first); | 108 EXPECT_EQ(birth_map.begin()->second, death_map.begin()->first); |
| 113 } | 109 } |
| 114 | 110 |
| 115 TEST_F(TrackedObjectsTest, DeathDataTest) { | 111 TEST_F(TrackedObjectsTest, DeathDataTest) { |
| 116 if (!ThreadData::InitializeAndSetTrackingStatus(true)) | 112 if (!ThreadData::InitializeAndSetTrackingStatus(true)) |
| 117 return; | 113 return; |
| 118 | 114 |
| 119 scoped_ptr<DeathData> data(new DeathData()); | 115 scoped_ptr<DeathData> data(new DeathData()); |
| 120 ASSERT_NE(data, reinterpret_cast<DeathData*>(NULL)); | 116 ASSERT_NE(data, reinterpret_cast<DeathData*>(NULL)); |
| 121 EXPECT_EQ(data->run_duration(), 0); | 117 EXPECT_EQ(data->run_duration_sum(), 0); |
| 122 EXPECT_EQ(data->queue_duration(), 0); | 118 EXPECT_EQ(data->run_duration_sample(), 0); |
| 123 EXPECT_EQ(data->AverageMsRunDuration(), 0); | 119 EXPECT_EQ(data->queue_duration_sum(), 0); |
| 124 EXPECT_EQ(data->AverageMsQueueDuration(), 0); | 120 EXPECT_EQ(data->queue_duration_sample(), 0); |
| 125 EXPECT_EQ(data->count(), 0); | 121 EXPECT_EQ(data->count(), 0); |
| 126 | 122 |
| 127 DurationInt run_ms = 42; | 123 DurationInt run_ms = 42; |
| 128 DurationInt queue_ms = 8; | 124 DurationInt queue_ms = 8; |
| 129 | 125 |
| 130 data->RecordDeath(queue_ms, run_ms); | 126 const int kUnrandomInt = 0; // Fake random int that ensure we sample data. |
| 131 EXPECT_EQ(data->run_duration(), run_ms); | 127 data->RecordDeath(queue_ms, run_ms, kUnrandomInt); |
| 132 EXPECT_EQ(data->queue_duration(), queue_ms); | 128 EXPECT_EQ(data->run_duration_sum(), run_ms); |
| 133 EXPECT_EQ(data->AverageMsRunDuration(), run_ms); | 129 EXPECT_EQ(data->run_duration_sample(), run_ms); |
| 134 EXPECT_EQ(data->AverageMsQueueDuration(), queue_ms); | 130 EXPECT_EQ(data->queue_duration_sum(), queue_ms); |
| 131 EXPECT_EQ(data->queue_duration_sample(), queue_ms); | |
| 135 EXPECT_EQ(data->count(), 1); | 132 EXPECT_EQ(data->count(), 1); |
| 136 | 133 |
| 137 data->RecordDeath(queue_ms, run_ms); | 134 data->RecordDeath(queue_ms, run_ms, kUnrandomInt); |
| 138 EXPECT_EQ(data->run_duration(), run_ms + run_ms); | 135 EXPECT_EQ(data->run_duration_sum(), run_ms + run_ms); |
| 139 EXPECT_EQ(data->queue_duration(), queue_ms + queue_ms); | 136 EXPECT_EQ(data->run_duration_sample(), run_ms); |
| 140 EXPECT_EQ(data->AverageMsRunDuration(), run_ms); | 137 EXPECT_EQ(data->queue_duration_sum(), queue_ms + queue_ms); |
| 141 EXPECT_EQ(data->AverageMsQueueDuration(), queue_ms); | 138 EXPECT_EQ(data->queue_duration_sample(), queue_ms); |
| 142 EXPECT_EQ(data->count(), 2); | 139 EXPECT_EQ(data->count(), 2); |
| 143 | 140 |
| 144 scoped_ptr<base::DictionaryValue> dictionary(data->ToValue()); | 141 scoped_ptr<base::DictionaryValue> dictionary(data->ToValue()); |
| 145 int integer; | 142 int integer; |
| 146 EXPECT_TRUE(dictionary->GetInteger("run_ms", &integer)); | 143 EXPECT_TRUE(dictionary->GetInteger("run_ms", &integer)); |
| 147 EXPECT_EQ(integer, 2 * run_ms); | 144 EXPECT_EQ(integer, 2 * run_ms); |
| 145 EXPECT_TRUE(dictionary->GetInteger("run_ms_sample", &integer)); | |
| 146 EXPECT_EQ(integer, run_ms); | |
| 148 EXPECT_TRUE(dictionary->GetInteger("queue_ms", &integer)); | 147 EXPECT_TRUE(dictionary->GetInteger("queue_ms", &integer)); |
| 149 EXPECT_EQ(integer, 2 * queue_ms); | 148 EXPECT_EQ(integer, 2 * queue_ms); |
| 149 EXPECT_TRUE(dictionary->GetInteger("queue_ms_sample", &integer)); | |
| 150 EXPECT_EQ(integer, queue_ms); | |
| 150 EXPECT_TRUE(dictionary->GetInteger("count", &integer)); | 151 EXPECT_TRUE(dictionary->GetInteger("count", &integer)); |
| 151 EXPECT_EQ(integer, 2); | 152 EXPECT_EQ(integer, 2); |
| 152 | 153 |
| 153 scoped_ptr<base::Value> value(data->ToValue()); | 154 scoped_ptr<base::Value> value(data->ToValue()); |
| 154 std::string json; | 155 std::string json; |
| 155 base::JSONWriter::Write(value.get(), false, &json); | 156 base::JSONWriter::Write(value.get(), false, &json); |
| 156 std::string birth_only_result = "{" | 157 std::string birth_only_result = "{" |
| 157 "\"count\":2," | 158 "\"count\":2," |
| 158 "\"queue_ms\":16," | 159 "\"queue_ms\":16," |
| 159 "\"queue_ms_max\":8," | 160 "\"queue_ms_max\":8," |
| 161 "\"queue_ms_sample\":8," | |
| 160 "\"run_ms\":84," | 162 "\"run_ms\":84," |
| 161 "\"run_ms_max\":42" | 163 "\"run_ms_max\":42," |
| 164 "\"run_ms_sample\":42" | |
| 162 "}"; | 165 "}"; |
| 163 EXPECT_EQ(birth_only_result, json); | 166 EXPECT_EQ(birth_only_result, json); |
| 164 } | 167 } |
| 165 | 168 |
| 166 TEST_F(TrackedObjectsTest, DeactivatedBirthOnlyToValueWorkerThread) { | 169 TEST_F(TrackedObjectsTest, DeactivatedBirthOnlyToValueWorkerThread) { |
| 167 // Transition to Deactivated state before doing anything. | 170 // Transition to Deactivated state before doing anything. |
| 168 if (!ThreadData::InitializeAndSetTrackingStatus(false)) | 171 if (!ThreadData::InitializeAndSetTrackingStatus(false)) |
| 169 return; | 172 return; |
| 170 // We don't initialize system with a thread name, so we're viewed as a worker | 173 // We don't initialize system with a thread name, so we're viewed as a worker |
| 171 // thread. | 174 // thread. |
| 172 const int kFakeLineNumber = 173; | 175 const int kFakeLineNumber = 173; |
| 173 const char* kFile = "FixedFileName"; | 176 const char* kFile = "FixedFileName"; |
| 174 const char* kFunction = "BirthOnlyToValueWorkerThread"; | 177 const char* kFunction = "BirthOnlyToValueWorkerThread"; |
| 175 Location location(kFunction, kFile, kFakeLineNumber, NULL); | 178 Location location(kFunction, kFile, kFakeLineNumber, NULL); |
| 176 Births* birth = ThreadData::TallyABirthIfActive(location); | 179 Births* birth = ThreadData::TallyABirthIfActive(location); |
| 177 // We should now see a NULL birth record. | 180 // We should now see a NULL birth record. |
| 178 EXPECT_EQ(birth, reinterpret_cast<Births*>(NULL)); | 181 EXPECT_EQ(birth, reinterpret_cast<Births*>(NULL)); |
| 179 | 182 |
| 180 scoped_ptr<base::Value> value(ThreadData::ToValue()); | 183 scoped_ptr<base::Value> value(ThreadData::ToValue(false)); |
| 181 std::string json; | 184 std::string json; |
| 182 base::JSONWriter::Write(value.get(), false, &json); | 185 base::JSONWriter::Write(value.get(), false, &json); |
| 183 std::string birth_only_result = "{" | 186 std::string birth_only_result = "{" |
| 184 "\"list\":[" | 187 "\"list\":[" |
| 185 "]" | 188 "]" |
| 186 "}"; | 189 "}"; |
| 187 EXPECT_EQ(json, birth_only_result); | 190 EXPECT_EQ(json, birth_only_result); |
| 188 } | 191 } |
| 189 | 192 |
| 190 TEST_F(TrackedObjectsTest, DeactivatedBirthOnlyToValueMainThread) { | 193 TEST_F(TrackedObjectsTest, DeactivatedBirthOnlyToValueMainThread) { |
| 191 // Start in the deactivated state. | 194 // Start in the deactivated state. |
| 192 if (!ThreadData::InitializeAndSetTrackingStatus(false)) | 195 if (!ThreadData::InitializeAndSetTrackingStatus(false)) |
| 193 return; | 196 return; |
| 194 | 197 |
| 195 // Use a well named thread. | 198 // Use a well named thread. |
| 196 ThreadData::InitializeThreadContext("SomeMainThreadName"); | 199 ThreadData::InitializeThreadContext("SomeMainThreadName"); |
| 197 const int kFakeLineNumber = 173; | 200 const int kFakeLineNumber = 173; |
| 198 const char* kFile = "FixedFileName"; | 201 const char* kFile = "FixedFileName"; |
| 199 const char* kFunction = "BirthOnlyToValueMainThread"; | 202 const char* kFunction = "BirthOnlyToValueMainThread"; |
| 200 Location location(kFunction, kFile, kFakeLineNumber, NULL); | 203 Location location(kFunction, kFile, kFakeLineNumber, NULL); |
| 201 // Do not delete birth. We don't own it. | 204 // Do not delete birth. We don't own it. |
| 202 Births* birth = ThreadData::TallyABirthIfActive(location); | 205 Births* birth = ThreadData::TallyABirthIfActive(location); |
| 203 // We expect to not get a birth record. | 206 // We expect to not get a birth record. |
| 204 EXPECT_EQ(birth, reinterpret_cast<Births*>(NULL)); | 207 EXPECT_EQ(birth, reinterpret_cast<Births*>(NULL)); |
| 205 | 208 |
| 206 scoped_ptr<base::Value> value(ThreadData::ToValue()); | 209 scoped_ptr<base::Value> value(ThreadData::ToValue(false)); |
| 207 std::string json; | 210 std::string json; |
| 208 base::JSONWriter::Write(value.get(), false, &json); | 211 base::JSONWriter::Write(value.get(), false, &json); |
| 209 std::string birth_only_result = "{" | 212 std::string birth_only_result = "{" |
| 210 "\"list\":[" | 213 "\"list\":[" |
| 211 "]" | 214 "]" |
| 212 "}"; | 215 "}"; |
| 213 EXPECT_EQ(json, birth_only_result); | 216 EXPECT_EQ(json, birth_only_result); |
| 214 } | 217 } |
| 215 | 218 |
| 216 TEST_F(TrackedObjectsTest, BirthOnlyToValueWorkerThread) { | 219 TEST_F(TrackedObjectsTest, BirthOnlyToValueWorkerThread) { |
| 217 if (!ThreadData::InitializeAndSetTrackingStatus(true)) | 220 if (!ThreadData::InitializeAndSetTrackingStatus(true)) |
| 218 return; | 221 return; |
| 219 // We don't initialize system with a thread name, so we're viewed as a worker | 222 // We don't initialize system with a thread name, so we're viewed as a worker |
| 220 // thread. | 223 // thread. |
| 221 const int kFakeLineNumber = 173; | 224 const int kFakeLineNumber = 173; |
| 222 const char* kFile = "FixedFileName"; | 225 const char* kFile = "FixedFileName"; |
| 223 const char* kFunction = "BirthOnlyToValueWorkerThread"; | 226 const char* kFunction = "BirthOnlyToValueWorkerThread"; |
| 224 Location location(kFunction, kFile, kFakeLineNumber, NULL); | 227 Location location(kFunction, kFile, kFakeLineNumber, NULL); |
| 225 Births* birth = ThreadData::TallyABirthIfActive(location); | 228 Births* birth = ThreadData::TallyABirthIfActive(location); |
| 226 EXPECT_NE(birth, reinterpret_cast<Births*>(NULL)); | 229 EXPECT_NE(birth, reinterpret_cast<Births*>(NULL)); |
| 227 | 230 |
| 228 scoped_ptr<base::Value> value(ThreadData::ToValue()); | 231 scoped_ptr<base::Value> value(ThreadData::ToValue(false)); |
| 229 std::string json; | 232 std::string json; |
| 230 base::JSONWriter::Write(value.get(), false, &json); | 233 base::JSONWriter::Write(value.get(), false, &json); |
| 231 std::string birth_only_result = "{" | 234 std::string birth_only_result = "{" |
| 232 "\"list\":[" | 235 "\"list\":[" |
| 233 "{" | 236 "{" |
| 234 "\"birth_thread\":\"WorkerThread-1\"," | 237 "\"birth_thread\":\"WorkerThread-1\"," |
| 235 "\"death_data\":{" | 238 "\"death_data\":{" |
| 236 "\"count\":1," | 239 "\"count\":1," |
| 237 "\"queue_ms\":0," | 240 "\"queue_ms\":0," |
| 238 "\"queue_ms_max\":0," | 241 "\"queue_ms_max\":0," |
| 242 "\"queue_ms_sample\":0," | |
| 239 "\"run_ms\":0," | 243 "\"run_ms\":0," |
| 240 "\"run_ms_max\":0" | 244 "\"run_ms_max\":0," |
| 245 "\"run_ms_sample\":0" | |
| 241 "}," | 246 "}," |
| 242 "\"death_thread\":\"Still_Alive\"," | 247 "\"death_thread\":\"Still_Alive\"," |
| 243 "\"location\":{" | 248 "\"location\":{" |
| 244 "\"file_name\":\"FixedFileName\"," | 249 "\"file_name\":\"FixedFileName\"," |
| 245 "\"function_name\":\"BirthOnlyToValueWorkerThread\"," | 250 "\"function_name\":\"BirthOnlyToValueWorkerThread\"," |
| 246 "\"line_number\":173" | 251 "\"line_number\":173" |
| 247 "}" | 252 "}" |
| 248 "}" | 253 "}" |
| 249 "]" | 254 "]" |
| 250 "}"; | 255 "}"; |
| 251 EXPECT_EQ(json, birth_only_result); | 256 EXPECT_EQ(json, birth_only_result); |
| 252 } | 257 } |
| 253 | 258 |
| 254 TEST_F(TrackedObjectsTest, BirthOnlyToValueMainThread) { | 259 TEST_F(TrackedObjectsTest, BirthOnlyToValueMainThread) { |
| 255 if (!ThreadData::InitializeAndSetTrackingStatus(true)) | 260 if (!ThreadData::InitializeAndSetTrackingStatus(true)) |
| 256 return; | 261 return; |
| 257 | 262 |
| 258 // Use a well named thread. | 263 // Use a well named thread. |
| 259 ThreadData::InitializeThreadContext("SomeMainThreadName"); | 264 ThreadData::InitializeThreadContext("SomeMainThreadName"); |
| 260 const int kFakeLineNumber = 173; | 265 const int kFakeLineNumber = 173; |
| 261 const char* kFile = "FixedFileName"; | 266 const char* kFile = "FixedFileName"; |
| 262 const char* kFunction = "BirthOnlyToValueMainThread"; | 267 const char* kFunction = "BirthOnlyToValueMainThread"; |
| 263 Location location(kFunction, kFile, kFakeLineNumber, NULL); | 268 Location location(kFunction, kFile, kFakeLineNumber, NULL); |
| 264 // Do not delete birth. We don't own it. | 269 // Do not delete birth. We don't own it. |
| 265 Births* birth = ThreadData::TallyABirthIfActive(location); | 270 Births* birth = ThreadData::TallyABirthIfActive(location); |
| 266 EXPECT_NE(birth, reinterpret_cast<Births*>(NULL)); | 271 EXPECT_NE(birth, reinterpret_cast<Births*>(NULL)); |
| 267 | 272 |
| 268 scoped_ptr<base::Value> value(ThreadData::ToValue()); | 273 scoped_ptr<base::Value> value(ThreadData::ToValue(false)); |
| 269 std::string json; | 274 std::string json; |
| 270 base::JSONWriter::Write(value.get(), false, &json); | 275 base::JSONWriter::Write(value.get(), false, &json); |
| 271 std::string birth_only_result = "{" | 276 std::string birth_only_result = "{" |
| 272 "\"list\":[" | 277 "\"list\":[" |
| 273 "{" | 278 "{" |
| 274 "\"birth_thread\":\"SomeMainThreadName\"," | 279 "\"birth_thread\":\"SomeMainThreadName\"," |
| 275 "\"death_data\":{" | 280 "\"death_data\":{" |
| 276 "\"count\":1," | 281 "\"count\":1," |
| 277 "\"queue_ms\":0," | 282 "\"queue_ms\":0," |
| 278 "\"queue_ms_max\":0," | 283 "\"queue_ms_max\":0," |
| 284 "\"queue_ms_sample\":0," | |
| 279 "\"run_ms\":0," | 285 "\"run_ms\":0," |
| 280 "\"run_ms_max\":0" | 286 "\"run_ms_max\":0," |
| 287 "\"run_ms_sample\":0" | |
| 281 "}," | 288 "}," |
| 282 "\"death_thread\":\"Still_Alive\"," | 289 "\"death_thread\":\"Still_Alive\"," |
| 283 "\"location\":{" | 290 "\"location\":{" |
| 284 "\"file_name\":\"FixedFileName\"," | 291 "\"file_name\":\"FixedFileName\"," |
| 285 "\"function_name\":\"BirthOnlyToValueMainThread\"," | 292 "\"function_name\":\"BirthOnlyToValueMainThread\"," |
| 286 "\"line_number\":173" | 293 "\"line_number\":173" |
| 287 "}" | 294 "}" |
| 288 "}" | 295 "}" |
| 289 "]" | 296 "]" |
| 290 "}"; | 297 "}"; |
| (...skipping 20 matching lines...) Expand all Loading... | |
| 311 // TrackingInfo will call TallyABirth() during construction. | 318 // TrackingInfo will call TallyABirth() during construction. |
| 312 base::TrackingInfo pending_task(location, kDelayedStartTime); | 319 base::TrackingInfo pending_task(location, kDelayedStartTime); |
| 313 pending_task.time_posted = kTimePosted; // Overwrite implied Now(). | 320 pending_task.time_posted = kTimePosted; // Overwrite implied Now(). |
| 314 | 321 |
| 315 const TrackedTime kStartOfRun = TrackedTime() + | 322 const TrackedTime kStartOfRun = TrackedTime() + |
| 316 Duration::FromMilliseconds(5); | 323 Duration::FromMilliseconds(5); |
| 317 const TrackedTime kEndOfRun = TrackedTime() + Duration::FromMilliseconds(7); | 324 const TrackedTime kEndOfRun = TrackedTime() + Duration::FromMilliseconds(7); |
| 318 ThreadData::TallyRunOnNamedThreadIfTracking(pending_task, | 325 ThreadData::TallyRunOnNamedThreadIfTracking(pending_task, |
| 319 kStartOfRun, kEndOfRun); | 326 kStartOfRun, kEndOfRun); |
| 320 | 327 |
| 321 scoped_ptr<base::Value> value(ThreadData::ToValue()); | 328 scoped_ptr<base::Value> value(ThreadData::ToValue(false)); |
| 322 std::string json; | 329 std::string json; |
| 323 base::JSONWriter::Write(value.get(), false, &json); | 330 base::JSONWriter::Write(value.get(), false, &json); |
| 324 std::string one_line_result = "{" | 331 std::string one_line_result = "{" |
| 325 "\"list\":[" | 332 "\"list\":[" |
| 326 "{" | 333 "{" |
| 327 "\"birth_thread\":\"SomeMainThreadName\"," | 334 "\"birth_thread\":\"SomeMainThreadName\"," |
| 328 "\"death_data\":{" | 335 "\"death_data\":{" |
| 329 "\"count\":1," | 336 "\"count\":1," |
| 330 "\"queue_ms\":4," | 337 "\"queue_ms\":4," |
| 331 "\"queue_ms_max\":4," | 338 "\"queue_ms_max\":4," |
| 339 "\"queue_ms_sample\":4," | |
| 332 "\"run_ms\":2," | 340 "\"run_ms\":2," |
| 333 "\"run_ms_max\":2" | 341 "\"run_ms_max\":2," |
| 342 "\"run_ms_sample\":2" | |
| 334 "}," | 343 "}," |
| 335 "\"death_thread\":\"SomeMainThreadName\"," | 344 "\"death_thread\":\"SomeMainThreadName\"," |
| 336 "\"location\":{" | 345 "\"location\":{" |
| 337 "\"file_name\":\"FixedFileName\"," | 346 "\"file_name\":\"FixedFileName\"," |
| 338 "\"function_name\":\"LifeCycleToValueMainThread\"," | 347 "\"function_name\":\"LifeCycleToValueMainThread\"," |
| 339 "\"line_number\":236" | 348 "\"line_number\":236" |
| 340 "}" | 349 "}" |
| 341 "}" | 350 "}" |
| 342 "]" | 351 "]" |
| 343 "}"; | 352 "}"; |
| (...skipping 27 matching lines...) Expand all Loading... | |
| 371 | 380 |
| 372 // Turn off tracking now that we have births. | 381 // Turn off tracking now that we have births. |
| 373 EXPECT_TRUE(ThreadData::InitializeAndSetTrackingStatus(false)); | 382 EXPECT_TRUE(ThreadData::InitializeAndSetTrackingStatus(false)); |
| 374 | 383 |
| 375 const TrackedTime kStartOfRun = TrackedTime() + | 384 const TrackedTime kStartOfRun = TrackedTime() + |
| 376 Duration::FromMilliseconds(5); | 385 Duration::FromMilliseconds(5); |
| 377 const TrackedTime kEndOfRun = TrackedTime() + Duration::FromMilliseconds(7); | 386 const TrackedTime kEndOfRun = TrackedTime() + Duration::FromMilliseconds(7); |
| 378 ThreadData::TallyRunOnNamedThreadIfTracking(pending_task, | 387 ThreadData::TallyRunOnNamedThreadIfTracking(pending_task, |
| 379 kStartOfRun, kEndOfRun); | 388 kStartOfRun, kEndOfRun); |
| 380 | 389 |
| 381 scoped_ptr<base::Value> value(ThreadData::ToValue()); | 390 scoped_ptr<base::Value> value(ThreadData::ToValue(false)); |
| 382 std::string json; | 391 std::string json; |
| 383 base::JSONWriter::Write(value.get(), false, &json); | 392 base::JSONWriter::Write(value.get(), false, &json); |
| 384 std::string one_line_result = "{" | 393 std::string one_line_result = "{" |
| 385 "\"list\":[" | 394 "\"list\":[" |
| 386 "{" | 395 "{" |
| 387 "\"birth_thread\":\"SomeMainThreadName\"," | 396 "\"birth_thread\":\"SomeMainThreadName\"," |
| 388 "\"death_data\":{" | 397 "\"death_data\":{" |
| 389 "\"count\":1," | 398 "\"count\":1," |
| 390 "\"queue_ms\":4," | 399 "\"queue_ms\":4," |
| 391 "\"queue_ms_max\":4," | 400 "\"queue_ms_max\":4," |
| 401 "\"queue_ms_sample\":4," | |
| 392 "\"run_ms\":2," | 402 "\"run_ms\":2," |
| 393 "\"run_ms_max\":2" | 403 "\"run_ms_max\":2," |
| 404 "\"run_ms_sample\":2" | |
| 394 "}," | 405 "}," |
| 395 "\"death_thread\":\"SomeMainThreadName\"," | 406 "\"death_thread\":\"SomeMainThreadName\"," |
| 396 "\"location\":{" | 407 "\"location\":{" |
| 397 "\"file_name\":\"FixedFileName\"," | 408 "\"file_name\":\"FixedFileName\"," |
| 398 "\"function_name\":\"LifeCycleToValueMainThread\"," | 409 "\"function_name\":\"LifeCycleToValueMainThread\"," |
| 399 "\"line_number\":236" | 410 "\"line_number\":236" |
| 400 "}" | 411 "}" |
| 401 "}" | 412 "}" |
| 402 "]" | 413 "]" |
| 403 "}"; | 414 "}"; |
| (...skipping 22 matching lines...) Expand all Loading... | |
| 426 // TrackingInfo will call TallyABirth() during construction. | 437 // TrackingInfo will call TallyABirth() during construction. |
| 427 base::TrackingInfo pending_task(location, kDelayedStartTime); | 438 base::TrackingInfo pending_task(location, kDelayedStartTime); |
| 428 pending_task.time_posted = kTimePosted; // Overwrite implied Now(). | 439 pending_task.time_posted = kTimePosted; // Overwrite implied Now(). |
| 429 | 440 |
| 430 const TrackedTime kStartOfRun = TrackedTime() + | 441 const TrackedTime kStartOfRun = TrackedTime() + |
| 431 Duration::FromMilliseconds(5); | 442 Duration::FromMilliseconds(5); |
| 432 const TrackedTime kEndOfRun = TrackedTime() + Duration::FromMilliseconds(7); | 443 const TrackedTime kEndOfRun = TrackedTime() + Duration::FromMilliseconds(7); |
| 433 ThreadData::TallyRunOnNamedThreadIfTracking(pending_task, | 444 ThreadData::TallyRunOnNamedThreadIfTracking(pending_task, |
| 434 kStartOfRun, kEndOfRun); | 445 kStartOfRun, kEndOfRun); |
| 435 | 446 |
| 436 scoped_ptr<base::Value> value(ThreadData::ToValue()); | 447 scoped_ptr<base::Value> value(ThreadData::ToValue(false)); |
| 437 std::string json; | 448 std::string json; |
| 438 base::JSONWriter::Write(value.get(), false, &json); | 449 base::JSONWriter::Write(value.get(), false, &json); |
| 439 std::string one_line_result = "{" | 450 std::string one_line_result = "{" |
| 440 "\"list\":[" | 451 "\"list\":[" |
| 441 "]" | 452 "]" |
| 442 "}"; | 453 "}"; |
| 443 EXPECT_EQ(one_line_result, json); | 454 EXPECT_EQ(one_line_result, json); |
| 444 } | 455 } |
| 445 | 456 |
| 446 TEST_F(TrackedObjectsTest, LifeCycleToValueWorkerThread) { | 457 TEST_F(TrackedObjectsTest, LifeCycleToValueWorkerThread) { |
| (...skipping 11 matching lines...) Expand all Loading... | |
| 458 Births* birth = ThreadData::TallyABirthIfActive(location); | 469 Births* birth = ThreadData::TallyABirthIfActive(location); |
| 459 EXPECT_NE(birth, reinterpret_cast<Births*>(NULL)); | 470 EXPECT_NE(birth, reinterpret_cast<Births*>(NULL)); |
| 460 | 471 |
| 461 const TrackedTime kTimePosted = TrackedTime() + Duration::FromMilliseconds(1); | 472 const TrackedTime kTimePosted = TrackedTime() + Duration::FromMilliseconds(1); |
| 462 const TrackedTime kStartOfRun = TrackedTime() + | 473 const TrackedTime kStartOfRun = TrackedTime() + |
| 463 Duration::FromMilliseconds(5); | 474 Duration::FromMilliseconds(5); |
| 464 const TrackedTime kEndOfRun = TrackedTime() + Duration::FromMilliseconds(7); | 475 const TrackedTime kEndOfRun = TrackedTime() + Duration::FromMilliseconds(7); |
| 465 ThreadData::TallyRunOnWorkerThreadIfTracking(birth, kTimePosted, | 476 ThreadData::TallyRunOnWorkerThreadIfTracking(birth, kTimePosted, |
| 466 kStartOfRun, kEndOfRun); | 477 kStartOfRun, kEndOfRun); |
| 467 | 478 |
| 468 scoped_ptr<base::Value> value(ThreadData::ToValue()); | 479 // Call for the ToValue, but tell it to not the maxes after scanning. |
| 480 scoped_ptr<base::Value> value(ThreadData::ToValue(false)); | |
| 469 std::string json; | 481 std::string json; |
| 470 base::JSONWriter::Write(value.get(), false, &json); | 482 base::JSONWriter::Write(value.get(), false, &json); |
| 471 std::string one_line_result = "{" | 483 std::string one_line_result = "{" |
| 472 "\"list\":[" | 484 "\"list\":[" |
| 473 "{" | 485 "{" |
| 474 "\"birth_thread\":\"WorkerThread-1\"," | 486 "\"birth_thread\":\"WorkerThread-1\"," |
| 475 "\"death_data\":{" | 487 "\"death_data\":{" |
| 476 "\"count\":1," | 488 "\"count\":1," |
| 477 "\"queue_ms\":4," | 489 "\"queue_ms\":4," |
| 478 "\"queue_ms_max\":4," | 490 "\"queue_ms_max\":4," |
| 491 "\"queue_ms_sample\":4," | |
| 479 "\"run_ms\":2," | 492 "\"run_ms\":2," |
| 480 "\"run_ms_max\":2" | 493 "\"run_ms_max\":2," |
| 494 "\"run_ms_sample\":2" | |
| 481 "}," | 495 "}," |
| 482 "\"death_thread\":\"WorkerThread-1\"," | 496 "\"death_thread\":\"WorkerThread-1\"," |
| 483 "\"location\":{" | 497 "\"location\":{" |
| 484 "\"file_name\":\"FixedFileName\"," | 498 "\"file_name\":\"FixedFileName\"," |
| 485 "\"function_name\":\"LifeCycleToValueWorkerThread\"," | 499 "\"function_name\":\"LifeCycleToValueWorkerThread\"," |
| 486 "\"line_number\":236" | 500 "\"line_number\":236" |
| 487 "}" | 501 "}" |
| 488 "}" | 502 "}" |
| 489 "]" | 503 "]" |
| 490 "}"; | 504 "}"; |
| 491 EXPECT_EQ(one_line_result, json); | 505 EXPECT_EQ(one_line_result, json); |
| 506 | |
| 507 // Call for the ToValue, but tell it to reset the maxes after scanning. | |
| 508 // We'll still get the same values, but the data will be reset (which we'll | |
| 509 // see in a moment) | |
|
ramant (doing other things)
2011/12/03 22:48:39
nit: Add a period.
jar (doing other things)
2011/12/04 00:46:22
Done.
| |
| 510 value.reset(ThreadData::ToValue(true)); | |
| 511 base::JSONWriter::Write(value.get(), false, &json); | |
| 512 // Result should be unchanged. | |
| 513 EXPECT_EQ(one_line_result, json); | |
| 514 | |
| 515 // Call for the ToValue, and now we'll see the result of the last translation, | |
| 516 // as the max will have been pushed back to zero. | |
| 517 value.reset(ThreadData::ToValue(false)); | |
| 518 base::JSONWriter::Write(value.get(), false, &json); | |
| 519 std::string one_line_result_with_zeros = "{" | |
| 520 "\"list\":[" | |
| 521 "{" | |
| 522 "\"birth_thread\":\"WorkerThread-1\"," | |
| 523 "\"death_data\":{" | |
| 524 "\"count\":1," | |
| 525 "\"queue_ms\":4," | |
| 526 "\"queue_ms_max\":0," // Note zero here. | |
| 527 "\"queue_ms_sample\":4," | |
| 528 "\"run_ms\":2," | |
| 529 "\"run_ms_max\":0," // Note zero here. | |
| 530 "\"run_ms_sample\":2" | |
| 531 "}," | |
| 532 "\"death_thread\":\"WorkerThread-1\"," | |
| 533 "\"location\":{" | |
| 534 "\"file_name\":\"FixedFileName\"," | |
| 535 "\"function_name\":\"LifeCycleToValueWorkerThread\"," | |
| 536 "\"line_number\":236" | |
| 537 "}" | |
| 538 "}" | |
| 539 "]" | |
| 540 "}"; | |
| 541 EXPECT_EQ(one_line_result_with_zeros, json); | |
| 492 } | 542 } |
| 493 | 543 |
| 494 TEST_F(TrackedObjectsTest, TwoLives) { | 544 TEST_F(TrackedObjectsTest, TwoLives) { |
| 495 if (!ThreadData::InitializeAndSetTrackingStatus(true)) | 545 if (!ThreadData::InitializeAndSetTrackingStatus(true)) |
| 496 return; | 546 return; |
| 497 | 547 |
| 498 // Use a well named thread. | 548 // Use a well named thread. |
| 499 ThreadData::InitializeThreadContext("SomeFileThreadName"); | 549 ThreadData::InitializeThreadContext("SomeFileThreadName"); |
| 500 const int kFakeLineNumber = 222; | 550 const int kFakeLineNumber = 222; |
| 501 const char* kFile = "AnotherFileName"; | 551 const char* kFile = "AnotherFileName"; |
| (...skipping 17 matching lines...) Expand all Loading... | |
| 519 ThreadData::TallyRunOnNamedThreadIfTracking(pending_task, | 569 ThreadData::TallyRunOnNamedThreadIfTracking(pending_task, |
| 520 kStartOfRun, kEndOfRun); | 570 kStartOfRun, kEndOfRun); |
| 521 | 571 |
| 522 // TrackingInfo will call TallyABirth() during construction. | 572 // TrackingInfo will call TallyABirth() during construction. |
| 523 base::TrackingInfo pending_task2(location, kDelayedStartTime); | 573 base::TrackingInfo pending_task2(location, kDelayedStartTime); |
| 524 pending_task2.time_posted = kTimePosted; // Overwrite implied Now(). | 574 pending_task2.time_posted = kTimePosted; // Overwrite implied Now(). |
| 525 | 575 |
| 526 ThreadData::TallyRunOnNamedThreadIfTracking(pending_task2, | 576 ThreadData::TallyRunOnNamedThreadIfTracking(pending_task2, |
| 527 kStartOfRun, kEndOfRun); | 577 kStartOfRun, kEndOfRun); |
| 528 | 578 |
| 529 scoped_ptr<base::Value> value(ThreadData::ToValue()); | 579 scoped_ptr<base::Value> value(ThreadData::ToValue(false)); |
| 530 std::string json; | 580 std::string json; |
| 531 base::JSONWriter::Write(value.get(), false, &json); | 581 base::JSONWriter::Write(value.get(), false, &json); |
| 532 std::string one_line_result = "{" | 582 std::string one_line_result = "{" |
| 533 "\"list\":[" | 583 "\"list\":[" |
| 534 "{" | 584 "{" |
| 535 "\"birth_thread\":\"SomeFileThreadName\"," | 585 "\"birth_thread\":\"SomeFileThreadName\"," |
| 536 "\"death_data\":{" | 586 "\"death_data\":{" |
| 537 "\"count\":2," | 587 "\"count\":2," |
| 538 "\"queue_ms\":8," | 588 "\"queue_ms\":8," |
| 539 "\"queue_ms_max\":4," | 589 "\"queue_ms_max\":4," |
| 590 "\"queue_ms_sample\":4," | |
| 540 "\"run_ms\":4," | 591 "\"run_ms\":4," |
| 541 "\"run_ms_max\":2" | 592 "\"run_ms_max\":2," |
| 593 "\"run_ms_sample\":2" | |
| 542 "}," | 594 "}," |
| 543 "\"death_thread\":\"SomeFileThreadName\"," | 595 "\"death_thread\":\"SomeFileThreadName\"," |
| 544 "\"location\":{" | 596 "\"location\":{" |
| 545 "\"file_name\":\"AnotherFileName\"," | 597 "\"file_name\":\"AnotherFileName\"," |
| 546 "\"function_name\":\"TwoLives\"," | 598 "\"function_name\":\"TwoLives\"," |
| 547 "\"line_number\":222" | 599 "\"line_number\":222" |
| 548 "}" | 600 "}" |
| 549 "}" | 601 "}" |
| 550 "]" | 602 "]" |
| 551 "}"; | 603 "}"; |
| (...skipping 24 matching lines...) Expand all Loading... | |
| 576 ThreadData::TallyRunOnNamedThreadIfTracking(pending_task, | 628 ThreadData::TallyRunOnNamedThreadIfTracking(pending_task, |
| 577 kStartOfRun, kEndOfRun); | 629 kStartOfRun, kEndOfRun); |
| 578 | 630 |
| 579 const int kSecondFakeLineNumber = 999; | 631 const int kSecondFakeLineNumber = 999; |
| 580 Location second_location(kFunction, kFile, kSecondFakeLineNumber, NULL); | 632 Location second_location(kFunction, kFile, kSecondFakeLineNumber, NULL); |
| 581 | 633 |
| 582 // TrackingInfo will call TallyABirth() during construction. | 634 // TrackingInfo will call TallyABirth() during construction. |
| 583 base::TrackingInfo pending_task2(second_location, kDelayedStartTime); | 635 base::TrackingInfo pending_task2(second_location, kDelayedStartTime); |
| 584 pending_task2.time_posted = kTimePosted; // Overwrite implied Now(). | 636 pending_task2.time_posted = kTimePosted; // Overwrite implied Now(). |
| 585 | 637 |
| 586 scoped_ptr<base::Value> value(ThreadData::ToValue()); | 638 scoped_ptr<base::Value> value(ThreadData::ToValue(false)); |
| 587 std::string json; | 639 std::string json; |
| 588 base::JSONWriter::Write(value.get(), false, &json); | 640 base::JSONWriter::Write(value.get(), false, &json); |
| 589 std::string one_line_result = "{" | 641 std::string one_line_result = "{" |
| 590 "\"list\":[" | 642 "\"list\":[" |
| 591 "{" | 643 "{" |
| 592 "\"birth_thread\":\"SomeFileThreadName\"," | 644 "\"birth_thread\":\"SomeFileThreadName\"," |
| 593 "\"death_data\":{" | 645 "\"death_data\":{" |
| 594 "\"count\":1," | 646 "\"count\":1," |
| 595 "\"queue_ms\":4," | 647 "\"queue_ms\":4," |
| 596 "\"queue_ms_max\":4," | 648 "\"queue_ms_max\":4," |
| 649 "\"queue_ms_sample\":4," | |
| 597 "\"run_ms\":2," | 650 "\"run_ms\":2," |
| 598 "\"run_ms_max\":2" | 651 "\"run_ms_max\":2," |
| 652 "\"run_ms_sample\":2" | |
| 599 "}," | 653 "}," |
| 600 "\"death_thread\":\"SomeFileThreadName\"," | 654 "\"death_thread\":\"SomeFileThreadName\"," |
| 601 "\"location\":{" | 655 "\"location\":{" |
| 602 "\"file_name\":\"AnotherFileName\"," | 656 "\"file_name\":\"AnotherFileName\"," |
| 603 "\"function_name\":\"DifferentLives\"," | 657 "\"function_name\":\"DifferentLives\"," |
| 604 "\"line_number\":567" | 658 "\"line_number\":567" |
| 605 "}" | 659 "}" |
| 606 "}," | 660 "}," |
| 607 "{" | 661 "{" |
| 608 "\"birth_thread\":\"SomeFileThreadName\"," | 662 "\"birth_thread\":\"SomeFileThreadName\"," |
| 609 "\"death_data\":{" | 663 "\"death_data\":{" |
| 610 "\"count\":1," | 664 "\"count\":1," |
| 611 "\"queue_ms\":0," | 665 "\"queue_ms\":0," |
| 612 "\"queue_ms_max\":0," | 666 "\"queue_ms_max\":0," |
| 667 "\"queue_ms_sample\":0," | |
| 613 "\"run_ms\":0," | 668 "\"run_ms\":0," |
| 614 "\"run_ms_max\":0" | 669 "\"run_ms_max\":0," |
| 670 "\"run_ms_sample\":0" | |
| 615 "}," | 671 "}," |
| 616 "\"death_thread\":\"Still_Alive\"," | 672 "\"death_thread\":\"Still_Alive\"," |
| 617 "\"location\":{" | 673 "\"location\":{" |
| 618 "\"file_name\":\"AnotherFileName\"," | 674 "\"file_name\":\"AnotherFileName\"," |
| 619 "\"function_name\":\"DifferentLives\"," | 675 "\"function_name\":\"DifferentLives\"," |
| 620 "\"line_number\":999" | 676 "\"line_number\":999" |
| 621 "}" | 677 "}" |
| 622 "}" | 678 "}" |
| 623 "]" | 679 "]" |
| 624 "}"; | 680 "}"; |
| 625 EXPECT_EQ(one_line_result, json); | 681 EXPECT_EQ(one_line_result, json); |
| 626 } | 682 } |
| 627 | 683 |
| 628 | 684 |
| 629 } // namespace tracked_objects | 685 } // namespace tracked_objects |
| OLD | NEW |