diff options
author | Allan Sandfeld Jensen <allan.jensen@theqtcompany.com> | 2016-07-14 17:41:05 +0200 |
---|---|---|
committer | Allan Sandfeld Jensen <allan.jensen@qt.io> | 2016-08-04 12:37:36 +0000 |
commit | 399c965b6064c440ddcf4015f5f8e9d131c7a0a6 (patch) | |
tree | 6b06b60ff365abef0e13b3503d593a0df48d20e8 /chromium/components/leveldb | |
parent | 7366110654eec46f21b6824f302356426f48cd74 (diff) | |
download | qtwebengine-chromium-399c965b6064c440ddcf4015f5f8e9d131c7a0a6.tar.gz |
BASELINE: Update Chromium to 52.0.2743.76 and Ninja to 1.7.1
Change-Id: I382f51b959689505a60f8b707255ecb344f7d8b4
Reviewed-by: Michael BrĂ¼ning <michael.bruning@qt.io>
Diffstat (limited to 'chromium/components/leveldb')
24 files changed, 613 insertions, 335 deletions
diff --git a/chromium/components/leveldb/BUILD.gn b/chromium/components/leveldb/BUILD.gn index 9d4a3e54960..67ce46b8a64 100644 --- a/chromium/components/leveldb/BUILD.gn +++ b/chromium/components/leveldb/BUILD.gn @@ -23,9 +23,8 @@ source_set("lib") { "//components/leveldb/public/cpp", "//components/leveldb/public/interfaces", "//mojo/common", - "//mojo/message_pump", "//mojo/platform_handle", - "//mojo/shell/public/cpp", + "//services/shell/public/cpp", "//third_party/leveldatabase", ] } @@ -44,8 +43,8 @@ mojo_native_application("leveldb") { "//mojo/platform_handle:for_shared_library", "//mojo/public/cpp/bindings", "//mojo/public/cpp/system", - "//mojo/services/tracing/public/cpp", - "//mojo/shell/public/cpp", + "//services/shell/public/cpp", + "//services/tracing/public/cpp", ] data_deps = [ @@ -72,9 +71,9 @@ test("leveldb_service_unittests") { "//mojo/common", "//mojo/platform_handle", "//mojo/public/cpp/bindings", - "//mojo/shell/public/cpp:shell_test_support", - "//mojo/shell/public/cpp:sources", - "//mojo/shell/public/cpp/test:run_all_shelltests", + "//services/shell/public/cpp:shell_test_support", + "//services/shell/public/cpp:sources", + "//services/shell/public/cpp/test:run_all_shelltests", "//third_party/leveldatabase", ] diff --git a/chromium/components/leveldb/DEPS b/chromium/components/leveldb/DEPS index 824c94d2d21..13b8f3f4510 100644 --- a/chromium/components/leveldb/DEPS +++ b/chromium/components/leveldb/DEPS @@ -1,11 +1,10 @@ include_rules = [ "+components/filesystem/public/interfaces", "+mojo/common", - "+mojo/message_pump", "+mojo/platform_handle", "+mojo/public", - "+mojo/services/tracing/public/cpp", - "+mojo/shell", "+mojo/util", + "+services/shell", + "+services/tracing/public/cpp", "+third_party/leveldatabase", ] diff --git a/chromium/components/leveldb/env_mojo.cc b/chromium/components/leveldb/env_mojo.cc index 089202f0d2f..54681d0d142 100644 --- a/chromium/components/leveldb/env_mojo.cc +++ b/chromium/components/leveldb/env_mojo.cc @@ -6,6 +6,8 @@ #include <errno.h> +#include <memory> + #include "base/trace_event/trace_event.h" #include "third_party/leveldatabase/chromium_logger.h" #include "third_party/leveldatabase/src/include/leveldb/status.h" @@ -24,10 +26,10 @@ base::File::Error LastFileError() { #endif } -Status FilesystemErrorToStatus(filesystem::FileError error, +Status FilesystemErrorToStatus(filesystem::mojom::FileError error, const std::string& filename, leveldb_env::MethodID method) { - if (error == filesystem::FileError::OK) + if (error == filesystem::mojom::FileError::OK) return Status::OK(); std::string err_str = @@ -191,8 +193,9 @@ class MojoWritableFile : public leveldb::WritableFile { enum Type { kManifest, kTable, kOther }; leveldb::Status SyncParent() { - filesystem::FileError error = thread_->SyncDirectory(dir_, parent_dir_); - return error == filesystem::FileError::OK + filesystem::mojom::FileError error = + thread_->SyncDirectory(dir_, parent_dir_); + return error == filesystem::mojom::FileError::OK ? Status::OK() : Status::IOError(filename_, base::File::ErrorToString(base::File::Error( @@ -224,7 +227,7 @@ Status MojoEnv::NewSequentialFile(const std::string& fname, TRACE_EVENT1("leveldb", "MojoEnv::NewSequentialFile", "fname", fname); base::File f = thread_->OpenFileHandle( dir_, mojo::String::From(fname), - filesystem::kFlagOpen | filesystem::kFlagRead); + filesystem::mojom::kFlagOpen | filesystem::mojom::kFlagRead); if (!f.IsValid()) { *result = nullptr; return MakeIOError(fname, "Unable to create sequential file", @@ -240,7 +243,7 @@ Status MojoEnv::NewRandomAccessFile(const std::string& fname, TRACE_EVENT1("leveldb", "MojoEnv::NewRandomAccessFile", "fname", fname); base::File f = thread_->OpenFileHandle( dir_, mojo::String::From(fname), - filesystem::kFlagRead | filesystem::kFlagOpen); + filesystem::mojom::kFlagRead | filesystem::mojom::kFlagOpen); if (!f.IsValid()) { *result = nullptr; base::File::Error error_code = f.error_details(); @@ -257,7 +260,7 @@ Status MojoEnv::NewWritableFile(const std::string& fname, TRACE_EVENT1("leveldb", "MojoEnv::NewWritableFile", "fname", fname); base::File f = thread_->OpenFileHandle( dir_, mojo::String::From(fname), - filesystem::kCreateAlways | filesystem::kFlagWrite); + filesystem::mojom::kCreateAlways | filesystem::mojom::kFlagWrite); if (!f.IsValid()) { *result = nullptr; return MakeIOError(fname, "Unable to create writable file", @@ -273,7 +276,7 @@ Status MojoEnv::NewAppendableFile(const std::string& fname, TRACE_EVENT1("leveldb", "MojoEnv::NewAppendableFile", "fname", fname); base::File f = thread_->OpenFileHandle( dir_, mojo::String::From(fname), - filesystem::kFlagOpenAlways | filesystem::kFlagAppend); + filesystem::mojom::kFlagOpenAlways | filesystem::mojom::kFlagAppend); if (!f.IsValid()) { *result = nullptr; return MakeIOError(fname, "Unable to create appendable file", @@ -311,8 +314,8 @@ Status MojoEnv::CreateDir(const std::string& dirname) { Status MojoEnv::DeleteDir(const std::string& dirname) { TRACE_EVENT1("leveldb", "MojoEnv::DeleteDir", "dirname", dirname); return FilesystemErrorToStatus( - thread_->Delete(dir_, dirname, filesystem::kDeleteFlagRecursive), dirname, - leveldb_env::kDeleteDir); + thread_->Delete(dir_, dirname, filesystem::mojom::kDeleteFlagRecursive), + dirname, leveldb_env::kDeleteDir); } Status MojoEnv::GetFileSize(const std::string& fname, uint64_t* file_size) { @@ -331,7 +334,7 @@ Status MojoEnv::RenameFile(const std::string& src, const std::string& target) { Status MojoEnv::LockFile(const std::string& fname, FileLock** lock) { TRACE_EVENT1("leveldb", "MojoEnv::LockFile", "fname", fname); - std::pair<filesystem::FileError, LevelDBMojoProxy::OpaqueLock*> p = + std::pair<filesystem::mojom::FileError, LevelDBMojoProxy::OpaqueLock*> p = thread_->LockFile(dir_, mojo::String::From(fname)); if (p.second) @@ -346,7 +349,7 @@ Status MojoEnv::UnlockFile(FileLock* lock) { std::string fname = my_lock ? my_lock->name() : "(invalid)"; TRACE_EVENT1("leveldb", "MojoEnv::UnlockFile", "fname", fname); - filesystem::FileError err = thread_->UnlockFile(my_lock->TakeLock()); + filesystem::mojom::FileError err = thread_->UnlockFile(my_lock->TakeLock()); delete my_lock; return FilesystemErrorToStatus(err, fname, leveldb_env::kUnlockFile); } @@ -362,9 +365,9 @@ Status MojoEnv::GetTestDirectory(std::string* path) { Status MojoEnv::NewLogger(const std::string& fname, Logger** result) { TRACE_EVENT1("leveldb", "MojoEnv::NewLogger", "fname", fname); - scoped_ptr<base::File> f(new base::File(thread_->OpenFileHandle( + std::unique_ptr<base::File> f(new base::File(thread_->OpenFileHandle( dir_, mojo::String::From(fname), - filesystem::kCreateAlways | filesystem::kFlagWrite))); + filesystem::mojom::kCreateAlways | filesystem::mojom::kFlagWrite))); if (!f->IsValid()) { *result = NULL; return MakeIOError(fname, "Unable to create log file", diff --git a/chromium/components/leveldb/leveldb.gyp b/chromium/components/leveldb/leveldb.gyp index 6d1a8eff616..ba1d2f80cad 100644 --- a/chromium/components/leveldb/leveldb.gyp +++ b/chromium/components/leveldb/leveldb.gyp @@ -30,8 +30,8 @@ 'dependencies': [ 'leveldb_public_lib', '../../components/filesystem/filesystem.gyp:filesystem_lib', - '../../mojo/mojo_base.gyp:mojo_application_base', '../../mojo/mojo_public.gyp:mojo_cpp_bindings', + '../../services/shell/shell_public.gyp:shell_public', '../../third_party/leveldatabase/leveldatabase.gyp:leveldatabase', ] }, @@ -47,9 +47,9 @@ ], 'dependencies': [ 'leveldb_bindings_mojom', - '../../mojo/mojo_base.gyp:mojo_application_base', '../../mojo/mojo_edk.gyp:mojo_system_impl', '../../mojo/mojo_public.gyp:mojo_cpp_bindings', + '../../services/shell/shell_public.gyp:shell_public', '../../third_party/leveldatabase/leveldatabase.gyp:leveldatabase', ] }, diff --git a/chromium/components/leveldb/leveldb_app.cc b/chromium/components/leveldb/leveldb_app.cc index 048fef52d5f..17afe655688 100644 --- a/chromium/components/leveldb/leveldb_app.cc +++ b/chromium/components/leveldb/leveldb_app.cc @@ -6,7 +6,7 @@ #include "base/message_loop/message_loop.h" #include "components/leveldb/leveldb_service_impl.h" -#include "mojo/shell/public/cpp/connection.h" +#include "services/shell/public/cpp/connection.h" namespace leveldb { @@ -14,19 +14,19 @@ LevelDBApp::LevelDBApp() {} LevelDBApp::~LevelDBApp() {} -void LevelDBApp::Initialize(mojo::Connector* connector, - const mojo::Identity& identity, +void LevelDBApp::Initialize(shell::Connector* connector, + const shell::Identity& identity, uint32_t id) { tracing_.Initialize(connector, identity.name()); } -bool LevelDBApp::AcceptConnection(mojo::Connection* connection) { - connection->AddInterface<LevelDBService>(this); +bool LevelDBApp::AcceptConnection(shell::Connection* connection) { + connection->AddInterface<mojom::LevelDBService>(this); return true; } -void LevelDBApp::Create(mojo::Connection* connection, - leveldb::LevelDBServiceRequest request) { +void LevelDBApp::Create(shell::Connection* connection, + leveldb::mojom::LevelDBServiceRequest request) { if (!service_) service_.reset( new LevelDBServiceImpl(base::MessageLoop::current()->task_runner())); diff --git a/chromium/components/leveldb/leveldb_app.h b/chromium/components/leveldb/leveldb_app.h index 26a115224b4..d53e9373a31 100644 --- a/chromium/components/leveldb/leveldb_app.h +++ b/chromium/components/leveldb/leveldb_app.h @@ -5,34 +5,36 @@ #ifndef COMPONENTS_LEVELDB_LEVELDB_APP_H_ #define COMPONENTS_LEVELDB_LEVELDB_APP_H_ +#include <memory> + #include "components/leveldb/public/interfaces/leveldb.mojom.h" #include "mojo/public/cpp/bindings/binding_set.h" -#include "mojo/services/tracing/public/cpp/tracing_impl.h" -#include "mojo/shell/public/cpp/interface_factory.h" -#include "mojo/shell/public/cpp/shell_client.h" +#include "services/shell/public/cpp/interface_factory.h" +#include "services/shell/public/cpp/shell_client.h" +#include "services/tracing/public/cpp/tracing_impl.h" namespace leveldb { -class LevelDBApp : public mojo::ShellClient, - public mojo::InterfaceFactory<LevelDBService> { +class LevelDBApp : public shell::ShellClient, + public shell::InterfaceFactory<mojom::LevelDBService> { public: LevelDBApp(); ~LevelDBApp() override; private: // |ShellClient| override: - void Initialize(mojo::Connector* connector, - const mojo::Identity& identity, + void Initialize(shell::Connector* connector, + const shell::Identity& identity, uint32_t id) override; - bool AcceptConnection(mojo::Connection* connection) override; + bool AcceptConnection(shell::Connection* connection) override; - // |InterfaceFactory<LevelDBService>| implementation: - void Create(mojo::Connection* connection, - leveldb::LevelDBServiceRequest request) override; + // |InterfaceFactory<mojom::LevelDBService>| implementation: + void Create(shell::Connection* connection, + leveldb::mojom::LevelDBServiceRequest request) override; mojo::TracingImpl tracing_; - scoped_ptr<LevelDBService> service_; - mojo::BindingSet<LevelDBService> bindings_; + std::unique_ptr<mojom::LevelDBService> service_; + mojo::BindingSet<mojom::LevelDBService> bindings_; DISALLOW_COPY_AND_ASSIGN(LevelDBApp); }; diff --git a/chromium/components/leveldb/leveldb_database_impl.cc b/chromium/components/leveldb/leveldb_database_impl.cc index 6a64706985b..f5d618cc190 100644 --- a/chromium/components/leveldb/leveldb_database_impl.cc +++ b/chromium/components/leveldb/leveldb_database_impl.cc @@ -28,12 +28,27 @@ uint64_t GetSafeRandomId(const std::map<uint64_t, T>& m) { return new_id; } +template <typename FunctionType> +leveldb::Status ForEachWithPrefix(leveldb::DB* db, + const leveldb::Slice& key_prefix, + FunctionType function) { + std::unique_ptr<leveldb::Iterator> it( + db->NewIterator(leveldb::ReadOptions())); + it->Seek(key_prefix); + for (; it->Valid(); it->Next()) { + if (!it->key().starts_with(key_prefix)) + break; + function(it->key(), it->value()); + } + return it->status(); +} + } // namespace LevelDBDatabaseImpl::LevelDBDatabaseImpl( - leveldb::LevelDBDatabaseRequest request, - scoped_ptr<leveldb::Env> environment, - scoped_ptr<leveldb::DB> db) + leveldb::mojom::LevelDBDatabaseRequest request, + std::unique_ptr<leveldb::Env> environment, + std::unique_ptr<leveldb::DB> db) : binding_(this, std::move(request)), environment_(std::move(environment)), db_(std::move(db)) {} @@ -60,21 +75,37 @@ void LevelDBDatabaseImpl::Delete(mojo::Array<uint8_t> key, callback.Run(LeveldbStatusToError(status)); } -void LevelDBDatabaseImpl::Write(mojo::Array<BatchedOperationPtr> operations, - const WriteCallback& callback) { +void LevelDBDatabaseImpl::DeletePrefixed( + mojo::Array<uint8_t> key_prefix, + const DeletePrefixedCallback& callback) { + leveldb::WriteBatch batch; + leveldb::Status status = DeletePrefixedHelper( + GetSliceFor(key_prefix), &batch); + if (status.ok()) + status = db_->Write(leveldb::WriteOptions(), &batch); + callback.Run(LeveldbStatusToError(status)); +} + +void LevelDBDatabaseImpl::Write( + mojo::Array<mojom::BatchedOperationPtr> operations, + const WriteCallback& callback) { leveldb::WriteBatch batch; for (size_t i = 0; i < operations.size(); ++i) { switch (operations[i]->type) { - case BatchOperationType::PUT_KEY: { + case mojom::BatchOperationType::PUT_KEY: { batch.Put(GetSliceFor(operations[i]->key), GetSliceFor(operations[i]->value)); break; } - case BatchOperationType::DELETE_KEY: { + case mojom::BatchOperationType::DELETE_KEY: { batch.Delete(GetSliceFor(operations[i]->key)); break; } + case mojom::BatchOperationType::DELETE_PREFIXED_KEY: { + DeletePrefixedHelper(GetSliceFor(operations[i]->key), &batch); + break; + } } } @@ -90,6 +121,20 @@ void LevelDBDatabaseImpl::Get(mojo::Array<uint8_t> key, callback.Run(LeveldbStatusToError(status), mojo::Array<uint8_t>::From(value)); } +void LevelDBDatabaseImpl::GetPrefixed(mojo::Array<uint8_t> key_prefix, + const GetPrefixedCallback& callback) { + mojo::Array<mojom::KeyValuePtr> data; + leveldb::Status status = ForEachWithPrefix( + db_.get(), GetSliceFor(key_prefix), + [&data](const leveldb::Slice& key, const leveldb::Slice& value) { + mojom::KeyValuePtr kv = mojom::KeyValue::New(); + kv->key = GetArrayFor(key); + kv->value = GetArrayFor(value); + data.push_back(std::move(kv)); + }); + callback.Run(LeveldbStatusToError(status), std::move(data)); +} + void LevelDBDatabaseImpl::GetSnapshot(const GetSnapshotCallback& callback) { const Snapshot* s = db_->GetSnapshot(); uint64_t new_id = GetSafeRandomId(snapshot_map_); @@ -111,7 +156,8 @@ void LevelDBDatabaseImpl::GetFromSnapshot(uint64_t snapshot_id, // If the snapshot id is invalid, send back invalid argument auto it = snapshot_map_.find(snapshot_id); if (it == snapshot_map_.end()) { - callback.Run(DatabaseError::INVALID_ARGUMENT, mojo::Array<uint8_t>()); + callback.Run(mojom::DatabaseError::INVALID_ARGUMENT, + mojo::Array<uint8_t>()); return; } @@ -161,7 +207,8 @@ void LevelDBDatabaseImpl::IteratorSeekToFirst( const IteratorSeekToFirstCallback& callback) { auto it = iterator_map_.find(iterator_id); if (it == iterator_map_.end()) { - callback.Run(false, DatabaseError::INVALID_ARGUMENT, nullptr, nullptr); + callback.Run(false, mojom::DatabaseError::INVALID_ARGUMENT, nullptr, + nullptr); return; } @@ -175,7 +222,8 @@ void LevelDBDatabaseImpl::IteratorSeekToLast( const IteratorSeekToLastCallback& callback) { auto it = iterator_map_.find(iterator_id); if (it == iterator_map_.end()) { - callback.Run(false, DatabaseError::INVALID_ARGUMENT, nullptr, nullptr); + callback.Run(false, mojom::DatabaseError::INVALID_ARGUMENT, nullptr, + nullptr); return; } @@ -190,7 +238,8 @@ void LevelDBDatabaseImpl::IteratorSeek( const IteratorSeekToLastCallback& callback) { auto it = iterator_map_.find(iterator_id); if (it == iterator_map_.end()) { - callback.Run(false, DatabaseError::INVALID_ARGUMENT, nullptr, nullptr); + callback.Run(false, mojom::DatabaseError::INVALID_ARGUMENT, nullptr, + nullptr); return; } @@ -203,7 +252,8 @@ void LevelDBDatabaseImpl::IteratorNext(uint64_t iterator_id, const IteratorNextCallback& callback) { auto it = iterator_map_.find(iterator_id); if (it == iterator_map_.end()) { - callback.Run(false, DatabaseError::INVALID_ARGUMENT, nullptr, nullptr); + callback.Run(false, mojom::DatabaseError::INVALID_ARGUMENT, nullptr, + nullptr); return; } @@ -216,7 +266,8 @@ void LevelDBDatabaseImpl::IteratorPrev(uint64_t iterator_id, const IteratorPrevCallback& callback) { auto it = iterator_map_.find(iterator_id); if (it == iterator_map_.end()) { - callback.Run(false, DatabaseError::INVALID_ARGUMENT, nullptr, nullptr); + callback.Run(false, mojom::DatabaseError::INVALID_ARGUMENT, nullptr, + nullptr); return; } @@ -237,4 +288,14 @@ void LevelDBDatabaseImpl::ReplyToIteratorMessage( GetArrayFor(it->value())); } +leveldb::Status LevelDBDatabaseImpl::DeletePrefixedHelper( + const leveldb::Slice& key_prefix, + leveldb::WriteBatch* batch) { + leveldb::Status status = ForEachWithPrefix(db_.get(), key_prefix, + [batch](const leveldb::Slice& key, const leveldb::Slice& value) { + batch->Delete(key); + }); + return status; +} + } // namespace leveldb diff --git a/chromium/components/leveldb/leveldb_database_impl.h b/chromium/components/leveldb/leveldb_database_impl.h index a6ccab77dcb..e16b4bf0e79 100644 --- a/chromium/components/leveldb/leveldb_database_impl.h +++ b/chromium/components/leveldb/leveldb_database_impl.h @@ -5,7 +5,8 @@ #ifndef COMPONENTS_LEVELDB_LEVELDB_DATABASE_IMPL_H_ #define COMPONENTS_LEVELDB_LEVELDB_DATABASE_IMPL_H_ -#include "base/memory/scoped_ptr.h" +#include <memory> + #include "components/leveldb/public/interfaces/leveldb.mojom.h" #include "mojo/public/cpp/bindings/interface_request.h" #include "mojo/public/cpp/bindings/strong_binding.h" @@ -16,11 +17,11 @@ namespace leveldb { class MojoEnv; // The backing to a database object that we pass to our called. -class LevelDBDatabaseImpl : public LevelDBDatabase { +class LevelDBDatabaseImpl : public mojom::LevelDBDatabase { public: - LevelDBDatabaseImpl(leveldb::LevelDBDatabaseRequest request, - scoped_ptr<leveldb::Env> environment, - scoped_ptr<leveldb::DB> db); + LevelDBDatabaseImpl(leveldb::mojom::LevelDBDatabaseRequest request, + std::unique_ptr<leveldb::Env> environment, + std::unique_ptr<leveldb::DB> db); ~LevelDBDatabaseImpl() override; // Overridden from LevelDBDatabase: @@ -29,9 +30,13 @@ class LevelDBDatabaseImpl : public LevelDBDatabase { const PutCallback& callback) override; void Delete(mojo::Array<uint8_t> key, const DeleteCallback& callback) override; - void Write(mojo::Array<BatchedOperationPtr> operations, + void DeletePrefixed(mojo::Array<uint8_t> key_prefix, + const DeletePrefixedCallback& callback) override; + void Write(mojo::Array<mojom::BatchedOperationPtr> operations, const WriteCallback& callback) override; void Get(mojo::Array<uint8_t> key, const GetCallback& callback) override; + void GetPrefixed(mojo::Array<uint8_t> key_prefix, + const GetPrefixedCallback& callback) override; void GetSnapshot(const GetSnapshotCallback& callback) override; void ReleaseSnapshot(uint64_t snapshot_id) override; void GetFromSnapshot(uint64_t snapshot_id, @@ -61,9 +66,12 @@ class LevelDBDatabaseImpl : public LevelDBDatabase { void ReplyToIteratorMessage(leveldb::Iterator* it, const IteratorSeekToFirstCallback& callback); - mojo::StrongBinding<LevelDBDatabase> binding_; - scoped_ptr<leveldb::Env> environment_; - scoped_ptr<leveldb::DB> db_; + leveldb::Status DeletePrefixedHelper(const leveldb::Slice& key_prefix, + leveldb::WriteBatch* batch); + + mojo::StrongBinding<mojom::LevelDBDatabase> binding_; + std::unique_ptr<leveldb::Env> environment_; + std::unique_ptr<leveldb::DB> db_; std::map<uint64_t, const Snapshot*> snapshot_map_; diff --git a/chromium/components/leveldb/leveldb_mojo_proxy.cc b/chromium/components/leveldb/leveldb_mojo_proxy.cc index 2d365f1e516..3820b6103c5 100644 --- a/chromium/components/leveldb/leveldb_mojo_proxy.cc +++ b/chromium/components/leveldb/leveldb_mojo_proxy.cc @@ -8,23 +8,22 @@ #include "base/bind.h" #include "base/callback.h" -#include "mojo/message_pump/message_pump_mojo.h" #include "mojo/platform_handle/platform_handle_functions.h" #include "mojo/public/cpp/bindings/interface_request.h" namespace leveldb { struct LevelDBMojoProxy::OpaqueLock { - filesystem::FilePtr lock_file; + filesystem::mojom::FilePtr lock_file; }; struct LevelDBMojoProxy::OpaqueDir { explicit OpaqueDir( - mojo::InterfacePtrInfo<filesystem::Directory> directory_info) { + mojo::InterfacePtrInfo<filesystem::mojom::Directory> directory_info) { directory.Bind(std::move(directory_info)); } - filesystem::DirectoryPtr directory; + filesystem::mojom::DirectoryPtr directory; }; LevelDBMojoProxy::LevelDBMojoProxy( @@ -32,7 +31,7 @@ LevelDBMojoProxy::LevelDBMojoProxy( : task_runner_(std::move(task_runner)), outstanding_opaque_dirs_(0) {} LevelDBMojoProxy::OpaqueDir* LevelDBMojoProxy::RegisterDirectory( - filesystem::DirectoryPtr directory) { + filesystem::mojom::DirectoryPtr directory) { OpaqueDir* out_dir = nullptr; RunInternal(base::Bind(&LevelDBMojoProxy::RegisterDirectoryImpl, this, base::Passed(directory.PassInterface()), @@ -55,9 +54,10 @@ base::File LevelDBMojoProxy::OpenFileHandle(OpaqueDir* dir, return file; } -filesystem::FileError LevelDBMojoProxy::SyncDirectory(OpaqueDir* dir, - const std::string& name) { - filesystem::FileError error = filesystem::FileError::FAILED; +filesystem::mojom::FileError LevelDBMojoProxy::SyncDirectory( + OpaqueDir* dir, + const std::string& name) { + filesystem::mojom::FileError error = filesystem::mojom::FileError::FAILED; RunInternal(base::Bind(&LevelDBMojoProxy::SyncDirectoryImpl, this, dir, name, &error)); return error; @@ -70,65 +70,67 @@ bool LevelDBMojoProxy::FileExists(OpaqueDir* dir, const std::string& name) { return exists; } -filesystem::FileError LevelDBMojoProxy::GetChildren( +filesystem::mojom::FileError LevelDBMojoProxy::GetChildren( OpaqueDir* dir, const std::string& path, std::vector<std::string>* result) { - filesystem::FileError error = filesystem::FileError::FAILED; + filesystem::mojom::FileError error = filesystem::mojom::FileError::FAILED; RunInternal(base::Bind(&LevelDBMojoProxy::GetChildrenImpl, this, dir, path, result, &error)); return error; } -filesystem::FileError LevelDBMojoProxy::Delete(OpaqueDir* dir, - const std::string& path, - uint32_t delete_flags) { - filesystem::FileError error = filesystem::FileError::FAILED; +filesystem::mojom::FileError LevelDBMojoProxy::Delete(OpaqueDir* dir, + const std::string& path, + uint32_t delete_flags) { + filesystem::mojom::FileError error = filesystem::mojom::FileError::FAILED; RunInternal(base::Bind(&LevelDBMojoProxy::DeleteImpl, this, dir, path, delete_flags, &error)); return error; } -filesystem::FileError LevelDBMojoProxy::CreateDir(OpaqueDir* dir, - const std::string& path) { - filesystem::FileError error = filesystem::FileError::FAILED; +filesystem::mojom::FileError LevelDBMojoProxy::CreateDir( + OpaqueDir* dir, + const std::string& path) { + filesystem::mojom::FileError error = filesystem::mojom::FileError::FAILED; RunInternal(base::Bind(&LevelDBMojoProxy::CreateDirImpl, this, dir, path, &error)); return error; } -filesystem::FileError LevelDBMojoProxy::GetFileSize(OpaqueDir* dir, - const std::string& path, - uint64_t* file_size) { - filesystem::FileError error = filesystem::FileError::FAILED; +filesystem::mojom::FileError LevelDBMojoProxy::GetFileSize( + OpaqueDir* dir, + const std::string& path, + uint64_t* file_size) { + filesystem::mojom::FileError error = filesystem::mojom::FileError::FAILED; RunInternal(base::Bind(&LevelDBMojoProxy::GetFileSizeImpl, this, dir, path, file_size, &error)); return error; } -filesystem::FileError LevelDBMojoProxy::RenameFile( +filesystem::mojom::FileError LevelDBMojoProxy::RenameFile( OpaqueDir* dir, const std::string& old_path, const std::string& new_path) { - filesystem::FileError error = filesystem::FileError::FAILED; + filesystem::mojom::FileError error = filesystem::mojom::FileError::FAILED; RunInternal(base::Bind(&LevelDBMojoProxy::RenameFileImpl, this, dir, old_path, new_path, &error)); return error; } -std::pair<filesystem::FileError, LevelDBMojoProxy::OpaqueLock*> +std::pair<filesystem::mojom::FileError, LevelDBMojoProxy::OpaqueLock*> LevelDBMojoProxy::LockFile(OpaqueDir* dir, const std::string& path) { - filesystem::FileError error = filesystem::FileError::FAILED; + filesystem::mojom::FileError error = filesystem::mojom::FileError::FAILED; OpaqueLock* out_lock = nullptr; RunInternal(base::Bind(&LevelDBMojoProxy::LockFileImpl, this, dir, path, &error, &out_lock)); return std::make_pair(error, out_lock); } -filesystem::FileError LevelDBMojoProxy::UnlockFile(OpaqueLock* lock) { +filesystem::mojom::FileError LevelDBMojoProxy::UnlockFile(OpaqueLock* lock) { // Take ownership of the incoming lock so it gets destroyed whatever happens. - scoped_ptr<OpaqueLock> scoped_lock(lock); - filesystem::FileError error = filesystem::FileError::FAILED; + std::unique_ptr<OpaqueLock> scoped_lock(lock); + filesystem::mojom::FileError error = filesystem::mojom::FileError::FAILED; RunInternal(base::Bind(&LevelDBMojoProxy::UnlockFileImpl, this, base::Passed(&scoped_lock), &error)); return error; @@ -160,7 +162,7 @@ void LevelDBMojoProxy::DoOnOtherThread(const base::Closure& c, } void LevelDBMojoProxy::RegisterDirectoryImpl( - mojo::InterfacePtrInfo<filesystem::Directory> directory_info, + mojo::InterfacePtrInfo<filesystem::mojom::Directory> directory_info, OpaqueDir** out_dir) { // Take the Directory pipe and bind it on this thread. *out_dir = new OpaqueDir(std::move(directory_info)); @@ -179,12 +181,12 @@ void LevelDBMojoProxy::OpenFileHandleImpl(OpaqueDir* dir, uint32_t open_flags, base::File* output_file) { mojo::ScopedHandle handle; - filesystem::FileError error = filesystem::FileError::FAILED; + filesystem::mojom::FileError error = filesystem::mojom::FileError::FAILED; bool completed = dir->directory->OpenFileHandle(mojo::String::From(name), open_flags, &error, &handle); DCHECK(completed); - if (error != filesystem::FileError::OK) { + if (error != filesystem::mojom::FileError::OK) { *output_file = base::File(static_cast<base::File::Error>(error)); } else { MojoPlatformHandle platform_handle; @@ -200,16 +202,17 @@ void LevelDBMojoProxy::OpenFileHandleImpl(OpaqueDir* dir, } } -void LevelDBMojoProxy::SyncDirectoryImpl(OpaqueDir* dir, - std::string name, - filesystem::FileError* out_error) { - filesystem::DirectoryPtr target; +void LevelDBMojoProxy::SyncDirectoryImpl( + OpaqueDir* dir, + std::string name, + filesystem::mojom::FileError* out_error) { + filesystem::mojom::DirectoryPtr target; bool completed = dir->directory->OpenDirectory( - name, GetProxy(&target), filesystem::kFlagRead | filesystem::kFlagWrite, - out_error); + name, GetProxy(&target), + filesystem::mojom::kFlagRead | filesystem::mojom::kFlagWrite, out_error); DCHECK(completed); - if (*out_error != filesystem::FileError::OK) + if (*out_error != filesystem::mojom::FileError::OK) return; completed = target->Flush(out_error); @@ -219,27 +222,28 @@ void LevelDBMojoProxy::SyncDirectoryImpl(OpaqueDir* dir, void LevelDBMojoProxy::FileExistsImpl(OpaqueDir* dir, std::string name, bool* exists) { - filesystem::FileError error = filesystem::FileError::FAILED; + filesystem::mojom::FileError error = filesystem::mojom::FileError::FAILED; bool completed = dir->directory->Exists(mojo::String::From(name), &error, exists); DCHECK(completed); } -void LevelDBMojoProxy::GetChildrenImpl(OpaqueDir* dir, - std::string name, - std::vector<std::string>* out_contents, - filesystem::FileError* out_error) { - filesystem::DirectoryPtr target; - filesystem::DirectoryRequest proxy = GetProxy(&target); +void LevelDBMojoProxy::GetChildrenImpl( + OpaqueDir* dir, + std::string name, + std::vector<std::string>* out_contents, + filesystem::mojom::FileError* out_error) { + filesystem::mojom::DirectoryPtr target; + filesystem::mojom::DirectoryRequest proxy = GetProxy(&target); bool completed = dir->directory->OpenDirectory( - name, std::move(proxy), filesystem::kFlagRead | filesystem::kFlagWrite, - out_error); + name, std::move(proxy), + filesystem::mojom::kFlagRead | filesystem::mojom::kFlagWrite, out_error); DCHECK(completed); - if (*out_error != filesystem::FileError::OK) + if (*out_error != filesystem::mojom::FileError::OK) return; - mojo::Array<filesystem::DirectoryEntryPtr> directory_contents; + mojo::Array<filesystem::mojom::DirectoryEntryPtr> directory_contents; completed = target->Read(out_error, &directory_contents); DCHECK(completed); @@ -252,7 +256,7 @@ void LevelDBMojoProxy::GetChildrenImpl(OpaqueDir* dir, void LevelDBMojoProxy::DeleteImpl(OpaqueDir* dir, std::string name, uint32_t delete_flags, - filesystem::FileError* out_error) { + filesystem::mojom::FileError* out_error) { bool completed = dir->directory->Delete(mojo::String::From(name), delete_flags, out_error); DCHECK(completed); @@ -260,19 +264,21 @@ void LevelDBMojoProxy::DeleteImpl(OpaqueDir* dir, void LevelDBMojoProxy::CreateDirImpl(OpaqueDir* dir, std::string name, - filesystem::FileError* out_error) { + filesystem::mojom::FileError* out_error) { bool completed = dir->directory->OpenDirectory( name, nullptr, - filesystem::kFlagRead | filesystem::kFlagWrite | filesystem::kFlagCreate, + filesystem::mojom::kFlagRead | filesystem::mojom::kFlagWrite | + filesystem::mojom::kFlagCreate, out_error); DCHECK(completed); } -void LevelDBMojoProxy::GetFileSizeImpl(OpaqueDir* dir, - const std::string& path, - uint64_t* file_size, - filesystem::FileError* out_error) { - filesystem::FileInformationPtr info; +void LevelDBMojoProxy::GetFileSizeImpl( + OpaqueDir* dir, + const std::string& path, + uint64_t* file_size, + filesystem::mojom::FileError* out_error) { + filesystem::mojom::FileInformationPtr info; bool completed = dir->directory->StatFile(path, out_error, &info); DCHECK(completed); if (info) @@ -282,7 +288,7 @@ void LevelDBMojoProxy::GetFileSizeImpl(OpaqueDir* dir, void LevelDBMojoProxy::RenameFileImpl(OpaqueDir* dir, const std::string& old_path, const std::string& new_path, - filesystem::FileError* out_error) { + filesystem::mojom::FileError* out_error) { bool completed = dir->directory->Rename( mojo::String::From(old_path), mojo::String::From(new_path), out_error); DCHECK(completed); @@ -290,34 +296,34 @@ void LevelDBMojoProxy::RenameFileImpl(OpaqueDir* dir, void LevelDBMojoProxy::LockFileImpl(OpaqueDir* dir, const std::string& path, - filesystem::FileError* out_error, + filesystem::mojom::FileError* out_error, OpaqueLock** out_lock) { // Since a lock is associated with a file descriptor, we need to open and // have a persistent file on the other side of the connection. - filesystem::FilePtr target; - filesystem::FileRequest proxy = GetProxy(&target); + filesystem::mojom::FilePtr target; + filesystem::mojom::FileRequest proxy = GetProxy(&target); bool completed = dir->directory->OpenFile( mojo::String::From(path), std::move(proxy), - filesystem::kFlagOpenAlways | filesystem::kFlagRead | - filesystem::kFlagWrite, + filesystem::mojom::kFlagOpenAlways | filesystem::mojom::kFlagRead | + filesystem::mojom::kFlagWrite, out_error); DCHECK(completed); - if (*out_error != filesystem::FileError::OK) + if (*out_error != filesystem::mojom::FileError::OK) return; completed = target->Lock(out_error); DCHECK(completed); - if (*out_error == filesystem::FileError::OK) { + if (*out_error == filesystem::mojom::FileError::OK) { OpaqueLock* l = new OpaqueLock; l->lock_file = std::move(target); *out_lock = l; } } -void LevelDBMojoProxy::UnlockFileImpl(scoped_ptr<OpaqueLock> lock, - filesystem::FileError* out_error) { +void LevelDBMojoProxy::UnlockFileImpl(std::unique_ptr<OpaqueLock> lock, + filesystem::mojom::FileError* out_error) { lock->lock_file->Unlock(out_error); } diff --git a/chromium/components/leveldb/leveldb_mojo_proxy.h b/chromium/components/leveldb/leveldb_mojo_proxy.h index aa64828b9e6..881e8b7e0da 100644 --- a/chromium/components/leveldb/leveldb_mojo_proxy.h +++ b/chromium/components/leveldb/leveldb_mojo_proxy.h @@ -6,6 +6,7 @@ #define COMPONENTS_LEVELDB_LEVELDB_MOJO_PROXY_H_ #include <map> +#include <memory> #include <string> #include <utility> #include <vector> @@ -46,7 +47,7 @@ class LevelDBMojoProxy : public base::RefCountedThreadSafe<LevelDBMojoProxy> { // Passes ownership of a |directory| to the other thread, giving a reference // handle back to the caller. - OpaqueDir* RegisterDirectory(filesystem::DirectoryPtr directory); + OpaqueDir* RegisterDirectory(filesystem::mojom::DirectoryPtr directory); void UnregisterDirectory(OpaqueDir* dir); // Synchronously calls Directory.OpenFileHandle(). @@ -55,45 +56,47 @@ class LevelDBMojoProxy : public base::RefCountedThreadSafe<LevelDBMojoProxy> { uint32_t open_flags); // Synchronously syncs |directory_|. - filesystem::FileError SyncDirectory(OpaqueDir* dir, const std::string& name); + filesystem::mojom::FileError SyncDirectory(OpaqueDir* dir, + const std::string& name); // Synchronously checks whether |name| exists. bool FileExists(OpaqueDir* dir, const std::string& name); // Synchronously returns the filenames of all files in |path|. - filesystem::FileError GetChildren(OpaqueDir* dir, - const std::string& path, - std::vector<std::string>* result); + filesystem::mojom::FileError GetChildren(OpaqueDir* dir, + const std::string& path, + std::vector<std::string>* result); // Synchronously deletes |path|. - filesystem::FileError Delete(OpaqueDir* dir, - const std::string& path, - uint32_t delete_flags); + filesystem::mojom::FileError Delete(OpaqueDir* dir, + const std::string& path, + uint32_t delete_flags); // Synchronously creates |path|. - filesystem::FileError CreateDir(OpaqueDir* dir, const std::string& path); + filesystem::mojom::FileError CreateDir(OpaqueDir* dir, + const std::string& path); // Synchronously gets the size of a file. - filesystem::FileError GetFileSize(OpaqueDir* dir, - const std::string& path, - uint64_t* file_size); + filesystem::mojom::FileError GetFileSize(OpaqueDir* dir, + const std::string& path, + uint64_t* file_size); // Synchronously renames a file. - filesystem::FileError RenameFile(OpaqueDir* dir, - const std::string& old_path, - const std::string& new_path); + filesystem::mojom::FileError RenameFile(OpaqueDir* dir, + const std::string& old_path, + const std::string& new_path); // Synchronously locks a file. Returns both the file return code, and if OK, // an opaque object to the lock to enforce going through this interface to // unlock the file so that unlocking happens on the correct thread. - std::pair<filesystem::FileError, OpaqueLock*> LockFile( + std::pair<filesystem::mojom::FileError, OpaqueLock*> LockFile( OpaqueDir* dir, const std::string& path); // Unlocks a file. LevelDBMojoProxy takes ownership of lock. (We don't make // this a scoped_ptr because exporting the ctor/dtor for this struct publicly // defeats the purpose of the struct.) - filesystem::FileError UnlockFile(OpaqueLock* lock); + filesystem::mojom::FileError UnlockFile(OpaqueLock* lock); private: friend class base::RefCountedThreadSafe<LevelDBMojoProxy>; @@ -107,7 +110,7 @@ class LevelDBMojoProxy : public base::RefCountedThreadSafe<LevelDBMojoProxy> { // were called from the thread that |task_runner_| is, these might be run // on the current thread or through PostTask(). void RegisterDirectoryImpl( - mojo::InterfacePtrInfo<filesystem::Directory> directory_info, + mojo::InterfacePtrInfo<filesystem::mojom::Directory> directory_info, OpaqueDir** out_dir); void UnregisterDirectoryImpl(OpaqueDir* dir); void OpenFileHandleImpl(OpaqueDir* dir, @@ -116,35 +119,35 @@ class LevelDBMojoProxy : public base::RefCountedThreadSafe<LevelDBMojoProxy> { base::File* out_file); void SyncDirectoryImpl(OpaqueDir* dir, std::string name, - filesystem::FileError* out_error); + filesystem::mojom::FileError* out_error); void FileExistsImpl(OpaqueDir* dir, std::string name, bool* exists); void GetChildrenImpl(OpaqueDir* dir, std::string name, std::vector<std::string>* contents, - filesystem::FileError* out_error); + filesystem::mojom::FileError* out_error); void DeleteImpl(OpaqueDir* dir, std::string name, uint32_t delete_flags, - filesystem::FileError* out_error); + filesystem::mojom::FileError* out_error); void CreateDirImpl(OpaqueDir* dir, std::string name, - filesystem::FileError* out_error); + filesystem::mojom::FileError* out_error); void GetFileSizeImpl(OpaqueDir* dir, const std::string& path, uint64_t* file_size, - filesystem::FileError* out_error); + filesystem::mojom::FileError* out_error); void RenameFileImpl(OpaqueDir* dir, const std::string& old_path, const std::string& new_path, - filesystem::FileError* out_error); + filesystem::mojom::FileError* out_error); void LockFileImpl(OpaqueDir* dir, const std::string& path, - filesystem::FileError* out_error, + filesystem::mojom::FileError* out_error, OpaqueLock** out_lock); - void UnlockFileImpl(scoped_ptr<OpaqueLock> lock, - filesystem::FileError* out_error); + void UnlockFileImpl(std::unique_ptr<OpaqueLock> lock, + filesystem::mojom::FileError* out_error); // The task runner which represents the thread that all mojo objects are // bound to. diff --git a/chromium/components/leveldb/leveldb_service_impl.cc b/chromium/components/leveldb/leveldb_service_impl.cc index 9c4a540f875..a36281349c2 100644 --- a/chromium/components/leveldb/leveldb_service_impl.cc +++ b/chromium/components/leveldb/leveldb_service_impl.cc @@ -4,6 +4,9 @@ #include "components/leveldb/leveldb_service_impl.h" +#include <memory> + +#include "base/memory/ptr_util.h" #include "components/leveldb/env_mojo.h" #include "components/leveldb/leveldb_database_impl.h" #include "components/leveldb/public/cpp/util.h" @@ -22,19 +25,19 @@ LevelDBServiceImpl::LevelDBServiceImpl( LevelDBServiceImpl::~LevelDBServiceImpl() {} -void LevelDBServiceImpl::Open(filesystem::DirectoryPtr directory, +void LevelDBServiceImpl::Open(filesystem::mojom::DirectoryPtr directory, const mojo::String& dbname, - leveldb::LevelDBDatabaseRequest database, + leveldb::mojom::LevelDBDatabaseRequest database, const OpenCallback& callback) { - OpenWithOptions(leveldb::OpenOptions::New(), std::move(directory), dbname, - std::move(database), callback); + OpenWithOptions(leveldb::mojom::OpenOptions::New(), std::move(directory), + dbname, std::move(database), callback); } void LevelDBServiceImpl::OpenWithOptions( - leveldb::OpenOptionsPtr open_options, - filesystem::DirectoryPtr directory, + leveldb::mojom::OpenOptionsPtr open_options, + filesystem::mojom::DirectoryPtr directory, const mojo::String& dbname, - leveldb::LevelDBDatabaseRequest database, + leveldb::mojom::LevelDBDatabaseRequest database, const OpenCallback& callback) { leveldb::Options options; options.create_if_missing = open_options->create_if_missing; @@ -50,7 +53,7 @@ void LevelDBServiceImpl::OpenWithOptions( LevelDBMojoProxy::OpaqueDir* dir = thread_->RegisterDirectory(std::move(directory)); - scoped_ptr<MojoEnv> env_mojo(new MojoEnv(thread_, dir)); + std::unique_ptr<MojoEnv> env_mojo(new MojoEnv(thread_, dir)); options.env = env_mojo.get(); leveldb::DB* db = nullptr; @@ -58,19 +61,21 @@ void LevelDBServiceImpl::OpenWithOptions( if (s.ok()) { new LevelDBDatabaseImpl(std::move(database), std::move(env_mojo), - scoped_ptr<leveldb::DB>(db)); + base::WrapUnique(db)); } callback.Run(LeveldbStatusToError(s)); } -void LevelDBServiceImpl::OpenInMemory(leveldb::LevelDBDatabaseRequest database, - const OpenCallback& callback) { +void LevelDBServiceImpl::OpenInMemory( + leveldb::mojom::LevelDBDatabaseRequest database, + const OpenCallback& callback) { leveldb::Options options; options.create_if_missing = true; options.max_open_files = 0; // Use minimum. - scoped_ptr<leveldb::Env> env(leveldb::NewMemEnv(leveldb::Env::Default())); + std::unique_ptr<leveldb::Env> env( + leveldb::NewMemEnv(leveldb::Env::Default())); options.env = env.get(); leveldb::DB* db = nullptr; @@ -78,7 +83,7 @@ void LevelDBServiceImpl::OpenInMemory(leveldb::LevelDBDatabaseRequest database, if (s.ok()) { new LevelDBDatabaseImpl(std::move(database), std::move(env), - scoped_ptr<leveldb::DB>(db)); + base::WrapUnique(db)); } callback.Run(LeveldbStatusToError(s)); diff --git a/chromium/components/leveldb/leveldb_service_impl.h b/chromium/components/leveldb/leveldb_service_impl.h index 910a8d58674..b380f6a123d 100644 --- a/chromium/components/leveldb/leveldb_service_impl.h +++ b/chromium/components/leveldb/leveldb_service_impl.h @@ -13,22 +13,22 @@ namespace leveldb { // Creates LevelDBDatabases based scoped to a |directory|/|dbname|. -class LevelDBServiceImpl : public LevelDBService { +class LevelDBServiceImpl : public mojom::LevelDBService { public: LevelDBServiceImpl(scoped_refptr<base::SingleThreadTaskRunner> task_runner); ~LevelDBServiceImpl() override; // Overridden from LevelDBService: - void Open(filesystem::DirectoryPtr directory, + void Open(filesystem::mojom::DirectoryPtr directory, const mojo::String& dbname, - leveldb::LevelDBDatabaseRequest database, + leveldb::mojom::LevelDBDatabaseRequest database, const OpenCallback& callback) override; - void OpenWithOptions(leveldb::OpenOptionsPtr open_options, - filesystem::DirectoryPtr directory, + void OpenWithOptions(leveldb::mojom::OpenOptionsPtr open_options, + filesystem::mojom::DirectoryPtr directory, const mojo::String& dbname, - leveldb::LevelDBDatabaseRequest database, + leveldb::mojom::LevelDBDatabaseRequest database, const OpenCallback& callback) override; - void OpenInMemory(leveldb::LevelDBDatabaseRequest database, + void OpenInMemory(leveldb::mojom::LevelDBDatabaseRequest database, const OpenInMemoryCallback& callback) override; private: diff --git a/chromium/components/leveldb/leveldb_service_unittest.cc b/chromium/components/leveldb/leveldb_service_unittest.cc index 5fa31e860cb..9e510aea9bb 100644 --- a/chromium/components/leveldb/leveldb_service_unittest.cc +++ b/chromium/components/leveldb/leveldb_service_unittest.cc @@ -2,6 +2,7 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. +#include "base/bind.h" #include "base/macros.h" #include "components/filesystem/public/interfaces/directory.mojom.h" #include "components/filesystem/public/interfaces/file_system.mojom.h" @@ -9,17 +10,17 @@ #include "components/leveldb/public/interfaces/leveldb.mojom.h" #include "mojo/common/common_type_converters.h" #include "mojo/public/cpp/bindings/binding_set.h" -#include "mojo/shell/public/cpp/shell_connection.h" -#include "mojo/shell/public/cpp/shell_test.h" #include "mojo/util/capture_util.h" +#include "services/shell/public/cpp/shell_connection.h" +#include "services/shell/public/cpp/shell_test.h" -using filesystem::FileError; +using filesystem::mojom::FileError; using mojo::Capture; namespace leveldb { namespace { -class LevelDBServiceTest : public mojo::test::ShellTest { +class LevelDBServiceTest : public shell::test::ShellTest { public: LevelDBServiceTest() : ShellTest("exe:leveldb_service_unittests") {} ~LevelDBServiceTest() override {} @@ -40,179 +41,212 @@ class LevelDBServiceTest : public mojo::test::ShellTest { // Note: This has an out parameter rather than returning the |DirectoryPtr|, // since |ASSERT_...()| doesn't work with return values. - void GetUserDataDir(filesystem::DirectoryPtr* directory) { + void GetTempDirectory(filesystem::mojom::DirectoryPtr* directory) { FileError error = FileError::FAILED; - files()->OpenPersistentFileSystem(GetProxy(directory), - mojo::Capture(&error)); + files()->OpenTempDirectory(GetProxy(directory), mojo::Capture(&error)); ASSERT_TRUE(files().WaitForIncomingResponse()); ASSERT_EQ(FileError::OK, error); } - filesystem::FileSystemPtr& files() { return files_; } - LevelDBServicePtr& leveldb() { return leveldb_; } + filesystem::mojom::FileSystemPtr& files() { return files_; } + mojom::LevelDBServicePtr& leveldb() { return leveldb_; } private: - filesystem::FileSystemPtr files_; - LevelDBServicePtr leveldb_; + filesystem::mojom::FileSystemPtr files_; + mojom::LevelDBServicePtr leveldb_; DISALLOW_COPY_AND_ASSIGN(LevelDBServiceTest); }; TEST_F(LevelDBServiceTest, Basic) { - filesystem::DirectoryPtr directory; - GetUserDataDir(&directory); - - DatabaseError error; - LevelDBDatabasePtr database; - leveldb()->Open(std::move(directory), "test", GetProxy(&database), - Capture(&error)); + mojom::DatabaseError error; + mojom::LevelDBDatabasePtr database; + leveldb()->OpenInMemory(GetProxy(&database), Capture(&error)); ASSERT_TRUE(leveldb().WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); // Write a key to the database. - error = DatabaseError::INVALID_ARGUMENT; + error = mojom::DatabaseError::INVALID_ARGUMENT; database->Put(mojo::Array<uint8_t>::From(std::string("key")), mojo::Array<uint8_t>::From(std::string("value")), Capture(&error)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); // Read the key back from the database. - error = DatabaseError::INVALID_ARGUMENT; + error = mojom::DatabaseError::INVALID_ARGUMENT; mojo::Array<uint8_t> value; database->Get(mojo::Array<uint8_t>::From(std::string("key")), Capture(&error, &value)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); EXPECT_EQ("value", value.To<std::string>()); // Delete the key from the database. - error = DatabaseError::INVALID_ARGUMENT; + error = mojom::DatabaseError::INVALID_ARGUMENT; database->Delete(mojo::Array<uint8_t>::From(std::string("key")), Capture(&error)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); // Read the key back from the database. - error = DatabaseError::INVALID_ARGUMENT; + error = mojom::DatabaseError::INVALID_ARGUMENT; value.SetToEmpty(); database->Get(mojo::Array<uint8_t>::From(std::string("key")), Capture(&error, &value)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::NOT_FOUND, error); + EXPECT_EQ(mojom::DatabaseError::NOT_FOUND, error); EXPECT_EQ("", value.To<std::string>()); } TEST_F(LevelDBServiceTest, WriteBatch) { - filesystem::DirectoryPtr directory; - GetUserDataDir(&directory); - - DatabaseError error; - LevelDBDatabasePtr database; - leveldb()->Open(std::move(directory), "test", GetProxy(&database), - Capture(&error)); + mojom::DatabaseError error; + mojom::LevelDBDatabasePtr database; + leveldb()->OpenInMemory(GetProxy(&database), Capture(&error)); ASSERT_TRUE(leveldb().WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); // Write a key to the database. database->Put(mojo::Array<uint8_t>::From(std::string("key")), mojo::Array<uint8_t>::From(std::string("value")), Capture(&error)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); // Create a batched operation which both deletes "key" and adds another write. - mojo::Array<BatchedOperationPtr> operations; - BatchedOperationPtr item = BatchedOperation::New(); - item->type = BatchOperationType::DELETE_KEY; + mojo::Array<mojom::BatchedOperationPtr> operations; + mojom::BatchedOperationPtr item = mojom::BatchedOperation::New(); + item->type = mojom::BatchOperationType::DELETE_KEY; item->key = mojo::Array<uint8_t>::From(std::string("key")); operations.push_back(std::move(item)); - item = BatchedOperation::New(); - item->type = BatchOperationType::PUT_KEY; + item = mojom::BatchedOperation::New(); + item->type = mojom::BatchOperationType::PUT_KEY; item->key = mojo::Array<uint8_t>::From(std::string("other")); item->value = mojo::Array<uint8_t>::From(std::string("more")); operations.push_back(std::move(item)); database->Write(std::move(operations), Capture(&error)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); // Reading "key" should be invalid now. - error = DatabaseError::INVALID_ARGUMENT; + error = mojom::DatabaseError::INVALID_ARGUMENT; mojo::Array<uint8_t> value; database->Get(mojo::Array<uint8_t>::From(std::string("key")), Capture(&error, &value)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::NOT_FOUND, error); + EXPECT_EQ(mojom::DatabaseError::NOT_FOUND, error); EXPECT_EQ("", value.To<std::string>()); // Reading "other" should return "more" - error = DatabaseError::INVALID_ARGUMENT; + error = mojom::DatabaseError::INVALID_ARGUMENT; database->Get(mojo::Array<uint8_t>::From(std::string("other")), Capture(&error, &value)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); EXPECT_EQ("more", value.To<std::string>()); + + // Write a some prefixed keys to the database. + database->Put(mojo::Array<uint8_t>::From(std::string("prefix-key1")), + mojo::Array<uint8_t>::From(std::string("value")), + Capture(&error)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + database->Put(mojo::Array<uint8_t>::From(std::string("prefix-key2")), + mojo::Array<uint8_t>::From(std::string("value")), + Capture(&error)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + + // Create a batched operation to delete them. + operations.SetToEmpty(); + item = mojom::BatchedOperation::New(); + item->type = mojom::BatchOperationType::DELETE_PREFIXED_KEY; + item->key = mojo::Array<uint8_t>::From(std::string("prefix")); + operations.push_back(std::move(item)); + database->Write(std::move(operations), Capture(&error)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + + // Reading all "prefix" keys should be invalid now. + error = mojom::DatabaseError::INVALID_ARGUMENT; + value = nullptr; + database->Get(mojo::Array<uint8_t>::From(std::string("prefix-key1")), + Capture(&error, &value)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::NOT_FOUND, error); + EXPECT_EQ("", value.To<std::string>()); + // Reading "key" should be invalid now. + error = mojom::DatabaseError::INVALID_ARGUMENT; + value = nullptr; + database->Get(mojo::Array<uint8_t>::From(std::string("prefix-key2")), + Capture(&error, &value)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::NOT_FOUND, error); + EXPECT_EQ("", value.To<std::string>()); } TEST_F(LevelDBServiceTest, Reconnect) { - DatabaseError error; + mojom::DatabaseError error; - { - filesystem::DirectoryPtr directory; - GetUserDataDir(&directory); + filesystem::mojom::DirectoryPtr temp_directory; + GetTempDirectory(&temp_directory); - LevelDBDatabasePtr database; - leveldb()->Open(std::move(directory), "test", GetProxy(&database), - Capture(&error)); + { + filesystem::mojom::DirectoryPtr directory; + temp_directory->Clone(GetProxy(&directory)); + + mojom::LevelDBDatabasePtr database; + leveldb::mojom::OpenOptionsPtr options = leveldb::mojom::OpenOptions::New(); + options->error_if_exists = true; + options->create_if_missing = true; + leveldb()->OpenWithOptions(std::move(options), + std::move(directory), "test", + GetProxy(&database), + Capture(&error)); ASSERT_TRUE(leveldb().WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); // Write a key to the database. - error = DatabaseError::INVALID_ARGUMENT; + error = mojom::DatabaseError::INVALID_ARGUMENT; database->Put(mojo::Array<uint8_t>::From(std::string("key")), mojo::Array<uint8_t>::From(std::string("value")), Capture(&error)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); // The database should go out of scope here. } { - filesystem::DirectoryPtr directory; - GetUserDataDir(&directory); + filesystem::mojom::DirectoryPtr directory; + temp_directory->Clone(GetProxy(&directory)); // Reconnect to the database. - LevelDBDatabasePtr database; + mojom::LevelDBDatabasePtr database; leveldb()->Open(std::move(directory), "test", GetProxy(&database), Capture(&error)); ASSERT_TRUE(leveldb().WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); // We should still be able to read the key back from the database. - error = DatabaseError::INVALID_ARGUMENT; + error = mojom::DatabaseError::INVALID_ARGUMENT; mojo::Array<uint8_t> value; database->Get(mojo::Array<uint8_t>::From(std::string("key")), Capture(&error, &value)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); EXPECT_EQ("value", value.To<std::string>()); } } TEST_F(LevelDBServiceTest, GetSnapshotSimple) { - DatabaseError error; - - filesystem::DirectoryPtr directory; - GetUserDataDir(&directory); - - LevelDBDatabasePtr database; - leveldb()->Open(std::move(directory), "test", GetProxy(&database), - Capture(&error)); + mojom::DatabaseError error; + mojom::LevelDBDatabasePtr database; + leveldb()->OpenInMemory(GetProxy(&database), Capture(&error)); ASSERT_TRUE(leveldb().WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); uint64_t snapshot_id = 0; database->GetSnapshot(Capture(&snapshot_id)); @@ -221,24 +255,19 @@ TEST_F(LevelDBServiceTest, GetSnapshotSimple) { } TEST_F(LevelDBServiceTest, GetFromSnapshots) { - DatabaseError error; - - filesystem::DirectoryPtr directory; - GetUserDataDir(&directory); - - LevelDBDatabasePtr database; - leveldb()->Open(std::move(directory), "test", GetProxy(&database), - Capture(&error)); + mojom::DatabaseError error; + mojom::LevelDBDatabasePtr database; + leveldb()->OpenInMemory(GetProxy(&database), Capture(&error)); ASSERT_TRUE(leveldb().WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); // Write a key to the database. - error = DatabaseError::INVALID_ARGUMENT; + error = mojom::DatabaseError::INVALID_ARGUMENT; database->Put(mojo::Array<uint8_t>::From(std::string("key")), mojo::Array<uint8_t>::From(std::string("value")), Capture(&error)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); // Take a snapshot where key=value. uint64_t key_value_snapshot = 0; @@ -246,98 +275,227 @@ TEST_F(LevelDBServiceTest, GetFromSnapshots) { ASSERT_TRUE(database.WaitForIncomingResponse()); // Change key to "yek". - error = DatabaseError::INVALID_ARGUMENT; + error = mojom::DatabaseError::INVALID_ARGUMENT; database->Put(mojo::Array<uint8_t>::From(std::string("key")), mojo::Array<uint8_t>::From(std::string("yek")), Capture(&error)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); // (Ensure this change is live on the database.) - error = DatabaseError::INVALID_ARGUMENT; + error = mojom::DatabaseError::INVALID_ARGUMENT; mojo::Array<uint8_t> value; database->Get(mojo::Array<uint8_t>::From(std::string("key")), Capture(&error, &value)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); EXPECT_EQ("yek", value.To<std::string>()); // But if we were to read from the snapshot, we'd still get value. - error = DatabaseError::INVALID_ARGUMENT; + error = mojom::DatabaseError::INVALID_ARGUMENT; value.SetToEmpty(); database->GetFromSnapshot( key_value_snapshot, mojo::Array<uint8_t>::From(std::string("key")), Capture(&error, &value)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); EXPECT_EQ("value", value.To<std::string>()); } TEST_F(LevelDBServiceTest, InvalidArgumentOnInvalidSnapshot) { - filesystem::DirectoryPtr directory; - GetUserDataDir(&directory); - - LevelDBDatabasePtr database; - DatabaseError error = DatabaseError::INVALID_ARGUMENT; - leveldb()->Open(std::move(directory), "test", GetProxy(&database), - Capture(&error)); + mojom::LevelDBDatabasePtr database; + mojom::DatabaseError error = mojom::DatabaseError::INVALID_ARGUMENT; + leveldb()->OpenInMemory(GetProxy(&database), Capture(&error)); ASSERT_TRUE(leveldb().WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); uint64_t invalid_snapshot = 8; - error = DatabaseError::OK; + error = mojom::DatabaseError::OK; mojo::Array<uint8_t> value; database->GetFromSnapshot( invalid_snapshot, mojo::Array<uint8_t>::From(std::string("key")), Capture(&error, &value)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::INVALID_ARGUMENT, error); + EXPECT_EQ(mojom::DatabaseError::INVALID_ARGUMENT, error); } TEST_F(LevelDBServiceTest, MemoryDBReadWrite) { - LevelDBDatabasePtr database; - DatabaseError error = DatabaseError::INVALID_ARGUMENT; + mojom::LevelDBDatabasePtr database; + mojom::DatabaseError error = mojom::DatabaseError::INVALID_ARGUMENT; leveldb()->OpenInMemory(GetProxy(&database), Capture(&error)); ASSERT_TRUE(leveldb().WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); // Write a key to the database. - error = DatabaseError::INVALID_ARGUMENT; + error = mojom::DatabaseError::INVALID_ARGUMENT; database->Put(mojo::Array<uint8_t>::From(std::string("key")), mojo::Array<uint8_t>::From(std::string("value")), Capture(&error)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); // Read the key back from the database. - error = DatabaseError::INVALID_ARGUMENT; + error = mojom::DatabaseError::INVALID_ARGUMENT; mojo::Array<uint8_t> value; database->Get(mojo::Array<uint8_t>::From(std::string("key")), Capture(&error, &value)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); EXPECT_EQ("value", value.To<std::string>()); // Delete the key from the database. - error = DatabaseError::INVALID_ARGUMENT; + error = mojom::DatabaseError::INVALID_ARGUMENT; database->Delete(mojo::Array<uint8_t>::From(std::string("key")), Capture(&error)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); // Read the key back from the database. - error = DatabaseError::INVALID_ARGUMENT; + error = mojom::DatabaseError::INVALID_ARGUMENT; value.SetToEmpty(); database->Get(mojo::Array<uint8_t>::From(std::string("key")), Capture(&error, &value)); ASSERT_TRUE(database.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::NOT_FOUND, error); + EXPECT_EQ(mojom::DatabaseError::NOT_FOUND, error); EXPECT_EQ("", value.To<std::string>()); } +TEST_F(LevelDBServiceTest, Prefixed) { + // Open an in memory database for speed. + mojom::DatabaseError error = mojom::DatabaseError::INVALID_ARGUMENT; + mojom::LevelDBDatabasePtr database; + leveldb()->OpenInMemory(GetProxy(&database), Capture(&error)); + ASSERT_TRUE(leveldb().WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + + const std::string prefix("prefix"); + mojo::Array<mojom::KeyValuePtr> key_values; + + // Completely empty database. + error = mojom::DatabaseError::INVALID_ARGUMENT; + database->GetPrefixed(mojo::Array<uint8_t>::From(prefix), + Capture(&error, &key_values)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + EXPECT_TRUE(key_values.empty()); + + // No values with our prefix, but values before and after. + error = mojom::DatabaseError::INVALID_ARGUMENT; + database->Put(mojo::Array<uint8_t>::From(std::string("a-before-prefix")), + mojo::Array<uint8_t>::From(std::string("value")), + Capture(&error)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + error = mojom::DatabaseError::INVALID_ARGUMENT; + database->Put(mojo::Array<uint8_t>::From(std::string("z-after-prefix")), + mojo::Array<uint8_t>::From(std::string("value")), + Capture(&error)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + key_values.SetToEmpty(); + error = mojom::DatabaseError::INVALID_ARGUMENT; + database->GetPrefixed(mojo::Array<uint8_t>::From(prefix), + Capture(&error, &key_values)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + EXPECT_TRUE(key_values.empty()); + + // One value with the exact prefix. + database->Put(mojo::Array<uint8_t>::From(prefix), + mojo::Array<uint8_t>::From(std::string("value")), + Capture(&error)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + error = mojom::DatabaseError::INVALID_ARGUMENT; + key_values.SetToEmpty(); + database->GetPrefixed(mojo::Array<uint8_t>::From(prefix), + Capture(&error, &key_values)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + EXPECT_EQ(1u, key_values.size()); + EXPECT_EQ("prefix", key_values[0]->key.To<std::string>()); + EXPECT_EQ("value", key_values[0]->value.To<std::string>()); + + // Multiple values with starting with the prefix. + database->Put(mojo::Array<uint8_t>::From(prefix + "2"), + mojo::Array<uint8_t>::From(std::string("value2")), + Capture(&error)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + error = mojom::DatabaseError::INVALID_ARGUMENT; + key_values.SetToEmpty(); + database->GetPrefixed(mojo::Array<uint8_t>::From(prefix), + Capture(&error, &key_values)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + EXPECT_EQ(2u, key_values.size()); + EXPECT_EQ("prefix", key_values[0]->key.To<std::string>()); + EXPECT_EQ("value", key_values[0]->value.To<std::string>()); + EXPECT_EQ("prefix2", key_values[1]->key.To<std::string>()); + EXPECT_EQ("value2", key_values[1]->value.To<std::string>()); + + // Delete the prefixed values. + error = mojom::DatabaseError::INVALID_ARGUMENT; + database->DeletePrefixed(mojo::Array<uint8_t>::From(prefix), + Capture(&error)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + error = mojom::DatabaseError::INVALID_ARGUMENT; + key_values.SetToEmpty(); + database->GetPrefixed(mojo::Array<uint8_t>::From(prefix), + Capture(&error, &key_values)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + EXPECT_TRUE(key_values.empty()); + + // Make sure the others are not deleted. + mojo::Array<uint8_t> value; + database->Get(mojo::Array<uint8_t>::From(std::string("a-before-prefix")), + Capture(&error, &value)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + EXPECT_EQ("value", value.To<std::string>()); + value.SetToEmpty(); + database->Get(mojo::Array<uint8_t>::From(std::string("z-after-prefix")), + Capture(&error, &value)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + EXPECT_EQ("value", value.To<std::string>()); + + // A key having our prefix, but no key matching it exactly. + // Even thought there is no exact matching key, GetPrefixed + // and DeletePrefixed still operate on the values. + error = mojom::DatabaseError::INVALID_ARGUMENT; + database->Put(mojo::Array<uint8_t>::From(prefix + "2"), + mojo::Array<uint8_t>::From(std::string("value2")), + Capture(&error)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + error = mojom::DatabaseError::INVALID_ARGUMENT; + key_values.SetToEmpty(); + database->GetPrefixed(mojo::Array<uint8_t>::From(prefix), + Capture(&error, &key_values)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + EXPECT_EQ(1u, key_values.size()); + EXPECT_EQ("prefix2", key_values[0]->key.To<std::string>()); + EXPECT_EQ("value2", key_values[0]->value.To<std::string>()); + error = mojom::DatabaseError::INVALID_ARGUMENT; + database->DeletePrefixed(mojo::Array<uint8_t>::From(prefix), + Capture(&error)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + error = mojom::DatabaseError::INVALID_ARGUMENT; + key_values.SetToEmpty(); + database->GetPrefixed(mojo::Array<uint8_t>::From(prefix), + Capture(&error, &key_values)); + ASSERT_TRUE(database.WaitForIncomingResponse()); + EXPECT_EQ(mojom::DatabaseError::OK, error); + EXPECT_TRUE(key_values.empty()); +} } // namespace } // namespace leveldb diff --git a/chromium/components/leveldb/main.cc b/chromium/components/leveldb/main.cc index 261529a2a47..7e5c9fb4ab5 100644 --- a/chromium/components/leveldb/main.cc +++ b/chromium/components/leveldb/main.cc @@ -5,9 +5,9 @@ #include "base/macros.h" #include "components/leveldb/leveldb_app.h" #include "mojo/public/c/system/main.h" -#include "mojo/shell/public/cpp/application_runner.h" +#include "services/shell/public/cpp/application_runner.h" MojoResult MojoMain(MojoHandle application_request) { - mojo::ApplicationRunner runner(new leveldb::LevelDBApp()); + shell::ApplicationRunner runner(new leveldb::LevelDBApp()); return runner.Run(application_request); } diff --git a/chromium/components/leveldb/manifest.json b/chromium/components/leveldb/manifest.json index ea917fc4abb..a56b36d94c7 100644 --- a/chromium/components/leveldb/manifest.json +++ b/chromium/components/leveldb/manifest.json @@ -1,5 +1,10 @@ { + "manifest_version": 1, "name": "mojo:leveldb", "display_name": "LevelDB Service", - "capabilities": { "*": ["*"] } + "capabilities": { + "required": { + "*": { "classes": [ "app" ] } + } + } } diff --git a/chromium/components/leveldb/public/cpp/BUILD.gn b/chromium/components/leveldb/public/cpp/BUILD.gn index 29e773a7643..f615abf657e 100644 --- a/chromium/components/leveldb/public/cpp/BUILD.gn +++ b/chromium/components/leveldb/public/cpp/BUILD.gn @@ -14,7 +14,7 @@ source_set("cpp") { "//base", "//components/leveldb/public/interfaces", "//mojo/common", - "//mojo/shell/public/cpp", + "//services/shell/public/cpp", "//third_party/leveldatabase", ] } diff --git a/chromium/components/leveldb/public/cpp/remote_iterator.cc b/chromium/components/leveldb/public/cpp/remote_iterator.cc index 39577a68bdc..b1042f70a53 100644 --- a/chromium/components/leveldb/public/cpp/remote_iterator.cc +++ b/chromium/components/leveldb/public/cpp/remote_iterator.cc @@ -8,11 +8,12 @@ namespace leveldb { -RemoteIterator::RemoteIterator(LevelDBDatabase* database, uint64_t iterator_id) +RemoteIterator::RemoteIterator(mojom::LevelDBDatabase* database, + uint64_t iterator_id) : database_(database), iterator_id_(iterator_id), valid_(false), - status_(DatabaseError::OK) {} + status_(mojom::DatabaseError::OK) {} RemoteIterator::~RemoteIterator() { database_->ReleaseIterator(iterator_id_); diff --git a/chromium/components/leveldb/public/cpp/remote_iterator.h b/chromium/components/leveldb/public/cpp/remote_iterator.h index 056a2bf96cf..1d3920ba123 100644 --- a/chromium/components/leveldb/public/cpp/remote_iterator.h +++ b/chromium/components/leveldb/public/cpp/remote_iterator.h @@ -11,15 +11,13 @@ namespace leveldb { -class LevelDBDatabase; - // A wrapper around the raw iterator movement methods on the mojo leveldb // interface to allow drop in replacement to current leveldb usage. // // Note: Next(), Prev() and all the Seek*() calls cause mojo sync calls. class RemoteIterator : public Iterator { public: - RemoteIterator(LevelDBDatabase* database, uint64_t iterator_id); + RemoteIterator(mojom::LevelDBDatabase* database, uint64_t iterator_id); ~RemoteIterator() override; // Overridden from leveldb::Iterator: @@ -34,11 +32,11 @@ class RemoteIterator : public Iterator { Status status() const override; private: - LevelDBDatabase* database_; + mojom::LevelDBDatabase* database_; uint64_t iterator_id_; bool valid_; - DatabaseError status_; + mojom::DatabaseError status_; mojo::Array<uint8_t> key_; mojo::Array<uint8_t> value_; diff --git a/chromium/components/leveldb/public/cpp/util.cc b/chromium/components/leveldb/public/cpp/util.cc index 3d60ea2e971..647f12c0d80 100644 --- a/chromium/components/leveldb/public/cpp/util.cc +++ b/chromium/components/leveldb/public/cpp/util.cc @@ -8,35 +8,35 @@ namespace leveldb { -DatabaseError LeveldbStatusToError(const leveldb::Status& s) { +mojom::DatabaseError LeveldbStatusToError(const leveldb::Status& s) { if (s.ok()) - return DatabaseError::OK; + return mojom::DatabaseError::OK; if (s.IsNotFound()) - return DatabaseError::NOT_FOUND; + return mojom::DatabaseError::NOT_FOUND; if (s.IsCorruption()) - return DatabaseError::CORRUPTION; + return mojom::DatabaseError::CORRUPTION; if (s.IsNotSupportedError()) - return DatabaseError::NOT_SUPPORTED; + return mojom::DatabaseError::NOT_SUPPORTED; if (s.IsIOError()) - return DatabaseError::IO_ERROR; - return DatabaseError::INVALID_ARGUMENT; + return mojom::DatabaseError::IO_ERROR; + return mojom::DatabaseError::INVALID_ARGUMENT; } -leveldb::Status DatabaseErrorToStatus(DatabaseError e, +leveldb::Status DatabaseErrorToStatus(mojom::DatabaseError e, const Slice& msg, const Slice& msg2) { switch (e) { - case DatabaseError::OK: + case mojom::DatabaseError::OK: return leveldb::Status::OK(); - case DatabaseError::NOT_FOUND: + case mojom::DatabaseError::NOT_FOUND: return leveldb::Status::NotFound(msg, msg2); - case DatabaseError::CORRUPTION: + case mojom::DatabaseError::CORRUPTION: return leveldb::Status::Corruption(msg, msg2); - case DatabaseError::NOT_SUPPORTED: + case mojom::DatabaseError::NOT_SUPPORTED: return leveldb::Status::NotSupported(msg, msg2); - case DatabaseError::INVALID_ARGUMENT: + case mojom::DatabaseError::INVALID_ARGUMENT: return leveldb::Status::InvalidArgument(msg, msg2); - case DatabaseError::IO_ERROR: + case mojom::DatabaseError::IO_ERROR: return leveldb::Status::IOError(msg, msg2); } diff --git a/chromium/components/leveldb/public/cpp/util.h b/chromium/components/leveldb/public/cpp/util.h index 2540be5241c..44f733af30d 100644 --- a/chromium/components/leveldb/public/cpp/util.h +++ b/chromium/components/leveldb/public/cpp/util.h @@ -12,13 +12,13 @@ namespace leveldb { class Slice; class Status; -// Builds a mojo DatabaseError from a leveldb::Status object. -DatabaseError LeveldbStatusToError(const leveldb::Status& s); +// Builds a mojo mojom::DatabaseError from a leveldb::Status object. +mojom::DatabaseError LeveldbStatusToError(const leveldb::Status& s); // Creates a leveldb Status object form a database error and two optional // messages. A mojoification of the various static leveldb::Status // constructors. -leveldb::Status DatabaseErrorToStatus(DatabaseError e, +leveldb::Status DatabaseErrorToStatus(mojom::DatabaseError e, const Slice& msg, const Slice& msg2); diff --git a/chromium/components/leveldb/public/interfaces/OWNERS b/chromium/components/leveldb/public/interfaces/OWNERS new file mode 100644 index 00000000000..9e621796752 --- /dev/null +++ b/chromium/components/leveldb/public/interfaces/OWNERS @@ -0,0 +1,13 @@ +# Changes to Mojo interfaces require a security review to avoid +# introducing new sandbox escapes. +per-file *.mojom=set noparent +per-file *.mojom=dcheng@chromium.org +per-file *.mojom=inferno@chromium.org +per-file *.mojom=jln@chromium.org +per-file *.mojom=jschuh@chromium.org +per-file *.mojom=kenrb@chromium.org +per-file *.mojom=mkwst@chromium.org +per-file *.mojom=nasko@chromium.org +per-file *.mojom=palmer@chromium.org +per-file *.mojom=tsepez@chromium.org +per-file *.mojom=wfh@chromium.org diff --git a/chromium/components/leveldb/public/interfaces/leveldb.mojom b/chromium/components/leveldb/public/interfaces/leveldb.mojom index 72bcc698945..1e7d38a0ed6 100644 --- a/chromium/components/leveldb/public/interfaces/leveldb.mojom +++ b/chromium/components/leveldb/public/interfaces/leveldb.mojom @@ -2,7 +2,7 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -module leveldb; +module leveldb.mojom; import "components/filesystem/public/interfaces/directory.mojom"; @@ -17,7 +17,8 @@ enum DatabaseError { enum BatchOperationType { PUT_KEY, - DELETE_KEY + DELETE_KEY, + DELETE_PREFIXED_KEY }; struct BatchedOperation { @@ -26,6 +27,11 @@ struct BatchedOperation { array<uint8>? value; }; +struct KeyValue { + array<uint8> key; + array<uint8> value; +}; + // Options which control the behavior of a database. (This struct corresponds // with the struct in leveldb's options.h.) struct OpenOptions { @@ -55,11 +61,11 @@ struct OpenOptions { // Service which hands out databases. interface LevelDBService { - Open(filesystem.Directory directory, + Open(filesystem.mojom.Directory directory, string dbname, LevelDBDatabase& database) => (DatabaseError status); OpenWithOptions(OpenOptions options, - filesystem.Directory directory, + filesystem.mojom.Directory directory, string dbname, LevelDBDatabase& database) => (DatabaseError status); @@ -78,11 +84,16 @@ interface LevelDBDatabase { // did not exist in the database. Delete(array<uint8> key) => (DatabaseError status); + DeletePrefixed(array<uint8> key_prefix) => (DatabaseError status); + // Atomically performs all |operations|. Write(array<BatchedOperation> operations) => (DatabaseError status); Get(array<uint8> key) => (DatabaseError status, array<uint8> value); + GetPrefixed(array<uint8> key_prefix) + => (DatabaseError status, array<KeyValue> data); + // Snapshots ------------------------------------------------------------- // Returns a handle to the current database state. diff --git a/chromium/components/leveldb/remote_iterator_unittest.cc b/chromium/components/leveldb/remote_iterator_unittest.cc index 6b97129e5d1..274229a6d23 100644 --- a/chromium/components/leveldb/remote_iterator_unittest.cc +++ b/chromium/components/leveldb/remote_iterator_unittest.cc @@ -8,16 +8,16 @@ #include "components/leveldb/public/cpp/remote_iterator.h" #include "components/leveldb/public/interfaces/leveldb.mojom.h" #include "mojo/common/common_type_converters.h" -#include "mojo/shell/public/cpp/shell_connection.h" -#include "mojo/shell/public/cpp/shell_test.h" #include "mojo/util/capture_util.h" +#include "services/shell/public/cpp/shell_connection.h" +#include "services/shell/public/cpp/shell_test.h" using mojo::Capture; namespace leveldb { namespace { -class RemoteIteratorTest : public mojo::test::ShellTest { +class RemoteIteratorTest : public shell::test::ShellTest { public: RemoteIteratorTest() : ShellTest("exe:leveldb_service_unittests") {} ~RemoteIteratorTest() override {} @@ -28,21 +28,21 @@ class RemoteIteratorTest : public mojo::test::ShellTest { ShellTest::SetUp(); connector()->ConnectToInterface("mojo:leveldb", &leveldb_); - DatabaseError error; + mojom::DatabaseError error; leveldb()->OpenInMemory(GetProxy(&database_), Capture(&error)); ASSERT_TRUE(leveldb().WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); std::map<std::string, std::string> data{ {"a", "first"}, {"b:suffix", "second"}, {"c", "third"}}; for (auto p : data) { // Write a key to the database. - error = DatabaseError::INVALID_ARGUMENT; + error = mojom::DatabaseError::INVALID_ARGUMENT; database_->Put(mojo::Array<uint8_t>::From(p.first), mojo::Array<uint8_t>::From(p.second), Capture(&error)); ASSERT_TRUE(database_.WaitForIncomingResponse()); - EXPECT_EQ(DatabaseError::OK, error); + EXPECT_EQ(mojom::DatabaseError::OK, error); } } @@ -51,12 +51,12 @@ class RemoteIteratorTest : public mojo::test::ShellTest { ShellTest::TearDown(); } - LevelDBServicePtr& leveldb() { return leveldb_; } - LevelDBDatabasePtr& database() { return database_; } + mojom::LevelDBServicePtr& leveldb() { return leveldb_; } + mojom::LevelDBDatabasePtr& database() { return database_; } private: - LevelDBServicePtr leveldb_; - LevelDBDatabasePtr database_; + mojom::LevelDBServicePtr leveldb_; + mojom::LevelDBDatabasePtr database_; DISALLOW_COPY_AND_ASSIGN(RemoteIteratorTest); }; diff --git a/chromium/components/leveldb/test_manifest.json b/chromium/components/leveldb/test_manifest.json index b013a4ac8d1..c59580f7ad3 100644 --- a/chromium/components/leveldb/test_manifest.json +++ b/chromium/components/leveldb/test_manifest.json @@ -1,5 +1,11 @@ { + "manifest_version": 1, "name": "exe:leveldb_service_unittests", "display_name": "LevelDB Service Unittests", - "capabilities": { "*": [ "*" ] } + "capabilities": { + "required": { + "mojo:filesystem": { "interfaces": [ "filesystem::mojom::FileSystem" ] }, + "mojo:leveldb": { "interfaces": [ "leveldb::mojom::LevelDBService" ] } + } + } } |