| Index: sync/engine/syncer_util.cc
|
| diff --git a/sync/engine/syncer_util.cc b/sync/engine/syncer_util.cc
|
| index fedf4d8f54859528af88700e0d69538574987f7b..05fd73881fa8fcf52db51e51f99af49c941fc2f8 100644
|
| --- a/sync/engine/syncer_util.cc
|
| +++ b/sync/engine/syncer_util.cc
|
| @@ -194,51 +194,6 @@ UpdateAttemptResponse AttemptToUpdateEntry(
|
| syncable::Id id = entry->Get(ID);
|
| const sync_pb::EntitySpecifics& specifics = entry->Get(SERVER_SPECIFICS);
|
|
|
| - // We intercept updates to the Nigori node, update the Cryptographer and
|
| - // encrypt any unsynced changes here because there is no Nigori
|
| - // ChangeProcessor. We never put the nigori node in a state of
|
| - // conflict_encryption.
|
| - //
|
| - // We always update the cryptographer with the server's nigori node,
|
| - // even if we have a locally modified nigori node (we manually merge nigori
|
| - // data in the conflict resolver in that case). This handles the case where
|
| - // two clients both set a different passphrase. The second client to attempt
|
| - // to commit will go into a state of having pending keys, unioned the set of
|
| - // encrypted types, and eventually re-encrypt everything with the passphrase
|
| - // of the first client and commit the set of merged encryption keys. Until the
|
| - // second client provides the pending passphrase, the cryptographer will
|
| - // preserve the encryption keys based on the local passphrase, while the
|
| - // nigori node will preserve the server encryption keys.
|
| - //
|
| - // If non-encryption changes are made to the nigori node, they will be
|
| - // lost as part of conflict resolution. This is intended, as we place a higher
|
| - // priority on preserving the server's passphrase change to preserving local
|
| - // non-encryption changes. Next time the non-encryption changes are made to
|
| - // the nigori node (e.g. on restart), they will commit without issue.
|
| - if (specifics.has_nigori()) {
|
| - const sync_pb::NigoriSpecifics& nigori = specifics.nigori();
|
| - cryptographer->Update(nigori);
|
| -
|
| - // Make sure any unsynced changes are properly encrypted as necessary.
|
| - // We only perform this if the cryptographer is ready. If not, these are
|
| - // re-encrypted at SetDecryptionPassphrase time (via ReEncryptEverything).
|
| - // This logic covers the case where the nigori update marked new datatypes
|
| - // for encryption, but didn't change the passphrase.
|
| - if (cryptographer->is_ready()) {
|
| - // Note that we don't bother to encrypt any data for which IS_UNSYNCED
|
| - // == false here. The machine that turned on encryption should know about
|
| - // and re-encrypt all synced data. It's possible it could get interrupted
|
| - // during this process, but we currently reencrypt everything at startup
|
| - // as well, so as soon as a client is restarted with this datatype marked
|
| - // for encryption, all the data should be updated as necessary.
|
| -
|
| - // If this fails, something is wrong with the cryptographer, but there's
|
| - // nothing we can do about it here.
|
| - DVLOG(1) << "Received new nigori, encrypting unsynced changes.";
|
| - syncable::ProcessUnsyncedChangesForEncryption(trans, cryptographer);
|
| - }
|
| - }
|
| -
|
| // Only apply updates that we can decrypt. If we can't decrypt the update, it
|
| // is likely because the passphrase has not arrived yet. Because the
|
| // passphrase may not arrive within this GetUpdates, we can't just return
|
| @@ -471,6 +426,39 @@ void UpdateLocalDataFromServerData(
|
| entry->Put(IS_UNAPPLIED_UPDATE, false);
|
| }
|
|
|
| +// Allow the server's changes to take precedence.
|
| +// This will take effect during the next ApplyUpdates step.
|
| +void IgnoreLocalChanges(MutableEntry* entry) {
|
| + DCHECK(entry->Get(IS_UNSYNCED));
|
| + DCHECK(entry->Get(IS_UNAPPLIED_UPDATE));
|
| + entry->Put(syncable::IS_UNSYNCED, false);
|
| +}
|
| +
|
| +// Overwrite the server with our own value.
|
| +// We will commit our local data, overwriting the server, at the next
|
| +// opportunity.
|
| +void OverwriteServerChanges(MutableEntry* entry) {
|
| + DCHECK(entry->Get(IS_UNSYNCED));
|
| + DCHECK(entry->Get(IS_UNAPPLIED_UPDATE));
|
| + entry->Put(syncable::BASE_VERSION, entry->Get(syncable::SERVER_VERSION));
|
| + entry->Put(syncable::IS_UNAPPLIED_UPDATE, false);
|
| +}
|
| +
|
| +// Having determined that everything matches, we ignore the non-conflict.
|
| +void IgnoreConflict(MutableEntry* entry) {
|
| + // If we didn't also unset IS_UNAPPLIED_UPDATE, then we would lose unsynced
|
| + // positional data from adjacent entries when the server update gets applied
|
| + // and the item is re-inserted into the PREV_ID/NEXT_ID linked list. This is
|
| + // primarily an issue because we commit after applying updates, and is most
|
| + // commonly seen when positional changes are made while a passphrase is
|
| + // required (and hence there will be many encryption conflicts).
|
| + DCHECK(entry->Get(IS_UNSYNCED));
|
| + DCHECK(entry->Get(IS_UNAPPLIED_UPDATE));
|
| + entry->Put(syncable::BASE_VERSION, entry->Get(syncable::SERVER_VERSION));
|
| + entry->Put(syncable::IS_UNAPPLIED_UPDATE, false);
|
| + entry->Put(syncable::IS_UNSYNCED, false);
|
| +}
|
| +
|
| VerifyCommitResult ValidateCommitEntry(syncable::Entry* entry) {
|
| syncable::Id id = entry->Get(ID);
|
| if (id == entry->Get(PARENT_ID)) {
|
|
|