xref: /aosp_15_r20/external/cronet/components/metrics/cloned_install_detector.h (revision 6777b5387eb2ff775bb5750e3f5d96f37fb7352b)
1 // Copyright 2014 The Chromium Authors
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 COMPONENTS_METRICS_CLONED_INSTALL_DETECTOR_H_
6 #define COMPONENTS_METRICS_CLONED_INSTALL_DETECTOR_H_
7 
8 #include "base/callback_list.h"
9 #include "base/functional/callback_forward.h"
10 #include "base/gtest_prod_util.h"
11 #include "base/memory/weak_ptr.h"
12 
13 class PrefRegistrySimple;
14 class PrefService;
15 
16 namespace metrics {
17 
18 // A struct that holds cloned install related fields in prefs that need to be
19 // reported in the system_profile.
20 struct ClonedInstallInfo {
21   int64_t last_reset_timestamp;
22   int64_t first_reset_timestamp;
23   int reset_count;
24 };
25 
26 // A class for detecting if an install is cloned. It does this by detecting
27 // when the hardware running Chrome changes.
28 class ClonedInstallDetector {
29  public:
30   ClonedInstallDetector();
31 
32   ClonedInstallDetector(const ClonedInstallDetector&) = delete;
33   ClonedInstallDetector& operator=(const ClonedInstallDetector&) = delete;
34 
35   virtual ~ClonedInstallDetector();
36 
37   // Posts a task to |task_runner| to generate a machine ID and store it to a
38   // local state pref. If the newly generated ID is different than the
39   // previously stored one, then the install is considered cloned. The ID is a
40   // 24-bit value based off of machine characteristics. This value should never
41   // be sent over the network.
42   void CheckForClonedInstall(PrefService* local_state);
43 
44   static void RegisterPrefs(PrefRegistrySimple* registry);
45 
46   // Reads cloned install info fields from |local_state| and returns them in
47   // a ClonedInstallInfo.
48   static ClonedInstallInfo ReadClonedInstallInfo(PrefService* local_state);
49 
50   // Clears cloned install info fields from |local_state|.
51   static void ClearClonedInstallInfo(PrefService* local_state);
52 
53   // Updates cloned install info fields in |local_state| on reset.
54   static void RecordClonedInstallInfo(PrefService* local_state);
55 
56   // Returns true for the whole session if we detected a cloned install during
57   // the construction of a client id.
58   bool ShouldResetClientIds(PrefService* local_state);
59 
60   // Returns true for the whole session if we detect a cloned install this
61   // session.
62   bool ClonedInstallDetectedInCurrentSession() const;
63 
64   // Adds a callback that is run if this install is detected as cloned during
65   // this session. If this is called after the detection had already occurred,
66   // the callback is run immediately.
67   base::CallbackListSubscription AddOnClonedInstallDetectedCallback(
68       base::OnceClosure callback);
69 
70   // Wrapper around SaveMachineId(). Used for testing in UKM (the tests cannot
71   // be declared as friends since they live in a different namespace).
72   void SaveMachineIdForTesting(PrefService* local_state,
73                                const std::string& raw_id);
74 
75  private:
76   FRIEND_TEST_ALL_PREFIXES(ClonedInstallDetectorTest, SaveId);
77   FRIEND_TEST_ALL_PREFIXES(ClonedInstallDetectorTest, DetectClone);
78   FRIEND_TEST_ALL_PREFIXES(ClonedInstallDetectorTest, ShouldResetClientIds);
79   FRIEND_TEST_ALL_PREFIXES(ClonedInstallDetectorTest,
80                            ClonedInstallDetectedInCurrentSession);
81   FRIEND_TEST_ALL_PREFIXES(ClonedInstallDetectorTest,
82                            ClonedInstallDetectedCallback);
83   FRIEND_TEST_ALL_PREFIXES(MetricsStateManagerTest, CheckProviderResetIds);
84   FRIEND_TEST_ALL_PREFIXES(MetricsServiceTestWithFeatures,
85                            PurgeLogsOnClonedInstallDetected);
86 
87   // Converts raw_id into a 24-bit hash and stores the hash in |local_state|.
88   // |raw_id| is not a const ref because it's passed from a cross-thread post
89   // task.
90   void SaveMachineId(PrefService* local_state, const std::string& raw_id);
91 
92   // Indicates that we detected a cloned install during the current session.
93   bool detected_this_session_ = false;
94 
95   // Indicates that we detected a cloned install during the construction of a
96   // client id and should reset client ids as a result.
97   bool should_reset_client_ids_ = false;
98 
99   base::OnceClosureList callback_list_;
100 
101   base::WeakPtrFactory<ClonedInstallDetector> weak_ptr_factory_{this};
102 };
103 
104 }  // namespace metrics
105 
106 #endif  // COMPONENTS_METRICS_CLONED_INSTALL_DETECTOR_H_
107