<div dir="ltr"><div><div>Hi,<br></div>I tried implementing getentropy on BBB, below is the patch. Please have a look.<br></div>I followed these(<a href="https://e2e.ti.com/support/arm/sitara_arm/f/791/t/355064">1</a> & <a href="http://ftp.netbsd.org/pub/NetBSD/NetBSD-current/src/sys/arch/arm/omap/am335x_trng.c">2</a>) links for code reference. and <a href="https://docs.google.com/spreadsheets/d/1VpghMlLtrWQIrcvCsRg3ueRZkX0eGSQkFnzjfsqrd8A/view#gid=0">this</a> for register reference. Moreover, what further configuration in RTEMS is needed to execute and test this code along with getentropy() sample testcode?<br><div><div><br><div><div><br>+ /*<br>+  * Copyright (c) 2018 embedded brains GmbH.  All rights reserved.<br>+  *<br>+  *  embedded brains GmbH<br>+  *  Dornierstr. 4<br>+  *  82178 Puchheim<br>+  *  Germany<br>+  *  <<a href="mailto:rtems@embedded-brains.de">rtems@embedded-brains.de</a>><br>+  *<br>+  * The license and distribution terms for this file may be<br>+  * found in the file LICENSE in this distribution or at<br>+  * <a href="http://www.rtems.org/license/LICENSE">http://www.rtems.org/license/LICENSE</a>.<br>+  */<br>+ <br>+ #include <libcpu/am335x.h><br>+ #include <unistd.h><br>+ #include <string.h><br>+ #include <rtems/sysinit.h><br>+ <br>+ #define RNG_BASE    0x48310000<br>+ #define CM_PER_RNG_CLKCTRL    0x44e00090<br>+ #define RNG_STATUS_RDY    (1u <<  0)  // output ready for reading<br>+ #define RNG_STATUS_ERR    (1u <<  1)  // FRO shutdown alarm<br>+ #define RNG_STATUS_CLK    (1u << 31)  // module functional clock active (no irq)<br>+ <br>+ typedef volatile struct rng *rng_ref_t;<br>+ <br>+ struct rng {<br>+ /*00*/    uint64_t output;    //r-<br>+ /*08*/    uint32_t status;    //r-<br>+ /*0c*/    uint32_t irq_en;    //rw<br>+ /*10*/    uint32_t status_clr;    //-c<br>+ /*14*/    uint32_t control;    //rw<br>+ /*18*/    uint32_t config;    //rw<br>+ }; <br>+ <br>+ static void TRNG_Enable(rng_ref_t rng){<br>+     rng->config = 0<br>+     | 34 << 16  // max refill 34 * 256 cycles<br>+     | 33 <<  0;  // min refill 33 * 64 cycles<br>+     rng->control = 0<br>+     | 33 << 16  // startup 33 * 256 cycles<br>+     |  1 << 10;  // enable module<br>+ }<br>+ <br>+ static void beagle_trng_clock_enable(void)<br>+ {<br>+     // enable module clock<br>+     *(volatile uint8_t *) CM_PER_RNG_CLKCTRL = 2;<br>+     while( *(volatile uint32_t *) CM_PER_RNG_CLKCTRL & 0x30000 ) {}<br>+ }<br>+ <br>+ static uint64_t TRNG_GetRandData(){<br>+     uint64_t output = rng->output;<br>+     return output;<br>+ }<br>+ <br>+ int getentropy(void *ptr, size_t n)<br>+ {<br>+     rng_ref_t const rng = (rng_ref_t) RNG_BASE;<br>+     TRNG_Enable(rng);<br>+     while (n > 0) {<br>+         uint64_t random;<br>+         size_t copy;<br>+ <br>+         while( ( rng->status & RNG_STATUS_RDY ) == 0 ); //wait<br>+ <br>+         random = TRNG_GetRandData(rng);<br>+ <br>+         /*<br>+          * Read TRNG status one more time to avoid race condition.<br>+          * Otherwise we can read (and clear) an old ready status but get<br>+          * a new value. The ready status for this value wouldn't be<br>+          * reset.<br>+          */<br>+         rng->status_clr = RNG_STATUS_RDY;<br>+ <br>+         copy = sizeof(random);<br>+         if (n < copy ) {<br>+             copy = n;<br>+         }<br>+         memcpy(ptr, &random, copy);<br>+         n -= copy;<br>+         ptr += copy;<br>+     }<br>+ <br>+     return 0;<br>+ }<br>+ <br>+ RTEMS_SYSINIT_ITEM(<br>+   beagle_trng_clock_enable,<br>+   RTEMS_SYSINIT_DEVICE_DRIVERS,<br>+   RTEMS_SYSINIT_ORDER_LAST<br>+ );<br><br></div><div>Regards,<br></div><div>Udit agarwal<br></div></div></div></div></div>