| Index: chrome/browser/sync/engine/syncer_thread.h
|
| ===================================================================
|
| --- chrome/browser/sync/engine/syncer_thread.h (revision 0)
|
| +++ chrome/browser/sync/engine/syncer_thread.h (revision 0)
|
| @@ -0,0 +1,235 @@
|
| +// Copyright (c) 2009 The Chromium Authors. All rights reserved.
|
| +// Use of this source code is governed by a BSD-style license that can be
|
| +// found in the LICENSE file.
|
| +//
|
| +// A class to run the syncer on a thread.
|
| +//
|
| +
|
| +#ifndef CHROME_BROWSER_SYNC_ENGINE_SYNCER_THREAD_H_
|
| +#define CHROME_BROWSER_SYNC_ENGINE_SYNCER_THREAD_H_
|
| +
|
| +#include <list>
|
| +#include <map>
|
| +#include <queue>
|
| +#include <vector>
|
| +
|
| +#include "base/basictypes.h"
|
| +#include "base/scoped_ptr.h"
|
| +#include "chrome/browser/sync/engine/all_status.h"
|
| +#include "chrome/browser/sync/engine/client_command_channel.h"
|
| +#include "chrome/browser/sync/util/event_sys-inl.h"
|
| +#include "chrome/browser/sync/util/pthread_helpers.h"
|
| +#include "testing/gtest/include/gtest/gtest_prod.h" // For FRIEND_TEST
|
| +
|
| +class EventListenerHookup;
|
| +
|
| +namespace syncable {
|
| +class DirectoryManager;
|
| +struct DirectoryManagerEvent;
|
| +}
|
| +
|
| +namespace browser_sync {
|
| +
|
| +class ModelSafeWorker;
|
| +class ServerConnectionManager;
|
| +class Syncer;
|
| +class TalkMediator;
|
| +class URLFactory;
|
| +struct ServerConnectionEvent;
|
| +struct SyncerEvent;
|
| +struct SyncerShutdownEvent;
|
| +struct TalkMediatorEvent;
|
| +
|
| +class SyncerThread {
|
| + FRIEND_TEST(SyncerThreadTest, CalculateSyncWaitTime);
|
| + FRIEND_TEST(SyncerThreadTest, CalculatePollingWaitTime);
|
| +
|
| + public:
|
| + friend class SyncerThreadTest;
|
| +
|
| + enum NudgeSource {
|
| + kUnknown = 0,
|
| + kNotification,
|
| + kLocal,
|
| + kContinuation
|
| + };
|
| +
|
| + // Server can overwrite these values via client commands.
|
| + // Standard short poll. This is used when XMPP is off.
|
| + static const int kDefaultShortPollIntervalSeconds = 60;
|
| + // Long poll is used when XMPP is on.
|
| + static const int kDefaultLongPollIntervalSeconds = 3600;
|
| + // 30 minutes by default. If exponential backoff kicks in, this is
|
| + // the longest possible poll interval.
|
| + static const int kDefaultMaxPollIntervalMs = 30 * 60 * 1000;
|
| +
|
| + SyncerThread(
|
| + ClientCommandChannel* command_channel,
|
| + syncable::DirectoryManager* mgr,
|
| + ServerConnectionManager* connection_manager,
|
| + AllStatus* all_status,
|
| + ModelSafeWorker* model_safe_worker);
|
| + ~SyncerThread();
|
| +
|
| + void WatchConnectionManager(ServerConnectionManager* conn_mgr);
|
| + // Creates and starts a syncer thread.
|
| + // Returns true if it creates a thread or if there's currently a thread
|
| + // running and false otherwise.
|
| + bool Start();
|
| +
|
| + // Stop processing. A max wait of at least 2*server RTT time is recommended.
|
| + // returns true if we stopped, false otherwise.
|
| + bool Stop(int max_wait);
|
| +
|
| + // Nudges the syncer to sync with a delay specified. This API is for access
|
| + // from the SyncerThread's controller and will cause a mutex lock.
|
| + bool NudgeSyncer(int milliseconds_from_now, NudgeSource source);
|
| +
|
| + // Registers this thread to watch talk mediator events.
|
| + void WatchTalkMediator(TalkMediator* talk_mediator);
|
| +
|
| + void WatchClientCommands(ClientCommandChannel* channel);
|
| +
|
| + SyncerEventChannel* channel();
|
| +
|
| + private:
|
| + // A few members to gate the rate at which we nudge the syncer.
|
| + enum {
|
| + kNudgeRateLimitCount = 6,
|
| + kNudgeRateLimitTime = 180,
|
| + };
|
| +
|
| + // A queue of all scheduled nudges. One insertion for every call to
|
| + // NudgeQueue().
|
| + typedef std::pair<timespec, NudgeSource> NudgeObject;
|
| +
|
| + struct IsTimeSpecGreater {
|
| + inline bool operator() (const NudgeObject& lhs, const NudgeObject& rhs) {
|
| + return lhs.first.tv_sec == rhs.first.tv_sec ?
|
| + lhs.first.tv_nsec > rhs.first.tv_nsec :
|
| + lhs.first.tv_sec > rhs.first.tv_sec;
|
| + }
|
| + };
|
| +
|
| + typedef std::priority_queue<NudgeObject,
|
| + std::vector<NudgeObject>, IsTimeSpecGreater>
|
| + NudgeQueue;
|
| +
|
| + // Threshold multipler for how long before user should be considered idle.
|
| + static const int kPollBackoffThresholdMultiplier = 10;
|
| +
|
| + friend void* RunSyncerThread(void* syncer_thread);
|
| + void* Run();
|
| + void HandleDirectoryManagerEvent(
|
| + const syncable::DirectoryManagerEvent& event);
|
| + void HandleSyncerEvent(const SyncerEvent& event);
|
| + void HandleClientCommand(ClientCommandChannel::EventType event);
|
| +
|
| + void HandleServerConnectionEvent(const ServerConnectionEvent& event);
|
| +
|
| + void HandleTalkMediatorEvent(const TalkMediatorEvent& event);
|
| +
|
| + void* ThreadMain();
|
| + void ThreadMainLoop();
|
| +
|
| + void SyncMain(Syncer* syncer);
|
| +
|
| + // Calculates the next sync wait time in seconds. last_poll_wait is the time
|
| + // duration of the previous polling timeout which was used.
|
| + // user_idle_milliseconds is updated by this method, and is a report of the
|
| + // full amount of time since the last period of activity for the user. The
|
| + // continue_sync_cycle parameter is used to determine whether or not we are
|
| + // calculating a polling wait time that is a continuation of an sync cycle
|
| + // which terminated while the syncer still had work to do.
|
| + int CalculatePollingWaitTime(
|
| + const AllStatus::Status& status,
|
| + int last_poll_wait, // in s
|
| + int* user_idle_milliseconds,
|
| + bool* continue_sync_cycle);
|
| + // Helper to above function, considers effect of user idle time.
|
| + int CalculateSyncWaitTime(int last_wait, int user_idle_ms);
|
| +
|
| + // Sets the source value of the controlled syncer's updates_source value.
|
| + // The initial sync boolean is updated if read as a sentinel. The following
|
| + // two methods work in concert to achieve this goal.
|
| + void UpdateNudgeSource(const timespec& now, bool* continue_sync_cycle,
|
| + bool* initial_sync);
|
| + void SetUpdatesSource(bool nudged, NudgeSource nudge_source,
|
| + bool* initial_sync);
|
| +
|
| + // for unit tests only
|
| + void DisableIdleDetection() { disable_idle_detection_ = true; }
|
| +
|
| + // false when we want to stop the thread.
|
| + bool stop_syncer_thread_;
|
| +
|
| + // we use one mutex for all members except the channel.
|
| + PThreadMutex mutex_;
|
| + typedef PThreadScopedLock<PThreadMutex> MutexLock;
|
| +
|
| + // Handle of the running thread.
|
| + pthread_t thread_;
|
| + bool thread_running_;
|
| +
|
| + // Gets signaled whenever a thread outside of the syncer thread
|
| + // changes a member variable.
|
| + PThreadCondVar changed_;
|
| +
|
| + // State of the server connection
|
| + bool connected_;
|
| +
|
| + // State of the notification framework is tracked by these values.
|
| + bool p2p_authenticated_;
|
| + bool p2p_subscribed_;
|
| +
|
| + scoped_ptr<EventListenerHookup> client_command_hookup_;
|
| + scoped_ptr<EventListenerHookup> conn_mgr_hookup_;
|
| + const AllStatus* allstatus_;
|
| +
|
| + Syncer* syncer_;
|
| +
|
| + syncable::DirectoryManager* dirman_;
|
| + ServerConnectionManager* scm_;
|
| +
|
| + // Modifiable versions of kDefaultLongPollIntervalSeconds which can be
|
| + // updated by the server.
|
| + int syncer_short_poll_interval_seconds_;
|
| + int syncer_long_poll_interval_seconds_;
|
| +
|
| + // The time we wait between polls in seconds. This is used as lower bound on
|
| + // our wait time. Updated once per loop from the command line flag.
|
| + int syncer_polling_interval_;
|
| +
|
| + // The upper bound on the nominal wait between polls in seconds. Note that
|
| + // this bounds the "nominal" poll interval, while the the actual interval
|
| + // also takes previous failures into account.
|
| + int syncer_max_interval_;
|
| +
|
| + scoped_ptr<SyncerEventChannel> syncer_event_channel_;
|
| +
|
| + // This causes syncer to start syncing ASAP. If the rate of requests is
|
| + // too high the request will be silently dropped. mutex_ should be held when
|
| + // this is called.
|
| + void NudgeSyncImpl(int milliseconds_from_now, NudgeSource source);
|
| +
|
| + NudgeQueue nudge_queue_;
|
| +
|
| + scoped_ptr<EventListenerHookup> talk_mediator_hookup_;
|
| + ClientCommandChannel* const command_channel_;
|
| + scoped_ptr<EventListenerHookup> directory_manager_hookup_;
|
| + scoped_ptr<EventListenerHookup> syncer_events_;
|
| +
|
| + // Handles any tasks that will result in model changes (modifications of
|
| + // syncable::Entries). Pass this to the syncer created and managed by |this|.
|
| + // Only non-null in syncapi case.
|
| + scoped_ptr<ModelSafeWorker> model_safe_worker_;
|
| +
|
| + // Useful for unit tests
|
| + bool disable_idle_detection_;
|
| +
|
| + DISALLOW_COPY_AND_ASSIGN(SyncerThread);
|
| +};
|
| +
|
| +} // namespace browser_sync
|
| +
|
| +#endif // CHROME_BROWSER_SYNC_ENGINE_SYNCER_THREAD_H_
|
|
|
| Property changes on: chrome\browser\sync\engine\syncer_thread.h
|
| ___________________________________________________________________
|
| Added: svn:eol-style
|
| + LF
|
|
|
|
|