| Index: webkit/quota/quota_temporary_storage_evictor.cc
|
| diff --git a/webkit/quota/quota_temporary_storage_evictor.cc b/webkit/quota/quota_temporary_storage_evictor.cc
|
| deleted file mode 100644
|
| index 5e4e088a1706f3f080d0de3dfec10ae93f8f9f79..0000000000000000000000000000000000000000
|
| --- a/webkit/quota/quota_temporary_storage_evictor.cc
|
| +++ /dev/null
|
| @@ -1,261 +0,0 @@
|
| -// Copyright (c) 2011 The Chromium Authors. All rights reserved.
|
| -// Use of this source code is governed by a BSD-style license that can be
|
| -// found in the LICENSE file.
|
| -
|
| -#include "webkit/quota/quota_temporary_storage_evictor.h"
|
| -
|
| -#include <algorithm>
|
| -
|
| -#include "base/bind.h"
|
| -#include "base/metrics/histogram.h"
|
| -#include "googleurl/src/gurl.h"
|
| -#include "webkit/quota/quota_manager.h"
|
| -
|
| -#define UMA_HISTOGRAM_MBYTES(name, sample) \
|
| - UMA_HISTOGRAM_CUSTOM_COUNTS( \
|
| - (name), static_cast<int>((sample) / kMBytes), \
|
| - 1, 10 * 1024 * 1024 /* 10TB */, 100)
|
| -
|
| -#define UMA_HISTOGRAM_MINUTES(name, sample) \
|
| - UMA_HISTOGRAM_CUSTOM_TIMES( \
|
| - (name), (sample), \
|
| - base::TimeDelta::FromMinutes(1), \
|
| - base::TimeDelta::FromDays(1), 50)
|
| -
|
| -namespace {
|
| -const int64 kMBytes = 1024 * 1024;
|
| -const double kUsageRatioToStartEviction = 0.7;
|
| -const int kThresholdOfErrorsToStopEviction = 5;
|
| -const int kHistogramReportIntervalMinutes = 60;
|
| -}
|
| -
|
| -namespace quota {
|
| -
|
| -const int QuotaTemporaryStorageEvictor::
|
| - kMinAvailableDiskSpaceToStartEvictionNotSpecified = -1;
|
| -
|
| -QuotaTemporaryStorageEvictor::EvictionRoundStatistics::EvictionRoundStatistics()
|
| - : in_round(false),
|
| - is_initialized(false),
|
| - usage_overage_at_round(-1),
|
| - diskspace_shortage_at_round(-1),
|
| - usage_on_beginning_of_round(-1),
|
| - usage_on_end_of_round(-1),
|
| - num_evicted_origins_in_round(0) {
|
| -}
|
| -
|
| -QuotaTemporaryStorageEvictor::QuotaTemporaryStorageEvictor(
|
| - QuotaEvictionHandler* quota_eviction_handler,
|
| - int64 interval_ms)
|
| - : min_available_disk_space_to_start_eviction_(
|
| - kMinAvailableDiskSpaceToStartEvictionNotSpecified),
|
| - quota_eviction_handler_(quota_eviction_handler),
|
| - interval_ms_(interval_ms),
|
| - repeated_eviction_(true),
|
| - weak_factory_(this) {
|
| - DCHECK(quota_eviction_handler);
|
| -}
|
| -
|
| -QuotaTemporaryStorageEvictor::~QuotaTemporaryStorageEvictor() {
|
| -}
|
| -
|
| -void QuotaTemporaryStorageEvictor::GetStatistics(
|
| - std::map<std::string, int64>* statistics) {
|
| - DCHECK(statistics);
|
| -
|
| - (*statistics)["errors-on-evicting-origin"] =
|
| - statistics_.num_errors_on_evicting_origin;
|
| - (*statistics)["errors-on-getting-usage-and-quota"] =
|
| - statistics_.num_errors_on_getting_usage_and_quota;
|
| - (*statistics)["evicted-origins"] =
|
| - statistics_.num_evicted_origins;
|
| - (*statistics)["eviction-rounds"] =
|
| - statistics_.num_eviction_rounds;
|
| - (*statistics)["skipped-eviction-rounds"] =
|
| - statistics_.num_skipped_eviction_rounds;
|
| -}
|
| -
|
| -void QuotaTemporaryStorageEvictor::ReportPerRoundHistogram() {
|
| - DCHECK(round_statistics_.in_round);
|
| - DCHECK(round_statistics_.is_initialized);
|
| -
|
| - base::Time now = base::Time::Now();
|
| - UMA_HISTOGRAM_TIMES("Quota.TimeSpentToAEvictionRound",
|
| - now - round_statistics_.start_time);
|
| - if (!time_of_end_of_last_round_.is_null())
|
| - UMA_HISTOGRAM_MINUTES("Quota.TimeDeltaOfEvictionRounds",
|
| - now - time_of_end_of_last_round_);
|
| - UMA_HISTOGRAM_MBYTES("Quota.UsageOverageOfTemporaryGlobalStorage",
|
| - round_statistics_.usage_overage_at_round);
|
| - UMA_HISTOGRAM_MBYTES("Quota.DiskspaceShortage",
|
| - round_statistics_.diskspace_shortage_at_round);
|
| - UMA_HISTOGRAM_MBYTES("Quota.EvictedBytesPerRound",
|
| - round_statistics_.usage_on_beginning_of_round -
|
| - round_statistics_.usage_on_end_of_round);
|
| - UMA_HISTOGRAM_COUNTS("Quota.NumberOfEvictedOriginsPerRound",
|
| - round_statistics_.num_evicted_origins_in_round);
|
| -}
|
| -
|
| -void QuotaTemporaryStorageEvictor::ReportPerHourHistogram() {
|
| - Statistics stats_in_hour(statistics_);
|
| - stats_in_hour.subtract_assign(previous_statistics_);
|
| - previous_statistics_ = statistics_;
|
| -
|
| - UMA_HISTOGRAM_COUNTS("Quota.ErrorsOnEvictingOriginPerHour",
|
| - stats_in_hour.num_errors_on_evicting_origin);
|
| - UMA_HISTOGRAM_COUNTS("Quota.ErrorsOnGettingUsageAndQuotaPerHour",
|
| - stats_in_hour.num_errors_on_getting_usage_and_quota);
|
| - UMA_HISTOGRAM_COUNTS("Quota.EvictedOriginsPerHour",
|
| - stats_in_hour.num_evicted_origins);
|
| - UMA_HISTOGRAM_COUNTS("Quota.EvictionRoundsPerHour",
|
| - stats_in_hour.num_eviction_rounds);
|
| - UMA_HISTOGRAM_COUNTS("Quota.SkippedEvictionRoundsPerHour",
|
| - stats_in_hour.num_skipped_eviction_rounds);
|
| -}
|
| -
|
| -void QuotaTemporaryStorageEvictor::OnEvictionRoundStarted() {
|
| - if (round_statistics_.in_round)
|
| - return;
|
| - round_statistics_.in_round = true;
|
| - round_statistics_.start_time = base::Time::Now();
|
| - ++statistics_.num_eviction_rounds;
|
| -}
|
| -
|
| -void QuotaTemporaryStorageEvictor::OnEvictionRoundFinished() {
|
| - // Check if skipped round
|
| - if (round_statistics_.num_evicted_origins_in_round) {
|
| - ReportPerRoundHistogram();
|
| - time_of_end_of_last_nonskipped_round_ = base::Time::Now();
|
| - } else {
|
| - ++statistics_.num_skipped_eviction_rounds;
|
| - }
|
| - // Reset stats for next round.
|
| - round_statistics_ = EvictionRoundStatistics();
|
| -}
|
| -
|
| -void QuotaTemporaryStorageEvictor::Start() {
|
| - DCHECK(CalledOnValidThread());
|
| - StartEvictionTimerWithDelay(0);
|
| -
|
| - if (histogram_timer_.IsRunning())
|
| - return;
|
| -
|
| - histogram_timer_.Start(
|
| - FROM_HERE, base::TimeDelta::FromMinutes(kHistogramReportIntervalMinutes),
|
| - this, &QuotaTemporaryStorageEvictor::ReportPerHourHistogram);
|
| -}
|
| -
|
| -void QuotaTemporaryStorageEvictor::StartEvictionTimerWithDelay(int delay_ms) {
|
| - if (eviction_timer_.IsRunning())
|
| - return;
|
| - eviction_timer_.Start(FROM_HERE, base::TimeDelta::FromMilliseconds(delay_ms),
|
| - this, &QuotaTemporaryStorageEvictor::ConsiderEviction);
|
| -}
|
| -
|
| -void QuotaTemporaryStorageEvictor::ConsiderEviction() {
|
| - OnEvictionRoundStarted();
|
| -
|
| - // Get usage and disk space, then continue.
|
| - quota_eviction_handler_->GetUsageAndQuotaForEviction(
|
| - base::Bind(&QuotaTemporaryStorageEvictor::OnGotUsageAndQuotaForEviction,
|
| - weak_factory_.GetWeakPtr()));
|
| -}
|
| -
|
| -void QuotaTemporaryStorageEvictor::OnGotUsageAndQuotaForEviction(
|
| - QuotaStatusCode status,
|
| - const UsageAndQuota& qau) {
|
| - DCHECK(CalledOnValidThread());
|
| -
|
| - int64 usage = qau.global_limited_usage;
|
| - DCHECK_GE(usage, 0);
|
| -
|
| - if (status != kQuotaStatusOk)
|
| - ++statistics_.num_errors_on_getting_usage_and_quota;
|
| -
|
| - int64 usage_overage = std::max(
|
| - static_cast<int64>(0),
|
| - usage - static_cast<int64>(qau.quota * kUsageRatioToStartEviction));
|
| -
|
| - // min_available_disk_space_to_start_eviction_ might be < 0 if no value
|
| - // is explicitly configured yet.
|
| - int64 diskspace_shortage = std::max(
|
| - static_cast<int64>(0),
|
| - min_available_disk_space_to_start_eviction_ - qau.available_disk_space);
|
| -
|
| - if (!round_statistics_.is_initialized) {
|
| - round_statistics_.usage_overage_at_round = usage_overage;
|
| - round_statistics_.diskspace_shortage_at_round = diskspace_shortage;
|
| - round_statistics_.usage_on_beginning_of_round = usage;
|
| - round_statistics_.is_initialized = true;
|
| - }
|
| - round_statistics_.usage_on_end_of_round = usage;
|
| -
|
| - int64 amount_to_evict = std::max(usage_overage, diskspace_shortage);
|
| - if (status == kQuotaStatusOk && amount_to_evict > 0) {
|
| - // Space is getting tight. Get the least recently used origin and continue.
|
| - // TODO(michaeln): if the reason for eviction is low physical disk space,
|
| - // make 'unlimited' origins subject to eviction too.
|
| - quota_eviction_handler_->GetLRUOrigin(
|
| - kStorageTypeTemporary,
|
| - base::Bind(&QuotaTemporaryStorageEvictor::OnGotLRUOrigin,
|
| - weak_factory_.GetWeakPtr()));
|
| - } else {
|
| - if (repeated_eviction_) {
|
| - // No action required, sleep for a while and check again later.
|
| - if (statistics_.num_errors_on_getting_usage_and_quota <
|
| - kThresholdOfErrorsToStopEviction) {
|
| - StartEvictionTimerWithDelay(interval_ms_);
|
| - } else {
|
| - // TODO(dmikurube): Try restarting eviction after a while.
|
| - LOG(WARNING) << "Stopped eviction of temporary storage due to errors "
|
| - "in GetUsageAndQuotaForEviction.";
|
| - }
|
| - }
|
| - OnEvictionRoundFinished();
|
| - }
|
| -
|
| - // TODO(dmikurube): Add error handling for the case status != kQuotaStatusOk.
|
| -}
|
| -
|
| -void QuotaTemporaryStorageEvictor::OnGotLRUOrigin(const GURL& origin) {
|
| - DCHECK(CalledOnValidThread());
|
| -
|
| - if (origin.is_empty()) {
|
| - if (repeated_eviction_)
|
| - StartEvictionTimerWithDelay(interval_ms_);
|
| - OnEvictionRoundFinished();
|
| - return;
|
| - }
|
| -
|
| - quota_eviction_handler_->EvictOriginData(origin, kStorageTypeTemporary,
|
| - base::Bind(
|
| - &QuotaTemporaryStorageEvictor::OnEvictionComplete,
|
| - weak_factory_.GetWeakPtr()));
|
| -}
|
| -
|
| -void QuotaTemporaryStorageEvictor::OnEvictionComplete(
|
| - QuotaStatusCode status) {
|
| - DCHECK(CalledOnValidThread());
|
| -
|
| - // Just calling ConsiderEviction() or StartEvictionTimerWithDelay() here is
|
| - // ok. No need to deal with the case that all of the Delete operations fail
|
| - // for a certain origin. It doesn't result in trying to evict the same
|
| - // origin permanently. The evictor skips origins which had deletion errors
|
| - // a few times.
|
| -
|
| - if (status == kQuotaStatusOk) {
|
| - ++statistics_.num_evicted_origins;
|
| - ++round_statistics_.num_evicted_origins_in_round;
|
| - // We many need to get rid of more space so reconsider immediately.
|
| - ConsiderEviction();
|
| - } else {
|
| - ++statistics_.num_errors_on_evicting_origin;
|
| - if (repeated_eviction_) {
|
| - // Sleep for a while and retry again until we see too many errors.
|
| - StartEvictionTimerWithDelay(interval_ms_);
|
| - }
|
| - OnEvictionRoundFinished();
|
| - }
|
| -}
|
| -
|
| -} // namespace quota
|
|
|