Delete unused downloads page asset.
[chromium-blink-merge.git] / storage / browser / quota / quota_manager.h
blob506aa0ad05f806d9bd3ec58f1734ca2829a97229
1 // Copyright 2013 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.
5 #ifndef STORAGE_BROWSER_QUOTA_QUOTA_MANAGER_H_
6 #define STORAGE_BROWSER_QUOTA_QUOTA_MANAGER_H_
8 #include <deque>
9 #include <list>
10 #include <map>
11 #include <set>
12 #include <string>
13 #include <utility>
14 #include <vector>
16 #include "base/basictypes.h"
17 #include "base/callback.h"
18 #include "base/files/file_path.h"
19 #include "base/memory/ref_counted.h"
20 #include "base/memory/scoped_ptr.h"
21 #include "base/memory/weak_ptr.h"
22 #include "base/sequenced_task_runner_helpers.h"
23 #include "storage/browser/quota/quota_callbacks.h"
24 #include "storage/browser/quota/quota_client.h"
25 #include "storage/browser/quota/quota_database.h"
26 #include "storage/browser/quota/quota_task.h"
27 #include "storage/browser/quota/special_storage_policy.h"
28 #include "storage/browser/quota/storage_observer.h"
29 #include "storage/browser/storage_browser_export.h"
31 namespace base {
32 class FilePath;
33 class SequencedTaskRunner;
34 class SingleThreadTaskRunner;
37 namespace quota_internals {
38 class QuotaInternalsProxy;
41 namespace content {
42 class MockQuotaManager;
43 class MockStorageClient;
44 class QuotaManagerTest;
45 class StorageMonitorTest;
49 namespace storage {
51 class QuotaDatabase;
52 class QuotaManagerProxy;
53 class QuotaTemporaryStorageEvictor;
54 class StorageMonitor;
55 class UsageTracker;
57 struct QuotaManagerDeleter;
59 struct STORAGE_EXPORT UsageAndQuota {
60 int64 usage;
61 int64 global_limited_usage;
62 int64 quota;
63 int64 available_disk_space;
65 UsageAndQuota();
66 UsageAndQuota(int64 usage,
67 int64 global_limited_usage,
68 int64 quota,
69 int64 available_disk_space);
72 // TODO(calamity): Use this in the temporary storage eviction path.
73 // An interface for deciding which origin's temporary storage should be evicted
74 // when the quota is exceeded.
75 class STORAGE_EXPORT QuotaEvictionPolicy {
76 public:
77 // Returns the next origin to evict. It might return an empty GURL when there
78 // are no evictable origins.
79 virtual void GetEvictionOrigin(
80 const scoped_refptr<SpecialStoragePolicy>& special_storage_policy,
81 const std::map<GURL, int64>& usage_map,
82 int64 global_quota,
83 const GetOriginCallback& callback) = 0;
86 // An interface called by QuotaTemporaryStorageEvictor.
87 class STORAGE_EXPORT QuotaEvictionHandler {
88 public:
89 typedef StatusCallback EvictOriginDataCallback;
90 typedef base::Callback<void(QuotaStatusCode status,
91 const UsageAndQuota& usage_and_quota)>
92 UsageAndQuotaCallback;
94 // Returns next origin to evict. It might return an empty GURL when there are
95 // no evictable origins.
96 virtual void GetEvictionOrigin(StorageType type,
97 const GetOriginCallback& callback) = 0;
99 virtual void EvictOriginData(
100 const GURL& origin,
101 StorageType type,
102 const EvictOriginDataCallback& callback) = 0;
104 virtual void GetUsageAndQuotaForEviction(
105 const UsageAndQuotaCallback& callback) = 0;
107 protected:
108 virtual ~QuotaEvictionHandler() {}
111 struct UsageInfo {
112 UsageInfo(const std::string& host, StorageType type, int64 usage)
113 : host(host),
114 type(type),
115 usage(usage) {}
116 std::string host;
117 StorageType type;
118 int64 usage;
121 // The quota manager class. This class is instantiated per profile and
122 // held by the profile. With the exception of the constructor and the
123 // proxy() method, all methods should only be called on the IO thread.
124 class STORAGE_EXPORT QuotaManager
125 : public QuotaTaskObserver,
126 public QuotaEvictionHandler,
127 public base::RefCountedThreadSafe<QuotaManager, QuotaManagerDeleter> {
128 public:
129 typedef base::Callback<void(QuotaStatusCode,
130 int64 /* usage */,
131 int64 /* quota */)>
132 GetUsageAndQuotaCallback;
134 static const int64 kIncognitoDefaultQuotaLimit;
135 static const int64 kNoLimit;
137 QuotaManager(
138 bool is_incognito,
139 const base::FilePath& profile_path,
140 const scoped_refptr<base::SingleThreadTaskRunner>& io_thread,
141 const scoped_refptr<base::SequencedTaskRunner>& db_thread,
142 const scoped_refptr<SpecialStoragePolicy>& special_storage_policy);
144 // Returns a proxy object that can be used on any thread.
145 QuotaManagerProxy* proxy() { return proxy_.get(); }
147 // Called by clients or webapps. Returns usage per host.
148 void GetUsageInfo(const GetUsageInfoCallback& callback);
150 // Called by Web Apps.
151 // This method is declared as virtual to allow test code to override it.
152 virtual void GetUsageAndQuotaForWebApps(
153 const GURL& origin,
154 StorageType type,
155 const GetUsageAndQuotaCallback& callback);
157 // Called by StorageClients.
158 // This method is declared as virtual to allow test code to override it.
160 // For UnlimitedStorage origins, this version skips usage and quota handling
161 // to avoid extra query cost.
162 // Do not call this method for apps/user-facing code.
163 virtual void GetUsageAndQuota(
164 const GURL& origin,
165 StorageType type,
166 const GetUsageAndQuotaCallback& callback);
168 // Called by clients via proxy.
169 // Client storage should call this method when storage is accessed.
170 // Used to maintain LRU ordering.
171 void NotifyStorageAccessed(QuotaClient::ID client_id,
172 const GURL& origin,
173 StorageType type);
175 // Called by clients via proxy.
176 // Client storage must call this method whenever they have made any
177 // modifications that change the amount of data stored in their storage.
178 void NotifyStorageModified(QuotaClient::ID client_id,
179 const GURL& origin,
180 StorageType type,
181 int64 delta);
183 // Used to avoid evicting origins with open pages.
184 // A call to NotifyOriginInUse must be balanced by a later call
185 // to NotifyOriginNoLongerInUse.
186 void NotifyOriginInUse(const GURL& origin);
187 void NotifyOriginNoLongerInUse(const GURL& origin);
188 bool IsOriginInUse(const GURL& origin) const {
189 return origins_in_use_.find(origin) != origins_in_use_.end();
192 void SetUsageCacheEnabled(QuotaClient::ID client_id,
193 const GURL& origin,
194 StorageType type,
195 bool enabled);
197 // DeleteOriginData and DeleteHostData (surprisingly enough) delete data of a
198 // particular StorageType associated with either a specific origin or set of
199 // origins. Each method additionally requires a |quota_client_mask| which
200 // specifies the types of QuotaClients to delete from the origin. This is
201 // specified by the caller as a bitmask built from QuotaClient::IDs. Setting
202 // the mask to QuotaClient::kAllClientsMask will remove all clients from the
203 // origin, regardless of type.
204 virtual void DeleteOriginData(const GURL& origin,
205 StorageType type,
206 int quota_client_mask,
207 const StatusCallback& callback);
208 void DeleteHostData(const std::string& host,
209 StorageType type,
210 int quota_client_mask,
211 const StatusCallback& callback);
213 // Called by UI and internal modules.
214 void GetAvailableSpace(const AvailableSpaceCallback& callback);
215 void GetTemporaryGlobalQuota(const QuotaCallback& callback);
217 // Ok to call with NULL callback.
218 void SetTemporaryGlobalOverrideQuota(int64 new_quota,
219 const QuotaCallback& callback);
221 void GetPersistentHostQuota(const std::string& host,
222 const QuotaCallback& callback);
223 void SetPersistentHostQuota(const std::string& host,
224 int64 new_quota,
225 const QuotaCallback& callback);
226 void GetGlobalUsage(StorageType type, const GlobalUsageCallback& callback);
227 void GetHostUsage(const std::string& host, StorageType type,
228 const UsageCallback& callback);
229 void GetHostUsage(const std::string& host, StorageType type,
230 QuotaClient::ID client_id,
231 const UsageCallback& callback);
233 bool IsTrackingHostUsage(StorageType type, QuotaClient::ID client_id) const;
235 void GetStatistics(std::map<std::string, std::string>* statistics);
237 bool IsStorageUnlimited(const GURL& origin, StorageType type) const;
239 bool CanQueryDiskSize(const GURL& origin) const {
240 return special_storage_policy_.get() &&
241 special_storage_policy_->CanQueryDiskSize(origin);
244 virtual void GetOriginsModifiedSince(StorageType type,
245 base::Time modified_since,
246 const GetOriginsCallback& callback);
248 bool ResetUsageTracker(StorageType type);
250 // Used to register/deregister observers that wish to monitor storage events.
251 void AddStorageObserver(StorageObserver* observer,
252 const StorageObserver::MonitorParams& params);
253 void RemoveStorageObserver(StorageObserver* observer);
254 void RemoveStorageObserverForFilter(StorageObserver* observer,
255 const StorageObserver::Filter& filter);
257 // Determines the portion of the temp pool that can be
258 // utilized by a single host (ie. 5 for 20%).
259 static const int kPerHostTemporaryPortion;
261 static const int64 kPerHostPersistentQuotaLimit;
263 static const char kDatabaseName[];
265 static const int kThresholdOfErrorsToBeBlacklisted;
267 static const int kEvictionIntervalInMilliSeconds;
269 // These are kept non-const so that test code can change the value.
270 // TODO(kinuko): Make this a real const value and add a proper way to set
271 // the quota for syncable storage. (http://crbug.com/155488)
272 static int64 kMinimumPreserveForSystem;
273 static int64 kSyncableStorageDefaultHostQuota;
275 protected:
276 ~QuotaManager() override;
278 private:
279 friend class base::DeleteHelper<QuotaManager>;
280 friend class base::RefCountedThreadSafe<QuotaManager, QuotaManagerDeleter>;
281 friend class content::QuotaManagerTest;
282 friend class content::StorageMonitorTest;
283 friend class content::MockQuotaManager;
284 friend class content::MockStorageClient;
285 friend class quota_internals::QuotaInternalsProxy;
286 friend class QuotaManagerProxy;
287 friend class QuotaTemporaryStorageEvictor;
288 friend struct QuotaManagerDeleter;
290 class GetUsageInfoTask;
292 class OriginDataDeleter;
293 class HostDataDeleter;
295 class GetModifiedSinceHelper;
296 class DumpQuotaTableHelper;
297 class DumpOriginInfoTableHelper;
299 typedef QuotaDatabase::QuotaTableEntry QuotaTableEntry;
300 typedef QuotaDatabase::OriginInfoTableEntry OriginInfoTableEntry;
301 typedef std::vector<QuotaTableEntry> QuotaTableEntries;
302 typedef std::vector<OriginInfoTableEntry> OriginInfoTableEntries;
304 // Function pointer type used to store the function which returns the
305 // available disk space for the disk containing the given FilePath.
306 typedef int64 (*GetAvailableDiskSpaceFn)(const base::FilePath&);
308 typedef base::Callback<void(const QuotaTableEntries&)>
309 DumpQuotaTableCallback;
310 typedef base::Callback<void(const OriginInfoTableEntries&)>
311 DumpOriginInfoTableCallback;
313 typedef CallbackQueue<base::Closure> ClosureQueue;
314 typedef CallbackQueue<AvailableSpaceCallback, QuotaStatusCode, int64>
315 AvailableSpaceCallbackQueue;
316 typedef CallbackQueueMap<QuotaCallback, std::string, QuotaStatusCode, int64>
317 HostQuotaCallbackMap;
319 struct EvictionContext {
320 EvictionContext();
321 virtual ~EvictionContext();
322 GURL evicted_origin;
323 StorageType evicted_type;
325 EvictOriginDataCallback evict_origin_data_callback;
328 typedef QuotaEvictionHandler::UsageAndQuotaCallback
329 UsageAndQuotaDispatcherCallback;
331 // This initialization method is lazily called on the IO thread
332 // when the first quota manager API is called.
333 // Initialize must be called after all quota clients are added to the
334 // manager by RegisterStorage.
335 void LazyInitialize();
337 // Called by clients via proxy.
338 // Registers a quota client to the manager.
339 // The client must remain valid until OnQuotaManagerDestored is called.
340 void RegisterClient(QuotaClient* client);
342 UsageTracker* GetUsageTracker(StorageType type) const;
344 // Extract cached origins list from the usage tracker.
345 // (Might return empty list if no origin is tracked by the tracker.)
346 void GetCachedOrigins(StorageType type, std::set<GURL>* origins);
348 // These internal methods are separately defined mainly for testing.
349 void NotifyStorageAccessedInternal(
350 QuotaClient::ID client_id,
351 const GURL& origin,
352 StorageType type,
353 base::Time accessed_time);
354 void NotifyStorageModifiedInternal(
355 QuotaClient::ID client_id,
356 const GURL& origin,
357 StorageType type,
358 int64 delta,
359 base::Time modified_time);
361 void DumpQuotaTable(const DumpQuotaTableCallback& callback);
362 void DumpOriginInfoTable(const DumpOriginInfoTableCallback& callback);
364 // Methods for eviction logic.
365 void StartEviction();
366 void DeleteOriginFromDatabase(const GURL& origin, StorageType type);
368 void DidOriginDataEvicted(QuotaStatusCode status);
370 void ReportHistogram();
371 void DidGetTemporaryGlobalUsageForHistogram(int64 usage,
372 int64 unlimited_usage);
373 void DidGetPersistentGlobalUsageForHistogram(int64 usage,
374 int64 unlimited_usage);
376 // QuotaEvictionHandler.
377 void GetEvictionOrigin(StorageType type,
378 const GetOriginCallback& callback) override;
379 void EvictOriginData(const GURL& origin,
380 StorageType type,
381 const EvictOriginDataCallback& callback) override;
382 void GetUsageAndQuotaForEviction(
383 const UsageAndQuotaCallback& callback) override;
385 void GetLRUOrigin(StorageType type, const GetOriginCallback& callback);
387 void DidSetTemporaryGlobalOverrideQuota(const QuotaCallback& callback,
388 const int64* new_quota,
389 bool success);
390 void DidGetPersistentHostQuota(const std::string& host,
391 const int64* quota,
392 bool success);
393 void DidSetPersistentHostQuota(const std::string& host,
394 const QuotaCallback& callback,
395 const int64* new_quota,
396 bool success);
397 void DidInitialize(int64* temporary_quota_override,
398 int64* desired_available_space,
399 bool success);
400 void DidGetLRUOrigin(const GURL* origin,
401 bool success);
402 void DidGetInitialTemporaryGlobalQuota(QuotaStatusCode status,
403 int64 quota_unused);
404 void DidInitializeTemporaryOriginsInfo(bool success);
405 void DidGetAvailableSpace(int64 space);
406 void DidDatabaseWork(bool success);
408 void DeleteOnCorrectThread() const;
410 void PostTaskAndReplyWithResultForDBThread(
411 const tracked_objects::Location& from_here,
412 const base::Callback<bool(QuotaDatabase*)>& task,
413 const base::Callback<void(bool)>& reply);
415 const bool is_incognito_;
416 const base::FilePath profile_path_;
418 scoped_refptr<QuotaManagerProxy> proxy_;
419 bool db_disabled_;
420 bool eviction_disabled_;
421 scoped_refptr<base::SingleThreadTaskRunner> io_thread_;
422 scoped_refptr<base::SequencedTaskRunner> db_thread_;
423 mutable scoped_ptr<QuotaDatabase> database_;
425 GetOriginCallback lru_origin_callback_;
426 std::set<GURL> access_notified_origins_;
428 QuotaClientList clients_;
430 scoped_ptr<UsageTracker> temporary_usage_tracker_;
431 scoped_ptr<UsageTracker> persistent_usage_tracker_;
432 scoped_ptr<UsageTracker> syncable_usage_tracker_;
433 // TODO(michaeln): Need a way to clear the cache, drop and
434 // reinstantiate the trackers when they're not handling requests.
436 scoped_ptr<QuotaTemporaryStorageEvictor> temporary_storage_evictor_;
437 EvictionContext eviction_context_;
439 ClosureQueue db_initialization_callbacks_;
440 AvailableSpaceCallbackQueue available_space_callbacks_;
441 HostQuotaCallbackMap persistent_host_quota_callbacks_;
443 bool temporary_quota_initialized_;
444 int64 temporary_quota_override_;
446 int64 desired_available_space_;
448 // Map from origin to count.
449 std::map<GURL, int> origins_in_use_;
450 // Map from origin to error count.
451 std::map<GURL, int> origins_in_error_;
453 scoped_refptr<SpecialStoragePolicy> special_storage_policy_;
455 base::RepeatingTimer<QuotaManager> histogram_timer_;
457 // Pointer to the function used to get the available disk space. This is
458 // overwritten by QuotaManagerTest in order to attain a deterministic reported
459 // value. The default value points to base::SysInfo::AmountOfFreeDiskSpace.
460 GetAvailableDiskSpaceFn get_disk_space_fn_;
462 scoped_ptr<StorageMonitor> storage_monitor_;
464 base::WeakPtrFactory<QuotaManager> weak_factory_;
466 DISALLOW_COPY_AND_ASSIGN(QuotaManager);
469 struct QuotaManagerDeleter {
470 static void Destruct(const QuotaManager* manager) {
471 manager->DeleteOnCorrectThread();
475 } // namespace storage
477 #endif // STORAGE_BROWSER_QUOTA_QUOTA_MANAGER_H_