summaryrefslogtreecommitdiffstats
path: root/chrome/browser/extensions/install_verifier.h
blob: 522c508a0e5e4a6e971948c75fe628974f7274c7 (plain)
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
// Copyright 2013 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 CHROME_BROWSER_EXTENSIONS_INSTALL_VERIFIER_H_
#define CHROME_BROWSER_EXTENSIONS_INSTALL_VERIFIER_H_

#include <queue>
#include <set>
#include <string>

#include "base/basictypes.h"
#include "base/callback.h"
#include "base/memory/linked_ptr.h"
#include "base/memory/scoped_ptr.h"
#include "extensions/browser/management_policy.h"
#include "extensions/common/extension.h"

namespace net {
class URLRequestContextGetter;
}

namespace extensions {

class ExtensionPrefs;
class InstallSigner;
struct InstallSignature;

// This class implements verification that a set of extensions are either from
// the webstore or are whitelisted by enterprise policy.  The webstore
// verification process works by sending a request to a backend server to get a
// signature proving that a set of extensions are verified. This signature is
// written into the extension preferences and is checked for validity when
// being read back again.
//
// This class should be kept notified of runtime changes to the set of
// extensions installed from the webstore.
class InstallVerifier : public ManagementPolicy::Provider {
 public:
  InstallVerifier(ExtensionPrefs* prefs,
                  net::URLRequestContextGetter* context_getter);
  virtual ~InstallVerifier();

  // Returns whether |extension| is of a type that needs verification.
  static bool NeedsVerification(const Extension& extension);

  // Initializes this object for use, including reading preferences and
  // validating the stored signature.
  void Init();

  // Do we need to be bootstrapped? (i.e. do we have a signature already). If
  // this is true, then consumers of this class should use Add/AddMany to get
  // an initial one so that MustRemainDisabled can actually check against it.
  bool NeedsBootstrap();

  // A callback for indicating success/failure of adding new ids.
  typedef base::Callback<void(bool)> AddResultCallback;

  // Try adding a new |id| (or set of ids) to the list of verified ids. When
  // this process is finished |callback| will be run with success/failure of
  // the signature request (not necessarily whether the ids were verified).
  void Add(const std::string& id, const AddResultCallback& callback);
  void AddMany(const ExtensionIdSet& ids,
               const AddResultCallback& callback);

  // Call this to add a set of ids that will immediately be considered allowed,
  // and kick off an aysnchronous request to Add.
  void AddProvisional(const ExtensionIdSet& ids);

  // Removes an id or set of ids from the verified list.
  void Remove(const std::string& id);
  void RemoveMany(const ExtensionIdSet& ids);

  // ManagementPolicy::Provider interface.
  virtual std::string GetDebugPolicyProviderName() const OVERRIDE;
  virtual bool MustRemainDisabled(const Extension* extension,
                                  Extension::DisableReason* reason,
                                  base::string16* error) const OVERRIDE;

 private:
  // We keep a list of operations to the current set of extensions - either
  // additions or removals.
  enum OperationType {
    ADD,
    REMOVE
  };

  // This is an operation we want to apply to the current set of verified ids.
  struct PendingOperation {
    OperationType type;

    // This is the set of ids being either added or removed.
    ExtensionIdSet ids;

    AddResultCallback callback;

    explicit PendingOperation();
    ~PendingOperation();
  };

  // Removes any no-longer-installed ids, requesting a new signature if needed.
  void GarbageCollect();

  // Returns whether an extension id is allowed by policy.
  bool AllowedByEnterprisePolicy(const std::string& id) const;

  // Returns whether the given |id| is included in our verified signature.
  bool IsVerified(const std::string& id) const;

  // Begins the process of fetching a new signature, based on applying the
  // operation at the head of the queue to the current set of ids in
  // |signature_| (if any) and then sending a request to sign that.
  void BeginFetch();

  // Saves the current value of |signature_| to the prefs;
  void SaveToPrefs();

  // Called with the result of a signature request, or NULL on failure.
  void SignatureCallback(scoped_ptr<InstallSignature> signature);

  ExtensionPrefs* prefs_;
  net::URLRequestContextGetter* context_getter_;

  // This is the most up-to-date signature, read out of |prefs_| during
  // initialization and updated anytime we get new id's added.
  scoped_ptr<InstallSignature> signature_;

  // The current InstallSigner, if we have a signature request running.
  scoped_ptr<InstallSigner> signer_;

  // A queue of operations to apply to the current set of allowed ids.
  std::queue<linked_ptr<PendingOperation> > operation_queue_;

  // A set of ids that have been provisionally added, which we're willing to
  // consider allowed until we hear back from the server signature request.
  ExtensionIdSet provisional_;

  DISALLOW_COPY_AND_ASSIGN(InstallVerifier);
};

}  // namespace extensions

#endif  // CHROME_BROWSER_EXTENSIONS_INSTALL_VERIFIER_H_