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

Side by Side Diff: webkit/plugins/ppapi/ppb_file_ref_impl.cc

Issue 13726024: Refactor FileSystem (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 7 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
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 "webkit/plugins/ppapi/ppb_file_ref_impl.h" 5 #include "webkit/plugins/ppapi/ppb_file_ref_impl.h"
6 6
7 #include "base/platform_file.h" 7 #include "base/platform_file.h"
8 #include "base/string_util.h" 8 #include "base/string_util.h"
9 #include "base/utf_string_conversions.h" 9 #include "base/utf_string_conversions.h"
10 #include "googleurl/src/gurl.h" 10 #include "googleurl/src/gurl.h"
11 #include "net/base/escape.h" 11 #include "net/base/escape.h"
12 #include "ppapi/c/pp_errors.h" 12 #include "ppapi/c/pp_errors.h"
13 #include "ppapi/shared_impl/file_type_conversion.h" 13 #include "ppapi/shared_impl/file_type_conversion.h"
14 #include "ppapi/shared_impl/time_conversion.h" 14 #include "ppapi/shared_impl/time_conversion.h"
15 #include "ppapi/shared_impl/var.h" 15 #include "ppapi/shared_impl/var.h"
16 #include "ppapi/thunk/enter.h" 16 #include "ppapi/thunk/enter.h"
17 #include "ppapi/thunk/ppb_file_system_api.h" 17 #include "ppapi/thunk/ppb_file_system_api.h"
18 #include "webkit/plugins/ppapi/common.h" 18 #include "webkit/plugins/ppapi/common.h"
19 #include "webkit/plugins/ppapi/file_callbacks.h" 19 #include "webkit/plugins/ppapi/file_callbacks.h"
20 #include "webkit/plugins/ppapi/plugin_delegate.h" 20 #include "webkit/plugins/ppapi/plugin_delegate.h"
21 #include "webkit/plugins/ppapi/plugin_module.h" 21 #include "webkit/plugins/ppapi/plugin_module.h"
22 #include "webkit/plugins/ppapi/ppapi_plugin_instance.h" 22 #include "webkit/plugins/ppapi/ppapi_plugin_instance.h"
23 #include "webkit/plugins/ppapi/ppb_file_system_impl.h"
24 #include "webkit/plugins/ppapi/resource_helper.h" 23 #include "webkit/plugins/ppapi/resource_helper.h"
25 24
26 using ppapi::HostResource; 25 using ppapi::HostResource;
27 using ppapi::PPB_FileRef_CreateInfo; 26 using ppapi::PPB_FileRef_CreateInfo;
28 using ppapi::PPTimeToTime; 27 using ppapi::PPTimeToTime;
29 using ppapi::StringVar; 28 using ppapi::StringVar;
30 using ppapi::TrackedCallback; 29 using ppapi::TrackedCallback;
31 using ppapi::thunk::EnterResourceNoLock; 30 using ppapi::thunk::EnterResourceNoLock;
32 using ppapi::thunk::PPB_FileRef_API; 31 using ppapi::thunk::PPB_FileRef_API;
33 using ppapi::thunk::PPB_FileSystem_API; 32 using ppapi::thunk::PPB_FileSystem_API;
(...skipping 108 matching lines...) Expand 10 before | Expand all | Expand 10 after
142 callback))) { 141 callback))) {
143 base::FileUtilProxy::Close( 142 base::FileUtilProxy::Close(
144 task_runner, file, base::Bind(&IgnoreCloseCallback)); 143 task_runner, file, base::Bind(&IgnoreCloseCallback));
145 callback->Run(PP_ERROR_FAILED); 144 callback->Run(PP_ERROR_FAILED);
146 } 145 }
147 } 146 }
148 147
149 } // namespace 148 } // namespace
150 149
151 PPB_FileRef_Impl::PPB_FileRef_Impl(const PPB_FileRef_CreateInfo& info, 150 PPB_FileRef_Impl::PPB_FileRef_Impl(const PPB_FileRef_CreateInfo& info,
152 PPB_FileSystem_Impl* file_system) 151 PP_Resource file_system)
153 : PPB_FileRef_Shared(::ppapi::OBJECT_IS_IMPL, info), 152 : PPB_FileRef_Shared(::ppapi::OBJECT_IS_IMPL, info),
154 file_system_(file_system), 153 file_system_(file_system),
155 external_file_system_path_() { 154 external_file_system_path_() {
156 } 155 }
157 156
158 PPB_FileRef_Impl::PPB_FileRef_Impl(const PPB_FileRef_CreateInfo& info, 157 PPB_FileRef_Impl::PPB_FileRef_Impl(const PPB_FileRef_CreateInfo& info,
159 const base::FilePath& external_file_path) 158 const base::FilePath& external_file_path)
160 : PPB_FileRef_Shared(::ppapi::OBJECT_IS_IMPL, info), 159 : PPB_FileRef_Shared(::ppapi::OBJECT_IS_IMPL, info),
161 file_system_(), 160 file_system_(),
162 external_file_system_path_(external_file_path) { 161 external_file_system_path_(external_file_path) {
163 } 162 }
164 163
165 PPB_FileRef_Impl::~PPB_FileRef_Impl() { 164 PPB_FileRef_Impl::~PPB_FileRef_Impl() {
166 } 165 }
167 166
168 // static 167 // static
169 PPB_FileRef_Impl* PPB_FileRef_Impl::CreateInternal(PP_Resource pp_file_system, 168 PPB_FileRef_Impl* PPB_FileRef_Impl::CreateInternal(PP_Instance instance,
169 PP_Resource pp_file_system,
170 const std::string& path) { 170 const std::string& path) {
171 EnterResourceNoLock<PPB_FileSystem_API> enter(pp_file_system, true); 171 PluginInstance* plugin_instance =
172 if (enter.failed()) 172 ResourceHelper::PPInstanceToPluginInstance(instance);
173 if (!plugin_instance || !plugin_instance->delegate())
173 return 0; 174 return 0;
174 175
175 PPB_FileSystem_Impl* file_system = 176 PP_FileSystemType type =
176 static_cast<PPB_FileSystem_Impl*>(enter.object()); 177 plugin_instance->delegate()->GetFileSystemType(instance, pp_file_system);
177 if (!file_system->pp_instance()) 178 if (type != PP_FILESYSTEMTYPE_LOCALPERSISTENT &&
178 return 0; 179 type != PP_FILESYSTEMTYPE_LOCALTEMPORARY &&
179 180 type != PP_FILESYSTEMTYPE_EXTERNAL)
180 if (file_system->type() != PP_FILESYSTEMTYPE_LOCALPERSISTENT &&
181 file_system->type() != PP_FILESYSTEMTYPE_LOCALTEMPORARY &&
182 file_system->type() != PP_FILESYSTEMTYPE_EXTERNAL)
183 return 0; 181 return 0;
184 182
185 PPB_FileRef_CreateInfo info; 183 PPB_FileRef_CreateInfo info;
186 info.resource = HostResource::MakeInstanceOnly(file_system->pp_instance()); 184 info.resource = HostResource::MakeInstanceOnly(instance);
187 info.file_system_type = file_system->type(); 185 info.file_system_plugin_resource = pp_file_system;
186 info.file_system_type = type;
188 187
189 // Validate the path. 188 // Validate the path.
190 info.path = path; 189 info.path = path;
191 if (!IsValidLocalPath(info.path)) 190 if (!IsValidLocalPath(info.path))
192 return 0; 191 return 0;
193 TrimTrailingSlash(&info.path); 192 TrimTrailingSlash(&info.path);
194 193
195 info.name = GetNameForVirtualFilePath(info.path); 194 info.name = GetNameForVirtualFilePath(info.path);
196 195
197 return new PPB_FileRef_Impl(info, file_system); 196 return new PPB_FileRef_Impl(info, pp_file_system);
198 } 197 }
199 198
200 // static 199 // static
201 PPB_FileRef_Impl* PPB_FileRef_Impl::CreateExternal( 200 PPB_FileRef_Impl* PPB_FileRef_Impl::CreateExternal(
202 PP_Instance instance, 201 PP_Instance instance,
203 const base::FilePath& external_file_path, 202 const base::FilePath& external_file_path,
204 const std::string& display_name) { 203 const std::string& display_name) {
205 PPB_FileRef_CreateInfo info; 204 PPB_FileRef_CreateInfo info;
206 info.resource = HostResource::MakeInstanceOnly(instance); 205 info.resource = HostResource::MakeInstanceOnly(instance);
206 info.file_system_plugin_resource = 0;
207 info.file_system_type = PP_FILESYSTEMTYPE_EXTERNAL; 207 info.file_system_type = PP_FILESYSTEMTYPE_EXTERNAL;
208 if (display_name.empty()) 208 if (display_name.empty())
209 info.name = GetNameForExternalFilePath(external_file_path); 209 info.name = GetNameForExternalFilePath(external_file_path);
210 else 210 else
211 info.name = display_name; 211 info.name = display_name;
212 212
213 return new PPB_FileRef_Impl(info, external_file_path); 213 return new PPB_FileRef_Impl(info, external_file_path);
214 } 214 }
215 215
216 PP_Resource PPB_FileRef_Impl::GetParent() { 216 PP_Resource PPB_FileRef_Impl::GetParent() {
217 if (GetFileSystemType() == PP_FILESYSTEMTYPE_EXTERNAL) 217 if (GetFileSystemType() == PP_FILESYSTEMTYPE_EXTERNAL)
218 return 0; 218 return 0;
219 219
220 const std::string& virtual_path = GetCreateInfo().path; 220 const std::string& virtual_path = GetCreateInfo().path;
221 221
222 // There should always be a leading slash at least! 222 // There should always be a leading slash at least!
223 size_t pos = virtual_path.rfind('/'); 223 size_t pos = virtual_path.rfind('/');
224 CHECK(pos != std::string::npos); 224 CHECK(pos != std::string::npos);
225 225
226 // If the path is "/foo", then we want to include the slash. 226 // If the path is "/foo", then we want to include the slash.
227 if (pos == 0) 227 if (pos == 0)
228 pos++; 228 pos++;
229 std::string parent_path = virtual_path.substr(0, pos); 229 std::string parent_path = virtual_path.substr(0, pos);
230 230
231 scoped_refptr<PPB_FileRef_Impl> parent_ref( 231 scoped_refptr<PPB_FileRef_Impl> parent_ref(
232 CreateInternal(file_system_->pp_resource(), parent_path)); 232 CreateInternal(pp_instance(), file_system_, parent_path));
233 if (!parent_ref.get()) 233 if (!parent_ref.get())
234 return 0; 234 return 0;
235 return parent_ref->GetReference(); 235 return parent_ref->GetReference();
236 } 236 }
237 237
238 int32_t PPB_FileRef_Impl::MakeDirectory( 238 int32_t PPB_FileRef_Impl::MakeDirectory(
239 PP_Bool make_ancestors, 239 PP_Bool make_ancestors,
240 scoped_refptr<TrackedCallback> callback) { 240 scoped_refptr<TrackedCallback> callback) {
241 if (!IsValidNonExternalFileSystem()) 241 if (!IsValidNonExternalFileSystem())
242 return PP_ERROR_NOACCESS; 242 return PP_ERROR_NOACCESS;
243 243
244 PluginInstance* plugin_instance = ResourceHelper::GetPluginInstance(this); 244 PluginInstance* plugin_instance = ResourceHelper::GetPluginInstance(this);
245 if (!plugin_instance) 245 if (!plugin_instance)
246 return PP_ERROR_FAILED; 246 return PP_ERROR_FAILED;
247 if (!plugin_instance->delegate()->MakeDirectory( 247 if (!plugin_instance->delegate()->MakeDirectory(
248 GetFileSystemURL(), PP_ToBool(make_ancestors), 248 GetFileSystemURL(), PP_ToBool(make_ancestors),
249 new FileCallbacks(this, callback, NULL, NULL))) 249 new FileCallbacks(this, callback, NULL)))
250 return PP_ERROR_FAILED; 250 return PP_ERROR_FAILED;
251 return PP_OK_COMPLETIONPENDING; 251 return PP_OK_COMPLETIONPENDING;
252 } 252 }
253 253
254 int32_t PPB_FileRef_Impl::Touch(PP_Time last_access_time, 254 int32_t PPB_FileRef_Impl::Touch(PP_Time last_access_time,
255 PP_Time last_modified_time, 255 PP_Time last_modified_time,
256 scoped_refptr<TrackedCallback> callback) { 256 scoped_refptr<TrackedCallback> callback) {
257 if (!IsValidNonExternalFileSystem()) 257 if (!IsValidNonExternalFileSystem())
258 return PP_ERROR_NOACCESS; 258 return PP_ERROR_NOACCESS;
259 259
260 PluginInstance* plugin_instance = ResourceHelper::GetPluginInstance(this); 260 PluginInstance* plugin_instance = ResourceHelper::GetPluginInstance(this);
261 if (!plugin_instance) 261 if (!plugin_instance)
262 return PP_ERROR_FAILED; 262 return PP_ERROR_FAILED;
263 if (!plugin_instance->delegate()->Touch( 263 if (!plugin_instance->delegate()->Touch(
264 GetFileSystemURL(), 264 GetFileSystemURL(),
265 PPTimeToTime(last_access_time), 265 PPTimeToTime(last_access_time),
266 PPTimeToTime(last_modified_time), 266 PPTimeToTime(last_modified_time),
267 new FileCallbacks(this, callback, NULL, NULL))) 267 new FileCallbacks(this, callback, NULL)))
268 return PP_ERROR_FAILED; 268 return PP_ERROR_FAILED;
269 return PP_OK_COMPLETIONPENDING; 269 return PP_OK_COMPLETIONPENDING;
270 } 270 }
271 271
272 int32_t PPB_FileRef_Impl::Delete(scoped_refptr<TrackedCallback> callback) { 272 int32_t PPB_FileRef_Impl::Delete(scoped_refptr<TrackedCallback> callback) {
273 if (!IsValidNonExternalFileSystem()) 273 if (!IsValidNonExternalFileSystem())
274 return PP_ERROR_NOACCESS; 274 return PP_ERROR_NOACCESS;
275 275
276 PluginInstance* plugin_instance = ResourceHelper::GetPluginInstance(this); 276 PluginInstance* plugin_instance = ResourceHelper::GetPluginInstance(this);
277 if (!plugin_instance) 277 if (!plugin_instance)
278 return PP_ERROR_FAILED; 278 return PP_ERROR_FAILED;
279 if (!plugin_instance->delegate()->Delete( 279 if (!plugin_instance->delegate()->Delete(
280 GetFileSystemURL(), 280 GetFileSystemURL(),
281 new FileCallbacks(this, callback, NULL, NULL))) 281 new FileCallbacks(this, callback, NULL)))
282 return PP_ERROR_FAILED; 282 return PP_ERROR_FAILED;
283 return PP_OK_COMPLETIONPENDING; 283 return PP_OK_COMPLETIONPENDING;
284 } 284 }
285 285
286 int32_t PPB_FileRef_Impl::Rename(PP_Resource new_pp_file_ref, 286 int32_t PPB_FileRef_Impl::Rename(PP_Resource new_pp_file_ref,
287 scoped_refptr<TrackedCallback> callback) { 287 scoped_refptr<TrackedCallback> callback) {
288 EnterResourceNoLock<PPB_FileRef_API> enter(new_pp_file_ref, true); 288 EnterResourceNoLock<PPB_FileRef_API> enter(new_pp_file_ref, true);
289 if (enter.failed()) 289 if (enter.failed())
290 return PP_ERROR_BADRESOURCE; 290 return PP_ERROR_BADRESOURCE;
291 PPB_FileRef_Impl* new_file_ref = 291 PPB_FileRef_Impl* new_file_ref =
292 static_cast<PPB_FileRef_Impl*>(enter.object()); 292 static_cast<PPB_FileRef_Impl*>(enter.object());
293 293
294 if (!IsValidNonExternalFileSystem() || 294 if (!IsValidNonExternalFileSystem() ||
295 file_system_.get() != new_file_ref->file_system_.get()) 295 file_system_ != new_file_ref->file_system_)
296 return PP_ERROR_NOACCESS; 296 return PP_ERROR_NOACCESS;
297 297
298 // TODO(viettrungluu): Also cancel when the new file ref is destroyed? 298 // TODO(viettrungluu): Also cancel when the new file ref is destroyed?
299 // http://crbug.com/67624 299 // http://crbug.com/67624
300 PluginInstance* plugin_instance = ResourceHelper::GetPluginInstance(this); 300 PluginInstance* plugin_instance = ResourceHelper::GetPluginInstance(this);
301 if (!plugin_instance) 301 if (!plugin_instance)
302 return PP_ERROR_FAILED; 302 return PP_ERROR_FAILED;
303 if (!plugin_instance->delegate()->Rename( 303 if (!plugin_instance->delegate()->Rename(
304 GetFileSystemURL(), new_file_ref->GetFileSystemURL(), 304 GetFileSystemURL(), new_file_ref->GetFileSystemURL(),
305 new FileCallbacks(this, callback, NULL, NULL))) 305 new FileCallbacks(this, callback, NULL)))
306 return PP_ERROR_FAILED; 306 return PP_ERROR_FAILED;
307 return PP_OK_COMPLETIONPENDING; 307 return PP_OK_COMPLETIONPENDING;
308 } 308 }
309 309
310 PP_Var PPB_FileRef_Impl::GetAbsolutePath() { 310 PP_Var PPB_FileRef_Impl::GetAbsolutePath() {
311 if (GetFileSystemType() != PP_FILESYSTEMTYPE_EXTERNAL) 311 if (GetFileSystemType() != PP_FILESYSTEMTYPE_EXTERNAL)
312 return GetPath(); 312 return GetPath();
313 if (!external_path_var_.get()) { 313 if (!external_path_var_.get()) {
314 external_path_var_ = new StringVar( 314 external_path_var_ = new StringVar(
315 external_file_system_path_.AsUTF8Unsafe()); 315 external_file_system_path_.AsUTF8Unsafe());
(...skipping 17 matching lines...) Expand all
333 return GURL(); 333 return GURL();
334 } 334 }
335 335
336 const std::string& virtual_path = GetCreateInfo().path; 336 const std::string& virtual_path = GetCreateInfo().path;
337 CHECK(!virtual_path.empty()); // Should always be at least "/". 337 CHECK(!virtual_path.empty()); // Should always be at least "/".
338 338
339 // Since |virtual_path_| starts with a '/', it looks like an absolute path. 339 // Since |virtual_path_| starts with a '/', it looks like an absolute path.
340 // We need to trim off the '/' before calling Resolve, as FileSystem URLs 340 // We need to trim off the '/' before calling Resolve, as FileSystem URLs
341 // start with a storage type identifier that looks like a path segment. 341 // start with a storage type identifier that looks like a path segment.
342 342
343 return file_system_->root_url().Resolve( 343 PluginInstance* plugin_instance = ResourceHelper::GetPluginInstance(this);
344 net::EscapePath(virtual_path.substr(1))); 344 PluginDelegate* delegate =
345 plugin_instance ? plugin_instance->delegate() : NULL;
346 if (!delegate)
347 return GURL();
348 return GURL(delegate->GetFileSystemRootUrl(pp_instance(), file_system_))
349 .Resolve(net::EscapePath(virtual_path.substr(1)));
350 }
351
352 bool PPB_FileRef_Impl::IsValidNonExternalFileSystem() const {
353 PluginInstance* plugin_instance = ResourceHelper::GetPluginInstance(this);
354 PluginDelegate* delegate =
355 plugin_instance ? plugin_instance->delegate() : NULL;
356 return delegate &&
357 delegate->IsFileSystemOpened(pp_instance(), file_system_) &&
358 delegate->GetFileSystemType(pp_instance(), file_system_) !=
359 PP_FILESYSTEMTYPE_EXTERNAL;
345 } 360 }
346 361
347 bool PPB_FileRef_Impl::HasValidFileSystem() const { 362 bool PPB_FileRef_Impl::HasValidFileSystem() const {
348 return file_system_ && file_system_->opened(); 363 PluginInstance* plugin_instance = ResourceHelper::GetPluginInstance(this);
349 } 364 PluginDelegate* delegate =
350 365 plugin_instance ? plugin_instance->delegate() : NULL;
351 bool PPB_FileRef_Impl::IsValidNonExternalFileSystem() const { 366 return delegate && delegate->IsFileSystemOpened(pp_instance(), file_system_);
352 return file_system_ && file_system_->opened() &&
353 file_system_->type() != PP_FILESYSTEMTYPE_EXTERNAL;
354 } 367 }
355 368
356 int32_t PPB_FileRef_Impl::Query(PP_FileInfo* info, 369 int32_t PPB_FileRef_Impl::Query(PP_FileInfo* info,
357 scoped_refptr<TrackedCallback> callback) { 370 scoped_refptr<TrackedCallback> callback) {
358 scoped_refptr<PluginInstance> plugin_instance = 371 scoped_refptr<PluginInstance> plugin_instance =
359 ResourceHelper::GetPluginInstance(this); 372 ResourceHelper::GetPluginInstance(this);
360 if (!plugin_instance.get()) 373 if (!plugin_instance.get())
361 return PP_ERROR_FAILED; 374 return PP_ERROR_FAILED;
362 375
363 if (!file_system_) { 376 if (!file_system_) {
364 // External file system 377 // External file system
365 // We have to do something totally different for external file systems. 378 // We have to do something totally different for external file systems.
366 379
367 // TODO(teravest): Use the SequencedWorkerPool instead. 380 // TODO(teravest): Use the SequencedWorkerPool instead.
368 scoped_refptr<base::TaskRunner> task_runner = 381 scoped_refptr<base::TaskRunner> task_runner =
369 plugin_instance->delegate()->GetFileThreadMessageLoopProxy(); 382 plugin_instance->delegate()->GetFileThreadMessageLoopProxy();
370 if (!plugin_instance->delegate()->AsyncOpenFile( 383 if (!plugin_instance->delegate()->AsyncOpenFile(
371 GetSystemPath(), 384 GetSystemPath(),
372 base::PLATFORM_FILE_OPEN | base::PLATFORM_FILE_READ, 385 base::PLATFORM_FILE_OPEN | base::PLATFORM_FILE_READ,
373 base::Bind(&QueryCallback, task_runner, info, callback))) 386 base::Bind(&QueryCallback, task_runner, info, callback)))
374 return PP_ERROR_FAILED; 387 return PP_ERROR_FAILED;
375 } else { 388 } else {
376 // Non-external file system 389 // Non-external file system
377 if (!HasValidFileSystem()) 390 if (!HasValidFileSystem())
378 return PP_ERROR_NOACCESS; 391 return PP_ERROR_NOACCESS;
379 392
393 PluginInstance* plugin_instance = ResourceHelper::GetPluginInstance(this);
394 PluginDelegate* delegate =
395 plugin_instance ? plugin_instance->delegate() : NULL;
396 if (!delegate)
397 return PP_ERROR_FAILED;
398
380 if (!plugin_instance->delegate()->Query( 399 if (!plugin_instance->delegate()->Query(
381 GetFileSystemURL(), 400 GetFileSystemURL(),
382 new FileCallbacks(this, callback, info, file_system_))) 401 new FileCallbacks(this, callback, info,
402 delegate->GetFileSystemType(pp_instance(),
403 file_system_))))
383 return PP_ERROR_FAILED; 404 return PP_ERROR_FAILED;
384 405
385 } 406 }
386 return PP_OK_COMPLETIONPENDING; 407 return PP_OK_COMPLETIONPENDING;
387 } 408 }
388 409
389 } // namespace ppapi 410 } // namespace ppapi
390 } // namespace webkit 411 } // namespace webkit
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698