| OLD | NEW |
| (Empty) |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | |
| 2 // Use of this source code is governed by a BSD-style license that can be | |
| 3 // found in the LICENSE file. | |
| 4 | |
| 5 #ifndef WEBKIT_FILEAPI_ISOLATED_CONTEXT_H_ | |
| 6 #define WEBKIT_FILEAPI_ISOLATED_CONTEXT_H_ | |
| 7 | |
| 8 #include <map> | |
| 9 #include <set> | |
| 10 #include <string> | |
| 11 #include <vector> | |
| 12 | |
| 13 #include "base/basictypes.h" | |
| 14 #include "base/files/file_path.h" | |
| 15 #include "base/lazy_instance.h" | |
| 16 #include "base/memory/singleton.h" | |
| 17 #include "base/synchronization/lock.h" | |
| 18 #include "webkit/fileapi/file_system_types.h" | |
| 19 #include "webkit/fileapi/mount_points.h" | |
| 20 #include "webkit/storage/webkit_storage_export.h" | |
| 21 | |
| 22 namespace fileapi { | |
| 23 class FileSystemURL; | |
| 24 } | |
| 25 | |
| 26 namespace fileapi { | |
| 27 | |
| 28 // Manages isolated filesystem mount points which have no well-known names | |
| 29 // and are identified by a string 'filesystem ID', which usually just looks | |
| 30 // like random value. | |
| 31 // This type of filesystem can be created on the fly and may go away when it has | |
| 32 // no references from renderers. | |
| 33 // Files in an isolated filesystem are registered with corresponding names and | |
| 34 // identified by a filesystem URL like: | |
| 35 // | |
| 36 // filesystem:<origin>/isolated/<filesystem_id>/<name>/relative/path | |
| 37 // | |
| 38 // Some methods of this class are virtual just for mocking. | |
| 39 // | |
| 40 class WEBKIT_STORAGE_EXPORT IsolatedContext : public MountPoints { | |
| 41 public: | |
| 42 class WEBKIT_STORAGE_EXPORT FileInfoSet { | |
| 43 public: | |
| 44 FileInfoSet(); | |
| 45 ~FileInfoSet(); | |
| 46 | |
| 47 // Add the given |path| to the set and populates |registered_name| with | |
| 48 // the registered name assigned for the path. |path| needs to be | |
| 49 // absolute and should not contain parent references. | |
| 50 // Return false if the |path| is not valid and could not be added. | |
| 51 bool AddPath(const base::FilePath& path, std::string* registered_name); | |
| 52 | |
| 53 // Add the given |path| with the |name|. | |
| 54 // Return false if the |name| is already registered in the set or | |
| 55 // is not valid and could not be added. | |
| 56 bool AddPathWithName(const base::FilePath& path, const std::string& name); | |
| 57 | |
| 58 const std::set<MountPointInfo>& fileset() const { return fileset_; } | |
| 59 | |
| 60 private: | |
| 61 std::set<MountPointInfo> fileset_; | |
| 62 }; | |
| 63 | |
| 64 // The instance is lazily created per browser process. | |
| 65 static IsolatedContext* GetInstance(); | |
| 66 | |
| 67 // Returns true if the given filesystem type is managed by IsolatedContext | |
| 68 // (i.e. if the given |type| is Isolated or External). | |
| 69 // TODO(kinuko): needs a better function name. | |
| 70 static bool IsIsolatedType(FileSystemType type); | |
| 71 | |
| 72 // Registers a new isolated filesystem with the given FileInfoSet |files| | |
| 73 // and returns the new filesystem_id. The files are registered with their | |
| 74 // register_name as their keys so that later we can resolve the full paths | |
| 75 // for the given name. We only expose the name and the ID for the | |
| 76 // newly created filesystem to the renderer for the sake of security. | |
| 77 // | |
| 78 // The renderer will be sending filesystem requests with a virtual path like | |
| 79 // '/<filesystem_id>/<registered_name>/<relative_path_from_the_dropped_path>' | |
| 80 // for which we could crack in the browser process by calling | |
| 81 // CrackIsolatedPath to get the full path. | |
| 82 // | |
| 83 // For example: if a dropped file has a path like '/a/b/foo' and we register | |
| 84 // the path with the name 'foo' in the newly created filesystem. | |
| 85 // Later if the context is asked to crack a virtual path like '/<fsid>/foo' | |
| 86 // it can properly return the original path '/a/b/foo' by looking up the | |
| 87 // internal mapping. Similarly if a dropped entry is a directory and its | |
| 88 // path is like '/a/b/dir' a virtual path like '/<fsid>/dir/foo' can be | |
| 89 // cracked into '/a/b/dir/foo'. | |
| 90 // | |
| 91 // Note that the path in |fileset| that contains '..' or is not an | |
| 92 // absolute path is skipped and is not registered. | |
| 93 std::string RegisterDraggedFileSystem(const FileInfoSet& files); | |
| 94 | |
| 95 // Registers a new isolated filesystem for a given |path| of filesystem | |
| 96 // |type| filesystem and returns a new filesystem ID. | |
| 97 // |path| must be an absolute path which has no parent references ('..'). | |
| 98 // If |register_name| is non-null and has non-empty string the path is | |
| 99 // registered as the given |register_name|, otherwise it is populated | |
| 100 // with the name internally assigned to the path. | |
| 101 std::string RegisterFileSystemForPath(FileSystemType type, | |
| 102 const base::FilePath& path, | |
| 103 std::string* register_name); | |
| 104 | |
| 105 // Revokes all filesystem(s) registered for the given path. | |
| 106 // This is assumed to be called when the registered path becomes | |
| 107 // globally invalid, e.g. when a device for the path is detached. | |
| 108 // | |
| 109 // Note that this revokes the filesystem no matter how many references it has. | |
| 110 // It is ok to call this for the path that has no associated filesystems. | |
| 111 // Note that this only works for the filesystems registered by | |
| 112 // |RegisterFileSystemForPath|. | |
| 113 void RevokeFileSystemByPath(const base::FilePath& path); | |
| 114 | |
| 115 // Adds a reference to a filesystem specified by the given filesystem_id. | |
| 116 void AddReference(const std::string& filesystem_id); | |
| 117 | |
| 118 // Removes a reference to a filesystem specified by the given filesystem_id. | |
| 119 // If the reference count reaches 0 the isolated context gets destroyed. | |
| 120 // It is OK to call this on the filesystem that has been already deleted | |
| 121 // (e.g. by RevokeFileSystemByPath). | |
| 122 void RemoveReference(const std::string& filesystem_id); | |
| 123 | |
| 124 // Returns a set of dragged MountPointInfos registered for the | |
| 125 // |filesystem_id|. | |
| 126 // The filesystem_id must be pointing to a dragged file system | |
| 127 // (i.e. must be the one registered by RegisterDraggedFileSystem). | |
| 128 // Returns false if the |filesystem_id| is not valid. | |
| 129 bool GetDraggedFileInfo(const std::string& filesystem_id, | |
| 130 std::vector<MountPointInfo>* files) const; | |
| 131 | |
| 132 // MountPoints overrides. | |
| 133 virtual bool HandlesFileSystemMountType(FileSystemType type) const OVERRIDE; | |
| 134 virtual bool RevokeFileSystem(const std::string& filesystem_id) OVERRIDE; | |
| 135 virtual bool GetRegisteredPath(const std::string& filesystem_id, | |
| 136 base::FilePath* path) const OVERRIDE; | |
| 137 virtual bool CrackVirtualPath(const base::FilePath& virtual_path, | |
| 138 std::string* filesystem_id, | |
| 139 FileSystemType* type, | |
| 140 base::FilePath* path) const OVERRIDE; | |
| 141 virtual FileSystemURL CrackURL(const GURL& url) const OVERRIDE; | |
| 142 virtual FileSystemURL CreateCrackedFileSystemURL( | |
| 143 const GURL& origin, | |
| 144 FileSystemType type, | |
| 145 const base::FilePath& path) const OVERRIDE; | |
| 146 | |
| 147 // Returns the virtual root path that looks like /<filesystem_id>. | |
| 148 base::FilePath CreateVirtualRootPath(const std::string& filesystem_id) const; | |
| 149 | |
| 150 private: | |
| 151 friend struct base::DefaultLazyInstanceTraits<IsolatedContext>; | |
| 152 | |
| 153 // Represents each file system instance (defined in the .cc). | |
| 154 class Instance; | |
| 155 | |
| 156 typedef std::map<std::string, Instance*> IDToInstance; | |
| 157 | |
| 158 // Reverse map from registered path to IDs. | |
| 159 typedef std::map<base::FilePath, std::set<std::string> > PathToID; | |
| 160 | |
| 161 // Obtain an instance of this class via GetInstance(). | |
| 162 IsolatedContext(); | |
| 163 virtual ~IsolatedContext(); | |
| 164 | |
| 165 // MountPoints overrides. | |
| 166 virtual FileSystemURL CrackFileSystemURL( | |
| 167 const FileSystemURL& url) const OVERRIDE; | |
| 168 | |
| 169 // Unregisters a file system of given |filesystem_id|. Must be called with | |
| 170 // lock_ held. Returns true if the file system is unregistered. | |
| 171 bool UnregisterFileSystem(const std::string& filesystem_id); | |
| 172 | |
| 173 // Returns a new filesystem_id. Called with lock. | |
| 174 std::string GetNewFileSystemId() const; | |
| 175 | |
| 176 // This lock needs to be obtained when accessing the instance_map_. | |
| 177 mutable base::Lock lock_; | |
| 178 | |
| 179 IDToInstance instance_map_; | |
| 180 PathToID path_to_id_map_; | |
| 181 | |
| 182 DISALLOW_COPY_AND_ASSIGN(IsolatedContext); | |
| 183 }; | |
| 184 | |
| 185 } // namespace fileapi | |
| 186 | |
| 187 #endif // WEBKIT_FILEAPI_ISOLATED_CONTEXT_H_ | |
| OLD | NEW |