1// Copyright 2013 The Chromium Authors. All rights reserved. 2// Use of this source code is governed by a BSD-style license that can be 3// found in the LICENSE file. 4 5#ifndef CONTENT_CHILD_INDEXED_DB_INDEXED_DB_DISPATCHER_H_ 6#define CONTENT_CHILD_INDEXED_DB_INDEXED_DB_DISPATCHER_H_ 7 8#include <map> 9#include <vector> 10 11#include "base/gtest_prod_util.h" 12#include "base/id_map.h" 13#include "base/memory/ref_counted.h" 14#include "base/strings/nullable_string16.h" 15#include "content/common/content_export.h" 16#include "ipc/ipc_sync_message_filter.h" 17#include "third_party/WebKit/public/platform/WebIDBCallbacks.h" 18#include "third_party/WebKit/public/platform/WebIDBCursor.h" 19#include "third_party/WebKit/public/platform/WebIDBDatabase.h" 20#include "third_party/WebKit/public/platform/WebIDBDatabaseCallbacks.h" 21#include "webkit/child/worker_task_runner.h" 22 23struct IndexedDBDatabaseMetadata; 24struct IndexedDBMsg_CallbacksSuccessCursorContinue_Params; 25struct IndexedDBMsg_CallbacksSuccessCursorPrefetch_Params; 26struct IndexedDBMsg_CallbacksSuccessIDBCursor_Params; 27struct IndexedDBMsg_CallbacksUpgradeNeeded_Params; 28 29namespace WebKit { 30class WebData; 31} 32 33namespace content { 34class IndexedDBKey; 35class IndexedDBKeyPath; 36class IndexedDBKeyRange; 37class RendererWebIDBCursorImpl; 38class RendererWebIDBDatabaseImpl; 39class ThreadSafeSender; 40 41CONTENT_EXPORT extern const size_t kMaxIDBValueSizeInBytes; 42 43// Handle the indexed db related communication for this context thread - the 44// main thread and each worker thread have their own copies. 45class CONTENT_EXPORT IndexedDBDispatcher 46 : public webkit_glue::WorkerTaskRunner::Observer { 47 public: 48 // Constructor made public to allow RenderThreadImpl to own a copy without 49 // failing a NOTREACHED in ThreadSpecificInstance in tests that instantiate 50 // two copies of RenderThreadImpl on the same thread. Everyone else probably 51 // wants to use ThreadSpecificInstance(). 52 explicit IndexedDBDispatcher(ThreadSafeSender* thread_safe_sender); 53 virtual ~IndexedDBDispatcher(); 54 55 // |thread_safe_sender| needs to be passed in because if the call leads to 56 // construction it will be needed. 57 static IndexedDBDispatcher* ThreadSpecificInstance( 58 ThreadSafeSender* thread_safe_sender); 59 60 // webkit_glue::WorkerTaskRunner::Observer implementation. 61 virtual void OnWorkerRunLoopStopped() OVERRIDE; 62 63 static WebKit::WebIDBMetadata ConvertMetadata( 64 const IndexedDBDatabaseMetadata& idb_metadata); 65 66 void OnMessageReceived(const IPC::Message& msg); 67 bool Send(IPC::Message* msg); 68 69 void RequestIDBFactoryGetDatabaseNames( 70 WebKit::WebIDBCallbacks* callbacks, 71 const std::string& database_identifier); 72 73 void RequestIDBFactoryOpen( 74 const string16& name, 75 int64 version, 76 int64 transaction_id, 77 WebKit::WebIDBCallbacks* callbacks, 78 WebKit::WebIDBDatabaseCallbacks* database_callbacks, 79 const std::string& database_identifier); 80 81 void RequestIDBFactoryDeleteDatabase(const string16& name, 82 WebKit::WebIDBCallbacks* callbacks, 83 const std::string& database_identifier); 84 85 void RequestIDBCursorAdvance(unsigned long count, 86 WebKit::WebIDBCallbacks* callbacks_ptr, 87 int32 ipc_cursor_id); 88 89 virtual void RequestIDBCursorContinue(const IndexedDBKey& key, 90 WebKit::WebIDBCallbacks* callbacks_ptr, 91 int32 ipc_cursor_id); 92 93 virtual void RequestIDBCursorPrefetch(int n, 94 WebKit::WebIDBCallbacks* callbacks_ptr, 95 int32 ipc_cursor_id); 96 97 void RequestIDBCursorPrefetchReset(int used_prefetches, 98 int unused_prefetches, 99 int32 ipc_cursor_id); 100 101 void RequestIDBDatabaseClose(int32 ipc_database_id, 102 int32 ipc_database_callbacks_id); 103 104 void RequestIDBDatabaseCreateTransaction( 105 int32 ipc_database_id, 106 int64 transaction_id, 107 WebKit::WebIDBDatabaseCallbacks* database_callbacks_ptr, 108 WebKit::WebVector<long long> object_store_ids, 109 unsigned short mode); 110 111 void RequestIDBDatabaseGet(int32 ipc_database_id, 112 int64 transaction_id, 113 int64 object_store_id, 114 int64 index_id, 115 const IndexedDBKeyRange& key_range, 116 bool key_only, 117 WebKit::WebIDBCallbacks* callbacks); 118 119 void RequestIDBDatabasePut( 120 int32 ipc_database_id, 121 int64 transaction_id, 122 int64 object_store_id, 123 const WebKit::WebData& value, 124 const IndexedDBKey& key, 125 WebKit::WebIDBDatabase::PutMode put_mode, 126 WebKit::WebIDBCallbacks* callbacks, 127 const WebKit::WebVector<long long>& index_ids, 128 const WebKit::WebVector<WebKit::WebVector<WebKit::WebIDBKey> >& 129 index_keys); 130 131 void RequestIDBDatabaseOpenCursor(int32 ipc_database_id, 132 int64 transaction_id, 133 int64 object_store_id, 134 int64 index_id, 135 const IndexedDBKeyRange& key_range, 136 unsigned short direction, 137 bool key_only, 138 WebKit::WebIDBDatabase::TaskType task_type, 139 WebKit::WebIDBCallbacks* callbacks); 140 141 void RequestIDBDatabaseCount(int32 ipc_database_id, 142 int64 transaction_id, 143 int64 object_store_id, 144 int64 index_id, 145 const IndexedDBKeyRange& key_range, 146 WebKit::WebIDBCallbacks* callbacks); 147 148 void RequestIDBDatabaseDeleteRange(int32 ipc_database_id, 149 int64 transaction_id, 150 int64 object_store_id, 151 const IndexedDBKeyRange& key_range, 152 WebKit::WebIDBCallbacks* callbacks); 153 154 void RequestIDBDatabaseClear(int32 ipc_database_id, 155 int64 transaction_id, 156 int64 object_store_id, 157 WebKit::WebIDBCallbacks* callbacks); 158 159 virtual void CursorDestroyed(int32 ipc_cursor_id); 160 void DatabaseDestroyed(int32 ipc_database_id); 161 162 private: 163 FRIEND_TEST_ALL_PREFIXES(IndexedDBDispatcherTest, ValueSizeTest); 164 165 static int32 CurrentWorkerId() { 166 return webkit_glue::WorkerTaskRunner::Instance()->CurrentWorkerId(); 167 } 168 169 template <typename T> 170 void init_params(T& params, WebKit::WebIDBCallbacks* callbacks_ptr) { 171 scoped_ptr<WebKit::WebIDBCallbacks> callbacks(callbacks_ptr); 172 params.ipc_thread_id = CurrentWorkerId(); 173 params.ipc_callbacks_id = pending_callbacks_.Add(callbacks.release()); 174 } 175 176 // IDBCallback message handlers. 177 void OnSuccessIDBDatabase(int32 ipc_thread_id, 178 int32 ipc_callbacks_id, 179 int32 ipc_database_callbacks_id, 180 int32 ipc_object_id, 181 const IndexedDBDatabaseMetadata& idb_metadata); 182 void OnSuccessIndexedDBKey(int32 ipc_thread_id, 183 int32 ipc_callbacks_id, 184 const IndexedDBKey& key); 185 186 void OnSuccessOpenCursor( 187 const IndexedDBMsg_CallbacksSuccessIDBCursor_Params& p); 188 void OnSuccessCursorContinue( 189 const IndexedDBMsg_CallbacksSuccessCursorContinue_Params& p); 190 void OnSuccessCursorPrefetch( 191 const IndexedDBMsg_CallbacksSuccessCursorPrefetch_Params& p); 192 void OnSuccessStringList(int32 ipc_thread_id, 193 int32 ipc_callbacks_id, 194 const std::vector<string16>& value); 195 void OnSuccessValue(int32 ipc_thread_id, 196 int32 ipc_callbacks_id, 197 const std::string& value); 198 void OnSuccessValueWithKey(int32 ipc_thread_id, 199 int32 ipc_callbacks_id, 200 const std::string& value, 201 const IndexedDBKey& primary_key, 202 const IndexedDBKeyPath& key_path); 203 void OnSuccessInteger(int32 ipc_thread_id, 204 int32 ipc_callbacks_id, 205 int64 value); 206 void OnSuccessUndefined(int32 ipc_thread_id, int32 ipc_callbacks_id); 207 void OnError(int32 ipc_thread_id, 208 int32 ipc_callbacks_id, 209 int code, 210 const string16& message); 211 void OnIntBlocked(int32 ipc_thread_id, 212 int32 ipc_callbacks_id, 213 int64 existing_version); 214 void OnUpgradeNeeded(const IndexedDBMsg_CallbacksUpgradeNeeded_Params& p); 215 void OnAbort(int32 ipc_thread_id, 216 int32 ipc_database_id, 217 int64 transaction_id, 218 int code, 219 const string16& message); 220 void OnComplete(int32 ipc_thread_id, 221 int32 ipc_database_id, 222 int64 transaction_id); 223 void OnForcedClose(int32 ipc_thread_id, int32 ipc_database_id); 224 void OnIntVersionChange(int32 ipc_thread_id, 225 int32 ipc_database_id, 226 int64 old_version, 227 int64 new_version); 228 229 // Reset cursor prefetch caches for all cursors except exception_cursor_id. 230 void ResetCursorPrefetchCaches(int32 ipc_exception_cursor_id = -1); 231 232 scoped_refptr<ThreadSafeSender> thread_safe_sender_; 233 234 // Careful! WebIDBCallbacks wraps non-threadsafe data types. It must be 235 // destroyed and used on the same thread it was created on. 236 IDMap<WebKit::WebIDBCallbacks, IDMapOwnPointer> pending_callbacks_; 237 IDMap<WebKit::WebIDBDatabaseCallbacks, IDMapOwnPointer> 238 pending_database_callbacks_; 239 240 // Map from cursor id to RendererWebIDBCursorImpl. 241 std::map<int32, RendererWebIDBCursorImpl*> cursors_; 242 243 std::map<int32, RendererWebIDBDatabaseImpl*> databases_; 244 245 DISALLOW_COPY_AND_ASSIGN(IndexedDBDispatcher); 246}; 247 248} // namespace content 249 250#endif // CONTENT_CHILD_INDEXED_DB_INDEXED_DB_DISPATCHER_H_ 251