0% found this document useful (0 votes)
15 views39 pages

Assertions LECTURE5 V1 1

Uploaded by

vemulasri91
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PPT, PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
15 views39 pages

Assertions LECTURE5 V1 1

Uploaded by

vemulasri91
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PPT, PDF, TXT or read online on Scribd
You are on page 1/ 39

Assertions

Jean-Michel Chabloz
Assertions basic Idea
• We assert that a certain “thing” should be
true.
– If it is true, fine
– If it is false, then we get an error/warning/etc.

• Pieces of code that continuously inspect


the waveforms and signal whenever they
find something strange
SVA
• SVA stands for System Verilog Assertions

• it is almost an independent language,


often taught as stand-alone.

• 150 pages of the LRM (CRSG and


functional coverage are around 50 pages
each)
Immediate assertions
• are found inside procedural code:

initial begin

assert(a==10) else $info(“a is not 10”);

end

• We could do the same check with an “if”


• The only advantages are:
– we can give a name to the assertion, so we can deactivate it, monitor it,
etc.
– it can be inserted into RTL code, the synthesizer will automatically
ignore it (it will not ignore an “if”)
• Immediate assertions are found also in VHDL

• Bottom line: nothing special


Concurrent Assertions
• This is the powerful stuff. It allows us to do
complex checks across many clock cycles.
• has the keyword “property”
• From now on in this lecture we use assertions as
synonym of concurrent assertions

• Example:

checkOnReq: assert property (@(negedge clk) req |->


##2 !req ##1 valid==1) else $error(“error found”);
Failure action
In an assertion we specify what to do when the assertion
fails, because that’s what interests us.

checkOnReq: assert property (@(negedge clk) req |-> ##2 !req ##1
valid==1) else $error(“error found”);

• we could write also what to do when the assertion succeeds, but


normally this is not done because we are interested in the assertion
failures only.

• from now on in these slides we abbreviate


– a.p. (req |-> ##2 !req ##1 valid==1)
• for
– assert property (@(negedge clk) req |-> ##1 !req ##1 valid==1)
Severity level
assert property (…) else
• $fatal(“…”);
– close the simulation, the error was so bad that it is worthless to
continue
• $error(“…”);
– stop the simulation – the user might continue if he so wishes
• $warning(“…”);
– like error, but can be disabled
• $info(“…”);
– just print a message to the console without stopping the
simulation, this was not a real error, just want to print some info
for us
Single-cycle assertions
• Assertions that complete in a single cycle, no
implication.
• assert property (@(negedge clk) cond)
– if cond is false the assertion fails
• variable a should never be 3
– assert property (@(negedge clk) a!=3)

• the value of a is checked on every negative


edge of the clock
• If ever a becomes 3 during the simulation the
assertion will fail
Implication in Single-Cycle
assertions
• If a is one then b must be one
– assert property (@(negedge clk) a |-> b)

• Any alternatives?
Implication in Single-Cycle
assertions
• If a is one then b must be one
– assert property (@(negedge clk) a |-> b)

• Alternatives: accepted (a,b)=(0,0),(0,1),(1,1)

• a.p. (!(a & !b))


• a.p. (!a | b)
• a.p. (!b |-> !a)
Writing assertions
• Often writing assertions consists in
translating the rules in the specs from
english to SVA.
• Pay attention to all the words
Implication in Single-Cycle
assertions
• if cond2, then cond1 must be true
– a.p. (cond2 |-> cond1)

• cond1 can be true only if cond2


– a.p. (cond1 |-> cond2)
– a.p. (!cond2 |-> !cond1);

• If cond2, then cond1 can be true


– same as the last example
Multicycle Assertions
• a.p.(a==2 ##1 a==4)

• a: 2 4 2 2 4
• c: 0 1 2 3 4

• one evaluation attempt is started in every cycle: the assertion fails


as soon as it is determined that it cannot match.

• In cycle 0: matches at 1
• In cycle 1: fails at 1
– at 1 we know the assertion will never match
• In cycle 2: fails at 3
– at 2 we think the assertion may match
– at 3 we realize we were wrong
• In cycle 3: matches at 4
Multicycle assertions
• We normally want to write assertions that are
triggered by something

• a.p.(req |-> ##1 grant)

• one evaluation attempt is started in every cycle


• if the enabling condition is false, then the
attempt is aborted (no failure)
• if the enabling condition matches, then we check
if what is right of the implication matches
Overlapped and non-overlapped
implication
• |-> what is right must start in the same
cycle as what is left ends

• |=> what is right must start one cycle after


what is left ends
– equivalent to: |-> ##1
sampled functions
• $rose(a): a is one and was zero in the past cycle
• $fell(a): a is zero and was one in the past cycle
• $stable(a): a has the same value as in the past
cycle
• $past(a): the value that a had in the past cycle
• $past(a,7): the value that a had 7 cycles ago
sampled functions
•a 0010111101000011001
• $rose(a) 0010100001000010001
• $fell(a) ?001000010100000100
• $stable(a) ?100011100011101010
• $past(a) ?001011110100001100
• $past(a,2) ??00101111010000110
Common error
• check that grant rises three cycles after a request is issued

• g: 0 0 0 0 0 0 0 1 1 1
• r: 0 0 0 0 1 1 1 1 1 1
• c: 0 1 2 3 4 5 6 7 8 9

• a.p. (r |-> ##3 $rose(g)) // wrong

• the assertion will abort immediately at 0,1,2,3 because the enabling


condition doesn’t match
• the enabling condition matches at 4, 5, 6, 7…
• The attempt started at 4 matches at 7
• All other attempts (5, 6, 7, …) fail
Common error
• Grant rises three cycles after a request is issued

• g: 0 0 0 0 0 0 0 1 1 1
• r: 0 0 0 0 1 1 1 1 1 1
• c: 0 1 2 3 4 5 6 7 8 9

• a.p. ($rose(r) |-> ##3 $rose(g)) //good

• the assertion will abort immediately at 0,1,2,3,5,6,7,… because the


enabling condition doesn’t match
• the enabling condition matches at 4
• The attempt started at 4 matches at 7
• No failure
sequence in the enabling condition
• a.p.(a ##1 !a ##1 a |-> ##1 grant ##1 !grant)

• c: 0 1 2 3 4 5 6 7 8 9
• a: 0 1 0 1 0 1 0 0 0 1
• g: 0 0 0 0 1 0 0 0 1 0

• e.a. started at 0: aborted at 0


• e.a. started at 1: matches at 5
• e.a. started at 2: aborted at 2
• e.a. started at 3: fails at 6 (en.cond. matched)
• e.a. started at 4: aborted at 4
• e.a. started at 5: aborted at 7
or
• At least one between two or more sequences
match
• the sequence matches at all times in which at
least one of the two sequences matches

• example: a.p. ($rose(r) |-> (##1 !r) or (##1 g


##1 !g))

• the assertion will match as soon as it is


determined that at least one of the two ORed
sequences matches
or
• a.p. (a ##1 !a ##1 a) or (a##1 !a ##1 !a ##1 a)

• will match both 101 and 1001

• alternative syntax:

• (a ##1 !a [*1:2] ##1 a)


or
• (a ##1 !a [*1:$] ##1 a)
• matches both 101, 1001, 10001, 100001,
etc.

• (a ##1 !a [*0:$] ##1 a)


• matches both 11, 101, 1001, 10001, etc.
and
• Both sequences should match
• Example:
– $rose(r) |-> (!g [*2:$] ##1 g) and (r [*2:$] ##1 !r)
• If request rose, then grant should be zero for at least two
cycles and then go to one; r should remain one for at
least two cycles and then go to zero
• e.a. started at 1 will succeed (at 6) in the following
waveforms (grant sequence matches at 4, req sequence
matches at 6)
• c: 0 1 2 3 4 5 6 7 8 9
• r: 0 1 1 1 1 1 0 0 0 0
• g: 0 0 0 0 1 1 1 1 1 1
intersect
• Both sequences should match at the same time
• Example:
– $rose(r) |-> (!g [*2:$] ##1 g) intersect (r [*2:$] ##1 !r)
• If request rose, then grant should be zero for at least two
cycles and then go to one; r should remain one for at
least two cycles and then go to zero; the time at which r
drops must be the time at which g rises.
• e.a. started at 1 will fail (at 4) in the following waveforms
(grant sequence matches at 4, req sequence matches at
5, at 4 it is determined that the two cannot match in the
same cycle)
• c: 0 1 2 3 4 5 6 7 8 9
• r: 0 1 1 1 1 1 0 0 0 0
• g: 0 0 0 0 1 1 1 1 1 1
ORed enabling sequences
• When a certain sequence happens, then some other
sequence should start

• a ##1 !a [*0:$] ##1 b |-> c ##1 [*0:$] ##1 d

• The sequence after the implication must match every


time the enabling sequence matches

• One evaluation attempt can result into two or more


matches of the enabling condition at different times, the
sequence after the implication should match for all of
them
ORed enabling sequences
• Normally you want to have enabling
sequences that match only once – that
doesn’t mean they can’t be ORed

• Typical example: check that the first time a


rises after reset, cond1 is satisfied
• $rose(reset) ##1 !a [*0:$] ##1 a |-> cond1

• will match only once


ORed enabling sequences
• sequence that match on the first occurrence of a == 1 after b was 1

• b ##1 !a [*0:$] ##1 a

• c: 0 1 2 3 4 5 6 7 8 9
• b: 0 1 0 0 0 0 1 0 0 0
• a: 0 0 0 1 0 1 0 1 1 0

• The evaluation attempt started at 1 matches only at 3, not at 5, 7, 8


• The evaluation attempt started at 6 matches only at 7, not at 8
• all other evaluation attempts fail as soon as they start because b is
not 1
range delay operator
• There is also the operator ##[1:4] - equivalent to ##1 or ##2 or ##3 or ##4
• Can use the $: ##[1:$]
• Easy to make mistakes with it:

• c: 0 1 2 3 4 5 6 7 8 9
• b: 0 1 0 0 0 0 0 0 0 0
• a: 0 0 0 1 0 1 0 1 1 0

• b ##[1:$] a |-> cond1


• The evaluation attempt started at 1 will fail if condition 1 is false at 3, 5, 7, 8… every
time a is 1 after a single issuing of b. After b has become one, the enabling condition
will match every time a is one.

• b ##1 !a [*0:$] ##1 a |-> cond1 is different – The evaluation attempt started at 1 will
fail if condition 1 is false at 3 (first occurrence of a==1 after b). It will not fail if cond1 is
false at 5, 7, 8.

• Recommendation: do not use ##[n:m]– easy to make mistakes with it


Evaluation attempts
• With concurrent assertions, one evaluation attempt is
started in every cycle
• An evaluation attempt will be aborted as soon as it is
determined that the evaluation condition cannot match
• The sequence at the right of the implication sign must
match for all cycles in which the enabling condition
matches
• As soon as it is determined that it is so, the evaluation
attempt succeeds
• As soon as it is determined that it is not so, the
evaluation attempt fails
Evaluation attempts
• Three possible outcomes:
– aborted
– failed
– matched

• By probing the assertions as transactions,


we can see on the waveforms all
evaluation attempts: when they start and
when they match or fail.
Stand-alone sequences
• Sometimes it is efficient to define stand-alone sequences

• sequence s1;
• ##1 b [*0:$] ##1 b;
• endsequence

• sequence s2;
• $fell(b) ##1 !b ##1 b;
• endsequence

• We can then write


– a.p. (s1 |-> ##2 s2)
– a.p. (a==0 |=> s1 or s2)
– a.p. (s1 ##1 s2 |-> a==5)
– 1.p. (s1 and s2 |=> b==1 ##1 b==0)
– etc. etc.

• Good for code reuse and for keeping a good coding style
Internal variables
• The other big advantage of sequences is that they can have local
variables

• sequence s1;
• int cnt;
• (a==1, b=cnt) ##1 !a [*0:$] ##1 (a && b==cnt+1);
• endsequence

• the sequence corresponds to: if a is 1, save the value of b in cnt,


then wait until a rises again and check that b is equal to cnt+1;

• In other words: every time that a is 1, b must be one more


compared to the last time a was 1
Internal variables
• If a is one, then the next time a is one the value of b should be equal to the value that
b had the last time a was one, plus one

• a.p. (a |-> s1)

• sequence s1;
• int cnt;
• (1, cnt=b) ##1 !a *[0:$] ##1 (a & b==cnt+1);
• endsequence

• since in the sequence we want to record the value cnt every time a is one, we don’t
have a condition. But we cannot write
• cnt=b ##1 !a *[0:...
• We always need a condition, in case there is no condition then use the trivial
condition “1”

• You can have multiple assignments:


• (1, cnt=b, cnt2=c)

• Can even have function calls and $display – useful for debugging – example ##1
(a==1, $display(cnt))
throughout
• Often the assertions take the form:
• after r is one, then r will go to zero and
remain at zero for at least one cycle
cycles, then it will raise. Check that cond1
is true for all the cycles in which r is zero

• a.p. (r |-> ##1 !r [*1:$] ##1 r) is the


assertion that checks that r goes to zero
for at least one cycle and then rises.
throughout
• a.p. (r |-> cond1 throughout (##1 !r [*1:$] ##1 r))

• checks that cond1 is true from the cycle in


which r is one to the next cycle in which r
is one included
throughout
• a.p. (r |-> ##1 (cond1 throughout (!r [*1:$] ##1 r)))

• checks that cond1 is true from the cycle in


which r goes to zero to the next cycle in
which r is one included
throughout
• a.p. (r |-> ##1 (cond1 throughout (!r [*1:$])) ##1 r)

• checks that cond1 is true during all the


cycles during which r is zero
Finishing a simulation with
assertions on
• When finishing a simulation with $finish, all
evaluation attempts of the assertions for
which the enabling condition has already
met fail (the implied sequence will not
match because the simulation is ended)

• Good to add $assertkill before $finish, this


kills all ongoing evaluation attempts.

You might also like