summaryrefslogtreecommitdiff
path: root/src/parser/smt2
diff options
context:
space:
mode:
authorAndrew Reynolds <andrew.j.reynolds@gmail.com>2019-08-12 15:40:26 -0500
committerGitHub <noreply@github.com>2019-08-12 15:40:26 -0500
commiteba03c5af0112aea04d83977333ae37e8a13137d (patch)
treeeefef30537be62f6116a9e99a614049a93fa14b8 /src/parser/smt2
parent75d70649e2d72d6d6bb46f47cf96ee523b718cb9 (diff)
Clean smt2 parsing of named attributes (#3172)
Diffstat (limited to 'src/parser/smt2')
-rw-r--r--src/parser/smt2/Smt2.g59
-rw-r--r--src/parser/smt2/smt2.cpp24
-rw-r--r--src/parser/smt2/smt2.h11
3 files changed, 36 insertions, 58 deletions
diff --git a/src/parser/smt2/Smt2.g b/src/parser/smt2/Smt2.g
index c672d8ff5..a5109361b 100644
--- a/src/parser/smt2/Smt2.g
+++ b/src/parser/smt2/Smt2.g
@@ -150,41 +150,6 @@ using namespace CVC4::parser;
#define SOLVER PARSER_STATE->getSolver()
#define UNSUPPORTED PARSER_STATE->unimplementedFeature
-static bool isClosed(const Expr& e, std::set<Expr>& free, std::unordered_set<Expr, ExprHashFunction>& closedCache) {
- if(closedCache.find(e) != closedCache.end()) {
- return true;
- }
-
- if(e.getKind() == kind::FORALL || e.getKind() == kind::EXISTS || e.getKind() == kind::LAMBDA) {
- isClosed(e[1], free, closedCache);
- for(Expr::const_iterator i = e[0].begin(); i != e[0].end(); ++i) {
- free.erase(*i);
- }
- } else if(e.getKind() == kind::BOUND_VARIABLE) {
- free.insert(e);
- return false;
- } else {
- if(e.hasOperator()) {
- isClosed(e.getOperator(), free, closedCache);
- }
- for(Expr::const_iterator i = e.begin(); i != e.end(); ++i) {
- isClosed(*i, free, closedCache);
- }
- }
-
- if(free.empty()) {
- closedCache.insert(e);
- return true;
- } else {
- return false;
- }
-}
-
-static inline bool isClosed(const Expr& e, std::set<Expr>& free) {
- std::unordered_set<Expr, ExprHashFunction> cache;
- return isClosed(e, free, cache);
-}
-
}/* parser::postinclude */
/**
@@ -2842,30 +2807,8 @@ attribute[CVC4::Expr& expr, CVC4::Expr& retExpr, std::string& attr]
| ATTRIBUTE_NAMED_TOK symbolicExpr[sexpr]
{
attr = std::string(":named");
- if(!sexpr.isKeyword()) {
- PARSER_STATE->parseError("improperly formed :named annotation");
- }
+ Expr func = PARSER_STATE->setNamedAttribute(expr, sexpr);
std::string name = sexpr.getValue();
- PARSER_STATE->checkUserSymbol(name);
- // ensure expr is a closed subterm
- std::set<Expr> freeVars;
- if(!isClosed(expr, freeVars)) {
- assert(!freeVars.empty());
- std::stringstream ss;
- ss << ":named annotations can only name terms that are closed; this "
- << "one contains free variables:";
- for(std::set<Expr>::const_iterator i = freeVars.begin();
- i != freeVars.end(); ++i) {
- ss << " " << *i;
- }
- PARSER_STATE->parseError(ss.str());
- }
- // check that sexpr is a fresh function symbol, and reserve it
- PARSER_STATE->reserveSymbolAtAssertionLevel(name);
- // define it
- Expr func = PARSER_STATE->mkVar(name, expr.getType());
- // remember the last term to have been given a :named attribute
- PARSER_STATE->setLastNamedTerm(expr, name);
// bind name to expr with define-fun
Command* c =
new DefineNamedFunctionCommand(name, func, std::vector<Expr>(), expr);
diff --git a/src/parser/smt2/smt2.cpp b/src/parser/smt2/smt2.cpp
index be0306a9e..d1fb3fe32 100644
--- a/src/parser/smt2/smt2.cpp
+++ b/src/parser/smt2/smt2.cpp
@@ -1566,5 +1566,29 @@ InputLanguage Smt2::getLanguage() const
return em->getOptions().getInputLanguage();
}
+Expr Smt2::setNamedAttribute(Expr& expr, const SExpr& sexpr)
+{
+ if (!sexpr.isKeyword())
+ {
+ parseError("improperly formed :named annotation");
+ }
+ std::string name = sexpr.getValue();
+ checkUserSymbol(name);
+ // ensure expr is a closed subterm
+ if (expr.hasFreeVariable())
+ {
+ std::stringstream ss;
+ ss << ":named annotations can only name terms that are closed";
+ parseError(ss.str());
+ }
+ // check that sexpr is a fresh function symbol, and reserve it
+ reserveSymbolAtAssertionLevel(name);
+ // define it
+ Expr func = mkVar(name, expr.getType());
+ // remember the last term to have been given a :named attribute
+ setLastNamedTerm(expr, name);
+ return func;
+}
+
} // namespace parser
}/* CVC4 namespace */
diff --git a/src/parser/smt2/smt2.h b/src/parser/smt2/smt2.h
index 3afbcd61a..669104954 100644
--- a/src/parser/smt2/smt2.h
+++ b/src/parser/smt2/smt2.h
@@ -425,6 +425,17 @@ class Smt2 : public Parser
}
}
}
+ /** Set named attribute
+ *
+ * This is called when expression expr is annotated with a name, i.e.
+ * (! expr :named sexpr). It sets up the necessary information to process
+ * this naming, including marking that expr is the last named term.
+ *
+ * We construct an expression symbol whose name is the name of s-expression
+ * which is used later for tracking assertions in unsat cores. This
+ * symbol is returned by this method.
+ */
+ Expr setNamedAttribute(Expr& expr, const SExpr& sexpr);
// Throw a ParserException with msg appended with the current logic.
inline void parseErrorLogic(const std::string& msg)
generated by cgit on debian on lair
contact matthew@masot.net with questions or feedback