diff options
author | alecflett@chromium.org <alecflett@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2013-05-30 23:09:08 +0000 |
---|---|---|
committer | alecflett@chromium.org <alecflett@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2013-05-30 23:09:08 +0000 |
commit | e1bcc0207442374ab4d539e6a5623fe4cf1fe8cb (patch) | |
tree | 01141ee8180a33ca0fba59379bf5d9e0f19c51db | |
parent | 71c1cbb0f63b371bc4167c9735e400457b376df2 (diff) | |
download | chromium_src-e1bcc0207442374ab4d539e6a5623fe4cf1fe8cb.zip chromium_src-e1bcc0207442374ab4d539e6a5623fe4cf1fe8cb.tar.gz chromium_src-e1bcc0207442374ab4d539e6a5623fe4cf1fe8cb.tar.bz2 |
Revert "Migrate the IndexedDB backend from Blink to Chromium"
This reverts commit 71c1cbb0f63b371bc4167c9735e400457b376df2.
Landed the wrong patch.
BUG=
TBR=jsbell
Review URL: https://codereview.chromium.org/15853013
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@203258 0039d316-1c4b-4281-b951-d872f2087c98
71 files changed, 425 insertions, 14745 deletions
diff --git a/android_webview/tools/third_party_files_whitelist.txt b/android_webview/tools/third_party_files_whitelist.txt index b135b85..4f67aee 100644 --- a/android_webview/tools/third_party_files_whitelist.txt +++ b/android_webview/tools/third_party_files_whitelist.txt @@ -73,10 +73,6 @@ chrome_frame/CFInstance.js chrome/tools/test/generate_mime_tests.pl # Copyright Alf Watt; BSD license. Not used on Android. content/browser/geolocation/osx_wifi.h -# Copyright The Chromium Authors and Apple Inc. Taken from Blink. -content/browser/indexed_db/leveldb/avltree.h -# Copyright The Chromium Authors and Apple Inc. Taken from Blink. -content/browser/indexed_db/leveldb/fixed_array.h # Copyright The Chromium Authors, Apple Inc and Graham Dennis; BSD license. Not # used on Android. content/browser/renderer_host/render_widget_host_view_mac.mm diff --git a/content/browser/in_process_webkit/indexed_db_database_callbacks.cc b/content/browser/in_process_webkit/indexed_db_database_callbacks.cc index a57193d..9a7cc10 100644 --- a/content/browser/in_process_webkit/indexed_db_database_callbacks.cc +++ b/content/browser/in_process_webkit/indexed_db_database_callbacks.cc @@ -4,7 +4,6 @@ #include "content/browser/in_process_webkit/indexed_db_database_callbacks.h" -#include "base/memory/scoped_vector.h" #include "content/browser/in_process_webkit/indexed_db_dispatcher_host.h" #include "content/common/indexed_db/indexed_db_messages.h" @@ -16,39 +15,46 @@ IndexedDBDatabaseCallbacks::IndexedDBDatabaseCallbacks( int ipc_database_callbacks_id) : dispatcher_host_(dispatcher_host), ipc_thread_id_(ipc_thread_id), - ipc_database_callbacks_id_(ipc_database_callbacks_id) {} + ipc_database_callbacks_id_(ipc_database_callbacks_id) { +} -IndexedDBDatabaseCallbacks::~IndexedDBDatabaseCallbacks() {} +IndexedDBDatabaseCallbacks::~IndexedDBDatabaseCallbacks() { +} void IndexedDBDatabaseCallbacks::onForcedClose() { - dispatcher_host_->Send(new IndexedDBMsg_DatabaseCallbacksForcedClose( - ipc_thread_id_, ipc_database_callbacks_id_)); + dispatcher_host_->Send( + new IndexedDBMsg_DatabaseCallbacksForcedClose( + ipc_thread_id_, + ipc_database_callbacks_id_)); } void IndexedDBDatabaseCallbacks::onVersionChange(long long old_version, long long new_version) { - dispatcher_host_->Send(new IndexedDBMsg_DatabaseCallbacksIntVersionChange( - ipc_thread_id_, ipc_database_callbacks_id_, old_version, new_version)); + dispatcher_host_->Send( + new IndexedDBMsg_DatabaseCallbacksIntVersionChange( + ipc_thread_id_, + ipc_database_callbacks_id_, + old_version, + new_version)); } void IndexedDBDatabaseCallbacks::onAbort( long long host_transaction_id, const WebKit::WebIDBDatabaseError& error) { - dispatcher_host_->FinishTransaction(host_transaction_id, false); - dispatcher_host_->Send(new IndexedDBMsg_DatabaseCallbacksAbort( - ipc_thread_id_, - ipc_database_callbacks_id_, - dispatcher_host_->RendererTransactionId(host_transaction_id), - error.code(), - error.message())); + dispatcher_host_->FinishTransaction(host_transaction_id, false); + dispatcher_host_->Send( + new IndexedDBMsg_DatabaseCallbacksAbort( + ipc_thread_id_, ipc_database_callbacks_id_, + dispatcher_host_->RendererTransactionId(host_transaction_id), + error.code(), error.message())); } void IndexedDBDatabaseCallbacks::onComplete(long long host_transaction_id) { - dispatcher_host_->FinishTransaction(host_transaction_id, true); - dispatcher_host_->Send(new IndexedDBMsg_DatabaseCallbacksComplete( - ipc_thread_id_, - ipc_database_callbacks_id_, - dispatcher_host_->RendererTransactionId(host_transaction_id))); + dispatcher_host_->FinishTransaction(host_transaction_id, true); + dispatcher_host_->Send( + new IndexedDBMsg_DatabaseCallbacksComplete( + ipc_thread_id_, ipc_database_callbacks_id_, + dispatcher_host_->RendererTransactionId(host_transaction_id))); } } // namespace content diff --git a/content/browser/in_process_webkit/indexed_db_dispatcher_host.cc b/content/browser/in_process_webkit/indexed_db_dispatcher_host.cc index 6d640c5..8532d21 100644 --- a/content/browser/in_process_webkit/indexed_db_dispatcher_host.cc +++ b/content/browser/in_process_webkit/indexed_db_dispatcher_host.cc @@ -41,24 +41,26 @@ using WebKit::WebIDBCallbacks; using WebKit::WebIDBCursor; using WebKit::WebIDBDatabase; using WebKit::WebIDBDatabaseError; +using WebKit::WebIDBIndex; using WebKit::WebIDBKey; using WebKit::WebIDBMetadata; +using WebKit::WebIDBObjectStore; using WebKit::WebString; using WebKit::WebVector; namespace content { namespace { -template <class T> void DeleteOnWebKitThread(T* obj) { - if (!BrowserThread::DeleteSoon( - BrowserThread::WEBKIT_DEPRECATED, FROM_HERE, obj)) +template <class T> +void DeleteOnWebKitThread(T* obj) { + if (!BrowserThread::DeleteSoon(BrowserThread::WEBKIT_DEPRECATED, + FROM_HERE, obj)) delete obj; } } IndexedDBDispatcherHost::IndexedDBDispatcherHost( - int ipc_process_id, - IndexedDBContextImpl* indexed_db_context) + int ipc_process_id, IndexedDBContextImpl* indexed_db_context) : indexed_db_context_(indexed_db_context), database_dispatcher_host_(new DatabaseDispatcherHost(this)), cursor_dispatcher_host_(new CursorDispatcherHost(this)), @@ -66,14 +68,14 @@ IndexedDBDispatcherHost::IndexedDBDispatcherHost( DCHECK(indexed_db_context_.get()); } -IndexedDBDispatcherHost::~IndexedDBDispatcherHost() {} +IndexedDBDispatcherHost::~IndexedDBDispatcherHost() { +} void IndexedDBDispatcherHost::OnChannelClosing() { BrowserMessageFilter::OnChannelClosing(); bool success = BrowserThread::PostTask( - BrowserThread::WEBKIT_DEPRECATED, - FROM_HERE, + BrowserThread::WEBKIT_DEPRECATED, FROM_HERE, base::Bind(&IndexedDBDispatcherHost::ResetDispatcherHosts, this)); if (!success) @@ -117,12 +119,12 @@ bool IndexedDBDispatcherHost::OnMessageReceived(const IPC::Message& message, if (!handled) { handled = true; IPC_BEGIN_MESSAGE_MAP_EX(IndexedDBDispatcherHost, message, *message_was_ok) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_FactoryGetDatabaseNames, - OnIDBFactoryGetDatabaseNames) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_FactoryOpen, OnIDBFactoryOpen) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_FactoryDeleteDatabase, - OnIDBFactoryDeleteDatabase) - IPC_MESSAGE_UNHANDLED(handled = false) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_FactoryGetDatabaseNames, + OnIDBFactoryGetDatabaseNames) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_FactoryOpen, OnIDBFactoryOpen) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_FactoryDeleteDatabase, + OnIDBFactoryDeleteDatabase) + IPC_MESSAGE_UNHANDLED(handled = false) IPC_END_MESSAGE_MAP() } return handled; @@ -149,8 +151,10 @@ int32 IndexedDBDispatcherHost::Add(WebIDBDatabase* idb_database, return ipc_database_id; } -void IndexedDBDispatcherHost::RegisterTransactionId(int64 host_transaction_id, - const GURL& url) { +void IndexedDBDispatcherHost::RegisterTransactionId( + int64 host_transaction_id, + const GURL& url) +{ if (!database_dispatcher_host_) return; database_dispatcher_host_->transaction_url_map_[host_transaction_id] = url; @@ -171,8 +175,8 @@ int64 IndexedDBDispatcherHost::HostTransactionId(int64 transaction_id) { int64 IndexedDBDispatcherHost::RendererTransactionId( int64 host_transaction_id) { - DCHECK(host_transaction_id >> 32 == base::GetProcId(peer_handle())) - << "Invalid renderer target for transaction id"; + DCHECK(host_transaction_id >> 32 == base::GetProcId(peer_handle())) << + "Invalid renderer target for transaction id"; return host_transaction_id & 0xffffffff; } @@ -182,7 +186,8 @@ WebIDBCursor* IndexedDBDispatcherHost::GetCursorFromId(int32 ipc_cursor_id) { } IndexedDBDatabaseMetadata IndexedDBDispatcherHost::ConvertMetadata( - const WebIDBMetadata& web_metadata) { + const WebIDBMetadata& web_metadata) +{ IndexedDBDatabaseMetadata metadata; metadata.id = web_metadata.id; metadata.name = web_metadata.name; @@ -222,9 +227,8 @@ void IndexedDBDispatcherHost::OnIDBFactoryGetDatabaseNames( base::FilePath indexed_db_path = indexed_db_context_->data_path(); Context()->GetIDBFactory()->getDatabaseNames( - new IndexedDBCallbacks<WebVector<WebString> >( - this, params.ipc_thread_id, params.ipc_callbacks_id), - params.database_identifier, + new IndexedDBCallbacks<WebVector<WebString> >(this, params.ipc_thread_id, + params.ipc_callbacks_id), params.database_identifier, webkit_base::FilePathToWebString(indexed_db_path)); } @@ -242,20 +246,19 @@ void IndexedDBDispatcherHost::OnIDBFactoryOpen( // TODO(dgrogan): Don't let a non-existing database be opened (and therefore // created) if this origin is already over quota. - Context()->GetIDBFactory() - ->open(params.name, - params.version, - host_transaction_id, - new IndexedDBCallbacksDatabase(this, - params.ipc_thread_id, - params.ipc_callbacks_id, - params.ipc_database_callbacks_id, - host_transaction_id, - origin_url), - new IndexedDBDatabaseCallbacks( - this, params.ipc_thread_id, params.ipc_database_callbacks_id), - params.database_identifier, - webkit_base::FilePathToWebString(indexed_db_path)); + Context()->GetIDBFactory()->open( + params.name, + params.version, + host_transaction_id, + new IndexedDBCallbacksDatabase(this, params.ipc_thread_id, + params.ipc_callbacks_id, + params.ipc_database_callbacks_id, + host_transaction_id, + origin_url), + new IndexedDBDatabaseCallbacks(this, params.ipc_thread_id, + params.ipc_database_callbacks_id), + params.database_identifier, + webkit_base::FilePathToWebString(indexed_db_path)); } void IndexedDBDispatcherHost::OnIDBFactoryDeleteDatabase( @@ -263,22 +266,23 @@ void IndexedDBDispatcherHost::OnIDBFactoryDeleteDatabase( base::FilePath indexed_db_path = indexed_db_context_->data_path(); DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - Context()->GetIDBFactory() - ->deleteDatabase(params.name, - new IndexedDBCallbacks<WebData>( - this, params.ipc_thread_id, params.ipc_callbacks_id), - params.database_identifier, - webkit_base::FilePathToWebString(indexed_db_path)); + Context()->GetIDBFactory()->deleteDatabase( + params.name, + new IndexedDBCallbacks<WebData>(this, + params.ipc_thread_id, + params.ipc_callbacks_id), + params.database_identifier, + webkit_base::FilePathToWebString(indexed_db_path)); } -void IndexedDBDispatcherHost::FinishTransaction(int64 host_transaction_id, - bool committed) { +void IndexedDBDispatcherHost::FinishTransaction( + int64 host_transaction_id, bool committed) { TransactionIDToURLMap& transaction_url_map = - database_dispatcher_host_->transaction_url_map_; + database_dispatcher_host_->transaction_url_map_; TransactionIDToSizeMap& transaction_size_map = - database_dispatcher_host_->transaction_size_map_; + database_dispatcher_host_->transaction_size_map_; TransactionIDToDatabaseIDMap& transaction_database_map = - database_dispatcher_host_->transaction_database_map_; + database_dispatcher_host_->transaction_database_map_; if (committed) Context()->TransactionComplete(transaction_url_map[host_transaction_id]); // It's unclear if std::map::erase(key) has defined behavior if the @@ -301,8 +305,7 @@ void IndexedDBDispatcherHost::FinishTransaction(int64 host_transaction_id, template <typename ObjectType> ObjectType* IndexedDBDispatcherHost::GetOrTerminateProcess( - IDMap<ObjectType, IDMapOwnPointer>* map, - int32 ipc_return_object_id) { + IDMap<ObjectType, IDMapOwnPointer>* map, int32 ipc_return_object_id) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); ObjectType* return_object = map->Lookup(ipc_return_object_id); if (!return_object) { @@ -316,12 +319,12 @@ ObjectType* IndexedDBDispatcherHost::GetOrTerminateProcess( template <typename ObjectType> void IndexedDBDispatcherHost::DestroyObject( - IDMap<ObjectType, IDMapOwnPointer>* map, - int32 ipc_object_id) { + IDMap<ObjectType, IDMapOwnPointer>* map, int32 ipc_object_id) { GetOrTerminateProcess(map, ipc_object_id); map->Remove(ipc_object_id); } + ////////////////////////////////////////////////////////////////////// // IndexedDBDispatcherHost::DatabaseDispatcherHost // @@ -350,16 +353,14 @@ void IndexedDBDispatcherHost::DatabaseDispatcherHost::CloseAll() { ++iter; WebIDBDatabase* database = map_.Lookup(ipc_database_id); if (database) { - database->abort( - transaction_id, - WebIDBDatabaseError(WebKit::WebIDBDatabaseExceptionUnknownError)); + database->abort(transaction_id, WebIDBDatabaseError( + WebKit::WebIDBDatabaseExceptionUnknownError)); } } DCHECK(transaction_database_map_.empty()); for (WebIDBObjectIDToURLMap::iterator iter = database_url_map_.begin(); - iter != database_url_map_.end(); - iter++) { + iter != database_url_map_.end(); iter++) { WebIDBDatabase* database = map_.Lookup(iter->first); if (database) { database->close(); @@ -369,33 +370,37 @@ void IndexedDBDispatcherHost::DatabaseDispatcherHost::CloseAll() { } bool IndexedDBDispatcherHost::DatabaseDispatcherHost::OnMessageReceived( - const IPC::Message& message, - bool* msg_is_ok) { + const IPC::Message& message, bool* msg_is_ok) { bool handled = true; - IPC_BEGIN_MESSAGE_MAP_EX( - IndexedDBDispatcherHost::DatabaseDispatcherHost, message, *msg_is_ok) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseCreateObjectStore, - OnCreateObjectStore) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseDeleteObjectStore, - OnDeleteObjectStore) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseCreateTransaction, - OnCreateTransaction) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseClose, OnClose) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseDestroyed, OnDestroyed) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseGet, OnGet) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabasePut, OnPut) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseSetIndexKeys, OnSetIndexKeys) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseSetIndexesReady, - OnSetIndexesReady) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseOpenCursor, OnOpenCursor) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseCount, OnCount) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseDeleteRange, OnDeleteRange) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseClear, OnClear) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseCreateIndex, OnCreateIndex) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseDeleteIndex, OnDeleteIndex) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseAbort, OnAbort) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseCommit, OnCommit) - IPC_MESSAGE_UNHANDLED(handled = false) + IPC_BEGIN_MESSAGE_MAP_EX(IndexedDBDispatcherHost::DatabaseDispatcherHost, + message, *msg_is_ok) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseCreateObjectStore, + OnCreateObjectStore) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseDeleteObjectStore, + OnDeleteObjectStore) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseCreateTransaction, + OnCreateTransaction) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseClose, OnClose) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseDestroyed, OnDestroyed) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseGet, OnGet) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabasePut, OnPut) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseSetIndexKeys, + OnSetIndexKeys) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseSetIndexesReady, + OnSetIndexesReady) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseOpenCursor, OnOpenCursor) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseCount, OnCount) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseDeleteRange, OnDeleteRange) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseClear, OnClear) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseCreateIndex, + OnCreateIndex) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseDeleteIndex, + OnDeleteIndex) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseAbort, + OnAbort) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_DatabaseCommit, + OnCommit) + IPC_MESSAGE_UNHANDLED(handled = false) IPC_END_MESSAGE_MAP() return handled; } @@ -408,22 +413,20 @@ void IndexedDBDispatcherHost::DatabaseDispatcherHost::Send( void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnCreateObjectStore( const IndexedDBHostMsg_DatabaseCreateObjectStore_Params& params) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBDatabase* database = - parent_->GetOrTerminateProcess(&map_, params.ipc_database_id); + WebIDBDatabase* database = parent_->GetOrTerminateProcess( + &map_, params.ipc_database_id); if (!database) return; int64 host_transaction_id = parent_->HostTransactionId(params.transaction_id); - database->createObjectStore(host_transaction_id, - params.object_store_id, - params.name, - params.key_path, - params.auto_increment); + database->createObjectStore( + host_transaction_id, + params.object_store_id, + params.name, params.key_path, params.auto_increment); if (parent_->Context()->IsOverQuota( - database_url_map_[params.ipc_database_id])) { - database->abort( - host_transaction_id, - WebIDBDatabaseError(WebKit::WebIDBDatabaseExceptionQuotaError)); + database_url_map_[params.ipc_database_id])) { + database->abort(host_transaction_id, WebIDBDatabaseError( + WebKit::WebIDBDatabaseExceptionQuotaError)); } } @@ -432,8 +435,8 @@ void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnDeleteObjectStore( int64 transaction_id, int64 object_store_id) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBDatabase* database = - parent_->GetOrTerminateProcess(&map_, ipc_database_id); + WebIDBDatabase* database = parent_->GetOrTerminateProcess( + &map_, ipc_database_id); if (!database) return; @@ -443,23 +446,22 @@ void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnDeleteObjectStore( void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnCreateTransaction( const IndexedDBHostMsg_DatabaseCreateTransaction_Params& params) { - WebIDBDatabase* database = - parent_->GetOrTerminateProcess(&map_, params.ipc_database_id); + WebIDBDatabase* database = parent_->GetOrTerminateProcess( + &map_, params.ipc_database_id); if (!database) - return; + return; WebVector<long long> object_stores(params.object_store_ids.size()); for (size_t i = 0; i < params.object_store_ids.size(); ++i) - object_stores[i] = params.object_store_ids[i]; + object_stores[i] = params.object_store_ids[i]; int64 host_transaction_id = parent_->HostTransactionId(params.transaction_id); database->createTransaction( host_transaction_id, - new IndexedDBDatabaseCallbacks( - parent_, params.ipc_thread_id, params.ipc_database_callbacks_id), - object_stores, - params.mode); + new IndexedDBDatabaseCallbacks(parent_, params.ipc_thread_id, + params.ipc_database_callbacks_id), + object_stores, params.mode); transaction_database_map_[host_transaction_id] = params.ipc_database_id; parent_->RegisterTransactionId(host_transaction_id, database_url_map_[params.ipc_database_id]); @@ -467,8 +469,8 @@ void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnCreateTransaction( void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnClose( int32 ipc_database_id) { - WebIDBDatabase* database = - parent_->GetOrTerminateProcess(&map_, ipc_database_id); + WebIDBDatabase* database = parent_->GetOrTerminateProcess( + &map_, ipc_database_id); if (!database) return; database->close(); @@ -477,8 +479,8 @@ void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnClose( void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnDestroyed( int32 ipc_object_id) { WebIDBDatabase* database = map_.Lookup(ipc_object_id); - parent_->Context() - ->ConnectionClosed(database_url_map_[ipc_object_id], database); + parent_->Context()->ConnectionClosed(database_url_map_[ipc_object_id], + database); database_url_map_.erase(ipc_object_id); parent_->DestroyObject(&map_, ipc_object_id); } @@ -486,42 +488,41 @@ void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnDestroyed( void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnGet( const IndexedDBHostMsg_DatabaseGet_Params& params) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBDatabase* database = - parent_->GetOrTerminateProcess(&map_, params.ipc_database_id); + WebIDBDatabase* database = parent_->GetOrTerminateProcess( + &map_, params.ipc_database_id); if (!database) return; - scoped_ptr<WebIDBCallbacks> callbacks(new IndexedDBCallbacks<WebData>( - parent_, params.ipc_thread_id, params.ipc_callbacks_id)); + scoped_ptr<WebIDBCallbacks> callbacks( + new IndexedDBCallbacks<WebData>( + parent_, params.ipc_thread_id, + params.ipc_callbacks_id)); database->get(parent_->HostTransactionId(params.transaction_id), params.object_store_id, params.index_id, - params.key_range, - params.key_only, - callbacks.release()); + params.key_range, params.key_only, callbacks.release()); } void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnPut( const IndexedDBHostMsg_DatabasePut_Params& params) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBDatabase* database = - parent_->GetOrTerminateProcess(&map_, params.ipc_database_id); + WebIDBDatabase* database = parent_->GetOrTerminateProcess( + &map_, params.ipc_database_id); if (!database) return; - scoped_ptr<WebIDBCallbacks> callbacks(new IndexedDBCallbacks<WebIDBKey>( - parent_, params.ipc_thread_id, params.ipc_callbacks_id)); + scoped_ptr<WebIDBCallbacks> callbacks( + new IndexedDBCallbacks<WebIDBKey>(parent_, params.ipc_thread_id, + params.ipc_callbacks_id)); // Be careful with empty vectors. WebData value; if (params.value.size()) - value.assign(¶ms.value.front(), params.value.size()); + value.assign(¶ms.value.front(), params.value.size()); int64 host_transaction_id = parent_->HostTransactionId(params.transaction_id); database->put(host_transaction_id, params.object_store_id, - value, - params.key, - params.put_mode, - callbacks.release(), + value, params.key, + params.put_mode, callbacks.release(), params.index_ids, params.index_keys); TransactionIDToSizeMap* map = @@ -534,25 +535,22 @@ void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnPut( void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnSetIndexKeys( const IndexedDBHostMsg_DatabaseSetIndexKeys_Params& params) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBDatabase* database = - parent_->GetOrTerminateProcess(&map_, params.ipc_database_id); + WebIDBDatabase* database = parent_->GetOrTerminateProcess( + &map_, params.ipc_database_id); if (!database) return; int64 host_transaction_id = parent_->HostTransactionId(params.transaction_id); if (params.index_ids.size() != params.index_keys.size()) { - database->abort( - host_transaction_id, - WebIDBDatabaseError( - WebKit::WebIDBDatabaseExceptionUnknownError, - "Malformed IPC message: index_ids.size() != index_keys.size()")); + database->abort(host_transaction_id, WebIDBDatabaseError( + WebKit::WebIDBDatabaseExceptionUnknownError, + "Malformed IPC message: index_ids.size() != index_keys.size()")); return; } database->setIndexKeys(host_transaction_id, params.object_store_id, - params.primary_key, - params.index_ids, + params.primary_key, params.index_ids, params.index_keys); } @@ -562,8 +560,8 @@ void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnSetIndexesReady( int64 object_store_id, const std::vector<int64>& index_ids) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBDatabase* database = - parent_->GetOrTerminateProcess(&map_, ipc_database_id); + WebIDBDatabase* database = parent_->GetOrTerminateProcess( + &map_, ipc_database_id); if (!database) return; @@ -575,54 +573,54 @@ void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnSetIndexesReady( void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnOpenCursor( const IndexedDBHostMsg_DatabaseOpenCursor_Params& params) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBDatabase* database = - parent_->GetOrTerminateProcess(&map_, params.ipc_database_id); + WebIDBDatabase* database = parent_->GetOrTerminateProcess( + &map_, params.ipc_database_id); if (!database) return; - scoped_ptr<WebIDBCallbacks> callbacks(new IndexedDBCallbacks<WebIDBCursor>( - parent_, params.ipc_thread_id, params.ipc_callbacks_id, -1)); - database->openCursor(parent_->HostTransactionId(params.transaction_id), - params.object_store_id, - params.index_id, - params.key_range, - params.direction, - params.key_only, - params.task_type, - callbacks.release()); + scoped_ptr<WebIDBCallbacks> callbacks( + new IndexedDBCallbacks<WebIDBCursor>(parent_, params.ipc_thread_id, + params.ipc_callbacks_id, -1)); + database->openCursor( + parent_->HostTransactionId(params.transaction_id), + params.object_store_id, params.index_id, + params.key_range, params.direction, params.key_only, params.task_type, + callbacks.release()); } void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnCount( const IndexedDBHostMsg_DatabaseCount_Params& params) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBDatabase* database = - parent_->GetOrTerminateProcess(&map_, params.ipc_database_id); + WebIDBDatabase* database = parent_->GetOrTerminateProcess( + &map_, params.ipc_database_id); if (!database) return; - scoped_ptr<WebIDBCallbacks> callbacks(new IndexedDBCallbacks<WebData>( - parent_, params.ipc_thread_id, params.ipc_callbacks_id)); - database->count(parent_->HostTransactionId(params.transaction_id), - params.object_store_id, - params.index_id, - params.key_range, - callbacks.release()); + scoped_ptr<WebIDBCallbacks> callbacks( + new IndexedDBCallbacks<WebData>( + parent_, params.ipc_thread_id, + params.ipc_callbacks_id)); + database->count( + parent_->HostTransactionId(params.transaction_id), + params.object_store_id, params.index_id, + params.key_range, callbacks.release()); } void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnDeleteRange( const IndexedDBHostMsg_DatabaseDeleteRange_Params& params) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBDatabase* database = - parent_->GetOrTerminateProcess(&map_, params.ipc_database_id); + WebIDBDatabase* database = parent_->GetOrTerminateProcess( + &map_, params.ipc_database_id); if (!database) return; - scoped_ptr<WebIDBCallbacks> callbacks(new IndexedDBCallbacks<WebData>( - parent_, params.ipc_thread_id, params.ipc_callbacks_id)); + scoped_ptr<WebIDBCallbacks> callbacks( + new IndexedDBCallbacks<WebData>( + parent_, params.ipc_thread_id, + params.ipc_callbacks_id)); database->deleteRange(parent_->HostTransactionId(params.transaction_id), params.object_store_id, - params.key_range, - callbacks.release()); + params.key_range, callbacks.release()); } void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnClear( @@ -632,25 +630,26 @@ void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnClear( int64 transaction_id, int64 object_store_id) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBDatabase* database = - parent_->GetOrTerminateProcess(&map_, ipc_database_id); + WebIDBDatabase* database = parent_->GetOrTerminateProcess( + &map_, ipc_database_id); if (!database) return; - scoped_ptr<WebIDBCallbacks> callbacks(new IndexedDBCallbacks<WebData>( - parent_, ipc_thread_id, ipc_callbacks_id)); + scoped_ptr<WebIDBCallbacks> callbacks( + new IndexedDBCallbacks<WebData>( + parent_, ipc_thread_id, + ipc_callbacks_id)); database->clear(parent_->HostTransactionId(transaction_id), - object_store_id, - callbacks.release()); + object_store_id, callbacks.release()); } void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnAbort( int32 ipc_database_id, int64 transaction_id) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBDatabase* database = - parent_->GetOrTerminateProcess(&map_, ipc_database_id); + WebIDBDatabase* database = parent_->GetOrTerminateProcess( + &map_, ipc_database_id); if (!database) return; @@ -661,19 +660,17 @@ void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnCommit( int32 ipc_database_id, int64 transaction_id) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBDatabase* database = - parent_->GetOrTerminateProcess(&map_, ipc_database_id); + WebIDBDatabase* database = parent_->GetOrTerminateProcess( + &map_, ipc_database_id); if (!database) return; int64 host_transaction_id = parent_->HostTransactionId(transaction_id); int64 transaction_size = transaction_size_map_[host_transaction_id]; - if (transaction_size && - parent_->Context()->WouldBeOverQuota( - transaction_url_map_[host_transaction_id], transaction_size)) { - database->abort( - host_transaction_id, - WebIDBDatabaseError(WebKit::WebIDBDatabaseExceptionQuotaError)); + if (transaction_size && parent_->Context()->WouldBeOverQuota( + transaction_url_map_[host_transaction_id], transaction_size)) { + database->abort(host_transaction_id, WebIDBDatabaseError( + WebKit::WebIDBDatabaseExceptionQuotaError)); return; } @@ -683,24 +680,24 @@ void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnCommit( void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnCreateIndex( const IndexedDBHostMsg_DatabaseCreateIndex_Params& params) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBDatabase* database = - parent_->GetOrTerminateProcess(&map_, params.ipc_database_id); + WebIDBDatabase* database = parent_->GetOrTerminateProcess( + &map_, params.ipc_database_id); if (!database) return; int64 host_transaction_id = parent_->HostTransactionId(params.transaction_id); - database->createIndex(host_transaction_id, - params.object_store_id, - params.index_id, - params.name, - params.key_path, - params.unique, - params.multi_entry); + database->createIndex( + host_transaction_id, + params.object_store_id, + params.index_id, + params.name, + params.key_path, + params.unique, + params.multi_entry); if (parent_->Context()->IsOverQuota( - database_url_map_[params.ipc_database_id])) { - database->abort( - host_transaction_id, - WebIDBDatabaseError(WebKit::WebIDBDatabaseExceptionQuotaError)); + database_url_map_[params.ipc_database_id])) { + database->abort(host_transaction_id, WebIDBDatabaseError( + WebKit::WebIDBDatabaseExceptionQuotaError)); } } @@ -710,13 +707,13 @@ void IndexedDBDispatcherHost::DatabaseDispatcherHost::OnDeleteIndex( int64 object_store_id, int64 index_id) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBDatabase* database = - parent_->GetOrTerminateProcess(&map_, ipc_database_id); + WebIDBDatabase* database = parent_->GetOrTerminateProcess( + &map_, ipc_database_id); if (!database) return; - database->deleteIndex( - parent_->HostTransactionId(transaction_id), object_store_id, index_id); + database->deleteIndex(parent_->HostTransactionId(transaction_id), + object_store_id, index_id); } ////////////////////////////////////////////////////////////////////// @@ -729,45 +726,48 @@ IndexedDBDispatcherHost::CursorDispatcherHost::CursorDispatcherHost( map_.set_check_on_null_data(true); } -IndexedDBDispatcherHost::CursorDispatcherHost::~CursorDispatcherHost() {} +IndexedDBDispatcherHost::CursorDispatcherHost::~CursorDispatcherHost() { +} bool IndexedDBDispatcherHost::CursorDispatcherHost::OnMessageReceived( - const IPC::Message& message, - bool* msg_is_ok) { + const IPC::Message& message, bool* msg_is_ok) { bool handled = true; - IPC_BEGIN_MESSAGE_MAP_EX( - IndexedDBDispatcherHost::CursorDispatcherHost, message, *msg_is_ok) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_CursorAdvance, OnAdvance) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_CursorContinue, OnContinue) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_CursorPrefetch, OnPrefetch) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_CursorPrefetchReset, OnPrefetchReset) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_CursorDelete, OnDelete) - IPC_MESSAGE_HANDLER(IndexedDBHostMsg_CursorDestroyed, OnDestroyed) - IPC_MESSAGE_UNHANDLED(handled = false) + IPC_BEGIN_MESSAGE_MAP_EX(IndexedDBDispatcherHost::CursorDispatcherHost, + message, *msg_is_ok) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_CursorAdvance, OnAdvance) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_CursorContinue, OnContinue) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_CursorPrefetch, OnPrefetch) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_CursorPrefetchReset, OnPrefetchReset) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_CursorDelete, OnDelete) + IPC_MESSAGE_HANDLER(IndexedDBHostMsg_CursorDestroyed, OnDestroyed) + IPC_MESSAGE_UNHANDLED(handled = false) IPC_END_MESSAGE_MAP() return handled; } + void IndexedDBDispatcherHost::CursorDispatcherHost::Send( IPC::Message* message) { parent_->Send(message); } + void IndexedDBDispatcherHost::CursorDispatcherHost::OnAdvance( int32 ipc_cursor_id, int32 ipc_thread_id, int32 ipc_callbacks_id, unsigned long count) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBCursor* idb_cursor = - parent_->GetOrTerminateProcess(&map_, ipc_cursor_id); + WebIDBCursor* idb_cursor = parent_->GetOrTerminateProcess( + &map_, ipc_cursor_id); if (!idb_cursor) return; - idb_cursor->advance( - count, - new IndexedDBCallbacks<WebIDBCursor>( - parent_, ipc_thread_id, ipc_callbacks_id, ipc_cursor_id)); + idb_cursor->advance(count, + new IndexedDBCallbacks<WebIDBCursor>(parent_, + ipc_thread_id, + ipc_callbacks_id, + ipc_cursor_id)); } void IndexedDBDispatcherHost::CursorDispatcherHost::OnContinue( @@ -776,15 +776,15 @@ void IndexedDBDispatcherHost::CursorDispatcherHost::OnContinue( int32 ipc_callbacks_id, const IndexedDBKey& key) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBCursor* idb_cursor = - parent_->GetOrTerminateProcess(&map_, ipc_cursor_id); + WebIDBCursor* idb_cursor = parent_->GetOrTerminateProcess(&map_, + ipc_cursor_id); if (!idb_cursor) return; idb_cursor->continueFunction( - key, - new IndexedDBCallbacks<WebIDBCursor>( - parent_, ipc_thread_id, ipc_callbacks_id, ipc_cursor_id)); + key, new IndexedDBCallbacks<WebIDBCursor>(parent_, ipc_thread_id, + ipc_callbacks_id, + ipc_cursor_id)); } void IndexedDBDispatcherHost::CursorDispatcherHost::OnPrefetch( @@ -793,24 +793,22 @@ void IndexedDBDispatcherHost::CursorDispatcherHost::OnPrefetch( int32 ipc_callbacks_id, int n) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBCursor* idb_cursor = - parent_->GetOrTerminateProcess(&map_, ipc_cursor_id); + WebIDBCursor* idb_cursor = parent_->GetOrTerminateProcess(&map_, + ipc_cursor_id); if (!idb_cursor) return; idb_cursor->prefetchContinue( - n, - new IndexedDBCallbacks<WebIDBCursor>( - parent_, ipc_thread_id, ipc_callbacks_id, ipc_cursor_id)); + n, new IndexedDBCallbacks<WebIDBCursor>(parent_, ipc_thread_id, + ipc_callbacks_id, + ipc_cursor_id)); } void IndexedDBDispatcherHost::CursorDispatcherHost::OnPrefetchReset( - int32 ipc_cursor_id, - int used_prefetches, - int unused_prefetches) { + int32 ipc_cursor_id, int used_prefetches, int unused_prefetches) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBCursor* idb_cursor = - parent_->GetOrTerminateProcess(&map_, ipc_cursor_id); + WebIDBCursor* idb_cursor = parent_->GetOrTerminateProcess(&map_, + ipc_cursor_id); if (!idb_cursor) return; @@ -822,13 +820,14 @@ void IndexedDBDispatcherHost::CursorDispatcherHost::OnDelete( int32 ipc_thread_id, int32 ipc_callbacks_id) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - WebIDBCursor* idb_cursor = - parent_->GetOrTerminateProcess(&map_, ipc_cursor_id); + WebIDBCursor* idb_cursor = parent_->GetOrTerminateProcess(&map_, + ipc_cursor_id); if (!idb_cursor) return; - idb_cursor->deleteFunction(new IndexedDBCallbacks<WebData>( - parent_, ipc_thread_id, ipc_callbacks_id)); + idb_cursor->deleteFunction( + new IndexedDBCallbacks<WebData>(parent_, ipc_thread_id, + ipc_callbacks_id)); } void IndexedDBDispatcherHost::CursorDispatcherHost::OnDestroyed( diff --git a/content/browser/in_process_webkit/indexed_db_dispatcher_host.h b/content/browser/in_process_webkit/indexed_db_dispatcher_host.h index 9908e31..48a75d7 100644 --- a/content/browser/in_process_webkit/indexed_db_dispatcher_host.h +++ b/content/browser/in_process_webkit/indexed_db_dispatcher_host.h @@ -30,6 +30,8 @@ struct IndexedDBHostMsg_FactoryOpen_Params; namespace WebKit { class WebIDBCursor; class WebIDBDatabase; +class WebIDBIndex; +class WebIDBObjectStore; struct WebIDBMetadata; } @@ -91,8 +93,8 @@ class IndexedDBDispatcherHost : public BrowserMessageFilter { // Helper templates. template <class ReturnType> - ReturnType* GetOrTerminateProcess(IDMap<ReturnType, IDMapOwnPointer>* map, - int32 ipc_return_object_id); + ReturnType* GetOrTerminateProcess( + IDMap<ReturnType, IDMapOwnPointer>* map, int32 ipc_return_object_id); template <typename ObjectType> void DestroyObject(IDMap<ObjectType, IDMapOwnPointer>* map, @@ -111,7 +113,7 @@ class IndexedDBDispatcherHost : public BrowserMessageFilter { ~DatabaseDispatcherHost(); void CloseAll(); - bool OnMessageReceived(const IPC::Message& message, bool* msg_is_ok); + bool OnMessageReceived(const IPC::Message& message, bool *msg_is_ok); void Send(IPC::Message* message); void OnCreateObjectStore( @@ -121,8 +123,7 @@ class IndexedDBDispatcherHost : public BrowserMessageFilter { int64 object_store_id); void OnCreateTransaction( const IndexedDBHostMsg_DatabaseCreateTransaction_Params&); - void OnOpen(int32 ipc_database_id, - int32 ipc_thread_id, + void OnOpen(int32 ipc_database_id, int32 ipc_thread_id, int32 ipc_callbacks_id); void OnClose(int32 ipc_database_id); void OnDestroyed(int32 ipc_database_id); @@ -131,11 +132,13 @@ class IndexedDBDispatcherHost : public BrowserMessageFilter { void OnPut(const IndexedDBHostMsg_DatabasePut_Params& params); void OnSetIndexKeys( const IndexedDBHostMsg_DatabaseSetIndexKeys_Params& params); - void OnSetIndexesReady(int32 ipc_database_id, - int64 transaction_id, - int64 object_store_id, - const std::vector<int64>& ids); - void OnOpenCursor(const IndexedDBHostMsg_DatabaseOpenCursor_Params& params); + void OnSetIndexesReady( + int32 ipc_database_id, + int64 transaction_id, + int64 object_store_id, + const std::vector<int64>& ids); + void OnOpenCursor( + const IndexedDBHostMsg_DatabaseOpenCursor_Params& params); void OnCount(const IndexedDBHostMsg_DatabaseCount_Params& params); void OnDeleteRange( const IndexedDBHostMsg_DatabaseDeleteRange_Params& params); @@ -166,7 +169,7 @@ class IndexedDBDispatcherHost : public BrowserMessageFilter { explicit CursorDispatcherHost(IndexedDBDispatcherHost* parent); ~CursorDispatcherHost(); - bool OnMessageReceived(const IPC::Message& message, bool* msg_is_ok); + bool OnMessageReceived(const IPC::Message& message, bool *msg_is_ok); void Send(IPC::Message* message); void OnAdvance(int32 ipc_object_store_id, @@ -181,8 +184,7 @@ class IndexedDBDispatcherHost : public BrowserMessageFilter { int32 ipc_thread_id, int32 ipc_callbacks_id, int n); - void OnPrefetchReset(int32 ipc_cursor_id, - int used_prefetches, + void OnPrefetchReset(int32 ipc_cursor_id, int used_prefetches, int unused_prefetches); void OnDelete(int32 ipc_object_store_id, int32 ipc_thread_id, diff --git a/content/browser/indexed_db/DEPS b/content/browser/indexed_db/DEPS deleted file mode 100644 index 743a2f3..0000000 --- a/content/browser/indexed_db/DEPS +++ /dev/null @@ -1,3 +0,0 @@ -include_rules = [ - "+third_party/leveldatabase", -] diff --git a/content/browser/indexed_db/indexed_db.h b/content/browser/indexed_db/indexed_db.h deleted file mode 100644 index 3714d40..0000000 --- a/content/browser/indexed_db/indexed_db.h +++ /dev/null @@ -1,34 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_H_ -#define CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_H_ - -namespace content { - -namespace indexed_db { - -enum TransactionMode { - TRANSACTION_READ_ONLY = 0, - TRANSACTION_READ_WRITE = 1, - TRANSACTION_VERSION_CHANGE = 2 -}; - -enum CursorDirection { - CURSOR_NEXT = 0, - CURSOR_NEXT_NO_DUPLICATE = 1, - CURSOR_PREV = 2, - CURSOR_PREV_NO_DUPLICATE = 3, -}; - -enum CursorType { - CURSOR_KEY_AND_VALUE = 0, - CURSOR_KEY_ONLY -}; - -} // namespace indexed_db - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_H_ diff --git a/content/browser/indexed_db/indexed_db_backing_store.cc b/content/browser/indexed_db/indexed_db_backing_store.cc deleted file mode 100644 index 1596aef..0000000 --- a/content/browser/indexed_db/indexed_db_backing_store.cc +++ /dev/null @@ -1,2543 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/indexed_db_backing_store.h" - -#include <string> - -#include "base/file_util.h" -#include "base/logging.h" -#include "base/metrics/histogram.h" -#include "base/utf_string_conversions.h" -#include "content/browser/indexed_db/indexed_db_leveldb_coding.h" -#include "content/browser/indexed_db/indexed_db_metadata.h" -#include "content/browser/indexed_db/indexed_db_tracing.h" -#include "content/browser/indexed_db/leveldb/leveldb_comparator.h" -#include "content/browser/indexed_db/leveldb/leveldb_database.h" -#include "content/browser/indexed_db/leveldb/leveldb_iterator.h" -#include "content/browser/indexed_db/leveldb/leveldb_slice.h" -#include "content/browser/indexed_db/leveldb/leveldb_transaction.h" -#include "content/common/indexed_db/indexed_db_key.h" -#include "content/common/indexed_db/indexed_db_key_path.h" -#include "content/common/indexed_db/indexed_db_key_range.h" -#include "third_party/WebKit/public/platform/WebIDBKey.h" -#include "third_party/WebKit/public/platform/WebIDBKeyPath.h" - -// TODO(jsbell): Make blink push the version during the open() call. -static const uint32 kWireVersion = 2; - -namespace content { - -static const int64 kKeyGeneratorInitialNumber = - 1; // From the IndexedDB specification. - -enum IndexedDBBackingStoreErrorSource { - // 0 - 2 are no longer used. - FIND_KEY_IN_INDEX = 3, - GET_IDBDATABASE_METADATA, - GET_INDEXES, - GET_KEY_GENERATOR_CURRENT_NUMBER, - GET_OBJECT_STORES, - GET_RECORD, - KEY_EXISTS_IN_OBJECT_STORE, - LOAD_CURRENT_ROW, - SET_UP_METADATA, - GET_PRIMARY_KEY_VIA_INDEX, - KEY_EXISTS_IN_INDEX, - VERSION_EXISTS, - DELETE_OBJECT_STORE, - SET_MAX_OBJECT_STORE_ID, - SET_MAX_INDEX_ID, - GET_NEW_DATABASE_ID, - GET_NEW_VERSION_NUMBER, - CREATE_IDBDATABASE_METADATA, - DELETE_DATABASE, - TRANSACTION_COMMIT_METHOD, // TRANSACTION_COMMIT is a WinNT.h macro - INTERNAL_ERROR_MAX, -}; - -static void RecordInternalError(const char* type, - IndexedDBBackingStoreErrorSource location) { - string16 name = ASCIIToUTF16("WebCore.IndexedDB.BackingStore.") + - UTF8ToUTF16(type) + ASCIIToUTF16("Error"); - base::Histogram::FactoryGet(UTF16ToUTF8(name), - 1, - INTERNAL_ERROR_MAX, - INTERNAL_ERROR_MAX + 1, - base::HistogramBase::kUmaTargetedHistogramFlag) - ->Add(location); -} - -// Use to signal conditions that usually indicate developer error, but -// could be caused by data corruption. A macro is used instead of an -// inline function so that the assert and log report the line number. -#define REPORT_ERROR(type, location) \ - do { \ - LOG(ERROR) << "IndexedDB " type " Error: " #location; \ - NOTREACHED(); \ - RecordInternalError(type, location); \ - } while (0) - -#define INTERNAL_READ_ERROR(location) REPORT_ERROR("Read", location) -#define INTERNAL_CONSISTENCY_ERROR(location) \ - REPORT_ERROR("Consistency", location) -#define INTERNAL_WRITE_ERROR(location) REPORT_ERROR("Write", location) - -static void PutBool(LevelDBTransaction* transaction, - const LevelDBSlice& key, - bool value) { - transaction->Put(key, EncodeBool(value)); -} - -template <typename DBOrTransaction> -static bool GetInt(DBOrTransaction* db, - const LevelDBSlice& key, - int64& found_int, - bool& found) { - std::vector<char> result; - bool ok = db->Get(key, result, found); - if (!ok) - return false; - if (!found) - return true; - - found_int = DecodeInt(result.begin(), result.end()); - return true; -} - -static void PutInt(LevelDBTransaction* transaction, - const LevelDBSlice& key, - int64 value) { - DCHECK_GE(value, 0); - transaction->Put(key, EncodeInt(value)); -} - -template <typename DBOrTransaction> -WARN_UNUSED_RESULT static bool GetVarInt(DBOrTransaction* db, - const LevelDBSlice& key, - int64& found_int, - bool& found) { - std::vector<char> result; - bool ok = db->Get(key, result, found); - if (!ok) - return false; - if (!found) - return true; - if (!result.size()) - return false; - - found = DecodeVarInt(&*result.begin(), &*result.rbegin() + 1, found_int) == - &*result.rbegin() + 1; - return true; -} - -static void PutVarInt(LevelDBTransaction* transaction, - const LevelDBSlice& key, - int64 value) { - transaction->Put(key, EncodeVarInt(value)); -} - -template <typename DBOrTransaction> -WARN_UNUSED_RESULT static bool GetString(DBOrTransaction* db, - const LevelDBSlice& key, - string16& found_string, - bool& found) { - std::vector<char> result; - found = false; - bool ok = db->Get(key, result, found); - if (!ok) - return false; - if (!found) - return true; - if (!result.size()) { - found_string.clear(); - return true; - } - - found_string = DecodeString(&*result.begin(), &*result.rbegin() + 1); - return true; -} - -static void PutString(LevelDBTransaction* transaction, - const LevelDBSlice& key, - const string16& value) { - transaction->Put(key, EncodeString(value)); -} - -static void PutIDBKeyPath(LevelDBTransaction* transaction, - const LevelDBSlice& key, - const IndexedDBKeyPath& value) { - transaction->Put(key, EncodeIDBKeyPath(value)); -} - -static int CompareKeys(const LevelDBSlice& a, const LevelDBSlice& b) { - return Compare(a, b); -} - -static int CompareIndexKeys(const LevelDBSlice& a, const LevelDBSlice& b) { - return Compare(a, b, true); -} - -class Comparator : public LevelDBComparator { - public: - virtual int Compare(const LevelDBSlice& a, const LevelDBSlice& b) const - OVERRIDE { - return content::Compare(a, b); - } - virtual const char* Name() const OVERRIDE { return "idb_cmp1"; } -}; - -// 0 - Initial version. -// 1 - Adds UserIntVersion to DatabaseMetaData. -// 2 - Adds DataVersion to to global metadata. -static const int64 kLatestKnownSchemaVersion = 2; -WARN_UNUSED_RESULT static bool IsSchemaKnown(LevelDBDatabase* db, bool* known) { - int64 db_schema_version = 0; - bool found = false; - bool ok = GetInt( - db, LevelDBSlice(SchemaVersionKey::Encode()), db_schema_version, found); - if (!ok) - return false; - if (!found) { - *known = true; - return true; - } - if (db_schema_version > kLatestKnownSchemaVersion) { - *known = false; - return true; - } - - const uint32 latest_known_data_version = kWireVersion; - int64 db_data_version = 0; - ok = GetInt( - db, LevelDBSlice(DataVersionKey::Encode()), db_data_version, found); - if (!ok) - return false; - if (!found) { - *known = true; - return true; - } - - if (db_data_version > latest_known_data_version) { - *known = false; - return true; - } - - *known = true; - return true; -} - -WARN_UNUSED_RESULT static bool SetUpMetadata(LevelDBDatabase* db, - const string16& origin) { - const uint32 latest_known_data_version = kWireVersion; - const std::vector<char> schema_version_key = SchemaVersionKey::Encode(); - const std::vector<char> data_version_key = DataVersionKey::Encode(); - - scoped_refptr<LevelDBTransaction> transaction = - LevelDBTransaction::Create(db); - - int64 db_schema_version = 0; - int64 db_data_version = 0; - bool found = false; - bool ok = GetInt(transaction.get(), - LevelDBSlice(schema_version_key), - db_schema_version, - found); - if (!ok) { - INTERNAL_READ_ERROR(SET_UP_METADATA); - return false; - } - if (!found) { - // Initialize new backing store. - db_schema_version = kLatestKnownSchemaVersion; - PutInt( - transaction.get(), LevelDBSlice(schema_version_key), db_schema_version); - db_data_version = latest_known_data_version; - PutInt(transaction.get(), LevelDBSlice(data_version_key), db_data_version); - } else { - // Upgrade old backing store. - DCHECK_LE(db_schema_version, kLatestKnownSchemaVersion); - if (db_schema_version < 1) { - db_schema_version = 1; - PutInt(transaction.get(), - LevelDBSlice(schema_version_key), - db_schema_version); - const std::vector<char> start_key = - DatabaseNameKey::EncodeMinKeyForOrigin(origin); - const std::vector<char> stop_key = - DatabaseNameKey::EncodeStopKeyForOrigin(origin); - scoped_ptr<LevelDBIterator> it = db->CreateIterator(); - for (it->Seek(LevelDBSlice(start_key)); - it->IsValid() && CompareKeys(it->Key(), LevelDBSlice(stop_key)) < 0; - it->Next()) { - int64 database_id = 0; - found = false; - bool ok = GetInt(transaction.get(), it->Key(), database_id, found); - if (!ok) { - INTERNAL_READ_ERROR(SET_UP_METADATA); - return false; - } - if (!found) { - INTERNAL_CONSISTENCY_ERROR(SET_UP_METADATA); - return false; - } - std::vector<char> int_version_key = DatabaseMetaDataKey::Encode( - database_id, DatabaseMetaDataKey::USER_INT_VERSION); - PutVarInt(transaction.get(), - LevelDBSlice(int_version_key), - IndexedDBDatabaseMetadata::DEFAULT_INT_VERSION); - } - } - if (db_schema_version < 2) { - db_schema_version = 2; - PutInt(transaction.get(), - LevelDBSlice(schema_version_key), - db_schema_version); - db_data_version = kWireVersion; - PutInt( - transaction.get(), LevelDBSlice(data_version_key), db_data_version); - } - } - - // All new values will be written using this serialization version. - found = false; - ok = GetInt(transaction.get(), - LevelDBSlice(data_version_key), - db_data_version, - found); - if (!ok) { - INTERNAL_READ_ERROR(SET_UP_METADATA); - return false; - } - if (!found) { - INTERNAL_CONSISTENCY_ERROR(SET_UP_METADATA); - return false; - } - if (db_data_version < latest_known_data_version) { - db_data_version = latest_known_data_version; - PutInt(transaction.get(), LevelDBSlice(data_version_key), db_data_version); - } - - DCHECK_EQ(db_schema_version, kLatestKnownSchemaVersion); - DCHECK_EQ(db_data_version, latest_known_data_version); - - if (!transaction->Commit()) { - INTERNAL_WRITE_ERROR(SET_UP_METADATA); - return false; - } - return true; -} - -template <typename DBOrTransaction> -WARN_UNUSED_RESULT static bool GetMaxObjectStoreId(DBOrTransaction* db, - int64 database_id, - int64& max_object_store_id) { - const std::vector<char> max_object_store_id_key = DatabaseMetaDataKey::Encode( - database_id, DatabaseMetaDataKey::MAX_OBJECT_STORE_ID); - bool ok = - GetMaxObjectStoreId(db, max_object_store_id_key, max_object_store_id); - return ok; -} - -template <typename DBOrTransaction> -WARN_UNUSED_RESULT static bool GetMaxObjectStoreId( - DBOrTransaction* db, - const std::vector<char>& max_object_store_id_key, - int64& max_object_store_id) { - max_object_store_id = -1; - bool found = false; - bool ok = GetInt( - db, LevelDBSlice(max_object_store_id_key), max_object_store_id, found); - if (!ok) - return false; - if (!found) - max_object_store_id = 0; - - DCHECK_GE(max_object_store_id, 0); - return true; -} - -class DefaultLevelDBFactory : public LevelDBFactory { - public: - virtual scoped_ptr<LevelDBDatabase> OpenLevelDB( - const base::FilePath& file_name, - const LevelDBComparator* comparator) OVERRIDE { - return LevelDBDatabase::Open(file_name, comparator); - } - virtual bool DestroyLevelDB(const base::FilePath& file_name) OVERRIDE { - return LevelDBDatabase::Destroy(file_name); - } -}; - -IndexedDBBackingStore::IndexedDBBackingStore( - const string16& identifier, - scoped_ptr<LevelDBDatabase> db, - scoped_ptr<LevelDBComparator> comparator) - : identifier_(identifier), - db_(db.Pass()), - comparator_(comparator.Pass()), - weak_factory_(this) {} - -IndexedDBBackingStore::~IndexedDBBackingStore() { - // db_'s destructor uses comparator_. The order of destruction is important. - db_.reset(); - comparator_.reset(); -} - -IndexedDBBackingStore::RecordIdentifier::RecordIdentifier( - const std::vector<char>& primary_key, - int64 version) - : primary_key_(primary_key), version_(version) { - DCHECK(!primary_key.empty()); -} -IndexedDBBackingStore::RecordIdentifier::RecordIdentifier() - : primary_key_(), version_(-1) {} -IndexedDBBackingStore::RecordIdentifier::~RecordIdentifier() {} - -IndexedDBBackingStore::Cursor::CursorOptions::CursorOptions() {} -IndexedDBBackingStore::Cursor::CursorOptions::~CursorOptions() {} - -enum IndexedDBLevelDBBackingStoreOpenResult { - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MEMORY_SUCCESS, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_SUCCESS, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_FAILED_DIRECTORY, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_FAILED_UNKNOWN_SCHEMA, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_CLEANUP_DESTROY_FAILED, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_CLEANUP_REOPEN_FAILED, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_CLEANUP_REOPEN_SUCCESS, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_FAILED_IO_ERROR_CHECKING_SCHEMA, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_FAILED_UNKNOWN_ERR, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MEMORY_FAILED, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_ATTEMPT_NON_ASCII, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX, -}; - -scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::Open( - const string16& database_identifier, - const string16& path_base_arg, - const string16& file_identifier) { - DefaultLevelDBFactory leveldb_factory; - return IndexedDBBackingStore::Open( - database_identifier, path_base_arg, file_identifier, &leveldb_factory); -} - -scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::Open( - const string16& database_identifier, - const string16& path_base_arg, - const string16& file_identifier, - LevelDBFactory* leveldb_factory) { - IDB_TRACE("IndexedDBBackingStore::open"); - DCHECK(!path_base_arg.empty()); - string16 path_base = path_base_arg; - - scoped_ptr<LevelDBComparator> comparator(new Comparator()); - scoped_ptr<LevelDBDatabase> db; - - if (!IsStringASCII(path_base)) { - base::Histogram::FactoryGet("WebCore.IndexedDB.BackingStore.OpenStatus", - 1, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX + 1, - base::HistogramBase::kUmaTargetedHistogramFlag) - ->Add(INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_ATTEMPT_NON_ASCII); - } - base::FilePath file_path_base = - base::FilePath::FromUTF8Unsafe(UTF16ToUTF8(path_base)); - if (!file_util::CreateDirectory(file_path_base)) { - LOG(ERROR) << "Unable to create IndexedDB database path " << path_base; - base::Histogram::FactoryGet("WebCore.IndexedDB.BackingStore.OpenStatus", - 1, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX + 1, - base::HistogramBase::kUmaTargetedHistogramFlag) - ->Add(INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_FAILED_DIRECTORY); - return scoped_refptr<IndexedDBBackingStore>(); - } - - // TODO(jsbell): Rework to use FilePath throughout. - base::FilePath identifier_path = - base::FilePath::FromUTF8Unsafe(UTF16ToUTF8(database_identifier)); - base::FilePath file_path = - file_path_base.Append(identifier_path).AppendASCII(".indexeddb.leveldb"); - - db = leveldb_factory->OpenLevelDB(file_path, comparator.get()); - - if (db) { - bool known = false; - bool ok = IsSchemaKnown(db.get(), &known); - if (!ok) { - LOG(ERROR) << "IndexedDB had IO error checking schema, treating it as " - "failure to open"; - base::Histogram::FactoryGet( - "WebCore.IndexedDB.BackingStore.OpenStatus", - 1, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX + 1, - base::HistogramBase::kUmaTargetedHistogramFlag) - ->Add(INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_FAILED_IO_ERROR_CHECKING_SCHEMA); - db.reset(); - } else if (!known) { - LOG(ERROR) << "IndexedDB backing store had unknown schema, treating it " - "as failure to open"; - base::Histogram::FactoryGet( - "WebCore.IndexedDB.BackingStore.OpenStatus", - 1, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX + 1, - base::HistogramBase::kUmaTargetedHistogramFlag) - ->Add(INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_FAILED_UNKNOWN_SCHEMA); - db.reset(); - } - } - - if (db) { - base::Histogram::FactoryGet("WebCore.IndexedDB.BackingStore.OpenStatus", - 1, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX + 1, - base::HistogramBase::kUmaTargetedHistogramFlag) - ->Add(INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_SUCCESS); - } else { - LOG(ERROR) << "IndexedDB backing store open failed, attempting cleanup"; - bool success = leveldb_factory->DestroyLevelDB(file_path); - if (!success) { - LOG(ERROR) << "IndexedDB backing store cleanup failed"; - base::Histogram::FactoryGet( - "WebCore.IndexedDB.BackingStore.OpenStatus", - 1, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX + 1, - base::HistogramBase::kUmaTargetedHistogramFlag) - ->Add(INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_CLEANUP_DESTROY_FAILED); - return scoped_refptr<IndexedDBBackingStore>(); - } - - LOG(ERROR) << "IndexedDB backing store cleanup succeeded, reopening"; - db = leveldb_factory->OpenLevelDB(file_path, comparator.get()); - if (!db) { - LOG(ERROR) << "IndexedDB backing store reopen after recovery failed"; - base::Histogram::FactoryGet( - "WebCore.IndexedDB.BackingStore.OpenStatus", - 1, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX + 1, - base::HistogramBase::kUmaTargetedHistogramFlag) - ->Add(INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_CLEANUP_REOPEN_FAILED); - return scoped_refptr<IndexedDBBackingStore>(); - } - base::Histogram::FactoryGet("WebCore.IndexedDB.BackingStore.OpenStatus", - 1, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX + 1, - base::HistogramBase::kUmaTargetedHistogramFlag) - ->Add(INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_CLEANUP_REOPEN_SUCCESS); - } - - if (!db) { - NOTREACHED(); - base::Histogram::FactoryGet("WebCore.IndexedDB.BackingStore.OpenStatus", - 1, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX + 1, - base::HistogramBase::kUmaTargetedHistogramFlag) - ->Add(INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_FAILED_UNKNOWN_ERR); - return scoped_refptr<IndexedDBBackingStore>(); - } - - return Create(file_identifier, db.Pass(), comparator.Pass()); -} - -scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::OpenInMemory( - const string16& identifier) { - DefaultLevelDBFactory leveldb_factory; - return IndexedDBBackingStore::OpenInMemory(identifier, &leveldb_factory); -} - -scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::OpenInMemory( - const string16& identifier, - LevelDBFactory* leveldb_factory) { - IDB_TRACE("IndexedDBBackingStore::open_in_memory"); - - scoped_ptr<LevelDBComparator> comparator(new Comparator()); - scoped_ptr<LevelDBDatabase> db = - LevelDBDatabase::OpenInMemory(comparator.get()); - if (!db) { - LOG(ERROR) << "LevelDBDatabase::open_in_memory failed."; - base::Histogram::FactoryGet("WebCore.IndexedDB.BackingStore.OpenStatus", - 1, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX + 1, - base::HistogramBase::kUmaTargetedHistogramFlag) - ->Add(INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MEMORY_FAILED); - return scoped_refptr<IndexedDBBackingStore>(); - } - base::Histogram::FactoryGet("WebCore.IndexedDB.BackingStore.OpenStatus", - 1, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX, - INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MAX + 1, - base::HistogramBase::kUmaTargetedHistogramFlag) - ->Add(INDEXED_DB_LEVEL_DB_BACKING_STORE_OPEN_MEMORY_SUCCESS); - - return Create(identifier, db.Pass(), comparator.Pass()); -} - -scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::Create( - const string16& identifier, - scoped_ptr<LevelDBDatabase> db, - scoped_ptr<LevelDBComparator> comparator) { - // TODO(jsbell): Handle comparator name changes. - scoped_refptr<IndexedDBBackingStore> backing_store( - new IndexedDBBackingStore(identifier, db.Pass(), comparator.Pass())); - - if (!SetUpMetadata(backing_store->db_.get(), identifier)) - return scoped_refptr<IndexedDBBackingStore>(); - - return backing_store; -} - -std::vector<string16> IndexedDBBackingStore::GetDatabaseNames() { - std::vector<string16> found_names; - const std::vector<char> start_key = - DatabaseNameKey::EncodeMinKeyForOrigin(identifier_); - const std::vector<char> stop_key = - DatabaseNameKey::EncodeStopKeyForOrigin(identifier_); - - DCHECK(found_names.empty()); - - scoped_ptr<LevelDBIterator> it = db_->CreateIterator(); - for (it->Seek(LevelDBSlice(start_key)); - it->IsValid() && CompareKeys(it->Key(), LevelDBSlice(stop_key)) < 0; - it->Next()) { - const char* p = it->Key().begin(); - const char* limit = it->Key().end(); - - DatabaseNameKey database_name_key; - p = DatabaseNameKey::Decode(p, limit, &database_name_key); - DCHECK(p); - - found_names.push_back(database_name_key.database_name()); - } - return found_names; -} - -bool IndexedDBBackingStore::GetIDBDatabaseMetaData( - const string16& name, - IndexedDBDatabaseMetadata* metadata, - bool& found) { - const std::vector<char> key = DatabaseNameKey::Encode(identifier_, name); - found = false; - - bool ok = GetInt(db_.get(), LevelDBSlice(key), metadata->id, found); - if (!ok) { - INTERNAL_READ_ERROR(GET_IDBDATABASE_METADATA); - return false; - } - if (!found) - return true; - - ok = GetString(db_.get(), - LevelDBSlice(DatabaseMetaDataKey::Encode( - metadata->id, DatabaseMetaDataKey::USER_VERSION)), - metadata->version, - found); - if (!ok) { - INTERNAL_READ_ERROR(GET_IDBDATABASE_METADATA); - return false; - } - if (!found) { - INTERNAL_CONSISTENCY_ERROR(GET_IDBDATABASE_METADATA); - return false; - } - - ok = GetVarInt(db_.get(), - LevelDBSlice(DatabaseMetaDataKey::Encode( - metadata->id, DatabaseMetaDataKey::USER_INT_VERSION)), - metadata->int_version, - found); - if (!ok) { - INTERNAL_READ_ERROR(GET_IDBDATABASE_METADATA); - return false; - } - if (!found) { - INTERNAL_CONSISTENCY_ERROR(GET_IDBDATABASE_METADATA); - return false; - } - - if (metadata->int_version == IndexedDBDatabaseMetadata::DEFAULT_INT_VERSION) - metadata->int_version = IndexedDBDatabaseMetadata::NO_INT_VERSION; - - ok = GetMaxObjectStoreId( - db_.get(), metadata->id, metadata->max_object_store_id); - if (!ok) { - INTERNAL_READ_ERROR(GET_IDBDATABASE_METADATA); - return false; - } - - return true; -} - -WARN_UNUSED_RESULT static bool GetNewDatabaseId(LevelDBDatabase* db, - int64& new_id) { - scoped_refptr<LevelDBTransaction> transaction = - LevelDBTransaction::Create(db); - - new_id = -1; - int64 max_database_id = -1; - bool found = false; - bool ok = GetInt(transaction.get(), - LevelDBSlice(MaxDatabaseIdKey::Encode()), - max_database_id, - found); - if (!ok) { - INTERNAL_READ_ERROR(GET_NEW_DATABASE_ID); - return false; - } - if (!found) - max_database_id = 0; - - DCHECK_GE(max_database_id, 0); - - int64 database_id = max_database_id + 1; - PutInt( - transaction.get(), LevelDBSlice(MaxDatabaseIdKey::Encode()), database_id); - if (!transaction->Commit()) { - INTERNAL_WRITE_ERROR(GET_NEW_DATABASE_ID); - return false; - } - new_id = database_id; - return true; -} - -bool IndexedDBBackingStore::CreateIDBDatabaseMetaData(const string16& name, - const string16& version, - int64 int_version, - int64& row_id) { - bool ok = GetNewDatabaseId(db_.get(), row_id); - if (!ok) - return false; - DCHECK_GE(row_id, 0); - - if (int_version == IndexedDBDatabaseMetadata::NO_INT_VERSION) - int_version = IndexedDBDatabaseMetadata::DEFAULT_INT_VERSION; - - scoped_refptr<LevelDBTransaction> transaction = - LevelDBTransaction::Create(db_.get()); - PutInt(transaction.get(), - LevelDBSlice(DatabaseNameKey::Encode(identifier_, name)), - row_id); - PutString(transaction.get(), - LevelDBSlice(DatabaseMetaDataKey::Encode( - row_id, DatabaseMetaDataKey::USER_VERSION)), - version); - PutVarInt(transaction.get(), - LevelDBSlice(DatabaseMetaDataKey::Encode( - row_id, DatabaseMetaDataKey::USER_INT_VERSION)), - int_version); - if (!transaction->Commit()) { - INTERNAL_WRITE_ERROR(CREATE_IDBDATABASE_METADATA); - return false; - } - return true; -} - -bool IndexedDBBackingStore::UpdateIDBDatabaseIntVersion( - IndexedDBBackingStore::Transaction* transaction, - int64 row_id, - int64 int_version) { - if (int_version == IndexedDBDatabaseMetadata::NO_INT_VERSION) - int_version = IndexedDBDatabaseMetadata::DEFAULT_INT_VERSION; - DCHECK_GE(int_version, 0) << "int_version was " << int_version; - PutVarInt(Transaction::LevelDBTransactionFrom(transaction), - LevelDBSlice(DatabaseMetaDataKey::Encode( - row_id, DatabaseMetaDataKey::USER_INT_VERSION)), - int_version); - return true; -} - -bool IndexedDBBackingStore::UpdateIDBDatabaseMetaData( - IndexedDBBackingStore::Transaction* transaction, - int64 row_id, - const string16& version) { - PutString(Transaction::LevelDBTransactionFrom(transaction), - LevelDBSlice(DatabaseMetaDataKey::Encode( - row_id, DatabaseMetaDataKey::USER_VERSION)), - version); - return true; -} - -static void DeleteRange(LevelDBTransaction* transaction, - const std::vector<char>& begin, - const std::vector<char>& end) { - scoped_ptr<LevelDBIterator> it = transaction->CreateIterator(); - for (it->Seek(LevelDBSlice(begin)); - it->IsValid() && CompareKeys(it->Key(), LevelDBSlice(end)) < 0; - it->Next()) - transaction->Remove(it->Key()); -} - -bool IndexedDBBackingStore::DeleteDatabase(const string16& name) { - IDB_TRACE("IndexedDBBackingStore::delete_database"); - scoped_ptr<LevelDBWriteOnlyTransaction> transaction = - LevelDBWriteOnlyTransaction::Create(db_.get()); - - IndexedDBDatabaseMetadata metadata; - bool success = false; - bool ok = GetIDBDatabaseMetaData(name, &metadata, success); - if (!ok) - return false; - if (!success) - return true; - - const std::vector<char> start_key = DatabaseMetaDataKey::Encode( - metadata.id, DatabaseMetaDataKey::ORIGIN_NAME); - const std::vector<char> stop_key = DatabaseMetaDataKey::Encode( - metadata.id + 1, DatabaseMetaDataKey::ORIGIN_NAME); - scoped_ptr<LevelDBIterator> it = db_->CreateIterator(); - for (it->Seek(LevelDBSlice(start_key)); - it->IsValid() && CompareKeys(it->Key(), LevelDBSlice(stop_key)) < 0; - it->Next()) - transaction->Remove(it->Key()); - - const std::vector<char> key = DatabaseNameKey::Encode(identifier_, name); - transaction->Remove(LevelDBSlice(key)); - - if (!transaction->Commit()) { - INTERNAL_WRITE_ERROR(DELETE_DATABASE); - return false; - } - return true; -} - -static bool CheckObjectStoreAndMetaDataType(const LevelDBIterator* it, - const std::vector<char>& stop_key, - int64 object_store_id, - int64 meta_data_type) { - if (!it->IsValid() || CompareKeys(it->Key(), LevelDBSlice(stop_key)) >= 0) - return false; - - ObjectStoreMetaDataKey meta_data_key; - const char* p = ObjectStoreMetaDataKey::Decode( - it->Key().begin(), it->Key().end(), &meta_data_key); - DCHECK(p); - if (meta_data_key.ObjectStoreId() != object_store_id) - return false; - if (meta_data_key.MetaDataType() != meta_data_type) - return false; - return true; -} - -// TODO(jsbell): This should do some error handling rather than -// plowing ahead when bad data is encountered. -bool IndexedDBBackingStore::GetObjectStores( - int64 database_id, - IndexedDBDatabaseMetadata::ObjectStoreMap* object_stores) { - IDB_TRACE("IndexedDBBackingStore::get_object_stores"); - if (!KeyPrefix::IsValidDatabaseId(database_id)) - return false; - const std::vector<char> start_key = - ObjectStoreMetaDataKey::Encode(database_id, 1, 0); - const std::vector<char> stop_key = - ObjectStoreMetaDataKey::EncodeMaxKey(database_id); - - DCHECK(object_stores->empty()); - - scoped_ptr<LevelDBIterator> it = db_->CreateIterator(); - it->Seek(LevelDBSlice(start_key)); - while (it->IsValid() && CompareKeys(it->Key(), LevelDBSlice(stop_key)) < 0) { - const char* p = it->Key().begin(); - const char* limit = it->Key().end(); - - ObjectStoreMetaDataKey meta_data_key; - p = ObjectStoreMetaDataKey::Decode(p, limit, &meta_data_key); - DCHECK(p); - if (meta_data_key.MetaDataType() != ObjectStoreMetaDataKey::NAME) { - INTERNAL_CONSISTENCY_ERROR(GET_OBJECT_STORES); - // Possible stale metadata, but don't fail the load. - it->Next(); - continue; - } - - int64 object_store_id = meta_data_key.ObjectStoreId(); - - // TODO(jsbell): Do this by direct key lookup rather than iteration, to - // simplify. - string16 object_store_name = - DecodeString(it->Value().begin(), it->Value().end()); - - it->Next(); - if (!CheckObjectStoreAndMetaDataType(it.get(), - stop_key, - object_store_id, - ObjectStoreMetaDataKey::KEY_PATH)) { - INTERNAL_CONSISTENCY_ERROR(GET_OBJECT_STORES); - break; - } - IndexedDBKeyPath key_path = - DecodeIDBKeyPath(it->Value().begin(), it->Value().end()); - - it->Next(); - if (!CheckObjectStoreAndMetaDataType( - it.get(), - stop_key, - object_store_id, - ObjectStoreMetaDataKey::AUTO_INCREMENT)) { - INTERNAL_CONSISTENCY_ERROR(GET_OBJECT_STORES); - break; - } - bool auto_increment = DecodeBool(it->Value().begin(), it->Value().end()); - - it->Next(); // Is evicatble. - if (!CheckObjectStoreAndMetaDataType(it.get(), - stop_key, - object_store_id, - ObjectStoreMetaDataKey::EVICTABLE)) { - INTERNAL_CONSISTENCY_ERROR(GET_OBJECT_STORES); - break; - } - - it->Next(); // Last version. - if (!CheckObjectStoreAndMetaDataType( - it.get(), - stop_key, - object_store_id, - ObjectStoreMetaDataKey::LAST_VERSION)) { - INTERNAL_CONSISTENCY_ERROR(GET_OBJECT_STORES); - break; - } - - it->Next(); // Maximum index id allocated. - if (!CheckObjectStoreAndMetaDataType( - it.get(), - stop_key, - object_store_id, - ObjectStoreMetaDataKey::MAX_INDEX_ID)) { - INTERNAL_CONSISTENCY_ERROR(GET_OBJECT_STORES); - break; - } - int64 max_index_id = DecodeInt(it->Value().begin(), it->Value().end()); - - it->Next(); // [optional] has key path (is not null) - if (CheckObjectStoreAndMetaDataType(it.get(), - stop_key, - object_store_id, - ObjectStoreMetaDataKey::HAS_KEY_PATH)) { - bool has_key_path = DecodeBool(it->Value().begin(), it->Value().end()); - // This check accounts for two layers of legacy coding: - // (1) Initially, has_key_path was added to distinguish null vs. string. - // (2) Later, null vs. string vs. array was stored in the key_path itself. - // So this check is only relevant for string-type key_paths. - if (!has_key_path && - (key_path.type() == WebKit::WebIDBKeyPath::StringType && - !key_path.string().empty())) { - INTERNAL_CONSISTENCY_ERROR(GET_OBJECT_STORES); - break; - } - if (!has_key_path) - key_path = IndexedDBKeyPath(); - it->Next(); - } - - int64 key_generator_current_number = -1; - if (CheckObjectStoreAndMetaDataType( - it.get(), - stop_key, - object_store_id, - ObjectStoreMetaDataKey::KEY_GENERATOR_CURRENT_NUMBER)) { - key_generator_current_number = - DecodeInt(it->Value().begin(), it->Value().end()); - // TODO(jsbell): Return key_generator_current_number, cache in - // object store, and write lazily to backing store. For now, - // just assert that if it was written it was valid. - DCHECK_GE(key_generator_current_number, kKeyGeneratorInitialNumber); - it->Next(); - } - - IndexedDBObjectStoreMetadata metadata(object_store_name, - object_store_id, - key_path, - auto_increment, - max_index_id); - if (!GetIndexes(database_id, object_store_id, &metadata.indexes)) - return false; - (*object_stores)[object_store_id] = metadata; - } - return true; -} - -WARN_UNUSED_RESULT static bool SetMaxObjectStoreId( - LevelDBTransaction* transaction, - int64 database_id, - int64 object_store_id) { - const std::vector<char> max_object_store_id_key = DatabaseMetaDataKey::Encode( - database_id, DatabaseMetaDataKey::MAX_OBJECT_STORE_ID); - int64 max_object_store_id = -1; - bool ok = GetMaxObjectStoreId( - transaction, max_object_store_id_key, max_object_store_id); - if (!ok) { - INTERNAL_READ_ERROR(SET_MAX_OBJECT_STORE_ID); - return false; - } - - if (object_store_id <= max_object_store_id) { - INTERNAL_CONSISTENCY_ERROR(SET_MAX_OBJECT_STORE_ID); - return false; - } - PutInt(transaction, LevelDBSlice(max_object_store_id_key), object_store_id); - return true; -} - -bool IndexedDBBackingStore::CreateObjectStore( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - const string16& name, - const IndexedDBKeyPath& key_path, - bool auto_increment) { - IDB_TRACE("IndexedDBBackingStore::create_object_store"); - if (!KeyPrefix::ValidIds(database_id, object_store_id)) - return false; - LevelDBTransaction* leveldb_transaction = - IndexedDBBackingStore::Transaction::LevelDBTransactionFrom(transaction); - if (!SetMaxObjectStoreId(leveldb_transaction, database_id, object_store_id)) - return false; - - const std::vector<char> name_key = ObjectStoreMetaDataKey::Encode( - database_id, object_store_id, ObjectStoreMetaDataKey::NAME); - const std::vector<char> key_path_key = ObjectStoreMetaDataKey::Encode( - database_id, object_store_id, ObjectStoreMetaDataKey::KEY_PATH); - const std::vector<char> auto_increment_key = ObjectStoreMetaDataKey::Encode( - database_id, object_store_id, ObjectStoreMetaDataKey::AUTO_INCREMENT); - const std::vector<char> evictable_key = ObjectStoreMetaDataKey::Encode( - database_id, object_store_id, ObjectStoreMetaDataKey::EVICTABLE); - const std::vector<char> last_version_key = ObjectStoreMetaDataKey::Encode( - database_id, object_store_id, ObjectStoreMetaDataKey::LAST_VERSION); - const std::vector<char> max_index_id_key = ObjectStoreMetaDataKey::Encode( - database_id, object_store_id, ObjectStoreMetaDataKey::MAX_INDEX_ID); - const std::vector<char> has_key_path_key = ObjectStoreMetaDataKey::Encode( - database_id, object_store_id, ObjectStoreMetaDataKey::HAS_KEY_PATH); - const std::vector<char> key_generator_current_number_key = - ObjectStoreMetaDataKey::Encode( - database_id, - object_store_id, - ObjectStoreMetaDataKey::KEY_GENERATOR_CURRENT_NUMBER); - const std::vector<char> names_key = - ObjectStoreNamesKey::Encode(database_id, name); - - PutString(leveldb_transaction, LevelDBSlice(name_key), name); - PutIDBKeyPath(leveldb_transaction, LevelDBSlice(key_path_key), key_path); - PutInt(leveldb_transaction, LevelDBSlice(auto_increment_key), auto_increment); - PutInt(leveldb_transaction, LevelDBSlice(evictable_key), false); - PutInt(leveldb_transaction, LevelDBSlice(last_version_key), 1); - PutInt(leveldb_transaction, LevelDBSlice(max_index_id_key), kMinimumIndexId); - PutBool( - leveldb_transaction, LevelDBSlice(has_key_path_key), !key_path.IsNull()); - PutInt(leveldb_transaction, - LevelDBSlice(key_generator_current_number_key), - kKeyGeneratorInitialNumber); - PutInt(leveldb_transaction, LevelDBSlice(names_key), object_store_id); - return true; -} - -bool IndexedDBBackingStore::DeleteObjectStore( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id) { - IDB_TRACE("IndexedDBBackingStore::delete_object_store"); - if (!KeyPrefix::ValidIds(database_id, object_store_id)) - return false; - LevelDBTransaction* leveldb_transaction = - IndexedDBBackingStore::Transaction::LevelDBTransactionFrom(transaction); - - string16 object_store_name; - bool found = false; - bool ok = GetString( - leveldb_transaction, - LevelDBSlice(ObjectStoreMetaDataKey::Encode( - database_id, object_store_id, ObjectStoreMetaDataKey::NAME)), - object_store_name, - found); - if (!ok) { - INTERNAL_READ_ERROR(DELETE_OBJECT_STORE); - return false; - } - if (!found) { - INTERNAL_CONSISTENCY_ERROR(DELETE_OBJECT_STORE); - return false; - } - - DeleteRange( - leveldb_transaction, - ObjectStoreMetaDataKey::Encode(database_id, object_store_id, 0), - ObjectStoreMetaDataKey::EncodeMaxKey(database_id, object_store_id)); - - leveldb_transaction->Remove(LevelDBSlice( - ObjectStoreNamesKey::Encode(database_id, object_store_name))); - - DeleteRange(leveldb_transaction, - IndexFreeListKey::Encode(database_id, object_store_id, 0), - IndexFreeListKey::EncodeMaxKey(database_id, object_store_id)); - DeleteRange(leveldb_transaction, - IndexMetaDataKey::Encode(database_id, object_store_id, 0, 0), - IndexMetaDataKey::EncodeMaxKey(database_id, object_store_id)); - - return ClearObjectStore(transaction, database_id, object_store_id); -} - -bool IndexedDBBackingStore::GetRecord( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - const IndexedDBKey& key, - std::vector<char>& record) { - IDB_TRACE("IndexedDBBackingStore::get_record"); - if (!KeyPrefix::ValidIds(database_id, object_store_id)) - return false; - LevelDBTransaction* leveldb_transaction = - IndexedDBBackingStore::Transaction::LevelDBTransactionFrom(transaction); - - const std::vector<char> leveldb_key = - ObjectStoreDataKey::Encode(database_id, object_store_id, key); - std::vector<char> data; - - record.clear(); - - bool found = false; - bool ok = leveldb_transaction->Get(LevelDBSlice(leveldb_key), data, found); - if (!ok) { - INTERNAL_READ_ERROR(GET_RECORD); - return false; - } - if (!found) - return true; - if (!data.size()) { - INTERNAL_READ_ERROR(GET_RECORD); - return false; - } - - int64 version; - const char* p = DecodeVarInt(&*data.begin(), &*data.rbegin() + 1, version); - if (!p) { - INTERNAL_READ_ERROR(GET_RECORD); - return false; - } - - record.insert(record.end(), p, static_cast<const char*>(&*data.rbegin()) + 1); - return true; -} - -WARN_UNUSED_RESULT static bool GetNewVersionNumber( - LevelDBTransaction* transaction, - int64 database_id, - int64 object_store_id, - int64& new_version_number) { - const std::vector<char> last_version_key = ObjectStoreMetaDataKey::Encode( - database_id, object_store_id, ObjectStoreMetaDataKey::LAST_VERSION); - - new_version_number = -1; - int64 last_version = -1; - bool found = false; - bool ok = - GetInt(transaction, LevelDBSlice(last_version_key), last_version, found); - if (!ok) { - INTERNAL_READ_ERROR(GET_NEW_VERSION_NUMBER); - return false; - } - if (!found) - last_version = 0; - - DCHECK_GE(last_version, 0); - - int64 version = last_version + 1; - PutInt(transaction, LevelDBSlice(last_version_key), version); - - DCHECK(version > - last_version); // TODO(jsbell): Think about how we want to handle - // the overflow scenario. - - new_version_number = version; - return true; -} - -bool IndexedDBBackingStore::PutRecord( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - const IndexedDBKey& key, - const std::vector<char>& value, - RecordIdentifier* record_identifier) { - IDB_TRACE("IndexedDBBackingStore::put_record"); - if (!KeyPrefix::ValidIds(database_id, object_store_id)) - return false; - DCHECK(key.IsValid()); - - LevelDBTransaction* leveldb_transaction = - IndexedDBBackingStore::Transaction::LevelDBTransactionFrom(transaction); - int64 version = -1; - bool ok = GetNewVersionNumber( - leveldb_transaction, database_id, object_store_id, version); - if (!ok) - return false; - DCHECK_GE(version, 0); - const std::vector<char> object_storedata_key = - ObjectStoreDataKey::Encode(database_id, object_store_id, key); - - std::vector<char> v(EncodeVarInt(version)); - - v.insert(v.end(), value.begin(), value.end()); - - leveldb_transaction->Put(LevelDBSlice(object_storedata_key), v); - - const std::vector<char> exists_entry_key = - ExistsEntryKey::Encode(database_id, object_store_id, key); - leveldb_transaction->Put(LevelDBSlice(exists_entry_key), EncodeInt(version)); - - record_identifier->Reset(EncodeIDBKey(key), version); - return true; -} - -bool IndexedDBBackingStore::ClearObjectStore( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id) { - IDB_TRACE("IndexedDBBackingStore::clear_object_store"); - if (!KeyPrefix::ValidIds(database_id, object_store_id)) - return false; - LevelDBTransaction* leveldb_transaction = - IndexedDBBackingStore::Transaction::LevelDBTransactionFrom(transaction); - const std::vector<char> start_key = - KeyPrefix(database_id, object_store_id).Encode(); - const std::vector<char> stop_key = - KeyPrefix(database_id, object_store_id + 1).Encode(); - - DeleteRange(leveldb_transaction, start_key, stop_key); - return true; -} - -bool IndexedDBBackingStore::DeleteRecord( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - const RecordIdentifier& record_identifier) { - IDB_TRACE("IndexedDBBackingStore::delete_record"); - if (!KeyPrefix::ValidIds(database_id, object_store_id)) - return false; - LevelDBTransaction* leveldb_transaction = - IndexedDBBackingStore::Transaction::LevelDBTransactionFrom(transaction); - - const std::vector<char> object_store_data_key = ObjectStoreDataKey::Encode( - database_id, object_store_id, record_identifier.primary_key()); - leveldb_transaction->Remove(LevelDBSlice(object_store_data_key)); - - const std::vector<char> exists_entry_key = ExistsEntryKey::Encode( - database_id, object_store_id, record_identifier.primary_key()); - leveldb_transaction->Remove(LevelDBSlice(exists_entry_key)); - return true; -} - -bool IndexedDBBackingStore::GetKeyGeneratorCurrentNumber( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64& key_generator_current_number) { - if (!KeyPrefix::ValidIds(database_id, object_store_id)) - return false; - LevelDBTransaction* leveldb_transaction = - IndexedDBBackingStore::Transaction::LevelDBTransactionFrom(transaction); - - const std::vector<char> key_generator_current_number_key = - ObjectStoreMetaDataKey::Encode( - database_id, - object_store_id, - ObjectStoreMetaDataKey::KEY_GENERATOR_CURRENT_NUMBER); - - key_generator_current_number = -1; - std::vector<char> data; - - bool found = false; - bool ok = leveldb_transaction->Get( - LevelDBSlice(key_generator_current_number_key), data, found); - if (!ok) { - INTERNAL_READ_ERROR(GET_KEY_GENERATOR_CURRENT_NUMBER); - return false; - } - if (found) { - key_generator_current_number = DecodeInt(data.begin(), data.end()); - } else { - // Previously, the key generator state was not stored explicitly - // but derived from the maximum numeric key present in existing - // data. This violates the spec as the data may be cleared but the - // key generator state must be preserved. - // TODO(jsbell): Fix this for all stores on database open? - const std::vector<char> start_key = - ObjectStoreDataKey::Encode(database_id, object_store_id, MinIDBKey()); - const std::vector<char> stop_key = - ObjectStoreDataKey::Encode(database_id, object_store_id, MaxIDBKey()); - - scoped_ptr<LevelDBIterator> it = leveldb_transaction->CreateIterator(); - int64 max_numeric_key = 0; - - for (it->Seek(LevelDBSlice(start_key)); - it->IsValid() && CompareKeys(it->Key(), LevelDBSlice(stop_key)) < 0; - it->Next()) { - const char* p = it->Key().begin(); - const char* limit = it->Key().end(); - - ObjectStoreDataKey data_key; - p = ObjectStoreDataKey::Decode(p, limit, &data_key); - DCHECK(p); - - scoped_ptr<IndexedDBKey> user_key = data_key.user_key(); - if (user_key->type() == WebKit::WebIDBKey::NumberType) { - int64 n = static_cast<int64>(user_key->number()); - if (n > max_numeric_key) - max_numeric_key = n; - } - } - - key_generator_current_number = max_numeric_key + 1; - } - - return true; -} - -bool IndexedDBBackingStore::MaybeUpdateKeyGeneratorCurrentNumber( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 new_number, - bool check_current) { - if (!KeyPrefix::ValidIds(database_id, object_store_id)) - return false; - LevelDBTransaction* leveldb_transaction = - IndexedDBBackingStore::Transaction::LevelDBTransactionFrom(transaction); - - if (check_current) { - int64 current_number; - bool ok = GetKeyGeneratorCurrentNumber( - transaction, database_id, object_store_id, current_number); - if (!ok) - return false; - if (new_number <= current_number) - return true; - } - - const std::vector<char> key_generator_current_number_key = - ObjectStoreMetaDataKey::Encode( - database_id, - object_store_id, - ObjectStoreMetaDataKey::KEY_GENERATOR_CURRENT_NUMBER); - PutInt(leveldb_transaction, - LevelDBSlice(key_generator_current_number_key), - new_number); - return true; -} - -bool IndexedDBBackingStore::KeyExistsInObjectStore( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - const IndexedDBKey& key, - RecordIdentifier* found_record_identifier, - bool& found) { - IDB_TRACE("IndexedDBBackingStore::key_exists_in_object_store"); - if (!KeyPrefix::ValidIds(database_id, object_store_id)) - return false; - found = false; - LevelDBTransaction* leveldb_transaction = - IndexedDBBackingStore::Transaction::LevelDBTransactionFrom(transaction); - const std::vector<char> leveldb_key = - ObjectStoreDataKey::Encode(database_id, object_store_id, key); - std::vector<char> data; - - bool ok = leveldb_transaction->Get(LevelDBSlice(leveldb_key), data, found); - if (!ok) { - INTERNAL_READ_ERROR(KEY_EXISTS_IN_OBJECT_STORE); - return false; - } - if (!found) - return true; - if (!data.size()) { - INTERNAL_READ_ERROR(KEY_EXISTS_IN_OBJECT_STORE); - return false; - } - - int64 version; - if (DecodeVarInt(&*data.begin(), &*data.rbegin() + 1, version) == 0) - return false; - - found_record_identifier->Reset(EncodeIDBKey(key), version); - return true; -} - -static bool CheckIndexAndMetaDataKey(const LevelDBIterator* it, - const std::vector<char>& stop_key, - int64 index_id, - unsigned char meta_data_type) { - if (!it->IsValid() || CompareKeys(it->Key(), LevelDBSlice(stop_key)) >= 0) - return false; - - IndexMetaDataKey meta_data_key; - const char* p = IndexMetaDataKey::Decode( - it->Key().begin(), it->Key().end(), &meta_data_key); - DCHECK(p); - if (meta_data_key.IndexId() != index_id) - return false; - if (meta_data_key.meta_data_type() != meta_data_type) - return false; - return true; -} - -// TODO(jsbell): This should do some error handling rather than plowing ahead -// when bad -// data is encountered. -bool IndexedDBBackingStore::GetIndexes( - int64 database_id, - int64 object_store_id, - IndexedDBObjectStoreMetadata::IndexMap* indexes) { - IDB_TRACE("IndexedDBBackingStore::get_indexes"); - if (!KeyPrefix::ValidIds(database_id, object_store_id)) - return false; - const std::vector<char> start_key = - IndexMetaDataKey::Encode(database_id, object_store_id, 0, 0); - const std::vector<char> stop_key = - IndexMetaDataKey::Encode(database_id, object_store_id + 1, 0, 0); - - DCHECK(indexes->empty()); - - scoped_ptr<LevelDBIterator> it = db_->CreateIterator(); - it->Seek(LevelDBSlice(start_key)); - while (it->IsValid() && - CompareKeys(LevelDBSlice(it->Key()), LevelDBSlice(stop_key)) < 0) { - const char* p = it->Key().begin(); - const char* limit = it->Key().end(); - - IndexMetaDataKey meta_data_key; - p = IndexMetaDataKey::Decode(p, limit, &meta_data_key); - DCHECK(p); - if (meta_data_key.meta_data_type() != IndexMetaDataKey::NAME) { - INTERNAL_CONSISTENCY_ERROR(GET_INDEXES); - // Possible stale metadata due to http://webkit.org/b/85557 but don't fail - // the load. - it->Next(); - continue; - } - - // TODO(jsbell): Do this by direct key lookup rather than iteration, to - // simplify. - int64 index_id = meta_data_key.IndexId(); - string16 index_name = DecodeString(it->Value().begin(), it->Value().end()); - - it->Next(); // unique flag - if (!CheckIndexAndMetaDataKey( - it.get(), stop_key, index_id, IndexMetaDataKey::UNIQUE)) { - INTERNAL_CONSISTENCY_ERROR(GET_INDEXES); - break; - } - bool index_unique = DecodeBool(it->Value().begin(), it->Value().end()); - - it->Next(); // key_path - if (!CheckIndexAndMetaDataKey( - it.get(), stop_key, index_id, IndexMetaDataKey::KEY_PATH)) { - INTERNAL_CONSISTENCY_ERROR(GET_INDEXES); - break; - } - IndexedDBKeyPath key_path = - DecodeIDBKeyPath(it->Value().begin(), it->Value().end()); - - it->Next(); // [optional] multi_entry flag - bool index_multi_entry = false; - if (CheckIndexAndMetaDataKey( - it.get(), stop_key, index_id, IndexMetaDataKey::MULTI_ENTRY)) { - index_multi_entry = DecodeBool(it->Value().begin(), it->Value().end()); - it->Next(); - } - - (*indexes)[index_id] = IndexedDBIndexMetadata( - index_name, index_id, key_path, index_unique, index_multi_entry); - } - return true; -} - -WARN_UNUSED_RESULT static bool SetMaxIndexId(LevelDBTransaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id) { - int64 max_index_id = -1; - const std::vector<char> max_index_id_key = ObjectStoreMetaDataKey::Encode( - database_id, object_store_id, ObjectStoreMetaDataKey::MAX_INDEX_ID); - bool found = false; - bool ok = - GetInt(transaction, LevelDBSlice(max_index_id_key), max_index_id, found); - if (!ok) { - INTERNAL_READ_ERROR(SET_MAX_INDEX_ID); - return false; - } - if (!found) - max_index_id = kMinimumIndexId; - - if (index_id <= max_index_id) { - INTERNAL_CONSISTENCY_ERROR(SET_MAX_INDEX_ID); - return false; - } - - PutInt(transaction, LevelDBSlice(max_index_id_key), index_id); - return true; -} - -bool IndexedDBBackingStore::CreateIndex( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - const string16& name, - const IndexedDBKeyPath& key_path, - bool is_unique, - bool is_multi_entry) { - IDB_TRACE("IndexedDBBackingStore::create_index"); - if (!KeyPrefix::ValidIds(database_id, object_store_id, index_id)) - return false; - LevelDBTransaction* leveldb_transaction = - IndexedDBBackingStore::Transaction::LevelDBTransactionFrom(transaction); - if (!SetMaxIndexId( - leveldb_transaction, database_id, object_store_id, index_id)) - return false; - - const std::vector<char> name_key = IndexMetaDataKey::Encode( - database_id, object_store_id, index_id, IndexMetaDataKey::NAME); - const std::vector<char> unique_key = IndexMetaDataKey::Encode( - database_id, object_store_id, index_id, IndexMetaDataKey::UNIQUE); - const std::vector<char> key_path_key = IndexMetaDataKey::Encode( - database_id, object_store_id, index_id, IndexMetaDataKey::KEY_PATH); - const std::vector<char> multi_entry_key = IndexMetaDataKey::Encode( - database_id, object_store_id, index_id, IndexMetaDataKey::MULTI_ENTRY); - - PutString(leveldb_transaction, LevelDBSlice(name_key), name); - PutBool(leveldb_transaction, LevelDBSlice(unique_key), is_unique); - PutIDBKeyPath(leveldb_transaction, LevelDBSlice(key_path_key), key_path); - PutBool(leveldb_transaction, LevelDBSlice(multi_entry_key), is_multi_entry); - return true; -} - -bool IndexedDBBackingStore::DeleteIndex( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id) { - IDB_TRACE("IndexedDBBackingStore::delete_index"); - if (!KeyPrefix::ValidIds(database_id, object_store_id, index_id)) - return false; - LevelDBTransaction* leveldb_transaction = - IndexedDBBackingStore::Transaction::LevelDBTransactionFrom(transaction); - - const std::vector<char> index_meta_data_start = - IndexMetaDataKey::Encode(database_id, object_store_id, index_id, 0); - const std::vector<char> index_meta_data_end = - IndexMetaDataKey::EncodeMaxKey(database_id, object_store_id, index_id); - DeleteRange(leveldb_transaction, index_meta_data_start, index_meta_data_end); - - const std::vector<char> index_data_start = - IndexDataKey::EncodeMinKey(database_id, object_store_id, index_id); - const std::vector<char> index_data_end = - IndexDataKey::EncodeMaxKey(database_id, object_store_id, index_id); - DeleteRange(leveldb_transaction, index_data_start, index_data_end); - return true; -} - -bool IndexedDBBackingStore::PutIndexDataForRecord( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - const IndexedDBKey& key, - const RecordIdentifier& record_identifier) { - IDB_TRACE("IndexedDBBackingStore::put_index_data_for_record"); - DCHECK(key.IsValid()); - if (!KeyPrefix::ValidIds(database_id, object_store_id, index_id)) - return false; - - LevelDBTransaction* leveldb_transaction = - IndexedDBBackingStore::Transaction::LevelDBTransactionFrom(transaction); - const std::vector<char> index_data_key = - IndexDataKey::Encode(database_id, - object_store_id, - index_id, - EncodeIDBKey(key), - record_identifier.primary_key()); - - std::vector<char> data(EncodeVarInt(record_identifier.version())); - const std::vector<char>& primary_key = record_identifier.primary_key(); - data.insert(data.end(), primary_key.begin(), primary_key.end()); - - leveldb_transaction->Put(LevelDBSlice(index_data_key), data); - return true; -} - -static bool FindGreatestKeyLessThanOrEqual(LevelDBTransaction* transaction, - const std::vector<char>& target, - std::vector<char>& found_key) { - scoped_ptr<LevelDBIterator> it = transaction->CreateIterator(); - it->Seek(LevelDBSlice(target)); - - if (!it->IsValid()) { - it->SeekToLast(); - if (!it->IsValid()) - return false; - } - - while (CompareIndexKeys(LevelDBSlice(it->Key()), LevelDBSlice(target)) > 0) { - it->Prev(); - if (!it->IsValid()) - return false; - } - - do { - found_key.assign(it->Key().begin(), it->Key().end()); - - // There can be several index keys that compare equal. We want the last one. - it->Next(); - } while (it->IsValid() && !CompareIndexKeys(it->Key(), LevelDBSlice(target))); - - return true; -} - -static bool VersionExists(LevelDBTransaction* transaction, - int64 database_id, - int64 object_store_id, - int64 version, - const std::vector<char>& encoded_primary_key, - bool& exists) { - const std::vector<char> key = - ExistsEntryKey::Encode(database_id, object_store_id, encoded_primary_key); - std::vector<char> data; - - bool ok = transaction->Get(LevelDBSlice(key), data, exists); - if (!ok) { - INTERNAL_READ_ERROR(VERSION_EXISTS); - return false; - } - if (!exists) - return true; - - exists = (DecodeInt(data.begin(), data.end()) == version); - return true; -} - -bool IndexedDBBackingStore::FindKeyInIndex( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - const IndexedDBKey& key, - std::vector<char>& found_encoded_primary_key, - bool& found) { - IDB_TRACE("IndexedDBBackingStore::find_key_in_index"); - DCHECK(KeyPrefix::ValidIds(database_id, object_store_id, index_id)); - - DCHECK(found_encoded_primary_key.empty()); - found = false; - - LevelDBTransaction* leveldb_transaction = - IndexedDBBackingStore::Transaction::LevelDBTransactionFrom(transaction); - const std::vector<char> leveldb_key = - IndexDataKey::Encode(database_id, object_store_id, index_id, key); - scoped_ptr<LevelDBIterator> it = leveldb_transaction->CreateIterator(); - it->Seek(LevelDBSlice(leveldb_key)); - - for (;;) { - if (!it->IsValid()) - return true; - if (CompareIndexKeys(it->Key(), LevelDBSlice(leveldb_key)) > 0) - return true; - - int64 version; - const char* p = - DecodeVarInt(it->Value().begin(), it->Value().end(), version); - if (!p) { - INTERNAL_READ_ERROR(FIND_KEY_IN_INDEX); - return false; - } - found_encoded_primary_key.insert( - found_encoded_primary_key.end(), p, it->Value().end()); - - bool exists = false; - bool ok = VersionExists(leveldb_transaction, - database_id, - object_store_id, - version, - found_encoded_primary_key, - exists); - if (!ok) - return false; - if (!exists) { - // Delete stale index data entry and continue. - leveldb_transaction->Remove(it->Key()); - it->Next(); - continue; - } - found = true; - return true; - } -} - -bool IndexedDBBackingStore::GetPrimaryKeyViaIndex( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - const IndexedDBKey& key, - scoped_ptr<IndexedDBKey>* primary_key) { - IDB_TRACE("IndexedDBBackingStore::get_primary_key_via_index"); - if (!KeyPrefix::ValidIds(database_id, object_store_id, index_id)) - return false; - - bool found = false; - std::vector<char> found_encoded_primary_key; - bool ok = FindKeyInIndex(transaction, - database_id, - object_store_id, - index_id, - key, - found_encoded_primary_key, - found); - if (!ok) { - INTERNAL_READ_ERROR(GET_PRIMARY_KEY_VIA_INDEX); - return false; - } - if (!found) - return true; - if (!found_encoded_primary_key.size()) { - INTERNAL_READ_ERROR(GET_PRIMARY_KEY_VIA_INDEX); - return false; - } - - DecodeIDBKey(&*found_encoded_primary_key.begin(), - &*found_encoded_primary_key.rbegin() + 1, - primary_key); - return true; -} - -bool IndexedDBBackingStore::KeyExistsInIndex( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - const IndexedDBKey& index_key, - scoped_ptr<IndexedDBKey>* found_primary_key, - bool& exists) { - IDB_TRACE("IndexedDBBackingStore::key_exists_in_index"); - if (!KeyPrefix::ValidIds(database_id, object_store_id, index_id)) - return false; - - exists = false; - std::vector<char> found_encoded_primary_key; - bool ok = FindKeyInIndex(transaction, - database_id, - object_store_id, - index_id, - index_key, - found_encoded_primary_key, - exists); - if (!ok) { - INTERNAL_READ_ERROR(KEY_EXISTS_IN_INDEX); - return false; - } - if (!exists) - return true; - if (!found_encoded_primary_key.size()) { - INTERNAL_READ_ERROR(KEY_EXISTS_IN_INDEX); - return false; - } - - DecodeIDBKey(&*found_encoded_primary_key.begin(), - &*found_encoded_primary_key.rbegin() + 1, - found_primary_key); - return true; -} - -IndexedDBBackingStore::Cursor::Cursor( - const IndexedDBBackingStore::Cursor* other) - : transaction_(other->transaction_), - cursor_options_(other->cursor_options_), - current_key_(new IndexedDBKey(*other->current_key_)) { - if (other->iterator_) { - iterator_ = transaction_->CreateIterator(); - - if (other->iterator_->IsValid()) { - iterator_->Seek(other->iterator_->Key()); - DCHECK(iterator_->IsValid()); - } - } -} - -IndexedDBBackingStore::Cursor::Cursor(LevelDBTransaction* transaction, - const CursorOptions& cursor_options) - : transaction_(transaction), cursor_options_(cursor_options) {} -IndexedDBBackingStore::Cursor::~Cursor() {} - -bool IndexedDBBackingStore::Cursor::FirstSeek() { - iterator_ = transaction_->CreateIterator(); - if (cursor_options_.forward) - iterator_->Seek(LevelDBSlice(cursor_options_.low_key)); - else - iterator_->Seek(LevelDBSlice(cursor_options_.high_key)); - - return ContinueFunction(0, READY); -} - -bool IndexedDBBackingStore::Cursor::Advance(unsigned long count) { - while (count--) { - if (!ContinueFunction()) - return false; - } - return true; -} - -bool IndexedDBBackingStore::Cursor::ContinueFunction(const IndexedDBKey* key, - IteratorState next_state) { - // TODO(alecflett): avoid a copy here? - IndexedDBKey previous_key = current_key_ ? *current_key_ : IndexedDBKey(); - - bool first_iteration = true; - - // When iterating with PrevNoDuplicate, spec requires that the - // value we yield for each key is the first duplicate in forwards - // order. - IndexedDBKey last_duplicate_key; - - bool forward = cursor_options_.forward; - - for (;;) { - if (next_state == SEEK) { - // TODO(jsbell): Optimize seeking for reverse cursors as well. - if (first_iteration && key && key->IsValid() && forward) { - iterator_->Seek(LevelDBSlice(EncodeKey(*key))); - first_iteration = false; - } else if (forward) { - iterator_->Next(); - } else { - iterator_->Prev(); - } - } else { - next_state = SEEK; // for subsequent iterations - } - - if (!iterator_->IsValid()) { - if (!forward && last_duplicate_key.IsValid()) { - // We need to walk forward because we hit the end of - // the data. - forward = true; - continue; - } - - return false; - } - - if (IsPastBounds()) { - if (!forward && last_duplicate_key.IsValid()) { - // We need to walk forward because now we're beyond the - // bounds defined by the cursor. - forward = true; - continue; - } - - return false; - } - - if (!HaveEnteredRange()) - continue; - - // The row may not load because there's a stale entry in the - // index. This is not fatal. - if (!LoadCurrentRow()) - continue; - - if (key && key->IsValid()) { - if (forward) { - if (current_key_->IsLessThan(*key)) - continue; - } else { - if (key->IsLessThan(*current_key_)) - continue; - } - } - - if (cursor_options_.unique) { - if (previous_key.IsValid() && current_key_->IsEqual(previous_key)) { - // We should never be able to walk forward all the way - // to the previous key. - DCHECK(!last_duplicate_key.IsValid()); - continue; - } - - if (!forward) { - if (!last_duplicate_key.IsValid()) { - last_duplicate_key = *current_key_; - continue; - } - - // We need to walk forward because we hit the boundary - // between key ranges. - if (!last_duplicate_key.IsEqual(*current_key_)) { - forward = true; - continue; - } - - continue; - } - } - break; - } - - DCHECK(!last_duplicate_key.IsValid() || - (forward && last_duplicate_key.IsEqual(*current_key_))); - return true; -} - -bool IndexedDBBackingStore::Cursor::HaveEnteredRange() const { - if (cursor_options_.forward) { - int compare = CompareIndexKeys(iterator_->Key(), - LevelDBSlice(cursor_options_.low_key)); - if (cursor_options_.low_open) { - return compare > 0; - } - return compare >= 0; - } - int compare = CompareIndexKeys(iterator_->Key(), - LevelDBSlice(cursor_options_.high_key)); - if (cursor_options_.high_open) { - return compare < 0; - } - return compare <= 0; -} - -bool IndexedDBBackingStore::Cursor::IsPastBounds() const { - if (cursor_options_.forward) { - int compare = CompareIndexKeys(iterator_->Key(), - LevelDBSlice(cursor_options_.high_key)); - if (cursor_options_.high_open) { - return compare >= 0; - } - return compare > 0; - } - int compare = - CompareIndexKeys(iterator_->Key(), LevelDBSlice(cursor_options_.low_key)); - if (cursor_options_.low_open) { - return compare <= 0; - } - return compare < 0; -} - -const IndexedDBKey& IndexedDBBackingStore::Cursor::primary_key() const { - return *current_key_; -} - -const IndexedDBBackingStore::RecordIdentifier& -IndexedDBBackingStore::Cursor::record_identifier() const { - return record_identifier_; -} - -class ObjectStoreKeyCursorImpl : public IndexedDBBackingStore::Cursor { - public: - ObjectStoreKeyCursorImpl( - LevelDBTransaction* transaction, - const IndexedDBBackingStore::Cursor::CursorOptions& cursor_options) - : IndexedDBBackingStore::Cursor(transaction, cursor_options) {} - - virtual Cursor* Clone() OVERRIDE { - return new ObjectStoreKeyCursorImpl(this); - } - - // IndexedDBBackingStore::Cursor - virtual std::vector<char>* Value() OVERRIDE { - NOTREACHED(); - return NULL; - } - virtual bool LoadCurrentRow() OVERRIDE; - - protected: - virtual std::vector<char> EncodeKey(const IndexedDBKey& key) OVERRIDE { - return ObjectStoreDataKey::Encode( - cursor_options_.database_id, cursor_options_.object_store_id, key); - } - - private: - explicit ObjectStoreKeyCursorImpl(const ObjectStoreKeyCursorImpl* other) - : IndexedDBBackingStore::Cursor(other) {} -}; - -bool ObjectStoreKeyCursorImpl::LoadCurrentRow() { - const char* key_position = iterator_->Key().begin(); - const char* key_limit = iterator_->Key().end(); - - ObjectStoreDataKey object_store_data_key; - key_position = ObjectStoreDataKey::Decode( - key_position, key_limit, &object_store_data_key); - if (!key_position) { - INTERNAL_READ_ERROR(LOAD_CURRENT_ROW); - return false; - } - - current_key_ = object_store_data_key.user_key(); - - int64 version; - const char* value_position = DecodeVarInt( - iterator_->Value().begin(), iterator_->Value().end(), version); - if (!value_position) { - INTERNAL_READ_ERROR(LOAD_CURRENT_ROW); - return false; - } - - // TODO(jsbell): This re-encodes what was just decoded; try and optimize. - record_identifier_.Reset(EncodeIDBKey(*current_key_), version); - - return true; -} - -class ObjectStoreCursorImpl : public IndexedDBBackingStore::Cursor { - public: - ObjectStoreCursorImpl( - LevelDBTransaction* transaction, - const IndexedDBBackingStore::Cursor::CursorOptions& cursor_options) - : IndexedDBBackingStore::Cursor(transaction, cursor_options) {} - - virtual Cursor* Clone() OVERRIDE { return new ObjectStoreCursorImpl(this); } - - // IndexedDBBackingStore::Cursor - virtual std::vector<char>* Value() OVERRIDE { return ¤t_value_; } - virtual bool LoadCurrentRow() OVERRIDE; - - protected: - virtual std::vector<char> EncodeKey(const IndexedDBKey& key) OVERRIDE { - return ObjectStoreDataKey::Encode( - cursor_options_.database_id, cursor_options_.object_store_id, key); - } - - private: - explicit ObjectStoreCursorImpl(const ObjectStoreCursorImpl* other) - : IndexedDBBackingStore::Cursor(other), - current_value_(other->current_value_) {} - - std::vector<char> current_value_; -}; - -bool ObjectStoreCursorImpl::LoadCurrentRow() { - const char* key_position = iterator_->Key().begin(); - const char* key_limit = iterator_->Key().end(); - - ObjectStoreDataKey object_store_data_key; - key_position = ObjectStoreDataKey::Decode( - key_position, key_limit, &object_store_data_key); - if (!key_position) { - INTERNAL_READ_ERROR(LOAD_CURRENT_ROW); - return false; - } - - current_key_ = object_store_data_key.user_key(); - - int64 version; - const char* value_position = DecodeVarInt( - iterator_->Value().begin(), iterator_->Value().end(), version); - if (!value_position) { - INTERNAL_READ_ERROR(LOAD_CURRENT_ROW); - return false; - } - - // TODO(jsbell): This re-encodes what was just decoded; try and optimize. - record_identifier_.Reset(EncodeIDBKey(*current_key_), version); - - std::vector<char> value; - value.insert(value.end(), value_position, iterator_->Value().end()); - current_value_.swap(value); - return true; -} - -class IndexKeyCursorImpl : public IndexedDBBackingStore::Cursor { - public: - IndexKeyCursorImpl( - LevelDBTransaction* transaction, - const IndexedDBBackingStore::Cursor::CursorOptions& cursor_options) - : IndexedDBBackingStore::Cursor(transaction, cursor_options) {} - - virtual Cursor* Clone() OVERRIDE { return new IndexKeyCursorImpl(this); } - - // IndexedDBBackingStore::Cursor - virtual std::vector<char>* Value() OVERRIDE { - NOTREACHED(); - return NULL; - } - virtual const IndexedDBKey& primary_key() const OVERRIDE { - return *primary_key_; - } - virtual const IndexedDBBackingStore::RecordIdentifier& RecordIdentifier() - const { - NOTREACHED(); - return record_identifier_; - } - virtual bool LoadCurrentRow() OVERRIDE; - - protected: - virtual std::vector<char> EncodeKey(const IndexedDBKey& key) OVERRIDE { - return IndexDataKey::Encode(cursor_options_.database_id, - cursor_options_.object_store_id, - cursor_options_.index_id, - key); - } - - private: - explicit IndexKeyCursorImpl(const IndexKeyCursorImpl* other) - : IndexedDBBackingStore::Cursor(other), - primary_key_(new IndexedDBKey(*other->primary_key_)) {} - - scoped_ptr<IndexedDBKey> primary_key_; -}; - -bool IndexKeyCursorImpl::LoadCurrentRow() { - const char* key_position = iterator_->Key().begin(); - const char* key_limit = iterator_->Key().end(); - - IndexDataKey index_data_key; - key_position = IndexDataKey::Decode(key_position, key_limit, &index_data_key); - - current_key_ = index_data_key.user_key(); - DCHECK(current_key_); - - int64 index_data_version; - const char* value_position = DecodeVarInt( - iterator_->Value().begin(), iterator_->Value().end(), index_data_version); - if (!value_position) { - INTERNAL_READ_ERROR(LOAD_CURRENT_ROW); - return false; - } - - value_position = - DecodeIDBKey(value_position, iterator_->Value().end(), &primary_key_); - if (!value_position) { - INTERNAL_READ_ERROR(LOAD_CURRENT_ROW); - return false; - } - - std::vector<char> primary_leveldb_key = - ObjectStoreDataKey::Encode(index_data_key.DatabaseId(), - index_data_key.ObjectStoreId(), - *primary_key_); - - std::vector<char> result; - bool found = false; - bool ok = transaction_->Get(LevelDBSlice(primary_leveldb_key), result, found); - if (!ok) { - INTERNAL_READ_ERROR(LOAD_CURRENT_ROW); - return false; - } - if (!found) { - transaction_->Remove(iterator_->Key()); - return false; - } - if (!result.size()) { - INTERNAL_READ_ERROR(LOAD_CURRENT_ROW); - return false; - } - - int64 object_store_data_version; - const char* t = DecodeVarInt( - &*result.begin(), &*result.rbegin() + 1, object_store_data_version); - if (!t) { - INTERNAL_READ_ERROR(LOAD_CURRENT_ROW); - return false; - } - - if (object_store_data_version != index_data_version) { - transaction_->Remove(iterator_->Key()); - return false; - } - - return true; -} - -class IndexCursorImpl : public IndexedDBBackingStore::Cursor { - public: - IndexCursorImpl( - LevelDBTransaction* transaction, - const IndexedDBBackingStore::Cursor::CursorOptions& cursor_options) - : IndexedDBBackingStore::Cursor(transaction, cursor_options) {} - - virtual Cursor* Clone() OVERRIDE { return new IndexCursorImpl(this); } - - // IndexedDBBackingStore::Cursor - virtual std::vector<char>* Value() OVERRIDE { return ¤t_value_; } - virtual const IndexedDBKey& primary_key() const OVERRIDE { - return *primary_key_; - } - virtual const IndexedDBBackingStore::RecordIdentifier& RecordIdentifier() - const { - NOTREACHED(); - return record_identifier_; - } - virtual bool LoadCurrentRow() OVERRIDE; - - protected: - virtual std::vector<char> EncodeKey(const IndexedDBKey& key) OVERRIDE { - return IndexDataKey::Encode(cursor_options_.database_id, - cursor_options_.object_store_id, - cursor_options_.index_id, - key); - } - - private: - explicit IndexCursorImpl(const IndexCursorImpl* other) - : IndexedDBBackingStore::Cursor(other), - primary_key_(new IndexedDBKey(*other->primary_key_)), - current_value_(other->current_value_), - primary_leveldb_key_(other->primary_leveldb_key_) {} - - scoped_ptr<IndexedDBKey> primary_key_; - std::vector<char> current_value_; - std::vector<char> primary_leveldb_key_; -}; - -bool IndexCursorImpl::LoadCurrentRow() { - const char* key_position = iterator_->Key().begin(); - const char* key_limit = iterator_->Key().end(); - - IndexDataKey index_data_key; - key_position = IndexDataKey::Decode(key_position, key_limit, &index_data_key); - - current_key_ = index_data_key.user_key(); - DCHECK(current_key_); - - const char* value_position = iterator_->Value().begin(); - const char* value_limit = iterator_->Value().end(); - - int64 index_data_version; - value_position = - DecodeVarInt(value_position, value_limit, index_data_version); - if (!value_position) { - INTERNAL_READ_ERROR(LOAD_CURRENT_ROW); - return false; - } - value_position = DecodeIDBKey(value_position, value_limit, &primary_key_); - if (!value_position) { - INTERNAL_READ_ERROR(LOAD_CURRENT_ROW); - return false; - } - - primary_leveldb_key_ = - ObjectStoreDataKey::Encode(index_data_key.DatabaseId(), - index_data_key.ObjectStoreId(), - *primary_key_); - - std::vector<char> result; - bool found = false; - bool ok = - transaction_->Get(LevelDBSlice(primary_leveldb_key_), result, found); - if (!ok) { - INTERNAL_READ_ERROR(LOAD_CURRENT_ROW); - return false; - } - if (!found) { - transaction_->Remove(iterator_->Key()); - return false; - } - if (!result.size()) { - INTERNAL_READ_ERROR(LOAD_CURRENT_ROW); - return false; - } - - int64 object_store_data_version; - value_position = DecodeVarInt( - &*result.begin(), &*result.rbegin() + 1, object_store_data_version); - if (!value_position) { - INTERNAL_READ_ERROR(LOAD_CURRENT_ROW); - return false; - } - - if (object_store_data_version != index_data_version) { - transaction_->Remove(iterator_->Key()); - return false; - } - - // TODO(jsbell): Make value_position an iterator. - std::vector<char> value; - value.insert(value.end(), - value_position, - static_cast<const char*>(&*result.rbegin()) + 1); - current_value_.swap(value); - return true; -} - -bool ObjectStoreCursorOptions( - LevelDBTransaction* transaction, - int64 database_id, - int64 object_store_id, - const IndexedDBKeyRange& range, - indexed_db::CursorDirection direction, - IndexedDBBackingStore::Cursor::CursorOptions& cursor_options) { - cursor_options.database_id = database_id; - cursor_options.object_store_id = object_store_id; - - bool lower_bound = range.lower().IsValid(); - bool upper_bound = range.upper().IsValid(); - cursor_options.forward = (direction == indexed_db::CURSOR_NEXT_NO_DUPLICATE || - direction == indexed_db::CURSOR_NEXT); - cursor_options.unique = (direction == indexed_db::CURSOR_NEXT_NO_DUPLICATE || - direction == indexed_db::CURSOR_PREV_NO_DUPLICATE); - - if (!lower_bound) { - cursor_options.low_key = - ObjectStoreDataKey::Encode(database_id, object_store_id, MinIDBKey()); - cursor_options.low_open = true; // Not included. - } else { - cursor_options.low_key = - ObjectStoreDataKey::Encode(database_id, object_store_id, range.lower()); - cursor_options.low_open = range.lowerOpen(); - } - - if (!upper_bound) { - cursor_options.high_key = - ObjectStoreDataKey::Encode(database_id, object_store_id, MaxIDBKey()); - - if (cursor_options.forward) { - cursor_options.high_open = true; // Not included. - } else { - // We need a key that exists. - if (!FindGreatestKeyLessThanOrEqual( - transaction, cursor_options.high_key, cursor_options.high_key)) - return false; - cursor_options.high_open = false; - } - } else { - cursor_options.high_key = - ObjectStoreDataKey::Encode(database_id, object_store_id, range.upper()); - cursor_options.high_open = range.upperOpen(); - - if (!cursor_options.forward) { - // For reverse cursors, we need a key that exists. - std::vector<char> found_high_key; - if (!FindGreatestKeyLessThanOrEqual( - transaction, cursor_options.high_key, found_high_key)) - return false; - - // If the target key should not be included, but we end up with a smaller - // key, we should include that. - if (cursor_options.high_open && - CompareIndexKeys(LevelDBSlice(found_high_key), - LevelDBSlice(cursor_options.high_key)) < - 0) - cursor_options.high_open = false; - - cursor_options.high_key = found_high_key; - } - } - - return true; -} - -bool IndexCursorOptions( - LevelDBTransaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - const IndexedDBKeyRange& range, - indexed_db::CursorDirection direction, - IndexedDBBackingStore::Cursor::CursorOptions& cursor_options) { - DCHECK(transaction); - if (!KeyPrefix::ValidIds(database_id, object_store_id, index_id)) - return false; - - cursor_options.database_id = database_id; - cursor_options.object_store_id = object_store_id; - cursor_options.index_id = index_id; - - bool lower_bound = range.lower().IsValid(); - bool upper_bound = range.upper().IsValid(); - cursor_options.forward = (direction == indexed_db::CURSOR_NEXT_NO_DUPLICATE || - direction == indexed_db::CURSOR_NEXT); - cursor_options.unique = (direction == indexed_db::CURSOR_NEXT_NO_DUPLICATE || - direction == indexed_db::CURSOR_PREV_NO_DUPLICATE); - - if (!lower_bound) { - cursor_options.low_key = - IndexDataKey::EncodeMinKey(database_id, object_store_id, index_id); - cursor_options.low_open = false; // Included. - } else { - cursor_options.low_key = IndexDataKey::Encode( - database_id, object_store_id, index_id, range.lower()); - cursor_options.low_open = range.lowerOpen(); - } - - if (!upper_bound) { - cursor_options.high_key = - IndexDataKey::EncodeMaxKey(database_id, object_store_id, index_id); - cursor_options.high_open = false; // Included. - - if (!cursor_options.forward) { // We need a key that exists. - if (!FindGreatestKeyLessThanOrEqual( - transaction, cursor_options.high_key, cursor_options.high_key)) - return false; - cursor_options.high_open = false; - } - } else { - cursor_options.high_key = IndexDataKey::Encode( - database_id, object_store_id, index_id, range.upper()); - cursor_options.high_open = range.upperOpen(); - - std::vector<char> found_high_key; - if (!FindGreatestKeyLessThanOrEqual( - transaction, - cursor_options.high_key, - found_high_key)) // Seek to the *last* key in the set of non-unique - // keys. - return false; - - // If the target key should not be included, but we end up with a smaller - // key, we should include that. - if (cursor_options.high_open && - CompareIndexKeys(LevelDBSlice(found_high_key), - LevelDBSlice(cursor_options.high_key)) < - 0) - cursor_options.high_open = false; - - cursor_options.high_key = found_high_key; - } - - return true; -} - -scoped_ptr<IndexedDBBackingStore::Cursor> -IndexedDBBackingStore::OpenObjectStoreCursor( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - const IndexedDBKeyRange& range, - indexed_db::CursorDirection direction) { - IDB_TRACE("IndexedDBBackingStore::open_object_store_cursor"); - LevelDBTransaction* leveldb_transaction = - IndexedDBBackingStore::Transaction::LevelDBTransactionFrom(transaction); - IndexedDBBackingStore::Cursor::CursorOptions cursor_options; - if (!ObjectStoreCursorOptions(leveldb_transaction, - database_id, - object_store_id, - range, - direction, - cursor_options)) - return scoped_ptr<IndexedDBBackingStore::Cursor>(); - scoped_ptr<ObjectStoreCursorImpl> cursor( - new ObjectStoreCursorImpl(leveldb_transaction, cursor_options)); - if (!cursor->FirstSeek()) - return scoped_ptr<IndexedDBBackingStore::Cursor>(); - - return cursor.PassAs<IndexedDBBackingStore::Cursor>(); -} - -scoped_ptr<IndexedDBBackingStore::Cursor> -IndexedDBBackingStore::OpenObjectStoreKeyCursor( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - const IndexedDBKeyRange& range, - indexed_db::CursorDirection direction) { - IDB_TRACE("IndexedDBBackingStore::open_object_store_key_cursor"); - LevelDBTransaction* leveldb_transaction = - IndexedDBBackingStore::Transaction::LevelDBTransactionFrom(transaction); - IndexedDBBackingStore::Cursor::CursorOptions cursor_options; - if (!ObjectStoreCursorOptions(leveldb_transaction, - database_id, - object_store_id, - range, - direction, - cursor_options)) - return scoped_ptr<IndexedDBBackingStore::Cursor>(); - scoped_ptr<ObjectStoreKeyCursorImpl> cursor( - new ObjectStoreKeyCursorImpl(leveldb_transaction, cursor_options)); - if (!cursor->FirstSeek()) - return scoped_ptr<IndexedDBBackingStore::Cursor>(); - - return cursor.PassAs<IndexedDBBackingStore::Cursor>(); -} - -scoped_ptr<IndexedDBBackingStore::Cursor> -IndexedDBBackingStore::OpenIndexKeyCursor( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - const IndexedDBKeyRange& range, - indexed_db::CursorDirection direction) { - IDB_TRACE("IndexedDBBackingStore::open_index_key_cursor"); - LevelDBTransaction* leveldb_transaction = - IndexedDBBackingStore::Transaction::LevelDBTransactionFrom(transaction); - IndexedDBBackingStore::Cursor::CursorOptions cursor_options; - if (!IndexCursorOptions(leveldb_transaction, - database_id, - object_store_id, - index_id, - range, - direction, - cursor_options)) - return scoped_ptr<IndexedDBBackingStore::Cursor>(); - scoped_ptr<IndexKeyCursorImpl> cursor( - new IndexKeyCursorImpl(leveldb_transaction, cursor_options)); - if (!cursor->FirstSeek()) - return scoped_ptr<IndexedDBBackingStore::Cursor>(); - - return cursor.PassAs<IndexedDBBackingStore::Cursor>(); -} - -scoped_ptr<IndexedDBBackingStore::Cursor> -IndexedDBBackingStore::OpenIndexCursor( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - const IndexedDBKeyRange& range, - indexed_db::CursorDirection direction) { - IDB_TRACE("IndexedDBBackingStore::open_index_cursor"); - LevelDBTransaction* leveldb_transaction = - IndexedDBBackingStore::Transaction::LevelDBTransactionFrom(transaction); - IndexedDBBackingStore::Cursor::CursorOptions cursor_options; - if (!IndexCursorOptions(leveldb_transaction, - database_id, - object_store_id, - index_id, - range, - direction, - cursor_options)) - return scoped_ptr<IndexedDBBackingStore::Cursor>(); - scoped_ptr<IndexCursorImpl> cursor( - new IndexCursorImpl(leveldb_transaction, cursor_options)); - if (!cursor->FirstSeek()) - return scoped_ptr<IndexedDBBackingStore::Cursor>(); - - return cursor.PassAs<IndexedDBBackingStore::Cursor>(); -} - -IndexedDBBackingStore::Transaction::Transaction( - IndexedDBBackingStore* backing_store) - : backing_store_(backing_store) {} - -IndexedDBBackingStore::Transaction::~Transaction() {} - -void IndexedDBBackingStore::Transaction::begin() { - IDB_TRACE("IndexedDBBackingStore::Transaction::begin"); - DCHECK(!transaction_); - transaction_ = LevelDBTransaction::Create(backing_store_->db_.get()); -} - -bool IndexedDBBackingStore::Transaction::Commit() { - IDB_TRACE("IndexedDBBackingStore::Transaction::commit"); - DCHECK(transaction_); - bool result = transaction_->Commit(); - transaction_ = NULL; - if (!result) - INTERNAL_WRITE_ERROR(TRANSACTION_COMMIT_METHOD); - return result; -} - -void IndexedDBBackingStore::Transaction::Rollback() { - IDB_TRACE("IndexedDBBackingStore::Transaction::rollback"); - DCHECK(transaction_); - transaction_->Rollback(); - transaction_ = NULL; -} - -} // namespace content diff --git a/content/browser/indexed_db/indexed_db_backing_store.h b/content/browser/indexed_db/indexed_db_backing_store.h deleted file mode 100644 index 6862d91..0000000 --- a/content/browser/indexed_db/indexed_db_backing_store.h +++ /dev/null @@ -1,319 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_BACKING_STORE_H_ -#define CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_BACKING_STORE_H_ - -#include <vector> - -#include "base/basictypes.h" -#include "base/files/file_path.h" -#include "base/memory/ref_counted.h" -#include "base/memory/scoped_ptr.h" -#include "base/memory/weak_ptr.h" -#include "content/browser/indexed_db/indexed_db.h" -#include "content/browser/indexed_db/indexed_db_metadata.h" -#include "content/browser/indexed_db/leveldb/leveldb_iterator.h" -#include "content/browser/indexed_db/leveldb/leveldb_transaction.h" -#include "content/common/content_export.h" -#include "content/common/indexed_db/indexed_db_key.h" -#include "content/common/indexed_db/indexed_db_key_path.h" -#include "content/common/indexed_db/indexed_db_key_range.h" - -namespace content { - -class LevelDBComparator; -class LevelDBDatabase; - -class LevelDBFactory { - public: - virtual scoped_ptr<LevelDBDatabase> OpenLevelDB( - const base::FilePath& file_name, - const LevelDBComparator* comparator) = 0; - virtual bool DestroyLevelDB(const base::FilePath& file_name) = 0; -}; - -class CONTENT_EXPORT IndexedDBBackingStore - : public base::RefCounted<IndexedDBBackingStore> { - public: - class CONTENT_EXPORT Transaction; - - static scoped_refptr<IndexedDBBackingStore> Open( - const string16& database_identifier, - const string16& path_base, - const string16& file_identifier); - static scoped_refptr<IndexedDBBackingStore> Open( - const string16& database_identifier, - const string16& path_base, - const string16& file_identifier, - LevelDBFactory* factory); - static scoped_refptr<IndexedDBBackingStore> OpenInMemory( - const string16& identifier); - static scoped_refptr<IndexedDBBackingStore> OpenInMemory( - const string16& identifier, - LevelDBFactory* factory); - base::WeakPtr<IndexedDBBackingStore> GetWeakPtr() { - return weak_factory_.GetWeakPtr(); - } - - virtual std::vector<string16> GetDatabaseNames(); - virtual bool GetIDBDatabaseMetaData(const string16& name, - IndexedDBDatabaseMetadata* metadata, - bool& success) WARN_UNUSED_RESULT; - virtual bool CreateIDBDatabaseMetaData(const string16& name, - const string16& version, - int64 int_version, - int64& row_id); - virtual bool UpdateIDBDatabaseMetaData( - IndexedDBBackingStore::Transaction* transaction, - int64 row_id, - const string16& version); - virtual bool UpdateIDBDatabaseIntVersion( - IndexedDBBackingStore::Transaction* transaction, - int64 row_id, - int64 int_version); - virtual bool DeleteDatabase(const string16& name); - - bool GetObjectStores(int64 database_id, - IndexedDBDatabaseMetadata::ObjectStoreMap* map) - WARN_UNUSED_RESULT; - virtual bool CreateObjectStore( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - const string16& name, - const IndexedDBKeyPath& key_path, - bool auto_increment); - virtual bool DeleteObjectStore( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id) WARN_UNUSED_RESULT; - - class CONTENT_EXPORT RecordIdentifier { - public: - RecordIdentifier(const std::vector<char>& primary_key, int64 version); - RecordIdentifier(); - ~RecordIdentifier(); - - const std::vector<char>& primary_key() const { return primary_key_; } - int64 version() const { return version_; } - void Reset(const std::vector<char>& primary_key, int64 version) { - primary_key_ = primary_key; - version_ = version; - } - - private: - std::vector<char> - primary_key_; // TODO(jsbell): Make it more clear that this is - // the *encoded* version of the key. - int64 version_; - DISALLOW_COPY_AND_ASSIGN(RecordIdentifier); - }; - - virtual bool GetRecord(IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - const IndexedDBKey& key, - std::vector<char>& record) WARN_UNUSED_RESULT; - virtual bool PutRecord(IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - const IndexedDBKey& key, - const std::vector<char>& value, - RecordIdentifier* record) WARN_UNUSED_RESULT; - virtual bool ClearObjectStore(IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id) WARN_UNUSED_RESULT; - virtual bool DeleteRecord(IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - const RecordIdentifier& record) WARN_UNUSED_RESULT; - virtual bool GetKeyGeneratorCurrentNumber( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64& current_number) WARN_UNUSED_RESULT; - virtual bool MaybeUpdateKeyGeneratorCurrentNumber( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 new_state, - bool check_current) WARN_UNUSED_RESULT; - virtual bool KeyExistsInObjectStore( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - const IndexedDBKey& key, - RecordIdentifier* found_record_identifier, - bool& found) WARN_UNUSED_RESULT; - - virtual bool CreateIndex(IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - const string16& name, - const IndexedDBKeyPath& key_path, - bool is_unique, - bool is_multi_entry) WARN_UNUSED_RESULT; - virtual bool DeleteIndex(IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id) WARN_UNUSED_RESULT; - virtual bool PutIndexDataForRecord( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - const IndexedDBKey& key, - const RecordIdentifier& record) WARN_UNUSED_RESULT; - virtual bool GetPrimaryKeyViaIndex( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - const IndexedDBKey& key, - scoped_ptr<IndexedDBKey>* primary_key) WARN_UNUSED_RESULT; - virtual bool KeyExistsInIndex(IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - const IndexedDBKey& key, - scoped_ptr<IndexedDBKey>* found_primary_key, - bool& exists) WARN_UNUSED_RESULT; - - class Cursor { - public: - virtual ~Cursor(); - - enum IteratorState { - READY = 0, - SEEK - }; - - struct CursorOptions { - CursorOptions(); - ~CursorOptions(); - int64 database_id; - int64 object_store_id; - int64 index_id; - std::vector<char> low_key; - bool low_open; - std::vector<char> high_key; - bool high_open; - bool forward; - bool unique; - }; - - const IndexedDBKey& key() const { return *current_key_; } - bool ContinueFunction(const IndexedDBKey* = 0, IteratorState = SEEK); - bool Advance(unsigned long); - bool FirstSeek(); - - virtual Cursor* Clone() = 0; - virtual const IndexedDBKey& primary_key() const; - virtual std::vector<char>* Value() = 0; - virtual const RecordIdentifier& record_identifier() const; - virtual bool LoadCurrentRow() = 0; - - protected: - Cursor(LevelDBTransaction* transaction, - const CursorOptions& cursor_options); - explicit Cursor(const IndexedDBBackingStore::Cursor* other); - - virtual std::vector<char> EncodeKey(const IndexedDBKey& key) = 0; - - bool IsPastBounds() const; - bool HaveEnteredRange() const; - - LevelDBTransaction* transaction_; - const CursorOptions cursor_options_; - scoped_ptr<LevelDBIterator> iterator_; - scoped_ptr<IndexedDBKey> current_key_; - IndexedDBBackingStore::RecordIdentifier record_identifier_; - }; - - virtual scoped_ptr<Cursor> OpenObjectStoreKeyCursor( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - const IndexedDBKeyRange& key_range, - indexed_db::CursorDirection); - virtual scoped_ptr<Cursor> OpenObjectStoreCursor( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - const IndexedDBKeyRange& key_range, - indexed_db::CursorDirection); - virtual scoped_ptr<Cursor> OpenIndexKeyCursor( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - const IndexedDBKeyRange& key_range, - indexed_db::CursorDirection); - virtual scoped_ptr<Cursor> OpenIndexCursor( - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - const IndexedDBKeyRange& key_range, - indexed_db::CursorDirection); - - class Transaction { - public: - explicit Transaction(IndexedDBBackingStore* backing_store); - ~Transaction(); - void begin(); - bool Commit(); - void Rollback(); - void Reset() { - backing_store_ = NULL; - transaction_ = NULL; - } - - static LevelDBTransaction* LevelDBTransactionFrom( - Transaction* transaction) { - return transaction->transaction_.get(); - } - - private: - IndexedDBBackingStore* backing_store_; - scoped_refptr<LevelDBTransaction> transaction_; - }; - - protected: - IndexedDBBackingStore(const string16& identifier, - scoped_ptr<LevelDBDatabase> db, - scoped_ptr<LevelDBComparator> comparator); - virtual ~IndexedDBBackingStore(); - friend class base::RefCounted<IndexedDBBackingStore>; - - private: - static scoped_refptr<IndexedDBBackingStore> Create( - const string16& identifier, - scoped_ptr<LevelDBDatabase> db, - scoped_ptr<LevelDBComparator> comparator); - - bool FindKeyInIndex(IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - const IndexedDBKey& key, - std::vector<char>& found_encoded_primary_key, - bool& found); - bool GetIndexes(int64 database_id, - int64 object_store_id, - IndexedDBObjectStoreMetadata::IndexMap* map) - WARN_UNUSED_RESULT; - - string16 identifier_; - - scoped_ptr<LevelDBDatabase> db_; - scoped_ptr<LevelDBComparator> comparator_; - base::WeakPtrFactory<IndexedDBBackingStore> weak_factory_; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_BACKING_STORE_H_ diff --git a/content/browser/indexed_db/indexed_db_backing_store_unittest.cc b/content/browser/indexed_db/indexed_db_backing_store_unittest.cc deleted file mode 100644 index 0e60d7b..0000000 --- a/content/browser/indexed_db/indexed_db_backing_store_unittest.cc +++ /dev/null @@ -1,403 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/indexed_db_backing_store.h" - -#include "base/files/scoped_temp_dir.h" -#include "base/logging.h" -#include "base/string16.h" -#include "base/strings/utf_string_conversions.h" -#include "content/browser/indexed_db/indexed_db_factory_impl.h" -#include "content/browser/indexed_db/indexed_db_leveldb_coding.h" -#include "testing/gtest/include/gtest/gtest.h" -#include "third_party/WebKit/Source/WebKit/chromium/public/WebSecurityOrigin.h" -#include "third_party/WebKit/public/platform/WebData.h" - -using WebKit::WebSecurityOrigin; -using WebKit::WebIDBKey; - -namespace content { - -namespace { - -class IndexedDBBackingStoreTest : public testing::Test { - public: - IndexedDBBackingStoreTest() {} - virtual void SetUp() { - string16 file_identifier; - backing_store_ = IndexedDBBackingStore::OpenInMemory(file_identifier); - - // useful keys and values during tests - const char raw_value1[] = "value1"; - - const char raw_value2[] = "value2"; - const char raw_value3[] = "value3"; - m_value1.insert( - m_value1.end(), &raw_value1[0], &raw_value1[0] + sizeof(raw_value1)); - m_value2.insert( - m_value2.end(), &raw_value2[0], &raw_value2[0] + sizeof(raw_value2)); - m_value3.insert( - m_value3.end(), &raw_value3[0], &raw_value3[0] + sizeof(raw_value3)); - m_key1 = IndexedDBKey(99, WebIDBKey::NumberType); - m_key2 = IndexedDBKey(ASCIIToUTF16("key2")); - m_key3 = IndexedDBKey(ASCIIToUTF16("key3")); - } - - protected: - scoped_refptr<IndexedDBBackingStore> backing_store_; - - // Sample keys and values that are consistent. - IndexedDBKey m_key1; - IndexedDBKey m_key2; - IndexedDBKey m_key3; - std::vector<char> m_value1; - std::vector<char> m_value2; - std::vector<char> m_value3; -}; - -TEST_F(IndexedDBBackingStoreTest, PutGetConsistency) { - { - IndexedDBBackingStore::Transaction transaction1(backing_store_.get()); - transaction1.begin(); - IndexedDBBackingStore::RecordIdentifier record; - bool ok = backing_store_->PutRecord( - &transaction1, 1, 1, m_key1, m_value1, &record); - EXPECT_TRUE(ok); - transaction1.Commit(); - } - - { - IndexedDBBackingStore::Transaction transaction2(backing_store_.get()); - transaction2.begin(); - std::vector<char> result_value; - bool ok = - backing_store_->GetRecord(&transaction2, 1, 1, m_key1, result_value); - transaction2.Commit(); - EXPECT_TRUE(ok); - EXPECT_EQ(m_value1, result_value); - } -} - -// Make sure that using very high ( more than 32 bit ) values for database_id -// and object_store_id still work. -TEST_F(IndexedDBBackingStoreTest, HighIds) { - const int64 high_database_id = 1ULL << 35; - const int64 high_object_store_id = 1ULL << 39; - // index_ids are capped at 32 bits for storage purposes. - const int64 high_index_id = 1ULL << 29; - - const int64 invalid_high_index_id = 1ULL << 37; - - const IndexedDBKey& index_key = m_key2; - std::vector<char> index_key_raw = EncodeIDBKey(index_key); - { - IndexedDBBackingStore::Transaction transaction1(backing_store_.get()); - transaction1.begin(); - IndexedDBBackingStore::RecordIdentifier record; - bool ok = backing_store_->PutRecord(&transaction1, - high_database_id, - high_object_store_id, - m_key1, - m_value1, - &record); - EXPECT_TRUE(ok); - - ok = backing_store_->PutIndexDataForRecord(&transaction1, - high_database_id, - high_object_store_id, - invalid_high_index_id, - index_key, - record); - EXPECT_FALSE(ok); - - ok = backing_store_->PutIndexDataForRecord(&transaction1, - high_database_id, - high_object_store_id, - high_index_id, - index_key, - record); - EXPECT_TRUE(ok); - - ok = transaction1.Commit(); - EXPECT_TRUE(ok); - } - - { - IndexedDBBackingStore::Transaction transaction2(backing_store_.get()); - transaction2.begin(); - std::vector<char> result_value; - bool ok = backing_store_->GetRecord(&transaction2, - high_database_id, - high_object_store_id, - m_key1, - result_value); - EXPECT_TRUE(ok); - EXPECT_EQ(m_value1, result_value); - - scoped_ptr<IndexedDBKey> new_primary_key; - ok = backing_store_->GetPrimaryKeyViaIndex(&transaction2, - high_database_id, - high_object_store_id, - invalid_high_index_id, - index_key, - &new_primary_key); - EXPECT_FALSE(ok); - - ok = backing_store_->GetPrimaryKeyViaIndex(&transaction2, - high_database_id, - high_object_store_id, - high_index_id, - index_key, - &new_primary_key); - EXPECT_TRUE(ok); - EXPECT_TRUE(new_primary_key->IsEqual(m_key1)); - - ok = transaction2.Commit(); - EXPECT_TRUE(ok); - } -} - -// Make sure that other invalid ids do not crash. -TEST_F(IndexedDBBackingStoreTest, InvalidIds) { - // valid ids for use when testing invalid ids - const int64 database_id = 1; - const int64 object_store_id = 1; - const int64 index_id = kMinimumIndexId; - const int64 invalid_low_index_id = 19; // index_ids must be > kMinimumIndexId - - std::vector<char> result_value; - - IndexedDBBackingStore::Transaction transaction1(backing_store_.get()); - transaction1.begin(); - - IndexedDBBackingStore::RecordIdentifier record; - bool ok = backing_store_->PutRecord(&transaction1, - database_id, - KeyPrefix::kInvalidId, - m_key1, - m_value1, - &record); - EXPECT_FALSE(ok); - ok = backing_store_->PutRecord( - &transaction1, database_id, 0, m_key1, m_value1, &record); - EXPECT_FALSE(ok); - ok = backing_store_->PutRecord(&transaction1, - KeyPrefix::kInvalidId, - object_store_id, - m_key1, - m_value1, - &record); - EXPECT_FALSE(ok); - ok = backing_store_->PutRecord( - &transaction1, 0, object_store_id, m_key1, m_value1, &record); - EXPECT_FALSE(ok); - - ok = backing_store_->GetRecord( - &transaction1, database_id, KeyPrefix::kInvalidId, m_key1, result_value); - EXPECT_FALSE(ok); - ok = backing_store_->GetRecord( - &transaction1, database_id, 0, m_key1, result_value); - EXPECT_FALSE(ok); - ok = backing_store_->GetRecord(&transaction1, - KeyPrefix::kInvalidId, - object_store_id, - m_key1, - result_value); - EXPECT_FALSE(ok); - ok = backing_store_->GetRecord( - &transaction1, 0, object_store_id, m_key1, result_value); - EXPECT_FALSE(ok); - - scoped_ptr<IndexedDBKey> new_primary_key; - ok = backing_store_->GetPrimaryKeyViaIndex(&transaction1, - database_id, - object_store_id, - KeyPrefix::kInvalidId, - m_key1, - &new_primary_key); - EXPECT_FALSE(ok); - ok = backing_store_->GetPrimaryKeyViaIndex(&transaction1, - database_id, - object_store_id, - invalid_low_index_id, - m_key1, - &new_primary_key); - EXPECT_FALSE(ok); - ok = backing_store_->GetPrimaryKeyViaIndex( - &transaction1, database_id, object_store_id, 0, m_key1, &new_primary_key); - EXPECT_FALSE(ok); - - ok = backing_store_->GetPrimaryKeyViaIndex(&transaction1, - KeyPrefix::kInvalidId, - object_store_id, - index_id, - m_key1, - &new_primary_key); - EXPECT_FALSE(ok); - ok = backing_store_->GetPrimaryKeyViaIndex(&transaction1, - database_id, - KeyPrefix::kInvalidId, - index_id, - m_key1, - &new_primary_key); - EXPECT_FALSE(ok); -} - -TEST_F(IndexedDBBackingStoreTest, CreateDatabase) { - const string16 database_name(ASCIIToUTF16("db1")); - int64 database_id; - const string16 version(ASCIIToUTF16("old_string_version")); - const int64 int_version = 9; - - const int64 object_store_id = 99; - const string16 object_store_name(ASCIIToUTF16("object_store1")); - const bool auto_increment = true; - const IndexedDBKeyPath object_store_key_path( - ASCIIToUTF16("object_store_key")); - - const int64 index_id = 999; - const string16 index_name(ASCIIToUTF16("index1")); - const bool unique = true; - const bool multi_entry = true; - const IndexedDBKeyPath index_key_path(ASCIIToUTF16("index_key")); - - { - bool ok = backing_store_->CreateIDBDatabaseMetaData( - database_name, version, int_version, database_id); - EXPECT_TRUE(ok); - EXPECT_GT(database_id, 0); - - IndexedDBBackingStore::Transaction transaction(backing_store_.get()); - transaction.begin(); - - ok = backing_store_->CreateObjectStore(&transaction, - database_id, - object_store_id, - object_store_name, - object_store_key_path, - auto_increment); - EXPECT_TRUE(ok); - - ok = backing_store_->CreateIndex(&transaction, - database_id, - object_store_id, - index_id, - index_name, - index_key_path, - unique, - multi_entry); - EXPECT_TRUE(ok); - - ok = transaction.Commit(); - EXPECT_TRUE(ok); - } - - { - IndexedDBDatabaseMetadata database; - bool found; - bool ok = - backing_store_->GetIDBDatabaseMetaData(database_name, &database, found); - EXPECT_TRUE(ok); - EXPECT_TRUE(found); - - // database.name is not filled in by the implementation. - EXPECT_EQ(version, database.version); - EXPECT_EQ(int_version, database.int_version); - EXPECT_EQ(database_id, database.id); - - ok = backing_store_->GetObjectStores(database.id, &database.object_stores); - EXPECT_TRUE(ok); - - EXPECT_EQ(1UL, database.object_stores.size()); - IndexedDBObjectStoreMetadata object_store = - database.object_stores[object_store_id]; - EXPECT_EQ(object_store_name, object_store.name); - EXPECT_EQ(object_store_key_path, object_store.key_path); - EXPECT_EQ(auto_increment, object_store.auto_increment); - - EXPECT_EQ(1UL, object_store.indexes.size()); - IndexedDBIndexMetadata index = object_store.indexes[index_id]; - EXPECT_EQ(index_name, index.name); - EXPECT_EQ(index_key_path, index.key_path); - EXPECT_EQ(unique, index.unique); - EXPECT_EQ(multi_entry, index.multi_entry); - } -} - -class MockIDBFactory : public IndexedDBFactoryImpl { - public: - static scoped_refptr<MockIDBFactory> Create() { - return make_scoped_refptr(new MockIDBFactory()); - } - - scoped_refptr<IndexedDBBackingStore> TestOpenBackingStore( - const WebSecurityOrigin& origin, - const base::FilePath& data_directory) { - string16 path = UTF8ToUTF16(data_directory.AsUTF8Unsafe()); - return OpenBackingStore(origin.databaseIdentifier(), path); - } - - private: - virtual ~MockIDBFactory() {} -}; - -TEST(IndexedDBFactoryTest, BackingStoreLifetime) { - WebSecurityOrigin origin1 = - WebSecurityOrigin::createFromString("http://localhost:81"); - WebSecurityOrigin origin2 = - WebSecurityOrigin::createFromString("http://localhost:82"); - - scoped_refptr<MockIDBFactory> factory = MockIDBFactory::Create(); - - base::ScopedTempDir temp_directory; - ASSERT_TRUE(temp_directory.CreateUniqueTempDir()); - scoped_refptr<IndexedDBBackingStore> disk_store1 = - factory->TestOpenBackingStore(origin1, temp_directory.path()); - EXPECT_TRUE(disk_store1->HasOneRef()); - - scoped_refptr<IndexedDBBackingStore> disk_store2 = - factory->TestOpenBackingStore(origin1, temp_directory.path()); - EXPECT_EQ(disk_store1.get(), disk_store2.get()); - // TODO(alecflett): Verify refcount indirectly. - // EXPECT_EQ(2, disk_store2->RefCount()); - - scoped_refptr<IndexedDBBackingStore> disk_store3 = - factory->TestOpenBackingStore(origin2, temp_directory.path()); - EXPECT_TRUE(disk_store3->HasOneRef()); - // TODO(alecflett): Verify refcount indirectly. - // EXPECT_EQ(2, disk_store1->RefCount()); -} - -TEST(IndexedDBFactoryTest, MemoryBackingStoreLifetime) { - WebSecurityOrigin origin1 = - WebSecurityOrigin::createFromString("http://localhost:81"); - WebSecurityOrigin origin2 = - WebSecurityOrigin::createFromString("http://localhost:82"); - - scoped_refptr<MockIDBFactory> factory = MockIDBFactory::Create(); - scoped_refptr<IndexedDBBackingStore> mem_store1 = - factory->TestOpenBackingStore(origin1, base::FilePath()); - // TODO(alecflett): Verify refcount indirectly. - // EXPECT_EQ(2, mem_store1->RefCount()); - scoped_refptr<IndexedDBBackingStore> mem_store2 = - factory->TestOpenBackingStore(origin1, base::FilePath()); - EXPECT_EQ(mem_store1.get(), mem_store2.get()); - // TODO(alecflett): Verify refcount indirectly. - // EXPECT_EQ(3, mem_store2->RefCount()); - - scoped_refptr<IndexedDBBackingStore> mem_store3 = - factory->TestOpenBackingStore(origin2, base::FilePath()); - // TODO(alecflett): Verify refcount indirectly. - // EXPECT_EQ(2, mem_store3->RefCount()); - // EXPECT_EQ(3, mem_store1->RefCount()); - - factory = NULL; - // TODO(alecflett): Verify refcount indirectly. - // EXPECT_EQ(2, mem_store1->RefCount()); - // EXPECT_EQ(1, mem_store3->RefCount()); -} - -} // namespace - -} // namespace content diff --git a/content/browser/indexed_db/indexed_db_callbacks_wrapper.cc b/content/browser/indexed_db/indexed_db_callbacks_wrapper.cc deleted file mode 100644 index 1c34878..0000000 --- a/content/browser/indexed_db/indexed_db_callbacks_wrapper.cc +++ /dev/null @@ -1,216 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/indexed_db_callbacks_wrapper.h" - -#include "content/browser/indexed_db/indexed_db_cursor.h" -#include "content/browser/indexed_db/indexed_db_metadata.h" -#include "content/browser/indexed_db/webidbcursor_impl.h" -#include "content/browser/indexed_db/webidbdatabase_impl.h" -#include "third_party/WebKit/public/platform/WebData.h" -#include "third_party/WebKit/public/platform/WebIDBDatabaseError.h" -#include "third_party/WebKit/public/platform/WebIDBKey.h" -#include "third_party/WebKit/public/platform/WebIDBMetadata.h" -#include "third_party/WebKit/public/platform/WebString.h" -#include "third_party/WebKit/public/platform/WebVector.h" - -namespace content { - -using WebKit::WebData; -using WebKit::WebIDBKey; -using WebKit::WebIDBMetadata; -using WebKit::WebString; -using WebKit::WebVector; - -IndexedDBCallbacksWrapper::IndexedDBCallbacksWrapper( - WebKit::WebIDBCallbacks* callbacks) - : callbacks_(callbacks), did_complete_(false), did_create_proxy_(false) {} - -IndexedDBCallbacksWrapper::~IndexedDBCallbacksWrapper() {} - -void IndexedDBCallbacksWrapper::OnError( - scoped_refptr<IndexedDBDatabaseError> error) { - DCHECK(callbacks_); - callbacks_->onError( - WebKit::WebIDBDatabaseError(error->code(), error->message())); - callbacks_.reset(); -} - -void IndexedDBCallbacksWrapper::OnSuccess(const std::vector<string16>& value) { - DCHECK(callbacks_); - callbacks_->onSuccess(WebVector<WebString>(value)); - callbacks_.reset(); -} - -void IndexedDBCallbacksWrapper::OnSuccess(scoped_refptr<IndexedDBCursor> cursor, - const IndexedDBKey& key, - const IndexedDBKey& primary_key, - std::vector<char>* value) { - DCHECK(callbacks_); - WebData web_value; - if (value && value->size()) - web_value.assign(&value->front(), value->size()); - callbacks_->onSuccess( - new WebIDBCursorImpl(cursor), WebIDBKey(key), primary_key, web_value); - callbacks_.reset(); -} - -void IndexedDBCallbacksWrapper::OnSuccess(const IndexedDBKey& key) { - DCHECK(callbacks_); - callbacks_->onSuccess(WebIDBKey(key)); - callbacks_.reset(); -} - -void IndexedDBCallbacksWrapper::OnSuccess(std::vector<char>* value) { - WebData web_value; - if (value && value->size()) - web_value.assign(&value->front(), value->size()); - - DCHECK(callbacks_); - callbacks_->onSuccess(web_value); - callbacks_.reset(); -} - -void IndexedDBCallbacksWrapper::OnSuccess(std::vector<char>* value, - const IndexedDBKey& key, - const IndexedDBKeyPath& key_path) { - WebData web_value; - if (value && value->size()) - web_value.assign(&value->front(), value->size()); - DCHECK(callbacks_); - callbacks_->onSuccess(web_value, WebIDBKey(key), key_path); - callbacks_.reset(); -} - -void IndexedDBCallbacksWrapper::OnSuccess(int64 value) { - DCHECK(callbacks_); - callbacks_->onSuccess(value); - callbacks_.reset(); -} - -void IndexedDBCallbacksWrapper::OnSuccess() { - DCHECK(callbacks_); - callbacks_->onSuccess(); - callbacks_.reset(); -} - -void IndexedDBCallbacksWrapper::OnSuccess(const IndexedDBKey& key, - const IndexedDBKey& primary_key, - std::vector<char>* value) { - WebData web_value; - if (value && value->size()) - web_value.assign(&value->front(), value->size()); - DCHECK(callbacks_); - callbacks_->onSuccess(key, primary_key, web_value); - callbacks_.reset(); -} - -void IndexedDBCallbacksWrapper::OnSuccessWithPrefetch( - const std::vector<IndexedDBKey>& keys, - const std::vector<IndexedDBKey>& primary_keys, - const std::vector<std::vector<char> >& values) { - DCHECK_EQ(keys.size(), primary_keys.size()); - DCHECK_EQ(keys.size(), values.size()); - - std::vector<WebIDBKey> web_keys(keys.size()); - std::vector<WebIDBKey> web_primary_keys(primary_keys.size()); - std::vector<WebData> web_values(values.size()); - for (size_t i = 0; i < keys.size(); ++i) { - web_keys[i] = keys[i]; - web_primary_keys[i] = primary_keys[i]; - if (values[i].size()) - web_values[i].assign(&values[i].front(), values[i].size()); - } - - DCHECK(callbacks_); - callbacks_->onSuccessWithPrefetch(web_keys, web_primary_keys, web_values); - callbacks_.reset(); -} - -void IndexedDBCallbacksWrapper::OnBlocked(int64 existing_version) { - DCHECK(callbacks_); - callbacks_->onBlocked(existing_version); -} - -WebIDBMetadata ConvertMetadata(const IndexedDBDatabaseMetadata& idb_metadata) { - WebIDBMetadata web_metadata; - web_metadata.id = idb_metadata.id; - web_metadata.name = idb_metadata.name; - web_metadata.version = idb_metadata.version; - web_metadata.intVersion = idb_metadata.int_version; - web_metadata.maxObjectStoreId = idb_metadata.max_object_store_id; - web_metadata.objectStores = - WebVector<WebIDBMetadata::ObjectStore>(idb_metadata.object_stores.size()); - - size_t i = 0; - for (IndexedDBDatabaseMetadata::ObjectStoreMap::const_iterator - it = idb_metadata.object_stores.begin(); - it != idb_metadata.object_stores.end(); - ++it, ++i) { - const IndexedDBObjectStoreMetadata& idb_store_metadata = it->second; - WebIDBMetadata::ObjectStore& web_store_metadata = - web_metadata.objectStores[i]; - - web_store_metadata.id = idb_store_metadata.id; - web_store_metadata.name = idb_store_metadata.name; - web_store_metadata.keyPath = idb_store_metadata.key_path; - web_store_metadata.autoIncrement = idb_store_metadata.auto_increment; - web_store_metadata.maxIndexId = idb_store_metadata.max_index_id; - web_store_metadata.indexes = - WebVector<WebIDBMetadata::Index>(idb_store_metadata.indexes.size()); - - size_t j = 0; - for (IndexedDBObjectStoreMetadata::IndexMap::const_iterator - it2 = idb_store_metadata.indexes.begin(); - it2 != idb_store_metadata.indexes.end(); - ++it2, ++j) { - const IndexedDBIndexMetadata& idb_index_metadata = it2->second; - WebIDBMetadata::Index& web_index_metadata = web_store_metadata.indexes[j]; - - web_index_metadata.id = idb_index_metadata.id; - web_index_metadata.name = idb_index_metadata.name; - web_index_metadata.keyPath = idb_index_metadata.key_path; - web_index_metadata.unique = idb_index_metadata.unique; - web_index_metadata.multiEntry = idb_index_metadata.multi_entry; - } - } - - return web_metadata; -} - -void IndexedDBCallbacksWrapper::OnUpgradeNeeded( - int64 old_version, - scoped_refptr<IndexedDBDatabase> database, - const IndexedDBDatabaseMetadata& metadata) { - DCHECK(callbacks_); - WebIDBMetadata web_metadata = ConvertMetadata(metadata); - did_create_proxy_ = true; - callbacks_->onUpgradeNeeded( - old_version, - new WebIDBDatabaseImpl(database, database_callbacks_), - web_metadata); - database_callbacks_ = NULL; -} - -void IndexedDBCallbacksWrapper::OnSuccess( - scoped_refptr<IndexedDBDatabase> database, - const IndexedDBDatabaseMetadata& metadata) { - DCHECK(callbacks_); - WebIDBMetadata web_metadata = ConvertMetadata(metadata); - scoped_refptr<IndexedDBCallbacksWrapper> self(this); - - WebIDBDatabaseImpl* impl = - did_create_proxy_ ? 0 - : new WebIDBDatabaseImpl(database, database_callbacks_); - database_callbacks_ = NULL; - - callbacks_->onSuccess(impl, web_metadata); - callbacks_.reset(); -} - -void IndexedDBCallbacksWrapper::SetDatabaseCallbacks( - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks) { - database_callbacks_ = database_callbacks; -} -} // namespace content diff --git a/content/browser/indexed_db/indexed_db_callbacks_wrapper.h b/content/browser/indexed_db/indexed_db_callbacks_wrapper.h deleted file mode 100644 index 7fdd4d5..0000000 --- a/content/browser/indexed_db/indexed_db_callbacks_wrapper.h +++ /dev/null @@ -1,95 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_CALLBACKS_WRAPPER_H_ -#define CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_CALLBACKS_WRAPPER_H_ - -#include <vector> - -#include "base/basictypes.h" -#include "base/logging.h" -#include "base/memory/ref_counted.h" -#include "base/memory/scoped_ptr.h" -#include "content/browser/indexed_db/indexed_db_database.h" -#include "content/browser/indexed_db/indexed_db_database_error.h" -#include "content/common/indexed_db/indexed_db_key.h" -#include "content/common/indexed_db/indexed_db_key_path.h" -#include "third_party/WebKit/public/platform/WebIDBCallbacks.h" - -namespace WebKit { -class WebIDBCallbacks; -} - -namespace content { -class IndexedDBCursor; -class WebIDBDatabaseImpl; - -class IndexedDBCallbacksWrapper - : public base::RefCounted<IndexedDBCallbacksWrapper> { - public: - static scoped_refptr<IndexedDBCallbacksWrapper> Create( - WebKit::WebIDBCallbacks* callbacks) { - return make_scoped_refptr(new IndexedDBCallbacksWrapper(callbacks)); - } - - virtual void OnError(scoped_refptr<IndexedDBDatabaseError> error); - // From IDBFactory.webkitGetDatabaseNames() - virtual void OnSuccess(const std::vector<string16>& string); - // From IDBObjectStore/IDBIndex.openCursor(), - // IDBIndex.openKeyCursor() - virtual void OnSuccess(scoped_refptr<IndexedDBCursor> cursor, - const IndexedDBKey& key, - const IndexedDBKey& primary_key, - std::vector<char>* value); - // From IDBObjectStore.add()/put(), IDBIndex.getKey() - virtual void OnSuccess(const IndexedDBKey& key); - // From IDBObjectStore/IDBIndex.get()/count(), and various methods - // that yield null/undefined. - virtual void OnSuccess(std::vector<char>* value); - // From IDBObjectStore/IDBIndex.get() (with key injection) - virtual void OnSuccess(std::vector<char>* data, - const IndexedDBKey& key, - const IndexedDBKeyPath& key_path); - // From IDBObjectStore/IDBIndex.count() - virtual void OnSuccess(int64 value); - - // From IDBFactor.deleteDatabase(), - // IDBObjectStore/IDBIndex.get(), IDBObjectStore.delete(), - // IDBObjectStore.clear() - virtual void OnSuccess(); - - // From IDBCursor.advance()/continue() - virtual void OnSuccess(const IndexedDBKey& key, - const IndexedDBKey& primary_key, - std::vector<char>* value); - // From IDBCursor.advance()/continue() - virtual void OnSuccessWithPrefetch( - const std::vector<IndexedDBKey>& keys, - const std::vector<IndexedDBKey>& primary_keys, - const std::vector<std::vector<char> >& values); - // From IDBFactory.open()/deleteDatabase() - virtual void OnBlocked(int64 /* existing_version */); - // From IDBFactory.open() - virtual void OnUpgradeNeeded(int64 /* old_version */, - scoped_refptr<IndexedDBDatabase> db, - const IndexedDBDatabaseMetadata& metadata); - virtual void OnSuccess(scoped_refptr<IndexedDBDatabase> db, - const IndexedDBDatabaseMetadata& metadata); - virtual void SetDatabaseCallbacks( - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks); - - private: - explicit IndexedDBCallbacksWrapper(WebKit::WebIDBCallbacks* callbacks); - virtual ~IndexedDBCallbacksWrapper(); - friend class base::RefCounted<IndexedDBCallbacksWrapper>; - scoped_ptr<WebIDBDatabaseImpl> web_database_impl_; - scoped_ptr<WebKit::WebIDBCallbacks> callbacks_; - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks_; - bool did_complete_; - bool did_create_proxy_; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_CALLBACKS_WRAPPER_H_ diff --git a/content/browser/indexed_db/indexed_db_cleanup_on_io_error_unittest.cc b/content/browser/indexed_db/indexed_db_cleanup_on_io_error_unittest.cc deleted file mode 100644 index af86147..0000000 --- a/content/browser/indexed_db/indexed_db_cleanup_on_io_error_unittest.cc +++ /dev/null @@ -1,74 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/files/file_path.h" -#include "base/files/scoped_temp_dir.h" -#include "base/string16.h" -#include "base/strings/utf_string_conversions.h" -#include "content/browser/indexed_db/indexed_db_backing_store.h" -#include "content/browser/indexed_db/leveldb/leveldb_database.h" -#include "testing/gtest/include/gtest/gtest.h" -#include "third_party/WebKit/Source/WebKit/chromium/public/WebSecurityOrigin.h" - -using WebKit::WebSecurityOrigin; -using content::IndexedDBBackingStore; -using content::LevelDBComparator; -using content::LevelDBDatabase; -using content::LevelDBFactory; -using content::LevelDBSlice; -using content::LevelDBSnapshot; - -namespace { - -class BustedLevelDBDatabase : public LevelDBDatabase { - public: - static scoped_ptr<LevelDBDatabase> Open( - const base::FilePath& file_name, - const LevelDBComparator* /*comparator*/) { - return scoped_ptr<LevelDBDatabase>(new BustedLevelDBDatabase); - } - virtual bool Get(const LevelDBSlice& key, - std::vector<char>& value, - bool& found, - const LevelDBSnapshot* = 0) OVERRIDE { - // false means IO error. - return false; - } -}; - -class MockLevelDBFactory : public LevelDBFactory { - public: - MockLevelDBFactory() : destroy_called_(false) {} - virtual scoped_ptr<LevelDBDatabase> OpenLevelDB( - const base::FilePath& file_name, - const LevelDBComparator* comparator) OVERRIDE { - return BustedLevelDBDatabase::Open(file_name, comparator); - } - virtual bool DestroyLevelDB(const base::FilePath& file_name) OVERRIDE { - EXPECT_FALSE(destroy_called_); - destroy_called_ = true; - return false; - } - virtual ~MockLevelDBFactory() { EXPECT_TRUE(destroy_called_); } - - private: - bool destroy_called_; -}; - -TEST(IndexedDBIOErrorTest, CleanUpTest) { - WebSecurityOrigin origin( - WebSecurityOrigin::createFromString("http://localhost:81")); - base::ScopedTempDir temp_directory; - ASSERT_TRUE(temp_directory.CreateUniqueTempDir()); - const base::FilePath path = temp_directory.path(); - string16 dummy_file_identifier; - MockLevelDBFactory mock_leveldb_factory; - scoped_refptr<IndexedDBBackingStore> backing_store = - IndexedDBBackingStore::Open(origin.databaseIdentifier(), - UTF8ToUTF16(path.AsUTF8Unsafe()), - dummy_file_identifier, - &mock_leveldb_factory); -} - -} // namespace diff --git a/content/browser/indexed_db/indexed_db_context_impl.cc b/content/browser/indexed_db/indexed_db_context_impl.cc index 0b61910..038ef94 100644 --- a/content/browser/indexed_db/indexed_db_context_impl.cc +++ b/content/browser/indexed_db/indexed_db_context_impl.cc @@ -14,7 +14,6 @@ #include "base/string_util.h" #include "base/utf_string_conversions.h" #include "content/browser/indexed_db/indexed_db_quota_client.h" -#include "content/browser/indexed_db/webidbfactory_impl.h" #include "content/public/browser/browser_thread.h" #include "content/public/browser/indexed_db_info.h" #include "content/public/common/content_switches.h" @@ -41,14 +40,15 @@ const base::FilePath::CharType IndexedDBContextImpl::kIndexedDBExtension[] = namespace { -void GetAllOriginsAndPaths(const base::FilePath& indexeddb_path, - std::vector<GURL>* origins, - std::vector<base::FilePath>* file_paths) { +void GetAllOriginsAndPaths( + const base::FilePath& indexeddb_path, + std::vector<GURL>* origins, + std::vector<base::FilePath>* file_paths) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); if (indexeddb_path.empty()) return; - file_util::FileEnumerator file_enumerator( - indexeddb_path, false, file_util::FileEnumerator::DIRECTORIES); + file_util::FileEnumerator file_enumerator(indexeddb_path, + false, file_util::FileEnumerator::DIRECTORIES); for (base::FilePath file_path = file_enumerator.Next(); !file_path.empty(); file_path = file_enumerator.Next()) { if (file_path.Extension() == IndexedDBContextImpl::kIndexedDBExtension) { @@ -74,8 +74,7 @@ void ClearSessionOnlyOrigins( std::vector<base::FilePath>::const_iterator file_path_iter = file_paths.begin(); for (std::vector<GURL>::const_iterator iter = origins.begin(); - iter != origins.end(); - ++iter, ++file_path_iter) { + iter != origins.end(); ++iter, ++file_path_iter) { if (!special_storage_policy->IsStorageSessionOnly(*iter)) continue; if (special_storage_policy->IsStorageProtected(*iter)) @@ -109,10 +108,7 @@ WebIDBFactory* IndexedDBContextImpl::GetIDBFactory() { // Prime our cache of origins with existing databases so we can // detect when dbs are newly created. GetOriginSet(); - if (CommandLine::ForCurrentProcess()->HasSwitch(switches::kNewIndexedDB)) - idb_factory_.reset(new content::WebIDBFactoryImpl()); - else - idb_factory_.reset(WebIDBFactory::create()); + idb_factory_.reset(WebIDBFactory::create()); } return idb_factory_.get(); } @@ -122,8 +118,7 @@ std::vector<GURL> IndexedDBContextImpl::GetAllOrigins() { std::vector<GURL> origins; std::set<GURL>* origins_set = GetOriginSet(); for (std::set<GURL>::const_iterator iter = origins_set->begin(); - iter != origins_set->end(); - ++iter) { + iter != origins_set->end(); ++iter) { origins.push_back(*iter); } return origins; @@ -133,8 +128,7 @@ std::vector<IndexedDBInfo> IndexedDBContextImpl::GetAllOriginsInfo() { std::vector<GURL> origins = GetAllOrigins(); std::vector<IndexedDBInfo> result; for (std::vector<GURL>::const_iterator iter = origins.begin(); - iter != origins.end(); - ++iter) { + iter != origins.end(); ++iter) { const GURL& origin_url = *iter; base::FilePath idb_directory = GetFilePath(origin_url); @@ -208,7 +202,7 @@ base::FilePath IndexedDBContextImpl::GetFilePath(const GURL& origin_url) { } base::FilePath IndexedDBContextImpl::GetFilePathForTesting( - const string16& origin_id) const { + const string16& origin_id) const { return GetIndexedDBFilePath(origin_id); } @@ -217,8 +211,7 @@ void IndexedDBContextImpl::ConnectionOpened(const GURL& origin_url, DCHECK_EQ(connections_[origin_url].count(connection), 0UL); if (quota_manager_proxy()) { quota_manager_proxy()->NotifyStorageAccessed( - quota::QuotaClient::kIndexedDatabase, - origin_url, + quota::QuotaClient::kIndexedDatabase, origin_url, quota::kStorageTypeTemporary); } connections_[origin_url].insert(connection); @@ -239,8 +232,7 @@ void IndexedDBContextImpl::ConnectionClosed(const GURL& origin_url, return; if (quota_manager_proxy()) { quota_manager_proxy()->NotifyStorageAccessed( - quota::QuotaClient::kIndexedDatabase, - origin_url, + quota::QuotaClient::kIndexedDatabase, origin_url, quota::kStorageTypeTemporary); } connections_[origin_url].erase(connection); @@ -279,8 +271,8 @@ quota::QuotaManagerProxy* IndexedDBContextImpl::quota_manager_proxy() { IndexedDBContextImpl::~IndexedDBContextImpl() { WebKit::WebIDBFactory* factory = idb_factory_.release(); if (factory) { - if (!BrowserThread::DeleteSoon( - BrowserThread::WEBKIT_DEPRECATED, FROM_HERE, factory)) + if (!BrowserThread::DeleteSoon(BrowserThread::WEBKIT_DEPRECATED, + FROM_HERE, factory)) delete factory; } @@ -301,17 +293,18 @@ IndexedDBContextImpl::~IndexedDBContextImpl() { // No WEBKIT thread here means we are running in a unit test where no clean // up is needed. BrowserThread::PostTask( - BrowserThread::WEBKIT_DEPRECATED, - FROM_HERE, - base::Bind( - &ClearSessionOnlyOrigins, data_path_, special_storage_policy_)); + BrowserThread::WEBKIT_DEPRECATED, FROM_HERE, + base::Bind(&ClearSessionOnlyOrigins, + data_path_, + special_storage_policy_)); } base::FilePath IndexedDBContextImpl::GetIndexedDBFilePath( const string16& origin_id) const { DCHECK(!data_path_.empty()); - base::FilePath::StringType id = webkit_base::WebStringToFilePathString( - origin_id).append(FILE_PATH_LITERAL(".indexeddb")); + base::FilePath::StringType id = + webkit_base::WebStringToFilePathString(origin_id).append( + FILE_PATH_LITERAL(".indexeddb")); return data_path_.Append(id.append(kIndexedDBExtension)); } @@ -338,20 +331,18 @@ void IndexedDBContextImpl::QueryDiskAndUpdateQuotaUsage( if (difference) { origin_size_map_[origin_url] = current_disk_usage; // quota_manager_proxy() is NULL in unit tests. - if (quota_manager_proxy()) { + if (quota_manager_proxy()) quota_manager_proxy()->NotifyStorageModified( quota::QuotaClient::kIndexedDatabase, origin_url, quota::kStorageTypeTemporary, difference); - } } } void IndexedDBContextImpl::GotUsageAndQuota(const GURL& origin_url, quota::QuotaStatusCode status, - int64 usage, - int64 quota) { + int64 usage, int64 quota) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); DCHECK(status == quota::kQuotaStatusOk || status == quota::kQuotaErrorAbort) << "status was " << status; @@ -359,17 +350,13 @@ void IndexedDBContextImpl::GotUsageAndQuota(const GURL& origin_url, // We seem to no longer care to wait around for the answer. return; } - BrowserThread::PostTask(BrowserThread::WEBKIT_DEPRECATED, - FROM_HERE, - base::Bind(&IndexedDBContextImpl::GotUpdatedQuota, - this, - origin_url, - usage, - quota)); + BrowserThread::PostTask( + BrowserThread::WEBKIT_DEPRECATED, FROM_HERE, + base::Bind(&IndexedDBContextImpl::GotUpdatedQuota, this, origin_url, + usage, quota)); } -void IndexedDBContextImpl::GotUpdatedQuota(const GURL& origin_url, - int64 usage, +void IndexedDBContextImpl::GotUpdatedQuota(const GURL& origin_url, int64 usage, int64 quota) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); space_available_map_[origin_url] = quota - usage; @@ -378,13 +365,11 @@ void IndexedDBContextImpl::GotUpdatedQuota(const GURL& origin_url, void IndexedDBContextImpl::QueryAvailableQuota(const GURL& origin_url) { if (!BrowserThread::CurrentlyOn(BrowserThread::IO)) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); - if (quota_manager_proxy()) { + if (quota_manager_proxy()) BrowserThread::PostTask( - BrowserThread::IO, - FROM_HERE, - base::Bind( - &IndexedDBContextImpl::QueryAvailableQuota, this, origin_url)); - } + BrowserThread::IO, FROM_HERE, + base::Bind(&IndexedDBContextImpl::QueryAvailableQuota, this, + origin_url)); return; } DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); @@ -402,8 +387,7 @@ std::set<GURL>* IndexedDBContextImpl::GetOriginSet() { std::vector<GURL> origins; GetAllOriginsAndPaths(data_path_, &origins, NULL); for (std::vector<GURL>::const_iterator iter = origins.begin(); - iter != origins.end(); - ++iter) { + iter != origins.end(); ++iter) { origin_set_->insert(*iter); } } diff --git a/content/browser/indexed_db/indexed_db_context_impl.h b/content/browser/indexed_db/indexed_db_context_impl.h index 846b2b1..48c9e07 100644 --- a/content/browser/indexed_db/indexed_db_context_impl.h +++ b/content/browser/indexed_db/indexed_db_context_impl.h @@ -66,8 +66,8 @@ class CONTENT_EXPORT IndexedDBContextImpl OVERRIDE; // Methods called by IndexedDBDispatcherHost for quota support. - void ConnectionOpened(const GURL& origin_url, WebKit::WebIDBDatabase* db); - void ConnectionClosed(const GURL& origin_url, WebKit::WebIDBDatabase* db); + void ConnectionOpened(const GURL& origin_url, WebKit::WebIDBDatabase*); + void ConnectionClosed(const GURL& origin_url, WebKit::WebIDBDatabase*); void TransactionComplete(const GURL& origin_url); bool WouldBeOverQuota(const GURL& origin_url, int64 additional_bytes); bool IsOverQuota(const GURL& origin_url); diff --git a/content/browser/indexed_db/indexed_db_cursor.h b/content/browser/indexed_db/indexed_db_cursor.h deleted file mode 100644 index 536b359..0000000 --- a/content/browser/indexed_db/indexed_db_cursor.h +++ /dev/null @@ -1,37 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_CURSOR_H_ -#define CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_CURSOR_H_ - -#include "base/memory/ref_counted.h" -#include "content/common/indexed_db/indexed_db_key.h" - -namespace content { - -class IndexedDBCallbacksWrapper; - -class IndexedDBCursor : public base::RefCounted<IndexedDBCursor> { - public: - virtual void Advance(unsigned long count, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) = 0; - virtual void ContinueFunction( - scoped_ptr<IndexedDBKey> key, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) = 0; - virtual void DeleteFunction( - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) = 0; - virtual void PrefetchContinue( - int number_to_fetch, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) = 0; - virtual void PrefetchReset(int used_prefetches, int unused_prefetches) = 0; - virtual void PostSuccessHandlerCallback() = 0; - - protected: - virtual ~IndexedDBCursor() {} - friend class base::RefCounted<IndexedDBCursor>; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_CURSOR_H_ diff --git a/content/browser/indexed_db/indexed_db_cursor_impl.cc b/content/browser/indexed_db/indexed_db_cursor_impl.cc deleted file mode 100644 index a11e880..0000000 --- a/content/browser/indexed_db/indexed_db_cursor_impl.cc +++ /dev/null @@ -1,223 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/indexed_db_cursor_impl.h" - -#include "base/logging.h" -#include "content/browser/indexed_db/indexed_db_backing_store.h" -#include "content/browser/indexed_db/indexed_db_callbacks_wrapper.h" -#include "content/browser/indexed_db/indexed_db_database_error.h" -#include "content/browser/indexed_db/indexed_db_database_impl.h" -#include "content/browser/indexed_db/indexed_db_tracing.h" -#include "content/browser/indexed_db/indexed_db_transaction.h" -#include "content/common/indexed_db/indexed_db_key_range.h" - -namespace content { - -class IndexedDBCursorImpl::CursorIterationOperation - : public IndexedDBTransaction::Operation { - public: - CursorIterationOperation(scoped_refptr<IndexedDBCursorImpl> cursor, - scoped_ptr<IndexedDBKey> key, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) - : cursor_(cursor), key_(key.Pass()), callbacks_(callbacks) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - scoped_refptr<IndexedDBCursorImpl> cursor_; - scoped_ptr<IndexedDBKey> key_; - scoped_refptr<IndexedDBCallbacksWrapper> callbacks_; -}; - -class IndexedDBCursorImpl::CursorAdvanceOperation - : public IndexedDBTransaction::Operation { - public: - CursorAdvanceOperation(scoped_refptr<IndexedDBCursorImpl> cursor, - unsigned long count, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) - : cursor_(cursor), count_(count), callbacks_(callbacks) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - scoped_refptr<IndexedDBCursorImpl> cursor_; - unsigned long count_; - scoped_refptr<IndexedDBCallbacksWrapper> callbacks_; -}; - -class IndexedDBCursorImpl::CursorPrefetchIterationOperation - : public IndexedDBTransaction::Operation { - public: - CursorPrefetchIterationOperation( - scoped_refptr<IndexedDBCursorImpl> cursor, - int number_to_fetch, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) - : cursor_(cursor), - number_to_fetch_(number_to_fetch), - callbacks_(callbacks) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - scoped_refptr<IndexedDBCursorImpl> cursor_; - int number_to_fetch_; - scoped_refptr<IndexedDBCallbacksWrapper> callbacks_; -}; - -IndexedDBCursorImpl::IndexedDBCursorImpl( - scoped_ptr<IndexedDBBackingStore::Cursor> cursor, - indexed_db::CursorType cursor_type, - IndexedDBDatabase::TaskType task_type, - IndexedDBTransaction* transaction, - int64 object_store_id) - : task_type_(task_type), - cursor_type_(cursor_type), - transaction_(transaction), - object_store_id_(object_store_id), - cursor_(cursor.Pass()), - closed_(false) { - transaction_->RegisterOpenCursor(this); -} - -IndexedDBCursorImpl::~IndexedDBCursorImpl() { - transaction_->UnregisterOpenCursor(this); -} - -void IndexedDBCursorImpl::ContinueFunction( - scoped_ptr<IndexedDBKey> key, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) { - IDB_TRACE("IndexedDBCursorImpl::continue"); - - transaction_->ScheduleTask( - task_type_, new CursorIterationOperation(this, key.Pass(), callbacks)); -} - -void IndexedDBCursorImpl::Advance( - unsigned long count, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) { - IDB_TRACE("IndexedDBCursorImpl::advance"); - - transaction_->ScheduleTask( - new CursorAdvanceOperation(this, count, callbacks)); -} - -void IndexedDBCursorImpl::CursorAdvanceOperation::Perform( - IndexedDBTransaction* /*transaction*/) { - IDB_TRACE("CursorAdvanceOperation"); - if (!cursor_->cursor_ || !cursor_->cursor_->Advance(count_)) { - cursor_->cursor_.reset(); - callbacks_->OnSuccess(static_cast<std::vector<char>*>(NULL)); - return; - } - - callbacks_->OnSuccess( - cursor_->key(), cursor_->primary_key(), cursor_->Value()); -} - -void IndexedDBCursorImpl::CursorIterationOperation::Perform( - IndexedDBTransaction* /*transaction*/) { - IDB_TRACE("CursorIterationOperation"); - if (!cursor_->cursor_ || !cursor_->cursor_->ContinueFunction(key_.get())) { - cursor_->cursor_.reset(); - callbacks_->OnSuccess(static_cast<std::vector<char>*>(NULL)); - return; - } - - callbacks_->OnSuccess( - cursor_->key(), cursor_->primary_key(), cursor_->Value()); -} - -void IndexedDBCursorImpl::DeleteFunction( - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) { - IDB_TRACE("IndexedDBCursorImpl::delete"); - DCHECK_NE(transaction_->mode(), indexed_db::TRANSACTION_READ_ONLY); - scoped_ptr<IndexedDBKeyRange> key_range = - make_scoped_ptr(new IndexedDBKeyRange(cursor_->primary_key())); - transaction_->database()->DeleteRange( - transaction_->id(), object_store_id_, key_range.Pass(), callbacks); -} - -void IndexedDBCursorImpl::PrefetchContinue( - int number_to_fetch, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) { - IDB_TRACE("IndexedDBCursorImpl::prefetch_continue"); - - transaction_->ScheduleTask( - task_type_, - new CursorPrefetchIterationOperation(this, number_to_fetch, callbacks)); -} - -void IndexedDBCursorImpl::CursorPrefetchIterationOperation::Perform( - IndexedDBTransaction* /*transaction*/) { - IDB_TRACE("CursorPrefetchIterationOperation"); - - std::vector<IndexedDBKey> found_keys; - std::vector<IndexedDBKey> found_primary_keys; - std::vector<std::vector<char> > found_values; - - if (cursor_->cursor_) - cursor_->saved_cursor_.reset(cursor_->cursor_->Clone()); - const size_t max_size_estimate = 10 * 1024 * 1024; - size_t size_estimate = 0; - - for (int i = 0; i < number_to_fetch_; ++i) { - if (!cursor_->cursor_ || !cursor_->cursor_->ContinueFunction(0)) { - cursor_->cursor_.reset(); - break; - } - - found_keys.push_back(cursor_->cursor_->key()); - found_primary_keys.push_back(cursor_->cursor_->primary_key()); - - switch (cursor_->cursor_type_) { - case indexed_db::CURSOR_KEY_ONLY: - found_values.push_back(std::vector<char>()); - break; - case indexed_db::CURSOR_KEY_AND_VALUE: { - std::vector<char> value; - value.swap(*cursor_->cursor_->Value()); - size_estimate += value.size(); - found_values.push_back(value); - break; - } - default: - NOTREACHED(); - } - size_estimate += cursor_->cursor_->key().size_estimate(); - size_estimate += cursor_->cursor_->primary_key().size_estimate(); - - if (size_estimate > max_size_estimate) - break; - } - - if (!found_keys.size()) { - callbacks_->OnSuccess(static_cast<std::vector<char>*>(NULL)); - return; - } - - callbacks_->OnSuccessWithPrefetch( - found_keys, found_primary_keys, found_values); -} - -void IndexedDBCursorImpl::PrefetchReset(int used_prefetches, int) { - IDB_TRACE("IndexedDBCursorImpl::prefetch_reset"); - cursor_.swap(saved_cursor_); - saved_cursor_.reset(); - - if (closed_) - return; - if (cursor_) { - for (int i = 0; i < used_prefetches; ++i) { - bool ok = cursor_->ContinueFunction(); - DCHECK(ok); - } - } -} - -void IndexedDBCursorImpl::Close() { - IDB_TRACE("IndexedDBCursorImpl::close"); - closed_ = true; - cursor_.reset(); - saved_cursor_.reset(); -} - -} // namespace content diff --git a/content/browser/indexed_db/indexed_db_cursor_impl.h b/content/browser/indexed_db/indexed_db_cursor_impl.h deleted file mode 100644 index 8b79d27..0000000 --- a/content/browser/indexed_db/indexed_db_cursor_impl.h +++ /dev/null @@ -1,98 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_CURSOR_IMPL_H_ -#define CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_CURSOR_IMPL_H_ - -#include <vector> - -#include "base/basictypes.h" -#include "base/memory/ref_counted.h" -#include "base/memory/scoped_ptr.h" -#include "content/browser/indexed_db/indexed_db_backing_store.h" -#include "content/browser/indexed_db/indexed_db_cursor.h" -#include "content/browser/indexed_db/indexed_db_database.h" -#include "content/common/indexed_db/indexed_db_key_range.h" - -namespace content { - -class IndexedDBDatabaseImpl; -class IndexedDBTransaction; - -class IndexedDBCursorImpl : public IndexedDBCursor { - public: - static scoped_refptr<IndexedDBCursorImpl> Create( - scoped_ptr<IndexedDBBackingStore::Cursor> cursor, - indexed_db::CursorType cursor_type, - IndexedDBTransaction* transaction, - int64 object_store_id) { - return make_scoped_refptr( - new IndexedDBCursorImpl(cursor.Pass(), - cursor_type, - IndexedDBDatabase::NORMAL_TASK, - transaction, - object_store_id)); - } - static scoped_refptr<IndexedDBCursorImpl> Create( - scoped_ptr<IndexedDBBackingStore::Cursor> cursor, - indexed_db::CursorType cursor_type, - IndexedDBDatabase::TaskType task_type, - IndexedDBTransaction* transaction, - int64 object_store_id) { - return make_scoped_refptr(new IndexedDBCursorImpl( - cursor.Pass(), cursor_type, task_type, transaction, object_store_id)); - } - - // IndexedDBCursor - virtual void Advance(unsigned long, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) - OVERRIDE; - virtual void ContinueFunction( - scoped_ptr<IndexedDBKey> key, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) OVERRIDE; - virtual void DeleteFunction( - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) OVERRIDE; - virtual void PrefetchContinue( - int number_to_fetch, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) OVERRIDE; - virtual void PrefetchReset(int used_prefetches, int unused_prefetches) - OVERRIDE; - virtual void PostSuccessHandlerCallback() OVERRIDE {} - - const IndexedDBKey& key() const { return cursor_->key(); } - const IndexedDBKey& primary_key() const { return cursor_->primary_key(); } - std::vector<char>* Value() const { - return (cursor_type_ == indexed_db::CURSOR_KEY_ONLY) ? NULL - : cursor_->Value(); - } - void Close(); - - private: - IndexedDBCursorImpl(scoped_ptr<IndexedDBBackingStore::Cursor> cursor, - indexed_db::CursorType cursor_type, - IndexedDBDatabase::TaskType task_type, - IndexedDBTransaction* transaction, - int64 object_store_id); - virtual ~IndexedDBCursorImpl(); - - class CursorIterationOperation; - class CursorAdvanceOperation; - class CursorPrefetchIterationOperation; - - IndexedDBDatabase::TaskType task_type_; - indexed_db::CursorType cursor_type_; - const scoped_refptr<IndexedDBTransaction> transaction_; - const int64 object_store_id_; - - // Must be destroyed before transaction_. - scoped_ptr<IndexedDBBackingStore::Cursor> cursor_; - // Must be destroyed before transaction_. - scoped_ptr<IndexedDBBackingStore::Cursor> saved_cursor_; - - bool closed_; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_CURSOR_IMPL_H_ diff --git a/content/browser/indexed_db/indexed_db_database.h b/content/browser/indexed_db/indexed_db_database.h deleted file mode 100644 index 880e880..0000000 --- a/content/browser/indexed_db/indexed_db_database.h +++ /dev/null @@ -1,131 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_DATABASE_H_ -#define CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_DATABASE_H_ - -#include <vector> - -#include "base/basictypes.h" -#include "base/memory/ref_counted.h" -#include "base/memory/scoped_ptr.h" -#include "base/string16.h" -#include "content/browser/indexed_db/indexed_db.h" -#include "content/browser/indexed_db/indexed_db_database_error.h" -#include "content/common/indexed_db/indexed_db_key.h" -#include "content/common/indexed_db/indexed_db_key_path.h" -#include "content/common/indexed_db/indexed_db_key_range.h" - -namespace content { - -class IndexedDBCallbacksWrapper; -class IndexedDBDatabaseCallbacksWrapper; -struct IndexedDBDatabaseMetadata; - -// This is implemented by IndexedDBDatabaseImpl and optionally others (in order -// to proxy calls across process barriers). All calls to these classes should be -// non-blocking and trigger work on a background thread if necessary. -class IndexedDBDatabase : public base::RefCounted<IndexedDBDatabase> { - public: - virtual void CreateObjectStore(int64 transaction_id, - int64 object_store_id, - const string16& name, - const IndexedDBKeyPath& key_path, - bool auto_increment) = 0; - virtual void DeleteObjectStore(int64 transaction_id, - int64 object_store_id) = 0; - virtual void CreateTransaction( - int64 transaction_id, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> callbacks, - const std::vector<int64>& object_store_ids, - uint16 mode) = 0; - virtual void Close( - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> callbacks) = 0; - - // Transaction-specific operations. - virtual void Commit(int64 transaction_id) = 0; - virtual void Abort(int64 transaction_id) = 0; - virtual void Abort(int64 transaction_id, - scoped_refptr<IndexedDBDatabaseError> error) = 0; - - virtual void CreateIndex(int64 transaction_id, - int64 object_store_id, - int64 index_id, - const string16& name, - const IndexedDBKeyPath& key_path, - bool unique, - bool multi_entry) = 0; - virtual void DeleteIndex(int64 transaction_id, - int64 object_store_id, - int64 index_id) = 0; - - enum TaskType { - NORMAL_TASK = 0, - PREEMPTIVE_TASK - }; - - enum PutMode { - ADD_OR_UPDATE, - ADD_ONLY, - CURSOR_UPDATE - }; - - static const int64 kMinimumIndexId = 30; - - typedef std::vector<IndexedDBKey> IndexKeys; - - virtual void Get(int64 transaction_id, - int64 object_store_id, - int64 index_id, - scoped_ptr<IndexedDBKeyRange> key_range, - bool key_only, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) = 0; - // This will swap() with value. - virtual void Put(int64 transaction_id, - int64 object_store_id, - std::vector<char>* value, - scoped_ptr<IndexedDBKey> key, - PutMode mode, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - const std::vector<int64>& index_ids, - const std::vector<IndexKeys>& index_keys) = 0; - virtual void SetIndexKeys(int64 transaction_id, - int64 object_store_id, - scoped_ptr<IndexedDBKey> primary_key, - const std::vector<int64>& index_ids, - const std::vector<IndexKeys>& index_keys) = 0; - virtual void SetIndexesReady(int64 transaction_id, - int64 object_store_id, - const std::vector<int64>& index_ids) = 0; - virtual void OpenCursor( - int64 transaction_id, - int64 object_store_id, - int64 index_id, - scoped_ptr<IndexedDBKeyRange> key_Range, - indexed_db::CursorDirection direction, - bool key_only, - TaskType task_type, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) = 0; - virtual void Count(int64 transaction_id, - int64 object_store_id, - int64 index_id, - scoped_ptr<IndexedDBKeyRange> key_range, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) = 0; - virtual void DeleteRange( - int64 transaction_id, - int64 object_store_id, - scoped_ptr<IndexedDBKeyRange> key_range, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) = 0; - virtual void Clear(int64 transaction_id, - int64 object_store_id, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) = 0; - - protected: - virtual ~IndexedDBDatabase() {} - friend class base::RefCounted<IndexedDBDatabase>; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_DATABASE_H_ diff --git a/content/browser/indexed_db/indexed_db_database_callbacks_wrapper.cc b/content/browser/indexed_db/indexed_db_database_callbacks_wrapper.cc deleted file mode 100644 index 6e99f0c..0000000 --- a/content/browser/indexed_db/indexed_db_database_callbacks_wrapper.cc +++ /dev/null @@ -1,42 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/indexed_db_database_callbacks_wrapper.h" - -namespace content { - -IndexedDBDatabaseCallbacksWrapper::IndexedDBDatabaseCallbacksWrapper( - WebKit::WebIDBDatabaseCallbacks* callbacks) - : callbacks_(callbacks) {} -IndexedDBDatabaseCallbacksWrapper::~IndexedDBDatabaseCallbacksWrapper() {} - -void IndexedDBDatabaseCallbacksWrapper::OnForcedClose() { - if (!callbacks_) - return; - callbacks_->onForcedClose(); - callbacks_.reset(); -} -void IndexedDBDatabaseCallbacksWrapper::OnVersionChange(int64 old_version, - int64 new_version) { - if (!callbacks_) - return; - callbacks_->onVersionChange(old_version, new_version); -} - -void IndexedDBDatabaseCallbacksWrapper::OnAbort( - int64 transaction_id, - scoped_refptr<IndexedDBDatabaseError> error) { - if (!callbacks_) - return; - callbacks_->onAbort( - transaction_id, - WebKit::WebIDBDatabaseError(error->code(), error->message())); -} -void IndexedDBDatabaseCallbacksWrapper::OnComplete(int64 transaction_id) { - if (!callbacks_) - return; - callbacks_->onComplete(transaction_id); -} - -} // namespace content diff --git a/content/browser/indexed_db/indexed_db_database_callbacks_wrapper.h b/content/browser/indexed_db/indexed_db_database_callbacks_wrapper.h deleted file mode 100644 index 920f2d2..0000000 --- a/content/browser/indexed_db/indexed_db_database_callbacks_wrapper.h +++ /dev/null @@ -1,43 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_DATABASE_CALLBACKS_WRAPPER_H_ -#define CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_DATABASE_CALLBACKS_WRAPPER_H_ - -#include "base/basictypes.h" -#include "base/memory/ref_counted.h" -#include "base/memory/scoped_ptr.h" -#include "base/string16.h" -#include "content/browser/indexed_db/indexed_db_database_error.h" -#include "third_party/WebKit/public/platform/WebIDBDatabaseCallbacks.h" - -namespace content { - -class IndexedDBDatabaseCallbacksWrapper - : public base::RefCounted<IndexedDBDatabaseCallbacksWrapper> { - public: - static scoped_refptr<IndexedDBDatabaseCallbacksWrapper> Create( - WebKit::WebIDBDatabaseCallbacks* callbacks) { - return make_scoped_refptr(new IndexedDBDatabaseCallbacksWrapper(callbacks)); - } - - virtual void OnForcedClose(); - virtual void OnVersionChange(int64 old_version, int64 new_version); - - virtual void OnAbort(int64 transaction_id, - scoped_refptr<IndexedDBDatabaseError> error); - virtual void OnComplete(int64 transaction_id); - - private: - explicit IndexedDBDatabaseCallbacksWrapper( - WebKit::WebIDBDatabaseCallbacks* callbacks); - virtual ~IndexedDBDatabaseCallbacksWrapper(); - friend class base::RefCounted<IndexedDBDatabaseCallbacksWrapper>; - - scoped_ptr<WebKit::WebIDBDatabaseCallbacks> callbacks_; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_DATABASE_CALLBACKS_WRAPPER_H_ diff --git a/content/browser/indexed_db/indexed_db_database_error.h b/content/browser/indexed_db/indexed_db_database_error.h deleted file mode 100644 index aa798c9..0000000 --- a/content/browser/indexed_db/indexed_db_database_error.h +++ /dev/null @@ -1,43 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_DATABASE_ERROR_H_ -#define CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_DATABASE_ERROR_H_ - -#include "base/basictypes.h" -#include "base/logging.h" -#include "base/memory/ref_counted.h" -#include "base/string16.h" -#include "third_party/WebKit/public/platform/WebIDBDatabaseError.h" - -namespace content { - -class IndexedDBDatabaseError : public base::RefCounted<IndexedDBDatabaseError> { - public: - static scoped_refptr<IndexedDBDatabaseError> Create(uint16 code, - const string16& message) { - // TODO(jsbell): Assert that this is a valid WebIDBDatabaseException code. - return make_scoped_refptr(new IndexedDBDatabaseError(code, message)); - } - static scoped_refptr<IndexedDBDatabaseError> Create( - const WebKit::WebIDBDatabaseError& other) { - return make_scoped_refptr( - new IndexedDBDatabaseError(other.code(), other.message())); - } - - uint16 code() const { return code_; } - const string16& message() const { return message_; } - - private: - IndexedDBDatabaseError(uint16 code, const string16& message) - : code_(code), message_(message) {} - ~IndexedDBDatabaseError() {} - friend class base::RefCounted<IndexedDBDatabaseError>; - const uint16 code_; - const string16 message_; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_DATABASE_ERROR_H_ diff --git a/content/browser/indexed_db/indexed_db_database_impl.cc b/content/browser/indexed_db/indexed_db_database_impl.cc deleted file mode 100644 index 9ecc611..0000000 --- a/content/browser/indexed_db/indexed_db_database_impl.cc +++ /dev/null @@ -1,1823 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/indexed_db_database_impl.h" - -#include <math.h> -#include <vector> - -#include "base/auto_reset.h" -#include "base/logging.h" -#include "base/memory/scoped_ptr.h" -#include "base/strings/string_number_conversions.h" -#include "base/utf_string_conversions.h" -#include "content/browser/indexed_db/indexed_db_backing_store.h" -#include "content/browser/indexed_db/indexed_db_cursor_impl.h" -#include "content/browser/indexed_db/indexed_db_factory_impl.h" -#include "content/browser/indexed_db/indexed_db_index_writer.h" -#include "content/browser/indexed_db/indexed_db_tracing.h" -#include "content/browser/indexed_db/indexed_db_transaction.h" -#include "content/common/indexed_db/indexed_db_key_path.h" -#include "content/common/indexed_db/indexed_db_key_range.h" -#include "third_party/WebKit/public/platform/WebIDBDatabaseException.h" - -using base::Int64ToString16; -using WebKit::WebIDBKey; - -namespace content { - -class CreateObjectStoreOperation : public IndexedDBTransaction::Operation { - public: - CreateObjectStoreOperation( - scoped_refptr<IndexedDBBackingStore> backing_store, - const IndexedDBObjectStoreMetadata& object_store_metadata) - : backing_store_(backing_store), - object_store_metadata_(object_store_metadata) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - const scoped_refptr<IndexedDBBackingStore> backing_store_; - const IndexedDBObjectStoreMetadata object_store_metadata_; -}; - -class DeleteObjectStoreOperation : public IndexedDBTransaction::Operation { - public: - DeleteObjectStoreOperation( - scoped_refptr<IndexedDBBackingStore> backing_store, - const IndexedDBObjectStoreMetadata& object_store_metadata) - : backing_store_(backing_store), - object_store_metadata_(object_store_metadata) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - const scoped_refptr<IndexedDBBackingStore> backing_store_; - const IndexedDBObjectStoreMetadata object_store_metadata_; -}; - -class IndexedDBDatabaseImpl::VersionChangeOperation - : public IndexedDBTransaction::Operation { - public: - VersionChangeOperation( - scoped_refptr<IndexedDBDatabaseImpl> database, - int64 transaction_id, - int64 version, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks) - : database_(database), - transaction_id_(transaction_id), - version_(version), - callbacks_(callbacks), - database_callbacks_(database_callbacks) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - scoped_refptr<IndexedDBDatabaseImpl> database_; - int64 transaction_id_; - int64 version_; - scoped_refptr<IndexedDBCallbacksWrapper> callbacks_; - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks_; -}; - -class CreateObjectStoreAbortOperation : public IndexedDBTransaction::Operation { - public: - CreateObjectStoreAbortOperation(scoped_refptr<IndexedDBDatabaseImpl> database, - int64 object_store_id) - : database_(database), object_store_id_(object_store_id) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - const scoped_refptr<IndexedDBDatabaseImpl> database_; - const int64 object_store_id_; -}; - -class DeleteObjectStoreAbortOperation : public IndexedDBTransaction::Operation { - public: - DeleteObjectStoreAbortOperation( - scoped_refptr<IndexedDBDatabaseImpl> database, - const IndexedDBObjectStoreMetadata& object_store_metadata) - : database_(database), object_store_metadata_(object_store_metadata) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - scoped_refptr<IndexedDBDatabaseImpl> database_; - IndexedDBObjectStoreMetadata object_store_metadata_; -}; - -class IndexedDBDatabaseImpl::VersionChangeAbortOperation - : public IndexedDBTransaction::Operation { - public: - VersionChangeAbortOperation(scoped_refptr<IndexedDBDatabaseImpl> database, - const string16& previous_version, - int64 previous_int_version) - : database_(database), - previous_version_(previous_version), - previous_int_version_(previous_int_version) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - scoped_refptr<IndexedDBDatabaseImpl> database_; - string16 previous_version_; - int64 previous_int_version_; -}; - -class CreateIndexOperation : public IndexedDBTransaction::Operation { - public: - CreateIndexOperation(scoped_refptr<IndexedDBBackingStore> backing_store, - int64 object_store_id, - const IndexedDBIndexMetadata& index_metadata) - : backing_store_(backing_store), - object_store_id_(object_store_id), - index_metadata_(index_metadata) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - const scoped_refptr<IndexedDBBackingStore> backing_store_; - const int64 object_store_id_; - const IndexedDBIndexMetadata index_metadata_; -}; - -class DeleteIndexOperation : public IndexedDBTransaction::Operation { - public: - DeleteIndexOperation(scoped_refptr<IndexedDBBackingStore> backing_store, - int64 object_store_id, - const IndexedDBIndexMetadata& index_metadata) - : backing_store_(backing_store), - object_store_id_(object_store_id), - index_metadata_(index_metadata) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - const scoped_refptr<IndexedDBBackingStore> backing_store_; - const int64 object_store_id_; - const IndexedDBIndexMetadata index_metadata_; -}; - -class CreateIndexAbortOperation : public IndexedDBTransaction::Operation { - public: - CreateIndexAbortOperation(scoped_refptr<IndexedDBDatabaseImpl> database, - int64 object_store_id, - int64 index_id) - : database_(database), - object_store_id_(object_store_id), - index_id_(index_id) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - const scoped_refptr<IndexedDBDatabaseImpl> database_; - const int64 object_store_id_; - const int64 index_id_; -}; - -class DeleteIndexAbortOperation : public IndexedDBTransaction::Operation { - public: - DeleteIndexAbortOperation(scoped_refptr<IndexedDBDatabaseImpl> database, - int64 object_store_id, - const IndexedDBIndexMetadata& index_metadata) - : database_(database), - object_store_id_(object_store_id), - index_metadata_(index_metadata) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - const scoped_refptr<IndexedDBDatabaseImpl> database_; - const int64 object_store_id_; - const IndexedDBIndexMetadata index_metadata_; -}; - -class GetOperation : public IndexedDBTransaction::Operation { - public: - GetOperation(scoped_refptr<IndexedDBBackingStore> backing_store, - const IndexedDBDatabaseMetadata& metadata, - int64 object_store_id, - int64 index_id, - scoped_ptr<IndexedDBKeyRange> key_range, - indexed_db::CursorType cursor_type, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) - : backing_store_(backing_store), - database_id_(metadata.id), - object_store_id_(object_store_id), - index_id_(index_id), - key_path_(metadata.object_stores.find(object_store_id) - ->second.key_path), - auto_increment_(metadata.object_stores.find(object_store_id) - ->second.auto_increment), - key_range_(key_range.Pass()), - cursor_type_(cursor_type), - callbacks_(callbacks) { - DCHECK(metadata.object_stores.find(object_store_id) != - metadata.object_stores.end()); - DCHECK(metadata.object_stores.find(object_store_id)->second.id == - object_store_id); - } - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - const scoped_refptr<IndexedDBBackingStore> backing_store_; - const int64 database_id_; - const int64 object_store_id_; - const int64 index_id_; - const IndexedDBKeyPath key_path_; - const bool auto_increment_; - const scoped_ptr<IndexedDBKeyRange> key_range_; - const indexed_db::CursorType cursor_type_; - const scoped_refptr<IndexedDBCallbacksWrapper> callbacks_; -}; - -class PutOperation : public IndexedDBTransaction::Operation { - public: - PutOperation(scoped_refptr<IndexedDBBackingStore> backing_store, - int64 database_id, - const IndexedDBObjectStoreMetadata& object_store, - std::vector<char>* value, - scoped_ptr<IndexedDBKey> key, - IndexedDBDatabase::PutMode put_mode, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - const std::vector<int64>& index_ids, - const std::vector<IndexedDBDatabase::IndexKeys>& index_keys) - : backing_store_(backing_store), - database_id_(database_id), - object_store_(object_store), - key_(key.Pass()), - put_mode_(put_mode), - callbacks_(callbacks), - index_ids_(index_ids), - index_keys_(index_keys) { - value_.swap(*value); - } - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - const scoped_refptr<IndexedDBBackingStore> backing_store_; - const int64 database_id_; - const IndexedDBObjectStoreMetadata object_store_; - std::vector<char> value_; - scoped_ptr<IndexedDBKey> key_; - const IndexedDBDatabase::PutMode put_mode_; - const scoped_refptr<IndexedDBCallbacksWrapper> callbacks_; - const std::vector<int64> index_ids_; - const std::vector<IndexedDBDatabase::IndexKeys> index_keys_; -}; - -class SetIndexesReadyOperation : public IndexedDBTransaction::Operation { - public: - explicit SetIndexesReadyOperation(size_t index_count) - : index_count_(index_count) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - const size_t index_count_; -}; - -class OpenCursorOperation : public IndexedDBTransaction::Operation { - public: - OpenCursorOperation(scoped_refptr<IndexedDBBackingStore> backing_store, - int64 database_id, - int64 object_store_id, - int64 index_id, - scoped_ptr<IndexedDBKeyRange> key_range, - indexed_db::CursorDirection direction, - indexed_db::CursorType cursor_type, - IndexedDBDatabase::TaskType task_type, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) - : backing_store_(backing_store), - database_id_(database_id), - object_store_id_(object_store_id), - index_id_(index_id), - key_range_(key_range.Pass()), - direction_(direction), - cursor_type_(cursor_type), - task_type_(task_type), - callbacks_(callbacks) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - const scoped_refptr<IndexedDBBackingStore> backing_store_; - const int64 database_id_; - const int64 object_store_id_; - const int64 index_id_; - const scoped_ptr<IndexedDBKeyRange> key_range_; - const indexed_db::CursorDirection direction_; - const indexed_db::CursorType cursor_type_; - const IndexedDBDatabase::TaskType task_type_; - const scoped_refptr<IndexedDBCallbacksWrapper> callbacks_; -}; - -class CountOperation : public IndexedDBTransaction::Operation { - public: - CountOperation(scoped_refptr<IndexedDBBackingStore> backing_store, - int64 database_id, - int64 object_store_id, - int64 index_id, - scoped_ptr<IndexedDBKeyRange> key_range, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) - : backing_store_(backing_store), - database_id_(database_id), - object_store_id_(object_store_id), - index_id_(index_id), - key_range_(key_range.Pass()), - callbacks_(callbacks) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - const scoped_refptr<IndexedDBBackingStore> backing_store_; - const int64 database_id_; - const int64 object_store_id_; - const int64 index_id_; - const scoped_ptr<IndexedDBKeyRange> key_range_; - const scoped_refptr<IndexedDBCallbacksWrapper> callbacks_; -}; - -class DeleteRangeOperation : public IndexedDBTransaction::Operation { - public: - DeleteRangeOperation(scoped_refptr<IndexedDBBackingStore> backing_store, - int64 database_id, - int64 object_store_id, - scoped_ptr<IndexedDBKeyRange> key_range, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) - : backing_store_(backing_store), - database_id_(database_id), - object_store_id_(object_store_id), - key_range_(key_range.Pass()), - callbacks_(callbacks) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - const scoped_refptr<IndexedDBBackingStore> backing_store_; - const int64 database_id_; - const int64 object_store_id_; - const scoped_ptr<IndexedDBKeyRange> key_range_; - const scoped_refptr<IndexedDBCallbacksWrapper> callbacks_; -}; - -class ClearOperation : public IndexedDBTransaction::Operation { - public: - ClearOperation(scoped_refptr<IndexedDBBackingStore> backing_store, - int64 database_id, - int64 object_store_id, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) - : backing_store_(backing_store), - database_id_(database_id), - object_store_id_(object_store_id), - callbacks_(callbacks) {} - virtual void Perform(IndexedDBTransaction* transaction) OVERRIDE; - - private: - const scoped_refptr<IndexedDBBackingStore> backing_store_; - const int64 database_id_; - const int64 object_store_id_; - const scoped_refptr<IndexedDBCallbacksWrapper> callbacks_; -}; - -class IndexedDBDatabaseImpl::PendingOpenCall { - public: - PendingOpenCall( - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks, - int64 transaction_id, - int64 version) - : callbacks_(callbacks), - database_callbacks_(database_callbacks), - version_(version), - transaction_id_(transaction_id) {} - scoped_refptr<IndexedDBCallbacksWrapper> Callbacks() { return callbacks_; } - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> DatabaseCallbacks() { - return database_callbacks_; - } - int64 Version() { return version_; } - int64 TransactionId() const { return transaction_id_; } - - private: - scoped_refptr<IndexedDBCallbacksWrapper> callbacks_; - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks_; - int64 version_; - const int64 transaction_id_; -}; - -class IndexedDBDatabaseImpl::PendingDeleteCall { - public: - explicit PendingDeleteCall(scoped_refptr<IndexedDBCallbacksWrapper> callbacks) - : callbacks_(callbacks) {} - scoped_refptr<IndexedDBCallbacksWrapper> Callbacks() { return callbacks_; } - - private: - scoped_refptr<IndexedDBCallbacksWrapper> callbacks_; -}; - -scoped_refptr<IndexedDBDatabaseImpl> IndexedDBDatabaseImpl::Create( - const string16& name, - IndexedDBBackingStore* database, - IndexedDBFactoryImpl* factory, - const string16& unique_identifier) { - scoped_refptr<IndexedDBDatabaseImpl> backend = - new IndexedDBDatabaseImpl(name, database, factory, unique_identifier); - if (!backend->OpenInternal()) - return 0; - return backend; -} - -namespace { -const base::string16::value_type kNoStringVersion[] = {0}; -} - -IndexedDBDatabaseImpl::IndexedDBDatabaseImpl( - const string16& name, - IndexedDBBackingStore* backing_store, - IndexedDBFactoryImpl* factory, - const string16& unique_identifier) - : backing_store_(backing_store), - metadata_(name, - kInvalidId, - kNoStringVersion, - IndexedDBDatabaseMetadata::NO_INT_VERSION, - kInvalidId), - identifier_(unique_identifier), - factory_(factory), - running_version_change_transaction_(NULL), - closing_connection_(false) { - DCHECK(!metadata_.name.empty()); -} - -void IndexedDBDatabaseImpl::AddObjectStore( - const IndexedDBObjectStoreMetadata& object_store, - int64 new_max_object_store_id) { - DCHECK(metadata_.object_stores.find(object_store.id) == - metadata_.object_stores.end()); - if (new_max_object_store_id != IndexedDBObjectStoreMetadata::kInvalidId) { - DCHECK_LT(metadata_.max_object_store_id, new_max_object_store_id); - metadata_.max_object_store_id = new_max_object_store_id; - } - metadata_.object_stores[object_store.id] = object_store; -} - -void IndexedDBDatabaseImpl::RemoveObjectStore(int64 object_store_id) { - DCHECK(metadata_.object_stores.find(object_store_id) != - metadata_.object_stores.end()); - metadata_.object_stores.erase(object_store_id); -} - -void IndexedDBDatabaseImpl::AddIndex(int64 object_store_id, - const IndexedDBIndexMetadata& index, - int64 new_max_index_id) { - DCHECK(metadata_.object_stores.find(object_store_id) != - metadata_.object_stores.end()); - IndexedDBObjectStoreMetadata object_store = - metadata_.object_stores[object_store_id]; - - DCHECK(object_store.indexes.find(index.id) == object_store.indexes.end()); - object_store.indexes[index.id] = index; - if (new_max_index_id != IndexedDBIndexMetadata::kInvalidId) { - DCHECK_LT(object_store.max_index_id, new_max_index_id); - object_store.max_index_id = new_max_index_id; - } - metadata_.object_stores[object_store_id] = object_store; -} - -void IndexedDBDatabaseImpl::RemoveIndex(int64 object_store_id, int64 index_id) { - DCHECK(metadata_.object_stores.find(object_store_id) != - metadata_.object_stores.end()); - IndexedDBObjectStoreMetadata object_store = - metadata_.object_stores[object_store_id]; - - DCHECK(object_store.indexes.find(index_id) != object_store.indexes.end()); - object_store.indexes.erase(index_id); - metadata_.object_stores[object_store_id] = object_store; -} - -bool IndexedDBDatabaseImpl::OpenInternal() { - bool success = false; - bool ok = backing_store_->GetIDBDatabaseMetaData( - metadata_.name, &metadata_, success); - DCHECK(success == (metadata_.id != kInvalidId)) << "success = " << success - << " id_ = " << metadata_.id; - if (!ok) - return false; - if (success) - return backing_store_->GetObjectStores(metadata_.id, - &metadata_.object_stores); - - return backing_store_->CreateIDBDatabaseMetaData( - metadata_.name, metadata_.version, metadata_.int_version, metadata_.id); -} - -IndexedDBDatabaseImpl::~IndexedDBDatabaseImpl() { - DCHECK(transactions_.empty()); - DCHECK(pending_open_calls_.empty()); - DCHECK(pending_delete_calls_.empty()); -} - -scoped_refptr<IndexedDBBackingStore> IndexedDBDatabaseImpl::BackingStore() - const { - return backing_store_; -} - -void IndexedDBDatabaseImpl::CreateObjectStore(int64 transaction_id, - int64 object_store_id, - const string16& name, - const IndexedDBKeyPath& key_path, - bool auto_increment) { - IDB_TRACE("IndexedDBDatabaseImpl::create_object_store"); - TransactionMap::const_iterator trans_iterator = - transactions_.find(transaction_id); - if (trans_iterator == transactions_.end()) - return; - IndexedDBTransaction* transaction = trans_iterator->second; - DCHECK_EQ(transaction->mode(), indexed_db::TRANSACTION_VERSION_CHANGE); - - DCHECK(metadata_.object_stores.find(object_store_id) == - metadata_.object_stores.end()); - IndexedDBObjectStoreMetadata object_store_metadata( - name, - object_store_id, - key_path, - auto_increment, - IndexedDBDatabase::kMinimumIndexId); - - transaction->ScheduleTask( - new CreateObjectStoreOperation(backing_store_, object_store_metadata), - new CreateObjectStoreAbortOperation(this, object_store_id)); - - AddObjectStore(object_store_metadata, object_store_id); -} - -void CreateObjectStoreOperation::Perform(IndexedDBTransaction* transaction) { - IDB_TRACE("CreateObjectStoreOperation"); - if (!backing_store_->CreateObjectStore( - transaction->BackingStoreTransaction(), - transaction->database()->id(), - object_store_metadata_.id, - object_store_metadata_.name, - object_store_metadata_.key_path, - object_store_metadata_.auto_increment)) { - string16 error_string = - ASCIIToUTF16("Internal error creating object store '") + - object_store_metadata_.name + ASCIIToUTF16("'."); - - scoped_refptr<IndexedDBDatabaseError> error = - IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, error_string); - transaction->Abort(error); - return; - } -} - -void IndexedDBDatabaseImpl::DeleteObjectStore(int64 transaction_id, - int64 object_store_id) { - IDB_TRACE("IndexedDBDatabaseImpl::delete_object_store"); - TransactionMap::const_iterator trans_iterator = - transactions_.find(transaction_id); - if (trans_iterator == transactions_.end()) - return; - IndexedDBTransaction* transaction = trans_iterator->second; - DCHECK_EQ(transaction->mode(), indexed_db::TRANSACTION_VERSION_CHANGE); - - DCHECK(metadata_.object_stores.find(object_store_id) != - metadata_.object_stores.end()); - const IndexedDBObjectStoreMetadata& object_store_metadata = - metadata_.object_stores[object_store_id]; - - transaction->ScheduleTask( - new DeleteObjectStoreOperation(backing_store_, object_store_metadata), - new DeleteObjectStoreAbortOperation(this, object_store_metadata)); - RemoveObjectStore(object_store_id); -} - -void IndexedDBDatabaseImpl::CreateIndex(int64 transaction_id, - int64 object_store_id, - int64 index_id, - const string16& name, - const IndexedDBKeyPath& key_path, - bool unique, - bool multi_entry) { - IDB_TRACE("IndexedDBDatabaseImpl::create_index"); - TransactionMap::const_iterator trans_iterator = - transactions_.find(transaction_id); - if (trans_iterator == transactions_.end()) - return; - IndexedDBTransaction* transaction = trans_iterator->second; - DCHECK_EQ(transaction->mode(), indexed_db::TRANSACTION_VERSION_CHANGE); - - DCHECK(metadata_.object_stores.find(object_store_id) != - metadata_.object_stores.end()); - const IndexedDBObjectStoreMetadata object_store = - metadata_.object_stores[object_store_id]; - - DCHECK(object_store.indexes.find(index_id) == object_store.indexes.end()); - const IndexedDBIndexMetadata index_metadata( - name, index_id, key_path, unique, multi_entry); - - transaction->ScheduleTask( - new CreateIndexOperation(backing_store_, object_store_id, index_metadata), - new CreateIndexAbortOperation(this, object_store_id, index_id)); - - AddIndex(object_store_id, index_metadata, index_id); -} - -void CreateIndexOperation::Perform(IndexedDBTransaction* transaction) { - IDB_TRACE("CreateIndexOperation"); - if (!backing_store_->CreateIndex(transaction->BackingStoreTransaction(), - transaction->database()->id(), - object_store_id_, - index_metadata_.id, - index_metadata_.name, - index_metadata_.key_path, - index_metadata_.unique, - index_metadata_.multi_entry)) { - string16 error_string = ASCIIToUTF16("Internal error creating index '") + - index_metadata_.name + ASCIIToUTF16("'."); - transaction->Abort(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, error_string)); - return; - } -} - -void CreateIndexAbortOperation::Perform(IndexedDBTransaction* transaction) { - IDB_TRACE("CreateIndexAbortOperation"); - DCHECK(!transaction); - database_->RemoveIndex(object_store_id_, index_id_); -} - -void IndexedDBDatabaseImpl::DeleteIndex(int64 transaction_id, - int64 object_store_id, - int64 index_id) { - IDB_TRACE("IndexedDBDatabaseImpl::delete_index"); - TransactionMap::const_iterator trans_iterator = - transactions_.find(transaction_id); - if (trans_iterator == transactions_.end()) - return; - IndexedDBTransaction* transaction = trans_iterator->second; - DCHECK_EQ(transaction->mode(), indexed_db::TRANSACTION_VERSION_CHANGE); - - DCHECK(metadata_.object_stores.find(object_store_id) != - metadata_.object_stores.end()); - IndexedDBObjectStoreMetadata object_store = - metadata_.object_stores[object_store_id]; - - DCHECK(object_store.indexes.find(index_id) != object_store.indexes.end()); - const IndexedDBIndexMetadata& index_metadata = object_store.indexes[index_id]; - - transaction->ScheduleTask( - new DeleteIndexOperation(backing_store_, object_store_id, index_metadata), - new DeleteIndexAbortOperation(this, object_store_id, index_metadata)); - - RemoveIndex(object_store_id, index_id); -} - -void DeleteIndexOperation::Perform(IndexedDBTransaction* transaction) { - IDB_TRACE("DeleteIndexOperation"); - bool ok = backing_store_->DeleteIndex(transaction->BackingStoreTransaction(), - transaction->database()->id(), - object_store_id_, - index_metadata_.id); - if (!ok) { - string16 error_string = ASCIIToUTF16("Internal error deleting index '") + - index_metadata_.name + ASCIIToUTF16("'."); - scoped_refptr<IndexedDBDatabaseError> error = - IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, error_string); - transaction->Abort(error); - } -} - -void DeleteIndexAbortOperation::Perform(IndexedDBTransaction* transaction) { - IDB_TRACE("DeleteIndexAbortOperation"); - DCHECK(!transaction); - database_->AddIndex( - object_store_id_, index_metadata_, IndexedDBIndexMetadata::kInvalidId); -} - -void IndexedDBDatabaseImpl::Commit(int64 transaction_id) { - // The frontend suggests that we commit, but we may have previously initiated - // an abort, and so have disposed of the transaction. on_abort has already - // been dispatched to the frontend, so it will find out about that - // asynchronously. - if (transactions_.find(transaction_id) != transactions_.end()) - transactions_[transaction_id]->Commit(); -} - -void IndexedDBDatabaseImpl::Abort(int64 transaction_id) { - // If the transaction is unknown, then it has already been aborted by the - // backend before this call so it is safe to ignore it. - if (transactions_.find(transaction_id) != transactions_.end()) - transactions_[transaction_id]->Abort(); -} - -void IndexedDBDatabaseImpl::Abort(int64 transaction_id, - scoped_refptr<IndexedDBDatabaseError> error) { - // If the transaction is unknown, then it has already been aborted by the - // backend before this call so it is safe to ignore it. - if (transactions_.find(transaction_id) != transactions_.end()) - transactions_[transaction_id]->Abort(error); -} - -void IndexedDBDatabaseImpl::Get( - int64 transaction_id, - int64 object_store_id, - int64 index_id, - scoped_ptr<IndexedDBKeyRange> key_range, - bool key_only, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) { - IDB_TRACE("IndexedDBDatabaseImpl::get"); - TransactionMap::const_iterator trans_iterator = - transactions_.find(transaction_id); - if (trans_iterator == transactions_.end()) - return; - IndexedDBTransaction* transaction = trans_iterator->second; - - transaction->ScheduleTask(new GetOperation( - backing_store_, - metadata_, - object_store_id, - index_id, - key_range.Pass(), - key_only ? indexed_db::CURSOR_KEY_ONLY : indexed_db::CURSOR_KEY_AND_VALUE, - callbacks)); -} - -void GetOperation::Perform(IndexedDBTransaction* transaction) { - IDB_TRACE("GetOperation"); - - const IndexedDBKey* key; - - scoped_ptr<IndexedDBBackingStore::Cursor> backing_store_cursor; - if (key_range_->IsOnlyKey()) { - key = &key_range_->lower(); - } else { - if (index_id_ == IndexedDBIndexMetadata::kInvalidId) { - DCHECK_NE(cursor_type_, indexed_db::CURSOR_KEY_ONLY); - // ObjectStore Retrieval Operation - backing_store_cursor = backing_store_->OpenObjectStoreCursor( - transaction->BackingStoreTransaction(), - database_id_, - object_store_id_, - *key_range_, - indexed_db::CURSOR_NEXT); - } else if (cursor_type_ == indexed_db::CURSOR_KEY_ONLY) { - // Index Value Retrieval Operation - backing_store_cursor = backing_store_->OpenIndexKeyCursor( - transaction->BackingStoreTransaction(), - database_id_, - object_store_id_, - index_id_, - *key_range_, - indexed_db::CURSOR_NEXT); - } else { - // Index Referenced Value Retrieval Operation - backing_store_cursor = backing_store_->OpenIndexCursor( - transaction->BackingStoreTransaction(), - database_id_, - object_store_id_, - index_id_, - *key_range_, - indexed_db::CURSOR_NEXT); - } - - if (!backing_store_cursor) { - callbacks_->OnSuccess(); - return; - } - - key = &backing_store_cursor->key(); - } - - scoped_ptr<IndexedDBKey> primary_key; - bool ok; - if (index_id_ == IndexedDBIndexMetadata::kInvalidId) { - // Object Store Retrieval Operation - std::vector<char> value; - ok = backing_store_->GetRecord(transaction->BackingStoreTransaction(), - database_id_, - object_store_id_, - *key, - value); - if (!ok) { - callbacks_->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16("Internal error in get_record."))); - return; - } - - if (value.empty()) { - callbacks_->OnSuccess(); - return; - } - - if (auto_increment_ && !key_path_.IsNull()) { - callbacks_->OnSuccess(&value, *key, key_path_); - return; - } - - callbacks_->OnSuccess(&value); - return; - } - - // From here we are dealing only with indexes. - ok = backing_store_->GetPrimaryKeyViaIndex( - transaction->BackingStoreTransaction(), - database_id_, - object_store_id_, - index_id_, - *key, - &primary_key); - if (!ok) { - callbacks_->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16("Internal error in get_primary_key_via_index."))); - return; - } - if (!primary_key) { - callbacks_->OnSuccess(); - return; - } - if (cursor_type_ == indexed_db::CURSOR_KEY_ONLY) { - // Index Value Retrieval Operation - callbacks_->OnSuccess(*primary_key); - return; - } - - // Index Referenced Value Retrieval Operation - std::vector<char> value; - ok = backing_store_->GetRecord(transaction->BackingStoreTransaction(), - database_id_, - object_store_id_, - *primary_key, - value); - if (!ok) { - callbacks_->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16("Internal error in get_record."))); - return; - } - - if (value.empty()) { - callbacks_->OnSuccess(); - return; - } - if (auto_increment_ && !key_path_.IsNull()) { - callbacks_->OnSuccess(&value, *primary_key, key_path_); - return; - } - callbacks_->OnSuccess(&value); -} - -static scoped_ptr<IndexedDBKey> GenerateKey( - scoped_refptr<IndexedDBBackingStore> backing_store, - scoped_refptr<IndexedDBTransaction> transaction, - int64 database_id, - int64 object_store_id) { - const int64 max_generator_value = - 9007199254740992LL; // Maximum integer storable as ECMAScript number. - int64 current_number; - bool ok = backing_store->GetKeyGeneratorCurrentNumber( - transaction->BackingStoreTransaction(), - database_id, - object_store_id, - current_number); - if (!ok) { - LOG(ERROR) << "Failed to get_key_generator_current_number"; - return make_scoped_ptr(new IndexedDBKey()); - } - if (current_number < 0 || current_number > max_generator_value) - return make_scoped_ptr(new IndexedDBKey()); - - return make_scoped_ptr( - new IndexedDBKey(current_number, WebIDBKey::NumberType)); -} - -static bool UpdateKeyGenerator( - scoped_refptr<IndexedDBBackingStore> backing_store, - scoped_refptr<IndexedDBTransaction> transaction, - int64 database_id, - int64 object_store_id, - const IndexedDBKey* key, - bool check_current) { - DCHECK(key && key->type() == WebIDBKey::NumberType); - return backing_store->MaybeUpdateKeyGeneratorCurrentNumber( - transaction->BackingStoreTransaction(), - database_id, - object_store_id, - static_cast<int64>(floor(key->number())) + 1, - check_current); -} - -void IndexedDBDatabaseImpl::Put( - int64 transaction_id, - int64 object_store_id, - std::vector<char>* value, - scoped_ptr<IndexedDBKey> key, - PutMode put_mode, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - const std::vector<int64>& index_ids, - const std::vector<IndexKeys>& index_keys) { - IDB_TRACE("IndexedDBDatabaseImpl::put"); - TransactionMap::const_iterator trans_iterator = - transactions_.find(transaction_id); - if (trans_iterator == transactions_.end()) - return; - IndexedDBTransaction* transaction = trans_iterator->second; - DCHECK_NE(transaction->mode(), indexed_db::TRANSACTION_READ_ONLY); - - const IndexedDBObjectStoreMetadata object_store_metadata = - metadata_.object_stores[object_store_id]; - - DCHECK(key); - DCHECK(object_store_metadata.auto_increment || key->IsValid()); - transaction->ScheduleTask(new PutOperation(backing_store_, - id(), - object_store_metadata, - value, - key.Pass(), - put_mode, - callbacks, - index_ids, - index_keys)); -} - -void PutOperation::Perform(IndexedDBTransaction* transaction) { - IDB_TRACE("PutOperation"); - DCHECK_NE(transaction->mode(), indexed_db::TRANSACTION_READ_ONLY); - DCHECK_EQ(index_ids_.size(), index_keys_.size()); - bool key_was_generated = false; - - scoped_ptr<IndexedDBKey> key; - if (put_mode_ != IndexedDBDatabase::CURSOR_UPDATE && - object_store_.auto_increment && !key_->IsValid()) { - scoped_ptr<IndexedDBKey> auto_inc_key = GenerateKey( - backing_store_, transaction, database_id_, object_store_.id); - key_was_generated = true; - if (!auto_inc_key->IsValid()) { - callbacks_->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionConstraintError, - ASCIIToUTF16("Maximum key generator value reached."))); - return; - } - key = auto_inc_key.Pass(); - } else { - key = key_.Pass(); - } - - DCHECK(key->IsValid()); - - IndexedDBBackingStore::RecordIdentifier record_identifier; - if (put_mode_ == IndexedDBDatabase::ADD_ONLY) { - bool found = false; - bool ok = backing_store_->KeyExistsInObjectStore( - transaction->BackingStoreTransaction(), - database_id_, - object_store_.id, - *key.get(), - &record_identifier, - found); - if (!ok) { - callbacks_->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16("Internal error checking key existence."))); - return; - } - if (found) { - callbacks_->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionConstraintError, - ASCIIToUTF16("Key already exists in the object store."))); - return; - } - } - - ScopedVector<IndexedDBObjectStoreImpl::IndexWriter> index_writers; - string16 error_message; - bool obeys_constraints = false; - bool backing_store_success = - IndexedDBObjectStoreImpl::MakeIndexWriters(transaction, - backing_store_.get(), - database_id_, - object_store_, - *key, - key_was_generated, - index_ids_, - index_keys_, - &index_writers, - &error_message, - &obeys_constraints); - if (!backing_store_success) { - callbacks_->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16( - "Internal error: backing store error updating index keys."))); - return; - } - if (!obeys_constraints) { - callbacks_->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionConstraintError, error_message)); - return; - } - - // Before this point, don't do any mutation. After this point, rollback the - // transaction in case of error. - backing_store_success = - backing_store_->PutRecord(transaction->BackingStoreTransaction(), - database_id_, - object_store_.id, - *key.get(), - value_, - &record_identifier); - if (!backing_store_success) { - callbacks_->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16( - "Internal error: backing store error performing put/add."))); - return; - } - - for (size_t i = 0; i < index_writers.size(); ++i) { - IndexedDBObjectStoreImpl::IndexWriter* index_writer = index_writers[i]; - index_writer->WriteIndexKeys(record_identifier, - backing_store_, - transaction->BackingStoreTransaction(), - database_id_, - object_store_.id); - } - - if (object_store_.auto_increment && - put_mode_ != IndexedDBDatabase::CURSOR_UPDATE && - key->type() == WebIDBKey::NumberType) { - bool ok = UpdateKeyGenerator(backing_store_, - transaction, - database_id_, - object_store_.id, - key.get(), - !key_was_generated); - if (!ok) { - callbacks_->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16("Internal error updating key generator."))); - return; - } - } - - callbacks_->OnSuccess(*key); -} - -void IndexedDBDatabaseImpl::SetIndexKeys( - int64 transaction_id, - int64 object_store_id, - scoped_ptr<IndexedDBKey> primary_key, - const std::vector<int64>& index_ids, - const std::vector<IndexKeys>& index_keys) { - IDB_TRACE("IndexedDBDatabaseImpl::set_index_keys"); - TransactionMap::const_iterator trans_iterator = - transactions_.find(transaction_id); - if (trans_iterator == transactions_.end()) - return; - IndexedDBTransaction* transaction = trans_iterator->second; - DCHECK_EQ(transaction->mode(), indexed_db::TRANSACTION_VERSION_CHANGE); - - scoped_refptr<IndexedDBBackingStore> store = BackingStore(); - // TODO(jsbell): This method could be asynchronous, but we need to - // evaluate if it's worth the extra complexity. - IndexedDBBackingStore::RecordIdentifier record_identifier; - bool found = false; - bool ok = - store->KeyExistsInObjectStore(transaction->BackingStoreTransaction(), - metadata_.id, - object_store_id, - *primary_key, - &record_identifier, - found); - if (!ok) { - transaction->Abort(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16("Internal error setting index keys."))); - return; - } - if (!found) { - scoped_refptr<IndexedDBDatabaseError> error = - IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16( - "Internal error setting index keys for object store.")); - transaction->Abort(error); - return; - } - - ScopedVector<IndexedDBObjectStoreImpl::IndexWriter> index_writers; - string16 error_message; - bool obeys_constraints = false; - DCHECK(metadata_.object_stores.find(object_store_id) != - metadata_.object_stores.end()); - const IndexedDBObjectStoreMetadata& object_store_metadata = - metadata_.object_stores[object_store_id]; - bool backing_store_success = - IndexedDBObjectStoreImpl::MakeIndexWriters(transaction, - store.get(), - id(), - object_store_metadata, - *primary_key, - false, - index_ids, - index_keys, - &index_writers, - &error_message, - &obeys_constraints); - if (!backing_store_success) { - transaction->Abort(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16( - "Internal error: backing store error updating index keys."))); - return; - } - if (!obeys_constraints) { - transaction->Abort(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionConstraintError, error_message)); - return; - } - - for (size_t i = 0; i < index_writers.size(); ++i) { - IndexedDBObjectStoreImpl::IndexWriter* index_writer = index_writers[i]; - index_writer->WriteIndexKeys(record_identifier, - store.get(), - transaction->BackingStoreTransaction(), - id(), - object_store_id); - } -} - -void IndexedDBDatabaseImpl::SetIndexesReady( - int64 transaction_id, - int64, - const std::vector<int64>& index_ids) { - IDB_TRACE("IndexedDBObjectStoreImpl::set_indexes_ready"); - - TransactionMap::const_iterator trans_iterator = - transactions_.find(transaction_id); - if (trans_iterator == transactions_.end()) - return; - IndexedDBTransaction* transaction = trans_iterator->second; - - transaction->ScheduleTask(IndexedDBDatabase::PREEMPTIVE_TASK, - new SetIndexesReadyOperation(index_ids.size())); -} - -void SetIndexesReadyOperation::Perform(IndexedDBTransaction* transaction) { - IDB_TRACE("SetIndexesReadyOperation"); - for (size_t i = 0; i < index_count_; ++i) - transaction->DidCompletePreemptiveEvent(); -} - -void IndexedDBDatabaseImpl::OpenCursor( - int64 transaction_id, - int64 object_store_id, - int64 index_id, - scoped_ptr<IndexedDBKeyRange> key_range, - indexed_db::CursorDirection direction, - bool key_only, - TaskType task_type, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) { - IDB_TRACE("IndexedDBDatabaseImpl::open_cursor"); - TransactionMap::const_iterator trans_iterator = - transactions_.find(transaction_id); - if (trans_iterator == transactions_.end()) - return; - IndexedDBTransaction* transaction = trans_iterator->second; - - transaction->ScheduleTask(new OpenCursorOperation( - backing_store_, - id(), - object_store_id, - index_id, - key_range.Pass(), - direction, - key_only ? indexed_db::CURSOR_KEY_ONLY : indexed_db::CURSOR_KEY_AND_VALUE, - task_type, - callbacks)); -} - -void OpenCursorOperation::Perform(IndexedDBTransaction* transaction) { - IDB_TRACE("OpenCursorOperation"); - - // The frontend has begun indexing, so this pauses the transaction - // until the indexing is complete. This can't happen any earlier - // because we don't want to switch to early mode in case multiple - // indexes are being created in a row, with Put()'s in between. - if (task_type_ == IndexedDBDatabase::PREEMPTIVE_TASK) - transaction->AddPreemptiveEvent(); - - scoped_ptr<IndexedDBBackingStore::Cursor> backing_store_cursor; - if (index_id_ == IndexedDBIndexMetadata::kInvalidId) { - DCHECK_NE(cursor_type_, indexed_db::CURSOR_KEY_ONLY); - backing_store_cursor = backing_store_->OpenObjectStoreCursor( - transaction->BackingStoreTransaction(), - database_id_, - object_store_id_, - *key_range_, - direction_); - } else { - DCHECK_EQ(task_type_, IndexedDBDatabase::NORMAL_TASK); - if (cursor_type_ == indexed_db::CURSOR_KEY_ONLY) { - backing_store_cursor = backing_store_->OpenIndexKeyCursor( - transaction->BackingStoreTransaction(), - database_id_, - object_store_id_, - index_id_, - *key_range_, - direction_); - } else { - backing_store_cursor = backing_store_->OpenIndexCursor( - transaction->BackingStoreTransaction(), - database_id_, - object_store_id_, - index_id_, - *key_range_, - direction_); - } - } - - if (!backing_store_cursor) { - callbacks_->OnSuccess(static_cast<std::vector<char>*>(NULL)); - return; - } - - IndexedDBDatabase::TaskType task_type( - static_cast<IndexedDBDatabase::TaskType>(task_type_)); - scoped_refptr<IndexedDBCursorImpl> cursor = - IndexedDBCursorImpl::Create(backing_store_cursor.Pass(), - cursor_type_, - task_type, - transaction, - object_store_id_); - callbacks_->OnSuccess( - cursor, cursor->key(), cursor->primary_key(), cursor->Value()); -} - -void IndexedDBDatabaseImpl::Count( - int64 transaction_id, - int64 object_store_id, - int64 index_id, - scoped_ptr<IndexedDBKeyRange> key_range, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) { - IDB_TRACE("IndexedDBDatabaseImpl::count"); - TransactionMap::const_iterator trans_iterator = - transactions_.find(transaction_id); - if (trans_iterator == transactions_.end()) - return; - IndexedDBTransaction* transaction = trans_iterator->second; - - DCHECK(metadata_.object_stores.find(object_store_id) != - metadata_.object_stores.end()); - transaction->ScheduleTask(new CountOperation(backing_store_, - id(), - object_store_id, - index_id, - key_range.Pass(), - callbacks)); -} - -void CountOperation::Perform(IndexedDBTransaction* transaction) { - IDB_TRACE("CountOperation"); - uint32 count = 0; - scoped_ptr<IndexedDBBackingStore::Cursor> backing_store_cursor; - - if (index_id_ == IndexedDBIndexMetadata::kInvalidId) { - backing_store_cursor = backing_store_->OpenObjectStoreKeyCursor( - transaction->BackingStoreTransaction(), - database_id_, - object_store_id_, - *key_range_, - indexed_db::CURSOR_NEXT); - } else { - backing_store_cursor = backing_store_->OpenIndexKeyCursor( - transaction->BackingStoreTransaction(), - database_id_, - object_store_id_, - index_id_, - *key_range_, - indexed_db::CURSOR_NEXT); - } - if (!backing_store_cursor) { - callbacks_->OnSuccess(count); - return; - } - - do { - ++count; - } while (backing_store_cursor->ContinueFunction(0)); - - callbacks_->OnSuccess(count); -} - -void IndexedDBDatabaseImpl::DeleteRange( - int64 transaction_id, - int64 object_store_id, - scoped_ptr<IndexedDBKeyRange> key_range, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) { - IDB_TRACE("IndexedDBDatabaseImpl::delete_range"); - TransactionMap::const_iterator trans_iterator = - transactions_.find(transaction_id); - if (trans_iterator == transactions_.end()) - return; - IndexedDBTransaction* transaction = trans_iterator->second; - - transaction->ScheduleTask(new DeleteRangeOperation( - backing_store_, id(), object_store_id, key_range.Pass(), callbacks)); -} - -void DeleteRangeOperation::Perform(IndexedDBTransaction* transaction) { - IDB_TRACE("DeleteRangeOperation"); - scoped_ptr<IndexedDBBackingStore::Cursor> backing_store_cursor = - backing_store_->OpenObjectStoreCursor( - transaction->BackingStoreTransaction(), - database_id_, - object_store_id_, - *key_range_, - indexed_db::CURSOR_NEXT); - if (backing_store_cursor) { - do { - if (!backing_store_->DeleteRecord( - transaction->BackingStoreTransaction(), - database_id_, - object_store_id_, - backing_store_cursor->record_identifier())) { - callbacks_->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16("Internal error deleting data in range"))); - return; - } - } while (backing_store_cursor->ContinueFunction(0)); - } - - callbacks_->OnSuccess(); -} - -void IndexedDBDatabaseImpl::Clear( - int64 transaction_id, - int64 object_store_id, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) { - IDB_TRACE("IndexedDBDatabaseImpl::clear"); - TransactionMap::const_iterator trans_iterator = - transactions_.find(transaction_id); - if (trans_iterator == transactions_.end()) - return; - IndexedDBTransaction* transaction = trans_iterator->second; - DCHECK_NE(transaction->mode(), indexed_db::TRANSACTION_READ_ONLY); - - transaction->ScheduleTask( - new ClearOperation(backing_store_, id(), object_store_id, callbacks)); -} - -void ClearOperation::Perform(IndexedDBTransaction* transaction) { - IDB_TRACE("ObjectStoreClearOperation"); - if (!backing_store_->ClearObjectStore(transaction->BackingStoreTransaction(), - database_id_, - object_store_id_)) { - callbacks_->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16("Internal error clearing object store"))); - return; - } - callbacks_->OnSuccess(); -} - -void DeleteObjectStoreOperation::Perform(IndexedDBTransaction* transaction) { - IDB_TRACE("DeleteObjectStoreOperation"); - bool ok = - backing_store_->DeleteObjectStore(transaction->BackingStoreTransaction(), - transaction->database()->id(), - object_store_metadata_.id); - if (!ok) { - string16 error_string = - ASCIIToUTF16("Internal error deleting object store '") + - object_store_metadata_.name + ASCIIToUTF16("'."); - scoped_refptr<IndexedDBDatabaseError> error = - IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, error_string); - transaction->Abort(error); - } -} - -void IndexedDBDatabaseImpl::VersionChangeOperation::Perform( - IndexedDBTransaction* transaction) { - IDB_TRACE("VersionChangeOperation"); - int64 database_id = database_->id(); - int64 old_version = database_->metadata_.int_version; - DCHECK_GT(version_, old_version); - database_->metadata_.int_version = version_; - if (!database_->backing_store_->UpdateIDBDatabaseIntVersion( - transaction->BackingStoreTransaction(), - database_id, - database_->metadata_.int_version)) { - scoped_refptr<IndexedDBDatabaseError> error = - IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16("Internal error writing data to stable storage when " - "updating version.")); - callbacks_->OnError(error); - transaction->Abort(error); - return; - } - DCHECK(!database_->pending_second_half_open_); - database_->pending_second_half_open_.reset(new PendingOpenCall( - callbacks_, database_callbacks_, transaction_id_, version_)); - callbacks_->OnUpgradeNeeded(old_version, database_, database_->metadata()); -} - -void IndexedDBDatabaseImpl::TransactionStarted( - IndexedDBTransaction* transaction) { - - if (transaction->mode() == indexed_db::TRANSACTION_VERSION_CHANGE) { - DCHECK(!running_version_change_transaction_); - running_version_change_transaction_ = transaction; - } -} - -void IndexedDBDatabaseImpl::TransactionFinished( - IndexedDBTransaction* transaction) { - - DCHECK(transactions_.find(transaction->id()) != transactions_.end()); - DCHECK_EQ(transactions_[transaction->id()], transaction); - transactions_.erase(transaction->id()); - if (transaction->mode() == indexed_db::TRANSACTION_VERSION_CHANGE) { - DCHECK_EQ(transaction, running_version_change_transaction_); - running_version_change_transaction_ = NULL; - } -} - -void IndexedDBDatabaseImpl::TransactionFinishedAndAbortFired( - IndexedDBTransaction* transaction) { - if (transaction->mode() == indexed_db::TRANSACTION_VERSION_CHANGE) { - if (pending_second_half_open_) { - pending_second_half_open_->Callbacks() - ->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionAbortError, - ASCIIToUTF16("Version change transaction was aborted in " - "upgradeneeded event handler."))); - pending_second_half_open_.reset(); - } - ProcessPendingCalls(); - } -} - -void IndexedDBDatabaseImpl::TransactionFinishedAndCompleteFired( - IndexedDBTransaction* transaction) { - if (transaction->mode() == indexed_db::TRANSACTION_VERSION_CHANGE) { - DCHECK(pending_second_half_open_); - if (pending_second_half_open_) { - DCHECK_EQ(pending_second_half_open_->Version(), metadata_.int_version); - DCHECK(metadata_.id != kInvalidId); - pending_second_half_open_->Callbacks()->OnSuccess(this, this->metadata()); - pending_second_half_open_.reset(); - } - ProcessPendingCalls(); - } -} - -size_t IndexedDBDatabaseImpl::ConnectionCount() const { - // This does not include pending open calls, as those should not block version - // changes and deletes. - return database_callbacks_set_.size(); -} - -void IndexedDBDatabaseImpl::ProcessPendingCalls() { - if (pending_second_half_open_) { - DCHECK_EQ(pending_second_half_open_->Version(), metadata_.int_version); - DCHECK(metadata_.id != kInvalidId); - scoped_ptr<PendingOpenCall> pending_call = pending_second_half_open_.Pass(); - pending_call->Callbacks()->OnSuccess(this, this->metadata()); - // Fall through when complete, as pending opens may be unblocked. - } - - if (pending_run_version_change_transaction_call_ && ConnectionCount() == 1) { - DCHECK(pending_run_version_change_transaction_call_->Version() > - metadata_.int_version); - scoped_ptr<PendingOpenCall> pending_call = - pending_run_version_change_transaction_call_.Pass(); - RunVersionChangeTransactionFinal(pending_call->Callbacks(), - pending_call->DatabaseCallbacks(), - pending_call->TransactionId(), - pending_call->Version()); - DCHECK_EQ(static_cast<size_t>(1), ConnectionCount()); - // Fall through would be a no-op, since transaction must complete - // asynchronously. - DCHECK(IsDeleteDatabaseBlocked()); - DCHECK(IsOpenConnectionBlocked()); - return; - } - - if (!IsDeleteDatabaseBlocked()) { - PendingDeleteCallList pending_delete_calls; - pending_delete_calls_.swap(pending_delete_calls); - while (!pending_delete_calls.empty()) { - // Only the first delete call will delete the database, but each must fire - // callbacks. - scoped_ptr<PendingDeleteCall> pending_delete_call( - pending_delete_calls.front()); - pending_delete_calls.pop_front(); - DeleteDatabaseFinal(pending_delete_call->Callbacks()); - } - // delete_database_final should never re-queue calls. - DCHECK(pending_delete_calls_.empty()); - // Fall through when complete, as pending opens may be unblocked. - } - - if (!IsOpenConnectionBlocked()) { - PendingOpenCallList pending_open_calls; - pending_open_calls_.swap(pending_open_calls); - while (!pending_open_calls.empty()) { - scoped_ptr<PendingOpenCall> pending_open_call(pending_open_calls.front()); - pending_open_calls.pop_front(); - OpenConnection(pending_open_call->Callbacks(), - pending_open_call->DatabaseCallbacks(), - pending_open_call->TransactionId(), - pending_open_call->Version()); - } - } -} - -void IndexedDBDatabaseImpl::CreateTransaction( - int64 transaction_id, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> callbacks, - const std::vector<int64>& object_store_ids, - uint16 mode) { - - DCHECK(database_callbacks_set_.has(callbacks)); - - scoped_refptr<IndexedDBTransaction> transaction = - IndexedDBTransaction::Create( - transaction_id, - callbacks, - object_store_ids, - static_cast<indexed_db::TransactionMode>(mode), - this); - DCHECK(transactions_.find(transaction_id) == transactions_.end()); - transactions_[transaction_id] = transaction; -} - -bool IndexedDBDatabaseImpl::IsOpenConnectionBlocked() const { - return !pending_delete_calls_.empty() || - running_version_change_transaction_ || - pending_run_version_change_transaction_call_; -} - -void IndexedDBDatabaseImpl::OpenConnection( - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks, - int64 transaction_id, - int64 version) { - DCHECK(backing_store_.get()); - - // TODO(jsbell): Should have a priority queue so that higher version - // requests are processed first. http://crbug.com/225850 - if (IsOpenConnectionBlocked()) { - pending_open_calls_.push_back(new PendingOpenCall( - callbacks, database_callbacks, transaction_id, version)); - return; - } - - if (metadata_.id == kInvalidId) { - // The database was deleted then immediately re-opened; OpenInternal() - // recreates it in the backing store. - if (OpenInternal()) { - DCHECK_EQ(metadata_.int_version, - IndexedDBDatabaseMetadata::NO_INT_VERSION); - } else { - string16 message; - scoped_refptr<IndexedDBDatabaseError> error; - if (version == IndexedDBDatabaseMetadata::NO_INT_VERSION) - message = ASCIIToUTF16( - "Internal error opening database with no version specified."); - else - message = - ASCIIToUTF16("Internal error opening database with version ") + - Int64ToString16(version); - callbacks->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, message)); - return; - } - } - - // We infer that the database didn't exist from its lack of either type of - // version. - bool is_new_database = - metadata_.version == kNoStringVersion && - metadata_.int_version == IndexedDBDatabaseMetadata::NO_INT_VERSION; - - if (version == IndexedDBDatabaseMetadata::DEFAULT_INT_VERSION) { - // For unit tests only - skip upgrade steps. Calling from script with - // DEFAULT_INT_VERSION throws exception. - // TODO(jsbell): Assert that we're executing a unit test. - DCHECK(is_new_database); - database_callbacks_set_.insert(database_callbacks); - callbacks->OnSuccess(this, this->metadata()); - return; - } - - if (version == IndexedDBDatabaseMetadata::NO_INT_VERSION) { - if (!is_new_database) { - database_callbacks_set_.insert(database_callbacks); - callbacks->OnSuccess(this, this->metadata()); - return; - } - // Spec says: If no version is specified and no database exists, set - // database version to 1. - version = 1; - } - - if (version > metadata_.int_version) { - database_callbacks_set_.insert(database_callbacks); - RunVersionChangeTransaction( - callbacks, database_callbacks, transaction_id, version); - return; - } - if (version < metadata_.int_version) { - callbacks->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionVersionError, - ASCIIToUTF16("The requested version (") + Int64ToString16(version) + - ASCIIToUTF16(") is less than the existing version (") + - Int64ToString16(metadata_.int_version) + ASCIIToUTF16(")."))); - return; - } - DCHECK_EQ(version, metadata_.int_version); - database_callbacks_set_.insert(database_callbacks); - callbacks->OnSuccess(this, this->metadata()); -} - -void IndexedDBDatabaseImpl::RunVersionChangeTransaction( - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks, - int64 transaction_id, - int64 requested_version) { - - DCHECK(callbacks); - DCHECK(database_callbacks_set_.has(database_callbacks)); - if (ConnectionCount() > 1) { - // Front end ensures the event is not fired at connections that have - // close_pending set. - for (DatabaseCallbacksSet::const_iterator it = - database_callbacks_set_.begin(); - it != database_callbacks_set_.end(); - ++it) { - if (*it != database_callbacks.get()) - (*it)->OnVersionChange(metadata_.int_version, requested_version); - } - // TODO(jsbell): Remove the call to on_blocked and instead wait - // until the frontend tells us that all the "versionchange" events - // have been delivered. http://crbug.com/100123 - callbacks->OnBlocked(metadata_.int_version); - - DCHECK(!pending_run_version_change_transaction_call_); - pending_run_version_change_transaction_call_.reset(new PendingOpenCall( - callbacks, database_callbacks, transaction_id, requested_version)); - return; - } - RunVersionChangeTransactionFinal( - callbacks, database_callbacks, transaction_id, requested_version); -} - -void IndexedDBDatabaseImpl::RunVersionChangeTransactionFinal( - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks, - int64 transaction_id, - int64 requested_version) { - - std::vector<int64> object_store_ids; - CreateTransaction(transaction_id, - database_callbacks, - object_store_ids, - indexed_db::TRANSACTION_VERSION_CHANGE); - scoped_refptr<IndexedDBTransaction> transaction = - transactions_[transaction_id]; - - transaction->ScheduleTask( - new VersionChangeOperation(this, - transaction_id, - requested_version, - callbacks, - database_callbacks), - new VersionChangeAbortOperation( - this, metadata_.version, metadata_.int_version)); - - DCHECK(!pending_second_half_open_); -} - -void IndexedDBDatabaseImpl::DeleteDatabase( - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) { - - if (IsDeleteDatabaseBlocked()) { - for (DatabaseCallbacksSet::const_iterator it = - database_callbacks_set_.begin(); - it != database_callbacks_set_.end(); - ++it) { - // Front end ensures the event is not fired at connections that have - // close_pending set. - (*it)->OnVersionChange(metadata_.int_version, - IndexedDBDatabaseMetadata::NO_INT_VERSION); - } - // TODO(jsbell): Only fire on_blocked if there are open - // connections after the VersionChangeEvents are received, not - // just set up to fire. http://crbug.com/100123 - callbacks->OnBlocked(metadata_.int_version); - pending_delete_calls_.push_back(new PendingDeleteCall(callbacks)); - return; - } - DeleteDatabaseFinal(callbacks); -} - -bool IndexedDBDatabaseImpl::IsDeleteDatabaseBlocked() const { - return !!ConnectionCount(); -} - -void IndexedDBDatabaseImpl::DeleteDatabaseFinal( - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) { - DCHECK(!IsDeleteDatabaseBlocked()); - DCHECK(backing_store_); - if (!backing_store_->DeleteDatabase(metadata_.name)) { - callbacks->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16("Internal error deleting database."))); - return; - } - metadata_.version = kNoStringVersion; - metadata_.id = kInvalidId; - metadata_.int_version = IndexedDBDatabaseMetadata::NO_INT_VERSION; - metadata_.object_stores.clear(); - callbacks->OnSuccess(); -} - -void IndexedDBDatabaseImpl::Close( - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> callbacks) { - DCHECK(callbacks); - DCHECK(database_callbacks_set_.has(callbacks)); - - // Close outstanding transactions from the closing connection. This - // can not happen if the close is requested by the connection itself - // as the front-end defers the close until all transactions are - // complete, so something unusual has happened e.g. unexpected - // process termination. - { - TransactionMap transactions(transactions_); - for (TransactionMap::const_iterator it = transactions.begin(), - end = transactions.end(); - it != end; - ++it) { - if (it->second->connection() == callbacks) - it->second->Abort(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16("Connection is closing."))); - } - } - - database_callbacks_set_.erase(callbacks); - if (pending_second_half_open_ && - pending_second_half_open_->DatabaseCallbacks() == callbacks) { - pending_second_half_open_->Callbacks() - ->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionAbortError, - ASCIIToUTF16("The connection was closed."))); - pending_second_half_open_.reset(); - } - - // process_pending_calls allows the inspector to process a pending open call - // and call close, reentering IndexedDBDatabaseImpl::close. Then the - // backend would be removed both by the inspector closing its connection, and - // by the connection that first called close. - // To avoid that situation, don't proceed in case of reentrancy. - if (closing_connection_) - return; - base::AutoReset<bool> ClosingConnection(&closing_connection_, true); - ProcessPendingCalls(); - - // TODO(jsbell): Add a test for the pending_open_calls_ cases below. - if (!ConnectionCount() && !pending_open_calls_.size() && - !pending_delete_calls_.size()) { - DCHECK(transactions_.empty()); - - backing_store_ = NULL; - - // This check should only be false in unit tests. - // TODO(jsbell): Assert factory_ || we're executing a unit test. - if (factory_) - factory_->RemoveIDBDatabaseBackend(identifier_); - } -} - -void CreateObjectStoreAbortOperation::Perform( - IndexedDBTransaction* transaction) { - IDB_TRACE("CreateObjectStoreAbortOperation"); - DCHECK(!transaction); - database_->RemoveObjectStore(object_store_id_); -} - -void DeleteObjectStoreAbortOperation::Perform( - IndexedDBTransaction* transaction) { - IDB_TRACE("DeleteObjectStoreAbortOperation"); - DCHECK(!transaction); - database_->AddObjectStore(object_store_metadata_, - IndexedDBObjectStoreMetadata::kInvalidId); -} - -void IndexedDBDatabaseImpl::VersionChangeAbortOperation::Perform( - IndexedDBTransaction* transaction) { - IDB_TRACE("VersionChangeAbortOperation"); - DCHECK(!transaction); - database_->metadata_.version = previous_version_; - database_->metadata_.int_version = previous_int_version_; -} - -} // namespace content diff --git a/content/browser/indexed_db/indexed_db_database_impl.h b/content/browser/indexed_db/indexed_db_database_impl.h deleted file mode 100644 index d71cf0e..0000000 --- a/content/browser/indexed_db/indexed_db_database_impl.h +++ /dev/null @@ -1,204 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_DATABASE_IMPL_H_ -#define CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_DATABASE_IMPL_H_ - -#include <list> -#include <map> -#include <vector> - -#include "base/basictypes.h" -#include "content/browser/indexed_db/indexed_db_callbacks_wrapper.h" -#include "content/browser/indexed_db/indexed_db_metadata.h" -#include "content/browser/indexed_db/indexed_db_transaction_coordinator.h" -#include "content/browser/indexed_db/list_set.h" - -namespace content { - -class IndexedDBBackingStore; -class IndexedDBDatabase; -class IndexedDBFactoryImpl; -class IndexedDBTransaction; - -class IndexedDBDatabaseImpl : public IndexedDBDatabase { - public: - static scoped_refptr<IndexedDBDatabaseImpl> Create( - const string16& name, - IndexedDBBackingStore* database, - IndexedDBFactoryImpl* factory, - const string16& unique_identifier); - scoped_refptr<IndexedDBBackingStore> BackingStore() const; - - static const int64 kInvalidId = 0; - int64 id() const { return metadata_.id; } - void AddObjectStore(const IndexedDBObjectStoreMetadata& metadata, - int64 new_max_object_store_id); - void RemoveObjectStore(int64 object_store_id); - void AddIndex(int64 object_store_id, - const IndexedDBIndexMetadata& metadata, - int64 new_max_index_id); - void RemoveIndex(int64 object_store_id, int64 index_id); - - void OpenConnection( - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks, - int64 transaction_id, - int64 version); - void DeleteDatabase(scoped_refptr<IndexedDBCallbacksWrapper> callbacks); - const IndexedDBDatabaseMetadata& metadata() const { return metadata_; } - - // IndexedDBDatabase - virtual void CreateObjectStore(int64 transaction_id, - int64 object_store_id, - const string16& name, - const IndexedDBKeyPath& key_path, - bool auto_increment) OVERRIDE; - virtual void DeleteObjectStore(int64 transaction_id, int64 object_store_id) - OVERRIDE; - virtual void CreateTransaction( - int64 transaction_id, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> callbacks, - const std::vector<int64>& object_store_ids, - uint16 mode) OVERRIDE; - virtual void Close(scoped_refptr<IndexedDBDatabaseCallbacksWrapper> callbacks) - OVERRIDE; - - virtual void Commit(int64 transaction_id) OVERRIDE; - virtual void Abort(int64 transaction_id) OVERRIDE; - virtual void Abort(int64 transaction_id, - scoped_refptr<IndexedDBDatabaseError> error) OVERRIDE; - - virtual void CreateIndex(int64 transaction_id, - int64 object_store_id, - int64 index_id, - const string16& name, - const IndexedDBKeyPath& key_path, - bool unique, - bool multi_entry) OVERRIDE; - virtual void DeleteIndex(int64 transaction_id, - int64 object_store_id, - int64 index_id) OVERRIDE; - - IndexedDBTransactionCoordinator& transaction_coordinator() { - return transaction_coordinator_; - } - - void TransactionStarted(IndexedDBTransaction* transaction); - void TransactionFinished(IndexedDBTransaction* transaction); - void TransactionFinishedAndCompleteFired(IndexedDBTransaction* transaction); - void TransactionFinishedAndAbortFired(IndexedDBTransaction* transaction); - - virtual void Get(int64 transaction_id, - int64 object_store_id, - int64 index_id, - scoped_ptr<IndexedDBKeyRange> key_range, - bool key_only, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) OVERRIDE; - virtual void Put(int64 transaction_id, - int64 object_store_id, - std::vector<char>* value, - scoped_ptr<IndexedDBKey> key, - PutMode mode, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - const std::vector<int64>& index_ids, - const std::vector<IndexKeys>& index_keys) OVERRIDE; - virtual void SetIndexKeys(int64 transaction_id, - int64 object_store_id, - scoped_ptr<IndexedDBKey> primary_key, - const std::vector<int64>& index_ids, - const std::vector<IndexKeys>& index_keys) OVERRIDE; - virtual void SetIndexesReady(int64 transaction_id, - int64 object_store_id, - const std::vector<int64>& index_ids) OVERRIDE; - virtual void OpenCursor(int64 transaction_id, - int64 object_store_id, - int64 index_id, - scoped_ptr<IndexedDBKeyRange> key_range, - indexed_db::CursorDirection, - bool key_only, - TaskType task_type, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) - OVERRIDE; - virtual void Count(int64 transaction_id, - int64 object_store_id, - int64 index_id, - scoped_ptr<IndexedDBKeyRange> key_range, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) - OVERRIDE; - virtual void DeleteRange(int64 transaction_id, - int64 object_store_id, - scoped_ptr<IndexedDBKeyRange> key_range, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) - OVERRIDE; - virtual void Clear(int64 transaction_id, - int64 object_store_id, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks) - OVERRIDE; - - private: - IndexedDBDatabaseImpl(const string16& name, - IndexedDBBackingStore* database, - IndexedDBFactoryImpl* factory, - const string16& unique_identifier); - virtual ~IndexedDBDatabaseImpl(); - - bool IsOpenConnectionBlocked() const; - bool OpenInternal(); - void RunVersionChangeTransaction( - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks, - int64 transaction_id, - int64 requested_version); - void RunVersionChangeTransactionFinal( - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks, - int64 transaction_id, - int64 requested_version); - size_t ConnectionCount() const; - void ProcessPendingCalls(); - - bool IsDeleteDatabaseBlocked() const; - void DeleteDatabaseFinal(scoped_refptr<IndexedDBCallbacksWrapper> callbacks); - - class VersionChangeOperation; - - // When a "versionchange" transaction aborts, these restore the back-end - // object hierarchy. - class VersionChangeAbortOperation; - - scoped_refptr<IndexedDBBackingStore> backing_store_; - IndexedDBDatabaseMetadata metadata_; - - string16 identifier_; - // This might not need to be a scoped_refptr since the factory's lifetime is - // that of the page group, but it's better to be conservitive than sorry. - scoped_refptr<IndexedDBFactoryImpl> factory_; - - IndexedDBTransactionCoordinator transaction_coordinator_; - IndexedDBTransaction* running_version_change_transaction_; - - typedef std::map<int64, IndexedDBTransaction*> TransactionMap; - TransactionMap transactions_; - - class PendingOpenCall; - typedef std::list<PendingOpenCall*> PendingOpenCallList; - PendingOpenCallList pending_open_calls_; - scoped_ptr<PendingOpenCall> pending_run_version_change_transaction_call_; - scoped_ptr<PendingOpenCall> pending_second_half_open_; - - class PendingDeleteCall; - typedef std::list<PendingDeleteCall*> PendingDeleteCallList; - PendingDeleteCallList pending_delete_calls_; - - typedef list_set<scoped_refptr<IndexedDBDatabaseCallbacksWrapper> > - DatabaseCallbacksSet; - DatabaseCallbacksSet database_callbacks_set_; - - bool closing_connection_; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_DATABASE_IMPL_H_ diff --git a/content/browser/indexed_db/indexed_db_factory.h b/content/browser/indexed_db/indexed_db_factory.h deleted file mode 100644 index b7d380a..0000000 --- a/content/browser/indexed_db/indexed_db_factory.h +++ /dev/null @@ -1,47 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_FACTORY_H_ -#define CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_FACTORY_H_ - -#include "base/basictypes.h" -#include "base/memory/ref_counted.h" -#include "base/string16.h" - -namespace content { - -class IndexedDBCallbacksWrapper; -class IndexedDBDatabase; -class IndexedDBDatabaseCallbacksWrapper; - -class IndexedDBFactory : public base::RefCounted<IndexedDBFactory> { - public: - static scoped_refptr<IndexedDBFactory> Create(); - - virtual void GetDatabaseNames( - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - const string16& database_identifier, - const string16& data_dir) = 0; - virtual void Open( - const string16& name, - int64 version, - int64 transaction_id, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks, - const string16& database_identifier, - const string16& data_dir) = 0; - virtual void DeleteDatabase( - const string16& name, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - const string16& database_identifier, - const string16& data_dir) = 0; - - protected: - virtual ~IndexedDBFactory() {} - friend class base::RefCounted<IndexedDBFactory>; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_FACTORY_H_ diff --git a/content/browser/indexed_db/indexed_db_factory_impl.cc b/content/browser/indexed_db/indexed_db_factory_impl.cc deleted file mode 100644 index b8b6263..0000000 --- a/content/browser/indexed_db/indexed_db_factory_impl.cc +++ /dev/null @@ -1,197 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/indexed_db_factory_impl.h" - -#include "base/logging.h" -#include "base/utf_string_conversions.h" -#include "content/browser/indexed_db/indexed_db_backing_store.h" -#include "content/browser/indexed_db/indexed_db_database_impl.h" -#include "content/browser/indexed_db/indexed_db_tracing.h" -#include "content/browser/indexed_db/indexed_db_transaction_coordinator.h" -#include "third_party/WebKit/public/platform/WebIDBDatabaseException.h" - -namespace content { - -template <typename K, typename M> -static void CleanWeakMap(std::map<K, base::WeakPtr<M> >& map) { - std::map<K, base::WeakPtr<M> > other; - other.swap(map); - - typename std::map<K, base::WeakPtr<M> >::const_iterator iter = other.begin(); - while (iter != other.end()) { - if (iter->second.get()) - map[iter->first] = iter->second; - ++iter; - } -} - -static string16 ComputeFileIdentifier(const string16& database_identifier) { - string16 suffix(ASCIIToUTF16("@1")); - string16 result(database_identifier); - result.insert(result.end(), suffix.begin(), suffix.end()); - return result; -} - -static string16 ComputeUniqueIdentifier(const string16& name, - const string16& database_identifier) { - return ComputeFileIdentifier(database_identifier) + name; -} - -IndexedDBFactoryImpl::IndexedDBFactoryImpl() {} - -IndexedDBFactoryImpl::~IndexedDBFactoryImpl() {} - -void IndexedDBFactoryImpl::RemoveIDBDatabaseBackend( - const string16& unique_identifier) { - DCHECK(database_backend_map_.find(unique_identifier) != - database_backend_map_.end()); - database_backend_map_.erase(unique_identifier); -} - -void IndexedDBFactoryImpl::GetDatabaseNames( - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - const string16& database_identifier, - const string16& data_directory) { - IDB_TRACE("IndexedDBFactoryImpl::get_database_names"); - scoped_refptr<IndexedDBBackingStore> backing_store = - OpenBackingStore(database_identifier, data_directory); - if (!backing_store) { - callbacks->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16("Internal error opening backing store for " - "indexed_db.webkit_get_database_names."))); - return; - } - - callbacks->OnSuccess(backing_store->GetDatabaseNames()); -} - -void IndexedDBFactoryImpl::DeleteDatabase( - const string16& name, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - const string16& database_identifier, - const string16& data_directory) { - IDB_TRACE("IndexedDBFactoryImpl::delete_database"); - const string16 unique_identifier = - ComputeUniqueIdentifier(name, database_identifier); - - IndexedDBDatabaseMap::iterator it = - database_backend_map_.find(unique_identifier); - if (it != database_backend_map_.end()) { - // If there are any connections to the database, directly delete the - // database. - it->second->DeleteDatabase(callbacks); - return; - } - - // TODO(jsbell): Everything from now on should be done on another thread. - scoped_refptr<IndexedDBBackingStore> backing_store = - OpenBackingStore(database_identifier, data_directory); - if (!backing_store) { - callbacks->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16("Internal error opening backing store " - "for indexed_db.delete_database."))); - return; - } - - scoped_refptr<IndexedDBDatabaseImpl> database_backend = - IndexedDBDatabaseImpl::Create( - name, backing_store.get(), this, unique_identifier); - if (!database_backend) { - callbacks->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16("Internal error creating database backend for " - "indexed_db.delete_database."))); - return; - } - - database_backend_map_[unique_identifier] = database_backend.get(); - database_backend->DeleteDatabase(callbacks); - database_backend_map_.erase(unique_identifier); -} - -scoped_refptr<IndexedDBBackingStore> IndexedDBFactoryImpl::OpenBackingStore( - const string16& database_identifier, - const string16& data_directory) { - const string16 file_identifier = ComputeFileIdentifier(database_identifier); - const bool open_in_memory = data_directory.empty(); - - IndexedDBBackingStoreMap::iterator it2 = - backing_store_map_.find(file_identifier); - if (it2 != backing_store_map_.end() && it2->second.get()) - return it2->second.get(); - - scoped_refptr<IndexedDBBackingStore> backing_store; - if (open_in_memory) { - backing_store = IndexedDBBackingStore::OpenInMemory(file_identifier); - } else { - backing_store = IndexedDBBackingStore::Open( - database_identifier, data_directory, file_identifier); - } - - if (backing_store) { - CleanWeakMap(backing_store_map_); - backing_store_map_[file_identifier] = backing_store->GetWeakPtr(); - // If an in-memory database, bind lifetime to this factory instance. - if (open_in_memory) - session_only_backing_stores_.insert(backing_store); - - // All backing stores associated with this factory should be of the same - // type. - DCHECK(session_only_backing_stores_.empty() || open_in_memory); - - return backing_store; - } - - return 0; -} - -void IndexedDBFactoryImpl::Open( - const string16& name, - int64 version, - int64 transaction_id, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks, - const string16& database_identifier, - const string16& data_directory) { - IDB_TRACE("IndexedDBFactoryImpl::open"); - const string16 unique_identifier = - ComputeUniqueIdentifier(name, database_identifier); - - scoped_refptr<IndexedDBDatabaseImpl> database_backend; - IndexedDBDatabaseMap::iterator it = - database_backend_map_.find(unique_identifier); - if (it == database_backend_map_.end()) { - scoped_refptr<IndexedDBBackingStore> backing_store = - OpenBackingStore(database_identifier, data_directory); - if (!backing_store) { - callbacks->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16( - "Internal error opening backing store for indexedDB.open."))); - return; - } - - database_backend = IndexedDBDatabaseImpl::Create( - name, backing_store.get(), this, unique_identifier); - if (!database_backend) { - callbacks->OnError(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16( - "Internal error creating database backend for indexedDB.open."))); - return; - } - - database_backend_map_[unique_identifier] = database_backend.get(); - } else { - database_backend = it->second; - } - - database_backend->OpenConnection( - callbacks, database_callbacks, transaction_id, version); -} - -} // namespace content diff --git a/content/browser/indexed_db/indexed_db_factory_impl.h b/content/browser/indexed_db/indexed_db_factory_impl.h deleted file mode 100644 index c049585..0000000 --- a/content/browser/indexed_db/indexed_db_factory_impl.h +++ /dev/null @@ -1,77 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_FACTORY_IMPL_H_ -#define CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_FACTORY_IMPL_H_ - -#include <map> -#include <set> - -#include "base/basictypes.h" -#include "base/memory/ref_counted.h" -#include "base/memory/weak_ptr.h" -#include "content/browser/indexed_db/indexed_db_callbacks_wrapper.h" -#include "content/browser/indexed_db/indexed_db_database_callbacks_wrapper.h" -#include "content/browser/indexed_db/indexed_db_factory.h" -#include "content/common/content_export.h" - -namespace content { - -class IndexedDBBackingStore; -class IndexedDBDatabaseImpl; - -class CONTENT_EXPORT IndexedDBFactoryImpl - : NON_EXPORTED_BASE(public IndexedDBFactory) { - public: - static scoped_refptr<IndexedDBFactoryImpl> Create() { - return make_scoped_refptr(new IndexedDBFactoryImpl()); - } - - // Notifications from weak pointers. - virtual void RemoveIDBDatabaseBackend(const string16& unique_identifier); - - virtual void GetDatabaseNames( - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - const string16& database_identifier, - const string16& data_dir) OVERRIDE; - virtual void Open( - const string16& name, - int64 version, - int64 transaction_id, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks, - const string16& database_identifier, - const string16& data_dir) OVERRIDE; - - virtual void DeleteDatabase( - const string16& name, - scoped_refptr<IndexedDBCallbacksWrapper> callbacks, - const string16& database_identifier, - const string16& data_dir) OVERRIDE; - - protected: - IndexedDBFactoryImpl(); - virtual ~IndexedDBFactoryImpl(); - virtual scoped_refptr<IndexedDBBackingStore> OpenBackingStore( - const string16& database_identifier, - const string16& data_dir); - - private: - typedef std::map<string16, scoped_refptr<IndexedDBDatabaseImpl> > - IndexedDBDatabaseMap; - IndexedDBDatabaseMap database_backend_map_; - - typedef std::map<string16, base::WeakPtr<IndexedDBBackingStore> > - IndexedDBBackingStoreMap; - IndexedDBBackingStoreMap backing_store_map_; - - std::set<scoped_refptr<IndexedDBBackingStore> > session_only_backing_stores_; - - // Only one instance of the factory should exist at any given time. - static IndexedDBFactoryImpl* idb_factory_backend_impl; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_FACTORY_IMPL_H_ diff --git a/content/browser/indexed_db/indexed_db_index_writer.cc b/content/browser/indexed_db/indexed_db_index_writer.cc deleted file mode 100644 index 6104111..0000000 --- a/content/browser/indexed_db/indexed_db_index_writer.cc +++ /dev/null @@ -1,169 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/indexed_db_index_writer.h" - -#include "base/logging.h" -#include "base/utf_string_conversions.h" -#include "content/browser/indexed_db/indexed_db_backing_store.h" -#include "content/browser/indexed_db/indexed_db_tracing.h" -#include "content/browser/indexed_db/indexed_db_transaction.h" -#include "content/common/indexed_db/indexed_db_key.h" -#include "content/common/indexed_db/indexed_db_key_path.h" -#include "content/common/indexed_db/indexed_db_key_range.h" - -namespace content { - -IndexedDBObjectStoreImpl::IndexWriter::IndexWriter( - const IndexedDBIndexMetadata& index_metadata) - : index_metadata_(index_metadata) {} - -IndexedDBObjectStoreImpl::IndexWriter::IndexWriter( - const IndexedDBIndexMetadata& index_metadata, - const IndexedDBDatabase::IndexKeys& index_keys) - : index_metadata_(index_metadata), index_keys_(index_keys) {} - -IndexedDBObjectStoreImpl::IndexWriter::~IndexWriter() {} - -bool IndexedDBObjectStoreImpl::IndexWriter::VerifyIndexKeys( - IndexedDBBackingStore* backing_store, - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - bool* can_add_keys, - const IndexedDBKey& primary_key, - string16* error_message) const { - *can_add_keys = false; - for (size_t i = 0; i < index_keys_.size(); ++i) { - bool ok = AddingKeyAllowed(backing_store, - transaction, - database_id, - object_store_id, - index_id, - (index_keys_)[i], - primary_key, - can_add_keys); - if (!ok) - return false; - if (!*can_add_keys) { - if (error_message) - *error_message = ASCIIToUTF16("Unable to add key to index '") + - index_metadata_.name + - ASCIIToUTF16("': at least one key does not satisfy " - "the uniqueness requirements."); - return true; - } - } - *can_add_keys = true; - return true; -} - -void IndexedDBObjectStoreImpl::IndexWriter::WriteIndexKeys( - const IndexedDBBackingStore::RecordIdentifier& record_identifier, - IndexedDBBackingStore* backing_store, - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id) const { - int64 index_id = index_metadata_.id; - for (size_t i = 0; i < index_keys_.size(); ++i) { - bool ok = backing_store->PutIndexDataForRecord(transaction, - database_id, - object_store_id, - index_id, - index_keys_[i], - record_identifier); - // This should have already been verified as a valid write during - // verify_index_keys. - DCHECK(ok); - } -} - -bool IndexedDBObjectStoreImpl::IndexWriter::AddingKeyAllowed( - IndexedDBBackingStore* backing_store, - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - const IndexedDBKey& index_key, - const IndexedDBKey& primary_key, - bool* allowed) const { - *allowed = false; - if (!index_metadata_.unique) { - *allowed = true; - return true; - } - - scoped_ptr<IndexedDBKey> found_primary_key; - bool found = false; - bool ok = backing_store->KeyExistsInIndex(transaction, - database_id, - object_store_id, - index_id, - index_key, - &found_primary_key, - found); - if (!ok) - return false; - if (!found || - (primary_key.IsValid() && found_primary_key->IsEqual(primary_key))) - *allowed = true; - return true; -} - -bool IndexedDBObjectStoreImpl::MakeIndexWriters( - scoped_refptr<IndexedDBTransaction> transaction, - IndexedDBBackingStore* backing_store, - int64 database_id, - const IndexedDBObjectStoreMetadata& object_store, - const IndexedDBKey& primary_key, // makes a copy - bool key_was_generated, - const std::vector<int64>& index_ids, - const std::vector<IndexedDBDatabase::IndexKeys>& index_keys, - ScopedVector<IndexWriter>* index_writers, - string16* error_message, - bool* completed) { - DCHECK_EQ(index_ids.size(), index_keys.size()); - *completed = false; - - std::map<int64, IndexedDBDatabase::IndexKeys> index_key_map; - for (size_t i = 0; i < index_ids.size(); ++i) - index_key_map[index_ids[i]] = index_keys[i]; - - for (IndexedDBObjectStoreMetadata::IndexMap::const_iterator it = - object_store.indexes.begin(); - it != object_store.indexes.end(); - ++it) { - const IndexedDBIndexMetadata& index = it->second; - - IndexedDBDatabase::IndexKeys keys = index_key_map[it->first]; - // If the object_store is using auto_increment, then any indexes with an - // identical key_path need to also use the primary (generated) key as a key. - if (key_was_generated && (index.key_path == object_store.key_path)) - keys.push_back(primary_key); - - scoped_ptr<IndexWriter> index_writer(new IndexWriter(index, keys)); - bool can_add_keys = false; - bool backing_store_success = - index_writer->VerifyIndexKeys(backing_store, - transaction->BackingStoreTransaction(), - database_id, - object_store.id, - index.id, - &can_add_keys, - primary_key, - error_message); - if (!backing_store_success) - return false; - if (!can_add_keys) - return true; - - index_writers->push_back(index_writer.release()); - } - - *completed = true; - return true; -} - -} // namespace content diff --git a/content/browser/indexed_db/indexed_db_index_writer.h b/content/browser/indexed_db/indexed_db_index_writer.h deleted file mode 100644 index 372e6b5..0000000 --- a/content/browser/indexed_db/indexed_db_index_writer.h +++ /dev/null @@ -1,82 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_INDEX_WRITER_H_ -#define CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_INDEX_WRITER_H_ - -#include <map> -#include <vector> - -#include "base/basictypes.h" -#include "base/memory/scoped_vector.h" -#include "content/browser/indexed_db/indexed_db_backing_store.h" -#include "content/browser/indexed_db/indexed_db_database_impl.h" -#include "content/browser/indexed_db/indexed_db_metadata.h" -#include "content/common/indexed_db/indexed_db_key_path.h" - -namespace content { - -class IndexedDBDatabaseImpl; -class IndexedDBTransaction; -struct IndexedDBObjectStoreMetadata; - -// TODO(alecflett): this namespace is temporary until we move its contents out -// to their own home. -namespace IndexedDBObjectStoreImpl { - -class IndexWriter { - public: - explicit IndexWriter(const IndexedDBIndexMetadata& index_metadata); - - IndexWriter(const IndexedDBIndexMetadata& index_metadata, - const IndexedDBDatabase::IndexKeys& index_keys); - - bool VerifyIndexKeys(IndexedDBBackingStore* store, - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - bool* can_add_keys, - const IndexedDBKey& primary_key, - string16* error_message = 0) const WARN_UNUSED_RESULT; - - void WriteIndexKeys(const IndexedDBBackingStore::RecordIdentifier& record, - IndexedDBBackingStore* store, - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id) const; - - ~IndexWriter(); - - private: - bool AddingKeyAllowed(IndexedDBBackingStore* store, - IndexedDBBackingStore::Transaction* transaction, - int64 database_id, - int64 object_store_id, - int64 index_id, - const IndexedDBKey& index_key, - const IndexedDBKey& primary_key, - bool* allowed) const WARN_UNUSED_RESULT; - - const IndexedDBIndexMetadata index_metadata_; - IndexedDBDatabase::IndexKeys index_keys_; -}; - -bool MakeIndexWriters( - scoped_refptr<IndexedDBTransaction> transaction, - IndexedDBBackingStore* store, - int64 database_id, - const IndexedDBObjectStoreMetadata& metadata, - const IndexedDBKey& primary_key, - bool key_was_generated, - const std::vector<int64>& index_ids, - const std::vector<IndexedDBDatabase::IndexKeys>& index_keys, - ScopedVector<IndexWriter>* index_writers, - string16* error_message, - bool* completed) WARN_UNUSED_RESULT; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_INDEX_WRITER_H_ diff --git a/content/browser/indexed_db/indexed_db_internals_ui.cc b/content/browser/indexed_db/indexed_db_internals_ui.cc index 0f7bc3e..7203768 100644 --- a/content/browser/indexed_db/indexed_db_internals_ui.cc +++ b/content/browser/indexed_db/indexed_db_internals_ui.cc @@ -301,8 +301,8 @@ void IndexedDBInternalsUI::OnDownloadStarted( net::Error error) { if (error != net::OK) { - LOG(ERROR) - << "Error downloading database dump: " << net::ErrorToString(error); + LOG(ERROR) << "Error downloading database dump: " + << net::ErrorToString(error); return; } diff --git a/content/browser/indexed_db/indexed_db_internals_ui.h b/content/browser/indexed_db/indexed_db_internals_ui.h index 1412ec0..bc9a5da 100644 --- a/content/browser/indexed_db/indexed_db_internals_ui.h +++ b/content/browser/indexed_db/indexed_db_internals_ui.h @@ -13,9 +13,7 @@ #include "content/public/browser/web_ui_controller.h" #include "net/base/net_errors.h" -namespace base { -class ListValue; -} +namespace base { class ListValue; } namespace content { diff --git a/content/browser/indexed_db/indexed_db_leveldb_coding.cc b/content/browser/indexed_db/indexed_db_leveldb_coding.cc deleted file mode 100644 index 590fe93..0000000 --- a/content/browser/indexed_db/indexed_db_leveldb_coding.cc +++ /dev/null @@ -1,1884 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/indexed_db_leveldb_coding.h" - -#include <iterator> -#include <limits> -#include <string> - -#include "base/logging.h" -#include "base/string16.h" -#include "base/sys_byteorder.h" -#include "content/browser/indexed_db/leveldb/leveldb_slice.h" -#include "content/common/indexed_db/indexed_db_key.h" -#include "content/common/indexed_db/indexed_db_key_path.h" -#include "third_party/WebKit/public/platform/WebIDBKeyPath.h" - -// LevelDB stores key/value pairs. Keys and values are strings of bytes, -// normally of type std::vector<char>. -// -// The keys in the backing store are variable-length tuples with different types -// of fields. Each key in the backing store starts with a ternary prefix: -// (database id, object store id, index id). For each, 0 is reserved for -// meta-data. -// The prefix makes sure that data for a specific database, object store, and -// index are grouped together. The locality is important for performance: common -// operations should only need a minimal number of seek operations. For example, -// all the meta-data for a database is grouped together so that reading that -// meta-data only requires one seek. -// -// Each key type has a class (in square brackets below) which knows how to -// encode, decode, and compare that key type. -// -// Global meta-data have keys with prefix (0,0,0), followed by a type byte: -// -// <0, 0, 0, 0> => -// IndexedDB/LevelDB schema version [SchemaVersionKey] -// <0, 0, 0, 1> => The maximum -// database id ever allocated [MaxDatabaseIdKey] -// <0, 0, 0, 2> => -// SerializedScriptValue version [DataVersionKey] -// <0, 0, 0, 100, database id> => Existence -// implies the database id is in the free list [DatabaseFreeListKey] -// <0, 0, 0, 201, utf16 origin name, utf16 database name> => Database id -// [DatabaseNameKey] -// -// -// Database meta-data: -// -// Again, the prefix is followed by a type byte. -// -// <database id, 0, 0, 0> => utf16 origin name [DatabaseMetaDataKey] -// <database id, 0, 0, 1> => utf16 database name [DatabaseMetaDataKey] -// <database id, 0, 0, 2> => utf16 user version data [DatabaseMetaDataKey] -// <database id, 0, 0, 3> => maximum object store id ever allocated -// [DatabaseMetaDataKey] -// <database id, 0, 0, 4> => user integer version (var int) -// [DatabaseMetaDataKey] -// -// -// Object store meta-data: -// -// The prefix is followed by a type byte, then a variable-length integer, -// and then another type byte. -// -// <database id, 0, 0, 50, object store id, 0> => utf16 object store name -// [ObjectStoreMetaDataKey] -// <database id, 0, 0, 50, object store id, 1> => utf16 key path -// [ObjectStoreMetaDataKey] -// <database id, 0, 0, 50, object store id, 2> => has auto increment -// [ObjectStoreMetaDataKey] -// <database id, 0, 0, 50, object store id, 3> => is evictable -// [ObjectStoreMetaDataKey] -// <database id, 0, 0, 50, object store id, 4> => last "version" number -// [ObjectStoreMetaDataKey] -// <database id, 0, 0, 50, object store id, 5> => maximum index id ever -// allocated [ObjectStoreMetaDataKey] -// <database id, 0, 0, 50, object store id, 6> => has key path (vs. null) -// [ObjectStoreMetaDataKey] -// <database id, 0, 0, 50, object store id, 7> => key generator current -// number [ObjectStoreMetaDataKey] -// -// -// Index meta-data: -// -// The prefix is followed by a type byte, then two variable-length integers, -// and then another type byte. -// -// <database id, 0, 0, 100, object store id, index id, 0> => utf16 index -// name [IndexMetaDataKey] -// <database id, 0, 0, 100, object store id, index id, 1> => are index keys -// unique [IndexMetaDataKey] -// <database id, 0, 0, 100, object store id, index id, 2> => utf16 key path -// [IndexMetaDataKey] -// <database id, 0, 0, 100, object store id, index id, 3> => is index -// multi-entry [IndexMetaDataKey] -// -// -// Other object store and index meta-data: -// -// The prefix is followed by a type byte. The object store and index id are -// variable length integers, the utf16 strings are variable length strings. -// -// <database id, 0, 0, 150, object store id> => existence -// implies the object store id is in the free list [ObjectStoreFreeListKey] -// <database id, 0, 0, 151, object store id, index id> => existence -// implies the index id is in the free list [IndexFreeListKey] -// <database id, 0, 0, 200, utf16 object store name> => object -// store id [ObjectStoreNamesKey] -// <database id, 0, 0, 201, object store id, utf16 index name> => index id -// [IndexNamesKey] -// -// -// Object store data: -// -// The prefix is followed by a type byte. The user key is an encoded -// IndexedDBKey. -// -// <database id, object store id, 1, user key> => "version", serialized -// script value [ObjectStoreDataKey] -// -// -// "Exists" entry: -// -// The prefix is followed by a type byte. The user key is an encoded -// IndexedDBKey. -// -// <database id, object store id, 2, user key> => "version" [ExistsEntryKey] -// -// -// Index data: -// -// The prefix is followed by a type byte. The index key is an encoded -// IndexedDBKey. The sequence number is a variable length integer. -// The primary key is an encoded IndexedDBKey. -// -// <database id, object store id, index id, index key, sequence number, -// primary key> => "version", primary key [IndexDataKey] -// -// (The sequence number is obsolete; it was used to allow two entries with -// the same user (index) key in non-unique indexes prior to the inclusion of -// the primary key in the data. The "version" field is used to weed out -// stale -// index data. Whenever new object store data is inserted, it gets a new -// "version" number, and new index data is written with this number. When -// the index is used for look-ups, entries are validated against the -// "exists" entries, and records with old "version" numbers are deleted -// when they are encountered in get_primary_key_via_index, -// IndexCursorImpl::load_current_row, and -// IndexKeyCursorImpl::load_current_row). - -using WebKit::WebIDBKey; -using WebKit::WebIDBKeyPath; - -namespace content { - -// As most of the IndexedDBKeys and encoded values are short, we -// initialize some Vectors with a default inline buffer size to reduce -// the memory re-allocations when the Vectors are appended. -static const size_t kDefaultInlineBufferSize = 32; - -static const unsigned char kIndexedDBKeyNullTypeByte = 0; -static const unsigned char kIndexedDBKeyStringTypeByte = 1; -static const unsigned char kIndexedDBKeyDateTypeByte = 2; -static const unsigned char kIndexedDBKeyNumberTypeByte = 3; -static const unsigned char kIndexedDBKeyArrayTypeByte = 4; -static const unsigned char kIndexedDBKeyMinKeyTypeByte = 5; - -static const unsigned char kIndexedDBKeyPathTypeCodedByte1 = 0; -static const unsigned char kIndexedDBKeyPathTypeCodedByte2 = 0; - -static const unsigned char kObjectStoreDataIndexId = 1; -static const unsigned char kExistsEntryIndexId = 2; - -static const unsigned char kSchemaVersionTypeByte = 0; -static const unsigned char kMaxDatabaseIdTypeByte = 1; -static const unsigned char kDataVersionTypeByte = 2; -static const unsigned char kMaxSimpleGlobalMetaDataTypeByte = - 3; // Insert before this and increment. -static const unsigned char kDatabaseFreeListTypeByte = 100; -static const unsigned char kDatabaseNameTypeByte = 201; - -static const unsigned char kObjectStoreMetaDataTypeByte = 50; -static const unsigned char kIndexMetaDataTypeByte = 100; -static const unsigned char kObjectStoreFreeListTypeByte = 150; -static const unsigned char kIndexFreeListTypeByte = 151; -static const unsigned char kObjectStoreNamesTypeByte = 200; -static const unsigned char kIndexNamesKeyTypeByte = 201; - -static const unsigned char kObjectMetaDataTypeMaximum = 255; -static const unsigned char kIndexMetaDataTypeMaximum = 255; - -const unsigned char kMinimumIndexId = 30; - -std::vector<char> EncodeByte(unsigned char c) { - std::vector<char> v; - v.reserve(kDefaultInlineBufferSize); - v.push_back(c); - - DCHECK_LE(v.size(), kDefaultInlineBufferSize); - return v; -} - -const char* DecodeByte(const char* p, - const char* limit, - unsigned char& found_char) { - DCHECK_GE(limit, p); - if (p >= limit) - return 0; - - found_char = *p++; - return p; -} - -std::vector<char> MaxIDBKey() { return EncodeByte(kIndexedDBKeyNullTypeByte); } - -std::vector<char> MinIDBKey() { - return EncodeByte(kIndexedDBKeyMinKeyTypeByte); -} - -std::vector<char> EncodeBool(bool b) { - std::vector<char> ret; - ret.reserve(kDefaultInlineBufferSize); - ret.push_back(b ? 1 : 0); - - DCHECK_LE(ret.size(), kDefaultInlineBufferSize); - return ret; -} - -bool DecodeBool(const char* p, const char* limit) { - DCHECK_GT(limit, p); - return !!*p; -} - -std::vector<char> EncodeInt(int64 nParam) { -#ifndef NDEBUG - // Exercised by unit tests in debug only. - DCHECK_GE(nParam, 0); -#endif - uint64 n = static_cast<uint64>(nParam); - std::vector<char> ret; - ret.reserve(kDefaultInlineBufferSize); - - do { - unsigned char c = n; - ret.push_back(c); - n >>= 8; - } while (n); - - DCHECK_LE(ret.size(), kDefaultInlineBufferSize); - return ret; -} - -static int CompareInts(int64 a, int64 b) { -#ifndef NDEBUG - // Exercised by unit tests in debug only. - DCHECK_GE(a, 0); - DCHECK_GE(b, 0); -#endif - int64 diff = a - b; - if (diff < 0) - return -1; - if (diff > 0) - return 1; - return 0; -} - -std::vector<char> EncodeVarInt(int64 nParam) { -#ifndef NDEBUG - // Exercised by unit tests in debug only. - DCHECK_GE(nParam, 0); -#endif - uint64 n = static_cast<uint64>(nParam); - std::vector<char> ret; - ret.reserve(kDefaultInlineBufferSize); - - do { - unsigned char c = n & 0x7f; - n >>= 7; - if (n) - c |= 0x80; - ret.push_back(c); - } while (n); - - DCHECK_LE(ret.size(), kDefaultInlineBufferSize); - return ret; -} - -const char* DecodeVarInt(const char* p, const char* limit, int64& found_int) { - DCHECK_GE(limit, p); - found_int = 0; - int shift = 0; - - do { - if (p >= limit) - return 0; - - unsigned char c = *p; - found_int |= static_cast<int64>(c & 0x7f) << shift; - shift += 7; - } while (*p++ & 0x80); - return p; -} - -std::vector<char> EncodeString(const string16& s) { - // Backing store is UTF-16BE, convert from host endianness. - size_t length = s.length(); - std::vector<char> ret(length * sizeof(char16)); - if (!length) - return ret; - - const char16* src = s.c_str(); - char16* dst = reinterpret_cast<char16*>(&*ret.begin()); - for (unsigned i = 0; i < length; ++i) - *dst++ = htons(*src++); - - return ret; -} - -string16 DecodeString(const char* p, const char* limit) { - // Backing store is UTF-16BE, convert to host endianness. - DCHECK_GE(limit, p); - DCHECK(!((limit - p) % sizeof(char16))); - - size_t length = (limit - p) / sizeof(char16); - string16 decoded; - decoded.reserve(length); - const char16* encoded = reinterpret_cast<const char16*>(p); - for (unsigned i = 0; i < length; ++i) - decoded.push_back(ntohs(*encoded++)); - return decoded; -} - -std::vector<char> EncodeStringWithLength(const string16& s) { - std::vector<char> result = EncodeVarInt(s.length()); - std::vector<char> encoded_value = EncodeString(s); - result.insert(result.end(), encoded_value.begin(), encoded_value.end()); - return result; -} - -const char* DecodeStringWithLength(const char* p, - const char* limit, - string16& found_string) { - DCHECK_GE(limit, p); - int64 len; - p = DecodeVarInt(p, limit, len); - if (!p || len < 0 || p + len * 2 > limit) - return 0; - - found_string = DecodeString(p, p + len * 2); - p += len * 2; - return p; -} - -int CompareEncodedStringsWithLength(const char*& p, - const char* limit_p, - const char*& q, - const char* limit_q, - bool& ok) { - DCHECK_NE(&p, &q); - DCHECK_GT(limit_p, p); - DCHECK_GT(limit_q, q); - int64 len_p, len_q; - p = DecodeVarInt(p, limit_p, len_p); - q = DecodeVarInt(q, limit_q, len_q); - if (!p || !q || len_p < 0 || len_q < 0) { - ok = false; - return 0; - } - DCHECK(p && q); - DCHECK_GE(len_p, 0); - DCHECK_GE(len_q, 0); - DCHECK_LE(p + len_p * 2, limit_p); - DCHECK_LE(q + len_q * 2, limit_q); - - const char* start_p = p; - const char* start_q = q; - p += len_p * 2; - q += len_q * 2; - - if (p > limit_p || q > limit_q) { - ok = false; - return 0; - } - - ok = true; - const size_t lmin = static_cast<size_t>(len_p < len_q ? len_p : len_q); - if (int x = memcmp(start_p, start_q, lmin * 2)) - return x; - - if (len_p == len_q) - return 0; - - return (len_p > len_q) ? 1 : -1; -} - -std::vector<char> EncodeDouble(double x) { - // TODO(jsbell): It would be nice if we could be byte order independent. - const char* p = reinterpret_cast<char*>(&x); - std::vector<char> v; - v.reserve(kDefaultInlineBufferSize); - v.insert(v.end(), p, p + sizeof(x)); - - DCHECK_LE(v.size(), kDefaultInlineBufferSize); - return v; -} - -const char* DecodeDouble(const char* p, const char* limit, double* d) { - if (p + sizeof(*d) > limit) - return 0; - - char* x = reinterpret_cast<char*>(d); - for (size_t i = 0; i < sizeof(*d); ++i) - *x++ = *p++; - return p; -} - -std::vector<char> EncodeIDBKey(const IndexedDBKey& key) { - std::vector<char> ret; - ret.reserve(kDefaultInlineBufferSize); - EncodeIDBKey(key, ret); - return ret; -} - -void EncodeIDBKey(const IndexedDBKey& key, std::vector<char>& into) { - size_t previous_size = into.size(); - DCHECK(key.IsValid()); - switch (key.type()) { - case WebIDBKey::NullType: - case WebIDBKey::InvalidType: - case WebIDBKey::MinType: { - NOTREACHED(); - into.push_back(kIndexedDBKeyNullTypeByte); - return; - } - case WebIDBKey::ArrayType: { - into.push_back(kIndexedDBKeyArrayTypeByte); - size_t length = key.array().size(); - std::vector<char> encoded_length = EncodeVarInt(length); - into.insert(into.end(), encoded_length.begin(), encoded_length.end()); - for (size_t i = 0; i < length; ++i) - EncodeIDBKey(key.array()[i], into); - DCHECK_GT(into.size(), previous_size); - return; - } - case WebIDBKey::StringType: { - into.push_back(kIndexedDBKeyStringTypeByte); - std::vector<char> tmp = EncodeStringWithLength(key.string()); - into.insert(into.end(), tmp.begin(), tmp.end()); - DCHECK_GT(into.size(), previous_size); - return; - } - case WebIDBKey::DateType: { - into.push_back(kIndexedDBKeyDateTypeByte); - std::vector<char> tmp = EncodeDouble(key.date()); - into.insert(into.end(), tmp.begin(), tmp.end()); - DCHECK_EQ(static_cast<size_t>(9), - static_cast<size_t>(into.size() - previous_size)); - return; - } - case WebIDBKey::NumberType: { - into.push_back(kIndexedDBKeyNumberTypeByte); - std::vector<char> tmp = EncodeDouble(key.number()); - into.insert(into.end(), tmp.begin(), tmp.end()); - DCHECK_EQ(static_cast<size_t>(9), - static_cast<size_t>(into.size() - previous_size)); - return; - } - } - - NOTREACHED(); -} - -const char* DecodeIDBKey(const char* p, - const char* limit, - scoped_ptr<IndexedDBKey>* found_key) { - DCHECK_GE(limit, p); - if (p >= limit) - return 0; - - unsigned char type = *p++; - - switch (type) { - case kIndexedDBKeyNullTypeByte: - *found_key = make_scoped_ptr(new IndexedDBKey()); - return p; - - case kIndexedDBKeyArrayTypeByte: { - int64 length; - p = DecodeVarInt(p, limit, length); - if (!p || length < 0) - return 0; - IndexedDBKey::KeyArray array; - while (length--) { - scoped_ptr<IndexedDBKey> key; - p = DecodeIDBKey(p, limit, &key); - if (!p) - return 0; - array.push_back(*key); - } - *found_key = make_scoped_ptr(new IndexedDBKey(array)); - return p; - } - case kIndexedDBKeyStringTypeByte: { - string16 s; - p = DecodeStringWithLength(p, limit, s); - if (!p) - return 0; - *found_key = make_scoped_ptr(new IndexedDBKey(s)); - return p; - } - case kIndexedDBKeyDateTypeByte: { - double d; - p = DecodeDouble(p, limit, &d); - if (!p) - return 0; - *found_key = make_scoped_ptr(new IndexedDBKey(d, WebIDBKey::DateType)); - return p; - } - case kIndexedDBKeyNumberTypeByte: { - double d; - p = DecodeDouble(p, limit, &d); - if (!p) - return 0; - *found_key = make_scoped_ptr(new IndexedDBKey(d, WebIDBKey::NumberType)); - return p; - } - } - - NOTREACHED(); - return 0; -} - -const char* ExtractEncodedIDBKey(const char* start, - const char* limit, - std::vector<char>* result = 0) { - DCHECK_GT(limit, start); - const char* p = start; - if (p >= limit) - return 0; - - unsigned char type = *p++; - - switch (type) { - case kIndexedDBKeyNullTypeByte: - case kIndexedDBKeyMinKeyTypeByte: - break; - case kIndexedDBKeyArrayTypeByte: { - int64 length; - p = DecodeVarInt(p, limit, length); - if (!p || length < 0) - return 0; - while (length--) { - p = ExtractEncodedIDBKey(p, limit); - if (!p) - return 0; - } - break; - } - case kIndexedDBKeyStringTypeByte: { - int64 length; - p = DecodeVarInt(p, limit, length); - if (!p || length < 0 || p + length * 2 > limit) - return 0; - p += length * 2; - break; - } - case kIndexedDBKeyDateTypeByte: - case kIndexedDBKeyNumberTypeByte: - if (p + sizeof(double) > limit) - return 0; - p += sizeof(double); - break; - } - - if (result) { - DCHECK(p); - DCHECK_LE(p, limit); - result->assign(start, p); - } - - return p; -} - -static WebIDBKey::Type KeyTypeByteToKeyType(unsigned char type) { - switch (type) { - case kIndexedDBKeyNullTypeByte: - return WebIDBKey::InvalidType; - case kIndexedDBKeyArrayTypeByte: - return WebIDBKey::ArrayType; - case kIndexedDBKeyStringTypeByte: - return WebIDBKey::StringType; - case kIndexedDBKeyDateTypeByte: - return WebIDBKey::DateType; - case kIndexedDBKeyNumberTypeByte: - return WebIDBKey::NumberType; - case kIndexedDBKeyMinKeyTypeByte: - return WebIDBKey::MinType; - } - - NOTREACHED(); - return WebIDBKey::InvalidType; -} - -static int CompareTypes(WebIDBKey::Type a, WebIDBKey::Type b) { return b - a; } - -int CompareEncodedIDBKeys(const char*& ptr_a, - const char* limit_a, - const char*& ptr_b, - const char* limit_b, - bool& ok) { - ok = true; - DCHECK_NE(&ptr_a, &ptr_b); - DCHECK_LT(ptr_a, limit_a); - DCHECK_LT(ptr_b, limit_b); - unsigned char type_a = *ptr_a++; - unsigned char type_b = *ptr_b++; - - if (int x = CompareTypes(KeyTypeByteToKeyType(type_a), - KeyTypeByteToKeyType(type_b))) - return x; - - switch (type_a) { - case kIndexedDBKeyNullTypeByte: - case kIndexedDBKeyMinKeyTypeByte: - // Null type or max type; no payload to compare. - return 0; - case kIndexedDBKeyArrayTypeByte: { - int64 length_a, length_b; - ptr_a = DecodeVarInt(ptr_a, limit_a, length_a); - ptr_b = DecodeVarInt(ptr_b, limit_b, length_b); - if (!ptr_a || !ptr_b || length_a < 0 || length_b < 0) { - ok = false; - return 0; - } - for (int64 i = 0; i < length_a && i < length_b; ++i) { - int result = CompareEncodedIDBKeys(ptr_a, limit_a, ptr_b, limit_b, ok); - if (!ok || result) - return result; - } - if (length_a < length_b) - return -1; - if (length_a > length_b) - return 1; - return 0; - } - case kIndexedDBKeyStringTypeByte: - return CompareEncodedStringsWithLength( - ptr_a, limit_a, ptr_b, limit_b, ok); - case kIndexedDBKeyDateTypeByte: - case kIndexedDBKeyNumberTypeByte: { - double d, e; - ptr_a = DecodeDouble(ptr_a, limit_a, &d); - ptr_b = DecodeDouble(ptr_b, limit_b, &e); - DCHECK(ptr_a); - DCHECK(ptr_b); - if (!ptr_a || !ptr_b) { - ok = false; - return 0; - } - if (d < e) - return -1; - if (d > e) - return 1; - return 0; - } - } - - NOTREACHED(); - return 0; -} - -int CompareEncodedIDBKeys(const std::vector<char>& key_a, - const std::vector<char>& key_b, - bool& ok) { - DCHECK_GE(key_a.size(), static_cast<size_t>(1)); - DCHECK_GE(key_b.size(), static_cast<size_t>(1)); - - const char* ptr_a = &*key_a.begin(); - const char* limit_a = &*key_a.rbegin() + 1; - const char* ptr_b = &*key_b.begin(); - const char* limit_b = &*key_b.rbegin() + 1; - - return CompareEncodedIDBKeys(ptr_a, limit_a, ptr_b, limit_b, ok); -} - -std::vector<char> EncodeIDBKeyPath(const IndexedDBKeyPath& key_path) { - // May be typed, or may be a raw string. An invalid leading - // byte is used to identify typed coding. New records are - // always written as typed. - std::vector<char> ret; - ret.reserve(kDefaultInlineBufferSize); - ret.push_back(kIndexedDBKeyPathTypeCodedByte1); - ret.push_back(kIndexedDBKeyPathTypeCodedByte2); - ret.push_back(static_cast<char>(key_path.type())); - switch (key_path.type()) { - case WebIDBKeyPath::NullType: - break; - case WebIDBKeyPath::StringType: { - std::vector<char> encoded_string = - EncodeStringWithLength(key_path.string()); - ret.insert(ret.end(), encoded_string.begin(), encoded_string.end()); - break; - } - case WebIDBKeyPath::ArrayType: { - const std::vector<string16>& array = key_path.array(); - size_t count = array.size(); - std::vector<char> encoded_count = EncodeVarInt(count); - ret.insert(ret.end(), encoded_count.begin(), encoded_count.end()); - for (size_t i = 0; i < count; ++i) { - std::vector<char> encoded_string = EncodeStringWithLength(array[i]); - ret.insert(ret.end(), encoded_string.begin(), encoded_string.end()); - } - break; - } - } - return ret; -} - -IndexedDBKeyPath DecodeIDBKeyPath(const char* p, const char* limit) { - // May be typed, or may be a raw string. An invalid leading - // byte sequence is used to identify typed coding. New records are - // always written as typed. - if (p == limit || - (limit - p >= 2 && (*p != kIndexedDBKeyPathTypeCodedByte1 || - *(p + 1) != kIndexedDBKeyPathTypeCodedByte2))) - return IndexedDBKeyPath(DecodeString(p, limit)); - p += 2; - - DCHECK_NE(p, limit); - WebIDBKeyPath::Type type = static_cast<WebIDBKeyPath::Type>(*p++); - switch (type) { - case WebIDBKeyPath::NullType: - DCHECK_EQ(p, limit); - return IndexedDBKeyPath(); - case WebIDBKeyPath::StringType: { - string16 string; - p = DecodeStringWithLength(p, limit, string); - DCHECK_EQ(p, limit); - return IndexedDBKeyPath(string); - } - case WebIDBKeyPath::ArrayType: { - std::vector<string16> array; - int64 count; - p = DecodeVarInt(p, limit, count); - DCHECK(p); - DCHECK_GE(count, 0); - while (count--) { - string16 string; - p = DecodeStringWithLength(p, limit, string); - DCHECK(p); - array.push_back(string); - } - DCHECK_EQ(p, limit); - return IndexedDBKeyPath(array); - } - } - NOTREACHED(); - return IndexedDBKeyPath(); -} - -namespace { - -template <typename KeyType> -int Compare(const LevelDBSlice& a, const LevelDBSlice& b, bool, bool& ok) { - KeyType key_a; - KeyType key_b; - - const char* ptr_a = KeyType::Decode(a.begin(), a.end(), &key_a); - DCHECK(ptr_a); - if (!ptr_a) { - ok = false; - return 0; - } - const char* ptr_b = KeyType::Decode(b.begin(), b.end(), &key_b); - DCHECK(ptr_b); - if (!ptr_b) { - ok = false; - return 0; - } - - ok = true; - return key_a.Compare(key_b); -} - -template <> -int Compare<ExistsEntryKey>(const LevelDBSlice& a, - const LevelDBSlice& b, - bool, - bool& ok) { - KeyPrefix prefix_a; - KeyPrefix prefix_b; - const char* ptr_a = KeyPrefix::Decode(a.begin(), a.end(), &prefix_a); - const char* ptr_b = KeyPrefix::Decode(b.begin(), b.end(), &prefix_b); - DCHECK(ptr_a); - DCHECK(ptr_b); - DCHECK(prefix_a.database_id_); - DCHECK(prefix_a.object_store_id_); - DCHECK_EQ(prefix_a.index_id_, ExistsEntryKey::kSpecialIndexNumber); - DCHECK(prefix_b.database_id_); - DCHECK(prefix_b.object_store_id_); - DCHECK_EQ(prefix_b.index_id_, ExistsEntryKey::kSpecialIndexNumber); - DCHECK_NE(ptr_a, a.end()); - DCHECK_NE(ptr_b, b.end()); - // Prefixes are not compared - it is assumed this was already done. - DCHECK(!prefix_a.Compare(prefix_b)); - - return CompareEncodedIDBKeys(ptr_a, a.end(), ptr_b, b.end(), ok); -} - -template <> -int Compare<ObjectStoreDataKey>(const LevelDBSlice& a, - const LevelDBSlice& b, - bool, - bool& ok) { - KeyPrefix prefix_a; - KeyPrefix prefix_b; - const char* ptr_a = KeyPrefix::Decode(a.begin(), a.end(), &prefix_a); - const char* ptr_b = KeyPrefix::Decode(b.begin(), b.end(), &prefix_b); - DCHECK(ptr_a); - DCHECK(ptr_b); - DCHECK(prefix_a.database_id_); - DCHECK(prefix_a.object_store_id_); - DCHECK_EQ(prefix_a.index_id_, ObjectStoreDataKey::kSpecialIndexNumber); - DCHECK(prefix_b.database_id_); - DCHECK(prefix_b.object_store_id_); - DCHECK_EQ(prefix_b.index_id_, ObjectStoreDataKey::kSpecialIndexNumber); - DCHECK_NE(ptr_a, a.end()); - DCHECK_NE(ptr_b, b.end()); - // Prefixes are not compared - it is assumed this was already done. - DCHECK(!prefix_a.Compare(prefix_b)); - - return CompareEncodedIDBKeys(ptr_a, a.end(), ptr_b, b.end(), ok); -} - -template <> -int Compare<IndexDataKey>(const LevelDBSlice& a, - const LevelDBSlice& b, - bool ignore_duplicates, - bool& ok) { - KeyPrefix prefix_a; - KeyPrefix prefix_b; - const char* ptr_a = KeyPrefix::Decode(a.begin(), a.end(), &prefix_a); - const char* ptr_b = KeyPrefix::Decode(b.begin(), b.end(), &prefix_b); - DCHECK(ptr_a); - DCHECK(ptr_b); - DCHECK(prefix_a.database_id_); - DCHECK(prefix_a.object_store_id_); - DCHECK_GE(prefix_a.index_id_, kMinimumIndexId); - DCHECK(prefix_b.database_id_); - DCHECK(prefix_b.object_store_id_); - DCHECK_GE(prefix_b.index_id_, kMinimumIndexId); - DCHECK_NE(ptr_a, a.end()); - DCHECK_NE(ptr_b, b.end()); - // Prefixes are not compared - it is assumed this was already done. - DCHECK(!prefix_a.Compare(prefix_b)); - - // index key - int result = CompareEncodedIDBKeys(ptr_a, a.end(), ptr_b, b.end(), ok); - if (!ok || result) - return result; - if (ignore_duplicates) - return 0; - - // sequence number [optional] - int64 sequence_number_a = -1; - int64 sequence_number_b = -1; - if (ptr_a != a.end()) - ptr_a = DecodeVarInt(ptr_a, a.end(), sequence_number_a); - if (ptr_b != b.end()) - ptr_b = DecodeVarInt(ptr_b, b.end(), sequence_number_b); - - // primary key [optional] - if (!ptr_a || !ptr_b) - return 0; - if (ptr_a == a.end() && ptr_b == b.end()) - return 0; - if (ptr_a == a.end()) - return -1; - if (ptr_b == b.end()) - return 1; - - result = CompareEncodedIDBKeys(ptr_a, a.end(), ptr_b, b.end(), ok); - if (!ok || result) - return result; - - return CompareInts(sequence_number_a, sequence_number_b); -} - -int Compare(const LevelDBSlice& a, - const LevelDBSlice& b, - bool index_keys, - bool& ok) { - const char* ptr_a = a.begin(); - const char* ptr_b = b.begin(); - const char* end_a = a.end(); - const char* end_b = b.end(); - - KeyPrefix prefix_a; - KeyPrefix prefix_b; - - ptr_a = KeyPrefix::Decode(ptr_a, end_a, &prefix_a); - ptr_b = KeyPrefix::Decode(ptr_b, end_b, &prefix_b); - DCHECK(ptr_a); - DCHECK(ptr_b); - if (!ptr_a || !ptr_b) { - ok = false; - return 0; - } - - ok = true; - if (int x = prefix_a.Compare(prefix_b)) - return x; - - if (prefix_a.type() == KeyPrefix::GLOBAL_METADATA) { - DCHECK_NE(ptr_a, end_a); - DCHECK_NE(ptr_b, end_b); - - unsigned char type_byte_a = *ptr_a++; - unsigned char type_byte_b = *ptr_b++; - - if (int x = type_byte_a - type_byte_b) - return x; - if (type_byte_a < kMaxSimpleGlobalMetaDataTypeByte) - return 0; - - const bool ignore_duplicates = false; - if (type_byte_a == kDatabaseFreeListTypeByte) - return Compare<DatabaseFreeListKey>(a, b, ignore_duplicates, ok); - if (type_byte_a == kDatabaseNameTypeByte) - return Compare<DatabaseNameKey>(a, b, ignore_duplicates, ok); - } - - if (prefix_a.type() == KeyPrefix::DATABASE_METADATA) { - DCHECK_NE(ptr_a, end_a); - DCHECK_NE(ptr_b, end_b); - - unsigned char type_byte_a = *ptr_a++; - unsigned char type_byte_b = *ptr_b++; - - if (int x = type_byte_a - type_byte_b) - return x; - if (type_byte_a < DatabaseMetaDataKey::MAX_SIMPLE_METADATA_TYPE) - return 0; - - const bool ignore_duplicates = false; - if (type_byte_a == kObjectStoreMetaDataTypeByte) - return Compare<ObjectStoreMetaDataKey>(a, b, ignore_duplicates, ok); - if (type_byte_a == kIndexMetaDataTypeByte) - return Compare<IndexMetaDataKey>(a, b, ignore_duplicates, ok); - if (type_byte_a == kObjectStoreFreeListTypeByte) - return Compare<ObjectStoreFreeListKey>(a, b, ignore_duplicates, ok); - if (type_byte_a == kIndexFreeListTypeByte) - return Compare<IndexFreeListKey>(a, b, ignore_duplicates, ok); - if (type_byte_a == kObjectStoreNamesTypeByte) - return Compare<ObjectStoreNamesKey>(a, b, ignore_duplicates, ok); - if (type_byte_a == kIndexNamesKeyTypeByte) - return Compare<IndexNamesKey>(a, b, ignore_duplicates, ok); - } - - if (prefix_a.type() == KeyPrefix::OBJECT_STORE_DATA) { - if (ptr_a == end_a && ptr_b == end_b) - return 0; - if (ptr_a == end_a) - return -1; - if (ptr_b == end_b) - return 1; // TODO(jsbell): This case of non-existing user keys should not - // have to be handled this way. - - const bool ignore_duplicates = false; - return Compare<ObjectStoreDataKey>(a, b, ignore_duplicates, ok); - } - if (prefix_a.type() == KeyPrefix::EXISTS_ENTRY) { - if (ptr_a == end_a && ptr_b == end_b) - return 0; - if (ptr_a == end_a) - return -1; - if (ptr_b == end_b) - return 1; // TODO(jsbell): This case of non-existing user keys should not - // have to be handled this way. - - const bool ignore_duplicates = false; - return Compare<ExistsEntryKey>(a, b, ignore_duplicates, ok); - } - if (prefix_a.type() == KeyPrefix::INDEX_DATA) { - if (ptr_a == end_a && ptr_b == end_b) - return 0; - if (ptr_a == end_a) - return -1; - if (ptr_b == end_b) - return 1; // TODO(jsbell): This case of non-existing user keys should not - // have to be handled this way. - - bool ignore_duplicates = index_keys; - return Compare<IndexDataKey>(a, b, ignore_duplicates, ok); - } - - NOTREACHED(); - ok = false; - return 0; -} - -} // namespace - -int Compare(const LevelDBSlice& a, const LevelDBSlice& b, bool index_keys) { - bool ok; - int result = Compare(a, b, index_keys, ok); - DCHECK(ok); - if (!ok) - return 0; - return result; -} - -KeyPrefix::KeyPrefix() - : database_id_(INVALID_TYPE), - object_store_id_(INVALID_TYPE), - index_id_(INVALID_TYPE) {} - -KeyPrefix::KeyPrefix(int64 database_id) - : database_id_(database_id), object_store_id_(0), index_id_(0) { - DCHECK(KeyPrefix::IsValidDatabaseId(database_id)); -} - -KeyPrefix::KeyPrefix(int64 database_id, int64 object_store_id) - : database_id_(database_id), - object_store_id_(object_store_id), - index_id_(0) { - DCHECK(KeyPrefix::IsValidDatabaseId(database_id)); - DCHECK(KeyPrefix::IsValidObjectStoreId(object_store_id)); -} - -KeyPrefix::KeyPrefix(int64 database_id, int64 object_store_id, int64 index_id) - : database_id_(database_id), - object_store_id_(object_store_id), - index_id_(index_id) { - DCHECK(KeyPrefix::IsValidDatabaseId(database_id)); - DCHECK(KeyPrefix::IsValidObjectStoreId(object_store_id)); - DCHECK(KeyPrefix::IsValidIndexId(index_id)); -} - -KeyPrefix::KeyPrefix(enum Type type, - int64 database_id, - int64 object_store_id, - int64 index_id) - : database_id_(database_id), - object_store_id_(object_store_id), - index_id_(index_id) { - DCHECK_EQ(type, INVALID_TYPE); - DCHECK(KeyPrefix::IsValidDatabaseId(database_id)); - DCHECK(KeyPrefix::IsValidObjectStoreId(object_store_id)); -} - -KeyPrefix KeyPrefix::CreateWithSpecialIndex(int64 database_id, - int64 object_store_id, - int64 index_id) { - DCHECK(KeyPrefix::IsValidDatabaseId(database_id)); - DCHECK(KeyPrefix::IsValidObjectStoreId(object_store_id)); - DCHECK(index_id); - return KeyPrefix(INVALID_TYPE, database_id, object_store_id, index_id); -} - -bool KeyPrefix::IsValidDatabaseId(int64 database_id) { - return (database_id > 0) && (database_id < KeyPrefix::kMaxDatabaseId); -} - -bool KeyPrefix::IsValidObjectStoreId(int64 object_store_id) { - return (object_store_id > 0) && - (object_store_id < KeyPrefix::kMaxObjectStoreId); -} - -bool KeyPrefix::IsValidIndexId(int64 index_id) { - return (index_id >= kMinimumIndexId) && (index_id < KeyPrefix::kMaxIndexId); -} - -const char* KeyPrefix::Decode(const char* start, - const char* limit, - KeyPrefix* result) { - if (start == limit) - return 0; - - unsigned char first_byte = *start++; - - int database_id_bytes = ((first_byte >> 5) & 0x7) + 1; - int object_store_id_bytes = ((first_byte >> 2) & 0x7) + 1; - int index_id_bytes = (first_byte & 0x3) + 1; - - if (start + database_id_bytes + object_store_id_bytes + index_id_bytes > - limit) - return 0; - - result->database_id_ = DecodeInt(start, start + database_id_bytes); - start += database_id_bytes; - result->object_store_id_ = DecodeInt(start, start + object_store_id_bytes); - start += object_store_id_bytes; - result->index_id_ = DecodeInt(start, start + index_id_bytes); - start += index_id_bytes; - - return start; -} - -std::vector<char> KeyPrefix::EncodeEmpty() { - const std::vector<char> result(4, 0); - DCHECK(EncodeInternal(0, 0, 0) == std::vector<char>(4, 0)); - return result; -} - -std::vector<char> KeyPrefix::Encode() const { - DCHECK(database_id_ != kInvalidId); - DCHECK(object_store_id_ != kInvalidId); - DCHECK(index_id_ != kInvalidId); - return EncodeInternal(database_id_, object_store_id_, index_id_); -} - -std::vector<char> KeyPrefix::EncodeInternal(int64 database_id, - int64 object_store_id, - int64 index_id) { - std::vector<char> database_id_string = - EncodeIntSafely(database_id, kMaxDatabaseId); - std::vector<char> object_store_id_string = - EncodeIntSafely(object_store_id, kMaxObjectStoreId); - std::vector<char> index_id_string = EncodeIntSafely(index_id, kMaxIndexId); - - DCHECK(database_id_string.size() <= kMaxDatabaseIdSizeBytes); - DCHECK(object_store_id_string.size() <= kMaxObjectStoreIdSizeBytes); - DCHECK(index_id_string.size() <= kMaxIndexIdSizeBytes); - - unsigned char first_byte = - (database_id_string.size() - 1) - << (kMaxObjectStoreIdSizeBits + kMaxIndexIdSizeBits) | - (object_store_id_string.size() - 1) << kMaxIndexIdSizeBits | - (index_id_string.size() - 1); - COMPILE_ASSERT(kMaxDatabaseIdSizeBits + kMaxObjectStoreIdSizeBits + - kMaxIndexIdSizeBits == - sizeof(first_byte) * 8, - CANT_ENCODE_IDS); - std::vector<char> ret; - ret.reserve(kDefaultInlineBufferSize); - ret.push_back(first_byte); - ret.insert(ret.end(), database_id_string.begin(), database_id_string.end()); - ret.insert( - ret.end(), object_store_id_string.begin(), object_store_id_string.end()); - ret.insert(ret.end(), index_id_string.begin(), index_id_string.end()); - - DCHECK_LE(ret.size(), kDefaultInlineBufferSize); - return ret; -} - -int KeyPrefix::Compare(const KeyPrefix& other) const { - DCHECK(database_id_ != kInvalidId); - DCHECK(object_store_id_ != kInvalidId); - DCHECK(index_id_ != kInvalidId); - - if (database_id_ != other.database_id_) - return CompareInts(database_id_, other.database_id_); - if (object_store_id_ != other.object_store_id_) - return CompareInts(object_store_id_, other.object_store_id_); - if (index_id_ != other.index_id_) - return CompareInts(index_id_, other.index_id_); - return 0; -} - -KeyPrefix::Type KeyPrefix::type() const { - DCHECK(database_id_ != kInvalidId); - DCHECK(object_store_id_ != kInvalidId); - DCHECK(index_id_ != kInvalidId); - - if (!database_id_) - return GLOBAL_METADATA; - if (!object_store_id_) - return DATABASE_METADATA; - if (index_id_ == kObjectStoreDataIndexId) - return OBJECT_STORE_DATA; - if (index_id_ == kExistsEntryIndexId) - return EXISTS_ENTRY; - if (index_id_ >= kMinimumIndexId) - return INDEX_DATA; - - NOTREACHED(); - return INVALID_TYPE; -} - -std::vector<char> SchemaVersionKey::Encode() { - std::vector<char> ret = KeyPrefix::EncodeEmpty(); - ret.push_back(kSchemaVersionTypeByte); - return ret; -} - -std::vector<char> MaxDatabaseIdKey::Encode() { - std::vector<char> ret = KeyPrefix::EncodeEmpty(); - ret.push_back(kMaxDatabaseIdTypeByte); - return ret; -} - -std::vector<char> DataVersionKey::Encode() { - std::vector<char> ret = KeyPrefix::EncodeEmpty(); - ret.push_back(kDataVersionTypeByte); - return ret; -} - -DatabaseFreeListKey::DatabaseFreeListKey() : database_id_(-1) {} - -const char* DatabaseFreeListKey::Decode(const char* start, - const char* limit, - DatabaseFreeListKey* result) { - KeyPrefix prefix; - const char* p = KeyPrefix::Decode(start, limit, &prefix); - if (!p) - return 0; - DCHECK(!prefix.database_id_); - DCHECK(!prefix.object_store_id_); - DCHECK(!prefix.index_id_); - if (p == limit) - return 0; - unsigned char type_byte = 0; - p = DecodeByte(p, limit, type_byte); - DCHECK_EQ(type_byte, kDatabaseFreeListTypeByte); - if (p == limit) - return 0; - return DecodeVarInt(p, limit, result->database_id_); -} - -std::vector<char> DatabaseFreeListKey::Encode(int64 database_id) { - std::vector<char> ret = KeyPrefix::EncodeEmpty(); - ret.push_back(kDatabaseFreeListTypeByte); - std::vector<char> tmp = EncodeVarInt(database_id); - ret.insert(ret.end(), tmp.begin(), tmp.end()); - return ret; -} - -std::vector<char> DatabaseFreeListKey::EncodeMaxKey() { - return Encode(std::numeric_limits<int64>::max()); -} - -int64 DatabaseFreeListKey::DatabaseId() const { - DCHECK_GE(database_id_, 0); - return database_id_; -} - -int DatabaseFreeListKey::Compare(const DatabaseFreeListKey& other) const { - DCHECK_GE(database_id_, 0); - return CompareInts(database_id_, other.database_id_); -} - -const char* DatabaseNameKey::Decode(const char* start, - const char* limit, - DatabaseNameKey* result) { - KeyPrefix prefix; - const char* p = KeyPrefix::Decode(start, limit, &prefix); - if (!p) - return p; - DCHECK(!prefix.database_id_); - DCHECK(!prefix.object_store_id_); - DCHECK(!prefix.index_id_); - if (p == limit) - return 0; - unsigned char type_byte = 0; - p = DecodeByte(p, limit, type_byte); - DCHECK_EQ(type_byte, kDatabaseNameTypeByte); - if (p == limit) - return 0; - p = DecodeStringWithLength(p, limit, result->origin_); - if (!p) - return 0; - return DecodeStringWithLength(p, limit, result->database_name_); -} - -std::vector<char> DatabaseNameKey::Encode(const string16& origin, - const string16& database_name) { - std::vector<char> ret = KeyPrefix::EncodeEmpty(); - ret.push_back(kDatabaseNameTypeByte); - std::vector<char> tmp = EncodeStringWithLength(origin); - ret.insert(ret.end(), tmp.begin(), tmp.end()); - tmp = EncodeStringWithLength(database_name); - ret.insert(ret.end(), tmp.begin(), tmp.end()); - return ret; -} - -std::vector<char> DatabaseNameKey::EncodeMinKeyForOrigin( - const string16& origin) { - return Encode(origin, string16()); -} - -std::vector<char> DatabaseNameKey::EncodeStopKeyForOrigin( - const string16& origin) { - // just after origin in collation order - return EncodeMinKeyForOrigin(origin + base::char16('\x01')); -} - -int DatabaseNameKey::Compare(const DatabaseNameKey& other) { - if (int x = origin_.compare(other.origin_)) - return x; - return database_name_.compare(other.database_name_); -} - -std::vector<char> DatabaseMetaDataKey::Encode(int64 database_id, - MetaDataType meta_data_type) { - KeyPrefix prefix(database_id); - std::vector<char> ret = prefix.Encode(); - ret.push_back(meta_data_type); - return ret; -} - -ObjectStoreMetaDataKey::ObjectStoreMetaDataKey() - : object_store_id_(-1), meta_data_type_(-1) {} - -const char* ObjectStoreMetaDataKey::Decode(const char* start, - const char* limit, - ObjectStoreMetaDataKey* result) { - KeyPrefix prefix; - const char* p = KeyPrefix::Decode(start, limit, &prefix); - if (!p) - return 0; - DCHECK(prefix.database_id_); - DCHECK(!prefix.object_store_id_); - DCHECK(!prefix.index_id_); - if (p == limit) - return 0; - unsigned char type_byte = 0; - p = DecodeByte(p, limit, type_byte); - DCHECK_EQ(type_byte, kObjectStoreMetaDataTypeByte); - if (p == limit) - return 0; - p = DecodeVarInt(p, limit, result->object_store_id_); - if (!p) - return 0; - DCHECK(result->object_store_id_); - if (p == limit) - return 0; - return DecodeByte(p, limit, result->meta_data_type_); -} - -std::vector<char> ObjectStoreMetaDataKey::Encode(int64 database_id, - int64 object_store_id, - unsigned char meta_data_type) { - KeyPrefix prefix(database_id); - std::vector<char> ret = prefix.Encode(); - ret.push_back(kObjectStoreMetaDataTypeByte); - std::vector<char> tmp = EncodeVarInt(object_store_id); - ret.insert(ret.end(), tmp.begin(), tmp.end()); - ret.push_back(meta_data_type); - return ret; -} - -std::vector<char> ObjectStoreMetaDataKey::EncodeMaxKey(int64 database_id) { - return Encode(database_id, - std::numeric_limits<int64>::max(), - kObjectMetaDataTypeMaximum); -} - -std::vector<char> ObjectStoreMetaDataKey::EncodeMaxKey(int64 database_id, - int64 object_store_id) { - return Encode(database_id, object_store_id, kObjectMetaDataTypeMaximum); -} - -int64 ObjectStoreMetaDataKey::ObjectStoreId() const { - DCHECK_GE(object_store_id_, 0); - return object_store_id_; -} -unsigned char ObjectStoreMetaDataKey::MetaDataType() const { - return meta_data_type_; -} - -int ObjectStoreMetaDataKey::Compare(const ObjectStoreMetaDataKey& other) { - DCHECK_GE(object_store_id_, 0); - if (int x = CompareInts(object_store_id_, other.object_store_id_)) - return x; - int64 result = meta_data_type_ - other.meta_data_type_; - if (result < 0) - return -1; - return (result > 0) ? 1 : result; -} - -IndexMetaDataKey::IndexMetaDataKey() - : object_store_id_(-1), index_id_(-1), meta_data_type_(0) {} - -const char* IndexMetaDataKey::Decode(const char* start, - const char* limit, - IndexMetaDataKey* result) { - KeyPrefix prefix; - const char* p = KeyPrefix::Decode(start, limit, &prefix); - if (!p) - return 0; - DCHECK(prefix.database_id_); - DCHECK(!prefix.object_store_id_); - DCHECK(!prefix.index_id_); - if (p == limit) - return 0; - unsigned char type_byte = 0; - p = DecodeByte(p, limit, type_byte); - DCHECK_EQ(type_byte, kIndexMetaDataTypeByte); - if (p == limit) - return 0; - p = DecodeVarInt(p, limit, result->object_store_id_); - if (!p) - return 0; - p = DecodeVarInt(p, limit, result->index_id_); - if (!p) - return 0; - if (p == limit) - return 0; - return DecodeByte(p, limit, result->meta_data_type_); -} - -std::vector<char> IndexMetaDataKey::Encode(int64 database_id, - int64 object_store_id, - int64 index_id, - unsigned char meta_data_type) { - KeyPrefix prefix(database_id); - std::vector<char> ret = prefix.Encode(); - ret.push_back(kIndexMetaDataTypeByte); - std::vector<char> tmp = EncodeVarInt(object_store_id); - ret.insert(ret.end(), tmp.begin(), tmp.end()); - tmp = EncodeVarInt(index_id); - ret.insert(ret.end(), tmp.begin(), tmp.end()); - tmp = EncodeByte(meta_data_type); - ret.insert(ret.end(), tmp.begin(), tmp.end()); - return ret; -} - -std::vector<char> IndexMetaDataKey::EncodeMaxKey(int64 database_id, - int64 object_store_id) { - return Encode(database_id, - object_store_id, - std::numeric_limits<int64>::max(), - kIndexMetaDataTypeMaximum); -} - -std::vector<char> IndexMetaDataKey::EncodeMaxKey(int64 database_id, - int64 object_store_id, - int64 index_id) { - return Encode( - database_id, object_store_id, index_id, kIndexMetaDataTypeMaximum); -} - -int IndexMetaDataKey::Compare(const IndexMetaDataKey& other) { - DCHECK_GE(object_store_id_, 0); - DCHECK_GE(index_id_, 0); - - if (int x = CompareInts(object_store_id_, other.object_store_id_)) - return x; - if (int x = CompareInts(index_id_, other.index_id_)) - return x; - return meta_data_type_ - other.meta_data_type_; -} - -int64 IndexMetaDataKey::IndexId() const { - DCHECK_GE(index_id_, 0); - return index_id_; -} - -ObjectStoreFreeListKey::ObjectStoreFreeListKey() : object_store_id_(-1) {} - -const char* ObjectStoreFreeListKey::Decode(const char* start, - const char* limit, - ObjectStoreFreeListKey* result) { - KeyPrefix prefix; - const char* p = KeyPrefix::Decode(start, limit, &prefix); - if (!p) - return 0; - DCHECK(prefix.database_id_); - DCHECK(!prefix.object_store_id_); - DCHECK(!prefix.index_id_); - if (p == limit) - return 0; - unsigned char type_byte = 0; - p = DecodeByte(p, limit, type_byte); - DCHECK_EQ(type_byte, kObjectStoreFreeListTypeByte); - if (p == limit) - return 0; - return DecodeVarInt(p, limit, result->object_store_id_); -} - -std::vector<char> ObjectStoreFreeListKey::Encode(int64 database_id, - int64 object_store_id) { - KeyPrefix prefix(database_id); - std::vector<char> ret = prefix.Encode(); - ret.push_back(kObjectStoreFreeListTypeByte); - std::vector<char> tmp = EncodeVarInt(object_store_id); - ret.insert(ret.end(), tmp.begin(), tmp.end()); - return ret; -} - -std::vector<char> ObjectStoreFreeListKey::EncodeMaxKey(int64 database_id) { - return Encode(database_id, std::numeric_limits<int64>::max()); -} - -int64 ObjectStoreFreeListKey::ObjectStoreId() const { - DCHECK_GE(object_store_id_, 0); - return object_store_id_; -} - -int ObjectStoreFreeListKey::Compare(const ObjectStoreFreeListKey& other) { - // TODO(jsbell): It may seem strange that we're not comparing database id's, - // but that comparison will have been made earlier. - // We should probably make this more clear, though... - DCHECK_GE(object_store_id_, 0); - return CompareInts(object_store_id_, other.object_store_id_); -} - -IndexFreeListKey::IndexFreeListKey() : object_store_id_(-1), index_id_(-1) {} - -const char* IndexFreeListKey::Decode(const char* start, - const char* limit, - IndexFreeListKey* result) { - KeyPrefix prefix; - const char* p = KeyPrefix::Decode(start, limit, &prefix); - if (!p) - return 0; - DCHECK(prefix.database_id_); - DCHECK(!prefix.object_store_id_); - DCHECK(!prefix.index_id_); - if (p == limit) - return 0; - unsigned char type_byte = 0; - p = DecodeByte(p, limit, type_byte); - DCHECK_EQ(type_byte, kIndexFreeListTypeByte); - if (p == limit) - return 0; - p = DecodeVarInt(p, limit, result->object_store_id_); - if (!p) - return 0; - return DecodeVarInt(p, limit, result->index_id_); -} - -std::vector<char> IndexFreeListKey::Encode(int64 database_id, - int64 object_store_id, - int64 index_id) { - KeyPrefix prefix(database_id); - std::vector<char> ret = prefix.Encode(); - ret.push_back(kIndexFreeListTypeByte); - std::vector<char> tmp = EncodeVarInt(object_store_id); - ret.insert(ret.end(), tmp.begin(), tmp.end()); - tmp = EncodeVarInt(index_id); - ret.insert(ret.end(), tmp.begin(), tmp.end()); - return ret; -} - -std::vector<char> IndexFreeListKey::EncodeMaxKey(int64 database_id, - int64 object_store_id) { - return Encode( - database_id, object_store_id, std::numeric_limits<int64>::max()); -} - -int IndexFreeListKey::Compare(const IndexFreeListKey& other) { - DCHECK_GE(object_store_id_, 0); - DCHECK_GE(index_id_, 0); - if (int x = CompareInts(object_store_id_, other.object_store_id_)) - return x; - return CompareInts(index_id_, other.index_id_); -} - -int64 IndexFreeListKey::ObjectStoreId() const { - DCHECK_GE(object_store_id_, 0); - return object_store_id_; -} - -int64 IndexFreeListKey::IndexId() const { - DCHECK_GE(index_id_, 0); - return index_id_; -} - -// TODO(jsbell): We never use this to look up object store ids, -// because a mapping is kept in the IndexedDBDatabaseImpl. Can the -// mapping become unreliable? Can we remove this? -const char* ObjectStoreNamesKey::Decode(const char* start, - const char* limit, - ObjectStoreNamesKey* result) { - KeyPrefix prefix; - const char* p = KeyPrefix::Decode(start, limit, &prefix); - if (!p) - return 0; - DCHECK(prefix.database_id_); - DCHECK(!prefix.object_store_id_); - DCHECK(!prefix.index_id_); - if (p == limit) - return 0; - unsigned char type_byte = 0; - p = DecodeByte(p, limit, type_byte); - DCHECK_EQ(type_byte, kObjectStoreNamesTypeByte); - return DecodeStringWithLength(p, limit, result->object_store_name_); -} - -std::vector<char> ObjectStoreNamesKey::Encode( - int64 database_id, - const string16& object_store_name) { - KeyPrefix prefix(database_id); - std::vector<char> ret = prefix.Encode(); - ret.push_back(kObjectStoreNamesTypeByte); - std::vector<char> tmp = EncodeStringWithLength(object_store_name); - ret.insert(ret.end(), tmp.begin(), tmp.end()); - return ret; -} - -int ObjectStoreNamesKey::Compare(const ObjectStoreNamesKey& other) { - return object_store_name_.compare(other.object_store_name_); -} - -IndexNamesKey::IndexNamesKey() : object_store_id_(-1) {} - -// TODO(jsbell): We never use this to look up index ids, because a mapping -// is kept at a higher level. -const char* IndexNamesKey::Decode(const char* start, - const char* limit, - IndexNamesKey* result) { - KeyPrefix prefix; - const char* p = KeyPrefix::Decode(start, limit, &prefix); - if (!p) - return 0; - DCHECK(prefix.database_id_); - DCHECK(!prefix.object_store_id_); - DCHECK(!prefix.index_id_); - if (p == limit) - return 0; - unsigned char type_byte = 0; - p = DecodeByte(p, limit, type_byte); - DCHECK_EQ(type_byte, kIndexNamesKeyTypeByte); - if (p == limit) - return 0; - p = DecodeVarInt(p, limit, result->object_store_id_); - if (!p) - return 0; - return DecodeStringWithLength(p, limit, result->index_name_); -} - -std::vector<char> IndexNamesKey::Encode(int64 database_id, - int64 object_store_id, - const string16& index_name) { - KeyPrefix prefix(database_id); - std::vector<char> ret = prefix.Encode(); - ret.push_back(kIndexNamesKeyTypeByte); - std::vector<char> tmp = EncodeVarInt(object_store_id); - ret.insert(ret.end(), tmp.begin(), tmp.end()); - tmp = EncodeStringWithLength(index_name); - ret.insert(ret.end(), tmp.begin(), tmp.end()); - return ret; -} - -int IndexNamesKey::Compare(const IndexNamesKey& other) { - DCHECK_GE(object_store_id_, 0); - if (int x = CompareInts(object_store_id_, other.object_store_id_)) - return x; - return index_name_.compare(other.index_name_); -} - -ObjectStoreDataKey::ObjectStoreDataKey() {} -ObjectStoreDataKey::~ObjectStoreDataKey() {} - -const char* ObjectStoreDataKey::Decode(const char* start, - const char* end, - ObjectStoreDataKey* result) { - KeyPrefix prefix; - const char* p = KeyPrefix::Decode(start, end, &prefix); - if (!p) - return 0; - DCHECK(prefix.database_id_); - DCHECK(prefix.object_store_id_); - DCHECK_EQ(prefix.index_id_, kSpecialIndexNumber); - if (p == end) - return 0; - return ExtractEncodedIDBKey(p, end, &result->encoded_user_key_); -} - -std::vector<char> ObjectStoreDataKey::Encode( - int64 database_id, - int64 object_store_id, - const std::vector<char> encoded_user_key) { - KeyPrefix prefix(KeyPrefix::CreateWithSpecialIndex( - database_id, object_store_id, kSpecialIndexNumber)); - std::vector<char> ret = prefix.Encode(); - ret.insert(ret.end(), encoded_user_key.begin(), encoded_user_key.end()); - - return ret; -} - -std::vector<char> ObjectStoreDataKey::Encode(int64 database_id, - int64 object_store_id, - const IndexedDBKey& user_key) { - return Encode(database_id, object_store_id, EncodeIDBKey(user_key)); -} - -int ObjectStoreDataKey::Compare(const ObjectStoreDataKey& other, bool& ok) { - return CompareEncodedIDBKeys(encoded_user_key_, other.encoded_user_key_, ok); -} - -scoped_ptr<IndexedDBKey> ObjectStoreDataKey::user_key() const { - scoped_ptr<IndexedDBKey> key; - DecodeIDBKey(&encoded_user_key_[0], - &encoded_user_key_[0] + encoded_user_key_.size(), - &key); - return key.Pass(); -} - -const int64 ObjectStoreDataKey::kSpecialIndexNumber = kObjectStoreDataIndexId; - -ExistsEntryKey::ExistsEntryKey() {} -ExistsEntryKey::~ExistsEntryKey() {} - -const char* ExistsEntryKey::Decode(const char* start, - const char* end, - ExistsEntryKey* result) { - KeyPrefix prefix; - const char* p = KeyPrefix::Decode(start, end, &prefix); - if (!p) - return 0; - DCHECK(prefix.database_id_); - DCHECK(prefix.object_store_id_); - DCHECK_EQ(prefix.index_id_, kSpecialIndexNumber); - if (p == end) - return 0; - return ExtractEncodedIDBKey(p, end, &result->encoded_user_key_); -} - -std::vector<char> ExistsEntryKey::Encode(int64 database_id, - int64 object_store_id, - const std::vector<char>& encoded_key) { - KeyPrefix prefix(KeyPrefix::CreateWithSpecialIndex( - database_id, object_store_id, kSpecialIndexNumber)); - std::vector<char> ret = prefix.Encode(); - ret.insert(ret.end(), encoded_key.begin(), encoded_key.end()); - return ret; -} - -std::vector<char> ExistsEntryKey::Encode(int64 database_id, - int64 object_store_id, - const IndexedDBKey& user_key) { - return Encode(database_id, object_store_id, EncodeIDBKey(user_key)); -} - -int ExistsEntryKey::Compare(const ExistsEntryKey& other, bool& ok) { - return CompareEncodedIDBKeys(encoded_user_key_, other.encoded_user_key_, ok); -} - -scoped_ptr<IndexedDBKey> ExistsEntryKey::user_key() const { - scoped_ptr<IndexedDBKey> key; - DecodeIDBKey(&encoded_user_key_[0], - &encoded_user_key_[0] + encoded_user_key_.size(), - &key); - return key.Pass(); -} - -const int64 ExistsEntryKey::kSpecialIndexNumber = kExistsEntryIndexId; - -IndexDataKey::IndexDataKey() - : database_id_(-1), - object_store_id_(-1), - index_id_(-1), - sequence_number_(-1) {} - -IndexDataKey::~IndexDataKey() {} - -const char* IndexDataKey::Decode(const char* start, - const char* limit, - IndexDataKey* result) { - KeyPrefix prefix; - const char* p = KeyPrefix::Decode(start, limit, &prefix); - if (!p) - return 0; - DCHECK(prefix.database_id_); - DCHECK(prefix.object_store_id_); - DCHECK_GE(prefix.index_id_, kMinimumIndexId); - result->database_id_ = prefix.database_id_; - result->object_store_id_ = prefix.object_store_id_; - result->index_id_ = prefix.index_id_; - result->sequence_number_ = -1; - result->encoded_primary_key_ = MinIDBKey(); - - p = ExtractEncodedIDBKey(p, limit, &result->encoded_user_key_); - if (!p) - return 0; - - // [optional] sequence number - if (p == limit) - return p; - p = DecodeVarInt(p, limit, result->sequence_number_); - if (!p) - return 0; - - // [optional] primary key - if (p == limit) - return p; - p = ExtractEncodedIDBKey(p, limit, &result->encoded_primary_key_); - if (!p) - return 0; - - return p; -} - -std::vector<char> IndexDataKey::Encode( - int64 database_id, - int64 object_store_id, - int64 index_id, - const std::vector<char>& encoded_user_key, - const std::vector<char>& encoded_primary_key, - int64 sequence_number) { - KeyPrefix prefix(database_id, object_store_id, index_id); - std::vector<char> ret = prefix.Encode(); - ret.insert(ret.end(), encoded_user_key.begin(), encoded_user_key.end()); - std::vector<char> tmp = EncodeVarInt(sequence_number); - ret.insert(ret.end(), tmp.begin(), tmp.end()); - ret.insert(ret.end(), encoded_primary_key.begin(), encoded_primary_key.end()); - return ret; -} - -std::vector<char> IndexDataKey::Encode(int64 database_id, - int64 object_store_id, - int64 index_id, - const IndexedDBKey& user_key) { - return Encode(database_id, - object_store_id, - index_id, - EncodeIDBKey(user_key), - MinIDBKey()); -} - -std::vector<char> IndexDataKey::EncodeMinKey(int64 database_id, - int64 object_store_id, - int64 index_id) { - return Encode( - database_id, object_store_id, index_id, MinIDBKey(), MinIDBKey()); -} - -std::vector<char> IndexDataKey::EncodeMaxKey(int64 database_id, - int64 object_store_id, - int64 index_id) { - return Encode(database_id, - object_store_id, - index_id, - MaxIDBKey(), - MaxIDBKey(), - std::numeric_limits<int64>::max()); -} - -int IndexDataKey::Compare(const IndexDataKey& other, - bool ignore_duplicates, - bool& ok) { - DCHECK_GE(database_id_, 0); - DCHECK_GE(object_store_id_, 0); - DCHECK_GE(index_id_, 0); - int result = - CompareEncodedIDBKeys(encoded_user_key_, other.encoded_user_key_, ok); - if (!ok || result) - return result; - if (ignore_duplicates) - return 0; - result = CompareEncodedIDBKeys( - encoded_primary_key_, other.encoded_primary_key_, ok); - if (!ok || result) - return result; - return CompareInts(sequence_number_, other.sequence_number_); -} - -int64 IndexDataKey::DatabaseId() const { - DCHECK_GE(database_id_, 0); - return database_id_; -} - -int64 IndexDataKey::ObjectStoreId() const { - DCHECK_GE(object_store_id_, 0); - return object_store_id_; -} - -int64 IndexDataKey::IndexId() const { - DCHECK_GE(index_id_, 0); - return index_id_; -} - -scoped_ptr<IndexedDBKey> IndexDataKey::user_key() const { - scoped_ptr<IndexedDBKey> key; - DecodeIDBKey(&encoded_user_key_[0], - &encoded_user_key_[0] + encoded_user_key_.size(), - &key); - return key.Pass(); -} - -scoped_ptr<IndexedDBKey> IndexDataKey::primary_key() const { - scoped_ptr<IndexedDBKey> key; - DecodeIDBKey(&encoded_primary_key_[0], - &encoded_primary_key_[0] + encoded_primary_key_.size(), - &key); - return key.Pass(); -} - -} // namespace content diff --git a/content/browser/indexed_db/indexed_db_leveldb_coding.h b/content/browser/indexed_db/indexed_db_leveldb_coding.h deleted file mode 100644 index ff8f5a1..0000000 --- a/content/browser/indexed_db/indexed_db_leveldb_coding.h +++ /dev/null @@ -1,467 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_LEVELDB_CODING_H_ -#define CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_LEVELDB_CODING_H_ - -#include <vector> - -#include "base/basictypes.h" -#include "base/logging.h" -#include "base/memory/ref_counted.h" -#include "base/memory/scoped_ptr.h" -#include "base/string16.h" -#include "content/common/indexed_db/indexed_db_key.h" -#include "content/common/indexed_db/indexed_db_key_path.h" - -namespace content { - -class LevelDBSlice; - -CONTENT_EXPORT extern const unsigned char kMinimumIndexId; - -CONTENT_EXPORT std::vector<char> EncodeByte(unsigned char); -CONTENT_EXPORT const char* DecodeByte(const char* p, - const char* limit, - unsigned char& found_char); -CONTENT_EXPORT std::vector<char> MaxIDBKey(); -CONTENT_EXPORT std::vector<char> MinIDBKey(); -CONTENT_EXPORT std::vector<char> EncodeBool(bool value); -CONTENT_EXPORT bool DecodeBool(const char* begin, const char* end); -CONTENT_EXPORT std::vector<char> EncodeInt(int64); -inline std::vector<char> EncodeIntSafely(int64 nParam, int64 max) { - DCHECK_LE(nParam, max); - return EncodeInt(nParam); -} - -template <class T> int64 DecodeInt(T begin, T end) { - // TODO(alecflett): Make this a DCHECK_LE(). - DCHECK(begin <= end); - int64 ret = 0; - - int shift = 0; - while (begin < end) { - unsigned char c = *begin++; - ret |= static_cast<int64>(c) << shift; - shift += 8; - } - - return ret; -} - -CONTENT_EXPORT std::vector<char> EncodeVarInt(int64); -CONTENT_EXPORT const char* DecodeVarInt(const char* p, - const char* limit, - int64& found_int); -CONTENT_EXPORT std::vector<char> EncodeString(const string16& string); -CONTENT_EXPORT string16 DecodeString(const char* p, const char* end); -CONTENT_EXPORT std::vector<char> EncodeStringWithLength(const string16& string); -CONTENT_EXPORT const char* DecodeStringWithLength(const char* p, - const char* limit, - string16& found_string); -CONTENT_EXPORT int CompareEncodedStringsWithLength(const char*& p, - const char* limit_p, - const char*& q, - const char* limit_q, - bool& ok); -CONTENT_EXPORT std::vector<char> EncodeDouble(double value); -CONTENT_EXPORT const char* DecodeDouble(const char* p, - const char* limit, - double* value); -void EncodeIDBKey(const IndexedDBKey& key, std::vector<char>& into); -CONTENT_EXPORT std::vector<char> EncodeIDBKey(const IndexedDBKey& key); -CONTENT_EXPORT const char* DecodeIDBKey(const char* p, - const char* limit, - scoped_ptr<IndexedDBKey>* found_key); -CONTENT_EXPORT const char* ExtractEncodedIDBKey(const char* start, - const char* limit, - std::vector<char>* result); -CONTENT_EXPORT int CompareEncodedIDBKeys(const std::vector<char>& a, - const std::vector<char>& b, - bool& ok); -CONTENT_EXPORT std::vector<char> EncodeIDBKeyPath( - const IndexedDBKeyPath& key_path); -CONTENT_EXPORT IndexedDBKeyPath DecodeIDBKeyPath(const char* start, - const char* limit); - -CONTENT_EXPORT int Compare(const LevelDBSlice& a, - const LevelDBSlice& b, - bool index_keys = false); - -class KeyPrefix { - public: - KeyPrefix(); - explicit KeyPrefix(int64 database_id); - KeyPrefix(int64 database_id, int64 object_store_id); - KeyPrefix(int64 database_id, int64 object_store_id, int64 index_id); - static KeyPrefix CreateWithSpecialIndex(int64 database_id, - int64 object_store_id, - int64 index_id); - - static const char* Decode(const char* start, - const char* limit, - KeyPrefix* result); - std::vector<char> Encode() const; - static std::vector<char> EncodeEmpty(); - int Compare(const KeyPrefix& other) const; - - enum Type { - GLOBAL_METADATA, - DATABASE_METADATA, - OBJECT_STORE_DATA, - EXISTS_ENTRY, - INDEX_DATA, - INVALID_TYPE - }; - - static const size_t kMaxDatabaseIdSizeBits = 3; - static const size_t kMaxObjectStoreIdSizeBits = 3; - static const size_t kMaxIndexIdSizeBits = 2; - - static const size_t kMaxDatabaseIdSizeBytes = - 1ULL << kMaxDatabaseIdSizeBits; // 8 - static const size_t kMaxObjectStoreIdSizeBytes = - 1ULL << kMaxObjectStoreIdSizeBits; // 8 - static const size_t kMaxIndexIdSizeBytes = 1ULL << kMaxIndexIdSizeBits; // 4 - - static const size_t kMaxDatabaseIdBits = - kMaxDatabaseIdSizeBytes * 8 - 1; // 63 - static const size_t kMaxObjectStoreIdBits = - kMaxObjectStoreIdSizeBytes * 8 - 1; // 63 - static const size_t kMaxIndexIdBits = kMaxIndexIdSizeBytes * 8 - 1; // 31 - - static const int64 kMaxDatabaseId = - (1ULL << kMaxDatabaseIdBits) - 1; // max signed int64 - static const int64 kMaxObjectStoreId = - (1ULL << kMaxObjectStoreIdBits) - 1; // max signed int64 - static const int64 kMaxIndexId = - (1ULL << kMaxIndexIdBits) - 1; // max signed int32 - - static bool IsValidDatabaseId(int64 database_id); - static bool IsValidObjectStoreId(int64 index_id); - static bool IsValidIndexId(int64 index_id); - static bool ValidIds(int64 database_id, - int64 object_store_id, - int64 index_id) { - return IsValidDatabaseId(database_id) && - IsValidObjectStoreId(object_store_id) && IsValidIndexId(index_id); - } - static bool ValidIds(int64 database_id, int64 object_store_id) { - return IsValidDatabaseId(database_id) && - IsValidObjectStoreId(object_store_id); - } - - Type type() const; - - int64 database_id_; - int64 object_store_id_; - int64 index_id_; - - static const int64 kInvalidId = -1; - - private: - static std::vector<char> EncodeInternal(int64 database_id, - int64 object_store_id, - int64 index_id); - // Special constructor for CreateWithSpecialIndex() - KeyPrefix(enum Type, - int64 database_id, - int64 object_store_id, - int64 index_id); -}; - -class SchemaVersionKey { - public: - CONTENT_EXPORT static std::vector<char> Encode(); -}; - -class MaxDatabaseIdKey { - public: - CONTENT_EXPORT static std::vector<char> Encode(); -}; - -class DataVersionKey { - public: - static std::vector<char> Encode(); -}; - -class DatabaseFreeListKey { - public: - DatabaseFreeListKey(); - static const char* Decode(const char* start, - const char* limit, - DatabaseFreeListKey* result); - CONTENT_EXPORT static std::vector<char> Encode(int64 database_id); - static CONTENT_EXPORT std::vector<char> EncodeMaxKey(); - int64 DatabaseId() const; - int Compare(const DatabaseFreeListKey& other) const; - - private: - int64 database_id_; -}; - -class DatabaseNameKey { - public: - static const char* Decode(const char* start, - const char* limit, - DatabaseNameKey* result); - CONTENT_EXPORT static std::vector<char> Encode(const string16& origin, - const string16& database_name); - static std::vector<char> EncodeMinKeyForOrigin(const string16& origin); - static std::vector<char> EncodeStopKeyForOrigin(const string16& origin); - string16 origin() const { return origin_; } - string16 database_name() const { return database_name_; } - int Compare(const DatabaseNameKey& other); - - private: - string16 origin_; // TODO(jsbell): Store encoded strings, or just pointers. - string16 database_name_; -}; - -class DatabaseMetaDataKey { - public: - enum MetaDataType { - ORIGIN_NAME = 0, - DATABASE_NAME = 1, - USER_VERSION = 2, - MAX_OBJECT_STORE_ID = 3, - USER_INT_VERSION = 4, - MAX_SIMPLE_METADATA_TYPE = 5 - }; - - CONTENT_EXPORT static std::vector<char> Encode(int64 database_id, - MetaDataType type); -}; - -class ObjectStoreMetaDataKey { - public: - enum MetaDataType { - NAME = 0, - KEY_PATH = 1, - AUTO_INCREMENT = 2, - EVICTABLE = 3, - LAST_VERSION = 4, - MAX_INDEX_ID = 5, - HAS_KEY_PATH = 6, - KEY_GENERATOR_CURRENT_NUMBER = 7 - }; - - ObjectStoreMetaDataKey(); - static const char* Decode(const char* start, - const char* limit, - ObjectStoreMetaDataKey* result); - CONTENT_EXPORT static std::vector<char> Encode(int64 database_id, - int64 object_store_id, - unsigned char meta_data_type); - CONTENT_EXPORT static std::vector<char> EncodeMaxKey(int64 database_id); - CONTENT_EXPORT static std::vector<char> EncodeMaxKey(int64 database_id, - int64 object_store_id); - int64 ObjectStoreId() const; - unsigned char MetaDataType() const; - int Compare(const ObjectStoreMetaDataKey& other); - - private: - int64 object_store_id_; - unsigned char meta_data_type_; -}; - -class IndexMetaDataKey { - public: - enum MetaDataType { - NAME = 0, - UNIQUE = 1, - KEY_PATH = 2, - MULTI_ENTRY = 3 - }; - - IndexMetaDataKey(); - static const char* Decode(const char* start, - const char* limit, - IndexMetaDataKey* result); - CONTENT_EXPORT static std::vector<char> Encode(int64 database_id, - int64 object_store_id, - int64 index_id, - unsigned char meta_data_type); - CONTENT_EXPORT static std::vector<char> EncodeMaxKey(int64 database_id, - int64 object_store_id); - CONTENT_EXPORT static std::vector<char> EncodeMaxKey(int64 database_id, - int64 object_store_id, - int64 index_id); - int Compare(const IndexMetaDataKey& other); - int64 IndexId() const; - unsigned char meta_data_type() const { return meta_data_type_; } - - private: - int64 object_store_id_; - int64 index_id_; - unsigned char meta_data_type_; -}; - -class ObjectStoreFreeListKey { - public: - ObjectStoreFreeListKey(); - static const char* Decode(const char* start, - const char* limit, - ObjectStoreFreeListKey* result); - CONTENT_EXPORT static std::vector<char> Encode(int64 database_id, - int64 object_store_id); - CONTENT_EXPORT static std::vector<char> EncodeMaxKey(int64 database_id); - int64 ObjectStoreId() const; - int Compare(const ObjectStoreFreeListKey& other); - - private: - int64 object_store_id_; -}; - -class IndexFreeListKey { - public: - IndexFreeListKey(); - static const char* Decode(const char* start, - const char* limit, - IndexFreeListKey* result); - CONTENT_EXPORT static std::vector<char> Encode(int64 database_id, - int64 object_store_id, - int64 index_id); - CONTENT_EXPORT static std::vector<char> EncodeMaxKey(int64 database_id, - int64 object_store_id); - int Compare(const IndexFreeListKey& other); - int64 ObjectStoreId() const; - int64 IndexId() const; - - private: - int64 object_store_id_; - int64 index_id_; -}; - -class ObjectStoreNamesKey { - public: - // TODO(jsbell): We never use this to look up object store ids, - // because a mapping is kept in the IndexedDBDatabaseImpl. Can the - // mapping become unreliable? Can we remove this? - static const char* Decode(const char* start, - const char* limit, - ObjectStoreNamesKey* result); - CONTENT_EXPORT static std::vector<char> Encode( - int64 database_id, - const string16& object_store_name); - int Compare(const ObjectStoreNamesKey& other); - string16 object_store_name() const { return object_store_name_; } - - private: - string16 - object_store_name_; // TODO(jsbell): Store the encoded string, or just - // pointers to it. -}; - -class IndexNamesKey { - public: - IndexNamesKey(); - // TODO(jsbell): We never use this to look up index ids, because a mapping - // is kept at a higher level. - static const char* Decode(const char* start, - const char* limit, - IndexNamesKey* result); - CONTENT_EXPORT static std::vector<char> Encode(int64 database_id, - int64 object_store_id, - const string16& index_name); - int Compare(const IndexNamesKey& other); - string16 index_name() const { return index_name_; } - - private: - int64 object_store_id_; - string16 index_name_; -}; - -class ObjectStoreDataKey { - public: - static const char* Decode(const char* start, - const char* end, - ObjectStoreDataKey* result); - CONTENT_EXPORT static std::vector<char> Encode( - int64 database_id, - int64 object_store_id, - const std::vector<char> encoded_user_key); - static std::vector<char> Encode(int64 database_id, - int64 object_store_id, - const IndexedDBKey& user_key); - int Compare(const ObjectStoreDataKey& other, bool& ok); - scoped_ptr<IndexedDBKey> user_key() const; - static const int64 kSpecialIndexNumber; - ObjectStoreDataKey(); - ~ObjectStoreDataKey(); - - private: - std::vector<char> encoded_user_key_; -}; - -class ExistsEntryKey { - public: - ExistsEntryKey(); - ~ExistsEntryKey(); - - static const char* Decode(const char* start, - const char* end, - ExistsEntryKey* result); - CONTENT_EXPORT static std::vector<char> Encode( - int64 database_id, - int64 object_store_id, - const std::vector<char>& encoded_key); - static std::vector<char> Encode(int64 database_id, - int64 object_store_id, - const IndexedDBKey& user_key); - int Compare(const ExistsEntryKey& other, bool& ok); - scoped_ptr<IndexedDBKey> user_key() const; - - static const int64 kSpecialIndexNumber; - - private: - std::vector<char> encoded_user_key_; - DISALLOW_COPY_AND_ASSIGN(ExistsEntryKey); -}; - -class IndexDataKey { - public: - IndexDataKey(); - ~IndexDataKey(); - static const char* Decode(const char* start, - const char* limit, - IndexDataKey* result); - CONTENT_EXPORT static std::vector<char> Encode( - int64 database_id, - int64 object_store_id, - int64 index_id, - const std::vector<char>& encoded_user_key, - const std::vector<char>& encoded_primary_key, - int64 sequence_number = 0); - static std::vector<char> Encode(int64 database_id, - int64 object_store_id, - int64 index_id, - const IndexedDBKey& user_key); - static std::vector<char> EncodeMinKey(int64 database_id, - int64 object_store_id, - int64 index_id); - CONTENT_EXPORT static std::vector<char> EncodeMaxKey(int64 database_id, - int64 object_store_id, - int64 index_id); - int Compare(const IndexDataKey& other, bool ignore_duplicates, bool& ok); - int64 DatabaseId() const; - int64 ObjectStoreId() const; - int64 IndexId() const; - scoped_ptr<IndexedDBKey> user_key() const; - scoped_ptr<IndexedDBKey> primary_key() const; - - private: - int64 database_id_; - int64 object_store_id_; - int64 index_id_; - std::vector<char> encoded_user_key_; - std::vector<char> encoded_primary_key_; - int64 sequence_number_; - - DISALLOW_COPY_AND_ASSIGN(IndexDataKey); -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_LEVELDB_CODING_H_ diff --git a/content/browser/indexed_db/indexed_db_leveldb_coding_unittest.cc b/content/browser/indexed_db/indexed_db_leveldb_coding_unittest.cc deleted file mode 100644 index 6bbcf9a..0000000 --- a/content/browser/indexed_db/indexed_db_leveldb_coding_unittest.cc +++ /dev/null @@ -1,755 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/indexed_db_leveldb_coding.h" - -#include <limits> -#include <string> -#include <vector> - -#include "base/string16.h" -#include "base/strings/utf_string_conversions.h" -#include "content/browser/indexed_db/leveldb/leveldb_slice.h" -#include "content/common/indexed_db/indexed_db_key.h" -#include "content/common/indexed_db/indexed_db_key_path.h" -#include "testing/gtest/include/gtest/gtest.h" - -using WebKit::WebIDBKey; -using WebKit::WebIDBKeyPath; - -namespace content { - -namespace { - -static IndexedDBKey CreateArrayIDBKey() { - return IndexedDBKey(IndexedDBKey::KeyArray()); -} - -static IndexedDBKey CreateArrayIDBKey(const IndexedDBKey& key1) { - IndexedDBKey::KeyArray array; - array.push_back(key1); - return IndexedDBKey(array); -} - -static IndexedDBKey CreateArrayIDBKey(const IndexedDBKey& key1, - const IndexedDBKey& key2) { - IndexedDBKey::KeyArray array; - array.push_back(key1); - array.push_back(key2); - return IndexedDBKey(array); -} - -TEST(IndexedDBLevelDBCodingTest, EncodeByte) { - std::vector<char> expected; - expected.push_back(0); - unsigned char c; - - c = 0; - expected[0] = c; - EXPECT_EQ(expected, EncodeByte(c)); - - c = 1; - expected[0] = c; - EXPECT_EQ(expected, EncodeByte(c)); - - c = 255; - expected[0] = c; - EXPECT_EQ(expected, EncodeByte(c)); -} - -TEST(IndexedDBLevelDBCodingTest, DecodeByte) { - std::vector<unsigned char> test_cases; - test_cases.push_back(0); - test_cases.push_back(1); - test_cases.push_back(255); - - for (size_t i = 0; i < test_cases.size(); ++i) { - unsigned char n = test_cases[i]; - std::vector<char> v = EncodeByte(n); - - unsigned char res; - const char* p = DecodeByte(&*v.begin(), &*v.rbegin() + 1, res); - EXPECT_EQ(n, res); - EXPECT_EQ(&*v.rbegin() + 1, p); - } -} - -TEST(IndexedDBLevelDBCodingTest, EncodeBool) { - { - std::vector<char> expected; - expected.push_back(1); - EXPECT_EQ(expected, EncodeBool(true)); - } - { - std::vector<char> expected; - expected.push_back(0); - EXPECT_EQ(expected, EncodeBool(false)); - } -} - -static int CompareKeys(const std::vector<char>& a, const std::vector<char>& b) { - bool ok; - int result = CompareEncodedIDBKeys(a, b, ok); - EXPECT_TRUE(ok); - return result; -} - -TEST(IndexedDBLevelDBCodingTest, MaxIDBKey) { - std::vector<char> max_key = MaxIDBKey(); - - std::vector<char> min_key = MinIDBKey(); - std::vector<char> array_key = - EncodeIDBKey(IndexedDBKey(IndexedDBKey::KeyArray())); - std::vector<char> string_key = - EncodeIDBKey(IndexedDBKey(ASCIIToUTF16("Hello world"))); - std::vector<char> number_key = - EncodeIDBKey(IndexedDBKey(3.14, WebIDBKey::NumberType)); - std::vector<char> date_key = - EncodeIDBKey(IndexedDBKey(1000000, WebIDBKey::DateType)); - - EXPECT_GT(CompareKeys(max_key, min_key), 0); - EXPECT_GT(CompareKeys(max_key, array_key), 0); - EXPECT_GT(CompareKeys(max_key, string_key), 0); - EXPECT_GT(CompareKeys(max_key, number_key), 0); - EXPECT_GT(CompareKeys(max_key, date_key), 0); -} - -TEST(IndexedDBLevelDBCodingTest, MinIDBKey) { - std::vector<char> min_key = MinIDBKey(); - - std::vector<char> max_key = MaxIDBKey(); - std::vector<char> array_key = - EncodeIDBKey(IndexedDBKey(IndexedDBKey::KeyArray())); - std::vector<char> string_key = - EncodeIDBKey(IndexedDBKey(ASCIIToUTF16("Hello world"))); - std::vector<char> number_key = - EncodeIDBKey(IndexedDBKey(3.14, WebIDBKey::NumberType)); - std::vector<char> date_key = - EncodeIDBKey(IndexedDBKey(1000000, WebIDBKey::DateType)); - - EXPECT_LT(CompareKeys(min_key, max_key), 0); - EXPECT_LT(CompareKeys(min_key, array_key), 0); - EXPECT_LT(CompareKeys(min_key, string_key), 0); - EXPECT_LT(CompareKeys(min_key, number_key), 0); - EXPECT_LT(CompareKeys(min_key, date_key), 0); -} - -TEST(IndexedDBLevelDBCodingTest, EncodeInt) { - EXPECT_EQ(static_cast<size_t>(1), EncodeInt(0).size()); - EXPECT_EQ(static_cast<size_t>(1), EncodeInt(1).size()); - EXPECT_EQ(static_cast<size_t>(1), EncodeInt(255).size()); - EXPECT_EQ(static_cast<size_t>(2), EncodeInt(256).size()); - EXPECT_EQ(static_cast<size_t>(4), EncodeInt(0xffffffff).size()); -#ifdef NDEBUG - EXPECT_EQ(static_cast<size_t>(8), EncodeInt(-1).size()); -#endif -} - -TEST(IndexedDBLevelDBCodingTest, DecodeBool) { - { - std::vector<char> encoded; - encoded.push_back(1); - EXPECT_TRUE(DecodeBool(&*encoded.begin(), &*encoded.rbegin() + 1)); - } - { - std::vector<char> encoded; - encoded.push_back(0); - EXPECT_FALSE(DecodeBool(&*encoded.begin(), &*encoded.rbegin() + 1)); - } -} - -TEST(IndexedDBLevelDBCodingTest, DecodeInt) { - std::vector<int64> test_cases; - test_cases.push_back(0); - test_cases.push_back(1); - test_cases.push_back(255); - test_cases.push_back(256); - test_cases.push_back(65535); - test_cases.push_back(655536); - test_cases.push_back(7711192431755665792ll); - test_cases.push_back(0x7fffffffffffffffll); -#ifdef NDEBUG - test_cases.push_back(-3); -#endif - - for (size_t i = 0; i < test_cases.size(); ++i) { - int64 n = test_cases[i]; - std::vector<char> v = EncodeInt(n); - EXPECT_EQ(n, DecodeInt(&*v.begin(), &*v.rbegin() + 1)); - } -} - -TEST(IndexedDBLevelDBCodingTest, EncodeVarInt) { - EXPECT_EQ(static_cast<size_t>(1), EncodeVarInt(0).size()); - EXPECT_EQ(static_cast<size_t>(1), EncodeVarInt(1).size()); - EXPECT_EQ(static_cast<size_t>(2), EncodeVarInt(255).size()); - EXPECT_EQ(static_cast<size_t>(2), EncodeVarInt(256).size()); - EXPECT_EQ(static_cast<size_t>(5), EncodeVarInt(0xffffffff).size()); - EXPECT_EQ(static_cast<size_t>(8), EncodeVarInt(0xfffffffffffffLL).size()); - EXPECT_EQ(static_cast<size_t>(9), EncodeVarInt(0x7fffffffffffffffLL).size()); -#ifdef NDEBUG - EXPECT_EQ(static_cast<size_t>(10), EncodeVarInt(-100).size()); -#endif -} - -TEST(IndexedDBLevelDBCodingTest, DecodeVarInt) { - std::vector<int64> test_cases; - test_cases.push_back(0); - test_cases.push_back(1); - test_cases.push_back(255); - test_cases.push_back(256); - test_cases.push_back(65535); - test_cases.push_back(655536); - test_cases.push_back(7711192431755665792ll); - test_cases.push_back(0x7fffffffffffffffll); -#ifdef NDEBUG - test_cases.push_back(-3); -#endif - - for (size_t i = 0; i < test_cases.size(); ++i) { - int64 n = test_cases[i]; - std::vector<char> v = EncodeVarInt(n); - - int64 res; - const char* p = DecodeVarInt(&*v.begin(), &*v.rbegin() + 1, res); - EXPECT_EQ(n, res); - EXPECT_EQ(&*v.rbegin() + 1, p); - - p = DecodeVarInt(&*v.begin(), &*v.rbegin(), res); - EXPECT_EQ(0, p); - p = DecodeVarInt(&*v.begin(), &*v.begin(), res); - EXPECT_EQ(0, p); - } -} - -TEST(IndexedDBLevelDBCodingTest, EncodeString) { - const char16 test_string_a[] = {'f', 'o', 'o', '\0'}; - const char16 test_string_b[] = {0xdead, 0xbeef, '\0'}; - - EXPECT_EQ(static_cast<size_t>(0), EncodeString(ASCIIToUTF16("")).size()); - EXPECT_EQ(static_cast<size_t>(2), EncodeString(ASCIIToUTF16("a")).size()); - EXPECT_EQ(static_cast<size_t>(6), EncodeString(ASCIIToUTF16("foo")).size()); - EXPECT_EQ(static_cast<size_t>(6), - EncodeString(string16(test_string_a)).size()); - EXPECT_EQ(static_cast<size_t>(4), - EncodeString(string16(test_string_b)).size()); -} - -TEST(IndexedDBLevelDBCodingTest, DecodeString) { - const char16 test_string_a[] = {'f', 'o', 'o', '\0'}; - const char16 test_string_b[] = {0xdead, 0xbeef, '\0'}; - const char empty[] = {0}; - std::vector<char> v; - - EXPECT_EQ(string16(), DecodeString(empty, empty)); - - v = EncodeString(ASCIIToUTF16("a")); - EXPECT_EQ(ASCIIToUTF16("a"), DecodeString(&*v.begin(), &*v.rbegin() + 1)); - - v = EncodeString(ASCIIToUTF16("foo")); - EXPECT_EQ(ASCIIToUTF16("foo"), DecodeString(&*v.begin(), &*v.rbegin() + 1)); - - v = EncodeString(string16(test_string_a)); - EXPECT_EQ(string16(test_string_a), - DecodeString(&*v.begin(), &*v.rbegin() + 1)); - - v = EncodeString(string16(test_string_b)); - EXPECT_EQ(string16(test_string_b), - DecodeString(&*v.begin(), &*v.rbegin() + 1)); -} - -TEST(IndexedDBLevelDBCodingTest, EncodeStringWithLength) { - const char16 test_string_a[] = {'f', 'o', 'o', '\0'}; - const char16 test_string_b[] = {0xdead, 0xbeef, '\0'}; - - EXPECT_EQ(static_cast<size_t>(1), EncodeStringWithLength(string16()).size()); - EXPECT_EQ(static_cast<size_t>(3), - EncodeStringWithLength(ASCIIToUTF16("a")).size()); - EXPECT_EQ(static_cast<size_t>(7), - EncodeStringWithLength(string16(test_string_a)).size()); - EXPECT_EQ(static_cast<size_t>(5), - EncodeStringWithLength(string16(test_string_b)).size()); -} - -TEST(IndexedDBLevelDBCodingTest, DecodeStringWithLength) { - const char16 test_string_a[] = {'f', 'o', 'o', '\0'}; - const char16 test_string_b[] = {0xdead, 0xbeef, '\0'}; - - const int kLongStringLen = 1234; - char16 long_string[kLongStringLen + 1]; - for (int i = 0; i < kLongStringLen; ++i) - long_string[i] = i; - long_string[kLongStringLen] = 0; - - std::vector<string16> test_cases; - test_cases.push_back(ASCIIToUTF16("")); - test_cases.push_back(ASCIIToUTF16("a")); - test_cases.push_back(ASCIIToUTF16("foo")); - test_cases.push_back(string16(test_string_a)); - test_cases.push_back(string16(test_string_b)); - test_cases.push_back(string16(long_string)); - - for (size_t i = 0; i < test_cases.size(); ++i) { - string16 s = test_cases[i]; - std::vector<char> v = EncodeStringWithLength(s); - string16 res; - const char* p = DecodeStringWithLength(&*v.begin(), &*v.rbegin() + 1, res); - EXPECT_EQ(s, res); - EXPECT_EQ(&*v.rbegin() + 1, p); - - EXPECT_EQ(0, DecodeStringWithLength(&*v.begin(), &*v.rbegin(), res)); - EXPECT_EQ(0, DecodeStringWithLength(&*v.begin(), &*v.begin(), res)); - } -} - -static int CompareStrings(const char* p, - const char* limit_p, - const char* q, - const char* limit_q) { - bool ok; - int result = CompareEncodedStringsWithLength(p, limit_p, q, limit_q, ok); - EXPECT_TRUE(ok); - EXPECT_EQ(p, limit_p); - EXPECT_EQ(q, limit_q); - return result; -} - -TEST(IndexedDBLevelDBCodingTest, CompareEncodedStringsWithLength) { - const char16 test_string_a[] = {0x1000, 0x1000, '\0'}; - const char16 test_string_b[] = {0x1000, 0x1000, 0x1000, '\0'}; - const char16 test_string_c[] = {0x1000, 0x1000, 0x1001, '\0'}; - const char16 test_string_d[] = {0x1001, 0x1000, 0x1000, '\0'}; - const char16 test_string_e[] = {0xd834, 0xdd1e, '\0'}; - const char16 test_string_f[] = {0xfffd, '\0'}; - - std::vector<string16> test_cases; - test_cases.push_back(ASCIIToUTF16("")); - test_cases.push_back(ASCIIToUTF16("a")); - test_cases.push_back(ASCIIToUTF16("b")); - test_cases.push_back(ASCIIToUTF16("baaa")); - test_cases.push_back(ASCIIToUTF16("baab")); - test_cases.push_back(ASCIIToUTF16("c")); - test_cases.push_back(string16(test_string_a)); - test_cases.push_back(string16(test_string_b)); - test_cases.push_back(string16(test_string_c)); - test_cases.push_back(string16(test_string_d)); - test_cases.push_back(string16(test_string_e)); - test_cases.push_back(string16(test_string_f)); - - for (size_t i = 0; i < test_cases.size() - 1; ++i) { - string16 a = test_cases[i]; - string16 b = test_cases[i + 1]; - - EXPECT_LT(a.compare(b), 0); - EXPECT_GT(b.compare(a), 0); - EXPECT_EQ(a.compare(a), 0); - EXPECT_EQ(b.compare(b), 0); - - std::vector<char> encoded_a = EncodeStringWithLength(a); - EXPECT_TRUE(encoded_a.size()); - std::vector<char> encoded_b = EncodeStringWithLength(b); - EXPECT_TRUE(encoded_a.size()); - - const char* p = &*encoded_a.begin(); - const char* limit_p = &*encoded_a.rbegin() + 1; - const char* q = &*encoded_b.begin(); - const char* limit_q = &*encoded_b.rbegin() + 1; - - EXPECT_LT(CompareStrings(p, limit_p, q, limit_q), 0); - EXPECT_GT(CompareStrings(q, limit_q, p, limit_p), 0); - EXPECT_EQ(CompareStrings(p, limit_p, p, limit_p), 0); - EXPECT_EQ(CompareStrings(q, limit_q, q, limit_q), 0); - } -} - -TEST(IndexedDBLevelDBCodingTest, EncodeDouble) { - EXPECT_EQ(static_cast<size_t>(8), EncodeDouble(0).size()); - EXPECT_EQ(static_cast<size_t>(8), EncodeDouble(3.14).size()); -} - -TEST(IndexedDBLevelDBCodingTest, DecodeDouble) { - std::vector<char> v; - const char* p; - double d; - - v = EncodeDouble(3.14); - p = DecodeDouble(&*v.begin(), &*v.rbegin() + 1, &d); - EXPECT_EQ(3.14, d); - EXPECT_EQ(&*v.rbegin() + 1, p); - - v = EncodeDouble(-3.14); - p = DecodeDouble(&*v.begin(), &*v.rbegin() + 1, &d); - EXPECT_EQ(-3.14, d); - EXPECT_EQ(&*v.rbegin() + 1, p); - - v = EncodeDouble(3.14); - p = DecodeDouble(&*v.begin(), &*v.rbegin(), &d); - EXPECT_EQ(0, p); -} - -TEST(IndexedDBLevelDBCodingTest, EncodeDecodeIDBKey) { - IndexedDBKey expected_key; - scoped_ptr<IndexedDBKey> decoded_key; - std::vector<char> v; - const char* p; - - expected_key = IndexedDBKey(1234, WebIDBKey::NumberType); - v = EncodeIDBKey(expected_key); - p = DecodeIDBKey(&*v.begin(), &*v.rbegin() + 1, &decoded_key); - EXPECT_TRUE(decoded_key->IsEqual(expected_key)); - EXPECT_EQ(&*v.rbegin() + 1, p); - EXPECT_EQ(0, DecodeIDBKey(&*v.begin(), &*v.rbegin(), &decoded_key)); - - expected_key = IndexedDBKey(ASCIIToUTF16("Hello World!")); - v = EncodeIDBKey(expected_key); - p = DecodeIDBKey(&*v.begin(), &*v.rbegin() + 1, &decoded_key); - EXPECT_TRUE(decoded_key->IsEqual(expected_key)); - EXPECT_EQ(&*v.rbegin() + 1, p); - EXPECT_EQ(0, DecodeIDBKey(&*v.begin(), &*v.rbegin(), &decoded_key)); - - expected_key = IndexedDBKey(IndexedDBKey::KeyArray()); - v = EncodeIDBKey(expected_key); - p = DecodeIDBKey(&*v.begin(), &*v.rbegin() + 1, &decoded_key); - EXPECT_TRUE(decoded_key->IsEqual(expected_key)); - EXPECT_EQ(&*v.rbegin() + 1, p); - EXPECT_EQ(0, DecodeIDBKey(&*v.begin(), &*v.rbegin(), &decoded_key)); - - expected_key = IndexedDBKey(7890, WebIDBKey::DateType); - v = EncodeIDBKey(expected_key); - p = DecodeIDBKey(&*v.begin(), &*v.rbegin() + 1, &decoded_key); - EXPECT_TRUE(decoded_key->IsEqual(expected_key)); - EXPECT_EQ(&*v.rbegin() + 1, p); - EXPECT_EQ(0, DecodeIDBKey(&*v.begin(), &*v.rbegin(), &decoded_key)); - - IndexedDBKey::KeyArray array; - array.push_back(IndexedDBKey(1234, WebIDBKey::NumberType)); - array.push_back(IndexedDBKey(ASCIIToUTF16("Hello World!"))); - array.push_back(IndexedDBKey(7890, WebIDBKey::DateType)); - expected_key = IndexedDBKey(array); - v = EncodeIDBKey(expected_key); - p = DecodeIDBKey(&*v.begin(), &*v.rbegin() + 1, &decoded_key); - EXPECT_TRUE(decoded_key->IsEqual(expected_key)); - EXPECT_EQ(&*v.rbegin() + 1, p); - EXPECT_EQ(0, DecodeIDBKey(&*v.begin(), &*v.rbegin(), &decoded_key)); -} - -TEST(IndexedDBLevelDBCodingTest, EncodeIDBKeyPath) { - const unsigned char kIDBKeyPathTypeCodedByte1 = 0; - const unsigned char kIDBKeyPathTypeCodedByte2 = 0; - { - IndexedDBKeyPath key_path; - EXPECT_EQ(key_path.type(), WebIDBKeyPath::NullType); - std::vector<char> v = EncodeIDBKeyPath(key_path); - EXPECT_EQ(v.size(), 3U); - EXPECT_EQ(v[0], kIDBKeyPathTypeCodedByte1); - EXPECT_EQ(v[1], kIDBKeyPathTypeCodedByte2); - EXPECT_EQ(v[2], WebIDBKeyPath::NullType); - } - - { - std::vector<string16> test_cases; - test_cases.push_back(string16()); - test_cases.push_back(ASCIIToUTF16("foo")); - test_cases.push_back(ASCIIToUTF16("foo.bar")); - - for (size_t i = 0; i < test_cases.size(); ++i) { - IndexedDBKeyPath key_path = IndexedDBKeyPath(test_cases[i]); - std::vector<char> v = EncodeIDBKeyPath(key_path); - EXPECT_EQ(v.size(), EncodeStringWithLength(test_cases[i]).size() + 3); - const char* p = &*v.begin(); - const char* limit = &*v.rbegin() + 1; - EXPECT_EQ(*p++, kIDBKeyPathTypeCodedByte1); - EXPECT_EQ(*p++, kIDBKeyPathTypeCodedByte2); - EXPECT_EQ(*p++, WebIDBKeyPath::StringType); - string16 string; - p = DecodeStringWithLength(p, limit, string); - EXPECT_EQ(string, test_cases[i]); - EXPECT_EQ(p, limit); - } - } - - { - std::vector<string16> test_case; - test_case.push_back(string16()); - test_case.push_back(ASCIIToUTF16("foo")); - test_case.push_back(ASCIIToUTF16("foo.bar")); - - IndexedDBKeyPath key_path(test_case); - EXPECT_EQ(key_path.type(), WebIDBKeyPath::ArrayType); - std::vector<char> v = EncodeIDBKeyPath(key_path); - const char* p = &*v.begin(); - const char* limit = &*v.rbegin() + 1; - EXPECT_EQ(*p++, kIDBKeyPathTypeCodedByte1); - EXPECT_EQ(*p++, kIDBKeyPathTypeCodedByte2); - EXPECT_EQ(*p++, WebIDBKeyPath::ArrayType); - int64 count; - p = DecodeVarInt(p, limit, count); - EXPECT_EQ(count, static_cast<int64>(test_case.size())); - for (size_t i = 0; i < static_cast<size_t>(count); ++i) { - string16 string; - p = DecodeStringWithLength(p, limit, string); - EXPECT_EQ(string, test_case[i]); - } - EXPECT_EQ(p, limit); - } -} - -TEST(IndexedDBLevelDBCodingTest, DecodeIDBKeyPath) { - const unsigned char kIDBKeyPathTypeCodedByte1 = 0; - const unsigned char kIDBKeyPathTypeCodedByte2 = 0; - const char empty[] = {0}; - { - // Legacy encoding of string key paths. - std::vector<string16> test_cases; - test_cases.push_back(string16()); - test_cases.push_back(ASCIIToUTF16("foo")); - test_cases.push_back(ASCIIToUTF16("foo.bar")); - - for (size_t i = 0; i < test_cases.size(); ++i) { - std::vector<char> v = EncodeString(test_cases[i]); - const char* begin; - const char* end; - if (!v.size()) { - begin = empty; - end = empty; - } else { - begin = &*v.begin(); - end = &*v.rbegin() + 1; - } - IndexedDBKeyPath key_path = DecodeIDBKeyPath(begin, end); - EXPECT_EQ(key_path.type(), WebIDBKeyPath::StringType); - EXPECT_EQ(test_cases[i], key_path.string()); - } - } - { - std::vector<char> v; - v.push_back(kIDBKeyPathTypeCodedByte1); - v.push_back(kIDBKeyPathTypeCodedByte2); - v.push_back(WebIDBKeyPath::NullType); - IndexedDBKeyPath key_path = DecodeIDBKeyPath(&*v.begin(), &*v.rbegin() + 1); - EXPECT_EQ(key_path.type(), WebIDBKeyPath::NullType); - EXPECT_TRUE(key_path.IsNull()); - } - { - std::vector<string16> test_cases; - test_cases.push_back(string16()); - test_cases.push_back(ASCIIToUTF16("foo")); - test_cases.push_back(ASCIIToUTF16("foo.bar")); - - for (size_t i = 0; i < test_cases.size(); ++i) { - std::vector<char> v; - v.push_back(kIDBKeyPathTypeCodedByte1); - v.push_back(kIDBKeyPathTypeCodedByte2); - v.push_back(WebIDBKeyPath::StringType); - std::vector<char> test_case = EncodeStringWithLength(test_cases[i]); - v.insert(v.end(), test_case.begin(), test_case.end()); - IndexedDBKeyPath key_path = - DecodeIDBKeyPath(&*v.begin(), &*v.rbegin() + 1); - EXPECT_EQ(key_path.type(), WebIDBKeyPath::StringType); - EXPECT_EQ(test_cases[i], key_path.string()); - } - } - { - std::vector<string16> test_case; - test_case.push_back(string16()); - test_case.push_back(ASCIIToUTF16("foo")); - test_case.push_back(ASCIIToUTF16("foo.bar")); - - std::vector<char> v; - v.push_back(kIDBKeyPathTypeCodedByte1); - v.push_back(kIDBKeyPathTypeCodedByte2); - v.push_back(WebIDBKeyPath::ArrayType); - std::vector<char> int_value = EncodeVarInt(test_case.size()); - v.insert(v.end(), int_value.begin(), int_value.end()); - for (size_t i = 0; i < test_case.size(); ++i) { - std::vector<char> test_case_value = EncodeStringWithLength(test_case[i]); - v.insert(v.end(), test_case_value.begin(), test_case_value.end()); - } - IndexedDBKeyPath key_path = DecodeIDBKeyPath(&*v.begin(), &*v.rbegin() + 1); - EXPECT_EQ(key_path.type(), WebIDBKeyPath::ArrayType); - EXPECT_EQ(key_path.array().size(), test_case.size()); - for (size_t i = 0; i < test_case.size(); ++i) - EXPECT_EQ(key_path.array()[i], test_case[i]); - } -} - -TEST(IndexedDBLevelDBCodingTest, ExtractAndCompareIDBKeys) { - std::vector<IndexedDBKey> keys; - - keys.push_back(IndexedDBKey(-10, WebIDBKey::NumberType)); - keys.push_back(IndexedDBKey(0, WebIDBKey::NumberType)); - keys.push_back(IndexedDBKey(3.14, WebIDBKey::NumberType)); - - keys.push_back(IndexedDBKey(0, WebIDBKey::DateType)); - keys.push_back(IndexedDBKey(100, WebIDBKey::DateType)); - keys.push_back(IndexedDBKey(100000, WebIDBKey::DateType)); - - keys.push_back(IndexedDBKey(ASCIIToUTF16(""))); - keys.push_back(IndexedDBKey(ASCIIToUTF16("a"))); - keys.push_back(IndexedDBKey(ASCIIToUTF16("b"))); - keys.push_back(IndexedDBKey(ASCIIToUTF16("baaa"))); - keys.push_back(IndexedDBKey(ASCIIToUTF16("baab"))); - keys.push_back(IndexedDBKey(ASCIIToUTF16("c"))); - - keys.push_back(CreateArrayIDBKey()); - keys.push_back(CreateArrayIDBKey(IndexedDBKey(0, WebIDBKey::NumberType))); - keys.push_back(CreateArrayIDBKey(IndexedDBKey(0, WebIDBKey::NumberType), - IndexedDBKey(3.14, WebIDBKey::NumberType))); - keys.push_back(CreateArrayIDBKey(IndexedDBKey(0, WebIDBKey::DateType))); - keys.push_back(CreateArrayIDBKey(IndexedDBKey(0, WebIDBKey::DateType), - IndexedDBKey(0, WebIDBKey::DateType))); - keys.push_back(CreateArrayIDBKey(IndexedDBKey(ASCIIToUTF16("")))); - keys.push_back(CreateArrayIDBKey(IndexedDBKey(ASCIIToUTF16("")), - IndexedDBKey(ASCIIToUTF16("a")))); - keys.push_back(CreateArrayIDBKey(CreateArrayIDBKey())); - keys.push_back(CreateArrayIDBKey(CreateArrayIDBKey(), CreateArrayIDBKey())); - keys.push_back(CreateArrayIDBKey(CreateArrayIDBKey(CreateArrayIDBKey()))); - keys.push_back(CreateArrayIDBKey( - CreateArrayIDBKey(CreateArrayIDBKey(CreateArrayIDBKey())))); - - for (size_t i = 0; i < keys.size() - 1; ++i) { - const IndexedDBKey& key_a = keys[i]; - const IndexedDBKey& key_b = keys[i + 1]; - - EXPECT_TRUE(key_a.IsLessThan(key_b)); - - std::vector<char> encoded_a = EncodeIDBKey(key_a); - EXPECT_TRUE(encoded_a.size()); - std::vector<char> encoded_b = EncodeIDBKey(key_b); - EXPECT_TRUE(encoded_b.size()); - - std::vector<char> extracted_a; - std::vector<char> extracted_b; - - const char* p = ExtractEncodedIDBKey( - &*encoded_a.begin(), &*encoded_a.rbegin() + 1, &extracted_a); - EXPECT_EQ(&*encoded_a.rbegin() + 1, p); - EXPECT_EQ(encoded_a, extracted_a); - - const char* q = ExtractEncodedIDBKey( - &*encoded_b.begin(), &*encoded_b.rbegin() + 1, &extracted_b); - EXPECT_EQ(&*encoded_b.rbegin() + 1, q); - EXPECT_EQ(encoded_b, extracted_b); - - EXPECT_LT(CompareKeys(extracted_a, extracted_b), 0); - EXPECT_GT(CompareKeys(extracted_b, extracted_a), 0); - EXPECT_EQ(CompareKeys(extracted_a, extracted_a), 0); - EXPECT_EQ(CompareKeys(extracted_b, extracted_b), 0); - - EXPECT_EQ(0, - ExtractEncodedIDBKey( - &*encoded_a.begin(), &*encoded_a.rbegin(), &extracted_a)); - } -} - -TEST(IndexedDBLevelDBCodingTest, ComparisonTest) { - std::vector<std::vector<char> > keys; - keys.push_back(SchemaVersionKey::Encode()); - keys.push_back(MaxDatabaseIdKey::Encode()); - keys.push_back(DatabaseFreeListKey::Encode(0)); - keys.push_back(DatabaseFreeListKey::EncodeMaxKey()); - keys.push_back(DatabaseNameKey::Encode(ASCIIToUTF16(""), ASCIIToUTF16(""))); - keys.push_back(DatabaseNameKey::Encode(ASCIIToUTF16(""), ASCIIToUTF16("a"))); - keys.push_back(DatabaseNameKey::Encode(ASCIIToUTF16("a"), ASCIIToUTF16("a"))); - keys.push_back( - DatabaseMetaDataKey::Encode(1, DatabaseMetaDataKey::ORIGIN_NAME)); - keys.push_back( - DatabaseMetaDataKey::Encode(1, DatabaseMetaDataKey::DATABASE_NAME)); - keys.push_back( - DatabaseMetaDataKey::Encode(1, DatabaseMetaDataKey::USER_VERSION)); - keys.push_back( - DatabaseMetaDataKey::Encode(1, DatabaseMetaDataKey::MAX_OBJECT_STORE_ID)); - keys.push_back( - DatabaseMetaDataKey::Encode(1, DatabaseMetaDataKey::USER_INT_VERSION)); - keys.push_back( - ObjectStoreMetaDataKey::Encode(1, 1, ObjectStoreMetaDataKey::NAME)); - keys.push_back( - ObjectStoreMetaDataKey::Encode(1, 1, ObjectStoreMetaDataKey::KEY_PATH)); - keys.push_back(ObjectStoreMetaDataKey::Encode( - 1, 1, ObjectStoreMetaDataKey::AUTO_INCREMENT)); - keys.push_back( - ObjectStoreMetaDataKey::Encode(1, 1, ObjectStoreMetaDataKey::EVICTABLE)); - keys.push_back(ObjectStoreMetaDataKey::Encode( - 1, 1, ObjectStoreMetaDataKey::LAST_VERSION)); - keys.push_back(ObjectStoreMetaDataKey::Encode( - 1, 1, ObjectStoreMetaDataKey::MAX_INDEX_ID)); - keys.push_back(ObjectStoreMetaDataKey::Encode( - 1, 1, ObjectStoreMetaDataKey::HAS_KEY_PATH)); - keys.push_back(ObjectStoreMetaDataKey::Encode( - 1, 1, ObjectStoreMetaDataKey::KEY_GENERATOR_CURRENT_NUMBER)); - keys.push_back(ObjectStoreMetaDataKey::EncodeMaxKey(1, 1)); - keys.push_back(ObjectStoreMetaDataKey::EncodeMaxKey(1, 2)); - keys.push_back(ObjectStoreMetaDataKey::EncodeMaxKey(1)); - keys.push_back(IndexMetaDataKey::Encode(1, 1, 30, IndexMetaDataKey::NAME)); - keys.push_back(IndexMetaDataKey::Encode(1, 1, 30, IndexMetaDataKey::UNIQUE)); - keys.push_back( - IndexMetaDataKey::Encode(1, 1, 30, IndexMetaDataKey::KEY_PATH)); - keys.push_back( - IndexMetaDataKey::Encode(1, 1, 30, IndexMetaDataKey::MULTI_ENTRY)); - keys.push_back(IndexMetaDataKey::Encode(1, 1, 31, 0)); - keys.push_back(IndexMetaDataKey::Encode(1, 1, 31, 1)); - keys.push_back(IndexMetaDataKey::EncodeMaxKey(1, 1, 31)); - keys.push_back(IndexMetaDataKey::EncodeMaxKey(1, 1, 32)); - keys.push_back(IndexMetaDataKey::EncodeMaxKey(1, 1)); - keys.push_back(IndexMetaDataKey::EncodeMaxKey(1, 2)); - keys.push_back(ObjectStoreFreeListKey::Encode(1, 1)); - keys.push_back(ObjectStoreFreeListKey::EncodeMaxKey(1)); - keys.push_back(IndexFreeListKey::Encode(1, 1, kMinimumIndexId)); - keys.push_back(IndexFreeListKey::EncodeMaxKey(1, 1)); - keys.push_back(IndexFreeListKey::Encode(1, 2, kMinimumIndexId)); - keys.push_back(IndexFreeListKey::EncodeMaxKey(1, 2)); - keys.push_back(ObjectStoreNamesKey::Encode(1, ASCIIToUTF16(""))); - keys.push_back(ObjectStoreNamesKey::Encode(1, ASCIIToUTF16("a"))); - keys.push_back(IndexNamesKey::Encode(1, 1, ASCIIToUTF16(""))); - keys.push_back(IndexNamesKey::Encode(1, 1, ASCIIToUTF16("a"))); - keys.push_back(IndexNamesKey::Encode(1, 2, ASCIIToUTF16("a"))); - keys.push_back(ObjectStoreDataKey::Encode(1, 1, MinIDBKey())); - keys.push_back(ObjectStoreDataKey::Encode(1, 1, MaxIDBKey())); - keys.push_back(ExistsEntryKey::Encode(1, 1, MinIDBKey())); - keys.push_back(ExistsEntryKey::Encode(1, 1, MaxIDBKey())); - keys.push_back(IndexDataKey::Encode(1, 1, 30, MinIDBKey(), MinIDBKey(), 0)); - keys.push_back(IndexDataKey::Encode(1, 1, 30, MinIDBKey(), MinIDBKey(), 1)); - keys.push_back(IndexDataKey::Encode(1, 1, 30, MinIDBKey(), MaxIDBKey(), 0)); - keys.push_back(IndexDataKey::Encode(1, 1, 30, MinIDBKey(), MaxIDBKey(), 1)); - keys.push_back(IndexDataKey::Encode(1, 1, 30, MaxIDBKey(), MinIDBKey(), 0)); - keys.push_back(IndexDataKey::Encode(1, 1, 30, MaxIDBKey(), MinIDBKey(), 1)); - keys.push_back(IndexDataKey::Encode(1, 1, 30, MaxIDBKey(), MaxIDBKey(), 0)); - keys.push_back(IndexDataKey::Encode(1, 1, 30, MaxIDBKey(), MaxIDBKey(), 1)); - keys.push_back(IndexDataKey::Encode(1, 1, 31, MinIDBKey(), MinIDBKey(), 0)); - keys.push_back(IndexDataKey::Encode(1, 2, 30, MinIDBKey(), MinIDBKey(), 0)); - keys.push_back( - IndexDataKey::EncodeMaxKey(1, 2, std::numeric_limits<int32>::max() - 1)); - - for (size_t i = 0; i < keys.size(); ++i) { - const LevelDBSlice key_a(keys[i]); - EXPECT_EQ(Compare(key_a, key_a), 0); - - for (size_t j = i + 1; j < keys.size(); ++j) { - const LevelDBSlice key_b(keys[j]); - EXPECT_LT(Compare(key_a, key_b), 0); - EXPECT_GT(Compare(key_b, key_a), 0); - } - } -} - -TEST(IndexedDBLevelDBCodingTest, EncodeVarIntVSEncodeByteTest) { - std::vector<unsigned char> test_cases; - test_cases.push_back(0); - test_cases.push_back(1); - test_cases.push_back(127); - - for (size_t i = 0; i < test_cases.size(); ++i) { - unsigned char n = test_cases[i]; - - std::vector<char> vA = EncodeByte(n); - std::vector<char> vB = EncodeVarInt(static_cast<int64>(n)); - - EXPECT_EQ(vA.size(), vB.size()); - EXPECT_EQ(*vA.begin(), *vB.begin()); - } -} - -} // namespace - -} // namespace content diff --git a/content/browser/indexed_db/indexed_db_metadata.cc b/content/browser/indexed_db/indexed_db_metadata.cc deleted file mode 100644 index 80d3142..0000000 --- a/content/browser/indexed_db/indexed_db_metadata.cc +++ /dev/null @@ -1,39 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/indexed_db_metadata.h" - -namespace content { - -IndexedDBObjectStoreMetadata::IndexedDBObjectStoreMetadata( - const string16& name, - int64 id, - const IndexedDBKeyPath& key_path, - bool auto_increment, - int64 max_index_id) - : name(name), - id(id), - key_path(key_path), - auto_increment(auto_increment), - max_index_id(max_index_id) {} - -IndexedDBObjectStoreMetadata::IndexedDBObjectStoreMetadata() {} -IndexedDBObjectStoreMetadata::~IndexedDBObjectStoreMetadata() {} - -IndexedDBDatabaseMetadata::IndexedDBDatabaseMetadata() - : int_version(NO_INT_VERSION) {} -IndexedDBDatabaseMetadata::IndexedDBDatabaseMetadata(const string16& name, - int64 id, - const string16& version, - int64 int_version, - int64 max_object_store_id) - : name(name), - id(id), - version(version), - int_version(int_version), - max_object_store_id(max_object_store_id) {} - -IndexedDBDatabaseMetadata::~IndexedDBDatabaseMetadata() {} - -} // namespace content diff --git a/content/browser/indexed_db/indexed_db_metadata.h b/content/browser/indexed_db/indexed_db_metadata.h deleted file mode 100644 index 29f6a9f..0000000 --- a/content/browser/indexed_db/indexed_db_metadata.h +++ /dev/null @@ -1,84 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_METADATA_H_ -#define CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_METADATA_H_ - -#include <map> - -#include "base/basictypes.h" -#include "base/string16.h" -#include "content/common/indexed_db/indexed_db_key_path.h" - -namespace content { - -struct IndexedDBIndexMetadata { - IndexedDBIndexMetadata() {} - IndexedDBIndexMetadata(const string16& name, - int64 id, - const IndexedDBKeyPath& key_path, - bool unique, - bool multi_entry) - : name(name), - id(id), - key_path(key_path), - unique(unique), - multi_entry(multi_entry) {} - string16 name; - int64 id; - IndexedDBKeyPath key_path; - bool unique; - bool multi_entry; - - static const int64 kInvalidId = -1; -}; - -struct CONTENT_EXPORT IndexedDBObjectStoreMetadata { - IndexedDBObjectStoreMetadata(); - IndexedDBObjectStoreMetadata(const string16& name, - int64 id, - const IndexedDBKeyPath& key_path, - bool auto_increment, - int64 max_index_id); - ~IndexedDBObjectStoreMetadata(); - string16 name; - int64 id; - IndexedDBKeyPath key_path; - bool auto_increment; - int64 max_index_id; - - static const int64 kInvalidId = -1; - - typedef std::map<int64, IndexedDBIndexMetadata> IndexMap; - IndexMap indexes; -}; - -struct CONTENT_EXPORT IndexedDBDatabaseMetadata { - // TODO(jsbell): These can probably be collapsed into 0. - enum { - NO_INT_VERSION = -1, - DEFAULT_INT_VERSION = 0 - }; - - typedef std::map<int64, IndexedDBObjectStoreMetadata> ObjectStoreMap; - - IndexedDBDatabaseMetadata(); - IndexedDBDatabaseMetadata(const string16& name, - int64 id, - const string16& version, - int64 int_version, - int64 max_object_store_id); - ~IndexedDBDatabaseMetadata(); - - string16 name; - int64 id; - string16 version; - int64 int_version; - int64 max_object_store_id; - - ObjectStoreMap object_stores; -}; -} - -#endif // CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_METADATA_H_ diff --git a/content/browser/indexed_db/indexed_db_quota_client.cc b/content/browser/indexed_db/indexed_db_quota_client.cc index bbce16c..25f9668 100644 --- a/content/browser/indexed_db/indexed_db_quota_client.cc +++ b/content/browser/indexed_db/indexed_db_quota_client.cc @@ -26,33 +26,36 @@ quota::QuotaStatusCode DeleteOriginDataOnWebKitThread( return quota::kQuotaStatusOk; } -int64 GetOriginUsageOnWebKitThread(IndexedDBContextImpl* context, - const GURL& origin) { +int64 GetOriginUsageOnWebKitThread( + IndexedDBContextImpl* context, + const GURL& origin) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); return context->GetOriginDiskUsage(origin); } -void GetAllOriginsOnWebKitThread(IndexedDBContextImpl* context, - std::set<GURL>* origins_to_return) { +void GetAllOriginsOnWebKitThread( + IndexedDBContextImpl* context, + std::set<GURL>* origins_to_return) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); std::vector<GURL> all_origins = context->GetAllOrigins(); origins_to_return->insert(all_origins.begin(), all_origins.end()); } -void DidGetOrigins(const IndexedDBQuotaClient::GetOriginsCallback& callback, - const std::set<GURL>* origins) { +void DidGetOrigins( + const IndexedDBQuotaClient::GetOriginsCallback& callback, + const std::set<GURL>* origins) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); callback.Run(*origins); } -void GetOriginsForHostOnWebKitThread(IndexedDBContextImpl* context, - const std::string& host, - std::set<GURL>* origins_to_return) { +void GetOriginsForHostOnWebKitThread( + IndexedDBContextImpl* context, + const std::string& host, + std::set<GURL>* origins_to_return) { DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); std::vector<GURL> all_origins = context->GetAllOrigins(); for (std::vector<GURL>::const_iterator iter = all_origins.begin(); - iter != all_origins.end(); - ++iter) { + iter != all_origins.end(); ++iter) { if (host == net::GetHostOrSpecFromURL(*iter)) origins_to_return->insert(*iter); } @@ -66,17 +69,24 @@ IndexedDBQuotaClient::IndexedDBQuotaClient( base::MessageLoopProxy* webkit_thread_message_loop, IndexedDBContextImpl* indexed_db_context) : webkit_thread_message_loop_(webkit_thread_message_loop), - indexed_db_context_(indexed_db_context) {} + indexed_db_context_(indexed_db_context) { +} -IndexedDBQuotaClient::~IndexedDBQuotaClient() {} +IndexedDBQuotaClient::~IndexedDBQuotaClient() { +} -QuotaClient::ID IndexedDBQuotaClient::id() const { return kIndexedDatabase; } +QuotaClient::ID IndexedDBQuotaClient::id() const { + return kIndexedDatabase; +} -void IndexedDBQuotaClient::OnQuotaManagerDestroyed() { delete this; } +void IndexedDBQuotaClient::OnQuotaManagerDestroyed() { + delete this; +} -void IndexedDBQuotaClient::GetOriginUsage(const GURL& origin_url, - quota::StorageType type, - const GetUsageCallback& callback) { +void IndexedDBQuotaClient::GetOriginUsage( + const GURL& origin_url, + quota::StorageType type, + const GetUsageCallback& callback) { DCHECK(!callback.is_null()); DCHECK(indexed_db_context_.get()); @@ -89,8 +99,9 @@ void IndexedDBQuotaClient::GetOriginUsage(const GURL& origin_url, base::PostTaskAndReplyWithResult( webkit_thread_message_loop_, FROM_HERE, - base::Bind( - &GetOriginUsageOnWebKitThread, indexed_db_context_, origin_url), + base::Bind(&GetOriginUsageOnWebKitThread, + indexed_db_context_, + origin_url), callback); } @@ -112,7 +123,9 @@ void IndexedDBQuotaClient::GetOriginsForType( base::Bind(&GetAllOriginsOnWebKitThread, indexed_db_context_, base::Unretained(origins_to_return)), - base::Bind(&DidGetOrigins, callback, base::Owned(origins_to_return))); + base::Bind(&DidGetOrigins, + callback, + base::Owned(origins_to_return))); } void IndexedDBQuotaClient::GetOriginsForHost( @@ -135,12 +148,15 @@ void IndexedDBQuotaClient::GetOriginsForHost( indexed_db_context_, host, base::Unretained(origins_to_return)), - base::Bind(&DidGetOrigins, callback, base::Owned(origins_to_return))); + base::Bind(&DidGetOrigins, + callback, + base::Owned(origins_to_return))); } -void IndexedDBQuotaClient::DeleteOriginData(const GURL& origin, - quota::StorageType type, - const DeletionCallback& callback) { +void IndexedDBQuotaClient::DeleteOriginData( + const GURL& origin, + quota::StorageType type, + const DeletionCallback& callback) { if (type != quota::kStorageTypeTemporary) { callback.Run(quota::kQuotaErrorNotSupported); return; @@ -149,7 +165,9 @@ void IndexedDBQuotaClient::DeleteOriginData(const GURL& origin, base::PostTaskAndReplyWithResult( webkit_thread_message_loop_, FROM_HERE, - base::Bind(&DeleteOriginDataOnWebKitThread, indexed_db_context_, origin), + base::Bind(&DeleteOriginDataOnWebKitThread, + indexed_db_context_, + origin), callback); } diff --git a/content/browser/indexed_db/indexed_db_quota_client.h b/content/browser/indexed_db/indexed_db_quota_client.h index 605e705..e79f4aa 100644 --- a/content/browser/indexed_db/indexed_db_quota_client.h +++ b/content/browser/indexed_db/indexed_db_quota_client.h @@ -25,8 +25,9 @@ class IndexedDBContextImpl; class IndexedDBQuotaClient : public quota::QuotaClient, public quota::QuotaTaskObserver { public: - CONTENT_EXPORT IndexedDBQuotaClient(base::MessageLoopProxy* tracker_thread, - IndexedDBContextImpl* indexed_db_context); + CONTENT_EXPORT IndexedDBQuotaClient( + base::MessageLoopProxy* tracker_thread, + IndexedDBContextImpl* indexed_db_context); CONTENT_EXPORT virtual ~IndexedDBQuotaClient(); // QuotaClient method overrides @@ -43,7 +44,6 @@ class IndexedDBQuotaClient : public quota::QuotaClient, virtual void DeleteOriginData(const GURL& origin, quota::StorageType type, const DeletionCallback& callback) OVERRIDE; - private: scoped_refptr<base::MessageLoopProxy> webkit_thread_message_loop_; scoped_refptr<IndexedDBContextImpl> indexed_db_context_; diff --git a/content/browser/indexed_db/indexed_db_quota_client_unittest.cc b/content/browser/indexed_db/indexed_db_quota_client_unittest.cc index bcd037a..0d8628ac 100644 --- a/content/browser/indexed_db/indexed_db_quota_client_unittest.cc +++ b/content/browser/indexed_db/indexed_db_quota_client_unittest.cc @@ -48,15 +48,15 @@ class IndexedDBQuotaClientTest : public testing::Test { io_thread_(BrowserThread::IO, &message_loop_) { browser_context_.reset(new TestBrowserContext()); idb_context_ = static_cast<IndexedDBContextImpl*>( - BrowserContext::GetDefaultStoragePartition(browser_context_.get()) - ->GetIndexedDBContext()); + BrowserContext::GetDefaultStoragePartition(browser_context_.get())-> + GetIndexedDBContext()); message_loop_.RunUntilIdle(); setup_temp_dir(); } void setup_temp_dir() { ASSERT_TRUE(temp_dir_.CreateUniqueTempDir()); - base::FilePath indexeddb_dir = - temp_dir_.path().Append(IndexedDBContextImpl::kIndexedDBDirectory); + base::FilePath indexeddb_dir = temp_dir_.path().Append( + IndexedDBContextImpl::kIndexedDBDirectory); ASSERT_TRUE(file_util::CreateDirectory(indexeddb_dir)); idb_context()->set_data_path_for_testing(indexeddb_dir); } @@ -71,13 +71,13 @@ class IndexedDBQuotaClientTest : public testing::Test { base::MessageLoop::current()->RunUntilIdle(); } - int64 GetOriginUsage(quota::QuotaClient* client, - const GURL& origin, - quota::StorageType type) { + int64 GetOriginUsage( + quota::QuotaClient* client, + const GURL& origin, + quota::StorageType type) { usage_ = -1; client->GetOriginUsage( - origin, - type, + origin, type, base::Bind(&IndexedDBQuotaClientTest::OnGetOriginUsageComplete, weak_factory_.GetWeakPtr())); base::MessageLoop::current()->RunUntilIdle(); @@ -85,8 +85,9 @@ class IndexedDBQuotaClientTest : public testing::Test { return usage_; } - const std::set<GURL>& GetOriginsForType(quota::QuotaClient* client, - quota::StorageType type) { + const std::set<GURL>& GetOriginsForType( + quota::QuotaClient* client, + quota::StorageType type) { origins_.clear(); client->GetOriginsForType( type, @@ -96,13 +97,13 @@ class IndexedDBQuotaClientTest : public testing::Test { return origins_; } - const std::set<GURL>& GetOriginsForHost(quota::QuotaClient* client, - quota::StorageType type, - const std::string& host) { + const std::set<GURL>& GetOriginsForHost( + quota::QuotaClient* client, + quota::StorageType type, + const std::string& host) { origins_.clear(); client->GetOriginsForHost( - type, - host, + type, host, base::Bind(&IndexedDBQuotaClientTest::OnGetOriginsComplete, weak_factory_.GetWeakPtr())); base::MessageLoop::current()->RunUntilIdle(); @@ -113,8 +114,7 @@ class IndexedDBQuotaClientTest : public testing::Test { const GURL& origin_url) { delete_status_ = quota::kQuotaStatusUnknown; client->DeleteOriginData( - origin_url, - kTemp, + origin_url, kTemp, base::Bind(&IndexedDBQuotaClientTest::OnDeleteOriginComplete, weak_factory_.GetWeakPtr())); base::MessageLoop::current()->RunUntilIdle(); @@ -141,7 +141,9 @@ class IndexedDBQuotaClientTest : public testing::Test { } private: - void OnGetOriginUsageComplete(int64 usage) { usage_ = usage; } + void OnGetOriginUsageComplete(int64 usage) { + usage_ = usage; + } void OnGetOriginsComplete(const std::set<GURL>& origins) { origins_ = origins; @@ -167,7 +169,9 @@ class IndexedDBQuotaClientTest : public testing::Test { }; TEST_F(IndexedDBQuotaClientTest, GetOriginUsage) { - IndexedDBQuotaClient client(base::MessageLoopProxy::current(), idb_context()); + IndexedDBQuotaClient client( + base::MessageLoopProxy::current(), + idb_context()); AddFakeIndexedDB(kOriginA, 6); AddFakeIndexedDB(kOriginB, 3); @@ -184,7 +188,9 @@ TEST_F(IndexedDBQuotaClientTest, GetOriginUsage) { } TEST_F(IndexedDBQuotaClientTest, GetOriginsForHost) { - IndexedDBQuotaClient client(base::MessageLoopProxy::current(), idb_context()); + IndexedDBQuotaClient client( + base::MessageLoopProxy::current(), + idb_context()); EXPECT_EQ(kOriginA.host(), kOriginB.host()); EXPECT_NE(kOriginA.host(), kOriginOther.host()); @@ -208,7 +214,9 @@ TEST_F(IndexedDBQuotaClientTest, GetOriginsForHost) { } TEST_F(IndexedDBQuotaClientTest, GetOriginsForType) { - IndexedDBQuotaClient client(base::MessageLoopProxy::current(), idb_context()); + IndexedDBQuotaClient client( + base::MessageLoopProxy::current(), + idb_context()); EXPECT_TRUE(GetOriginsForType(&client, kTemp).empty()); EXPECT_TRUE(GetOriginsForType(&client, kPerm).empty()); @@ -222,7 +230,9 @@ TEST_F(IndexedDBQuotaClientTest, GetOriginsForType) { } TEST_F(IndexedDBQuotaClientTest, DeleteOrigin) { - IndexedDBQuotaClient client(base::MessageLoopProxy::current(), idb_context()); + IndexedDBQuotaClient client( + base::MessageLoopProxy::current(), + idb_context()); AddFakeIndexedDB(kOriginA, 1000); AddFakeIndexedDB(kOriginB, 50); diff --git a/content/browser/indexed_db/indexed_db_tracing.h b/content/browser/indexed_db/indexed_db_tracing.h deleted file mode 100644 index 86ddaa34b..0000000 --- a/content/browser/indexed_db/indexed_db_tracing.h +++ /dev/null @@ -1,11 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_TRACING_H_ -#define CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_TRACING_H_ - -#include "base/debug/trace_event.h" -#define IDB_TRACE(a) TRACE_EVENT0("IndexedDB", (a)); - -#endif // CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_TRACING_H_ diff --git a/content/browser/indexed_db/indexed_db_transaction.cc b/content/browser/indexed_db/indexed_db_transaction.cc deleted file mode 100644 index b0a9946..0000000 --- a/content/browser/indexed_db/indexed_db_transaction.cc +++ /dev/null @@ -1,308 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/indexed_db_transaction.h" - -#include <vector> -#include "base/logging.h" -#include "base/utf_string_conversions.h" -#include "content/browser/indexed_db/indexed_db_backing_store.h" -#include "content/browser/indexed_db/indexed_db_cursor_impl.h" -#include "content/browser/indexed_db/indexed_db_database_callbacks_wrapper.h" -#include "content/browser/indexed_db/indexed_db_database_impl.h" -#include "content/browser/indexed_db/indexed_db_tracing.h" -#include "content/browser/indexed_db/indexed_db_transaction_coordinator.h" -#include "third_party/WebKit/public/platform/WebIDBDatabaseException.h" - -namespace content { - -IndexedDBTransaction::TaskQueue::TaskQueue() {} -IndexedDBTransaction::TaskQueue::~TaskQueue() { clear(); } - -void IndexedDBTransaction::TaskQueue::clear() { - while (!queue_.empty()) - scoped_ptr<Operation> task(pop()); -} - -scoped_ptr<IndexedDBTransaction::Operation> -IndexedDBTransaction::TaskQueue::pop() { - DCHECK(!queue_.empty()); - scoped_ptr<Operation> task(queue_.front()); - queue_.pop(); - return task.Pass(); -} - -IndexedDBTransaction::TaskStack::TaskStack() {} -IndexedDBTransaction::TaskStack::~TaskStack() { clear(); } - -void IndexedDBTransaction::TaskStack::clear() { - while (!stack_.empty()) - scoped_ptr<Operation> task(pop()); -} - -scoped_ptr<IndexedDBTransaction::Operation> -IndexedDBTransaction::TaskStack::pop() { - DCHECK(!stack_.empty()); - scoped_ptr<Operation> task(stack_.top()); - stack_.pop(); - return task.Pass(); -} - -scoped_refptr<IndexedDBTransaction> IndexedDBTransaction::Create( - int64 id, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> callbacks, - const std::vector<int64>& object_store_ids, - indexed_db::TransactionMode mode, - IndexedDBDatabaseImpl* database) { - std::set<int64> object_store_hash_set; - for (size_t i = 0; i < object_store_ids.size(); ++i) - object_store_hash_set.insert(object_store_ids[i]); - - return make_scoped_refptr(new IndexedDBTransaction( - id, callbacks, object_store_hash_set, mode, database)); -} - -IndexedDBTransaction::IndexedDBTransaction( - int64 id, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> callbacks, - const std::set<int64>& object_store_ids, - indexed_db::TransactionMode mode, - IndexedDBDatabaseImpl* database) - : id_(id), - object_store_ids_(object_store_ids), - mode_(mode), - state_(UNUSED), - commit_pending_(false), - callbacks_(callbacks), - database_(database), - transaction_(database->BackingStore().get()), - pending_preemptive_events_(0) { - database_->transaction_coordinator().DidCreateTransaction(this); -} - -IndexedDBTransaction::~IndexedDBTransaction() { - // It shouldn't be possible for this object to get deleted until it's either - // complete or aborted. - DCHECK_EQ(state_, FINISHED); - DCHECK(preemptive_task_queue_.empty()); - DCHECK(task_queue_.empty()); - DCHECK(abort_task_stack_.empty()); -} - -void IndexedDBTransaction::ScheduleTask(IndexedDBDatabase::TaskType type, - Operation* task, - Operation* abort_task) { - if (state_ == FINISHED) - return; - - if (type == IndexedDBDatabase::NORMAL_TASK) - task_queue_.push(task); - else - preemptive_task_queue_.push(task); - - if (abort_task) - abort_task_stack_.push(abort_task); - - if (state_ == UNUSED) - Start(); - else if (state_ == RUNNING && !task_timer_.IsRunning()) - task_timer_.Start(FROM_HERE, - base::TimeDelta::FromSeconds(0), - this, - &IndexedDBTransaction::TaskTimerFired); -} - -void IndexedDBTransaction::Abort() { - Abort(IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16("Internal error (unknown cause)"))); -} - -void IndexedDBTransaction::Abort(scoped_refptr<IndexedDBDatabaseError> error) { - IDB_TRACE("IndexedDBTransaction::abort"); - if (state_ == FINISHED) - return; - - bool was_running = state_ == RUNNING; - - // The last reference to this object may be released while performing the - // abort steps below. We therefore take a self reference to keep ourselves - // alive while executing this method. - scoped_refptr<IndexedDBTransaction> protect(this); - - state_ = FINISHED; - task_timer_.Stop(); - - if (was_running) - transaction_.Rollback(); - - // Run the abort tasks, if any. - while (!abort_task_stack_.empty()) { - scoped_ptr<Operation> task(abort_task_stack_.pop()); - task->Perform(0); - } - preemptive_task_queue_.clear(); - task_queue_.clear(); - - // Backing store resources (held via cursors) must be released - // before script callbacks are fired, as the script callbacks may - // release references and allow the backing store itself to be - // released, and order is critical. - CloseOpenCursors(); - transaction_.Reset(); - - // Transactions must also be marked as completed before the - // front-end is notified, as the transaction completion unblocks - // operations like closing connections. - database_->transaction_coordinator().DidFinishTransaction(this); -#ifndef NDEBUG - DCHECK(!database_->transaction_coordinator().IsActive(this)); -#endif - database_->TransactionFinished(this); - - if (callbacks_) - callbacks_->OnAbort(id_, error); - - database_->TransactionFinishedAndAbortFired(this); - - database_ = NULL; -} - -bool IndexedDBTransaction::IsTaskQueueEmpty() const { - return preemptive_task_queue_.empty() && task_queue_.empty(); -} - -bool IndexedDBTransaction::HasPendingTasks() const { - return pending_preemptive_events_ || !IsTaskQueueEmpty(); -} - -void IndexedDBTransaction::RegisterOpenCursor(IndexedDBCursorImpl* cursor) { - open_cursors_.insert(cursor); -} - -void IndexedDBTransaction::UnregisterOpenCursor(IndexedDBCursorImpl* cursor) { - open_cursors_.erase(cursor); -} - -void IndexedDBTransaction::Run() { - // TransactionCoordinator has started this transaction. Schedule a timer - // to process the first task. - DCHECK(state_ == START_PENDING || state_ == RUNNING); - DCHECK(!task_timer_.IsRunning()); - - task_timer_.Start(FROM_HERE, - base::TimeDelta::FromSeconds(0), - this, - &IndexedDBTransaction::TaskTimerFired); -} - -void IndexedDBTransaction::Start() { - DCHECK_EQ(state_, UNUSED); - - state_ = START_PENDING; - database_->transaction_coordinator().DidStartTransaction(this); - database_->TransactionStarted(this); -} - -void IndexedDBTransaction::Commit() { - IDB_TRACE("IndexedDBTransaction::commit"); - - // In multiprocess ports, front-end may have requested a commit but - // an abort has already been initiated asynchronously by the - // back-end. - if (state_ == FINISHED) - return; - - DCHECK(state_ == UNUSED || state_ == RUNNING); - commit_pending_ = true; - - // Front-end has requested a commit, but there may be tasks like - // create_index which are considered synchronous by the front-end - // but are processed asynchronously. - if (HasPendingTasks()) - return; - - // The last reference to this object may be released while performing the - // commit steps below. We therefore take a self reference to keep ourselves - // alive while executing this method. - scoped_refptr<IndexedDBTransaction> protect(this); - - // TODO(jsbell): Run abort tasks if commit fails? http://crbug.com/241843 - abort_task_stack_.clear(); - - bool unused = state_ == UNUSED; - state_ = FINISHED; - - bool committed = unused || transaction_.Commit(); - - // Backing store resources (held via cursors) must be released - // before script callbacks are fired, as the script callbacks may - // release references and allow the backing store itself to be - // released, and order is critical. - CloseOpenCursors(); - transaction_.Reset(); - - // Transactions must also be marked as completed before the - // front-end is notified, as the transaction completion unblocks - // operations like closing connections. - if (!unused) - database_->transaction_coordinator().DidFinishTransaction(this); - database_->TransactionFinished(this); - - if (committed) { - callbacks_->OnComplete(id_); - database_->TransactionFinishedAndCompleteFired(this); - } else { - callbacks_->OnAbort( - id_, - IndexedDBDatabaseError::Create( - WebKit::WebIDBDatabaseExceptionUnknownError, - ASCIIToUTF16("Internal error committing transaction."))); - database_->TransactionFinishedAndAbortFired(this); - } - - database_ = NULL; -} - -void IndexedDBTransaction::TaskTimerFired() { - IDB_TRACE("IndexedDBTransaction::task_timer_fired"); - DCHECK(!IsTaskQueueEmpty()); - - if (state_ == START_PENDING) { - transaction_.begin(); - state_ = RUNNING; - } - - // The last reference to this object may be released while performing the - // tasks. Take take a self reference to keep this object alive so that - // the loop termination conditions can be checked. - scoped_refptr<IndexedDBTransaction> protect(this); - - TaskQueue* task_queue = - pending_preemptive_events_ ? &preemptive_task_queue_ : &task_queue_; - while (!task_queue->empty() && state_ != FINISHED) { - DCHECK_EQ(state_, RUNNING); - scoped_ptr<Operation> task(task_queue->pop()); - task->Perform(this); - - // Event itself may change which queue should be processed next. - task_queue = - pending_preemptive_events_ ? &preemptive_task_queue_ : &task_queue_; - } - - // If there are no pending tasks, we haven't already committed/aborted, - // and the front-end requested a commit, it is now safe to do so. - if (!HasPendingTasks() && state_ != FINISHED && commit_pending_) - Commit(); -} - -void IndexedDBTransaction::CloseOpenCursors() { - for (std::set<IndexedDBCursorImpl*>::iterator i = open_cursors_.begin(); - i != open_cursors_.end(); - ++i) - (*i)->Close(); - open_cursors_.clear(); -} - -} // namespace content diff --git a/content/browser/indexed_db/indexed_db_transaction.h b/content/browser/indexed_db/indexed_db_transaction.h deleted file mode 100644 index ca0f929..0000000 --- a/content/browser/indexed_db/indexed_db_transaction.h +++ /dev/null @@ -1,150 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_TRANSACTION_H_ -#define CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_TRANSACTION_H_ - -#include <queue> -#include <set> -#include <stack> -#include <vector> - -#include "base/basictypes.h" -#include "base/memory/ref_counted.h" -#include "base/memory/scoped_ptr.h" -#include "base/timer.h" -#include "content/browser/indexed_db/indexed_db_backing_store.h" -#include "content/browser/indexed_db/indexed_db_database.h" -#include "content/browser/indexed_db/indexed_db_database_error.h" - -namespace content { - -class IndexedDBDatabaseImpl; -class IndexedDBCursorImpl; -class IndexedDBDatabaseCallbacksWrapper; - -class IndexedDBTransaction : public base::RefCounted<IndexedDBTransaction> { - public: - static scoped_refptr<IndexedDBTransaction> Create( - int64 transaction_id, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> callbacks, - const std::vector<int64>& scope, - indexed_db::TransactionMode, - IndexedDBDatabaseImpl* db); - - virtual void Abort(); - void Commit(); - - class Operation { - public: - Operation() {} - virtual ~Operation() {} - virtual void Perform(IndexedDBTransaction* transaction) = 0; - }; - - void Abort(scoped_refptr<IndexedDBDatabaseError> error); - void Run(); - indexed_db::TransactionMode mode() const { return mode_; } - const std::set<int64>& scope() const { return object_store_ids_; } - void ScheduleTask(Operation* task, Operation* abort_task = NULL) { - ScheduleTask(IndexedDBDatabase::NORMAL_TASK, task, abort_task); - } - void ScheduleTask(IndexedDBDatabase::TaskType, - Operation* task, - Operation* abort_task = NULL); - void RegisterOpenCursor(IndexedDBCursorImpl* cursor); - void UnregisterOpenCursor(IndexedDBCursorImpl* cursor); - void AddPreemptiveEvent() { pending_preemptive_events_++; } - void DidCompletePreemptiveEvent() { - pending_preemptive_events_--; - DCHECK_GE(pending_preemptive_events_, 0); - } - IndexedDBBackingStore::Transaction* BackingStoreTransaction() { - return &transaction_; - } - int64 id() const { return id_; } - - IndexedDBDatabaseImpl* database() const { return database_.get(); } - IndexedDBDatabaseCallbacksWrapper* connection() const { - return callbacks_.get(); - } - - protected: - virtual ~IndexedDBTransaction(); - friend class base::RefCounted<IndexedDBTransaction>; - - private: - IndexedDBTransaction( - int64 id, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> callbacks, - const std::set<int64>& object_store_ids, - indexed_db::TransactionMode, - IndexedDBDatabaseImpl* db); - - enum State { - UNUSED, // Created, but no tasks yet. - START_PENDING, // Enqueued tasks, but backing store transaction not yet - // started. - RUNNING, // Backing store transaction started but not yet finished. - FINISHED, // Either aborted or committed. - }; - - void Start(); - - bool IsTaskQueueEmpty() const; - bool HasPendingTasks() const; - - void TaskTimerFired(); - void CloseOpenCursors(); - - const int64 id_; - const std::set<int64> object_store_ids_; - const indexed_db::TransactionMode mode_; - - State state_; - bool commit_pending_; - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> callbacks_; - scoped_refptr<IndexedDBDatabaseImpl> database_; - - class TaskQueue { - public: - TaskQueue(); - ~TaskQueue(); - bool empty() const { return queue_.empty(); } - void push(Operation* task) { queue_.push(task); } - scoped_ptr<Operation> pop(); - void clear(); - - private: - std::queue<Operation*> queue_; - }; - - class TaskStack { - public: - TaskStack(); - ~TaskStack(); - bool empty() const { return stack_.empty(); } - void push(Operation* task) { stack_.push(task); } - scoped_ptr<Operation> pop(); - void clear(); - - private: - std::stack<Operation*> stack_; - }; - - TaskQueue task_queue_; - TaskQueue preemptive_task_queue_; - TaskStack abort_task_stack_; - - IndexedDBBackingStore::Transaction transaction_; - - base::OneShotTimer<IndexedDBTransaction> task_timer_; - int pending_preemptive_events_; - - std::set<IndexedDBCursorImpl*> open_cursors_; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_TRANSACTION_H_ diff --git a/content/browser/indexed_db/indexed_db_transaction_coordinator.cc b/content/browser/indexed_db/indexed_db_transaction_coordinator.cc deleted file mode 100644 index 06d6fa0..0000000 --- a/content/browser/indexed_db/indexed_db_transaction_coordinator.cc +++ /dev/null @@ -1,135 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/indexed_db_transaction_coordinator.h" - -#include "base/basictypes.h" -#include "base/logging.h" -#include "content/browser/indexed_db/indexed_db_transaction.h" - -namespace content { - -IndexedDBTransactionCoordinator::IndexedDBTransactionCoordinator() {} - -IndexedDBTransactionCoordinator::~IndexedDBTransactionCoordinator() { - // TODO(jsbell): DCHECK that all queues are empty. http://crbug.com/241821 -} - -void IndexedDBTransactionCoordinator::DidCreateTransaction( - IndexedDBTransaction* transaction) { - DCHECK(transactions_.find(transaction) == transactions_.end()); - transactions_[transaction] = transaction; -} - -void IndexedDBTransactionCoordinator::DidStartTransaction( - IndexedDBTransaction* transaction) { - DCHECK(transactions_.find(transaction) != transactions_.end()); - - queued_transactions_.insert(transaction); - ProcessStartedTransactions(); -} - -void IndexedDBTransactionCoordinator::DidFinishTransaction( - IndexedDBTransaction* transaction) { - DCHECK(transactions_.find(transaction) != transactions_.end()); - - if (queued_transactions_.has(transaction)) { - DCHECK(started_transactions_.find(transaction) == - started_transactions_.end()); - queued_transactions_.erase(transaction); - } else { - if (started_transactions_.find(transaction) != started_transactions_.end()) - started_transactions_.erase(transaction); - } - transactions_.erase(transaction); - - ProcessStartedTransactions(); -} - -#ifndef NDEBUG -// Verifies internal consistency while returning whether anything is found. -bool IndexedDBTransactionCoordinator::IsActive( - IndexedDBTransaction* transaction) { - bool found = false; - if (queued_transactions_.has(transaction)) - found = true; - if (started_transactions_.find(transaction) != started_transactions_.end()) { - DCHECK(!found); - found = true; - } - DCHECK_EQ(found, (transactions_.find(transaction) != transactions_.end())); - return found; -} -#endif - -void IndexedDBTransactionCoordinator::ProcessStartedTransactions() { - if (queued_transactions_.empty()) - return; - - DCHECK(started_transactions_.empty() || - (*started_transactions_.begin())->mode() != - indexed_db::TRANSACTION_VERSION_CHANGE); - - list_set<IndexedDBTransaction*>::const_iterator it = - queued_transactions_.begin(); - while (it != queued_transactions_.end()) { - IndexedDBTransaction* transaction = *it; - ++it; - if (CanRunTransaction(transaction)) { - queued_transactions_.erase(transaction); - started_transactions_.insert(transaction); - transaction->Run(); - } - } -} - -static bool DoScopesOverlap(const std::set<int64>& scope1, - const std::set<int64>& scope2) { - for (std::set<int64>::const_iterator it = scope1.begin(); it != scope1.end(); - ++it) { - if (scope2.find(*it) != scope2.end()) - return true; - } - return false; -} - -bool IndexedDBTransactionCoordinator::CanRunTransaction( - IndexedDBTransaction* transaction) { - DCHECK(queued_transactions_.has(transaction)); - switch (transaction->mode()) { - case indexed_db::TRANSACTION_VERSION_CHANGE: - DCHECK(queued_transactions_.size() == 1); - DCHECK(started_transactions_.empty()); - return true; - - case indexed_db::TRANSACTION_READ_ONLY: - return true; - - case indexed_db::TRANSACTION_READ_WRITE: - for (std::set<IndexedDBTransaction*>::const_iterator it = - started_transactions_.begin(); - it != started_transactions_.end(); - ++it) { - IndexedDBTransaction* other = *it; - if (other->mode() == indexed_db::TRANSACTION_READ_WRITE && - DoScopesOverlap(transaction->scope(), other->scope())) - return false; - } - for (list_set<IndexedDBTransaction*>::const_iterator it = - queued_transactions_.begin(); - *it != transaction; - ++it) { - DCHECK(it != queued_transactions_.end()); - IndexedDBTransaction* other = *it; - if (other->mode() == indexed_db::TRANSACTION_READ_WRITE && - DoScopesOverlap(transaction->scope(), other->scope())) - return false; - } - return true; - } - NOTREACHED(); - return false; -} - -} // namespace content diff --git a/content/browser/indexed_db/indexed_db_transaction_coordinator.h b/content/browser/indexed_db/indexed_db_transaction_coordinator.h deleted file mode 100644 index 1e01e9e..0000000 --- a/content/browser/indexed_db/indexed_db_transaction_coordinator.h +++ /dev/null @@ -1,50 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_TRANSACTION_COORDINATOR_H_ -#define CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_TRANSACTION_COORDINATOR_H_ - -#include <map> -#include <set> - -#include "base/memory/ref_counted.h" -#include "base/memory/scoped_ptr.h" -#include "content/browser/indexed_db/list_set.h" - -namespace content { - -class IndexedDBTransaction; - -// Transactions are executed in the order the were created. -class IndexedDBTransactionCoordinator { - public: - IndexedDBTransactionCoordinator(); - ~IndexedDBTransactionCoordinator(); - - // Called by transactions as they start and finish. - void DidCreateTransaction(IndexedDBTransaction* transaction); - void DidStartTransaction(IndexedDBTransaction* transaction); - void DidFinishTransaction(IndexedDBTransaction* transaction); - -#ifndef NDEBUG - bool IsActive(IndexedDBTransaction* transaction); -#endif - - // TODO(jsbell): API to handle closed connections. http://crbug.com/241821 - - private: - void ProcessStartedTransactions(); - bool CanRunTransaction(IndexedDBTransaction* transaction); - - // This is just an efficient way to keep references to all transactions. - std::map<IndexedDBTransaction*, scoped_refptr<IndexedDBTransaction> > - transactions_; - // Transactions in different states are grouped below. - list_set<IndexedDBTransaction*> queued_transactions_; - std::set<IndexedDBTransaction*> started_transactions_; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_INDEXED_DB_TRANSACTION_COORDINATOR_H_ diff --git a/content/browser/indexed_db/indexed_db_unittest.cc b/content/browser/indexed_db/indexed_db_unittest.cc index 9e90b8a..d4a9fb9 100644 --- a/content/browser/indexed_db/indexed_db_unittest.cc +++ b/content/browser/indexed_db/indexed_db_unittest.cc @@ -55,9 +55,10 @@ TEST_F(IndexedDBTest, ClearSessionOnlyDatabases) { // Create some indexedDB paths. // With the levelDB backend, these are directories. - IndexedDBContextImpl* idb_context = static_cast<IndexedDBContextImpl*>( - BrowserContext::GetDefaultStoragePartition(&browser_context) - ->GetIndexedDBContext()); + IndexedDBContextImpl* idb_context = + static_cast<IndexedDBContextImpl*>( + BrowserContext::GetDefaultStoragePartition(&browser_context)-> + GetIndexedDBContext()); // Override the storage policy with our own. idb_context->special_storage_policy_ = special_storage_policy; @@ -98,9 +99,10 @@ TEST_F(IndexedDBTest, SetForceKeepSessionState) { // Create some indexedDB paths. // With the levelDB backend, these are directories. - IndexedDBContextImpl* idb_context = static_cast<IndexedDBContextImpl*>( - BrowserContext::GetDefaultStoragePartition(&browser_context) - ->GetIndexedDBContext()); + IndexedDBContextImpl* idb_context = + static_cast<IndexedDBContextImpl*>( + BrowserContext::GetDefaultStoragePartition(&browser_context)-> + GetIndexedDBContext()); // Override the storage policy with our own. idb_context->special_storage_policy_ = special_storage_policy; @@ -126,16 +128,20 @@ TEST_F(IndexedDBTest, SetForceKeepSessionState) { EXPECT_TRUE(file_util::DirectoryExists(session_only_path)); } -class MockWebIDBDatabase : public WebKit::WebIDBDatabase { +class MockWebIDBDatabase : public WebKit::WebIDBDatabase +{ public: MockWebIDBDatabase(bool expect_force_close) - : expect_force_close_(expect_force_close), force_close_called_(false) {} + : expect_force_close_(expect_force_close), + force_close_called_(false) {} - virtual ~MockWebIDBDatabase() { + virtual ~MockWebIDBDatabase() + { EXPECT_TRUE(force_close_called_ == expect_force_close_); } - virtual void forceClose() { + virtual void forceClose() + { ASSERT_TRUE(expect_force_close_); force_close_called_ = true; } @@ -145,6 +151,7 @@ class MockWebIDBDatabase : public WebKit::WebIDBDatabase { bool force_close_called_; }; + TEST_F(IndexedDBTest, ForceCloseOpenDatabasesOnDelete) { base::ScopedTempDir temp_dir; ASSERT_TRUE(temp_dir.CreateUniqueTempDir()); @@ -158,9 +165,10 @@ TEST_F(IndexedDBTest, ForceCloseOpenDatabasesOnDelete) { const GURL kTestOrigin("http://test/"); - IndexedDBContextImpl* idb_context = static_cast<IndexedDBContextImpl*>( - BrowserContext::GetDefaultStoragePartition(&browser_context) - ->GetIndexedDBContext()); + IndexedDBContextImpl* idb_context = + static_cast<IndexedDBContextImpl*>( + BrowserContext::GetDefaultStoragePartition(&browser_context)-> + GetIndexedDBContext()); idb_context->quota_manager_proxy_ = NULL; idb_context->set_data_path_for_testing(temp_dir.path()); diff --git a/content/browser/indexed_db/leveldb/avltree.h b/content/browser/indexed_db/leveldb/avltree.h deleted file mode 100644 index 104d69b..0000000 --- a/content/browser/indexed_db/leveldb/avltree.h +++ /dev/null @@ -1,979 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -/* - * Copyright (C) 2008 Apple Inc. All rights reserved. - * - * Based on Abstract AVL Tree Template v1.5 by Walt Karas - * <http://geocities.com/wkaras/gen_cpp/avl_tree.html>. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of - * its contributors may be used to endorse or promote products derived - * from this software without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY - * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED - * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE - * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY - * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES - * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; - * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND - * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT - * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF - * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - */ - -#ifndef CONTENT_BROWSER_INDEXED_DB_LEVELDB_AVLTREE_H_ -#define CONTENT_BROWSER_INDEXED_DB_LEVELDB_AVLTREE_H_ - -#include "base/logging.h" -#include "content/browser/indexed_db/leveldb/fixed_array.h" - -namespace content { - -// Here is the reference class for BSet. -// -// class BSet -// { -// public: -// -// class ANY_bitref -// { -// public: -// operator bool (); -// void operator = (bool b); -// }; -// -// // Does not have to initialize bits. -// BSet(); -// -// // Must return a valid value for index when 0 <= index < maxDepth -// ANY_bitref operator [] (unsigned index); -// -// // Set all bits to 1. -// void set(); -// -// // Set all bits to 0. -// void reset(); -// }; - -template <unsigned maxDepth> class AVLTreeDefaultBSet { - public: - bool& operator[](unsigned i) { -#if defined(ADDRESS_SANITIZER) - CHECK(i < maxDepth); -#endif - return m_data[i]; - } - void set() { - for (unsigned i = 0; i < maxDepth; ++i) - m_data[i] = true; - } - void reset() { - for (unsigned i = 0; i < maxDepth; ++i) - m_data[i] = false; - } - - private: - FixedArray<bool, maxDepth> m_data; -}; - -// How to determine maxDepth: -// d Minimum number of nodes -// 2 2 -// 3 4 -// 4 7 -// 5 12 -// 6 20 -// 7 33 -// 8 54 -// 9 88 -// 10 143 -// 11 232 -// 12 376 -// 13 609 -// 14 986 -// 15 1,596 -// 16 2,583 -// 17 4,180 -// 18 6,764 -// 19 10,945 -// 20 17,710 -// 21 28,656 -// 22 46,367 -// 23 75,024 -// 24 121,392 -// 25 196,417 -// 26 317,810 -// 27 514,228 -// 28 832,039 -// 29 1,346,268 -// 30 2,178,308 -// 31 3,524,577 -// 32 5,702,886 -// 33 9,227,464 -// 34 14,930,351 -// 35 24,157,816 -// 36 39,088,168 -// 37 63,245,985 -// 38 102,334,154 -// 39 165,580,140 -// 40 267,914,295 -// 41 433,494,436 -// 42 701,408,732 -// 43 1,134,903,169 -// 44 1,836,311,902 -// 45 2,971,215,072 -// -// E.g., if, in a particular instantiation, the maximum number of nodes in a -// tree instance is 1,000,000, the maximum depth should be 28. -// You pick 28 because MN(28) is 832,039, which is less than or equal to -// 1,000,000, and MN(29) is 1,346,268, which is strictly greater than 1,000,000. - -template <class Abstractor, - unsigned maxDepth = 32, - class BSet = AVLTreeDefaultBSet<maxDepth> > -class AVLTree { - public: - typedef typename Abstractor::key key; - typedef typename Abstractor::handle handle; - typedef typename Abstractor::size size; - - enum SearchType { - EQUAL = 1, - LESS = 2, - GREATER = 4, - LESS_EQUAL = EQUAL | LESS, - GREATER_EQUAL = EQUAL | GREATER - }; - - Abstractor& abstractor() { return abs; } - - inline handle insert(handle h); - - inline handle search(key k, SearchType st = EQUAL); - inline handle search_least(); - inline handle search_greatest(); - - inline handle remove(key k); - - inline handle subst(handle new_node); - - void purge() { abs.root = null(); } - - bool is_empty() { return abs.root == null(); } - - AVLTree() { abs.root = null(); } - - class Iterator { - public: - // Initialize depth to invalid value, to indicate iterator is - // invalid. (Depth is zero-base.) - Iterator() { depth = ~0U; } - - void start_iter(AVLTree& tree, key k, SearchType st = EQUAL) { - // Mask of high bit in an int. - const int kMaskHighBit = (int) ~((~(unsigned) 0) >> 1); - - // Save the tree that we're going to iterate through in a - // member variable. - tree_ = &tree; - - int cmp, target_cmp; - handle h = tree_->abs.root; - unsigned d = 0; - - depth = ~0U; - - if (h == null()) { - // Tree is empty. - return; - } - - if (st & LESS) { - // Key can be greater than key of starting node. - target_cmp = 1; - } else if (st & GREATER) { - // Key can be less than key of starting node. - target_cmp = -1; - } else { - // Key must be same as key of starting node. - target_cmp = 0; - } - - for (;;) { - cmp = cmp_k_n(k, h); - if (cmp == 0) { - if (st & EQUAL) { - // Equal node was sought and found as starting node. - depth = d; - break; - } - cmp = -target_cmp; - } else if (target_cmp != 0) { - if (!((cmp ^ target_cmp) & kMaskHighBit)) { - // cmp and target_cmp are both negative or both positive. - depth = d; - } - } - h = cmp < 0 ? get_lt(h) : get_gt(h); - if (h == null()) - break; - branch[d] = cmp > 0; - path_h[d++] = h; - } - } - - void start_iter_least(AVLTree& tree) { - tree_ = &tree; - - handle h = tree_->abs.root; - - depth = ~0U; - - branch.reset(); - - while (h != null()) { - if (depth != ~0U) - path_h[depth] = h; - depth++; - h = get_lt(h); - } - } - - void start_iter_greatest(AVLTree& tree) { - tree_ = &tree; - - handle h = tree_->abs.root; - - depth = ~0U; - - branch.set(); - - while (h != null()) { - if (depth != ~0U) - path_h[depth] = h; - depth++; - h = get_gt(h); - } - } - - handle operator*() { - if (depth == ~0U) - return null(); - - return depth == 0 ? tree_->abs.root : path_h[depth - 1]; - } - - void operator++() { - if (depth != ~0U) { - handle h = get_gt(**this); - if (h == null()) { - do { - if (depth == 0) { - depth = ~0U; - break; - } - depth--; - } while (branch[depth]); - } else { - branch[depth] = true; - path_h[depth++] = h; - for (;;) { - h = get_lt(h); - if (h == null()) - break; - branch[depth] = false; - path_h[depth++] = h; - } - } - } - } - - void operator--() { - if (depth != ~0U) { - handle h = get_lt(**this); - if (h == null()) { - do { - if (depth == 0) { - depth = ~0U; - break; - } - depth--; - } while (!branch[depth]); - } else { - branch[depth] = false; - path_h[depth++] = h; - for (;;) { - h = get_gt(h); - if (h == null()) - break; - branch[depth] = true; - path_h[depth++] = h; - } - } - } - } - - void operator++(int) { ++(*this); } - void operator--(int) { --(*this); } - - protected: - - // Tree being iterated over. - AVLTree* tree_; - - // Records a path into the tree. If branch[n] is true, indicates - // take greater branch from the nth node in the path, otherwise - // take the less branch. branch[0] gives branch from root, and - // so on. - BSet branch; - - // Zero-based depth of path into tree. - unsigned depth; - - // Handles of nodes in path from root to current node (returned by *). - handle path_h[maxDepth - 1]; - - int cmp_k_n(key k, handle h) { return tree_->abs.compare_key_node(k, h); } - int cmp_n_n(handle h1, handle h2) { - return tree_->abs.compare_node_node(h1, h2); - } - handle get_lt(handle h) { return tree_->abs.get_less(h); } - handle get_gt(handle h) { return tree_->abs.get_greater(h); } - handle null() { return tree_->abs.null(); } - }; - - template <typename fwd_iter> bool build(fwd_iter p, size num_nodes) { - if (num_nodes == 0) { - abs.root = null(); - return true; - } - - // Gives path to subtree being built. If branch[N] is false, branch - // less from the node at depth N, if true branch greater. - BSet branch; - - // If rem[N] is true, then for the current subtree at depth N, it's - // greater subtree has one more node than it's less subtree. - BSet rem; - - // Depth of root node of current subtree. - unsigned depth = 0; - - // Number of nodes in current subtree. - size num_sub = num_nodes; - - // The algorithm relies on a stack of nodes whose less subtree has - // been built, but whose right subtree has not yet been built. The - // stack is implemented as linked list. The nodes are linked - // together by having the "greater" handle of a node set to the - // next node in the list. "less_parent" is the handle of the first - // node in the list. - handle less_parent = null(); - - // h is root of current subtree, child is one of its children. - handle h, child; - - for (;;) { - while (num_sub > 2) { - // Subtract one for root of subtree. - num_sub--; - rem[depth] = !!(num_sub & 1); - branch[depth++] = false; - num_sub >>= 1; - } - - if (num_sub == 2) { - // Build a subtree with two nodes, slanting to greater. - // I arbitrarily chose to always have the extra node in the - // greater subtree when there is an odd number of nodes to - // split between the two subtrees. - - h = *p; - p++; - child = *p; - p++; - set_lt(child, null()); - set_gt(child, null()); - set_bf(child, 0); - set_gt(h, child); - set_lt(h, null()); - set_bf(h, 1); - } else { // num_sub == 1 - // Build a subtree with one node. - - h = *p; - p++; - set_lt(h, null()); - set_gt(h, null()); - set_bf(h, 0); - } - - while (depth) { - depth--; - if (!branch[depth]) { - // We've completed a less subtree. - break; - } - - // We've completed a greater subtree, so attach it to - // its parent (that is less than it). We pop the parent - // off the stack of less parents. - child = h; - h = less_parent; - less_parent = get_gt(h); - set_gt(h, child); - // num_sub = 2 * (num_sub - rem[depth]) + rem[depth] + 1 - num_sub <<= 1; - num_sub += 1 - rem[depth]; - if (num_sub & (num_sub - 1)) { - // num_sub is not a power of 2 - set_bf(h, 0); - } else { - // num_sub is a power of 2 - set_bf(h, 1); - } - } - - if (num_sub == num_nodes) { - // We've completed the full tree. - break; - } - - // The subtree we've completed is the less subtree of the - // next node in the sequence. - - child = h; - h = *p; - p++; - set_lt(h, child); - - // Put h into stack of less parents. - set_gt(h, less_parent); - less_parent = h; - - // Proceed to creating greater than subtree of h. - branch[depth] = true; - num_sub += rem[depth++]; - - } // end for (;;) - - abs.root = h; - - return true; - } - - protected: - - friend class Iterator; - - // Create a class whose sole purpose is to take advantage of - // the "empty member" optimization. - struct abs_plus_root : public Abstractor { - // The handle of the root element in the AVL tree. - handle root; - }; - - abs_plus_root abs; - - handle get_lt(handle h) { return abs.get_less(h); } - void set_lt(handle h, handle lh) { abs.set_less(h, lh); } - - handle get_gt(handle h) { return abs.get_greater(h); } - void set_gt(handle h, handle gh) { abs.set_greater(h, gh); } - - int get_bf(handle h) { return abs.get_balance_factor(h); } - void set_bf(handle h, int bf) { abs.set_balance_factor(h, bf); } - - int cmp_k_n(key k, handle h) { return abs.compare_key_node(k, h); } - int cmp_n_n(handle h1, handle h2) { return abs.compare_node_node(h1, h2); } - - handle null() { return abs.null(); } - - private: - - // Balances subtree, returns handle of root node of subtree - // after balancing. - handle balance(handle bal_h) { - handle deep_h; - - // Either the "greater than" or the "less than" subtree of - // this node has to be 2 levels deeper (or else it wouldn't - // need balancing). - - if (get_bf(bal_h) > 0) { - // "Greater than" subtree is deeper. - - deep_h = get_gt(bal_h); - - if (get_bf(deep_h) < 0) { - handle old_h = bal_h; - bal_h = get_lt(deep_h); - - set_gt(old_h, get_lt(bal_h)); - set_lt(deep_h, get_gt(bal_h)); - set_lt(bal_h, old_h); - set_gt(bal_h, deep_h); - - int bf = get_bf(bal_h); - if (bf != 0) { - if (bf > 0) { - set_bf(old_h, -1); - set_bf(deep_h, 0); - } else { - set_bf(deep_h, 1); - set_bf(old_h, 0); - } - set_bf(bal_h, 0); - } else { - set_bf(old_h, 0); - set_bf(deep_h, 0); - } - } else { - set_gt(bal_h, get_lt(deep_h)); - set_lt(deep_h, bal_h); - if (get_bf(deep_h) == 0) { - set_bf(deep_h, -1); - set_bf(bal_h, 1); - } else { - set_bf(deep_h, 0); - set_bf(bal_h, 0); - } - bal_h = deep_h; - } - } else { - // "Less than" subtree is deeper. - - deep_h = get_lt(bal_h); - - if (get_bf(deep_h) > 0) { - handle old_h = bal_h; - bal_h = get_gt(deep_h); - set_lt(old_h, get_gt(bal_h)); - set_gt(deep_h, get_lt(bal_h)); - set_gt(bal_h, old_h); - set_lt(bal_h, deep_h); - - int bf = get_bf(bal_h); - if (bf != 0) { - if (bf < 0) { - set_bf(old_h, 1); - set_bf(deep_h, 0); - } else { - set_bf(deep_h, -1); - set_bf(old_h, 0); - } - set_bf(bal_h, 0); - } else { - set_bf(old_h, 0); - set_bf(deep_h, 0); - } - } else { - set_lt(bal_h, get_gt(deep_h)); - set_gt(deep_h, bal_h); - if (get_bf(deep_h) == 0) { - set_bf(deep_h, 1); - set_bf(bal_h, -1); - } else { - set_bf(deep_h, 0); - set_bf(bal_h, 0); - } - bal_h = deep_h; - } - } - - return bal_h; - } - -}; - -template <class Abstractor, unsigned maxDepth, class BSet> -inline typename AVLTree<Abstractor, maxDepth, BSet>::handle -AVLTree<Abstractor, maxDepth, BSet>::insert(handle h) { - set_lt(h, null()); - set_gt(h, null()); - set_bf(h, 0); - - if (abs.root == null()) { - abs.root = h; - } else { - // Last unbalanced node encountered in search for insertion point. - handle unbal = null(); - // Parent of last unbalanced node. - handle parent_unbal = null(); - // Balance factor of last unbalanced node. - int unbal_bf; - - // Zero-based depth in tree. - unsigned depth = 0, unbal_depth = 0; - - // Records a path into the tree. If branch[n] is true, indicates - // take greater branch from the nth node in the path, otherwise - // take the less branch. branch[0] gives branch from root, and - // so on. - BSet branch; - - handle hh = abs.root; - handle parent = null(); - int cmp; - - do { - if (get_bf(hh) != 0) { - unbal = hh; - parent_unbal = parent; - unbal_depth = depth; - } - cmp = cmp_n_n(h, hh); - if (cmp == 0) { - // Duplicate key. - return hh; - } - parent = hh; - hh = cmp < 0 ? get_lt(hh) : get_gt(hh); - branch[depth++] = cmp > 0; - } while (hh != null()); - - // Add node to insert as leaf of tree. - if (cmp < 0) - set_lt(parent, h); - else - set_gt(parent, h); - - depth = unbal_depth; - - if (unbal == null()) { - hh = abs.root; - } else { - cmp = branch[depth++] ? 1 : -1; - unbal_bf = get_bf(unbal); - if (cmp < 0) - unbal_bf--; - else // cmp > 0 - unbal_bf++; - hh = cmp < 0 ? get_lt(unbal) : get_gt(unbal); - if ((unbal_bf != -2) && (unbal_bf != 2)) { - // No rebalancing of tree is necessary. - set_bf(unbal, unbal_bf); - unbal = null(); - } - } - - if (hh != null()) { - while (h != hh) { - cmp = branch[depth++] ? 1 : -1; - if (cmp < 0) { - set_bf(hh, -1); - hh = get_lt(hh); - } else { // cmp > 0 - set_bf(hh, 1); - hh = get_gt(hh); - } - } - } - - if (unbal != null()) { - unbal = balance(unbal); - if (parent_unbal == null()) { - abs.root = unbal; - } else { - depth = unbal_depth - 1; - cmp = branch[depth] ? 1 : -1; - if (cmp < 0) - set_lt(parent_unbal, unbal); - else // cmp > 0 - set_gt(parent_unbal, unbal); - } - } - } - - return h; -} - -template <class Abstractor, unsigned maxDepth, class BSet> -inline typename AVLTree<Abstractor, maxDepth, BSet>::handle -AVLTree<Abstractor, maxDepth, BSet>::search( - key k, - typename AVLTree<Abstractor, maxDepth, BSet>::SearchType st) { - const int kMaskHighBit = (int) ~((~(unsigned) 0) >> 1); - - int cmp, target_cmp; - handle match_h = null(); - handle h = abs.root; - - if (st & LESS) - target_cmp = 1; - else if (st & GREATER) - target_cmp = -1; - else - target_cmp = 0; - - while (h != null()) { - cmp = cmp_k_n(k, h); - if (cmp == 0) { - if (st & EQUAL) { - match_h = h; - break; - } - cmp = -target_cmp; - } else if (target_cmp != 0) { - if (!((cmp ^ target_cmp) & kMaskHighBit)) { - // cmp and target_cmp are both positive or both negative. - match_h = h; - } - } - h = cmp < 0 ? get_lt(h) : get_gt(h); - } - - return match_h; -} - -template <class Abstractor, unsigned maxDepth, class BSet> -inline typename AVLTree<Abstractor, maxDepth, BSet>::handle -AVLTree<Abstractor, maxDepth, BSet>::search_least() { - handle h = abs.root, parent = null(); - - while (h != null()) { - parent = h; - h = get_lt(h); - } - - return parent; -} - -template <class Abstractor, unsigned maxDepth, class BSet> -inline typename AVLTree<Abstractor, maxDepth, BSet>::handle -AVLTree<Abstractor, maxDepth, BSet>::search_greatest() { - handle h = abs.root, parent = null(); - - while (h != null()) { - parent = h; - h = get_gt(h); - } - - return parent; -} - -template <class Abstractor, unsigned maxDepth, class BSet> -inline typename AVLTree<Abstractor, maxDepth, BSet>::handle -AVLTree<Abstractor, maxDepth, BSet>::remove(key k) { - // Zero-based depth in tree. - unsigned depth = 0, rm_depth; - - // Records a path into the tree. If branch[n] is true, indicates - // take greater branch from the nth node in the path, otherwise - // take the less branch. branch[0] gives branch from root, and - // so on. - BSet branch; - - handle h = abs.root; - handle parent = null(), child; - int cmp, cmp_shortened_sub_with_path = 0; - - for (;;) { - if (h == null()) { - // No node in tree with given key. - return null(); - } - cmp = cmp_k_n(k, h); - if (cmp == 0) { - // Found node to remove. - break; - } - parent = h; - h = cmp < 0 ? get_lt(h) : get_gt(h); - branch[depth++] = cmp > 0; - cmp_shortened_sub_with_path = cmp; - } - handle rm = h; - handle parent_rm = parent; - rm_depth = depth; - - // If the node to remove is not a leaf node, we need to get a - // leaf node, or a node with a single leaf as its child, to put - // in the place of the node to remove. We will get the greatest - // node in the less subtree (of the node to remove), or the least - // node in the greater subtree. We take the leaf node from the - // deeper subtree, if there is one. - - if (get_bf(h) < 0) { - child = get_lt(h); - branch[depth] = false; - cmp = -1; - } else { - child = get_gt(h); - branch[depth] = true; - cmp = 1; - } - depth++; - - if (child != null()) { - cmp = -cmp; - do { - parent = h; - h = child; - if (cmp < 0) { - child = get_lt(h); - branch[depth] = false; - } else { - child = get_gt(h); - branch[depth] = true; - } - depth++; - } while (child != null()); - - if (parent == rm) { - // Only went through do loop once. Deleted node will be replaced - // in the tree structure by one of its immediate children. - cmp_shortened_sub_with_path = -cmp; - } else { - cmp_shortened_sub_with_path = cmp; - } - - // Get the handle of the opposite child, which may not be null. - child = cmp > 0 ? get_lt(h) : get_gt(h); - } - - if (parent == null()) { - // There were only 1 or 2 nodes in this tree. - abs.root = child; - } else if (cmp_shortened_sub_with_path < 0) { - set_lt(parent, child); - } else { - set_gt(parent, child); - } - - // "path" is the parent of the subtree being eliminated or reduced - // from a depth of 2 to 1. If "path" is the node to be removed, we - // set path to the node we're about to poke into the position of the - // node to be removed. - handle path = parent == rm ? h : parent; - - if (h != rm) { - // Poke in the replacement for the node to be removed. - set_lt(h, get_lt(rm)); - set_gt(h, get_gt(rm)); - set_bf(h, get_bf(rm)); - if (parent_rm == null()) { - abs.root = h; - } else { - depth = rm_depth - 1; - if (branch[depth]) - set_gt(parent_rm, h); - else - set_lt(parent_rm, h); - } - } - - if (path != null()) { - // Create a temporary linked list from the parent of the path node - // to the root node. - h = abs.root; - parent = null(); - depth = 0; - while (h != path) { - if (branch[depth++]) { - child = get_gt(h); - set_gt(h, parent); - } else { - child = get_lt(h); - set_lt(h, parent); - } - parent = h; - h = child; - } - - // Climb from the path node to the root node using the linked - // list, restoring the tree structure and rebalancing as necessary. - bool reduced_depth = true; - int bf; - cmp = cmp_shortened_sub_with_path; - for (;;) { - if (reduced_depth) { - bf = get_bf(h); - if (cmp < 0) - bf++; - else // cmp > 0 - bf--; - if ((bf == -2) || (bf == 2)) { - h = balance(h); - bf = get_bf(h); - } else { - set_bf(h, bf); - } - reduced_depth = (bf == 0); - } - if (parent == null()) - break; - child = h; - h = parent; - cmp = branch[--depth] ? 1 : -1; - if (cmp < 0) { - parent = get_lt(h); - set_lt(h, child); - } else { - parent = get_gt(h); - set_gt(h, child); - } - } - abs.root = h; - } - - return rm; -} - -template <class Abstractor, unsigned maxDepth, class BSet> -inline typename AVLTree<Abstractor, maxDepth, BSet>::handle -AVLTree<Abstractor, maxDepth, BSet>::subst(handle new_node) { - handle h = abs.root; - handle parent = null(); - int cmp, last_cmp; - - // Search for node already in tree with same key. - for (;;) { - if (h == null()) { - // No node in tree with same key as new node. - return null(); - } - cmp = cmp_n_n(new_node, h); - if (cmp == 0) { - // Found the node to substitute new one for. - break; - } - last_cmp = cmp; - parent = h; - h = cmp < 0 ? get_lt(h) : get_gt(h); - } - - // Copy tree housekeeping fields from node in tree to new node. - set_lt(new_node, get_lt(h)); - set_gt(new_node, get_gt(h)); - set_bf(new_node, get_bf(h)); - - if (parent == null()) { - // New node is also new root. - abs.root = new_node; - } else { - // Make parent point to new node. - if (last_cmp < 0) - set_lt(parent, new_node); - else - set_gt(parent, new_node); - } - - return h; -} - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_LEVELDB_AVLTREE_H_ diff --git a/content/browser/indexed_db/leveldb/fixed_array.h b/content/browser/indexed_db/leveldb/fixed_array.h deleted file mode 100644 index 8e67a63..0000000 --- a/content/browser/indexed_db/leveldb/fixed_array.h +++ /dev/null @@ -1,62 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -/* - * Copyright (C) 2010 Apple Inc. All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' - * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, - * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR - * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS - * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR - * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF - * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS - * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN - * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) - * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF - * THE POSSIBILITY OF SUCH DAMAGE. - */ - -#ifndef CONTENT_BROWSER_INDEXED_DB_LEVELDB_FIXED_ARRAY_H_ -#define CONTENT_BROWSER_INDEXED_DB_LEVELDB_FIXED_ARRAY_H_ - -#include "base/logging.h" - -namespace content { - -template <typename T, size_t Size> class FixedArray { - public: - T& operator[](size_t i) { -#if defined(ADDRESS_SANITIZER) - CHECK(i < Size); -#endif - return m_data[i]; - } - - const T& operator[](size_t i) const { -#if defined(ADDRESS_SANITIZER) - CHECK(i < Size); -#endif - return m_data[i]; - } - - T* data() { return m_data; } - size_t size() const { return Size; } - - private: - T m_data[Size]; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_LEVELDB_FIXED_ARRAY_H_ diff --git a/content/browser/indexed_db/leveldb/leveldb_comparator.h b/content/browser/indexed_db/leveldb/leveldb_comparator.h deleted file mode 100644 index 920d97e..0000000 --- a/content/browser/indexed_db/leveldb/leveldb_comparator.h +++ /dev/null @@ -1,24 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_COMPARATOR_H_ -#define CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_COMPARATOR_H_ - -#include "base/string16.h" - -namespace content { - -class LevelDBSlice; - -class LevelDBComparator { - public: - virtual ~LevelDBComparator() {} - - virtual int Compare(const LevelDBSlice& a, const LevelDBSlice& b) const = 0; - virtual const char* Name() const = 0; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_COMPARATOR_H_ diff --git a/content/browser/indexed_db/leveldb/leveldb_database.cc b/content/browser/indexed_db/leveldb/leveldb_database.cc deleted file mode 100644 index b843230..0000000 --- a/content/browser/indexed_db/leveldb/leveldb_database.cc +++ /dev/null @@ -1,362 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/leveldb/leveldb_database.h" - -#include <string> - -#include "base/basictypes.h" -#include "base/logging.h" -#include "base/memory/scoped_ptr.h" -#include "base/metrics/histogram.h" -#include "base/string16.h" -#include "base/sys_info.h" -#include "base/utf_string_conversions.h" -#include "content/browser/indexed_db/leveldb/leveldb_comparator.h" -#include "content/browser/indexed_db/leveldb/leveldb_iterator.h" -#include "content/browser/indexed_db/leveldb/leveldb_slice.h" -#include "content/browser/indexed_db/leveldb/leveldb_write_batch.h" -#include "third_party/leveldatabase/env_idb.h" -#include "third_party/leveldatabase/src/helpers/memenv/memenv.h" -#include "third_party/leveldatabase/src/include/leveldb/comparator.h" -#include "third_party/leveldatabase/src/include/leveldb/db.h" -#include "third_party/leveldatabase/src/include/leveldb/env.h" -#include "third_party/leveldatabase/src/include/leveldb/slice.h" - -namespace content { - -static leveldb::Slice MakeSlice(const std::vector<char>& value) { - DCHECK_GT(value.size(), static_cast<size_t>(0)); - return leveldb::Slice(&*value.begin(), value.size()); -} - -static leveldb::Slice MakeSlice(const LevelDBSlice& s) { - return leveldb::Slice(s.begin(), s.end() - s.begin()); -} - -static LevelDBSlice MakeLevelDBSlice(const leveldb::Slice& s) { - return LevelDBSlice(s.data(), s.data() + s.size()); -} - -class ComparatorAdapter : public leveldb::Comparator { - public: - explicit ComparatorAdapter(const LevelDBComparator* comparator) - : comparator_(comparator) {} - - virtual int Compare(const leveldb::Slice& a, const leveldb::Slice& b) const - OVERRIDE { - return comparator_->Compare(MakeLevelDBSlice(a), MakeLevelDBSlice(b)); - } - - virtual const char* Name() const OVERRIDE { return comparator_->Name(); } - - // TODO(jsbell): Support the methods below in the future. - virtual void FindShortestSeparator(std::string* start, - const leveldb::Slice& limit) const - OVERRIDE {} - virtual void FindShortSuccessor(std::string* key) const OVERRIDE {} - - private: - const LevelDBComparator* comparator_; -}; - -LevelDBSnapshot::LevelDBSnapshot(LevelDBDatabase* db) - : db_(db->db_.get()), snapshot_(db_->GetSnapshot()) {} - -LevelDBSnapshot::~LevelDBSnapshot() { db_->ReleaseSnapshot(snapshot_); } - -LevelDBDatabase::LevelDBDatabase() {} - -LevelDBDatabase::~LevelDBDatabase() { - // db_'s destructor uses comparator_adapter_; order of deletion is important. - db_.reset(); - comparator_adapter_.reset(); - env_.reset(); -} - -static leveldb::Status OpenDB(leveldb::Comparator* comparator, - leveldb::Env* env, - const base::FilePath& path, - leveldb::DB** db) { - leveldb::Options options; - options.comparator = comparator; - options.create_if_missing = true; - options.paranoid_checks = true; - - // Marking compression as explicitly off so snappy support can be - // compiled in for other leveldb clients without implicitly enabling - // it for IndexedDB. http://crbug.com/81384 - options.compression = leveldb::kNoCompression; - - // 20 max_open_files is the minimum LevelDB allows but its cache behaves - // poorly with less than 4 files per shard. As of this writing the latest - // leveldb (1.9) hardcodes 16 shards. See - // https://code.google.com/p/chromium/issues/detail?id=227313#c11 - options.max_open_files = 80; - options.env = env; - - // ChromiumEnv assumes UTF8, converts back to FilePath before using. - return leveldb::DB::Open(options, path.AsUTF8Unsafe(), db); -} - -bool LevelDBDatabase::Destroy(const base::FilePath& file_name) { - leveldb::Options options; - options.env = leveldb::IDBEnv(); - // ChromiumEnv assumes UTF8, converts back to FilePath before using. - const leveldb::Status s = - leveldb::DestroyDB(file_name.AsUTF8Unsafe(), options); - return s.ok(); -} - -static void HistogramFreeSpace(const char* type, - const base::FilePath& file_name) { - string16 name = ASCIIToUTF16("WebCore.IndexedDB.LevelDB.Open") + - ASCIIToUTF16(type) + ASCIIToUTF16("FreeDiskSpace"); - int64 free_disk_space_in_k_bytes = - base::SysInfo::AmountOfFreeDiskSpace(file_name) / 1024; - if (free_disk_space_in_k_bytes < 0) { - base::Histogram::FactoryGet( - "WebCore.IndexedDB.LevelDB.FreeDiskSpaceFailure", - 1, - 2 /*boundary*/, - 2 /*boundary*/ + 1, - base::HistogramBase::kUmaTargetedHistogramFlag)->Add(1 /*sample*/); - return; - } - int clamped_disk_space_k_bytes = - free_disk_space_in_k_bytes > INT_MAX ? INT_MAX - : free_disk_space_in_k_bytes; - const uint64 histogram_max = static_cast<uint64>(1e9); - COMPILE_ASSERT(histogram_max <= INT_MAX, histogram_max_too_big); - base::Histogram::FactoryGet(UTF16ToUTF8(name), - 1, - histogram_max, - 11 /*buckets*/, - base::HistogramBase::kUmaTargetedHistogramFlag) - ->Add(clamped_disk_space_k_bytes); -} - -static void HistogramLevelDBError(const char* histogram_name, - const leveldb::Status& s) { - DCHECK(!s.ok()); - enum { - LEVEL_DB_NOT_FOUND, - LEVEL_DB_CORRUPTION, - LEVEL_DB_IO_ERROR, - LEVEL_DB_OTHER, - LEVEL_DB_MAX_ERROR - }; - int leveldb_error = LEVEL_DB_OTHER; - if (s.IsNotFound()) - leveldb_error = LEVEL_DB_NOT_FOUND; - else if (s.IsCorruption()) - leveldb_error = LEVEL_DB_CORRUPTION; - else if (s.IsIOError()) - leveldb_error = LEVEL_DB_IO_ERROR; - base::Histogram::FactoryGet(histogram_name, - 1, - LEVEL_DB_MAX_ERROR, - LEVEL_DB_MAX_ERROR + 1, - base::HistogramBase::kUmaTargetedHistogramFlag) - ->Add(leveldb_error); -} - -scoped_ptr<LevelDBDatabase> LevelDBDatabase::Open( - const base::FilePath& file_name, - const LevelDBComparator* comparator) { - scoped_ptr<ComparatorAdapter> comparator_adapter( - new ComparatorAdapter(comparator)); - - leveldb::DB* db; - const leveldb::Status s = - OpenDB(comparator_adapter.get(), leveldb::IDBEnv(), file_name, &db); - - if (!s.ok()) { - HistogramLevelDBError("WebCore.IndexedDB.LevelDBOpenErrors", s); - HistogramFreeSpace("Failure", file_name); - - LOG(ERROR) << "Failed to open LevelDB database from " - << file_name.AsUTF8Unsafe() << "," << s.ToString(); - return scoped_ptr<LevelDBDatabase>(); - } - - HistogramFreeSpace("Success", file_name); - - scoped_ptr<LevelDBDatabase> result(new LevelDBDatabase); - result->db_ = make_scoped_ptr(db); - result->comparator_adapter_ = comparator_adapter.Pass(); - result->comparator_ = comparator; - - return result.Pass(); -} - -scoped_ptr<LevelDBDatabase> LevelDBDatabase::OpenInMemory( - const LevelDBComparator* comparator) { - scoped_ptr<ComparatorAdapter> comparator_adapter( - new ComparatorAdapter(comparator)); - scoped_ptr<leveldb::Env> in_memory_env(leveldb::NewMemEnv(leveldb::IDBEnv())); - - leveldb::DB* db; - const leveldb::Status s = OpenDB( - comparator_adapter.get(), in_memory_env.get(), base::FilePath(), &db); - - if (!s.ok()) { - LOG(ERROR) << "Failed to open in-memory LevelDB database: " << s.ToString(); - return scoped_ptr<LevelDBDatabase>(); - } - - scoped_ptr<LevelDBDatabase> result(new LevelDBDatabase); - result->env_ = in_memory_env.Pass(); - result->db_ = make_scoped_ptr(db); - result->comparator_adapter_ = comparator_adapter.Pass(); - result->comparator_ = comparator; - - return result.Pass(); -} - -bool LevelDBDatabase::Put(const LevelDBSlice& key, - const std::vector<char>& value) { - leveldb::WriteOptions write_options; - write_options.sync = true; - - const leveldb::Status s = - db_->Put(write_options, MakeSlice(key), MakeSlice(value)); - if (s.ok()) - return true; - LOG(ERROR) << "LevelDB put failed: " << s.ToString(); - return false; -} - -bool LevelDBDatabase::Remove(const LevelDBSlice& key) { - leveldb::WriteOptions write_options; - write_options.sync = true; - - const leveldb::Status s = db_->Delete(write_options, MakeSlice(key)); - if (s.ok()) - return true; - if (s.IsNotFound()) - return false; - LOG(ERROR) << "LevelDB remove failed: " << s.ToString(); - return false; -} - -bool LevelDBDatabase::Get(const LevelDBSlice& key, - std::vector<char>& value, - bool& found, - const LevelDBSnapshot* snapshot) { - found = false; - std::string result; - leveldb::ReadOptions read_options; - read_options.verify_checksums = true; // TODO(jsbell): Disable this if the - // performance impact is too great. - read_options.snapshot = snapshot ? snapshot->snapshot_ : 0; - - const leveldb::Status s = db_->Get(read_options, MakeSlice(key), &result); - if (s.ok()) { - found = true; - value.clear(); - value.insert(value.end(), result.begin(), result.end()); - return true; - } - if (s.IsNotFound()) - return true; - LOG(ERROR) << "LevelDB get failed: " << s.ToString(); - return false; -} - -bool LevelDBDatabase::Write(LevelDBWriteBatch& write_batch) { - leveldb::WriteOptions write_options; - write_options.sync = true; - - const leveldb::Status s = - db_->Write(write_options, write_batch.write_batch_.get()); - if (s.ok()) - return true; - HistogramLevelDBError("WebCore.IndexedDB.LevelDBWriteErrors", s); - LOG(ERROR) << "LevelDB write failed: " << s.ToString(); - return false; -} - -namespace { -class IteratorImpl : public LevelDBIterator { - public: - virtual ~IteratorImpl() {} - - virtual bool IsValid() const OVERRIDE; - virtual void SeekToLast() OVERRIDE; - virtual void Seek(const LevelDBSlice& target) OVERRIDE; - virtual void Next() OVERRIDE; - virtual void Prev() OVERRIDE; - virtual LevelDBSlice Key() const OVERRIDE; - virtual LevelDBSlice Value() const OVERRIDE; - - private: - friend class content::LevelDBDatabase; - IteratorImpl(scoped_ptr<leveldb::Iterator> iterator); - void CheckStatus(); - - scoped_ptr<leveldb::Iterator> iterator_; -}; -} - -IteratorImpl::IteratorImpl(scoped_ptr<leveldb::Iterator> it) - : iterator_(it.Pass()) {} - -void IteratorImpl::CheckStatus() { - const leveldb::Status s = iterator_->status(); - if (!s.ok()) - LOG(ERROR) << "LevelDB iterator error: " << s.ToString(); -} - -bool IteratorImpl::IsValid() const { return iterator_->Valid(); } - -void IteratorImpl::SeekToLast() { - iterator_->SeekToLast(); - CheckStatus(); -} - -void IteratorImpl::Seek(const LevelDBSlice& target) { - iterator_->Seek(MakeSlice(target)); - CheckStatus(); -} - -void IteratorImpl::Next() { - DCHECK(IsValid()); - iterator_->Next(); - CheckStatus(); -} - -void IteratorImpl::Prev() { - DCHECK(IsValid()); - iterator_->Prev(); - CheckStatus(); -} - -LevelDBSlice IteratorImpl::Key() const { - DCHECK(IsValid()); - return MakeLevelDBSlice(iterator_->key()); -} - -LevelDBSlice IteratorImpl::Value() const { - DCHECK(IsValid()); - return MakeLevelDBSlice(iterator_->value()); -} - -scoped_ptr<LevelDBIterator> LevelDBDatabase::CreateIterator( - const LevelDBSnapshot* snapshot) { - leveldb::ReadOptions read_options; - read_options.verify_checksums = true; // TODO(jsbell): Disable this if the - // performance impact is too great. - read_options.snapshot = snapshot ? snapshot->snapshot_ : 0; - scoped_ptr<leveldb::Iterator> i(db_->NewIterator(read_options)); - if (!i) // TODO(jsbell): Double check if we actually need to check this. - return scoped_ptr<LevelDBIterator>(); - return scoped_ptr<LevelDBIterator>(new IteratorImpl(i.Pass())); -} - -const LevelDBComparator* LevelDBDatabase::Comparator() const { - return comparator_; -} - -} // namespace content diff --git a/content/browser/indexed_db/leveldb/leveldb_database.h b/content/browser/indexed_db/leveldb/leveldb_database.h deleted file mode 100644 index 0c7427b..0000000 --- a/content/browser/indexed_db/leveldb/leveldb_database.h +++ /dev/null @@ -1,75 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_DATABASE_H_ -#define CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_DATABASE_H_ - -#include <vector> - -#include "base/files/file_path.h" -#include "base/memory/scoped_ptr.h" -#include "base/string16.h" -#include "content/common/content_export.h" - -namespace leveldb { -class Comparator; -class DB; -class Env; -class Snapshot; -} - -namespace content { - -class LevelDBComparator; -class LevelDBDatabase; -class LevelDBIterator; -class LevelDBSlice; -class LevelDBWriteBatch; - -class LevelDBSnapshot { - private: - friend class LevelDBDatabase; - friend class LevelDBTransaction; - - explicit LevelDBSnapshot(LevelDBDatabase* db); - ~LevelDBSnapshot(); - - leveldb::DB* db_; - const leveldb::Snapshot* snapshot_; -}; - -class CONTENT_EXPORT LevelDBDatabase { - public: - static scoped_ptr<LevelDBDatabase> Open(const base::FilePath& file_name, - const LevelDBComparator* comparator); - static scoped_ptr<LevelDBDatabase> OpenInMemory( - const LevelDBComparator* comparator); - static bool Destroy(const base::FilePath& file_name); - virtual ~LevelDBDatabase(); - - bool Put(const LevelDBSlice& key, const std::vector<char>& value); - bool Remove(const LevelDBSlice& key); - virtual bool Get(const LevelDBSlice& key, - std::vector<char>& value, - bool& found, - const LevelDBSnapshot* = 0); - bool Write(LevelDBWriteBatch& batch); - scoped_ptr<LevelDBIterator> CreateIterator(const LevelDBSnapshot* = 0); - const LevelDBComparator* Comparator() const; - - protected: - LevelDBDatabase(); - - private: - friend class LevelDBSnapshot; - - scoped_ptr<leveldb::Env> env_; - scoped_ptr<leveldb::Comparator> comparator_adapter_; - scoped_ptr<leveldb::DB> db_; - const LevelDBComparator* comparator_; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_DATABASE_H_ diff --git a/content/browser/indexed_db/leveldb/leveldb_iterator.h b/content/browser/indexed_db/leveldb/leveldb_iterator.h deleted file mode 100644 index b78747f..0000000 --- a/content/browser/indexed_db/leveldb/leveldb_iterator.h +++ /dev/null @@ -1,26 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_ITERATOR_H_ -#define CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_ITERATOR_H_ - -#include "content/browser/indexed_db/leveldb/leveldb_slice.h" - -namespace content { - -class LevelDBIterator { - public: - virtual ~LevelDBIterator() {} - virtual bool IsValid() const = 0; - virtual void SeekToLast() = 0; - virtual void Seek(const LevelDBSlice& target) = 0; - virtual void Next() = 0; - virtual void Prev() = 0; - virtual LevelDBSlice Key() const = 0; - virtual LevelDBSlice Value() const = 0; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_ITERATOR_H_ diff --git a/content/browser/indexed_db/leveldb/leveldb_slice.h b/content/browser/indexed_db/leveldb/leveldb_slice.h deleted file mode 100644 index 7962b69..0000000 --- a/content/browser/indexed_db/leveldb/leveldb_slice.h +++ /dev/null @@ -1,38 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_SLICE_H_ -#define CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_SLICE_H_ - -#include <vector> - -#include "base/logging.h" - -namespace content { - -class LevelDBSlice { - public: - LevelDBSlice(const char* begin, const char* end) : begin_(begin), end_(end) { - DCHECK_GE(end_, begin_); - } - - explicit LevelDBSlice(const std::vector<char>& v) - : begin_(&*v.begin()), end_(&*v.rbegin() + 1) { - DCHECK_GT(v.size(), static_cast<size_t>(0)); - DCHECK_GE(end_, begin_); - } - - ~LevelDBSlice() {} - - const char* begin() const { return begin_; } - const char* end() const { return end_; } - - private: - const char* begin_; - const char* end_; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_SLICE_H_ diff --git a/content/browser/indexed_db/leveldb/leveldb_transaction.cc b/content/browser/indexed_db/leveldb/leveldb_transaction.cc deleted file mode 100644 index a8b3a3d..0000000 --- a/content/browser/indexed_db/leveldb/leveldb_transaction.cc +++ /dev/null @@ -1,490 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/leveldb/leveldb_transaction.h" - -#include "base/logging.h" -#include "content/browser/indexed_db/leveldb/leveldb_database.h" -#include "content/browser/indexed_db/leveldb/leveldb_slice.h" -#include "content/browser/indexed_db/leveldb/leveldb_write_batch.h" -#include "third_party/leveldatabase/src/include/leveldb/db.h" - -namespace content { - -scoped_refptr<LevelDBTransaction> LevelDBTransaction::Create( - LevelDBDatabase* db) { - return make_scoped_refptr(new LevelDBTransaction(db)); -} - -LevelDBTransaction::LevelDBTransaction(LevelDBDatabase* db) - : db_(db), snapshot_(db), comparator_(db->Comparator()), finished_(false) { - tree_.abstractor().comparator_ = comparator_; -} - -LevelDBTransaction::AVLTreeNode::AVLTreeNode() {} -LevelDBTransaction::AVLTreeNode::~AVLTreeNode() {} - -void LevelDBTransaction::ClearTree() { - TreeType::Iterator iterator; - iterator.start_iter_least(tree_); - - std::vector<AVLTreeNode*> nodes; - - while (*iterator) { - nodes.push_back(*iterator); - ++iterator; - } - tree_.purge(); - - for (size_t i = 0; i < nodes.size(); ++i) - delete nodes[i]; -} - -LevelDBTransaction::~LevelDBTransaction() { ClearTree(); } - -static void InitVector(const LevelDBSlice& slice, std::vector<char>* vector) { - vector->clear(); - vector->insert(vector->end(), slice.begin(), slice.end()); -} - -void LevelDBTransaction::Set(const LevelDBSlice& key, - const std::vector<char>& value, - bool deleted) { - DCHECK(!finished_); - bool new_node = false; - AVLTreeNode* node = tree_.search(key); - - if (!node) { - node = new AVLTreeNode; - InitVector(key, &node->key); - tree_.insert(node); - new_node = true; - } - node->value = value; - node->deleted = deleted; - - if (new_node) - NotifyIteratorsOfTreeChange(); -} - -void LevelDBTransaction::Put(const LevelDBSlice& key, - const std::vector<char>& value) { - Set(key, value, false); -} - -void LevelDBTransaction::Remove(const LevelDBSlice& key) { - Set(key, std::vector<char>(), true); -} - -bool LevelDBTransaction::Get(const LevelDBSlice& key, - std::vector<char>& value, - bool& found) { - found = false; - DCHECK(!finished_); - AVLTreeNode* node = tree_.search(key); - - if (node) { - if (node->deleted) - return true; - - value = node->value; - found = true; - return true; - } - - bool ok = db_->Get(key, value, found, &snapshot_); - if (!ok) { - DCHECK(!found); - return false; - } - return true; -} - -bool LevelDBTransaction::Commit() { - DCHECK(!finished_); - - if (tree_.is_empty()) { - finished_ = true; - return true; - } - - scoped_ptr<LevelDBWriteBatch> write_batch = LevelDBWriteBatch::Create(); - - TreeType::Iterator iterator; - iterator.start_iter_least(tree_); - - while (*iterator) { - AVLTreeNode* node = *iterator; - if (!node->deleted) - write_batch->Put(LevelDBSlice(node->key), LevelDBSlice(node->value)); - else - write_batch->Remove(LevelDBSlice(node->key)); - ++iterator; - } - - if (!db_->Write(*write_batch)) - return false; - - ClearTree(); - finished_ = true; - return true; -} - -void LevelDBTransaction::Rollback() { - DCHECK(!finished_); - finished_ = true; - ClearTree(); -} - -scoped_ptr<LevelDBIterator> LevelDBTransaction::CreateIterator() { - return TransactionIterator::Create(this).PassAs<LevelDBIterator>(); -} - -scoped_ptr<LevelDBTransaction::TreeIterator> -LevelDBTransaction::TreeIterator::Create(LevelDBTransaction* transaction) { - return make_scoped_ptr(new TreeIterator(transaction)); -} - -bool LevelDBTransaction::TreeIterator::IsValid() const { return !!*iterator_; } - -void LevelDBTransaction::TreeIterator::SeekToLast() { - iterator_.start_iter_greatest(*tree_); - if (IsValid()) - key_ = (*iterator_)->key; -} - -void LevelDBTransaction::TreeIterator::Seek(const LevelDBSlice& target) { - iterator_.start_iter(*tree_, target, TreeType::EQUAL); - if (!IsValid()) - iterator_.start_iter(*tree_, target, TreeType::GREATER); - - if (IsValid()) - key_ = (*iterator_)->key; -} - -void LevelDBTransaction::TreeIterator::Next() { - DCHECK(IsValid()); - ++iterator_; - if (IsValid()) { - DCHECK(transaction_->comparator_->Compare(LevelDBSlice((*iterator_)->key), - LevelDBSlice(key_)) > - 0); - (void) transaction_; - key_ = (*iterator_)->key; - } -} - -void LevelDBTransaction::TreeIterator::Prev() { - DCHECK(IsValid()); - --iterator_; - if (IsValid()) { - DCHECK(tree_->abstractor().comparator_->Compare( - LevelDBSlice((*iterator_)->key), LevelDBSlice(key_)) < - 0); - key_ = (*iterator_)->key; - } -} - -LevelDBSlice LevelDBTransaction::TreeIterator::Key() const { - DCHECK(IsValid()); - return LevelDBSlice(key_); -} - -LevelDBSlice LevelDBTransaction::TreeIterator::Value() const { - DCHECK(IsValid()); - DCHECK(!IsDeleted()); - return LevelDBSlice((*iterator_)->value); -} - -bool LevelDBTransaction::TreeIterator::IsDeleted() const { - DCHECK(IsValid()); - return (*iterator_)->deleted; -} - -void LevelDBTransaction::TreeIterator::Reset() { - DCHECK(IsValid()); - iterator_.start_iter(*tree_, LevelDBSlice(key_), TreeType::EQUAL); - DCHECK(IsValid()); -} - -LevelDBTransaction::TreeIterator::~TreeIterator() {} - -LevelDBTransaction::TreeIterator::TreeIterator(LevelDBTransaction* transaction) - : tree_(&transaction->tree_), transaction_(transaction) {} - -scoped_ptr<LevelDBTransaction::TransactionIterator> -LevelDBTransaction::TransactionIterator::Create( - scoped_refptr<LevelDBTransaction> transaction) { - return make_scoped_ptr(new TransactionIterator(transaction)); -} - -LevelDBTransaction::TransactionIterator::TransactionIterator( - scoped_refptr<LevelDBTransaction> transaction) - : transaction_(transaction), - comparator_(transaction_->comparator_), - tree_iterator_(TreeIterator::Create(transaction_.get())), - db_iterator_(transaction_->db_->CreateIterator(&transaction_->snapshot_)), - current_(0), - direction_(FORWARD), - tree_changed_(false) { - transaction_->RegisterIterator(this); -} - -LevelDBTransaction::TransactionIterator::~TransactionIterator() { - transaction_->UnregisterIterator(this); -} - -bool LevelDBTransaction::TransactionIterator::IsValid() const { - return !!current_; -} - -void LevelDBTransaction::TransactionIterator::SeekToLast() { - tree_iterator_->SeekToLast(); - db_iterator_->SeekToLast(); - direction_ = REVERSE; - - HandleConflictsAndDeletes(); - SetCurrentIteratorToLargestKey(); -} - -void LevelDBTransaction::TransactionIterator::Seek(const LevelDBSlice& target) { - tree_iterator_->Seek(target); - db_iterator_->Seek(target); - direction_ = FORWARD; - - HandleConflictsAndDeletes(); - SetCurrentIteratorToSmallestKey(); -} - -void LevelDBTransaction::TransactionIterator::Next() { - DCHECK(IsValid()); - if (tree_changed_) - RefreshTreeIterator(); - - if (direction_ != FORWARD) { - // Ensure the non-current iterator is positioned after Key(). - - LevelDBIterator* non_current = - (current_ == db_iterator_.get()) ? tree_iterator_.get() - : db_iterator_.get(); - - non_current->Seek(Key()); - if (non_current->IsValid() && - !comparator_->Compare(non_current->Key(), Key())) - non_current->Next(); // Take an extra step so the non-current key is - // strictly greater than Key(). - - DCHECK(!non_current->IsValid() || - comparator_->Compare(non_current->Key(), Key()) > 0); - - direction_ = FORWARD; - } - - current_->Next(); - HandleConflictsAndDeletes(); - SetCurrentIteratorToSmallestKey(); -} - -void LevelDBTransaction::TransactionIterator::Prev() { - DCHECK(IsValid()); - if (tree_changed_) - RefreshTreeIterator(); - - if (direction_ != REVERSE) { - // Ensure the non-current iterator is positioned before Key(). - - LevelDBIterator* non_current = - (current_ == db_iterator_.get()) ? tree_iterator_.get() - : db_iterator_.get(); - - non_current->Seek(Key()); - if (non_current->IsValid()) { - // Iterator is at first entry >= Key(). - // Step back once to entry < key. - // This is why we don't check for the keys being the same before - // stepping, like we do in Next() above. - non_current->Prev(); - } else { - non_current->SeekToLast(); // Iterator has no entries >= Key(). Position - // at last entry. - } - DCHECK(!non_current->IsValid() || - comparator_->Compare(non_current->Key(), Key()) < 0); - - direction_ = REVERSE; - } - - current_->Prev(); - HandleConflictsAndDeletes(); - SetCurrentIteratorToLargestKey(); -} - -LevelDBSlice LevelDBTransaction::TransactionIterator::Key() const { - DCHECK(IsValid()); - if (tree_changed_) - RefreshTreeIterator(); - return current_->Key(); -} - -LevelDBSlice LevelDBTransaction::TransactionIterator::Value() const { - DCHECK(IsValid()); - if (tree_changed_) - RefreshTreeIterator(); - return current_->Value(); -} - -void LevelDBTransaction::TransactionIterator::TreeChanged() { - tree_changed_ = true; -} - -void LevelDBTransaction::TransactionIterator::RefreshTreeIterator() const { - DCHECK(tree_changed_); - - tree_changed_ = false; - - if (tree_iterator_->IsValid() && tree_iterator_.get() == current_) { - tree_iterator_->Reset(); - return; - } - - if (db_iterator_->IsValid()) { - - // There could be new nodes in the tree that we should iterate over. - - if (direction_ == FORWARD) { - // Try to seek tree iterator to something greater than the db iterator. - tree_iterator_->Seek(db_iterator_->Key()); - if (tree_iterator_->IsValid() && - !comparator_->Compare(tree_iterator_->Key(), db_iterator_->Key())) - tree_iterator_->Next(); // If equal, take another step so the tree - // iterator is strictly greater. - } else { - // If going backward, seek to a key less than the db iterator. - DCHECK_EQ(REVERSE, direction_); - tree_iterator_->Seek(db_iterator_->Key()); - if (tree_iterator_->IsValid()) - tree_iterator_->Prev(); - } - } -} - -bool LevelDBTransaction::TransactionIterator::TreeIteratorIsLower() const { - return comparator_->Compare(tree_iterator_->Key(), db_iterator_->Key()) < 0; -} - -bool LevelDBTransaction::TransactionIterator::TreeIteratorIsHigher() const { - return comparator_->Compare(tree_iterator_->Key(), db_iterator_->Key()) > 0; -} - -void LevelDBTransaction::TransactionIterator::HandleConflictsAndDeletes() { - bool loop = true; - - while (loop) { - loop = false; - - if (tree_iterator_->IsValid() && db_iterator_->IsValid() && - !comparator_->Compare(tree_iterator_->Key(), db_iterator_->Key())) { - // For equal keys, the tree iterator takes precedence, so move the - // database iterator another step. - if (direction_ == FORWARD) - db_iterator_->Next(); - else - db_iterator_->Prev(); - } - - // Skip over delete markers in the tree iterator until it catches up with - // the db iterator. - if (tree_iterator_->IsValid() && tree_iterator_->IsDeleted()) { - if (direction_ == FORWARD && - (!db_iterator_->IsValid() || TreeIteratorIsLower())) { - tree_iterator_->Next(); - loop = true; - } else if (direction_ == REVERSE && - (!db_iterator_->IsValid() || TreeIteratorIsHigher())) { - tree_iterator_->Prev(); - loop = true; - } - } - } -} - -void -LevelDBTransaction::TransactionIterator::SetCurrentIteratorToSmallestKey() { - LevelDBIterator* smallest = 0; - - if (tree_iterator_->IsValid()) - smallest = tree_iterator_.get(); - - if (db_iterator_->IsValid()) { - if (!smallest || - comparator_->Compare(db_iterator_->Key(), smallest->Key()) < 0) - smallest = db_iterator_.get(); - } - - current_ = smallest; -} - -void LevelDBTransaction::TransactionIterator::SetCurrentIteratorToLargestKey() { - LevelDBIterator* largest = 0; - - if (tree_iterator_->IsValid()) - largest = tree_iterator_.get(); - - if (db_iterator_->IsValid()) { - if (!largest || - comparator_->Compare(db_iterator_->Key(), largest->Key()) > 0) - largest = db_iterator_.get(); - } - - current_ = largest; -} - -void LevelDBTransaction::RegisterIterator(TransactionIterator* iterator) { - DCHECK(iterators_.find(iterator) == iterators_.end()); - iterators_.insert(iterator); -} - -void LevelDBTransaction::UnregisterIterator(TransactionIterator* iterator) { - DCHECK(iterators_.find(iterator) != iterators_.end()); - iterators_.erase(iterator); -} - -void LevelDBTransaction::NotifyIteratorsOfTreeChange() { - for (std::set<TransactionIterator*>::iterator i = iterators_.begin(); - i != iterators_.end(); - ++i) { - TransactionIterator* transaction_iterator = *i; - transaction_iterator->TreeChanged(); - } -} - -scoped_ptr<LevelDBWriteOnlyTransaction> LevelDBWriteOnlyTransaction::Create( - LevelDBDatabase* db) { - return make_scoped_ptr(new LevelDBWriteOnlyTransaction(db)); -} - -LevelDBWriteOnlyTransaction::LevelDBWriteOnlyTransaction(LevelDBDatabase* db) - : db_(db), write_batch_(LevelDBWriteBatch::Create()), finished_(false) {} - -LevelDBWriteOnlyTransaction::~LevelDBWriteOnlyTransaction() { - write_batch_->Clear(); -} - -void LevelDBWriteOnlyTransaction::Remove(const LevelDBSlice& key) { - DCHECK(!finished_); - write_batch_->Remove(key); -} - -bool LevelDBWriteOnlyTransaction::Commit() { - DCHECK(!finished_); - - if (!db_->Write(*write_batch_)) - return false; - - finished_ = true; - write_batch_->Clear(); - return true; -} - -} // namespace content diff --git a/content/browser/indexed_db/leveldb/leveldb_transaction.h b/content/browser/indexed_db/leveldb/leveldb_transaction.h deleted file mode 100644 index 39d1a30..0000000 --- a/content/browser/indexed_db/leveldb/leveldb_transaction.h +++ /dev/null @@ -1,179 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_TRANSACTION_H_ -#define CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_TRANSACTION_H_ - -#include <set> -#include <vector> - -#include "base/memory/ref_counted.h" -#include "base/memory/scoped_ptr.h" -#include "content/browser/indexed_db/leveldb/avltree.h" -#include "content/browser/indexed_db/leveldb/leveldb_comparator.h" -#include "content/browser/indexed_db/leveldb/leveldb_database.h" -#include "content/browser/indexed_db/leveldb/leveldb_iterator.h" -#include "content/browser/indexed_db/leveldb/leveldb_slice.h" - -namespace content { - -class LevelDBWriteBatch; - -class CONTENT_EXPORT LevelDBTransaction - : public base::RefCounted<LevelDBTransaction> { - public: - static scoped_refptr<LevelDBTransaction> Create(LevelDBDatabase* db); - - void Put(const LevelDBSlice& key, const std::vector<char>& value); - void Remove(const LevelDBSlice& key); - bool Get(const LevelDBSlice& key, std::vector<char>& value, bool& found); - bool Commit(); - void Rollback(); - - scoped_ptr<LevelDBIterator> CreateIterator(); - - private: - LevelDBTransaction(LevelDBDatabase* db); - virtual ~LevelDBTransaction(); - friend class base::RefCounted<LevelDBTransaction>; - - struct AVLTreeNode { - AVLTreeNode(); - ~AVLTreeNode(); - std::vector<char> key; - std::vector<char> value; - bool deleted; - - AVLTreeNode* less; - AVLTreeNode* greater; - int balance_factor; - DISALLOW_COPY_AND_ASSIGN(AVLTreeNode); - }; - - struct AVLTreeAbstractor { - typedef AVLTreeNode* handle; - typedef size_t size; - typedef LevelDBSlice key; - - handle get_less(handle h) { return h->less; } - void set_less(handle h, handle less) { h->less = less; } - handle get_greater(handle h) { return h->greater; } - void set_greater(handle h, handle greater) { h->greater = greater; } - - int get_balance_factor(handle h) { return h->balance_factor; } - void set_balance_factor(handle h, int bf) { h->balance_factor = bf; } - - int compare_key_key(const key& ka, const key& kb) { - return comparator_->Compare(ka, kb); - } - int compare_key_node(const key& k, handle h) { - return compare_key_key(k, key(h->key)); - } - int compare_node_node(handle ha, handle hb) { - return compare_key_key(key(ha->key), key(hb->key)); - } - - static handle null() { return 0; } - - const LevelDBComparator* comparator_; - }; - - typedef AVLTree<AVLTreeAbstractor> TreeType; - - class TreeIterator : public LevelDBIterator { - public: - static scoped_ptr<TreeIterator> Create(LevelDBTransaction* transaction); - virtual ~TreeIterator(); - - virtual bool IsValid() const OVERRIDE; - virtual void SeekToLast() OVERRIDE; - virtual void Seek(const LevelDBSlice& slice) OVERRIDE; - virtual void Next() OVERRIDE; - virtual void Prev() OVERRIDE; - virtual LevelDBSlice Key() const OVERRIDE; - virtual LevelDBSlice Value() const OVERRIDE; - bool IsDeleted() const; - void Reset(); - - private: - TreeIterator(LevelDBTransaction* transaction); - mutable TreeType::Iterator iterator_; // Dereferencing this is non-const. - TreeType* tree_; - LevelDBTransaction* transaction_; - std::vector<char> key_; - }; - - class TransactionIterator : public LevelDBIterator { - public: - virtual ~TransactionIterator(); - static scoped_ptr<TransactionIterator> Create( - scoped_refptr<LevelDBTransaction> transaction); - - virtual bool IsValid() const OVERRIDE; - virtual void SeekToLast() OVERRIDE; - virtual void Seek(const LevelDBSlice& target) OVERRIDE; - virtual void Next() OVERRIDE; - virtual void Prev() OVERRIDE; - virtual LevelDBSlice Key() const OVERRIDE; - virtual LevelDBSlice Value() const OVERRIDE; - void TreeChanged(); - - private: - TransactionIterator(scoped_refptr<LevelDBTransaction> transaction); - void HandleConflictsAndDeletes(); - void SetCurrentIteratorToSmallestKey(); - void SetCurrentIteratorToLargestKey(); - void RefreshTreeIterator() const; - bool TreeIteratorIsLower() const; - bool TreeIteratorIsHigher() const; - - scoped_refptr<LevelDBTransaction> transaction_; - const LevelDBComparator* comparator_; - mutable scoped_ptr<TreeIterator> tree_iterator_; - scoped_ptr<LevelDBIterator> db_iterator_; - LevelDBIterator* current_; - - enum Direction { - FORWARD, - REVERSE - }; - Direction direction_; - mutable bool tree_changed_; - }; - - void Set(const LevelDBSlice& key, - const std::vector<char>& value, - bool deleted); - void ClearTree(); - void RegisterIterator(TransactionIterator* iterator); - void UnregisterIterator(TransactionIterator* iterator); - void NotifyIteratorsOfTreeChange(); - - LevelDBDatabase* db_; - const LevelDBSnapshot snapshot_; - const LevelDBComparator* comparator_; - TreeType tree_; - bool finished_; - std::set<TransactionIterator*> iterators_; -}; - -class LevelDBWriteOnlyTransaction { - public: - static scoped_ptr<LevelDBWriteOnlyTransaction> Create(LevelDBDatabase* db); - - ~LevelDBWriteOnlyTransaction(); - void Remove(const LevelDBSlice& key); - bool Commit(); - - private: - LevelDBWriteOnlyTransaction(LevelDBDatabase* db); - - LevelDBDatabase* db_; - scoped_ptr<LevelDBWriteBatch> write_batch_; - bool finished_; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_TRANSACTION_H_ diff --git a/content/browser/indexed_db/leveldb/leveldb_unittest.cc b/content/browser/indexed_db/leveldb/leveldb_unittest.cc deleted file mode 100644 index 6508e09..0000000 --- a/content/browser/indexed_db/leveldb/leveldb_unittest.cc +++ /dev/null @@ -1,193 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include <algorithm> -#include <cstring> -#include <vector> - -#include "base/files/file_path.h" -#include "base/files/scoped_temp_dir.h" -#include "base/platform_file.h" -#include "base/string16.h" -#include "content/browser/indexed_db/leveldb/leveldb_comparator.h" -#include "content/browser/indexed_db/leveldb/leveldb_database.h" -#include "content/browser/indexed_db/leveldb/leveldb_iterator.h" -#include "content/browser/indexed_db/leveldb/leveldb_slice.h" -#include "content/browser/indexed_db/leveldb/leveldb_transaction.h" -#include "testing/gtest/include/gtest/gtest.h" - -namespace content { - -namespace { - -class SimpleComparator : public LevelDBComparator { - public: - virtual int Compare(const LevelDBSlice& a, const LevelDBSlice& b) const - OVERRIDE { - size_t len = std::min(a.end() - a.begin(), b.end() - b.begin()); - return memcmp(a.begin(), b.begin(), len); - } - virtual const char* Name() const OVERRIDE { return "temp_comparator"; } -}; - -std::vector<char> EncodeString(const std::string& s) { - std::vector<char> ret(s.size()); - for (size_t i = 0; i < s.size(); ++i) - ret[i] = s[i]; - return ret; -} - -TEST(LevelDBDatabaseTest, CorruptionTest) { - base::ScopedTempDir temp_directory; - ASSERT_TRUE(temp_directory.CreateUniqueTempDir()); - - const std::vector<char> key = EncodeString("key"); - const std::vector<char> put_value = EncodeString("value"); - std::vector<char> got_value; - SimpleComparator comparator; - - scoped_ptr<LevelDBDatabase> leveldb = - LevelDBDatabase::Open(temp_directory.path(), &comparator); - EXPECT_TRUE(leveldb); - bool success = leveldb->Put(LevelDBSlice(key), put_value); - EXPECT_TRUE(success); - leveldb.Pass(); - EXPECT_FALSE(leveldb); - - leveldb = LevelDBDatabase::Open(temp_directory.path(), &comparator); - EXPECT_TRUE(leveldb); - bool found = false; - success = leveldb->Get(LevelDBSlice(key), got_value, found); - EXPECT_TRUE(success); - EXPECT_TRUE(found); - EXPECT_EQ(put_value, got_value); - leveldb.Pass(); - EXPECT_FALSE(leveldb); - - base::FilePath file_path = temp_directory.path().AppendASCII("CURRENT"); - base::PlatformFile handle = base::CreatePlatformFile( - file_path, - base::PLATFORM_FILE_OPEN | base::PLATFORM_FILE_WRITE, - NULL, - NULL); - base::TruncatePlatformFile(handle, 0); - base::ClosePlatformFile(handle); - - leveldb = LevelDBDatabase::Open(temp_directory.path(), &comparator); - EXPECT_FALSE(leveldb); - - bool destroyed = LevelDBDatabase::Destroy(temp_directory.path()); - EXPECT_TRUE(destroyed); - - leveldb = LevelDBDatabase::Open(temp_directory.path(), &comparator); - EXPECT_TRUE(leveldb); - success = leveldb->Get(LevelDBSlice(key), got_value, found); - EXPECT_TRUE(success); - EXPECT_FALSE(found); -} - -TEST(LevelDBDatabaseTest, Transaction) { - base::ScopedTempDir temp_directory; - ASSERT_TRUE(temp_directory.CreateUniqueTempDir()); - - const std::vector<char> key = EncodeString("key"); - std::vector<char> got_value; - SimpleComparator comparator; - - scoped_ptr<LevelDBDatabase> leveldb = - LevelDBDatabase::Open(temp_directory.path(), &comparator); - EXPECT_TRUE(leveldb); - - const std::vector<char> old_value = EncodeString("value"); - bool success = leveldb->Put(LevelDBSlice(key), old_value); - EXPECT_TRUE(success); - - scoped_refptr<LevelDBTransaction> transaction = - LevelDBTransaction::Create(leveldb.get()); - - const std::vector<char> new_value = EncodeString("new value"); - success = leveldb->Put(LevelDBSlice(key), new_value); - EXPECT_TRUE(success); - - bool found = false; - success = transaction->Get(LevelDBSlice(key), got_value, found); - EXPECT_TRUE(success); - EXPECT_TRUE(found); - EXPECT_EQ( - comparator.Compare(LevelDBSlice(got_value), LevelDBSlice(old_value)), 0); - - found = false; - success = leveldb->Get(LevelDBSlice(key), got_value, found); - EXPECT_TRUE(success); - EXPECT_TRUE(found); - EXPECT_EQ( - comparator.Compare(LevelDBSlice(got_value), LevelDBSlice(new_value)), 0); - - const std::vector<char> added_key = EncodeString("added key"); - const std::vector<char> added_value = EncodeString("added value"); - success = leveldb->Put(LevelDBSlice(added_key), added_value); - EXPECT_TRUE(success); - - success = leveldb->Get(LevelDBSlice(added_key), got_value, found); - EXPECT_TRUE(success); - EXPECT_TRUE(found); - EXPECT_EQ( - comparator.Compare(LevelDBSlice(got_value), LevelDBSlice(added_value)), - 0); - - success = transaction->Get(LevelDBSlice(added_key), got_value, found); - EXPECT_TRUE(success); - EXPECT_FALSE(found); -} - -TEST(LevelDBDatabaseTest, TransactionIterator) { - base::ScopedTempDir temp_directory; - ASSERT_TRUE(temp_directory.CreateUniqueTempDir()); - - const std::vector<char> key1 = EncodeString("key1"); - const std::vector<char> value1 = EncodeString("value1"); - const std::vector<char> key2 = EncodeString("key2"); - const std::vector<char> value2 = EncodeString("value2"); - - SimpleComparator comparator; - bool success; - - scoped_ptr<LevelDBDatabase> leveldb = - LevelDBDatabase::Open(temp_directory.path(), &comparator); - EXPECT_TRUE(leveldb); - - success = leveldb->Put(LevelDBSlice(key1), value1); - EXPECT_TRUE(success); - success = leveldb->Put(LevelDBSlice(key2), value2); - EXPECT_TRUE(success); - - scoped_refptr<LevelDBTransaction> transaction = - LevelDBTransaction::Create(leveldb.get()); - - success = leveldb->Remove(LevelDBSlice(key2)); - EXPECT_TRUE(success); - - scoped_ptr<LevelDBIterator> it = transaction->CreateIterator(); - - const char empty[] = { 0 }; - it->Seek(LevelDBSlice(empty, empty)); - - EXPECT_TRUE(it->IsValid()); - EXPECT_EQ(comparator.Compare(LevelDBSlice(it->Key()), LevelDBSlice(key1)), 0); - EXPECT_EQ(comparator.Compare(it->Value(), LevelDBSlice(value1)), 0); - - it->Next(); - - EXPECT_TRUE(it->IsValid()); - EXPECT_EQ(comparator.Compare(it->Key(), LevelDBSlice(key2)), 0); - EXPECT_EQ(comparator.Compare(it->Value(), LevelDBSlice(value2)), 0); - - it->Next(); - - EXPECT_FALSE(it->IsValid()); -} - -} // namespace - -} // namespace content diff --git a/content/browser/indexed_db/leveldb/leveldb_write_batch.cc b/content/browser/indexed_db/leveldb/leveldb_write_batch.cc deleted file mode 100644 index b15c4fa..0000000 --- a/content/browser/indexed_db/leveldb/leveldb_write_batch.cc +++ /dev/null @@ -1,37 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/leveldb/leveldb_write_batch.h" - -#include "content/browser/indexed_db/leveldb/leveldb_slice.h" -#include "third_party/leveldatabase/src/include/leveldb/slice.h" -#include "third_party/leveldatabase/src/include/leveldb/write_batch.h" - -namespace content { - -scoped_ptr<LevelDBWriteBatch> LevelDBWriteBatch::Create() { - return make_scoped_ptr(new LevelDBWriteBatch); -} - -LevelDBWriteBatch::LevelDBWriteBatch() - : write_batch_(new leveldb::WriteBatch) {} - -LevelDBWriteBatch::~LevelDBWriteBatch() {} - -static leveldb::Slice MakeSlice(const LevelDBSlice& s) { - return leveldb::Slice(s.begin(), s.end() - s.begin()); -} - -void LevelDBWriteBatch::Put(const LevelDBSlice& key, - const LevelDBSlice& value) { - write_batch_->Put(MakeSlice(key), MakeSlice(value)); -} - -void LevelDBWriteBatch::Remove(const LevelDBSlice& key) { - write_batch_->Delete(MakeSlice(key)); -} - -void LevelDBWriteBatch::Clear() { write_batch_->Clear(); } - -} // namespace content diff --git a/content/browser/indexed_db/leveldb/leveldb_write_batch.h b/content/browser/indexed_db/leveldb/leveldb_write_batch.h deleted file mode 100644 index 2849687..0000000 --- a/content/browser/indexed_db/leveldb/leveldb_write_batch.h +++ /dev/null @@ -1,38 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_WRITE_BATCH_H_ -#define CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_WRITE_BATCH_H_ - -#include "base/memory/scoped_ptr.h" - -namespace leveldb { -class WriteBatch; -} - -namespace content { - -class LevelDBSlice; - -// Wrapper around leveldb::WriteBatch. -// This class holds a collection of updates to apply atomically to a database. -class LevelDBWriteBatch { - public: - static scoped_ptr<LevelDBWriteBatch> Create(); - ~LevelDBWriteBatch(); - - void Put(const LevelDBSlice& key, const LevelDBSlice& value); - void Remove(const LevelDBSlice& key); // Add remove operation to the batch. - void Clear(); - - private: - friend class LevelDBDatabase; - LevelDBWriteBatch(); - - scoped_ptr<leveldb::WriteBatch> write_batch_; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_LEVELDB_LEVELDB_WRITE_BATCH_H_ diff --git a/content/browser/indexed_db/list_set.h b/content/browser/indexed_db/list_set.h deleted file mode 100644 index 2ddd65d..0000000 --- a/content/browser/indexed_db/list_set.h +++ /dev/null @@ -1,158 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_LIST_SET_H_ -#define CONTENT_BROWSER_INDEXED_DB_LIST_SET_H_ - -#include <algorithm> -#include <iterator> -#include <list> -#include <set> -#include "base/logging.h" -#include "base/memory/scoped_ptr.h" - -// -// A container class that provides fast containment test (like a set) -// but maintains insertion order for iteration (like list). -// -// Member types of value (primitives and objects by value), raw pointers -// and scoped_refptr<> are supported. -// -template <typename T> class list_set { - public: - list_set() {} - list_set(const list_set<T>& other) : list_(other.list_), set_(other.set_) {} - list_set& operator=(const list_set<T>& other) { - list_ = other.list_; - set_ = other.set_; - return *this; - } - - void insert(const T& elem) { - if (set_.find(elem) != set_.end()) - return; - set_.insert(elem); - list_.push_back(elem); - } - - void erase(const T& elem) { - if (set_.find(elem) == set_.end()) - return; - set_.erase(elem); - typename std::list<T>::iterator it = - std::find(list_.begin(), list_.end(), elem); - DCHECK(it != list_.end()); - list_.erase(it); - } - - bool has(const T& elem) { return set_.find(elem) != set_.end(); } - - size_t size() const { - DCHECK_EQ(list_.size(), set_.size()); - return set_.size(); - } - - bool empty() const { - DCHECK_EQ(list_.empty(), set_.empty()); - return set_.empty(); - } - - class const_iterator; - - class iterator { - public: - typedef iterator self_type; - typedef T value_type; - typedef T& reference; - typedef T* pointer; - typedef std::bidirectional_iterator_tag iterator_category; - typedef std::ptrdiff_t difference_type; - - inline iterator(typename std::list<T>::iterator it) : it_(it) {} - inline self_type& operator++() { - ++it_; - return *this; - } - inline self_type operator++(int) { - self_type result(*this); - ++(*this); - return result; - } - inline self_type& operator--() { - --it_; - return *this; - } - inline self_type operator--(int) { - self_type result(*this); - --(*this); - return result; - } - inline value_type& operator*() { return *it_; } - inline value_type* operator->() { return &(*it_); } - inline bool operator==(const iterator& rhs) const { return it_ == rhs.it_; } - inline bool operator!=(const iterator& rhs) const { return it_ != rhs.it_; } - - inline operator const_iterator() const { return const_iterator(it_); } - - private: - typename std::list<T>::iterator it_; - }; - - class const_iterator { - public: - typedef const_iterator self_type; - typedef T value_type; - typedef T& reference; - typedef T* pointer; - typedef std::bidirectional_iterator_tag iterator_category; - typedef std::ptrdiff_t difference_type; - - inline const_iterator(typename std::list<T>::const_iterator it) : it_(it) {} - inline self_type& operator++() { - ++it_; - return *this; - } - inline self_type operator++(int) { - self_type result(*this); - ++(*this); - return result; - } - inline self_type& operator--() { - --it_; - return *this; - } - inline self_type operator--(int) { - self_type result(*this); - --(*this); - return result; - } - inline const value_type& operator*() { return *it_; } - inline const value_type* operator->() { return &(*it_); } - inline bool operator==(const const_iterator& rhs) const { - return it_ == rhs.it_; - } - inline bool operator!=(const const_iterator& rhs) const { - return it_ != rhs.it_; - } - - private: - typename std::list<T>::const_iterator it_; - }; - - iterator begin() { return iterator(list_.begin()); } - iterator end() { return iterator(list_.end()); } - const_iterator begin() const { return const_iterator(list_.begin()); } - const_iterator end() const { return const_iterator(list_.end()); } - - private: - std::list<T> list_; - std::set<T> set_; -}; - -// Prevent instantiation of list_set<scoped_ptr<T>> as the current -// implementation would fail. -// TODO(jsbell): Support scoped_ptr through specialization. -template <typename T> class list_set<scoped_ptr<T> >; - -#endif // CONTENT_BROWSER_INDEXED_DB_LIST_SET_H_ diff --git a/content/browser/indexed_db/list_set_unittest.cc b/content/browser/indexed_db/list_set_unittest.cc deleted file mode 100644 index af5d8cf..0000000 --- a/content/browser/indexed_db/list_set_unittest.cc +++ /dev/null @@ -1,239 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/memory/ref_counted.h" -#include "base/memory/scoped_ptr.h" -#include "content/browser/indexed_db/list_set.h" -#include "testing/gtest/include/gtest/gtest.h" - -namespace content { - -TEST(ListSetTest, ListSetIterator) { - list_set<int> set; - for (int i = 3; i > 0; --i) - set.insert(i); - - list_set<int>::iterator it = set.begin(); - EXPECT_EQ(3, *it); - ++it; - EXPECT_EQ(2, *it); - it++; - EXPECT_EQ(1, *it); - --it; - EXPECT_EQ(2, *it); - it--; - EXPECT_EQ(3, *it); - ++it; - EXPECT_EQ(2, *it); - it++; - EXPECT_EQ(1, *it); - ++it; - EXPECT_EQ(set.end(), it); -} - -TEST(ListSetTest, ListSetConstIterator) { - list_set<int> set; - for (int i = 5; i > 0; --i) - set.insert(i); - - const list_set<int>& ref = set; - - list_set<int>::const_iterator it = ref.begin(); - for (int i = 5; i > 0; --i) { - EXPECT_EQ(i, *it); - ++it; - } - EXPECT_EQ(ref.end(), it); -} - -TEST(ListSetTest, ListSetPrimitive) { - list_set<int> set; - EXPECT_TRUE(set.empty()); - EXPECT_EQ(static_cast<size_t>(0), set.size()); - { - list_set<int>::iterator it = set.begin(); - EXPECT_EQ(set.end(), it); - } - - for (int i = 5; i > 0; --i) - set.insert(i); - EXPECT_EQ(static_cast<size_t>(5), set.size()); - EXPECT_FALSE(set.empty()); - - set.erase(3); - EXPECT_EQ(static_cast<size_t>(4), set.size()); - - EXPECT_TRUE(set.has(2)); - set.erase(2); - EXPECT_FALSE(set.has(2)); - EXPECT_EQ(static_cast<size_t>(3), set.size()); - - { - list_set<int>::iterator it = set.begin(); - EXPECT_EQ(5, *it); - ++it; - EXPECT_EQ(4, *it); - ++it; - EXPECT_EQ(1, *it); - ++it; - EXPECT_EQ(set.end(), it); - } - - set.erase(1); - set.erase(4); - set.erase(5); - - EXPECT_EQ(static_cast<size_t>(0), set.size()); - EXPECT_TRUE(set.empty()); - { - list_set<int>::iterator it = set.begin(); - EXPECT_EQ(set.end(), it); - } -} - -template <typename T> class Wrapped { - public: - Wrapped(const T& value) : value_(value) {} - Wrapped(const Wrapped<T>& other) : value_(other.value_) {} - Wrapped& operator=(const Wrapped<T>& rhs) { - value_ = rhs.value_; - return *this; - } - int value() const { return value_; } - bool operator<(const Wrapped<T>& rhs) const { return value_ < rhs.value_; } - bool operator==(const Wrapped<T>& rhs) const { return value_ == rhs.value_; } - - private: - T value_; -}; - -TEST(ListSetTest, ListSetObject) { - list_set<Wrapped<int> > set; - EXPECT_EQ(static_cast<size_t>(0), set.size()); - { - list_set<Wrapped<int> >::iterator it = set.begin(); - EXPECT_EQ(set.end(), it); - } - - set.insert(Wrapped<int>(0)); - set.insert(Wrapped<int>(1)); - set.insert(Wrapped<int>(2)); - - EXPECT_EQ(static_cast<size_t>(3), set.size()); - - { - list_set<Wrapped<int> >::iterator it = set.begin(); - EXPECT_EQ(0, it->value()); - ++it; - EXPECT_EQ(1, it->value()); - ++it; - EXPECT_EQ(2, it->value()); - ++it; - EXPECT_EQ(set.end(), it); - } - - set.erase(Wrapped<int>(0)); - set.erase(Wrapped<int>(1)); - set.erase(Wrapped<int>(2)); - - EXPECT_EQ(static_cast<size_t>(0), set.size()); - { - list_set<Wrapped<int> >::iterator it = set.begin(); - EXPECT_EQ(set.end(), it); - } -} - -TEST(ListSetTest, ListSetPointer) { - scoped_ptr<Wrapped<int> > w0(new Wrapped<int>(0)); - scoped_ptr<Wrapped<int> > w1(new Wrapped<int>(1)); - scoped_ptr<Wrapped<int> > w2(new Wrapped<int>(2)); - - list_set<Wrapped<int>*> set; - EXPECT_EQ(static_cast<size_t>(0), set.size()); - { - list_set<Wrapped<int>*>::iterator it = set.begin(); - EXPECT_EQ(set.end(), it); - } - - set.insert(w0.get()); - set.insert(w1.get()); - set.insert(w2.get()); - - EXPECT_EQ(static_cast<size_t>(3), set.size()); - - { - list_set<Wrapped<int>*>::iterator it = set.begin(); - EXPECT_EQ(0, (*it)->value()); - ++it; - EXPECT_EQ(1, (*it)->value()); - ++it; - EXPECT_EQ(2, (*it)->value()); - ++it; - EXPECT_EQ(set.end(), it); - } - - set.erase(w0.get()); - set.erase(w1.get()); - set.erase(w2.get()); - - EXPECT_EQ(static_cast<size_t>(0), set.size()); - { - list_set<Wrapped<int>*>::iterator it = set.begin(); - EXPECT_EQ(set.end(), it); - } -} - -template <typename T> -class RefCounted : public base::RefCounted<RefCounted<T> > { - public: - RefCounted(const T& value) : value_(value) {} - T value() { return value_; } - - private: - virtual ~RefCounted() {} - friend class base::RefCounted<RefCounted<T> >; - T value_; -}; - -TEST(ListSetTest, ListSetRefCounted) { - list_set<scoped_refptr<RefCounted<int> > > set; - EXPECT_EQ(static_cast<size_t>(0), set.size()); - { - list_set<scoped_refptr<RefCounted<int> > >::iterator it = set.begin(); - EXPECT_EQ(set.end(), it); - } - - scoped_refptr<RefCounted<int> > r0(new RefCounted<int>(0)); - scoped_refptr<RefCounted<int> > r1(new RefCounted<int>(1)); - scoped_refptr<RefCounted<int> > r2(new RefCounted<int>(2)); - - set.insert(r0); - set.insert(r1); - set.insert(r2); - - EXPECT_EQ(static_cast<size_t>(3), set.size()); - - { - list_set<scoped_refptr<RefCounted<int> > >::iterator it = set.begin(); - EXPECT_EQ(0, (*it)->value()); - ++it; - EXPECT_EQ(1, (*it)->value()); - ++it; - EXPECT_EQ(2, (*it)->value()); - ++it; - EXPECT_EQ(set.end(), it); - } - - set.erase(r0); - set.erase(r1); - set.erase(r2); - - EXPECT_EQ(static_cast<size_t>(0), set.size()); - { - list_set<scoped_refptr<RefCounted<int> > >::iterator it = set.begin(); - EXPECT_EQ(set.end(), it); - } -} - -} // namespace content diff --git a/content/browser/indexed_db/webidbcursor_impl.cc b/content/browser/indexed_db/webidbcursor_impl.cc deleted file mode 100644 index 629ebaf..0000000 --- a/content/browser/indexed_db/webidbcursor_impl.cc +++ /dev/null @@ -1,51 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/webidbcursor_impl.h" - -#include "content/browser/indexed_db/indexed_db_callbacks_wrapper.h" -#include "content/browser/indexed_db/indexed_db_cursor.h" -#include "content/common/indexed_db/indexed_db_key.h" -#include "third_party/WebKit/public/platform/WebIDBKey.h" - -using WebKit::WebIDBCallbacks; - -namespace content { - -WebIDBCursorImpl::WebIDBCursorImpl( - scoped_refptr<IndexedDBCursor> idb_cursor_backend) - : idb_cursor_backend_(idb_cursor_backend) {} - -WebIDBCursorImpl::~WebIDBCursorImpl() {} - -void WebIDBCursorImpl::advance(unsigned long count, - WebIDBCallbacks* callbacks) { - idb_cursor_backend_->Advance(count, - IndexedDBCallbacksWrapper::Create(callbacks)); -} - -void WebIDBCursorImpl::continueFunction(const WebKit::WebIDBKey& key, - WebIDBCallbacks* callbacks) { - idb_cursor_backend_->ContinueFunction( - make_scoped_ptr(new IndexedDBKey(key)), - IndexedDBCallbacksWrapper::Create(callbacks)); -} - -void WebIDBCursorImpl::deleteFunction(WebIDBCallbacks* callbacks) { - idb_cursor_backend_->DeleteFunction( - IndexedDBCallbacksWrapper::Create(callbacks)); -} - -void WebIDBCursorImpl::prefetchContinue(int number_to_fetch, - WebKit::WebIDBCallbacks* callbacks) { - idb_cursor_backend_->PrefetchContinue( - number_to_fetch, IndexedDBCallbacksWrapper::Create(callbacks)); -} - -void WebIDBCursorImpl::prefetchReset(int used_prefetches, - int unused_prefetches) { - idb_cursor_backend_->PrefetchReset(used_prefetches, unused_prefetches); -} - -} // namespace content diff --git a/content/browser/indexed_db/webidbcursor_impl.h b/content/browser/indexed_db/webidbcursor_impl.h deleted file mode 100644 index ec89877..0000000 --- a/content/browser/indexed_db/webidbcursor_impl.h +++ /dev/null @@ -1,33 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_WEBIDBCURSOR_IMPL_H_ -#define CONTENT_BROWSER_INDEXED_DB_WEBIDBCURSOR_IMPL_H_ - -#include "base/memory/ref_counted.h" -#include "third_party/WebKit/public/platform/WebIDBCursor.h" - -namespace content { -class IndexedDBCursor; - -class WebIDBCursorImpl : public WebKit::WebIDBCursor { - public: - explicit WebIDBCursorImpl(scoped_refptr<IndexedDBCursor> cursor); - virtual ~WebIDBCursorImpl(); - - virtual void advance(unsigned long, WebKit::WebIDBCallbacks* callbacks); - virtual void continueFunction(const WebKit::WebIDBKey& key, - WebKit::WebIDBCallbacks* callbacks); - virtual void deleteFunction(WebKit::WebIDBCallbacks* callbacks); - virtual void prefetchContinue(int number_to_fetch, - WebKit::WebIDBCallbacks* callbacks); - virtual void prefetchReset(int used_prefetches, int unused_prefetches); - - private: - scoped_refptr<IndexedDBCursor> idb_cursor_backend_; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_WEBIDBCURSOR_IMPL_H_ diff --git a/content/browser/indexed_db/webidbdatabase_impl.cc b/content/browser/indexed_db/webidbdatabase_impl.cc deleted file mode 100644 index 7c2c7e3..0000000 --- a/content/browser/indexed_db/webidbdatabase_impl.cc +++ /dev/null @@ -1,278 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/webidbdatabase_impl.h" - -#include <vector> - -#include "base/basictypes.h" -#include "base/logging.h" -#include "content/browser/indexed_db/indexed_db_callbacks_wrapper.h" -#include "content/browser/indexed_db/indexed_db_cursor.h" -#include "content/browser/indexed_db/indexed_db_database.h" -#include "content/browser/indexed_db/indexed_db_metadata.h" -#include "content/common/indexed_db/indexed_db_key_range.h" -#include "third_party/WebKit/public/platform/WebData.h" -#include "third_party/WebKit/public/platform/WebIDBCallbacks.h" -#include "third_party/WebKit/public/platform/WebIDBDatabaseCallbacks.h" -#include "third_party/WebKit/public/platform/WebIDBDatabaseError.h" -#include "third_party/WebKit/public/platform/WebIDBKey.h" -#include "third_party/WebKit/public/platform/WebIDBKeyRange.h" -#include "third_party/WebKit/public/platform/WebIDBMetadata.h" - -using WebKit::WebString; -using WebKit::WebIDBKey; -using WebKit::WebData; -using WebKit::WebIDBKeyPath; -using WebKit::WebIDBKeyRange; -using WebKit::WebIDBDatabaseCallbacks; -using WebKit::WebIDBCallbacks; -using WebKit::WebVector; -using WebKit::WebIDBDatabaseError; - -namespace content { - -WebIDBDatabaseImpl::WebIDBDatabaseImpl( - scoped_refptr<IndexedDBDatabase> database_backend, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks) - : database_backend_(database_backend), - database_callbacks_(database_callbacks) {} - -WebIDBDatabaseImpl::~WebIDBDatabaseImpl() {} - -void WebIDBDatabaseImpl::createObjectStore(long long transaction_id, - long long object_store_id, - const WebString& name, - const WebIDBKeyPath& key_path, - bool auto_increment) { - database_backend_->CreateObjectStore(transaction_id, - object_store_id, - name, - IndexedDBKeyPath(key_path), - auto_increment); -} - -void WebIDBDatabaseImpl::deleteObjectStore(long long transaction_id, - long long object_store_id) { - database_backend_->DeleteObjectStore(transaction_id, object_store_id); -} - -void WebIDBDatabaseImpl::createTransaction( - long long id, - WebIDBDatabaseCallbacks* /*callbacks*/, - const WebVector<long long>& object_store_ids, - unsigned short mode) { - if (!database_callbacks_) - return; - std::vector<int64> object_store_id_list(object_store_ids.size()); - for (size_t i = 0; i < object_store_ids.size(); ++i) - object_store_id_list[i] = object_store_ids[i]; - database_backend_->CreateTransaction( - id, database_callbacks_.get(), object_store_id_list, mode); -} - -void WebIDBDatabaseImpl::close() { - // Use the callbacks passed in to the constructor so that the backend in - // multi-process chromium knows which database connection is closing. - if (!database_callbacks_) - return; - database_backend_->Close(database_callbacks_); - database_callbacks_ = NULL; -} - -void WebIDBDatabaseImpl::forceClose() { - if (!database_callbacks_) - return; - database_backend_->Close(database_callbacks_); - database_callbacks_->OnForcedClose(); - database_callbacks_ = NULL; -} - -void WebIDBDatabaseImpl::abort(long long transaction_id) { - if (database_backend_) - database_backend_->Abort(transaction_id); -} - -void WebIDBDatabaseImpl::abort(long long transaction_id, - const WebIDBDatabaseError& error) { - if (database_backend_) - database_backend_->Abort(transaction_id, - IndexedDBDatabaseError::Create(error)); -} - -void WebIDBDatabaseImpl::commit(long long transaction_id) { - if (database_backend_) - database_backend_->Commit(transaction_id); -} - -void WebIDBDatabaseImpl::openCursor(long long transaction_id, - long long object_store_id, - long long index_id, - const WebIDBKeyRange& key_range, - unsigned short direction, - bool key_only, - TaskType task_type, - WebIDBCallbacks* callbacks) { - if (database_backend_) - database_backend_->OpenCursor( - transaction_id, - object_store_id, - index_id, - make_scoped_ptr(new IndexedDBKeyRange(key_range)), - static_cast<indexed_db::CursorDirection>(direction), - key_only, - static_cast<IndexedDBDatabase::TaskType>(task_type), - IndexedDBCallbacksWrapper::Create(callbacks)); -} - -void WebIDBDatabaseImpl::count(long long transaction_id, - long long object_store_id, - long long index_id, - const WebIDBKeyRange& key_range, - WebIDBCallbacks* callbacks) { - if (database_backend_) - database_backend_->Count(transaction_id, - object_store_id, - index_id, - make_scoped_ptr(new IndexedDBKeyRange(key_range)), - IndexedDBCallbacksWrapper::Create(callbacks)); -} - -void WebIDBDatabaseImpl::get(long long transaction_id, - long long object_store_id, - long long index_id, - const WebIDBKeyRange& key_range, - bool key_only, - WebIDBCallbacks* callbacks) { - if (database_backend_) - database_backend_->Get(transaction_id, - object_store_id, - index_id, - make_scoped_ptr(new IndexedDBKeyRange(key_range)), - key_only, - IndexedDBCallbacksWrapper::Create(callbacks)); -} - -void WebIDBDatabaseImpl::put(long long transaction_id, - long long object_store_id, - const WebData& value, - const WebIDBKey& key, - PutMode put_mode, - WebIDBCallbacks* callbacks, - const WebVector<long long>& web_index_ids, - const WebVector<WebIndexKeys>& web_index_keys) { - if (!database_backend_) - return; - - DCHECK_EQ(web_index_ids.size(), web_index_keys.size()); - std::vector<int64> index_ids(web_index_ids.size()); - std::vector<IndexedDBDatabase::IndexKeys> index_keys(web_index_keys.size()); - - for (size_t i = 0; i < web_index_ids.size(); ++i) { - index_ids[i] = web_index_ids[i]; - IndexedDBKey::KeyArray index_key_list; - for (size_t j = 0; j < web_index_keys[i].size(); ++j) - index_key_list.push_back(IndexedDBKey(web_index_keys[i][j])); - index_keys[i] = index_key_list; - } - - std::vector<char> value_buffer(value.data(), value.data() + value.size()); - database_backend_->Put(transaction_id, - object_store_id, - &value_buffer, - make_scoped_ptr(new IndexedDBKey(key)), - static_cast<IndexedDBDatabase::PutMode>(put_mode), - IndexedDBCallbacksWrapper::Create(callbacks), - index_ids, - index_keys); -} - -void WebIDBDatabaseImpl::setIndexKeys( - long long transaction_id, - long long object_store_id, - const WebIDBKey& primary_key, - const WebVector<long long>& web_index_ids, - const WebVector<WebIndexKeys>& web_index_keys) { - if (!database_backend_) - return; - - DCHECK_EQ(web_index_ids.size(), web_index_keys.size()); - std::vector<int64> index_ids(web_index_ids.size()); - std::vector<IndexedDBDatabase::IndexKeys> index_keys(web_index_keys.size()); - - for (size_t i = 0; i < web_index_ids.size(); ++i) { - index_ids[i] = web_index_ids[i]; - IndexedDBKey::KeyArray index_key_list; - for (size_t j = 0; j < web_index_keys[i].size(); ++j) - index_key_list.push_back(IndexedDBKey(web_index_keys[i][j])); - index_keys[i] = index_key_list; - } - database_backend_->SetIndexKeys( - transaction_id, - object_store_id, - make_scoped_ptr(new IndexedDBKey(primary_key)), - index_ids, - index_keys); -} - -void WebIDBDatabaseImpl::setIndexesReady( - long long transaction_id, - long long object_store_id, - const WebVector<long long>& web_index_ids) { - if (!database_backend_) - return; - - std::vector<int64> index_ids(web_index_ids.size()); - for (size_t i = 0; i < web_index_ids.size(); ++i) - index_ids[i] = web_index_ids[i]; - database_backend_->SetIndexesReady( - transaction_id, object_store_id, index_ids); -} - -void WebIDBDatabaseImpl::deleteRange(long long transaction_id, - long long object_store_id, - const WebIDBKeyRange& key_range, - WebIDBCallbacks* callbacks) { - if (database_backend_) - database_backend_->DeleteRange( - transaction_id, - object_store_id, - make_scoped_ptr(new IndexedDBKeyRange(key_range)), - IndexedDBCallbacksWrapper::Create(callbacks)); -} - -void WebIDBDatabaseImpl::clear(long long transaction_id, - long long object_store_id, - WebIDBCallbacks* callbacks) { - if (database_backend_) - database_backend_->Clear(transaction_id, - object_store_id, - IndexedDBCallbacksWrapper::Create(callbacks)); -} - -void WebIDBDatabaseImpl::createIndex(long long transaction_id, - long long object_store_id, - long long index_id, - const WebString& name, - const WebIDBKeyPath& key_path, - bool unique, - bool multi_entry) { - if (database_backend_) - database_backend_->CreateIndex(transaction_id, - object_store_id, - index_id, - name, - IndexedDBKeyPath(key_path), - unique, - multi_entry); -} - -void WebIDBDatabaseImpl::deleteIndex(long long transaction_id, - long long object_store_id, - long long index_id) { - if (database_backend_) - database_backend_->DeleteIndex(transaction_id, object_store_id, index_id); -} - -} // namespace WebKit diff --git a/content/browser/indexed_db/webidbdatabase_impl.h b/content/browser/indexed_db/webidbdatabase_impl.h deleted file mode 100644 index 52c137f..0000000 --- a/content/browser/indexed_db/webidbdatabase_impl.h +++ /dev/null @@ -1,110 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_WEBIDBDATABASE_IMPL_H_ -#define CONTENT_BROWSER_INDEXED_DB_WEBIDBDATABASE_IMPL_H_ - -#include "base/memory/ref_counted.h" -#include "content/browser/indexed_db/indexed_db_database.h" -#include "content/browser/indexed_db/indexed_db_database_callbacks_wrapper.h" -#include "third_party/WebKit/public/platform/WebIDBDatabase.h" - -namespace WebKit { -class WebIDBDatabaseCallbacks; -class WebIDBDatabaseError; -class WebIDBDatabaseMetadata; -} - -namespace content { -class IndexedDBDatabase; -class IndexedDBDatabaseCallbacksWrapper; - -// See comment in WebIDBFactory for a high level overview these classes. -class WebIDBDatabaseImpl : public WebKit::WebIDBDatabase { - public: - WebIDBDatabaseImpl( - scoped_refptr<IndexedDBDatabase> db, - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> callbacks); - virtual ~WebIDBDatabaseImpl(); - - virtual void createObjectStore(long long transaction_id, - long long object_store_id, - const WebKit::WebString& name, - const WebKit::WebIDBKeyPath& key_path, - bool auto_increment); - virtual void deleteObjectStore(long long object_store_id, - long long transaction_id); - virtual void createTransaction(long long id, - WebKit::WebIDBDatabaseCallbacks* callbacks, - const WebKit::WebVector<long long>& scope, - unsigned short mode); - virtual void forceClose(); - virtual void close(); - virtual void abort(long long transaction_id); - virtual void abort(long long transaction_id, - const WebKit::WebIDBDatabaseError& error); - virtual void commit(long long transaction_id); - - virtual void get(long long transaction_id, - long long object_store_id, - long long index_id, - const WebKit::WebIDBKeyRange& range, - bool key_only, - WebKit::WebIDBCallbacks* callbacks); - virtual void put(long long transaction_id, - long long object_store_id, - const WebKit::WebData& value, - const WebKit::WebIDBKey& key, - PutMode mode, - WebKit::WebIDBCallbacks* callbacks, - const WebKit::WebVector<long long>& index_ids, - const WebKit::WebVector<WebIndexKeys>& index_keys); - virtual void setIndexKeys(long long transaction_id, - long long object_store_id, - const WebKit::WebIDBKey& key, - const WebKit::WebVector<long long>& index_ids, - const WebKit::WebVector<WebIndexKeys>& index_keys); - virtual void setIndexesReady(long long transaction_id, - long long object_store_id, - const WebKit::WebVector<long long>& index_ids); - virtual void openCursor(long long transaction_id, - long long object_store_id, - long long index_id, - const WebKit::WebIDBKeyRange& range, - unsigned short direction, - bool key_only, - TaskType task_type, - WebKit::WebIDBCallbacks* callbacks); - virtual void count(long long transaction_id, - long long object_store_id, - long long index_id, - const WebKit::WebIDBKeyRange& range, - WebKit::WebIDBCallbacks* callbacks); - virtual void deleteRange(long long transaction_id, - long long object_store_id, - const WebKit::WebIDBKeyRange& range, - WebKit::WebIDBCallbacks* callbacks); - virtual void clear(long long transaction_id, - long long object_store_id, - WebKit::WebIDBCallbacks* callbacks); - - virtual void createIndex(long long transaction_id, - long long object_store_id, - long long index_id, - const WebKit::WebString& name, - const WebKit::WebIDBKeyPath& key_path, - bool unique, - bool multi_entry); - virtual void deleteIndex(long long transaction_id, - long long object_store_id, - long long index_id); - - private: - scoped_refptr<IndexedDBDatabase> database_backend_; - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks_; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_WEBIDBDATABASE_IMPL_H_ diff --git a/content/browser/indexed_db/webidbfactory_impl.cc b/content/browser/indexed_db/webidbfactory_impl.cc deleted file mode 100644 index 1fc78fa..0000000 --- a/content/browser/indexed_db/webidbfactory_impl.cc +++ /dev/null @@ -1,68 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "content/browser/indexed_db/webidbfactory_impl.h" - -#include "base/memory/scoped_ptr.h" -#include "content/browser/indexed_db/indexed_db_callbacks_wrapper.h" -#include "content/browser/indexed_db/indexed_db_factory.h" -#include "content/browser/indexed_db/indexed_db_factory_impl.h" -#include "third_party/WebKit/public/platform/WebIDBDatabaseCallbacks.h" -#include "third_party/WebKit/public/platform/WebIDBDatabaseError.h" - -using WebKit::WebIDBCallbacks; -using WebKit::WebIDBDatabaseCallbacks; -using WebKit::WebIDBFactory; -using WebKit::WebString; - -namespace content { - -WebIDBFactoryImpl::WebIDBFactoryImpl() - : idb_factory_backend_(IndexedDBFactoryImpl::Create()) {} - -WebIDBFactoryImpl::~WebIDBFactoryImpl() {} - -void WebIDBFactoryImpl::getDatabaseNames(WebIDBCallbacks* callbacks, - const WebString& database_identifier, - const WebString& data_dir) { - idb_factory_backend_->GetDatabaseNames( - IndexedDBCallbacksWrapper::Create(callbacks), - database_identifier, - data_dir); -} - -void WebIDBFactoryImpl::open(const WebString& name, - long long version, - long long transaction_id, - WebIDBCallbacks* callbacks, - WebIDBDatabaseCallbacks* database_callbacks, - const WebString& database_identifier, - const WebString& data_dir) { - scoped_refptr<IndexedDBCallbacksWrapper> callbacks_proxy = - IndexedDBCallbacksWrapper::Create(callbacks); - scoped_refptr<IndexedDBDatabaseCallbacksWrapper> database_callbacks_proxy = - IndexedDBDatabaseCallbacksWrapper::Create(database_callbacks); - - callbacks_proxy->SetDatabaseCallbacks(database_callbacks_proxy); - idb_factory_backend_->Open(name, - version, - transaction_id, - callbacks_proxy.get(), - database_callbacks_proxy.get(), - database_identifier, - data_dir); -} - -void WebIDBFactoryImpl::deleteDatabase(const WebString& name, - WebIDBCallbacks* callbacks, - const WebString& database_identifier, - const WebString& data_dir) { - idb_factory_backend_->DeleteDatabase( - name, - IndexedDBCallbacksWrapper::Create(callbacks), - database_identifier, - data_dir); -} - -} // namespace WebKit diff --git a/content/browser/indexed_db/webidbfactory_impl.h b/content/browser/indexed_db/webidbfactory_impl.h deleted file mode 100644 index 3835285..0000000 --- a/content/browser/indexed_db/webidbfactory_impl.h +++ /dev/null @@ -1,41 +0,0 @@ -// Copyright (c) 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_INDEXED_DB_WEBIDBFACTORY_IMPL_H_ -#define CONTENT_BROWSER_INDEXED_DB_WEBIDBFACTORY_IMPL_H_ - -#include "base/memory/ref_counted.h" -#include "third_party/WebKit/public/platform/WebIDBFactory.h" - -namespace content { - -class IndexedDBFactory; - -class WebIDBFactoryImpl : public WebKit::WebIDBFactory { - public: - WebIDBFactoryImpl(); - virtual ~WebIDBFactoryImpl(); - - virtual void getDatabaseNames(WebKit::WebIDBCallbacks* callbacks, - const WebKit::WebString& database_identifier, - const WebKit::WebString& data_dir); - virtual void open(const WebKit::WebString& name, - long long version, - long long transaction_id, - WebKit::WebIDBCallbacks* callbacks, - WebKit::WebIDBDatabaseCallbacks* database_callbacks, - const WebKit::WebString& database_identifier, - const WebKit::WebString& data_dir); - virtual void deleteDatabase(const WebKit::WebString& name, - WebKit::WebIDBCallbacks* callbacks, - const WebKit::WebString& database_identifier, - const WebKit::WebString& data_dir); - - private: - scoped_refptr<IndexedDBFactory> idb_factory_backend_; -}; - -} // namespace content - -#endif // CONTENT_BROWSER_INDEXED_DB_WEBIDBFACTORY_IMPL_H_ diff --git a/content/common/indexed_db/indexed_db_key.cc b/content/common/indexed_db/indexed_db_key.cc index 3d24ade..4083fd3 100644 --- a/content/common/indexed_db/indexed_db_key.cc +++ b/content/common/indexed_db/indexed_db_key.cc @@ -4,7 +4,6 @@ #include "content/common/indexed_db/indexed_db_key.h" -#include <string> #include "base/logging.h" #include "third_party/WebKit/public/platform/WebString.h" #include "third_party/WebKit/public/platform/WebVector.h" @@ -61,7 +60,7 @@ static IndexedDBKey::KeyArray CopyKeyArray(const WebIDBKey& other) { } return result; } -} // namespace +} // namespace IndexedDBKey::IndexedDBKey() : type_(WebIDBKey::NullType), @@ -105,8 +104,6 @@ IndexedDBKey::IndexedDBKey(const string16& key) IndexedDBKey::~IndexedDBKey() {} int IndexedDBKey::Compare(const IndexedDBKey& other) const { - DCHECK(IsValid()); - DCHECK(other.IsValid()); if (type_ != other.type_) return type_ > other.type_ ? -1 : 1; @@ -124,17 +121,15 @@ int IndexedDBKey::Compare(const IndexedDBKey& other) const { case WebIDBKey::StringType: return -other.string_.compare(string_); case WebIDBKey::DateType: - return (date_ < other.date_) ? -1 : (date_ > other.date_) ? 1 : 0; case WebIDBKey::NumberType: return (number_ < other.number_) ? -1 : (number_ > other.number_) ? 1 : 0; case WebIDBKey::InvalidType: case WebIDBKey::NullType: - case WebIDBKey::MinType: + default: + // This is a placeholder for WebKit::WebIDBKey::MinType NOTREACHED(); return 0; } - NOTREACHED(); - return 0; } bool IndexedDBKey::IsLessThan(const IndexedDBKey& other) const { @@ -145,20 +140,6 @@ bool IndexedDBKey::IsEqual(const IndexedDBKey& other) const { return !Compare(other); } -bool IndexedDBKey::IsValid() const { - if (type_ == WebIDBKey::InvalidType || type_ == WebIDBKey::NullType) - return false; - - if (type_ == WebIDBKey::ArrayType) { - for (size_t i = 0; i < array_.size(); i++) { - if (!array_[i].IsValid()) - return false; - } - } - - return true; -} - IndexedDBKey::operator WebIDBKey() const { switch (type_) { case WebIDBKey::ArrayType: @@ -173,12 +154,11 @@ IndexedDBKey::operator WebIDBKey() const { return WebIDBKey::createInvalid(); case WebIDBKey::NullType: return WebIDBKey::createNull(); - case WebIDBKey::MinType: + default: + // This is a placeholder for WebKit::WebIDBKey::MinType NOTREACHED(); return WebIDBKey::createInvalid(); } - NOTREACHED(); - return WebIDBKey::createInvalid(); } } // namespace content diff --git a/content/common/indexed_db/indexed_db_param_traits.cc b/content/common/indexed_db/indexed_db_param_traits.cc index 58019ce..8593f75 100644 --- a/content/common/indexed_db/indexed_db_param_traits.cc +++ b/content/common/indexed_db/indexed_db_param_traits.cc @@ -4,8 +4,6 @@ #include "content/common/indexed_db/indexed_db_param_traits.h" -#include <string> -#include <vector> #include "content/common/indexed_db/indexed_db_key.h" #include "content/common/indexed_db/indexed_db_key_path.h" #include "content/common/indexed_db/indexed_db_key_range.h" @@ -21,7 +19,7 @@ using WebKit::WebIDBKeyPath; namespace IPC { void ParamTraits<IndexedDBKey>::Write(Message* m, const param_type& p) { - WriteParam(m, static_cast<int>(p.type())); + WriteParam(m, int(p.type())); switch (p.type()) { case WebIDBKey::ArrayType: WriteParam(m, p.array()); @@ -38,7 +36,8 @@ void ParamTraits<IndexedDBKey>::Write(Message* m, const param_type& p) { case WebIDBKey::InvalidType: case WebIDBKey::NullType: return; - case WebIDBKey::MinType: + default: + // This is a placeholder for WebKit::WebIDBKey::MinType NOTREACHED(); return; } @@ -79,17 +78,16 @@ bool ParamTraits<IndexedDBKey>::Read(const Message* m, case WebIDBKey::NullType: *r = IndexedDBKey(web_type); return true; - case WebIDBKey::MinType: + default: + // This is a placeholder for WebKit::WebIDBKey::MinType NOTREACHED(); return false; } - NOTREACHED(); - return false; } void ParamTraits<IndexedDBKey>::Log(const param_type& p, std::string* l) { l->append("<IndexedDBKey>("); - LogParam(static_cast<int>(p.type()), l); + LogParam(int(p.type()), l); l->append(", "); l->append("["); std::vector<IndexedDBKey>::const_iterator it = p.array().begin(); @@ -109,7 +107,7 @@ void ParamTraits<IndexedDBKey>::Log(const param_type& p, std::string* l) { } void ParamTraits<IndexedDBKeyPath>::Write(Message* m, const param_type& p) { - WriteParam(m, static_cast<int>(p.type())); + WriteParam(m, int(p.type())); switch (p.type()) { case WebIDBKeyPath::ArrayType: WriteParam(m, p.array()); @@ -155,7 +153,7 @@ bool ParamTraits<IndexedDBKeyPath>::Read(const Message* m, void ParamTraits<IndexedDBKeyPath>::Log(const param_type& p, std::string* l) { l->append("<IndexedDBKeyPath>("); - LogParam(static_cast<int>(p.type()), l); + LogParam(int(p.type()), l); l->append(", "); LogParam(p.string(), l); l->append(", "); diff --git a/content/content_browser.gypi b/content/content_browser.gypi index 7a3d3f5..d7b81c0 100644 --- a/content/content_browser.gypi +++ b/content/content_browser.gypi @@ -542,56 +542,12 @@ 'browser/in_process_webkit/indexed_db_dispatcher_host.h', 'browser/in_process_webkit/webkit_thread.cc', 'browser/in_process_webkit/webkit_thread.h', - 'browser/indexed_db/indexed_db.h', - 'browser/indexed_db/indexed_db_backing_store.cc', - 'browser/indexed_db/indexed_db_backing_store.h', - 'browser/indexed_db/indexed_db_callbacks_wrapper.cc', - 'browser/indexed_db/indexed_db_callbacks_wrapper.h', 'browser/indexed_db/indexed_db_context_impl.cc', 'browser/indexed_db/indexed_db_context_impl.h', - 'browser/indexed_db/indexed_db_cursor.h', - 'browser/indexed_db/indexed_db_cursor_impl.cc', - 'browser/indexed_db/indexed_db_cursor_impl.h', - 'browser/indexed_db/indexed_db_database.h', - 'browser/indexed_db/indexed_db_database_callbacks_wrapper.cc', - 'browser/indexed_db/indexed_db_database_callbacks_wrapper.h', - 'browser/indexed_db/indexed_db_database_error.h', - 'browser/indexed_db/indexed_db_database_impl.cc', - 'browser/indexed_db/indexed_db_database_impl.h', - 'browser/indexed_db/indexed_db_factory.h', - 'browser/indexed_db/indexed_db_factory_impl.cc', - 'browser/indexed_db/indexed_db_factory_impl.h', - 'browser/indexed_db/indexed_db_index_writer.cc', - 'browser/indexed_db/indexed_db_index_writer.h', 'browser/indexed_db/indexed_db_internals_ui.cc', 'browser/indexed_db/indexed_db_internals_ui.h', - 'browser/indexed_db/indexed_db_leveldb_coding.cc', - 'browser/indexed_db/indexed_db_leveldb_coding.h', - 'browser/indexed_db/indexed_db_metadata.cc', - 'browser/indexed_db/indexed_db_metadata.h', 'browser/indexed_db/indexed_db_quota_client.cc', 'browser/indexed_db/indexed_db_quota_client.h', - 'browser/indexed_db/indexed_db_transaction.cc', - 'browser/indexed_db/indexed_db_transaction.h', - 'browser/indexed_db/indexed_db_transaction_coordinator.cc', - 'browser/indexed_db/indexed_db_transaction_coordinator.h', - 'browser/indexed_db/leveldb/avltree.h', - 'browser/indexed_db/leveldb/fixed_array.h', - 'browser/indexed_db/leveldb/leveldb_comparator.h', - 'browser/indexed_db/leveldb/leveldb_database.cc', - 'browser/indexed_db/leveldb/leveldb_database.h', - 'browser/indexed_db/leveldb/leveldb_iterator.h', - 'browser/indexed_db/leveldb/leveldb_slice.h', - 'browser/indexed_db/leveldb/leveldb_transaction.cc', - 'browser/indexed_db/leveldb/leveldb_transaction.h', - 'browser/indexed_db/leveldb/leveldb_write_batch.cc', - 'browser/indexed_db/leveldb/leveldb_write_batch.h', - 'browser/indexed_db/webidbcursor_impl.cc', - 'browser/indexed_db/webidbcursor_impl.h', - 'browser/indexed_db/webidbdatabase_impl.cc', - 'browser/indexed_db/webidbdatabase_impl.h', - 'browser/indexed_db/webidbfactory_impl.cc', - 'browser/indexed_db/webidbfactory_impl.h', 'browser/loader/async_resource_handler.cc', 'browser/loader/async_resource_handler.h', 'browser/loader/buffered_resource_handler.cc', @@ -1145,7 +1101,6 @@ '../net/net.gyp:http_server', '../printing/printing.gyp:printing', '../third_party/WebKit/Source/WebKit/chromium/WebKit.gyp:webkit', - '../third_party/leveldatabase/leveldatabase.gyp:leveldatabase', '../ui/surface/surface.gyp:surface', '../webkit/support/webkit_support.gyp:webkit_resources', '../webkit/support/webkit_support.gyp:webkit_storage', diff --git a/content/content_tests.gypi b/content/content_tests.gypi index d884392..ab2c2ac 100644 --- a/content/content_tests.gypi +++ b/content/content_tests.gypi @@ -233,7 +233,6 @@ 'type': '<(gtest_target_type)', 'defines!': ['CONTENT_IMPLEMENTATION'], 'dependencies': [ - 'content_browser', 'content_common', 'test_support_content', 'browser/speech/proto/speech_proto.gyp:speech_proto', diff --git a/content/public/common/content_switches.cc b/content/public/common/content_switches.cc index dc71e4c..0682c1d 100644 --- a/content/public/common/content_switches.cc +++ b/content/public/common/content_switches.cc @@ -554,10 +554,6 @@ const char kNoSandbox[] = "no-sandbox"; // finishes. const char kAllowNoSandboxJob[] = "allow-no-sandbox-job"; -// Use the new IndexedDB backend implemented in Chromium. By default, -// the old backend implemented in Blink is used. -const char kNewIndexedDB[] = "new-indexeddb"; - // Specifies a command that should be used to launch the plugin process. Useful // for running the plugin process through purify or quantify. Ex: // --plugin-launcher="path\to\purify /Run=yes" diff --git a/content/public/common/content_switches.h b/content/public/common/content_switches.h index 5a7404f..870a943 100644 --- a/content/public/common/content_switches.h +++ b/content/public/common/content_switches.h @@ -167,7 +167,6 @@ extern const char kLoadPlugin[]; CONTENT_EXPORT extern const char kLoggingLevel[]; extern const char kLogPluginMessages[]; extern const char kMemoryMetrics[]; -extern const char kNewIndexedDB[]; CONTENT_EXPORT extern const char kNoReferrers[]; CONTENT_EXPORT extern const char kNoSandbox[]; CONTENT_EXPORT extern const char kAllowNoSandboxJob[]; diff --git a/content/renderer/renderer_webkitplatformsupport_impl.cc b/content/renderer/renderer_webkitplatformsupport_impl.cc index 80c8b53..133bfc2 100644 --- a/content/renderer/renderer_webkitplatformsupport_impl.cc +++ b/content/renderer/renderer_webkitplatformsupport_impl.cc @@ -362,9 +362,8 @@ RendererWebKitPlatformSupportImpl::createLocalStorageNamespace( WebIDBFactory* RendererWebKitPlatformSupportImpl::idbFactory() { if (!web_idb_factory_) { - if (CommandLine::ForCurrentProcess()->HasSwitch(switches::kSingleProcess) && - !CommandLine::ForCurrentProcess()->HasSwitch(switches::kNewIndexedDB)) - web_idb_factory_.reset(WebIDBFactory::create()); + if (CommandLine::ForCurrentProcess()->HasSwitch(switches::kSingleProcess)) + web_idb_factory_.reset(WebIDBFactory::create()); else web_idb_factory_.reset(new RendererWebIDBFactoryImpl()); } |