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

Side by Side Diff: chrome/browser/media_galleries/fileapi/native_media_file_util.cc

Issue 15653004: Picasa import: Make NativeMediaFileUtil an AsyncFileUtil (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Address vandebo comments. Created 7 years, 6 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 "chrome/browser/media_galleries/fileapi/native_media_file_util.h" 5 #include "chrome/browser/media_galleries/fileapi/native_media_file_util.h"
6 6
7 #include "base/bind.h"
7 #include "base/file_util.h" 8 #include "base/file_util.h"
8 #include "base/string_util.h" 9 #include "base/string_util.h"
9 #include "chrome/browser/media_galleries/fileapi/filtering_file_enumerator.h" 10 #include "base/task_runner_util.h"
10 #include "chrome/browser/media_galleries/fileapi/media_file_system_mount_point_p rovider.h" 11 #include "chrome/browser/media_galleries/fileapi/media_file_system_mount_point_p rovider.h"
11 #include "chrome/browser/media_galleries/fileapi/media_path_filter.h" 12 #include "chrome/browser/media_galleries/fileapi/media_path_filter.h"
13 #include "content/public/browser/browser_thread.h"
12 #include "googleurl/src/gurl.h" 14 #include "googleurl/src/gurl.h"
13 #include "net/base/mime_sniffer.h" 15 #include "net/base/mime_sniffer.h"
14 #include "webkit/browser/fileapi/file_system_context.h" 16 #include "webkit/browser/fileapi/file_system_context.h"
15 #include "webkit/browser/fileapi/file_system_operation_context.h" 17 #include "webkit/browser/fileapi/file_system_operation_context.h"
16 #include "webkit/browser/fileapi/file_system_task_runners.h" 18 #include "webkit/browser/fileapi/file_system_task_runners.h"
17 #include "webkit/browser/fileapi/native_file_util.h" 19 #include "webkit/browser/fileapi/native_file_util.h"
20 #include "webkit/common/blob/shareable_file_reference.h"
18 21
22 using base::Bind;
23 using base::Owned;
19 using base::PlatformFile; 24 using base::PlatformFile;
20 using base::PlatformFileError; 25 using base::PlatformFileError;
21 using base::PlatformFileInfo; 26 using base::PlatformFileInfo;
27 using base::Unretained;
22 using fileapi::FileSystemOperationContext; 28 using fileapi::FileSystemOperationContext;
23 using fileapi::FileSystemURL; 29 using fileapi::FileSystemURL;
24 using fileapi::NativeFileUtil; 30 using fileapi::NativeFileUtil;
25 31
26 namespace chrome { 32 namespace chrome {
27 33
28 namespace { 34 namespace {
29 35
30 // Modelled after ScopedFILEClose. 36 // Modelled after ScopedFILEClose.
31 struct ScopedPlatformFileClose { 37 struct ScopedPlatformFileClose {
32 void operator()(base::PlatformFile* file) { 38 void operator()(base::PlatformFile* file) {
33 if (file && *file != base::kInvalidPlatformFileValue) 39 if (file && *file != base::kInvalidPlatformFileValue)
34 base::ClosePlatformFile(*file); 40 base::ClosePlatformFile(*file);
35 } 41 }
36 }; 42 };
37 43
38 typedef scoped_ptr<base::PlatformFile, ScopedPlatformFileClose> 44 typedef scoped_ptr<base::PlatformFile, ScopedPlatformFileClose>
39 ScopedPlatformFile; 45 ScopedPlatformFile;
40 46
47 // Used to skip the hidden folders and files. Returns true if the file specified
48 // by |path| should be skipped.
49 bool ShouldSkip(const base::FilePath& path) {
50 const base::FilePath::StringType base_name = path.BaseName().value();
51 if (base_name.empty())
52 return false;
53
54 // Dot files (aka hidden files)
55 if (base_name[0] == '.')
56 return true;
57
58 // Mac OS X file.
59 if (base_name == FILE_PATH_LITERAL("__MACOSX"))
60 return true;
61
62 #if defined(OS_WIN)
63 DWORD file_attributes = ::GetFileAttributes(path.value().c_str());
64 if ((file_attributes != INVALID_FILE_ATTRIBUTES) &&
65 ((file_attributes & FILE_ATTRIBUTE_HIDDEN) != 0))
66 return true;
67 #else
68 // Windows always creates a recycle bin folder in the attached device to store
69 // all the deleted contents. On non-windows operating systems, there is no way
70 // to get the hidden attribute of windows recycle bin folders that are present
71 // on the attached device. Therefore, compare the file path name to the
72 // recycle bin name and exclude those folders. For more details, please refer
73 // to http://support.microsoft.com/kb/171694.
74 const char win_98_recycle_bin_name[] = "RECYCLED";
75 const char win_xp_recycle_bin_name[] = "RECYCLER";
76 const char win_vista_recycle_bin_name[] = "$Recycle.bin";
77 if ((base::strncasecmp(base_name.c_str(),
78 win_98_recycle_bin_name,
79 strlen(win_98_recycle_bin_name)) == 0) ||
80 (base::strncasecmp(base_name.c_str(),
81 win_xp_recycle_bin_name,
82 strlen(win_xp_recycle_bin_name)) == 0) ||
83 (base::strncasecmp(base_name.c_str(),
84 win_vista_recycle_bin_name,
85 strlen(win_vista_recycle_bin_name)) == 0))
86 return true;
87 #endif
88 return false;
89 }
90
41 // Returns true if the current thread is capable of doing IO. 91 // Returns true if the current thread is capable of doing IO.
42 bool IsOnTaskRunnerThread(fileapi::FileSystemOperationContext* context) { 92 bool IsOnTaskRunnerThread(fileapi::FileSystemOperationContext* context) {
43 return context->file_system_context()->task_runners()-> 93 return context->file_system_context()->task_runners()->
44 media_task_runner()->RunsTasksOnCurrentThread(); 94 media_task_runner()->RunsTasksOnCurrentThread();
45 } 95 }
46 96
47 MediaPathFilter* GetMediaPathFilter(FileSystemOperationContext* context) { 97 MediaPathFilter* GetMediaPathFilter(FileSystemOperationContext* context) {
48 return context->GetUserValue<MediaPathFilter*>( 98 return context->GetUserValue<MediaPathFilter*>(
49 MediaFileSystemMountPointProvider::kMediaPathFilterKey); 99 MediaFileSystemMountPointProvider::kMediaPathFilterKey);
50 } 100 }
51 101
102 void FinishStatusCallback(
vandebo (ex-Chrome) 2013/06/02 04:30:24 You don't need this callback.
103 const NativeMediaFileUtil::StatusCallback& callback,
104 PlatformFileError error) {
105 callback.Run(error);
106 }
107
52 } // namespace 108 } // namespace
53 109
54 NativeMediaFileUtil::NativeMediaFileUtil() { 110 NativeMediaFileUtil::NativeMediaFileUtil() {
55 } 111 }
56 112
57 PlatformFileError NativeMediaFileUtil::CreateOrOpen( 113 bool NativeMediaFileUtil::CreateOrOpen(
58 FileSystemOperationContext* context, 114 FileSystemOperationContext* context,
59 const FileSystemURL& url, 115 const FileSystemURL& url,
60 int file_flags, 116 int file_flags,
61 PlatformFile* file_handle, 117 const CreateOrOpenCallback& callback) {
62 bool* created) { 118 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::IO));
63 // Only called by NaCl, which should not have access to media file systems. 119 // Only called by NaCl, which should not have access to media file systems.
64 return base::PLATFORM_FILE_ERROR_SECURITY; 120 base::PlatformFile invalid_file(base::kInvalidPlatformFileValue);
65 } 121 callback.Run(base::PLATFORM_FILE_ERROR_SECURITY,
66 122 base::PassPlatformFile(&invalid_file),
67 PlatformFileError NativeMediaFileUtil::EnsureFileExists( 123 false);
68 FileSystemOperationContext* context, 124 return true;
69 const FileSystemURL& url, bool* created) { 125 }
126
127 bool NativeMediaFileUtil::EnsureFileExists(
128 FileSystemOperationContext* context,
129 const FileSystemURL& url,
130 const EnsureFileExistsCallback& callback) {
131 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::IO));
132 callback.Run(base::PLATFORM_FILE_ERROR_SECURITY, false);
133 return true;
134 }
135
136 bool NativeMediaFileUtil::CreateDirectory(
137 FileSystemOperationContext* context,
138 const FileSystemURL& url,
139 bool exclusive,
140 bool recursive,
141 const StatusCallback& callback) {
142 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::IO));
143 return base::PostTaskAndReplyWithResult(
144 context->task_runner(),
145 FROM_HERE,
146 Bind(&NativeMediaFileUtil::CreateDirectorySync, Unretained(this),
vandebo (ex-Chrome) 2013/06/02 04:30:24 I don't think Unretained(this) is safe, use a weak
147 context, url, exclusive, recursive),
148 Bind(&FinishStatusCallback, callback));
vandebo (ex-Chrome) 2013/06/02 04:30:24 No Bind, just callback
149 }
150
151 bool NativeMediaFileUtil::GetFileInfo(
152 FileSystemOperationContext* context,
153 const FileSystemURL& url,
154 const GetFileInfoCallback& callback) {
155 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::IO));
156 return context->task_runner()->PostTask(
157 FROM_HERE,
158 Bind(&NativeMediaFileUtil::GetFileInfoOnTaskRunnerThread,
159 Unretained(this), context, url, callback));
160 }
161
162 bool NativeMediaFileUtil::ReadDirectory(
163 FileSystemOperationContext* context,
164 const FileSystemURL& url,
165 const ReadDirectoryCallback& callback) {
166 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::IO));
167 return context->task_runner()->PostTask(
168 FROM_HERE,
169 Bind(&NativeMediaFileUtil::ReadDirectoryOnTaskRunnerThread,
170 Unretained(this), context, url, callback));
171 }
172
173 bool NativeMediaFileUtil::Touch(
174 FileSystemOperationContext* context,
175 const FileSystemURL& url,
176 const base::Time& last_access_time,
177 const base::Time& last_modified_time,
178 const StatusCallback& callback) {
179 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::IO));
180 callback.Run(base::PLATFORM_FILE_ERROR_SECURITY);
181 return true;
182 }
183
184 bool NativeMediaFileUtil::Truncate(
185 FileSystemOperationContext* context,
186 const FileSystemURL& url,
187 int64 length,
188 const StatusCallback& callback) {
189 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::IO));
190 callback.Run(base::PLATFORM_FILE_ERROR_SECURITY);
191 return true;
192 }
193
194 bool NativeMediaFileUtil::CopyFileLocal(
195 FileSystemOperationContext* context,
196 const FileSystemURL& src_url,
197 const FileSystemURL& dest_url,
198 const StatusCallback& callback) {
199 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::IO));
200 return base::PostTaskAndReplyWithResult(
201 context->task_runner(),
202 FROM_HERE,
203 Bind(&NativeMediaFileUtil::CopyOrMoveFileSync, Unretained(this),
204 context, src_url, dest_url, true /* copy */),
205 Bind(&FinishStatusCallback, callback));
206 }
207
208 bool NativeMediaFileUtil::MoveFileLocal(
209 FileSystemOperationContext* context,
210 const FileSystemURL& src_url,
211 const FileSystemURL& dest_url,
212 const StatusCallback& callback) {
213 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::IO));
214 return base::PostTaskAndReplyWithResult(
215 context->task_runner(),
216 FROM_HERE,
217 Bind(&NativeMediaFileUtil::CopyOrMoveFileSync, Unretained(this),
218 context, src_url, dest_url, false /* copy */),
219 Bind(&FinishStatusCallback, callback));
220 }
221
222 bool NativeMediaFileUtil::CopyInForeignFile(
223 FileSystemOperationContext* context,
224 const base::FilePath& src_file_path,
225 const FileSystemURL& dest_url,
226 const StatusCallback& callback) {
227 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::IO));
228 return base::PostTaskAndReplyWithResult(
229 context->task_runner(),
230 FROM_HERE,
231 Bind(&NativeMediaFileUtil::CopyInForeignFileSync, Unretained(this),
232 context, src_file_path, dest_url),
233 Bind(&FinishStatusCallback, callback));
234 }
235
236 bool NativeMediaFileUtil::DeleteFile(
237 FileSystemOperationContext* context,
238 const FileSystemURL& url,
239 const StatusCallback& callback) {
240 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::IO));
241 callback.Run(base::PLATFORM_FILE_ERROR_SECURITY);
242 return true;
243 }
244
245 bool NativeMediaFileUtil::DeleteDirectory(
246 FileSystemOperationContext* context,
247 const FileSystemURL& url,
248 const StatusCallback& callback) {
249 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::IO));
250 return base::PostTaskAndReplyWithResult(
251 context->task_runner(),
252 FROM_HERE,
253 Bind(&NativeMediaFileUtil::DeleteDirectorySync, Unretained(this),
254 context, url),
255 Bind(&FinishStatusCallback, callback));
256 }
257
258 bool NativeMediaFileUtil::CreateSnapshotFile(
259 FileSystemOperationContext* context,
260 const FileSystemURL& url,
261 const CreateSnapshotFileCallback& callback) {
262 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::IO));
263 return context->task_runner()->PostTask(
264 FROM_HERE,
265 Bind(&NativeMediaFileUtil::CreateSnapshotFileOnTaskRunnerThread,
266 Unretained(this), context, url, callback));
267 }
268
269 PlatformFileError NativeMediaFileUtil::CreateDirectorySync(
270 FileSystemOperationContext* context,
271 const FileSystemURL& url,
272 bool exclusive,
273 bool recursive) {
70 base::FilePath file_path; 274 base::FilePath file_path;
71 PlatformFileError error = GetFilteredLocalFilePath(context, url, &file_path); 275 PlatformFileError error = GetLocalFilePath(context, url, &file_path);
72 if (error != base::PLATFORM_FILE_OK) 276 if (error != base::PLATFORM_FILE_OK)
73 return error; 277 return error;
74 return NativeFileUtil::EnsureFileExists(file_path, created); 278 return NativeFileUtil::CreateDirectory(file_path, exclusive, recursive);
75 } 279 }
76 280
77 scoped_ptr<fileapi::FileSystemFileUtil::AbstractFileEnumerator> 281 PlatformFileError NativeMediaFileUtil::GetLocalFilePath(
78 NativeMediaFileUtil::CreateFileEnumerator( 282 FileSystemOperationContext* context,
79 FileSystemOperationContext* context, 283 const FileSystemURL& url,
80 const FileSystemURL& root_url) { 284 base::FilePath* local_file_path) {
81 DCHECK(context); 285 DCHECK(local_file_path);
82 return make_scoped_ptr(new FilteringFileEnumerator( 286 DCHECK(url.is_valid());
83 IsolatedFileUtil::CreateFileEnumerator(context, root_url), 287 if (url.path().empty()) {
84 GetMediaPathFilter(context))) 288 // Root direcory case, which should not be accessed.
85 .PassAs<FileSystemFileUtil::AbstractFileEnumerator>(); 289 return base::PLATFORM_FILE_ERROR_ACCESS_DENIED;
86 } 290 }
87 291 *local_file_path = url.path();
88 PlatformFileError NativeMediaFileUtil::Touch( 292 return base::PLATFORM_FILE_OK;
89 FileSystemOperationContext* context, 293 }
90 const FileSystemURL& url, 294
91 const base::Time& last_access_time, 295 PlatformFileError NativeMediaFileUtil::ReadDirectorySync(
92 const base::Time& last_modified_time) { 296 FileSystemOperationContext* context,
93 base::FilePath file_path; 297 const FileSystemURL& url,
94 PlatformFileError error = GetFilteredLocalFilePathForExistingFileOrDirectory( 298 EntryList* file_list) {
95 context, 299 DCHECK(IsOnTaskRunnerThread(context));
96 url, 300 DCHECK(file_list);
97 // Touch fails for non-existent paths and filtered paths. 301 DCHECK(file_list->empty());
98 base::PLATFORM_FILE_ERROR_FAILED, 302 base::PlatformFileInfo file_info;
99 &file_path); 303 base::FilePath platform_path;
304 PlatformFileError error = GetFileInfoSync(context, url, &file_info,
305 &platform_path);
306
307 if (error == base::PLATFORM_FILE_OK && !file_info.is_directory)
308 return base::PLATFORM_FILE_ERROR_NOT_A_DIRECTORY;
309
100 if (error != base::PLATFORM_FILE_OK) 310 if (error != base::PLATFORM_FILE_OK)
101 return error; 311 return error;
102 return NativeFileUtil::Touch(file_path, last_access_time, last_modified_time); 312
103 } 313 file_util::FileEnumerator file_enum(
104 314 platform_path,
105 PlatformFileError NativeMediaFileUtil::Truncate( 315 false /* recursive */,
106 FileSystemOperationContext* context, 316 file_util::FileEnumerator::FILES |
107 const FileSystemURL& url, 317 file_util::FileEnumerator::DIRECTORIES);
108 int64 length) { 318 file_util::FileEnumerator::FindInfo file_util_info;
109 base::FilePath file_path; 319 #if defined(OS_WIN)
110 PlatformFileError error = GetFilteredLocalFilePathForExistingFileOrDirectory( 320 memset(&file_util_info, 0, sizeof(file_util_info));
111 context, 321 #endif // defined(OS_WIN)
112 url, 322
113 // Cannot truncate paths that do not exist, or are filtered. 323 for (base::FilePath platform_path = file_enum.Next();
114 base::PLATFORM_FILE_ERROR_NOT_FOUND, 324 !platform_path.empty();
115 &file_path); 325 platform_path = file_enum.Next()) {
116 if (error != base::PLATFORM_FILE_OK) 326 // Skip symlinks.
117 return error; 327 if (file_util::IsLink(platform_path))
118 return NativeFileUtil::Truncate(file_path, length); 328 continue;
119 } 329
120 330 file_enum.GetFindInfo(&file_util_info);
121 PlatformFileError NativeMediaFileUtil::CopyOrMoveFile( 331
332 // NativeMediaFileUtil skip criteria.
333 if (ShouldSkip(platform_path))
334 continue;
335 if (!file_util::FileEnumerator::IsDirectory(file_util_info) &&
336 !GetMediaPathFilter(context)->Match(platform_path))
337 continue;
338
339 fileapi::DirectoryEntry entry;
340 entry.is_directory = file_util::FileEnumerator::IsDirectory(file_util_info);
341 entry.name = platform_path.BaseName().value();
342 entry.size = file_util::FileEnumerator::GetFilesize(file_util_info);
343 entry.last_modified_time =
344 file_util::FileEnumerator::GetLastModifiedTime(file_util_info);
345
346 file_list->push_back(entry);
347 }
348
349 return base::PLATFORM_FILE_OK;
350 }
351
352 PlatformFileError NativeMediaFileUtil::CopyOrMoveFileSync(
122 FileSystemOperationContext* context, 353 FileSystemOperationContext* context,
123 const FileSystemURL& src_url, 354 const FileSystemURL& src_url,
124 const FileSystemURL& dest_url, 355 const FileSystemURL& dest_url,
125 bool copy) { 356 bool copy) {
357 DCHECK(IsOnTaskRunnerThread(context));
126 base::FilePath src_file_path; 358 base::FilePath src_file_path;
127 PlatformFileError error = 359 PlatformFileError error =
128 GetFilteredLocalFilePathForExistingFileOrDirectory( 360 GetFilteredLocalFilePathForExistingFileOrDirectory(
129 context, src_url, 361 context, src_url,
130 base::PLATFORM_FILE_ERROR_NOT_FOUND, 362 base::PLATFORM_FILE_ERROR_NOT_FOUND,
131 &src_file_path); 363 &src_file_path);
132 if (error != base::PLATFORM_FILE_OK) 364 if (error != base::PLATFORM_FILE_OK)
133 return error; 365 return error;
134 if (NativeFileUtil::DirectoryExists(src_file_path)) 366 if (NativeFileUtil::DirectoryExists(src_file_path))
135 return base::PLATFORM_FILE_ERROR_NOT_A_FILE; 367 return base::PLATFORM_FILE_ERROR_NOT_A_FILE;
136 368
137 base::FilePath dest_file_path; 369 base::FilePath dest_file_path;
138 error = GetLocalFilePath(context, dest_url, &dest_file_path); 370 error = GetLocalFilePath(context, dest_url, &dest_file_path);
139 if (error != base::PLATFORM_FILE_OK) 371 if (error != base::PLATFORM_FILE_OK)
140 return error; 372 return error;
141 PlatformFileInfo file_info; 373 PlatformFileInfo file_info;
142 error = NativeFileUtil::GetFileInfo(dest_file_path, &file_info); 374 error = NativeFileUtil::GetFileInfo(dest_file_path, &file_info);
143 if (error != base::PLATFORM_FILE_OK && 375 if (error != base::PLATFORM_FILE_OK &&
144 error != base::PLATFORM_FILE_ERROR_NOT_FOUND) 376 error != base::PLATFORM_FILE_ERROR_NOT_FOUND)
145 return error; 377 return error;
146 if (error == base::PLATFORM_FILE_OK && file_info.is_directory) 378 if (error == base::PLATFORM_FILE_OK && file_info.is_directory)
147 return base::PLATFORM_FILE_ERROR_INVALID_OPERATION; 379 return base::PLATFORM_FILE_ERROR_INVALID_OPERATION;
148 if (!GetMediaPathFilter(context)->Match(dest_file_path)) 380 if (!GetMediaPathFilter(context)->Match(dest_file_path))
149 return base::PLATFORM_FILE_ERROR_SECURITY; 381 return base::PLATFORM_FILE_ERROR_SECURITY;
150 382
151 return NativeFileUtil::CopyOrMoveFile(src_file_path, dest_file_path, copy); 383 return NativeFileUtil::CopyOrMoveFile(src_file_path, dest_file_path, copy);
152 } 384 }
153 385
154 PlatformFileError NativeMediaFileUtil::CopyInForeignFile( 386 PlatformFileError NativeMediaFileUtil::CopyInForeignFileSync(
155 FileSystemOperationContext* context, 387 FileSystemOperationContext* context,
156 const base::FilePath& src_file_path, 388 const base::FilePath& src_file_path,
157 const FileSystemURL& dest_url) { 389 const FileSystemURL& dest_url) {
390 DCHECK(IsOnTaskRunnerThread(context));
158 if (src_file_path.empty()) 391 if (src_file_path.empty())
159 return base::PLATFORM_FILE_ERROR_INVALID_OPERATION; 392 return base::PLATFORM_FILE_ERROR_INVALID_OPERATION;
160 393
161 base::FilePath dest_file_path; 394 base::FilePath dest_file_path;
162 PlatformFileError error = 395 PlatformFileError error =
163 GetFilteredLocalFilePath(context, dest_url, &dest_file_path); 396 GetFilteredLocalFilePath(context, dest_url, &dest_file_path);
164 if (error != base::PLATFORM_FILE_OK) 397 if (error != base::PLATFORM_FILE_OK)
165 return error; 398 return error;
166 return NativeFileUtil::CopyOrMoveFile(src_file_path, dest_file_path, true); 399 return NativeFileUtil::CopyOrMoveFile(src_file_path, dest_file_path, true);
167 } 400 }
168 401
169 PlatformFileError NativeMediaFileUtil::DeleteFile(
170 FileSystemOperationContext* context,
171 const FileSystemURL& url) {
172 base::FilePath file_path;
173 PlatformFileError error = GetLocalFilePath(context, url, &file_path);
174 if (error != base::PLATFORM_FILE_OK)
175 return error;
176 PlatformFileInfo file_info;
177 error = NativeFileUtil::GetFileInfo(file_path, &file_info);
178 if (error != base::PLATFORM_FILE_OK)
179 return error;
180 if (file_info.is_directory)
181 return base::PLATFORM_FILE_ERROR_NOT_A_FILE;
182 if (!GetMediaPathFilter(context)->Match(file_path))
183 return base::PLATFORM_FILE_ERROR_NOT_FOUND;
184 return NativeFileUtil::DeleteFile(file_path);
185 }
186
187 PlatformFileError NativeMediaFileUtil::GetFileInfo(
188 FileSystemOperationContext* context,
189 const FileSystemURL& url,
190 PlatformFileInfo* file_info,
191 base::FilePath* platform_path) {
192 DCHECK(context);
193 DCHECK(GetMediaPathFilter(context));
194 DCHECK(file_info);
195 DCHECK(platform_path);
196
197 base::PlatformFileError error =
198 IsolatedFileUtil::GetFileInfo(context, url, file_info, platform_path);
199 if (error != base::PLATFORM_FILE_OK)
200 return error;
201
202 if (file_info->is_directory ||
203 GetMediaPathFilter(context)->Match(*platform_path)) {
204 return base::PLATFORM_FILE_OK;
205 }
206 return base::PLATFORM_FILE_ERROR_NOT_FOUND;
207 }
208
209 PlatformFileError NativeMediaFileUtil::GetFilteredLocalFilePath( 402 PlatformFileError NativeMediaFileUtil::GetFilteredLocalFilePath(
210 FileSystemOperationContext* context, 403 FileSystemOperationContext* context,
211 const FileSystemURL& file_system_url, 404 const FileSystemURL& file_system_url,
212 base::FilePath* local_file_path) { 405 base::FilePath* local_file_path) {
406 DCHECK(IsOnTaskRunnerThread(context));
213 base::FilePath file_path; 407 base::FilePath file_path;
214 PlatformFileError error = 408 PlatformFileError error =
215 IsolatedFileUtil::GetLocalFilePath(context, file_system_url, &file_path); 409 GetLocalFilePath(context, file_system_url, &file_path);
216 if (error != base::PLATFORM_FILE_OK) 410 if (error != base::PLATFORM_FILE_OK)
217 return error; 411 return error;
218 if (!GetMediaPathFilter(context)->Match(file_path)) 412 if (!GetMediaPathFilter(context)->Match(file_path))
219 return base::PLATFORM_FILE_ERROR_SECURITY; 413 return base::PLATFORM_FILE_ERROR_SECURITY;
220 414
221 *local_file_path = file_path; 415 *local_file_path = file_path;
222 return base::PLATFORM_FILE_OK; 416 return base::PLATFORM_FILE_OK;
223 } 417 }
224 418
419 PlatformFileError NativeMediaFileUtil::GetFileInfoSync(
420 FileSystemOperationContext* context,
421 const FileSystemURL& url,
422 PlatformFileInfo* file_info,
423 base::FilePath* platform_path) {
424 DCHECK(IsOnTaskRunnerThread(context));
425 DCHECK(context);
426 DCHECK(file_info);
427 DCHECK(GetMediaPathFilter(context));
428
429 base::FilePath file_path;
430 PlatformFileError error = GetLocalFilePath(context, url, &file_path);
431 if (error != base::PLATFORM_FILE_OK)
432 return error;
433 if (file_util::IsLink(file_path))
434 return base::PLATFORM_FILE_ERROR_NOT_FOUND;
435 error = NativeFileUtil::GetFileInfo(file_path, file_info);
436 if (error != base::PLATFORM_FILE_OK)
437 return error;
438
439 if (platform_path)
440 *platform_path = file_path;
441 if (file_info->is_directory ||
442 GetMediaPathFilter(context)->Match(file_path)) {
443 return base::PLATFORM_FILE_OK;
444 }
445 return base::PLATFORM_FILE_ERROR_NOT_FOUND;
446 }
447
225 PlatformFileError 448 PlatformFileError
226 NativeMediaFileUtil::GetFilteredLocalFilePathForExistingFileOrDirectory( 449 NativeMediaFileUtil::GetFilteredLocalFilePathForExistingFileOrDirectory(
227 FileSystemOperationContext* context, 450 FileSystemOperationContext* context,
228 const FileSystemURL& file_system_url, 451 const FileSystemURL& file_system_url,
229 PlatformFileError failure_error, 452 PlatformFileError failure_error,
230 base::FilePath* local_file_path) { 453 base::FilePath* local_file_path) {
454 DCHECK(IsOnTaskRunnerThread(context));
231 base::FilePath file_path; 455 base::FilePath file_path;
232 PlatformFileError error = 456 PlatformFileError error =
233 GetLocalFilePath(context, file_system_url, &file_path); 457 GetLocalFilePath(context, file_system_url, &file_path);
234 if (error != base::PLATFORM_FILE_OK) 458 if (error != base::PLATFORM_FILE_OK)
235 return error; 459 return error;
236 460
237 if (!file_util::PathExists(file_path)) 461 if (!file_util::PathExists(file_path))
238 return failure_error; 462 return failure_error;
239 PlatformFileInfo file_info; 463 PlatformFileInfo file_info;
240 if (!file_util::GetFileInfo(file_path, &file_info)) 464 if (!file_util::GetFileInfo(file_path, &file_info))
241 return base::PLATFORM_FILE_ERROR_FAILED; 465 return base::PLATFORM_FILE_ERROR_FAILED;
242 466
243 if (!file_info.is_directory && 467 if (!file_info.is_directory &&
244 !GetMediaPathFilter(context)->Match(file_path)) { 468 !GetMediaPathFilter(context)->Match(file_path)) {
245 return failure_error; 469 return failure_error;
246 } 470 }
247 471
248 *local_file_path = file_path; 472 *local_file_path = file_path;
249 return base::PLATFORM_FILE_OK; 473 return base::PLATFORM_FILE_OK;
250 } 474 }
251 475
252 webkit_blob::ScopedFile NativeMediaFileUtil::CreateSnapshotFile( 476 PlatformFileError NativeMediaFileUtil::DeleteDirectorySync(
253 fileapi::FileSystemOperationContext* context, 477 FileSystemOperationContext* context,
478 const FileSystemURL& url) {
479 DCHECK(IsOnTaskRunnerThread(context));
480 base::FilePath file_path;
481 PlatformFileError error = GetLocalFilePath(context, url, &file_path);
482 if (error != base::PLATFORM_FILE_OK)
483 return error;
484 return NativeFileUtil::DeleteDirectory(file_path);
485 }
486
487 PlatformFileError NativeMediaFileUtil::CreateSnapshotFileSync(
488 FileSystemOperationContext* context,
254 const fileapi::FileSystemURL& url, 489 const fileapi::FileSystemURL& url,
255 base::PlatformFileError* error, 490 PlatformFileInfo* file_info,
256 base::PlatformFileInfo* file_info, 491 base::FilePath* platform_path,
257 base::FilePath* platform_path) { 492 scoped_refptr<webkit_blob::ShareableFileReference>* file_ref) {
258 DCHECK(IsOnTaskRunnerThread(context)); 493 DCHECK(IsOnTaskRunnerThread(context));
259 webkit_blob::ScopedFile file; 494 PlatformFileError error =
260 file = IsolatedFileUtil::CreateSnapshotFile( 495 GetFileInfoSync(context, url, file_info, platform_path);
261 context, url, error, file_info, platform_path); 496 if (error == base::PLATFORM_FILE_OK && file_info->is_directory)
262 if (*error != base::PLATFORM_FILE_OK) 497 error = base::PLATFORM_FILE_ERROR_NOT_A_FILE;
263 return file.Pass(); 498 if (error == base::PLATFORM_FILE_OK)
264 *error = IsMediaFile(*platform_path); 499 error = NativeMediaFileUtil::IsMediaFile(*platform_path);
265 if (*error == base::PLATFORM_FILE_OK) 500
266 return file.Pass(); 501 // We're just returning the local file information.
267 return webkit_blob::ScopedFile(); 502 *file_ref = scoped_refptr<webkit_blob::ShareableFileReference>();
503
504 return error;
268 } 505 }
269 506
270 // static 507 // static
271 base::PlatformFileError NativeMediaFileUtil::IsMediaFile( 508 PlatformFileError NativeMediaFileUtil::IsMediaFile(
272 const base::FilePath& path) { 509 const base::FilePath& path) {
273 base::PlatformFile file_handle; 510 base::PlatformFile file_handle;
274 const int flags = base::PLATFORM_FILE_OPEN | base::PLATFORM_FILE_READ; 511 const int flags = base::PLATFORM_FILE_OPEN | base::PLATFORM_FILE_READ;
275 base::PlatformFileError error = 512 PlatformFileError error =
276 NativeFileUtil::CreateOrOpen(path, flags, &file_handle, NULL); 513 NativeFileUtil::CreateOrOpen(path, flags, &file_handle, NULL);
277 if (error != base::PLATFORM_FILE_OK) 514 if (error != base::PLATFORM_FILE_OK)
278 return error; 515 return error;
279 516
280 ScopedPlatformFile scoped_platform_file(&file_handle); 517 ScopedPlatformFile scoped_platform_file(&file_handle);
281 char buffer[net::kMaxBytesToSniff]; 518 char buffer[net::kMaxBytesToSniff];
282 519
283 // Read as much as net::SniffMimeTypeFromLocalData() will bother looking at. 520 // Read as much as net::SniffMimeTypeFromLocalData() will bother looking at.
284 int64 len = 521 int64 len =
285 base::ReadPlatformFile(file_handle, 0, buffer, net::kMaxBytesToSniff); 522 base::ReadPlatformFile(file_handle, 0, buffer, net::kMaxBytesToSniff);
286 if (len < 0) 523 if (len < 0)
287 return base::PLATFORM_FILE_ERROR_FAILED; 524 return base::PLATFORM_FILE_ERROR_FAILED;
288 if (len == 0) 525 if (len == 0)
289 return base::PLATFORM_FILE_ERROR_SECURITY; 526 return base::PLATFORM_FILE_ERROR_SECURITY;
290 527
291 std::string mime_type; 528 std::string mime_type;
292 if (!net::SniffMimeTypeFromLocalData(buffer, len, &mime_type)) 529 if (!net::SniffMimeTypeFromLocalData(buffer, len, &mime_type))
293 return base::PLATFORM_FILE_ERROR_SECURITY; 530 return base::PLATFORM_FILE_ERROR_SECURITY;
294 531
295 if (StartsWithASCII(mime_type, "image/", true) || 532 if (StartsWithASCII(mime_type, "image/", true) ||
296 StartsWithASCII(mime_type, "audio/", true) || 533 StartsWithASCII(mime_type, "audio/", true) ||
297 StartsWithASCII(mime_type, "video/", true) || 534 StartsWithASCII(mime_type, "video/", true) ||
298 mime_type == "application/x-shockwave-flash") { 535 mime_type == "application/x-shockwave-flash") {
299 return base::PLATFORM_FILE_OK; 536 return base::PLATFORM_FILE_OK;
300 } 537 }
301 return base::PLATFORM_FILE_ERROR_SECURITY; 538 return base::PLATFORM_FILE_ERROR_SECURITY;
302 } 539 }
303 540
541 void NativeMediaFileUtil::GetFileInfoOnTaskRunnerThread(
542 FileSystemOperationContext* context,
543 const FileSystemURL& url,
544 const GetFileInfoCallback& callback) {
545 DCHECK(IsOnTaskRunnerThread(context));
546 PlatformFileInfo file_info;
547 base::FilePath platform_path;
548 PlatformFileError error =
549 GetFileInfoSync(context, url, &file_info, &platform_path);
550 content::BrowserThread::PostTask(
551 content::BrowserThread::IO,
552 FROM_HERE,
553 Bind(callback, error, file_info, platform_path));
554 }
555
556 void NativeMediaFileUtil::ReadDirectoryOnTaskRunnerThread(
557 FileSystemOperationContext* context,
558 const FileSystemURL& url,
559 const ReadDirectoryCallback& callback) {
560 DCHECK(IsOnTaskRunnerThread(context));
561 EntryList entry_list;
562 PlatformFileError error =
563 ReadDirectorySync(context, url, &entry_list);
564 content::BrowserThread::PostTask(
565 content::BrowserThread::IO,
566 FROM_HERE,
567 Bind(callback, error, entry_list, false /* has_more */));
568 }
569
570 void NativeMediaFileUtil::CreateSnapshotFileOnTaskRunnerThread(
571 FileSystemOperationContext* context,
572 const FileSystemURL& url,
573 const CreateSnapshotFileCallback& callback) {
574 DCHECK(IsOnTaskRunnerThread(context));
575 PlatformFileInfo file_info;
576 base::FilePath platform_path;
577 scoped_refptr<webkit_blob::ShareableFileReference> file_ref;
578 PlatformFileError error =
579 CreateSnapshotFileSync(context, url, &file_info, &platform_path,
580 &file_ref);
581 content::BrowserThread::PostTask(
582 content::BrowserThread::IO,
583 FROM_HERE,
584 Bind(callback, error, file_info, platform_path, file_ref));
585 }
586
304 } // namespace chrome 587 } // namespace chrome
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698