Hi,
So to look into this a bit better myself, I came up with a new script that would walk through the requested ranges. It will also output a CSV log (saved in the active Jupyter directory) for you so that if it crashes you can skip data points on your next go, however, it should be stable for you, as it will attempt to catch crashes and not lose your spot. At the end, it will make you a rejection map to show where you had successes/resets/expected outputs.
I have made the ext-offset a single range but changing that will have some effect. Obviously this is a very time-consuming test so I’d suggest running it overnight.
If it seems setup funny it’s because I was running it outside of Jupyter. I’ve attached the files in case you want to do the same. Note that if you want to cancel it with keyboard interrupts, you might have to try a few times as the error handling is aggressive.
To integrate this into Jupyter do the following:
Underneath the first cell (SCOPETYPE, etc.) insert a new cell with another cell from later in the tutorial:
%%bash -s "$PLATFORM"
cd ../hardware/victims/firmware/glitch-simple
make PLATFORM=$1 CRYPTO_TARGET=NONE FUNC_SEL=GLITCH_INF
Then insert another new cell and paste this in:
from enum import Enum
from tqdm import tnrange
import matplotlib
import matplotlib.pyplot as plt
from collections import namedtuple
import time
import chipwhisperer as cw
import csv
import re
from datetime import datetime
SCOPETYPE = 'OPENADC'
PLATFORM = 'CWLITEARM'
sample_size = 5
if "STM" in PLATFORM or PLATFORM == "CWLITEARM" or PLATFORM == "CWNANO":
prog = cw.programmers.STM32FProgrammer
elif PLATFORM == "CW303" or PLATFORM == "CWLITEXMEGA":
prog = cw.programmers.XMEGAProgrammer
else:
prog = None
try:
if not scope.connectStatus:
scope.con()
except NameError:
scope = cw.scope()
target = cw.target(scope)
try:
if not scope.connectStatus:
scope.con()
except NameError:
scope = cw.scope()
target = cw.target(scope)
SCOPETYPE = 'OPENADC'
PLATFORM = 'CWLITEARM'
sample_size = 5
import time
time.sleep(0.05)
scope.default_setup()
def reset_target(scope):
if PLATFORM == "CW303" or PLATFORM == "CWLITEXMEGA":
scope.io.pdic = 'low'
time.sleep(0.05)
scope.io.pdic = 'high_z' #XMEGA doesn't like pdic driven high
time.sleep(0.05)
else:
scope.io.nrst = 'low'
time.sleep(0.05)
scope.io.nrst = 'high'
time.sleep(0.05)
def setup():
fw_path = "../hardware/victims/firmware/glitch-simple/glitchsimple-{}.hex".format(PLATFORM)
prog = cw.programmers.STM32FProgrammer
scope = cw.scope()
time.sleep(0.05)
scope.default_setup()
reset_target(scope)
print(fw_path)
cw.program_target(scope, prog, fw_path)
def rejection_builder():
Range = namedtuple('Range', ['min', 'max', 'step'])
step_size = (1/512)*100
#step_size = 1
min_value = -49
max_value = min_value*-1
#change the values here:
width_range = Range(min_value, max_value, step_size)
offset_range = Range(min_value, max_value, step_size)
loop_ext_offset = 2185
scope.glitch.ext_offset = loop_ext_offset
loop_ext_max = 2186
dataReset = [[],[]]
dataSuccess = [[],[]]
dataExpected = [[],[]]
print("Starting loop: ")
#starting points
loop_offset = offset_range.min
loop_width = width_range.min
counter = 0
timestr = time.strftime("%Y-%m-%d__%H%M%S")
csv_file_name = 'rejection_builder_log' + timestr + ".csv"
f = open(csv_file_name,'w')
f.write("Time[s],EXT_Offset, Offset, Width, Result, Raw Line \n")
starting_time = datetime.utcnow()
while loop_ext_offset < loop_ext_max:
loop_offset = offset_range.min
while loop_offset < offset_range.max:
loop_width = width_range.min
while loop_width < width_range.max:
time_now = datetime.utcnow()
print("Last run at: {}".format(time_now.strftime("%H:%M:%S")))
date_time_delta = (time_now - starting_time)
seconds_elapsed = str(date_time_delta.total_seconds())
scope.glitch.width = loop_width
scope.glitch.offset = loop_offset
scope.glitch.trigger_src = "ext_single"
scope.glitch.repeat = 9
counter += 1
loop_width += width_range.step
try:
result, line = test_for_success(3)
except:
setup()
if result == Results.Success:
#if counter % 3:
dataSuccess[0].append(loop_offset)
dataSuccess[1].append(loop_width)
print("Loop width: {}, Loop offset: {} Loop ext_offset: {} Result: {} Raw Line: {}" .format(loop_width, loop_offset, loop_ext_offset, result, line))
print("success")
elif result == Results.Expected:
#elif counter % 2:
dataExpected[0].append(loop_offset)
dataExpected[1].append(loop_width)
elif result == Results.Reset:
#else:
dataReset[0].append(loop_offset)
dataReset[1].append(loop_width)
line_list = list(map(str.strip,line))
line = ''.join(line_list)
result_string = str(result).strip("Result.")
f.write("{},{},{},{},{},{}\n".format(seconds_elapsed, loop_ext_max, loop_offset, loop_width, result_string, line))
#print("Loop width: {}, Loop offset: {} Loop ext_offset: {} Result: {}" .format(loop_width, loop_offset, loop_ext_offset, result))
loop_offset += offset_range.step
loop_ext_offset += 1
f.close()
plt.scatter(dataReset[0], dataReset[1], marker='o')
plt.scatter(dataSuccess[0], dataSuccess[1], marker='x')
plt.scatter(dataExpected[0], dataExpected[1], marker='v')
#plt.scatter(dataSuccess[0], dataSuccess[1], 'r--', dataReset[0], dataReset[1], 'bs', dataExpected[0], dataExpected[1], 'g^')
plt.show()
class Results(Enum):
Reset = 0
Expected = 1
Success = 2
# Looks for a gltiched output
# If a success is detected it will break regardless of attempts left
# in order to reduce to a single data point of parameters
def test_for_success(attempts):
reset_target(scope)
target.flush()
time.sleep(1)
scope.arm()
if SCOPETYPE == "OPENADC":
scope.glitch.trigger_src = "ext_continuous"
result = Results.Expected
line = ""
for j in range(attempts):
line = ""
while "\n" not in line:
time.sleep(0.1)
line += target.read()
lines = line.split("\n")
if len(lines) > 1:
line = lines[-1]
else:
line = ""
while "\n" not in line:
time.sleep(0.1)
line += target.read()
if "hello" in line:
result = Results.Reset
nums = line.split(" ")
try:
if (int(nums[0]) != 40000 or int(nums[1]) != 200 or int(nums[2]) != 200 ) and nums[0] != '':
result = Results.Success
break
except ValueError as e:
if(result != Results.Success):
continue
else:
break
if SCOPETYPE == "OPENADC":
scope.glitch.trigger_src = "ext_single"
return result, line
setup()
rejection_builder()
Edit: Added last run on output so you can see if it’s stalled. Also trying in continuous mode
rejection_builder.zip (10.8 KB)