This post is older than 2 years and might not be relevant anymore
More Info: Consider searching for newer posts

NRF52840 and CC310 Random number generator hanging.

Hi,

Due to several reasons, we can't use the crypto API:s provided by the NRF_SDK (version 15.00) so we are creating a "driver" for direct access of the CC310 via the CRYS_* API:s available in ARM:s crypto library that is available in the before mentioned SDK version.

The AES crypto stuff is working as expected, but the RNG is behaving very badly.

In case 1, when we run Zephyr, the RNG hang in the function "CRYS_RndInit". I have not run this throug a debugger, so I have no additional information about this.

In case 2, when we use the nrf_sdk, the function "CRYS_RND_Reseeding" hangs in "SaSi_HalWaitInterrupt() at 0x3c342". AS far as I understand, the reseeding is required to get different  random numbers. At least, I continually get the same random number from the chip when not re-seeding.

Since I no longer have access the source code for ARM's cryptocell library, it's quite difficult for me to debug this. There must be something simple that I'm missing here (both for Zephyr and NRF_SDK).

Please advise since this is currently blocking the continuation of our porting.

This is the code that is running:

--- CUT AND PASTE ---

#include "crys_rnd.h"
#include "nrf52840.h"
#include "sns_silib.h"

int cc310_init(void)
{
        NVIC_EnableIRQ(CRYPTOCELL_IRQn);
        NRF_CRYPTOCELL->ENABLE = 1;

        ret = SaSi_LibInit();
        if (ret != SA_SILIB_RET_OK) {
                LOGE("Failed SaSi_LibInit - ret = 0x%x\n", ret);
                return HAL_RES_ERROR;
        }

        ret = CRYS_RndInit(&rndState, &rndWorkBuff);
        if (ret != SA_SILIB_RET_OK) {
                LOGE("Failed CRYS_RndInit - ret = 0x%x\n", ret);
                return HAL_RES_ERROR;
        }

        ret = CRYS_RND_Instantiation(&rndState, &rndWorkBuff);
        if (ret != SA_SILIB_RET_OK) {
                LOGE("Failed CRYS_RND_Instantiation - ret = 0x%x\n", ret);
                return HAL_RES_ERROR;
        }

        return 0;
}

int cc310_getRnd(uint32_t *const randomNumber)
{
        static uint8_t rand[sizeof(uint32_t)] = { 0 };
        int err = HAL_RES_OK;
        *randomNumber = 0;

        CRYS_RND_AddAdditionalInput(&rndState, rand, sizeof(rand));

        err = CRYS_RND_Reseeding(&rndState, &rndWorkBuff);
        if (SA_SILIB_RET_OK != err) {
                LOGE("Failed to re-seed the random number generator. Aborting");
                err = HAL_RES_ERROR;
                goto fail;
        }

        err = CRYS_RND_GenerateVector(&rndState, sizeof(uint32_t), rand);
        if (SA_SILIB_RET_OK != err) {
                LOGE("Failed to generate a random number. Aborting");
                err = HAL_RES_ERROR;
                goto fail;
        }

        *randomNumber = (uint32_t)rand;
        err = HAL_RES_OK;

fail:
        return err;
}

--- END CUT AND PASTE ---

Parents
  • Hi,

    I do not immediately see anything that should explain this behavior, but I will look into it and get back to you.

    In the meantime, have a few other comments that are not directly not related to the errors:

    • There is no need to call CRYS_RND_Instantiation(), as that is allready called from within CRYS_RndInit() (see API doc in crys_rnd.h). You can refer to how the RND is used in nrf_crypto by looking at the implementation in cc310_backend_rng.c in the nRF5 SDK, and use this as a reference. This should not be related to the issues you are seeings, though.)
    • Regarding reseeding, doing this every time you want  a random number is very inefficient. The idea is that the RNG is seeded initially, and then reseeded as needed. Between this you get a pseudo random sequence (PRBS), but this has very high quality.

    Br,

    Einar

Reply
  • Hi,

    I do not immediately see anything that should explain this behavior, but I will look into it and get back to you.

    In the meantime, have a few other comments that are not directly not related to the errors:

    • There is no need to call CRYS_RND_Instantiation(), as that is allready called from within CRYS_RndInit() (see API doc in crys_rnd.h). You can refer to how the RND is used in nrf_crypto by looking at the implementation in cc310_backend_rng.c in the nRF5 SDK, and use this as a reference. This should not be related to the issues you are seeings, though.)
    • Regarding reseeding, doing this every time you want  a random number is very inefficient. The idea is that the RNG is seeded initially, and then reseeded as needed. Between this you get a pseudo random sequence (PRBS), but this has very high quality.

    Br,

    Einar

Children
No Data
Related