-
Notifications
You must be signed in to change notification settings - Fork 273
Unit-test try_evaluate_pointer_comparison and bugfix #4774
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Unit-test try_evaluate_pointer_comparison and bugfix #4774
Conversation
This is so that we can unit-test this function.
b74ba9d
to
4bf2cd5
Compare
get_l1_object suggests we are comparing the address of the object, but the actually should interpret the symbol itself as a pointer. A unit test for the case of the issue that is fixed will be added in a following commit.
Field sensitivity the value set to keep track of pointers in individal fields, making it possible to evaluate equalities such as the one in the example. This is a case which would not work if try_evaluate_pointer_comparisons was using get_l1_object_identifier instead of getting the identifier of the whole l1 expression (not the underlying object). fixup! Check pointer evaluation in the array case
4bf2cd5
to
017cd09
Compare
src/pointer-analysis/value_set.cpp
Outdated
@@ -1220,7 +1221,8 @@ void value_sett::assign( | |||
std::cout << "--------------------------------------------\n"; | |||
output(ns, std::cout); | |||
#endif | |||
|
|||
PRECONDITION(is_l1_renamed(lhs)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is only true when used in symex-- otherwise we expect to operate on plain un-renamed expressions. Therefore these invariants should move to symex_dereference
or to some wrapper function in goto_statet
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I defined a wrapper class for value_sett
(a wrapper function wouldn't ensure we didn't continue to use the unchecked one)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Great unit tests. Some other edge cases you might want to consider testing: if the value-set contains ID_unknown
, ID_invalid
or a failed symbol then try_evaluate_pointer_comparison
should not be able to determine anything.
b056982
to
2253cbd
Compare
@owen-jones-diffblue I added some cases in the unit test, in particular some with unknown in the value set. |
Btw failed symbols are covered by the regression test that was merged in #4659, I believe. |
src/goto-symex/symex_value_set.h
Outdated
|
||
/// Wrapper for value_sett which ensures we access it in a consistent way. | ||
/// In particular level 1 names should be used. | ||
class symex_value_sett : value_sett |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Generally prefer composition to inheritence
src/goto-symex/goto_symex_state.cpp
Outdated
@@ -222,13 +138,13 @@ renamedt<ssa_exprt, L2> goto_symex_statet::assignment( | |||
ssa_exprt l1_lhs(lhs); | |||
l1_lhs.remove_level_2(); | |||
|
|||
if(run_validation_checks) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
These should still be guarded by if(run_validation_checks)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This PR appears to be doing at least 3 different things (and some of them I believe are wrong, see detailed comments).
src/goto-symex/renamed.cpp
Outdated
@@ -14,9 +14,6 @@ Author: Romain Brenguier, [email protected] | |||
#include <util/std_expr.h> | |||
bool is_l1_renamed(const exprt &expr) | |||
{ | |||
if(!is_l2_renamed(expr.type())) | |||
return false; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The claim made in the commit message seems wrong: the type may well be renamed to L2 even when the object itself is only L1. On the contrary, it actually makes no sense for the type to be renamed to L1 ever.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ok I didn't know that the type could be L2 while the object L1. But is it true that L1 object always have L2 types? It sounds wrong to me. It seems that when an ssa_exprt
is renamed to L1, its type is also renamed to L1.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Renaming to L1 effectively is instantiation/determines which instance of a named object we are using. At that point the type must be complete, i.e., must be L2.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It seems to be the case in symex_decl but not in symex_dereference and the other places where L1 renaming is used. Should we make rename<L1>
apply L2
renaming on the type to ensure this is consistent?
src/pointer-analysis/value_set.cpp
Outdated
@@ -22,6 +22,8 @@ Author: Daniel Kroening, [email protected] | |||
|
|||
#include <langapi/language_util.h> | |||
#include <util/range.h> | |||
#include <util/format_expr.h> | |||
#include <util/format_type.h> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
But then #include <langapi/language_util.h>
better be removed as well (and hopefully also the corresponding entry in module_dependencies.txt
).
src/pointer-analysis/value_set.cpp
Outdated
@@ -20,10 +20,11 @@ Author: Daniel Kroening, [email protected] | |||
#include <util/prefix.h> | |||
#include <util/simplify_expr.h> | |||
|
|||
#include <goto-symex/renamed.h> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't think a dependency from pointer-analysis towards goto-symex is right.
ded9716
to
e26f4cd
Compare
Yes you are right, I extracted what comes after the unit tests and bugfix into a new pull request |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
✔️
Passed Diffblue compatibility checks (cbmc commit: e26f4cd).
Build URL: https://travis-ci.com/diffblue/test-gen/builds/115206278
Codecov Report
@@ Coverage Diff @@
## develop #4774 +/- ##
==========================================
Coverage ? 68.62%
==========================================
Files ? 1276
Lines ? 105155
Branches ? 0
==========================================
Hits ? 72162
Misses ? 32993
Partials ? 0
Continue to review full report at Codecov.
|
This test the case where ptr1 can point to value1 or value2 and we evaluate `ptr1 != &value1`
This check the case where ptr1 is either &value1 or &value2 and we compare it to null.
This adds a unit test for the case where the value set contains unknown. In that case no comparison can be decided.
6f1891d
to
767d8f0
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
✔️
Passed Diffblue compatibility checks (cbmc commit: 767d8f0).
Build URL: https://travis-ci.com/diffblue/test-gen/builds/115226966
This adds some unit test for
try_evaluate_pointer_comparison
, then fix a small bug, and add an unit-test for the case that was buggy, then add some checks for an implicit invariant that I noticed while unit testing, and make value_sett::output more usable in particular for debugging unit tests.