How long is the target operation?#
When the capture is triggered by the TIO4
line (as it is in most of our course notebooks), ChipWhisperer measures the number of clock cycles that TIO4
is high for.
You can use this to set scope.adc.samples
to capture the full target operation.
Supported Capture Hardware:
❌ CW-Nano
✅ CW-Lite
✅ CW-Pro
✅ CW-Husky
Required ChipWhisperer software installation:
✅ any release (note: with CW-Lite/Pro on releases 5.7.0 and older, you can run into this issue)
%run '../connect.ipynb'
If your target is running simpleserial-aes
firmware, this will run the target AES operation. For different target firmware, substitute with what’s needed to make your target “go”:
trace = cw.capture_trace(scope, target, bytearray(16), bytearray(16))
Now we can learn how long the trigger was high via scope.adc.trig_count
:
oplen = scope.adc.trig_count
print('Operation length: %d cycles' % oplen)
Operation length: 31864 cycles
scope.adc.trig_count
measures in cycles of the ADC sampling clock, not the target clock.
This means you can directly set scope.adc.samples
:
scope.adc.samples = oplen
⚠️ On CW-Lite, this may exceed the maximum capture size. See “Capturing more samples than the hardware supports” to learn how to get around this problem.
⚠️ A somewhat common misconception is that ChipWhisperer automatically captures samples while the trigger line is high (however long that is). No! ChipWhisperer captures
scope.adc.samples
when it is triggered, independent of how long the trigger is high for. Unless, of course, we setscope.adc.samples
toscope.adc.trig_count
as we did here.
If we repeat the capture and plot it, we can see the 10 AES rounds:
trace = cw.capture_trace(scope, target, bytearray(16), bytearray(16))
cw.plot(trace.wave)
If you’re not convinced, let’s extend the capture to grab an additional 2000 samples before and after the trigger.
In the plot below, the green shaded section illustrates when the trigger was high:
scope.adc.presamples = 2000
scope.adc.samples = oplen + 4000
import holoviews as hv
vspan = hv.VSpan(scope.adc.presamples, scope.adc.presamples+oplen)
trace = cw.capture_trace(scope, target, bytearray(16), bytearray(16))
cw.plot(trace.wave)*vspan.opts(color='green', alpha=0.2)
assert not scope.adc.errors, scope.adc.errors