Protect local storage created by extension apps.
BUG=49228
TEST=ExtensionsServiceTest.InstallAppsAndCheckStorageProtection
TEST=DatabaseTrackerTest.*
Review URL: http://codereview.chromium.org/3256003
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@58108 0039d316-1c4b-4281-b951-d872f2087c98
diff --git a/chrome/browser/extensions/extensions_service.cc b/chrome/browser/extensions/extensions_service.cc
index 7ba0f42..4d1ce3b 100644
--- a/chrome/browser/extensions/extensions_service.cc
+++ b/chrome/browser/extensions/extensions_service.cc
@@ -4,6 +4,8 @@
#include "chrome/browser/extensions/extensions_service.h"
+#include <algorithm>
+
#include "base/basictypes.h"
#include "base/command_line.h"
#include "base/file_util.h"
@@ -85,9 +87,18 @@
pattern != patterns.end(); ++pattern) {
if (pattern->match_subdomains() || pattern->match_all_urls())
continue;
- GURL origin = GURL(pattern->GetAsString()).GetOrigin();
- if (origin.is_valid())
- set.insert(origin);
+ // Wildcard URL schemes won't parse into a valid GURL, so explicit schemes
+ // must be used.
+ PatternList explicit_patterns = pattern->ConvertToExplicitSchemes();
+ for (PatternList::const_iterator explicit_p = explicit_patterns.begin();
+ explicit_p != explicit_patterns.end(); ++explicit_p) {
+ GURL origin = GURL(explicit_p->GetAsString()).GetOrigin();
+ if (origin.is_valid()) {
+ set.insert(origin);
+ } else {
+ NOTREACHED();
+ }
+ }
}
for (std::set<GURL>::const_iterator unique = set.begin();
@@ -700,6 +711,11 @@
// Check if this permission requires unlimited storage quota
if (extension->HasApiPermission(Extension::kUnlimitedStoragePermission))
GrantUnlimitedStorage(extension);
+
+ // If the extension is an app, protect its local storage from
+ // "Clear browsing data."
+ if (extension->is_app())
+ GrantProtectedStorage(extension);
}
LOG(INFO) << "Sending EXTENSION_LOADED";
@@ -725,6 +741,31 @@
// in-memory quota.
if (extension->HasApiPermission(Extension::kUnlimitedStoragePermission))
RevokeUnlimitedStorage(extension);
+
+ // If this is an app, then stop protecting its storage so it can be deleted.
+ if (extension->is_app())
+ RevokeProtectedStorage(extension);
+ }
+}
+
+void ExtensionsService::GrantProtectedStorage(Extension* extension) {
+ DCHECK(extension->is_app()) << "Only Apps are allowed protected storage.";
+ std::vector<GURL> origins;
+ GetExplicitOriginsInExtent(extension, &origins);
+ for (size_t i = 0; i < origins.size(); ++i)
+ ++protected_storage_map_[origins[i]];
+}
+
+void ExtensionsService::RevokeProtectedStorage(Extension* extension) {
+ DCHECK(extension->is_app()) << "Attempting to revoke protected storage from "
+ << " a non-app extension.";
+ std::vector<GURL> origins;
+ GetExplicitOriginsInExtent(extension, &origins);
+ for (size_t i = 0; i < origins.size(); ++i) {
+ const GURL& origin = origins[i];
+ DCHECK(protected_storage_map_[origin] > 0);
+ if (--protected_storage_map_[origin] <= 0)
+ protected_storage_map_.erase(origin);
}
}