Coverage Report

Created: 2018-09-25 14:53

/work/obj-fuzz/dist/include/mozilla/dom/CryptoKey.h
Line
Count
Source (jump to first uncovered line)
1
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
3
/* This Source Code Form is subject to the terms of the Mozilla Public
4
 * License, v. 2.0. If a copy of the MPL was not distributed with this
5
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
7
#ifndef mozilla_dom_CryptoKey_h
8
#define mozilla_dom_CryptoKey_h
9
10
#include "nsCycleCollectionParticipant.h"
11
#include "nsWrapperCache.h"
12
#include "nsIGlobalObject.h"
13
#include "pk11pub.h"
14
#include "keyhi.h"
15
#include "ScopedNSSTypes.h"
16
#include "mozilla/ErrorResult.h"
17
#include "mozilla/dom/CryptoBuffer.h"
18
#include "mozilla/dom/KeyAlgorithmProxy.h"
19
#include "js/StructuredClone.h"
20
#include "js/TypeDecls.h"
21
22
0
#define CRYPTOKEY_SC_VERSION 0x00000001
23
24
class nsIGlobalObject;
25
26
namespace mozilla {
27
namespace dom {
28
29
/*
30
31
The internal structure of keys is dictated by the need for cloning.
32
We store everything besides the key data itself in a 32-bit bitmask,
33
with the following structure (byte-aligned for simplicity, in order
34
from least to most significant):
35
36
Bits  Usage
37
0     Extractable
38
1-7   [reserved]
39
8-15  KeyType
40
16-23 KeyUsage
41
24-31 [reserved]
42
43
In the order of a hex value for a uint32_t
44
45
   3                   2                   1                   0
46
 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0
47
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
48
|~~~~~~~~~~~~~~~|     Usage     |     Type      |~~~~~~~~~~~~~|E|
49
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
50
51
Thus, internally, a key has the following fields:
52
* uint32_t - flags for extractable, usage, type
53
* KeyAlgorithm - the algorithm (which must serialize/deserialize itself)
54
* The actual keys (which the CryptoKey must serialize)
55
56
*/
57
58
struct JsonWebKey;
59
60
class CryptoKey final : public nsISupports
61
                      , public nsWrapperCache
62
{
63
public:
64
  NS_DECL_CYCLE_COLLECTING_ISUPPORTS
65
  NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_CLASS(CryptoKey)
66
67
  static const uint32_t CLEAR_EXTRACTABLE = 0xFFFFFFE;
68
  static const uint32_t EXTRACTABLE = 0x00000001;
69
70
  static const uint32_t CLEAR_TYPE = 0xFFFF00FF;
71
  static const uint32_t TYPE_MASK = 0x0000FF00;
72
  enum KeyType {
73
    UNKNOWN = 0x00000000,
74
    SECRET  = 0x00000100,
75
    PUBLIC  = 0x00000200,
76
    PRIVATE = 0x00000300
77
  };
78
79
  static const uint32_t CLEAR_USAGES = 0xFF00FFFF;
80
  static const uint32_t USAGES_MASK = 0x00FF0000;
81
  enum KeyUsage {
82
    ENCRYPT    = 0x00010000,
83
    DECRYPT    = 0x00020000,
84
    SIGN       = 0x00040000,
85
    VERIFY     = 0x00080000,
86
    DERIVEKEY  = 0x00100000,
87
    DERIVEBITS = 0x00200000,
88
    WRAPKEY    = 0x00400000,
89
    UNWRAPKEY  = 0x00800000
90
  };
91
92
  explicit CryptoKey(nsIGlobalObject* aWindow);
93
94
  nsIGlobalObject* GetParentObject() const
95
0
  {
96
0
    return mGlobal;
97
0
  }
98
99
  virtual JSObject* WrapObject(JSContext* aCx, JS::Handle<JSObject*> aGivenProto) override;
100
101
  // WebIDL methods
102
  void GetType(nsString& aRetVal) const;
103
  bool Extractable() const;
104
  void GetAlgorithm(JSContext* cx, JS::MutableHandle<JSObject*> aRetVal,
105
                    ErrorResult& aRv) const;
106
  void GetUsages(nsTArray<nsString>& aRetVal) const;
107
108
  // The below methods are not exposed to JS, but C++ can use
109
  // them to manipulate the object
110
111
  KeyAlgorithmProxy& Algorithm();
112
  const KeyAlgorithmProxy& Algorithm() const;
113
  KeyType GetKeyType() const;
114
  nsresult SetType(const nsString& aType);
115
  void SetType(KeyType aType);
116
  void SetExtractable(bool aExtractable);
117
  nsresult AddPublicKeyData(SECKEYPublicKey* point);
118
  void ClearUsages();
119
  nsresult AddUsage(const nsString& aUsage);
120
  nsresult AddUsageIntersecting(const nsString& aUsage, uint32_t aUsageMask);
121
  void AddUsage(KeyUsage aUsage);
122
  bool HasAnyUsage();
123
  bool HasUsage(KeyUsage aUsage);
124
  bool HasUsageOtherThan(uint32_t aUsages);
125
  static bool IsRecognizedUsage(const nsString& aUsage);
126
  static bool AllUsagesRecognized(const Sequence<nsString>& aUsages);
127
128
  nsresult SetSymKey(const CryptoBuffer& aSymKey);
129
  nsresult SetPrivateKey(SECKEYPrivateKey* aPrivateKey);
130
  nsresult SetPublicKey(SECKEYPublicKey* aPublicKey);
131
132
  // Accessors for the keys themselves
133
  const CryptoBuffer& GetSymKey() const;
134
  UniqueSECKEYPrivateKey GetPrivateKey() const;
135
  UniqueSECKEYPublicKey GetPublicKey() const;
136
137
  // Serialization and deserialization convenience methods
138
  // Note:
139
  // 1. The inputs aKeyData are non-const only because the NSS import
140
  //    functions lack the const modifier.  They should not be modified.
141
  // 2. All of the NSS key objects returned need to be freed by the caller.
142
  static UniqueSECKEYPrivateKey PrivateKeyFromPkcs8(CryptoBuffer& aKeyData);
143
  static nsresult PrivateKeyToPkcs8(SECKEYPrivateKey* aPrivKey,
144
                                    CryptoBuffer& aRetVal);
145
146
  static UniqueSECKEYPublicKey PublicKeyFromSpki(CryptoBuffer& aKeyData);
147
  static nsresult PublicKeyToSpki(SECKEYPublicKey* aPubKey,
148
                                  CryptoBuffer& aRetVal);
149
150
  static UniqueSECKEYPrivateKey PrivateKeyFromJwk(const JsonWebKey& aJwk);
151
  static nsresult PrivateKeyToJwk(SECKEYPrivateKey* aPrivKey,
152
                                  JsonWebKey& aRetVal);
153
154
  static UniqueSECKEYPublicKey PublicKeyFromJwk(const JsonWebKey& aKeyData);
155
  static nsresult PublicKeyToJwk(SECKEYPublicKey* aPubKey,
156
                                 JsonWebKey& aRetVal);
157
158
  static UniqueSECKEYPublicKey PublicDhKeyFromRaw(
159
    CryptoBuffer& aKeyData,
160
    const CryptoBuffer& aPrime,
161
    const CryptoBuffer& aGenerator);
162
  static nsresult PublicDhKeyToRaw(SECKEYPublicKey* aPubKey,
163
                                   CryptoBuffer& aRetVal);
164
165
  static UniqueSECKEYPublicKey PublicECKeyFromRaw(
166
    CryptoBuffer& aKeyData,
167
    const nsString& aNamedCurve);
168
  static nsresult PublicECKeyToRaw(SECKEYPublicKey* aPubKey,
169
                                   CryptoBuffer& aRetVal);
170
171
  static bool PublicKeyValid(SECKEYPublicKey* aPubKey);
172
173
  // Structured clone methods use these to clone keys
174
  bool WriteStructuredClone(JSStructuredCloneWriter* aWriter) const;
175
  bool ReadStructuredClone(JSStructuredCloneReader* aReader);
176
177
private:
178
0
  ~CryptoKey() {}
179
180
  RefPtr<nsIGlobalObject> mGlobal;
181
  uint32_t mAttributes; // see above
182
  KeyAlgorithmProxy mAlgorithm;
183
184
  // Only one key handle should be set, according to the KeyType
185
  CryptoBuffer mSymKey;
186
  UniqueSECKEYPrivateKey mPrivateKey;
187
  UniqueSECKEYPublicKey mPublicKey;
188
};
189
190
} // namespace dom
191
} // namespace mozilla
192
193
#endif // mozilla_dom_CryptoKey_h