Upstream version 9.37.195.0
[platform/framework/web/crosswalk.git] / src / extensions / common / permissions / permissions_data_unittest.cc
1 // Copyright (c) 2013 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 <vector>
6
7 #include "base/command_line.h"
8 #include "base/memory/ref_counted.h"
9 #include "base/strings/string16.h"
10 #include "base/strings/utf_string_conversions.h"
11 #include "chrome/common/chrome_version_info.h"
12 #include "chrome/common/extensions/extension_test_util.h"
13 #include "chrome/common/extensions/features/feature_channel.h"
14 #include "content/public/common/socket_permission_request.h"
15 #include "extensions/common/error_utils.h"
16 #include "extensions/common/extension.h"
17 #include "extensions/common/extension_builder.h"
18 #include "extensions/common/id_util.h"
19 #include "extensions/common/manifest.h"
20 #include "extensions/common/manifest_constants.h"
21 #include "extensions/common/permissions/api_permission.h"
22 #include "extensions/common/permissions/permission_set.h"
23 #include "extensions/common/permissions/permissions_data.h"
24 #include "extensions/common/permissions/socket_permission.h"
25 #include "extensions/common/switches.h"
26 #include "extensions/common/url_pattern_set.h"
27 #include "extensions/common/value_builder.h"
28 #include "testing/gtest/include/gtest/gtest.h"
29 #include "url/gurl.h"
30
31 using base::UTF16ToUTF8;
32 using content::SocketPermissionRequest;
33 using extension_test_util::LoadManifest;
34 using extension_test_util::LoadManifestUnchecked;
35 using extension_test_util::LoadManifestStrict;
36
37 namespace extensions {
38
39 namespace {
40
41 const char kAllHostsPermission[] = "*://*/*";
42
43 bool CheckSocketPermission(
44     scoped_refptr<Extension> extension,
45     SocketPermissionRequest::OperationType type,
46     const char* host,
47     int port) {
48   SocketPermission::CheckParam param(type, host, port);
49   return extension->permissions_data()->CheckAPIPermissionWithParam(
50       APIPermission::kSocket, &param);
51 }
52
53 // Creates and returns an extension with the given |id|, |host_permissions|, and
54 // manifest |location|.
55 scoped_refptr<const Extension> GetExtensionWithHostPermission(
56     const std::string& id,
57     const std::string& host_permissions,
58     Manifest::Location location) {
59   ListBuilder permissions;
60   if (!host_permissions.empty())
61     permissions.Append(host_permissions);
62
63   return ExtensionBuilder()
64       .SetManifest(
65           DictionaryBuilder()
66               .Set("name", id)
67               .Set("description", "an extension")
68               .Set("manifest_version", 2)
69               .Set("version", "1.0.0")
70               .Set("permissions", permissions.Pass())
71               .Build())
72       .SetLocation(location)
73       .SetID(id)
74       .Build();
75 }
76
77 bool RequiresActionForScriptExecution(const std::string& extension_id,
78                                       const std::string& host_permissions,
79                                       Manifest::Location location) {
80   scoped_refptr<const Extension> extension =
81       GetExtensionWithHostPermission(extension_id,
82                                      host_permissions,
83                                      location);
84   return extension->permissions_data()->RequiresActionForScriptExecution(
85       extension,
86       -1,  // Ignore tab id for these.
87       GURL::EmptyGURL());
88 }
89
90 // Checks that urls are properly restricted for the given extension.
91 void CheckRestrictedUrls(const Extension* extension,
92                          bool block_chrome_urls) {
93   // We log the name so we know _which_ extension failed here.
94   const std::string& name = extension->name();
95   const GURL chrome_settings_url("chrome://settings/");
96   const GURL chrome_extension_url("chrome-extension://foo/bar.html");
97   const GURL google_url("https://www.google.com/");
98   const GURL self_url("chrome-extension://" + extension->id() + "/foo.html");
99   const GURL invalid_url("chrome-debugger://foo/bar.html");
100
101   std::string error;
102   EXPECT_EQ(block_chrome_urls,
103             PermissionsData::IsRestrictedUrl(
104                 chrome_settings_url,
105                 chrome_settings_url,
106                 extension,
107                 &error)) << name;
108   if (block_chrome_urls)
109     EXPECT_EQ(manifest_errors::kCannotAccessChromeUrl, error) << name;
110   else
111     EXPECT_TRUE(error.empty()) << name;
112
113   error.clear();
114   EXPECT_EQ(block_chrome_urls,
115             PermissionsData::IsRestrictedUrl(
116                 chrome_extension_url,
117                 chrome_extension_url,
118                 extension,
119                 &error)) << name;
120   if (block_chrome_urls)
121     EXPECT_EQ(manifest_errors::kCannotAccessExtensionUrl, error) << name;
122   else
123     EXPECT_TRUE(error.empty()) << name;
124
125   // Google should never be a restricted url.
126   error.clear();
127   EXPECT_FALSE(PermissionsData::IsRestrictedUrl(
128       google_url, google_url, extension, &error)) << name;
129   EXPECT_TRUE(error.empty()) << name;
130
131   // We should always be able to access our own extension pages.
132   error.clear();
133   EXPECT_FALSE(PermissionsData::IsRestrictedUrl(
134       self_url, self_url, extension, &error)) << name;
135   EXPECT_TRUE(error.empty()) << name;
136
137   // We should only allow other schemes for extensions when it's a whitelisted
138   // extension.
139   error.clear();
140   bool allow_on_other_schemes =
141       PermissionsData::CanExecuteScriptEverywhere(extension);
142   EXPECT_EQ(!allow_on_other_schemes,
143             PermissionsData::IsRestrictedUrl(
144                 invalid_url, invalid_url, extension, &error)) << name;
145   if (!allow_on_other_schemes) {
146     EXPECT_EQ(ErrorUtils::FormatErrorMessage(
147                   manifest_errors::kCannotAccessPage,
148                   invalid_url.spec()),
149               error) << name;
150   } else {
151     EXPECT_TRUE(error.empty());
152   }
153 }
154
155 }  // namespace
156
157 TEST(ExtensionPermissionsTest, EffectiveHostPermissions) {
158   scoped_refptr<Extension> extension;
159   URLPatternSet hosts;
160
161   extension = LoadManifest("effective_host_permissions", "empty.json");
162   EXPECT_EQ(0u,
163             extension->permissions_data()
164                 ->GetEffectiveHostPermissions()
165                 .patterns()
166                 .size());
167   EXPECT_FALSE(hosts.MatchesURL(GURL("http://www.google.com")));
168   EXPECT_FALSE(extension->permissions_data()->HasEffectiveAccessToAllHosts());
169
170   extension = LoadManifest("effective_host_permissions", "one_host.json");
171   hosts = extension->permissions_data()->GetEffectiveHostPermissions();
172   EXPECT_TRUE(hosts.MatchesURL(GURL("http://www.google.com")));
173   EXPECT_FALSE(hosts.MatchesURL(GURL("https://www.google.com")));
174   EXPECT_FALSE(extension->permissions_data()->HasEffectiveAccessToAllHosts());
175
176   extension = LoadManifest("effective_host_permissions",
177                            "one_host_wildcard.json");
178   hosts = extension->permissions_data()->GetEffectiveHostPermissions();
179   EXPECT_TRUE(hosts.MatchesURL(GURL("http://google.com")));
180   EXPECT_TRUE(hosts.MatchesURL(GURL("http://foo.google.com")));
181   EXPECT_FALSE(extension->permissions_data()->HasEffectiveAccessToAllHosts());
182
183   extension = LoadManifest("effective_host_permissions", "two_hosts.json");
184   hosts = extension->permissions_data()->GetEffectiveHostPermissions();
185   EXPECT_TRUE(hosts.MatchesURL(GURL("http://www.google.com")));
186   EXPECT_TRUE(hosts.MatchesURL(GURL("http://www.reddit.com")));
187   EXPECT_FALSE(extension->permissions_data()->HasEffectiveAccessToAllHosts());
188
189   extension = LoadManifest("effective_host_permissions",
190                            "https_not_considered.json");
191   hosts = extension->permissions_data()->GetEffectiveHostPermissions();
192   EXPECT_TRUE(hosts.MatchesURL(GURL("http://google.com")));
193   EXPECT_TRUE(hosts.MatchesURL(GURL("https://google.com")));
194   EXPECT_FALSE(extension->permissions_data()->HasEffectiveAccessToAllHosts());
195
196   extension = LoadManifest("effective_host_permissions",
197                            "two_content_scripts.json");
198   hosts = extension->permissions_data()->GetEffectiveHostPermissions();
199   EXPECT_TRUE(hosts.MatchesURL(GURL("http://google.com")));
200   EXPECT_TRUE(hosts.MatchesURL(GURL("http://www.reddit.com")));
201   EXPECT_TRUE(extension->permissions_data()
202                   ->active_permissions()
203                   ->HasEffectiveAccessToURL(GURL("http://www.reddit.com")));
204   EXPECT_TRUE(hosts.MatchesURL(GURL("http://news.ycombinator.com")));
205   EXPECT_TRUE(
206       extension->permissions_data()
207           ->active_permissions()
208           ->HasEffectiveAccessToURL(GURL("http://news.ycombinator.com")));
209   EXPECT_FALSE(extension->permissions_data()->HasEffectiveAccessToAllHosts());
210
211   extension = LoadManifest("effective_host_permissions", "all_hosts.json");
212   hosts = extension->permissions_data()->GetEffectiveHostPermissions();
213   EXPECT_TRUE(hosts.MatchesURL(GURL("http://test/")));
214   EXPECT_FALSE(hosts.MatchesURL(GURL("https://test/")));
215   EXPECT_TRUE(hosts.MatchesURL(GURL("http://www.google.com")));
216   EXPECT_TRUE(extension->permissions_data()->HasEffectiveAccessToAllHosts());
217
218   extension = LoadManifest("effective_host_permissions", "all_hosts2.json");
219   hosts = extension->permissions_data()->GetEffectiveHostPermissions();
220   EXPECT_TRUE(hosts.MatchesURL(GURL("http://test/")));
221   EXPECT_TRUE(hosts.MatchesURL(GURL("http://www.google.com")));
222   EXPECT_TRUE(extension->permissions_data()->HasEffectiveAccessToAllHosts());
223
224   extension = LoadManifest("effective_host_permissions", "all_hosts3.json");
225   hosts = extension->permissions_data()->GetEffectiveHostPermissions();
226   EXPECT_FALSE(hosts.MatchesURL(GURL("http://test/")));
227   EXPECT_TRUE(hosts.MatchesURL(GURL("https://test/")));
228   EXPECT_TRUE(hosts.MatchesURL(GURL("http://www.google.com")));
229   EXPECT_TRUE(extension->permissions_data()->HasEffectiveAccessToAllHosts());
230 }
231
232 TEST(ExtensionPermissionsTest, SocketPermissions) {
233   // Set feature current channel to appropriate value.
234   ScopedCurrentChannel scoped_channel(chrome::VersionInfo::CHANNEL_DEV);
235   scoped_refptr<Extension> extension;
236   std::string error;
237
238   extension = LoadManifest("socket_permissions", "empty.json");
239   EXPECT_FALSE(CheckSocketPermission(extension,
240       SocketPermissionRequest::TCP_CONNECT, "www.example.com", 80));
241
242   extension = LoadManifestUnchecked("socket_permissions",
243                                     "socket1.json",
244                                     Manifest::INTERNAL, Extension::NO_FLAGS,
245                                     &error);
246   EXPECT_TRUE(extension.get() == NULL);
247   std::string expected_error_msg_header = ErrorUtils::FormatErrorMessage(
248       manifest_errors::kInvalidPermissionWithDetail,
249       "socket",
250       "NULL or empty permission list");
251   EXPECT_EQ(expected_error_msg_header, error);
252
253   extension = LoadManifest("socket_permissions", "socket2.json");
254   EXPECT_TRUE(CheckSocketPermission(extension,
255       SocketPermissionRequest::TCP_CONNECT, "www.example.com", 80));
256   EXPECT_FALSE(CheckSocketPermission(
257         extension, SocketPermissionRequest::UDP_BIND, "", 80));
258   EXPECT_TRUE(CheckSocketPermission(
259         extension, SocketPermissionRequest::UDP_BIND, "", 8888));
260
261   EXPECT_FALSE(CheckSocketPermission(
262         extension, SocketPermissionRequest::UDP_SEND_TO, "example.com", 1900));
263   EXPECT_TRUE(CheckSocketPermission(
264         extension,
265         SocketPermissionRequest::UDP_SEND_TO,
266         "239.255.255.250", 1900));
267 }
268
269 TEST(ExtensionPermissionsTest, RequiresActionForScriptExecution) {
270   // Extensions with all_hosts should require action.
271   EXPECT_TRUE(RequiresActionForScriptExecution(
272       "all_hosts_permissions", kAllHostsPermission, Manifest::INTERNAL));
273   // Extensions with nearly all hosts are treated the same way.
274   EXPECT_TRUE(RequiresActionForScriptExecution(
275       "pseudo_all_hosts_permissions", "*://*.com/*", Manifest::INTERNAL));
276   // Extensions with explicit permissions shouldn't require action.
277   EXPECT_FALSE(RequiresActionForScriptExecution(
278       "explicit_permissions", "https://www.google.com/*", Manifest::INTERNAL));
279   // Policy extensions are exempt...
280   EXPECT_FALSE(RequiresActionForScriptExecution(
281       "policy", kAllHostsPermission, Manifest::EXTERNAL_POLICY));
282   // ... as are component extensions.
283   EXPECT_FALSE(RequiresActionForScriptExecution(
284       "component", kAllHostsPermission, Manifest::COMPONENT));
285   // Throw in an external pref extension to make sure that it's not just working
286   // for everything non-internal.
287   EXPECT_TRUE(RequiresActionForScriptExecution(
288       "external_pref", kAllHostsPermission, Manifest::EXTERNAL_PREF));
289
290   // If we grant an extension tab permissions, then it should no longer require
291   // action.
292   scoped_refptr<const Extension> extension =
293       GetExtensionWithHostPermission("all_hosts_permissions",
294                                      kAllHostsPermission,
295                                      Manifest::INTERNAL);
296   URLPatternSet allowed_hosts;
297   allowed_hosts.AddPattern(
298       URLPattern(URLPattern::SCHEME_HTTPS, "https://www.google.com/*"));
299   scoped_refptr<PermissionSet> tab_permissions(
300       new PermissionSet(APIPermissionSet(),
301                         ManifestPermissionSet(),
302                         allowed_hosts,
303                         URLPatternSet()));
304   extension->permissions_data()->UpdateTabSpecificPermissions(0,
305                                                               tab_permissions);
306   EXPECT_FALSE(extension->permissions_data()->RequiresActionForScriptExecution(
307       extension, 0, GURL("https://www.google.com/")));
308 }
309
310 TEST(ExtensionPermissionsTest, IsRestrictedUrl) {
311   scoped_refptr<const Extension> extension =
312       GetExtensionWithHostPermission("normal_extension",
313                                      kAllHostsPermission,
314                                      Manifest::INTERNAL);
315   // Chrome urls should be blocked for normal extensions.
316   CheckRestrictedUrls(extension, true);
317
318   scoped_refptr<const Extension> component =
319       GetExtensionWithHostPermission("component",
320                                      kAllHostsPermission,
321                                      Manifest::COMPONENT);
322   // Chrome urls should be accessible by component extensions.
323   CheckRestrictedUrls(component, false);
324
325   base::CommandLine::ForCurrentProcess()->AppendSwitch(
326       switches::kExtensionsOnChromeURLs);
327   // Enabling the switch should allow all extensions to access chrome urls.
328   CheckRestrictedUrls(extension, false);
329
330 }
331
332 TEST(ExtensionPermissionsTest, GetPermissionMessages_ManyAPIPermissions) {
333   scoped_refptr<Extension> extension;
334   extension = LoadManifest("permissions", "many-apis.json");
335   std::vector<base::string16> warnings =
336       extension->permissions_data()->GetPermissionMessageStrings();
337   // Warning for "tabs" is suppressed by "history" permission.
338   ASSERT_EQ(5u, warnings.size());
339   EXPECT_EQ("Read and modify your data on api.flickr.com",
340             UTF16ToUTF8(warnings[0]));
341   EXPECT_EQ("Read and modify your bookmarks", UTF16ToUTF8(warnings[1]));
342   EXPECT_EQ("Detect your physical location", UTF16ToUTF8(warnings[2]));
343   EXPECT_EQ("Read and modify your browsing history", UTF16ToUTF8(warnings[3]));
344   EXPECT_EQ("Manage your apps, extensions, and themes",
345             UTF16ToUTF8(warnings[4]));
346 }
347
348 TEST(ExtensionPermissionsTest, GetPermissionMessages_ManyHostsPermissions) {
349   scoped_refptr<Extension> extension;
350   extension = LoadManifest("permissions", "more-than-3-hosts.json");
351   std::vector<base::string16> warnings =
352       extension->permissions_data()->GetPermissionMessageStrings();
353   std::vector<base::string16> warnings_details =
354       extension->permissions_data()->GetPermissionMessageDetailsStrings();
355   ASSERT_EQ(1u, warnings.size());
356   ASSERT_EQ(1u, warnings_details.size());
357   EXPECT_EQ("Read and modify your data on 5 websites",
358             UTF16ToUTF8(warnings[0]));
359   EXPECT_EQ("- www.a.com\n- www.b.com\n- www.c.com\n- www.d.com\n- www.e.com",
360             UTF16ToUTF8(warnings_details[0]));
361 }
362
363 TEST(ExtensionPermissionsTest, GetPermissionMessages_LocationApiPermission) {
364   scoped_refptr<Extension> extension;
365   extension = LoadManifest("permissions",
366                            "location-api.json",
367                            Manifest::COMPONENT,
368                            Extension::NO_FLAGS);
369   std::vector<base::string16> warnings =
370       extension->permissions_data()->GetPermissionMessageStrings();
371   ASSERT_EQ(1u, warnings.size());
372   EXPECT_EQ("Detect your physical location", UTF16ToUTF8(warnings[0]));
373 }
374
375 TEST(ExtensionPermissionsTest, GetPermissionMessages_ManyHosts) {
376   scoped_refptr<Extension> extension;
377   extension = LoadManifest("permissions", "many-hosts.json");
378   std::vector<base::string16> warnings =
379       extension->permissions_data()->GetPermissionMessageStrings();
380   ASSERT_EQ(1u, warnings.size());
381   EXPECT_EQ(
382       "Read and modify your data on encrypted.google.com and www.google.com",
383       UTF16ToUTF8(warnings[0]));
384 }
385
386 TEST(ExtensionPermissionsTest, GetPermissionMessages_Plugins) {
387   scoped_refptr<Extension> extension;
388   extension = LoadManifest("permissions", "plugins.json");
389   std::vector<base::string16> warnings =
390       extension->permissions_data()->GetPermissionMessageStrings();
391 // We don't parse the plugins key on Chrome OS, so it should not ask for any
392 // permissions.
393 #if defined(OS_CHROMEOS)
394   ASSERT_EQ(0u, warnings.size());
395 #else
396   ASSERT_EQ(1u, warnings.size());
397   EXPECT_EQ(
398       "Read and modify all your data on your computer and the websites you "
399       "visit",
400       UTF16ToUTF8(warnings[0]));
401 #endif
402 }
403
404 // Base class for testing the CanAccessPage and CanCaptureVisiblePage
405 // methods of Extension for extensions with various permissions.
406 class ExtensionScriptAndCaptureVisibleTest : public testing::Test {
407  protected:
408   ExtensionScriptAndCaptureVisibleTest()
409       : http_url("http://www.google.com"),
410         http_url_with_path("http://www.google.com/index.html"),
411         https_url("https://www.google.com"),
412         file_url("file:///foo/bar"),
413         favicon_url("chrome://favicon/http://www.google.com"),
414         extension_url("chrome-extension://" +
415             id_util::GenerateIdForPath(
416                 base::FilePath(FILE_PATH_LITERAL("foo")))),
417         settings_url("chrome://settings"),
418         about_url("about:flags") {
419     urls_.insert(http_url);
420     urls_.insert(http_url_with_path);
421     urls_.insert(https_url);
422     urls_.insert(file_url);
423     urls_.insert(favicon_url);
424     urls_.insert(extension_url);
425     urls_.insert(settings_url);
426     urls_.insert(about_url);
427     // Ignore the policy delegate for this test.
428     PermissionsData::SetPolicyDelegate(NULL);
429   }
430
431   bool AllowedScript(const Extension* extension, const GURL& url,
432                      const GURL& top_url) {
433     return AllowedScript(extension, url, top_url, -1);
434   }
435
436   bool AllowedScript(const Extension* extension, const GURL& url,
437                      const GURL& top_url, int tab_id) {
438     return extension->permissions_data()->CanAccessPage(
439         extension, url, top_url, tab_id, -1, NULL);
440   }
441
442   bool BlockedScript(const Extension* extension, const GURL& url,
443                      const GURL& top_url) {
444     return !extension->permissions_data()->CanAccessPage(
445         extension, url, top_url, -1, -1, NULL);
446   }
447
448   bool Allowed(const Extension* extension, const GURL& url) {
449     return Allowed(extension, url, -1);
450   }
451
452   bool Allowed(const Extension* extension, const GURL& url, int tab_id) {
453     return (extension->permissions_data()->CanAccessPage(
454                 extension, url, url, tab_id, -1, NULL) &&
455             extension->permissions_data()->CanCaptureVisiblePage(tab_id, NULL));
456   }
457
458   bool CaptureOnly(const Extension* extension, const GURL& url) {
459     return CaptureOnly(extension, url, -1);
460   }
461
462   bool CaptureOnly(const Extension* extension, const GURL& url, int tab_id) {
463     return !extension->permissions_data()->CanAccessPage(
464                extension, url, url, tab_id, -1, NULL) &&
465            extension->permissions_data()->CanCaptureVisiblePage(tab_id, NULL);
466   }
467
468   bool ScriptOnly(const Extension* extension, const GURL& url,
469                   const GURL& top_url) {
470     return ScriptOnly(extension, url, top_url, -1);
471   }
472
473   bool ScriptOnly(const Extension* extension, const GURL& url,
474                   const GURL& top_url, int tab_id) {
475     return AllowedScript(extension, url, top_url, tab_id) &&
476            !extension->permissions_data()->CanCaptureVisiblePage(tab_id, NULL);
477   }
478
479   bool Blocked(const Extension* extension, const GURL& url) {
480     return Blocked(extension, url, -1);
481   }
482
483   bool Blocked(const Extension* extension, const GURL& url, int tab_id) {
484     return !(extension->permissions_data()->CanAccessPage(
485                  extension, url, url, tab_id, -1, NULL) ||
486              extension->permissions_data()->CanCaptureVisiblePage(tab_id,
487                                                                   NULL));
488   }
489
490   bool ScriptAllowedExclusivelyOnTab(
491       const Extension* extension,
492       const std::set<GURL>& allowed_urls,
493       int tab_id) {
494     bool result = true;
495     for (std::set<GURL>::iterator it = urls_.begin(); it != urls_.end(); ++it) {
496       const GURL& url = *it;
497       if (allowed_urls.count(url))
498         result &= AllowedScript(extension, url, url, tab_id);
499       else
500         result &= Blocked(extension, url, tab_id);
501     }
502     return result;
503   }
504
505   // URLs that are "safe" to provide scripting and capture visible tab access
506   // to if the permissions allow it.
507   const GURL http_url;
508   const GURL http_url_with_path;
509   const GURL https_url;
510   const GURL file_url;
511
512   // We should allow host permission but not scripting permission for favicon
513   // urls.
514   const GURL favicon_url;
515
516   // URLs that regular extensions should never get access to.
517   const GURL extension_url;
518   const GURL settings_url;
519   const GURL about_url;
520
521  private:
522   // The set of all URLs above.
523   std::set<GURL> urls_;
524 };
525
526 TEST_F(ExtensionScriptAndCaptureVisibleTest, Permissions) {
527   // Test <all_urls> for regular extensions.
528   scoped_refptr<Extension> extension = LoadManifestStrict("script_and_capture",
529       "extension_regular_all.json");
530
531   EXPECT_TRUE(Allowed(extension.get(), http_url));
532   EXPECT_TRUE(Allowed(extension.get(), https_url));
533   EXPECT_TRUE(CaptureOnly(extension.get(), file_url));
534   EXPECT_TRUE(CaptureOnly(extension.get(), settings_url));
535   EXPECT_TRUE(CaptureOnly(extension.get(), favicon_url));
536   EXPECT_TRUE(CaptureOnly(extension.get(), about_url));
537   EXPECT_TRUE(CaptureOnly(extension.get(), extension_url));
538
539   // Test access to iframed content.
540   GURL within_extension_url = extension->GetResourceURL("page.html");
541   EXPECT_TRUE(AllowedScript(extension.get(), http_url, http_url_with_path));
542   EXPECT_TRUE(AllowedScript(extension.get(), https_url, http_url_with_path));
543   EXPECT_TRUE(AllowedScript(extension.get(), http_url, within_extension_url));
544   EXPECT_TRUE(AllowedScript(extension.get(), https_url, within_extension_url));
545   EXPECT_TRUE(BlockedScript(extension.get(), http_url, extension_url));
546   EXPECT_TRUE(BlockedScript(extension.get(), https_url, extension_url));
547
548   EXPECT_FALSE(extension->permissions_data()->HasHostPermission(settings_url));
549   EXPECT_FALSE(extension->permissions_data()->HasHostPermission(about_url));
550   EXPECT_TRUE(extension->permissions_data()->HasHostPermission(favicon_url));
551
552   // Test * for scheme, which implies just the http/https schemes.
553   extension = LoadManifestStrict("script_and_capture",
554       "extension_wildcard.json");
555   EXPECT_TRUE(ScriptOnly(extension.get(), http_url, http_url));
556   EXPECT_TRUE(ScriptOnly(extension.get(), https_url, https_url));
557   EXPECT_TRUE(Blocked(extension.get(), settings_url));
558   EXPECT_TRUE(Blocked(extension.get(), about_url));
559   EXPECT_TRUE(Blocked(extension.get(), file_url));
560   EXPECT_TRUE(Blocked(extension.get(), favicon_url));
561   extension =
562       LoadManifest("script_and_capture", "extension_wildcard_settings.json");
563   EXPECT_TRUE(Blocked(extension.get(), settings_url));
564
565   // Having chrome://*/ should not work for regular extensions. Note that
566   // for favicon access, we require the explicit pattern chrome://favicon/*.
567   std::string error;
568   extension = LoadManifestUnchecked("script_and_capture",
569                                     "extension_wildcard_chrome.json",
570                                     Manifest::INTERNAL, Extension::NO_FLAGS,
571                                     &error);
572   std::vector<InstallWarning> warnings = extension->install_warnings();
573   EXPECT_FALSE(warnings.empty());
574   EXPECT_EQ(ErrorUtils::FormatErrorMessage(
575                 manifest_errors::kInvalidPermissionScheme,
576                 "chrome://*/"),
577             warnings[0].message);
578   EXPECT_TRUE(Blocked(extension.get(), settings_url));
579   EXPECT_TRUE(Blocked(extension.get(), favicon_url));
580   EXPECT_TRUE(Blocked(extension.get(), about_url));
581
582   // Having chrome://favicon/* should not give you chrome://*
583   extension = LoadManifestStrict("script_and_capture",
584       "extension_chrome_favicon_wildcard.json");
585   EXPECT_TRUE(Blocked(extension.get(), settings_url));
586   EXPECT_TRUE(Blocked(extension.get(), favicon_url));
587   EXPECT_TRUE(Blocked(extension.get(), about_url));
588   EXPECT_TRUE(extension->permissions_data()->HasHostPermission(favicon_url));
589
590   // Having http://favicon should not give you chrome://favicon
591   extension = LoadManifestStrict("script_and_capture",
592       "extension_http_favicon.json");
593   EXPECT_TRUE(Blocked(extension.get(), settings_url));
594   EXPECT_TRUE(Blocked(extension.get(), favicon_url));
595
596   // Component extensions with <all_urls> should get everything.
597   extension = LoadManifest("script_and_capture", "extension_component_all.json",
598       Manifest::COMPONENT, Extension::NO_FLAGS);
599   EXPECT_TRUE(Allowed(extension.get(), http_url));
600   EXPECT_TRUE(Allowed(extension.get(), https_url));
601   EXPECT_TRUE(Allowed(extension.get(), settings_url));
602   EXPECT_TRUE(Allowed(extension.get(), about_url));
603   EXPECT_TRUE(Allowed(extension.get(), favicon_url));
604   EXPECT_TRUE(extension->permissions_data()->HasHostPermission(favicon_url));
605
606   // Component extensions should only get access to what they ask for.
607   extension = LoadManifest("script_and_capture",
608       "extension_component_google.json", Manifest::COMPONENT,
609       Extension::NO_FLAGS);
610   EXPECT_TRUE(ScriptOnly(extension.get(), http_url, http_url));
611   EXPECT_TRUE(Blocked(extension.get(), https_url));
612   EXPECT_TRUE(Blocked(extension.get(), file_url));
613   EXPECT_TRUE(Blocked(extension.get(), settings_url));
614   EXPECT_TRUE(Blocked(extension.get(), favicon_url));
615   EXPECT_TRUE(Blocked(extension.get(), about_url));
616   EXPECT_TRUE(Blocked(extension.get(), extension_url));
617   EXPECT_FALSE(extension->permissions_data()->HasHostPermission(settings_url));
618 }
619
620 TEST_F(ExtensionScriptAndCaptureVisibleTest, PermissionsWithChromeURLsEnabled) {
621   CommandLine::ForCurrentProcess()->AppendSwitch(
622       switches::kExtensionsOnChromeURLs);
623
624   scoped_refptr<Extension> extension;
625
626   // Test <all_urls> for regular extensions.
627   extension = LoadManifestStrict("script_and_capture",
628       "extension_regular_all.json");
629   EXPECT_TRUE(Allowed(extension.get(), http_url));
630   EXPECT_TRUE(Allowed(extension.get(), https_url));
631   EXPECT_TRUE(CaptureOnly(extension.get(), file_url));
632   EXPECT_TRUE(CaptureOnly(extension.get(), settings_url));
633   EXPECT_TRUE(Allowed(extension.get(), favicon_url));  // chrome:// requested
634   EXPECT_TRUE(CaptureOnly(extension.get(), about_url));
635   EXPECT_TRUE(CaptureOnly(extension.get(), extension_url));
636
637   // Test access to iframed content.
638   GURL within_extension_url = extension->GetResourceURL("page.html");
639   EXPECT_TRUE(AllowedScript(extension.get(), http_url, http_url_with_path));
640   EXPECT_TRUE(AllowedScript(extension.get(), https_url, http_url_with_path));
641   EXPECT_TRUE(AllowedScript(extension.get(), http_url, within_extension_url));
642   EXPECT_TRUE(AllowedScript(extension.get(), https_url, within_extension_url));
643   EXPECT_TRUE(AllowedScript(extension.get(), http_url, extension_url));
644   EXPECT_TRUE(AllowedScript(extension.get(), https_url, extension_url));
645
646   const PermissionsData* permissions_data = extension->permissions_data();
647   EXPECT_FALSE(permissions_data->HasHostPermission(settings_url));
648   EXPECT_FALSE(permissions_data->HasHostPermission(about_url));
649   EXPECT_TRUE(permissions_data->HasHostPermission(favicon_url));
650
651   // Test * for scheme, which implies just the http/https schemes.
652   extension = LoadManifestStrict("script_and_capture",
653       "extension_wildcard.json");
654   EXPECT_TRUE(ScriptOnly(extension.get(), http_url, http_url));
655   EXPECT_TRUE(ScriptOnly(extension.get(), https_url, https_url));
656   EXPECT_TRUE(Blocked(extension.get(), settings_url));
657   EXPECT_TRUE(Blocked(extension.get(), about_url));
658   EXPECT_TRUE(Blocked(extension.get(), file_url));
659   EXPECT_TRUE(Blocked(extension.get(), favicon_url));
660   extension =
661       LoadManifest("script_and_capture", "extension_wildcard_settings.json");
662   EXPECT_TRUE(Blocked(extension.get(), settings_url));
663
664   // Having chrome://*/ should work for regular extensions with the flag
665   // enabled.
666   std::string error;
667   extension = LoadManifestUnchecked("script_and_capture",
668                                     "extension_wildcard_chrome.json",
669                                     Manifest::INTERNAL, Extension::NO_FLAGS,
670                                     &error);
671   EXPECT_FALSE(extension.get() == NULL);
672   EXPECT_TRUE(Blocked(extension.get(), http_url));
673   EXPECT_TRUE(Blocked(extension.get(), https_url));
674   EXPECT_TRUE(ScriptOnly(extension.get(), settings_url, settings_url));
675   EXPECT_TRUE(Blocked(extension.get(), about_url));
676   EXPECT_TRUE(Blocked(extension.get(), file_url));
677   EXPECT_TRUE(ScriptOnly(extension.get(), favicon_url, favicon_url));
678
679   // Having chrome://favicon/* should not give you chrome://*
680   extension = LoadManifestStrict("script_and_capture",
681       "extension_chrome_favicon_wildcard.json");
682   EXPECT_TRUE(Blocked(extension.get(), settings_url));
683   EXPECT_TRUE(ScriptOnly(extension.get(), favicon_url, favicon_url));
684   EXPECT_TRUE(Blocked(extension.get(), about_url));
685   EXPECT_TRUE(extension->permissions_data()->HasHostPermission(favicon_url));
686
687   // Having http://favicon should not give you chrome://favicon
688   extension = LoadManifestStrict("script_and_capture",
689       "extension_http_favicon.json");
690   EXPECT_TRUE(Blocked(extension.get(), settings_url));
691   EXPECT_TRUE(Blocked(extension.get(), favicon_url));
692
693   // Component extensions with <all_urls> should get everything.
694   extension = LoadManifest("script_and_capture", "extension_component_all.json",
695       Manifest::COMPONENT, Extension::NO_FLAGS);
696   EXPECT_TRUE(Allowed(extension.get(), http_url));
697   EXPECT_TRUE(Allowed(extension.get(), https_url));
698   EXPECT_TRUE(Allowed(extension.get(), settings_url));
699   EXPECT_TRUE(Allowed(extension.get(), about_url));
700   EXPECT_TRUE(Allowed(extension.get(), favicon_url));
701   EXPECT_TRUE(extension->permissions_data()->HasHostPermission(favicon_url));
702
703   // Component extensions should only get access to what they ask for.
704   extension = LoadManifest("script_and_capture",
705       "extension_component_google.json", Manifest::COMPONENT,
706       Extension::NO_FLAGS);
707   EXPECT_TRUE(ScriptOnly(extension.get(), http_url, http_url));
708   EXPECT_TRUE(Blocked(extension.get(), https_url));
709   EXPECT_TRUE(Blocked(extension.get(), file_url));
710   EXPECT_TRUE(Blocked(extension.get(), settings_url));
711   EXPECT_TRUE(Blocked(extension.get(), favicon_url));
712   EXPECT_TRUE(Blocked(extension.get(), about_url));
713   EXPECT_TRUE(Blocked(extension.get(), extension_url));
714   EXPECT_FALSE(extension->permissions_data()->HasHostPermission(settings_url));
715 }
716
717 TEST_F(ExtensionScriptAndCaptureVisibleTest, TabSpecific) {
718   scoped_refptr<Extension> extension =
719       LoadManifestStrict("script_and_capture", "tab_specific.json");
720
721   const PermissionsData* permissions_data = extension->permissions_data();
722   EXPECT_FALSE(permissions_data->GetTabSpecificPermissionsForTesting(0));
723   EXPECT_FALSE(permissions_data->GetTabSpecificPermissionsForTesting(1));
724   EXPECT_FALSE(permissions_data->GetTabSpecificPermissionsForTesting(2));
725
726   std::set<GURL> no_urls;
727
728   EXPECT_TRUE(ScriptAllowedExclusivelyOnTab(extension.get(), no_urls, 0));
729   EXPECT_TRUE(ScriptAllowedExclusivelyOnTab(extension.get(), no_urls, 1));
730   EXPECT_TRUE(ScriptAllowedExclusivelyOnTab(extension.get(), no_urls, 2));
731
732   URLPatternSet allowed_hosts;
733   allowed_hosts.AddPattern(URLPattern(URLPattern::SCHEME_ALL,
734                                       http_url.spec()));
735   std::set<GURL> allowed_urls;
736   allowed_urls.insert(http_url);
737   // http_url_with_path() will also be allowed, because Extension should be
738   // considering the security origin of the URL not the URL itself, and
739   // http_url is in allowed_hosts.
740   allowed_urls.insert(http_url_with_path);
741
742   {
743     scoped_refptr<PermissionSet> permissions(
744         new PermissionSet(APIPermissionSet(), ManifestPermissionSet(),
745                           allowed_hosts, URLPatternSet()));
746     permissions_data->UpdateTabSpecificPermissions(0, permissions);
747     EXPECT_EQ(permissions->explicit_hosts(),
748               permissions_data->GetTabSpecificPermissionsForTesting(0)
749                   ->explicit_hosts());
750   }
751
752   EXPECT_TRUE(ScriptAllowedExclusivelyOnTab(extension.get(), allowed_urls, 0));
753   EXPECT_TRUE(ScriptAllowedExclusivelyOnTab(extension.get(), no_urls, 1));
754   EXPECT_TRUE(ScriptAllowedExclusivelyOnTab(extension.get(), no_urls, 2));
755
756   permissions_data->ClearTabSpecificPermissions(0);
757   EXPECT_FALSE(permissions_data->GetTabSpecificPermissionsForTesting(0));
758
759   EXPECT_TRUE(ScriptAllowedExclusivelyOnTab(extension.get(), no_urls, 0));
760   EXPECT_TRUE(ScriptAllowedExclusivelyOnTab(extension.get(), no_urls, 1));
761   EXPECT_TRUE(ScriptAllowedExclusivelyOnTab(extension.get(), no_urls, 2));
762
763   std::set<GURL> more_allowed_urls = allowed_urls;
764   more_allowed_urls.insert(https_url);
765   URLPatternSet more_allowed_hosts = allowed_hosts;
766   more_allowed_hosts.AddPattern(URLPattern(URLPattern::SCHEME_ALL,
767                                            https_url.spec()));
768
769   {
770     scoped_refptr<PermissionSet> permissions(
771         new PermissionSet(APIPermissionSet(),  ManifestPermissionSet(),
772                           allowed_hosts, URLPatternSet()));
773     permissions_data->UpdateTabSpecificPermissions(0, permissions);
774     EXPECT_EQ(permissions->explicit_hosts(),
775               permissions_data->GetTabSpecificPermissionsForTesting(0)
776                   ->explicit_hosts());
777
778     permissions = new PermissionSet(APIPermissionSet(),
779                                     ManifestPermissionSet(),
780                                     more_allowed_hosts,
781                                     URLPatternSet());
782     permissions_data->UpdateTabSpecificPermissions(1, permissions);
783     EXPECT_EQ(permissions->explicit_hosts(),
784               permissions_data->GetTabSpecificPermissionsForTesting(1)
785                   ->explicit_hosts());
786   }
787
788   EXPECT_TRUE(ScriptAllowedExclusivelyOnTab(extension.get(), allowed_urls, 0));
789   EXPECT_TRUE(
790       ScriptAllowedExclusivelyOnTab(extension.get(), more_allowed_urls, 1));
791   EXPECT_TRUE(ScriptAllowedExclusivelyOnTab(extension.get(), no_urls, 2));
792
793   permissions_data->ClearTabSpecificPermissions(0);
794   EXPECT_FALSE(permissions_data->GetTabSpecificPermissionsForTesting(0));
795
796   EXPECT_TRUE(ScriptAllowedExclusivelyOnTab(extension.get(), no_urls, 0));
797   EXPECT_TRUE(
798       ScriptAllowedExclusivelyOnTab(extension.get(), more_allowed_urls, 1));
799   EXPECT_TRUE(ScriptAllowedExclusivelyOnTab(extension.get(), no_urls, 2));
800
801   permissions_data->ClearTabSpecificPermissions(1);
802   EXPECT_FALSE(permissions_data->GetTabSpecificPermissionsForTesting(1));
803
804   EXPECT_TRUE(ScriptAllowedExclusivelyOnTab(extension.get(), no_urls, 0));
805   EXPECT_TRUE(ScriptAllowedExclusivelyOnTab(extension.get(), no_urls, 1));
806   EXPECT_TRUE(ScriptAllowedExclusivelyOnTab(extension.get(), no_urls, 2));
807 }
808
809 }  // namespace extensions