diff options
author | jochen@chromium.org <jochen@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-12-10 10:00:12 +0000 |
---|---|---|
committer | jochen@chromium.org <jochen@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-12-10 10:00:12 +0000 |
commit | e4dabe9993a51a1c59b5423c71c6de8d77f84eca (patch) | |
tree | 8728b7d1abef2cf07c0679ff65650ce589bc6bf7 | |
parent | 2b9d1feeaaeb0bb98e7bd5a6f1bdc29db9d37f9c (diff) | |
download | chromium_src-e4dabe9993a51a1c59b5423c71c6de8d77f84eca.zip chromium_src-e4dabe9993a51a1c59b5423c71c6de8d77f84eca.tar.gz chromium_src-e4dabe9993a51a1c59b5423c71c6de8d77f84eca.tar.bz2 |
Implement preference and policy based content settings providers.
BUG=64753
TEST=*ContentSettings*.*
Review URL: http://codereview.chromium.org/5528010
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@68834 0039d316-1c4b-4281-b951-d872f2087c98
17 files changed, 1006 insertions, 369 deletions
diff --git a/chrome/browser/content_settings/content_settings_provider.h b/chrome/browser/content_settings/content_settings_provider.h index 3229779a..2754bfc 100644 --- a/chrome/browser/content_settings/content_settings_provider.h +++ b/chrome/browser/content_settings/content_settings_provider.h @@ -12,14 +12,17 @@ class ContentSettingsProviderInterface { public: + virtual ~ContentSettingsProviderInterface() {} + // True if this provider can provide a default setting for the |content_type|. - virtual bool CanProvideDefaultSetting(ContentSettingsType content_type) = 0; + virtual bool CanProvideDefaultSetting( + ContentSettingsType content_type) const = 0; // Returns the default content setting this provider has for the given // |content_type|, or CONTENT_SETTING_DEFAULT if nothing be provided for this // type. virtual ContentSetting ProvideDefaultSetting( - ContentSettingsType content_type) = 0; + ContentSettingsType content_type) const = 0; // Notifies the provider that the host content settings map would like to // update the default setting for the given |content_type|. The provider may @@ -27,12 +30,13 @@ class ContentSettingsProviderInterface { virtual void UpdateDefaultSetting(ContentSettingsType content_type, ContentSetting setting) = 0; + // Resets the state of the provider to the default. + virtual void ResetToDefaults() = 0; + // True if the default setting for the |content_type| is policy managed, i.e., // there shouldn't be any UI shown to modify this setting. - virtual bool DefaultSettingIsManaged(ContentSettingsType content_type) = 0; - - protected: - virtual ~ContentSettingsProviderInterface() {}; + virtual bool DefaultSettingIsManaged( + ContentSettingsType content_type) const = 0; }; #endif // CHROME_BROWSER_CONTENT_SETTINGS_CONTENT_SETTINGS_PROVIDER_H_ diff --git a/chrome/browser/content_settings/host_content_settings_map.cc b/chrome/browser/content_settings/host_content_settings_map.cc index c2dea38..7de7a80 100644 --- a/chrome/browser/content_settings/host_content_settings_map.cc +++ b/chrome/browser/content_settings/host_content_settings_map.cc @@ -9,6 +9,8 @@ #include "base/utf_string_conversions.h" #include "chrome/browser/browser_thread.h" #include "chrome/browser/content_settings/content_settings_details.h" +#include "chrome/browser/content_settings/policy_content_settings_provider.h" +#include "chrome/browser/content_settings/pref_content_settings_provider.h" #include "chrome/browser/metrics/user_metrics.h" #include "chrome/browser/prefs/pref_service.h" #include "chrome/browser/profiles/profile.h" @@ -20,19 +22,11 @@ #include "chrome/common/pref_names.h" #include "chrome/common/url_constants.h" #include "googleurl/src/gurl.h" -#include "googleurl/src/url_canon.h" -#include "googleurl/src/url_parse.h" -#include "net/base/dns_util.h" #include "net/base/net_util.h" #include "net/base/static_cookie_policy.h" namespace { -// Base pref path of the prefs that contain the managed default content -// settings values. -const std::string kManagedSettings = - "profile.managed_default_content_settings"; - // The preference keys where resource identifiers are stored for // ContentSettingsType values that support resource identifiers. const char* kResourceTypeNames[CONTENT_SETTINGS_NUM_TYPES] = { @@ -56,28 +50,6 @@ const char* kTypeNames[CONTENT_SETTINGS_NUM_TYPES] = { NULL, // Not used for Notifications }; -// The preferences used to manage ContentSettingsTypes. -const char* kPrefToManageType[CONTENT_SETTINGS_NUM_TYPES] = { - prefs::kManagedDefaultCookiesSetting, - prefs::kManagedDefaultImagesSetting, - prefs::kManagedDefaultJavaScriptSetting, - prefs::kManagedDefaultPluginsSetting, - prefs::kManagedDefaultPopupsSetting, - NULL, // Not used for Geolocation - NULL, // Not used for Notifications -}; - -// The default setting for each content type. -const ContentSetting kDefaultSettings[CONTENT_SETTINGS_NUM_TYPES] = { - CONTENT_SETTING_ALLOW, // CONTENT_SETTINGS_TYPE_COOKIES - CONTENT_SETTING_ALLOW, // CONTENT_SETTINGS_TYPE_IMAGES - CONTENT_SETTING_ALLOW, // CONTENT_SETTINGS_TYPE_JAVASCRIPT - CONTENT_SETTING_ALLOW, // CONTENT_SETTINGS_TYPE_PLUGINS - CONTENT_SETTING_BLOCK, // CONTENT_SETTINGS_TYPE_POPUPS - CONTENT_SETTING_ASK, // Not used for Geolocation - CONTENT_SETTING_ASK, // Not used for Notifications -}; - // True if a given content settings type requires additional resource // identifiers. const bool kRequiresResourceIdentifier[CONTENT_SETTINGS_NUM_TYPES] = { @@ -115,6 +87,12 @@ ContentSetting ClickToPlayFixup(ContentSettingsType content_type, return setting; } +typedef std::vector<linked_ptr<ContentSettingsProviderInterface> >::iterator + provider_iterator; +typedef + std::vector<linked_ptr<ContentSettingsProviderInterface> >::const_iterator + const_provider_iterator; + } // namespace @@ -125,10 +103,20 @@ struct HostContentSettingsMap::ExtendedContentSettings { HostContentSettingsMap::HostContentSettingsMap(Profile* profile) : profile_(profile), - block_third_party_cookies_(false), - is_block_third_party_cookies_managed_(false), is_off_the_record_(profile_->IsOffTheRecord()), - updating_preferences_(false) { + updating_preferences_(false), + block_third_party_cookies_(false), + is_block_third_party_cookies_managed_(false) { + // The order in which the content settings providers are created is critical, + // as providers that are further down in the list (i.e. added later) override + // providers further up. + content_settings_providers_.push_back( + linked_ptr<ContentSettingsProviderInterface>( + new PrefContentSettingsProvider(profile))); + content_settings_providers_.push_back( + linked_ptr<ContentSettingsProviderInterface>( + new PolicyContentSettingsProvider(profile))); + PrefService* prefs = profile_->GetPrefs(); MigrateObsoleteCookiePref(prefs); @@ -137,11 +125,6 @@ HostContentSettingsMap::HostContentSettingsMap(Profile* profile) MigrateObsoletePerhostPref(prefs); - // Read global defaults. - DCHECK_EQ(arraysize(kTypeNames), - static_cast<size_t>(CONTENT_SETTINGS_NUM_TYPES)); - ReadDefaultSettings(false); - // Read misc. global settings. block_third_party_cookies_ = prefs->GetBoolean(prefs::kBlockThirdPartyCookies); @@ -165,29 +148,15 @@ HostContentSettingsMap::HostContentSettingsMap(Profile* profile) ReadExceptions(false); pref_change_registrar_.Init(prefs); - pref_change_registrar_.Add(prefs::kDefaultContentSettings, this); pref_change_registrar_.Add(prefs::kContentSettingsPatterns, this); pref_change_registrar_.Add(prefs::kBlockThirdPartyCookies, this); pref_change_registrar_.Add(prefs::kBlockNonsandboxedPlugins, this); - // The following preferences are only used to indicate if a - // default-content-setting is managed and to hold the managed default-setting - // value. If the value for any of the following perferences is set then the - // corresponding default-content-setting is managed. These preferences exist - // in parallel to the preference default-content-settings. If a - // default-content-settings-type is managed any user defined excpetions - // (patterns) for this type are ignored. - pref_change_registrar_.Add(prefs::kManagedDefaultCookiesSetting, this); - pref_change_registrar_.Add(prefs::kManagedDefaultImagesSetting, this); - pref_change_registrar_.Add(prefs::kManagedDefaultJavaScriptSetting, this); - pref_change_registrar_.Add(prefs::kManagedDefaultPluginsSetting, this); - pref_change_registrar_.Add(prefs::kManagedDefaultPopupsSetting, this); notification_registrar_.Add(this, NotificationType::PROFILE_DESTROYED, Source<Profile>(profile_)); } // static void HostContentSettingsMap::RegisterUserPrefs(PrefService* prefs) { - prefs->RegisterDictionaryPref(prefs::kDefaultContentSettings); prefs->RegisterIntegerPref(prefs::kContentSettingsVersion, ContentSettingsPattern::kContentSettingsPatternVersion); prefs->RegisterDictionaryPref(prefs::kContentSettingsPatterns); @@ -195,19 +164,6 @@ void HostContentSettingsMap::RegisterUserPrefs(PrefService* prefs) { prefs->RegisterBooleanPref(prefs::kBlockNonsandboxedPlugins, false); prefs->RegisterIntegerPref(prefs::kContentSettingsWindowLastTabIndex, 0); - // Preferences for default content setting policies. A policy is not set of - // the corresponding preferences below is set to CONTENT_SETTING_DEFAULT. - prefs->RegisterIntegerPref(prefs::kManagedDefaultCookiesSetting, - CONTENT_SETTING_DEFAULT); - prefs->RegisterIntegerPref(prefs::kManagedDefaultImagesSetting, - CONTENT_SETTING_DEFAULT); - prefs->RegisterIntegerPref(prefs::kManagedDefaultJavaScriptSetting, - CONTENT_SETTING_DEFAULT); - prefs->RegisterIntegerPref(prefs::kManagedDefaultPluginsSetting, - CONTENT_SETTING_DEFAULT); - prefs->RegisterIntegerPref(prefs::kManagedDefaultPopupsSetting, - CONTENT_SETTING_DEFAULT); - // Obsolete prefs, for migration: prefs->RegisterIntegerPref(prefs::kCookieBehavior, net::StaticCookiePolicy::ALLOW_ALL_COOKIES); @@ -217,10 +173,21 @@ void HostContentSettingsMap::RegisterUserPrefs(PrefService* prefs) { ContentSetting HostContentSettingsMap::GetDefaultContentSetting( ContentSettingsType content_type) const { - AutoLock auto_lock(lock_); - if (IsDefaultContentSettingManaged(content_type)) - return managed_default_content_settings_.settings[content_type]; - return default_content_settings_.settings[content_type]; + ContentSetting setting = CONTENT_SETTING_DEFAULT; + for (const_provider_iterator provider = content_settings_providers_.begin(); + provider != content_settings_providers_.end(); ++provider) { + if (!(*provider)->CanProvideDefaultSetting(content_type)) + continue; + ContentSetting provided_setting = + (*provider)->ProvideDefaultSetting(content_type); + if (provided_setting != CONTENT_SETTING_DEFAULT) + setting = provided_setting; + } + // The method GetDefaultContentSetting always has to return an explicit + // value that is to be used as default. We here rely on the + // PrefContentSettingProvider to always provide a value. + CHECK_NE(CONTENT_SETTING_DEFAULT, setting); + return setting; } ContentSetting HostContentSettingsMap::GetContentSetting( @@ -318,22 +285,17 @@ ContentSettings HostContentSettingsMap::GetContentSettings( const GURL& url) const { ContentSettings output = GetNonDefaultContentSettings(url); - AutoLock auto_lock(lock_); - // If we require a resource identifier, set the content settings to default, // otherwise make the defaults explicit. for (int j = 0; j < CONTENT_SETTINGS_NUM_TYPES; ++j) { if (RequiresResourceIdentifier(ContentSettingsType(j))) { output.settings[j] = CONTENT_SETTING_DEFAULT; } else { - if (output.settings[j] == CONTENT_SETTING_DEFAULT) { - output.settings[j] = default_content_settings_.settings[j]; - } // A managed default content setting has the highest priority and hence // will overwrite any previously set value. - if (IsDefaultContentSettingManaged(ContentSettingsType(j))) { - output.settings[j] = - managed_default_content_settings_.settings[j]; + if ((output.settings[j] == CONTENT_SETTING_DEFAULT) || + IsDefaultContentSettingManaged(ContentSettingsType(j))) { + output.settings[j] = GetDefaultContentSetting(ContentSettingsType(j)); } } } @@ -441,7 +403,6 @@ void HostContentSettingsMap::SetDefaultContentSetting( setting != CONTENT_SETTING_ASK || CommandLine::ForCurrentProcess()->HasSwitch( switches::kEnableClickToPlay)); - PrefService* prefs = profile_->GetPrefs(); // The default settings may not be directly modified for OTR sessions. // Instead, they are synced to the main profile's setting. @@ -450,29 +411,10 @@ void HostContentSettingsMap::SetDefaultContentSetting( return; } - DictionaryValue* default_settings_dictionary = - prefs->GetMutableDictionary(prefs::kDefaultContentSettings); - std::string dictionary_path(kTypeNames[content_type]); - updating_preferences_ = true; - { - AutoLock auto_lock(lock_); - ScopedPrefUpdate update(prefs, prefs::kDefaultContentSettings); - if ((setting == CONTENT_SETTING_DEFAULT) || - (setting == kDefaultSettings[content_type])) { - default_content_settings_.settings[content_type] = - kDefaultSettings[content_type]; - default_settings_dictionary->RemoveWithoutPathExpansion(dictionary_path, - NULL); - } else { - default_content_settings_.settings[content_type] = setting; - default_settings_dictionary->SetWithoutPathExpansion( - dictionary_path, Value::CreateIntegerValue(setting)); - } + for (provider_iterator provider = content_settings_providers_.begin(); + provider != content_settings_providers_.end(); ++provider) { + (*provider)->UpdateDefaultSetting(content_type, setting); } - updating_preferences_ = false; - - NotifyObservers( - ContentSettingsDetails(ContentSettingsPattern(), content_type, "")); } void HostContentSettingsMap::SetContentSetting( @@ -727,10 +669,10 @@ void HostContentSettingsMap::ResetToDefaults() { { AutoLock auto_lock(lock_); - default_content_settings_ = ContentSettings(); - ForceDefaultsToBeExplicit(); - // Clear all content settings map except the - // managed_default_content_settings. + for (provider_iterator provider = content_settings_providers_.begin(); + provider != content_settings_providers_.end(); ++provider) { + (*provider)->ResetToDefaults(); + } host_content_settings_.clear(); off_the_record_settings_.clear(); // Don't reset block third party cookies if they are managed. @@ -742,7 +684,6 @@ void HostContentSettingsMap::ResetToDefaults() { if (!is_off_the_record_) { PrefService* prefs = profile_->GetPrefs(); updating_preferences_ = true; - prefs->ClearPref(prefs::kDefaultContentSettings); prefs->ClearPref(prefs::kContentSettingsPatterns); // If the block third party cookies preference is managed we still must // clear it in order to restore the default value for later when the @@ -761,46 +702,25 @@ void HostContentSettingsMap::Observe(NotificationType type, const NotificationDetails& details) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); - if (NotificationType::PREF_CHANGED == type) { + if (type == NotificationType::PREF_CHANGED) { + DCHECK_EQ(profile_->GetPrefs(), Source<PrefService>(source).ptr()); if (updating_preferences_) return; std::string* name = Details<std::string>(details).ptr(); - if (prefs::kDefaultContentSettings == *name) { - ReadDefaultSettings(true); - } else if (prefs::kContentSettingsPatterns == *name) { + if (*name == prefs::kContentSettingsPatterns) { ReadExceptions(true); - } else if (prefs::kBlockThirdPartyCookies == *name) { + } else if (*name == prefs::kBlockThirdPartyCookies) { AutoLock auto_lock(lock_); block_third_party_cookies_ = profile_->GetPrefs()->GetBoolean( prefs::kBlockThirdPartyCookies); is_block_third_party_cookies_managed_ = profile_->GetPrefs()->IsManagedPreference( prefs::kBlockThirdPartyCookies); - } else if (prefs::kBlockNonsandboxedPlugins == *name) { + } else if (*name == prefs::kBlockNonsandboxedPlugins) { AutoLock auto_lock(lock_); block_nonsandboxed_plugins_ = profile_->GetPrefs()->GetBoolean( prefs::kBlockNonsandboxedPlugins); - } else if (prefs::kManagedDefaultCookiesSetting == *name) { - UpdateManagedDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES, - profile_->GetPrefs(), - &managed_default_content_settings_); - } else if (prefs::kManagedDefaultImagesSetting == *name) { - UpdateManagedDefaultSetting(CONTENT_SETTINGS_TYPE_IMAGES, - profile_->GetPrefs(), - &managed_default_content_settings_); - } else if (prefs::kManagedDefaultJavaScriptSetting == *name) { - UpdateManagedDefaultSetting(CONTENT_SETTINGS_TYPE_JAVASCRIPT, - profile_->GetPrefs(), - &managed_default_content_settings_); - } else if (prefs::kManagedDefaultPluginsSetting == *name) { - UpdateManagedDefaultSetting(CONTENT_SETTINGS_TYPE_PLUGINS, - profile_->GetPrefs(), - &managed_default_content_settings_); - } else if (prefs::kManagedDefaultPopupsSetting == *name) { - UpdateManagedDefaultSetting(CONTENT_SETTINGS_TYPE_POPUPS, - profile_->GetPrefs(), - &managed_default_content_settings_); } else { NOTREACHED() << "Unexpected preference observed"; return; @@ -811,7 +731,8 @@ void HostContentSettingsMap::Observe(NotificationType type, CONTENT_SETTINGS_TYPE_DEFAULT, "")); } - } else if (NotificationType::PROFILE_DESTROYED == type) { + } else if (type == NotificationType::PROFILE_DESTROYED) { + DCHECK_EQ(profile_, Source<Profile>(source).ptr()); UnregisterObservers(); } else { NOTREACHED() << "Unexpected notification"; @@ -881,16 +802,6 @@ void HostContentSettingsMap::GetResourceSettingsFromDictionary( } } -void HostContentSettingsMap::ForceDefaultsToBeExplicit() { - DCHECK_EQ(arraysize(kDefaultSettings), - static_cast<size_t>(CONTENT_SETTINGS_NUM_TYPES)); - - for (int i = 0; i < CONTENT_SETTINGS_NUM_TYPES; ++i) { - if (default_content_settings_.settings[i] == CONTENT_SETTING_DEFAULT) - default_content_settings_.settings[i] = kDefaultSettings[i]; - } -} - bool HostContentSettingsMap::AllDefault( const ExtendedContentSettings& settings) const { for (size_t i = 0; i < arraysize(settings.content_settings.settings); ++i) { @@ -900,64 +811,19 @@ bool HostContentSettingsMap::AllDefault( return settings.content_settings_for_resources.empty(); } -void HostContentSettingsMap::ReadDefaultSettings(bool overwrite) { - PrefService* prefs = profile_->GetPrefs(); - const DictionaryValue* default_settings_dictionary = - prefs->GetDictionary(prefs::kDefaultContentSettings); - - if (overwrite) - default_content_settings_ = ContentSettings(); - - // Careful: The returned value could be NULL if the pref has never been set. - if (default_settings_dictionary != NULL) { - GetSettingsFromDictionary(default_settings_dictionary, - &default_content_settings_); - } - ForceDefaultsToBeExplicit(); - - // Read managed default content settings. - ReadManagedDefaultSettings(prefs, &managed_default_content_settings_); -} - -void HostContentSettingsMap::ReadManagedDefaultSettings( - const PrefService* prefs, ContentSettings* settings) { - for (size_t type = 0; type < arraysize(kPrefToManageType); ++type) { - if (kPrefToManageType[type] == NULL) { - // TODO(markusheintz): Handle Geolocation and notification separately. - continue; - } - UpdateManagedDefaultSetting(ContentSettingsType(type), prefs, settings); - } -} - -void HostContentSettingsMap::UpdateManagedDefaultSetting( - ContentSettingsType type, - const PrefService* prefs, - ContentSettings* settings) { - // If a pref to manage a default-content-setting was not set (NOTICE: - // "HasPrefPath" returns false if no value was set for a registered pref) then - // the default value of the preference is used. The default value of a - // preference to manage a default-content-settings is - // CONTENT_SETTING_DEFAULT. This indicates that no managed value is set. If a - // pref was set, than it MUST be managed. - DCHECK(!prefs->HasPrefPath(kPrefToManageType[type]) || - prefs->IsManagedPreference(kPrefToManageType[type])); - AutoLock auto_lock(lock_); - settings->settings[type] = IntToContentSetting( - prefs->GetInteger(kPrefToManageType[type])); -} - bool HostContentSettingsMap::IsDefaultContentSettingManaged( ContentSettingsType content_type) const { - // All managed_default_content_settings_ are always set explicitly or - // initialized to CONTENT_SETTINGS_DEFAULT. Hence each content settings type - // that is set to CONTENT_SETTINGS_DEFAULT is not managed since it was not set - // explicitly. - return managed_default_content_settings_.settings[content_type] != - CONTENT_SETTING_DEFAULT; + for (const_provider_iterator provider = content_settings_providers_.begin(); + provider != content_settings_providers_.end(); ++provider) { + if ((*provider)->DefaultSettingIsManaged(content_type)) + return true; + } + return false; } void HostContentSettingsMap::ReadExceptions(bool overwrite) { + AutoLock lock(lock_); + PrefService* prefs = profile_->GetPrefs(); DictionaryValue* all_settings_dictionary = prefs->GetMutableDictionary(prefs::kContentSettingsPatterns); diff --git a/chrome/browser/content_settings/host_content_settings_map.h b/chrome/browser/content_settings/host_content_settings_map.h index e19c125..915d974 100644 --- a/chrome/browser/content_settings/host_content_settings_map.h +++ b/chrome/browser/content_settings/host_content_settings_map.h @@ -15,6 +15,7 @@ #include <vector> #include "base/basictypes.h" +#include "base/linked_ptr.h" #include "base/lock.h" #include "base/ref_counted.h" #include "chrome/browser/browser_thread.h" @@ -25,6 +26,7 @@ #include "chrome/common/notification_registrar.h" class ContentSettingsDetails; +class ContentSettingsProviderInterface; class DictionaryValue; class GURL; class PrefService; @@ -187,30 +189,9 @@ class HostContentSettingsMap void GetResourceSettingsFromDictionary(const DictionaryValue* dictionary, ResourceContentSettings* settings); - // Forces the default settings to be explicitly set instead of themselves - // being CONTENT_SETTING_DEFAULT. - void ForceDefaultsToBeExplicit(); - // Returns true if |settings| consists entirely of CONTENT_SETTING_DEFAULT. bool AllDefault(const ExtendedContentSettings& settings) const; - // Reads the default settings from the prefereces service. If |overwrite| is - // true and the preference is missing, the local copy will be cleared as well. - void ReadDefaultSettings(bool overwrite); - - // Reads managed default content settings from the preference service |prefs|. - // |settings| is set to the respective content setting for managed settings, - // and to CONTENT_SETTING_DEFAULT for other settings. - void ReadManagedDefaultSettings(const PrefService* prefs, - ContentSettings* settings); - - // Updates the managed setting of the default-content-settings-type |type|. - // The updated setting is read from the preference service |prefs| and written - // to |settings|. - void UpdateManagedDefaultSetting(ContentSettingsType type, - const PrefService* prefs, - ContentSettings* settings); - // Reads the host exceptions from the prefereces service. If |overwrite| is // true and the preference is missing, the local copy will be cleared as well. void ReadExceptions(bool overwrite); @@ -240,9 +221,22 @@ class HostContentSettingsMap NotificationRegistrar notification_registrar_; PrefChangeRegistrar pref_change_registrar_; - // Copies of the pref data, so that we can read it on the IO thread. - ContentSettings default_content_settings_; - ContentSettings managed_default_content_settings_; + // Whether this settings map is for an OTR session. + bool is_off_the_record_; + + // Whether we are currently updating preferences, this is used to ignore + // notifications from the preferences service that we triggered ourself. + bool updating_preferences_; + + // Content setting providers. + std::vector<linked_ptr<ContentSettingsProviderInterface> > + content_settings_providers_; + + // Used around accesses to the following objects to guarantee thread safety. + mutable Lock lock_; + + // Copies of the pref data, so that we can read it on threads other than the + // UI thread. HostContentSettings host_content_settings_; // Differences to the preference-stored host content settings for @@ -254,16 +248,6 @@ class HostContentSettingsMap bool is_block_third_party_cookies_managed_; bool block_nonsandboxed_plugins_; - // Used around accesses to the settings objects to guarantee thread safety. - mutable Lock lock_; - - // Whether this settings map is for an OTR session. - bool is_off_the_record_; - - // Whether we are currently updating preferences, this is used to ignore - // notifications from the preferences service that we triggered ourself. - bool updating_preferences_; - DISALLOW_COPY_AND_ASSIGN(HostContentSettingsMap); }; diff --git a/chrome/browser/content_settings/host_content_settings_map_unittest.cc b/chrome/browser/content_settings/host_content_settings_map_unittest.cc index 280799b..2e0929e 100644 --- a/chrome/browser/content_settings/host_content_settings_map_unittest.cc +++ b/chrome/browser/content_settings/host_content_settings_map_unittest.cc @@ -2,7 +2,7 @@ // 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/host_content_settings_map.h" +#include "chrome/browser/content_settings/host_content_settings_map_unittest.h" #include "base/auto_reset.h" #include "base/command_line.h" @@ -33,40 +33,6 @@ bool SettingsEqual(const ContentSettings& settings1, return true; } -class StubSettingsObserver : public NotificationObserver { - public: - StubSettingsObserver() : last_notifier(NULL), counter(0) { - registrar_.Add(this, NotificationType::CONTENT_SETTINGS_CHANGED, - NotificationService::AllSources()); - } - - virtual void Observe(NotificationType type, - const NotificationSource& source, - const NotificationDetails& details) { - ++counter; - Source<HostContentSettingsMap> content_settings(source); - Details<ContentSettingsDetails> settings_details(details); - last_notifier = content_settings.ptr(); - last_pattern = settings_details.ptr()->pattern(); - last_update_all = settings_details.ptr()->update_all(); - last_update_all_types = settings_details.ptr()->update_all_types(); - last_type = settings_details.ptr()->type(); - // This checks that calling a Get function from an observer doesn't - // deadlock. - last_notifier->GetContentSettings(GURL("http://random-hostname.com/")); - } - - HostContentSettingsMap* last_notifier; - ContentSettingsPattern last_pattern; - bool last_update_all; - bool last_update_all_types; - int counter; - ContentSettingsType last_type; - - private: - NotificationRegistrar registrar_; -}; - class HostContentSettingsMapTest : public testing::Test { public: HostContentSettingsMapTest() : ui_thread_(BrowserThread::UI, &message_loop_) { @@ -831,75 +797,6 @@ TEST_F(HostContentSettingsMapTest, OverwrittenDefaultContentSetting) { CONTENT_SETTINGS_TYPE_COOKIES)); } -// When a default-content-setting is set to a managed setting a -// CONTENT_SETTINGS_CHANGED notification should be fired. The same should happen -// if the managed setting is removed. -TEST_F(HostContentSettingsMapTest, ObserveManagedSettingsChange) { - TestingProfile profile; - HostContentSettingsMap* host_content_settings_map = - profile.GetHostContentSettingsMap(); - StubSettingsObserver observer; - TestingPrefService* prefs = profile.GetTestingPrefService(); - - // TODO(markusheintz): I think it would be better to send notifications only - // for a specific content-settings-type. - - // Set the managed default-content-setting. - prefs->SetManagedPref(prefs::kManagedDefaultImagesSetting, - Value::CreateIntegerValue(CONTENT_SETTING_BLOCK)); - EXPECT_EQ(host_content_settings_map, observer.last_notifier); - EXPECT_EQ(ContentSettingsPattern(), observer.last_pattern); - EXPECT_EQ(CONTENT_SETTINGS_TYPE_DEFAULT, observer.last_type); - EXPECT_TRUE(observer.last_update_all); - EXPECT_TRUE(observer.last_update_all_types); - EXPECT_EQ(1, observer.counter); - - // Remove the managed default-content-setting. - prefs->RemoveManagedPref(prefs::kManagedDefaultImagesSetting); - EXPECT_EQ(host_content_settings_map, observer.last_notifier); - EXPECT_EQ(CONTENT_SETTINGS_TYPE_DEFAULT, observer.last_type); - EXPECT_EQ(ContentSettingsPattern(), observer.last_pattern); - EXPECT_TRUE(observer.last_update_all); - EXPECT_TRUE(observer.last_update_all_types); - EXPECT_EQ(2, observer.counter); -} - -// When a default-content-setting is set to a managed setting a -// CONTENT_SETTINGS_CHANGED notification should be fired. The same should happen -// if the managed setting is removed. In this test-case the actual managed -// setting is the same. Just the managed status of the default-content-setting -// changes. -TEST_F(HostContentSettingsMapTest, ObserveManagedSettingsNoChange) { - TestingProfile profile; - HostContentSettingsMap* host_content_settings_map = - profile.GetHostContentSettingsMap(); - StubSettingsObserver observer; - TestingPrefService* prefs = profile.GetTestingPrefService(); - - // TODO(markusheintz): I think it would be better to send notifications only - // for a specific content-settings-type. - - // Set the managed default-content-setting. In this case the actual setting - // does not change. - prefs->SetManagedPref(prefs::kManagedDefaultImagesSetting, - Value::CreateIntegerValue(CONTENT_SETTING_ALLOW)); - EXPECT_EQ(host_content_settings_map, observer.last_notifier); - EXPECT_EQ(ContentSettingsPattern(), observer.last_pattern); - EXPECT_EQ(CONTENT_SETTINGS_TYPE_DEFAULT, observer.last_type); - EXPECT_TRUE(observer.last_update_all); - EXPECT_TRUE(observer.last_update_all_types); - EXPECT_EQ(1, observer.counter); - - // Remove the managed default-content-setting. - prefs->RemoveManagedPref(prefs::kManagedDefaultImagesSetting); - EXPECT_EQ(host_content_settings_map, observer.last_notifier); - EXPECT_EQ(CONTENT_SETTINGS_TYPE_DEFAULT, observer.last_type); - EXPECT_EQ(ContentSettingsPattern(), observer.last_pattern); - EXPECT_TRUE(observer.last_update_all); - EXPECT_TRUE(observer.last_update_all_types); - EXPECT_EQ(2, observer.counter); -} - // If a setting for a default-content-setting-type is set while the type is // managed, then the new setting should be preserved and used after the // default-content-setting-type is not managed anymore. diff --git a/chrome/browser/content_settings/host_content_settings_map_unittest.h b/chrome/browser/content_settings/host_content_settings_map_unittest.h new file mode 100644 index 0000000..ba56ab4 --- /dev/null +++ b/chrome/browser/content_settings/host_content_settings_map_unittest.h @@ -0,0 +1,49 @@ +// Copyright (c) 2010 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. + +#ifndef CHROME_BROWSER_CONTENT_SETTINGS_HOST_CONTENT_SETTINGS_MAP_UNITTEST_H_ +#define CHROME_BROWSER_CONTENT_SETTINGS_HOST_CONTENT_SETTINGS_MAP_UNITTEST_H_ +#pragma once + +#include "chrome/browser/content_settings/content_settings_details.h" +#include "chrome/browser/content_settings/host_content_settings_map.h" +#include "chrome/common/notification_service.h" +#include "googleurl/src/gurl.h" + +class HostContentSettingsMap; + +class StubSettingsObserver : public NotificationObserver { + public: + StubSettingsObserver() : last_notifier(NULL), counter(0) { + registrar_.Add(this, NotificationType::CONTENT_SETTINGS_CHANGED, + NotificationService::AllSources()); + } + + virtual void Observe(NotificationType type, + const NotificationSource& source, + const NotificationDetails& details) { + ++counter; + Source<HostContentSettingsMap> content_settings(source); + Details<ContentSettingsDetails> settings_details(details); + last_notifier = content_settings.ptr(); + last_pattern = settings_details.ptr()->pattern(); + last_update_all = settings_details.ptr()->update_all(); + last_update_all_types = settings_details.ptr()->update_all_types(); + last_type = settings_details.ptr()->type(); + // This checks that calling a Get function from an observer doesn't + // deadlock. + last_notifier->GetContentSettings(GURL("http://random-hostname.com/")); + } + + HostContentSettingsMap* last_notifier; + ContentSettingsPattern last_pattern; + bool last_update_all; + bool last_update_all_types; + int counter; + ContentSettingsType last_type; + + private: + NotificationRegistrar registrar_; +}; +#endif // CHROME_BROWSER_CONTENT_SETTINGS_HOST_CONTENT_SETTINGS_MAP_UNITTEST_H_ diff --git a/chrome/browser/content_settings/mock_content_settings_provider.cc b/chrome/browser/content_settings/mock_content_settings_provider.cc index f93f7ce..ee3e845 100644 --- a/chrome/browser/content_settings/mock_content_settings_provider.cc +++ b/chrome/browser/content_settings/mock_content_settings_provider.cc @@ -19,12 +19,12 @@ MockContentSettingsProvider::~MockContentSettingsProvider() { } bool MockContentSettingsProvider::CanProvideDefaultSetting( - ContentSettingsType content_type) { + ContentSettingsType content_type) const { return content_type == content_type_; } ContentSetting MockContentSettingsProvider::ProvideDefaultSetting( - ContentSettingsType content_type) { + ContentSettingsType content_type) const { return content_type == content_type_ ? setting_ : CONTENT_SETTING_DEFAULT; } @@ -36,6 +36,9 @@ void MockContentSettingsProvider::UpdateDefaultSetting( } bool MockContentSettingsProvider::DefaultSettingIsManaged( - ContentSettingsType content_type) { + ContentSettingsType content_type) const { return content_type == content_type_ && is_managed_; } + +void MockContentSettingsProvider::ResetToDefaults() { +} diff --git a/chrome/browser/content_settings/mock_content_settings_provider.h b/chrome/browser/content_settings/mock_content_settings_provider.h index e716909..113a8ae 100644 --- a/chrome/browser/content_settings/mock_content_settings_provider.h +++ b/chrome/browser/content_settings/mock_content_settings_provider.h @@ -20,12 +20,13 @@ class MockContentSettingsProvider : public ContentSettingsProviderInterface { virtual ~MockContentSettingsProvider(); // ContentSettingsProviderInterface implementation. - virtual bool CanProvideDefaultSetting(ContentSettingsType content_type); + virtual bool CanProvideDefaultSetting(ContentSettingsType content_type) const; virtual ContentSetting ProvideDefaultSetting( - ContentSettingsType content_type); + ContentSettingsType content_type) const; virtual void UpdateDefaultSetting(ContentSettingsType content_type, ContentSetting setting); - virtual bool DefaultSettingIsManaged(ContentSettingsType content_type); + virtual void ResetToDefaults(); + virtual bool DefaultSettingIsManaged(ContentSettingsType content_type) const; private: ContentSettingsType content_type_; diff --git a/chrome/browser/content_settings/policy_content_settings_provider.cc b/chrome/browser/content_settings/policy_content_settings_provider.cc new file mode 100644 index 0000000..5bc8e9f --- /dev/null +++ b/chrome/browser/content_settings/policy_content_settings_provider.cc @@ -0,0 +1,204 @@ +// Copyright (c) 2010 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/policy_content_settings_provider.h" + +#include "base/command_line.h" +#include "chrome/browser/browser_thread.h" +#include "chrome/browser/content_settings/content_settings_details.h" +#include "chrome/browser/content_settings/content_settings_pattern.h" +#include "chrome/browser/prefs/pref_service.h" +#include "chrome/browser/prefs/scoped_pref_update.h" +#include "chrome/browser/profiles/profile.h" +#include "chrome/common/chrome_switches.h" +#include "chrome/common/notification_details.h" +#include "chrome/common/notification_service.h" +#include "chrome/common/notification_source.h" +#include "chrome/common/pref_names.h" + +namespace { + +// Base pref path of the prefs that contain the managed default content +// settings values. +const std::string kManagedSettings = + "profile.managed_default_content_settings"; + +// The preferences used to manage ContentSettingsTypes. +const char* kPrefToManageType[CONTENT_SETTINGS_NUM_TYPES] = { + prefs::kManagedDefaultCookiesSetting, + prefs::kManagedDefaultImagesSetting, + prefs::kManagedDefaultJavaScriptSetting, + prefs::kManagedDefaultPluginsSetting, + prefs::kManagedDefaultPopupsSetting, + NULL, // Not used for Geolocation + NULL, // Not used for Notifications +}; + +} // namespace + +PolicyContentSettingsProvider::PolicyContentSettingsProvider(Profile* profile) + : profile_(profile), + is_off_the_record_(profile_->IsOffTheRecord()) { + PrefService* prefs = profile->GetPrefs(); + + // Read global defaults. + DCHECK_EQ(arraysize(kPrefToManageType), + static_cast<size_t>(CONTENT_SETTINGS_NUM_TYPES)); + ReadManagedDefaultSettings(); + + pref_change_registrar_.Init(prefs); + // The following preferences are only used to indicate if a + // default-content-setting is managed and to hold the managed default-setting + // value. If the value for any of the following perferences is set then the + // corresponding default-content-setting is managed. These preferences exist + // in parallel to the preference default-content-settings. If a + // default-content-settings-type is managed any user defined excpetions + // (patterns) for this type are ignored. + pref_change_registrar_.Add(prefs::kManagedDefaultCookiesSetting, this); + pref_change_registrar_.Add(prefs::kManagedDefaultImagesSetting, this); + pref_change_registrar_.Add(prefs::kManagedDefaultJavaScriptSetting, this); + pref_change_registrar_.Add(prefs::kManagedDefaultPluginsSetting, this); + pref_change_registrar_.Add(prefs::kManagedDefaultPopupsSetting, this); + notification_registrar_.Add(this, NotificationType::PROFILE_DESTROYED, + Source<Profile>(profile_)); +} + +PolicyContentSettingsProvider::~PolicyContentSettingsProvider() { + UnregisterObservers(); +} + +bool PolicyContentSettingsProvider::CanProvideDefaultSetting( + ContentSettingsType content_type) const { + AutoLock lock(lock_); + if (managed_default_content_settings_.settings[content_type] != + CONTENT_SETTING_DEFAULT) { + return true; + } else { + return false; + } +} + +ContentSetting PolicyContentSettingsProvider::ProvideDefaultSetting( + ContentSettingsType content_type) const { + AutoLock auto_lock(lock_); + return managed_default_content_settings_.settings[content_type]; +} + +void PolicyContentSettingsProvider::UpdateDefaultSetting( + ContentSettingsType content_type, + ContentSetting setting) { +} + +bool PolicyContentSettingsProvider::DefaultSettingIsManaged( + ContentSettingsType content_type) const { + AutoLock lock(lock_); + if (managed_default_content_settings_.settings[content_type] != + CONTENT_SETTING_DEFAULT) { + return true; + } else { + return false; + } +} + +void PolicyContentSettingsProvider::ResetToDefaults() { +} + +void PolicyContentSettingsProvider::Observe(NotificationType type, + const NotificationSource& source, + const NotificationDetails& details) { + DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); + + if (type == NotificationType::PREF_CHANGED) { + DCHECK_EQ(profile_->GetPrefs(), Source<PrefService>(source).ptr()); + std::string* name = Details<std::string>(details).ptr(); + if (*name == prefs::kManagedDefaultCookiesSetting) { + UpdateManagedDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES); + } else if (*name == prefs::kManagedDefaultImagesSetting) { + UpdateManagedDefaultSetting(CONTENT_SETTINGS_TYPE_IMAGES); + } else if (*name == prefs::kManagedDefaultJavaScriptSetting) { + UpdateManagedDefaultSetting(CONTENT_SETTINGS_TYPE_JAVASCRIPT); + } else if (*name == prefs::kManagedDefaultPluginsSetting) { + UpdateManagedDefaultSetting(CONTENT_SETTINGS_TYPE_PLUGINS); + } else if (*name == prefs::kManagedDefaultPopupsSetting) { + UpdateManagedDefaultSetting(CONTENT_SETTINGS_TYPE_POPUPS); + } else { + NOTREACHED() << "Unexpected preference observed"; + return; + } + + if (!is_off_the_record_) { + NotifyObservers(ContentSettingsDetails( + ContentSettingsPattern(), CONTENT_SETTINGS_TYPE_DEFAULT, "")); + } + } else if (type == NotificationType::PROFILE_DESTROYED) { + DCHECK_EQ(profile_, Source<Profile>(source).ptr()); + UnregisterObservers(); + } else { + NOTREACHED() << "Unexpected notification"; + } +} + +void PolicyContentSettingsProvider::UnregisterObservers() { + DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); + if (!profile_) + return; + pref_change_registrar_.RemoveAll(); + notification_registrar_.Remove(this, NotificationType::PROFILE_DESTROYED, + Source<Profile>(profile_)); + profile_ = NULL; +} + + +void PolicyContentSettingsProvider::NotifyObservers( + const ContentSettingsDetails& details) { + DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); + if (profile_ == NULL) + return; + NotificationService::current()->Notify( + NotificationType::CONTENT_SETTINGS_CHANGED, + Source<HostContentSettingsMap>(profile_->GetHostContentSettingsMap()), + Details<const ContentSettingsDetails>(&details)); +} + +void PolicyContentSettingsProvider::ReadManagedDefaultSettings() { + for (size_t type = 0; type < arraysize(kPrefToManageType); ++type) { + if (kPrefToManageType[type] == NULL) { + // TODO(markusheintz): Handle Geolocation and notification separately. + continue; + } + UpdateManagedDefaultSetting(ContentSettingsType(type)); + } +} + +void PolicyContentSettingsProvider::UpdateManagedDefaultSetting( + ContentSettingsType type) { + // If a pref to manage a default-content-setting was not set (NOTICE: + // "HasPrefPath" returns false if no value was set for a registered pref) then + // the default value of the preference is used. The default value of a + // preference to manage a default-content-settings is + // CONTENT_SETTING_DEFAULT. This indicates that no managed value is set. If a + // pref was set, than it MUST be managed. + PrefService* prefs = profile_->GetPrefs(); + DCHECK(!prefs->HasPrefPath(kPrefToManageType[type]) || + prefs->IsManagedPreference(kPrefToManageType[type])); + AutoLock auto_lock(lock_); + managed_default_content_settings_.settings[type] = IntToContentSetting( + prefs->GetInteger(kPrefToManageType[type])); +} + +// static +void PolicyContentSettingsProvider::RegisterUserPrefs(PrefService* prefs) { + // Preferences for default content setting policies. A policy is not set of + // the corresponding preferences below is set to CONTENT_SETTING_DEFAULT. + prefs->RegisterIntegerPref(prefs::kManagedDefaultCookiesSetting, + CONTENT_SETTING_DEFAULT); + prefs->RegisterIntegerPref(prefs::kManagedDefaultImagesSetting, + CONTENT_SETTING_DEFAULT); + prefs->RegisterIntegerPref(prefs::kManagedDefaultJavaScriptSetting, + CONTENT_SETTING_DEFAULT); + prefs->RegisterIntegerPref(prefs::kManagedDefaultPluginsSetting, + CONTENT_SETTING_DEFAULT); + prefs->RegisterIntegerPref(prefs::kManagedDefaultPopupsSetting, + CONTENT_SETTING_DEFAULT); +} diff --git a/chrome/browser/content_settings/policy_content_settings_provider.h b/chrome/browser/content_settings/policy_content_settings_provider.h new file mode 100644 index 0000000..1844234 --- /dev/null +++ b/chrome/browser/content_settings/policy_content_settings_provider.h @@ -0,0 +1,78 @@ +// Copyright (c) 2010 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. + +#ifndef CHROME_BROWSER_CONTENT_SETTINGS_POLICY_CONTENT_SETTINGS_PROVIDER_H_ +#define CHROME_BROWSER_CONTENT_SETTINGS_POLICY_CONTENT_SETTINGS_PROVIDER_H_ +#pragma once + +// A content settings provider that takes its settings out of policies. + +#include "base/basictypes.h" +#include "base/lock.h" +#include "chrome/browser/content_settings/content_settings_provider.h" +#include "chrome/browser/prefs/pref_change_registrar.h" +#include "chrome/common/notification_observer.h" +#include "chrome/common/notification_registrar.h" + +class ContentSettingsDetails; +class DictionaryValue; +class PrefService; +class Profile; + +class PolicyContentSettingsProvider : public ContentSettingsProviderInterface, + public NotificationObserver { + public: + explicit PolicyContentSettingsProvider(Profile* profile); + virtual ~PolicyContentSettingsProvider(); + + // ContentSettingsProviderInterface implementation. + virtual bool CanProvideDefaultSetting(ContentSettingsType content_type) const; + virtual ContentSetting ProvideDefaultSetting( + ContentSettingsType content_type) const; + virtual void UpdateDefaultSetting(ContentSettingsType content_type, + ContentSetting setting); + virtual void ResetToDefaults(); + virtual bool DefaultSettingIsManaged(ContentSettingsType content_type) const; + + static void RegisterUserPrefs(PrefService* prefs); + + // NotificationObserver implementation. + virtual void Observe(NotificationType type, + const NotificationSource& source, + const NotificationDetails& details); + + private: + // Informs observers that content settings have changed. Make sure that + // |lock_| is not held when calling this, as listeners will usually call one + // of the GetSettings functions in response, which would then lead to a + // mutex deadlock. + void NotifyObservers(const ContentSettingsDetails& details); + + void UnregisterObservers(); + + // Reads the policy managed default settings. + void ReadManagedDefaultSettings(); + + // Reads the policy controlled default settings for a specific content type. + void UpdateManagedDefaultSetting(ContentSettingsType content_type); + + // Copies of the pref data, so that we can read it on the IO thread. + ContentSettings managed_default_content_settings_; + + Profile* profile_; + + // Whether this settings map is for an OTR session. + bool is_off_the_record_; + + // Used around accesses to the managed_default_content_settings_ object to + // guarantee thread safety. + mutable Lock lock_; + + PrefChangeRegistrar pref_change_registrar_; + NotificationRegistrar notification_registrar_; + + DISALLOW_COPY_AND_ASSIGN(PolicyContentSettingsProvider); +}; + +#endif // CHROME_BROWSER_CONTENT_SETTINGS_POLICY_CONTENT_SETTINGS_PROVIDER_H_ diff --git a/chrome/browser/content_settings/policy_content_settings_provider_unittest.cc b/chrome/browser/content_settings/policy_content_settings_provider_unittest.cc new file mode 100644 index 0000000..9c639ab --- /dev/null +++ b/chrome/browser/content_settings/policy_content_settings_provider_unittest.cc @@ -0,0 +1,88 @@ +// Copyright (c) 2010 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/policy_content_settings_provider.h" + +#include "chrome/browser/content_settings/host_content_settings_map_unittest.h" +#include "chrome/browser/prefs/pref_service.h" +#include "chrome/common/pref_names.h" +#include "chrome/common/url_constants.h" +#include "chrome/test/testing_pref_service.h" +#include "chrome/test/testing_profile.h" +#include "testing/gtest/include/gtest/gtest.h" + + +namespace { + +class PolicyContentSettingsProviderTest : public testing::Test { + public: + PolicyContentSettingsProviderTest() + : ui_thread_(BrowserThread::UI, &message_loop_) { + } + + protected: + MessageLoop message_loop_; + BrowserThread ui_thread_; +}; + +TEST_F(PolicyContentSettingsProviderTest, DefaultValues) { + TestingProfile profile; + PolicyContentSettingsProvider provider(&profile); + TestingPrefService* prefs = profile.GetTestingPrefService(); + + // By default, policies should be off. + ASSERT_FALSE( + provider.CanProvideDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES)); + ASSERT_FALSE( + provider.DefaultSettingIsManaged(CONTENT_SETTINGS_TYPE_COOKIES)); + + // Set managed-default-content-setting through the coresponding preferences. + prefs->SetManagedPref(prefs::kManagedDefaultCookiesSetting, + Value::CreateIntegerValue(CONTENT_SETTING_BLOCK)); + ASSERT_TRUE( + provider.CanProvideDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES)); + ASSERT_TRUE( + provider.DefaultSettingIsManaged(CONTENT_SETTINGS_TYPE_COOKIES)); + ASSERT_EQ(CONTENT_SETTING_BLOCK, + provider.ProvideDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES)); + + // Remove managed-default-content-settings-preferences. + prefs->RemoveManagedPref(prefs::kManagedDefaultCookiesSetting); + ASSERT_FALSE( + provider.CanProvideDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES)); + ASSERT_FALSE( + provider.DefaultSettingIsManaged(CONTENT_SETTINGS_TYPE_COOKIES)); +} + +// When a default-content-setting is set to a managed setting a +// CONTENT_SETTINGS_CHANGED notification should be fired. The same should happen +// if the managed setting is removed. +TEST_F(PolicyContentSettingsProviderTest, ObserveManagedSettingsChange) { + TestingProfile profile; + StubSettingsObserver observer; + // Make sure the content settings map exists. + profile.GetHostContentSettingsMap(); + TestingPrefService* prefs = profile.GetTestingPrefService(); + + // Set the managed default-content-setting. + prefs->SetManagedPref(prefs::kManagedDefaultImagesSetting, + Value::CreateIntegerValue(CONTENT_SETTING_BLOCK)); + EXPECT_EQ(profile.GetHostContentSettingsMap(), observer.last_notifier); + EXPECT_EQ(ContentSettingsPattern(), observer.last_pattern); + EXPECT_EQ(CONTENT_SETTINGS_TYPE_DEFAULT, observer.last_type); + EXPECT_TRUE(observer.last_update_all); + EXPECT_TRUE(observer.last_update_all_types); + EXPECT_EQ(1, observer.counter); + + // Remove the managed default-content-setting. + prefs->RemoveManagedPref(prefs::kManagedDefaultImagesSetting); + EXPECT_EQ(profile.GetHostContentSettingsMap(), observer.last_notifier); + EXPECT_EQ(CONTENT_SETTINGS_TYPE_DEFAULT, observer.last_type); + EXPECT_EQ(ContentSettingsPattern(), observer.last_pattern); + EXPECT_TRUE(observer.last_update_all); + EXPECT_TRUE(observer.last_update_all_types); + EXPECT_EQ(2, observer.counter); +} + +} // namespace diff --git a/chrome/browser/content_settings/pref_content_settings_provider.cc b/chrome/browser/content_settings/pref_content_settings_provider.cc new file mode 100644 index 0000000..01ac055 --- /dev/null +++ b/chrome/browser/content_settings/pref_content_settings_provider.cc @@ -0,0 +1,263 @@ +// Copyright (c) 2010 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/pref_content_settings_provider.h" + +#include "base/command_line.h" +#include "chrome/browser/browser_thread.h" +#include "chrome/browser/content_settings/content_settings_details.h" +#include "chrome/browser/content_settings/content_settings_pattern.h" +#include "chrome/browser/prefs/pref_service.h" +#include "chrome/browser/prefs/scoped_pref_update.h" +#include "chrome/browser/profiles/profile.h" +#include "chrome/common/chrome_switches.h" +#include "chrome/common/notification_details.h" +#include "chrome/common/notification_service.h" +#include "chrome/common/notification_source.h" +#include "chrome/common/pref_names.h" + +namespace { + +// The default setting for each content type. +const ContentSetting kDefaultSettings[CONTENT_SETTINGS_NUM_TYPES] = { + CONTENT_SETTING_ALLOW, // CONTENT_SETTINGS_TYPE_COOKIES + CONTENT_SETTING_ALLOW, // CONTENT_SETTINGS_TYPE_IMAGES + CONTENT_SETTING_ALLOW, // CONTENT_SETTINGS_TYPE_JAVASCRIPT + CONTENT_SETTING_ALLOW, // CONTENT_SETTINGS_TYPE_PLUGINS + CONTENT_SETTING_BLOCK, // CONTENT_SETTINGS_TYPE_POPUPS + CONTENT_SETTING_ASK, // Not used for Geolocation + CONTENT_SETTING_ASK, // Not used for Notifications +}; + +// The names of the ContentSettingsType values, for use with dictionary prefs. +const char* kTypeNames[CONTENT_SETTINGS_NUM_TYPES] = { + "cookies", + "images", + "javascript", + "plugins", + "popups", + NULL, // Not used for Geolocation + NULL, // Not used for Notifications +}; + + +// Map ASK for the plugins content type to BLOCK if click-to-play is +// not enabled. +ContentSetting 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 + +PrefContentSettingsProvider::PrefContentSettingsProvider(Profile* profile) + : profile_(profile), + is_off_the_record_(profile_->IsOffTheRecord()), + updating_preferences_(false) { + PrefService* prefs = profile->GetPrefs(); + + // Read global defaults. + DCHECK_EQ(arraysize(kTypeNames), + static_cast<size_t>(CONTENT_SETTINGS_NUM_TYPES)); + ReadDefaultSettings(true); + + pref_change_registrar_.Init(prefs); + pref_change_registrar_.Add(prefs::kDefaultContentSettings, this); + notification_registrar_.Add(this, NotificationType::PROFILE_DESTROYED, + Source<Profile>(profile_)); +} + +PrefContentSettingsProvider::~PrefContentSettingsProvider() { + UnregisterObservers(); +} + +bool PrefContentSettingsProvider::CanProvideDefaultSetting( + ContentSettingsType content_type) const { + return true; +} + +ContentSetting PrefContentSettingsProvider::ProvideDefaultSetting( + ContentSettingsType content_type) const { + AutoLock lock(lock_); + return default_content_settings_.settings[content_type]; +} + +void PrefContentSettingsProvider::UpdateDefaultSetting( + ContentSettingsType content_type, + ContentSetting setting) { + DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); + DCHECK(kTypeNames[content_type] != NULL); // Don't call this for Geolocation. + DCHECK(content_type != CONTENT_SETTINGS_TYPE_PLUGINS || + setting != CONTENT_SETTING_ASK || + CommandLine::ForCurrentProcess()->HasSwitch( + switches::kEnableClickToPlay)); + + // The default settings may not be directly modified for OTR sessions. + // Instead, they are synced to the main profile's setting. + if (is_off_the_record_) + return; + + PrefService* prefs = profile_->GetPrefs(); + + DictionaryValue* default_settings_dictionary = + prefs->GetMutableDictionary(prefs::kDefaultContentSettings); + std::string dictionary_path(kTypeNames[content_type]); + updating_preferences_ = true; + { + AutoLock lock(lock_); + ScopedPrefUpdate update(prefs, prefs::kDefaultContentSettings); + if ((setting == CONTENT_SETTING_DEFAULT) || + (setting == kDefaultSettings[content_type])) { + default_content_settings_.settings[content_type] = + kDefaultSettings[content_type]; + default_settings_dictionary->RemoveWithoutPathExpansion(dictionary_path, + NULL); + } else { + default_content_settings_.settings[content_type] = setting; + default_settings_dictionary->SetWithoutPathExpansion( + dictionary_path, Value::CreateIntegerValue(setting)); + } + } + updating_preferences_ = false; + + NotifyObservers( + ContentSettingsDetails(ContentSettingsPattern(), content_type, "")); +} + +bool PrefContentSettingsProvider::DefaultSettingIsManaged( + ContentSettingsType content_type) const { + return false; +} + +void PrefContentSettingsProvider::ResetToDefaults() { + DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); + AutoLock lock(lock_); + default_content_settings_ = ContentSettings(); + ForceDefaultsToBeExplicit(); + + if (!is_off_the_record_) { + PrefService* prefs = profile_->GetPrefs(); + updating_preferences_ = true; + prefs->ClearPref(prefs::kDefaultContentSettings); + updating_preferences_ = false; + } +} + +void PrefContentSettingsProvider::Observe(NotificationType type, + const NotificationSource& source, + const NotificationDetails& details) { + DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); + + if (type == NotificationType::PREF_CHANGED) { + DCHECK_EQ(profile_->GetPrefs(), Source<PrefService>(source).ptr()); + if (updating_preferences_) + return; + + std::string* name = Details<std::string>(details).ptr(); + if (*name == prefs::kDefaultContentSettings) { + ReadDefaultSettings(true); + } else { + NOTREACHED() << "Unexpected preference observed"; + return; + } + + if (!is_off_the_record_) { + NotifyObservers(ContentSettingsDetails( + ContentSettingsPattern(), CONTENT_SETTINGS_TYPE_DEFAULT, "")); + } + } else if (type == NotificationType::PROFILE_DESTROYED) { + DCHECK_EQ(profile_, Source<Profile>(source).ptr()); + UnregisterObservers(); + } else { + NOTREACHED() << "Unexpected notification"; + } +} + +void PrefContentSettingsProvider::UnregisterObservers() { + DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); + if (!profile_) + return; + pref_change_registrar_.RemoveAll(); + notification_registrar_.Remove(this, NotificationType::PROFILE_DESTROYED, + Source<Profile>(profile_)); + profile_ = NULL; +} + +void PrefContentSettingsProvider::ReadDefaultSettings(bool overwrite) { + PrefService* prefs = profile_->GetPrefs(); + const DictionaryValue* default_settings_dictionary = + prefs->GetDictionary(prefs::kDefaultContentSettings); + + AutoLock lock(lock_); + + if (overwrite) + default_content_settings_ = ContentSettings(); + + // Careful: The returned value could be NULL if the pref has never been set. + if (default_settings_dictionary != NULL) { + GetSettingsFromDictionary(default_settings_dictionary, + &default_content_settings_); + } + ForceDefaultsToBeExplicit(); +} + +void PrefContentSettingsProvider::ForceDefaultsToBeExplicit() { + DCHECK_EQ(arraysize(kDefaultSettings), + static_cast<size_t>(CONTENT_SETTINGS_NUM_TYPES)); + + for (int i = 0; i < CONTENT_SETTINGS_NUM_TYPES; ++i) { + if (default_content_settings_.settings[i] == CONTENT_SETTING_DEFAULT) + default_content_settings_.settings[i] = kDefaultSettings[i]; + } +} + +void PrefContentSettingsProvider::GetSettingsFromDictionary( + const DictionaryValue* dictionary, + ContentSettings* settings) { + for (DictionaryValue::key_iterator i(dictionary->begin_keys()); + i != dictionary->end_keys(); ++i) { + const std::string& content_type(*i); + for (size_t type = 0; type < arraysize(kTypeNames); ++type) { + if ((kTypeNames[type] != NULL) && (kTypeNames[type] == content_type)) { + int setting = CONTENT_SETTING_DEFAULT; + bool found = dictionary->GetIntegerWithoutPathExpansion(content_type, + &setting); + DCHECK(found); + settings->settings[type] = IntToContentSetting(setting); + break; + } + } + } + // Migrate obsolete cookie prompt mode. + if (settings->settings[CONTENT_SETTINGS_TYPE_COOKIES] == + CONTENT_SETTING_ASK) + settings->settings[CONTENT_SETTINGS_TYPE_COOKIES] = CONTENT_SETTING_BLOCK; + + settings->settings[CONTENT_SETTINGS_TYPE_PLUGINS] = + ClickToPlayFixup(CONTENT_SETTINGS_TYPE_PLUGINS, + settings->settings[CONTENT_SETTINGS_TYPE_PLUGINS]); +} + +void PrefContentSettingsProvider::NotifyObservers( + const ContentSettingsDetails& details) { + DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); + if (profile_ == NULL) + return; + NotificationService::current()->Notify( + NotificationType::CONTENT_SETTINGS_CHANGED, + Source<HostContentSettingsMap>(profile_->GetHostContentSettingsMap()), + Details<const ContentSettingsDetails>(&details)); +} + + +// static +void PrefContentSettingsProvider::RegisterUserPrefs(PrefService* prefs) { + prefs->RegisterDictionaryPref(prefs::kDefaultContentSettings); +} diff --git a/chrome/browser/content_settings/pref_content_settings_provider.h b/chrome/browser/content_settings/pref_content_settings_provider.h new file mode 100644 index 0000000..178e903 --- /dev/null +++ b/chrome/browser/content_settings/pref_content_settings_provider.h @@ -0,0 +1,88 @@ +// Copyright (c) 2010 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. + +#ifndef CHROME_BROWSER_CONTENT_SETTINGS_PREF_CONTENT_SETTINGS_PROVIDER_H_ +#define CHROME_BROWSER_CONTENT_SETTINGS_PREF_CONTENT_SETTINGS_PROVIDER_H_ +#pragma once + +// A content settings provider that takes its settings out of the pref service. + +#include "base/basictypes.h" +#include "base/lock.h" +#include "chrome/browser/content_settings/content_settings_provider.h" +#include "chrome/browser/prefs/pref_change_registrar.h" +#include "chrome/common/notification_observer.h" +#include "chrome/common/notification_registrar.h" + +class ContentSettingsDetails; +class DictionaryValue; +class PrefService; +class Profile; + +class PrefContentSettingsProvider : public ContentSettingsProviderInterface, + public NotificationObserver { + public: + explicit PrefContentSettingsProvider(Profile* profile); + virtual ~PrefContentSettingsProvider(); + + // ContentSettingsProviderInterface implementation. + virtual bool CanProvideDefaultSetting(ContentSettingsType content_type) const; + virtual ContentSetting ProvideDefaultSetting( + ContentSettingsType content_type) const; + virtual void UpdateDefaultSetting(ContentSettingsType content_type, + ContentSetting setting); + virtual void ResetToDefaults(); + virtual bool DefaultSettingIsManaged(ContentSettingsType content_type) const; + + static void RegisterUserPrefs(PrefService* prefs); + + // NotificationObserver implementation. + virtual void Observe(NotificationType type, + const NotificationSource& source, + const NotificationDetails& details); + + private: + // Informs observers that content settings have changed. Make sure that + // |lock_| is not held when calling this, as listeners will usually call one + // of the GetSettings functions in response, which would then lead to a + // mutex deadlock. + void NotifyObservers(const ContentSettingsDetails& details); + + void UnregisterObservers(); + + // Sets the fields of |settings| based on the values in |dictionary|. + void GetSettingsFromDictionary(const DictionaryValue* dictionary, + ContentSettings* settings); + + // Forces the default settings to be explicitly set instead of themselves + // being CONTENT_SETTING_DEFAULT. + void ForceDefaultsToBeExplicit(); + + // Reads the default settings from the preferences service. If |overwrite| is + // true and the preference is missing, the local copy will be cleared as well. + void ReadDefaultSettings(bool overwrite); + + // Copies of the pref data, so that we can read it on the IO thread. + ContentSettings default_content_settings_; + + Profile* profile_; + + // Whether this settings map is for an OTR session. + bool is_off_the_record_; + + // Used around accesses to the default_content_settings_ object to guarantee + // thread safety. + mutable Lock lock_; + + PrefChangeRegistrar pref_change_registrar_; + NotificationRegistrar notification_registrar_; + + // Whether we are currently updating preferences, this is used to ignore + // notifications from the preferences service that we triggered ourself. + bool updating_preferences_; + + DISALLOW_COPY_AND_ASSIGN(PrefContentSettingsProvider); +}; + +#endif // CHROME_BROWSER_CONTENT_SETTINGS_PREF_CONTENT_SETTINGS_PROVIDER_H_ diff --git a/chrome/browser/content_settings/pref_content_settings_provider_unittest.cc b/chrome/browser/content_settings/pref_content_settings_provider_unittest.cc new file mode 100644 index 0000000..f4289f3 --- /dev/null +++ b/chrome/browser/content_settings/pref_content_settings_provider_unittest.cc @@ -0,0 +1,124 @@ +// Copyright (c) 2010 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/pref_content_settings_provider.h" + +#include "chrome/browser/content_settings/host_content_settings_map_unittest.h" +#include "chrome/browser/prefs/pref_service.h" +#include "chrome/common/pref_names.h" +#include "chrome/common/url_constants.h" +#include "chrome/test/testing_pref_service.h" +#include "chrome/test/testing_profile.h" +#include "testing/gtest/include/gtest/gtest.h" + + +namespace { + +class PrefContentSettingsProviderTest : public testing::Test { + public: + PrefContentSettingsProviderTest() + : ui_thread_(BrowserThread::UI, &message_loop_) { + } + + protected: + MessageLoop message_loop_; + BrowserThread ui_thread_; +}; + +TEST_F(PrefContentSettingsProviderTest, DefaultValues) { + TestingProfile profile; + PrefContentSettingsProvider provider(&profile); + + ASSERT_TRUE( + provider.CanProvideDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES)); + ASSERT_FALSE( + provider.DefaultSettingIsManaged(CONTENT_SETTINGS_TYPE_COOKIES)); + + // Check setting defaults. + EXPECT_EQ(CONTENT_SETTING_ALLOW, + provider.ProvideDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES)); + provider.UpdateDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES, + CONTENT_SETTING_BLOCK); + EXPECT_EQ(CONTENT_SETTING_BLOCK, + provider.ProvideDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES)); + provider.ResetToDefaults(); + EXPECT_EQ(CONTENT_SETTING_ALLOW, + provider.ProvideDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES)); +} + +TEST_F(PrefContentSettingsProviderTest, Observer) { + TestingProfile profile; + PrefContentSettingsProvider provider(&profile); + StubSettingsObserver observer; + + provider.UpdateDefaultSetting( + CONTENT_SETTINGS_TYPE_IMAGES, CONTENT_SETTING_BLOCK); + EXPECT_EQ(profile.GetHostContentSettingsMap(), observer.last_notifier); + EXPECT_TRUE(observer.last_update_all); + EXPECT_FALSE(observer.last_update_all_types); + EXPECT_EQ(1, observer.counter); +} + +TEST_F(PrefContentSettingsProviderTest, ObserveDefaultPref) { + TestingProfile profile; + PrefContentSettingsProvider provider(&profile); + + PrefService* prefs = profile.GetPrefs(); + + // Make a copy of the default pref value so we can reset it later. + scoped_ptr<Value> default_value(prefs->FindPreference( + prefs::kDefaultContentSettings)->GetValue()->DeepCopy()); + + provider.UpdateDefaultSetting( + CONTENT_SETTINGS_TYPE_COOKIES, CONTENT_SETTING_BLOCK); + EXPECT_EQ(CONTENT_SETTING_BLOCK, + provider.ProvideDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES)); + + // Make a copy of the pref's new value so we can reset it later. + scoped_ptr<Value> new_value(prefs->FindPreference( + prefs::kDefaultContentSettings)->GetValue()->DeepCopy()); + + // Clearing the backing pref should also clear the internal cache. + prefs->Set(prefs::kDefaultContentSettings, *default_value); + EXPECT_EQ(CONTENT_SETTING_ALLOW, + provider.ProvideDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES)); + + // Reseting the pref to its previous value should update the cache. + prefs->Set(prefs::kDefaultContentSettings, *new_value); + EXPECT_EQ(CONTENT_SETTING_BLOCK, + provider.ProvideDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES)); +} + +TEST_F(PrefContentSettingsProviderTest, OffTheRecord) { + TestingProfile profile; + PrefContentSettingsProvider provider(&profile); + + profile.set_off_the_record(true); + PrefContentSettingsProvider otr_provider(&profile); + profile.set_off_the_record(false); + + EXPECT_EQ(CONTENT_SETTING_ALLOW, + provider.ProvideDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES)); + EXPECT_EQ(CONTENT_SETTING_ALLOW, + otr_provider.ProvideDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES)); + + // Changing content settings on the main provider should also affect the + // off-the-record map. + provider.UpdateDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES, + CONTENT_SETTING_BLOCK); + EXPECT_EQ(CONTENT_SETTING_BLOCK, + provider.ProvideDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES)); + EXPECT_EQ(CONTENT_SETTING_BLOCK, + otr_provider.ProvideDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES)); + + // Changing content settings on the off-the-record provider should be ignored. + otr_provider.UpdateDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES, + CONTENT_SETTING_ALLOW); + EXPECT_EQ(CONTENT_SETTING_BLOCK, + provider.ProvideDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES)); + EXPECT_EQ(CONTENT_SETTING_BLOCK, + otr_provider.ProvideDefaultSetting(CONTENT_SETTINGS_TYPE_COOKIES)); +} + +} // namespace diff --git a/chrome/browser/cookies_tree_model_unittest.cc b/chrome/browser/cookies_tree_model_unittest.cc index 0ba3960..aa5159a 100644 --- a/chrome/browser/cookies_tree_model_unittest.cc +++ b/chrome/browser/cookies_tree_model_unittest.cc @@ -6,8 +6,7 @@ #include <string> -#include "chrome/browser/content_settings/content_settings_details.h" -#include "chrome/browser/content_settings/host_content_settings_map.h" +#include "chrome/browser/content_settings/host_content_settings_map_unittest.h" #include "chrome/browser/mock_browsing_data_appcache_helper.h" #include "chrome/browser/mock_browsing_data_database_helper.h" #include "chrome/browser/mock_browsing_data_indexed_db_helper.h" @@ -23,28 +22,6 @@ namespace { -class StubSettingsObserver : public NotificationObserver { - public: - StubSettingsObserver() : counter(0) { - registrar_.Add(this, NotificationType::CONTENT_SETTINGS_CHANGED, - NotificationService::AllSources()); - } - - virtual void Observe(NotificationType type, - const NotificationSource& source, - const NotificationDetails& details) { - ++counter; - Details<ContentSettingsDetails> settings_details(details); - last_pattern = settings_details.ptr()->pattern(); - } - - ContentSettingsPattern last_pattern; - int counter; - - private: - NotificationRegistrar registrar_; -}; - class CookiesTreeModelTest : public testing::Test { public: CookiesTreeModelTest() : ui_thread_(BrowserThread::UI, &message_loop_), diff --git a/chrome/browser/prefs/browser_prefs.cc b/chrome/browser/prefs/browser_prefs.cc index df68921..b947969 100644 --- a/chrome/browser/prefs/browser_prefs.cc +++ b/chrome/browser/prefs/browser_prefs.cc @@ -12,6 +12,8 @@ #include "chrome/browser/bookmarks/bookmark_utils.h" #include "chrome/browser/browser_shutdown.h" #include "chrome/browser/content_settings/host_content_settings_map.h" +#include "chrome/browser/content_settings/policy_content_settings_provider.h" +#include "chrome/browser/content_settings/pref_content_settings_provider.h" #include "chrome/browser/debugger/devtools_manager.h" #include "chrome/browser/dom_ui/flags_ui.h" #include "chrome/browser/dom_ui/new_tab_ui.h" @@ -127,6 +129,8 @@ void RegisterUserPrefs(PrefService* user_prefs) { PluginsUI::RegisterUserPrefs(user_prefs); ProfileImpl::RegisterUserPrefs(user_prefs); HostContentSettingsMap::RegisterUserPrefs(user_prefs); + PolicyContentSettingsProvider::RegisterUserPrefs(user_prefs); + PrefContentSettingsProvider::RegisterUserPrefs(user_prefs); HostZoomMap::RegisterUserPrefs(user_prefs); DevToolsManager::RegisterUserPrefs(user_prefs); PinnedTabCodec::RegisterUserPrefs(user_prefs); diff --git a/chrome/chrome_browser.gypi b/chrome/chrome_browser.gypi index 6698c06..0469357 100644 --- a/chrome/chrome_browser.gypi +++ b/chrome/chrome_browser.gypi @@ -800,6 +800,10 @@ 'browser/content_settings/content_settings_provider.h', 'browser/content_settings/host_content_settings_map.cc', 'browser/content_settings/host_content_settings_map.h', + 'browser/content_settings/policy_content_settings_provider.cc', + 'browser/content_settings/policy_content_settings_provider.h', + 'browser/content_settings/pref_content_settings_provider.cc', + 'browser/content_settings/pref_content_settings_provider.h', 'browser/cookies_tree_model.cc', 'browser/cookies_tree_model.h', 'browser/cross_site_request_manager.cc', diff --git a/chrome/chrome_tests.gypi b/chrome/chrome_tests.gypi index 31ce387..88ca592 100644 --- a/chrome/chrome_tests.gypi +++ b/chrome/chrome_tests.gypi @@ -1115,6 +1115,9 @@ 'browser/content_settings/content_settings_pattern_unittest.cc', 'browser/content_settings/content_settings_provider_unittest.cc', 'browser/content_settings/host_content_settings_map_unittest.cc', + 'browser/content_settings/host_content_settings_map_unittest.h', + 'browser/content_settings/policy_content_settings_provider_unittest.cc', + 'browser/content_settings/pref_content_settings_provider_unittest.cc', 'browser/content_settings/mock_content_settings_provider.cc', 'browser/content_settings/mock_content_settings_provider.h', 'browser/cookies_tree_model_unittest.cc', |