15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved. 25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be 35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file. 45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 52a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/browser/media_galleries/media_file_system_registry.h" 65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <set> 85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <vector> 95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/bind.h" 115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/callback.h" 122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "base/files/file_path.h" 132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "base/prefs/pref_service.h" 145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/stl_util.h" 155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/extensions/extension_service.h" 16effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch#include "chrome/browser/media_galleries/fileapi/media_file_system_backend.h" 173551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)#include "chrome/browser/media_galleries/fileapi/mtp_device_map_service.h" 18116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch#include "chrome/browser/media_galleries/gallery_watch_manager.h" 1990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include "chrome/browser/media_galleries/imported_media_gallery_registry.h" 202a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/browser/media_galleries/media_file_system_context.h" 2190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include "chrome/browser/media_galleries/media_galleries_dialog_controller.h" 2268043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)#include "chrome/browser/media_galleries/media_galleries_histograms.h" 232a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/browser/media_galleries/media_galleries_preferences_factory.h" 245d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "chrome/browser/media_galleries/media_scan_manager.h" 255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/profiles/profile.h" 265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/common/chrome_paths.h" 275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/common/extensions/extension_constants.h" 285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/common/pref_names.h" 295d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "components/storage_monitor/media_storage_util.h" 305d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "components/storage_monitor/storage_monitor.h" 315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/browser_thread.h" 323551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)#include "content/public/browser/navigation_details.h" 335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/render_process_host.h" 345d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "content/public/browser/render_process_host_observer.h" 355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/render_view_host.h" 365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/web_contents.h" 375d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "content/public/browser/web_contents_observer.h" 385d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "extensions/browser/extension_system.h" 39f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include "extensions/common/extension.h" 405d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "extensions/common/extension_set.h" 411320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "storage/browser/fileapi/external_mount_points.h" 421320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "storage/common/fileapi/file_system_mount_option.h" 431320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "storage/common/fileapi/file_system_types.h" 445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::BrowserThread; 465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::NavigationController; 475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::RenderProcessHost; 485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::WebContents; 4903b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles)using storage::ExternalMountPoints; 50a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)using storage_monitor::MediaStorageUtil; 51a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)using storage_monitor::StorageInfo; 52a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)using storage_monitor::StorageMonitor; 535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace { 555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)struct InvalidatedGalleriesInfo { 575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::set<ExtensionGalleriesHost*> extension_hosts; 585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::set<MediaGalleryPrefId> pref_ids; 595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 612a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// Tracks the liveness of multiple RenderProcessHosts that the caller is 625d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// interested in. Once all of the RPHs have closed or been destroyed a call 632a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// back informs the caller. 645d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)class RPHReferenceManager { 655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 662a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // |no_references_callback| is called when the last RenderViewHost reference 672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // goes away. RenderViewHost references are added through ReferenceFromRVH(). 685d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) explicit RPHReferenceManager(const base::Closure& no_references_callback); 695d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) virtual ~RPHReferenceManager(); 702a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 712a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Remove all references, but don't call |no_references_callback|. 725d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) void Reset() { STLDeleteValues(&observer_map_); } 732a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 742a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Returns true if there are no references; 755d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) bool empty() const { return observer_map_.empty(); } 762a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 772a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Adds a reference to the passed |rvh|. Calling this multiple times with 782a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // the same |rvh| is a no-op. 795d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) void ReferenceFromRVH(const content::RenderViewHost* rvh); 805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 825d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) class RPHWebContentsObserver : public content::WebContentsObserver { 835d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) public: 845d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) RPHWebContentsObserver(RPHReferenceManager* manager, 855d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) WebContents* web_contents); 865d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 875d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) private: 885d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // content::WebContentsObserver 89010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles) virtual void WebContentsDestroyed() OVERRIDE; 905d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) virtual void NavigationEntryCommitted( 915d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) const content::LoadCommittedDetails& load_details) OVERRIDE; 925d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 935d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) RPHReferenceManager* manager_; 942a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) }; 955d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 965d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) class RPHObserver : public content::RenderProcessHostObserver { 975d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) public: 985d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) RPHObserver(RPHReferenceManager* manager, RenderProcessHost* host); 995d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) virtual ~RPHObserver(); 1005d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1015d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) void AddWebContentsObserver(WebContents* web_contents); 1025d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) void RemoveWebContentsObserver(WebContents* web_contents); 1035d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) bool HasWebContentsObservers() { 1045d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) return observed_web_contentses_.size() > 0; 1052a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1075d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) private: 1085d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) virtual void RenderProcessHostDestroyed(RenderProcessHost* host) OVERRIDE; 1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1105d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) RPHReferenceManager* manager_; 1115d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) RenderProcessHost* host_; 1125d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) typedef std::map<WebContents*, RPHWebContentsObserver*> WCObserverMap; 1135d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) WCObserverMap observed_web_contentses_; 1145d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) }; 1155d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) typedef std::map<const RenderProcessHost*, RPHObserver*> RPHObserverMap; 1165d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1175d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Handlers for observed events. 1185d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) void OnRenderProcessHostDestroyed(RenderProcessHost* rph); 1195d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) void OnWebContentsDestroyedOrNavigated(WebContents* contents); 1202a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 1212a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // A callback to call when the last RVH reference goes away. 1225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::Closure no_references_callback_; 1235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // The set of render processes and web contents that may have references to 1252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // the file system ids this instance manages. 1265d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) RPHObserverMap observer_map_; 1275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 1285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1295d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)RPHReferenceManager::RPHReferenceManager( 1305d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) const base::Closure& no_references_callback) 1315d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) : no_references_callback_(no_references_callback) { 1325d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} 1335d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1345d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)RPHReferenceManager::~RPHReferenceManager() { 1355d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) Reset(); 1365d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} 1375d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1385d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)void RPHReferenceManager::ReferenceFromRVH(const content::RenderViewHost* rvh) { 1395d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) WebContents* contents = WebContents::FromRenderViewHost(rvh); 1405d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) RenderProcessHost* rph = contents->GetRenderProcessHost(); 1415d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) RPHObserver* state = NULL; 1425d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) if (!ContainsKey(observer_map_, rph)) { 1435d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) state = new RPHObserver(this, rph); 1445d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) observer_map_[rph] = state; 1455d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) } else { 1465d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) state = observer_map_[rph]; 1475d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) } 1485d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1495d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) state->AddWebContentsObserver(contents); 1505d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} 1515d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1525d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)RPHReferenceManager::RPHWebContentsObserver::RPHWebContentsObserver( 1535d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) RPHReferenceManager* manager, 1545d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) WebContents* web_contents) 1555d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) : content::WebContentsObserver(web_contents), 1565d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) manager_(manager) { 1575d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} 1585d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 159010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)void RPHReferenceManager::RPHWebContentsObserver::WebContentsDestroyed() { 160010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles) manager_->OnWebContentsDestroyedOrNavigated(web_contents()); 1615d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} 1625d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1635d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)void RPHReferenceManager::RPHWebContentsObserver::NavigationEntryCommitted( 1645d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) const content::LoadCommittedDetails& load_details) { 1655d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) if (load_details.is_in_page) 1665d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) return; 1675d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1685d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) manager_->OnWebContentsDestroyedOrNavigated(web_contents()); 1695d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} 1705d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1715d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)RPHReferenceManager::RPHObserver::RPHObserver( 1725d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) RPHReferenceManager* manager, RenderProcessHost* host) 1735d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) : manager_(manager), 1745d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) host_(host) { 1755d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) host->AddObserver(this); 1765d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} 1775d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1785d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)RPHReferenceManager::RPHObserver::~RPHObserver() { 1795d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) STLDeleteValues(&observed_web_contentses_); 1805d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) if (host_) 1815d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) host_->RemoveObserver(this); 1825d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} 1835d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1845d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)void RPHReferenceManager::RPHObserver::AddWebContentsObserver( 1855d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) WebContents* web_contents) { 1865d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) if (ContainsKey(observed_web_contentses_, web_contents)) 1875d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) return; 1885d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1895d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) RPHWebContentsObserver* observer = 1905d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) new RPHWebContentsObserver(manager_, web_contents); 1915d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) observed_web_contentses_[web_contents] = observer; 1925d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} 1935d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1945d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)void RPHReferenceManager::RPHObserver::RemoveWebContentsObserver( 1955d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) WebContents* web_contents) { 1965d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) WCObserverMap::iterator wco_iter = 1975d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) observed_web_contentses_.find(web_contents); 1985d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) DCHECK(wco_iter != observed_web_contentses_.end()); 1995d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) delete wco_iter->second; 2005d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) observed_web_contentses_.erase(wco_iter); 2015d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} 2025d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 2035d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)void RPHReferenceManager::RPHObserver::RenderProcessHostDestroyed( 2045d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) RenderProcessHost* host) { 2055d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) host_ = NULL; 2065d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) manager_->OnRenderProcessHostDestroyed(host); 2075d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} 2085d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 2095d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)void RPHReferenceManager::OnRenderProcessHostDestroyed( 2105d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) RenderProcessHost* rph) { 2115d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) RPHObserverMap::iterator rph_info = observer_map_.find(rph); 2125d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // This could be a potential problem if the RPH is navigated to a page on the 2135d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // same renderer (triggering OnWebContentsDestroyedOrNavigated()) and then the 2145d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // renderer crashes. 2155d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) if (rph_info == observer_map_.end()) { 2165d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) NOTREACHED(); 2175d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) return; 2185d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) } 2195d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) delete rph_info->second; 2205d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) observer_map_.erase(rph_info); 2215d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) if (observer_map_.empty()) 2225d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) no_references_callback_.Run(); 2235d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} 2245d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 2255d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)void RPHReferenceManager::OnWebContentsDestroyedOrNavigated( 2265d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) WebContents* contents) { 2275d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) RenderProcessHost* rph = contents->GetRenderProcessHost(); 2285d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) RPHObserverMap::iterator rph_info = observer_map_.find(rph); 2295d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) DCHECK(rph_info != observer_map_.end()); 2305d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 2315d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) rph_info->second->RemoveWebContentsObserver(contents); 2325d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) if (!rph_info->second->HasWebContentsObservers()) 2335d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) OnRenderProcessHostDestroyed(rph); 2345d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} 2355d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 2364e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)} // namespace 2374e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) 238a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)MediaFileSystemInfo::MediaFileSystemInfo(const base::string16& fs_name, 2394e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) const base::FilePath& fs_path, 2404e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) const std::string& filesystem_id, 2414e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) MediaGalleryPrefId pref_id, 2424e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) const std::string& transient_device_id, 2434e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) bool removable, 2444e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) bool media_device) 2454e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) : name(fs_name), 2464e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) path(fs_path), 2474e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) fsid(filesystem_id), 2484e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) pref_id(pref_id), 2494e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) transient_device_id(transient_device_id), 2504e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) removable(removable), 2514e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) media_device(media_device) { 2524e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)} 2534e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) 2544e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)MediaFileSystemInfo::MediaFileSystemInfo() {} 2554e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)MediaFileSystemInfo::~MediaFileSystemInfo() {} 2564e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) 2575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// The main owner of this class is 2585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// |MediaFileSystemRegistry::extension_hosts_map_|, but a callback may 2595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// temporarily hold a reference. 2605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class ExtensionGalleriesHost 2612a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) : public base::RefCountedThreadSafe<ExtensionGalleriesHost> { 2625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 2635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // |no_references_callback| is called when the last RenderViewHost reference 2645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // goes away. RenderViewHost references are added through ReferenceFromRVH(). 2655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ExtensionGalleriesHost(MediaFileSystemContext* file_system_context, 266effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const base::FilePath& profile_path, 267effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const std::string& extension_id, 2685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const base::Closure& no_references_callback) 2695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : file_system_context_(file_system_context), 270effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch profile_path_(profile_path), 271effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch extension_id_(extension_id), 2722a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) no_references_callback_(no_references_callback), 2732a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rph_refs_(base::Bind(&ExtensionGalleriesHost::CleanUp, 2742a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::Unretained(this))) { 2755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // For each gallery in the list of permitted |galleries|, checks if the 278effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch // device is attached and if so looks up or creates a file system name and 2795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // passes the information needed for the renderer to create those file 2805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // system objects to the |callback|. 2815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void GetMediaFileSystems(const MediaGalleryPrefIdSet& galleries, 2825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const MediaGalleriesPrefInfoMap& galleries_info, 2835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const MediaFileSystemsCallback& callback) { 284116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch DCHECK_CURRENTLY_ON(BrowserThread::UI); 285116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch 2865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Extract all the device ids so we can make sure they are attached. 2875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) MediaStorageUtil::DeviceIdSet* device_ids = 2885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) new MediaStorageUtil::DeviceIdSet; 2895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) for (std::set<MediaGalleryPrefId>::const_iterator id = galleries.begin(); 2905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) id != galleries.end(); 2915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ++id) { 2925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) device_ids->insert(galleries_info.find(*id)->second.device_id); 2935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) MediaStorageUtil::FilterAttachedDevices(device_ids, base::Bind( 2955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &ExtensionGalleriesHost::GetMediaFileSystemsForAttachedDevices, this, 2965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::Owned(device_ids), galleries, galleries_info, callback)); 2975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 299effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch // Checks if |gallery| is attached and if so, registers the file system and 300effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch // then calls |callback| with the result. 301effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch void RegisterMediaFileSystem( 302effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const MediaGalleryPrefInfo& gallery, 303effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const base::Callback<void(base::File::Error result)>& callback) { 304effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch // Extract all the device ids so we can make sure they are attached. 305effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch MediaStorageUtil::DeviceIdSet* device_ids = 306effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch new MediaStorageUtil::DeviceIdSet; 307effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch device_ids->insert(gallery.device_id); 308effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch MediaStorageUtil::FilterAttachedDevices(device_ids, base::Bind( 309effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch &ExtensionGalleriesHost::RegisterAttachedMediaFileSystem, this, 310effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch base::Owned(device_ids), gallery, callback)); 311effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch } 312effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch 3135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Revoke the file system for |id| if this extension has created one for |id|. 3145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void RevokeGalleryByPrefId(MediaGalleryPrefId id) { 3155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PrefIdFsInfoMap::iterator gallery = pref_id_map_.find(id); 3165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (gallery == pref_id_map_.end()) 3175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 3185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) file_system_context_->RevokeFileSystem(gallery->second.fsid); 3205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pref_id_map_.erase(gallery); 3215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3222a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (pref_id_map_.empty()) { 3232a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rph_refs_.Reset(); 3242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) CleanUp(); 3252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 3265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Indicate that the passed |rvh| will reference the file system ids created 3292a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // by this class. 3305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void ReferenceFromRVH(const content::RenderViewHost* rvh) { 3312a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rph_refs_.ReferenceFromRVH(rvh); 3325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 3352a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) typedef std::map<MediaGalleryPrefId, MediaFileSystemInfo> PrefIdFsInfoMap; 3365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Private destructor and friend declaration for ref counted implementation. 3385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) friend class base::RefCountedThreadSafe<ExtensionGalleriesHost>; 3395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual ~ExtensionGalleriesHost() { 3415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(rph_refs_.empty()); 3425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(pref_id_map_.empty()); 3435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void GetMediaFileSystemsForAttachedDevices( 3465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const MediaStorageUtil::DeviceIdSet* attached_devices, 3475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const MediaGalleryPrefIdSet& galleries, 3485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const MediaGalleriesPrefInfoMap& galleries_info, 3495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const MediaFileSystemsCallback& callback) { 3505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::vector<MediaFileSystemInfo> result; 3515d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 3525d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) if (rph_refs_.empty()) { 3535d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // We're actually in the middle of shutdown, and Filter...() lagging 3545d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // which can invoke this method interleaved in the destruction callback 3555d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // sequence and re-populate pref_id_map_. 3565d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) callback.Run(result); 3575d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) return; 3585d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) } 3595d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 3605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) for (std::set<MediaGalleryPrefId>::const_iterator pref_id_it = 3615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) galleries.begin(); 3625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pref_id_it != galleries.end(); 3635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ++pref_id_it) { 3645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const MediaGalleryPrefId& pref_id = *pref_id_it; 3655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const MediaGalleryPrefInfo& gallery_info = 3665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) galleries_info.find(pref_id)->second; 3675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const std::string& device_id = gallery_info.device_id; 3685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!ContainsKey(*attached_devices, device_id)) 3695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) continue; 3705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PrefIdFsInfoMap::const_iterator existing_info = 3725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pref_id_map_.find(pref_id); 3735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (existing_info != pref_id_map_.end()) { 3745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) result.push_back(existing_info->second); 3755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) continue; 3765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3782a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::FilePath path = gallery_info.AbsolutePath(); 3792a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (!MediaStorageUtil::CanCreateFileSystem(device_id, path)) 3805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) continue; 3815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 382effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch std::string fs_name = MediaFileSystemBackend::ConstructMountName( 383effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch profile_path_, extension_id_, pref_id); 384effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch if (!file_system_context_->RegisterFileSystem(device_id, fs_name, path)) 385868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) continue; 3865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) MediaFileSystemInfo new_entry( 388eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch gallery_info.GetGalleryDisplayName(), 389effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch file_system_context_->GetRegisteredPath(fs_name), 390effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch fs_name, 3912a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) pref_id, 3922a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) GetTransientIdForRemovableDeviceId(device_id), 39390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) StorageInfo::IsRemovableDevice(device_id), 39490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) StorageInfo::IsMediaDevice(device_id)); 3955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) result.push_back(new_entry); 3965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pref_id_map_[pref_id] = new_entry; 3975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3992a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (result.size() == 0) { 4002a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rph_refs_.Reset(); 4012a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) CleanUp(); 4022a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 4035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4045d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) DCHECK_EQ(pref_id_map_.size(), result.size()); 4055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) callback.Run(result); 4065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 4075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 408effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch void RegisterAttachedMediaFileSystem( 409effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const MediaStorageUtil::DeviceIdSet* attached_device, 410effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const MediaGalleryPrefInfo& gallery, 411effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const base::Callback<void(base::File::Error result)>& callback) { 412effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch base::File::Error result = base::File::FILE_ERROR_NOT_FOUND; 413effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch 414effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch // If rph_refs is empty then we're actually in the middle of shutdown, and 415effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch // Filter...() lagging which can invoke this method interleaved in the 416effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch // destruction callback sequence and re-populate pref_id_map_. 417effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch if (!attached_device->empty() && !rph_refs_.empty()) { 418effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch std::string fs_name = MediaFileSystemBackend::ConstructMountName( 419effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch profile_path_, extension_id_, gallery.pref_id); 420effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch base::FilePath path = gallery.AbsolutePath(); 421effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const std::string& device_id = gallery.device_id; 422effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch 423effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch if (ContainsKey(pref_id_map_, gallery.pref_id)) { 424effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch result = base::File::FILE_OK; 425effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch } else if (MediaStorageUtil::CanCreateFileSystem(device_id, path) && 426effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch file_system_context_->RegisterFileSystem(device_id, fs_name, 427effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch path)) { 428effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch result = base::File::FILE_OK; 429effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch pref_id_map_[gallery.pref_id] = MediaFileSystemInfo( 430effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch gallery.GetGalleryDisplayName(), 431effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch file_system_context_->GetRegisteredPath(fs_name), 432effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch fs_name, 433effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch gallery.pref_id, 434effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch GetTransientIdForRemovableDeviceId(device_id), 435effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch StorageInfo::IsRemovableDevice(device_id), 436effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch StorageInfo::IsMediaDevice(device_id)); 437effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch } 438effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch } 439effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch 440effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch if (pref_id_map_.empty()) { 441effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch rph_refs_.Reset(); 442effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch CleanUp(); 443effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch } 444effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch BrowserThread::PostTask(BrowserThread::IO, FROM_HERE, 445effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch base::Bind(callback, result)); 446effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch } 447effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch 4482a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) std::string GetTransientIdForRemovableDeviceId(const std::string& device_id) { 44990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) if (!StorageInfo::IsRemovableDevice(device_id)) 4502a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) return std::string(); 4515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 452868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) return StorageMonitor::GetInstance()->GetTransientIdForDeviceId(device_id); 4532a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 4545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4552a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) void CleanUp() { 4562a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) DCHECK(rph_refs_.empty()); 4572a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) for (PrefIdFsInfoMap::const_iterator it = pref_id_map_.begin(); 4582a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) it != pref_id_map_.end(); 4592a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) ++it) { 4602a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) file_system_context_->RevokeFileSystem(it->second.fsid); 4612a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 4622a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) pref_id_map_.clear(); 4635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) no_references_callback_.Run(); 4655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 4665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // MediaFileSystemRegistry owns |this| and |file_system_context_|, so it's 4685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // safe to store a raw pointer. 4695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) MediaFileSystemContext* file_system_context_; 4705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 471effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch // Path for the active profile. 472effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const base::FilePath profile_path_; 473effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch 474effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch // Id of the extension this host belongs to. 475effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const std::string extension_id_; 476effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch 4775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // A callback to call when the last RVH reference goes away. 4785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::Closure no_references_callback_; 4795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // A map from the gallery preferences id to the file system information. 4815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PrefIdFsInfoMap pref_id_map_; 4825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // The set of render processes and web contents that may have references to 4845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // the file system ids this instance manages. 4852a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) RPHReferenceManager rph_refs_; 4865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(ExtensionGalleriesHost); 4885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 4895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/****************** 4915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Public methods 4925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ******************/ 4935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void MediaFileSystemRegistry::GetMediaFileSystemsForExtension( 4955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const content::RenderViewHost* rvh, 4965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const extensions::Extension* extension, 4975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const MediaFileSystemsCallback& callback) { 498116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch // TODO(tommycli): Change to DCHECK after fixing http://crbug.com/374330. 499116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch CHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); 5005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Profile* profile = 5025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Profile::FromBrowserContext(rvh->GetProcess()->GetBrowserContext()); 5035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) MediaGalleriesPreferences* preferences = GetPreferences(profile); 5045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) MediaGalleryPrefIdSet galleries = 5055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) preferences->GalleriesForExtension(*extension); 5065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (galleries.empty()) { 5085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) callback.Run(std::vector<MediaFileSystemInfo>()); 5095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 5105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 5115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ExtensionGalleriesHost* extension_host = 513effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch GetExtensionGalleryHost(profile, preferences, extension->id()); 514effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch 5155d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // This must come before the GetMediaFileSystems call to make sure the 5165d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // RVH of the context is referenced before the filesystems are retrieved. 5175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) extension_host->ReferenceFromRVH(rvh); 5185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) extension_host->GetMediaFileSystems(galleries, preferences->known_galleries(), 5205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) callback); 5215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 523effb81e5f8246d0db0270817048dc992db66e9fbBen Murdochvoid MediaFileSystemRegistry::RegisterMediaFileSystemForExtension( 524effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const content::RenderViewHost* rvh, 525effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const extensions::Extension* extension, 526effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch MediaGalleryPrefId pref_id, 527effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const base::Callback<void(base::File::Error result)>& callback) { 528e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK_CURRENTLY_ON(BrowserThread::UI); 529effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch DCHECK_NE(kInvalidMediaGalleryPrefId, pref_id); 530effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch 531effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch Profile* profile = 532effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch Profile::FromBrowserContext(rvh->GetProcess()->GetBrowserContext()); 533effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch MediaGalleriesPreferences* preferences = GetPreferences(profile); 534effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch MediaGalleriesPrefInfoMap::const_iterator gallery = 535effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch preferences->known_galleries().find(pref_id); 536effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch MediaGalleryPrefIdSet permitted_galleries = 537effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch preferences->GalleriesForExtension(*extension); 538effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch 539effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch if (gallery == preferences->known_galleries().end() || 540effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch !ContainsKey(permitted_galleries, pref_id)) { 541effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch BrowserThread::PostTask( 542effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch BrowserThread::IO, FROM_HERE, 543effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch base::Bind(callback, base::File::FILE_ERROR_NOT_FOUND)); 544effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch return; 545effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch } 546effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch 547effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch ExtensionGalleriesHost* extension_host = 548effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch GetExtensionGalleryHost(profile, preferences, extension->id()); 549effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch 550effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch // This must come before the GetMediaFileSystems call to make sure the 551effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch // RVH of the context is referenced before the filesystems are retrieved. 552effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch extension_host->ReferenceFromRVH(rvh); 553effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch 554effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch extension_host->RegisterMediaFileSystem(gallery->second, callback); 555effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch} 556effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch 5575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)MediaGalleriesPreferences* MediaFileSystemRegistry::GetPreferences( 5585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Profile* profile) { 5594e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) // Create an empty ExtensionHostMap for this profile on first initialization. 560a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles) if (!ContainsKey(extension_hosts_map_, profile)) { 5614e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) extension_hosts_map_[profile] = ExtensionHostMap(); 562a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles) media_galleries::UsageCount(media_galleries::PROFILES_WITH_USAGE); 563a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles) } 5642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 5654e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) return MediaGalleriesPreferencesFactory::GetForProfile(profile); 5665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5685d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)MediaScanManager* MediaFileSystemRegistry::media_scan_manager() { 5695d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) if (!media_scan_manager_) 5705d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) media_scan_manager_.reset(new MediaScanManager); 5715d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) return media_scan_manager_.get(); 5725d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} 5735d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 574116680a4aac90f2aa7413d9095a592090648e557Ben MurdochGalleryWatchManager* MediaFileSystemRegistry::gallery_watch_manager() { 575116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch if (!gallery_watch_manager_) 576116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch gallery_watch_manager_.reset(new GalleryWatchManager); 577116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch return gallery_watch_manager_.get(); 578116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch} 579116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch 5805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void MediaFileSystemRegistry::OnRemovableStorageDetached( 5812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const StorageInfo& info) { 582e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK_CURRENTLY_ON(BrowserThread::UI); 5835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Since revoking a gallery in the ExtensionGalleriesHost may cause it 5855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // to be removed from the map and therefore invalidate any iterator pointing 5865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // to it, this code first copies all the invalid gallery ids and the 5875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // extension hosts in which they may appear (per profile) and revoked it in 5885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // a second step. 5895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::vector<InvalidatedGalleriesInfo> invalid_galleries_info; 5905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) for (ExtensionGalleriesHostMap::iterator profile_it = 5925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) extension_hosts_map_.begin(); 5935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) profile_it != extension_hosts_map_.end(); 5945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ++profile_it) { 5955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) MediaGalleriesPreferences* preferences = GetPreferences(profile_it->first); 5964e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) // If |preferences| is not yet initialized, it won't contain any galleries. 5974e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) if (!preferences->IsInitialized()) 5984e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) continue; 5994e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) 6005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) InvalidatedGalleriesInfo invalid_galleries_in_profile; 6015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) invalid_galleries_in_profile.pref_ids = 60290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) preferences->LookUpGalleriesByDeviceId(info.device_id()); 6035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) for (ExtensionHostMap::const_iterator extension_host_it = 6055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) profile_it->second.begin(); 6065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) extension_host_it != profile_it->second.end(); 6075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ++extension_host_it) { 6085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) invalid_galleries_in_profile.extension_hosts.insert( 6095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) extension_host_it->second.get()); 6105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 6115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) invalid_galleries_info.push_back(invalid_galleries_in_profile); 6135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 6145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) for (size_t i = 0; i < invalid_galleries_info.size(); i++) { 6165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) for (std::set<ExtensionGalleriesHost*>::const_iterator extension_host_it = 6175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) invalid_galleries_info[i].extension_hosts.begin(); 6185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) extension_host_it != invalid_galleries_info[i].extension_hosts.end(); 6195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ++extension_host_it) { 6205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) for (std::set<MediaGalleryPrefId>::const_iterator pref_id_it = 6215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) invalid_galleries_info[i].pref_ids.begin(); 6225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pref_id_it != invalid_galleries_info[i].pref_ids.end(); 6235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ++pref_id_it) { 6245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) (*extension_host_it)->RevokeGalleryByPrefId(*pref_id_it); 6255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 6265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 6275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 6285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 6295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/****************** 6315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Private methods 6325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ******************/ 6335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class MediaFileSystemRegistry::MediaFileSystemContextImpl 6355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : public MediaFileSystemContext { 6365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 637effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch MediaFileSystemContextImpl() {} 6385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual ~MediaFileSystemContextImpl() {} 6395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 640effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch virtual bool RegisterFileSystem(const std::string& device_id, 641effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const std::string& fs_name, 642effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const base::FilePath& path) OVERRIDE { 6431e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) if (StorageInfo::IsMassStorageDevice(device_id)) { 644effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch return RegisterFileSystemForMassStorage(device_id, fs_name, path); 6451e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) } else { 646effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch return RegisterFileSystemForMTPDevice(device_id, fs_name, path); 6471e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) } 6481e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) } 6491e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) 650effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch virtual void RevokeFileSystem(const std::string& fs_name) OVERRIDE { 6511e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) ImportedMediaGalleryRegistry* imported_registry = 6521e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) ImportedMediaGalleryRegistry::GetInstance(); 653effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch if (imported_registry->RevokeImportedFilesystemOnUIThread(fs_name)) 6541e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) return; 6551e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) 656effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch ExternalMountPoints::GetSystemInstance()->RevokeFileSystem(fs_name); 6571e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) 658effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch BrowserThread::PostTask(BrowserThread::IO, FROM_HERE, base::Bind( 659effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch &MTPDeviceMapService::RevokeMTPFileSystem, 660effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch base::Unretained(MTPDeviceMapService::GetInstance()), 661effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch fs_name)); 662effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch } 663effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch 664effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch virtual base::FilePath GetRegisteredPath( 665effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const std::string& fs_name) const OVERRIDE { 666effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch base::FilePath result; 667effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch if (!ExternalMountPoints::GetSystemInstance()->GetRegisteredPath(fs_name, 668effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch &result)) { 669effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch return base::FilePath(); 670effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch } 671effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch return result; 6721e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) } 6731e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) 6741e9bf3e0803691d0a228da41fc608347b6db4340Torne (Richard Coles) private: 6755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Registers and returns the file system id for the mass storage device 6765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // specified by |device_id| and |path|. 677effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch bool RegisterFileSystemForMassStorage(const std::string& device_id, 678effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const std::string& fs_name, 679effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const base::FilePath& path) { 680e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK_CURRENTLY_ON(BrowserThread::UI); 68190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) DCHECK(StorageInfo::IsMassStorageDevice(device_id)); 6825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Sanity checks for |path|. 6845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CHECK(path.IsAbsolute()); 6855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CHECK(!path.ReferencesParent()); 68690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) 6874e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) // TODO(gbillock): refactor ImportedMediaGalleryRegistry to delegate this 6884e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) // call tree, probably by having it figure out by device id what 6894e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) // registration is needed, or having per-device-type handlers at the 6904e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) // next higher level. 691effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch bool result = false; 69290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) if (StorageInfo::IsITunesDevice(device_id)) { 693effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch ImportedMediaGalleryRegistry* registry = 694868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) ImportedMediaGalleryRegistry::GetInstance(); 695effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch result = registry->RegisterITunesFilesystemOnUIThread(fs_name, path); 69690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) } else if (StorageInfo::IsPicasaDevice(device_id)) { 697effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch ImportedMediaGalleryRegistry* registry = 698868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) ImportedMediaGalleryRegistry::GetInstance(); 699effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch result = registry->RegisterPicasaFilesystemOnUIThread(fs_name, path); 7004e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) } else if (StorageInfo::IsIPhotoDevice(device_id)) { 701effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch ImportedMediaGalleryRegistry* registry = 7024e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles) ImportedMediaGalleryRegistry::GetInstance(); 703effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch result = registry->RegisterIPhotoFilesystemOnUIThread(fs_name, path); 70490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) } else { 705effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch result = ExternalMountPoints::GetSystemInstance()->RegisterFileSystem( 70603b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) fs_name, 70703b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) storage::kFileSystemTypeNativeMedia, 70803b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) storage::FileSystemMountOption(), 70903b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) path); 71090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) } 711effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch return result; 7125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 7135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 714effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch bool RegisterFileSystemForMTPDevice(const std::string& device_id, 715effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const std::string fs_name, 716effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const base::FilePath& path) { 717e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK_CURRENTLY_ON(BrowserThread::UI); 71890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) DCHECK(!StorageInfo::IsMassStorageDevice(device_id)); 7195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Sanity checks for |path|. 7212a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) CHECK(MediaStorageUtil::CanCreateFileSystem(device_id, path)); 722effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch bool result = ExternalMountPoints::GetSystemInstance()->RegisterFileSystem( 72303b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) fs_name, 72403b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) storage::kFileSystemTypeDeviceMedia, 72503b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) storage::FileSystemMountOption(), 72603b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) path); 727effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch CHECK(result); 728effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch BrowserThread::PostTask(BrowserThread::IO, FROM_HERE, base::Bind( 729effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch &MTPDeviceMapService::RegisterMTPFileSystem, 730effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch base::Unretained(MTPDeviceMapService::GetInstance()), 731effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch path.value(), fs_name)); 732effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch return result; 7335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 7345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(MediaFileSystemContextImpl); 7365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 7375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7384e180b6a0b4720a9b8e9e959a882386f690f08ffTorne (Richard Coles)// Constructor in 'private' section because depends on private class definition. 7395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)MediaFileSystemRegistry::MediaFileSystemRegistry() 740effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch : file_system_context_(new MediaFileSystemContextImpl) { 741868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) StorageMonitor::GetInstance()->AddObserver(this); 7425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 7435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)MediaFileSystemRegistry::~MediaFileSystemRegistry() { 745868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // TODO(gbillock): This is needed because the unit test uses the 746868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // g_browser_process registry. We should create one in the unit test, 747868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) // and then can remove this. 748868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) if (StorageMonitor::GetInstance()) 749868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) StorageMonitor::GetInstance()->RemoveObserver(this); 7505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 7515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 752d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)void MediaFileSystemRegistry::OnPermissionRemoved( 753d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) MediaGalleriesPreferences* prefs, 754d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) const std::string& extension_id, 755d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) MediaGalleryPrefId pref_id) { 756d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) Profile* profile = prefs->profile(); 757d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) ExtensionGalleriesHostMap::const_iterator host_map_it = 758d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) extension_hosts_map_.find(profile); 759d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) DCHECK(host_map_it != extension_hosts_map_.end()); 760d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) const ExtensionHostMap& extension_host_map = host_map_it->second; 761d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) ExtensionHostMap::const_iterator gallery_host_it = 762d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) extension_host_map.find(extension_id); 763d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) if (gallery_host_it == extension_host_map.end()) 764d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) return; 765d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) gallery_host_it->second->RevokeGalleryByPrefId(pref_id); 766d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)} 7675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 768d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)void MediaFileSystemRegistry::OnGalleryRemoved( 769d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) MediaGalleriesPreferences* prefs, 770d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) MediaGalleryPrefId pref_id) { 771d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) Profile* profile = prefs->profile(); 7725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Get the Extensions, MediaGalleriesPreferences and ExtensionHostMap for 7735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // |profile|. 7745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const ExtensionService* extension_service = 7755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) extensions::ExtensionSystem::Get(profile)->extension_service(); 7765d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) const extensions::ExtensionSet* extensions_set = 7775d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) extension_service->extensions(); 7785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ExtensionGalleriesHostMap::const_iterator host_map_it = 7795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) extension_hosts_map_.find(profile); 7805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(host_map_it != extension_hosts_map_.end()); 7815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const ExtensionHostMap& extension_host_map = host_map_it->second; 7825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 783d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) // Go through ExtensionHosts, and remove indicated gallery, if any. 784d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) // RevokeGalleryByPrefId() may end up deleting from |extension_host_map| and 7852a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // even delete |extension_host_map| altogether. So do this in two loops to 7862a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // avoid using an invalidated iterator or deleted map. 7872a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) std::vector<const extensions::Extension*> extensions; 7882a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) for (ExtensionHostMap::const_iterator it = extension_host_map.begin(); 7892a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) it != extension_host_map.end(); 7902a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) ++it) { 7912a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) extensions.push_back(extensions_set->GetByID(it->first)); 7922a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 7932a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) for (size_t i = 0; i < extensions.size(); ++i) { 7942a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (!ContainsKey(extension_hosts_map_, profile)) 7952a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 7962a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) ExtensionHostMap::const_iterator gallery_host_it = 7972a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) extension_host_map.find(extensions[i]->id()); 7982a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (gallery_host_it == extension_host_map.end()) 7992a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) continue; 800d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) gallery_host_it->second->RevokeGalleryByPrefId(pref_id); 8015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 8025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 8035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 804effb81e5f8246d0db0270817048dc992db66e9fbBen MurdochExtensionGalleriesHost* MediaFileSystemRegistry::GetExtensionGalleryHost( 805effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch Profile* profile, 806effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch MediaGalleriesPreferences* preferences, 807effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const std::string& extension_id) { 808effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch ExtensionGalleriesHostMap::iterator extension_hosts = 809effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch extension_hosts_map_.find(profile); 810effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch // GetPreferences(), which had to be called because preferences is an 811effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch // argument, ensures that profile is in the map. 812effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch DCHECK(extension_hosts != extension_hosts_map_.end()); 813effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch if (extension_hosts->second.empty()) 814effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch preferences->AddGalleryChangeObserver(this); 815effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch 816effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch ExtensionGalleriesHost* result = extension_hosts->second[extension_id].get(); 817effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch if (!result) { 818effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch result = new ExtensionGalleriesHost( 819effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch file_system_context_.get(), 820effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch profile->GetPath(), 821effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch extension_id, 822effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch base::Bind(&MediaFileSystemRegistry::OnExtensionGalleriesHostEmpty, 823effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch base::Unretained(this), 824effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch profile, 825effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch extension_id)); 826effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch extension_hosts_map_[profile][extension_id] = result; 827effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch } 828effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch return result; 829effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch} 830effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch 8315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void MediaFileSystemRegistry::OnExtensionGalleriesHostEmpty( 8325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Profile* profile, const std::string& extension_id) { 833e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK_CURRENTLY_ON(BrowserThread::UI); 8345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 8355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ExtensionGalleriesHostMap::iterator extension_hosts = 8365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) extension_hosts_map_.find(profile); 8375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(extension_hosts != extension_hosts_map_.end()); 8385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ExtensionHostMap::size_type erase_count = 8395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) extension_hosts->second.erase(extension_id); 8405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK_EQ(1U, erase_count); 8415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (extension_hosts->second.empty()) { 8422a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // When a profile has no ExtensionGalleriesHosts left, remove the 843d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) // matching gallery-change-watcher since it is no longer needed. Leave the 8442a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // |extension_hosts| entry alone, since it indicates the profile has been 8452a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // previously used. 846d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) MediaGalleriesPreferences* preferences = GetPreferences(profile); 847d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) preferences->RemoveGalleryChangeObserver(this); 8485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 8495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 850