Skip to content

Commit 2139c20

Browse files
author
Leonardo Alt
committed
[SMTChecker] Support delete
1 parent e99efec commit 2139c20

File tree

8 files changed

+151
-0
lines changed

8 files changed

+151
-0
lines changed

Changelog.md

+1
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ Language Features:
77
Compiler Features:
88
* SMTChecker: Support inherited state variables.
99
* SMTChecker: Support tuple assignments and function calls with multiple return values.
10+
* SMTChecker: Support ``delete``.
1011

1112

1213
Bugfixes:

libsolidity/formal/SMTChecker.cpp

+24
Original file line numberDiff line numberDiff line change
@@ -546,6 +546,30 @@ void SMTChecker::endVisit(UnaryOperation const& _op)
546546
);
547547
break;
548548
}
549+
case Token::Delete:
550+
{
551+
auto const& subExpr = _op.subExpression();
552+
if (auto decl = identifierToVariable(subExpr))
553+
{
554+
newValue(*decl);
555+
setZeroValue(*decl);
556+
}
557+
else
558+
{
559+
solAssert(knownExpr(subExpr), "");
560+
auto const& symbVar = m_expressions[&subExpr];
561+
symbVar->increaseIndex();
562+
setZeroValue(*symbVar);
563+
if (dynamic_cast<IndexAccess const*>(&_op.subExpression()))
564+
arrayIndexAssignment(_op.subExpression(), symbVar->currentValue());
565+
else
566+
m_errorReporter.warning(
567+
_op.location(),
568+
"Assertion checker does not yet implement \"delete\" for this expression."
569+
);
570+
}
571+
break;
572+
}
549573
default:
550574
m_errorReporter.warning(
551575
_op.location(),
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
pragma experimental SMTChecker;
2+
3+
contract C
4+
{
5+
uint[] a;
6+
function f(bool b) public {
7+
a[2] = 3;
8+
require(b);
9+
if (b)
10+
delete a;
11+
else
12+
delete a[2];
13+
// Assertion fails as false positive because
14+
// setZeroValue for arrays needs \forall i . a[i] = 0
15+
// which is still unimplemented.
16+
assert(a[2] == 0);
17+
}
18+
}
19+
// ----
20+
// Warning: (118-119): Condition is always true.
21+
// Warning: (297-314): Assertion violation happens here
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
pragma experimental SMTChecker;
2+
3+
contract C
4+
{
5+
uint[][] a;
6+
function f() public {
7+
require(a[2][3] == 4);
8+
delete a;
9+
// Fails as false positive.
10+
// setZeroValue needs forall for arrays.
11+
assert(a[2][3] == 0);
12+
}
13+
}
14+
// ----
15+
// Warning: (194-214): Assertion violation happens here
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
pragma experimental SMTChecker;
2+
3+
contract C
4+
{
5+
uint[] a;
6+
function f(bool b) public {
7+
a[2] = 3;
8+
require(!b);
9+
if (b)
10+
delete a;
11+
else
12+
delete a[2];
13+
assert(a[2] == 0);
14+
}
15+
}
16+
// ----
17+
// Warning: (119-120): Condition is always false.
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
pragma experimental SMTChecker;
2+
3+
contract C
4+
{
5+
uint[][] a;
6+
function f(bool b) public {
7+
require(a[2][3] == 4);
8+
if (b)
9+
delete a;
10+
else
11+
delete a[2];
12+
// Fails as false positive since
13+
// setZeroValue for arrays needs forall
14+
// which is unimplemented.
15+
assert(a[2][3] == 0);
16+
}
17+
}
18+
// ----
19+
// Warning: (266-286): Assertion violation happens here
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
pragma experimental SMTChecker;
2+
3+
contract C
4+
{
5+
uint[] a;
6+
function g() internal {
7+
delete a;
8+
}
9+
function h() internal {
10+
delete a[2];
11+
}
12+
function f(bool b) public {
13+
a[2] = 3;
14+
require(b);
15+
if (b)
16+
g();
17+
else
18+
h();
19+
// Assertion fails as false positive because
20+
// setZeroValue for arrays needs \forall i . a[i] = 0
21+
// which is still unimplemented.
22+
assert(a[2] == 0);
23+
}
24+
}
25+
// ----
26+
// Warning: (201-202): Condition is always true.
27+
// Warning: (367-384): Assertion violation happens here
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
pragma experimental SMTChecker;
2+
3+
contract C
4+
{
5+
struct S
6+
{
7+
uint x;
8+
}
9+
function f(bool b) public {
10+
S memory s;
11+
s.x = 2;
12+
if (b)
13+
delete s;
14+
else
15+
delete s.x;
16+
assert(s.x == 0);
17+
}
18+
}
19+
// ----
20+
// Warning: (73-192): Function state mutability can be restricted to pure
21+
// Warning: (103-113): Assertion checker does not yet support the type of this variable.
22+
// Warning: (117-120): Assertion checker does not yet support this expression.
23+
// Warning: (117-124): Assertion checker does not yet implement such assignments.
24+
// Warning: (165-168): Assertion checker does not yet support this expression.
25+
// Warning: (158-168): Assertion checker does not yet implement "delete" for this expression.
26+
// Warning: (179-182): Assertion checker does not yet support this expression.
27+
// Warning: (172-188): Assertion violation happens here

0 commit comments

Comments
 (0)