Skip to content

Commit e375252

Browse files
ahasztagnvlsianpu
authored andcommitted
boot: Enable Encryption with PSA + ECDSA
This configuration was not supported until now. Signed-off-by: Artur Hadasz <artur.hadasz@nordicsemi.no>
1 parent 21ed226 commit e375252

File tree

3 files changed

+130
-40
lines changed

3 files changed

+130
-40
lines changed

boot/bootutil/src/encrypted.c

Lines changed: 33 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -22,11 +22,11 @@
2222
#include "bootutil/crypto/aes_kw.h"
2323
#endif
2424

25+
#if !defined(MCUBOOT_USE_PSA_CRYPTO)
2526
#if defined(MCUBOOT_ENCRYPT_EC256)
2627
#include "bootutil/crypto/ecdh_p256.h"
2728
#endif
2829

29-
#if !defined(MCUBOOT_USE_PSA_CRYPTO)
3030
#if defined(MCUBOOT_ENCRYPT_X25519)
3131
#include "bootutil/crypto/ecdh_x25519.h"
3232
#endif
@@ -50,7 +50,7 @@ BOOT_LOG_MODULE_DECLARE(mcuboot);
5050
#include "bootutil_priv.h"
5151

5252
/* NOUP Fixme: */
53-
#if !defined(CONFIG_BOOT_ED25519_PSA)
53+
#if !defined(CONFIG_BOOT_ED25519_PSA) && !defined(CONFIG_BOOT_ECDSA_PSA)
5454
#if defined(MCUBOOT_ENCRYPT_EC256) || defined(MCUBOOT_ENCRYPT_X25519)
5555
#if defined(_compare)
5656
static inline int bootutil_constant_time_compare(const uint8_t *a, const uint8_t *b, size_t size)
@@ -105,65 +105,64 @@ static const uint8_t ec_secp256r1_oid[] = MBEDTLS_OID_EC_GRP_SECP256R1;
105105
* curve keypair. See RFC5208 and RFC5915.
106106
*/
107107
static int
108-
parse_ec256_enckey(uint8_t **p, uint8_t *end, uint8_t *private_key)
108+
parse_priv_enckey(uint8_t **p, uint8_t *end, uint8_t *private_key)
109109
{
110-
int rc;
111110
size_t len;
112111
int version;
113112
mbedtls_asn1_buf alg;
114113
mbedtls_asn1_buf param;
115114

116-
if ((rc = mbedtls_asn1_get_tag(p, end, &len,
117-
MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE)) != 0) {
115+
if (mbedtls_asn1_get_tag(p, end, &len,
116+
MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE) != 0) {
118117
return -1;
119118
}
120119

121120
if (*p + len != end) {
122-
return -2;
121+
return -1;
123122
}
124123

125124
version = 0;
126125
if (mbedtls_asn1_get_int(p, end, &version) || version != 0) {
127-
return -3;
126+
return -1;
128127
}
129128

130-
if ((rc = mbedtls_asn1_get_alg(p, end, &alg, &param)) != 0) {
131-
return -5;
129+
if (mbedtls_asn1_get_alg(p, end, &alg, &param) != 0) {
130+
return -1;
132131
}
133132

134133
if (alg.ASN1_CONTEXT_MEMBER(len) != sizeof(ec_pubkey_oid) - 1 ||
135134
memcmp(alg.ASN1_CONTEXT_MEMBER(p), ec_pubkey_oid, sizeof(ec_pubkey_oid) - 1)) {
136-
return -6;
135+
return -1;
137136
}
138137
if (param.ASN1_CONTEXT_MEMBER(len) != sizeof(ec_secp256r1_oid) - 1 ||
139138
memcmp(param.ASN1_CONTEXT_MEMBER(p), ec_secp256r1_oid, sizeof(ec_secp256r1_oid) - 1)) {
140-
return -7;
139+
return -1;
141140
}
142141

143-
if ((rc = mbedtls_asn1_get_tag(p, end, &len, MBEDTLS_ASN1_OCTET_STRING)) != 0) {
144-
return -8;
142+
if (mbedtls_asn1_get_tag(p, end, &len, MBEDTLS_ASN1_OCTET_STRING) != 0) {
143+
return -1;
145144
}
146145

147146
/* RFC5915 - ECPrivateKey */
148147

149-
if ((rc = mbedtls_asn1_get_tag(p, end, &len,
150-
MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE)) != 0) {
151-
return -9;
148+
if (mbedtls_asn1_get_tag(p, end, &len,
149+
MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE) != 0) {
150+
return -1;
152151
}
153152

154153
version = 0;
155154
if (mbedtls_asn1_get_int(p, end, &version) || version != 1) {
156-
return -10;
155+
return -1;
157156
}
158157

159158
/* privateKey */
160159

161-
if ((rc = mbedtls_asn1_get_tag(p, end, &len, MBEDTLS_ASN1_OCTET_STRING)) != 0) {
162-
return -11;
160+
if (mbedtls_asn1_get_tag(p, end, &len, MBEDTLS_ASN1_OCTET_STRING) != 0) {
161+
return -1;
163162
}
164163

165164
if (len != NUM_ECC_BYTES) {
166-
return -12;
165+
return -1;
167166
}
168167

169168
memcpy(private_key, *p, len);
@@ -180,7 +179,7 @@ static const uint8_t ec_pubkey_oid[] = MBEDTLS_OID_ISO_IDENTIFIED_ORG \
180179
MBEDTLS_OID_ORG_GOV X25519_OID;
181180

182181
static int
183-
parse_x25519_enckey(uint8_t **p, uint8_t *end, uint8_t *private_key)
182+
parse_priv_enckey(uint8_t **p, uint8_t *end, uint8_t *private_key)
184183
{
185184
size_t len;
186185
int version;
@@ -193,33 +192,33 @@ parse_x25519_enckey(uint8_t **p, uint8_t *end, uint8_t *private_key)
193192
}
194193

195194
if (*p + len != end) {
196-
return -2;
195+
return -1;
197196
}
198197

199198
version = 0;
200199
if (mbedtls_asn1_get_int(p, end, &version) || version != 0) {
201-
return -3;
200+
return -1;
202201
}
203202

204203
if (mbedtls_asn1_get_alg(p, end, &alg, &param) != 0) {
205-
return -4;
204+
return -1;
206205
}
207206

208207
if (alg.ASN1_CONTEXT_MEMBER(len) != sizeof(ec_pubkey_oid) - 1 ||
209208
memcmp(alg.ASN1_CONTEXT_MEMBER(p), ec_pubkey_oid, sizeof(ec_pubkey_oid) - 1)) {
210-
return -5;
209+
return -1;
211210
}
212211

213212
if (mbedtls_asn1_get_tag(p, end, &len, MBEDTLS_ASN1_OCTET_STRING) != 0) {
214-
return -6;
213+
return -1;
215214
}
216215

217216
if (mbedtls_asn1_get_tag(p, end, &len, MBEDTLS_ASN1_OCTET_STRING) != 0) {
218-
return -7;
217+
return -1;
219218
}
220219

221220
if (len != EC_PRIVK_LEN) {
222-
return -8;
221+
return -1;
223222
}
224223

225224
memcpy(private_key, *p, EC_PRIVK_LEN);
@@ -444,8 +443,9 @@ boot_decrypt_key(const uint8_t *buf, uint8_t *enckey)
444443
* Load the stored EC256 decryption private key
445444
*/
446445

447-
rc = parse_ec256_enckey(&cp, cpend, private_key);
446+
rc = parse_priv_enckey(&cp, cpend, private_key);
448447
if (rc) {
448+
BOOT_LOG_ERR("Failed to parse ASN1 private key");
449449
return rc;
450450
}
451451

@@ -467,8 +467,9 @@ boot_decrypt_key(const uint8_t *buf, uint8_t *enckey)
467467
* Load the stored X25519 decryption private key
468468
*/
469469

470-
rc = parse_x25519_enckey(&cp, cpend, private_key);
470+
rc = parse_priv_enckey(&cp, cpend, private_key);
471471
if (rc) {
472+
BOOT_LOG_ERR("Failed to parse ASN1 private key");
472473
return rc;
473474
}
474475

@@ -562,7 +563,7 @@ boot_decrypt_key(const uint8_t *buf, uint8_t *enckey)
562563

563564
return rc;
564565
}
565-
#endif /* CONFIG_BOOT_ED25519_PSA */
566+
#endif /* CONFIG_BOOT_ED25519_PSA && CONFIG_BOOT_ECDSA_PSA */
566567

567568
/*
568569
* Load encryption key.

boot/bootutil/src/encrypted_psa.c

Lines changed: 92 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -33,9 +33,18 @@ BOOT_LOG_MODULE_DECLARE(mcuboot_psa_enc);
3333
#define PSA_HMAC_HKDF_SHA PSA_ALG_SHA_256
3434
#endif
3535

36+
#if defined(MCUBOOT_ENCRYPT_EC256)
37+
#define NUM_ECC_BYTES (256 / 8)
38+
static const uint8_t ec_pubkey_oid[] = MBEDTLS_OID_EC_ALG_UNRESTRICTED;
39+
static const uint8_t ec_secp256r1_oid[] = MBEDTLS_OID_EC_GRP_SECP256R1;
40+
#define ECC_FAMILY PSA_ECC_FAMILY_SECP_R1
41+
#endif /* defined(MCUBOOT_ENCRYPT_EC256) */
42+
#if defined(MCUBOOT_ENCRYPT_X25519)
3643
#define X25519_OID "\x6e"
3744
static const uint8_t ec_pubkey_oid[] = MBEDTLS_OID_ISO_IDENTIFIED_ORG \
3845
MBEDTLS_OID_ORG_GOV X25519_OID;
46+
#define ECC_FAMILY PSA_ECC_FAMILY_MONTGOMERY
47+
#endif /* defined(MCUBOOT_ENCRYPT_X25519) */
3948

4049
/* Partitioning of HKDF derived material, from the exchange derived key */
4150
/* AES key encryption key */
@@ -51,9 +60,86 @@ static const uint8_t ec_pubkey_oid[] = MBEDTLS_OID_ISO_IDENTIFIED_ORG \
5160
/* Total size */
5261
#define HKDF_SIZE (HKDF_AES_KEY_SIZE + HKDF_MAC_FEED_SIZE)
5362

63+
#if defined(MCUBOOT_ENCRYPT_EC256)
64+
/* Fixme: This duplicates code from encrypted.c and depends on mbedtls */
65+
66+
/*
67+
* Parses the output of `imgtool keygen`, which produces a PKCS#8 elliptic
68+
* curve keypair. See RFC5208 and RFC5915.
69+
*/
70+
static int
71+
parse_priv_enckey(uint8_t **p, uint8_t *end, uint8_t *private_key)
72+
{
73+
size_t len;
74+
int version;
75+
mbedtls_asn1_buf alg;
76+
mbedtls_asn1_buf param;
77+
78+
if (mbedtls_asn1_get_tag(p, end, &len,
79+
MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE) != 0) {
80+
return -1;
81+
}
82+
83+
if (*p + len != end) {
84+
return -1;
85+
}
86+
87+
version = 0;
88+
if (mbedtls_asn1_get_int(p, end, &version) || version != 0) {
89+
return -1;
90+
}
91+
92+
if (mbedtls_asn1_get_alg(p, end, &alg, &param) != 0) {
93+
return -1;
94+
}
95+
96+
if (alg.ASN1_CONTEXT_MEMBER(len) != sizeof(ec_pubkey_oid) - 1 ||
97+
memcmp(alg.ASN1_CONTEXT_MEMBER(p), ec_pubkey_oid, sizeof(ec_pubkey_oid) - 1)) {
98+
return -1;
99+
}
100+
if (param.ASN1_CONTEXT_MEMBER(len) != sizeof(ec_secp256r1_oid) - 1 ||
101+
memcmp(param.ASN1_CONTEXT_MEMBER(p), ec_secp256r1_oid, sizeof(ec_secp256r1_oid) - 1)) {
102+
return -1;
103+
}
104+
105+
if (mbedtls_asn1_get_tag(p, end, &len, MBEDTLS_ASN1_OCTET_STRING) != 0) {
106+
return -1;
107+
}
108+
109+
/* RFC5915 - ECPrivateKey */
110+
111+
if (mbedtls_asn1_get_tag(p, end, &len,
112+
MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE) != 0) {
113+
return -1;
114+
}
115+
116+
version = 0;
117+
if (mbedtls_asn1_get_int(p, end, &version) || version != 1) {
118+
return -1;
119+
}
120+
121+
/* privateKey */
122+
123+
if (mbedtls_asn1_get_tag(p, end, &len, MBEDTLS_ASN1_OCTET_STRING) != 0) {
124+
return -1;
125+
}
126+
127+
if (len != NUM_ECC_BYTES) {
128+
return -1;
129+
}
130+
131+
memcpy(private_key, *p, len);
132+
133+
/* publicKey usually follows but is not parsed here */
134+
135+
return 0;
136+
}
137+
#endif /* defined(MCUBOOT_ENCRYPT_EC256) */
138+
139+
#if defined(MCUBOOT_ENCRYPT_X25519)
54140
/* Fixme: This duplicates code from encrypted.c and depends on mbedtls */
55141
static int
56-
parse_x25519_enckey(uint8_t **p, uint8_t *end, uint8_t *private_key)
142+
parse_priv_enckey(uint8_t **p, uint8_t *end, uint8_t *private_key)
57143
{
58144
size_t len;
59145
int version;
@@ -98,6 +184,7 @@ parse_x25519_enckey(uint8_t **p, uint8_t *end, uint8_t *private_key)
98184
memcpy(private_key, *p, EC_PRIVK_LEN);
99185
return 0;
100186
}
187+
#endif /* defined(MCUBOOT_ENCRYPT_X25519) */
101188

102189
void bootutil_aes_ctr_init(bootutil_aes_ctr_context *ctx)
103190
{
@@ -153,14 +240,15 @@ boot_decrypt_key(const uint8_t *buf, uint8_t *enckey)
153240
}
154241

155242
/*
156-
* Load the stored X25519 decryption private key
243+
* * Load the stored decryption private key
157244
*/
158-
rc = parse_x25519_enckey(&cp, cpend, private_key);
245+
rc = parse_priv_enckey(&cp, cpend, private_key);
159246
if (rc) {
247+
BOOT_LOG_ERR("Failed to parse ASN1 private key");
160248
return rc;
161249
}
162250

163-
psa_set_key_type(&kattr, PSA_KEY_TYPE_ECC_KEY_PAIR(PSA_ECC_FAMILY_MONTGOMERY));
251+
psa_set_key_type(&kattr, PSA_KEY_TYPE_ECC_KEY_PAIR(ECC_FAMILY));
164252
psa_set_key_usage_flags(&kattr, PSA_KEY_USAGE_DERIVE);
165253
psa_set_key_algorithm(&kattr, PSA_ALG_ECDH);
166254

boot/zephyr/CMakeLists.txt

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -112,11 +112,12 @@ zephyr_library_sources(
112112
${BOOT_DIR}/bootutil/src/fault_injection_hardening.c
113113
)
114114

115-
if(DEFINED CONFIG_BOOT_ENCRYPT_X25519 AND DEFINED CONFIG_BOOT_ED25519_PSA)
115+
if((CONFIG_BOOT_ENCRYPT_X25519 AND CONFIG_BOOT_ED25519_PSA)
116+
OR (CONFIG_BOOT_ENCRYPT_EC256 AND CONFIG_BOOT_ECDSA_PSA))
116117
zephyr_library_sources(${BOOT_DIR}/bootutil/src/encrypted_psa.c)
117118
endif()
118119

119-
if(DEFINED CONFIG_MEASURED_BOOT OR DEFINED CONFIG_BOOT_SHARE_DATA)
120+
if(CONFIG_MEASURED_BOOT OR CONFIG_BOOT_SHARE_DATA)
120121
zephyr_library_sources(
121122
${BOOT_DIR}/bootutil/src/boot_record.c
122123
)
@@ -296,7 +297,7 @@ elseif(CONFIG_BOOT_SIGNATURE_TYPE_ED25519 OR CONFIG_BOOT_ENCRYPT_X25519)
296297
endif()
297298
endif()
298299

299-
if(NOT CONFIG_BOOT_ED25519_PSA)
300+
if(NOT CONFIG_BOOT_ED25519_PSA AND NOT CONFIG_BOOT_ECDSA_PSA)
300301
if(CONFIG_BOOT_ENCRYPT_EC256 OR CONFIG_BOOT_ENCRYPT_X25519)
301302
zephyr_library_sources(
302303
${TINYCRYPT_DIR}/source/aes_encrypt.c
@@ -308,7 +309,7 @@ if(NOT CONFIG_BOOT_ED25519_PSA)
308309
endif()
309310
endif()
310311

311-
if(CONFIG_BOOT_ENCRYPT_EC256)
312+
if(CONFIG_BOOT_ENCRYPT_EC256 AND NOT CONFIG_BOOT_ECDSA_PSA)
312313
zephyr_library_sources(
313314
${TINYCRYPT_DIR}/source/ecc_dh.c
314315
)

0 commit comments

Comments
 (0)