Skip to content

Commit 35e5313

Browse files
authored
Merge pull request #693 from diffblue/indexed_nexttime
SVA: introduce `sva_indexed_nexttime_exprt` and `sva_indexed_s_nexttime_exprt`
2 parents 4a82eca + 7e3d3bb commit 35e5313

File tree

6 files changed

+117
-60
lines changed

6 files changed

+117
-60
lines changed

src/hw_cbmc_irep_ids.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,7 +43,9 @@ IREP_ID_ONE(sva_s_always)
4343
IREP_ID_ONE(sva_assume)
4444
IREP_ID_ONE(sva_cover)
4545
IREP_ID_ONE(sva_nexttime)
46+
IREP_ID_ONE(sva_indexed_nexttime)
4647
IREP_ID_ONE(sva_s_nexttime)
48+
IREP_ID_ONE(sva_indexed_s_nexttime)
4749
IREP_ID_ONE(sva_eventually)
4850
IREP_ID_ONE(sva_s_eventually)
4951
IREP_ID_ONE(sva_until)

src/temporal-logic/normalize_property.cpp

Lines changed: 14 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -171,21 +171,23 @@ exprt normalize_property(exprt expr)
171171
expr = normalize_pre_sva_or(to_sva_or_expr(expr));
172172
else if(expr.id() == ID_sva_nexttime)
173173
{
174-
auto &nexttime_expr = to_sva_nexttime_expr(expr);
175-
if(nexttime_expr.is_indexed())
176-
expr = sva_ranged_always_exprt{
177-
nexttime_expr.index(), nexttime_expr.index(), nexttime_expr.op()};
178-
else
179-
expr = X_exprt{nexttime_expr.op()};
174+
expr = X_exprt{to_sva_nexttime_expr(expr).op()};
180175
}
181176
else if(expr.id() == ID_sva_s_nexttime)
182177
{
183-
auto &nexttime_expr = to_sva_s_nexttime_expr(expr);
184-
if(nexttime_expr.is_indexed())
185-
expr = sva_s_always_exprt{
186-
nexttime_expr.index(), nexttime_expr.index(), nexttime_expr.op()};
187-
else
188-
expr = X_exprt{to_sva_s_nexttime_expr(expr).op()};
178+
expr = X_exprt{to_sva_s_nexttime_expr(expr).op()};
179+
}
180+
else if(expr.id() == ID_sva_indexed_nexttime)
181+
{
182+
auto &nexttime_expr = to_sva_indexed_nexttime_expr(expr);
183+
expr = sva_ranged_always_exprt{
184+
nexttime_expr.index(), nexttime_expr.index(), nexttime_expr.op()};
185+
}
186+
else if(expr.id() == ID_sva_indexed_s_nexttime)
187+
{
188+
auto &nexttime_expr = to_sva_indexed_s_nexttime_expr(expr);
189+
expr = sva_s_always_exprt{
190+
nexttime_expr.index(), nexttime_expr.index(), nexttime_expr.op()};
189191
}
190192
else if(expr.id() == ID_sva_cycle_delay)
191193
expr = normalize_pre_sva_cycle_delay(to_sva_cycle_delay_expr(expr));

src/verilog/expr2verilog.cpp

Lines changed: 13 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1499,16 +1499,25 @@ expr2verilogt::resultt expr2verilogt::convert_rec(const exprt &src)
14991499

15001500
else if(src.id()==ID_sva_nexttime)
15011501
return precedence = verilog_precedencet::MIN,
1502-
convert_sva_indexed_binary("nexttime", to_sva_nexttime_expr(src));
1502+
convert_sva_unary("nexttime", to_sva_nexttime_expr(src));
15031503

1504-
else if(src.id() == ID_sva_disable_iff)
1504+
else if(src.id() == ID_sva_indexed_nexttime)
15051505
return precedence = verilog_precedencet::MIN,
1506-
convert_sva_abort("disable iff", to_sva_abort_expr(src));
1506+
convert_sva_indexed_binary(
1507+
"nexttime", to_sva_indexed_nexttime_expr(src));
15071508

15081509
else if(src.id()==ID_sva_s_nexttime)
1510+
return precedence = verilog_precedencet::MIN,
1511+
convert_sva_unary("s_nexttime", to_sva_s_nexttime_expr(src));
1512+
1513+
else if(src.id() == ID_sva_indexed_s_nexttime)
15091514
return precedence = verilog_precedencet::MIN,
15101515
convert_sva_indexed_binary(
1511-
"s_nexttime", to_sva_s_nexttime_expr(src));
1516+
"s_nexttime", to_sva_indexed_s_nexttime_expr(src));
1517+
1518+
else if(src.id() == ID_sva_disable_iff)
1519+
return precedence = verilog_precedencet::MIN,
1520+
convert_sva_abort("disable iff", to_sva_abort_expr(src));
15121521

15131522
else if(src.id()==ID_sva_eventually)
15141523
{

src/verilog/parser.y

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2179,13 +2179,13 @@ property_expr_proper:
21792179
| sequence_expr "#=#" property_expr
21802180
{ init($$, ID_sva_nonoverlapped_followed_by); mto($$, $1); mto($$, $3); }
21812181
| "nexttime" property_expr
2182-
{ init($$, "sva_nexttime"); stack_expr($$).add_to_operands(nil_exprt()); mto($$, $2); }
2182+
{ init($$, "sva_nexttime"); mto($$, $2); }
21832183
| "nexttime" '[' constant_expression ']' property_expr %prec "nexttime"
2184-
{ init($$, "sva_nexttime"); mto($$, $3); mto($$, $5); }
2184+
{ init($$, "sva_indexed_nexttime"); mto($$, $3); mto($$, $5); }
21852185
| "s_nexttime" property_expr
2186-
{ init($$, "sva_s_nexttime"); stack_expr($$).add_to_operands(nil_exprt()); mto($$, $2); }
2186+
{ init($$, "sva_s_nexttime"); mto($$, $2); }
21872187
| "s_nexttime" '[' constant_expression ']' property_expr %prec "s_nexttime"
2188-
{ init($$, "sva_s_nexttime"); mto($$, $3); mto($$, $5); }
2188+
{ init($$, "sva_indexed_s_nexttime"); mto($$, $3); mto($$, $5); }
21892189
| "always" '[' cycle_delay_const_range_expression ']' property_expr %prec "always"
21902190
{ init($$, ID_sva_ranged_always); swapop($$, $3); mto($$, $5); }
21912191
| "always" property_expr

src/verilog/sva_expr.h

Lines changed: 76 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -84,18 +84,62 @@ static inline sva_disable_iff_exprt &to_sva_disable_iff_expr(exprt &expr)
8484
return static_cast<sva_disable_iff_exprt &>(expr);
8585
}
8686

87-
class sva_nexttime_exprt : public binary_predicate_exprt
87+
/// nonindexed variant
88+
class sva_nexttime_exprt : public unary_predicate_exprt
8889
{
8990
public:
90-
// nonindexed variant
9191
explicit sva_nexttime_exprt(exprt op)
92-
: binary_predicate_exprt(nil_exprt(), ID_sva_nexttime, std::move(op))
92+
: unary_predicate_exprt(ID_sva_nexttime, std::move(op))
9393
{
9494
}
95+
};
96+
97+
static inline const sva_nexttime_exprt &to_sva_nexttime_expr(const exprt &expr)
98+
{
99+
PRECONDITION(expr.id() == ID_sva_nexttime);
100+
sva_nexttime_exprt::check(expr, validation_modet::INVARIANT);
101+
return static_cast<const sva_nexttime_exprt &>(expr);
102+
}
103+
104+
static inline sva_nexttime_exprt &to_sva_nexttime_expr(exprt &expr)
105+
{
106+
PRECONDITION(expr.id() == ID_sva_nexttime);
107+
sva_nexttime_exprt::check(expr, validation_modet::INVARIANT);
108+
return static_cast<sva_nexttime_exprt &>(expr);
109+
}
110+
111+
/// nonindexed variant
112+
class sva_s_nexttime_exprt : public unary_predicate_exprt
113+
{
114+
public:
115+
explicit sva_s_nexttime_exprt(exprt op)
116+
: unary_predicate_exprt(ID_sva_s_nexttime, std::move(op))
117+
{
118+
}
119+
};
120+
121+
static inline const sva_s_nexttime_exprt &
122+
to_sva_s_nexttime_expr(const exprt &expr)
123+
{
124+
PRECONDITION(expr.id() == ID_sva_s_nexttime);
125+
sva_s_nexttime_exprt::check(expr, validation_modet::INVARIANT);
126+
return static_cast<const sva_s_nexttime_exprt &>(expr);
127+
}
128+
129+
static inline sva_s_nexttime_exprt &to_sva_s_nexttime_expr(exprt &expr)
130+
{
131+
PRECONDITION(expr.id() == ID_sva_s_nexttime);
132+
sva_s_nexttime_exprt::check(expr, validation_modet::INVARIANT);
133+
return static_cast<sva_s_nexttime_exprt &>(expr);
134+
}
95135

96-
bool is_indexed() const
136+
/// indexed variant of sva_nexttime_exprt
137+
class sva_indexed_nexttime_exprt : public binary_predicate_exprt
138+
{
139+
public:
140+
sva_indexed_nexttime_exprt(exprt index, exprt op)
141+
: binary_predicate_exprt(std::move(index), ID_sva_nexttime, std::move(op))
97142
{
98-
return index().is_not_nil();
99143
}
100144

101145
const exprt &index() const
@@ -123,32 +167,32 @@ class sva_nexttime_exprt : public binary_predicate_exprt
123167
using binary_predicate_exprt::op1;
124168
};
125169

126-
static inline const sva_nexttime_exprt &to_sva_nexttime_expr(const exprt &expr)
170+
static inline const sva_indexed_nexttime_exprt &
171+
to_sva_indexed_nexttime_expr(const exprt &expr)
127172
{
128-
PRECONDITION(expr.id() == ID_sva_nexttime);
129-
sva_nexttime_exprt::check(expr, validation_modet::INVARIANT);
130-
return static_cast<const sva_nexttime_exprt &>(expr);
173+
PRECONDITION(expr.id() == ID_sva_indexed_nexttime);
174+
sva_indexed_nexttime_exprt::check(expr, validation_modet::INVARIANT);
175+
return static_cast<const sva_indexed_nexttime_exprt &>(expr);
131176
}
132177

133-
static inline sva_nexttime_exprt &to_sva_nexttime_expr(exprt &expr)
178+
static inline sva_indexed_nexttime_exprt &
179+
to_sva_indexed_nexttime_expr(exprt &expr)
134180
{
135-
PRECONDITION(expr.id() == ID_sva_nexttime);
136-
sva_nexttime_exprt::check(expr, validation_modet::INVARIANT);
137-
return static_cast<sva_nexttime_exprt &>(expr);
181+
PRECONDITION(expr.id() == ID_sva_indexed_nexttime);
182+
sva_indexed_nexttime_exprt::check(expr, validation_modet::INVARIANT);
183+
return static_cast<sva_indexed_nexttime_exprt &>(expr);
138184
}
139185

140-
class sva_s_nexttime_exprt : public binary_predicate_exprt
186+
/// indexed variant of sva_s_nexttime_exprt
187+
class sva_indexed_s_nexttime_exprt : public binary_predicate_exprt
141188
{
142189
public:
143-
// nonindexed variant
144-
explicit sva_s_nexttime_exprt(exprt op)
145-
: binary_predicate_exprt(nil_exprt(), ID_sva_s_nexttime, std::move(op))
146-
{
147-
}
148-
149-
bool is_indexed() const
190+
sva_indexed_s_nexttime_exprt(exprt index, exprt op)
191+
: binary_predicate_exprt(
192+
std::move(index),
193+
ID_sva_indexed_s_nexttime,
194+
std::move(op))
150195
{
151-
return index().is_not_nil();
152196
}
153197

154198
const exprt &index() const
@@ -176,19 +220,20 @@ class sva_s_nexttime_exprt : public binary_predicate_exprt
176220
using binary_predicate_exprt::op1;
177221
};
178222

179-
static inline const sva_s_nexttime_exprt &
180-
to_sva_s_nexttime_expr(const exprt &expr)
223+
static inline const sva_indexed_s_nexttime_exprt &
224+
to_sva_indexed_s_nexttime_expr(const exprt &expr)
181225
{
182-
PRECONDITION(expr.id() == ID_sva_s_nexttime);
183-
sva_s_nexttime_exprt::check(expr, validation_modet::INVARIANT);
184-
return static_cast<const sva_s_nexttime_exprt &>(expr);
226+
PRECONDITION(expr.id() == ID_sva_indexed_s_nexttime);
227+
sva_indexed_s_nexttime_exprt::check(expr, validation_modet::INVARIANT);
228+
return static_cast<const sva_indexed_s_nexttime_exprt &>(expr);
185229
}
186230

187-
static inline sva_s_nexttime_exprt &to_sva_s_nexttime_expr(exprt &expr)
231+
static inline sva_indexed_s_nexttime_exprt &
232+
to_sva_indexed_s_nexttime_expr(exprt &expr)
188233
{
189-
PRECONDITION(expr.id() == ID_sva_s_nexttime);
190-
sva_s_nexttime_exprt::check(expr, validation_modet::INVARIANT);
191-
return static_cast<sva_s_nexttime_exprt &>(expr);
234+
PRECONDITION(expr.id() == ID_sva_indexed_s_nexttime);
235+
sva_indexed_s_nexttime_exprt::check(expr, validation_modet::INVARIANT);
236+
return static_cast<sva_indexed_s_nexttime_exprt &>(expr);
192237
}
193238

194239
class sva_ranged_predicate_exprt : public ternary_exprt

src/verilog/verilog_typecheck_expr.cpp

Lines changed: 8 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2405,7 +2405,8 @@ exprt verilog_typecheck_exprt::convert_unary_expr(unary_exprt expr)
24052405
expr.id() == ID_sva_always || expr.id() == ID_sva_s_eventually ||
24062406
expr.id() == ID_sva_cycle_delay_plus ||
24072407
expr.id() == ID_sva_cycle_delay_star || expr.id() == ID_sva_weak ||
2408-
expr.id() == ID_sva_strong)
2408+
expr.id() == ID_sva_strong || expr.id() == ID_sva_nexttime ||
2409+
expr.id() == ID_sva_s_nexttime)
24092410
{
24102411
convert_expr(expr.op());
24112412
make_boolean(expr.op());
@@ -2821,24 +2822,22 @@ exprt verilog_typecheck_exprt::convert_binary_expr(binary_exprt expr)
28212822
expr.type() = bool_typet();
28222823
return std::move(expr);
28232824
}
2824-
else if(expr.id() == ID_sva_nexttime)
2825+
else if(expr.id() == ID_sva_indexed_nexttime)
28252826
{
2826-
if(to_sva_nexttime_expr(expr).is_indexed())
2827-
convert_expr(to_sva_nexttime_expr(expr).index());
2827+
convert_expr(to_sva_indexed_nexttime_expr(expr).index());
28282828

2829-
auto &op = to_sva_nexttime_expr(expr).op();
2829+
auto &op = to_sva_indexed_nexttime_expr(expr).op();
28302830
convert_expr(op);
28312831
make_boolean(op);
28322832
expr.type() = bool_typet();
28332833

28342834
return std::move(expr);
28352835
}
2836-
else if(expr.id() == ID_sva_s_nexttime)
2836+
else if(expr.id() == ID_sva_indexed_s_nexttime)
28372837
{
2838-
if(to_sva_s_nexttime_expr(expr).is_indexed())
2839-
convert_expr(to_sva_s_nexttime_expr(expr).index());
2838+
convert_expr(to_sva_indexed_s_nexttime_expr(expr).index());
28402839

2841-
auto &op = to_sva_s_nexttime_expr(expr).op();
2840+
auto &op = to_sva_indexed_s_nexttime_expr(expr).op();
28422841
convert_expr(op);
28432842
make_boolean(op);
28442843
expr.type() = bool_typet();

0 commit comments

Comments
 (0)