Line data Source code
1 : /*
2 : *
3 : * Copyright (c) 2020 Project CHIP Authors
4 : * Copyright (c) 2016-2017 Nest Labs, Inc.
5 : *
6 : * Licensed under the Apache License, Version 2.0 (the "License");
7 : * you may not use this file except in compliance with the License.
8 : * You may obtain a copy of the License at
9 : *
10 : * http://www.apache.org/licenses/LICENSE-2.0
11 : *
12 : * Unless required by applicable law or agreed to in writing, software
13 : * distributed under the License is distributed on an "AS IS" BASIS,
14 : * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 : * See the License for the specific language governing permissions and
16 : * limitations under the License.
17 : */
18 :
19 : /**
20 : * @file
21 : * This file defines constant enumerations for all CHIP key types,
22 : * key flags, key ID fields, and helper API functions.
23 : *
24 : */
25 : #pragma once
26 :
27 : #include <stdint.h>
28 :
29 : namespace chip {
30 :
31 : /**
32 : * @class ChipKeyId
33 : *
34 : * @brief
35 : * The definition of the CHIP Key identifier. This class contains
36 : * key types, key flags, key ID fields definition, and API functions.
37 : *
38 : */
39 : class ChipKeyId
40 : {
41 : private:
42 : /**
43 : * @brief
44 : * Private CHIP key ID fields, flags, and types.
45 : */
46 : enum
47 : {
48 : kMask_KeyFlags = 0xF0000000, /**< CHIP key flag field mask. */
49 : kMask_KeyType = 0x0FFFF000, /**< CHIP key type field mask. */
50 : kMask_KeyNumber = 0x00000FFF, /**< CHIP key number field mask. */
51 : kMask_RootKeyNumber = 0x00000C00, /**< Application group root key number field mask. */
52 : kMask_EpochKeyNumber = 0x00000380, /**< Application group epoch key number field mask. */
53 : kMask_GroupLocalNumber = 0x0000007F, /**< Application group local number field mask. */
54 :
55 : kShift_RootKeyNumber = 10, /**< Application group root key number field shift. */
56 : kShift_EpochKeyNumber = 7, /**< Application group epoch key number field shift. */
57 : kShift_GroupLocalNumber = 0, /**< Application group local number field shift. */
58 :
59 : kFlag_UseCurrentEpochKey = 0x80000000, /**< Used to indicate that the key is of logical current type. */
60 :
61 : kTypeModifier_IncorporatesEpochKey = 0x00001000, /**< Used to indicate that the key incorporates group epoch key. */
62 : };
63 :
64 : public:
65 : /**
66 : * @brief
67 : * Public CHIP key ID fields, flags, and types.
68 : */
69 : enum
70 : {
71 : /**
72 : * @brief CHIP key types used for CHIP message encryption.
73 : *
74 : * @note 16 (out of 32) most significant bits of the message encryption key
75 : * type should be zero because only 16 least significant bits of the ID
76 : * are encoded in the CHIP message.
77 : * @{
78 : */
79 : kType_None = 0x00000000, /**< CHIP message is unencrypted. */
80 : kType_General = 0x00001000, /**< General key type. */
81 : kType_Session = 0x00002000, /**< Session key type. */
82 : kType_AppStaticKey = 0x00004000, /**< Application static key type. */
83 : /** Application rotating key type. */
84 : kType_AppRotatingKey = kType_AppStaticKey | kTypeModifier_IncorporatesEpochKey,
85 : /** @} */
86 :
87 : /**
88 : * @brief CHIP key types (other than CHIP message encryption types).
89 : *
90 : * @note 16 (out of 32) most significant bits of these types cannot be all zeros,
91 : * because these values are reserved for the CHIP message encryption keys only.
92 : * @{
93 : */
94 :
95 : /**
96 : * @brief Constituent group key types.
97 : * @{
98 : */
99 : /** Application group root key type. */
100 : kType_AppRootKey = 0x00010000,
101 : /** Application group epoch key type. */
102 : kType_AppEpochKey = 0x00020000 | kTypeModifier_IncorporatesEpochKey,
103 : /** Application group master key type. */
104 : kType_AppGroupMasterKey = 0x00030000,
105 : /** Application group intermediate key type. */
106 : kType_AppIntermediateKey = kType_AppRootKey | kTypeModifier_IncorporatesEpochKey,
107 : /** @} */
108 :
109 : /**
110 : * @brief CHIP global key IDs.
111 : * @{
112 : */
113 : /** Unspecified CHIP key ID. */
114 : kNone = kType_None | 0x0000,
115 : /** CHIP fabric secret ID. */
116 : kFabricSecret = kType_General | 0x0001,
117 : /** Fabric root key ID. */
118 : kFabricRootKey = kType_AppRootKey | (0 << kShift_RootKeyNumber),
119 : /** Client root key ID. */
120 : kClientRootKey = kType_AppRootKey | (1 << kShift_RootKeyNumber),
121 : /** Service root key ID. */
122 : kServiceRootKey = kType_AppRootKey | (2 << kShift_RootKeyNumber),
123 : /** @} */
124 :
125 : /**
126 : * @brief Maximum values for key ID subfields.
127 : * @{
128 : */
129 : kKeyNumber_Max = kMask_KeyNumber,
130 : kRootKeyNumber_Max = (kMask_RootKeyNumber >> kShift_RootKeyNumber),
131 : kEpochKeyNumber_Max = (kMask_EpochKeyNumber >> kShift_EpochKeyNumber),
132 : kGroupLocalNumber_Max = (kMask_GroupLocalNumber >> kShift_GroupLocalNumber),
133 : /** @} */
134 : };
135 :
136 : /**
137 : * Get CHIP key type of the specified key ID.
138 : *
139 : * @param[in] keyId CHIP key identifier.
140 : * @return type of the key ID.
141 : *
142 : */
143 0 : static uint32_t GetType(uint32_t keyId) { return keyId & kMask_KeyType; }
144 :
145 : /**
146 : * Determine whether the specified key ID is of a general type.
147 : *
148 : * @param[in] keyId CHIP key identifier.
149 : * @return true if the keyId has General type.
150 : *
151 : */
152 : static bool IsGeneralKey(uint32_t keyId) { return GetType(keyId) == kType_General; }
153 :
154 : /**
155 : * Determine whether the specified key ID is of a session type.
156 : *
157 : * @param[in] keyId CHIP key identifier.
158 : * @return true if the keyId of a session type.
159 : *
160 : */
161 : static bool IsSessionKey(uint32_t keyId) { return GetType(keyId) == kType_Session; }
162 :
163 : /**
164 : * Determine whether the specified key ID is of an application static type.
165 : *
166 : * @param[in] keyId CHIP key identifier.
167 : * @return true if the keyId of an application static type.
168 : *
169 : */
170 0 : static bool IsAppStaticKey(uint32_t keyId) { return GetType(keyId) == kType_AppStaticKey; }
171 :
172 : /**
173 : * Determine whether the specified key ID is of an application rotating type.
174 : *
175 : * @param[in] keyId CHIP key identifier.
176 : * @return true if the keyId of an application rotating type.
177 : *
178 : */
179 0 : static bool IsAppRotatingKey(uint32_t keyId) { return GetType(keyId) == kType_AppRotatingKey; }
180 :
181 : static bool IsAppGroupKey(uint32_t keyId);
182 :
183 : /**
184 : * Determine whether the specified key ID is of an application root key type.
185 : *
186 : * @param[in] keyId CHIP key identifier.
187 : * @return true if the keyId of an application root key type.
188 : *
189 : */
190 : static bool IsAppRootKey(uint32_t keyId) { return GetType(keyId) == kType_AppRootKey; }
191 :
192 : /**
193 : * Determine whether the specified key ID is of an application epoch key type.
194 : *
195 : * @param[in] keyId CHIP key identifier.
196 : * @return true if the keyId of an application epoch key type.
197 : *
198 : */
199 0 : static bool IsAppEpochKey(uint32_t keyId) { return GetType(keyId) == kType_AppEpochKey; }
200 :
201 : /**
202 : * Determine whether the specified key ID is of an application group master key type.
203 : *
204 : * @param[in] keyId CHIP key identifier.
205 : * @return true if the keyId of an application group master key type.
206 : *
207 : */
208 : static bool IsAppGroupMasterKey(uint32_t keyId) { return GetType(keyId) == kType_AppGroupMasterKey; }
209 :
210 : /**
211 : * Construct session key ID given session key number.
212 : *
213 : * @param[in] sessionKeyNumber Session key number.
214 : * @return session key ID.
215 : *
216 : */
217 : static uint16_t MakeSessionKeyId(uint16_t sessionKeyNumber)
218 : {
219 : static_assert(kType_Session <= UINT16_MAX, "We'll overflow");
220 : return static_cast<uint16_t>(kType_Session | (sessionKeyNumber & kMask_KeyNumber));
221 : }
222 :
223 : /**
224 : * Construct general key ID given general key number.
225 : *
226 : * @param[in] generalKeyNumber General key number.
227 : * @return general key ID.
228 : *
229 : */
230 : static uint16_t MakeGeneralKeyId(uint16_t generalKeyNumber)
231 : {
232 : static_assert(kType_General <= UINT16_MAX, "We'll overflow");
233 : return static_cast<uint16_t>(kType_General | (generalKeyNumber & kMask_KeyNumber));
234 : }
235 :
236 : /**
237 : * Get application group root key ID that was used to derive specified application key.
238 : *
239 : * @param[in] keyId CHIP application group key identifier.
240 : * @return root key ID.
241 : *
242 : */
243 0 : static uint32_t GetRootKeyId(uint32_t keyId) { return kType_AppRootKey | (keyId & kMask_RootKeyNumber); }
244 :
245 : /**
246 : * Get application group epoch key ID that was used to derive specified application key.
247 : *
248 : * @param[in] keyId CHIP application group key identifier.
249 : * @return epoch key ID.
250 : *
251 : */
252 : static uint32_t GetEpochKeyId(uint32_t keyId) { return kType_AppEpochKey | (keyId & kMask_EpochKeyNumber); }
253 :
254 : /**
255 : * Get application group master key ID that was used to derive specified application key.
256 : *
257 : * @param[in] keyId CHIP application group key identifier.
258 : * @return application group master key ID.
259 : *
260 : */
261 0 : static uint32_t GetAppGroupMasterKeyId(uint32_t keyId) { return kType_AppGroupMasterKey | (keyId & kMask_GroupLocalNumber); }
262 :
263 : /**
264 : * Get application group root key number that was used to derive specified application key.
265 : *
266 : * @param[in] keyId CHIP application group key identifier.
267 : * @return root key number.
268 : *
269 : */
270 : static uint8_t GetRootKeyNumber(uint32_t keyId)
271 : {
272 : return static_cast<uint8_t>((keyId & kMask_RootKeyNumber) >> kShift_RootKeyNumber);
273 : }
274 :
275 : /**
276 : * Get application group epoch key number that was used to derive specified application key.
277 : *
278 : * @param[in] keyId CHIP application group key identifier.
279 : * @return epoch key number.
280 : *
281 : */
282 : static uint8_t GetEpochKeyNumber(uint32_t keyId)
283 : {
284 : return static_cast<uint8_t>((keyId & kMask_EpochKeyNumber) >> kShift_EpochKeyNumber);
285 : }
286 :
287 : /**
288 : * Get application group local number that was used to derive specified application key.
289 : *
290 : * @param[in] keyId CHIP application group key identifier.
291 : * @return application group local number.
292 : *
293 : */
294 : static uint8_t GetAppGroupLocalNumber(uint32_t keyId)
295 : {
296 : return static_cast<uint8_t>((keyId & kMask_GroupLocalNumber) >> kShift_GroupLocalNumber);
297 : }
298 :
299 : /**
300 : * Construct application group root key ID given root key number.
301 : *
302 : * @param[in] rootKeyNumber Root key number.
303 : * @return root key ID.
304 : *
305 : */
306 : static uint32_t MakeRootKeyId(uint8_t rootKeyNumber)
307 : {
308 : return static_cast<uint32_t>(kType_AppRootKey | (rootKeyNumber << kShift_RootKeyNumber));
309 : }
310 :
311 : /**
312 : * Construct application group root key ID given epoch key number.
313 : *
314 : * @param[in] epochKeyNumber Epoch key number.
315 : * @return epoch key ID.
316 : *
317 : */
318 : static uint32_t MakeEpochKeyId(uint8_t epochKeyNumber)
319 : {
320 : return static_cast<uint32_t>(kType_AppEpochKey | (epochKeyNumber << kShift_EpochKeyNumber));
321 : }
322 :
323 : /**
324 : * Construct application group master key ID given application group local number.
325 : *
326 : * @param[in] appGroupLocalNumber Application group local number.
327 : * @return application group master key ID.
328 : *
329 : */
330 : static uint32_t MakeAppGroupMasterKeyId(uint8_t appGroupLocalNumber)
331 : {
332 : return static_cast<uint32_t>(kType_AppGroupMasterKey | (appGroupLocalNumber << kShift_GroupLocalNumber));
333 : }
334 :
335 : /**
336 : * Convert application group key ID to application current key ID.
337 : *
338 : * @param[in] keyId Application key ID.
339 : * @return application current key ID.
340 : *
341 : */
342 : static uint32_t ConvertToCurrentAppKeyId(uint32_t keyId) { return (keyId & ~kMask_EpochKeyNumber) | kFlag_UseCurrentEpochKey; }
343 :
344 : /**
345 : * Determine whether the specified application group key ID incorporates epoch key.
346 : *
347 : * @param[in] keyId CHIP application group key identifier.
348 : * @return true if the keyId incorporates epoch key.
349 : *
350 : */
351 0 : static bool IncorporatesEpochKey(uint32_t keyId) { return (keyId & kTypeModifier_IncorporatesEpochKey) != 0; }
352 :
353 : static bool UsesCurrentEpochKey(uint32_t keyId);
354 : static bool IncorporatesRootKey(uint32_t keyId);
355 : static bool IncorporatesAppGroupMasterKey(uint32_t keyId);
356 :
357 : static uint32_t MakeAppKeyId(uint32_t keyType, uint32_t rootKeyId, uint32_t epochKeyId, uint32_t appGroupMasterKeyId,
358 : bool useCurrentEpochKey);
359 : static uint32_t MakeAppIntermediateKeyId(uint32_t rootKeyId, uint32_t epochKeyId, bool useCurrentEpochKey);
360 : static uint32_t MakeAppRotatingKeyId(uint32_t rootKeyId, uint32_t epochKeyId, uint32_t appGroupMasterKeyId,
361 : bool useCurrentEpochKey);
362 : static uint32_t MakeAppStaticKeyId(uint32_t rootKeyId, uint32_t appGroupMasterKeyId);
363 : static uint32_t ConvertToStaticAppKeyId(uint32_t keyId);
364 : static uint32_t UpdateEpochKeyId(uint32_t keyId, uint32_t epochKeyId);
365 :
366 : static bool IsValidKeyId(uint32_t keyId);
367 : static bool IsMessageSessionId(uint32_t keyId, bool allowLogicalKeys = true);
368 : static bool IsSameKeyOrGroup(uint32_t keyId1, uint32_t keyId2);
369 : static const char * DescribeKey(uint32_t keyId);
370 : };
371 :
372 : } // namespace chip
|