Chromium Code Reviews| 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 // Histogram is an object that aggregates statistics, and can summarize them in | 5 // Histogram is an object that aggregates statistics, and can summarize them in |
| 6 // various forms, including ASCII graphical, HTML, and numerically (as a | 6 // various forms, including ASCII graphical, HTML, and numerically (as a |
| 7 // vector of numbers corresponding to each of the aggregating buckets). | 7 // vector of numbers corresponding to each of the aggregating buckets). |
| 8 | 8 |
| 9 // It supports calls to accumulate either time intervals (which are processed | 9 // It supports calls to accumulate either time intervals (which are processed |
| 10 // as integral number of milliseconds), or arbitrary integral units. | 10 // as integral number of milliseconds), or arbitrary integral units. |
| (...skipping 71 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 82 #include "base/metrics/histogram_macros.h" | 82 #include "base/metrics/histogram_macros.h" |
| 83 #include "base/metrics/histogram_samples.h" | 83 #include "base/metrics/histogram_samples.h" |
| 84 #include "base/time/time.h" | 84 #include "base/time/time.h" |
| 85 | 85 |
| 86 namespace base { | 86 namespace base { |
| 87 | 87 |
| 88 class BooleanHistogram; | 88 class BooleanHistogram; |
| 89 class CustomHistogram; | 89 class CustomHistogram; |
| 90 class Histogram; | 90 class Histogram; |
| 91 class LinearHistogram; | 91 class LinearHistogram; |
| 92 class PersistentMemoryAllocator; | |
| 92 class Pickle; | 93 class Pickle; |
| 93 class PickleIterator; | 94 class PickleIterator; |
| 94 class SampleVector; | 95 class SampleVector; |
| 95 | 96 |
| 97 struct PersistentHistogramData; | |
| 98 | |
| 96 class BASE_EXPORT Histogram : public HistogramBase { | 99 class BASE_EXPORT Histogram : public HistogramBase { |
| 97 public: | 100 public: |
| 98 // Initialize maximum number of buckets in histograms as 16,384. | 101 // Initialize maximum number of buckets in histograms as 16,384. |
| 99 static const size_t kBucketCount_MAX; | 102 static const size_t kBucketCount_MAX; |
| 100 | 103 |
| 101 typedef std::vector<Count> Counts; | 104 typedef std::vector<Count> Counts; |
| 102 | 105 |
| 103 //---------------------------------------------------------------------------- | 106 //---------------------------------------------------------------------------- |
| 104 // For a valid histogram, input should follow these restrictions: | 107 // For a valid histogram, input should follow these restrictions: |
| 105 // minimum > 0 (if a minimum below 1 is specified, it will implicitly be | 108 // minimum > 0 (if a minimum below 1 is specified, it will implicitly be |
| (...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 183 size_t expected_bucket_count) const override; | 186 size_t expected_bucket_count) const override; |
| 184 void Add(Sample value) override; | 187 void Add(Sample value) override; |
| 185 void AddCount(Sample value, int count) override; | 188 void AddCount(Sample value, int count) override; |
| 186 scoped_ptr<HistogramSamples> SnapshotSamples() const override; | 189 scoped_ptr<HistogramSamples> SnapshotSamples() const override; |
| 187 void AddSamples(const HistogramSamples& samples) override; | 190 void AddSamples(const HistogramSamples& samples) override; |
| 188 bool AddSamplesFromPickle(base::PickleIterator* iter) override; | 191 bool AddSamplesFromPickle(base::PickleIterator* iter) override; |
| 189 void WriteHTMLGraph(std::string* output) const override; | 192 void WriteHTMLGraph(std::string* output) const override; |
| 190 void WriteAscii(std::string* output) const override; | 193 void WriteAscii(std::string* output) const override; |
| 191 | 194 |
| 192 protected: | 195 protected: |
| 196 // This class, defined entirely within the .cc file, contains all the | |
| 197 // common logic for building a Histogram and can be overridden by more | |
| 198 // specific types to alter details of how the creation is done. It is | |
| 199 // defined as an embedded class (rather than an anonymous one) so it | |
| 200 // can access the protected constructors. | |
| 201 class Factory; | |
| 202 | |
| 193 // |ranges| should contain the underflow and overflow buckets. See top | 203 // |ranges| should contain the underflow and overflow buckets. See top |
| 194 // comments for example. | 204 // comments for example. |
| 195 Histogram(const std::string& name, | 205 Histogram(const std::string& name, |
| 196 Sample minimum, | 206 Sample minimum, |
| 197 Sample maximum, | 207 Sample maximum, |
| 198 const BucketRanges* ranges); | 208 const BucketRanges* ranges); |
| 199 | 209 |
| 210 // Traditionally, histograms allocate their own memory for the bucket | |
| 211 // vector but "shared" histograms use memory regions allocated from a | |
| 212 // special memory segment that is passed in here. It is assumed that | |
| 213 // the life of this memory is managed externally and exceeds the lifetime | |
| 214 // of this object. Practically, this memory is never released until the | |
| 215 // process exits and the OS cleans it up. | |
| 216 Histogram(const std::string& name, | |
| 217 Sample minimum, | |
| 218 Sample maximum, | |
| 219 const BucketRanges* ranges, | |
| 220 HistogramBase::AtomicCount* counts, | |
| 221 size_t counts_size, | |
| 222 HistogramSamples::Metadata* meta); | |
| 223 | |
| 200 ~Histogram() override; | 224 ~Histogram() override; |
| 201 | 225 |
| 202 // HistogramBase implementation: | 226 // HistogramBase implementation: |
| 203 bool SerializeInfoImpl(base::Pickle* pickle) const override; | 227 bool SerializeInfoImpl(base::Pickle* pickle) const override; |
| 204 | 228 |
| 205 // Method to override to skip the display of the i'th bucket if it's empty. | 229 // Method to override to skip the display of the i'th bucket if it's empty. |
| 206 virtual bool PrintEmptyBucket(size_t index) const; | 230 virtual bool PrintEmptyBucket(size_t index) const; |
| 207 | 231 |
| 208 // Get normalized size, relative to the ranges(i). | 232 // Get normalized size, relative to the ranges(i). |
| 209 virtual double GetBucketSize(Count current, size_t i) const; | 233 virtual double GetBucketSize(Count current, size_t i) const; |
| 210 | 234 |
| 211 // Return a string description of what goes in a given bucket. | 235 // Return a string description of what goes in a given bucket. |
| 212 // Most commonly this is the numeric value, but in derived classes it may | 236 // Most commonly this is the numeric value, but in derived classes it may |
| 213 // be a name (or string description) given to the bucket. | 237 // be a name (or string description) given to the bucket. |
| 214 virtual const std::string GetAsciiBucketRange(size_t it) const; | 238 virtual const std::string GetAsciiBucketRange(size_t it) const; |
| 215 | 239 |
| 216 private: | 240 private: |
| 217 // Allow tests to corrupt our innards for testing purposes. | 241 // Allow tests to corrupt our innards for testing purposes. |
| 218 FRIEND_TEST_ALL_PREFIXES(HistogramTest, BoundsTest); | 242 FRIEND_TEST_ALL_PREFIXES(HistogramTest, BoundsTest); |
| 219 FRIEND_TEST_ALL_PREFIXES(HistogramTest, BucketPlacementTest); | 243 FRIEND_TEST_ALL_PREFIXES(HistogramTest, BucketPlacementTest); |
| 220 FRIEND_TEST_ALL_PREFIXES(HistogramTest, CorruptBucketBounds); | 244 FRIEND_TEST_ALL_PREFIXES(HistogramTest, CorruptBucketBounds); |
| 221 FRIEND_TEST_ALL_PREFIXES(HistogramTest, CorruptSampleCounts); | 245 FRIEND_TEST_ALL_PREFIXES(HistogramTest, CorruptSampleCounts); |
| 222 FRIEND_TEST_ALL_PREFIXES(HistogramTest, NameMatchTest); | 246 FRIEND_TEST_ALL_PREFIXES(HistogramTest, NameMatchTest); |
| 223 FRIEND_TEST_ALL_PREFIXES(HistogramTest, AddCountTest); | 247 FRIEND_TEST_ALL_PREFIXES(HistogramTest, AddCountTest); |
| 224 | 248 |
| 225 friend class StatisticsRecorder; // To allow it to delete duplicates. | 249 friend class StatisticsRecorder; // To allow it to delete duplicates. |
| 226 friend class StatisticsRecorderTest; | 250 friend class StatisticsRecorderTest; |
| 227 | 251 |
| 252 friend BASE_EXPORT HistogramBase* CreatePersistentHistogram( | |
| 253 PersistentMemoryAllocator* allocator, | |
| 254 PersistentHistogramData* histogram_data); | |
| 228 friend BASE_EXPORT HistogramBase* DeserializeHistogramInfo( | 255 friend BASE_EXPORT HistogramBase* DeserializeHistogramInfo( |
| 229 base::PickleIterator* iter); | 256 base::PickleIterator* iter); |
| 230 static HistogramBase* DeserializeInfoImpl(base::PickleIterator* iter); | 257 static HistogramBase* DeserializeInfoImpl(base::PickleIterator* iter); |
| 231 | 258 |
| 232 // Implementation of SnapshotSamples function. | 259 // Implementation of SnapshotSamples function. |
| 233 scoped_ptr<SampleVector> SnapshotSampleVector() const; | 260 scoped_ptr<SampleVector> SnapshotSampleVector() const; |
| 234 | 261 |
| 235 //---------------------------------------------------------------------------- | 262 //---------------------------------------------------------------------------- |
| 236 // Helpers for emitting Ascii graphic. Each method appends data to output. | 263 // Helpers for emitting Ascii graphic. Each method appends data to output. |
| 237 | 264 |
| (...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 272 | 299 |
| 273 DISALLOW_COPY_AND_ASSIGN(Histogram); | 300 DISALLOW_COPY_AND_ASSIGN(Histogram); |
| 274 }; | 301 }; |
| 275 | 302 |
| 276 //------------------------------------------------------------------------------ | 303 //------------------------------------------------------------------------------ |
| 277 | 304 |
| 278 // LinearHistogram is a more traditional histogram, with evenly spaced | 305 // LinearHistogram is a more traditional histogram, with evenly spaced |
| 279 // buckets. | 306 // buckets. |
| 280 class BASE_EXPORT LinearHistogram : public Histogram { | 307 class BASE_EXPORT LinearHistogram : public Histogram { |
| 281 public: | 308 public: |
| 282 ~LinearHistogram() override; | |
|
Alexei Svitkine (slow)
2015/12/21 19:32:11
Why is this removed?
Non-trivial classes should h
bcwhite
2015/12/22 20:50:38
I removed it because it was the only one of the th
| |
| 283 | |
| 284 /* minimum should start from 1. 0 is as minimum is invalid. 0 is an implicit | 309 /* minimum should start from 1. 0 is as minimum is invalid. 0 is an implicit |
| 285 default underflow bucket. */ | 310 default underflow bucket. */ |
| 286 static HistogramBase* FactoryGet(const std::string& name, | 311 static HistogramBase* FactoryGet(const std::string& name, |
| 287 Sample minimum, | 312 Sample minimum, |
| 288 Sample maximum, | 313 Sample maximum, |
| 289 size_t bucket_count, | 314 size_t bucket_count, |
| 290 int32 flags); | 315 int32 flags); |
| 291 static HistogramBase* FactoryTimeGet(const std::string& name, | 316 static HistogramBase* FactoryTimeGet(const std::string& name, |
| 292 TimeDelta minimum, | 317 TimeDelta minimum, |
| 293 TimeDelta maximum, | 318 TimeDelta maximum, |
| (...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 327 const DescriptionPair descriptions[]); | 352 const DescriptionPair descriptions[]); |
| 328 | 353 |
| 329 static void InitializeBucketRanges(Sample minimum, | 354 static void InitializeBucketRanges(Sample minimum, |
| 330 Sample maximum, | 355 Sample maximum, |
| 331 BucketRanges* ranges); | 356 BucketRanges* ranges); |
| 332 | 357 |
| 333 // Overridden from Histogram: | 358 // Overridden from Histogram: |
| 334 HistogramType GetHistogramType() const override; | 359 HistogramType GetHistogramType() const override; |
| 335 | 360 |
| 336 protected: | 361 protected: |
| 362 class Factory; | |
| 363 | |
| 337 LinearHistogram(const std::string& name, | 364 LinearHistogram(const std::string& name, |
| 338 Sample minimum, | 365 Sample minimum, |
| 339 Sample maximum, | 366 Sample maximum, |
| 340 const BucketRanges* ranges); | 367 const BucketRanges* ranges); |
| 341 | 368 |
| 369 LinearHistogram(const std::string& name, | |
| 370 Sample minimum, | |
| 371 Sample maximum, | |
| 372 const BucketRanges* ranges, | |
| 373 HistogramBase::AtomicCount* counts, | |
| 374 size_t counts_size, | |
| 375 HistogramSamples::Metadata* meta); | |
| 376 | |
| 342 double GetBucketSize(Count current, size_t i) const override; | 377 double GetBucketSize(Count current, size_t i) const override; |
| 343 | 378 |
| 344 // If we have a description for a bucket, then return that. Otherwise | 379 // If we have a description for a bucket, then return that. Otherwise |
| 345 // let parent class provide a (numeric) description. | 380 // let parent class provide a (numeric) description. |
| 346 const std::string GetAsciiBucketRange(size_t i) const override; | 381 const std::string GetAsciiBucketRange(size_t i) const override; |
| 347 | 382 |
| 348 // Skip printing of name for numeric range if we have a name (and if this is | 383 // Skip printing of name for numeric range if we have a name (and if this is |
| 349 // an empty bucket). | 384 // an empty bucket). |
| 350 bool PrintEmptyBucket(size_t index) const override; | 385 bool PrintEmptyBucket(size_t index) const override; |
| 351 | 386 |
| 352 private: | 387 private: |
| 388 friend BASE_EXPORT HistogramBase* CreatePersistentHistogram( | |
| 389 PersistentMemoryAllocator* allocator, | |
| 390 PersistentHistogramData* histogram_data); | |
| 353 friend BASE_EXPORT HistogramBase* DeserializeHistogramInfo( | 391 friend BASE_EXPORT HistogramBase* DeserializeHistogramInfo( |
| 354 base::PickleIterator* iter); | 392 base::PickleIterator* iter); |
| 355 static HistogramBase* DeserializeInfoImpl(base::PickleIterator* iter); | 393 static HistogramBase* DeserializeInfoImpl(base::PickleIterator* iter); |
| 356 | 394 |
| 357 // For some ranges, we store a printable description of a bucket range. | 395 // For some ranges, we store a printable description of a bucket range. |
| 358 // If there is no description, then GetAsciiBucketRange() uses parent class | 396 // If there is no description, then GetAsciiBucketRange() uses parent class |
| 359 // to provide a description. | 397 // to provide a description. |
| 360 typedef std::map<Sample, std::string> BucketDescriptionMap; | 398 typedef std::map<Sample, std::string> BucketDescriptionMap; |
| 361 BucketDescriptionMap bucket_description_; | 399 BucketDescriptionMap bucket_description_; |
| 362 | 400 |
| 363 DISALLOW_COPY_AND_ASSIGN(LinearHistogram); | 401 DISALLOW_COPY_AND_ASSIGN(LinearHistogram); |
| 364 }; | 402 }; |
| 365 | 403 |
| 366 //------------------------------------------------------------------------------ | 404 //------------------------------------------------------------------------------ |
| 367 | 405 |
| 368 // BooleanHistogram is a histogram for booleans. | 406 // BooleanHistogram is a histogram for booleans. |
| 369 class BASE_EXPORT BooleanHistogram : public LinearHistogram { | 407 class BASE_EXPORT BooleanHistogram : public LinearHistogram { |
| 370 public: | 408 public: |
| 371 static HistogramBase* FactoryGet(const std::string& name, int32 flags); | 409 static HistogramBase* FactoryGet(const std::string& name, int32 flags); |
| 372 | 410 |
| 373 // Overload of the above function that takes a const char* |name| param, | 411 // Overload of the above function that takes a const char* |name| param, |
| 374 // to avoid code bloat from the std::string constructor being inlined into | 412 // to avoid code bloat from the std::string constructor being inlined into |
| 375 // call sites. | 413 // call sites. |
| 376 static HistogramBase* FactoryGet(const char* name, int32 flags); | 414 static HistogramBase* FactoryGet(const char* name, int32 flags); |
| 377 | 415 |
| 378 HistogramType GetHistogramType() const override; | 416 HistogramType GetHistogramType() const override; |
| 379 | 417 |
| 418 protected: | |
| 419 class Factory; | |
| 420 | |
| 380 private: | 421 private: |
| 381 BooleanHistogram(const std::string& name, const BucketRanges* ranges); | 422 BooleanHistogram(const std::string& name, const BucketRanges* ranges); |
| 423 BooleanHistogram(const std::string& name, | |
| 424 const BucketRanges* ranges, | |
| 425 HistogramBase::AtomicCount* counts, | |
| 426 HistogramSamples::Metadata* meta); | |
| 382 | 427 |
| 428 friend BASE_EXPORT HistogramBase* CreatePersistentHistogram( | |
| 429 PersistentMemoryAllocator* allocator, | |
| 430 PersistentHistogramData* histogram_data); | |
| 383 friend BASE_EXPORT HistogramBase* DeserializeHistogramInfo( | 431 friend BASE_EXPORT HistogramBase* DeserializeHistogramInfo( |
| 384 base::PickleIterator* iter); | 432 base::PickleIterator* iter); |
| 385 static HistogramBase* DeserializeInfoImpl(base::PickleIterator* iter); | 433 static HistogramBase* DeserializeInfoImpl(base::PickleIterator* iter); |
| 386 | 434 |
| 387 DISALLOW_COPY_AND_ASSIGN(BooleanHistogram); | 435 DISALLOW_COPY_AND_ASSIGN(BooleanHistogram); |
| 388 }; | 436 }; |
| 389 | 437 |
| 390 //------------------------------------------------------------------------------ | 438 //------------------------------------------------------------------------------ |
| 391 | 439 |
| 392 // CustomHistogram is a histogram for a set of custom integers. | 440 // CustomHistogram is a histogram for a set of custom integers. |
| (...skipping 19 matching lines...) Expand all Loading... | |
| 412 | 460 |
| 413 // Helper method for transforming an array of valid enumeration values | 461 // Helper method for transforming an array of valid enumeration values |
| 414 // to the std::vector<int> expected by UMA_HISTOGRAM_CUSTOM_ENUMERATION. | 462 // to the std::vector<int> expected by UMA_HISTOGRAM_CUSTOM_ENUMERATION. |
| 415 // This function ensures that a guard bucket exists right after any | 463 // This function ensures that a guard bucket exists right after any |
| 416 // valid sample value (unless the next higher sample is also a valid value), | 464 // valid sample value (unless the next higher sample is also a valid value), |
| 417 // so that invalid samples never fall into the same bucket as valid samples. | 465 // so that invalid samples never fall into the same bucket as valid samples. |
| 418 // TODO(kaiwang): Change name to ArrayToCustomEnumRanges. | 466 // TODO(kaiwang): Change name to ArrayToCustomEnumRanges. |
| 419 static std::vector<Sample> ArrayToCustomRanges(const Sample* values, | 467 static std::vector<Sample> ArrayToCustomRanges(const Sample* values, |
| 420 size_t num_values); | 468 size_t num_values); |
| 421 protected: | 469 protected: |
| 470 class Factory; | |
| 471 | |
| 422 CustomHistogram(const std::string& name, | 472 CustomHistogram(const std::string& name, |
| 423 const BucketRanges* ranges); | 473 const BucketRanges* ranges); |
| 424 | 474 |
| 475 CustomHistogram(const std::string& name, | |
| 476 const BucketRanges* ranges, | |
| 477 HistogramBase::AtomicCount* counts, | |
| 478 size_t counts_size, | |
| 479 HistogramSamples::Metadata* meta); | |
| 480 | |
| 425 // HistogramBase implementation: | 481 // HistogramBase implementation: |
| 426 bool SerializeInfoImpl(base::Pickle* pickle) const override; | 482 bool SerializeInfoImpl(base::Pickle* pickle) const override; |
| 427 | 483 |
| 428 double GetBucketSize(Count current, size_t i) const override; | 484 double GetBucketSize(Count current, size_t i) const override; |
| 429 | 485 |
| 430 private: | 486 private: |
| 487 friend BASE_EXPORT HistogramBase* CreatePersistentHistogram( | |
| 488 PersistentMemoryAllocator* allocator, | |
| 489 PersistentHistogramData* histogram_data); | |
| 431 friend BASE_EXPORT HistogramBase* DeserializeHistogramInfo( | 490 friend BASE_EXPORT HistogramBase* DeserializeHistogramInfo( |
| 432 base::PickleIterator* iter); | 491 base::PickleIterator* iter); |
| 433 static HistogramBase* DeserializeInfoImpl(base::PickleIterator* iter); | 492 static HistogramBase* DeserializeInfoImpl(base::PickleIterator* iter); |
| 434 | 493 |
| 435 static bool ValidateCustomRanges(const std::vector<Sample>& custom_ranges); | 494 static bool ValidateCustomRanges(const std::vector<Sample>& custom_ranges); |
| 436 static BucketRanges* CreateBucketRangesFromCustomRanges( | |
| 437 const std::vector<Sample>& custom_ranges); | |
| 438 | 495 |
| 439 DISALLOW_COPY_AND_ASSIGN(CustomHistogram); | 496 DISALLOW_COPY_AND_ASSIGN(CustomHistogram); |
| 440 }; | 497 }; |
| 441 | 498 |
| 442 } // namespace base | 499 } // namespace base |
| 443 | 500 |
| 444 #endif // BASE_METRICS_HISTOGRAM_H_ | 501 #endif // BASE_METRICS_HISTOGRAM_H_ |
| OLD | NEW |