Upstream version 7.36.149.0
[platform/framework/web/crosswalk.git] / src / remoting / host / setup / daemon_controller.h
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #ifndef REMOTING_HOST_SETUP_DAEMON_CONTROLLER_H_
6 #define REMOTING_HOST_SETUP_DAEMON_CONTROLLER_H_
7
8 #include <queue>
9 #include <string>
10
11 #include "base/callback.h"
12 #include "base/memory/ref_counted.h"
13 #include "base/memory/scoped_ptr.h"
14
15 namespace base {
16 class DictionaryValue;
17 class SingleThreadTaskRunner;
18 }  // namespace base
19
20 namespace remoting {
21
22 class AutoThread;
23 class AutoThreadTaskRunner;
24
25 class DaemonController : public base::RefCountedThreadSafe<DaemonController> {
26  public:
27   // Note that these enumeration values are duplicated in host_controller.js and
28   // must be kept in sync.
29   enum State {
30     // Placeholder state for platforms on which the daemon process is not
31     // implemented. The web-app will not show the corresponding UI. This value
32     // will eventually be deprecated or removed.
33     STATE_NOT_IMPLEMENTED = -1,
34     // The daemon is not installed. This is functionally equivalent to
35     // STATE_STOPPED, but the start method is expected to be significantly
36     // slower, and might involve user interaction. It might be appropriate to
37     // indicate this in the UI.
38     STATE_NOT_INSTALLED = 0,
39     // The daemon is being installed.
40     STATE_INSTALLING = 1,
41     // The daemon is installed but not running. Call Start to start it.
42     STATE_STOPPED = 2,
43     // The daemon process is starting.
44     STATE_STARTING = 3,
45     // The daemon process is running. Call Start again to change the PIN or
46     // Stop to stop it.
47     STATE_STARTED = 4,
48     // The daemon process is stopping.
49     STATE_STOPPING = 5,
50     // The state cannot be determined. This could indicate that the plugin
51     // has not been provided with sufficient information, for example, the
52     // user for which to query state on a multi-user system.
53     STATE_UNKNOWN = 6
54   };
55
56   // Enum used for completion callback.
57   enum AsyncResult {
58     RESULT_OK = 0,
59
60     // The operation has FAILED.
61     RESULT_FAILED = 1,
62
63     // User has cancelled the action (e.g. rejected UAC prompt).
64     // TODO(sergeyu): Current implementations don't return this value.
65     RESULT_CANCELLED = 2,
66
67     // Failed to access host directory.
68     RESULT_FAILED_DIRECTORY = 3
69
70     // TODO(sergeyu): Add more error codes when we know how to handle
71     // them in the webapp.
72   };
73
74   // Callback type for GetConfig(). If the host is configured then a dictionary
75   // is returned containing host_id and xmpp_login, with security-sensitive
76   // fields filtered out. An empty dictionary is returned if the host is not
77   // configured, and NULL if the configuration is corrupt or cannot be read.
78   typedef base::Callback<void (scoped_ptr<base::DictionaryValue> config)>
79       GetConfigCallback;
80
81   // Callback used for asynchronous operations, e.g. when
82   // starting/stopping the service.
83   typedef base::Callback<void (AsyncResult result)> CompletionCallback;
84
85   // Callback type for GetVersion().
86   typedef base::Callback<void (const std::string&)> GetVersionCallback;
87
88   struct UsageStatsConsent {
89     // Indicates whether crash dump reporting is supported by the host.
90     bool supported;
91
92     // Indicates if crash dump reporting is allowed by the user.
93     bool allowed;
94
95     // Carries information whether the crash dump reporting is controlled by
96     // policy.
97     bool set_by_policy;
98   };
99
100   // Callback type for GetUsageStatsConsent().
101   typedef base::Callback<void (const UsageStatsConsent&)>
102       GetUsageStatsConsentCallback;
103
104   // Interface representing the platform-spacific back-end. Most of its methods
105   // are blocking and should be called on a background thread. There are two
106   // exceptions:
107   //   - GetState() is synchronous and called on the UI thread. It should avoid
108   //         accessing any data members of the implementation.
109   //   - SetConfigAndStart(), UpdateConfig() and Stop() indicate completion via
110   //         a callback. There methods can be long running and should be caled
111   //         on a background thread.
112   class Delegate {
113    public:
114     virtual ~Delegate() {}
115
116     // Return the "installed/running" state of the daemon process. This method
117     // should avoid accessing any data members of the implementation.
118     virtual State GetState() = 0;
119
120     // Queries current host configuration. Any values that might be security
121     // sensitive have been filtered out.
122     virtual scoped_ptr<base::DictionaryValue> GetConfig() = 0;
123
124     // Download and install the host component. |done| is invoked on the
125     // calling thread when the operation is completed.
126     virtual void InstallHost(const CompletionCallback& done) = 0;
127
128     // Starts the daemon process. This may require that the daemon be
129     // downloaded and installed. |done| is invoked on the calling thread when
130     // the operation is completed.
131     virtual void SetConfigAndStart(
132         scoped_ptr<base::DictionaryValue> config,
133         bool consent,
134         const CompletionCallback& done) = 0;
135
136     // Updates current host configuration with the values specified in
137     // |config|. Any value in the existing configuration that isn't specified in
138     // |config| is preserved. |config| must not contain host_id or xmpp_login
139     // values, because implementations of this method cannot change them. |done|
140     // is invoked on the calling thread when the operation is completed.
141     virtual void UpdateConfig(
142         scoped_ptr<base::DictionaryValue> config,
143         const CompletionCallback& done) = 0;
144
145     // Stops the daemon process. |done| is invoked on the calling thread when
146     // the operation is completed.
147     virtual void Stop(const CompletionCallback& done) = 0;
148
149     // Caches the native handle of the plugin window so it can be used to focus
150     // elevation prompts properly.
151     virtual void SetWindow(void* window_handle) = 0;
152
153     // Get the version of the daemon as a dotted decimal string of the form
154     // major.minor.build.patch, if it is installed, or "" otherwise.
155     virtual std::string GetVersion() = 0;
156
157     // Get the user's consent to crash reporting.
158     virtual UsageStatsConsent GetUsageStatsConsent() = 0;
159   };
160
161   static scoped_refptr<DaemonController> Create();
162
163   explicit DaemonController(scoped_ptr<Delegate> delegate);
164
165   // Return the "installed/running" state of the daemon process.
166   //
167   // TODO(sergeyu): This method is called synchronously from the
168   // webapp. In most cases it requires IO operations, so it may block
169   // the user interface. Replace it with asynchronous notifications,
170   // e.g. with StartStateNotifications()/StopStateNotifications() methods.
171   State GetState();
172
173   // Queries current host configuration. The |done| is called
174   // after the configuration is read, and any values that might be security
175   // sensitive have been filtered out.
176   void GetConfig(const GetConfigCallback& done);
177
178   // Download and install the host component. |done| is called when the
179   // operation is finished or fails.
180   void InstallHost(const CompletionCallback& done);
181
182   // Start the daemon process. This may require that the daemon be
183   // downloaded and installed. |done| is called when the
184   // operation is finished or fails.
185   //
186   // TODO(sergeyu): This method writes config and starts the host -
187   // these two steps are merged for simplicity. Consider splitting it
188   // into SetConfig() and Start() once we have basic host setup flow
189   // working.
190   void SetConfigAndStart(scoped_ptr<base::DictionaryValue> config,
191                          bool consent,
192                          const CompletionCallback& done);
193
194   // Updates current host configuration with the values specified in
195   // |config|. Changes must take effect before the call completes.
196   // Any value in the existing configuration that isn't specified in |config|
197   // is preserved. |config| must not contain host_id or xmpp_login values,
198   // because implementations of this method cannot change them.
199   void UpdateConfig(scoped_ptr<base::DictionaryValue> config,
200                     const CompletionCallback& done);
201
202   // Stop the daemon process. It is permitted to call Stop while the daemon
203   // process is being installed, in which case the installation should be
204   // aborted if possible; if not then it is sufficient to ensure that the
205   // daemon process is not started automatically upon successful installation.
206   // As with Start, Stop may return before the operation is complete--poll
207   // GetState until the state is STATE_STOPPED.
208   void Stop(const CompletionCallback& done);
209
210   // Caches the native handle of the plugin window so it can be used to focus
211   // elevation prompts properly.
212   void SetWindow(void* window_handle);
213
214   // Get the version of the daemon as a dotted decimal string of the form
215   // major.minor.build.patch, if it is installed, or "" otherwise.
216   void GetVersion(const GetVersionCallback& done);
217
218   // Get the user's consent to crash reporting.
219   void GetUsageStatsConsent(const GetUsageStatsConsentCallback& done);
220
221  private:
222   friend class base::RefCountedThreadSafe<DaemonController>;
223   virtual ~DaemonController();
224
225   // Blocking helper methods used to call the delegate.
226   void DoGetConfig(const GetConfigCallback& done);
227   void DoInstallHost(const CompletionCallback& done);
228   void DoSetConfigAndStart(scoped_ptr<base::DictionaryValue> config,
229                            bool consent,
230                            const CompletionCallback& done);
231   void DoUpdateConfig(scoped_ptr<base::DictionaryValue> config,
232                       const CompletionCallback& done);
233   void DoStop(const CompletionCallback& done);
234   void DoSetWindow(void* window_handle, const base::Closure& done);
235   void DoGetVersion(const GetVersionCallback& done);
236   void DoGetUsageStatsConsent(const GetUsageStatsConsentCallback& done);
237
238   // "Trampoline" callbacks that schedule the next pending request and then
239   // invoke the original caller-supplied callback.
240   void InvokeCompletionCallbackAndScheduleNext(
241       const CompletionCallback& done,
242       AsyncResult result);
243   void InvokeConfigCallbackAndScheduleNext(
244       const GetConfigCallback& done,
245       scoped_ptr<base::DictionaryValue> config);
246   void InvokeConsentCallbackAndScheduleNext(
247       const GetUsageStatsConsentCallback& done,
248       const UsageStatsConsent& consent);
249   void InvokeVersionCallbackAndScheduleNext(
250       const GetVersionCallback& done,
251       const std::string& version);
252
253   // Queue management methods.
254   void ScheduleNext();
255   void ServiceOrQueueRequest(const base::Closure& request);
256   void ServiceNextRequest();
257
258   // Task runner on which all public methods of this class should be called.
259   scoped_refptr<base::SingleThreadTaskRunner> caller_task_runner_;
260
261   // Task runner used to run blocking calls to the delegate. A single thread
262   // task runner is used to guarantee that one method of the delegate is
263   // called at a time.
264   scoped_refptr<AutoThreadTaskRunner> delegate_task_runner_;
265
266   scoped_ptr<AutoThread> delegate_thread_;
267
268   scoped_ptr<Delegate> delegate_;
269
270   std::queue<base::Closure> pending_requests_;
271
272   DISALLOW_COPY_AND_ASSIGN(DaemonController);
273 };
274
275 }  // namespace remoting
276
277 #endif  // REMOTING_HOST_SETUP_DAEMON_CONTROLLER_H_