From 47a3ce26f2322e8ee601837b6c8b12eecddfe1e2 Mon Sep 17 00:00:00 2001 From: Andrzej Kaczmarek Date: Fri, 4 May 2018 13:22:24 +0200 Subject: [PATCH 1/2] nimble/ll: Use TRNG driver if available This patch enabled controller to use TRNG via driver, if enabled, instead of ble_hw interfaces. In case of nRF52 this is the same peripheral as used by ble_hw, but by accessing it via driver it can be shared with other RNG users. --- nimble/controller/src/ble_ll_rand.c | 26 +++++++++++++++++++++++++- 1 file changed, 25 insertions(+), 1 deletion(-) diff --git a/nimble/controller/src/ble_ll_rand.c b/nimble/controller/src/ble_ll_rand.c index 0256fe032..7b384e9db 100644 --- a/nimble/controller/src/ble_ll_rand.c +++ b/nimble/controller/src/ble_ll_rand.c @@ -26,7 +26,13 @@ #include "nimble/nimble_opt.h" #include "controller/ble_hw.h" #include "controller/ble_ll.h" +#if MYNEWT_VAL(TRNG) +#include "trng/trng.h" +#endif +#if MYNEWT_VAL(TRNG) +static struct trng_dev *g_trng; +#else /* This is a simple circular buffer for holding N samples of random data */ struct ble_ll_rnum_data { @@ -61,11 +67,21 @@ ble_ll_rand_sample(uint8_t rnum) } OS_EXIT_CRITICAL(sr); } +#endif /* Get 'len' bytes of random data */ int ble_ll_rand_data_get(uint8_t *buf, uint8_t len) { +#if MYNEWT_VAL(TRNG) + size_t num; + + while (len) { + num = trng_read(g_trng, buf, len); + buf += num; + len -= num; + } +#else uint8_t rnums; os_sr_t sr; @@ -100,7 +116,7 @@ ble_ll_rand_data_get(uint8_t *buf, uint8_t len) } } } - +#endif return BLE_ERR_SUCCESS; } @@ -138,10 +154,14 @@ ble_ll_rand_prand_get(uint8_t *prand) int ble_ll_rand_start(void) { +#if MYNEWT_VAL(TRNG) + /* Nothing to do - this is handled by driver */ +#else /* Start the generation of numbers if we are not full */ if (g_ble_ll_rnum_data.rnd_size < MYNEWT_VAL(BLE_LL_RNG_BUFSIZE)) { ble_hw_rng_start(); } +#endif return 0; } @@ -154,8 +174,12 @@ ble_ll_rand_start(void) int ble_ll_rand_init(void) { +#if MYNEWT_VAL(TRNG) + g_trng = (struct trng_dev *) os_dev_open("trng", OS_TIMEOUT_NEVER, NULL); +#else g_ble_ll_rnum_data.rnd_in = g_ble_ll_rnum_buf; g_ble_ll_rnum_data.rnd_out = g_ble_ll_rnum_buf; ble_hw_rng_init(ble_ll_rand_sample, 1); +#endif return 0; } From 0a9320d84d86f4c8970895bb34ae7debf1acff7d Mon Sep 17 00:00:00 2001 From: Andrzej Kaczmarek Date: Fri, 4 May 2018 13:55:44 +0200 Subject: [PATCH 2/2] nimble/host: Use TRNG driver if available If TRNG is enabled, let's use it directly instead of going through HCI. As a bonus, this way uECC can be used even before NimBLE is synced with controller. --- nimble/host/src/ble_sm_alg.c | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) diff --git a/nimble/host/src/ble_sm_alg.c b/nimble/host/src/ble_sm_alg.c index 91639d9e2..6698e2b0f 100644 --- a/nimble/host/src/ble_sm_alg.c +++ b/nimble/host/src/ble_sm_alg.c @@ -35,6 +35,13 @@ #if MYNEWT_VAL(BLE_SM_SC) #include "tinycrypt/cmac_mode.h" #include "tinycrypt/ecc_dh.h" +#if MYNEWT_VAL(TRNG) +#include "trng/trng.h" +#endif +#endif + +#if MYNEWT_VAL(BLE_SM_SC) && MYNEWT_VAL(TRNG) +static struct trng_dev *g_trng; #endif static void @@ -473,9 +480,24 @@ ble_sm_alg_gen_key_pair(uint8_t *pub, uint8_t *priv) static int ble_sm_alg_rand(uint8_t *dst, unsigned int size) { +#if MYNEWT_VAL(TRNG) + size_t num; + + if (!g_trng) { + g_trng = (struct trng_dev *)os_dev_open("trng", OS_WAIT_FOREVER, NULL); + assert(g_trng); + } + + while (size) { + num = trng_read(g_trng, dst, size); + dst += num; + size -= num; + } +#else if (ble_hs_hci_util_rand(dst, size)) { return 0; } +#endif return 1; }