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_backing_store.h" | 5 #include "content/browser/indexed_db/indexed_db_backing_store.h" |
6 | 6 |
7 #include "base/file_util.h" | 7 #include "base/file_util.h" |
8 #include "base/files/file_path.h" | 8 #include "base/files/file_path.h" |
9 #include "base/format_macros.h" | 9 #include "base/format_macros.h" |
10 #include "base/json/json_reader.h" | 10 #include "base/json/json_reader.h" |
(...skipping 690 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
701 return true; | 701 return true; |
702 } | 702 } |
703 | 703 |
704 IndexedDBBackingStore::IndexedDBBackingStore( | 704 IndexedDBBackingStore::IndexedDBBackingStore( |
705 IndexedDBFactory* indexed_db_factory, | 705 IndexedDBFactory* indexed_db_factory, |
706 const GURL& origin_url, | 706 const GURL& origin_url, |
707 const base::FilePath& blob_path, | 707 const base::FilePath& blob_path, |
708 net::URLRequestContext* request_context, | 708 net::URLRequestContext* request_context, |
709 scoped_ptr<LevelDBDatabase> db, | 709 scoped_ptr<LevelDBDatabase> db, |
710 scoped_ptr<LevelDBComparator> comparator, | 710 scoped_ptr<LevelDBComparator> comparator, |
711 base::TaskRunner* task_runner) | 711 base::SequencedTaskRunner* task_runner) |
712 : indexed_db_factory_(indexed_db_factory), | 712 : indexed_db_factory_(indexed_db_factory), |
713 origin_url_(origin_url), | 713 origin_url_(origin_url), |
714 blob_path_(blob_path), | 714 blob_path_(blob_path), |
715 origin_identifier_(ComputeOriginIdentifier(origin_url)), | 715 origin_identifier_(ComputeOriginIdentifier(origin_url)), |
716 request_context_(request_context), | 716 request_context_(request_context), |
717 task_runner_(task_runner), | 717 task_runner_(task_runner), |
718 db_(db.Pass()), | 718 db_(db.Pass()), |
719 comparator_(comparator.Pass()), | 719 comparator_(comparator.Pass()), |
720 active_blob_registry_(this) { | 720 active_blob_registry_(this) { |
721 } | 721 } |
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
773 | 773 |
774 // static | 774 // static |
775 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::Open( | 775 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::Open( |
776 IndexedDBFactory* indexed_db_factory, | 776 IndexedDBFactory* indexed_db_factory, |
777 const GURL& origin_url, | 777 const GURL& origin_url, |
778 const base::FilePath& path_base, | 778 const base::FilePath& path_base, |
779 net::URLRequestContext* request_context, | 779 net::URLRequestContext* request_context, |
780 blink::WebIDBDataLoss* data_loss, | 780 blink::WebIDBDataLoss* data_loss, |
781 std::string* data_loss_message, | 781 std::string* data_loss_message, |
782 bool* disk_full, | 782 bool* disk_full, |
783 base::TaskRunner* task_runner, | 783 base::SequencedTaskRunner* task_runner, |
784 bool clean_journal, | 784 bool clean_journal, |
785 leveldb::Status* status) { | 785 leveldb::Status* status) { |
786 *data_loss = blink::WebIDBDataLossNone; | 786 *data_loss = blink::WebIDBDataLossNone; |
787 DefaultLevelDBFactory leveldb_factory; | 787 DefaultLevelDBFactory leveldb_factory; |
788 return IndexedDBBackingStore::Open(indexed_db_factory, | 788 return IndexedDBBackingStore::Open(indexed_db_factory, |
789 origin_url, | 789 origin_url, |
790 path_base, | 790 path_base, |
791 request_context, | 791 request_context, |
792 data_loss, | 792 data_loss, |
793 data_loss_message, | 793 data_loss_message, |
(...skipping 134 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
928 // static | 928 // static |
929 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::Open( | 929 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::Open( |
930 IndexedDBFactory* indexed_db_factory, | 930 IndexedDBFactory* indexed_db_factory, |
931 const GURL& origin_url, | 931 const GURL& origin_url, |
932 const base::FilePath& path_base, | 932 const base::FilePath& path_base, |
933 net::URLRequestContext* request_context, | 933 net::URLRequestContext* request_context, |
934 blink::WebIDBDataLoss* data_loss, | 934 blink::WebIDBDataLoss* data_loss, |
935 std::string* data_loss_message, | 935 std::string* data_loss_message, |
936 bool* is_disk_full, | 936 bool* is_disk_full, |
937 LevelDBFactory* leveldb_factory, | 937 LevelDBFactory* leveldb_factory, |
938 base::TaskRunner* task_runner, | 938 base::SequencedTaskRunner* task_runner, |
939 bool clean_journal, | 939 bool clean_journal, |
940 leveldb::Status* status) { | 940 leveldb::Status* status) { |
941 IDB_TRACE("IndexedDBBackingStore::Open"); | 941 IDB_TRACE("IndexedDBBackingStore::Open"); |
942 DCHECK(!path_base.empty()); | 942 DCHECK(!path_base.empty()); |
943 *data_loss = blink::WebIDBDataLossNone; | 943 *data_loss = blink::WebIDBDataLossNone; |
944 *data_loss_message = ""; | 944 *data_loss_message = ""; |
945 *is_disk_full = false; | 945 *is_disk_full = false; |
946 | 946 |
947 *status = leveldb::Status::OK(); | 947 *status = leveldb::Status::OK(); |
948 | 948 |
(...skipping 126 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1075 HistogramOpenStatus( | 1075 HistogramOpenStatus( |
1076 INDEXED_DB_BACKING_STORE_OPEN_FAILED_CLEANUP_JOURNAL_ERROR, origin_url); | 1076 INDEXED_DB_BACKING_STORE_OPEN_FAILED_CLEANUP_JOURNAL_ERROR, origin_url); |
1077 return scoped_refptr<IndexedDBBackingStore>(); | 1077 return scoped_refptr<IndexedDBBackingStore>(); |
1078 } | 1078 } |
1079 return backing_store; | 1079 return backing_store; |
1080 } | 1080 } |
1081 | 1081 |
1082 // static | 1082 // static |
1083 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::OpenInMemory( | 1083 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::OpenInMemory( |
1084 const GURL& origin_url, | 1084 const GURL& origin_url, |
1085 base::TaskRunner* task_runner, | 1085 base::SequencedTaskRunner* task_runner, |
1086 leveldb::Status* status) { | 1086 leveldb::Status* status) { |
1087 DefaultLevelDBFactory leveldb_factory; | 1087 DefaultLevelDBFactory leveldb_factory; |
1088 return IndexedDBBackingStore::OpenInMemory( | 1088 return IndexedDBBackingStore::OpenInMemory( |
1089 origin_url, &leveldb_factory, task_runner, status); | 1089 origin_url, &leveldb_factory, task_runner, status); |
1090 } | 1090 } |
1091 | 1091 |
1092 // static | 1092 // static |
1093 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::OpenInMemory( | 1093 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::OpenInMemory( |
1094 const GURL& origin_url, | 1094 const GURL& origin_url, |
1095 LevelDBFactory* leveldb_factory, | 1095 LevelDBFactory* leveldb_factory, |
1096 base::TaskRunner* task_runner, | 1096 base::SequencedTaskRunner* task_runner, |
1097 leveldb::Status* status) { | 1097 leveldb::Status* status) { |
1098 IDB_TRACE("IndexedDBBackingStore::OpenInMemory"); | 1098 IDB_TRACE("IndexedDBBackingStore::OpenInMemory"); |
1099 | 1099 |
1100 scoped_ptr<LevelDBComparator> comparator(new Comparator()); | 1100 scoped_ptr<LevelDBComparator> comparator(new Comparator()); |
1101 scoped_ptr<LevelDBDatabase> db = | 1101 scoped_ptr<LevelDBDatabase> db = |
1102 LevelDBDatabase::OpenInMemory(comparator.get()); | 1102 LevelDBDatabase::OpenInMemory(comparator.get()); |
1103 if (!db) { | 1103 if (!db) { |
1104 LOG(ERROR) << "LevelDBDatabase::OpenInMemory failed."; | 1104 LOG(ERROR) << "LevelDBDatabase::OpenInMemory failed."; |
1105 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_MEMORY_FAILED, | 1105 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_MEMORY_FAILED, |
1106 origin_url); | 1106 origin_url); |
(...skipping 12 matching lines...) Expand all Loading... |
1119 } | 1119 } |
1120 | 1120 |
1121 // static | 1121 // static |
1122 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::Create( | 1122 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::Create( |
1123 IndexedDBFactory* indexed_db_factory, | 1123 IndexedDBFactory* indexed_db_factory, |
1124 const GURL& origin_url, | 1124 const GURL& origin_url, |
1125 const base::FilePath& blob_path, | 1125 const base::FilePath& blob_path, |
1126 net::URLRequestContext* request_context, | 1126 net::URLRequestContext* request_context, |
1127 scoped_ptr<LevelDBDatabase> db, | 1127 scoped_ptr<LevelDBDatabase> db, |
1128 scoped_ptr<LevelDBComparator> comparator, | 1128 scoped_ptr<LevelDBComparator> comparator, |
1129 base::TaskRunner* task_runner, | 1129 base::SequencedTaskRunner* task_runner, |
1130 leveldb::Status* status) { | 1130 leveldb::Status* status) { |
1131 // TODO(jsbell): Handle comparator name changes. | 1131 // TODO(jsbell): Handle comparator name changes. |
1132 scoped_refptr<IndexedDBBackingStore> backing_store( | 1132 scoped_refptr<IndexedDBBackingStore> backing_store( |
1133 new IndexedDBBackingStore(indexed_db_factory, | 1133 new IndexedDBBackingStore(indexed_db_factory, |
1134 origin_url, | 1134 origin_url, |
1135 blob_path, | 1135 blob_path, |
1136 request_context, | 1136 request_context, |
1137 db.Pass(), | 1137 db.Pass(), |
1138 comparator.Pass(), | 1138 comparator.Pass(), |
1139 task_runner)); | 1139 task_runner)); |
(...skipping 1106 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2246 int64 database_id_; | 2246 int64 database_id_; |
2247 IndexedDBBackingStore* backing_store_; | 2247 IndexedDBBackingStore* backing_store_; |
2248 scoped_refptr<IndexedDBBackingStore::BlobWriteCallback> callback_; | 2248 scoped_refptr<IndexedDBBackingStore::BlobWriteCallback> callback_; |
2249 scoped_ptr<FileWriterDelegate> delegate_; | 2249 scoped_ptr<FileWriterDelegate> delegate_; |
2250 bool aborted_; | 2250 bool aborted_; |
2251 | 2251 |
2252 DISALLOW_COPY_AND_ASSIGN(ChainedBlobWriterImpl); | 2252 DISALLOW_COPY_AND_ASSIGN(ChainedBlobWriterImpl); |
2253 }; | 2253 }; |
2254 | 2254 |
2255 class LocalWriteClosure : public FileWriterDelegate::DelegateWriteCallback, | 2255 class LocalWriteClosure : public FileWriterDelegate::DelegateWriteCallback, |
2256 public base::RefCounted<LocalWriteClosure> { | 2256 public base::RefCountedThreadSafe<LocalWriteClosure> { |
2257 public: | 2257 public: |
2258 LocalWriteClosure(IndexedDBBackingStore::Transaction::ChainedBlobWriter* | 2258 LocalWriteClosure(IndexedDBBackingStore::Transaction::ChainedBlobWriter* |
2259 chained_blob_writer, | 2259 chained_blob_writer, |
2260 base::TaskRunner* task_runner) | 2260 base::SequencedTaskRunner* task_runner) |
2261 : chained_blob_writer_(chained_blob_writer), | 2261 : chained_blob_writer_(chained_blob_writer), |
2262 task_runner_(task_runner), | 2262 task_runner_(task_runner), |
2263 bytes_written_(0) {} | 2263 bytes_written_(0) {} |
2264 | 2264 |
2265 void Run(base::File::Error rv, | 2265 void Run(base::File::Error rv, |
2266 int64 bytes, | 2266 int64 bytes, |
2267 FileWriterDelegate::WriteProgressStatus write_status) { | 2267 FileWriterDelegate::WriteProgressStatus write_status) { |
2268 DCHECK_GE(bytes, 0); | 2268 DCHECK_GE(bytes, 0); |
2269 bytes_written_ += bytes; | 2269 bytes_written_ += bytes; |
2270 if (write_status == FileWriterDelegate::SUCCESS_IO_PENDING) | 2270 if (write_status == FileWriterDelegate::SUCCESS_IO_PENDING) |
2271 return; // We don't care about progress events. | 2271 return; // We don't care about progress events. |
2272 if (rv == base::File::FILE_OK) { | 2272 if (rv == base::File::FILE_OK) { |
2273 DCHECK_EQ(write_status, FileWriterDelegate::SUCCESS_COMPLETED); | 2273 DCHECK_EQ(write_status, FileWriterDelegate::SUCCESS_COMPLETED); |
2274 } else { | 2274 } else { |
2275 DCHECK(write_status == FileWriterDelegate::ERROR_WRITE_STARTED || | 2275 DCHECK(write_status == FileWriterDelegate::ERROR_WRITE_STARTED || |
2276 write_status == FileWriterDelegate::ERROR_WRITE_NOT_STARTED); | 2276 write_status == FileWriterDelegate::ERROR_WRITE_NOT_STARTED); |
2277 } | 2277 } |
2278 task_runner_->PostTask( | 2278 task_runner_->PostTask( |
2279 FROM_HERE, | 2279 FROM_HERE, |
2280 base::Bind(&LocalWriteClosure::callBlobCallbackOnIDBTaskRunner, | 2280 base::Bind(&IndexedDBBackingStore::Transaction::ChainedBlobWriter:: |
2281 this, | 2281 ReportWriteCompletion, |
2282 write_status == FileWriterDelegate::SUCCESS_COMPLETED)); | 2282 chained_blob_writer_, |
| 2283 write_status == FileWriterDelegate::SUCCESS_COMPLETED, |
| 2284 bytes_written_)); |
2283 } | 2285 } |
2284 | 2286 |
2285 void writeBlobToFileOnIOThread(const FilePath& file_path, | 2287 void writeBlobToFileOnIOThread(const FilePath& file_path, |
2286 const GURL& blob_url, | 2288 const GURL& blob_url, |
2287 net::URLRequestContext* request_context) { | 2289 net::URLRequestContext* request_context) { |
2288 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::IO)); | 2290 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::IO)); |
2289 scoped_ptr<fileapi::FileStreamWriter> writer( | 2291 scoped_ptr<fileapi::FileStreamWriter> writer( |
2290 fileapi::FileStreamWriter::CreateForLocalFile( | 2292 fileapi::FileStreamWriter::CreateForLocalFile( |
2291 task_runner_, file_path, 0, | 2293 task_runner_, file_path, 0, |
2292 fileapi::FileStreamWriter::CREATE_NEW_FILE)); | 2294 fileapi::FileStreamWriter::CREATE_NEW_FILE)); |
2293 scoped_ptr<FileWriterDelegate> delegate( | 2295 scoped_ptr<FileWriterDelegate> delegate( |
2294 new FileWriterDelegate(writer.Pass(), | 2296 new FileWriterDelegate(writer.Pass(), |
2295 FileWriterDelegate::FLUSH_ON_COMPLETION)); | 2297 FileWriterDelegate::FLUSH_ON_COMPLETION)); |
2296 | 2298 |
2297 DCHECK(blob_url.is_valid()); | 2299 DCHECK(blob_url.is_valid()); |
2298 scoped_ptr<net::URLRequest> blob_request(request_context->CreateRequest( | 2300 scoped_ptr<net::URLRequest> blob_request(request_context->CreateRequest( |
2299 blob_url, net::DEFAULT_PRIORITY, delegate.get(), NULL)); | 2301 blob_url, net::DEFAULT_PRIORITY, delegate.get(), NULL)); |
2300 | 2302 |
2301 delegate->Start(blob_request.Pass(), | 2303 delegate->Start(blob_request.Pass(), |
2302 base::Bind(&LocalWriteClosure::Run, this)); | 2304 base::Bind(&LocalWriteClosure::Run, this)); |
2303 chained_blob_writer_->set_delegate(delegate.Pass()); | 2305 chained_blob_writer_->set_delegate(delegate.Pass()); |
2304 } | 2306 } |
2305 | 2307 |
2306 private: | 2308 private: |
2307 virtual ~LocalWriteClosure() {} | 2309 virtual ~LocalWriteClosure() { |
2308 friend class base::RefCounted<LocalWriteClosure>; | 2310 // Make sure the last reference to a ChainedBlobWriter is released (and |
| 2311 // deleted) on the IDB thread since it owns a transaction which has thread |
| 2312 // affinity. |
| 2313 IndexedDBBackingStore::Transaction::ChainedBlobWriter* raw_tmp = |
| 2314 chained_blob_writer_.get(); |
| 2315 raw_tmp->AddRef(); |
| 2316 chained_blob_writer_ = NULL; |
| 2317 task_runner_->ReleaseSoon(FROM_HERE, raw_tmp); |
| 2318 } |
| 2319 friend class base::RefCountedThreadSafe<LocalWriteClosure>; |
2309 | 2320 |
2310 void callBlobCallbackOnIDBTaskRunner(bool succeeded) { | 2321 scoped_refptr<IndexedDBBackingStore::Transaction::ChainedBlobWriter> |
2311 DCHECK(task_runner_->RunsTasksOnCurrentThread()); | 2322 chained_blob_writer_; |
2312 chained_blob_writer_->ReportWriteCompletion(succeeded, bytes_written_); | 2323 scoped_refptr<base::SequencedTaskRunner> task_runner_; |
2313 } | |
2314 | |
2315 IndexedDBBackingStore::Transaction::ChainedBlobWriter* chained_blob_writer_; | |
2316 base::TaskRunner* task_runner_; | |
2317 int64 bytes_written_; | 2324 int64 bytes_written_; |
2318 | 2325 |
2319 DISALLOW_COPY_AND_ASSIGN(LocalWriteClosure); | 2326 DISALLOW_COPY_AND_ASSIGN(LocalWriteClosure); |
2320 }; | 2327 }; |
2321 | 2328 |
2322 bool IndexedDBBackingStore::WriteBlobFile( | 2329 bool IndexedDBBackingStore::WriteBlobFile( |
2323 int64 database_id, | 2330 int64 database_id, |
2324 const Transaction::WriteDescriptor& descriptor, | 2331 const Transaction::WriteDescriptor& descriptor, |
2325 Transaction::ChainedBlobWriter* chained_blob_writer) { | 2332 Transaction::ChainedBlobWriter* chained_blob_writer) { |
2326 | 2333 |
(...skipping 1932 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4259 int64_t size, | 4266 int64_t size, |
4260 base::Time last_modified) | 4267 base::Time last_modified) |
4261 : is_file_(true), | 4268 : is_file_(true), |
4262 file_path_(file_path), | 4269 file_path_(file_path), |
4263 key_(key), | 4270 key_(key), |
4264 size_(size), | 4271 size_(size), |
4265 last_modified_(last_modified) { | 4272 last_modified_(last_modified) { |
4266 } | 4273 } |
4267 | 4274 |
4268 } // namespace content | 4275 } // namespace content |
OLD | NEW |