Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1263)

Unified Diff: chrome/browser/content_settings/content_settings_provider.cc

Issue 6484035: Add a content_settings::BaseProvider for code that is shared by all content settings providers. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: only fixed one nit Created 9 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: chrome/browser/content_settings/content_settings_provider.cc
diff --git a/chrome/browser/content_settings/content_settings_provider.cc b/chrome/browser/content_settings/content_settings_provider.cc
new file mode 100644
index 0000000000000000000000000000000000000000..a69b92c237c4f035048e88e95e80f3776fd338aa
--- /dev/null
+++ b/chrome/browser/content_settings/content_settings_provider.cc
@@ -0,0 +1,242 @@
+// 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 "chrome/browser/content_settings/content_settings_provider.h"
+
+#include "base/command_line.h"
+#include "base/logging.h"
+#include "chrome/common/chrome_switches.h"
+#include "googleurl/src/gurl.h"
+#include "net/base/net_util.h"
+
+namespace {
+
+// True if a given content settings type requires additional resource
+// identifiers.
+const bool kRequiresResourceIdentifier[CONTENT_SETTINGS_NUM_TYPES] = {
+ false, // CONTENT_SETTINGS_TYPE_COOKIES
+ false, // CONTENT_SETTINGS_TYPE_IMAGES
+ false, // CONTENT_SETTINGS_TYPE_JAVASCRIPT
+ true, // CONTENT_SETTINGS_TYPE_PLUGINS
+ false, // CONTENT_SETTINGS_TYPE_POPUPS
+ false, // Not used for Geolocation
+ false, // Not used for Notifications
+};
+
+} // namespace
+
+namespace content_settings {
+
+// ////////////////////////////////////////////////////////////////////////////
+// BaseProvider
+//
+bool BaseProvider::RequiresResourceIdentifier(
+ ContentSettingsType content_type) const {
+ if (CommandLine::ForCurrentProcess()->HasSwitch(
+ switches::kEnableResourceContentSettings)) {
+ return kRequiresResourceIdentifier[content_type];
+ } else {
+ return false;
+ }
+}
+
+bool BaseProvider::AllDefault(
+ const ExtendedContentSettings& settings) const {
+ for (size_t i = 0; i < arraysize(settings.content_settings.settings); ++i) {
+ if (settings.content_settings.settings[i] != CONTENT_SETTING_DEFAULT)
+ return false;
+ }
+ return settings.content_settings_for_resources.empty();
+}
+
+ContentSetting BaseProvider::GetContentSetting(
+ const GURL& requesting_url,
+ const GURL& embedding_url,
+ ContentSettingsType content_type,
+ const ResourceIdentifier& resource_identifier) const {
+ // Support for embedding_patterns is not implemented yet.
+ DCHECK(requesting_url == embedding_url);
+
+ if (!RequiresResourceIdentifier(content_type))
+ return GetNonDefaultContentSettings(requesting_url).settings[content_type];
+
+ if (RequiresResourceIdentifier(content_type) && resource_identifier.empty())
+ return CONTENT_SETTING_DEFAULT;
+
+ // TODO(markusheintz) Remove this DCHECK.
+ if (CommandLine::ForCurrentProcess()->HasSwitch(
+ switches::kEnableResourceContentSettings)) {
+ DCHECK(!resource_identifier.empty());
+ }
+
+ // Resolve content settings with resource identifier.
+ // 1. Check for pattern that exactly match the url/host
+ // 1.1 In the content-settings-map
+ // 1.2 In the off_the_record content-settings-map
+ // 3. Shorten the url subdomain by subdomain and try to find a pattern in
+ // 3.1 OTR content-settings-map
+ // 3.2 content-settings-map
+ base::AutoLock auto_lock(lock_);
+ const std::string host(net::GetHostOrSpecFromURL(requesting_url));
+ ContentSettingsTypeResourceIdentifierPair
+ requested_setting(content_type, resource_identifier);
+
+ // Check for exact matches first.
+ HostContentSettings::const_iterator i(host_content_settings_.find(host));
+ if (i != host_content_settings_.end() &&
+ i->second.content_settings_for_resources.find(requested_setting) !=
+ i->second.content_settings_for_resources.end()) {
+ return i->second.content_settings_for_resources.find(
+ requested_setting)->second;
+ }
+
+ // If this map is not for an off-the-record profile, these searches will never
+ // match. The additional off-the-record exceptions always overwrite the
+ // regular ones.
+ i = off_the_record_settings_.find(host);
+ if (i != off_the_record_settings_.end() &&
+ i->second.content_settings_for_resources.find(requested_setting) !=
+ i->second.content_settings_for_resources.end()) {
+ return i->second.content_settings_for_resources.find(
+ requested_setting)->second;
+ }
+
+ // Match patterns starting with the most concrete pattern match.
+ for (std::string key =
+ std::string(ContentSettingsPattern::kDomainWildcard) + host; ; ) {
+ HostContentSettings::const_iterator i(off_the_record_settings_.find(key));
+ if (i != off_the_record_settings_.end() &&
+ i->second.content_settings_for_resources.find(requested_setting) !=
+ i->second.content_settings_for_resources.end()) {
+ return i->second.content_settings_for_resources.find(
+ requested_setting)->second;
+ }
+
+ i = host_content_settings_.find(key);
+ if (i != host_content_settings_.end() &&
+ i->second.content_settings_for_resources.find(requested_setting) !=
+ i->second.content_settings_for_resources.end()) {
+ return i->second.content_settings_for_resources.find(
+ requested_setting)->second;
+ }
+
+ const size_t next_dot =
+ key.find('.', ContentSettingsPattern::kDomainWildcardLength);
+ if (next_dot == std::string::npos)
+ break;
+ key.erase(ContentSettingsPattern::kDomainWildcardLength,
+ next_dot - ContentSettingsPattern::kDomainWildcardLength + 1);
+ }
+
+ return CONTENT_SETTING_DEFAULT;
+}
+
+void BaseProvider::GetAllContentSettingsRules(
+ ContentSettingsType content_type,
+ const ResourceIdentifier& resource_identifier,
+ Rules* content_setting_rules) const {
+ DCHECK(RequiresResourceIdentifier(content_type) !=
+ resource_identifier.empty());
+ DCHECK(content_setting_rules);
+ content_setting_rules->clear();
+
+ const HostContentSettings* map_to_return =
+ is_off_the_record_ ? &off_the_record_settings_ : &host_content_settings_;
+ ContentSettingsTypeResourceIdentifierPair requested_setting(
+ content_type, resource_identifier);
+
+ base::AutoLock auto_lock(lock_);
+ for (HostContentSettings::const_iterator i(map_to_return->begin());
+ i != map_to_return->end(); ++i) {
+ ContentSetting setting;
+ if (RequiresResourceIdentifier(content_type)) {
+ if (i->second.content_settings_for_resources.find(requested_setting) !=
+ i->second.content_settings_for_resources.end()) {
+ setting = i->second.content_settings_for_resources.find(
+ requested_setting)->second;
+ } else {
+ setting = CONTENT_SETTING_DEFAULT;
+ }
+ } else {
+ setting = i->second.content_settings.settings[content_type];
+ }
+ if (setting != CONTENT_SETTING_DEFAULT) {
+ // Use of push_back() relies on the map iterator traversing in order of
+ // ascending keys.
+ content_setting_rules->push_back(Rule(ContentSettingsPattern(i->first),
+ ContentSettingsPattern(i->first),
+ setting));
+ }
+ }
+}
+
+ContentSettings BaseProvider::GetNonDefaultContentSettings(
+ const GURL& url) const {
+ base::AutoLock auto_lock(lock_);
+
+ const std::string host(net::GetHostOrSpecFromURL(url));
+ ContentSettings output;
+ for (int j = 0; j < CONTENT_SETTINGS_NUM_TYPES; ++j)
+ output.settings[j] = CONTENT_SETTING_DEFAULT;
+
+ // Check for exact matches first.
+ HostContentSettings::const_iterator i(host_content_settings_.find(host));
+ if (i != host_content_settings_.end())
+ output = i->second.content_settings;
+
+ // If this map is not for an off-the-record profile, these searches will never
+ // match. The additional off-the-record exceptions always overwrite the
+ // regular ones.
+ i = off_the_record_settings_.find(host);
+ if (i != off_the_record_settings_.end()) {
+ for (int j = 0; j < CONTENT_SETTINGS_NUM_TYPES; ++j)
+ if (i->second.content_settings.settings[j] != CONTENT_SETTING_DEFAULT)
+ output.settings[j] = i->second.content_settings.settings[j];
+ }
+
+ // Match patterns starting with the most concrete pattern match.
+ for (std::string key =
+ std::string(ContentSettingsPattern::kDomainWildcard) + host; ; ) {
+ HostContentSettings::const_iterator i(off_the_record_settings_.find(key));
+ if (i != off_the_record_settings_.end()) {
+ for (int j = 0; j < CONTENT_SETTINGS_NUM_TYPES; ++j) {
+ if (output.settings[j] == CONTENT_SETTING_DEFAULT)
+ output.settings[j] = i->second.content_settings.settings[j];
+ }
+ }
+ i = host_content_settings_.find(key);
+ if (i != host_content_settings_.end()) {
+ for (int j = 0; j < CONTENT_SETTINGS_NUM_TYPES; ++j) {
+ if (output.settings[j] == CONTENT_SETTING_DEFAULT)
+ output.settings[j] = i->second.content_settings.settings[j];
+ }
+ }
+ const size_t next_dot =
+ key.find('.', ContentSettingsPattern::kDomainWildcardLength);
+ if (next_dot == std::string::npos)
+ break;
+ key.erase(ContentSettingsPattern::kDomainWildcardLength,
+ next_dot - ContentSettingsPattern::kDomainWildcardLength + 1);
+ }
+
+ return output;
+}
+
+// ////////////////////////////////////////////////////////////////////////////
+// ProviderUtil
+//
+
+// static
+ContentSetting ProviderUtil::ClickToPlayFixup(ContentSettingsType content_type,
+ ContentSetting setting) {
+ if (setting == CONTENT_SETTING_ASK &&
+ content_type == CONTENT_SETTINGS_TYPE_PLUGINS &&
+ !CommandLine::ForCurrentProcess()->HasSwitch(
+ switches::kEnableClickToPlay)) {
+ return CONTENT_SETTING_BLOCK;
+ }
+ return setting;
+}
+
+} // namespace content_settings

Powered by Google App Engine
This is Rietveld 408576698