OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 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 Histogram class | 5 // Test of Histogram class |
6 | 6 |
| 7 #include <climits> |
7 #include <algorithm> | 8 #include <algorithm> |
8 #include <vector> | 9 #include <vector> |
9 | 10 |
10 #include "base/logging.h" | 11 #include "base/logging.h" |
11 #include "base/memory/scoped_ptr.h" | 12 #include "base/memory/scoped_ptr.h" |
12 #include "base/metrics/bucket_ranges.h" | 13 #include "base/metrics/bucket_ranges.h" |
13 #include "base/metrics/histogram.h" | 14 #include "base/metrics/histogram.h" |
| 15 #include "base/metrics/sample_vector.h" |
14 #include "base/metrics/statistics_recorder.h" | 16 #include "base/metrics/statistics_recorder.h" |
15 #include "base/time.h" | 17 #include "base/time.h" |
16 #include "testing/gtest/include/gtest/gtest.h" | 18 #include "testing/gtest/include/gtest/gtest.h" |
17 | 19 |
18 using std::vector; | 20 using std::vector; |
19 | 21 |
20 namespace base { | 22 namespace base { |
21 | 23 |
22 // Check for basic syntax and use. | 24 // Check for basic syntax and use. |
23 TEST(HistogramTest, BasicTest) { | 25 TEST(HistogramTest, BasicTest) { |
(...skipping 175 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
199 "Bounded", 10, 100, kBucketCount, Histogram::kNoFlags)); | 201 "Bounded", 10, 100, kBucketCount, Histogram::kNoFlags)); |
200 | 202 |
201 // Put two samples "out of bounds" above and below. | 203 // Put two samples "out of bounds" above and below. |
202 histogram->Add(5); | 204 histogram->Add(5); |
203 histogram->Add(-50); | 205 histogram->Add(-50); |
204 | 206 |
205 histogram->Add(100); | 207 histogram->Add(100); |
206 histogram->Add(10000); | 208 histogram->Add(10000); |
207 | 209 |
208 // Verify they landed in the underflow, and overflow buckets. | 210 // Verify they landed in the underflow, and overflow buckets. |
209 Histogram::SampleSet sample; | 211 scoped_ptr<SampleVector> samples = histogram->SnapshotSamples(); |
210 histogram->SnapshotSample(&sample); | 212 EXPECT_EQ(2, samples->GetCountAtIndex(0)); |
211 EXPECT_EQ(2, sample.counts(0)); | 213 EXPECT_EQ(0, samples->GetCountAtIndex(1)); |
212 EXPECT_EQ(0, sample.counts(1)); | |
213 size_t array_size = histogram->bucket_count(); | 214 size_t array_size = histogram->bucket_count(); |
214 EXPECT_EQ(kBucketCount, array_size); | 215 EXPECT_EQ(kBucketCount, array_size); |
215 EXPECT_EQ(0, sample.counts(array_size - 2)); | 216 EXPECT_EQ(0, samples->GetCountAtIndex(array_size - 2)); |
216 EXPECT_EQ(2, sample.counts(array_size - 1)); | 217 EXPECT_EQ(2, samples->GetCountAtIndex(array_size - 1)); |
217 | 218 |
218 vector<int> custom_ranges; | 219 vector<int> custom_ranges; |
219 custom_ranges.push_back(10); | 220 custom_ranges.push_back(10); |
220 custom_ranges.push_back(50); | 221 custom_ranges.push_back(50); |
221 custom_ranges.push_back(100); | 222 custom_ranges.push_back(100); |
222 Histogram* test_custom_histogram(CustomHistogram::FactoryGet( | 223 Histogram* test_custom_histogram(CustomHistogram::FactoryGet( |
223 "TestCustomRangeBoundedHistogram", custom_ranges, Histogram::kNoFlags)); | 224 "TestCustomRangeBoundedHistogram", custom_ranges, Histogram::kNoFlags)); |
224 | 225 |
225 // Put two samples "out of bounds" above and below. | 226 // Put two samples "out of bounds" above and below. |
226 test_custom_histogram->Add(5); | 227 test_custom_histogram->Add(5); |
227 test_custom_histogram->Add(-50); | 228 test_custom_histogram->Add(-50); |
228 test_custom_histogram->Add(100); | 229 test_custom_histogram->Add(100); |
229 test_custom_histogram->Add(1000); | 230 test_custom_histogram->Add(1000); |
| 231 test_custom_histogram->Add(INT_MAX); |
230 | 232 |
231 // Verify they landed in the underflow, and overflow buckets. | 233 // Verify they landed in the underflow, and overflow buckets. |
232 Histogram::SampleSet custom_sample; | 234 scoped_ptr<SampleVector> custom_samples = |
233 test_custom_histogram->SnapshotSample(&custom_sample); | 235 test_custom_histogram->SnapshotSamples(); |
234 EXPECT_EQ(2, custom_sample.counts(0)); | 236 EXPECT_EQ(2, custom_samples->GetCountAtIndex(0)); |
235 EXPECT_EQ(0, custom_sample.counts(1)); | 237 EXPECT_EQ(0, custom_samples->GetCountAtIndex(1)); |
236 size_t custom_array_size = test_custom_histogram->bucket_count(); | 238 size_t bucket_count = test_custom_histogram->bucket_count(); |
237 EXPECT_EQ(0, custom_sample.counts(custom_array_size - 2)); | 239 EXPECT_EQ(0, custom_samples->GetCountAtIndex(bucket_count - 2)); |
238 EXPECT_EQ(2, custom_sample.counts(custom_array_size - 1)); | 240 EXPECT_EQ(3, custom_samples->GetCountAtIndex(bucket_count - 1)); |
239 } | 241 } |
240 | 242 |
241 // Check to be sure samples land as expected is "correct" buckets. | 243 // Check to be sure samples land as expected is "correct" buckets. |
242 TEST(HistogramTest, BucketPlacementTest) { | 244 TEST(HistogramTest, BucketPlacementTest) { |
243 Histogram* histogram(Histogram::FactoryGet( | 245 Histogram* histogram(Histogram::FactoryGet( |
244 "Histogram", 1, 64, 8, Histogram::kNoFlags)); | 246 "Histogram", 1, 64, 8, Histogram::kNoFlags)); |
245 | 247 |
246 // Add i+1 samples to the i'th bucket. | 248 // Add i+1 samples to the i'th bucket. |
247 histogram->Add(0); | 249 histogram->Add(0); |
248 int power_of_2 = 1; | 250 int power_of_2 = 1; |
249 for (int i = 1; i < 8; i++) { | 251 for (int i = 1; i < 8; i++) { |
250 for (int j = 0; j <= i; j++) | 252 for (int j = 0; j <= i; j++) |
251 histogram->Add(power_of_2); | 253 histogram->Add(power_of_2); |
252 power_of_2 *= 2; | 254 power_of_2 *= 2; |
253 } | 255 } |
254 | 256 |
255 // Check to see that the bucket counts reflect our additions. | 257 // Check to see that the bucket counts reflect our additions. |
256 Histogram::SampleSet sample; | 258 scoped_ptr<SampleVector> samples = histogram->SnapshotSamples(); |
257 histogram->SnapshotSample(&sample); | |
258 for (int i = 0; i < 8; i++) | 259 for (int i = 0; i < 8; i++) |
259 EXPECT_EQ(i + 1, sample.counts(i)); | 260 EXPECT_EQ(i + 1, samples->GetCountAtIndex(i)); |
260 } | 261 } |
261 | 262 |
262 TEST(HistogramTest, CorruptSampleCounts) { | 263 TEST(HistogramTest, CorruptSampleCounts) { |
263 Histogram* histogram(Histogram::FactoryGet( | 264 Histogram* histogram(Histogram::FactoryGet( |
264 "Histogram", 1, 64, 8, Histogram::kNoFlags)); // As per header file. | 265 "Histogram", 1, 64, 8, Histogram::kNoFlags)); // As per header file. |
265 | 266 |
266 EXPECT_EQ(0, histogram->sample_.redundant_count()); | 267 // Add some samples. |
267 histogram->Add(20); // Add some samples. | 268 histogram->Add(20); |
268 histogram->Add(40); | 269 histogram->Add(40); |
269 EXPECT_EQ(2, histogram->sample_.redundant_count()); | |
270 | 270 |
271 Histogram::SampleSet snapshot; | 271 scoped_ptr<SampleVector> snapshot = histogram->SnapshotSamples(); |
272 histogram->SnapshotSample(&snapshot); | 272 EXPECT_EQ(Histogram::NO_INCONSISTENCIES, |
273 EXPECT_EQ(Histogram::NO_INCONSISTENCIES, 0); | 273 histogram->FindCorruption(*snapshot)); |
274 EXPECT_EQ(0, histogram->FindCorruption(snapshot)); // No default corruption. | 274 EXPECT_EQ(2, snapshot->redundant_count()); |
275 EXPECT_EQ(2, snapshot.redundant_count()); | 275 EXPECT_EQ(2, snapshot->TotalCount()); |
276 | 276 |
277 snapshot.counts_[3] += 100; // Sample count won't match redundant count. | 277 snapshot->counts_[3] += 100; // Sample count won't match redundant count. |
278 EXPECT_EQ(Histogram::COUNT_LOW_ERROR, histogram->FindCorruption(snapshot)); | 278 EXPECT_EQ(Histogram::COUNT_LOW_ERROR, |
279 snapshot.counts_[2] -= 200; | 279 histogram->FindCorruption(*snapshot)); |
280 EXPECT_EQ(Histogram::COUNT_HIGH_ERROR, histogram->FindCorruption(snapshot)); | 280 snapshot->counts_[2] -= 200; |
| 281 EXPECT_EQ(Histogram::COUNT_HIGH_ERROR, |
| 282 histogram->FindCorruption(*snapshot)); |
281 | 283 |
282 // But we can't spot a corruption if it is compensated for. | 284 // But we can't spot a corruption if it is compensated for. |
283 snapshot.counts_[1] += 100; | 285 snapshot->counts_[1] += 100; |
284 EXPECT_EQ(0, histogram->FindCorruption(snapshot)); | 286 EXPECT_EQ(Histogram::NO_INCONSISTENCIES, |
| 287 histogram->FindCorruption(*snapshot)); |
285 } | 288 } |
286 | 289 |
287 TEST(HistogramTest, CorruptBucketBounds) { | 290 TEST(HistogramTest, CorruptBucketBounds) { |
288 Histogram* histogram(Histogram::FactoryGet( | 291 Histogram* histogram(Histogram::FactoryGet( |
289 "Histogram", 1, 64, 8, Histogram::kNoFlags)); // As per header file. | 292 "Histogram", 1, 64, 8, Histogram::kNoFlags)); // As per header file. |
290 | 293 |
291 Histogram::SampleSet snapshot; | 294 scoped_ptr<SampleVector> snapshot = histogram->SnapshotSamples(); |
292 histogram->SnapshotSample(&snapshot); | 295 EXPECT_EQ(Histogram::NO_INCONSISTENCIES, |
293 EXPECT_EQ(Histogram::NO_INCONSISTENCIES, 0); | 296 histogram->FindCorruption(*snapshot)); |
294 EXPECT_EQ(0, histogram->FindCorruption(snapshot)); // No default corruption. | |
295 | 297 |
296 BucketRanges* bucket_ranges = | 298 BucketRanges* bucket_ranges = |
297 const_cast<BucketRanges*>(histogram->bucket_ranges()); | 299 const_cast<BucketRanges*>(histogram->bucket_ranges()); |
298 HistogramBase::Sample tmp = bucket_ranges->range(1); | 300 HistogramBase::Sample tmp = bucket_ranges->range(1); |
299 bucket_ranges->set_range(1, bucket_ranges->range(2)); | 301 bucket_ranges->set_range(1, bucket_ranges->range(2)); |
300 bucket_ranges->set_range(2, tmp); | 302 bucket_ranges->set_range(2, tmp); |
301 EXPECT_EQ(Histogram::BUCKET_ORDER_ERROR | Histogram::RANGE_CHECKSUM_ERROR, | 303 EXPECT_EQ(Histogram::BUCKET_ORDER_ERROR | Histogram::RANGE_CHECKSUM_ERROR, |
302 histogram->FindCorruption(snapshot)); | 304 histogram->FindCorruption(*snapshot)); |
303 | 305 |
304 bucket_ranges->set_range(2, bucket_ranges->range(1)); | 306 bucket_ranges->set_range(2, bucket_ranges->range(1)); |
305 bucket_ranges->set_range(1, tmp); | 307 bucket_ranges->set_range(1, tmp); |
306 EXPECT_EQ(0, histogram->FindCorruption(snapshot)); | 308 EXPECT_EQ(0, histogram->FindCorruption(*snapshot)); |
307 | 309 |
| 310 // Show that two simple changes don't offset each other |
308 bucket_ranges->set_range(3, bucket_ranges->range(3) + 1); | 311 bucket_ranges->set_range(3, bucket_ranges->range(3) + 1); |
309 EXPECT_EQ(Histogram::RANGE_CHECKSUM_ERROR, | 312 EXPECT_EQ(Histogram::RANGE_CHECKSUM_ERROR, |
310 histogram->FindCorruption(snapshot)); | 313 histogram->FindCorruption(*snapshot)); |
311 | 314 |
312 // Show that two simple changes don't offset each other | |
313 bucket_ranges->set_range(4, bucket_ranges->range(4) - 1); | 315 bucket_ranges->set_range(4, bucket_ranges->range(4) - 1); |
314 EXPECT_EQ(Histogram::RANGE_CHECKSUM_ERROR, | 316 EXPECT_EQ(Histogram::RANGE_CHECKSUM_ERROR, |
315 histogram->FindCorruption(snapshot)); | 317 histogram->FindCorruption(*snapshot)); |
316 | 318 |
317 // Repair histogram so that destructor won't DCHECK(). | 319 // Repair histogram so that destructor won't DCHECK(). |
318 bucket_ranges->set_range(3, bucket_ranges->range(3) - 1); | 320 bucket_ranges->set_range(3, bucket_ranges->range(3) - 1); |
319 bucket_ranges->set_range(4, bucket_ranges->range(4) + 1); | 321 bucket_ranges->set_range(4, bucket_ranges->range(4) + 1); |
320 } | 322 } |
321 | 323 |
322 #if GTEST_HAS_DEATH_TEST | 324 #if GTEST_HAS_DEATH_TEST |
323 // For Histogram, LinearHistogram and CustomHistogram, the minimum for a | 325 // For Histogram, LinearHistogram and CustomHistogram, the minimum for a |
324 // declared range is 1, while the maximum is (HistogramBase::kSampleType_MAX - | 326 // declared range is 1, while the maximum is (HistogramBase::kSampleType_MAX - |
325 // 1). But we accept ranges exceeding those limits, and silently clamped to | 327 // 1). But we accept ranges exceeding those limits, and silently clamped to |
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
357 // CustomHistogram needs at least 1 valid range. | 359 // CustomHistogram needs at least 1 valid range. |
358 custom_ranges.clear(); | 360 custom_ranges.clear(); |
359 custom_ranges.push_back(0); | 361 custom_ranges.push_back(0); |
360 EXPECT_DEATH(CustomHistogram::FactoryGet("BadRangesCustom3", custom_ranges, | 362 EXPECT_DEATH(CustomHistogram::FactoryGet("BadRangesCustom3", custom_ranges, |
361 Histogram::kNoFlags), | 363 Histogram::kNoFlags), |
362 ""); | 364 ""); |
363 } | 365 } |
364 #endif | 366 #endif |
365 | 367 |
366 } // namespace base | 368 } // namespace base |
OLD | NEW |