Index: webkit/fileapi/sandbox_mount_point_provider.cc |
diff --git a/webkit/fileapi/sandbox_mount_point_provider.cc b/webkit/fileapi/sandbox_mount_point_provider.cc |
index 95edc813ca631c4977433dbfefb8fce17f5af6a3..c0b65f2a1087e70dca05a83d5b837553cf47e973 100644 |
--- a/webkit/fileapi/sandbox_mount_point_provider.cc |
+++ b/webkit/fileapi/sandbox_mount_point_provider.cc |
@@ -16,6 +16,7 @@ |
#include "base/metrics/histogram.h" |
#include "googleurl/src/gurl.h" |
#include "net/base/net_util.h" |
+#include "webkit/fileapi/file_system_operation.h" |
#include "webkit/fileapi/file_system_operation_context.h" |
#include "webkit/fileapi/file_system_options.h" |
#include "webkit/fileapi/file_system_types.h" |
@@ -28,6 +29,8 @@ |
using quota::QuotaManagerProxy; |
+namespace fileapi { |
+ |
namespace { |
const char kChromeScheme[] = "chrome"; |
@@ -96,10 +99,9 @@ base::PlatformFileError OldReadOriginDirectory(const FilePath& base_path, |
} |
class ObfuscatedOriginEnumerator |
- : public fileapi::SandboxMountPointProvider::OriginEnumerator { |
+ : public SandboxMountPointProvider::OriginEnumerator { |
public: |
- explicit ObfuscatedOriginEnumerator( |
- fileapi::ObfuscatedFileUtil* file_util) { |
+ explicit ObfuscatedOriginEnumerator(ObfuscatedFileUtil* file_util) { |
enum_.reset(file_util->CreateOriginEnumerator()); |
} |
virtual ~ObfuscatedOriginEnumerator() {} |
@@ -113,11 +115,11 @@ class ObfuscatedOriginEnumerator |
} |
private: |
- scoped_ptr<fileapi::ObfuscatedFileUtil::AbstractOriginEnumerator> enum_; |
+ scoped_ptr<ObfuscatedFileUtil::AbstractOriginEnumerator> enum_; |
}; |
class OldSandboxOriginEnumerator |
- : public fileapi::SandboxMountPointProvider::OriginEnumerator { |
+ : public SandboxMountPointProvider::OriginEnumerator { |
public: |
explicit OldSandboxOriginEnumerator(const FilePath& base_path) |
: enumerator_(base_path, false /* recursive */, |
@@ -128,8 +130,7 @@ class OldSandboxOriginEnumerator |
current_ = enumerator_.Next(); |
if (current_.empty()) |
return GURL(); |
- return fileapi::GetOriginURLFromIdentifier( |
- current_.BaseName().MaybeAsASCII()); |
+ return GetOriginURLFromIdentifier(current_.BaseName().MaybeAsASCII()); |
} |
virtual bool HasFileSystemType(fileapi::FileSystemType type) const OVERRIDE { |
@@ -148,7 +149,7 @@ class OldSandboxOriginEnumerator |
FilePath OldGetBaseDirectoryForOrigin( |
const FilePath& old_base_path, |
const GURL& origin_url) { |
- std::string id = fileapi::GetOriginIdentifierFromURL(origin_url); |
+ std::string id = GetOriginIdentifierFromURL(origin_url); |
if (!id.empty()) |
return old_base_path.AppendASCII(id); |
return FilePath(); |
@@ -172,7 +173,7 @@ FilePath OldGetBaseDirectoryForOriginAndType( |
} |
bool MigrateOneOldFileSystem( |
- fileapi::ObfuscatedFileUtil* file_util, |
+ ObfuscatedFileUtil* file_util, |
const FilePath& old_base_path, const GURL& origin, |
fileapi::FileSystemType type) { |
FilePath base_path = OldGetBaseDirectoryForOriginAndType( |
@@ -201,7 +202,7 @@ bool MigrateOneOldFileSystem( |
} |
void MigrateAllOldFileSystems( |
- fileapi::ObfuscatedFileUtil* file_util, |
+ ObfuscatedFileUtil* file_util, |
const FilePath& old_base_path) { |
scoped_ptr<OldSandboxOriginEnumerator> old_origins( |
new OldSandboxOriginEnumerator(old_base_path)); |
@@ -209,15 +210,15 @@ void MigrateAllOldFileSystems( |
int failures = 0; |
while (!(origin = old_origins->Next()).is_empty()) { |
int failures_this_origin = 0; |
- if (old_origins->HasFileSystemType(fileapi::kFileSystemTypeTemporary) && |
+ if (old_origins->HasFileSystemType(kFileSystemTypeTemporary) && |
!MigrateOneOldFileSystem( |
file_util, old_base_path, origin, |
- fileapi::kFileSystemTypeTemporary)) |
+ kFileSystemTypeTemporary)) |
++failures_this_origin; |
- if (old_origins->HasFileSystemType(fileapi::kFileSystemTypePersistent) && |
+ if (old_origins->HasFileSystemType(kFileSystemTypePersistent) && |
!MigrateOneOldFileSystem( |
file_util, old_base_path, origin, |
- fileapi::kFileSystemTypePersistent)) |
+ kFileSystemTypePersistent)) |
++failures_this_origin; |
if (!failures_this_origin) { |
FilePath origin_base_path = |
@@ -238,7 +239,7 @@ void MigrateAllOldFileSystems( |
// necessary. |
FilePath new_path = |
old_base_path.DirName().Append( |
- fileapi::SandboxMountPointProvider::kRenamedOldFileSystemDirectory); |
+ SandboxMountPointProvider::kRenamedOldFileSystemDirectory); |
file_util::ReplaceFile(old_base_path, new_path); |
} |
} |
@@ -250,15 +251,45 @@ void MigrateAllOldFileSystems( |
// to look up the filesystem's root, so we can take care of most of them by |
// putting a check there. |
void MigrateIfNeeded( |
- fileapi::ObfuscatedFileUtil* file_util, |
+ ObfuscatedFileUtil* file_util, |
const FilePath& old_base_path) { |
if (file_util::DirectoryExists(old_base_path)) |
MigrateAllOldFileSystems(file_util, old_base_path); |
} |
-} // anonymous namespace |
+void PassPointerErrorByValue( |
+ const base::Callback<void(PlatformFileError)>& callback, |
+ PlatformFileError* error_ptr) { |
+ DCHECK(error_ptr); |
+ callback.Run(*error_ptr); |
+} |
-namespace fileapi { |
+void ValidateRootOnFileThread(ObfuscatedFileUtil* file_util, |
+ const GURL& origin_url, |
+ FileSystemType type, |
+ const FilePath& old_base_path, |
+ bool create, |
+ base::PlatformFileError* error_ptr) { |
+ DCHECK(error_ptr); |
+ MigrateIfNeeded(file_util, old_base_path); |
+ FilePath root_path = |
+ file_util->GetDirectoryForOriginAndType(origin_url, type, create); |
+ if (root_path.empty()) { |
+ UMA_HISTOGRAM_ENUMERATION(kOpenFileSystem, |
+ kCreateDirectoryError, |
+ kFileSystemErrorMax); |
+ // TODO(kinuko): We should return appropriate error code. |
+ *error_ptr = base::PLATFORM_FILE_ERROR_FAILED; |
+ } else { |
+ UMA_HISTOGRAM_ENUMERATION(kOpenFileSystem, kOK, kFileSystemErrorMax); |
+ *error_ptr = base::PLATFORM_FILE_OK; |
+ } |
+ // The reference of file_util will be derefed on the FILE thread |
+ // when the storage of this callback gets deleted regardless of whether |
+ // this method is called or not. |
+} |
+ |
+} // anonymous namespace |
const FilePath::CharType SandboxMountPointProvider::kOldFileSystemDirectory[] = |
FILE_PATH_LITERAL("FileSystem"); |
@@ -270,85 +301,6 @@ const FilePath::CharType |
SandboxMountPointProvider::kRenamedOldFileSystemDirectory[] = |
FILE_PATH_LITERAL("FS.old"); |
-class SandboxMountPointProvider::GetFileSystemRootPathTask |
- : public base::RefCountedThreadSafe< |
- SandboxMountPointProvider::GetFileSystemRootPathTask> { |
- public: |
- GetFileSystemRootPathTask( |
- scoped_refptr<base::MessageLoopProxy> file_message_loop, |
- const GURL& origin_url, |
- FileSystemType type, |
- ObfuscatedFileUtil* file_util, |
- const FilePath& old_base_path, |
- const FileSystemMountPointProvider::GetRootPathCallback& callback) |
- : file_message_loop_(file_message_loop), |
- origin_message_loop_proxy_( |
- base::MessageLoopProxy::current()), |
- origin_url_(origin_url), |
- type_(type), |
- file_util_(file_util), |
- old_base_path_(old_base_path), |
- callback_(callback) { |
- } |
- |
- virtual ~GetFileSystemRootPathTask() { |
- // Just in case we get deleted without running, make sure to clean up the |
- // file_util_ on the right thread. |
- if (file_util_.get() && !file_message_loop_->BelongsToCurrentThread()) |
- file_message_loop_->ReleaseSoon(FROM_HERE, file_util_.release()); |
- } |
- |
- void Start(bool create) { |
- file_message_loop_->PostTask( |
- FROM_HERE, |
- base::Bind( |
- &GetFileSystemRootPathTask::GetFileSystemRootPathOnFileThread, this, |
- create)); |
- } |
- |
- private: |
- void GetFileSystemRootPathOnFileThread(bool create) { |
- MigrateIfNeeded(file_util_, old_base_path_); |
- DispatchCallbackOnCallerThread( |
- file_util_->GetDirectoryForOriginAndType(origin_url_, type_, create)); |
- // We must clear the reference on the file thread. |
- file_util_ = NULL; |
- } |
- |
- void DispatchCallbackOnCallerThread(const FilePath& root_path) { |
- if (root_path.empty()) { |
- UMA_HISTOGRAM_ENUMERATION(kOpenFileSystem, |
- kCreateDirectoryError, |
- kFileSystemErrorMax); |
- } |
- origin_message_loop_proxy_->PostTask( |
- FROM_HERE, |
- base::Bind(&GetFileSystemRootPathTask::DispatchCallback, this, |
- root_path)); |
- } |
- |
- void DispatchCallback(const FilePath& root_path) { |
- std::string origin_identifier = GetOriginIdentifierFromURL(origin_url_); |
- std::string type_string = GetFileSystemTypeString(type_); |
- DCHECK(!type_string.empty()); |
- std::string name = origin_identifier + ":" + type_string; |
- |
- if (!root_path.empty()) |
- UMA_HISTOGRAM_ENUMERATION(kOpenFileSystem, kOK, kFileSystemErrorMax); |
- |
- callback_.Run(!root_path.empty(), root_path, name); |
- callback_.Reset(); |
- } |
- |
- scoped_refptr<base::MessageLoopProxy> file_message_loop_; |
- scoped_refptr<base::MessageLoopProxy> origin_message_loop_proxy_; |
- GURL origin_url_; |
- FileSystemType type_; |
- scoped_refptr<ObfuscatedFileUtil> file_util_; |
- FilePath old_base_path_; |
- FileSystemMountPointProvider::GetRootPathCallback callback_; |
-}; |
- |
SandboxMountPointProvider::SandboxMountPointProvider( |
scoped_refptr<base::MessageLoopProxy> file_message_loop, |
const FilePath& profile_path, |
@@ -368,24 +320,12 @@ SandboxMountPointProvider::~SandboxMountPointProvider() { |
file_message_loop_->ReleaseSoon(FROM_HERE, sandbox_file_util_.release()); |
} |
-bool SandboxMountPointProvider::IsAccessAllowed(const GURL& origin_url, |
- FileSystemType type, |
- const FilePath& unused) { |
- if (type != kFileSystemTypeTemporary && type != kFileSystemTypePersistent) |
- return false; |
- // We essentially depend on quota to do our access controls, so here |
- // we only check if the requested scheme is allowed or not. |
- return IsAllowedScheme(origin_url); |
-} |
- |
-void SandboxMountPointProvider::ValidateFileSystemRootAndGetURL( |
+void SandboxMountPointProvider::ValidateFileSystemRoot( |
const GURL& origin_url, fileapi::FileSystemType type, bool create, |
- const FileSystemMountPointProvider::GetRootPathCallback& callback) { |
- FilePath origin_base_path; |
- |
+ const ValidateFileSystemCallback& callback) { |
if (file_system_options_.is_incognito()) { |
// TODO(kinuko): return an isolated temporary directory. |
- callback.Run(false, FilePath(), std::string()); |
+ callback.Run(base::PLATFORM_FILE_ERROR_SECURITY); |
UMA_HISTOGRAM_ENUMERATION(kOpenFileSystem, |
kIncognito, |
kFileSystemErrorMax); |
@@ -393,22 +333,26 @@ void SandboxMountPointProvider::ValidateFileSystemRootAndGetURL( |
} |
if (!IsAllowedScheme(origin_url)) { |
- callback.Run(false, FilePath(), std::string()); |
+ callback.Run(base::PLATFORM_FILE_ERROR_SECURITY); |
UMA_HISTOGRAM_ENUMERATION(kOpenFileSystem, |
kInvalidScheme, |
kFileSystemErrorMax); |
return; |
} |
- scoped_refptr<GetFileSystemRootPathTask> task( |
- new GetFileSystemRootPathTask( |
- file_message_loop_, origin_url, type, sandbox_file_util_.get(), |
- old_base_path(), callback)); |
- task->Start(create); |
+ base::PlatformFileError* error_ptr = new base::PlatformFileError; |
+ file_message_loop_->PostTaskAndReply( |
+ FROM_HERE, |
+ base::Bind(&ValidateRootOnFileThread, |
+ sandbox_file_util_, |
+ origin_url, type, old_base_path(), create, |
+ base::Unretained(error_ptr)), |
+ base::Bind(base::Bind(&PassPointerErrorByValue, callback), |
+ base::Owned(error_ptr))); |
}; |
FilePath |
-SandboxMountPointProvider::ValidateFileSystemRootAndGetPathOnFileThread( |
+SandboxMountPointProvider::GetFileSystemRootPathOnFileThread( |
const GURL& origin_url, FileSystemType type, const FilePath& unused, |
bool create) { |
if (file_system_options_.is_incognito()) |
@@ -424,6 +368,16 @@ SandboxMountPointProvider::ValidateFileSystemRootAndGetPathOnFileThread( |
origin_url, type, create); |
} |
+bool SandboxMountPointProvider::IsAccessAllowed(const GURL& origin_url, |
+ FileSystemType type, |
+ const FilePath& unused) { |
+ if (type != kFileSystemTypeTemporary && type != kFileSystemTypePersistent) |
+ return false; |
+ // We essentially depend on quota to do our access controls, so here |
+ // we only check if the requested scheme is allowed or not. |
+ return IsAllowedScheme(origin_url); |
+} |
+ |
bool SandboxMountPointProvider::IsRestrictedFileName(const FilePath& filename) |
const { |
if (filename.value().empty()) |
@@ -504,8 +458,8 @@ bool SandboxMountPointProvider::DeleteOriginDataOnFileThread( |
void SandboxMountPointProvider::GetOriginsForTypeOnFileThread( |
fileapi::FileSystemType type, std::set<GURL>* origins) { |
- DCHECK(type == fileapi::kFileSystemTypeTemporary || |
- type == fileapi::kFileSystemTypePersistent); |
+ DCHECK(type == kFileSystemTypeTemporary || |
+ type == kFileSystemTypePersistent); |
DCHECK(origins); |
scoped_ptr<OriginEnumerator> enumerator(CreateOriginEnumerator()); |
GURL origin; |
@@ -518,8 +472,8 @@ void SandboxMountPointProvider::GetOriginsForTypeOnFileThread( |
void SandboxMountPointProvider::GetOriginsForHostOnFileThread( |
fileapi::FileSystemType type, const std::string& host, |
std::set<GURL>* origins) { |
- DCHECK(type == fileapi::kFileSystemTypeTemporary || |
- type == fileapi::kFileSystemTypePersistent); |
+ DCHECK(type == kFileSystemTypeTemporary || |
+ type == kFileSystemTypePersistent); |
DCHECK(origins); |
scoped_ptr<OriginEnumerator> enumerator(CreateOriginEnumerator()); |
GURL origin; |
@@ -532,8 +486,8 @@ void SandboxMountPointProvider::GetOriginsForHostOnFileThread( |
int64 SandboxMountPointProvider::GetOriginUsageOnFileThread( |
const GURL& origin_url, fileapi::FileSystemType type) { |
- DCHECK(type == fileapi::kFileSystemTypeTemporary || |
- type == fileapi::kFileSystemTypePersistent); |
+ DCHECK(type == kFileSystemTypeTemporary || |
+ type == kFileSystemTypePersistent); |
FilePath base_path = |
GetBaseDirectoryForOriginAndType(origin_url, type, false); |
if (base_path.empty() || !file_util::DirectoryExists(base_path)) return 0; |
@@ -576,8 +530,8 @@ int64 SandboxMountPointProvider::GetOriginUsageOnFileThread( |
void SandboxMountPointProvider::NotifyOriginWasAccessedOnIOThread( |
QuotaManagerProxy* proxy, const GURL& origin_url, |
fileapi::FileSystemType type) { |
- DCHECK(type == fileapi::kFileSystemTypeTemporary || |
- type == fileapi::kFileSystemTypePersistent); |
+ DCHECK(type == kFileSystemTypeTemporary || |
+ type == kFileSystemTypePersistent); |
if (proxy) { |
proxy->NotifyStorageAccessed( |
quota::QuotaClient::kFileSystem, |
@@ -589,8 +543,8 @@ void SandboxMountPointProvider::NotifyOriginWasAccessedOnIOThread( |
void SandboxMountPointProvider::UpdateOriginUsageOnFileThread( |
QuotaManagerProxy* proxy, const GURL& origin_url, |
fileapi::FileSystemType type, int64 delta) { |
- DCHECK(type == fileapi::kFileSystemTypeTemporary || |
- type == fileapi::kFileSystemTypePersistent); |
+ DCHECK(type == kFileSystemTypeTemporary || |
+ type == kFileSystemTypePersistent); |
FilePath usage_file_path = GetUsageCachePathForOriginAndType( |
origin_url, type); |
DCHECK(!usage_file_path.empty()); |
@@ -607,8 +561,8 @@ void SandboxMountPointProvider::UpdateOriginUsageOnFileThread( |
void SandboxMountPointProvider::StartUpdateOriginOnFileThread( |
const GURL& origin_url, fileapi::FileSystemType type) { |
- DCHECK(type == fileapi::kFileSystemTypeTemporary || |
- type == fileapi::kFileSystemTypePersistent); |
+ DCHECK(type == kFileSystemTypeTemporary || |
+ type == kFileSystemTypePersistent); |
FilePath usage_file_path = GetUsageCachePathForOriginAndType( |
origin_url, type); |
FileSystemUsageCache::IncrementDirty(usage_file_path); |
@@ -616,8 +570,8 @@ void SandboxMountPointProvider::StartUpdateOriginOnFileThread( |
void SandboxMountPointProvider::EndUpdateOriginOnFileThread( |
const GURL& origin_url, fileapi::FileSystemType type) { |
- DCHECK(type == fileapi::kFileSystemTypeTemporary || |
- type == fileapi::kFileSystemTypePersistent); |
+ DCHECK(type == kFileSystemTypeTemporary || |
+ type == kFileSystemTypePersistent); |
FilePath usage_file_path = GetUsageCachePathForOriginAndType( |
origin_url, type); |
FileSystemUsageCache::DecrementDirty(usage_file_path); |
@@ -625,8 +579,8 @@ void SandboxMountPointProvider::EndUpdateOriginOnFileThread( |
void SandboxMountPointProvider::InvalidateUsageCache( |
const GURL& origin_url, fileapi::FileSystemType type) { |
- DCHECK(type == fileapi::kFileSystemTypeTemporary || |
- type == fileapi::kFileSystemTypePersistent); |
+ DCHECK(type == kFileSystemTypeTemporary || |
+ type == kFileSystemTypePersistent); |
FilePath usage_file_path = GetUsageCachePathForOriginAndType( |
origin_url, type); |
FileSystemUsageCache::IncrementDirty(usage_file_path); |