1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #include "chrome/browser/plugins/plugin_prefs.h" 6 7 #include "base/at_exit.h" 8 #include "base/bind.h" 9 #include "base/path_service.h" 10 #include "base/run_loop.h" 11 #include "base/strings/utf_string_conversions.h" 12 #include "chrome/common/chrome_constants.h" 13 #include "chrome/common/chrome_paths.h" 14 #include "content/public/browser/plugin_service.h" 15 #include "content/public/browser/render_process_host.h" 16 #include "content/public/common/webplugininfo.h" 17 #include "content/public/test/test_browser_thread_bundle.h" 18 #include "content/public/test/test_utils.h" 19 #include "testing/gtest/include/gtest/gtest.h" 20 21 using base::ASCIIToUTF16; 22 using content::BrowserThread; 23 using content::PluginService; 24 25 namespace { 26 27 void CanEnablePluginCallback(const base::Closure& quit_closure, 28 bool expected_can_change, 29 bool did_change) { 30 EXPECT_EQ(expected_can_change, did_change); 31 quit_closure.Run(); 32 } 33 34 #if !(defined(OS_LINUX) && defined(USE_AURA)) 35 base::FilePath GetComponentUpdatedPepperFlashPath( 36 const base::FilePath::StringType& version) { 37 base::FilePath path; 38 EXPECT_TRUE(PathService::Get( 39 chrome::DIR_COMPONENT_UPDATED_PEPPER_FLASH_PLUGIN, &path)); 40 path = path.Append(version); 41 path = path.Append(chrome::kPepperFlashPluginFilename); 42 return path; 43 } 44 45 base::FilePath GetBundledPepperFlashPath() { 46 base::FilePath path; 47 EXPECT_TRUE(PathService::Get(chrome::FILE_PEPPER_FLASH_PLUGIN, &path)); 48 return path; 49 } 50 #endif // !(defined(OS_LINUX) && defined(USE_AURA)) 51 52 void GotPlugins(const base::Closure& quit_closure, 53 const std::vector<content::WebPluginInfo>& plugins) { 54 quit_closure.Run(); 55 } 56 57 } // namespace 58 59 class PluginPrefsTest : public ::testing::Test { 60 public: 61 virtual void SetUp() OVERRIDE { 62 plugin_prefs_ = new PluginPrefs(); 63 } 64 65 void SetPolicyEnforcedPluginPatterns( 66 const std::set<base::string16>& disabled, 67 const std::set<base::string16>& disabled_exceptions, 68 const std::set<base::string16>& enabled) { 69 plugin_prefs_->SetPolicyEnforcedPluginPatterns( 70 disabled, disabled_exceptions, enabled); 71 } 72 73 protected: 74 void EnablePluginSynchronously(bool enabled, 75 const base::FilePath& path, 76 bool expected_can_change) { 77 base::RunLoop run_loop; 78 plugin_prefs_->EnablePlugin( 79 enabled, path, 80 base::Bind(&CanEnablePluginCallback, run_loop.QuitClosure(), 81 expected_can_change)); 82 run_loop.Run(); 83 } 84 85 void RefreshPluginsSynchronously() { 86 PluginService::GetInstance()->RefreshPlugins(); 87 #if !defined(OS_WIN) 88 // Can't go out of process in unit tests. 89 content::RenderProcessHost::SetRunRendererInProcess(true); 90 #endif 91 scoped_refptr<content::MessageLoopRunner> runner = 92 new content::MessageLoopRunner; 93 PluginService::GetInstance()->GetPlugins( 94 base::Bind(&GotPlugins, runner->QuitClosure())); 95 runner->Run(); 96 #if !defined(OS_WIN) 97 content::RenderProcessHost::SetRunRendererInProcess(false); 98 #endif 99 } 100 101 scoped_refptr<PluginPrefs> plugin_prefs_; 102 }; 103 104 TEST_F(PluginPrefsTest, DisabledByPolicy) { 105 std::set<base::string16> disabled_plugins; 106 disabled_plugins.insert(ASCIIToUTF16("Disable this!")); 107 disabled_plugins.insert(ASCIIToUTF16("*Google*")); 108 SetPolicyEnforcedPluginPatterns(disabled_plugins, 109 std::set<base::string16>(), 110 std::set<base::string16>()); 111 112 EXPECT_EQ(PluginPrefs::NO_POLICY, 113 plugin_prefs_->PolicyStatusForPlugin(ASCIIToUTF16("42"))); 114 EXPECT_EQ(PluginPrefs::POLICY_DISABLED, 115 plugin_prefs_->PolicyStatusForPlugin( 116 ASCIIToUTF16("Disable this!"))); 117 EXPECT_EQ(PluginPrefs::POLICY_DISABLED, 118 plugin_prefs_->PolicyStatusForPlugin(ASCIIToUTF16("Google Earth"))); 119 } 120 121 TEST_F(PluginPrefsTest, EnabledByPolicy) { 122 std::set<base::string16> enabled_plugins; 123 enabled_plugins.insert(ASCIIToUTF16("Enable that!")); 124 enabled_plugins.insert(ASCIIToUTF16("PDF*")); 125 SetPolicyEnforcedPluginPatterns(std::set<base::string16>(), 126 std::set<base::string16>(), 127 enabled_plugins); 128 129 EXPECT_EQ(PluginPrefs::NO_POLICY, 130 plugin_prefs_->PolicyStatusForPlugin(ASCIIToUTF16("42"))); 131 EXPECT_EQ(PluginPrefs::POLICY_ENABLED, 132 plugin_prefs_->PolicyStatusForPlugin(ASCIIToUTF16("Enable that!"))); 133 EXPECT_EQ(PluginPrefs::POLICY_ENABLED, 134 plugin_prefs_->PolicyStatusForPlugin(ASCIIToUTF16("PDF Reader"))); 135 } 136 137 TEST_F(PluginPrefsTest, EnabledAndDisabledByPolicy) { 138 const base::string16 k42(ASCIIToUTF16("42")); 139 const base::string16 kEnabled(ASCIIToUTF16("Enabled")); 140 const base::string16 kEnabled2(ASCIIToUTF16("Enabled 2")); 141 const base::string16 kEnabled3(ASCIIToUTF16("Enabled 3")); 142 const base::string16 kException(ASCIIToUTF16("Exception")); 143 const base::string16 kException2(ASCIIToUTF16("Exception 2")); 144 const base::string16 kGoogleMars(ASCIIToUTF16("Google Mars")); 145 const base::string16 kGoogleEarth(ASCIIToUTF16("Google Earth")); 146 147 std::set<base::string16> disabled_plugins; 148 std::set<base::string16> disabled_plugins_exceptions; 149 std::set<base::string16> enabled_plugins; 150 151 disabled_plugins.insert(kEnabled); 152 disabled_plugins_exceptions.insert(kEnabled); 153 enabled_plugins.insert(kEnabled); 154 155 disabled_plugins_exceptions.insert(kException); 156 157 disabled_plugins.insert(kEnabled2); 158 enabled_plugins.insert(kEnabled2); 159 160 disabled_plugins.insert(kException2); 161 disabled_plugins_exceptions.insert(kException2); 162 163 disabled_plugins_exceptions.insert(kEnabled3); 164 enabled_plugins.insert(kEnabled3); 165 166 SetPolicyEnforcedPluginPatterns(disabled_plugins, 167 disabled_plugins_exceptions, 168 enabled_plugins); 169 170 EXPECT_EQ(PluginPrefs::NO_POLICY, plugin_prefs_->PolicyStatusForPlugin(k42)); 171 172 EXPECT_EQ(PluginPrefs::POLICY_ENABLED, 173 plugin_prefs_->PolicyStatusForPlugin(kEnabled)); 174 EXPECT_EQ(PluginPrefs::POLICY_ENABLED, 175 plugin_prefs_->PolicyStatusForPlugin(kEnabled2)); 176 EXPECT_EQ(PluginPrefs::POLICY_ENABLED, 177 plugin_prefs_->PolicyStatusForPlugin(kEnabled3)); 178 179 EXPECT_EQ(PluginPrefs::NO_POLICY, 180 plugin_prefs_->PolicyStatusForPlugin(kException)); 181 EXPECT_EQ(PluginPrefs::NO_POLICY, 182 plugin_prefs_->PolicyStatusForPlugin(kException2)); 183 184 disabled_plugins.clear(); 185 disabled_plugins_exceptions.clear(); 186 enabled_plugins.clear(); 187 188 disabled_plugins.insert(ASCIIToUTF16("*")); 189 disabled_plugins_exceptions.insert(ASCIIToUTF16("*Google*")); 190 enabled_plugins.insert(kGoogleEarth); 191 192 SetPolicyEnforcedPluginPatterns(disabled_plugins, 193 disabled_plugins_exceptions, 194 enabled_plugins); 195 196 EXPECT_EQ(PluginPrefs::POLICY_ENABLED, 197 plugin_prefs_->PolicyStatusForPlugin(kGoogleEarth)); 198 EXPECT_EQ(PluginPrefs::NO_POLICY, 199 plugin_prefs_->PolicyStatusForPlugin(kGoogleMars)); 200 EXPECT_EQ(PluginPrefs::POLICY_DISABLED, 201 plugin_prefs_->PolicyStatusForPlugin(k42)); 202 } 203 204 // Linux Aura doesn't support NPAPI. 205 #if !(defined(OS_LINUX) && defined(USE_AURA)) 206 207 TEST_F(PluginPrefsTest, UnifiedPepperFlashState) { 208 content::TestBrowserThreadBundle browser_threads; 209 base::ShadowingAtExitManager at_exit_manager_; // Destroys the PluginService. 210 211 PluginService::GetInstance()->Init(); 212 PluginService::GetInstance()->DisablePluginsDiscoveryForTesting(); 213 214 base::string16 component_updated_plugin_name( 215 ASCIIToUTF16("Component-updated Pepper Flash")); 216 content::WebPluginInfo component_updated_plugin_1( 217 component_updated_plugin_name, 218 GetComponentUpdatedPepperFlashPath(FILE_PATH_LITERAL("11.3.31.227")), 219 ASCIIToUTF16("11.3.31.227"), 220 ASCIIToUTF16("")); 221 content::WebPluginInfo component_updated_plugin_2( 222 component_updated_plugin_name, 223 GetComponentUpdatedPepperFlashPath(FILE_PATH_LITERAL("11.3.31.228")), 224 ASCIIToUTF16("11.3.31.228"), 225 ASCIIToUTF16("")); 226 content::WebPluginInfo bundled_plugin(ASCIIToUTF16("Pepper Flash"), 227 GetBundledPepperFlashPath(), 228 ASCIIToUTF16("11.3.31.229"), 229 ASCIIToUTF16("")); 230 231 PluginService::GetInstance()->RegisterInternalPlugin( 232 component_updated_plugin_1, false); 233 PluginService::GetInstance()->RegisterInternalPlugin( 234 component_updated_plugin_2, false); 235 PluginService::GetInstance()->RegisterInternalPlugin(bundled_plugin, false); 236 237 RefreshPluginsSynchronously(); 238 239 // Set the state of any of the three plugins will affect the others. 240 EnablePluginSynchronously(true, component_updated_plugin_1.path, true); 241 EXPECT_TRUE(plugin_prefs_->IsPluginEnabled(component_updated_plugin_1)); 242 EXPECT_TRUE(plugin_prefs_->IsPluginEnabled(component_updated_plugin_2)); 243 EXPECT_TRUE(plugin_prefs_->IsPluginEnabled(bundled_plugin)); 244 245 EnablePluginSynchronously(false, bundled_plugin.path, true); 246 EXPECT_FALSE(plugin_prefs_->IsPluginEnabled(component_updated_plugin_1)); 247 EXPECT_FALSE(plugin_prefs_->IsPluginEnabled(component_updated_plugin_2)); 248 EXPECT_FALSE(plugin_prefs_->IsPluginEnabled(bundled_plugin)); 249 250 EnablePluginSynchronously(true, component_updated_plugin_2.path, true); 251 EXPECT_TRUE(plugin_prefs_->IsPluginEnabled(component_updated_plugin_1)); 252 EXPECT_TRUE(plugin_prefs_->IsPluginEnabled(component_updated_plugin_2)); 253 EXPECT_TRUE(plugin_prefs_->IsPluginEnabled(bundled_plugin)); 254 255 std::set<base::string16> disabled_plugins; 256 disabled_plugins.insert(component_updated_plugin_name); 257 SetPolicyEnforcedPluginPatterns(disabled_plugins, 258 std::set<base::string16>(), 259 std::set<base::string16>()); 260 261 // Policy settings should be respected. 262 EXPECT_FALSE(plugin_prefs_->IsPluginEnabled(component_updated_plugin_1)); 263 EXPECT_FALSE(plugin_prefs_->IsPluginEnabled(component_updated_plugin_2)); 264 EXPECT_TRUE(plugin_prefs_->IsPluginEnabled(bundled_plugin)); 265 266 EnablePluginSynchronously(false, bundled_plugin.path, true); 267 EXPECT_FALSE(plugin_prefs_->IsPluginEnabled(bundled_plugin)); 268 269 // Trying to change the state of a policy-enforced plugin should not take 270 // effect. And it shouldn't change the state of other plugins either, even if 271 // they are not restricted by any policy. 272 EnablePluginSynchronously(true, component_updated_plugin_1.path, false); 273 EXPECT_FALSE(plugin_prefs_->IsPluginEnabled(component_updated_plugin_1)); 274 EXPECT_FALSE(plugin_prefs_->IsPluginEnabled(component_updated_plugin_2)); 275 EXPECT_FALSE(plugin_prefs_->IsPluginEnabled(bundled_plugin)); 276 277 EnablePluginSynchronously(true, bundled_plugin.path, true); 278 EXPECT_FALSE(plugin_prefs_->IsPluginEnabled(component_updated_plugin_1)); 279 EXPECT_FALSE(plugin_prefs_->IsPluginEnabled(component_updated_plugin_2)); 280 EXPECT_TRUE(plugin_prefs_->IsPluginEnabled(bundled_plugin)); 281 } 282 283 #endif 284