OTBN Tracer
The tracer consists of a module (otbn_tracer.sv
) and an interface
(otbn_trace_if.sv
). The interface is responsible for directly probing the
design and implementing any basic tracking logic that is required. The module
takes an instance of this interface and uses it to produce trace data.
Trace output is provided to the simulation environment by calling the
accept_otbn_trace_string
function which is imported via DPI (the simulator
environment provides its implementation). Each call to
accept_otbn_trace_string
provides a trace record and a cycle count. There is
at most one call per cycle. Further details are below.
A typical setup would bind an instantiation of otbn_trace_if
and
otbn_tracer
into otbn_core
passing the otbn_trace_if
instance into the
otbn_tracer
instance. However this is no need for otbn_tracer
to be bound
into otbn_core
provided it is given a otbn_trace_if
instance.
Trace Format
Trace output is generated as a series of records. Every record has zero or more header lines, followed by zero or more body lines. There is no fixed ordering within the header lines or the body lines.
The type of any line can be identified by its first character. The possible types for header lines are as follows:
S
: Instruction stall. An instruction is stalled.E
: Instruction execute. An instruction completed its execution.U
: Wipe in progress. OTBN is in the middle of an internal wipe.V
: Wipe complete. An internal wipe has completed.
The possible types for body lines are:
<
: Register read: A register has been read.>
: Register write: A register has been written.R
: Memory load: A value has been loaded from memory.W
: Memory store: A value has been stored to memory.
See the sections below for details of what information is in the different lines.
A well-formed record has exactly one header line, but it’s possible for the tracer to generate other records if something goes wrong in the design. It is not the tracer’s responsibility to detect bugs; the simulation environment should flag these as errors in a suitable way.
An instruction execution will be represented by zero or more S
records,
followed by one E
record that represents the retirement of the instruction.
The secure wipe phase at the end of OTBN’s operation will be represented by
zero or more U
records, followed by a final V
record.
Whilst the tracer does not aim to detect bugs, there may be instances where the
signals it traces do something unexpected that requires special behaviour.
Where this happens, the string "ERR"
will be placed somewhere in the line
that contains information about the unexpected signals. See information on
Memory Write (W
) lines below for an example. ERR
will not be present in
trace output for any other reason.
Record examples
(The first line of each example illustrates the instruction being traced to aid the example and is not part of the record)
Executing BN.SID x26++, 0(x25)
at PC 0x00000158:
E PC: 0x00000158, insn: 0x01acd08b
< w20: 0x78fccc06_2228e9d6_89c9b54f_887cf14e_c79af825_69be57d4_fecd21a1_b9dd0141
< x25: 0x00000020
< x26: 0x00000014
> x26: 0x00000015
W [0x00000020]: 0x78fccc06_2228e9d6_89c9b54f_887cf14e_c79af825_69be57d4_fecd21a1_b9dd0141
Executing BN.ADD w3, w1, w2
at PC 0x000000e8:
E PC: 0x000000e8, insn: 0x002081ab
< w01: 0x78fccc06_2228e9d6_89c9b54f_887cf14e_c79af825_69be586e_9866bb3b_53769ada
< w02: 0x99999999_99999999_99999999_99999999_99999999_99999999_99999999_99999999
> w03: 0x1296659f_bbc28370_23634ee9_22168ae8_613491bf_0357f208_320054d4_ed103473
> FLAGS0: {C: 1, M: 0, L: 1, Z: 0}
Line formats
Instruction Execute (E
) and Stall (S
) lines
These indicate that an instruction is executing or stalling. An ‘E’ line indicates the instruction completed in the trace record’s cycle. An instruction that is stalled will first produce a record containing an ‘S’ line and will produce a matching ‘E’ line in a future record on the cycle it unstalls and finishes. The line provides the PC and raw instruction bits.
Instruction at 0x0000014c is 0x01800d13 and stalling (a future record will contain a matching ‘E’ line):
S PC: 0x0000014c, insn: 0x01800d13
Instruction at 0x00000150 is 0x01acc10b is executing and will complete:
E PC: 0x00000150, insn: 0x01acc10b
Secure wipe (U
and V
) lines
These indicate that a secure wipe operation is in progress. There is no other
information, so the line consists of a bare U
or V
character.
Register Read (<
) and Write (>
) lines
These show data that has been read or written to either register files or special purpose registers (such as ACC or the bignum side flags). The line provides the register name and the data read/written
Register x26 was read and contained value 0x00000018:
< x26: 0x00000018
Register w24 had value
0xcccccccc_bbbbbbbb_aaaaaaaa_facefeed_deadbeef_cafed00d_d0beb533_1234abcd
written to it:
> w24: 0xcccccccc_bbbbbbbb_aaaaaaaa_facefeed_deadbeef_cafed00d_d0beb533_1234abcd
Accumulator had value
0x00000000_00000000_00311bcb_5e157313_a2fd5453_c7eb58ce_1a1d070d_673963ce
written to it:
> ACC: 0x00000000_00000000_00311bcb_5e157313_a2fd5453_c7eb58ce_1a1d070d_673963ce
Flag group 0 had value {C: 1, M: 1, L: 1, Z: 0}
written to it:
> FLAGS0: {C: 1, M: 1, L: 1, Z: 0}
Memory Read (R
) and Write (W
) lines
These indicate activity on the Dmem bus. The line provides the address and data written/read. For a read the data is always WLEN bits and the address is WLEN aligned (for an execution of LW only a 32-bit chunk of that data is required). For a write the write mask is examined. Where the mask indicates a bignum side write (BN.SID) full WLEN bit data is provided and the address is WLEN aligned. Where the mask indicates a base side write (SW) only 32-bit data is provided and the address is 32-bit aligned (giving the full address of the written chunk).
Address 0x00000040
was read and contained value
0xcccccccc_bbbbbbbb_aaaaaaaa_facefeed_deadbeef_cafed00d_baadf00d_1234abcd
:
R [0x00000040]: 0xcccccccc_bbbbbbbb_aaaaaaaa_facefeed_deadbeef_cafed00d_baadf00d_1234abcd
Address 0x00000004
had value 0xd0beb533
written to it:
W [0x00000004]: 0xd0beb533
In the event of an OTBN bug that produces bad memory masks on writes (where the write is neither to a full 256 bits nor a aligned 32-bit chunk), an error line is produced giving the full mask and data
W [0x00000080]: Mask ERR Mask: 0xfffff800_0000ffff_ffffffff_00000000_00000000_00000000_00000000_00000000 Data: 0xcccccccc_bbbbbbbb_aaaaaaaa_facefeed_deadbeef_cafed00d_baadf00d_1234abcd
Using with dvsim
To use this code, depend on the core file. If you’re using dvsim,
you’ll also need to include otbn_tracer_sim_opts.hjson
in your
simulator configuration and add "{tool}_otbn_tracer_build_opts"
to
the en_build_modes
variable.