Skip to content

Commit fabfdcf

Browse files
committed
More ssl work
1 parent 944d388 commit fabfdcf

File tree

9 files changed

+138
-69
lines changed

9 files changed

+138
-69
lines changed

ports/raspberrypi/Makefile

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -350,12 +350,17 @@ SRC_MBEDTLS := $(addprefix lib/mbedtls/library/, \
350350
x509write_csr.c \
351351
xtea.c \
352352
)
353-
SRC_C += $(SRC_MBEDTLS) mbedtls/mbedtls_port.c
353+
SRC_C += $(SRC_MBEDTLS) mbedtls/mbedtls_port.c mbedtls/crt_bundle.c
354354
CFLAGS += \
355355
-isystem $(TOP)/lib/mbedtls/include \
356356
-DMBEDTLS_CONFIG_FILE='"mbedtls/mbedtls_config.h"' \
357357

358+
$(BUILD)/x509_crt_bundle.S: $(TOP)/lib/certificates/nina-fw/data/roots.pem $(TOP)/tools/gen_crt_bundle.py
359+
$(Q)$(PYTHON) $(TOP)/tools/gen_crt_bundle.py -i $< -o $@ --asm
360+
OBJ_MBEDTLS := $(BUILD)/x509_crt_bundle.o
358361
$(patsubst %.c,$(BUILD)/%.o,$(SRC_MBEDTLS))): CFLAGS += -Wno-suggest-attribute=format
362+
else
363+
OBJ_MBEDTLS :=
359364
endif
360365

361366
SRC_COMMON_HAL_EXPANDED = $(addprefix shared-bindings/, $(SRC_COMMON_HAL)) \
@@ -396,9 +401,9 @@ OBJ += $(addprefix $(BUILD)/, $(SRC_S:.s=.o))
396401
OBJ += $(addprefix $(BUILD)/, $(SRC_S_UPPER:.S=.o))
397402
OBJ += $(addprefix $(BUILD)/, $(SRC_MOD:.c=.o))
398403
OBJ += $(BUILD)/boot2_padded_checksummed.o
399-
OBJ += $(OBJ_CYW43)
404+
OBJ += $(OBJ_CYW43) $(OBJ_MBEDTLS)
400405

401-
$(BUILD)/boot2_padded_checksummed.o: $(BUILD)/boot2_padded_checksummed.S
406+
$(BUILD)/%.o: $(BUILD)/%.S
402407
$(STEPECHO) "CC $<"
403408
$(Q)$(CC) $(CFLAGS) -c -o $@ $<
404409

ports/raspberrypi/common-hal/ssl/SSLContext.c

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,16 +31,27 @@
3131
#include "py/runtime.h"
3232
#include "py/stream.h"
3333

34+
#include "mbedtls/crt_bundle.h"
35+
3436
void common_hal_ssl_sslcontext_construct(ssl_sslcontext_obj_t *self) {
37+
common_hal_ssl_sslcontext_set_default_verify_paths(self);
3538
}
3639

3740
void common_hal_ssl_sslcontext_load_verify_locations(ssl_sslcontext_obj_t *self,
3841
const char *cadata) {
3942
mp_raise_NotImplementedError(NULL);
43+
44+
// self->crt_bundle_attach = NULL;
45+
// self->use_global_ca_store = false;
46+
// self->cacert_buf = (const unsigned char *)cadata;
47+
// self->cacert_bytes = strlen(cadata) + 1;
4048
}
4149

4250
void common_hal_ssl_sslcontext_set_default_verify_paths(ssl_sslcontext_obj_t *self) {
43-
mp_raise_NotImplementedError(NULL);
51+
self->crt_bundle_attach = crt_bundle_attach;
52+
self->use_global_ca_store = true;
53+
self->cacert_buf = NULL;
54+
self->cacert_bytes = 0;
4455
}
4556

4657
bool common_hal_ssl_sslcontext_get_check_hostname(ssl_sslcontext_obj_t *self) {

ports/raspberrypi/common-hal/ssl/SSLContext.h

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,8 +28,12 @@
2828
#pragma once
2929

3030
#include "py/obj.h"
31+
#include "mbedtls/ssl.h"
3132

3233
typedef struct {
3334
mp_obj_base_t base;
34-
bool check_name;
35+
bool check_name, use_global_ca_store;
36+
const unsigned char *cacert_buf;
37+
size_t cacert_bytes;
38+
int (*crt_bundle_attach)(mbedtls_ssl_config *conf);
3539
} ssl_sslcontext_obj_t;

ports/raspberrypi/common-hal/ssl/SSLSocket.c

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -171,8 +171,15 @@ ssl_sslsocket_obj_t *common_hal_ssl_sslcontext_wrap_socket(ssl_sslcontext_obj_t
171171
goto cleanup;
172172
}
173173

174-
// no certificate checking now
175-
mbedtls_ssl_conf_authmode(&o->conf, MBEDTLS_SSL_VERIFY_NONE);
174+
if (self->crt_bundle_attach != NULL) {
175+
mp_printf(&mp_plat_print, "attaching bundle\n");
176+
mbedtls_ssl_conf_authmode(&o->conf, MBEDTLS_SSL_VERIFY_REQUIRED);
177+
self->crt_bundle_attach(&o->conf);
178+
// } else if(self->cacert_buf && self->cacert_bytes) { // TODO: user bundle
179+
} else {
180+
mp_printf(&mp_plat_print, "yolo\n");
181+
mbedtls_ssl_conf_authmode(&o->conf, MBEDTLS_SSL_VERIFY_NONE);
182+
}
176183
mbedtls_ssl_conf_rng(&o->conf, mbedtls_ctr_drbg_random, &o->ctr_drbg);
177184
#ifdef MBEDTLS_DEBUG_C
178185
mbedtls_ssl_conf_dbg(&o->conf, mbedtls_debug, NULL);

ports/raspberrypi/common-hal/ssl/__init__.c

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,8 +25,15 @@
2525
* THE SOFTWARE.
2626
*/
2727

28+
#include "common-hal/ssl/__init__.h"
2829
#include "shared-bindings/ssl/__init__.h"
2930
#include "shared-bindings/ssl/SSLContext.h"
31+
#include "mbedtls/crt_bundle.h"
3032

3133
void common_hal_ssl_create_default_context(ssl_sslcontext_obj_t *self) {
34+
common_hal_ssl_sslcontext_construct(self);
35+
}
36+
37+
void ssl_reset(void) {
38+
crt_bundle_detach(NULL);
3239
}

ports/raspberrypi/common-hal/ssl/__init__.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,3 +25,5 @@
2525
*/
2626

2727
#pragma once
28+
29+
void ssl_reset(void);
Lines changed: 66 additions & 62 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
// Copyright 2018-2019 Espressif Systems (Shanghai) PTE LTD
2+
// Copyright 2022 Jeff Epler for Adafruit Industries
23
//
34
// Licensed under the Apache License, Version 2.0 (the "License");
45
// you may not use this file except in compliance with the License.
@@ -12,24 +13,35 @@
1213
// See the License for the specific language governing permissions and
1314
// limitations under the License.
1415

16+
#define BUNDLE_MAX_CERTS (200)
1517

1618
#include <string.h>
17-
#include <esp_system.h>
18-
#include "esp_crt_bundle.h"
19-
#include "esp_log.h"
19+
20+
#include "py/runtime.h"
21+
#include "py/mperrno.h"
22+
#include "mbedtls/x509_crt.h"
23+
#include "mbedtls/crt_bundle.h"
2024

2125
#define BUNDLE_HEADER_OFFSET 2
2226
#define CRT_HEADER_OFFSET 4
2327

24-
static const char *TAG = "esp-x509-crt-bundle";
25-
2628
/* a dummy certificate so that
2729
* cacert_ptr passes non-NULL check during handshake */
2830
static mbedtls_x509_crt s_dummy_crt;
2931

32+
#define TAG "x509-crt-bundle"
33+
34+
#define LOGE(tag, fmt, ...) mp_printf(&mp_plat_print, tag ":" fmt "\n",##__VA_ARGS__)
35+
#if 0
36+
#define LOGI(tag, fmt, ...) mp_printf(&mp_plat_print, tag ":" fmt "\n",##__VA_ARGS__)
37+
#define LOGD(tag, fmt, ...) mp_printf(&mp_plat_print, tag ":" fmt "\n",##__VA_ARGS__)
38+
#else
39+
#define LOGI(tag, fmt, ...) do {} while (0)
40+
#define LOGD(tag, fmt, ...) do {} while (0)
41+
#endif
3042

31-
extern const uint8_t x509_crt_imported_bundle_bin_start[] asm("_binary_x509_crt_bundle_start");
32-
extern const uint8_t x509_crt_imported_bundle_bin_end[] asm("_binary_x509_crt_bundle_end");
43+
extern const uint8_t x509_crt_imported_bundle_bin_start[] asm ("_binary_x509_crt_bundle_start");
44+
extern const uint8_t x509_crt_imported_bundle_bin_end[] asm ("_binary_x509_crt_bundle_end");
3345

3446

3547
typedef struct crt_bundle_t {
@@ -40,42 +52,41 @@ typedef struct crt_bundle_t {
4052

4153
static crt_bundle_t s_crt_bundle;
4254

43-
static int esp_crt_check_signature(mbedtls_x509_crt *child, const uint8_t *pub_key_buf, size_t pub_key_len);
55+
static int crt_check_signature(mbedtls_x509_crt *child, const uint8_t *pub_key_buf, size_t pub_key_len);
4456

4557

46-
static int esp_crt_check_signature(mbedtls_x509_crt *child, const uint8_t *pub_key_buf, size_t pub_key_len)
47-
{
58+
static int crt_check_signature(mbedtls_x509_crt *child, const uint8_t *pub_key_buf, size_t pub_key_len) {
4859
int ret = 0;
4960
mbedtls_x509_crt parent;
5061
const mbedtls_md_info_t *md_info;
5162
unsigned char hash[MBEDTLS_MD_MAX_SIZE];
5263

5364
mbedtls_x509_crt_init(&parent);
5465

55-
if ( (ret = mbedtls_pk_parse_public_key(&parent.pk, pub_key_buf, pub_key_len) ) != 0) {
56-
ESP_LOGE(TAG, "PK parse failed with error %X", ret);
66+
if ((ret = mbedtls_pk_parse_public_key(&parent.pk, pub_key_buf, pub_key_len)) != 0) {
67+
LOGE(TAG, "PK parse failed with error %X", ret);
5768
goto cleanup;
5869
}
5970

6071

6172
// Fast check to avoid expensive computations when not necessary
6273
if (!mbedtls_pk_can_do(&parent.pk, child->sig_pk)) {
63-
ESP_LOGE(TAG, "Simple compare failed");
74+
LOGE(TAG, "Simple compare failed");
6475
ret = -1;
6576
goto cleanup;
6677
}
6778

6879
md_info = mbedtls_md_info_from_type(child->sig_md);
69-
if ( (ret = mbedtls_md( md_info, child->tbs.p, child->tbs.len, hash )) != 0 ) {
70-
ESP_LOGE(TAG, "Internal mbedTLS error %X", ret);
80+
if ((ret = mbedtls_md(md_info, child->tbs.p, child->tbs.len, hash)) != 0) {
81+
LOGE(TAG, "Internal mbedTLS error %X", ret);
7182
goto cleanup;
7283
}
7384

74-
if ( (ret = mbedtls_pk_verify_ext( child->sig_pk, child->sig_opts, &parent.pk,
75-
child->sig_md, hash, mbedtls_md_get_size( md_info ),
76-
child->sig.p, child->sig.len )) != 0 ) {
85+
if ((ret = mbedtls_pk_verify_ext(child->sig_pk, child->sig_opts, &parent.pk,
86+
child->sig_md, hash, mbedtls_md_get_size(md_info),
87+
child->sig.p, child->sig.len)) != 0) {
7788

78-
ESP_LOGE(TAG, "PK verify failed with error %X", ret);
89+
LOGE(TAG, "PK verify failed with error %X", ret);
7990
goto cleanup;
8091
}
8192
cleanup:
@@ -91,8 +102,7 @@ static int esp_crt_check_signature(mbedtls_x509_crt *child, const uint8_t *pub_k
91102
* only verify the first untrusted link in the chain is signed by the
92103
* root certificate in the trusted bundle
93104
*/
94-
int esp_crt_verify_callback(void *buf, mbedtls_x509_crt *crt, int depth, uint32_t *flags)
95-
{
105+
static int crt_verify_callback(void *buf, mbedtls_x509_crt *crt, int depth, uint32_t *flags) {
96106
mbedtls_x509_crt *child = crt;
97107

98108
/* It's OK for a trusted cert to have a weak signature hash alg.
@@ -105,11 +115,11 @@ int esp_crt_verify_callback(void *buf, mbedtls_x509_crt *crt, int depth, uint32_
105115

106116

107117
if (s_crt_bundle.crts == NULL) {
108-
ESP_LOGE(TAG, "No certificates in bundle");
118+
LOGE(TAG, "No certificates in bundle");
109119
return MBEDTLS_ERR_X509_FATAL_ERROR;
110120
}
111121

112-
ESP_LOGD(TAG, "%d certificates in bundle", s_crt_bundle.num_certs);
122+
LOGD(TAG, "%d certificates in bundle", s_crt_bundle.num_certs);
113123

114124
size_t name_len = 0;
115125
const uint8_t *crt_name;
@@ -124,7 +134,7 @@ int esp_crt_verify_callback(void *buf, mbedtls_x509_crt *crt, int depth, uint32_
124134
name_len = s_crt_bundle.crts[middle][0] << 8 | s_crt_bundle.crts[middle][1];
125135
crt_name = s_crt_bundle.crts[middle] + CRT_HEADER_OFFSET;
126136

127-
int cmp_res = memcmp(child->issuer_raw.p, crt_name, name_len );
137+
int cmp_res = memcmp(child->issuer_raw.p, crt_name, name_len);
128138
if (cmp_res == 0) {
129139
crt_found = true;
130140
break;
@@ -139,42 +149,41 @@ int esp_crt_verify_callback(void *buf, mbedtls_x509_crt *crt, int depth, uint32_
139149
int ret = MBEDTLS_ERR_X509_FATAL_ERROR;
140150
if (crt_found) {
141151
size_t key_len = s_crt_bundle.crts[middle][2] << 8 | s_crt_bundle.crts[middle][3];
142-
ret = esp_crt_check_signature(child, s_crt_bundle.crts[middle] + CRT_HEADER_OFFSET + name_len, key_len);
152+
ret = crt_check_signature(child, s_crt_bundle.crts[middle] + CRT_HEADER_OFFSET + name_len, key_len);
143153
}
144154

145155
if (ret == 0) {
146-
ESP_LOGI(TAG, "Certificate validated");
156+
LOGI(TAG, "Certificate validated");
147157
*flags = 0;
148158
return 0;
149159
}
150160

151-
ESP_LOGE(TAG, "Failed to verify certificate");
161+
LOGE(TAG, "Failed to verify certificate");
152162
return MBEDTLS_ERR_X509_FATAL_ERROR;
153163
}
154164

155165

156166
/* Initialize the bundle into an array so we can do binary search for certs,
157167
the bundle generated by the python utility is already presorted by subject name
158168
*/
159-
static esp_err_t esp_crt_bundle_init(const uint8_t *x509_bundle, size_t bundle_size)
160-
{
169+
static err_t crt_bundle_init(const uint8_t *x509_bundle, size_t bundle_size) {
161170
if (bundle_size < BUNDLE_HEADER_OFFSET + CRT_HEADER_OFFSET) {
162-
ESP_LOGE(TAG, "Invalid certificate bundle");
163-
return ESP_ERR_INVALID_ARG;
171+
LOGE(TAG, "Invalid certificate bundle");
172+
return -MP_EINVAL;
164173
}
165174

166175
uint16_t num_certs = (x509_bundle[0] << 8) | x509_bundle[1];
167-
if (num_certs > CONFIG_MBEDTLS_CERTIFICATE_BUNDLE_MAX_CERTS) {
168-
ESP_LOGE(TAG, "No. of certs in the certificate bundle = %d exceeds\n"
169-
"Max allowed certificates in the certificate bundle = %d\n"
170-
"Please update the menuconfig option with appropriate value", num_certs, CONFIG_MBEDTLS_CERTIFICATE_BUNDLE_MAX_CERTS);
171-
return ESP_ERR_INVALID_ARG;
176+
if (num_certs > BUNDLE_MAX_CERTS) {
177+
// No. of certs in the certificate bundle = %d exceeds\n"
178+
// Max allowed certificates in the certificate bundle = %d\n"
179+
// Please update the menuconfig option with appropriate value", num_certs, BUNDLE_MAX_CERTS
180+
return -MP_E2BIG;
172181
}
173182

174-
const uint8_t **crts = calloc(num_certs, sizeof(x509_bundle));
183+
const uint8_t **crts = m_tracked_calloc(num_certs, sizeof(x509_bundle));
175184
if (crts == NULL) {
176-
ESP_LOGE(TAG, "Unable to allocate memory for bundle");
177-
return ESP_ERR_NO_MEM;
185+
LOGE(TAG, "Unable to allocate memory for bundle");
186+
return -MP_ENOMEM;
178187
}
179188

180189
const uint8_t *cur_crt;
@@ -185,67 +194,62 @@ static esp_err_t esp_crt_bundle_init(const uint8_t *x509_bundle, size_t bundle_s
185194
for (int i = 0; i < num_certs; i++) {
186195
crts[i] = cur_crt;
187196
if (cur_crt + CRT_HEADER_OFFSET > bundle_end) {
188-
ESP_LOGE(TAG, "Invalid certificate bundle");
189-
free(crts);
190-
return ESP_ERR_INVALID_ARG;
197+
LOGE(TAG, "Invalid certificate bundle");
198+
m_tracked_free(crts);
199+
return -MP_EINVAL;
191200
}
192201
size_t name_len = cur_crt[0] << 8 | cur_crt[1];
193202
size_t key_len = cur_crt[2] << 8 | cur_crt[3];
194203
cur_crt = cur_crt + CRT_HEADER_OFFSET + name_len + key_len;
195204
}
196205

197206
if (cur_crt > bundle_end) {
198-
ESP_LOGE(TAG, "Invalid certificate bundle");
199-
free(crts);
200-
return ESP_ERR_INVALID_ARG;
207+
LOGE(TAG, "Invalid certificate bundle");
208+
m_tracked_free(crts);
209+
return -MP_EINVAL;
201210
}
202211

203212
/* The previous crt bundle is only updated when initialization of the
204213
* current crt_bundle is successful */
205214
/* Free previous crt_bundle */
206-
free(s_crt_bundle.crts);
215+
m_tracked_free(s_crt_bundle.crts);
207216
s_crt_bundle.num_certs = num_certs;
208217
s_crt_bundle.crts = crts;
209-
return ESP_OK;
218+
return 0;
210219
}
211220

212-
esp_err_t esp_crt_bundle_attach(void *conf)
213-
{
214-
esp_err_t ret = ESP_OK;
221+
int crt_bundle_attach(mbedtls_ssl_config *ssl_conf) {
222+
int ret = 0;
215223
// If no bundle has been set by the user then use the bundle embedded in the binary
216224
if (s_crt_bundle.crts == NULL) {
217-
ret = esp_crt_bundle_init(x509_crt_imported_bundle_bin_start, x509_crt_imported_bundle_bin_end - x509_crt_imported_bundle_bin_start);
225+
ret = crt_bundle_init(x509_crt_imported_bundle_bin_start, x509_crt_imported_bundle_bin_end - x509_crt_imported_bundle_bin_start);
218226
}
219227

220-
if (ret != ESP_OK) {
221-
ESP_LOGE(TAG, "Failed to attach bundle");
228+
if (ret != 0) {
222229
return ret;
223230
}
224231

225-
if (conf) {
232+
if (ssl_conf) {
226233
/* point to a dummy certificate
227234
* This is only required so that the
228235
* cacert_ptr passes non-NULL check during handshake
229236
*/
230-
mbedtls_ssl_config *ssl_conf = (mbedtls_ssl_config *)conf;
231237
mbedtls_x509_crt_init(&s_dummy_crt);
232238
mbedtls_ssl_conf_ca_chain(ssl_conf, &s_dummy_crt, NULL);
233-
mbedtls_ssl_conf_verify(ssl_conf, esp_crt_verify_callback, NULL);
239+
mbedtls_ssl_conf_verify(ssl_conf, crt_verify_callback, NULL);
234240
}
235241

236242
return ret;
237243
}
238244

239-
void esp_crt_bundle_detach(mbedtls_ssl_config *conf)
240-
{
241-
free(s_crt_bundle.crts);
245+
void crt_bundle_detach(mbedtls_ssl_config *conf) {
246+
m_tracked_free(s_crt_bundle.crts);
242247
s_crt_bundle.crts = NULL;
243248
if (conf) {
244249
mbedtls_ssl_conf_verify(conf, NULL, NULL);
245250
}
246251
}
247252

248-
esp_err_t esp_crt_bundle_set(const uint8_t *x509_bundle, size_t bundle_size)
249-
{
250-
return esp_crt_bundle_init(x509_bundle, bundle_size);
253+
int crt_bundle_set(const uint8_t *x509_bundle, size_t bundle_size) {
254+
return crt_bundle_init(x509_bundle, bundle_size);
251255
}

0 commit comments

Comments
 (0)