Chromium Code Reviews| Index: content/browser/dom_storage/dom_storage_context_impl.cc |
| diff --git a/content/browser/dom_storage/dom_storage_context_impl.cc b/content/browser/dom_storage/dom_storage_context_impl.cc |
| index 1e6afa770e521e38a77f85825d066a4760759e4e..26a2da93845a20522f9eb3634d11b90660835233 100644 |
| --- a/content/browser/dom_storage/dom_storage_context_impl.cc |
| +++ b/content/browser/dom_storage/dom_storage_context_impl.cc |
| @@ -13,6 +13,8 @@ |
| #include "base/files/file_util.h" |
| #include "base/guid.h" |
| #include "base/location.h" |
| +#include "base/metrics/histogram.h" |
| +#include "base/sys_info.h" |
| #include "base/time/time.h" |
| #include "base/trace_event/memory_dump_manager.h" |
| #include "base/trace_event/process_memory_dump.h" |
| @@ -28,12 +30,39 @@ |
| #include "storage/browser/quota/special_storage_policy.h" |
| namespace content { |
| +namespace { |
| -static const int kSessionStoraceScavengingSeconds = 60; |
| +// Limits on the cache size and number of areas in memory, over which the areas |
| +// are purged. |
| +#if defined(OS_ANDROID) |
| +const unsigned kMaxStorageAreaCount = 20; |
| +const size_t kMaxCacheSize = 2 * 1024 * 1024; |
| +#else |
| +const unsigned kMaxStorageAreaCount = 100; |
| +const size_t kMaxCacheSize = 20 * 1024 * 1024; |
| +#endif |
| + |
| +const int kSessionStoraceScavengingSeconds = 60; |
| // Offset the session storage namespace ids generated by different contexts |
| // to help identify when an id from one is mistakenly used in another. |
| -static int g_session_id_offset_sequence = 1; |
| +int g_session_id_offset_sequence = 1; |
| + |
| +// Aggregates statistics from all the namespaces. |
| +DOMStorageNamespace::UsageStatistics GetTotalNamespaceStatistics( |
| + const DOMStorageContextImpl::StorageNamespaceMap& namespace_map) { |
| + DOMStorageNamespace::UsageStatistics total_stats = {0}; |
| + for (const auto& it : namespace_map) { |
| + DOMStorageNamespace::UsageStatistics stats = |
| + it.second->GetUsageStatistics(); |
| + total_stats.total_cache_size += stats.total_cache_size; |
| + total_stats.total_area_count += stats.total_area_count; |
| + total_stats.inactive_area_count += stats.inactive_area_count; |
| + } |
| + return total_stats; |
| +} |
| + |
| +} // namespace |
| DOMStorageContextImpl::DOMStorageContextImpl( |
| const base::FilePath& localstorage_directory, |
| @@ -47,7 +76,8 @@ DOMStorageContextImpl::DOMStorageContextImpl( |
| is_shutdown_(false), |
| force_keep_session_state_(false), |
| special_storage_policy_(special_storage_policy), |
| - scavenging_started_(false) { |
| + scavenging_started_(false), |
| + is_low_end_device_(base::SysInfo::IsLowEndDevice()) { |
| // AtomicSequenceNum starts at 0 but we want to start session |
| // namespace ids at one since zero is reserved for the |
| // kLocalStorageNamespaceId. |
| @@ -396,6 +426,45 @@ void DOMStorageContextImpl::StartScavengingUnusedSessionStorage() { |
| } |
| } |
| +void DOMStorageContextImpl::PurgeMemory(PurgeOption purge_option) { |
| + if (is_shutdown_) |
| + return; |
| + |
| + DOMStorageNamespace::UsageStatistics initial_stats = |
| + GetTotalNamespaceStatistics(namespaces_); |
| + |
| + // Track the total localStorage cache size. |
| + UMA_HISTOGRAM_CUSTOM_COUNTS("LocalStorage.BrowserLocalStorageCacheSizeInKB", |
| + initial_stats.total_cache_size / 1024, 0, 100000, |
|
Mark P
2016/05/23 18:27:14
There is already an "underflow" bucket; please use
ssid
2016/05/23 18:42:17
Done.
|
| + 50); |
| + |
| + if (purge_option == PURGE_IF_NEEDED) { |
| + // Purging is done based on the cache sizes without including the database |
| + // size since it can be expensive trying to estimate the sqlite usage for |
| + // all databases. For low end devices purge all inactive areas. |
| + bool should_purge = |
| + (is_low_end_device_ && initial_stats.inactive_area_count) || |
| + initial_stats.total_cache_size > kMaxCacheSize || |
| + initial_stats.total_area_count > kMaxStorageAreaCount; |
| + if (!should_purge) |
| + return; |
| + |
| + purge_option = PURGE_UNOPENED; |
| + } |
| + |
| + bool aggressively = purge_option == PURGE_AGGRESSIVE; |
| + for (const auto& it : namespaces_) |
| + it.second->PurgeMemory(aggressively); |
| + |
| + // Track the size of cache purged. |
| + UMA_HISTOGRAM_CUSTOM_COUNTS( |
| + "LocalStorage.BrowserLocalStorageCachePurgedInKB", |
| + (initial_stats.total_cache_size - |
| + GetTotalNamespaceStatistics(namespaces_).total_cache_size) / |
| + 1024, |
| + 0, 100000, 50); |
| +} |
| + |
| bool DOMStorageContextImpl::OnMemoryDump( |
| const base::trace_event::MemoryDumpArgs& args, |
| base::trace_event::ProcessMemoryDump* pmd) { |