summaryrefslogtreecommitdiff
path: root/src/theory/arith
diff options
context:
space:
mode:
authorAndrew Reynolds <andrew.j.reynolds@gmail.com>2021-03-15 14:08:03 -0500
committerGitHub <noreply@github.com>2021-03-15 19:08:03 +0000
commit216f3c9fb07a08909942b91a2a4739cd178f5a72 (patch)
tree00de2d826d1b4ad6124856536923a2463c4d8641 /src/theory/arith
parent6cbb7824dabd7ab8e85472a22ba30ad2498afebc (diff)
Make nonlinear extension account for relevant term set (#6147)
This fixes a subtle issue with non-linear and theory combination. It currently could use irrelevant terms preregistered to the ExtTheory for its model-based refinement. This means that the non-linear extension could accidentally modify values for terms that are not included in its term set, violating theory combination. In particular, in the minimized example from #5662, (* a k) was a stale term in ExtTheory, and non-linear extension falsely believed that a was a term whose model value could be modified, since moreover a was not a shared term. In reality, a was not a shared term since it only was registered to UF. Fixes #5662.
Diffstat (limited to 'src/theory/arith')
-rw-r--r--src/theory/arith/nl/nonlinear_extension.cpp19
-rw-r--r--src/theory/arith/nl/nonlinear_extension.h5
-rw-r--r--src/theory/arith/theory_arith.cpp2
3 files changed, 19 insertions, 7 deletions
diff --git a/src/theory/arith/nl/nonlinear_extension.cpp b/src/theory/arith/nl/nonlinear_extension.cpp
index 671c3f44a..25aebf6d4 100644
--- a/src/theory/arith/nl/nonlinear_extension.cpp
+++ b/src/theory/arith/nl/nonlinear_extension.cpp
@@ -301,7 +301,7 @@ void NonlinearExtension::check(Theory::Effort e)
}
}
-bool NonlinearExtension::modelBasedRefinement()
+bool NonlinearExtension::modelBasedRefinement(const std::set<Node>& termSet)
{
++(d_stats.d_mbrRuns);
d_checkCounter++;
@@ -317,8 +317,18 @@ bool NonlinearExtension::modelBasedRefinement()
Trace("nl-ext") << "# false asserts = " << false_asserts.size() << std::endl;
// get the extended terms belonging to this theory
+ std::vector<Node> xtsAll;
+ d_extTheory.getTerms(xtsAll);
+ // only consider those that are currently relevant based on the current
+ // assertions, i.e. those contained in termSet
std::vector<Node> xts;
- d_extTheory.getTerms(xts);
+ for (const Node& x : xtsAll)
+ {
+ if (termSet.find(x) != termSet.end())
+ {
+ xts.push_back(x);
+ }
+ }
if (Trace.isOn("nl-ext-debug"))
{
@@ -496,7 +506,8 @@ bool NonlinearExtension::modelBasedRefinement()
return false;
}
-void NonlinearExtension::interceptModel(std::map<Node, Node>& arithModel)
+void NonlinearExtension::interceptModel(std::map<Node, Node>& arithModel,
+ const std::set<Node>& termSet)
{
if (!needsCheckLastEffort())
{
@@ -509,7 +520,7 @@ void NonlinearExtension::interceptModel(std::map<Node, Node>& arithModel)
if (!d_builtModel.get())
{
Trace("nl-ext") << "interceptModel: do model-based refinement" << std::endl;
- modelBasedRefinement();
+ modelBasedRefinement(termSet);
}
if (d_builtModel.get())
{
diff --git a/src/theory/arith/nl/nonlinear_extension.h b/src/theory/arith/nl/nonlinear_extension.h
index baa0f886c..09e3a8370 100644
--- a/src/theory/arith/nl/nonlinear_extension.h
+++ b/src/theory/arith/nl/nonlinear_extension.h
@@ -128,7 +128,8 @@ class NonlinearExtension
* arithModel so that it satisfies certain nonlinear constraints. This may
* involve e.g. solving for variables in nonlinear equations.
*/
- void interceptModel(std::map<Node, Node>& arithModel);
+ void interceptModel(std::map<Node, Node>& arithModel,
+ const std::set<Node>& termSet);
/** Does this class need a call to check(...) at last call effort? */
bool needsCheckLastEffort() const { return d_needsLastCall; }
/** presolve
@@ -158,7 +159,7 @@ class NonlinearExtension
* may have information regarding how to construct a model, in the case that
* we determined the problem is satisfiable.
*/
- bool modelBasedRefinement();
+ bool modelBasedRefinement(const std::set<Node>& termSet);
/** get assertions
*
diff --git a/src/theory/arith/theory_arith.cpp b/src/theory/arith/theory_arith.cpp
index 83337dd90..36b2d3eb8 100644
--- a/src/theory/arith/theory_arith.cpp
+++ b/src/theory/arith/theory_arith.cpp
@@ -248,7 +248,7 @@ bool TheoryArith::collectModelValues(TheoryModel* m,
{
// Non-linear may repair values to satisfy non-linear constraints (see
// documentation for NonlinearExtension::interceptModel).
- d_nonlinearExtension->interceptModel(arithModel);
+ d_nonlinearExtension->interceptModel(arithModel, termSet);
}
// We are now ready to assert the model.
for (const std::pair<const Node, Node>& p : arithModel)
generated by cgit on debian on lair
contact matthew@masot.net with questions or feedback