Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(123)

Side by Side Diff: chrome/browser/webdata/web_database.cc

Issue 13392014: Move c/b/webdata/ code to components/webdata/ (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Pure merge Created 7 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
1 // Copyright (c) 2012 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 #include "chrome/browser/webdata/web_database.h"
6
7 #include <algorithm>
8
9 #include "base/stl_util.h"
10 #include "content/public/browser/notification_service.h"
11 #include "sql/statement.h"
12 #include "sql/transaction.h"
13
14 // Current version number. Note: when changing the current version number,
15 // corresponding changes must happen in the unit tests, and new migration test
16 // added. See |WebDatabaseMigrationTest::kCurrentTestedVersionNumber|.
17 // static
18 const int WebDatabase::kCurrentVersionNumber = 49;
19
20 namespace {
21
22 const int kCompatibleVersionNumber = 48;
23
24 // Change the version number and possibly the compatibility version of
25 // |meta_table_|.
26 void ChangeVersion(sql::MetaTable* meta_table,
27 int version_num,
28 bool update_compatible_version_num) {
29 meta_table->SetVersionNumber(version_num);
30 if (update_compatible_version_num) {
31 meta_table->SetCompatibleVersionNumber(
32 std::min(version_num, kCompatibleVersionNumber));
33 }
34 }
35
36 // Outputs the failed version number as a warning and always returns
37 // |sql::INIT_FAILURE|.
38 sql::InitStatus FailedMigrationTo(int version_num) {
39 LOG(WARNING) << "Unable to update web database to version "
40 << version_num << ".";
41 NOTREACHED();
42 return sql::INIT_FAILURE;
43 }
44
45 } // namespace
46
47 WebDatabase::WebDatabase() {}
48
49 WebDatabase::~WebDatabase() {
50 }
51
52 void WebDatabase::AddTable(WebDatabaseTable* table) {
53 tables_[table->GetTypeKey()] = table;
54 }
55
56 WebDatabaseTable* WebDatabase::GetTable(WebDatabaseTable::TypeKey key) {
57 return tables_[key];
58 }
59
60 void WebDatabase::BeginTransaction() {
61 db_.BeginTransaction();
62 }
63
64 void WebDatabase::CommitTransaction() {
65 db_.CommitTransaction();
66 }
67
68 sql::Connection* WebDatabase::GetSQLConnection() {
69 return &db_;
70 }
71
72 sql::InitStatus WebDatabase::Init(const base::FilePath& db_name) {
73 // When running in unit tests, there is already a NotificationService object.
74 // Since only one can exist at a time per thread, check first.
75 if (!content::NotificationService::current())
76 notification_service_.reset(content::NotificationService::Create());
77
78 db_.set_error_histogram_name("Sqlite.Web.Error");
79
80 // We don't store that much data in the tables so use a small page size.
81 // This provides a large benefit for empty tables (which is very likely with
82 // the tables we create).
83 db_.set_page_size(2048);
84
85 // We shouldn't have much data and what access we currently have is quite
86 // infrequent. So we go with a small cache size.
87 db_.set_cache_size(32);
88
89 // Run the database in exclusive mode. Nobody else should be accessing the
90 // database while we're running, and this will give somewhat improved perf.
91 db_.set_exclusive_locking();
92
93 if (!db_.Open(db_name))
94 return sql::INIT_FAILURE;
95
96 // Initialize various tables
97 sql::Transaction transaction(&db_);
98 if (!transaction.Begin())
99 return sql::INIT_FAILURE;
100
101 // Version check.
102 if (!meta_table_.Init(&db_, kCurrentVersionNumber, kCompatibleVersionNumber))
103 return sql::INIT_FAILURE;
104 if (meta_table_.GetCompatibleVersionNumber() > kCurrentVersionNumber) {
105 LOG(WARNING) << "Web database is too new.";
106 return sql::INIT_TOO_NEW;
107 }
108
109 // Initialize the tables.
110 for (TableMap::iterator it = tables_.begin();
111 it != tables_.end();
112 ++it) {
113 if (!it->second->Init(&db_, &meta_table_)) {
114 LOG(WARNING) << "Unable to initialize the web database.";
115 return sql::INIT_FAILURE;
116 }
117 }
118
119 // If the file on disk is an older database version, bring it up to date.
120 // If the migration fails we return an error to caller and do not commit
121 // the migration.
122 sql::InitStatus migration_status = MigrateOldVersionsAsNeeded();
123 if (migration_status != sql::INIT_OK)
124 return migration_status;
125
126 return transaction.Commit() ? sql::INIT_OK : sql::INIT_FAILURE;
127 }
128
129 sql::InitStatus WebDatabase::MigrateOldVersionsAsNeeded() {
130 // Some malware used to lower the version number, causing migration to
131 // fail. Ensure the version number is at least as high as the compatible
132 // version number.
133 int current_version = std::max(meta_table_.GetVersionNumber(),
134 meta_table_.GetCompatibleVersionNumber());
135 if (current_version > meta_table_.GetVersionNumber())
136 ChangeVersion(&meta_table_, current_version, false);
137
138 if (current_version < 20) {
139 // Versions 1 - 19 are unhandled. Version numbers greater than
140 // kCurrentVersionNumber should have already been weeded out by the caller.
141 //
142 // When the version is too old, we return failure error code. The schema
143 // is too out of date to migrate.
144 //
145 // There should not be a released product that makes a database too old to
146 // migrate. If we do encounter such a legacy database, we will need a
147 // better solution to handle it (i.e., pop up a dialog to tell the user,
148 // erase all their prefs and start over, etc.).
149 LOG(WARNING) << "Web database version " << current_version <<
150 " is too old to handle.";
151 NOTREACHED();
152 return sql::INIT_FAILURE;
153 }
154
155 for (int next_version = current_version + 1;
156 next_version <= kCurrentVersionNumber;
157 ++next_version) {
158 // Give each table a chance to migrate to this version.
159 for (TableMap::iterator it = tables_.begin();
160 it != tables_.end();
161 ++it) {
162 // Any of the tables may set this to true, but by default it is false.
163 bool update_compatible_version = false;
164 if (!it->second->MigrateToVersion(next_version,
165 &update_compatible_version)) {
166 return FailedMigrationTo(next_version);
167 }
168
169 ChangeVersion(&meta_table_, next_version, update_compatible_version);
170 }
171 }
172 return sql::INIT_OK;
173 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698