ASTNode SubstitutionMap::applySubstitutionMap(const ASTNode& n)
{
ASTNodeMap cache;
- return replace(n,*SolverMap,cache,bm->defaultNodeFactory);
+ return replace(n,*SolverMap,cache,bm->defaultNodeFactory, false);
+}
+
+ASTNode SubstitutionMap::applySubstitutionMapUntilArrays(const ASTNode& n)
+{
+ ASTNodeMap cache;
+ return replace(n,*SolverMap,cache,bm->defaultNodeFactory, true);
+}
+
+ASTNode SubstitutionMap::replace(const ASTNode& n, ASTNodeMap& fromTo,
+ ASTNodeMap& cache, NodeFactory * nf)
+{
+ return replace(n,fromTo,cache,nf,false);
}
// NOTE the fromTo map is changed as we traverse downwards.
// will return 5, rather than y.
ASTNode SubstitutionMap::replace(const ASTNode& n, ASTNodeMap& fromTo,
- ASTNodeMap& cache, NodeFactory * nf)
+ ASTNodeMap& cache, NodeFactory * nf, bool stopAtArrays)
{
ASTNodeMap::const_iterator it;
const ASTNode& r = it->second;
assert(r.GetIndexWidth() == n.GetIndexWidth());
assert(BVTypeCheck(r));
- ASTNode replaced = replace(r, fromTo, cache,nf);
+ ASTNode replaced = replace(r, fromTo, cache,nf,stopAtArrays);
if (replaced != r)
fromTo[n] = replaced;
return replaced;
}
- ASTNode replaced = replace(it->second, fromTo, cache,nf);
+ ASTNode replaced = replace(it->second, fromTo, cache,nf,stopAtArrays);
if (replaced != it->second)
fromTo[n] = replaced;
if (n.isConstant() || n.GetKind() == SYMBOL /*|| n.GetKind() == WRITE*/)
return n;
+ if (stopAtArrays && n.GetType() == ARRAY_TYPE)
+ {
+ return n;
+ }
+
ASTVec children;
children.reserve(n.GetChildren().size());
for (unsigned i = 0; i < n.GetChildren().size(); i++)
{
- children.push_back(replace(n[i], fromTo, cache,nf));
+ children.push_back(replace(n[i], fromTo, cache,nf,stopAtArrays));
}
// This code short-cuts if the children are the same. Nodes with the same children,
ASTNode applySubstitutionMap(const ASTNode& n);
+ ASTNode applySubstitutionMapUntilArrays(const ASTNode& n);
+
// Replace any nodes in "n" that exist in the fromTo map.
// NB the fromTo map is changed.
static ASTNode replace(const ASTNode& n, ASTNodeMap& fromTo, ASTNodeMap& cache, NodeFactory *nf);
+
+ static ASTNode replace(const ASTNode& n, ASTNodeMap& fromTo, ASTNodeMap& cache, NodeFactory *nf, bool stopAtArrays);
+
};
}
Simplifying through arrays is very expensive though. I know how to fix it, but
don't have time. Trev.
*/
-
#if 1
- ASTNode aaa =
- (any_solved
- && EQ == it->GetKind()) ?
- _simp->SimplifyFormula_TopLevel(*it, false) :
- *it;
-
+ ASTNode aaa = (any_solved && EQ == it->GetKind()) ? _simp->applySubstitutionMapUntilArrays(*it) : *it;
#else
+ ASTNode aaa = *it;
+ if (any_solved && EQ == aaa.GetKind())
+ {
+ bool found = false;
- ASTNode aaa = *it;
+ ASTNodeSet var;
+ SetofVarsSeenInTerm(aaa[0], var);
- if (any_solved && EQ == aaa.GetKind())
- {
- bool done = false;
- {
- ASTNodeSet lhs;
- SetofVarsSeenInTerm(aaa[0], lhs);
-
- for (ASTNodeSet::const_iterator it = lhs.begin(); it != lhs.end(); it++)
- if (_simp->CheckSubstitutionMap(*it))
- {
- aaa = _simp->applySubstitutionMap(aaa);
- done = true;
- break;
- }
+ for (ASTNodeSet::const_iterator it = var.begin(); it != var.end(); it++)
+ if (_simp->CheckSubstitutionMap(*it))
+ {
+ found = true;
+ break;
}
- if (!done)
+
+ if (!found)
{
- ASTNodeSet rhs;
- SetofVarsSeenInTerm(aaa[1], rhs);
-
- for (ASTNodeSet::const_iterator it = rhs.begin(); it != rhs.end(); it++)
- if (_simp->CheckSubstitutionMap(*it))
- {
- aaa = _simp->applySubstitutionMap(aaa);
- done = true;
- break;
- }
+ var.clear();
+ SetofVarsSeenInTerm(aaa[1], var);
+
+ for (ASTNodeSet::const_iterator it = var.begin(); it != var.end(); it++)
+ if (_simp->CheckSubstitutionMap(*it))
+ {
+ found = true;
+ break;
+ }
}
+ if (found)
+ aaa = _simp->applySubstitutionMapUntilArrays(aaa);
}
+
#endif
+
//_bm->ASTNodeStats("Printing after calling simplifyformula
//inside the solver:", aaa);
aaa = BVSolve_Odd(aaa);
}
}
if (ASTTrue == aaa)
- any_solved=true;
+ {
+ any_solved=true;
+ }
}
ASTNode evens;
output = solveForAndOfXOR(output);
+ // Imagine in the last conjunct A is replaced by B. But there could
+ // be variable A's in the first conjunct. This gets rid of 'em.
+ output = _simp->applySubstitutionMapUntilArrays(output);
+
UpdateAlreadySolvedMap(_input, output);
_bm->GetRunTimes()->stop(RunTimes::BVSolver);
return output;
return substitutionMap.applySubstitutionMap(n);
}
+ ASTNode Simplifier::applySubstitutionMapUntilArrays(const ASTNode& n)
+ {
+ return substitutionMap.applySubstitutionMapUntilArrays(n);
+ }
+
+
bool Simplifier::CheckSubstitutionMap(const ASTNode& key)
{
return substitutionMap.CheckSubstitutionMap(key);
else
output = actualInputterm;
- inputterm = output;
+ inputterm = output;
}
const ASTVec& children = inputterm.GetChildren();
//memoize
UpdateSimplifyMap(inputterm, output, false, VarConstMap);
UpdateSimplifyMap(actualInputterm, output, false, VarConstMap);
+
//cerr << "SimplifyTerm: output" << output << endl;
// CheckSimplifyInvariant(inputterm,output);
- assert(!output.IsNull());
- assert(inputterm.GetValueWidth() == output.GetValueWidth());
- assert(inputterm.GetIndexWidth() == output.GetIndexWidth());
+ assert(!output.IsNull());
+ assert(inputterm.GetValueWidth() == output.GetValueWidth());
+ assert(inputterm.GetIndexWidth() == output.GetIndexWidth());
return output;
} //end of SimplifyTerm()
bool UpdateSubstitutionMap(const ASTNode& e0, const ASTNode& e1);
ASTNode applySubstitutionMap(const ASTNode& n);
+ ASTNode applySubstitutionMapUntilArrays(const ASTNode& n);
void ResetSimplifyMaps(void);