syncable_file_operation_runner.h revision 1320f92c476a1ad9d19dba2a48c72b75566198e9
1eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch// Copyright 2013 The Chromium Authors. All rights reserved.
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file.
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifndef CHROME_BROWSER_SYNC_FILE_SYSTEM_LOCAL_SYNCABLE_FILE_OPERATION_RUNNER_H_
65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#define CHROME_BROWSER_SYNC_FILE_SYSTEM_LOCAL_SYNCABLE_FILE_OPERATION_RUNNER_H_
71320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci
82a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include <list>
95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <vector>
105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
112a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "base/basictypes.h"
12868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)#include "base/callback.h"
13868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)#include "base/memory/scoped_ptr.h"
14eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch#include "base/memory/weak_ptr.h"
15eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch#include "base/threading/non_thread_safe.h"
16eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch#include "chrome/browser/sync_file_system/local/local_file_sync_status.h"
17eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch#include "storage/browser/fileapi/file_system_url.h"
18eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
19eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdochnamespace storage {
20eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdochclass FileSystemURL;
217d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)}
22a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)
23c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)namespace sync_file_system {
245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// This class must run only on IO thread.
265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Owned by LocalFileSyncContext.
278bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)class SyncableFileOperationRunner
285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : public base::NonThreadSafe,
295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      public base::SupportsWeakPtr<SyncableFileOperationRunner>,
305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      public LocalFileSyncStatus::Observer {
31c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) public:
32c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  // Represents an operation task (which usually wraps one FileSystemOperation).
335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  class Task {
345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)   public:
35a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)    Task() {}
36a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)    virtual ~Task() {}
375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Only one of Run() or Cancel() is called.
395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    virtual void Run() = 0;
405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    virtual void Cancel() = 0;
415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)   protected:
435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // This is never called after Run() or Cancel() is called.
445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    virtual const std::vector<storage::FileSystemURL>& target_paths() const = 0;
455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)   private:
475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    friend class SyncableFileOperationRunner;
485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    bool IsRunnable(LocalFileSyncStatus* status) const;
495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    void Start(LocalFileSyncStatus* status);
505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    static void CancelAndDelete(Task* task);
515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DISALLOW_COPY_AND_ASSIGN(Task);
535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  };
545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  SyncableFileOperationRunner(int64 max_inflight_tasks,
565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                              LocalFileSyncStatus* sync_status);
575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  virtual ~SyncableFileOperationRunner();
585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // LocalFileSyncStatus::Observer overrides.
608bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  virtual void OnSyncEnabled(const storage::FileSystemURL& url) OVERRIDE;
618bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  virtual void OnWriteEnabled(const storage::FileSystemURL& url) OVERRIDE;
628bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
638bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  // Runs the given |task| if no sync operation is running on any of
645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // its target_paths(). This also runs pending tasks that have become
655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // runnable (before running the given operation).
668bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  // If there're ongoing sync tasks on the target_paths this method
675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // just queues up the |task|.
685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Pending tasks are cancelled when this class is destructed.
695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  void PostOperationTask(scoped_ptr<Task> task);
708bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Runs a next runnable task (if there's any).
725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  void RunNextRunnableTask();
73a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)
74a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  // Called when an operation is completed. This will make |target_paths|
755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // writable and may start a next runnable task.
76a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  void OnOperationCompleted(
775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      const std::vector<storage::FileSystemURL>& target_paths);
785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
798bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  LocalFileSyncStatus* sync_status() const { return sync_status_; }
808bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
81a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  int64 num_pending_tasks() const {
82a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)    return static_cast<int64>(pending_tasks_.size());
83a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  }
84a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)
85a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  int64 num_inflight_tasks() const { return num_inflight_tasks_; }
86a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)
87a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles) private:
888bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  // Returns true if we should start more tasks.
898bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  bool ShouldStartMoreTasks() const;
908bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
918bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  // Keeps track of the writing/syncing status. Not owned.
928bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  LocalFileSyncStatus* sync_status_;
938bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
948bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  std::list<Task*> pending_tasks_;
958bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
968bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  const int64 max_inflight_tasks_;
978bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  int64 num_inflight_tasks_;
988bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
998bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)  DISALLOW_COPY_AND_ASSIGN(SyncableFileOperationRunner);
1008bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)};
1018bcbed890bc3ce4d7a057a8f32cab53fa534672eTorne (Richard Coles)
102a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)}  // namespace sync_file_system
103a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)
104a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)#endif  // CHROME_BROWSER_SYNC_FILE_SYSTEM_LOCAL_SYNCABLE_FILE_OPERATION_RUNNER_H_
105a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)