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

Side by Side Diff: chrome/browser/chromeos/extensions/file_handler_util.cc

Issue 10067021: Postpone setting up file handler's file permissions if handler is running lazy background page. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: rebase Created 8 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 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 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "chrome/browser/chromeos/extensions/file_handler_util.h" 5 #include "chrome/browser/chromeos/extensions/file_handler_util.h"
6 6
7 #include "base/bind.h" 7 #include "base/bind.h"
8 #include "base/file_util.h" 8 #include "base/file_util.h"
9 #include "base/i18n/case_conversion.h" 9 #include "base/i18n/case_conversion.h"
10 #include "base/json/json_writer.h" 10 #include "base/json/json_writer.h"
11 #include "base/string_util.h" 11 #include "base/string_util.h"
12 #include "base/stringprintf.h" 12 #include "base/stringprintf.h"
13 #include "base/utf_string_conversions.h" 13 #include "base/utf_string_conversions.h"
14 #include "chrome/browser/chromeos/gdata/gdata_util.h" 14 #include "chrome/browser/chromeos/gdata/gdata_util.h"
15 #include "chrome/browser/chromeos/extensions/file_manager_util.h" 15 #include "chrome/browser/chromeos/extensions/file_manager_util.h"
16 #include "chrome/browser/extensions/extension_event_router.h" 16 #include "chrome/browser/extensions/extension_event_router.h"
17 #include "chrome/browser/extensions/extension_host.h"
17 #include "chrome/browser/extensions/extension_service.h" 18 #include "chrome/browser/extensions/extension_service.h"
19 #include "chrome/browser/extensions/extension_system.h"
18 #include "chrome/browser/extensions/extension_tab_util.h" 20 #include "chrome/browser/extensions/extension_tab_util.h"
21 #include "chrome/browser/extensions/lazy_background_task_queue.h"
19 #include "chrome/browser/prefs/scoped_user_pref_update.h" 22 #include "chrome/browser/prefs/scoped_user_pref_update.h"
20 #include "chrome/browser/profiles/profile.h" 23 #include "chrome/browser/profiles/profile.h"
21 #include "chrome/browser/ui/browser.h" 24 #include "chrome/browser/ui/browser.h"
22 #include "chrome/common/extensions/file_browser_handler.h" 25 #include "chrome/common/extensions/file_browser_handler.h"
23 #include "chrome/common/pref_names.h" 26 #include "chrome/common/pref_names.h"
24 #include "content/public/browser/browser_thread.h" 27 #include "content/public/browser/browser_thread.h"
25 #include "content/public/browser/child_process_security_policy.h" 28 #include "content/public/browser/child_process_security_policy.h"
26 #include "content/public/browser/render_process_host.h" 29 #include "content/public/browser/render_process_host.h"
27 #include "content/public/browser/site_instance.h" 30 #include "content/public/browser/site_instance.h"
28 #include "content/public/browser/web_contents.h" 31 #include "content/public/browser/web_contents.h"
(...skipping 413 matching lines...) Expand 10 before | Expand all | Expand 10 after
442 // If the file is under gdata mount point, there is no actual file to be 445 // If the file is under gdata mount point, there is no actual file to be
443 // found on the final_file_path. 446 // found on the final_file_path.
444 if (!is_gdata_file) { 447 if (!is_gdata_file) {
445 if (!file_util::PathExists(final_file_path) || 448 if (!file_util::PathExists(final_file_path) ||
446 file_util::IsLink(final_file_path) || 449 file_util::IsLink(final_file_path) ||
447 !file_util::GetFileInfo(final_file_path, &file_info)) { 450 !file_util::GetFileInfo(final_file_path, &file_info)) {
448 return false; 451 return false;
449 } 452 }
450 } 453 }
451 454
452 ChildProcessSecurityPolicy::GetInstance()->GrantPermissionsForFile(
453 handler_pid_,
454 final_file_path,
455 GetAccessPermissionsForHandler(handler_extension_.get(), action_id_));
456
457 // Grant access to this particular file to target extension. This will 455 // Grant access to this particular file to target extension. This will
458 // ensure that the target extension can access only this FS entry and 456 // ensure that the target extension can access only this FS entry and
459 // prevent from traversing FS hierarchy upward. 457 // prevent from traversing FS hierarchy upward.
460 external_provider->GrantFileAccessToExtension(handler_extension_->id(), 458 external_provider->GrantFileAccessToExtension(handler_extension_->id(),
461 virtual_path); 459 virtual_path);
462 460
463 // Output values. 461 // Output values.
464 GURL target_origin_url(Extension::GetBaseURLFromExtensionId( 462 GURL target_origin_url(Extension::GetBaseURLFromExtensionId(
465 handler_extension_->id())); 463 handler_extension_->id()));
466 GURL base_url = fileapi::GetFileSystemRootURI(target_origin_url, 464 GURL base_url = fileapi::GetFileSystemRootURI(target_origin_url,
(...skipping 17 matching lines...) Expand all
484 DISALLOW_COPY_AND_ASSIGN(ExecuteTasksFileSystemCallbackDispatcher); 482 DISALLOW_COPY_AND_ASSIGN(ExecuteTasksFileSystemCallbackDispatcher);
485 }; 483 };
486 484
487 FileTaskExecutor::FileTaskExecutor(Profile* profile, 485 FileTaskExecutor::FileTaskExecutor(Profile* profile,
488 const GURL source_url, 486 const GURL source_url,
489 const std::string& extension_id, 487 const std::string& extension_id,
490 const std::string& action_id) 488 const std::string& action_id)
491 : profile_(profile), 489 : profile_(profile),
492 source_url_(source_url), 490 source_url_(source_url),
493 extension_id_(extension_id), 491 extension_id_(extension_id),
494 action_id_(action_id) 492 action_id_(action_id) {
495 {} 493 }
496 494
497 FileTaskExecutor::~FileTaskExecutor() {} 495 FileTaskExecutor::~FileTaskExecutor() {}
498 496
499 bool FileTaskExecutor::Execute(const std::vector<GURL>& file_urls) { 497 bool FileTaskExecutor::Execute(const std::vector<GURL>& file_urls) {
500 ExtensionService* service = profile_->GetExtensionService(); 498 ExtensionService* service = profile_->GetExtensionService();
501 if (!service) 499 if (!service)
502 return false; 500 return false;
503 501
504 scoped_refptr<const Extension> handler = 502 scoped_refptr<const Extension> handler =
505 service->GetExtensionById(extension_id_, false); 503 service->GetExtensionById(extension_id_, false);
506 504
507 if (!handler.get()) 505 if (!handler.get())
508 return false; 506 return false;
509 507
510 int handler_pid = ExtractProcessFromExtensionId(handler->id(), profile_); 508 int handler_pid = ExtractProcessFromExtensionId(handler->id(), profile_);
511 if (handler_pid < 0) 509 if (handler_pid <= 0) {
512 return false; 510 if (!handler->has_lazy_background_page())
511 return false;
512 }
513 513
514 // Get local file system instance on file thread. 514 // Get local file system instance on file thread.
515 BrowserThread::PostTask( 515 BrowserThread::PostTask(
516 BrowserThread::FILE, FROM_HERE, 516 BrowserThread::FILE, FROM_HERE,
517 base::Bind( 517 base::Bind(
518 &FileTaskExecutor::RequestFileEntryOnFileThread, 518 &FileTaskExecutor::RequestFileEntryOnFileThread,
519 this, 519 this,
520 Extension::GetBaseURLFromExtensionId(handler->id()), 520 Extension::GetBaseURLFromExtensionId(handler->id()),
521 handler, 521 handler,
522 handler_pid, 522 handler_pid,
(...skipping 17 matching lines...) Expand all
540 handler, 540 handler,
541 handler_pid, 541 handler_pid,
542 action_id_, 542 action_id_,
543 file_urls)); 543 file_urls));
544 } 544 }
545 545
546 void FileTaskExecutor::ExecuteFailedOnUIThread() { 546 void FileTaskExecutor::ExecuteFailedOnUIThread() {
547 Done(false); 547 Done(false);
548 } 548 }
549 549
550 void FileTaskExecutor::SetupFileAccessPermissionsForGDataCache(
551 const FileDefinitionList& file_list,
552 int handler_pid) {
553 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
554
555 for (FileDefinitionList::const_iterator iter = file_list.begin();
556 iter != file_list.end();
557 ++iter) {
558 if (!gdata::util::IsUnderGDataMountPoint(iter->absolute_path))
559 continue;
560 gdata::util::SetPermissionsForGDataCacheFiles(profile_, handler_pid,
561 iter->absolute_path);
562 }
563 }
564
565 void FileTaskExecutor::ExecuteFileActionsOnUIThread( 550 void FileTaskExecutor::ExecuteFileActionsOnUIThread(
566 const std::string& file_system_name, 551 const std::string& file_system_name,
567 const GURL& file_system_root, 552 const GURL& file_system_root,
568 const FileDefinitionList& file_list, 553 const FileDefinitionList& file_list,
569 int handler_pid) { 554 int handler_pid) {
570 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); 555 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
571 556
572 ExtensionService* service = profile_->GetExtensionService(); 557 ExtensionService* service = profile_->GetExtensionService();
573 if (!service) { 558 if (!service) {
574 Done(false); 559 Done(false);
575 return; 560 return;
576 } 561 }
577 562
578 const Extension* extension = service->GetExtensionById(extension_id_, false); 563 const Extension* extension = service->GetExtensionById(extension_id_, false);
579 if (!extension) { 564 if (!extension) {
580 Done(false); 565 Done(false);
581 return; 566 return;
582 } 567 }
583 568
569 InitHandlerHostFileAccessPermissions(file_list, extension, action_id_);
570
571 if (handler_pid > 0) {
572 SetupPermissionsAndDispatchEvent(file_system_name, file_system_root,
573 file_list, handler_pid, NULL);
574 } else {
575 // We have to wake the handler background page before we proceed.
576 extensions::LazyBackgroundTaskQueue* queue =
577 ExtensionSystem::Get(profile_)->lazy_background_task_queue();
578 if (!queue->ShouldEnqueueTask(profile_, extension)) {
579 Done(false);
580 return;
581 }
582 queue->AddPendingTask(
583 profile_, extension_id_,
584 base::Bind(&FileTaskExecutor::SetupPermissionsAndDispatchEvent, this,
585 file_system_name, file_system_root, file_list, handler_pid));
586 }
587 }
588
589 void FileTaskExecutor::SetupPermissionsAndDispatchEvent(
590 const std::string& file_system_name,
591 const GURL& file_system_root,
592 const FileDefinitionList& file_list,
593 int handler_pid_in,
594 ExtensionHost* host) {
595 int handler_pid = host ? host->render_process_host()->GetID() :
596 handler_pid_in;
597
598 if (handler_pid <= 0) {
599 Done(false);
600 return;
601 }
602
584 ExtensionEventRouter* event_router = profile_->GetExtensionEventRouter(); 603 ExtensionEventRouter* event_router = profile_->GetExtensionEventRouter();
585 if (!event_router) { 604 if (!event_router) {
586 Done(false); 605 Done(false);
587 return; 606 return;
588 } 607 }
589 608
590 SetupFileAccessPermissionsForGDataCache(file_list, handler_pid); 609 SetupHandlerHostFileAccessPermissions(handler_pid);
591 610
592 scoped_ptr<ListValue> event_args(new ListValue()); 611 scoped_ptr<ListValue> event_args(new ListValue());
593 event_args->Append(Value::CreateStringValue(action_id_)); 612 event_args->Append(Value::CreateStringValue(action_id_));
594 DictionaryValue* details = new DictionaryValue(); 613 DictionaryValue* details = new DictionaryValue();
595 event_args->Append(details); 614 event_args->Append(details);
596 // Get file definitions. These will be replaced with Entry instances by 615 // Get file definitions. These will be replaced with Entry instances by
597 // chromeHidden.Event.dispatchJSON() method from even_binding.js. 616 // chromeHidden.Event.dispatchJSON() method from even_binding.js.
598 ListValue* files_urls = new ListValue(); 617 ListValue* files_urls = new ListValue();
599 details->Set("entries", files_urls); 618 details->Set("entries", files_urls);
600 for (FileDefinitionList::const_iterator iter = file_list.begin(); 619 for (FileDefinitionList::const_iterator iter = file_list.begin();
(...skipping 15 matching lines...) Expand all
616 } 635 }
617 636
618 UpdateFileHandlerUsageStats(profile_, MakeTaskID(extension_id_, action_id_)); 637 UpdateFileHandlerUsageStats(profile_, MakeTaskID(extension_id_, action_id_));
619 638
620 std::string json_args; 639 std::string json_args;
621 base::JSONWriter::Write(event_args.get(), &json_args); 640 base::JSONWriter::Write(event_args.get(), &json_args);
622 event_router->DispatchEventToExtension( 641 event_router->DispatchEventToExtension(
623 extension_id_, std::string("fileBrowserHandler.onExecute"), 642 extension_id_, std::string("fileBrowserHandler.onExecute"),
624 json_args, profile_, 643 json_args, profile_,
625 GURL()); 644 GURL());
645
626 Done(true); 646 Done(true);
627 } 647 }
628 648
649 void FileTaskExecutor::InitHandlerHostFileAccessPermissions(
650 const FileDefinitionList& file_list,
651 const Extension* handler_extension,
652 const std::string& action_id) {
653 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
654
655 for (FileDefinitionList::const_iterator iter = file_list.begin();
656 iter != file_list.end();
657 ++iter) {
658 // Setup permission for file's absolute file.
659 handler_host_permissions_.push_back(std::make_pair(
660 iter->absolute_path,
661 GetAccessPermissionsForHandler(handler_extension, action_id)));
662
663 if (!gdata::util::IsUnderGDataMountPoint(iter->absolute_path))
664 continue;
665
666 // If the file is on gdata mount point, we'll have to give handler host
667 // permissions for file's gdata cache paths.
668 // This has to be called on UI thread.
669 gdata::util::InsertGDataCachePathsPermissions(profile_, iter->absolute_path,
670 &handler_host_permissions_);
671 }
672 }
673
674 void FileTaskExecutor::SetupHandlerHostFileAccessPermissions(int handler_pid) {
675 for (size_t i = 0; i < handler_host_permissions_.size(); i++) {
676 content::ChildProcessSecurityPolicy::GetInstance()->GrantPermissionsForFile(
677 handler_pid,
678 handler_host_permissions_[i].first,
679 handler_host_permissions_[i].second);
680 }
681
682 // We don't need this anymore.
683 handler_host_permissions_.clear();
684 }
685
629 } // namespace file_handler_util 686 } // namespace file_handler_util
630 687
OLDNEW
« no previous file with comments | « chrome/browser/chromeos/extensions/file_handler_util.h ('k') | chrome/browser/chromeos/gdata/gdata_util.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698