true_rng/main.py

175 lines
4.4 KiB
Python

#!/usr/bin/python
# TrueRNG Read - Simple Example
# Chris K Cockrum
# 7/9/2021
#
# Requires Python 2.7 or 3.7+, pyserial
# On Linux - may need to be root or set /dev/tty port permissions to 666
#
# Python available here: https://www.python.org/
# Install Pyserial package with: python -m pip install pyserial
import serial
import time
import os
from serial.tools import list_ports
# Number of Bytes to Capture per Block
blocksize=1024
# Number of Blocks to Capture
numloops=1024
# Print our header
print('TrueRNG Counting Ones vs Zeros Example')
print('http://ubld.it')
print('==================================================')
import serial.tools.list_ports
# ubld.it TrueRNG
TrueRNGpid="04D8"
TrueRNGhid="F5FE"
# ubld.it TrueRNGpro
TrueRNGpropid="16D0"
TrueRNGprohid="0AA0"
# ubld.it TrueRNGproV2
TrueRNGproV2pid="04D8"
TrueRNGproV2hid="EBB5"
# Set default of None for com port
rng_com_port = None
ports = list(serial.tools.list_ports.comports())
for p in ports:
if(rng_com_port == None):
if TrueRNGproV2pid and TrueRNGproV2hid in p.hwid:
rng_com_port = p.device
print('TrueRNGproV2 Found')
break
if TrueRNGpropid and TrueRNGprohid in p.hwid:
rng_com_port = p.device
print('TrueRNGpro Found')
break
if TrueRNGpid and TrueRNGhid in p.hwid:
rng_com_port = p.device
print('TrueRNG Found')
break
if rng_com_port == None:
print('TrueRNG Not Found')
exit()
# Print which port we're using
print('Using com port: ' + str(rng_com_port))
# Print block size and number of loops
print('Block Size: ' + str(blocksize) + ' Bytes')
print('Number of loops: ' + str(numloops))
print('Total size: ' + str(blocksize * numloops) + ' Bytes')
print('Writing to: random.bin')
print('==================================================')
# Open/create the file random.bin in the current directory with 'write binary'
fp=open('random.bin','wb')
# Print an error if we can't open the file
if fp==None:
print('Error Opening File!')
# Try to setup and open the comport
try:
ser = serial.Serial(port=rng_com_port,timeout=10) # timeout set at 10 seconds in case the read fails
except:
print('Port Not Usable!')
print('Do you have permissions set to read ' + rng_com_port + ' ?')
# Open the serial port if it isn't open
if(ser.isOpen() == False):
ser.open()
# Set Data Terminal Ready to start flow
ser.setDTR(True)
# This clears the receive buffer so we aren't using buffered data
ser.flushInput()
# Keep track of total bytes read
totalbytes=0
totalzeros=0
# Generate look-up table for number of 1's in a byte
ones_in_byte = [0] * 256
for n in range(256):
ones_in_byte[n] = bin(n).count("1")
totalones=0
totalzeros=0
print('Starting data collection...')
starttime=time.time()
# Loop
for _ in range(numloops):
# Try to read the port and record the time before and after
try:
x=ser.read(blocksize) # read bytes from serial port
except:
print('Read Failed!!!')
break
# Update total bytes read
totalbytes +=len(x)
# Count ones
for n in range(len(x)):
totalones=totalones + ones_in_byte[x[n]]
totalzeros=totalzeros + 8-ones_in_byte[x[n]]
# If we were able to open the file, write to disk
if fp !=0:
fp.write(x)
# Calculate the rate
timenow=time.time()
if(timenow!=starttime):
rate=float(totalbytes) / ((timenow-starttime)*1000.0)
print(str(totalbytes) + ' Bytes Read at ' + '{:6.2f}'.format(rate) + ' Kbytes/s',end='\r')
endtime=time.time()
total_time = endtime - starttime
print('\n\nResults')
print( '=======')
print('Total execution time: {:.2f} seconds'.format(total_time))
print('Total Ones : ' + str(totalones))
print('Total Zeros: ' + str(totalzeros) + '\n')
print('Total Bits : ' + str(totalbytes*8))
if (totalones==totalzeros):
print('\nEqual Number of Ones and Zeros in Capture!')
if (totalones>totalzeros):
print('\nThere are ' + str(totalones-totalzeros) + ' more ones in the Capture!')
else:
print('\nThere are ' + str(totalzeros-totalones) + ' more zeros in the Capture!')
print( '=======')
# Close the serial port
ser.close()
# If the file is open then close it
if fp != 0:
fp.close()
# If we're on Linux set min on com port back to 1
# Pyserial screws this up
if os.name == 'posix':
os.system('stty -F '+rng_com_port+' min 1')