diff options
author | tim@chromium.org <tim@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-08-02 06:12:00 +0000 |
---|---|---|
committer | tim@chromium.org <tim@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-08-02 06:12:00 +0000 |
commit | 2f29377e44efc45a2b7346af87886818ace70b79 (patch) | |
tree | 6a31e6a2979fa326406fd6f5bf91f6e6f4008fd5 /chrome/browser/sync | |
parent | dfc4387102f93536017342b07069577e12ba14d2 (diff) | |
download | chromium_src-2f29377e44efc45a2b7346af87886818ace70b79.zip chromium_src-2f29377e44efc45a2b7346af87886818ace70b79.tar.gz chromium_src-2f29377e44efc45a2b7346af87886818ace70b79.tar.bz2 |
Stopgap fix for bug 48502. Stop syncing on db corruption.
BUG=48502
Review URL: http://codereview.chromium.org/3075015
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@54516 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome/browser/sync')
4 files changed, 45 insertions, 5 deletions
diff --git a/chrome/browser/sync/engine/syncapi.cc b/chrome/browser/sync/engine/syncapi.cc index e0fe352..41186a0 100644 --- a/chrome/browser/sync/engine/syncapi.cc +++ b/chrome/browser/sync/engine/syncapi.cc @@ -13,6 +13,7 @@ #include "base/basictypes.h" #include "base/base64.h" +#include "base/histogram.h" #include "base/lock.h" #include "base/logging.h" #include "base/message_loop.h" @@ -1496,7 +1497,17 @@ bool SyncManager::SyncInternal::AuthenticateForUser( // We optimize by opening the directory before the "fresh" authentication // attempt completes so that we can immediately begin processing changes. if (!dir_manager()->Open(username_for_share())) { - DCHECK(false) << "Had last known user but could not open directory"; + // TODO(tim): Cue a refresh if the db was corrupt. + if (observer_) + observer_->OnStopSyncingPermanently(); + +#if defined(OS_WIN) + UMA_HISTOGRAM_COUNTS_100("Sync.DirectoryOpenFailedWin", 1); +#elif defined (OS_MACOSX) + UMA_HISTOGRAM_COUNTS_100("Sync.DirectoryOpenFailedMac", 1); +#else + UMA_HISTOGRAM_COUNTS_100("Sync.DirectoryOpenFailedNotWinMac", 1); +#endif return false; } diff --git a/chrome/browser/sync/syncable/directory_backing_store.cc b/chrome/browser/sync/syncable/directory_backing_store.cc index 8cec2a9..c9f281e 100644 --- a/chrome/browser/sync/syncable/directory_backing_store.cc +++ b/chrome/browser/sync/syncable/directory_backing_store.cc @@ -184,6 +184,14 @@ bool DirectoryBackingStore::OpenAndConfigureHandleHelper( if (SQLITE_OK == sqlite_utils::OpenSqliteDb(backing_filepath_, handle)) { sqlite_utils::scoped_sqlite_db_ptr scoped_handle(*handle); sqlite3_busy_timeout(scoped_handle.get(), std::numeric_limits<int>::max()); + {
+ string integrity_error;
+ bool is_ok = CheckIntegrity(scoped_handle.get(), &integrity_error);
+ if (!is_ok) {
+ LOG(ERROR) << "Integrity check failed: " << integrity_error;
+ return false;
+ }
+ } { SQLStatement statement; statement.prepare(scoped_handle.get(), "PRAGMA fullfsync = 1"); @@ -215,6 +223,22 @@ bool DirectoryBackingStore::OpenAndConfigureHandleHelper( } return false; } +
+bool DirectoryBackingStore::CheckIntegrity(sqlite3* handle, string* error)
+ const {
+ SQLStatement statement;
+ statement.prepare(handle, "PRAGMA integrity_check(1)");
+ if (SQLITE_ROW != statement.step()) {
+ *error = sqlite3_errmsg(handle);
+ return false;
+ }
+ string integrity_result = statement.column_text(0);
+ if (integrity_result != "ok") {
+ *error = integrity_result;
+ return false;
+ }
+ return true;
+} DirOpenResult DirectoryBackingStore::DoLoad(MetahandlesIndex* entry_bucket, Directory::KernelLoadInfo* kernel_load_info) { @@ -261,9 +285,8 @@ bool DirectoryBackingStore::BeginLoad() { return ret; // Something's gone wrong. Nuke the database and try again. LOG(ERROR) << "Sync database " << backing_filepath_.value() - << " corrupt. Deleting and recreating."; - file_util::Delete(backing_filepath_, false); - return OpenAndConfigureHandleHelper(&load_dbhandle_); + << " corrupt."; + return false; } void DirectoryBackingStore::EndLoad() { diff --git a/chrome/browser/sync/syncable/directory_backing_store.h b/chrome/browser/sync/syncable/directory_backing_store.h index e1b0cca..766ba6a 100644 --- a/chrome/browser/sync/syncable/directory_backing_store.h +++ b/chrome/browser/sync/syncable/directory_backing_store.h @@ -146,6 +146,11 @@ class DirectoryBackingStore { static ModelType ModelIdToModelTypeEnum(const string& model_id); static string ModelTypeEnumToModelId(ModelType model_type); + // Runs an integrity check on the current database. If the
+ // integrity check fails, false is returned and error is populated
+ // with an error message.
+ bool CheckIntegrity(sqlite3* handle, string* error) const; + // Migration utilities. bool AddColumn(const ColumnSpec* column); bool RefreshColumns(); diff --git a/chrome/browser/sync/syncable/directory_backing_store_unittest.cc b/chrome/browser/sync/syncable/directory_backing_store_unittest.cc index c158f9a..7ec3d49 100644 --- a/chrome/browser/sync/syncable/directory_backing_store_unittest.cc +++ b/chrome/browser/sync/syncable/directory_backing_store_unittest.cc @@ -1019,7 +1019,8 @@ TEST_F(DirectoryBackingStoreTest, ModelTypeIds) { } } -TEST_F(DirectoryBackingStoreTest, Corruption) { +// TODO(tim): Disabled due to bug 48502. +TEST_F(DirectoryBackingStoreTest, DISABLED_Corruption) { { scoped_ptr<DirectoryBackingStore> dbs( new DirectoryBackingStore(GetUsername(), GetDatabasePath())); |