From dc0b3db1b4f1895a07e5fe280ee3790e87f97b9f Mon Sep 17 00:00:00 2001 From: Ataberk Date: Sun, 25 Sep 2022 17:22:03 +0200 Subject: Initial commit --- sources/apps/QUAC-TRNG/scripts/convert_ent.py | 32 ++++ sources/apps/QUAC-TRNG/scripts/ft200_rc/README.md | 21 +++ .../apps/QUAC-TRNG/scripts/ft200_rc/__init__.py | 0 .../scripts/ft200_rc/docs/1189902393_ft200_lcd.pdf | Bin 0 -> 14203337 bytes .../apps/QUAC-TRNG/scripts/ft200_rc/docs/210.pdf | Bin 0 -> 102947 bytes sources/apps/QUAC-TRNG/scripts/ft200_rc/ft200.py | 182 +++++++++++++++++++++ .../QUAC-TRNG/scripts/ft200_rc/usb_dev_path.sh | 13 ++ sources/apps/QUAC-TRNG/scripts/run_ent.py | 43 +++++ sources/apps/QUAC-TRNG/scripts/run_vn_nist.py | 125 ++++++++++++++ sources/apps/QUAC-TRNG/scripts/sha_bitstreams.py | 87 ++++++++++ sources/apps/QUAC-TRNG/scripts/top_ents.py | 35 ++++ 11 files changed, 538 insertions(+) create mode 100644 sources/apps/QUAC-TRNG/scripts/convert_ent.py create mode 100644 sources/apps/QUAC-TRNG/scripts/ft200_rc/README.md create mode 100644 sources/apps/QUAC-TRNG/scripts/ft200_rc/__init__.py create mode 100644 sources/apps/QUAC-TRNG/scripts/ft200_rc/docs/1189902393_ft200_lcd.pdf create mode 100644 sources/apps/QUAC-TRNG/scripts/ft200_rc/docs/210.pdf create mode 100644 sources/apps/QUAC-TRNG/scripts/ft200_rc/ft200.py create mode 100755 sources/apps/QUAC-TRNG/scripts/ft200_rc/usb_dev_path.sh create mode 100644 sources/apps/QUAC-TRNG/scripts/run_ent.py create mode 100644 sources/apps/QUAC-TRNG/scripts/run_vn_nist.py create mode 100644 sources/apps/QUAC-TRNG/scripts/sha_bitstreams.py create mode 100644 sources/apps/QUAC-TRNG/scripts/top_ents.py (limited to 'sources/apps/QUAC-TRNG/scripts') diff --git a/sources/apps/QUAC-TRNG/scripts/convert_ent.py b/sources/apps/QUAC-TRNG/scripts/convert_ent.py new file mode 100644 index 0000000..b2c66ea --- /dev/null +++ b/sources/apps/QUAC-TRNG/scripts/convert_ent.py @@ -0,0 +1,32 @@ +import os +import argparse +from numpy import array + +parser = argparse.ArgumentParser(description = "Run this script to preprocess entropy files") +parser.add_argument('indir', help="Path to entropy files") +args = parser.parse_args() + +files = [] +for fname in os.listdir(args.indir): + files.append(fname) + +for file in files: + print("Processing:", file) + # Add this placement + fpath = os.path.normpath(args.indir + '/' + file) + infile = open(fpath,'r') + wfile = file.split('.')[0] + '_floats.bin' + wfpath = os.path.normpath(args.indir + '/' + wfile) + output_file = open(wfpath, 'wb') + + lines = infile.readlines() + + # First row reserved for metadata + for lidx in range(1,len(lines)): + line = lines[lidx].strip() + split = line.split() + elements = [float(i) for i in split[1:]] + a = array(elements,'float32') + a.tofile(output_file) + + output_file.close() \ No newline at end of file diff --git a/sources/apps/QUAC-TRNG/scripts/ft200_rc/README.md b/sources/apps/QUAC-TRNG/scripts/ft200_rc/README.md new file mode 100644 index 0000000..de91b27 --- /dev/null +++ b/sources/apps/QUAC-TRNG/scripts/ft200_rc/README.md @@ -0,0 +1,21 @@ +# FT200 remote read and write + +Make sure that the FT200 controller match the parameters you are using in your script. +The relevant parameters are: + +PASS-0101 menu (see documentation in doc folder): +* ldN0 (Device address) +* bAUd (rate) +* UCR (parity) + +## Requirements +* pip3 install -U minimalmodbus + + +## Add your user to the dialout group + +sudo gpasswd --add ${USER} dialout +(You need to log out and log back in again for it to be effective) + +## Execute test +* python3 ft200.py diff --git a/sources/apps/QUAC-TRNG/scripts/ft200_rc/__init__.py b/sources/apps/QUAC-TRNG/scripts/ft200_rc/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/sources/apps/QUAC-TRNG/scripts/ft200_rc/docs/1189902393_ft200_lcd.pdf b/sources/apps/QUAC-TRNG/scripts/ft200_rc/docs/1189902393_ft200_lcd.pdf new file mode 100644 index 0000000..8c18eaa Binary files /dev/null and b/sources/apps/QUAC-TRNG/scripts/ft200_rc/docs/1189902393_ft200_lcd.pdf differ diff --git a/sources/apps/QUAC-TRNG/scripts/ft200_rc/docs/210.pdf b/sources/apps/QUAC-TRNG/scripts/ft200_rc/docs/210.pdf new file mode 100644 index 0000000..e4d0d39 Binary files /dev/null and b/sources/apps/QUAC-TRNG/scripts/ft200_rc/docs/210.pdf differ diff --git a/sources/apps/QUAC-TRNG/scripts/ft200_rc/ft200.py b/sources/apps/QUAC-TRNG/scripts/ft200_rc/ft200.py new file mode 100644 index 0000000..aa50a1f --- /dev/null +++ b/sources/apps/QUAC-TRNG/scripts/ft200_rc/ft200.py @@ -0,0 +1,182 @@ +""""" +Code for monitoring and controlling temperature in the Maxwell FT200 controller using the Modbus RS485 protocol +@author: Lois Orosa +""""" +import minimalmodbus as mm, serial, time +import time +import os +import sys +import pathlib + +class FT200: + """ + Controls and monitors the Maxwell FT200 tempoerature controller + """ + READ_ERROR = -999 + WRITE_ERROR = -998 + def __init__(self, _baud=9600, _ft200_addr=1, _temp_tolerance=2): + self.baud = _baud + self.write_reg = 5 # Write register + self.read_reg = 0 # Read register + self.ft200_addr = _ft200_addr # Address of the device (by default is 1) + self.temp_tolerance = _temp_tolerance # Temperature tolerance. By default, we consider that we reach the target value if the measured value is within +-0.2C + + try: + self.device = self.findDevice() # Get the USB-RS485 device + print("USB-RS485 Device: "+str(self.device)) + self.instrument = mm.Instrument(self.device , 3 , debug = False) + self.instrument.serial.baudrate = self.baud + self.instrument.address = self.ft200_addr + self.instrument.serial.timeout = 1 + self.instrument.serial.parity = serial.PARITY_NONE + self.instrument.mode = mm.MODE_RTU + print("Device "+self.device+": conected") + except: + raise + + # Automatically find the USB-RS485 Device + def findDevice(self): + ''' + Find the USB-RS485 device + This function might raise two exceptions: + -> NameError: There is more than 1 USB-RS485 device, or other USB device has a similar name as the USB-RS485 device + -> IOError: Device not found. + ''' + DEVICENAME = "1a86_USB" + name = '' + while True: + path = pathlib.Path(__file__).parent.absolute() + f = os.popen(str(path)+"/usb_dev_path.sh") + for device in f: + if DEVICENAME in device: + if name == '': + name = device.split()[0] + else: + raise NameError("There are at least two USB devices whose name contains "+str(DEVICENAME)) + if name == '': + raise IOError("Device not found.") + return name + + # Read Temperature from FT200 + # The output value has 1 decimal, and it is multiplied by 10 + # E.g., data= 102 represents a temperature of 10.2C + def readTemp(self): + try: + data = self.instrument.read_register(self.read_reg, functioncode=3) + return data + except IOError: + print("Failed to read from instrument") + return self.READ_ERROR + + # Check if the temperature reached a value + # The input value has 1 decimal, and it is multiplied by 10 + # E.g., data= 102 represents a temperature of 10.2C + def isTemp(self, temperature): + try: + data = self.instrument.read_register(self.read_reg, functioncode=3) + if data >= (temperature-self.temp_tolerance) and data <= (temperature+self.temp_tolerance): + return True + else: + return False + except IOError: + print("Failed to read from instrument") + return False + + # Set Temperature FT200 + # The value should be a integer, and it should be the temperature value with 1 decimal multiplied by 10 + # E.g., value= 102 represents a temperature of 10.2C + def setTemp(self, value): + try: + self.instrument.write_register(self.write_reg, value, functioncode=6) + except IOError: + print("Failed to write to instrument") + return self.WRITE_ERROR + return 0 + + # Set the temperature and wait for the temperature to be stable + # Optimized version that reach the target temperature earlier + # The value should be a integer, and it should be the temperature value with 1 decimal multiplied by 10 + # E.g., value= 102 represents a temperature of 10.2C + def autoSetAndWait(self, temperature, debug = False): + acceleration_factor = 5 + stability = 10 # Iterations that the temperature needs to be stable + time_sleep = 1 # 1 second wait per loop iteration + stable_count = stability # Counter for taking into account the stability of the temperature + stable_margin = 20 # We do not change the set temperature if we are within 2C from the target + optTemp = temperature + self.setTemp(optTemp) # Set the temperature + curTemp = self.readTemp() # Read the temperature + if debug: + print("[TEMPERATURE] current: "+str(curTemp/10.0)+", goal: "+str(temperature/10.0)+", programmed: "+str(optTemp/10.0)) + while (((curTemp > (temperature + self.temp_tolerance)) or (curTemp < (temperature - self.temp_tolerance))) or (stable_count!=0)): + if debug: + print("[TEMPERATURE] current: "+str(curTemp/10.0)+", goal: "+str(temperature/10.0)+", programmed: "+str(optTemp/10.0)+", stable_count: "+str(stable_count)) + prev_optTemp = optTemp + if (temperature - curTemp) > 0: #(stable_margin): # If we are far away more than 2C + optTemp = temperature + (temperature - curTemp)*acceleration_factor # Optimization to accelerate convergence + else: + optTemp = temperature + if optTemp != prev_optTemp: + self.setTemp(optTemp) # Set temperature only if different from the previous iteration + + time.sleep(time_sleep) # WAit for a while + + curTemp = self.readTemp() # Read the temperature + while (curTemp == self.READ_ERROR): # If there is an error, read again + curTemp = self.readTemp() + # Five iterations in the range + if (curTemp > (temperature + self.temp_tolerance)) or (curTemp < (temperature - self.temp_tolerance)): + stable_count = stability + else: + stable_count -= 1 # The temperature has to remain stable for a while + + def autoSetAndWait_2(self, temperature, debug = False): + acceleration_factor = 150 + stability = 10 # Iterations that the temperature needs to be stable + time_sleep = 1 # 1 second wait per loop iteration + stable_count = stability # Counter for taking into account the stability of the temperature + stable_margin = 5 # We do not change the set temperature if we are within 2C from the target + optTemp = temperature + self.setTemp(optTemp) # Set the temperature + curTemp = self.readTemp() # Read the temperature + if debug: + print("[TEMPERATURE] current: "+str(curTemp/10.0)+", goal: "+str(temperature/10.0)+", programmed: "+str(optTemp/10.0)) + while (((curTemp > (temperature + self.temp_tolerance)) or (curTemp < (temperature - self.temp_tolerance))) or (stable_count!=0)): + if debug: + print("[TEMPERATURE] current: "+str(curTemp/10.0)+", goal: "+str(temperature/10.0)+", programmed: "+str(optTemp/10.0)+", stable_count: "+str(stable_count)) + prev_optTemp = optTemp + if abs(temperature - curTemp) > (stable_margin): # If we are far away more than 2C + if temperature > curTemp: + optTemp = temperature + acceleration_factor # Optimization to accelerate convergence + else: + optTemp = temperature - acceleration_factor # Optimization to accelerate convergence + else: + optTemp = temperature + + time.sleep(time_sleep) # WAit for a while + + curTemp = self.readTemp() # Read the temperature + while (curTemp == self.READ_ERROR): # If there is an error, read again + curTemp = self.readTemp() + # Five iterations in the range + if (curTemp > (temperature + self.temp_tolerance)) or (curTemp < (temperature - self.temp_tolerance)): + stable_count = stability + else: + stable_count -= 1 # The temperature has to remain stable for a while + +if __name__ == '__main__': + ## Example of how to use the FT200 class + try: + tc = FT200() + except Exception as error: + print("[ERROR] "+ repr(error)) + sys.exit(0) + + # Temperature + value = int(sys.argv[1]) * 10 + print(value) + print(tc.readTemp()) + tc.autoSetAndWait(value,True) + + + diff --git a/sources/apps/QUAC-TRNG/scripts/ft200_rc/usb_dev_path.sh b/sources/apps/QUAC-TRNG/scripts/ft200_rc/usb_dev_path.sh new file mode 100755 index 0000000..241aef1 --- /dev/null +++ b/sources/apps/QUAC-TRNG/scripts/ft200_rc/usb_dev_path.sh @@ -0,0 +1,13 @@ +#!/bin/bash +# https://unix.stackexchange.com/questions/144029/command-to-determine-ports-of-a-device-like-dev-ttyusb0 +echo "USB devices:" +for sysdevpath in $(find /sys/bus/usb/devices/usb*/ -name dev); do + ( + syspath="${sysdevpath%/dev}" + devname="$(udevadm info -q name -p $syspath)" +[[ "$devname" == "bus/"* ]] && exit + eval "$(udevadm info -q property --export -p $syspath)" +[[ -z "$ID_SERIAL" ]] && exit + echo "/dev/$devname - $ID_SERIAL" + ) +done diff --git a/sources/apps/QUAC-TRNG/scripts/run_ent.py b/sources/apps/QUAC-TRNG/scripts/run_ent.py new file mode 100644 index 0000000..5163c5f --- /dev/null +++ b/sources/apps/QUAC-TRNG/scripts/run_ent.py @@ -0,0 +1,43 @@ +import os +import argparse +import subprocess +import time + +parser = argparse.ArgumentParser(description = "Collects entropy for different data patterns") + +parser.add_argument('dimm', help="DIMM label under test") +parser.add_argument('temperature', help="DIMM temperature in centigrades") +parser.add_argument('iters', help="How many times do we QUAC to find entropy") +parser.add_argument('stride', help="Stride (in rows) used to skim through segments, default: 4") + +args = parser.parse_args() + +# ---------------- SETUP DIRECTORIES ------------------- + +if not os.path.isdir("data"): + os.mkdir("data") + +if not os.path.isdir("data/" + args.dimm): + os.mkdir("data/" + args.dimm) + +if not os.path.isdir("data/" + args.dimm + "/ent"): + os.mkdir("data/" + args.dimm + "/ent") + +if not os.path.isdir("data/" + args.dimm + "/ent/" + args.temperature + "C"): + os.mkdir("data/" + args.dimm + "/ent/" + args.temperature + "C") + +outdir = os.path.normpath("data/" + args.dimm + "/ent/" + args.temperature + "C") + +# -------------------- RUN TESTS ----------------------- + +placements = ["1000", "1001", "1010", "1011", "1100" , "1101", "1110", "1111", \ + "0111", "0110", "0101", "0100", "0011" , "0010", "0001", "0000"] + +ent_path = os.path.normpath("bin/ENT") +results_path = outdir +stride = args.stride +iters = args.iters + +for placement in placements: + print("sudo " + ent_path + " " + results_path + " " + placement + " " + stride + " " + iters) + os.system("sudo " + ent_path + " " + results_path + " " + placement + " " + stride + " " + iters) diff --git a/sources/apps/QUAC-TRNG/scripts/run_vn_nist.py b/sources/apps/QUAC-TRNG/scripts/run_vn_nist.py new file mode 100644 index 0000000..c439da8 --- /dev/null +++ b/sources/apps/QUAC-TRNG/scripts/run_vn_nist.py @@ -0,0 +1,125 @@ +import os +import argparse +import subprocess +import time + +parser = argparse.ArgumentParser(description = "Run this script to evaluate bitstreams") + +parser.add_argument('dimm', help="DIMM label under test") +parser.add_argument('temperature', help="DIMM temperature in centigrades") + +args = parser.parse_args() + +# ---------------- SETUP DIRECTORIES ------------------- + +if not os.path.isdir("data"): + os.mkdir("data") + +if not os.path.isdir("data/" + args.dimm): + os.mkdir("data/" + args.dimm) + +if not os.path.isdir("data/" + args.dimm + "/vnc"): + os.mkdir("data/" + args.dimm + "/vnc") + +if not os.path.isdir("data/" + args.dimm + "/vnc/" + args.temperature + "C"): + os.mkdir("data/" + args.dimm + "/vnc/" + args.temperature + "C") + +if not os.path.isdir("data/" + args.dimm + "/vnc/" + + args.temperature + "C/nist_results"): + os.mkdir("data/" + args.dimm + "/vnc/" + args.temperature + "C/nist_results") + +if not os.path.isdir("data/" + args.dimm + "/vnc/" + + args.temperature + "C/binaries"): + os.mkdir("data/" + args.dimm + "/vnc/" + args.temperature + "C/binaries") + +outdir = os.path.normpath("data/" + args.dimm + "/vnc/" + args.temperature + "C/nist_results") +indir = os.path.normpath("data/" + args.dimm + "/vnc/" + args.temperature + "C/binaries") + +if not os.path.isfile(indir + "/lastrow.txt"): + input("I am going to overwrite 'lastrow.txt', proceed with caution") + init_file = open(indir + "/lastrow.txt", "w") + init_file.write(str(0) + "\n") + +# Hard-reset SoftMC before other experiments +reset_path = os.path.normpath("bin/SoftMC_reset") +reset = subprocess.Popen("exec sudo " + reset_path, shell=True, preexec_fn=os.setpgrp) +time.sleep(5) +os.system("sudo pkill -9 -P" + str(os.getpgid(reset.pid))) +reset.wait() + +# First run OBSERVE to collect von Neumann corrected bitstreams +observe_path = os.path.normpath("bin/OBSERVE " + indir) +observe_args = " > " + os.path.normpath(outdir + "/output.log") +observe = subprocess.Popen("exec sudo " + observe_path + observe_args, shell=True, preexec_fn=os.setpgrp) + +# Watch the bitstream directory for new files +before = ["lastrow.txt"] + +while True: + time.sleep(1) + after = os.listdir(indir) + s = set(before) + diff = [x for x in after if x not in s] + before = after + if len(diff) == 0: + continue + + bitstream = [[] for i in range(8)] # at most 8 STS runs + + # Partition + i = 0 + for fname in diff: + bitstream[i].append(fname) + i = (i+1) % 8 + + found = False + for i in range(len(bitstream[0])): + print("Finished " + str(i) + " out of " + str(len(bitstream[7]))) + processes = [] + for thr in range(0,8): + if len(bitstream[thr]) <= i: + break + command_output = os.path.normpath(outdir + "/thr" + str(thr)) + command_input = os.path.normpath(indir + '/' + bitstream[thr][i]) + command = 'tools/sts -O -i 1 -I 1 -S '+ str(1024*1024) +' -w ' + command_output +' -F r ' + command_input + " 2>/dev/null" + process = subprocess.Popen(command, shell=True) + processes.append(process) + + # Collect statuses + output = [p.wait() for p in processes] + + for thr in range(0,8): + if len(bitstream[thr]) <= i: + break + res_txt = open(os.path.normpath(outdir + '/thr' + str(thr) + '/finalAnalysisReport.txt'), "r") + lines = res_txt.readlines() + n_success = 0 + for j in range(7, len(lines)): + line = lines[j].strip() + if not ("1" in line or "0" in line): + break + split = line.split() + if "/" in split[11]: + n_success += int(split[11].split("/")[0]) + res_txt.close() + print(bitstream[thr][i] + " succeeded in " + str(n_success) + "tests + bits: " + str(1024*1024)) + if n_success < 187: + os.system("rm -f " + indir + "/" + bitstream[thr][i]) + if n_success > 186: + os.system("mkdir " + outdir + "/" + bitstream[thr][i]) + os.system("cp " + outdir + '/thr' + str(thr) + "/finalAnalysisReport.txt " + outdir + "/" + bitstream[thr][i]) + if n_success == 188: + os.system("sudo pkill -9 -P" + str(os.getpgid(observe.pid))) + observe.wait() # wait until the process actually terminates + found = True + if found: + break + +print("Finally found one cell that passes all NIST tests!") + +# Reset SoftMC because last process was killed prematurely +reset_path = os.path.normpath("bin/SoftMC_reset") +reset = subprocess.Popen("exec sudo " + observe_path, shell=True, preexec_fn=os.setpgrp) +time.sleep(5) +os.system("sudo pkill -9 -P" + str(os.getpgid(reset.pid))) +reset.wait() diff --git a/sources/apps/QUAC-TRNG/scripts/sha_bitstreams.py b/sources/apps/QUAC-TRNG/scripts/sha_bitstreams.py new file mode 100644 index 0000000..fd4dbfb --- /dev/null +++ b/sources/apps/QUAC-TRNG/scripts/sha_bitstreams.py @@ -0,0 +1,87 @@ +import os +import argparse +import subprocess +import time + +parser = argparse.ArgumentParser(description = "Collects sha bitstreams for a data pattern") + +parser.add_argument('dimm', help="DIMM label under test") +parser.add_argument('pattern', help="data pattern to use") +parser.add_argument('temperature', help="DIMM temperature in centigrades") + +args = parser.parse_args() + +bitstreams_available = False + +if not os.path.isdir("data/" + args.dimm + "/sha"): + os.mkdir("data/" + args.dimm + "/sha") + +if os.path.isdir("data/" + args.dimm + "/sha/" + args.temperature + "C"): + bitstreams_available = True + +if not os.path.isdir("data/" + args.dimm + "/sha/" + args.temperature + "C"): + os.mkdir("data/" + args.dimm + "/sha/" + args.temperature + "C") + +infile = os.path.normpath("data/" + args.dimm + "/ent/" + args.temperature + "C/top.txt") +outdir = os.path.normpath("data/" + args.dimm + "/sha/" + args.temperature + "C") + +if not os.path.isdir("data/" + args.dimm + "/sha"): + os.mkdir("data/" + args.dimm + "/sha_nist_results") + +if not os.path.isdir("data/" + args.dimm + "/sha/" + args.temperature + "C"): + os.mkdir("data/" + args.dimm + "/sha_nist_results/" + args.temperature + "C") + +sha_output = os.path.normpath("data/" + args.dimm + "/sha_nist_results/" + args.temperature + "C") + +if not bitstreams_available: + sha_path = "bin/SHA" + print("sudo " + sha_path + " " + outdir + " " + infile) + os.system("sudo " + sha_path + " " + outdir + " " + infile) +else: + print("I think we have the bitstreams available, I won't run softmc code again") + +i=0 +bitstream = [] + +for j in range(0,10): + bitstream.append([]) + +for fname in os.listdir(outdir): + bitstream[i].append(fname) + i+=1 + i = i % 10 + +print(bitstream) + +for i in range(len(bitstream[9])): + print("Finished " + str(i) + " out of " + str(len(bitstream[9]))) + processes = [] + for thr in range(0,10): + outpath = os.path.normpath(sha_output+'/thr'+str(thr)) + if not os.path.isdir(outpath): + os.mkdir(outpath) + command = 'tools/sts -O -i 1024 -I 1 -P 11=0.001 -S '+ str(1024*1024) +' -w '+ outpath +' -F r ' + outdir+'/'+bitstream[thr][i] + " 2>/dev/null" + process = subprocess.Popen(command, shell=True) + processes.append(process) + print(command) + + # Collect statuses + output = [p.wait() for p in processes] + + for thr in range(0,10): + outpath = os.path.normpath(sha_output+'/thr'+str(thr)) + res_txt = open(outpath + '/finalAnalysisReport.txt', "r") + lines = res_txt.readlines() + n_success = 0 + for j in range(7, len(lines)): + line = lines[j].strip() + if not ("1" in line or "0" in line): + break + split = line.split() + if "/" in split[11]: + n_success += int(split[11].split("/")[0]) + res_txt.close() + print(bitstream[thr][i] + " succeeded in " + str(n_success) + "tests + bits: " + str(1024*1024)) + if n_success > 186: + os.system("mkdir "+sha_output+"/" + bitstream[thr][i]) + os.system("cp "+sha_output+'/thr'+str(thr)+"/finalAnalysisReport.txt "+sha_output+"/" + bitstream[thr][i]) diff --git a/sources/apps/QUAC-TRNG/scripts/top_ents.py b/sources/apps/QUAC-TRNG/scripts/top_ents.py new file mode 100644 index 0000000..2a74569 --- /dev/null +++ b/sources/apps/QUAC-TRNG/scripts/top_ents.py @@ -0,0 +1,35 @@ +import os +import argparse +import pandas as pd +import numpy as np + +parser = argparse.ArgumentParser(description = "Postprocess entropy files and obtain top-10 segments with the highest entropy") +parser.add_argument('dimm', help="DIMM label") +parser.add_argument('pattern', help="4-bit data pattern [1000, 1001, 0111, etc]") +parser.add_argument('temp', help="temperature in centigrades") +args = parser.parse_args() + +dimm = args.dimm +pattern = args.pattern +temp = args.temp + +no_segments = 8192 +no_bitlines = 512 * 128 + +fn = "data/" + dimm + "/ent/" + temp + "C/1_1000_128_32768_" + pattern + "_floats.bin" +dirname = "data/" + dimm + "/ent/" + temp + "C/" + +arr = np.fromfile(fn, dtype=np.float32) +arr = arr.reshape(no_segments, no_bitlines) +arr = arr.sum(axis = 1) +indices = arr.argsort()[-10:][::-1] +print(indices) +print(arr[indices]) + +log = open(dirname + "top.txt", "w") +log.write("10\n") +for index in indices: + # bank is always 1 + # multiply segment # by 4 to get starting row addr + log.write("1 " + str(int(index) * 4) + " " + str(arr[index]) + " " + pattern + "\n") +log.close() -- cgit v1.2.3