OLD | NEW |
(Empty) | |
| 1 // Copyright 2015 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 #include "chrome/browser/chromeos/file_system_provider/throttled_file_system.h" |
| 6 |
| 7 #include <limits> |
| 8 #include <vector> |
| 9 |
| 10 #include "base/files/file.h" |
| 11 #include "chrome/browser/chromeos/file_system_provider/queue.h" |
| 12 |
| 13 namespace chromeos { |
| 14 namespace file_system_provider { |
| 15 |
| 16 ThrottledFileSystem::ThrottledFileSystem( |
| 17 scoped_ptr<ProvidedFileSystemInterface> file_system) |
| 18 : file_system_(file_system.Pass()), weak_ptr_factory_(this) { |
| 19 const int opened_files_limit = |
| 20 file_system_->GetFileSystemInfo().opened_files_limit(); |
| 21 open_queue_.reset(opened_files_limit |
| 22 ? new Queue(static_cast<size_t>(opened_files_limit)) |
| 23 : new Queue(std::numeric_limits<size_t>::max())); |
| 24 } |
| 25 |
| 26 ThrottledFileSystem::~ThrottledFileSystem() { |
| 27 } |
| 28 |
| 29 AbortCallback ThrottledFileSystem::RequestUnmount( |
| 30 const storage::AsyncFileUtil::StatusCallback& callback) { |
| 31 return file_system_->RequestUnmount(callback); |
| 32 } |
| 33 |
| 34 AbortCallback ThrottledFileSystem::GetMetadata( |
| 35 const base::FilePath& entry_path, |
| 36 MetadataFieldMask fields, |
| 37 const GetMetadataCallback& callback) { |
| 38 return file_system_->GetMetadata(entry_path, fields, callback); |
| 39 } |
| 40 |
| 41 AbortCallback ThrottledFileSystem::ReadDirectory( |
| 42 const base::FilePath& directory_path, |
| 43 const storage::AsyncFileUtil::ReadDirectoryCallback& callback) { |
| 44 return file_system_->ReadDirectory(directory_path, callback); |
| 45 } |
| 46 |
| 47 AbortCallback ThrottledFileSystem::ReadFile( |
| 48 int file_handle, |
| 49 net::IOBuffer* buffer, |
| 50 int64 offset, |
| 51 int length, |
| 52 const ReadChunkReceivedCallback& callback) { |
| 53 return file_system_->ReadFile(file_handle, buffer, offset, length, callback); |
| 54 } |
| 55 |
| 56 AbortCallback ThrottledFileSystem::OpenFile(const base::FilePath& file_path, |
| 57 OpenFileMode mode, |
| 58 const OpenFileCallback& callback) { |
| 59 const size_t task_token = open_queue_->NewToken(); |
| 60 return open_queue_->Enqueue( |
| 61 task_token, |
| 62 base::Bind( |
| 63 &ProvidedFileSystemInterface::OpenFile, |
| 64 base::Unretained(file_system_.get()), // Outlives the queue. |
| 65 file_path, mode, |
| 66 base::Bind(&ThrottledFileSystem::OnOpenFileCompleted, |
| 67 weak_ptr_factory_.GetWeakPtr(), task_token, callback))); |
| 68 } |
| 69 |
| 70 AbortCallback ThrottledFileSystem::CloseFile( |
| 71 int file_handle, |
| 72 const storage::AsyncFileUtil::StatusCallback& callback) { |
| 73 return file_system_->CloseFile( |
| 74 file_handle, |
| 75 base::Bind(&ThrottledFileSystem::OnCloseFileCompleted, |
| 76 weak_ptr_factory_.GetWeakPtr(), file_handle, callback)); |
| 77 } |
| 78 |
| 79 AbortCallback ThrottledFileSystem::CreateDirectory( |
| 80 const base::FilePath& directory_path, |
| 81 bool recursive, |
| 82 const storage::AsyncFileUtil::StatusCallback& callback) { |
| 83 return file_system_->CreateDirectory(directory_path, recursive, callback); |
| 84 } |
| 85 |
| 86 AbortCallback ThrottledFileSystem::DeleteEntry( |
| 87 const base::FilePath& entry_path, |
| 88 bool recursive, |
| 89 const storage::AsyncFileUtil::StatusCallback& callback) { |
| 90 return file_system_->DeleteEntry(entry_path, recursive, callback); |
| 91 } |
| 92 |
| 93 AbortCallback ThrottledFileSystem::CreateFile( |
| 94 const base::FilePath& file_path, |
| 95 const storage::AsyncFileUtil::StatusCallback& callback) { |
| 96 return file_system_->CreateFile(file_path, callback); |
| 97 } |
| 98 |
| 99 AbortCallback ThrottledFileSystem::CopyEntry( |
| 100 const base::FilePath& source_path, |
| 101 const base::FilePath& target_path, |
| 102 const storage::AsyncFileUtil::StatusCallback& callback) { |
| 103 return file_system_->CopyEntry(source_path, target_path, callback); |
| 104 } |
| 105 |
| 106 AbortCallback ThrottledFileSystem::WriteFile( |
| 107 int file_handle, |
| 108 net::IOBuffer* buffer, |
| 109 int64 offset, |
| 110 int length, |
| 111 const storage::AsyncFileUtil::StatusCallback& callback) { |
| 112 return file_system_->WriteFile(file_handle, buffer, offset, length, callback); |
| 113 } |
| 114 |
| 115 AbortCallback ThrottledFileSystem::MoveEntry( |
| 116 const base::FilePath& source_path, |
| 117 const base::FilePath& target_path, |
| 118 const storage::AsyncFileUtil::StatusCallback& callback) { |
| 119 return file_system_->MoveEntry(source_path, target_path, callback); |
| 120 } |
| 121 |
| 122 AbortCallback ThrottledFileSystem::Truncate( |
| 123 const base::FilePath& file_path, |
| 124 int64 length, |
| 125 const storage::AsyncFileUtil::StatusCallback& callback) { |
| 126 return file_system_->Truncate(file_path, length, callback); |
| 127 } |
| 128 |
| 129 AbortCallback ThrottledFileSystem::AddWatcher( |
| 130 const GURL& origin, |
| 131 const base::FilePath& entry_path, |
| 132 bool recursive, |
| 133 bool persistent, |
| 134 const storage::AsyncFileUtil::StatusCallback& callback, |
| 135 const storage::WatcherManager::NotificationCallback& |
| 136 notification_callback) { |
| 137 return file_system_->AddWatcher(origin, entry_path, recursive, persistent, |
| 138 callback, notification_callback); |
| 139 } |
| 140 |
| 141 void ThrottledFileSystem::RemoveWatcher( |
| 142 const GURL& origin, |
| 143 const base::FilePath& entry_path, |
| 144 bool recursive, |
| 145 const storage::AsyncFileUtil::StatusCallback& callback) { |
| 146 file_system_->RemoveWatcher(origin, entry_path, recursive, callback); |
| 147 } |
| 148 |
| 149 const ProvidedFileSystemInfo& ThrottledFileSystem::GetFileSystemInfo() const { |
| 150 return file_system_->GetFileSystemInfo(); |
| 151 } |
| 152 |
| 153 RequestManager* ThrottledFileSystem::GetRequestManager() { |
| 154 return file_system_->GetRequestManager(); |
| 155 } |
| 156 |
| 157 Watchers* ThrottledFileSystem::GetWatchers() { |
| 158 return file_system_->GetWatchers(); |
| 159 } |
| 160 |
| 161 void ThrottledFileSystem::AddObserver(ProvidedFileSystemObserver* observer) { |
| 162 file_system_->AddObserver(observer); |
| 163 } |
| 164 |
| 165 void ThrottledFileSystem::RemoveObserver(ProvidedFileSystemObserver* observer) { |
| 166 file_system_->RemoveObserver(observer); |
| 167 } |
| 168 |
| 169 void ThrottledFileSystem::Notify( |
| 170 const base::FilePath& entry_path, |
| 171 bool recursive, |
| 172 storage::WatcherManager::ChangeType change_type, |
| 173 scoped_ptr<ProvidedFileSystemObserver::Changes> changes, |
| 174 const std::string& tag, |
| 175 const storage::AsyncFileUtil::StatusCallback& callback) { |
| 176 return file_system_->Notify(entry_path, recursive, change_type, |
| 177 changes.Pass(), tag, callback); |
| 178 } |
| 179 |
| 180 base::WeakPtr<ProvidedFileSystemInterface> ThrottledFileSystem::GetWeakPtr() { |
| 181 return weak_ptr_factory_.GetWeakPtr(); |
| 182 } |
| 183 |
| 184 void ThrottledFileSystem::OnOpenFileCompleted(int queue_token, |
| 185 const OpenFileCallback& callback, |
| 186 int file_handle, |
| 187 base::File::Error result) { |
| 188 open_queue_->Complete(queue_token); |
| 189 |
| 190 // If the file is opened successfully then hold the queue token until the file |
| 191 // is closed. |
| 192 if (result == base::File::FILE_OK) |
| 193 opened_files_[file_handle] = queue_token; |
| 194 else |
| 195 open_queue_->Remove(queue_token); |
| 196 |
| 197 callback.Run(file_handle, result); |
| 198 } |
| 199 |
| 200 void ThrottledFileSystem::OnCloseFileCompleted( |
| 201 int file_handle, |
| 202 const storage::AsyncFileUtil::StatusCallback& callback, |
| 203 base::File::Error result) { |
| 204 // Closing is always final. Even if an error happened, the file is considered |
| 205 // closed on the C++ side. Release the task from the queue, so other files |
| 206 // which are enqueued can be opened. |
| 207 const auto it = opened_files_.find(file_handle); |
| 208 DCHECK(it != opened_files_.end()); |
| 209 |
| 210 const int queue_token = it->second; |
| 211 open_queue_->Remove(queue_token); |
| 212 opened_files_.erase(file_handle); |
| 213 |
| 214 callback.Run(result); |
| 215 } |
| 216 |
| 217 } // namespace file_system_provider |
| 218 } // namespace chromeos |
OLD | NEW |