Intro

MicroRNG is a hardware (true) random number generator device that can be used in embedded systems as a reliable source of entropy. This quick guide explains how to use MicroRNG device in UART mode on Linux platforms utilizing a serial interface.

Hardware requirements

  • A MicroRNG device configured for 2-wire UART operation mode (‘JP Mode select’ switch is set to position 1-2).
  • A Linux system with a serial port available.

Connecting components

Connect components with wires as shown in the picture below (connect also additional two wires for GND and 3.3V) or utilize MikroBUS socket if available.

Connecting MicroRNG in 2-wire UART mode

A Python sample code for retrieving serial number, version, model and 4 random bytes from MicroRNG as an integer

import serial
  
#
# The following Python3 sample code demonstrates how to use serial interface in Linux for connecting to MicroRNG device using a 2-wire UART connection.
# Before running this sample code, make sure the jumper of the 'JP Mode select' switch is set to position 1-2 (2-wire UART mode).
# For a complete UART API description visit https://tectrolabs.com/assets/documents/microrng-datasheet.pdf
#

# Set appropriate serial device parameters. Set UART speed as 19200 bps (19200 is a factory programmed default speed for the MicroRNG).
# Replace "/dev/ttyS2" with the appropriate device path specific to your Linux system.
ser = serial.Serial(port = "/dev/ttyS2", baudrate = 19200, timeout = 1)

# Send 'U' command to MicroRNG and make sure that it won't be running in sleep mode.
ser.write(b'U')

# Read the status byte from MicroRNG device
status = ser.read(1)

# The status byte value 0 indicates no errors
if status != b'\x00' :
    print("Could not detect a MicroRNG device")
    exit()

# Retrieve MicroRNG serial number using 's' command
ser.write(b's')
sn = ser.read(30) # Retrieve serial number as 30 ASCII characters
print("Device serial number: ", sn)
# Read the status byte
b = ser.read(1)
if status != b'\x00' :
    print("Could not retrieve serial number from MicroRNG device")
    exit()

# Retrieve MicroRNG version number using 'v' command
ser.write(b'v')
ver = ser.read(3) # Retrieve version number as 3 ASCII characters
print("Device version number: ", ver)
# Read the status byte
b = ser.read(1)
if status != b'\x00' :
    print("Could not retrieve version number from MicroRNG device")
    exit()

# Retrieve MicroRNG model using 'm' command
ser.write(b'm')
model = ser.read(6) # Retrieve model as 6 ASCII characters
print("Device model: ", model)
# Read the status byte
b = ser.read(1)
if status != b'\x00' :
    print("Could not retrieve model from MicroRNG device")
    exit()

# Send command '1' (code 49) to MicroRNG and request 4 random bytes for building a random integer.
# This 3 bytes command is used to retrieve true random bytes from the MicroRNG device. 
# The command byte is followed by a 16 bit unsigned integer which represents the
# requested amount of random bytes (max value is 50000), the lower byte
# is sent first and then the higher byte. The MicroRNG device
# expects to receive all three bytes within a reasonable amount of
# time. There should not be delays longer than 90 milliseconds
# between moments when sending each byte, as part of command,
# otherwise the device will ignore the command. 
request = bytearray([49, 4, 0])
ser.write(request)

# Read the response from MicroRNG as 4 bytes.
b = ser.read(4)
# Read the status byte from MicroRNG
status = ser.read(1)

if status != b'\x00' :
    print("Could not retrieve data from MicroRNG device")
    exit()

# Build a random integer from the retrieved bytes
int_val = int.from_bytes(b, 'little', signed=False)
print("Random integer: ", int_val)