| OLD | NEW |
| 1 // Copyright (c) 2013 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2013 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "content/browser/indexed_db/indexed_db_factory_impl.h" | 5 #include "content/browser/indexed_db/indexed_db_factory_impl.h" |
| 6 | 6 |
| 7 #include <stdint.h> | 7 #include <stdint.h> |
| 8 | 8 |
| 9 #include <utility> | 9 #include <utility> |
| 10 #include <vector> | 10 #include <vector> |
| (...skipping 155 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 166 backing_stores_with_active_blobs_.erase(it); | 166 backing_stores_with_active_blobs_.erase(it); |
| 167 ReleaseBackingStore(origin, false /* immediate */); | 167 ReleaseBackingStore(origin, false /* immediate */); |
| 168 } | 168 } |
| 169 } | 169 } |
| 170 } | 170 } |
| 171 | 171 |
| 172 void IndexedDBFactoryImpl::GetDatabaseNames( | 172 void IndexedDBFactoryImpl::GetDatabaseNames( |
| 173 scoped_refptr<IndexedDBCallbacks> callbacks, | 173 scoped_refptr<IndexedDBCallbacks> callbacks, |
| 174 const Origin& origin, | 174 const Origin& origin, |
| 175 const base::FilePath& data_directory, | 175 const base::FilePath& data_directory, |
| 176 const IndexedDBDataFormatVersion& client_data_format_version, |
| 176 scoped_refptr<net::URLRequestContextGetter> request_context_getter) { | 177 scoped_refptr<net::URLRequestContextGetter> request_context_getter) { |
| 177 IDB_TRACE("IndexedDBFactoryImpl::GetDatabaseNames"); | 178 IDB_TRACE("IndexedDBFactoryImpl::GetDatabaseNames"); |
| 178 // TODO(dgrogan): Plumb data_loss back to script eventually? | 179 // TODO(dgrogan): Plumb data_loss back to script eventually? |
| 179 IndexedDBDataLossInfo data_loss_info; | 180 IndexedDBDataLossInfo data_loss_info; |
| 180 bool disk_full; | 181 bool disk_full; |
| 181 leveldb::Status s; | 182 leveldb::Status s; |
| 182 // TODO(cmumford): Handle this error | 183 // TODO(cmumford): Handle this error |
| 183 scoped_refptr<IndexedDBBackingStore> backing_store = | 184 scoped_refptr<IndexedDBBackingStore> backing_store = |
| 184 OpenBackingStore(origin, data_directory, request_context_getter, | 185 OpenBackingStore(origin, data_directory, client_data_format_version, |
| 185 &data_loss_info, &disk_full, &s); | 186 request_context_getter, &data_loss_info, &disk_full, &s); |
| 186 if (!backing_store.get()) { | 187 if (!backing_store.get()) { |
| 187 callbacks->OnError( | 188 callbacks->OnError( |
| 188 IndexedDBDatabaseError(blink::WebIDBDatabaseExceptionUnknownError, | 189 IndexedDBDatabaseError(blink::WebIDBDatabaseExceptionUnknownError, |
| 189 "Internal error opening backing store for " | 190 "Internal error opening backing store for " |
| 190 "indexedDB.webkitGetDatabaseNames.")); | 191 "indexedDB.webkitGetDatabaseNames.")); |
| 191 return; | 192 return; |
| 192 } | 193 } |
| 193 | 194 |
| 194 std::vector<base::string16> names = backing_store->GetDatabaseNames(&s); | 195 std::vector<base::string16> names = backing_store->GetDatabaseNames(&s); |
| 195 if (!s.ok()) { | 196 if (!s.ok()) { |
| (...skipping 11 matching lines...) Expand all Loading... |
| 207 backing_store = NULL; | 208 backing_store = NULL; |
| 208 ReleaseBackingStore(origin, false /* immediate */); | 209 ReleaseBackingStore(origin, false /* immediate */); |
| 209 } | 210 } |
| 210 | 211 |
| 211 void IndexedDBFactoryImpl::DeleteDatabase( | 212 void IndexedDBFactoryImpl::DeleteDatabase( |
| 212 const base::string16& name, | 213 const base::string16& name, |
| 213 scoped_refptr<net::URLRequestContextGetter> request_context_getter, | 214 scoped_refptr<net::URLRequestContextGetter> request_context_getter, |
| 214 scoped_refptr<IndexedDBCallbacks> callbacks, | 215 scoped_refptr<IndexedDBCallbacks> callbacks, |
| 215 const Origin& origin, | 216 const Origin& origin, |
| 216 const base::FilePath& data_directory, | 217 const base::FilePath& data_directory, |
| 218 const IndexedDBDataFormatVersion& client_data_format_version, |
| 217 bool force_close) { | 219 bool force_close) { |
| 218 IDB_TRACE("IndexedDBFactoryImpl::DeleteDatabase"); | 220 IDB_TRACE("IndexedDBFactoryImpl::DeleteDatabase"); |
| 219 IndexedDBDatabase::Identifier unique_identifier(origin, name); | 221 IndexedDBDatabase::Identifier unique_identifier(origin, name); |
| 220 const auto& it = database_map_.find(unique_identifier); | 222 const auto& it = database_map_.find(unique_identifier); |
| 221 if (it != database_map_.end()) { | 223 if (it != database_map_.end()) { |
| 222 // If there are any connections to the database, directly delete the | 224 // If there are any connections to the database, directly delete the |
| 223 // database. | 225 // database. |
| 224 it->second->DeleteDatabase(callbacks, force_close); | 226 it->second->DeleteDatabase(callbacks, force_close); |
| 225 return; | 227 return; |
| 226 } | 228 } |
| 227 | 229 |
| 228 // TODO(dgrogan): Plumb data_loss back to script eventually? | 230 // TODO(dgrogan): Plumb data_loss back to script eventually? |
| 229 IndexedDBDataLossInfo data_loss_info; | 231 IndexedDBDataLossInfo data_loss_info; |
| 230 bool disk_full = false; | 232 bool disk_full = false; |
| 231 leveldb::Status s; | 233 leveldb::Status s; |
| 232 scoped_refptr<IndexedDBBackingStore> backing_store = | 234 scoped_refptr<IndexedDBBackingStore> backing_store = |
| 233 OpenBackingStore(origin, data_directory, request_context_getter, | 235 OpenBackingStore(origin, data_directory, client_data_format_version, |
| 234 &data_loss_info, &disk_full, &s); | 236 request_context_getter, &data_loss_info, &disk_full, &s); |
| 235 if (!backing_store.get()) { | 237 if (!backing_store.get()) { |
| 236 IndexedDBDatabaseError error(blink::WebIDBDatabaseExceptionUnknownError, | 238 IndexedDBDatabaseError error(blink::WebIDBDatabaseExceptionUnknownError, |
| 237 ASCIIToUTF16( | 239 ASCIIToUTF16( |
| 238 "Internal error opening backing store " | 240 "Internal error opening backing store " |
| 239 "for indexedDB.deleteDatabase.")); | 241 "for indexedDB.deleteDatabase.")); |
| 240 callbacks->OnError(error); | 242 callbacks->OnError(error); |
| 241 if (s.IsCorruption()) { | 243 if (s.IsCorruption()) { |
| 242 HandleBackingStoreCorruption(origin, error); | 244 HandleBackingStoreCorruption(origin, error); |
| 243 } | 245 } |
| 244 return; | 246 return; |
| (...skipping 100 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 345 const auto& it = backing_store_map_.find(origin); | 347 const auto& it = backing_store_map_.find(origin); |
| 346 if (it == backing_store_map_.end()) | 348 if (it == backing_store_map_.end()) |
| 347 return false; | 349 return false; |
| 348 return it->second->close_timer()->IsRunning(); | 350 return it->second->close_timer()->IsRunning(); |
| 349 } | 351 } |
| 350 | 352 |
| 351 scoped_refptr<IndexedDBBackingStore> | 353 scoped_refptr<IndexedDBBackingStore> |
| 352 IndexedDBFactoryImpl::OpenBackingStoreHelper( | 354 IndexedDBFactoryImpl::OpenBackingStoreHelper( |
| 353 const Origin& origin, | 355 const Origin& origin, |
| 354 const base::FilePath& data_directory, | 356 const base::FilePath& data_directory, |
| 357 const IndexedDBDataFormatVersion& data_format_version, |
| 355 scoped_refptr<net::URLRequestContextGetter> request_context_getter, | 358 scoped_refptr<net::URLRequestContextGetter> request_context_getter, |
| 356 IndexedDBDataLossInfo* data_loss_info, | 359 IndexedDBDataLossInfo* data_loss_info, |
| 357 bool* disk_full, | 360 bool* disk_full, |
| 358 bool first_time, | 361 bool first_time, |
| 359 leveldb::Status* status) { | 362 leveldb::Status* status) { |
| 360 return IndexedDBBackingStore::Open( | 363 return IndexedDBBackingStore::Open( |
| 361 this, origin, data_directory, request_context_getter, data_loss_info, | 364 this, origin, data_directory, data_format_version, request_context_getter, |
| 362 disk_full, context_->TaskRunner(), first_time, status); | 365 data_loss_info, disk_full, context_->TaskRunner(), first_time, status); |
| 363 } | 366 } |
| 364 | 367 |
| 365 scoped_refptr<IndexedDBBackingStore> IndexedDBFactoryImpl::OpenBackingStore( | 368 scoped_refptr<IndexedDBBackingStore> IndexedDBFactoryImpl::OpenBackingStore( |
| 366 const Origin& origin, | 369 const Origin& origin, |
| 367 const base::FilePath& data_directory, | 370 const base::FilePath& data_directory, |
| 371 const IndexedDBDataFormatVersion& data_format_version, |
| 368 scoped_refptr<net::URLRequestContextGetter> request_context_getter, | 372 scoped_refptr<net::URLRequestContextGetter> request_context_getter, |
| 369 IndexedDBDataLossInfo* data_loss_info, | 373 IndexedDBDataLossInfo* data_loss_info, |
| 370 bool* disk_full, | 374 bool* disk_full, |
| 371 leveldb::Status* status) { | 375 leveldb::Status* status) { |
| 372 const bool open_in_memory = data_directory.empty(); | 376 const bool open_in_memory = data_directory.empty(); |
| 373 | 377 |
| 374 const auto& it2 = backing_store_map_.find(origin); | 378 const auto& it2 = backing_store_map_.find(origin); |
| 375 if (it2 != backing_store_map_.end()) { | 379 if (it2 != backing_store_map_.end()) { |
| 376 it2->second->close_timer()->Stop(); | 380 scoped_refptr<IndexedDBBackingStore> backing_store = it2->second; |
| 377 return it2->second; | 381 if (backing_store->data_format_version() != data_format_version) { |
| 382 LOG(ERROR) << "IndexedDB backing store already open with a different " |
| 383 "data format version."; |
| 384 } |
| 385 backing_store->close_timer()->Stop(); |
| 386 return backing_store; |
| 378 } | 387 } |
| 379 | 388 |
| 380 scoped_refptr<IndexedDBBackingStore> backing_store; | 389 scoped_refptr<IndexedDBBackingStore> backing_store; |
| 381 bool first_time = false; | 390 bool first_time = false; |
| 382 if (open_in_memory) { | 391 if (open_in_memory) { |
| 383 backing_store = IndexedDBBackingStore::OpenInMemory( | 392 backing_store = IndexedDBBackingStore::OpenInMemory( |
| 384 origin, context_->TaskRunner(), status); | 393 origin, data_format_version, context_->TaskRunner(), status); |
| 385 } else { | 394 } else { |
| 386 first_time = !backends_opened_since_boot_.count(origin); | 395 first_time = !backends_opened_since_boot_.count(origin); |
| 387 | 396 |
| 388 backing_store = | 397 backing_store = OpenBackingStoreHelper( |
| 389 OpenBackingStoreHelper(origin, data_directory, request_context_getter, | 398 origin, data_directory, data_format_version, request_context_getter, |
| 390 data_loss_info, disk_full, first_time, status); | 399 data_loss_info, disk_full, first_time, status); |
| 391 } | 400 } |
| 392 | 401 |
| 393 if (backing_store.get()) { | 402 if (backing_store.get()) { |
| 394 if (first_time) | 403 if (first_time) |
| 395 backends_opened_since_boot_.insert(origin); | 404 backends_opened_since_boot_.insert(origin); |
| 396 backing_store_map_[origin] = backing_store; | 405 backing_store_map_[origin] = backing_store; |
| 397 // If an in-memory database, bind lifetime to this factory instance. | 406 // If an in-memory database, bind lifetime to this factory instance. |
| 398 if (open_in_memory) | 407 if (open_in_memory) |
| 399 session_only_backing_stores_.insert(backing_store); | 408 session_only_backing_stores_.insert(backing_store); |
| 400 | 409 |
| 401 // All backing stores associated with this factory should be of the same | 410 // All backing stores associated with this factory should be of the same |
| 402 // type. | 411 // type. |
| 403 DCHECK_NE(session_only_backing_stores_.empty(), open_in_memory); | 412 DCHECK_NE(session_only_backing_stores_.empty(), open_in_memory); |
| 404 | 413 |
| 405 return backing_store; | 414 return backing_store; |
| 406 } | 415 } |
| 407 | 416 |
| 408 return 0; | 417 return 0; |
| 409 } | 418 } |
| 410 | 419 |
| 411 void IndexedDBFactoryImpl::Open( | 420 void IndexedDBFactoryImpl::Open( |
| 412 const base::string16& name, | 421 const base::string16& name, |
| 413 std::unique_ptr<IndexedDBPendingConnection> connection, | 422 std::unique_ptr<IndexedDBPendingConnection> connection, |
| 414 scoped_refptr<net::URLRequestContextGetter> request_context_getter, | 423 scoped_refptr<net::URLRequestContextGetter> request_context_getter, |
| 415 const Origin& origin, | 424 const Origin& origin, |
| 416 const base::FilePath& data_directory) { | 425 const base::FilePath& data_directory, |
| 426 const IndexedDBDataFormatVersion& client_data_format_version) { |
| 417 IDB_TRACE("IndexedDBFactoryImpl::Open"); | 427 IDB_TRACE("IndexedDBFactoryImpl::Open"); |
| 418 scoped_refptr<IndexedDBDatabase> database; | 428 scoped_refptr<IndexedDBDatabase> database; |
| 419 IndexedDBDatabase::Identifier unique_identifier(origin, name); | 429 IndexedDBDatabase::Identifier unique_identifier(origin, name); |
| 420 const auto& it = database_map_.find(unique_identifier); | 430 const auto& it = database_map_.find(unique_identifier); |
| 421 IndexedDBDataLossInfo data_loss_info; | 431 IndexedDBDataLossInfo data_loss_info; |
| 422 bool disk_full = false; | 432 bool disk_full = false; |
| 423 bool was_open = (it != database_map_.end()); | 433 bool was_open = (it != database_map_.end()); |
| 424 if (!was_open) { | 434 if (!was_open) { |
| 425 leveldb::Status s; | 435 leveldb::Status s; |
| 426 scoped_refptr<IndexedDBBackingStore> backing_store = | 436 scoped_refptr<IndexedDBBackingStore> backing_store = OpenBackingStore( |
| 427 OpenBackingStore(origin, data_directory, request_context_getter, | 437 origin, data_directory, client_data_format_version, |
| 428 &data_loss_info, &disk_full, &s); | 438 request_context_getter, &data_loss_info, &disk_full, &s); |
| 429 if (!backing_store.get()) { | 439 if (!backing_store.get()) { |
| 430 if (disk_full) { | 440 if (disk_full) { |
| 431 connection->callbacks->OnError(IndexedDBDatabaseError( | 441 connection->callbacks->OnError(IndexedDBDatabaseError( |
| 432 blink::WebIDBDatabaseExceptionQuotaError, | 442 blink::WebIDBDatabaseExceptionQuotaError, |
| 433 ASCIIToUTF16("Encountered full disk while opening " | 443 ASCIIToUTF16("Encountered full disk while opening " |
| 434 "backing store for indexedDB.open."))); | 444 "backing store for indexedDB.open."))); |
| 435 return; | 445 return; |
| 436 } | 446 } |
| 437 IndexedDBDatabaseError error(blink::WebIDBDatabaseExceptionUnknownError, | 447 IndexedDBDatabaseError error(blink::WebIDBDatabaseExceptionUnknownError, |
| 438 ASCIIToUTF16( | 448 ASCIIToUTF16( |
| (...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 485 size_t count(0); | 495 size_t count(0); |
| 486 | 496 |
| 487 OriginDBs range = GetOpenDatabasesForOrigin(origin); | 497 OriginDBs range = GetOpenDatabasesForOrigin(origin); |
| 488 for (OriginDBMapIterator it = range.first; it != range.second; ++it) | 498 for (OriginDBMapIterator it = range.first; it != range.second; ++it) |
| 489 count += it->second->ConnectionCount(); | 499 count += it->second->ConnectionCount(); |
| 490 | 500 |
| 491 return count; | 501 return count; |
| 492 } | 502 } |
| 493 | 503 |
| 494 } // namespace content | 504 } // namespace content |
| OLD | NEW |