1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
ash / system / human_presence / snooping_protection_controller.h [blame]
// Copyright 2021 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef ASH_SYSTEM_HUMAN_PRESENCE_SNOOPING_PROTECTION_CONTROLLER_H_
#define ASH_SYSTEM_HUMAN_PRESENCE_SNOOPING_PROTECTION_CONTROLLER_H_
#include <memory>
#include <optional>
#include "ash/ash_export.h"
#include "ash/public/cpp/session/session_controller.h"
#include "ash/public/cpp/session/session_observer.h"
#include "ash/system/human_presence/human_presence_orientation_controller.h"
#include "base/observer_list.h"
#include "base/observer_list_types.h"
#include "base/scoped_observation.h"
#include "base/time/time.h"
#include "base/timer/timer.h"
#include "chromeos/ash/components/dbus/hps/hps_service.pb.h"
#include "chromeos/ash/components/dbus/human_presence/human_presence_dbus_client.h"
#include "components/session_manager/session_manager_types.h"
class PrefChangeRegistrar;
class PrefRegistrySimple;
namespace ash {
class SnoopingProtectionNotificationBlocker;
// Pushes status changes to the snooping protection icon and notification
// blocker based on DBus state, preferences and session type.
class ASH_EXPORT SnoopingProtectionController
: public SessionObserver,
public HumanPresenceOrientationController::Observer,
public HumanPresenceDBusClient::Observer {
public:
class Observer : public base::CheckedObserver {
public:
~Observer() override = default;
// Called when an observer should show or hide itself because the snooping
// status has changed. Argument is true if a snooper has now been detected.
virtual void OnSnoopingStatusChanged(bool snooper) = 0;
// Used to coordinate observers that might outlive the controller.
virtual void OnSnoopingProtectionControllerDestroyed() = 0;
};
SnoopingProtectionController();
SnoopingProtectionController(const SnoopingProtectionController&) = delete;
SnoopingProtectionController& operator=(const SnoopingProtectionController&) =
delete;
~SnoopingProtectionController() override;
static void RegisterProfilePrefs(PrefRegistrySimple* registry);
// SessionObserver:
void OnSessionStateChanged(session_manager::SessionState state) override;
void OnActiveUserPrefServiceChanged(PrefService* pref_service) override;
// HumanPresenceOrientationObserver:
void OnOrientationChanged(bool suitable_for_human_presence) override;
// HumanPresenceDBusClient::Observer:
void OnHpsSenseChanged(const hps::HpsResultProto&) override;
void OnHpsNotifyChanged(const hps::HpsResultProto&) override;
void OnRestart() override;
void OnShutdown() override;
// Add/remove views that are listening for snooper presence.
void AddObserver(Observer* observer);
void RemoveObserver(Observer* observer);
// The current snooper status.
bool SnooperPresent() const;
private:
// Used to track whether a signal should actually trigger a visibility change.
struct State {
// Whether a snooper is present, as last reported by the service.
bool present = false;
// Whether there is an active user session ongoing.
bool session_active = false;
// Whether the user has enabled the feature via preferences.
bool pref_enabled = false;
// Whether the daemon is available for communication.
bool service_available = false;
// Whether the daemon has been successfully configured.
bool service_configured = false;
// Whether the device is in physical orientation where our models are
// accurate.
bool orientation_suitable = false;
// Whether we are within the minimum time window for which to report a
// positive result.
bool within_pos_window = false;
};
// Updates snooper state as appropriate given the signal, session,
// preference and device orientation state. If changed, notifies observers.
void UpdateSnooperStatus(const State& new_state);
// Requests the start or stop of the snooping signal, so that the daemon need
// not be running snooping logic while the user has the feature disabled.
// Also updates the new state of service availability.
void ReconfigureService(State* new_state);
// Configures the daemon, polls its initial state and opts into its signals.
void StartServiceObservation(bool service_is_available);
// Performs the state update from the daemon response.
void UpdateServiceState(std::optional<hps::HpsResultProto> result);
// A callback to update visibility when the user enables or disables the
// feature.
void UpdatePrefState();
// A callback that fires once a positive signal has been emitted for the
// minimum allowed time. Sends out any delayed updates to observers.
void OnMinWindowExpired();
// Logs the amount of time a snooper was present / absent.
// An initial call just caches the current time (and doesn't log anything).
// Subsequent calls update the cache and log time elapsed if snooping status
// has changed.
// The cache can be cleared by resetting `last_presence_report_time_`.
void LogPresenceWindow(bool is_present);
// The state of all signals relevant to snooping status.
State state_;
// Used to enforce a minimum window of positive results.
base::RetainingOneShotTimer pos_window_timer_;
base::ScopedObservation<SessionController, SessionObserver>
session_observation_{this};
base::ScopedObservation<HumanPresenceOrientationController,
HumanPresenceOrientationController::Observer>
orientation_observation_{this};
base::ScopedObservation<HumanPresenceDBusClient,
HumanPresenceDBusClient::Observer>
human_presence_dbus_observation_{this};
// Used to notify ourselves of changes to the pref that enables / disables
// this feature.
std::unique_ptr<PrefChangeRegistrar> pref_change_registrar_;
// Clients listening for snooping status changes.
base::ObserverList<Observer> observers_;
// Controls popup hiding and our info notification.
const std::unique_ptr<SnoopingProtectionNotificationBlocker>
notification_blocker_;
// The minimum amount of time between emitting an initial positive signal and
// then a subsequent negative one.
const base::TimeDelta pos_window_;
// Last time the snooper became present or absent.
base::TimeTicks last_presence_report_time_;
// Must be last.
base::WeakPtrFactory<SnoopingProtectionController> weak_ptr_factory_{this};
};
} // namespace ash
#endif // ASH_SYSTEM_HUMAN_PRESENCE_SNOOPING_PROTECTION_CONTROLLER_H_