Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(834)

Unified Diff: base/metrics/histogram_persistence.cc

Issue 1734033003: Add support for persistent sparse histograms. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: some 'git cl format' changes and other cosmetic improvements Created 4 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: base/metrics/histogram_persistence.cc
diff --git a/base/metrics/histogram_persistence.cc b/base/metrics/histogram_persistence.cc
index f18d17528354329cd4995615d2451f6a52c59302..77515fffe9e3333899330aa751b751184ec3f574 100644
--- a/base/metrics/histogram_persistence.cc
+++ b/base/metrics/histogram_persistence.cc
@@ -10,6 +10,7 @@
#include "base/metrics/histogram.h"
#include "base/metrics/histogram_base.h"
#include "base/metrics/histogram_samples.h"
+#include "base/metrics/sparse_histogram.h"
#include "base/metrics/statistics_recorder.h"
#include "base/synchronization/lock.h"
@@ -238,6 +239,17 @@ HistogramBase* CreatePersistentHistogram(
return nullptr;
}
+ // Sparse histograms are quite different so handle them as a special case.
+ if (histogram_data_ptr->histogram_type == SPARSE_HISTOGRAM) {
+ HistogramBase* histogram = SparseHistogram::PersistentGet(
+ allocator,
+ histogram_data_ptr->name,
+ &histogram_data_ptr->samples_metadata,
+ &histogram_data_ptr->logged_metadata);
+ DCHECK(histogram);
+ return histogram;
+ }
+
// Copy the histogram_data to local storage because anything in persistent
// memory cannot be trusted as it could be changed at any moment by a
// malicious actor that shares access. The contents of histogram_data are
@@ -419,48 +431,68 @@ HistogramBase* AllocatePersistentHistogram(
return nullptr;
}
- // If CalculateRequiredCountsBytes() returns zero then the bucket_count
- // was not valid.
- size_t bucket_count = bucket_ranges->bucket_count();
- size_t counts_bytes = CalculateRequiredCountsBytes(bucket_count);
- if (!counts_bytes) {
- NOTREACHED();
- return nullptr;
- }
+ // Create all the metadata necessary for a persistent histogram. Sparse
+ // histograms are quite different so handle them as a special case.
+ PersistentMemoryAllocator::Reference histogram_ref = 0;
+ PersistentHistogramData* histogram_data = nullptr;
+ if (histogram_type == SPARSE_HISTOGRAM) {
+ histogram_ref = allocator->Allocate(
+ offsetof(PersistentHistogramData, name) + name.length() + 1,
+ kTypeIdHistogram);
+ histogram_data = allocator->GetAsObject<PersistentHistogramData>(
+ histogram_ref, kTypeIdHistogram);
+ if (histogram_data) {
+ strcpy(histogram_data->name, name.c_str());
+ histogram_data->histogram_type = histogram_type;
+ histogram_data->flags = flags;
+ }
+ } else {
+ // If CalculateRequiredCountsBytes() returns zero then the bucket_count
grt (UTC plus 2) 2016/03/02 20:00:42 nit: move this comment into the "!counts_bytes" bl
bcwhite 2016/03/02 22:32:43 Done.
+ // was not valid.
+ size_t bucket_count = bucket_ranges->bucket_count();
+ size_t counts_bytes = CalculateRequiredCountsBytes(bucket_count);
+ if (!counts_bytes) {
+ NOTREACHED();
+ return nullptr;
+ }
- size_t ranges_bytes = (bucket_count + 1) * sizeof(HistogramBase::Sample);
- PersistentMemoryAllocator::Reference ranges_ref =
- allocator->Allocate(ranges_bytes, kTypeIdRangesArray);
- PersistentMemoryAllocator::Reference counts_ref =
- allocator->Allocate(counts_bytes, kTypeIdCountsArray);
- PersistentMemoryAllocator::Reference histogram_ref =
- allocator->Allocate(offsetof(PersistentHistogramData, name) +
- name.length() + 1, kTypeIdHistogram);
- HistogramBase::Sample* ranges_data =
- allocator->GetAsObject<HistogramBase::Sample>(ranges_ref,
- kTypeIdRangesArray);
- PersistentHistogramData* histogram_data =
- allocator->GetAsObject<PersistentHistogramData>(histogram_ref,
- kTypeIdHistogram);
-
- // Only continue here if all allocations were successful. If they weren't
- // there is no way to free the space but that's not really a problem since
- // the allocations only fail because the space is full and so any future
- // attempts will also fail.
- if (counts_ref && ranges_data && histogram_data) {
- strcpy(histogram_data->name, name.c_str());
- for (size_t i = 0; i < bucket_ranges->size(); ++i)
- ranges_data[i] = bucket_ranges->range(i);
-
- histogram_data->histogram_type = histogram_type;
- histogram_data->flags = flags;
- histogram_data->minimum = minimum;
- histogram_data->maximum = maximum;
- histogram_data->bucket_count = static_cast<uint32_t>(bucket_count);
- histogram_data->ranges_ref = ranges_ref;
- histogram_data->ranges_checksum = bucket_ranges->checksum();
- histogram_data->counts_ref = counts_ref;
+ size_t ranges_bytes = (bucket_count + 1) * sizeof(HistogramBase::Sample);
+ PersistentMemoryAllocator::Reference counts_ref =
+ allocator->Allocate(counts_bytes, kTypeIdCountsArray);
+ PersistentMemoryAllocator::Reference ranges_ref =
+ allocator->Allocate(ranges_bytes, kTypeIdRangesArray);
+ HistogramBase::Sample* ranges_data =
+ allocator->GetAsObject<HistogramBase::Sample>(ranges_ref,
+ kTypeIdRangesArray);
+ histogram_ref = allocator->Allocate(
+ offsetof(PersistentHistogramData, name) + name.length() + 1,
+ kTypeIdHistogram);
+ histogram_data = allocator->GetAsObject<PersistentHistogramData>(
+ histogram_ref, kTypeIdHistogram);
+
+ // Only continue here if all allocations were successful. If they weren't
+ // there is no way to free the space but that's not really a problem since
+ // the allocations only fail because the space is full and so any future
+ // attempts will also fail.
+ if (counts_ref && ranges_data && histogram_data) {
+ strcpy(histogram_data->name, name.c_str());
grt (UTC plus 2) 2016/03/02 20:00:42 nit: use memcpy since you know the size
bcwhite 2016/03/02 22:32:43 Done.
+ for (size_t i = 0; i < bucket_ranges->size(); ++i)
+ ranges_data[i] = bucket_ranges->range(i);
+
+ histogram_data->histogram_type = histogram_type;
+ histogram_data->flags = flags;
+ histogram_data->minimum = minimum;
+ histogram_data->maximum = maximum;
+ histogram_data->bucket_count = static_cast<uint32_t>(bucket_count);
grt (UTC plus 2) 2016/03/02 20:00:42 i think this is safe on account of CalculateRequir
bcwhite 2016/03/02 22:32:43 It's actually limited because any allocation that
+ histogram_data->ranges_ref = ranges_ref;
+ histogram_data->ranges_checksum = bucket_ranges->checksum();
+ histogram_data->counts_ref = counts_ref;
+ } else {
+ histogram_data = nullptr; // Clear this for proper handling below.
+ }
+ }
+ if (histogram_data) {
// Create the histogram using resources in persistent memory. This ends up
// resolving the "ref" values stored in histogram_data instad of just
// using what is already known above but avoids duplicating the switch

Powered by Google App Engine
This is Rietveld 408576698