Hi and welcome to SVA.
In my answer i shall assume that you have defined a clock and are using this in your definition of "falling edge"
There are a few issues with your code and problem description. I only enumerate these to help with issues in the future:
- $past is not a macro but a system function
- You are not using the correct SVA implication operator. "->" is a blocking event trigger. The overlapping implication operator I guess you are after is |->
- ##2 $past(y) will actually insert a delay of 2 cycles, and then check that the past value of y was high. Really, you are checking that y is high one cycle after your initial trigger.
I am also not quite sure what your trigger condition is meant to be - x && y will spawn a property thread if both x and y are high. In fact, it won't trigger on a negedge of y.
In the following code I attempt to code up the SVA to your spec as I understood it. You can use a simple function to ensure that preceding n cycle, y was high. Feel free to replace $fell(y) with any trigger as required.
function bit y_high_preceding_n_cycles(int n)
for(int i = 1; i < n; i++) begin
// check if y wasnt high i cycles ago, just return 0
if (!$past(y, i, , @(posedge clk))) return 0;
end
return 1;
endfunction
prop_label: assert property($fell(y) |-> y_high_preceding_n_cycles(n));
This will check that on detection of $fell(y), y was high the preceding n cycles. Note that the iteration of the for loop i==1 will by definition be redundant (as trigger on $fell(y) i.e. definitely $past(y) == 1 holds assuming no Xs).
Hope this helps.