1 /*
2    Copyright (c) 2021 Fraunhofer AISEC. See the COPYRIGHT
3    file at the top-level directory of this distribution.
4 
5    Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
6    http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
7    <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
8    option. This file may not be copied, modified, or distributed
9    except according to those terms.
10 */
11 
12 #include <string.h>
13 
14 #include "oscore/aad.h"
15 #include "oscore/oscore_hkdf_info.h"
16 
17 #include "common/oscore_edhoc_error.h"
18 
19 #include "cbor/oscore_info.h"
20 
21 /*
22 HKDF = composition of HKDF-Extract and HKDF-Expand (RFC5869)
23 output = HKDF(salt, IKM, info, L
24 * salt = Master Salt
25 * IKM = Master Secret
26 * info = CBOR-array [
27      id: bstr,
28      alg_aead: int / tstr,
29      type: tstr,
30      L: uint,
31   ]
32      + id: SenderID / RecipientID for keys; empty string for CommonIV
33      + alg_aead: AEAD Algorithm
34      + type: "Key" / "IV", ascii string without nul-terminator
35      + L: size of key/iv for AEAD alg
36          - in bytes
37 * https://www.iana.org/assignments/cose/cose.xhtml
38 */
39 
oscore_create_hkdf_info(struct byte_array * id,struct byte_array * id_context,enum AEAD_algorithm aead_alg,enum derive_type type,struct byte_array * out)40 enum err oscore_create_hkdf_info(struct byte_array *id,
41 				 struct byte_array *id_context,
42 				 enum AEAD_algorithm aead_alg,
43 				 enum derive_type type, struct byte_array *out)
44 {
45 	struct oscore_info info_struct;
46 
47 	char type_enc[10];
48 	uint8_t len = 0;
49 	switch (type) {
50 	case KEY:
51 		strncpy(type_enc, "Key", 10);
52 		len = 16;
53 		break;
54 	case IV:
55 		strncpy(type_enc, "IV", 10);
56 		len = 13;
57 		break;
58 	}
59 
60 	info_struct.oscore_info_id.value = id->ptr;
61 	info_struct.oscore_info_id.len = id->len;
62 
63 	if (id_context->len == 0) {
64 		info_struct.oscore_info_id_context_choice =
65 			oscore_info_id_context_nil_c;
66 	} else {
67 		info_struct.oscore_info_id_context_choice =
68 			oscore_info_id_context_bstr_c;
69 		info_struct.oscore_info_id_context_bstr.value =
70 			id_context->ptr;
71 		info_struct.oscore_info_id_context_bstr.len = id_context->len;
72 	}
73 	info_struct.oscore_info_alg_aead_choice = oscore_info_alg_aead_int_c;
74 	info_struct.oscore_info_alg_aead_int = (int32_t)aead_alg;
75 
76 	info_struct.oscore_info_type.value = (uint8_t *)type_enc;
77 	info_struct.oscore_info_type.len = (uint32_t)strlen(type_enc);
78 	info_struct.oscore_info_L = len;
79 
80 	size_t payload_len_out;
81 
82 	TRY_EXPECT(cbor_encode_oscore_info(out->ptr, out->len, &info_struct,
83 					   &payload_len_out),
84 		   0);
85 
86 	out->len = (uint32_t)payload_len_out;
87 	return ok;
88 }
89