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.
5 #include "content/browser/child_process_security_policy_impl.h"
7 #include "base/command_line.h"
8 #include "base/files/file_path.h"
9 #include "base/logging.h"
10 #include "base/metrics/histogram.h"
11 #include "base/platform_file.h"
12 #include "base/stl_util.h"
13 #include "base/strings/string_util.h"
14 #include "content/browser/plugin_process_host.h"
15 #include "content/browser/site_instance_impl.h"
16 #include "content/public/browser/child_process_data.h"
17 #include "content/public/browser/content_browser_client.h"
18 #include "content/public/browser/render_process_host.h"
19 #include "content/public/common/bindings_policy.h"
20 #include "content/public/common/content_switches.h"
21 #include "content/public/common/url_constants.h"
22 #include "net/base/net_util.h"
23 #include "net/url_request/url_request.h"
25 #include "webkit/browser/fileapi/file_permission_policy.h"
26 #include "webkit/browser/fileapi/file_system_url.h"
27 #include "webkit/browser/fileapi/isolated_context.h"
28 #include "webkit/common/fileapi/file_system_util.h"
34 // Used internally only. These bit positions have no relationship to any
35 // underlying OS and can be changed to accommodate finer-grained permissions.
36 enum ChildProcessSecurityPermissions {
37 READ_FILE_PERMISSION = 1 << 0,
38 WRITE_FILE_PERMISSION = 1 << 1,
39 CREATE_NEW_FILE_PERMISSION = 1 << 2,
40 CREATE_OVERWRITE_FILE_PERMISSION = 1 << 3,
41 DELETE_FILE_PERMISSION = 1 << 4,
43 // Used by Media Galleries API
44 COPY_INTO_FILE_PERMISSION = 1 << 5,
47 // Used internally only. Bitmasks that are actually used by the Grant* and Can*
48 // methods. These contain one or more ChildProcessSecurityPermissions.
49 enum ChildProcessSecurityGrants {
50 READ_FILE_GRANT = READ_FILE_PERMISSION,
51 WRITE_FILE_GRANT = WRITE_FILE_PERMISSION,
53 CREATE_NEW_FILE_GRANT = CREATE_NEW_FILE_PERMISSION |
54 COPY_INTO_FILE_PERMISSION,
56 CREATE_READ_WRITE_FILE_GRANT = CREATE_NEW_FILE_PERMISSION |
57 CREATE_OVERWRITE_FILE_PERMISSION |
58 READ_FILE_PERMISSION |
59 WRITE_FILE_PERMISSION |
60 COPY_INTO_FILE_PERMISSION |
61 DELETE_FILE_PERMISSION,
63 COPY_INTO_FILE_GRANT = COPY_INTO_FILE_PERMISSION,
64 DELETE_FILE_GRANT = DELETE_FILE_PERMISSION,
69 // The SecurityState class is used to maintain per-child process security state
71 class ChildProcessSecurityPolicyImpl::SecurityState {
74 : enabled_bindings_(0),
75 can_read_raw_cookies_(false),
76 can_send_midi_sysex_(false) { }
79 scheme_policy_.clear();
80 fileapi::IsolatedContext* isolated_context =
81 fileapi::IsolatedContext::GetInstance();
82 for (FileSystemMap::iterator iter = filesystem_permissions_.begin();
83 iter != filesystem_permissions_.end();
85 isolated_context->RemoveReference(iter->first);
87 UMA_HISTOGRAM_COUNTS("ChildProcessSecurityPolicy.PerChildFilePermissions",
88 file_permissions_.size());
91 // Grant permission to request URLs with the specified scheme.
92 void GrantScheme(const std::string& scheme) {
93 scheme_policy_[scheme] = true;
96 // Revoke permission to request URLs with the specified scheme.
97 void RevokeScheme(const std::string& scheme) {
98 scheme_policy_[scheme] = false;
101 // Grant certain permissions to a file.
102 void GrantPermissionsForFile(const base::FilePath& file, int permissions) {
103 base::FilePath stripped = file.StripTrailingSeparators();
104 file_permissions_[stripped] |= permissions;
105 UMA_HISTOGRAM_COUNTS("ChildProcessSecurityPolicy.FilePermissionPathLength",
106 stripped.value().size());
109 // Grant navigation to a file but not the file:// scheme in general.
110 void GrantRequestOfSpecificFile(const base::FilePath &file) {
111 request_file_set_.insert(file.StripTrailingSeparators());
114 // Revokes all permissions granted to a file.
115 void RevokeAllPermissionsForFile(const base::FilePath& file) {
116 base::FilePath stripped = file.StripTrailingSeparators();
117 file_permissions_.erase(stripped);
118 request_file_set_.erase(stripped);
121 // Grant certain permissions to a file.
122 void GrantPermissionsForFileSystem(const std::string& filesystem_id,
124 if (!ContainsKey(filesystem_permissions_, filesystem_id))
125 fileapi::IsolatedContext::GetInstance()->AddReference(filesystem_id);
126 filesystem_permissions_[filesystem_id] |= permissions;
129 bool HasPermissionsForFileSystem(const std::string& filesystem_id,
131 FileSystemMap::const_iterator it =
132 filesystem_permissions_.find(filesystem_id);
133 if (it == filesystem_permissions_.end())
135 return (it->second & permissions) == permissions;
138 void GrantBindings(int bindings) {
139 enabled_bindings_ |= bindings;
142 void GrantReadRawCookies() {
143 can_read_raw_cookies_ = true;
146 void RevokeReadRawCookies() {
147 can_read_raw_cookies_ = false;
150 void GrantPermissionForMIDISysEx() {
151 can_send_midi_sysex_ = true;
154 // Determine whether permission has been granted to request |url|.
155 bool CanRequestURL(const GURL& url) {
156 // Having permission to a scheme implies permssion to all of its URLs.
157 SchemeMap::const_iterator judgment(scheme_policy_.find(url.scheme()));
158 if (judgment != scheme_policy_.end())
159 return judgment->second;
161 // file:// URLs are more granular. The child may have been given
162 // permission to a specific file but not the file:// scheme in general.
163 if (url.SchemeIs(chrome::kFileScheme)) {
165 if (net::FileURLToFilePath(url, &path))
166 return ContainsKey(request_file_set_, path);
169 return false; // Unmentioned schemes are disallowed.
172 // Determine if the certain permissions have been granted to a file.
173 bool HasPermissionsForFile(const base::FilePath& file, int permissions) {
174 if (!permissions || file.empty() || !file.IsAbsolute())
176 base::FilePath current_path = file.StripTrailingSeparators();
177 base::FilePath last_path;
179 while (current_path != last_path) {
180 base::FilePath base_name = current_path.BaseName();
181 if (base_name.value() == base::FilePath::kParentDirectory) {
183 } else if (skip > 0) {
184 if (base_name.value() != base::FilePath::kCurrentDirectory)
187 FileMap::const_iterator it = file_permissions_.find(current_path);
188 if (it != file_permissions_.end())
189 return (it->second & permissions) == permissions;
191 last_path = current_path;
192 current_path = current_path.DirName();
198 bool CanLoadPage(const GURL& gurl) {
199 if (origin_lock_.is_empty())
202 // TODO(creis): We must pass the valid browser_context to convert hosted
203 // apps URLs. Currently, hosted apps cannot be loaded in this mode.
204 // See http://crbug.com/160576.
205 GURL site_gurl = SiteInstanceImpl::GetSiteForURL(NULL, gurl);
206 return origin_lock_ == site_gurl;
209 bool CanAccessCookiesForOrigin(const GURL& gurl) {
210 if (origin_lock_.is_empty())
212 // TODO(creis): We must pass the valid browser_context to convert hosted
213 // apps URLs. Currently, hosted apps cannot set cookies in this mode.
214 // See http://crbug.com/160576.
215 GURL site_gurl = SiteInstanceImpl::GetSiteForURL(NULL, gurl);
216 return origin_lock_ == site_gurl;
219 bool CanSendCookiesForOrigin(const GURL& gurl) {
220 // We only block cross-site cookies on network requests if the
221 // --enable-strict-site-isolation flag is passed. This is expected to break
222 // compatibility with many sites. The similar --site-per-process flag only
223 // blocks JavaScript access to cross-site cookies (in
224 // CanAccessCookiesForOrigin).
225 const CommandLine& command_line = *CommandLine::ForCurrentProcess();
226 if (!command_line.HasSwitch(switches::kEnableStrictSiteIsolation))
229 if (origin_lock_.is_empty())
231 // TODO(creis): We must pass the valid browser_context to convert hosted
232 // apps URLs. Currently, hosted apps cannot set cookies in this mode.
233 // See http://crbug.com/160576.
234 GURL site_gurl = SiteInstanceImpl::GetSiteForURL(NULL, gurl);
235 return origin_lock_ == site_gurl;
238 void LockToOrigin(const GURL& gurl) {
242 bool has_web_ui_bindings() const {
243 return enabled_bindings_ & BINDINGS_POLICY_WEB_UI;
246 bool can_read_raw_cookies() const {
247 return can_read_raw_cookies_;
250 bool can_send_midi_sysex() const {
251 return can_send_midi_sysex_;
255 typedef std::map<std::string, bool> SchemeMap;
257 typedef int FilePermissionFlags; // bit-set of PlatformFileFlags
258 typedef std::map<base::FilePath, FilePermissionFlags> FileMap;
259 typedef std::map<std::string, FilePermissionFlags> FileSystemMap;
260 typedef std::set<base::FilePath> FileSet;
262 // Maps URL schemes to whether permission has been granted or revoked:
263 // |true| means the scheme has been granted.
264 // |false| means the scheme has been revoked.
265 // If a scheme is not present in the map, then it has never been granted
267 SchemeMap scheme_policy_;
269 // The set of files the child process is permited to upload to the web.
270 FileMap file_permissions_;
272 // The set of files the child process is permitted to load.
273 FileSet request_file_set_;
275 int enabled_bindings_;
277 bool can_read_raw_cookies_;
279 bool can_send_midi_sysex_;
283 // The set of isolated filesystems the child process is permitted to access.
284 FileSystemMap filesystem_permissions_;
286 DISALLOW_COPY_AND_ASSIGN(SecurityState);
289 ChildProcessSecurityPolicyImpl::ChildProcessSecurityPolicyImpl() {
290 // We know about these schemes and believe them to be safe.
291 RegisterWebSafeScheme(kHttpScheme);
292 RegisterWebSafeScheme(kHttpsScheme);
293 RegisterWebSafeScheme(chrome::kFtpScheme);
294 RegisterWebSafeScheme(chrome::kDataScheme);
295 RegisterWebSafeScheme("feed");
296 RegisterWebSafeScheme(chrome::kBlobScheme);
297 RegisterWebSafeScheme(chrome::kFileSystemScheme);
299 // We know about the following pseudo schemes and treat them specially.
300 RegisterPseudoScheme(chrome::kAboutScheme);
301 RegisterPseudoScheme(kJavaScriptScheme);
302 RegisterPseudoScheme(kViewSourceScheme);
305 ChildProcessSecurityPolicyImpl::~ChildProcessSecurityPolicyImpl() {
306 web_safe_schemes_.clear();
307 pseudo_schemes_.clear();
308 STLDeleteContainerPairSecondPointers(security_state_.begin(),
309 security_state_.end());
310 security_state_.clear();
314 ChildProcessSecurityPolicy* ChildProcessSecurityPolicy::GetInstance() {
315 return ChildProcessSecurityPolicyImpl::GetInstance();
318 ChildProcessSecurityPolicyImpl* ChildProcessSecurityPolicyImpl::GetInstance() {
319 return Singleton<ChildProcessSecurityPolicyImpl>::get();
322 void ChildProcessSecurityPolicyImpl::Add(int child_id) {
323 base::AutoLock lock(lock_);
327 void ChildProcessSecurityPolicyImpl::AddWorker(int child_id,
328 int main_render_process_id) {
329 base::AutoLock lock(lock_);
331 worker_map_[child_id] = main_render_process_id;
334 void ChildProcessSecurityPolicyImpl::Remove(int child_id) {
335 base::AutoLock lock(lock_);
336 SecurityStateMap::iterator it = security_state_.find(child_id);
337 if (it == security_state_.end())
338 return; // May be called multiple times.
341 security_state_.erase(it);
342 worker_map_.erase(child_id);
345 void ChildProcessSecurityPolicyImpl::RegisterWebSafeScheme(
346 const std::string& scheme) {
347 base::AutoLock lock(lock_);
348 DCHECK_EQ(0U, web_safe_schemes_.count(scheme)) << "Add schemes at most once.";
349 DCHECK_EQ(0U, pseudo_schemes_.count(scheme))
350 << "Web-safe implies not pseudo.";
352 web_safe_schemes_.insert(scheme);
355 bool ChildProcessSecurityPolicyImpl::IsWebSafeScheme(
356 const std::string& scheme) {
357 base::AutoLock lock(lock_);
359 return ContainsKey(web_safe_schemes_, scheme);
362 void ChildProcessSecurityPolicyImpl::RegisterPseudoScheme(
363 const std::string& scheme) {
364 base::AutoLock lock(lock_);
365 DCHECK_EQ(0U, pseudo_schemes_.count(scheme)) << "Add schemes at most once.";
366 DCHECK_EQ(0U, web_safe_schemes_.count(scheme))
367 << "Pseudo implies not web-safe.";
369 pseudo_schemes_.insert(scheme);
372 bool ChildProcessSecurityPolicyImpl::IsPseudoScheme(
373 const std::string& scheme) {
374 base::AutoLock lock(lock_);
376 return ContainsKey(pseudo_schemes_, scheme);
379 void ChildProcessSecurityPolicyImpl::GrantRequestURL(
380 int child_id, const GURL& url) {
383 return; // Can't grant the capability to request invalid URLs.
385 if (IsWebSafeScheme(url.scheme()))
386 return; // The scheme has already been whitelisted for every child process.
388 if (IsPseudoScheme(url.scheme())) {
389 // The view-source scheme is a special case of a pseudo-URL that eventually
390 // results in requesting its embedded URL.
391 if (url.SchemeIs(kViewSourceScheme)) {
392 // URLs with the view-source scheme typically look like:
393 // view-source:http://www.google.com/a
394 // In order to request these URLs, the child_id needs to be able to
395 // request the embedded URL.
396 GrantRequestURL(child_id, GURL(url.GetContent()));
399 return; // Can't grant the capability to request pseudo schemes.
403 base::AutoLock lock(lock_);
404 SecurityStateMap::iterator state = security_state_.find(child_id);
405 if (state == security_state_.end())
408 // When the child process has been commanded to request this scheme,
409 // we grant it the capability to request all URLs of that scheme.
410 state->second->GrantScheme(url.scheme());
414 void ChildProcessSecurityPolicyImpl::GrantRequestSpecificFileURL(
417 if (!url.SchemeIs(chrome::kFileScheme))
421 base::AutoLock lock(lock_);
422 SecurityStateMap::iterator state = security_state_.find(child_id);
423 if (state == security_state_.end())
426 // When the child process has been commanded to request a file:// URL,
427 // then we grant it the capability for that URL only.
429 if (net::FileURLToFilePath(url, &path))
430 state->second->GrantRequestOfSpecificFile(path);
434 void ChildProcessSecurityPolicyImpl::GrantReadFile(int child_id,
435 const base::FilePath& file) {
436 GrantPermissionsForFile(child_id, file, READ_FILE_GRANT);
439 void ChildProcessSecurityPolicyImpl::GrantCreateReadWriteFile(
440 int child_id, const base::FilePath& file) {
441 GrantPermissionsForFile(child_id, file, CREATE_READ_WRITE_FILE_GRANT);
444 void ChildProcessSecurityPolicyImpl::GrantPermissionsForFile(
445 int child_id, const base::FilePath& file, int permissions) {
446 base::AutoLock lock(lock_);
448 SecurityStateMap::iterator state = security_state_.find(child_id);
449 if (state == security_state_.end())
452 state->second->GrantPermissionsForFile(file, permissions);
455 void ChildProcessSecurityPolicyImpl::RevokeAllPermissionsForFile(
456 int child_id, const base::FilePath& file) {
457 base::AutoLock lock(lock_);
459 SecurityStateMap::iterator state = security_state_.find(child_id);
460 if (state == security_state_.end())
463 state->second->RevokeAllPermissionsForFile(file);
466 void ChildProcessSecurityPolicyImpl::GrantReadFileSystem(
467 int child_id, const std::string& filesystem_id) {
468 GrantPermissionsForFileSystem(child_id, filesystem_id, READ_FILE_GRANT);
471 void ChildProcessSecurityPolicyImpl::GrantWriteFileSystem(
472 int child_id, const std::string& filesystem_id) {
473 GrantPermissionsForFileSystem(child_id, filesystem_id, WRITE_FILE_GRANT);
476 void ChildProcessSecurityPolicyImpl::GrantCreateFileForFileSystem(
477 int child_id, const std::string& filesystem_id) {
478 GrantPermissionsForFileSystem(child_id, filesystem_id, CREATE_NEW_FILE_GRANT);
481 void ChildProcessSecurityPolicyImpl::GrantCopyIntoFileSystem(
482 int child_id, const std::string& filesystem_id) {
483 GrantPermissionsForFileSystem(child_id, filesystem_id, COPY_INTO_FILE_GRANT);
486 void ChildProcessSecurityPolicyImpl::GrantDeleteFromFileSystem(
487 int child_id, const std::string& filesystem_id) {
488 GrantPermissionsForFileSystem(child_id, filesystem_id, DELETE_FILE_GRANT);
491 void ChildProcessSecurityPolicyImpl::GrantSendMIDISysExMessage(int child_id) {
492 base::AutoLock lock(lock_);
494 SecurityStateMap::iterator state = security_state_.find(child_id);
495 if (state == security_state_.end())
498 state->second->GrantPermissionForMIDISysEx();
501 void ChildProcessSecurityPolicyImpl::GrantScheme(int child_id,
502 const std::string& scheme) {
503 base::AutoLock lock(lock_);
505 SecurityStateMap::iterator state = security_state_.find(child_id);
506 if (state == security_state_.end())
509 state->second->GrantScheme(scheme);
512 void ChildProcessSecurityPolicyImpl::GrantWebUIBindings(int child_id) {
513 base::AutoLock lock(lock_);
515 SecurityStateMap::iterator state = security_state_.find(child_id);
516 if (state == security_state_.end())
519 state->second->GrantBindings(BINDINGS_POLICY_WEB_UI);
521 // Web UI bindings need the ability to request chrome: URLs.
522 state->second->GrantScheme(chrome::kChromeUIScheme);
524 // Web UI pages can contain links to file:// URLs.
525 state->second->GrantScheme(chrome::kFileScheme);
528 void ChildProcessSecurityPolicyImpl::GrantReadRawCookies(int child_id) {
529 base::AutoLock lock(lock_);
531 SecurityStateMap::iterator state = security_state_.find(child_id);
532 if (state == security_state_.end())
535 state->second->GrantReadRawCookies();
538 void ChildProcessSecurityPolicyImpl::RevokeReadRawCookies(int child_id) {
539 base::AutoLock lock(lock_);
541 SecurityStateMap::iterator state = security_state_.find(child_id);
542 if (state == security_state_.end())
545 state->second->RevokeReadRawCookies();
548 bool ChildProcessSecurityPolicyImpl::CanLoadPage(
551 ResourceType::Type resource_type) {
552 // If --site-per-process flag is passed, we should enforce
553 // stronger security restrictions on page navigation.
554 if (CommandLine::ForCurrentProcess()->HasSwitch(switches::kSitePerProcess) &&
555 ResourceType::IsFrame(resource_type)) {
556 // TODO(nasko): Do the proper check for site-per-process, once
557 // out-of-process iframes is ready to go.
563 bool ChildProcessSecurityPolicyImpl::CanRequestURL(
564 int child_id, const GURL& url) {
566 return false; // Can't request invalid URLs.
568 if (IsWebSafeScheme(url.scheme()))
569 return true; // The scheme has been white-listed for every child process.
571 if (IsPseudoScheme(url.scheme())) {
572 // There are a number of special cases for pseudo schemes.
574 if (url.SchemeIs(kViewSourceScheme)) {
575 // A view-source URL is allowed if the child process is permitted to
576 // request the embedded URL. Careful to avoid pointless recursion.
577 GURL child_url(url.GetContent());
578 if (child_url.SchemeIs(kViewSourceScheme) &&
579 url.SchemeIs(kViewSourceScheme))
582 return CanRequestURL(child_id, child_url);
585 if (LowerCaseEqualsASCII(url.spec(), kAboutBlankURL))
586 return true; // Every child process can request <about:blank>.
588 // URLs like <about:memory> and <about:crash> shouldn't be requestable by
589 // any child process. Also, this case covers <javascript:...>, which should
590 // be handled internally by the process and not kicked up to the browser.
594 if (!GetContentClient()->browser()->IsHandledURL(url) &&
595 !net::URLRequest::IsHandledURL(url)) {
596 return true; // This URL request is destined for ShellExecute.
600 base::AutoLock lock(lock_);
602 SecurityStateMap::iterator state = security_state_.find(child_id);
603 if (state == security_state_.end())
606 // Otherwise, we consult the child process's security state to see if it is
607 // allowed to request the URL.
608 return state->second->CanRequestURL(url);
612 bool ChildProcessSecurityPolicyImpl::CanReadFile(int child_id,
613 const base::FilePath& file) {
614 return HasPermissionsForFile(child_id, file, READ_FILE_GRANT);
617 bool ChildProcessSecurityPolicyImpl::CanCreateReadWriteFile(
619 const base::FilePath& file) {
620 return HasPermissionsForFile(child_id, file, CREATE_READ_WRITE_FILE_GRANT);
623 bool ChildProcessSecurityPolicyImpl::CanReadFileSystem(
624 int child_id, const std::string& filesystem_id) {
625 return HasPermissionsForFileSystem(child_id, filesystem_id, READ_FILE_GRANT);
628 bool ChildProcessSecurityPolicyImpl::CanReadWriteFileSystem(
629 int child_id, const std::string& filesystem_id) {
630 return HasPermissionsForFileSystem(child_id, filesystem_id,
631 READ_FILE_GRANT | WRITE_FILE_GRANT);
634 bool ChildProcessSecurityPolicyImpl::CanCopyIntoFileSystem(
635 int child_id, const std::string& filesystem_id) {
636 return HasPermissionsForFileSystem(child_id, filesystem_id,
637 COPY_INTO_FILE_GRANT);
640 bool ChildProcessSecurityPolicyImpl::CanDeleteFromFileSystem(
641 int child_id, const std::string& filesystem_id) {
642 return HasPermissionsForFileSystem(child_id, filesystem_id,
646 void ChildProcessSecurityPolicyImpl::GrantCreateReadWriteFileSystem(
647 int child_id, const std::string& filesystem_id) {
648 GrantPermissionsForFileSystem(
649 child_id, filesystem_id, CREATE_READ_WRITE_FILE_GRANT);
652 bool ChildProcessSecurityPolicyImpl::HasPermissionsForFile(
653 int child_id, const base::FilePath& file, int permissions) {
654 base::AutoLock lock(lock_);
655 bool result = ChildProcessHasPermissionsForFile(child_id, file, permissions);
657 // If this is a worker thread that has no access to a given file,
658 // let's check that its renderer process has access to that file instead.
659 WorkerToMainProcessMap::iterator iter = worker_map_.find(child_id);
660 if (iter != worker_map_.end() && iter->second != 0) {
661 result = ChildProcessHasPermissionsForFile(iter->second,
669 bool ChildProcessSecurityPolicyImpl::HasPermissionsForFileSystemFile(
670 int child_id, const fileapi::FileSystemURL& url, int permissions) {
674 if (url.path().ReferencesParent())
677 // Any write access is disallowed on the root path.
678 if (fileapi::VirtualPath::IsRootPath(url.path()) &&
679 (permissions & ~READ_FILE_GRANT)) {
683 if (url.mount_type() == fileapi::kFileSystemTypeIsolated) {
684 // When Isolated filesystems is overlayed on top of another filesystem,
685 // its per-filesystem permission overrides the underlying filesystem
687 return HasPermissionsForFileSystem(
688 child_id, url.mount_filesystem_id(), permissions);
691 FileSystemPermissionPolicyMap::iterator found =
692 file_system_policy_map_.find(url.type());
693 if (found == file_system_policy_map_.end())
696 if ((found->second & fileapi::FILE_PERMISSION_READ_ONLY) &&
697 permissions & ~READ_FILE_GRANT) {
701 if (found->second & fileapi::FILE_PERMISSION_USE_FILE_PERMISSION)
702 return HasPermissionsForFile(child_id, url.path(), permissions);
704 if (found->second & fileapi::FILE_PERMISSION_SANDBOX)
710 bool ChildProcessSecurityPolicyImpl::CanReadFileSystemFile(
712 const fileapi::FileSystemURL& url) {
713 return HasPermissionsForFileSystemFile(child_id, url, READ_FILE_GRANT);
716 bool ChildProcessSecurityPolicyImpl::CanWriteFileSystemFile(
718 const fileapi::FileSystemURL& url) {
719 return HasPermissionsForFileSystemFile(child_id, url, WRITE_FILE_GRANT);
722 bool ChildProcessSecurityPolicyImpl::CanCreateFileSystemFile(
724 const fileapi::FileSystemURL& url) {
725 return HasPermissionsForFileSystemFile(child_id, url, CREATE_NEW_FILE_GRANT);
728 bool ChildProcessSecurityPolicyImpl::CanCreateReadWriteFileSystemFile(
730 const fileapi::FileSystemURL& url) {
731 return HasPermissionsForFileSystemFile(child_id, url,
732 CREATE_READ_WRITE_FILE_GRANT);
735 bool ChildProcessSecurityPolicyImpl::CanCopyIntoFileSystemFile(
737 const fileapi::FileSystemURL& url) {
738 return HasPermissionsForFileSystemFile(child_id, url, COPY_INTO_FILE_GRANT);
741 bool ChildProcessSecurityPolicyImpl::CanDeleteFileSystemFile(
743 const fileapi::FileSystemURL& url) {
744 return HasPermissionsForFileSystemFile(child_id, url, DELETE_FILE_GRANT);
747 bool ChildProcessSecurityPolicyImpl::HasWebUIBindings(int child_id) {
748 base::AutoLock lock(lock_);
750 SecurityStateMap::iterator state = security_state_.find(child_id);
751 if (state == security_state_.end())
754 return state->second->has_web_ui_bindings();
757 bool ChildProcessSecurityPolicyImpl::CanReadRawCookies(int child_id) {
758 base::AutoLock lock(lock_);
760 SecurityStateMap::iterator state = security_state_.find(child_id);
761 if (state == security_state_.end())
764 return state->second->can_read_raw_cookies();
767 void ChildProcessSecurityPolicyImpl::AddChild(int child_id) {
768 if (security_state_.count(child_id) != 0) {
769 NOTREACHED() << "Add child process at most once.";
773 security_state_[child_id] = new SecurityState();
776 bool ChildProcessSecurityPolicyImpl::ChildProcessHasPermissionsForFile(
777 int child_id, const base::FilePath& file, int permissions) {
778 SecurityStateMap::iterator state = security_state_.find(child_id);
779 if (state == security_state_.end())
781 return state->second->HasPermissionsForFile(file, permissions);
784 bool ChildProcessSecurityPolicyImpl::CanAccessCookiesForOrigin(
785 int child_id, const GURL& gurl) {
786 base::AutoLock lock(lock_);
787 SecurityStateMap::iterator state = security_state_.find(child_id);
788 if (state == security_state_.end())
790 return state->second->CanAccessCookiesForOrigin(gurl);
793 bool ChildProcessSecurityPolicyImpl::CanSendCookiesForOrigin(int child_id,
795 for (PluginProcessHostIterator iter; !iter.Done(); ++iter) {
796 if (iter.GetData().id == child_id) {
797 if (iter.GetData().process_type == PROCESS_TYPE_PLUGIN) {
798 // NPAPI plugin processes are unsandboxed and so are trusted. Plugins
799 // can make request to any origin.
806 base::AutoLock lock(lock_);
807 SecurityStateMap::iterator state = security_state_.find(child_id);
808 if (state == security_state_.end())
810 return state->second->CanSendCookiesForOrigin(gurl);
813 void ChildProcessSecurityPolicyImpl::LockToOrigin(int child_id,
815 // "gurl" can be currently empty in some cases, such as file://blah.
816 DCHECK(SiteInstanceImpl::GetSiteForURL(NULL, gurl) == gurl);
817 base::AutoLock lock(lock_);
818 SecurityStateMap::iterator state = security_state_.find(child_id);
819 DCHECK(state != security_state_.end());
820 state->second->LockToOrigin(gurl);
823 void ChildProcessSecurityPolicyImpl::GrantPermissionsForFileSystem(
825 const std::string& filesystem_id,
827 base::AutoLock lock(lock_);
829 SecurityStateMap::iterator state = security_state_.find(child_id);
830 if (state == security_state_.end())
832 state->second->GrantPermissionsForFileSystem(filesystem_id, permission);
835 bool ChildProcessSecurityPolicyImpl::HasPermissionsForFileSystem(
837 const std::string& filesystem_id,
839 base::AutoLock lock(lock_);
841 SecurityStateMap::iterator state = security_state_.find(child_id);
842 if (state == security_state_.end())
844 return state->second->HasPermissionsForFileSystem(filesystem_id, permission);
847 void ChildProcessSecurityPolicyImpl::RegisterFileSystemPermissionPolicy(
848 fileapi::FileSystemType type,
850 base::AutoLock lock(lock_);
851 file_system_policy_map_[type] = policy;
854 bool ChildProcessSecurityPolicyImpl::CanSendMIDISysExMessage(int child_id) {
855 base::AutoLock lock(lock_);
857 SecurityStateMap::iterator state = security_state_.find(child_id);
858 if (state == security_state_.end())
861 return state->second->can_send_midi_sysex();
864 } // namespace content