File: variations_seed_store.h

package info (click to toggle)
chromium-browser 57.0.2987.98-1~deb8u1
  • links: PTS, VCS
  • area: main
  • in suites: jessie
  • size: 2,637,852 kB
  • ctags: 2,544,394
  • sloc: cpp: 12,815,961; ansic: 3,676,222; python: 1,147,112; asm: 526,608; java: 523,212; xml: 286,794; perl: 92,654; sh: 86,408; objc: 73,271; makefile: 27,698; cs: 18,487; yacc: 13,031; tcl: 12,957; pascal: 4,875; ml: 4,716; lex: 3,904; sql: 3,862; ruby: 1,982; lisp: 1,508; php: 1,368; exp: 404; awk: 325; csh: 117; jsp: 39; sed: 37
file content (150 lines) | stat: -rw-r--r-- 5,913 bytes parent folder | download
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
// Copyright 2014 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#ifndef COMPONENTS_VARIATIONS_VARIATIONS_SEED_STORE_H_
#define COMPONENTS_VARIATIONS_VARIATIONS_SEED_STORE_H_

#include <string>

#include "base/compiler_specific.h"
#include "base/gtest_prod_util.h"
#include "base/macros.h"
#include "base/time/time.h"
#include "build/build_config.h"

class PrefService;
class PrefRegistrySimple;

namespace variations {
class VariationsSeed;
}

namespace variations {

// VariationsSeedStore is a helper class for reading and writing the variations
// seed from Local State.
class VariationsSeedStore {
 public:
  explicit VariationsSeedStore(PrefService* local_state);
  virtual ~VariationsSeedStore();

  // Loads the variations seed data from local state into |seed|. If there is a
  // problem with loading, the pref value is cleared and false is returned. If
  // successful, |seed| will contain the loaded data and true is returned.
  bool LoadSeed(variations::VariationsSeed* seed);

  // Stores the given seed |data| (serialized protobuf) to local state, along
  // with a base64-encoded digital signature for seed and the date when it was
  // fetched. If |is_gzip_compressed| is true, treats |data| as being gzip
  // compressed and decompresses it before any other processing.
  // If |is_delta_compressed| is true, treats |data| as being delta
  // compressed and attempts to decode it first using the store's seed data.
  // The actual seed data will be base64 encoded for storage. If the string
  // is invalid, the existing prefs are untouched and false is returned.
  // Additionally, stores the |country_code| that was received with the seed in
  // a separate pref. On success and if |parsed_seed| is not NULL, |parsed_seed|
  // will be filled with the de-serialized decoded protobuf.
  bool StoreSeedData(const std::string& data,
                     const std::string& base64_seed_signature,
                     const std::string& country_code,
                     const base::Time& date_fetched,
                     bool is_delta_compressed,
                     bool is_gzip_compressed,
                     variations::VariationsSeed* parsed_seed);

  // Updates |kVariationsSeedDate| and logs when previous date was from a
  // different day.
  void UpdateSeedDateAndLogDayChange(const base::Time& server_date_fetched);

  // Reports to UMA that the seed format specified by the server is unsupported.
  void ReportUnsupportedSeedFormatError();

  // Returns the serial number of the last loaded or stored seed.
  const std::string& variations_serial_number() const {
    return variations_serial_number_;
  }

  // Returns whether the last loaded or stored seed has the country field set.
  bool seed_has_country_code() const {
    return seed_has_country_code_;
  }

  // Returns the invalid signature in base64 format, or an empty string if the
  // signature was valid, missing, or if signature verification is disabled.
  std::string GetInvalidSignature() const;

  // Registers Local State prefs used by this class.
  static void RegisterPrefs(PrefRegistrySimple* registry);

 protected:
  // Note: UMA histogram enum - don't re-order or remove entries.
  enum VerifySignatureResult {
    VARIATIONS_SEED_SIGNATURE_MISSING,
    VARIATIONS_SEED_SIGNATURE_DECODE_FAILED,
    VARIATIONS_SEED_SIGNATURE_INVALID_SIGNATURE,
    VARIATIONS_SEED_SIGNATURE_INVALID_SEED,
    VARIATIONS_SEED_SIGNATURE_VALID,
    VARIATIONS_SEED_SIGNATURE_ENUM_SIZE,
  };

  // Verifies a variations seed (the serialized proto bytes) with the specified
  // base-64 encoded signature that was received from the server and returns the
  // result. The signature is assumed to be an "ECDSA with SHA-256" signature
  // (see kECDSAWithSHA256AlgorithmID in the .cc file). Returns the result of
  // signature verification or VARIATIONS_SEED_SIGNATURE_ENUM_SIZE if signature
  // verification is not enabled.
  virtual VariationsSeedStore::VerifySignatureResult VerifySeedSignature(
      const std::string& seed_bytes,
      const std::string& base64_seed_signature);

 private:
  FRIEND_TEST_ALL_PREFIXES(VariationsSeedStoreTest, VerifySeedSignature);
  FRIEND_TEST_ALL_PREFIXES(VariationsSeedStoreTest, ApplyDeltaPatch);

  // Clears all prefs related to variations seed storage.
  void ClearPrefs();

#if defined(OS_ANDROID)
  // Imports the variations seed data from Java side during the first
  // Chrome for Android run.
  void ImportFirstRunJavaSeed();
#endif  // OS_ANDROID

  // Reads the variations seed data from prefs; returns true on success.
  bool ReadSeedData(std::string* seed_data);

  // Internal version of |StoreSeedData()| that assumes |seed_data| is not delta
  // compressed.
  bool StoreSeedDataNoDelta(
      const std::string& seed_data,
      const std::string& base64_seed_signature,
      const std::string& country_code,
      const base::Time& date_fetched,
      variations::VariationsSeed* parsed_seed);

  // Applies a delta-compressed |patch| to |existing_data|, producing the result
  // in |output|. Returns whether the operation was successful.
  static bool ApplyDeltaPatch(const std::string& existing_data,
                              const std::string& patch,
                              std::string* output);

  // The pref service used to persist the variations seed.
  PrefService* local_state_;

  // Cached serial number from the most recently fetched variations seed.
  std::string variations_serial_number_;

  // Whether the most recently fetched variations seed has the country code
  // field set.
  bool seed_has_country_code_;

  // Keeps track of an invalid signature.
  std::string invalid_base64_signature_;

  DISALLOW_COPY_AND_ASSIGN(VariationsSeedStore);
};

}  // namespace variations

#endif  // COMPONENTS_VARIATIONS_VARIATIONS_SEED_STORE_H_