| 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 <algorithm> | 7 #include <algorithm> |
| 8 #include <utility> | 8 #include <utility> |
| 9 | 9 |
| 10 #include "base/files/file_path.h" | 10 #include "base/files/file_path.h" |
| (...skipping 68 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 79 return path; | 79 return path; |
| 80 } | 80 } |
| 81 | 81 |
| 82 bool MakeIDBBlobDirectory(const FilePath& path_base, | 82 bool MakeIDBBlobDirectory(const FilePath& path_base, |
| 83 int64_t database_id, | 83 int64_t database_id, |
| 84 int64_t key) { | 84 int64_t key) { |
| 85 FilePath path = GetBlobDirectoryNameForKey(path_base, database_id, key); | 85 FilePath path = GetBlobDirectoryNameForKey(path_base, database_id, key); |
| 86 return base::CreateDirectory(path); | 86 return base::CreateDirectory(path); |
| 87 } | 87 } |
| 88 | 88 |
| 89 static std::string ComputeOriginIdentifier(const GURL& origin_url) { | 89 static std::string ComputeOriginIdentifier(const url::Origin& origin) { |
| 90 return storage::GetIdentifierFromOrigin(origin_url) + "@1"; | 90 return storage::GetIdentifierFromOrigin(GURL(origin.Serialize())) + "@1"; |
| 91 } | 91 } |
| 92 | 92 |
| 93 static FilePath ComputeCorruptionFileName(const GURL& origin_url) { | 93 static FilePath ComputeCorruptionFileName(const url::Origin& origin) { |
| 94 return IndexedDBContextImpl::GetLevelDBFileName(origin_url) | 94 return IndexedDBContextImpl::GetLevelDBFileName(origin).Append( |
| 95 .Append(FILE_PATH_LITERAL("corruption_info.json")); | 95 FILE_PATH_LITERAL("corruption_info.json")); |
| 96 } | 96 } |
| 97 | 97 |
| 98 } // namespace | 98 } // namespace |
| 99 | 99 |
| 100 static const int64_t kKeyGeneratorInitialNumber = | 100 static const int64_t kKeyGeneratorInitialNumber = |
| 101 1; // From the IndexedDB specification. | 101 1; // From the IndexedDB specification. |
| 102 | 102 |
| 103 enum IndexedDBBackingStoreErrorSource { | 103 enum IndexedDBBackingStoreErrorSource { |
| 104 // 0 - 2 are no longer used. | 104 // 0 - 2 are no longer used. |
| 105 FIND_KEY_IN_INDEX = 3, | 105 FIND_KEY_IN_INDEX = 3, |
| (...skipping 632 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 738 ret.push_back(IndexedDBBlobInfo(type, static_cast<uint64_t>(size), key)); | 738 ret.push_back(IndexedDBBlobInfo(type, static_cast<uint64_t>(size), key)); |
| 739 } | 739 } |
| 740 } | 740 } |
| 741 output->swap(ret); | 741 output->swap(ret); |
| 742 | 742 |
| 743 return true; | 743 return true; |
| 744 } | 744 } |
| 745 | 745 |
| 746 IndexedDBBackingStore::IndexedDBBackingStore( | 746 IndexedDBBackingStore::IndexedDBBackingStore( |
| 747 IndexedDBFactory* indexed_db_factory, | 747 IndexedDBFactory* indexed_db_factory, |
| 748 const GURL& origin_url, | 748 const url::Origin& origin, |
| 749 const base::FilePath& blob_path, | 749 const base::FilePath& blob_path, |
| 750 net::URLRequestContext* request_context, | 750 net::URLRequestContext* request_context, |
| 751 scoped_ptr<LevelDBDatabase> db, | 751 scoped_ptr<LevelDBDatabase> db, |
| 752 scoped_ptr<LevelDBComparator> comparator, | 752 scoped_ptr<LevelDBComparator> comparator, |
| 753 base::SequencedTaskRunner* task_runner) | 753 base::SequencedTaskRunner* task_runner) |
| 754 : indexed_db_factory_(indexed_db_factory), | 754 : indexed_db_factory_(indexed_db_factory), |
| 755 origin_url_(origin_url), | 755 origin_(origin), |
| 756 blob_path_(blob_path), | 756 blob_path_(blob_path), |
| 757 origin_identifier_(ComputeOriginIdentifier(origin_url)), | 757 origin_identifier_(ComputeOriginIdentifier(origin)), |
| 758 request_context_(request_context), | 758 request_context_(request_context), |
| 759 task_runner_(task_runner), | 759 task_runner_(task_runner), |
| 760 db_(std::move(db)), | 760 db_(std::move(db)), |
| 761 comparator_(std::move(comparator)), | 761 comparator_(std::move(comparator)), |
| 762 active_blob_registry_(this), | 762 active_blob_registry_(this), |
| 763 committing_transaction_count_(0) {} | 763 committing_transaction_count_(0) {} |
| 764 | 764 |
| 765 IndexedDBBackingStore::~IndexedDBBackingStore() { | 765 IndexedDBBackingStore::~IndexedDBBackingStore() { |
| 766 if (!blob_path_.empty() && !child_process_ids_granted_.empty()) { | 766 if (!blob_path_.empty() && !child_process_ids_granted_.empty()) { |
| 767 ChildProcessSecurityPolicyImpl* policy = | 767 ChildProcessSecurityPolicyImpl* policy = |
| (...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 808 INDEXED_DB_BACKING_STORE_OPEN_ORIGIN_TOO_LONG, | 808 INDEXED_DB_BACKING_STORE_OPEN_ORIGIN_TOO_LONG, |
| 809 INDEXED_DB_BACKING_STORE_OPEN_NO_RECOVERY, | 809 INDEXED_DB_BACKING_STORE_OPEN_NO_RECOVERY, |
| 810 INDEXED_DB_BACKING_STORE_OPEN_FAILED_PRIOR_CORRUPTION, | 810 INDEXED_DB_BACKING_STORE_OPEN_FAILED_PRIOR_CORRUPTION, |
| 811 INDEXED_DB_BACKING_STORE_OPEN_FAILED_CLEANUP_JOURNAL_ERROR, | 811 INDEXED_DB_BACKING_STORE_OPEN_FAILED_CLEANUP_JOURNAL_ERROR, |
| 812 INDEXED_DB_BACKING_STORE_OPEN_MAX, | 812 INDEXED_DB_BACKING_STORE_OPEN_MAX, |
| 813 }; | 813 }; |
| 814 | 814 |
| 815 // static | 815 // static |
| 816 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::Open( | 816 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::Open( |
| 817 IndexedDBFactory* indexed_db_factory, | 817 IndexedDBFactory* indexed_db_factory, |
| 818 const GURL& origin_url, | 818 const url::Origin& origin, |
| 819 const base::FilePath& path_base, | 819 const base::FilePath& path_base, |
| 820 net::URLRequestContext* request_context, | 820 net::URLRequestContext* request_context, |
| 821 blink::WebIDBDataLoss* data_loss, | 821 blink::WebIDBDataLoss* data_loss, |
| 822 std::string* data_loss_message, | 822 std::string* data_loss_message, |
| 823 bool* disk_full, | 823 bool* disk_full, |
| 824 base::SequencedTaskRunner* task_runner, | 824 base::SequencedTaskRunner* task_runner, |
| 825 bool clean_journal, | 825 bool clean_journal, |
| 826 leveldb::Status* status) { | 826 leveldb::Status* status) { |
| 827 *data_loss = blink::WebIDBDataLossNone; | 827 *data_loss = blink::WebIDBDataLossNone; |
| 828 DefaultLevelDBFactory leveldb_factory; | 828 DefaultLevelDBFactory leveldb_factory; |
| 829 return IndexedDBBackingStore::Open(indexed_db_factory, | 829 return IndexedDBBackingStore::Open( |
| 830 origin_url, | 830 indexed_db_factory, origin, path_base, request_context, data_loss, |
| 831 path_base, | 831 data_loss_message, disk_full, &leveldb_factory, task_runner, |
| 832 request_context, | 832 clean_journal, status); |
| 833 data_loss, | |
| 834 data_loss_message, | |
| 835 disk_full, | |
| 836 &leveldb_factory, | |
| 837 task_runner, | |
| 838 clean_journal, | |
| 839 status); | |
| 840 } | 833 } |
| 841 | 834 |
| 842 static std::string OriginToCustomHistogramSuffix(const GURL& origin_url) { | 835 static std::string OriginToCustomHistogramSuffix(const url::Origin& origin) { |
| 843 if (origin_url.host() == "docs.google.com") | 836 if (origin.host() == "docs.google.com") |
| 844 return ".Docs"; | 837 return ".Docs"; |
| 845 return std::string(); | 838 return std::string(); |
| 846 } | 839 } |
| 847 | 840 |
| 848 static void HistogramOpenStatus(IndexedDBBackingStoreOpenResult result, | 841 static void HistogramOpenStatus(IndexedDBBackingStoreOpenResult result, |
| 849 const GURL& origin_url) { | 842 const url::Origin& origin) { |
| 850 UMA_HISTOGRAM_ENUMERATION("WebCore.IndexedDB.BackingStore.OpenStatus", | 843 UMA_HISTOGRAM_ENUMERATION("WebCore.IndexedDB.BackingStore.OpenStatus", |
| 851 result, | 844 result, |
| 852 INDEXED_DB_BACKING_STORE_OPEN_MAX); | 845 INDEXED_DB_BACKING_STORE_OPEN_MAX); |
| 853 const std::string suffix = OriginToCustomHistogramSuffix(origin_url); | 846 const std::string suffix = OriginToCustomHistogramSuffix(origin); |
| 854 // Data from the WebCore.IndexedDB.BackingStore.OpenStatus histogram is used | 847 // Data from the WebCore.IndexedDB.BackingStore.OpenStatus histogram is used |
| 855 // to generate a graph. So as not to alter the meaning of that graph, | 848 // to generate a graph. So as not to alter the meaning of that graph, |
| 856 // continue to collect all stats there (above) but also now collect docs stats | 849 // continue to collect all stats there (above) but also now collect docs stats |
| 857 // separately (below). | 850 // separately (below). |
| 858 if (!suffix.empty()) { | 851 if (!suffix.empty()) { |
| 859 base::LinearHistogram::FactoryGet( | 852 base::LinearHistogram::FactoryGet( |
| 860 "WebCore.IndexedDB.BackingStore.OpenStatus" + suffix, | 853 "WebCore.IndexedDB.BackingStore.OpenStatus" + suffix, |
| 861 1, | 854 1, |
| 862 INDEXED_DB_BACKING_STORE_OPEN_MAX, | 855 INDEXED_DB_BACKING_STORE_OPEN_MAX, |
| 863 INDEXED_DB_BACKING_STORE_OPEN_MAX + 1, | 856 INDEXED_DB_BACKING_STORE_OPEN_MAX + 1, |
| (...skipping 26 matching lines...) Expand all Loading... |
| 890 min, | 883 min, |
| 891 max, | 884 max, |
| 892 num_buckets); | 885 num_buckets); |
| 893 return true; | 886 return true; |
| 894 } | 887 } |
| 895 return false; | 888 return false; |
| 896 } | 889 } |
| 897 | 890 |
| 898 leveldb::Status IndexedDBBackingStore::DestroyBackingStore( | 891 leveldb::Status IndexedDBBackingStore::DestroyBackingStore( |
| 899 const base::FilePath& path_base, | 892 const base::FilePath& path_base, |
| 900 const GURL& origin_url) { | 893 const url::Origin& origin) { |
| 901 const base::FilePath file_path = | 894 const base::FilePath file_path = |
| 902 path_base.Append(IndexedDBContextImpl::GetLevelDBFileName(origin_url)); | 895 path_base.Append(IndexedDBContextImpl::GetLevelDBFileName(origin)); |
| 903 DefaultLevelDBFactory leveldb_factory; | 896 DefaultLevelDBFactory leveldb_factory; |
| 904 return leveldb_factory.DestroyLevelDB(file_path); | 897 return leveldb_factory.DestroyLevelDB(file_path); |
| 905 } | 898 } |
| 906 | 899 |
| 907 bool IndexedDBBackingStore::ReadCorruptionInfo(const base::FilePath& path_base, | 900 bool IndexedDBBackingStore::ReadCorruptionInfo(const base::FilePath& path_base, |
| 908 const GURL& origin_url, | 901 const url::Origin& origin, |
| 909 std::string* message) { | 902 std::string* message) { |
| 910 const base::FilePath info_path = | 903 const base::FilePath info_path = |
| 911 path_base.Append(ComputeCorruptionFileName(origin_url)); | 904 path_base.Append(ComputeCorruptionFileName(origin)); |
| 912 | 905 |
| 913 if (IsPathTooLong(info_path)) | 906 if (IsPathTooLong(info_path)) |
| 914 return false; | 907 return false; |
| 915 | 908 |
| 916 const int64_t max_json_len = 4096; | 909 const int64_t max_json_len = 4096; |
| 917 int64_t file_size(0); | 910 int64_t file_size(0); |
| 918 if (!GetFileSize(info_path, &file_size) || file_size > max_json_len) | 911 if (!GetFileSize(info_path, &file_size) || file_size > max_json_len) |
| 919 return false; | 912 return false; |
| 920 if (!file_size) { | 913 if (!file_size) { |
| 921 NOTREACHED(); | 914 NOTREACHED(); |
| (...skipping 17 matching lines...) Expand all Loading... |
| 939 file.Close(); | 932 file.Close(); |
| 940 } | 933 } |
| 941 | 934 |
| 942 base::DeleteFile(info_path, false); | 935 base::DeleteFile(info_path, false); |
| 943 | 936 |
| 944 return success; | 937 return success; |
| 945 } | 938 } |
| 946 | 939 |
| 947 bool IndexedDBBackingStore::RecordCorruptionInfo( | 940 bool IndexedDBBackingStore::RecordCorruptionInfo( |
| 948 const base::FilePath& path_base, | 941 const base::FilePath& path_base, |
| 949 const GURL& origin_url, | 942 const url::Origin& origin, |
| 950 const std::string& message) { | 943 const std::string& message) { |
| 951 const base::FilePath info_path = | 944 const base::FilePath info_path = |
| 952 path_base.Append(ComputeCorruptionFileName(origin_url)); | 945 path_base.Append(ComputeCorruptionFileName(origin)); |
| 953 if (IsPathTooLong(info_path)) | 946 if (IsPathTooLong(info_path)) |
| 954 return false; | 947 return false; |
| 955 | 948 |
| 956 base::DictionaryValue root_dict; | 949 base::DictionaryValue root_dict; |
| 957 root_dict.SetString("message", message); | 950 root_dict.SetString("message", message); |
| 958 std::string output_js; | 951 std::string output_js; |
| 959 base::JSONWriter::Write(root_dict, &output_js); | 952 base::JSONWriter::Write(root_dict, &output_js); |
| 960 | 953 |
| 961 base::File file(info_path, | 954 base::File file(info_path, |
| 962 base::File::FLAG_CREATE_ALWAYS | base::File::FLAG_WRITE); | 955 base::File::FLAG_CREATE_ALWAYS | base::File::FLAG_WRITE); |
| 963 if (!file.IsValid()) | 956 if (!file.IsValid()) |
| 964 return false; | 957 return false; |
| 965 int written = file.Write(0, output_js.c_str(), output_js.length()); | 958 int written = file.Write(0, output_js.c_str(), output_js.length()); |
| 966 return size_t(written) == output_js.length(); | 959 return size_t(written) == output_js.length(); |
| 967 } | 960 } |
| 968 | 961 |
| 969 // static | 962 // static |
| 970 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::Open( | 963 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::Open( |
| 971 IndexedDBFactory* indexed_db_factory, | 964 IndexedDBFactory* indexed_db_factory, |
| 972 const GURL& origin_url, | 965 const url::Origin& origin, |
| 973 const base::FilePath& path_base, | 966 const base::FilePath& path_base, |
| 974 net::URLRequestContext* request_context, | 967 net::URLRequestContext* request_context, |
| 975 blink::WebIDBDataLoss* data_loss, | 968 blink::WebIDBDataLoss* data_loss, |
| 976 std::string* data_loss_message, | 969 std::string* data_loss_message, |
| 977 bool* is_disk_full, | 970 bool* is_disk_full, |
| 978 LevelDBFactory* leveldb_factory, | 971 LevelDBFactory* leveldb_factory, |
| 979 base::SequencedTaskRunner* task_runner, | 972 base::SequencedTaskRunner* task_runner, |
| 980 bool clean_journal, | 973 bool clean_journal, |
| 981 leveldb::Status* status) { | 974 leveldb::Status* status) { |
| 982 IDB_TRACE("IndexedDBBackingStore::Open"); | 975 IDB_TRACE("IndexedDBBackingStore::Open"); |
| 983 DCHECK(!path_base.empty()); | 976 DCHECK(!path_base.empty()); |
| 984 *data_loss = blink::WebIDBDataLossNone; | 977 *data_loss = blink::WebIDBDataLossNone; |
| 985 *data_loss_message = ""; | 978 *data_loss_message = ""; |
| 986 *is_disk_full = false; | 979 *is_disk_full = false; |
| 987 | 980 |
| 988 *status = leveldb::Status::OK(); | 981 *status = leveldb::Status::OK(); |
| 989 | 982 |
| 990 scoped_ptr<LevelDBComparator> comparator(new Comparator()); | 983 scoped_ptr<LevelDBComparator> comparator(new Comparator()); |
| 991 | 984 |
| 992 if (!base::IsStringASCII(path_base.AsUTF8Unsafe())) { | 985 if (!base::IsStringASCII(path_base.AsUTF8Unsafe())) { |
| 993 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_ATTEMPT_NON_ASCII, | 986 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_ATTEMPT_NON_ASCII, |
| 994 origin_url); | 987 origin); |
| 995 } | 988 } |
| 996 if (!base::CreateDirectory(path_base)) { | 989 if (!base::CreateDirectory(path_base)) { |
| 997 *status = | 990 *status = |
| 998 leveldb::Status::IOError("Unable to create IndexedDB database path"); | 991 leveldb::Status::IOError("Unable to create IndexedDB database path"); |
| 999 LOG(ERROR) << status->ToString() << ": \"" << path_base.AsUTF8Unsafe() | 992 LOG(ERROR) << status->ToString() << ": \"" << path_base.AsUTF8Unsafe() |
| 1000 << "\""; | 993 << "\""; |
| 1001 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_FAILED_DIRECTORY, | 994 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_FAILED_DIRECTORY, origin); |
| 1002 origin_url); | |
| 1003 return scoped_refptr<IndexedDBBackingStore>(); | 995 return scoped_refptr<IndexedDBBackingStore>(); |
| 1004 } | 996 } |
| 1005 | 997 |
| 1006 const FilePath file_path = | 998 const FilePath file_path = |
| 1007 path_base.Append(IndexedDBContextImpl::GetLevelDBFileName(origin_url)); | 999 path_base.Append(IndexedDBContextImpl::GetLevelDBFileName(origin)); |
| 1008 const FilePath blob_path = | 1000 const FilePath blob_path = |
| 1009 path_base.Append(IndexedDBContextImpl::GetBlobStoreFileName(origin_url)); | 1001 path_base.Append(IndexedDBContextImpl::GetBlobStoreFileName(origin)); |
| 1010 | 1002 |
| 1011 if (IsPathTooLong(file_path)) { | 1003 if (IsPathTooLong(file_path)) { |
| 1012 *status = leveldb::Status::IOError("File path too long"); | 1004 *status = leveldb::Status::IOError("File path too long"); |
| 1013 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_ORIGIN_TOO_LONG, | 1005 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_ORIGIN_TOO_LONG, origin); |
| 1014 origin_url); | |
| 1015 return scoped_refptr<IndexedDBBackingStore>(); | 1006 return scoped_refptr<IndexedDBBackingStore>(); |
| 1016 } | 1007 } |
| 1017 | 1008 |
| 1018 scoped_ptr<LevelDBDatabase> db; | 1009 scoped_ptr<LevelDBDatabase> db; |
| 1019 *status = leveldb_factory->OpenLevelDB( | 1010 *status = leveldb_factory->OpenLevelDB( |
| 1020 file_path, comparator.get(), &db, is_disk_full); | 1011 file_path, comparator.get(), &db, is_disk_full); |
| 1021 | 1012 |
| 1022 DCHECK(!db == !status->ok()); | 1013 DCHECK(!db == !status->ok()); |
| 1023 if (!status->ok()) { | 1014 if (!status->ok()) { |
| 1024 if (leveldb_env::IndicatesDiskFull(*status)) { | 1015 if (leveldb_env::IndicatesDiskFull(*status)) { |
| 1025 *is_disk_full = true; | 1016 *is_disk_full = true; |
| 1026 } else if (status->IsCorruption()) { | 1017 } else if (status->IsCorruption()) { |
| 1027 *data_loss = blink::WebIDBDataLossTotal; | 1018 *data_loss = blink::WebIDBDataLossTotal; |
| 1028 *data_loss_message = leveldb_env::GetCorruptionMessage(*status); | 1019 *data_loss_message = leveldb_env::GetCorruptionMessage(*status); |
| 1029 } | 1020 } |
| 1030 } | 1021 } |
| 1031 | 1022 |
| 1032 bool is_schema_known = false; | 1023 bool is_schema_known = false; |
| 1033 if (db) { | 1024 if (db) { |
| 1034 std::string corruption_message; | 1025 std::string corruption_message; |
| 1035 if (ReadCorruptionInfo(path_base, origin_url, &corruption_message)) { | 1026 if (ReadCorruptionInfo(path_base, origin, &corruption_message)) { |
| 1036 LOG(ERROR) << "IndexedDB recovering from a corrupted (and deleted) " | 1027 LOG(ERROR) << "IndexedDB recovering from a corrupted (and deleted) " |
| 1037 "database."; | 1028 "database."; |
| 1038 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_FAILED_PRIOR_CORRUPTION, | 1029 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_FAILED_PRIOR_CORRUPTION, |
| 1039 origin_url); | 1030 origin); |
| 1040 db.reset(); | 1031 db.reset(); |
| 1041 *data_loss = blink::WebIDBDataLossTotal; | 1032 *data_loss = blink::WebIDBDataLossTotal; |
| 1042 *data_loss_message = | 1033 *data_loss_message = |
| 1043 "IndexedDB (database was corrupt): " + corruption_message; | 1034 "IndexedDB (database was corrupt): " + corruption_message; |
| 1044 } else if (!IsSchemaKnown(db.get(), &is_schema_known)) { | 1035 } else if (!IsSchemaKnown(db.get(), &is_schema_known)) { |
| 1045 LOG(ERROR) << "IndexedDB had IO error checking schema, treating it as " | 1036 LOG(ERROR) << "IndexedDB had IO error checking schema, treating it as " |
| 1046 "failure to open"; | 1037 "failure to open"; |
| 1047 HistogramOpenStatus( | 1038 HistogramOpenStatus( |
| 1048 INDEXED_DB_BACKING_STORE_OPEN_FAILED_IO_ERROR_CHECKING_SCHEMA, | 1039 INDEXED_DB_BACKING_STORE_OPEN_FAILED_IO_ERROR_CHECKING_SCHEMA, |
| 1049 origin_url); | 1040 origin); |
| 1050 db.reset(); | 1041 db.reset(); |
| 1051 *data_loss = blink::WebIDBDataLossTotal; | 1042 *data_loss = blink::WebIDBDataLossTotal; |
| 1052 *data_loss_message = "I/O error checking schema"; | 1043 *data_loss_message = "I/O error checking schema"; |
| 1053 } else if (!is_schema_known) { | 1044 } else if (!is_schema_known) { |
| 1054 LOG(ERROR) << "IndexedDB backing store had unknown schema, treating it " | 1045 LOG(ERROR) << "IndexedDB backing store had unknown schema, treating it " |
| 1055 "as failure to open"; | 1046 "as failure to open"; |
| 1056 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_FAILED_UNKNOWN_SCHEMA, | 1047 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_FAILED_UNKNOWN_SCHEMA, |
| 1057 origin_url); | 1048 origin); |
| 1058 db.reset(); | 1049 db.reset(); |
| 1059 *data_loss = blink::WebIDBDataLossTotal; | 1050 *data_loss = blink::WebIDBDataLossTotal; |
| 1060 *data_loss_message = "Unknown schema"; | 1051 *data_loss_message = "Unknown schema"; |
| 1061 } | 1052 } |
| 1062 } | 1053 } |
| 1063 | 1054 |
| 1064 DCHECK(status->ok() || !is_schema_known || status->IsIOError() || | 1055 DCHECK(status->ok() || !is_schema_known || status->IsIOError() || |
| 1065 status->IsCorruption()); | 1056 status->IsCorruption()); |
| 1066 | 1057 |
| 1067 if (db) { | 1058 if (db) { |
| 1068 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_SUCCESS, origin_url); | 1059 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_SUCCESS, origin); |
| 1069 } else if (status->IsIOError()) { | 1060 } else if (status->IsIOError()) { |
| 1070 LOG(ERROR) << "Unable to open backing store, not trying to recover - " | 1061 LOG(ERROR) << "Unable to open backing store, not trying to recover - " |
| 1071 << status->ToString(); | 1062 << status->ToString(); |
| 1072 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_NO_RECOVERY, origin_url); | 1063 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_NO_RECOVERY, origin); |
| 1073 return scoped_refptr<IndexedDBBackingStore>(); | 1064 return scoped_refptr<IndexedDBBackingStore>(); |
| 1074 } else { | 1065 } else { |
| 1075 DCHECK(!is_schema_known || status->IsCorruption()); | 1066 DCHECK(!is_schema_known || status->IsCorruption()); |
| 1076 LOG(ERROR) << "IndexedDB backing store open failed, attempting cleanup"; | 1067 LOG(ERROR) << "IndexedDB backing store open failed, attempting cleanup"; |
| 1077 *status = leveldb_factory->DestroyLevelDB(file_path); | 1068 *status = leveldb_factory->DestroyLevelDB(file_path); |
| 1078 if (!status->ok()) { | 1069 if (!status->ok()) { |
| 1079 LOG(ERROR) << "IndexedDB backing store cleanup failed"; | 1070 LOG(ERROR) << "IndexedDB backing store cleanup failed"; |
| 1080 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_CLEANUP_DESTROY_FAILED, | 1071 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_CLEANUP_DESTROY_FAILED, |
| 1081 origin_url); | 1072 origin); |
| 1082 return scoped_refptr<IndexedDBBackingStore>(); | 1073 return scoped_refptr<IndexedDBBackingStore>(); |
| 1083 } | 1074 } |
| 1084 | 1075 |
| 1085 LOG(ERROR) << "IndexedDB backing store cleanup succeeded, reopening"; | 1076 LOG(ERROR) << "IndexedDB backing store cleanup succeeded, reopening"; |
| 1086 *status = | 1077 *status = |
| 1087 leveldb_factory->OpenLevelDB(file_path, comparator.get(), &db, NULL); | 1078 leveldb_factory->OpenLevelDB(file_path, comparator.get(), &db, NULL); |
| 1088 if (!status->ok()) { | 1079 if (!status->ok()) { |
| 1089 DCHECK(!db); | 1080 DCHECK(!db); |
| 1090 LOG(ERROR) << "IndexedDB backing store reopen after recovery failed"; | 1081 LOG(ERROR) << "IndexedDB backing store reopen after recovery failed"; |
| 1091 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_CLEANUP_REOPEN_FAILED, | 1082 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_CLEANUP_REOPEN_FAILED, |
| 1092 origin_url); | 1083 origin); |
| 1093 return scoped_refptr<IndexedDBBackingStore>(); | 1084 return scoped_refptr<IndexedDBBackingStore>(); |
| 1094 } | 1085 } |
| 1095 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_CLEANUP_REOPEN_SUCCESS, | 1086 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_CLEANUP_REOPEN_SUCCESS, |
| 1096 origin_url); | 1087 origin); |
| 1097 } | 1088 } |
| 1098 | 1089 |
| 1099 base::trace_event::MemoryDumpManager::GetInstance() | 1090 base::trace_event::MemoryDumpManager::GetInstance() |
| 1100 ->RegisterDumpProviderWithSequencedTaskRunner( | 1091 ->RegisterDumpProviderWithSequencedTaskRunner( |
| 1101 db.get(), "IndexedDBBackingStore", task_runner, | 1092 db.get(), "IndexedDBBackingStore", task_runner, |
| 1102 base::trace_event::MemoryDumpProvider::Options()); | 1093 base::trace_event::MemoryDumpProvider::Options()); |
| 1103 | 1094 |
| 1104 scoped_refptr<IndexedDBBackingStore> backing_store = | 1095 scoped_refptr<IndexedDBBackingStore> backing_store = |
| 1105 Create(indexed_db_factory, origin_url, blob_path, request_context, | 1096 Create(indexed_db_factory, origin, blob_path, request_context, |
| 1106 std::move(db), std::move(comparator), task_runner, status); | 1097 std::move(db), std::move(comparator), task_runner, status); |
| 1107 | 1098 |
| 1108 if (clean_journal && backing_store.get()) { | 1099 if (clean_journal && backing_store.get()) { |
| 1109 *status = backing_store->CleanUpBlobJournal(LiveBlobJournalKey::Encode()); | 1100 *status = backing_store->CleanUpBlobJournal(LiveBlobJournalKey::Encode()); |
| 1110 if (!status->ok()) { | 1101 if (!status->ok()) { |
| 1111 HistogramOpenStatus( | 1102 HistogramOpenStatus( |
| 1112 INDEXED_DB_BACKING_STORE_OPEN_FAILED_CLEANUP_JOURNAL_ERROR, | 1103 INDEXED_DB_BACKING_STORE_OPEN_FAILED_CLEANUP_JOURNAL_ERROR, origin); |
| 1113 origin_url); | |
| 1114 return scoped_refptr<IndexedDBBackingStore>(); | 1104 return scoped_refptr<IndexedDBBackingStore>(); |
| 1115 } | 1105 } |
| 1116 } | 1106 } |
| 1117 return backing_store; | 1107 return backing_store; |
| 1118 } | 1108 } |
| 1119 | 1109 |
| 1120 // static | 1110 // static |
| 1121 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::OpenInMemory( | 1111 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::OpenInMemory( |
| 1122 const GURL& origin_url, | 1112 const url::Origin& origin, |
| 1123 base::SequencedTaskRunner* task_runner, | 1113 base::SequencedTaskRunner* task_runner, |
| 1124 leveldb::Status* status) { | 1114 leveldb::Status* status) { |
| 1125 DefaultLevelDBFactory leveldb_factory; | 1115 DefaultLevelDBFactory leveldb_factory; |
| 1126 return IndexedDBBackingStore::OpenInMemory( | 1116 return IndexedDBBackingStore::OpenInMemory(origin, &leveldb_factory, |
| 1127 origin_url, &leveldb_factory, task_runner, status); | 1117 task_runner, status); |
| 1128 } | 1118 } |
| 1129 | 1119 |
| 1130 // static | 1120 // static |
| 1131 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::OpenInMemory( | 1121 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::OpenInMemory( |
| 1132 const GURL& origin_url, | 1122 const url::Origin& origin, |
| 1133 LevelDBFactory* leveldb_factory, | 1123 LevelDBFactory* leveldb_factory, |
| 1134 base::SequencedTaskRunner* task_runner, | 1124 base::SequencedTaskRunner* task_runner, |
| 1135 leveldb::Status* status) { | 1125 leveldb::Status* status) { |
| 1136 IDB_TRACE("IndexedDBBackingStore::OpenInMemory"); | 1126 IDB_TRACE("IndexedDBBackingStore::OpenInMemory"); |
| 1137 | 1127 |
| 1138 scoped_ptr<LevelDBComparator> comparator(new Comparator()); | 1128 scoped_ptr<LevelDBComparator> comparator(new Comparator()); |
| 1139 scoped_ptr<LevelDBDatabase> db = | 1129 scoped_ptr<LevelDBDatabase> db = |
| 1140 LevelDBDatabase::OpenInMemory(comparator.get()); | 1130 LevelDBDatabase::OpenInMemory(comparator.get()); |
| 1141 if (!db) { | 1131 if (!db) { |
| 1142 LOG(ERROR) << "LevelDBDatabase::OpenInMemory failed."; | 1132 LOG(ERROR) << "LevelDBDatabase::OpenInMemory failed."; |
| 1143 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_MEMORY_FAILED, | 1133 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_MEMORY_FAILED, origin); |
| 1144 origin_url); | |
| 1145 return scoped_refptr<IndexedDBBackingStore>(); | 1134 return scoped_refptr<IndexedDBBackingStore>(); |
| 1146 } | 1135 } |
| 1147 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_MEMORY_SUCCESS, origin_url); | 1136 HistogramOpenStatus(INDEXED_DB_BACKING_STORE_OPEN_MEMORY_SUCCESS, origin); |
| 1148 base::trace_event::MemoryDumpManager::GetInstance() | 1137 base::trace_event::MemoryDumpManager::GetInstance() |
| 1149 ->RegisterDumpProviderWithSequencedTaskRunner( | 1138 ->RegisterDumpProviderWithSequencedTaskRunner( |
| 1150 db.get(), "IndexedDBBackingStore", task_runner, | 1139 db.get(), "IndexedDBBackingStore", task_runner, |
| 1151 base::trace_event::MemoryDumpProvider::Options()); | 1140 base::trace_event::MemoryDumpProvider::Options()); |
| 1152 | 1141 |
| 1153 return Create(NULL /* indexed_db_factory */, origin_url, base::FilePath(), | 1142 return Create(NULL /* indexed_db_factory */, origin, base::FilePath(), |
| 1154 NULL /* request_context */, std::move(db), | 1143 NULL /* request_context */, std::move(db), |
| 1155 std::move(comparator), task_runner, status); | 1144 std::move(comparator), task_runner, status); |
| 1156 } | 1145 } |
| 1157 | 1146 |
| 1158 // static | 1147 // static |
| 1159 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::Create( | 1148 scoped_refptr<IndexedDBBackingStore> IndexedDBBackingStore::Create( |
| 1160 IndexedDBFactory* indexed_db_factory, | 1149 IndexedDBFactory* indexed_db_factory, |
| 1161 const GURL& origin_url, | 1150 const url::Origin& origin, |
| 1162 const base::FilePath& blob_path, | 1151 const base::FilePath& blob_path, |
| 1163 net::URLRequestContext* request_context, | 1152 net::URLRequestContext* request_context, |
| 1164 scoped_ptr<LevelDBDatabase> db, | 1153 scoped_ptr<LevelDBDatabase> db, |
| 1165 scoped_ptr<LevelDBComparator> comparator, | 1154 scoped_ptr<LevelDBComparator> comparator, |
| 1166 base::SequencedTaskRunner* task_runner, | 1155 base::SequencedTaskRunner* task_runner, |
| 1167 leveldb::Status* status) { | 1156 leveldb::Status* status) { |
| 1168 // TODO(jsbell): Handle comparator name changes. | 1157 // TODO(jsbell): Handle comparator name changes. |
| 1169 scoped_refptr<IndexedDBBackingStore> backing_store(new IndexedDBBackingStore( | 1158 scoped_refptr<IndexedDBBackingStore> backing_store(new IndexedDBBackingStore( |
| 1170 indexed_db_factory, origin_url, blob_path, request_context, std::move(db), | 1159 indexed_db_factory, origin, blob_path, request_context, std::move(db), |
| 1171 std::move(comparator), task_runner)); | 1160 std::move(comparator), task_runner)); |
| 1172 *status = backing_store->SetUpMetadata(); | 1161 *status = backing_store->SetUpMetadata(); |
| 1173 if (!status->ok()) | 1162 if (!status->ok()) |
| 1174 return scoped_refptr<IndexedDBBackingStore>(); | 1163 return scoped_refptr<IndexedDBBackingStore>(); |
| 1175 | 1164 |
| 1176 return backing_store; | 1165 return backing_store; |
| 1177 } | 1166 } |
| 1178 | 1167 |
| 1179 void IndexedDBBackingStore::GrantChildProcessPermissions(int child_process_id) { | 1168 void IndexedDBBackingStore::GrantChildProcessPermissions(int child_process_id) { |
| 1180 if (!child_process_ids_granted_.count(child_process_id)) { | 1169 if (!child_process_ids_granted_.count(child_process_id)) { |
| (...skipping 3300 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4481 | 4470 |
| 4482 IndexedDBBackingStore::Transaction::WriteDescriptor::WriteDescriptor( | 4471 IndexedDBBackingStore::Transaction::WriteDescriptor::WriteDescriptor( |
| 4483 const WriteDescriptor& other) = default; | 4472 const WriteDescriptor& other) = default; |
| 4484 IndexedDBBackingStore::Transaction::WriteDescriptor::~WriteDescriptor() = | 4473 IndexedDBBackingStore::Transaction::WriteDescriptor::~WriteDescriptor() = |
| 4485 default; | 4474 default; |
| 4486 IndexedDBBackingStore::Transaction::WriteDescriptor& | 4475 IndexedDBBackingStore::Transaction::WriteDescriptor& |
| 4487 IndexedDBBackingStore::Transaction::WriteDescriptor:: | 4476 IndexedDBBackingStore::Transaction::WriteDescriptor:: |
| 4488 operator=(const WriteDescriptor& other) = default; | 4477 operator=(const WriteDescriptor& other) = default; |
| 4489 | 4478 |
| 4490 } // namespace content | 4479 } // namespace content |
| OLD | NEW |