Hi all,
I have a little of experience writing properties and I got weird behavior for a property I consider quite simple…
I have a signal
typedef enum logic {
INPUT_MODE,
OUTPUT_MODE
} i2c_mode_t;
i2c_mode_t i2c_mode;
and I want to check that when this signal switches from INPUT_MODE to OUTPUT_MODE, the i2c_scl signal is 0.
The 1st version I wrote is this one below. I tried to make it has much explicit as possible in order to make it easy to read for someone unexperienced. clk_asrt is a clk of 4ns period
property i2c_switch_mode_p;
@(clk_asrt) disable iff(sva_rst_n === 1'b0)
($changed(i2c_mode) && $past(i2c_mode) == INPUT_MODE && i2c_mode == OUTPUT_MODE)
|->
(i2c_scl === 1'b0);
endproperty: i2c_switch_mode_p
The problem with this one is it passes once at a correct moment but never pass again while it should.
(also, when I modify the consequent into “i2c_scl === 1’b1”, the fail counter increases each time I expect him to increase)
Then I rewrote the property like that:
property i2c_switch_mode_p;
@(posedge clk_asrt) disable iff(sva_rst_n === 1'b0)
(i2c_mode === INPUT_MODE) ##1 (i2c_mode === OUTPUT_MODE)
|->
(i2c_scl === 1'b0)
endproperty: i2c_switch_mode_p
and this time, it works fine. The property passes each time it should.
My question is: What is different from the 2 versions ? Is there something I misunderstood with the use of $changed and/or $past ?
thank you for you help!