1ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen// Copyright (c) 2011 The Chromium Authors. All rights reserved.
2c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// Use of this source code is governed by a BSD-style license that can be
3c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// found in the LICENSE file.
4c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
5c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// The 'sessions' namespace comprises all the pieces of state that are
6c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// combined to form a SyncSession instance. In that way, it can be thought of
7c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// as an extension of the SyncSession type itself. Session scoping gives
8c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// context to things like "conflict progress", "update progress", etc, and the
9c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// separation this file provides allows clients to only include the parts they
10c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// need rather than the entire session stack.
11c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
12c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#ifndef CHROME_BROWSER_SYNC_SESSIONS_SESSION_STATE_H_
13c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#define CHROME_BROWSER_SYNC_SESSIONS_SESSION_STATE_H_
143345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick#pragma once
15c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
16dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen#include <map>
17c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include <set>
18dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen#include <string>
19dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen#include <utility>
20c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include <vector>
21c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
22c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "base/basictypes.h"
23c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "chrome/browser/sync/engine/syncer_types.h"
24c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "chrome/browser/sync/engine/syncproto.h"
25c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "chrome/browser/sync/sessions/ordered_commit_set.h"
26c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "chrome/browser/sync/syncable/model_type.h"
27ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen#include "chrome/browser/sync/syncable/model_type_payload_map.h"
28c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "chrome/browser/sync/syncable/syncable.h"
29c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
3072a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsenclass DictionaryValue;
3172a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen
32c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochnamespace syncable {
33c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochclass DirectoryManager;
34c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch}
35c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
36c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochnamespace browser_sync {
37c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochnamespace sessions {
38c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
39c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochclass UpdateProgress;
40c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
4172a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen// A container for the source of a sync session. This includes the update
4272a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen// source, the datatypes triggering the sync session, and possible session
4372a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen// specific payloads which should be sent to the server.
4472a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsenstruct SyncSourceInfo {
4572a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  SyncSourceInfo();
46ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen  explicit SyncSourceInfo(const syncable::ModelTypePayloadMap& t);
47dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen  SyncSourceInfo(
4872a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen      const sync_pb::GetUpdatesCallerInfo::GetUpdatesSource& u,
49ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen      const syncable::ModelTypePayloadMap& t);
5072a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  ~SyncSourceInfo();
5172a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen
5272a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  // Caller takes ownership of the returned dictionary.
5372a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  DictionaryValue* ToValue() const;
5472a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen
5572a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  sync_pb::GetUpdatesCallerInfo::GetUpdatesSource updates_source;
56ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen  syncable::ModelTypePayloadMap types;
5772a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen};
5872a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen
59c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// Data pertaining to the status of an active Syncer object.
60c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochstruct SyncerStatus {
6172a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  SyncerStatus();
62ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen  ~SyncerStatus();
6372a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen
6472a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  // Caller takes ownership of the returned dictionary.
6572a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  DictionaryValue* ToValue() const;
66c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
67c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // True when we get such an INVALID_STORE error from the server.
68c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  bool invalid_store;
69c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // True iff we're stuck.
70c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  bool syncer_stuck;
71c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  bool syncing;
72c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  int num_successful_commits;
73c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // This is needed for monitoring extensions activity.
74c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  int num_successful_bookmark_commits;
7572a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen
7672a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  // Download event counters.
7772a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  int num_updates_downloaded_total;
7872a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  int num_tombstone_updates_downloaded_total;
79ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen
80ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen  // If the syncer encountered a MIGRATION_DONE code, these are the types that
81ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen  // the client must now "migrate", by purging and re-downloading all updates.
82ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen  syncable::ModelTypeSet types_needing_local_migration;
83c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch};
84c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
85c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// Counters for various errors that can occur repeatedly during a sync session.
86c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochstruct ErrorCounters {
8772a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  ErrorCounters();
8872a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen
8972a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  // Caller takes ownership of the returned dictionary.
9072a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  DictionaryValue* ToValue() const;
9172a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen
92c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  int num_conflicting_commits;
93c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
94c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // Number of commits hitting transient errors since the last successful
95c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // commit.
96c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  int consecutive_transient_error_commits;
97c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
98c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // Incremented when get_updates fails, commit fails, and when hitting
99c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // transient errors. When any of these succeed, this counter is reset.
100c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // TODO(chron): Reduce number of weird counters we use.
101c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  int consecutive_errors;
102c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch};
103c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
10472a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen// Caller takes ownership of the returned dictionary.
10572a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian MonsenDictionaryValue* DownloadProgressMarkersToValue(
10672a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen    const std::string
10772a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen        (&download_progress_markers)[syncable::MODEL_TYPE_COUNT]);
10872a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen
109c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// An immutable snapshot of state from a SyncSession.  Convenient to use as
110c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// part of notifications as it is inherently thread-safe.
111c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochstruct SyncSessionSnapshot {
11272a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  SyncSessionSnapshot(
11372a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen      const SyncerStatus& syncer_status,
114c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch      const ErrorCounters& errors,
115c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch      int64 num_server_changes_remaining,
116c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch      bool is_share_usable,
117c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch      const syncable::ModelTypeBitSet& initial_sync_ended,
11872a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen      const std::string
11972a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen          (&download_progress_markers)[syncable::MODEL_TYPE_COUNT],
120c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch      bool more_to_sync,
121c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch      bool is_silenced,
122c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch      int64 unsynced_count,
123c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch      int num_conflicting_updates,
12472a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen      bool did_commit_items,
12572a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen      const SyncSourceInfo& source);
126731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick  ~SyncSessionSnapshot();
127731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick
12872a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  // Caller takes ownership of the returned dictionary.
12972a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  DictionaryValue* ToValue() const;
13072a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen
131c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  const SyncerStatus syncer_status;
132c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  const ErrorCounters errors;
133c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  const int64 num_server_changes_remaining;
134c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  const bool is_share_usable;
135c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  const syncable::ModelTypeBitSet initial_sync_ended;
13672a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  const std::string download_progress_markers[syncable::MODEL_TYPE_COUNT];
137c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  const bool has_more_to_sync;
138c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  const bool is_silenced;
139c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  const int64 unsynced_count;
140c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  const int num_conflicting_updates;
141c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  const bool did_commit_items;
14272a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  const SyncSourceInfo source;
143c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch};
144c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
145c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// Tracks progress of conflicts and their resolution using conflict sets.
146c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochclass ConflictProgress {
147c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch public:
148731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick  explicit ConflictProgress(bool* dirty_flag);
149731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick  ~ConflictProgress();
150c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // Various iterators, size, and retrieval functions for conflict sets.
151c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  IdToConflictSetMap::const_iterator IdToConflictSetBegin() const;
152c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  IdToConflictSetMap::const_iterator IdToConflictSetEnd() const;
153c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  IdToConflictSetMap::size_type IdToConflictSetSize() const;
154c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  IdToConflictSetMap::const_iterator IdToConflictSetFind(
155c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch      const syncable::Id& the_id) const;
156c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  const ConflictSet* IdToConflictSetGet(const syncable::Id& the_id);
157c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  std::set<ConflictSet*>::const_iterator ConflictSetsBegin() const;
158c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  std::set<ConflictSet*>::const_iterator ConflictSetsEnd() const;
159c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  std::set<ConflictSet*>::size_type ConflictSetsSize() const;
160c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
161c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // Various mutators for tracking commit conflicts.
162c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  void AddConflictingItemById(const syncable::Id& the_id);
163c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  void EraseConflictingItemById(const syncable::Id& the_id);
164c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  int ConflictingItemsSize() const { return conflicting_item_ids_.size(); }
165c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  std::set<syncable::Id>::iterator ConflictingItemsBegin();
166c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  std::set<syncable::Id>::const_iterator ConflictingItemsBeginConst() const;
167c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  std::set<syncable::Id>::const_iterator ConflictingItemsEnd() const;
168c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
169c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  void MergeSets(const syncable::Id& set1, const syncable::Id& set2);
170c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  void CleanupSets();
171c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
172c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch private:
173c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // TODO(sync): move away from sets if it makes more sense.
174c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  std::set<syncable::Id> conflicting_item_ids_;
175c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  std::map<syncable::Id, ConflictSet*> id_to_conflict_set_;
176c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  std::set<ConflictSet*> conflict_sets_;
177c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
178c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // Whether a conflicting item was added or removed since
179c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // the last call to reset_progress_changed(), if any. In practice this
180c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // points to StatusController::is_dirty_.
181c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  bool* dirty_;
182c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch};
183c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
184c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochtypedef std::pair<VerifyResult, sync_pb::SyncEntity> VerifiedUpdate;
185c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochtypedef std::pair<UpdateAttemptResponse, syncable::Id> AppliedUpdate;
186c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
187c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// Tracks update application and verification.
188c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochclass UpdateProgress {
189c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch public:
190731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick  UpdateProgress();
191731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick  ~UpdateProgress();
192731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick
193c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  void AddVerifyResult(const VerifyResult& verify_result,
194c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch                       const sync_pb::SyncEntity& entity);
195c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
196c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // Log a successful or failing update attempt.
197c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  void AddAppliedUpdate(const UpdateAttemptResponse& response,
198c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch                        const syncable::Id& id);
199c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
200c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // Various iterators.
201c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  std::vector<AppliedUpdate>::iterator AppliedUpdatesBegin();
202c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  std::vector<VerifiedUpdate>::const_iterator VerifiedUpdatesBegin() const;
203c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  std::vector<AppliedUpdate>::const_iterator AppliedUpdatesEnd() const;
204c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  std::vector<VerifiedUpdate>::const_iterator VerifiedUpdatesEnd() const;
205c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
206c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // Returns the number of update application attempts.  This includes both
207c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // failures and successes.
208c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  int AppliedUpdatesSize() const { return applied_updates_.size(); }
209c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  int VerifiedUpdatesSize() const { return verified_updates_.size(); }
210c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  bool HasVerifiedUpdates() const { return !verified_updates_.empty(); }
211c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  bool HasAppliedUpdates() const { return !applied_updates_.empty(); }
212c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
213c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // Count the number of successful update applications that have happend this
214c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // cycle. Note that if an item is successfully applied twice, it will be
215c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // double counted here.
216c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  int SuccessfullyAppliedUpdateCount() const;
217c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
218c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // Returns true if at least one update application failed due to a conflict
219c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // during this sync cycle.
220c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  bool HasConflictingUpdates() const;
221c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
222c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch private:
223c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // Container for updates that passed verification.
224c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  std::vector<VerifiedUpdate> verified_updates_;
225c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
226c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // Stores the result of the various ApplyUpdate attempts we've made.
227c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // May contain duplicate entries.
228c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  std::vector<AppliedUpdate> applied_updates_;
229c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch};
230c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
231c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochstruct SyncCycleControlParameters {
232c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  SyncCycleControlParameters() : conflict_sets_built(false),
233c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch                                 conflicts_resolved(false),
234c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch                                 items_committed(false) {}
235c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // Set to true by BuildAndProcessConflictSetsCommand if the RESOLVE_CONFLICTS
236c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // step is needed.
237c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  bool conflict_sets_built;
238c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
239c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // Set to true by ResolveConflictsCommand if any forward progress was made.
240c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  bool conflicts_resolved;
241c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
242c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // Set to true by PostCommitMessageCommand if any commits were successful.
243c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  bool items_committed;
244c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch};
245c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
246c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// DirtyOnWrite wraps a value such that any write operation will update a
247c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// specified dirty bit, which can be used to determine if a notification should
248c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// be sent due to state change.
249c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochtemplate <typename T>
250c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochclass DirtyOnWrite {
251c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch public:
252c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  explicit DirtyOnWrite(bool* dirty) : dirty_(dirty) {}
253c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  DirtyOnWrite(bool* dirty, const T& t) : t_(t), dirty_(dirty) {}
254c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  T* mutate() {
255c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch    *dirty_ = true;
256c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch    return &t_;
257c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  }
258c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  const T& value() const { return t_; }
259c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch private:
260c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  T t_;
261c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  bool* dirty_;
262c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch};
263c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
264c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// The next 3 structures declare how all the state involved in running a sync
265c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// cycle is divided between global scope (applies to all model types),
266c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// ModelSafeGroup scope (applies to all data types in a group), and single
267c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// model type scope.  Within this breakdown, each struct declares which bits
268c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// of state are dirty-on-write and should incur dirty bit updates if changed.
269c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
270c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// Grouping of all state that applies to all model types.  Note that some
271c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// components of the global grouping can internally implement finer grained
272c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// scope control (such as OrderedCommitSet), but the top level entity is still
273c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// a singleton with respect to model types.
274c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochstruct AllModelTypeState {
275731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick  explicit AllModelTypeState(bool* dirty_flag);
276731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick  ~AllModelTypeState();
277731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick
278c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // Commits for all model types are bundled together into a single message.
279c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  ClientToServerMessage commit_message;
280c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  ClientToServerResponse commit_response;
281c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // We GetUpdates for some combination of types at once.
282c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // requested_update_types stores the set of types which were requested.
28372a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen  syncable::ModelTypeBitSet updates_request_types;
284c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  ClientToServerResponse updates_response;
285c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  // Used to build the shared commit message.
286c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  DirtyOnWrite<std::vector<int64> > unsynced_handles;
287c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  DirtyOnWrite<SyncerStatus> syncer_status;
288c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  DirtyOnWrite<ErrorCounters> error_counters;
289c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  SyncCycleControlParameters control_params;
290c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  DirtyOnWrite<int64> num_server_changes_remaining;
291c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  OrderedCommitSet commit_set;
292c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch};
293c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
294c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// Grouping of all state that applies to a single ModelSafeGroup.
295c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochstruct PerModelSafeGroupState {
296731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick  explicit PerModelSafeGroupState(bool* dirty_flag);
297731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick  ~PerModelSafeGroupState();
298731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick
299c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  UpdateProgress update_progress;
300c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch  ConflictProgress conflict_progress;
301c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch};
302c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
303c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch}  // namespace sessions
304c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch}  // namespace browser_sync
305c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch
306c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#endif  // CHROME_BROWSER_SYNC_SESSIONS_SESSION_STATE_H_
307