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

Side by Side Diff: components/leveldb/leveldb_mojo_proxy.cc

Issue 1839823002: mojo leveldb: Remove the created file thread. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: And cut out manual Signal()ing most places. Created 4 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
« no previous file with comments | « components/leveldb/leveldb_mojo_proxy.h ('k') | components/leveldb/leveldb_service_impl.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 // Copyright 2016 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 "components/leveldb/leveldb_mojo_proxy.h"
6
7 #include <set>
8
9 #include "base/bind.h"
10 #include "base/callback.h"
11 #include "mojo/message_pump/message_pump_mojo.h"
12 #include "mojo/platform_handle/platform_handle_functions.h"
13 #include "mojo/public/cpp/bindings/interface_request.h"
14
15 namespace leveldb {
16
17 struct LevelDBMojoProxy::OpaqueLock {
18 filesystem::FilePtr lock_file;
19 };
20
21 struct LevelDBMojoProxy::OpaqueDir {
22 explicit OpaqueDir(
23 mojo::InterfacePtrInfo<filesystem::Directory> directory_info) {
24 directory.Bind(std::move(directory_info));
25 }
26
27 filesystem::DirectoryPtr directory;
28 };
29
30 LevelDBMojoProxy::LevelDBMojoProxy(
31 scoped_refptr<base::SingleThreadTaskRunner> task_runner)
32 : task_runner_(std::move(task_runner)), outstanding_opaque_dirs_(0) {}
33
34 LevelDBMojoProxy::OpaqueDir* LevelDBMojoProxy::RegisterDirectory(
35 filesystem::DirectoryPtr directory) {
36 OpaqueDir* out_dir = nullptr;
37 RunInternal(base::Bind(&LevelDBMojoProxy::RegisterDirectoryImpl, this,
38 base::Passed(directory.PassInterface()),
39 &out_dir));
40
41 return out_dir;
42 }
43
44 void LevelDBMojoProxy::UnregisterDirectory(OpaqueDir* dir) {
45 RunInternal(base::Bind(&LevelDBMojoProxy::UnregisterDirectoryImpl,
46 this, dir));
47 }
48
49 base::File LevelDBMojoProxy::OpenFileHandle(OpaqueDir* dir,
50 const std::string& name,
51 uint32_t open_flags) {
52 base::File file;
53 RunInternal(base::Bind(&LevelDBMojoProxy::OpenFileHandleImpl, this, dir,
54 name, open_flags, &file));
55 return file;
56 }
57
58 filesystem::FileError LevelDBMojoProxy::SyncDirectory(OpaqueDir* dir,
59 const std::string& name) {
60 filesystem::FileError error = filesystem::FileError::FAILED;
61 RunInternal(base::Bind(&LevelDBMojoProxy::SyncDirectoryImpl, this, dir,
62 name, &error));
63 return error;
64 }
65
66 bool LevelDBMojoProxy::FileExists(OpaqueDir* dir, const std::string& name) {
67 bool exists = false;
68 RunInternal(base::Bind(&LevelDBMojoProxy::FileExistsImpl, this, dir,
69 name, &exists));
70 return exists;
71 }
72
73 filesystem::FileError LevelDBMojoProxy::GetChildren(
74 OpaqueDir* dir,
75 const std::string& path,
76 std::vector<std::string>* result) {
77 filesystem::FileError error = filesystem::FileError::FAILED;
78 RunInternal(base::Bind(&LevelDBMojoProxy::GetChildrenImpl, this, dir,
79 path, result, &error));
80 return error;
81 }
82
83 filesystem::FileError LevelDBMojoProxy::Delete(OpaqueDir* dir,
84 const std::string& path,
85 uint32_t delete_flags) {
86 filesystem::FileError error = filesystem::FileError::FAILED;
87 RunInternal(base::Bind(&LevelDBMojoProxy::DeleteImpl, this, dir, path,
88 delete_flags, &error));
89 return error;
90 }
91
92 filesystem::FileError LevelDBMojoProxy::CreateDir(OpaqueDir* dir,
93 const std::string& path) {
94 filesystem::FileError error = filesystem::FileError::FAILED;
95 RunInternal(base::Bind(&LevelDBMojoProxy::CreateDirImpl, this, dir, path,
96 &error));
97 return error;
98 }
99
100 filesystem::FileError LevelDBMojoProxy::GetFileSize(OpaqueDir* dir,
101 const std::string& path,
102 uint64_t* file_size) {
103 filesystem::FileError error = filesystem::FileError::FAILED;
104 RunInternal(base::Bind(&LevelDBMojoProxy::GetFileSizeImpl, this, dir,
105 path, file_size, &error));
106 return error;
107 }
108
109 filesystem::FileError LevelDBMojoProxy::RenameFile(
110 OpaqueDir* dir,
111 const std::string& old_path,
112 const std::string& new_path) {
113 filesystem::FileError error = filesystem::FileError::FAILED;
114 RunInternal(base::Bind(&LevelDBMojoProxy::RenameFileImpl, this, dir,
115 old_path, new_path, &error));
116 return error;
117 }
118
119 std::pair<filesystem::FileError, LevelDBMojoProxy::OpaqueLock*>
120 LevelDBMojoProxy::LockFile(OpaqueDir* dir, const std::string& path) {
121 filesystem::FileError error = filesystem::FileError::FAILED;
122 OpaqueLock* out_lock = nullptr;
123 RunInternal(base::Bind(&LevelDBMojoProxy::LockFileImpl, this, dir, path,
124 &error, &out_lock));
125 return std::make_pair(error, out_lock);
126 }
127
128 filesystem::FileError LevelDBMojoProxy::UnlockFile(OpaqueLock* lock) {
129 // Take ownership of the incoming lock so it gets destroyed whatever happens.
130 scoped_ptr<OpaqueLock> scoped_lock(lock);
131 filesystem::FileError error = filesystem::FileError::FAILED;
132 RunInternal(base::Bind(&LevelDBMojoProxy::UnlockFileImpl, this,
133 base::Passed(&scoped_lock), &error));
134 return error;
135 }
136
137 LevelDBMojoProxy::~LevelDBMojoProxy() {
138 DCHECK_EQ(0, outstanding_opaque_dirs_);
139 }
140
141 void LevelDBMojoProxy::RunInternal(const base::Closure& task) {
142 if (task_runner_->BelongsToCurrentThread()) {
143 task.Run();
144 } else {
145 base::WaitableEvent done_event(false, false);
146 task_runner_->PostTask(
147 FROM_HERE,
148 base::Bind(&LevelDBMojoProxy::DoOnOtherThread,
149 this,
150 task,
151 base::Unretained(&done_event)));
152 done_event.Wait();
153 }
154 }
155
156 void LevelDBMojoProxy::DoOnOtherThread(const base::Closure& c,
157 base::WaitableEvent* event) {
158 c.Run();
159 event->Signal();
160 }
161
162 void LevelDBMojoProxy::RegisterDirectoryImpl(
163 mojo::InterfacePtrInfo<filesystem::Directory> directory_info,
164 OpaqueDir** out_dir) {
165 // Take the Directory pipe and bind it on this thread.
166 *out_dir = new OpaqueDir(std::move(directory_info));
167 outstanding_opaque_dirs_++;
168 }
169
170 void LevelDBMojoProxy::UnregisterDirectoryImpl(
171 OpaqueDir* dir) {
172 // Only delete the directories on the thread that owns them.
173 delete dir;
174 outstanding_opaque_dirs_--;
175 }
176
177 void LevelDBMojoProxy::OpenFileHandleImpl(OpaqueDir* dir,
178 std::string name,
179 uint32_t open_flags,
180 base::File* output_file) {
181 mojo::ScopedHandle handle;
182 filesystem::FileError error = filesystem::FileError::FAILED;
183 bool completed = dir->directory->OpenFileHandle(mojo::String::From(name),
184 open_flags, &error, &handle);
185 DCHECK(completed);
186
187 if (error != filesystem::FileError::OK) {
188 *output_file = base::File(static_cast<base::File::Error>(error));
189 } else {
190 MojoPlatformHandle platform_handle;
191 MojoResult extract_result =
192 MojoExtractPlatformHandle(handle.release().value(), &platform_handle);
193
194 if (extract_result == MOJO_RESULT_OK) {
195 *output_file = base::File(platform_handle);
196 } else {
197 NOTREACHED();
198 *output_file = base::File(base::File::Error::FILE_ERROR_FAILED);
199 }
200 }
201 }
202
203 void LevelDBMojoProxy::SyncDirectoryImpl(OpaqueDir* dir,
204 std::string name,
205 filesystem::FileError* out_error) {
206 filesystem::DirectoryPtr target;
207 bool completed = dir->directory->OpenDirectory(
208 name, GetProxy(&target), filesystem::kFlagRead | filesystem::kFlagWrite,
209 out_error);
210 DCHECK(completed);
211
212 if (*out_error != filesystem::FileError::OK)
213 return;
214
215 completed = target->Flush(out_error);
216 DCHECK(completed);
217 }
218
219 void LevelDBMojoProxy::FileExistsImpl(OpaqueDir* dir,
220 std::string name,
221 bool* exists) {
222 filesystem::FileError error = filesystem::FileError::FAILED;
223 bool completed =
224 dir->directory->Exists(mojo::String::From(name), &error, exists);
225 DCHECK(completed);
226 }
227
228 void LevelDBMojoProxy::GetChildrenImpl(OpaqueDir* dir,
229 std::string name,
230 std::vector<std::string>* out_contents,
231 filesystem::FileError* out_error) {
232 filesystem::DirectoryPtr target;
233 filesystem::DirectoryRequest proxy = GetProxy(&target);
234 bool completed = dir->directory->OpenDirectory(
235 name, std::move(proxy), filesystem::kFlagRead | filesystem::kFlagWrite,
236 out_error);
237 DCHECK(completed);
238
239 if (*out_error != filesystem::FileError::OK)
240 return;
241
242 mojo::Array<filesystem::DirectoryEntryPtr> directory_contents;
243 completed = target->Read(out_error, &directory_contents);
244 DCHECK(completed);
245
246 if (!directory_contents.is_null()) {
247 for (size_t i = 0; i < directory_contents.size(); ++i)
248 out_contents->push_back(directory_contents[i]->name.To<std::string>());
249 }
250 }
251
252 void LevelDBMojoProxy::DeleteImpl(OpaqueDir* dir,
253 std::string name,
254 uint32_t delete_flags,
255 filesystem::FileError* out_error) {
256 bool completed =
257 dir->directory->Delete(mojo::String::From(name), delete_flags, out_error);
258 DCHECK(completed);
259 }
260
261 void LevelDBMojoProxy::CreateDirImpl(OpaqueDir* dir,
262 std::string name,
263 filesystem::FileError* out_error) {
264 bool completed = dir->directory->OpenDirectory(
265 name, nullptr,
266 filesystem::kFlagRead | filesystem::kFlagWrite | filesystem::kFlagCreate,
267 out_error);
268 DCHECK(completed);
269 }
270
271 void LevelDBMojoProxy::GetFileSizeImpl(OpaqueDir* dir,
272 const std::string& path,
273 uint64_t* file_size,
274 filesystem::FileError* out_error) {
275 filesystem::FileInformationPtr info;
276 bool completed = dir->directory->StatFile(path, out_error, &info);
277 DCHECK(completed);
278 if (info)
279 *file_size = info->size;
280 }
281
282 void LevelDBMojoProxy::RenameFileImpl(OpaqueDir* dir,
283 const std::string& old_path,
284 const std::string& new_path,
285 filesystem::FileError* out_error) {
286 bool completed = dir->directory->Rename(
287 mojo::String::From(old_path), mojo::String::From(new_path), out_error);
288 DCHECK(completed);
289 }
290
291 void LevelDBMojoProxy::LockFileImpl(OpaqueDir* dir,
292 const std::string& path,
293 filesystem::FileError* out_error,
294 OpaqueLock** out_lock) {
295 // Since a lock is associated with a file descriptor, we need to open and
296 // have a persistent file on the other side of the connection.
297 filesystem::FilePtr target;
298 filesystem::FileRequest proxy = GetProxy(&target);
299 bool completed = dir->directory->OpenFile(
300 mojo::String::From(path), std::move(proxy),
301 filesystem::kFlagOpenAlways | filesystem::kFlagRead |
302 filesystem::kFlagWrite,
303 out_error);
304 DCHECK(completed);
305
306 if (*out_error != filesystem::FileError::OK)
307 return;
308
309 completed = target->Lock(out_error);
310 DCHECK(completed);
311
312 if (*out_error == filesystem::FileError::OK) {
313 OpaqueLock* l = new OpaqueLock;
314 l->lock_file = std::move(target);
315 *out_lock = l;
316 }
317 }
318
319 void LevelDBMojoProxy::UnlockFileImpl(scoped_ptr<OpaqueLock> lock,
320 filesystem::FileError* out_error) {
321 lock->lock_file->Unlock(out_error);
322 }
323
324 } // namespace leveldb
OLDNEW
« no previous file with comments | « components/leveldb/leveldb_mojo_proxy.h ('k') | components/leveldb/leveldb_service_impl.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698