summaryrefslogtreecommitdiffstats
path: root/webkit/quota
diff options
context:
space:
mode:
authorjhawkins@chromium.org <jhawkins@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2012-08-24 18:54:52 +0000
committerjhawkins@chromium.org <jhawkins@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2012-08-24 18:54:52 +0000
commit5c10f0c3cbf485c5d4c7a6191fc59513ba4bcb33 (patch)
tree6de5d3b60e0dd46e47cbedba54692e97d4bbc0a6 /webkit/quota
parent43d6ac5c8967b4a0d99f879c13336e229487b1ad (diff)
downloadchromium_src-5c10f0c3cbf485c5d4c7a6191fc59513ba4bcb33.zip
chromium_src-5c10f0c3cbf485c5d4c7a6191fc59513ba4bcb33.tar.gz
chromium_src-5c10f0c3cbf485c5d4c7a6191fc59513ba4bcb33.tar.bz2
QuotaManager: Return the remaining free disk space as quota.
Previously we returned kNoLimit, which prevents apps from managing disk usage. BUG=141583 TEST= R=kinuko Review URL: https://chromiumcodereview.appspot.com/10826270 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@153248 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'webkit/quota')
-rw-r--r--webkit/quota/mock_special_storage_policy.cc4
-rw-r--r--webkit/quota/mock_special_storage_policy.h9
-rw-r--r--webkit/quota/quota_manager.cc32
-rw-r--r--webkit/quota/quota_manager.h20
-rw-r--r--webkit/quota/quota_manager_unittest.cc77
-rw-r--r--webkit/quota/special_storage_policy.h3
6 files changed, 107 insertions, 38 deletions
diff --git a/webkit/quota/mock_special_storage_policy.cc b/webkit/quota/mock_special_storage_policy.cc
index b8203a3..340e169 100644
--- a/webkit/quota/mock_special_storage_policy.cc
+++ b/webkit/quota/mock_special_storage_policy.cc
@@ -24,6 +24,10 @@ bool MockSpecialStoragePolicy::IsStorageSessionOnly(const GURL& origin) {
return session_only_.find(origin) != session_only_.end();
}
+bool MockSpecialStoragePolicy::IsInstalledApp(const GURL& origin) {
+ return installed_.find(origin) != installed_.end();
+}
+
bool MockSpecialStoragePolicy::IsFileHandler(const std::string& extension_id) {
return file_handlers_.find(extension_id) != file_handlers_.end();
}
diff --git a/webkit/quota/mock_special_storage_policy.h b/webkit/quota/mock_special_storage_policy.h
index 1ef6b7fc..b4dac27 100644
--- a/webkit/quota/mock_special_storage_policy.h
+++ b/webkit/quota/mock_special_storage_policy.h
@@ -20,6 +20,7 @@ class MockSpecialStoragePolicy : public quota::SpecialStoragePolicy {
virtual bool IsStorageProtected(const GURL& origin) OVERRIDE;
virtual bool IsStorageUnlimited(const GURL& origin) OVERRIDE;
virtual bool IsStorageSessionOnly(const GURL& origin) OVERRIDE;
+ virtual bool IsInstalledApp(const GURL& origin) OVERRIDE;
virtual bool IsFileHandler(const std::string& extension_id) OVERRIDE;
virtual bool HasSessionOnlyOrigins() OVERRIDE;
@@ -35,6 +36,12 @@ class MockSpecialStoragePolicy : public quota::SpecialStoragePolicy {
session_only_.insert(origin);
}
+ void AddInstalledApp(const GURL& origin) {
+ // Installed implies unlimited.
+ unlimited_.insert(origin);
+ installed_.insert(origin);
+ }
+
void AddFileHandler(const std::string& id) {
file_handlers_.insert(id);
}
@@ -47,6 +54,7 @@ class MockSpecialStoragePolicy : public quota::SpecialStoragePolicy {
protected_.clear();
unlimited_.clear();
session_only_.clear();
+ installed_.clear();
file_handlers_.clear();
all_unlimited_ = false;
}
@@ -62,6 +70,7 @@ class MockSpecialStoragePolicy : public quota::SpecialStoragePolicy {
std::set<GURL> protected_;
std::set<GURL> unlimited_;
std::set<GURL> session_only_;
+ std::set<GURL> installed_;
std::set<std::string> file_handlers_;
bool all_unlimited_;
diff --git a/webkit/quota/quota_manager.cc b/webkit/quota/quota_manager.cc
index 9917846..ce8c5e5 100644
--- a/webkit/quota/quota_manager.cc
+++ b/webkit/quota/quota_manager.cc
@@ -77,11 +77,21 @@ const int QuotaManager::kEvictionIntervalInMilliSeconds =
void CallGetUsageAndQuotaCallback(
const QuotaManager::GetUsageAndQuotaCallback& callback,
bool unlimited,
+ bool is_installed_app,
QuotaStatusCode status,
const QuotaAndUsage& quota_and_usage) {
- int64 usage =
- unlimited ? quota_and_usage.unlimited_usage : quota_and_usage.usage;
- int64 quota = unlimited ? QuotaManager::kNoLimit : quota_and_usage.quota;
+ int64 usage;
+ int64 quota;
+
+ if (unlimited) {
+ usage = quota_and_usage.unlimited_usage;
+ quota = is_installed_app ? quota_and_usage.available_disk_space :
+ QuotaManager::kNoLimit;
+ } else {
+ usage = quota_and_usage.usage;
+ quota = quota_and_usage.quota;
+ }
+
callback.Run(status, usage, quota);
}
@@ -408,6 +418,7 @@ class QuotaManager::UsageAndQuotaDispatcherTaskForPersistent
host(), NewWaitableHostUsageCallback());
manager()->GetPersistentHostQuota(
host(), NewWaitableHostQuotaCallback());
+ manager()->GetAvailableSpace(NewWaitableAvailableSpaceCallback());
}
virtual void DispatchCallbacks() OVERRIDE {
@@ -959,7 +970,9 @@ class QuotaManager::AvailableSpaceQueryTask : public QuotaThreadTask {
: QuotaThreadTask(manager, manager->db_thread_),
profile_path_(manager->profile_path_),
space_(-1),
+ get_disk_space_fn_(manager->get_disk_space_fn_),
callback_(callback) {
+ DCHECK(get_disk_space_fn_);
}
protected:
@@ -967,7 +980,7 @@ class QuotaManager::AvailableSpaceQueryTask : public QuotaThreadTask {
// QuotaThreadTask:
virtual void RunOnTargetThread() OVERRIDE {
- space_ = base::SysInfo::AmountOfFreeDiskSpace(profile_path_);
+ space_ = get_disk_space_fn_(profile_path_);
}
virtual void Aborted() OVERRIDE {
@@ -981,6 +994,7 @@ class QuotaManager::AvailableSpaceQueryTask : public QuotaThreadTask {
private:
FilePath profile_path_;
int64 space_;
+ GetAvailableDiskSpaceFn get_disk_space_fn_;
AvailableSpaceCallback callback_;
};
@@ -1202,7 +1216,8 @@ QuotaManager::QuotaManager(bool is_incognito,
temporary_quota_override_(-1),
desired_available_space_(-1),
special_storage_policy_(special_storage_policy),
- weak_factory_(ALLOW_THIS_IN_INITIALIZER_LIST(this)) {
+ weak_factory_(ALLOW_THIS_IN_INITIALIZER_LIST(this)),
+ get_disk_space_fn_(&base::SysInfo::AmountOfFreeDiskSpace) {
}
void QuotaManager::GetUsageInfo(const GetUsageInfoCallback& callback) {
@@ -1214,9 +1229,10 @@ void QuotaManager::GetUsageInfo(const GetUsageInfoCallback& callback) {
void QuotaManager::GetUsageAndQuota(
const GURL& origin, StorageType type,
const GetUsageAndQuotaCallback& callback) {
- GetUsageAndQuotaInternal(origin, type, false /* global */,
- base::Bind(&CallGetUsageAndQuotaCallback,
- callback, IsStorageUnlimited(origin)));
+ GetUsageAndQuotaInternal(
+ origin, type, false /* global */,
+ base::Bind(&CallGetUsageAndQuotaCallback, callback,
+ IsStorageUnlimited(origin), IsInstalledApp(origin)));
}
void QuotaManager::GetAvailableSpace(const AvailableSpaceCallback& callback) {
diff --git a/webkit/quota/quota_manager.h b/webkit/quota/quota_manager.h
index 6390b73..6f5b504 100644
--- a/webkit/quota/quota_manager.h
+++ b/webkit/quota/quota_manager.h
@@ -39,13 +39,13 @@ class QuotaInternalsProxy;
namespace quota {
-struct QuotaManagerDeleter;
-
+class MockQuotaManager;
class QuotaDatabase;
class QuotaManagerProxy;
class QuotaTemporaryStorageEvictor;
class UsageTracker;
-class MockQuotaManager;
+
+struct QuotaManagerDeleter;
struct QuotaAndUsage {
int64 usage;
@@ -188,6 +188,11 @@ class QuotaManager : public QuotaTaskObserver,
special_storage_policy_->IsStorageUnlimited(origin);
}
+ bool IsInstalledApp(const GURL& origin) const {
+ return special_storage_policy_.get() &&
+ special_storage_policy_->IsInstalledApp(origin);
+ }
+
virtual void GetOriginsModifiedSince(StorageType type,
base::Time modified_since,
const GetOriginsCallback& callback);
@@ -247,6 +252,10 @@ class QuotaManager : public QuotaTaskObserver,
typedef std::vector<QuotaTableEntry> QuotaTableEntries;
typedef std::vector<OriginInfoTableEntry> OriginInfoTableEntries;
+ // Function pointer type used to store the function which returns the
+ // available disk space for the disk containing the given FilePath.
+ typedef int64 (*GetAvailableDiskSpaceFn)(const FilePath&);
+
typedef base::Callback<void(const QuotaTableEntries&)>
DumpQuotaTableCallback;
typedef base::Callback<void(const OriginInfoTableEntries&)>
@@ -387,6 +396,11 @@ class QuotaManager : public QuotaTaskObserver,
base::WeakPtrFactory<QuotaManager> weak_factory_;
base::RepeatingTimer<QuotaManager> histogram_timer_;
+ // Pointer to the function used to get the available disk space. This is
+ // overwritten by QuotaManagerTest in order to attain a deterministic reported
+ // value. The default value points to base::SysInfo::AmountOfFreeDiskSpace.
+ GetAvailableDiskSpaceFn get_disk_space_fn_;
+
DISALLOW_COPY_AND_ASSIGN(QuotaManager);
};
diff --git a/webkit/quota/quota_manager_unittest.cc b/webkit/quota/quota_manager_unittest.cc
index 171f6b4..2002e84 100644
--- a/webkit/quota/quota_manager_unittest.cc
+++ b/webkit/quota/quota_manager_unittest.cc
@@ -33,6 +33,11 @@ const StorageType kPerm = kStorageTypePersistent;
const int kAllClients = QuotaClient::kAllClientsMask;
+// Returns a deterministic value for the amount of available disk space.
+int64 GetAvailableDiskSpaceForTest(const FilePath&) {
+ return 13377331;
+}
+
class QuotaManagerTest : public testing::Test {
protected:
typedef QuotaManager::QuotaTableEntry QuotaTableEntry;
@@ -56,6 +61,8 @@ class QuotaManagerTest : public testing::Test {
mock_special_storage_policy_);
// Don't (automatically) start the eviction for testing.
quota_manager_->eviction_disabled_ = true;
+ // Don't query the hard disk for remaining capacity.
+ quota_manager_->get_disk_space_fn_ = &GetAvailableDiskSpaceForTest;
additional_callback_count_ = 0;
}
@@ -85,14 +92,14 @@ class QuotaManagerTest : public testing::Test {
weak_factory_.GetWeakPtr()));
}
- void GetUsageAndQuota(const GURL& origin, StorageType type) {
+ void GetUsageAndQuota(const GURL& origin,
+ StorageType type) {
quota_status_ = kQuotaStatusUnknown;
usage_ = -1;
quota_ = -1;
quota_manager_->GetUsageAndQuota(
- origin, type,
- base::Bind(&QuotaManagerTest::DidGetUsageAndQuota,
- weak_factory_.GetWeakPtr()));
+ origin, type, base::Bind(&QuotaManagerTest::DidGetUsageAndQuota,
+ weak_factory_.GetWeakPtr()));
}
void GetTemporaryGlobalQuota() {
@@ -162,8 +169,8 @@ class QuotaManagerTest : public testing::Test {
}
void DeleteClientOriginData(QuotaClient* client,
- const GURL& origin,
- StorageType type) {
+ const GURL& origin,
+ StorageType type) {
DCHECK(client);
quota_status_ = kQuotaStatusUnknown;
client->DeleteOriginData(
@@ -595,17 +602,20 @@ TEST_F(QuotaManagerTest, GetTemporaryUsageAndQuota_MultiOrigins) {
TEST_F(QuotaManagerTest, GetUsage_MultipleClients) {
static const MockOriginData kData1[] = {
- { "http://foo.com/", kTemp, 10 },
- { "http://bar.com/", kTemp, 20 },
+ { "http://foo.com/", kTemp, 10 },
+ { "http://bar.com/", kTemp, 20 },
{ "http://bar.com/", kPerm, 50 },
- { "http://unlimited/", kPerm, 1 },
+ { "http://unlimited/", kPerm, 1 },
+ { "http://installed/", kPerm, 1 },
};
static const MockOriginData kData2[] = {
- { "https://foo.com/", kTemp, 30 },
+ { "https://foo.com/", kTemp, 30 },
{ "http://example.com/", kPerm, 40 },
- { "http://unlimited/", kTemp, 1 },
+ { "http://unlimited/", kTemp, 1 },
+ { "http://installed/", kTemp, 1 },
};
mock_special_storage_policy()->AddUnlimited(GURL("http://unlimited/"));
+ mock_special_storage_policy()->AddInstalledApp(GURL("http://installed/"));
RegisterClient(CreateClient(kData1, ARRAYSIZE_UNSAFE(kData1),
QuotaClient::kFileSystem));
RegisterClient(CreateClient(kData2, ARRAYSIZE_UNSAFE(kData2),
@@ -625,25 +635,42 @@ TEST_F(QuotaManagerTest, GetUsage_MultipleClients) {
MessageLoop::current()->RunAllPending();
EXPECT_EQ(kQuotaStatusOk, status());
EXPECT_EQ(1, usage());
- EXPECT_EQ(kint64max, quota());
+ EXPECT_EQ(QuotaManager::kNoLimit, quota());
GetUsageAndQuota(GURL("http://unlimited/"), kPerm);
MessageLoop::current()->RunAllPending();
EXPECT_EQ(kQuotaStatusOk, status());
EXPECT_EQ(1, usage());
- EXPECT_EQ(kint64max, quota());
+ EXPECT_EQ(QuotaManager::kNoLimit, quota());
+
+ GetAvailableSpace();
+ MessageLoop::current()->RunAllPending();
+ EXPECT_EQ(kQuotaStatusOk, status());
+ EXPECT_LE(0, available_space());
+
+ GetUsageAndQuota(GURL("http://installed/"), kTemp);
+ MessageLoop::current()->RunAllPending();
+ EXPECT_EQ(kQuotaStatusOk, status());
+ EXPECT_EQ(1, usage());
+ EXPECT_EQ(available_space(), quota());
+
+ GetUsageAndQuota(GURL("http://installed/"), kPerm);
+ MessageLoop::current()->RunAllPending();
+ EXPECT_EQ(kQuotaStatusOk, status());
+ EXPECT_EQ(1, usage());
+ EXPECT_EQ(available_space(), quota());
GetGlobalUsage(kTemp);
MessageLoop::current()->RunAllPending();
EXPECT_EQ(kQuotaStatusOk, status());
- EXPECT_EQ(10 + 20 + 30 + 1, usage());
- EXPECT_EQ(1, unlimited_usage());
+ EXPECT_EQ(10 + 20 + 30 + 1 + 1, usage());
+ EXPECT_EQ(2, unlimited_usage());
GetGlobalUsage(kPerm);
MessageLoop::current()->RunAllPending();
EXPECT_EQ(kQuotaStatusOk, status());
- EXPECT_EQ(40 + 50 + 1, usage());
- EXPECT_EQ(1, unlimited_usage());
+ EXPECT_EQ(40 + 50 + 1 + 1, usage());
+ EXPECT_EQ(2, unlimited_usage());
}
void QuotaManagerTest::GetUsage_WithModifyTestBody(const StorageType type) {
@@ -712,8 +739,7 @@ TEST_F(QuotaManagerTest, GetTemporaryUsageAndQuota_WithAdditionalTasks) {
RunAdditionalUsageAndQuotaTask(GURL("http://foo.com/"),
kTemp);
GetUsageAndQuota(GURL("http://foo.com/"), kTemp);
- RunAdditionalUsageAndQuotaTask(GURL("http://bar.com/"),
- kTemp);
+ RunAdditionalUsageAndQuotaTask(GURL("http://bar.com/"), kTemp);
MessageLoop::current()->RunAllPending();
EXPECT_EQ(kQuotaStatusOk, status());
EXPECT_EQ(10 + 20, usage());
@@ -820,7 +846,7 @@ TEST_F(QuotaManagerTest, GetTemporaryUsageAndQuota_Unlimited) {
MessageLoop::current()->RunAllPending();
EXPECT_EQ(kQuotaStatusOk, status());
EXPECT_EQ(4000, usage());
- EXPECT_EQ(kint64max, quota());
+ EXPECT_EQ(QuotaManager::kNoLimit, quota());
// Test when overbugdet.
SetTemporaryGlobalQuota(100);
@@ -845,7 +871,7 @@ TEST_F(QuotaManagerTest, GetTemporaryUsageAndQuota_Unlimited) {
MessageLoop::current()->RunAllPending();
EXPECT_EQ(kQuotaStatusOk, status());
EXPECT_EQ(4000, usage());
- EXPECT_EQ(kint64max, quota());
+ EXPECT_EQ(QuotaManager::kNoLimit, quota());
// Revoke the unlimited rights and make sure the change is noticed.
mock_special_storage_policy()->Reset();
@@ -985,8 +1011,7 @@ TEST_F(QuotaManagerTest, GetPersistentUsageAndQuota_WithAdditionalTasks) {
RunAdditionalUsageAndQuotaTask(GURL("http://foo.com/"),
kPerm);
GetUsageAndQuota(GURL("http://foo.com/"), kPerm);
- RunAdditionalUsageAndQuotaTask(GURL("http://bar.com/"),
- kPerm);
+ RunAdditionalUsageAndQuotaTask(GURL("http://bar.com/"), kPerm);
MessageLoop::current()->RunAllPending();
EXPECT_EQ(kQuotaStatusOk, status());
EXPECT_EQ(10 + 20, usage());
@@ -1006,10 +1031,8 @@ TEST_F(QuotaManagerTest, GetPersistentUsageAndQuota_NukeManager) {
set_additional_callback_count(0);
GetUsageAndQuota(GURL("http://foo.com/"), kPerm);
- RunAdditionalUsageAndQuotaTask(GURL("http://foo.com/"),
- kPerm);
- RunAdditionalUsageAndQuotaTask(GURL("http://bar.com/"),
- kPerm);
+ RunAdditionalUsageAndQuotaTask(GURL("http://foo.com/"), kPerm);
+ RunAdditionalUsageAndQuotaTask(GURL("http://bar.com/"), kPerm);
// Nuke before waiting for callbacks.
set_quota_manager(NULL);
diff --git a/webkit/quota/special_storage_policy.h b/webkit/quota/special_storage_policy.h
index f7d80f7..60ddaa0 100644
--- a/webkit/quota/special_storage_policy.h
+++ b/webkit/quota/special_storage_policy.h
@@ -38,6 +38,9 @@ class SpecialStoragePolicy
// Unlimited storage is not subject to 'quotas'.
virtual bool IsStorageUnlimited(const GURL& origin) = 0;
+ // Installed apps have access to the size of the remaining disk capacity.
+ virtual bool IsInstalledApp(const GURL& origin) = 0;
+
// Checks if extension identified with |extension_id| is registered as
// file handler.
virtual bool IsFileHandler(const std::string& extension_id) = 0;