1 // Copyright 2017 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 CHROME_BROWSER_SAFE_BROWSING_CHROME_CLEANER_CHROME_CLEANER_CONTROLLER_IMPL_WIN_H_
6 #define CHROME_BROWSER_SAFE_BROWSING_CHROME_CLEANER_CHROME_CLEANER_CONTROLLER_IMPL_WIN_H_
7 
8 #include "chrome/browser/safe_browsing/chrome_cleaner/chrome_cleaner_controller_win.h"
9 
10 #include <memory>
11 #include <set>
12 #include <vector>
13 
14 #include "base/memory/weak_ptr.h"
15 #include "base/observer_list.h"
16 #include "base/threading/thread_checker.h"
17 #include "chrome/browser/safe_browsing/chrome_cleaner/chrome_cleaner_runner_win.h"
18 #include "chrome/browser/safe_browsing/chrome_cleaner/chrome_cleaner_scanner_results_win.h"
19 #include "chrome/browser/safe_browsing/chrome_cleaner/chrome_prompt_actions_win.h"
20 #include "components/component_updater/component_updater_service.h"
21 
22 namespace extensions {
23 class ExtensionRegistry;
24 }
25 
26 namespace safe_browsing {
27 
28 // Delegate class that provides services to the ChromeCleanerController class
29 // and can be overridden by tests via
30 // SetChromeCleanerControllerDelegateForTesting().
31 class ChromeCleanerControllerDelegate {
32  public:
33   using FetchedCallback = base::OnceCallback<void(base::FilePath)>;
34 
35   ChromeCleanerControllerDelegate();
36   virtual ~ChromeCleanerControllerDelegate();
37 
38   // Fetches and verifies the Chrome Cleaner binary and passes the name of the
39   // executable to |fetched_callback|. The file name will have the ".exe"
40   // extension. If the operation fails, the file name passed to
41   // |fetched_callback| will be empty.
42   virtual void FetchAndVerifyChromeCleaner(FetchedCallback fetched_callback);
43   virtual bool IsMetricsAndCrashReportingEnabled();
44 
45   // Auxiliary methods for tagging and resetting open profiles.
46   virtual void TagForResetting(Profile* profile);
47   virtual void ResetTaggedProfiles(std::vector<Profile*> profiles,
48                                    base::OnceClosure continuation);
49 
50   // Starts the reboot prompt flow if a cleanup requires a machine restart.
51   virtual void StartRebootPromptFlow(ChromeCleanerController* controller);
52 
53   // Checks if the cleaner is allowed to run by enterprise policy.
54   virtual bool IsAllowedByPolicy();
55 };
56 
57 class ChromeCleanerControllerImpl : public ChromeCleanerController {
58  public:
59   // Returns the global controller object.
60   static ChromeCleanerControllerImpl* GetInstance();
61 
62   // ChromeCleanerController overrides.
63   State state() const override;
64   IdleReason idle_reason() const override;
65   void SetLogsEnabled(Profile* profile, bool logs_enabled) override;
66   bool logs_enabled(Profile* profile) const override;
67   void ResetIdleState() override;
68   void AddObserver(Observer* observer) override;
69   void RemoveObserver(Observer* observer) override;
70   bool HasObserver(Observer* observer) override;
71   void OnReporterSequenceStarted() override;
72   void OnReporterSequenceDone(SwReporterInvocationResult result) override;
73   void RequestUserInitiatedScan(Profile* profile) override;
74   void OnSwReporterReady(SwReporterInvocationSequence&& invocations) override;
75   void Scan(const SwReporterInvocation& reporter_invocation) override;
76   void ReplyWithUserResponse(Profile* profile,
77                              extensions::ExtensionService* extension_service,
78                              UserResponse user_response) override;
79   void Reboot() override;
80   bool IsAllowedByPolicy() override;
81   bool IsReportingManagedByPolicy(Profile* profile) override;
82 
83   static void ResetInstanceForTesting();
84   // Passing in a nullptr as |delegate| resets the delegate to a default
85   // production version.
86   void SetDelegateForTesting(ChromeCleanerControllerDelegate* delegate);
87 
88   // Force the current controller's state for tests that check the effect of
89   // starting and completing reporter runs.
90   void SetStateForTesting(State state);
91   void SetIdleForTesting(IdleReason idle_reason);
92 
93  private:
94   ChromeCleanerControllerImpl();
95   ~ChromeCleanerControllerImpl() override;
96 
97   void NotifyObserver(Observer* observer) const;
98   void SetStateAndNotifyObservers(State state);
99   // Used to invalidate weak pointers and reset accumulated data that is no
100   // longer needed when entering the kIdle or kRebootRequired states.
101   void ResetCleanerDataAndInvalidateWeakPtrs();
102 
103   // Callback that is called when the Chrome Cleaner binary has been fetched and
104   // verified. An empty |executable_path| signals failure. A non-empty
105   // |executable_path| must have the '.exe' file extension.
106   void OnChromeCleanerFetchedAndVerified(base::FilePath executable_path);
107 
108   // Callback that checks if the weak pointer |controller| is still valid, and
109   // if so will call OnPromptuser(). If |controller| is no longer valid, will
110   // immediately send an IPC response denying the cleanup operation.
111   //
112   // The other callbacks below do not need corresponding "weak" callbacks,
113   // because for those cases nothing needs to be done if the weak pointer
114   // referencing the controller instance is no longer valid (Chrome's Callback
115   // objects become no-ops if the bound weak pointer is not valid).
116   static void WeakOnPromptUser(
117       const base::WeakPtr<ChromeCleanerControllerImpl>& controller,
118       ChromeCleanerScannerResults&& reported_results,
119       ChromePromptActions::PromptUserReplyCallback reply_callback);
120 
121   void OnPromptUser(
122       ChromeCleanerScannerResults&& reported_results,
123       ChromePromptActions::PromptUserReplyCallback reply_callback);
124   void OnConnectionClosed();
125   void OnCleanerProcessDone(ChromeCleanerRunner::ProcessStatus process_status);
126   void InitiateReboot();
127 
128   std::unique_ptr<ChromeCleanerControllerDelegate> real_delegate_;
129   // Pointer to either real_delegate_ or one set by tests.
130   ChromeCleanerControllerDelegate* delegate_;
131 
132   extensions::ExtensionService* extension_service_ = nullptr;
133   extensions::ExtensionRegistry* extension_registry_ = nullptr;
134 
135   State state_ = State::kIdle;
136   // Whether Cleanup is powered by an external partner.
137   bool powered_by_partner_ = false;
138   IdleReason idle_reason_ = IdleReason::kInitial;
139   std::unique_ptr<SwReporterInvocation> reporter_invocation_;
140   ChromeCleanerScannerResults scanner_results_;
141   // Callback that should be called to send a response to the Chrome Cleaner
142   // process.
143   ChromePromptActions::PromptUserReplyCallback prompt_user_reply_callback_;
144 
145   // For metrics reporting.
146   base::Time time_scanning_started_;
147   base::Time time_cleanup_started_;
148 
149   base::ObserverList<Observer> observer_list_;
150 
151   // Mutex that guards |pending_invocation_type_|,
152   // |on_demand_sw_reporter_fetcher_| and |cached_reporter_invocations_|.
153   mutable base::Lock lock_;
154   SwReporterInvocationType pending_invocation_type_ =
155       SwReporterInvocationType::kPeriodicRun;
156   std::unique_ptr<component_updater::SwReporterOnDemandFetcher>
157       on_demand_sw_reporter_fetcher_;
158   // Note: SwReporterInvocationSequence is mutable and should not be used more
159   // than once. Special care must be taken that the invocations are not sent
160   // to a |ReporterRunner| more than once.
161   std::unique_ptr<SwReporterInvocationSequence> cached_reporter_invocations_;
162 
163   THREAD_CHECKER(thread_checker_);
164 
165   base::WeakPtrFactory<ChromeCleanerControllerImpl> weak_factory_{this};
166 
167   DISALLOW_COPY_AND_ASSIGN(ChromeCleanerControllerImpl);
168 };
169 
170 }  // namespace safe_browsing
171 
172 #endif  // CHROME_BROWSER_SAFE_BROWSING_CHROME_CLEANER_CHROME_CLEANER_CONTROLLER_IMPL_WIN_H_
173