[go: nahoru, domu]

blob: ebc116cd60bc89e1fed89c89b6f6bd037010aa30 [file] [log] [blame]
michaeln10e5fc352017-02-07 02:07:581// Copyright 2016 The Chromium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include "storage/browser/quota/quota_settings.h"
6
7#include <algorithm>
Victor Costanb410d1a2020-02-12 05:03:228#include <limits>
Jarryd451ab7b2019-02-12 06:39:069#include <memory>
Victor Costanb410d1a2020-02-12 05:03:2210#include <utility>
michaeln10e5fc352017-02-07 02:07:5811
Sebastien Marchand6d0558fd2019-01-25 16:49:3712#include "base/bind.h"
michaelnfa4c89402017-04-11 02:36:2013#include "base/rand_util.h"
Sebastien Marchand75a7cdf2018-11-13 23:47:0314#include "base/system/sys_info.h"
Gabriel Charette44db1422018-08-06 11:19:3315#include "base/task/post_task.h"
Gabriel Charette77285f42020-02-26 17:01:2316#include "base/task/thread_pool.h"
Etienne Pierre-Doray57cf4702018-11-16 17:04:1417#include "base/threading/scoped_blocking_call.h"
Kevin Marshallf1bf4e52017-08-15 19:37:5818#include "build/build_config.h"
Jarryd1f02b902019-11-07 03:29:5719#include "storage/browser/quota/quota_device_info_helper.h"
Jarryd7a79f0662019-01-24 07:26:4420#include "storage/browser/quota/quota_features.h"
Oscar Johansson357dd5c2018-08-07 10:42:0221#include "storage/browser/quota/quota_macros.h"
michaeln10e5fc352017-02-07 02:07:5822
23namespace storage {
24
michaelnfa4c89402017-04-11 02:36:2025namespace {
26
Ramin Halavati57e618932019-10-31 12:46:4727const int64_t kMBytes = 1024 * 1024;
28const int kRandomizedPercentage = 10;
Caitlin Fischer31f178122020-09-29 11:35:1529const double kDefaultPerHostRatio = 0.75;
Ramin Halavatif8e6df82020-10-05 21:39:4630const double kIncognitoQuotaRatioLowerBound = 0.15;
31const double kIncognitoQuotaRatioUpperBound = 0.2;
Ramin Halavati57e618932019-10-31 12:46:4732
michaelnfa4c89402017-04-11 02:36:2033// Skews |value| by +/- |percent|.
34int64_t RandomizeByPercent(int64_t value, int percent) {
35 double random_percent = (base::RandDouble() - 0.5) * percent * 2;
36 return value + (value * (random_percent / 100.0));
37}
38
Victor Costanb410d1a2020-02-12 05:03:2239QuotaSettings CalculateIncognitoDynamicSettings(
Ramin Halavati57e618932019-10-31 12:46:4740 int64_t physical_memory_amount) {
Ramin Halavatif8e6df82020-10-05 21:39:4641 // The incognito pool size is a fraction of the amount of system memory.
42 double incognito_pool_size_ratio =
43 kIncognitoQuotaRatioLowerBound +
44 (base::RandDouble() *
45 (kIncognitoQuotaRatioUpperBound - kIncognitoQuotaRatioLowerBound));
Ramin Halavati57e618932019-10-31 12:46:4746
Victor Costanb410d1a2020-02-12 05:03:2247 QuotaSettings settings;
Ramin Halavatif8e6df82020-10-05 21:39:4648 settings.pool_size =
49 static_cast<int64_t>(physical_memory_amount * incognito_pool_size_ratio);
Ramin Halavati57e618932019-10-31 12:46:4750 settings.per_host_quota = settings.pool_size / 3;
51 settings.session_only_per_host_quota = settings.per_host_quota;
52 settings.refresh_interval = base::TimeDelta::Max();
53 return settings;
54}
55
Victor Costanb410d1a2020-02-12 05:03:2256base::Optional<QuotaSettings> CalculateNominalDynamicSettings(
michaeln10e5fc352017-02-07 02:07:5857 const base::FilePath& partition_path,
Jarryd451ab7b2019-02-12 06:39:0658 bool is_incognito,
Jarryd1f02b902019-11-07 03:29:5759 QuotaDeviceInfoHelper* device_info_helper) {
Etienne Bergeron436d42212019-02-26 17:15:1260 base::ScopedBlockingCall scoped_blocking_call(FROM_HERE,
61 base::BlockingType::MAY_BLOCK);
michaeln10e5fc352017-02-07 02:07:5862
63 if (is_incognito) {
Ramin Halavati57e618932019-10-31 12:46:4764 return CalculateIncognitoDynamicSettings(
Jarryd1f02b902019-11-07 03:29:5765 device_info_helper->AmountOfPhysicalMemory());
michaeln10e5fc352017-02-07 02:07:5866 }
67
Victor Costanf39940a2019-12-02 19:37:2968 // The fraction of the device's storage the browser is willing to use for
69 // temporary storage.
Junbo Ke0f792b52021-01-26 22:58:1370 const double kTemporaryPoolSizeRatio = features::kPoolSizeRatio.Get();
71
72 // The fixed size in bytes the browser is willing to use for temporary
73 // storage. If both the ratio and the absolute size are set, the lower value
74 // will be honored.
75 const int64_t kTemporaryPoolSizeFixed =
76 static_cast<int64_t>(features::kPoolSizeBytes.Get());
michaeln10e5fc352017-02-07 02:07:5877
Joshua Bell1e5b5702018-02-28 06:36:2978 // The amount of the device's storage the browser attempts to
Joshua Bell9508bf4e2018-02-23 18:05:2079 // keep free. If there is less than this amount of storage free
80 // on the device, Chrome will grant 0 quota to origins.
Joshua Bell1e5b5702018-02-28 06:36:2981 //
Joshua Bell73b18e32018-05-02 23:06:2982 // Prior to M66, this was 10% of total storage instead of a fixed value on
83 // all devices. Now the minimum of a fixed value (2GB) and 10% is used to
84 // limit the reserve on devices with plenty of storage, but scale down for
85 // devices with extremely limited storage.
86 // * 1TB storage -- min(100GB,2GB) = 2GB
87 // * 500GB storage -- min(50GB,2GB) = 2GB
88 // * 64GB storage -- min(6GB,2GB) = 2GB
89 // * 16GB storage -- min(1.6GB,2GB) = 1.6GB
90 // * 8GB storage -- min(800MB,2GB) = 800MB
Junbo Ke0f792b52021-01-26 22:58:1391 const int64_t kShouldRemainAvailableFixed =
92 static_cast<int64_t>(features::kShouldRemainAvailableBytes.Get());
93 const double kShouldRemainAvailableRatio =
94 features::kShouldRemainAvailableRatio.Get();
michaeln10e5fc352017-02-07 02:07:5895
Joshua Bell1e5b5702018-02-28 06:36:2996 // The amount of the device's storage the browser attempts to
Joshua Bell9508bf4e2018-02-23 18:05:2097 // keep free at all costs. Data will be aggressively evicted.
Joshua Bell1e5b5702018-02-28 06:36:2998 //
Joshua Bell73b18e32018-05-02 23:06:2999 // Prior to M66, this was 1% of total storage instead of a fixed value on
100 // all devices. Now the minimum of a fixed value (1GB) and 1% is used to
101 // limit the reserve on devices with plenty of storage, but scale down for
102 // devices with extremely limited storage.
103 // * 1TB storage -- min(10GB,1GB) = 1GB
104 // * 500GB storage -- min(5GB,1GB) = 1GB
105 // * 64GB storage -- min(640MB,1GB) = 640MB
106 // * 16GB storage -- min(160MB,1GB) = 160MB
107 // * 8GB storage -- min(80MB,1GB) = 80MB
Junbo Ke0f792b52021-01-26 22:58:13108 const int64_t kMustRemainAvailableFixed =
109 static_cast<int64_t>(features::kMustRemainAvailableBytes.Get());
110 const double kMustRemainAvailableRatio =
111 features::kMustRemainAvailableRatio.Get();
michaeln10e5fc352017-02-07 02:07:58112
Victor Costanf39940a2019-12-02 19:37:29113 // The fraction of the temporary pool that can be utilized by a single host.
Jarryd48e85682020-10-01 01:51:19114 const double kPerHostTemporaryRatio = kDefaultPerHostRatio;
michaeln10e5fc352017-02-07 02:07:58115
michaelnfa4c89402017-04-11 02:36:20116 // SessionOnly (or ephemeral) origins are allotted a fraction of what
117 // normal origins are provided, and the amount is capped to a hard limit.
118 const double kSessionOnlyHostQuotaRatio = 0.1; // 10%
119 const int64_t kMaxSessionOnlyHostQuota = 300 * kMBytes;
120
Victor Costanb410d1a2020-02-12 05:03:22121 QuotaSettings settings;
michaeln10e5fc352017-02-07 02:07:58122
Jarryd1f02b902019-11-07 03:29:57123 int64_t total = device_info_helper->AmountOfTotalDiskSpace(partition_path);
michaeln10e5fc352017-02-07 02:07:58124 if (total == -1) {
125 LOG(ERROR) << "Unable to compute QuotaSettings.";
126 return base::nullopt;
127 }
128
Junbo Ke0f792b52021-01-26 22:58:13129 // Pool size calculated by ratio.
130 int64_t pool_size_by_ratio = total * kTemporaryPoolSizeRatio;
131
132 int64_t pool_size =
133 kTemporaryPoolSizeFixed > 0
134 ? std::min(kTemporaryPoolSizeFixed, pool_size_by_ratio)
135 : pool_size_by_ratio;
michaeln10e5fc352017-02-07 02:07:58136
137 settings.pool_size = pool_size;
Joshua Bell73b18e32018-05-02 23:06:29138 settings.should_remain_available =
139 std::min(kShouldRemainAvailableFixed,
140 static_cast<int64_t>(total * kShouldRemainAvailableRatio));
141 settings.must_remain_available =
142 std::min(kMustRemainAvailableFixed,
143 static_cast<int64_t>(total * kMustRemainAvailableRatio));
Jarryd7a79f0662019-01-24 07:26:44144 settings.per_host_quota = pool_size * kPerHostTemporaryRatio;
michaelnfa4c89402017-04-11 02:36:20145 settings.session_only_per_host_quota = std::min(
146 RandomizeByPercent(kMaxSessionOnlyHostQuota, kRandomizedPercentage),
147 static_cast<int64_t>(settings.per_host_quota *
148 kSessionOnlyHostQuotaRatio));
michaeln10e5fc352017-02-07 02:07:58149 settings.refresh_interval = base::TimeDelta::FromSeconds(60);
150 return settings;
151}
152
153} // namespace
taptede6d878e2017-06-24 01:53:45154
155void GetNominalDynamicSettings(const base::FilePath& partition_path,
156 bool is_incognito,
Jarryd1f02b902019-11-07 03:29:57157 QuotaDeviceInfoHelper* device_info_helper,
taptede6d878e2017-06-24 01:53:45158 OptionalQuotaSettingsCallback callback) {
Gabriel Charette77285f42020-02-26 17:01:23159 base::ThreadPool::PostTaskAndReplyWithResult(
taptede6d878e2017-06-24 01:53:45160 FROM_HERE,
Gabriel Charette77285f42020-02-26 17:01:23161 {base::MayBlock(), base::TaskPriority::USER_VISIBLE,
taptede6d878e2017-06-24 01:53:45162 base::TaskShutdownBehavior::CONTINUE_ON_SHUTDOWN},
163 base::BindOnce(&CalculateNominalDynamicSettings, partition_path,
Jarryd1f02b902019-11-07 03:29:57164 is_incognito, base::Unretained(device_info_helper)),
taptede6d878e2017-06-24 01:53:45165 std::move(callback));
166}
167
Jarryd1f02b902019-11-07 03:29:57168QuotaDeviceInfoHelper* GetDefaultDeviceInfoHelper() {
169 static base::NoDestructor<QuotaDeviceInfoHelper> singleton;
Jarryd451ab7b2019-02-12 06:39:06170 return singleton.get();
171}
172
Ramin Halavatif8e6df82020-10-05 21:39:46173double GetIncognitoQuotaRatioLowerBound_ForTesting() {
174 return kIncognitoQuotaRatioLowerBound;
175}
176double GetIncognitoQuotaRatioUpperBound_ForTesting() {
177 return kIncognitoQuotaRatioUpperBound;
178}
179
taptede6d878e2017-06-24 01:53:45180} // namespace storage