From: Andrew Reynolds Date: Thu, 5 Mar 2020 22:16:15 +0000 (-0600) Subject: Migrate a majority of the functionality in parsers to the new API (#3838) X-Git-Tag: cvc5-1.0.0~3563 X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=500f85f9c664001b84a90f4836bbb9577b871e29;p=cvc5.git Migrate a majority of the functionality in parsers to the new API (#3838) This PR migrates a majority of the functionality of the parsers (cvc, tptp, smt2/sygus) to the new API. The main omitted functionality not addressed in this PR is the datatypes. Largely, the Expr-level Datatype is still used throughout. Remaining tasks: Migrate the Datatypes to the new API in cvc/smt2. Eliminate the use of ExprManager::mkVar (with flags for DEFINED/GLOBAL). For the latter, I have made a utility function in Parser::mkVar that captures all calls to this function. Notice that the existing mkVar/mkBoundVar/mkDefinedFun have been renamed to the more fitting names bindVar/bindBoundVar/bindDefinedFun etc. Note: this PR contains no major code changes, each line of code should roughly correspond one-to-one with the changed version. This fixes CVC4/cvc4-projects#77, fixes CVC4/cvc4-projects#78, fixes CVC4/cvc4-projects#80, fixes CVC4/cvc4-projects#85. --- diff --git a/examples/nra-translate/smt2toisat.cpp b/examples/nra-translate/smt2toisat.cpp index 34745ad03..cf6377d98 100644 --- a/examples/nra-translate/smt2toisat.cpp +++ b/examples/nra-translate/smt2toisat.cpp @@ -73,7 +73,7 @@ int main(int argc, char* argv[]) DeclareFunctionCommand* declare = dynamic_cast(cmd); if (declare) { string name = declare->getSymbol(); - Expr var = parser->getVariable(name); + Expr var = parser->getVariable(name).getExpr(); unsigned n = variables.size(); variables[var] = n; delete cmd; diff --git a/examples/nra-translate/smt2tomathematica.cpp b/examples/nra-translate/smt2tomathematica.cpp index c5c2f3af4..916ada0d9 100644 --- a/examples/nra-translate/smt2tomathematica.cpp +++ b/examples/nra-translate/smt2tomathematica.cpp @@ -72,7 +72,7 @@ int main(int argc, char* argv[]) DeclareFunctionCommand* declare = dynamic_cast(cmd); if (declare) { string name = declare->getSymbol(); - Expr var = parser->getVariable(name); + Expr var = parser->getVariable(name).getExpr(); unsigned n = variables.size(); variables[var] = n; delete cmd; diff --git a/examples/nra-translate/smt2toqepcad.cpp b/examples/nra-translate/smt2toqepcad.cpp index cdc2e0878..2750ee191 100644 --- a/examples/nra-translate/smt2toqepcad.cpp +++ b/examples/nra-translate/smt2toqepcad.cpp @@ -74,7 +74,7 @@ int main(int argc, char* argv[]) dynamic_cast(cmd); if (declare) { string name = declare->getSymbol(); - Expr var = parser->getVariable(name); + Expr var = parser->getVariable(name).getExpr(); unsigned n = variables.size(); variables[var] = n; delete cmd; diff --git a/examples/nra-translate/smt2toredlog.cpp b/examples/nra-translate/smt2toredlog.cpp index 654a6a038..638f7c452 100644 --- a/examples/nra-translate/smt2toredlog.cpp +++ b/examples/nra-translate/smt2toredlog.cpp @@ -76,7 +76,7 @@ int main(int argc, char* argv[]) DeclareFunctionCommand* declare = dynamic_cast(cmd); if (declare) { string name = declare->getSymbol(); - Expr var = parser->getVariable(name); + Expr var = parser->getVariable(name).getExpr(); unsigned n = variables.size(); variables[var] = n; delete cmd; diff --git a/src/api/cvc4cpp.cpp b/src/api/cvc4cpp.cpp index 0d24139e8..63ebdbea6 100644 --- a/src/api/cvc4cpp.cpp +++ b/src/api/cvc4cpp.cpp @@ -2410,7 +2410,8 @@ Term Solver::mkTermInternal(Kind kind, const std::vector& children) const std::vector echildren = termVectorToExprs(children); CVC4::Kind k = extToIntKind(kind); - Assert(isDefinedIntKind(k)); + Assert(isDefinedIntKind(k)) + << "Not a defined internal kind : " << k << " " << kind; Term res; if (echildren.size() > 2) @@ -2988,7 +2989,7 @@ Term Solver::mkConstArray(Sort sort, Term val) const CVC4_API_SOLVER_TRY_CATCH_BEGIN; CVC4_API_ARG_CHECK_NOT_NULL(val); CVC4_API_CHECK(sort.isArray()) << "Not an array sort."; - CVC4_API_CHECK(sort.getArrayElementSort() == val.getSort()) + CVC4_API_CHECK(sort.getArrayElementSort().isComparableTo(val.getSort())) << "Value does not match element sort."; Term res = mkValHelper( CVC4::ArrayStoreAll(*sort.d_type, *val.d_expr)); diff --git a/src/parser/CMakeLists.txt b/src/parser/CMakeLists.txt index 77a9ba053..393b1597a 100644 --- a/src/parser/CMakeLists.txt +++ b/src/parser/CMakeLists.txt @@ -32,6 +32,7 @@ set(libcvc4parser_src_files line_buffer.h memory_mapped_input_buffer.cpp memory_mapped_input_buffer.h + parse_op.cpp parse_op.h parser.cpp parser.h diff --git a/src/parser/cvc/Cvc.g b/src/parser/cvc/Cvc.g index 637603997..ffdef5ba2 100644 --- a/src/parser/cvc/Cvc.g +++ b/src/parser/cvc/Cvc.g @@ -109,7 +109,7 @@ tokens { SUBTYPE_TOK = 'SUBTYPE'; SET_TOK = 'SET'; - + TUPLE_TOK = 'TUPLE'; FORALL_TOK = 'FORALL'; @@ -203,14 +203,14 @@ tokens { BVSGT_TOK = 'BVSGT'; BVSLE_TOK = 'BVSLE'; BVSGE_TOK = 'BVSGE'; - + // Relations JOIN_TOK = 'JOIN'; TRANSPOSE_TOK = 'TRANSPOSE'; PRODUCT_TOK = 'PRODUCT'; TRANSCLOSURE_TOK = 'TCLOSURE'; IDEN_TOK = 'IDEN'; - JOIN_IMAGE_TOK = 'JOIN_IMAGE'; + JOIN_IMAGE_TOK = 'JOIN_IMAGE'; // Strings STRING_TOK = 'STRING'; @@ -241,9 +241,9 @@ tokens { REGEXP_EMPTY_TOK = 'RE_EMPTY'; REGEXP_SIGMA_TOK = 'RE_SIGMA'; REGEXP_COMPLEMENT_TOK = 'RE_COMPLEMENT'; - + SETS_CARD_TOK = 'CARD'; - + FMF_CARD_TOK = 'HAS_CARD'; UNIVSET_TOK = 'UNIVERSE'; @@ -325,13 +325,13 @@ int getOperatorPrecedence(int type) { case TRANSPOSE_TOK: case PRODUCT_TOK: case IDEN_TOK: - case JOIN_IMAGE_TOK: + case JOIN_IMAGE_TOK: case TRANSCLOSURE_TOK: return 24; case LEQ_TOK: case LT_TOK: case GEQ_TOK: case GT_TOK: - case MEMBER_TOK: + case MEMBER_TOK: case SETS_CARD_TOK: case FMF_CARD_TOK: return 25; case EQUAL_TOK: @@ -354,46 +354,46 @@ int getOperatorPrecedence(int type) { } }/* getOperatorPrecedence() */ -Kind getOperatorKind(int type, bool& negate) { +api::Kind getOperatorKind(int type, bool& negate) { negate = false; switch(type) { // booleanBinop - case IFF_TOK: return kind::EQUAL; - case IMPLIES_TOK: return kind::IMPLIES; - case OR_TOK: return kind::OR; - case XOR_TOK: return kind::XOR; - case AND_TOK: return kind::AND; - - case PRODUCT_TOK: return kind::PRODUCT; - case JOIN_TOK: return kind::JOIN; - case JOIN_IMAGE_TOK: return kind::JOIN_IMAGE; + case IFF_TOK: return api::EQUAL; + case IMPLIES_TOK: return api::IMPLIES; + case OR_TOK: return api::OR; + case XOR_TOK: return api::XOR; + case AND_TOK: return api::AND; + + case PRODUCT_TOK: return api::PRODUCT; + case JOIN_TOK: return api::JOIN; + case JOIN_IMAGE_TOK: return api::JOIN_IMAGE; // comparisonBinop - case EQUAL_TOK: return kind::EQUAL; - case DISEQUAL_TOK: negate = true; return kind::EQUAL; - case GT_TOK: return kind::GT; - case GEQ_TOK: return kind::GEQ; - case LT_TOK: return kind::LT; - case LEQ_TOK: return kind::LEQ; - case MEMBER_TOK: return kind::MEMBER; - case SETS_CARD_TOK: return kind::CARD; - case FMF_CARD_TOK: return kind::CARDINALITY_CONSTRAINT; + case EQUAL_TOK: return api::EQUAL; + case DISEQUAL_TOK: negate = true; return api::EQUAL; + case GT_TOK: return api::GT; + case GEQ_TOK: return api::GEQ; + case LT_TOK: return api::LT; + case LEQ_TOK: return api::LEQ; + case MEMBER_TOK: return api::MEMBER; + case SETS_CARD_TOK: return api::CARD; + case FMF_CARD_TOK: return api::CARDINALITY_CONSTRAINT; // arithmeticBinop - case PLUS_TOK: return kind::PLUS; - case MINUS_TOK: return kind::MINUS; - case STAR_TOK: return kind::MULT; - case INTDIV_TOK: return kind::INTS_DIVISION; - case MOD_TOK: return kind::INTS_MODULUS; - case DIV_TOK: return kind::DIVISION; - case EXP_TOK: return kind::POW; + case PLUS_TOK: return api::PLUS; + case MINUS_TOK: return api::MINUS; + case STAR_TOK: return api::MULT; + case INTDIV_TOK: return api::INTS_DIVISION; + case MOD_TOK: return api::INTS_MODULUS; + case DIV_TOK: return api::DIVISION; + case EXP_TOK: return api::POW; // bvBinop - case CONCAT_TOK: return kind::BITVECTOR_CONCAT; - case BAR: return kind::BITVECTOR_OR; - case BVAND_TOK: return kind::BITVECTOR_AND; - + case CONCAT_TOK: return api::BITVECTOR_CONCAT; + case BAR: return api::BITVECTOR_OR; + case BVAND_TOK: return api::BITVECTOR_AND; + } std::stringstream ss; @@ -423,8 +423,8 @@ unsigned findPivot(const std::vector& operators, return pivot; }/* findPivot() */ -Expr createPrecedenceTree(Parser* parser, ExprManager* em, - const std::vector& expressions, +CVC4::api::Term createPrecedenceTree(Parser* parser, api::Solver* solver, + const std::vector& expressions, const std::vector& operators, unsigned startIndex, unsigned stopIndex) { assert(expressions.size() == operators.size() + 1); @@ -439,36 +439,38 @@ Expr createPrecedenceTree(Parser* parser, ExprManager* em, unsigned pivot = findPivot(operators, startIndex, stopIndex - 1); //Debug("prec") << "pivot[" << startIndex << "," << stopIndex - 1 << "] at " << pivot << std::endl; bool negate; - Kind k = getOperatorKind(operators[pivot], negate); - Expr lhs = createPrecedenceTree(parser, em, expressions, operators, startIndex, pivot); - Expr rhs = createPrecedenceTree(parser, em, expressions, operators, pivot + 1, stopIndex); + api::Kind k = getOperatorKind(operators[pivot], negate); + CVC4::api::Term lhs = createPrecedenceTree( + parser, solver, expressions, operators, startIndex, pivot); + CVC4::api::Term rhs = createPrecedenceTree( + parser, solver, expressions, operators, pivot + 1, stopIndex); - if (lhs.getType().isSet()) + if (lhs.getSort().isSet()) { switch (k) { - case kind::LEQ: k = kind::SUBSET; break; - case kind::MINUS: k = kind::SETMINUS; break; - case kind::BITVECTOR_AND: k = kind::INTERSECTION; break; - case kind::BITVECTOR_OR: k = kind::UNION; break; + case api::LEQ: k = api::SUBSET; break; + case api::MINUS: k = api::SETMINUS; break; + case api::BITVECTOR_AND: k = api::INTERSECTION; break; + case api::BITVECTOR_OR: k = api::UNION; break; default: break; } } - else if (lhs.getType().isString()) + else if (lhs.getSort().isString()) { switch (k) { - case kind::MEMBER: k = kind::STRING_IN_REGEXP; break; + case api::MEMBER: k = api::STRING_IN_REGEXP; break; default: break; } } - Expr e = em->mkExpr(k, lhs, rhs); - return negate ? em->mkExpr(kind::NOT, e) : e; + api::Term e = solver->mkTerm(k, lhs, rhs); + return negate ? e.notTerm() : e; }/* createPrecedenceTree() recursive variant */ -Expr createPrecedenceTree(Parser* parser, ExprManager* em, - const std::vector& expressions, +api::Term createPrecedenceTree(Parser* parser, api::Solver* s, + const std::vector& expressions, const std::vector& operators) { if(Debug.isOn("prec") && operators.size() > 1) { for(unsigned i = 0; i < expressions.size(); ++i) { @@ -480,7 +482,8 @@ Expr createPrecedenceTree(Parser* parser, ExprManager* em, Debug("prec") << std::endl; } - Expr e = createPrecedenceTree(parser, em, expressions, operators, 0, expressions.size() - 1); + api::Term e = createPrecedenceTree( + parser, s, expressions, operators, 0, expressions.size() - 1); if(Debug.isOn("prec") && operators.size() > 1) { language::SetLanguage::Scope ls(Debug("prec"), language::output::LANG_AST); Debug("prec") << "=> " << e << std::endl; @@ -489,9 +492,9 @@ Expr createPrecedenceTree(Parser* parser, ExprManager* em, }/* createPrecedenceTree() base variant */ /** Add n NOTs to the front of e and return the result. */ -Expr addNots(ExprManager* em, size_t n, Expr e) { +api::Term addNots(api::Solver* s, size_t n, api::Term e) { while(n-- > 0) { - e = em->mkExpr(kind::NOT, e); + e = e.notTerm(); } return e; }/* addNots() */ @@ -584,21 +587,19 @@ using namespace CVC4::parser; * by ANTLR *after* this section. (If they were functions, PARSER would be undefined.) */ #undef PARSER_STATE #define PARSER_STATE ((Parser*)PARSER->super) -#undef EXPR_MANAGER -#define EXPR_MANAGER PARSER_STATE->getExprManager() -#undef MK_EXPR -#define MK_EXPR EXPR_MANAGER->mkExpr -#undef MK_CONST -#define MK_CONST EXPR_MANAGER->mkConst +#undef SOLVER +#define SOLVER PARSER_STATE->getSolver() +#undef MK_TERM +#define MK_TERM SOLVER->mkTerm #define UNSUPPORTED PARSER_STATE->unimplementedFeature #define ENSURE_BV_SIZE(k, f) \ { \ - unsigned size = BitVectorType(f.getType()).getSize(); \ + unsigned size = f.getSort().getBVSize(); \ if(k > size) { \ - f = MK_EXPR(MK_CONST(BitVectorZeroExtend(k - size)), f); \ + f = SOLVER->mkTerm(SOLVER->mkOp(api::BITVECTOR_ZERO_EXTEND,k - size), f); \ } else if (k < size) { \ - f = MK_EXPR(MK_CONST(BitVectorExtract(k - 1, 0)), f); \ + f = SOLVER->mkTerm(SOLVER->mkOp(api::BITVECTOR_EXTRACT, k - 1, 0), f); \ } \ } @@ -608,7 +609,7 @@ using namespace CVC4::parser; * Parses an expression. * @return the parsed expression */ -parseExpr returns [CVC4::Expr expr = CVC4::Expr()] +parseExpr returns [CVC4::api::Term expr = CVC4::api::Term()] : formula[expr] | EOF ; @@ -678,29 +679,32 @@ options { backtrack = true; } mainCommand[std::unique_ptr* cmd] @init { - Expr f; + api::Term f; SExpr sexpr; std::string id; - Type t; + api::Sort t; std::vector dts; Debug("parser-extra") << "command: " << AntlrInput::tokenText(LT(1)) << std::endl; std::string s; - Expr func; - std::vector bvs; - std::vector funcs; - std::vector formulas; - std::vector> formals; + api::Term func; + std::vector bvs; + std::vector funcs; + std::vector formulas; + std::vector> formals; std::vector ids; - std::vector types; + std::vector types; bool idCommaFlag = true; bool formCommaFlag = true; } /* our bread & butter */ - : ASSERT_TOK formula[f] { cmd->reset(new AssertCommand(f)); } + : ASSERT_TOK formula[f] { cmd->reset(new AssertCommand(f.getExpr())); } - | QUERY_TOK formula[f] { cmd->reset(new QueryCommand(f)); } + | QUERY_TOK formula[f] { cmd->reset(new QueryCommand(f.getExpr())); } | CHECKSAT_TOK formula[f]? - { cmd->reset(f.isNull() ? new CheckSatCommand() : new CheckSatCommand(f)); } + { + cmd->reset(f.isNull() ? new CheckSatCommand() + : new CheckSatCommand(f.getExpr())); + } /* options */ | OPTION_TOK ( str[s] | IDENTIFIER { s = AntlrInput::tokenText($IDENTIFIER); } ) @@ -778,7 +782,7 @@ mainCommand[std::unique_ptr* cmd] { UNSUPPORTED("GET_OP command"); } | GET_VALUE_TOK formula[f] - { cmd->reset(new GetValueCommand(f)); } + { cmd->reset(new GetValueCommand(f.getExpr())); } | SUBSTITUTE_TOK identifier[id,CHECK_NONE,SYM_VARIABLE] COLON type[t,CHECK_DECLARED] EQUAL_TOK formula[f] LBRACKET @@ -812,7 +816,7 @@ mainCommand[std::unique_ptr* cmd] ) | TRANSFORM_TOK formula[f] - { cmd->reset(new SimplifyCommand(f)); } + { cmd->reset(new SimplifyCommand(f.getExpr())); } | PRINT_TOK formula[f] { UNSUPPORTED("PRINT command"); } @@ -867,7 +871,7 @@ mainCommand[std::unique_ptr* cmd] | CONTINUE_TOK { UNSUPPORTED("CONTINUE command"); } | RESTART_TOK formula[f] { UNSUPPORTED("RESTART command"); } - | RECURSIVE_FUNCTION_TOK (identifier[id,CHECK_NONE,SYM_VARIABLE] + | RECURSIVE_FUNCTION_TOK (identifier[id,CHECK_NONE,SYM_VARIABLE] { if(idCommaFlag){ idCommaFlag=false; @@ -878,9 +882,9 @@ mainCommand[std::unique_ptr* cmd] } COLON type[t,CHECK_DECLARED] (COMMA { idCommaFlag=true; - })? + })? { - func = PARSER_STATE->mkVar(id, t, ExprManager::VAR_FLAG_NONE, true); + func = PARSER_STATE->bindVar(id, t, ExprManager::VAR_FLAG_NONE, true); ids.push_back(id); types.push_back(t); funcs.push_back(func); @@ -898,7 +902,7 @@ mainCommand[std::unique_ptr* cmd] formCommaFlag=true; })? { - if( f.getKind()==kind::LAMBDA ){ + if( f.getKind()==api::LAMBDA ){ bvs.insert(bvs.end(), f[0].begin(), f[0].end()); formals.push_back(bvs); bvs.clear(); @@ -921,11 +925,19 @@ mainCommand[std::unique_ptr* cmd] PARSER_STATE->parseError("Number of functions doesn't match number of function definitions"); } for(unsigned int i = 0, size = funcs.size(); i < size; i++){ - if(!funcs[i].getType().isSubtypeOf(types[i])){ + if(!funcs[i].getSort().isSubsortOf(types[i])){ PARSER_STATE->parseError("Type mismatch in definition"); } } - cmd->reset(new DefineFunctionRecCommand(funcs,formals,formulas)); + std::vector> eformals; + for (unsigned i=0, fsize = formals.size(); ireset( + new DefineFunctionRecCommand(api::termVectorToExprs(funcs), + eformals, + api::termVectorToExprs(formulas))); } | toplevelDeclaration[cmd] ; @@ -966,7 +978,7 @@ symbolicExpr[CVC4::SExpr& sexpr] toplevelDeclaration[std::unique_ptr* cmd] @init { std::vector ids; - Type t; + api::Sort t; Debug("parser-extra") << "declaration: " << AntlrInput::tokenText(LT(1)) << std::endl; } @@ -978,7 +990,7 @@ toplevelDeclaration[std::unique_ptr* cmd] /** * A bound variable declaration. */ -boundVarDecl[std::vector& ids, CVC4::Type& t] +boundVarDecl[std::vector& ids, CVC4::api::Sort& t] @init { std::unique_ptr local_cmd; } @@ -992,31 +1004,31 @@ boundVarDecl[std::vector& ids, CVC4::Type& t] boundVarDecls @init { std::vector ids; - Type t; + api::Sort t; } : boundVarDecl[ids,t] ( COMMA boundVarDecl[ids,t] )* ; -boundVarDeclsReturn[std::vector& terms, - std::vector& types] +boundVarDeclsReturn[std::vector& terms, + std::vector& types] @init { std::vector ids; - Type t; + api::Sort t; terms.clear(); types.clear(); } : boundVarDeclReturn[terms,types] ( COMMA boundVarDeclReturn[terms,types] )* ; -boundVarDeclReturn[std::vector& terms, - std::vector& types] +boundVarDeclReturn[std::vector& terms, + std::vector& types] @init { std::vector ids; - Type t; + api::Sort t; // NOTE: do not clear the vectors here! } : identifierList[ids,CHECK_NONE,SYM_VARIABLE] COLON type[t,CHECK_DECLARED] - { const std::vector& vars = PARSER_STATE->mkBoundVars(ids, t); + { const std::vector& vars = PARSER_STATE->bindBoundVars(ids, t); terms.insert(terms.end(), vars.begin(), vars.end()); for(unsigned i = 0; i < vars.size(); ++i) { types.push_back(t); @@ -1034,7 +1046,7 @@ boundVarDeclReturn[std::vector& terms, declareTypes[std::unique_ptr* cmd, const std::vector& idList] @init { - Type t; + api::Sort t; } /* A sort declaration (e.g., "T : TYPE") */ : TYPE_TOK @@ -1046,8 +1058,8 @@ declareTypes[std::unique_ptr* cmd, // non-type variable can clash unambiguously. Break from CVC3 // behavior here. PARSER_STATE->checkDeclaration(*i, CHECK_UNDECLARED, SYM_SORT); - Type sort = PARSER_STATE->mkSort(*i); - Command* decl = new DeclareTypeCommand(*i, 0, sort); + api::Sort sort = PARSER_STATE->mkSort(*i); + Command* decl = new DeclareTypeCommand(*i, 0, sort.getType()); seq->addCommand(decl); } cmd->reset(seq.release()); @@ -1073,10 +1085,10 @@ declareTypes[std::unique_ptr* cmd, * permitted and "cmd" is output. If topLevel is false, bound vars * are created */ -declareVariables[std::unique_ptr* cmd, CVC4::Type& t, +declareVariables[std::unique_ptr* cmd, CVC4::api::Sort& t, const std::vector& idList, bool topLevel] @init { - Expr f; + api::Term f; Debug("parser-extra") << "declType: " << AntlrInput::tokenText(LT(1)) << std::endl; } /* A variable declaration (or definition) */ @@ -1094,7 +1106,7 @@ declareVariables[std::unique_ptr* cmd, CVC4::Type& t, i != i_end; ++i) { if(PARSER_STATE->isDeclared(*i, SYM_VARIABLE)) { - Type oldType = PARSER_STATE->getVariable(*i).getType(); + api::Sort oldType = PARSER_STATE->getVariable(*i).getSort(); Debug("parser") << " " << *i << " was declared previously " << "with type " << oldType << std::endl; if(oldType != t) { @@ -1111,18 +1123,20 @@ declareVariables[std::unique_ptr* cmd, CVC4::Type& t, } else { Debug("parser") << " " << *i << " not declared" << std::endl; if(topLevel) { - Expr func = PARSER_STATE->mkVar(*i, t, ExprManager::VAR_FLAG_GLOBAL); - Command* decl = new DeclareFunctionCommand(*i, func, t); + api::Term func = + PARSER_STATE->bindVar(*i, t, ExprManager::VAR_FLAG_GLOBAL); + Command* decl = + new DeclareFunctionCommand(*i, func.getExpr(), t.getType()); seq->addCommand(decl); } else { - PARSER_STATE->mkBoundVar(*i, t); + PARSER_STATE->bindBoundVar(*i, t); } } } } else { // f is not null-- meaning this is a definition not a declaration //Check if the formula f has the correct type, declared as t. - if(!f.getType().isSubtypeOf(t)){ + if(!f.getSort().isSubsortOf(t)){ PARSER_STATE->parseError("Type mismatch in definition"); } if(!topLevel) { @@ -1137,9 +1151,13 @@ declareVariables[std::unique_ptr* cmd, CVC4::Type& t, ++i) { Debug("parser") << "making " << *i << " : " << t << " = " << f << std::endl; PARSER_STATE->checkDeclaration(*i, CHECK_UNDECLARED, SYM_VARIABLE); - Expr func = EXPR_MANAGER->mkVar(*i, t, ExprManager::VAR_FLAG_GLOBAL | ExprManager::VAR_FLAG_DEFINED); + api::Term func = PARSER_STATE->mkVar( + *i, + t.getType(), + ExprManager::VAR_FLAG_GLOBAL | ExprManager::VAR_FLAG_DEFINED); PARSER_STATE->defineVar(*i, f); - Command* decl = new DefineFunctionCommand(*i, func, f); + Command* decl = + new DefineFunctionCommand(*i, func.getExpr(), f.getExpr()); seq->addCommand(decl); } } @@ -1189,29 +1207,29 @@ identifier[std::string& id, * way; then you should trace through Parser::mkMutualDatatypeType() * to figure out just what you're in for. */ -type[CVC4::Type& t, +type[CVC4::api::Sort& t, CVC4::parser::DeclarationCheck check] @init { - Type t2; + api::Sort t2; bool lhs; - std::vector args; + std::vector args; } /* a type, possibly a function */ : restrictedTypePossiblyFunctionLHS[t,check,lhs] { if(lhs) { assert(t.isTuple()); - args = ((DatatypeType)t).getTupleTypes(); + args = t.getTupleSorts(); } else { args.push_back(t); } } - ( ARROW_TOK type[t2,check] { args.push_back(t2); } )? + ( ARROW_TOK type[t2,check] )? { if(t2.isNull()) { if(lhs) { PARSER_STATE->parseError("improperly-placed type list; expected `->' after to define a function; or else maybe these parentheses were meant to be square brackets, to define a tuple type?"); } } else { - t = EXPR_MANAGER->mkFunctionType(args); + t = SOLVER->mkFunctionSort(args, t2); } } @@ -1233,7 +1251,7 @@ type[CVC4::Type& t, // there). The "type" rule above uses restictedTypePossiblyFunctionLHS // directly in order to implement that; this rule allows a type list to // parse but then issues an error. -restrictedType[CVC4::Type& t, +restrictedType[CVC4::api::Sort& t, CVC4::parser::DeclarationCheck check] @init { bool lhs; @@ -1246,15 +1264,15 @@ restrictedType[CVC4::Type& t, * lhs is set to "true" on output if we have a list of types, so an * ARROW must follow. An ARROW can always follow; lhs means it MUST. */ -restrictedTypePossiblyFunctionLHS[CVC4::Type& t, +restrictedTypePossiblyFunctionLHS[CVC4::api::Sort& t, CVC4::parser::DeclarationCheck check, bool& lhs] @init { - Type t2; - Expr f, f2; + api::Sort t2; + api::Term f, f2; std::string id; - std::vector types; - std::vector< std::pair > typeIds; + std::vector types; + std::vector< std::pair > typeIds; //SymbolTable* symtab; Parser* parser; lhs = false; @@ -1285,7 +1303,7 @@ restrictedTypePossiblyFunctionLHS[CVC4::Type& t, Debug("parser-param") << "param: make unres type " << id << std::endl; }else{ t = PARSER_STATE->mkUnresolvedTypeConstructor(id,types); - t = SortConstructorType(t).instantiate( types ); + t = t.instantiate( types ); Debug("parser-param") << "param: make unres param type " << id << " " << types.size() << " " << PARSER_STATE->getArity( id ) << std::endl; } @@ -1294,10 +1312,10 @@ restrictedTypePossiblyFunctionLHS[CVC4::Type& t, /* array types */ | ARRAY_TOK restrictedType[t,check] OF_TOK restrictedType[t2,check] - { t = EXPR_MANAGER->mkArrayType(t, t2); } + { t = SOLVER->mkArraySort(t, t2); } | SET_TOK OF_TOK restrictedType[t,check] - { t = EXPR_MANAGER->mkSetType(t); } - + { t = SOLVER->mkSetSort(t); } + /* subtypes */ | SUBTYPE_TOK LPAREN /* A bit tricky: this LAMBDA expression cannot refer to constants @@ -1325,45 +1343,45 @@ restrictedTypePossiblyFunctionLHS[CVC4::Type& t, PARSER_STATE->parseError("old-style function type syntax not supported anymore; please use the new syntax"); } else { // tuple type [ T, U, V... ] - t = EXPR_MANAGER->mkTupleType(types); + t = SOLVER->mkTupleSort(types); } } /* record types */ | SQHASH ( identifier[id,CHECK_NONE,SYM_SORT] COLON type[t,check] { typeIds.push_back(std::make_pair(id, t)); } ( COMMA identifier[id,CHECK_NONE,SYM_SORT] COLON type[t,check] { typeIds.push_back(std::make_pair(id, t)); } )* )? HASHSQ - { t = EXPR_MANAGER->mkRecordType(typeIds); } + { t = SOLVER->mkRecordSort(typeIds); } /* bitvector types */ | BITVECTOR_TOK LPAREN k=numeral RPAREN { if(k == 0) { PARSER_STATE->parseError("Illegal bitvector size: 0"); } - t = EXPR_MANAGER->mkBitVectorType(k); + t = SOLVER->mkBitVectorSort(k); } /* string type */ - | STRING_TOK { t = EXPR_MANAGER->stringType(); } + | STRING_TOK { t = SOLVER->getStringSort(); } /* basic types */ - | BOOLEAN_TOK { t = EXPR_MANAGER->booleanType(); } - | REAL_TOK { t = EXPR_MANAGER->realType(); } - | INT_TOK { t = EXPR_MANAGER->integerType(); } + | BOOLEAN_TOK { t = SOLVER->getBooleanSort(); } + | REAL_TOK { t = SOLVER->getRealSort(); } + | INT_TOK { t = SOLVER->getIntegerSort(); } /* Parenthesized general type, or the lhs of an ARROW (a list of * types). These two things are combined to avoid conflicts in * parsing. */ | LPAREN type[t,check] { types.push_back(t); } ( COMMA type[t,check] { lhs = true; types.push_back(t); } )* RPAREN - { if(lhs) { t = EXPR_MANAGER->mkTupleType(types); } + { if(lhs) { t = SOLVER->mkTupleSort(types); } // if !lhs, t is already set up correctly, nothing to do.. } ; parameterization[CVC4::parser::DeclarationCheck check, - std::vector& params] + std::vector& params] @init { - Type t; + api::Sort t; } : LBRACKET restrictedType[t,check] { Debug("parser-param") << "t = " << t << std::endl; params.push_back( t ); } ( COMMA restrictedType[t,check] { Debug("parser-param") << "t = " << t << std::endl; params.push_back( t ); } )* RBRACKET @@ -1376,7 +1394,7 @@ bound typeLetDecl[CVC4::parser::DeclarationCheck check] @init { - Type t; + api::Sort t; std::string id; } : identifier[id,CHECK_NONE,SYM_SORT] (COLON TYPE_TOK)? EQUAL_TOK restrictedType[t,check] @@ -1390,39 +1408,41 @@ typeLetDecl[CVC4::parser::DeclarationCheck check] * * @return the expression representing the formula/term */ -formula[CVC4::Expr& f] +formula[CVC4::api::Term& f] @init { Debug("parser-extra") << "formula: " << AntlrInput::tokenText(LT(1)) << std::endl; - Expr f2; - std::vector expressions; + api::Term f2; + std::vector expressions; std::vector operators; unsigned op; } : n=nots ( prefixFormula[f] - { f = addNots(EXPR_MANAGER, n, f); } + { f = addNots(SOLVER, n, f); } | comparison[f] - { f = addNots(EXPR_MANAGER, n, f); + { f = addNots(SOLVER, n, f); expressions.push_back(f); } morecomparisons[expressions,operators]? - { f = createPrecedenceTree(PARSER_STATE, EXPR_MANAGER, expressions, operators); } + { + f = createPrecedenceTree(PARSER_STATE, SOLVER, expressions, operators); + } ) ; -morecomparisons[std::vector& expressions, +morecomparisons[std::vector& expressions, std::vector& operators] returns [size_t i = 0] @init { unsigned op; - Expr f; + api::Term f; $i = expressions.size(); } : booleanBinop[op] { operators.push_back(op); } n=nots ( prefixFormula[f] - { expressions.push_back(addNots(EXPR_MANAGER, n, f)); } + { expressions.push_back(addNots(SOLVER, n, f)); } | comparison[f] - { f = addNots(EXPR_MANAGER, n, f); + { f = addNots(SOLVER, n, f); expressions.push_back(f); } morecomparisons[expressions,operators]? @@ -1434,41 +1454,41 @@ nots returns [size_t n = 0] : ( NOT_TOK { ++$n; } )* ; -prefixFormula[CVC4::Expr& f] +prefixFormula[CVC4::api::Term& f] @init { std::vector ids; - std::vector terms; - std::vector types; - std::vector bvs; - Type t; - Kind k; - Expr ipl; + std::vector terms; + std::vector types; + std::vector bvs; + api::Sort t; + api::Kind k; + api::Term ipl; } /* quantifiers */ - : ( FORALL_TOK { k = kind::FORALL; } | EXISTS_TOK { k = kind::EXISTS; } ) + : ( FORALL_TOK { k = api::FORALL; } | EXISTS_TOK { k = api::EXISTS; } ) { PARSER_STATE->pushScope(); } LPAREN boundVarDecl[ids,t] { for(std::vector::const_iterator i = ids.begin(); i != ids.end(); ++i) { - bvs.push_back(PARSER_STATE->mkBoundVar(*i, t)); + bvs.push_back(PARSER_STATE->bindBoundVar(*i, t)); } ids.clear(); } ( COMMA boundVarDecl[ids,t] { for(std::vector::const_iterator i = ids.begin(); i != ids.end(); ++i) { - bvs.push_back(PARSER_STATE->mkBoundVar(*i, t)); + bvs.push_back(PARSER_STATE->bindBoundVar(*i, t)); } ids.clear(); } )* RPAREN { - terms.push_back( EXPR_MANAGER->mkExpr( kind::BOUND_VAR_LIST, bvs ) ); } + terms.push_back( MK_TERM( api::BOUND_VAR_LIST, bvs ) ); } COLON instantiationPatterns[ipl]? formula[f] { PARSER_STATE->popScope(); terms.push_back(f); if(! ipl.isNull()) { terms.push_back(ipl); } - f = MK_EXPR(k, terms); + f = MK_TERM(k, terms); } /* lets: letDecl defines the variables and functionss, we just @@ -1483,23 +1503,23 @@ prefixFormula[CVC4::Expr& f] boundVarDeclsReturn[terms,types] RPAREN COLON formula[f] { PARSER_STATE->popScope(); - Expr bvl = EXPR_MANAGER->mkExpr( kind::BOUND_VAR_LIST, terms ); - f = EXPR_MANAGER->mkExpr( kind::LAMBDA, bvl, f ); + api::Term bvl = MK_TERM( api::BOUND_VAR_LIST, terms ); + f = MK_TERM( api::LAMBDA, bvl, f ); } ; -instantiationPatterns[ CVC4::Expr& expr ] +instantiationPatterns[ CVC4::api::Term& expr ] @init { - std::vector args; - Expr f; - std::vector patterns; + std::vector args; + api::Term f; + std::vector patterns; } : ( PATTERN_TOK LPAREN formula[f] { args.push_back( f ); } (COMMA formula[f] { args.push_back( f ); } )* RPAREN COLON - { patterns.push_back( EXPR_MANAGER->mkExpr( kind::INST_PATTERN, args ) ); + { patterns.push_back( MK_TERM( api::INST_PATTERN, args ) ); args.clear(); } )+ { if(! patterns.empty()) { - expr = EXPR_MANAGER->mkExpr( kind::INST_PATTERN_LIST, patterns ); + expr = MK_TERM( api::INST_PATTERN_LIST, patterns ); } } ; @@ -1509,11 +1529,13 @@ instantiationPatterns[ CVC4::Expr& expr ] */ letDecl @init { - Expr e; + api::Term e; std::string name; } : identifier[name,CHECK_NONE,SYM_VARIABLE] EQUAL_TOK formula[e] - { Debug("parser") << language::SetLanguage(language::output::LANG_CVC4) << e.getType() << std::endl; + { + Debug("parser") << language::SetLanguage(language::output::LANG_CVC4) + << e.getSort() << std::endl; PARSER_STATE->defineVar(name, e); Debug("parser") << "LET[" << PARSER_STATE->scopeLevel() << "]: " << name << std::endl @@ -1532,16 +1554,16 @@ booleanBinop[unsigned& op] | AND_TOK ; -comparison[CVC4::Expr& f] +comparison[CVC4::api::Term& f] @init { - std::vector expressions; + std::vector expressions; std::vector operators; unsigned op; } : term[f] { expressions.push_back(f); } ( comparisonBinop[op] term[f] { operators.push_back(op); expressions.push_back(f); } )* - { f = createPrecedenceTree(PARSER_STATE, EXPR_MANAGER, expressions, operators); } + { f = createPrecedenceTree(PARSER_STATE, SOLVER, expressions, operators); } ; comparisonBinop[unsigned& op] @@ -1572,12 +1594,12 @@ arithmeticBinop[unsigned& op] ; /** Parses an array/tuple/record assignment term. */ -term[CVC4::Expr& f] +term[CVC4::api::Term& f] @init { - std::vector expressions; + std::vector expressions; std::vector operators; unsigned op; - Type t; + api::Sort t; } : uminusTerm[f] ( WITH_TOK @@ -1586,7 +1608,7 @@ term[CVC4::Expr& f] | recordStore[f] ( COMMA DOT recordStore[f] )* ) ) | { expressions.push_back(f); } ( arithmeticBinop[op] uminusTerm[f] { operators.push_back(op); expressions.push_back(f); } )* - { f = createPrecedenceTree(PARSER_STATE, EXPR_MANAGER, expressions, operators); } + { f = createPrecedenceTree(PARSER_STATE, SOLVER, expressions, operators); } ) ; @@ -1594,62 +1616,60 @@ term[CVC4::Expr& f] * Parses just part of the array assignment (and constructs * the store terms). */ -arrayStore[CVC4::Expr& f] +arrayStore[CVC4::api::Term& f] @init { - Expr f2, k; + api::Term f2, k; } : LBRACKET formula[k] RBRACKET - { f2 = MK_EXPR(CVC4::kind::SELECT, f, k); } + { f2 = MK_TERM(CVC4::api::SELECT, f, k); } ( ( arrayStore[f2] | DOT ( tupleStore[f2] | recordStore[f2] ) ) | ASSIGN_TOK term[f2] ) - { f = MK_EXPR(CVC4::kind::STORE, f, k, f2); } + { f = MK_TERM(CVC4::api::STORE, f, k, f2); } ; /** * Parses just part of the tuple assignment (and constructs * the store terms). */ -tupleStore[CVC4::Expr& f] +tupleStore[CVC4::api::Term& f] @init { - Expr f2; + api::Term f2; } : k=numeral - { Type t = f.getType(); + { api::Sort t = f.getSort(); if(! t.isTuple()) { PARSER_STATE->parseError("tuple-update applied to non-tuple"); } - size_t length = ((DatatypeType)t).getTupleLength(); + size_t length = t.getTupleLength(); if(k >= length) { std::stringstream ss; ss << "tuple is of length " << length << "; cannot update index " << k; PARSER_STATE->parseError(ss.str()); } - std::vector args; - const Datatype & dt = ((DatatypeType)t).getDatatype(); - args.push_back( dt[0][k].getSelector() ); - args.push_back( f ); - f2 = MK_EXPR(CVC4::kind::APPLY_SELECTOR,args); + const Datatype & dt = ((DatatypeType)t.getType()).getDatatype(); + f2 = SOLVER->mkTerm( + api::APPLY_SELECTOR, api::Term(dt[0][k].getSelector()), f); } ( ( arrayStore[f2] | DOT ( tupleStore[f2] | recordStore[f2] ) ) | ASSIGN_TOK term[f2] ) - { f = MK_EXPR(MK_CONST(TupleUpdate(k)), f, f2); } + { f = SOLVER->mkTerm(SOLVER->mkOp(api::TUPLE_UPDATE,k), f, f2); } ; /** * Parses just part of the record assignment (and constructs * the store terms). */ -recordStore[CVC4::Expr& f] +recordStore[CVC4::api::Term& f] @init { std::string id; - Expr f2; + api::Term f2; } : identifier[id,CHECK_NONE,SYM_VARIABLE] - { Type t = f.getType(); + { api::Sort t = f.getSort(); if(! t.isRecord()) { std::stringstream ss; ss << "record-update applied to non-record term" << std::endl @@ -1657,43 +1677,46 @@ recordStore[CVC4::Expr& f] << "its type: " << t; PARSER_STATE->parseError(ss.str()); } - const Record& rec = ((DatatypeType)t).getRecord(); + const Record& rec = ((DatatypeType)t.getType()).getRecord(); if(! rec.contains(id)) { PARSER_STATE->parseError(std::string("no such field `") + id + "' in record"); } - std::vector args; - const Datatype & dt = ((DatatypeType)t).getDatatype(); - args.push_back( dt[0][id].getSelector() ); - args.push_back( f ); - f2 = MK_EXPR(CVC4::kind::APPLY_SELECTOR,args); + const Datatype & dt = ((DatatypeType)t.getType()).getDatatype(); + f2 = SOLVER->mkTerm( + api::APPLY_SELECTOR, api::Term(dt[0][id].getSelector()), f); } ( ( arrayStore[f2] | DOT ( tupleStore[f2] | recordStore[f2] ) ) | ASSIGN_TOK term[f2] ) - { f = MK_EXPR(MK_CONST(RecordUpdate(id)), f, f2); } + { f = SOLVER->mkTerm(SOLVER->mkOp(api::RECORD_UPDATE,id), f, f2); } ; /** Parses a unary minus term. */ -uminusTerm[CVC4::Expr& f] +uminusTerm[CVC4::api::Term& f] @init { unsigned minusCount = 0; } /* Unary minus */ : (MINUS_TOK { ++minusCount; })* bvBinaryOpTerm[f] - { while(minusCount > 0) { --minusCount; f = MK_EXPR(CVC4::kind::UMINUS, f); } } - ; + { + while (minusCount > 0) + { + --minusCount; + f = MK_TERM(CVC4::api::UMINUS, f); + } + }; /** Parses bitvectors. Starts with binary operators @, &, and |. */ -bvBinaryOpTerm[CVC4::Expr& f] +bvBinaryOpTerm[CVC4::api::Term& f] @init { - std::vector expressions; + std::vector expressions; std::vector operators; unsigned op; } : bvNegTerm[f] { expressions.push_back(f); } ( bvBinop[op] bvNegTerm[f] { operators.push_back(op); expressions.push_back(f); } )* - { f = createPrecedenceTree(PARSER_STATE, EXPR_MANAGER, expressions, operators); } + { f = createPrecedenceTree(PARSER_STATE, SOLVER, expressions, operators); } ; bvBinop[unsigned& op] @init { @@ -1704,10 +1727,13 @@ bvBinop[unsigned& op] | BVAND_TOK ; -bvNegTerm[CVC4::Expr& f] +bvNegTerm[CVC4::api::Term& f] /* BV neg */ : BVNEG_TOK bvNegTerm[f] - { f = f.getType().isSet() ? MK_EXPR(CVC4::kind::COMPLEMENT, f) : MK_EXPR(CVC4::kind::BITVECTOR_NOT, f); } + { + f = f.getSort().isSet() ? MK_TERM(CVC4::api::COMPLEMENT, f) + : MK_TERM(CVC4::api::BITVECTOR_NOT, f); + } | relationBinopTerm[f] ; @@ -1720,15 +1746,15 @@ relationBinop[unsigned& op] | JOIN_IMAGE_TOK ; -relationBinopTerm[CVC4::Expr& f] +relationBinopTerm[CVC4::api::Term& f] @init { - std::vector expressions; + std::vector expressions; std::vector operators; unsigned op; } : postfixTerm[f] { expressions.push_back(f); } ( relationBinop[op] postfixTerm[f] { operators.push_back(op); expressions.push_back(f); } )* - { f = createPrecedenceTree(PARSER_STATE, EXPR_MANAGER, expressions, operators); } + { f = createPrecedenceTree(PARSER_STATE, SOLVER, expressions, operators); } ; /** @@ -1740,13 +1766,13 @@ relationBinopTerm[CVC4::Expr& f] * brackets ], so we left-factor as much out as possible to make ANTLR * happy. */ -postfixTerm[CVC4::Expr& f] +postfixTerm[CVC4::api::Term& f] @init { - Expr f2; + api::Term f2; bool extract = false, left = false; - std::vector args; + std::vector args; std::string id; - Type t; + api::Sort t; } : ( relationTerm[f] ( /* array select / bitvector extract */ @@ -1756,22 +1782,24 @@ postfixTerm[CVC4::Expr& f] RBRACKET { if(extract) { /* bitvector extract */ - f = MK_EXPR(MK_CONST(BitVectorExtract(k1, k2)), f); + f = SOLVER->mkTerm(SOLVER->mkOp(api::BITVECTOR_EXTRACT,k1,k2), f); } else { /* array select */ - f = MK_EXPR(CVC4::kind::SELECT, f, f2); + f = MK_TERM(CVC4::api::SELECT, f, f2); } } /* left- or right-shift */ | ( LEFTSHIFT_TOK { left = true; } | RIGHTSHIFT_TOK { left = false; } ) k=numeral - { + { if(left) { - f = MK_EXPR(kind::BITVECTOR_CONCAT, f, MK_CONST(BitVector(k))); + f = MK_TERM(api::BITVECTOR_CONCAT, f, SOLVER->mkBitVector(k)); } else { - unsigned bv_size = BitVectorType(f.getType()).getSize(); - f = MK_EXPR(kind::BITVECTOR_CONCAT, MK_CONST(BitVector(k)), - MK_EXPR(MK_CONST(BitVectorExtract(bv_size - 1, k)), f)); + unsigned bv_size = f.getSort().getBVSize(); + f = MK_TERM(api::BITVECTOR_CONCAT, + SOLVER->mkBitVector(k), + SOLVER->mkTerm( + SOLVER->mkOp(api::BITVECTOR_EXTRACT, bv_size - 1, k), f)); } } @@ -1779,62 +1807,60 @@ postfixTerm[CVC4::Expr& f] | LPAREN { args.push_back(f); } formula[f] { args.push_back(f); } ( COMMA formula[f] { args.push_back(f); } )* RPAREN - { + { PARSER_STATE->checkFunctionLike(args.front()); - Kind kind = PARSER_STATE->getKindForFunction(args.front()); + api::Kind kind = PARSER_STATE->getKindForFunction(args.front()); Debug("parser") << "expr is " << args.front() << std::endl; Debug("parser") << "kind is " << kind << std::endl; - f = MK_EXPR(kind, args); + f = SOLVER->mkTerm(kind,args); } /* record / tuple select */ | DOT ( identifier[id,CHECK_NONE,SYM_VARIABLE] - { Type type = f.getType(); + { api::Sort type = f.getSort(); if(! type.isRecord()) { PARSER_STATE->parseError("record-select applied to non-record"); } - const Record& rec = ((DatatypeType)type).getRecord(); + const Record& rec = ((DatatypeType)type.getType()).getRecord(); if(!rec.contains(id)){ PARSER_STATE->parseError(std::string("no such field `") + id + "' in record"); } - const Datatype & dt = ((DatatypeType)type).getDatatype(); - std::vector sargs; - sargs.push_back( dt[0][id].getSelector() ); - sargs.push_back( f ); - f = MK_EXPR(CVC4::kind::APPLY_SELECTOR,sargs); + const Datatype & dt = ((DatatypeType)type.getType()).getDatatype(); + f = SOLVER->mkTerm(api::APPLY_SELECTOR,api::Term(dt[0][id].getSelector()), f); } | k=numeral - { Type type = f.getType(); + { + api::Sort type = f.getSort(); if(! type.isTuple()) { PARSER_STATE->parseError("tuple-select applied to non-tuple"); } - size_t length = ((DatatypeType)type).getTupleLength(); + size_t length = type.getTupleLength(); if(k >= length) { std::stringstream ss; ss << "tuple is of length " << length << "; cannot access index " << k; PARSER_STATE->parseError(ss.str()); } - const Datatype & dt = ((DatatypeType)type).getDatatype(); - std::vector sargs; - sargs.push_back( dt[0][k].getSelector() ); - sargs.push_back( f ); - f = MK_EXPR(CVC4::kind::APPLY_SELECTOR,sargs); + const Datatype & dt = ((DatatypeType)type.getType()).getDatatype(); + f = SOLVER->mkTerm(api::APPLY_SELECTOR,api::Term(dt[0][k].getSelector()), f); } ) )* | FLOOR_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::TO_INTEGER, f); } + { f = MK_TERM(CVC4::api::TO_INTEGER, f); } | IS_INTEGER_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::IS_INTEGER, f); } + { f = MK_TERM(CVC4::api::IS_INTEGER, f); } | ABS_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::ABS, f); } + { f = MK_TERM(CVC4::api::ABS, f); } | DIVISIBLE_TOK LPAREN formula[f] COMMA n=numeral RPAREN - { f = MK_EXPR(CVC4::kind::DIVISIBLE, MK_CONST(CVC4::Divisible(n)), f); } + { f = MK_TERM(SOLVER->mkOp(CVC4::api::DIVISIBLE,n), f); } | DISTINCT_TOK LPAREN formula[f] { args.push_back(f); } ( COMMA formula[f] { args.push_back(f); } )* RPAREN - { f = (args.size() == 1) ? MK_CONST(bool(true)) : MK_EXPR(CVC4::kind::DISTINCT, args); } + { + f = (args.size() == 1) ? SOLVER->mkTrue() + : MK_TERM(CVC4::api::DISTINCT, args); + } ) ( typeAscription[f, t] { @@ -1842,48 +1868,48 @@ postfixTerm[CVC4::Expr& f] } )? ; - -relationTerm[CVC4::Expr& f] + +relationTerm[CVC4::api::Term& f] /* relation terms */ : TRANSPOSE_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::TRANSPOSE, f); } + { f = MK_TERM(CVC4::api::TRANSPOSE, f); } | TRANSCLOSURE_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::TCLOSURE, f); } + { f = MK_TERM(CVC4::api::TCLOSURE, f); } | TUPLE_TOK LPAREN formula[f] RPAREN - { std::vector types; - std::vector args; + { std::vector types; + std::vector args; args.push_back(f); - types.push_back(f.getType()); - DatatypeType t = EXPR_MANAGER->mkTupleType(types); - const Datatype& dt = t.getDatatype(); - args.insert( args.begin(), dt[0].getConstructor() ); - f = MK_EXPR(kind::APPLY_CONSTRUCTOR, args); + types.push_back(f.getSort()); + api::Sort t = SOLVER->mkTupleSort(types); + const Datatype& dt = ((DatatypeType)t.getType()).getDatatype(); + args.insert( args.begin(), api::Term(dt[0].getConstructor()) ); + f = MK_TERM(api::APPLY_CONSTRUCTOR, args); } | IDEN_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::IDEN, f); } + { f = MK_TERM(CVC4::api::IDEN, f); } | bvTerm[f] ; - -bvTerm[CVC4::Expr& f] + +bvTerm[CVC4::api::Term& f] @init { - Expr f2; - std::vector args; + api::Term f2; + std::vector args; } /* BV xor */ : BVXOR_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_XOR, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_XOR, f, f2); } | BVNAND_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_NAND, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_NAND, f, f2); } | BVNOR_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_NOR, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_NOR, f, f2); } | BVCOMP_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_COMP, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_COMP, f, f2); } | BVXNOR_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_XNOR, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_XNOR, f, f2); } /* BV unary minus */ | BVUMINUS_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_NEG, f); } + { f = MK_TERM(CVC4::api::BITVECTOR_NEG, f); } /* BV addition */ | BVPLUS_TOK LPAREN k=numeral COMMA formula[f] { args.push_back(f); } ( COMMA formula[f2] { args.push_back(f2); } )+ RPAREN @@ -1894,7 +1920,7 @@ bvTerm[CVC4::Expr& f] for (unsigned i = 0; i < args.size(); ++ i) { ENSURE_BV_SIZE(k, args[i]); } - f = MK_EXPR(CVC4::kind::BITVECTOR_PLUS, args); + f = MK_TERM(CVC4::api::BITVECTOR_PLUS, args); } /* BV subtraction */ | BVSUB_TOK LPAREN k=numeral COMMA formula[f] COMMA formula[f2] RPAREN @@ -1904,7 +1930,7 @@ bvTerm[CVC4::Expr& f] } ENSURE_BV_SIZE(k, f); ENSURE_BV_SIZE(k, f2); - f = MK_EXPR(CVC4::kind::BITVECTOR_SUB, f, f2); + f = MK_TERM(CVC4::api::BITVECTOR_SUB, f, f2); } /* BV multiplication */ | BVMULT_TOK LPAREN k=numeral COMMA formula[f] COMMA formula[f2] RPAREN @@ -1914,175 +1940,177 @@ bvTerm[CVC4::Expr& f] } ENSURE_BV_SIZE(k, f); ENSURE_BV_SIZE(k, f2); - f = MK_EXPR(CVC4::kind::BITVECTOR_MULT, f, f2); + f = MK_TERM(CVC4::api::BITVECTOR_MULT, f, f2); } /* BV unsigned division */ | BVUDIV_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_UDIV, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_UDIV, f, f2); } /* BV signed division */ | BVSDIV_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_SDIV, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_SDIV, f, f2); } /* BV unsigned remainder */ | BVUREM_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_UREM, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_UREM, f, f2); } /* BV signed remainder */ | BVSREM_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_SREM, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_SREM, f, f2); } /* BV signed modulo */ | BVSMOD_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_SMOD, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_SMOD, f, f2); } /* BV left shift */ | BVSHL_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_SHL, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_SHL, f, f2); } /* BV arithmetic right shift */ | BVASHR_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_ASHR, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_ASHR, f, f2); } /* BV logical left shift */ | BVLSHR_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_LSHR, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_LSHR, f, f2); } /* BV sign extension */ | SX_TOK LPAREN formula[f] COMMA k=numeral RPAREN - { unsigned n = BitVectorType(f.getType()).getSize(); + { unsigned n = f.getSort().getBVSize(); // Sign extension in TheoryBitVector is defined as in SMT-LIB // which is different than in the CVC language // SX(BITVECTOR(k), n) in CVC language extends to n bits // In SMT-LIB, such a thing expands to k + n bits - f = MK_EXPR(MK_CONST(BitVectorSignExtend(k - n)), f); } + f = SOLVER->mkTerm(SOLVER->mkOp(api::BITVECTOR_SIGN_EXTEND,k-n), f); + } /* BV zero extension */ | BVZEROEXTEND_TOK LPAREN formula[f] COMMA k=numeral RPAREN - { unsigned n = BitVectorType(f.getType()).getSize(); + { unsigned n = f.getSort().getBVSize(); // Zero extension in TheoryBitVector is defined as in SMT-LIB // which is the same as in CVC3, but different than SX! // SX(BITVECTOR(k), n) in CVC language extends to n bits // BVZEROEXTEND(BITVECTOR(k), n) in CVC language extends to k + n bits - f = MK_EXPR(MK_CONST(BitVectorZeroExtend(k)), f); } + f = SOLVER->mkTerm(SOLVER->mkOp(api::BITVECTOR_ZERO_EXTEND,k), f); + } /* BV repeat operation */ | BVREPEAT_TOK LPAREN formula[f] COMMA k=numeral RPAREN - { f = MK_EXPR(MK_CONST(BitVectorRepeat(k)), f); } + { f = SOLVER->mkTerm(SOLVER->mkOp(api::BITVECTOR_REPEAT,k), f); } /* BV rotate right */ | BVROTR_TOK LPAREN formula[f] COMMA k=numeral RPAREN - { f = MK_EXPR(MK_CONST(BitVectorRotateRight(k)), f); } + { f = SOLVER->mkTerm(SOLVER->mkOp(api::BITVECTOR_ROTATE_RIGHT,k), f); } /* BV rotate left */ | BVROTL_TOK LPAREN formula[f] COMMA k=numeral RPAREN - { f = MK_EXPR(MK_CONST(BitVectorRotateLeft(k)), f); } + { f = SOLVER->mkTerm(SOLVER->mkOp(api::BITVECTOR_ROTATE_LEFT,k), f); } /* BV comparisons */ | BVLT_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_ULT, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_ULT, f, f2); } | BVLE_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_ULE, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_ULE, f, f2); } | BVGT_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_UGT, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_UGT, f, f2); } | BVGE_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_UGE, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_UGE, f, f2); } | BVSLT_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_SLT, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_SLT, f, f2); } | BVSLE_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_SLE, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_SLE, f, f2); } | BVSGT_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_SGT, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_SGT, f, f2); } | BVSGE_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::BITVECTOR_SGE, f, f2); } + { f = MK_TERM(CVC4::api::BITVECTOR_SGE, f, f2); } | stringTerm[f] ; -stringTerm[CVC4::Expr& f] +stringTerm[CVC4::api::Term& f] @init { - Expr f2; - Expr f3; + api::Term f2; + api::Term f3; std::string s; - std::vector args; + std::vector args; } /* String prefix operators */ : STRING_CONCAT_TOK LPAREN formula[f] { args.push_back(f); } ( COMMA formula[f2] { args.push_back(f2); } )+ RPAREN - { f = MK_EXPR(CVC4::kind::STRING_CONCAT, args); } + { f = MK_TERM(CVC4::api::STRING_CONCAT, args); } | STRING_LENGTH_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::STRING_LENGTH, f); } + { f = MK_TERM(CVC4::api::STRING_LENGTH, f); } | STRING_CONTAINS_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::STRING_STRCTN, f, f2); } + { f = MK_TERM(CVC4::api::STRING_STRCTN, f, f2); } | STRING_SUBSTR_TOK LPAREN formula[f] COMMA formula[f2] COMMA formula[f3] RPAREN - { f = MK_EXPR(CVC4::kind::STRING_SUBSTR, f, f2, f3); } + { f = MK_TERM(CVC4::api::STRING_SUBSTR, f, f2, f3); } | STRING_CHARAT_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::STRING_CHARAT, f, f2); } + { f = MK_TERM(CVC4::api::STRING_CHARAT, f, f2); } | STRING_INDEXOF_TOK LPAREN formula[f] COMMA formula[f2] COMMA formula[f3] RPAREN - { f = MK_EXPR(CVC4::kind::STRING_STRIDOF, f, f2, f3); } + { f = MK_TERM(CVC4::api::STRING_STRIDOF, f, f2, f3); } | STRING_REPLACE_TOK LPAREN formula[f] COMMA formula[f2] COMMA formula[f3] RPAREN - { f = MK_EXPR(CVC4::kind::STRING_STRREPL, f, f2, f3); } + { f = MK_TERM(CVC4::api::STRING_STRREPL, f, f2, f3); } | STRING_REPLACE_ALL_TOK LPAREN formula[f] COMMA formula[f2] COMMA formula[f3] RPAREN - { f = MK_EXPR(CVC4::kind::STRING_STRREPLALL, f, f2, f3); } + { f = MK_TERM(CVC4::api::STRING_STRREPLALL, f, f2, f3); } | STRING_PREFIXOF_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::STRING_PREFIX, f, f2); } + { f = MK_TERM(CVC4::api::STRING_PREFIX, f, f2); } | STRING_SUFFIXOF_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::STRING_SUFFIX, f, f2); } + { f = MK_TERM(CVC4::api::STRING_SUFFIX, f, f2); } | STRING_STOI_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::STRING_STOI, f); } + { f = MK_TERM(CVC4::api::STRING_STOI, f); } | STRING_ITOS_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::STRING_ITOS, f); } + { f = MK_TERM(CVC4::api::STRING_ITOS, f); } | STRING_TO_REGEXP_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::STRING_TO_REGEXP, f); } + { f = MK_TERM(CVC4::api::STRING_TO_REGEXP, f); } | STRING_TOLOWER_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::STRING_TOLOWER, f); } + { f = MK_TERM(CVC4::api::STRING_TOLOWER, f); } | STRING_TOUPPER_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::STRING_TOUPPER, f); } + { f = MK_TERM(CVC4::api::STRING_TOUPPER, f); } | STRING_REV_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::STRING_REV, f); } + { f = MK_TERM(CVC4::api::STRING_REV, f); } | REGEXP_CONCAT_TOK LPAREN formula[f] { args.push_back(f); } ( COMMA formula[f2] { args.push_back(f2); } )+ RPAREN - { f = MK_EXPR(CVC4::kind::REGEXP_CONCAT, args); } + { f = MK_TERM(CVC4::api::REGEXP_CONCAT, args); } | REGEXP_UNION_TOK LPAREN formula[f] { args.push_back(f); } ( COMMA formula[f2] { args.push_back(f2); } )+ RPAREN - { f = MK_EXPR(CVC4::kind::REGEXP_UNION, args); } + { f = MK_TERM(CVC4::api::REGEXP_UNION, args); } | REGEXP_INTER_TOK LPAREN formula[f] { args.push_back(f); } ( COMMA formula[f2] { args.push_back(f2); } )+ RPAREN - { f = MK_EXPR(CVC4::kind::REGEXP_INTER, args); } + { f = MK_TERM(CVC4::api::REGEXP_INTER, args); } | REGEXP_STAR_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::REGEXP_STAR, f); } + { f = MK_TERM(CVC4::api::REGEXP_STAR, f); } | REGEXP_PLUS_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::REGEXP_PLUS, f); } + { f = MK_TERM(CVC4::api::REGEXP_PLUS, f); } | REGEXP_OPT_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::REGEXP_OPT, f); } + { f = MK_TERM(CVC4::api::REGEXP_OPT, f); } | REGEXP_RANGE_TOK LPAREN formula[f] COMMA formula[f2] RPAREN - { f = MK_EXPR(CVC4::kind::REGEXP_RANGE, f, f2); } + { f = MK_TERM(CVC4::api::REGEXP_RANGE, f, f2); } | REGEXP_LOOP_TOK LPAREN formula[f] COMMA formula[f2] COMMA formula[f3] RPAREN - { f = MK_EXPR(CVC4::kind::REGEXP_LOOP, f, f2, f3); } + { f = MK_TERM(CVC4::api::REGEXP_LOOP, f, f2, f3); } | REGEXP_COMPLEMENT_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::REGEXP_COMPLEMENT, f); } + { f = MK_TERM(CVC4::api::REGEXP_COMPLEMENT, f); } | REGEXP_EMPTY_TOK - { f = MK_EXPR(CVC4::kind::REGEXP_EMPTY, std::vector()); } + { f = MK_TERM(CVC4::api::REGEXP_EMPTY, std::vector()); } | REGEXP_SIGMA_TOK - { f = MK_EXPR(CVC4::kind::REGEXP_SIGMA, std::vector()); } + { f = MK_TERM(CVC4::api::REGEXP_SIGMA, std::vector()); } /* string literal */ | str[s] - { f = MK_CONST(CVC4::String(s, true)); } + { f = SOLVER->mkString(s, true); } | setsTerm[f] ; - -setsTerm[CVC4::Expr& f] + +setsTerm[CVC4::api::Term& f] @init { } /* Sets prefix operators */ : SETS_CARD_TOK LPAREN formula[f] RPAREN - { f = MK_EXPR(CVC4::kind::CARD, f); } + { f = MK_TERM(CVC4::api::CARD, f); } | simpleTerm[f] ; - + /** Parses a simple term. */ -simpleTerm[CVC4::Expr& f] +simpleTerm[CVC4::api::Term& f] @init { std::string name; - std::vector args; + std::vector args; std::vector names; - Expr e; + api::Term e; Debug("parser-extra") << "term: " << AntlrInput::tokenText(LT(1)) << std::endl; - Type t, t2; + api::Sort t, t2; } /* if-then-else */ - : iteTerm[f] - + : iteTerm[f] + /* parenthesized sub-formula / tuple literals */ | LPAREN formula[f] { args.push_back(f); } ( COMMA formula[f] { args.push_back(f); } )* RPAREN @@ -2090,50 +2118,57 @@ simpleTerm[CVC4::Expr& f] /* If args has elements, we must be a tuple literal. * Otherwise, f is already the sub-formula, and * there's nothing to do */ - std::vector types; - for(std::vector::const_iterator i = args.begin(); i != args.end(); ++i) { - types.push_back((*i).getType()); + std::vector types; + for (std::vector::const_iterator i = args.begin(); + i != args.end(); + ++i) + { + types.push_back((*i).getSort()); } - DatatypeType dtype = EXPR_MANAGER->mkTupleType(types); - const Datatype& dt = dtype.getDatatype(); + api::Sort dtype = SOLVER->mkTupleSort(types); + const Datatype& dt = ((DatatypeType)dtype.getType()).getDatatype(); args.insert( args.begin(), dt[0].getConstructor() ); - f = MK_EXPR(kind::APPLY_CONSTRUCTOR, args); + f = MK_TERM(api::APPLY_CONSTRUCTOR, args); } - } + } /* empty tuple literal */ | LPAREN RPAREN - { std::vector types; - DatatypeType dtype = EXPR_MANAGER->mkTupleType(types); - const Datatype& dt = dtype.getDatatype(); - f = MK_EXPR(kind::APPLY_CONSTRUCTOR, dt[0].getConstructor()); } - + { std::vector types; + api::Sort dtype = SOLVER->mkTupleSort(types); + const Datatype& dt = ((DatatypeType)dtype.getType()).getDatatype(); + f = MK_TERM(api::APPLY_CONSTRUCTOR, api::Term(dt[0].getConstructor())); } + /* empty record literal */ | PARENHASH HASHPAREN - { DatatypeType dtype = EXPR_MANAGER->mkRecordType(std::vector< std::pair >()); - const Datatype& dt = dtype.getDatatype(); - f = MK_EXPR(kind::APPLY_CONSTRUCTOR, dt[0].getConstructor()); + { + api::Sort dtype = SOLVER->mkRecordSort( + std::vector>()); + const Datatype& dt = ((DatatypeType)dtype.getType()).getDatatype(); + f = MK_TERM(api::APPLY_CONSTRUCTOR, api::Term(dt[0].getConstructor())); } /* empty set literal */ | LBRACE RBRACE - { f = MK_CONST(EmptySet(Type())); } + { //boolean is placeholder + f = SOLVER->mkEmptySet(SOLVER->mkSetSort(SOLVER->getBooleanSort())); + } | UNIVSET_TOK - { //booleanType is placeholder - f = EXPR_MANAGER->mkNullaryOperator(EXPR_MANAGER->booleanType(), kind::UNIVERSE_SET); + { //boolean is placeholder + f = SOLVER->mkUniverseSet(SOLVER->mkSetSort(SOLVER->getBooleanSort())); } /* finite set literal */ | LBRACE formula[f] { args.push_back(f); } ( COMMA formula[f] { args.push_back(f); } )* RBRACE - { f = MK_EXPR(kind::SINGLETON, args[0]); + { f = MK_TERM(api::SINGLETON, args[0]); for(size_t i = 1; i < args.size(); ++i) { - f = MK_EXPR(kind::UNION, f, MK_EXPR(kind::SINGLETON, args[i])); + f = MK_TERM(api::UNION, f, MK_TERM(api::SINGLETON, args[i])); } } /* set cardinality literal */ | BAR BAR formula[f] { args.push_back(f); } BAR BAR - { f = MK_EXPR(kind::CARD, args[0]); + { f = MK_TERM(api::CARD, args[0]); } /* array literals */ @@ -2143,7 +2178,7 @@ simpleTerm[CVC4::Expr& f] { /* Eventually if we support a bound var (like a lambda) for array * literals, we can use the push/pop scope. */ /* PARSER_STATE->popScope(); */ - t = EXPR_MANAGER->mkArrayType(t, t2); + t = SOLVER->mkArraySort(t, t2); if(!f.isConst()) { std::stringstream ss; ss << "expected constant term inside array constant, but found " @@ -2151,55 +2186,65 @@ simpleTerm[CVC4::Expr& f] << "the term: " << f; PARSER_STATE->parseError(ss.str()); } - if(!t2.isComparableTo(f.getType())) { + if(!t2.isComparableTo(f.getSort())) { std::stringstream ss; ss << "type mismatch inside array constant term:" << std::endl << "array type: " << t << std::endl << "expected const type: " << t2 << std::endl - << "computed const type: " << f.getType(); + << "computed const type: " << f.getSort(); PARSER_STATE->parseError(ss.str()); } - f = MK_CONST( ArrayStoreAll(t, f) ); + f = SOLVER->mkConstArray(t, f); } /* boolean literals */ - | TRUE_TOK { f = MK_CONST(bool(true)); } - | FALSE_TOK { f = MK_CONST(bool(false)); } + | TRUE_TOK { f = SOLVER->mkTrue(); } + | FALSE_TOK { f = SOLVER->mkFalse(); } /* arithmetic literals */ /* syntactic predicate: never match INTEGER.DIGIT as an integer and a dot! * This is a rational constant! Otherwise the parser interprets it as a tuple * selector! */ - | DECIMAL_LITERAL { - f = MK_CONST(AntlrInput::tokenToRational($DECIMAL_LITERAL)); - if(f.getType().isInteger()) { + | DECIMAL_LITERAL { + Rational r = AntlrInput::tokenToRational($DECIMAL_LITERAL); + std::stringstream strRat; + strRat << r; + f = SOLVER->mkReal(strRat.str()); + if(f.getSort().isInteger()) { // Must cast to Real to ensure correct type is passed to parametric type constructors. // We do this cast using division with 1. // This has the advantage wrt using TO_REAL since (constant) division is always included in the theory. - f = MK_EXPR(kind::DIVISION, f, MK_CONST(Rational(1))); - } + f = MK_TERM(api::DIVISION, f, SOLVER->mkReal(1)); + } + } + | INTEGER_LITERAL { + Rational r = AntlrInput::tokenToRational($INTEGER_LITERAL); + std::stringstream strRat; + strRat << r; + f = SOLVER->mkReal(strRat.str()); } - | INTEGER_LITERAL { f = MK_CONST(AntlrInput::tokenToInteger($INTEGER_LITERAL)); } /* bitvector literals */ | HEX_LITERAL { assert( AntlrInput::tokenText($HEX_LITERAL).find("0hex") == 0 ); std::string hexString = AntlrInput::tokenTextSubstr($HEX_LITERAL, 4); - f = MK_CONST( BitVector(hexString, 16) ); } + f = SOLVER->mkBitVector(hexString, 16); + } | BINARY_LITERAL { assert( AntlrInput::tokenText($BINARY_LITERAL).find("0bin") == 0 ); std::string binString = AntlrInput::tokenTextSubstr($BINARY_LITERAL, 4); - f = MK_CONST( BitVector(binString, 2) ); } + f = SOLVER->mkBitVector(binString, 2); + } /* record literals */ | PARENHASH recordEntry[name,e] { names.push_back(name); args.push_back(e); } ( COMMA recordEntry[name,e] { names.push_back(name); args.push_back(e); } )* HASHPAREN - { std::vector< std::pair > typeIds; + { std::vector< std::pair > typeIds; assert(names.size() == args.size()); for(unsigned i = 0; i < names.size(); ++i) { - typeIds.push_back(std::make_pair(names[i], args[i].getType())); + typeIds.push_back(std::make_pair(names[i], args[i].getSort())); } - DatatypeType dtype = EXPR_MANAGER->mkRecordType(typeIds); - const Datatype& dt = dtype.getDatatype(); + api::Sort dtype = SOLVER->mkRecordSort(typeIds); + const Datatype& dt = ((DatatypeType)dtype.getType()).getDatatype(); args.insert( args.begin(), dt[0].getConstructor() ); - f = MK_EXPR(kind::APPLY_CONSTRUCTOR, args); + f = MK_TERM(api::APPLY_CONSTRUCTOR, args); } /* variable / zero-ary constructor application */ @@ -2207,10 +2252,10 @@ simpleTerm[CVC4::Expr& f] /* ascriptions will be required for parameterized zero-ary constructors */ { f = PARSER_STATE->getVariable(name); // datatypes: zero-ary constructors - Type dtype = f.getType(); - if(dtype.isConstructor() && ConstructorType(dtype).getArity() == 0) { + api::Sort dtype = f.getSort(); + if(dtype.isConstructor() && dtype.getConstructorArity() == 0) { // don't require parentheses, immediately turn it into an apply - f = MK_EXPR(CVC4::kind::APPLY_CONSTRUCTOR, f); + f = MK_TERM(CVC4::api::APPLY_CONSTRUCTOR, f); } } ; @@ -2219,7 +2264,7 @@ simpleTerm[CVC4::Expr& f] * Matches a type ascription. * The f arg is the term to check (it is an input-only argument). */ -typeAscription[const CVC4::Expr& f, CVC4::Type& t] +typeAscription[const CVC4::api::Term& f, CVC4::api::Sort& t] @init { } : COLON COLON type[t,CHECK_DECLARED] @@ -2228,38 +2273,38 @@ typeAscription[const CVC4::Expr& f, CVC4::Type& t] /** * Matches an entry in a record literal. */ -recordEntry[std::string& name, CVC4::Expr& ex] +recordEntry[std::string& name, CVC4::api::Term& ex] : identifier[name,CHECK_NONE,SYM_VARIABLE] ASSIGN_TOK formula[ex] ; /** * Parses an ITE term. */ -iteTerm[CVC4::Expr& f] +iteTerm[CVC4::api::Term& f] @init { - std::vector args; + std::vector args; Debug("parser-extra") << "ite: " << AntlrInput::tokenText(LT(1)) << std::endl; } : IF_TOK formula[f] { args.push_back(f); } THEN_TOK formula[f] { args.push_back(f); } iteElseTerm[f] { args.push_back(f); } ENDIF_TOK - { f = MK_EXPR(CVC4::kind::ITE, args); } + { f = MK_TERM(CVC4::api::ITE, args); } ; /** * Parses the else part of the ITE, i.e. ELSE f, or ELSIF b THEN f1 ... */ -iteElseTerm[CVC4::Expr& f] +iteElseTerm[CVC4::api::Term& f] @init { - std::vector args; + std::vector args; Debug("parser-extra") << "else: " << AntlrInput::tokenText(LT(1)) << std::endl; } : ELSE_TOK formula[f] | ELSEIF_TOK iteCondition = formula[f] { args.push_back(f); } THEN_TOK iteThen = formula[f] { args.push_back(f); } iteElse = iteElseTerm[f] { args.push_back(f); } - { f = MK_EXPR(CVC4::kind::ITE, args); } + { f = MK_TERM(CVC4::api::ITE, args); } ; /** @@ -2268,8 +2313,8 @@ iteElseTerm[CVC4::Expr& f] datatypeDef[std::vector& datatypes] @init { std::string id, id2; - Type t; - std::vector< Type > params; + api::Sort t; + std::vector< api::Sort > params; } /* This really needs to be CHECK_NONE, or mutually-recursive * datatypes won't work, because this type will already be @@ -2285,7 +2330,11 @@ datatypeDef[std::vector& datatypes] params.push_back( t ); } )* RBRACKET )? - { datatypes.push_back(Datatype(EXPR_MANAGER, id, params, false)); + { + datatypes.push_back(Datatype(PARSER_STATE->getExprManager(), + id, + api::sortVectorToTypes(params), + false)); if(!PARSER_STATE->isUnresolvedType(id)) { // if not unresolved, must be undeclared PARSER_STATE->checkDeclaration(id, CHECK_UNDECLARED, SYM_SORT); @@ -2325,10 +2374,10 @@ constructorDef[CVC4::Datatype& type] selector[std::unique_ptr* ctor] @init { std::string id; - Type t, t2; + api::Sort t, t2; } : identifier[id,CHECK_UNDECLARED,SYM_SORT] COLON type[t,CHECK_NONE] - { (*ctor)->addArg(id, t); + { (*ctor)->addArg(id, t.getType()); Debug("parser-idt") << "selector: " << id.c_str() << std::endl; } ; diff --git a/src/parser/cvc/cvc_input.cpp b/src/parser/cvc/cvc_input.cpp index 8c7b34410..38e3594e8 100644 --- a/src/parser/cvc/cvc_input.cpp +++ b/src/parser/cvc/cvc_input.cpp @@ -63,7 +63,7 @@ Command* CvcInput::parseCommand() { api::Term CvcInput::parseExpr() { - return api::Term(d_pCvcParser->parseExpr(d_pCvcParser)); + return d_pCvcParser->parseExpr(d_pCvcParser); } /* diff --git a/src/parser/parse_op.cpp b/src/parser/parse_op.cpp new file mode 100644 index 000000000..899ae6893 --- /dev/null +++ b/src/parser/parse_op.cpp @@ -0,0 +1,47 @@ +/********************* */ +/*! \file parse_op.cpp + ** \verbatim + ** Top contributors (to current version): + ** Andrew Reynolds + ** This file is part of the CVC4 project. + ** Copyright (c) 2009-2019 by the authors listed in the file AUTHORS + ** in the top-level source directory) and their institutional affiliations. + ** All rights reserved. See the file COPYING in the top-level source + ** directory for licensing information.\endverbatim + ** + ** \brief Implementation for parsed operators + **/ + +#include "parser/parse_op.h" + +namespace CVC4 { + +std::ostream& operator<<(std::ostream& os, const ParseOp& p) +{ + std::stringstream out; + out << "(ParseOp "; + if (!p.d_expr.isNull()) + { + out << " :expr " << p.d_expr; + } + if (!p.d_op.isNull()) + { + out << " :op " << p.d_op; + } + if (p.d_kind != api::NULL_EXPR) + { + out << " :kind " << p.d_kind; + } + if (!p.d_type.isNull()) + { + out << " :type " << p.d_type; + } + if (!p.d_name.empty()) + { + out << " :name " << p.d_name; + } + out << ")"; + return os << out.str(); +} + +} // namespace CVC4 diff --git a/src/parser/parse_op.h b/src/parser/parse_op.h index a224b2511..1105cf0c8 100644 --- a/src/parser/parse_op.h +++ b/src/parser/parse_op.h @@ -20,8 +20,6 @@ #include #include "api/cvc4cpp.h" -#include "expr/expr.h" -#include "expr/kind.h" namespace CVC4 { @@ -59,15 +57,15 @@ namespace CVC4 { */ struct CVC4_PUBLIC ParseOp { - ParseOp(Kind k = kind::NULL_EXPR) : d_kind(k) {} + ParseOp(api::Kind k = api::NULL_EXPR) : d_kind(k) {} /** The kind associated with the parsed operator, if it exists */ - Kind d_kind; + api::Kind d_kind; /** The name associated with the parsed operator, if it exists */ std::string d_name; /** The expression associated with the parsed operator, if it exists */ - Expr d_expr; + api::Term d_expr; /** The type associated with the parsed operator, if it exists */ - Type d_type; + api::Sort d_type; /** The operator associated with the parsed operator, if it exists */ api::Op d_op; @@ -79,33 +77,7 @@ struct CVC4_PUBLIC ParseOp } }; -inline std::ostream& operator<<(std::ostream& os, const ParseOp& p) -{ - std::stringstream out; - out << "(ParseOp "; - if (!p.d_expr.isNull()) - { - out << " :expr " << p.d_expr; - } - if (!p.d_op.isNull()) - { - out << " :op " << p.d_op; - } - if (p.d_kind != kind::NULL_EXPR) - { - out << " :kind " << p.d_kind; - } - if (!p.d_type.isNull()) - { - out << " :type " << p.d_type; - } - if (!p.d_name.empty()) - { - out << " :name " << p.d_name; - } - out << ")"; - return os << out.str(); -} +std::ostream& operator<<(std::ostream& os, const ParseOp& p); } // namespace CVC4 diff --git a/src/parser/parser.cpp b/src/parser/parser.cpp index eae9636a2..55a52e8d6 100644 --- a/src/parser/parser.cpp +++ b/src/parser/parser.cpp @@ -83,7 +83,8 @@ ExprManager* Parser::getExprManager() const api::Solver* Parser::getSolver() const { return d_solver; } -Expr Parser::getSymbol(const std::string& name, SymbolType type) { +api::Term Parser::getSymbol(const std::string& name, SymbolType type) +{ checkDeclaration(name, CHECK_DECLARED, type); assert(isDeclared(name, type)); @@ -96,23 +97,28 @@ Expr Parser::getSymbol(const std::string& name, SymbolType type) { return Expr(); } -Expr Parser::getVariable(const std::string& name) { +api::Term Parser::getVariable(const std::string& name) +{ return getSymbol(name, SYM_VARIABLE); } -Expr Parser::getFunction(const std::string& name) { +api::Term Parser::getFunction(const std::string& name) +{ return getSymbol(name, SYM_VARIABLE); } -Expr Parser::getExpressionForName(const std::string& name) { - Type t; +api::Term Parser::getExpressionForName(const std::string& name) +{ + api::Sort t; return getExpressionForNameAndType(name, t); } -Expr Parser::getExpressionForNameAndType(const std::string& name, Type t) { +api::Term Parser::getExpressionForNameAndType(const std::string& name, + api::Sort t) +{ assert(isDeclared(name)); // first check if the variable is declared and not overloaded - Expr expr = getVariable(name); + api::Term expr = getVariable(name); if(expr.isNull()) { // the variable is overloaded, try with type if the type exists if(!t.isNull()) { @@ -128,47 +134,52 @@ Expr Parser::getExpressionForNameAndType(const std::string& name, Type t) { } // now, post-process the expression assert( !expr.isNull() ); - Type te = expr.getType(); - if (te.isConstructor() && ConstructorType(te).getArity() == 0) + api::Sort te = expr.getSort(); + if (te.isConstructor() && te.getConstructorArity() == 0) { // nullary constructors have APPLY_CONSTRUCTOR kind with no children - expr = getExprManager()->mkExpr(CVC4::kind::APPLY_CONSTRUCTOR, expr); + expr = d_solver->mkTerm(api::APPLY_CONSTRUCTOR, expr); } return expr; } -Kind Parser::getKindForFunction(Expr fun) { - Type t = fun.getType(); +api::Kind Parser::getKindForFunction(api::Term fun) +{ + api::Sort t = fun.getSort(); if (t.isFunction()) { - return APPLY_UF; + return api::APPLY_UF; } else if (t.isConstructor()) { - return APPLY_CONSTRUCTOR; + return api::APPLY_CONSTRUCTOR; } else if (t.isSelector()) { - return APPLY_SELECTOR; + return api::APPLY_SELECTOR; } else if (t.isTester()) { - return APPLY_TESTER; + return api::APPLY_TESTER; } - return UNDEFINED_KIND; + return api::UNDEFINED_KIND; } -Type Parser::getSort(const std::string& name) { +api::Sort Parser::getSort(const std::string& name) +{ checkDeclaration(name, CHECK_DECLARED, SYM_SORT); assert(isDeclared(name, SYM_SORT)); - Type t = d_symtab->lookupType(name); + api::Sort t = api::Sort(d_symtab->lookupType(name)); return t; } -Type Parser::getSort(const std::string& name, const std::vector& params) { +api::Sort Parser::getSort(const std::string& name, + const std::vector& params) +{ checkDeclaration(name, CHECK_DECLARED, SYM_SORT); assert(isDeclared(name, SYM_SORT)); - Type t = d_symtab->lookupType(name, params); + api::Sort t = + api::Sort(d_symtab->lookupType(name, api::sortVectorToTypes(params))); return t; } @@ -180,122 +191,142 @@ size_t Parser::getArity(const std::string& sort_name) { /* Returns true if name is bound to a boolean variable. */ bool Parser::isBoolean(const std::string& name) { - Expr expr = getVariable(name); - return !expr.isNull() && expr.getType().isBoolean(); + api::Term expr = getVariable(name); + return !expr.isNull() && expr.getSort().isBoolean(); } -bool Parser::isFunctionLike(Expr fun) { +bool Parser::isFunctionLike(api::Term fun) +{ if(fun.isNull()) { return false; } - Type type = fun.getType(); + api::Sort type = fun.getSort(); return type.isFunction() || type.isConstructor() || type.isTester() || type.isSelector(); } /* Returns true if name is bound to a function returning boolean. */ bool Parser::isPredicate(const std::string& name) { - Expr expr = getVariable(name); - return !expr.isNull() && expr.getType().isPredicate(); + api::Term expr = getVariable(name); + return !expr.isNull() && expr.getSort().isPredicate(); } -Expr Parser::mkVar(const std::string& name, const Type& type, uint32_t flags, bool doOverload) { +api::Term Parser::bindVar(const std::string& name, + const api::Sort& type, + uint32_t flags, + bool doOverload) +{ if (d_globalDeclarations) { flags |= ExprManager::VAR_FLAG_GLOBAL; } - Debug("parser") << "mkVar(" << name << ", " << type << ")" << std::endl; - Expr expr = getExprManager()->mkVar(name, type, flags); + Debug("parser") << "bindVar(" << name << ", " << type << ")" << std::endl; + api::Term expr = mkVar(name, type, flags); defineVar(name, expr, flags & ExprManager::VAR_FLAG_GLOBAL, doOverload); return expr; } -Expr Parser::mkBoundVar(const std::string& name, const Type& type) { - Debug("parser") << "mkVar(" << name << ", " << type << ")" << std::endl; - Expr expr = getExprManager()->mkBoundVar(name, type); +api::Term Parser::bindBoundVar(const std::string& name, const api::Sort& type) +{ + Debug("parser") << "bindBoundVar(" << name << ", " << type << ")" + << std::endl; + api::Term expr = d_solver->mkVar(type, name); defineVar(name, expr, false); return expr; } -std::vector Parser::mkBoundVars( - std::vector >& sortedVarNames) +std::vector Parser::bindBoundVars( + std::vector >& sortedVarNames) { - std::vector vars; - for (std::pair& i : sortedVarNames) + std::vector vars; + for (std::pair& i : sortedVarNames) { - vars.push_back(mkBoundVar(i.first, i.second)); + vars.push_back(bindBoundVar(i.first, i.second.getType())); } return vars; } -Expr Parser::mkAnonymousFunction(const std::string& prefix, const Type& type, - uint32_t flags) { +api::Term Parser::mkAnonymousFunction(const std::string& prefix, + const api::Sort& type, + uint32_t flags) +{ if (d_globalDeclarations) { flags |= ExprManager::VAR_FLAG_GLOBAL; } stringstream name; name << prefix << "_anon_" << ++d_anonymousFunctionCount; - return getExprManager()->mkVar(name.str(), type, flags); + return mkVar(name.str(), type.getType(), flags); } -std::vector Parser::mkVars(const std::vector names, - const Type& type, uint32_t flags, bool doOverload) { +std::vector Parser::bindVars(const std::vector names, + const api::Sort& type, + uint32_t flags, + bool doOverload) +{ if (d_globalDeclarations) { flags |= ExprManager::VAR_FLAG_GLOBAL; } - std::vector vars; + std::vector vars; for (unsigned i = 0; i < names.size(); ++i) { - vars.push_back(mkVar(names[i], type, flags, doOverload)); + vars.push_back(bindVar(names[i], type, flags, doOverload)); } return vars; } -std::vector Parser::mkBoundVars(const std::vector names, - const Type& type) { - std::vector vars; +std::vector Parser::bindBoundVars( + const std::vector names, const api::Sort& type) +{ + std::vector vars; for (unsigned i = 0; i < names.size(); ++i) { - vars.push_back(mkBoundVar(names[i], type)); + vars.push_back(bindBoundVar(names[i], type)); } return vars; } -void Parser::defineVar(const std::string& name, const Expr& val, - bool levelZero, bool doOverload) { +void Parser::defineVar(const std::string& name, + const api::Term& val, + bool levelZero, + bool doOverload) +{ Debug("parser") << "defineVar( " << name << " := " << val << ")" << std::endl; - if (!d_symtab->bind(name, val, levelZero, doOverload)) { + if (!d_symtab->bind(name, val.getExpr(), levelZero, doOverload)) + { std::stringstream ss; - ss << "Cannot bind " << name << " to symbol of type " << val.getType(); + ss << "Cannot bind " << name << " to symbol of type " << val.getSort(); ss << ", maybe the symbol has already been defined?"; - parseError(ss.str()); + parseError(ss.str()); } assert(isDeclared(name)); } void Parser::defineType(const std::string& name, - const Type& type, + const api::Sort& type, bool levelZero) { - d_symtab->bindType(name, type, levelZero); + d_symtab->bindType(name, type.getType(), levelZero); assert(isDeclared(name, SYM_SORT)); } void Parser::defineType(const std::string& name, - const std::vector& params, - const Type& type, + const std::vector& params, + const api::Sort& type, bool levelZero) { - d_symtab->bindType(name, params, type, levelZero); + d_symtab->bindType( + name, api::sortVectorToTypes(params), type.getType(), levelZero); assert(isDeclared(name, SYM_SORT)); } void Parser::defineParameterizedType(const std::string& name, - const std::vector& params, - const Type& type) { + const std::vector& params, + const api::Sort& type) +{ if (Debug.isOn("parser")) { Debug("parser") << "defineParameterizedType(" << name << ", " << params.size() << ", ["; if (params.size() > 0) { - copy(params.begin(), params.end() - 1, - ostream_iterator(Debug("parser"), ", ")); + copy(params.begin(), + params.end() - 1, + ostream_iterator(Debug("parser"), ", ")); Debug("parser") << params.back(); } Debug("parser") << "], " << type << ")" << std::endl; @@ -303,9 +334,10 @@ void Parser::defineParameterizedType(const std::string& name, defineType(name, params, type); } -SortType Parser::mkSort(const std::string& name, uint32_t flags) { +api::Sort Parser::mkSort(const std::string& name, uint32_t flags) +{ Debug("parser") << "newSort(" << name << ")" << std::endl; - Type type = getExprManager()->mkSort(name, flags); + api::Sort type = getExprManager()->mkSort(name, flags); defineType( name, type, @@ -313,44 +345,46 @@ SortType Parser::mkSort(const std::string& name, uint32_t flags) { return type; } -SortConstructorType Parser::mkSortConstructor(const std::string& name, - size_t arity, - uint32_t flags) +api::Sort Parser::mkSortConstructor(const std::string& name, + size_t arity, + uint32_t flags) { Debug("parser") << "newSortConstructor(" << name << ", " << arity << ")" << std::endl; - SortConstructorType type = - getExprManager()->mkSortConstructor(name, arity, flags); + api::Sort type = getExprManager()->mkSortConstructor(name, arity, flags); defineType( name, - vector(arity), + vector(arity), type, d_globalDeclarations && !(flags & ExprManager::SORT_FLAG_PLACEHOLDER)); return type; } -SortType Parser::mkUnresolvedType(const std::string& name) { - SortType unresolved = mkSort(name, ExprManager::SORT_FLAG_PLACEHOLDER); +api::Sort Parser::mkUnresolvedType(const std::string& name) +{ + api::Sort unresolved = mkSort(name, ExprManager::SORT_FLAG_PLACEHOLDER); d_unresolved.insert(unresolved); return unresolved; } -SortConstructorType Parser::mkUnresolvedTypeConstructor(const std::string& name, - size_t arity) { - SortConstructorType unresolved = +api::Sort Parser::mkUnresolvedTypeConstructor(const std::string& name, + size_t arity) +{ + api::Sort unresolved = mkSortConstructor(name, arity, ExprManager::SORT_FLAG_PLACEHOLDER); d_unresolved.insert(unresolved); return unresolved; } -SortConstructorType Parser::mkUnresolvedTypeConstructor( - const std::string& name, const std::vector& params) { +api::Sort Parser::mkUnresolvedTypeConstructor( + const std::string& name, const std::vector& params) +{ Debug("parser") << "newSortConstructor(P)(" << name << ", " << params.size() << ")" << std::endl; - SortConstructorType unresolved = getExprManager()->mkSortConstructor( + api::Sort unresolved = getExprManager()->mkSortConstructor( name, params.size(), ExprManager::SORT_FLAG_PLACEHOLDER); defineType(name, params, unresolved); - Type t = getSort(name, params); + api::Sort t = getSort(name, params); d_unresolved.insert(unresolved); return unresolved; } @@ -366,32 +400,41 @@ std::vector Parser::mkMutualDatatypeTypes( std::vector& datatypes, bool doOverload, uint32_t flags) { try { - std::vector types = - getExprManager()->mkMutualDatatypeTypes(datatypes, d_unresolved, flags); + std::set tset = api::sortSetToTypes(d_unresolved); + std::vector dtypes = + getExprManager()->mkMutualDatatypeTypes(datatypes, tset, flags); + std::vector types; + for (unsigned i = 0, dtsize = dtypes.size(); i < dtsize; i++) + { + types.push_back(api::Sort(dtypes[i])); + } assert(datatypes.size() == types.size()); for (unsigned i = 0; i < datatypes.size(); ++i) { - DatatypeType t = types[i]; - const Datatype& dt = t.getDatatype(); + api::Sort t = types[i]; + const api::Datatype& dt = t.getDatatype(); const std::string& name = dt.getName(); Debug("parser-idt") << "define " << name << " as " << t << std::endl; if (isDeclared(name, SYM_SORT)) { throw ParserException(name + " already declared"); } - if (t.isParametric()) { - std::vector paramTypes = t.getParamTypes(); + if (t.isParametricDatatype()) + { + std::vector paramTypes = t.getDatatypeParamSorts(); defineType(name, paramTypes, t, d_globalDeclarations); - } else { + } + else + { defineType(name, t, d_globalDeclarations); } std::unordered_set< std::string > consNames; std::unordered_set< std::string > selNames; - for (Datatype::const_iterator j = dt.begin(), j_end = dt.end(); - j != j_end; ++j) { - const DatatypeConstructor& ctor = *j; + for (size_t j = 0, ncons = dt.getNumConstructors(); j < ncons; j++) + { + const api::DatatypeConstructor& ctor = dt[j]; expr::ExprPrintTypes::Scope pts(Debug("parser-idt"), true); - Expr constructor = ctor.getConstructor(); + api::Term constructor = ctor.getConstructorTerm(); Debug("parser-idt") << "+ define " << constructor << std::endl; string constructorName = ctor.getName(); if(consNames.find(constructorName)==consNames.end()) { @@ -404,19 +447,19 @@ std::vector Parser::mkMutualDatatypeTypes( }else{ throw ParserException(constructorName + " already declared in this datatype"); } - Expr tester = ctor.getTester(); + api::Term tester = ctor.getTesterTerm(); Debug("parser-idt") << "+ define " << tester << std::endl; string testerName = ctor.getTesterName(); if(!doOverload) { checkDeclaration(testerName, CHECK_UNDECLARED); } defineVar(testerName, tester, d_globalDeclarations, doOverload); - for (DatatypeConstructor::const_iterator k = ctor.begin(), - k_end = ctor.end(); - k != k_end; ++k) { - Expr selector = (*k).getSelector(); + for (size_t k = 0, nargs = ctor.getNumSelectors(); k < nargs; k++) + { + const api::DatatypeSelector& sel = ctor[k]; + api::Term selector = sel.getSelectorTerm(); Debug("parser-idt") << "+++ define " << selector << std::endl; - string selectorName = (*k).getName(); + string selectorName = sel.getName(); if(selNames.find(selectorName)==selNames.end()) { if(!doOverload) { checkDeclaration(selectorName, CHECK_UNDECLARED); @@ -437,45 +480,49 @@ std::vector Parser::mkMutualDatatypeTypes( // throw exception if any datatype is not well-founded for (unsigned i = 0; i < datatypes.size(); ++i) { - const Datatype& dt = types[i].getDatatype(); + const api::Datatype& dt = types[i].getDatatype(); if (!dt.isCodatatype() && !dt.isWellFounded()) { throw ParserException(dt.getName() + " is not well-founded"); } } - - return types; + std::vector retTypes; + for (unsigned i = 0, ntypes = types.size(); i < ntypes; i++) + { + retTypes.push_back(DatatypeType(types[i].getType())); + } + return retTypes; } catch (IllegalArgumentException& ie) { throw ParserException(ie.getMessage()); } } -Type Parser::mkFlatFunctionType(std::vector& sorts, - Type range, - std::vector& flattenVars) +api::Sort Parser::mkFlatFunctionType(std::vector& sorts, + api::Sort range, + std::vector& flattenVars) { if (range.isFunction()) { - std::vector domainTypes = - (static_cast(range)).getArgTypes(); + std::vector domainTypes = range.getFunctionDomainSorts(); for (unsigned i = 0, size = domainTypes.size(); i < size; i++) { sorts.push_back(domainTypes[i]); // the introduced variable is internal (not parsable) std::stringstream ss; ss << "__flatten_var_" << i; - Expr v = getExprManager()->mkBoundVar(ss.str(), domainTypes[i]); + api::Term v = d_solver->mkVar(domainTypes[i], ss.str()); flattenVars.push_back(v); } - range = static_cast(range).getRangeType(); + range = range.getFunctionCodomainSort(); } if (sorts.empty()) { return range; } - return getExprManager()->mkFunctionType(sorts, range); + return d_solver->mkFunctionSort(sorts, range); } -Type Parser::mkFlatFunctionType(std::vector& sorts, Type range) +api::Sort Parser::mkFlatFunctionType(std::vector& sorts, + api::Sort range) { if (sorts.empty()) { @@ -485,7 +532,7 @@ Type Parser::mkFlatFunctionType(std::vector& sorts, Type range) if (Debug.isOn("parser")) { Debug("parser") << "mkFlatFunctionType: range " << range << " and domains "; - for (Type t : sorts) + for (api::Sort t : sorts) { Debug("parser") << " " << t; } @@ -493,19 +540,18 @@ Type Parser::mkFlatFunctionType(std::vector& sorts, Type range) } while (range.isFunction()) { - std::vector domainTypes = - static_cast(range).getArgTypes(); + std::vector domainTypes = range.getFunctionDomainSorts(); sorts.insert(sorts.end(), domainTypes.begin(), domainTypes.end()); - range = static_cast(range).getRangeType(); + range = range.getFunctionCodomainSort(); } - return getExprManager()->mkFunctionType(sorts, range); + return d_solver->mkFunctionSort(sorts, range); } -Expr Parser::mkHoApply(Expr expr, std::vector& args) +api::Term Parser::mkHoApply(api::Term expr, const std::vector& args) { for (unsigned i = 0; i < args.size(); i++) { - expr = getExprManager()->mkExpr(HO_APPLY, expr, args[i]); + expr = d_solver->mkTerm(api::HO_APPLY, expr, args[i]); } return expr; } @@ -581,6 +627,15 @@ api::Term Parser::applyTypeAscription(api::Term t, api::Sort s) return t; } +//!!!!!!!!!!! temporary +api::Term Parser::mkVar(const std::string& name, + const api::Sort& type, + uint32_t flags) +{ + return api::Term(getExprManager()->mkVar(name, type.getType(), flags)); +} +//!!!!!!!!!!! temporary + bool Parser::isDeclared(const std::string& name, SymbolType type) { switch (type) { case SYM_VARIABLE: @@ -632,7 +687,7 @@ void Parser::checkDeclaration(const std::string& varName, } } -void Parser::checkFunctionLike(Expr fun) +void Parser::checkFunctionLike(api::Term fun) { if (d_checksEnabled && !isFunctionLike(fun)) { stringstream ss; @@ -643,39 +698,7 @@ void Parser::checkFunctionLike(Expr fun) } } -void Parser::checkArity(Kind kind, unsigned numArgs) -{ - if (!d_checksEnabled) { - return; - } - - unsigned min = getExprManager()->minArity(kind); - unsigned max = getExprManager()->maxArity(kind); - - if (numArgs < min || numArgs > max) { - stringstream ss; - ss << "Expecting "; - if (numArgs < min) { - ss << "at least " << min << " "; - } else { - ss << "at most " << max << " "; - } - ss << "arguments for operator '" << kind << "', "; - ss << "found " << numArgs; - parseError(ss.str()); - } -} - -void Parser::checkOperator(Kind kind, unsigned numArgs) -{ - if (d_strictMode && d_logicOperators.find(kind) == d_logicOperators.end()) { - parseError("Operator is not defined in the current logic: " + - kindToString(kind)); - } - checkArity(kind, numArgs); -} - -void Parser::addOperator(Kind kind) { d_logicOperators.insert(kind); } +void Parser::addOperator(api::Kind kind) { d_logicOperators.insert(kind); } void Parser::preemptCommand(Command* cmd) { d_commandQueue.push_back(cmd); } Command* Parser::nextCommand() diff --git a/src/parser/parser.h b/src/parser/parser.h index d40236208..373da6c47 100644 --- a/src/parser/parser.h +++ b/src/parser/parser.h @@ -42,9 +42,6 @@ class Command; class FunctionType; class Type; class ResourceManager; -namespace api { -class Solver; -} //for sygus gterm two-pass parsing class CVC4_PUBLIC SygusGTerm { @@ -59,10 +56,10 @@ public: gterm_unresolved, gterm_ignore, }; - Type d_type; + api::Sort d_type; /** The parsed operator */ ParseOp d_op; - std::vector< Expr > d_let_vars; + std::vector d_let_vars; unsigned d_gterm_type; std::string d_name; std::vector< SygusGTerm > d_children; @@ -214,7 +211,7 @@ private: std::string d_forcedLogic; /** The set of operators available in the current logic. */ - std::set d_logicOperators; + std::set d_logicOperators; /** The set of attributes already warned about. */ std::set d_attributesWarnedAbout; @@ -226,7 +223,7 @@ private: * depend on mkMutualDatatypeTypes() to check everything and clear * this out. */ - std::set d_unresolved; + std::set d_unresolved; /** * "Preemption commands": extra commands implied by subterms that @@ -240,7 +237,7 @@ private: /** Lookup a symbol in the given namespace (as specified by the type). * Only returns a symbol if it is not overloaded, returns null otherwise. */ - Expr getSymbol(const std::string& var_name, SymbolType type); + api::Term getSymbol(const std::string& var_name, SymbolType type); protected: /** The API Solver object. */ @@ -340,7 +337,7 @@ public: * @return the variable expression * Only returns a variable if its name is not overloaded, returns null otherwise. */ - Expr getVariable(const std::string& name); + api::Term getVariable(const std::string& name); /** * Gets the function currently bound to name. @@ -349,7 +346,7 @@ public: * @return the variable expression * Only returns a function if its name is not overloaded, returns null otherwise. */ - Expr getFunction(const std::string& name); + api::Term getFunction(const std::string& name); /** * Returns the expression that name should be interpreted as, based on the current binding. @@ -360,15 +357,16 @@ public: * a nullary constructor or a defined function. * Only returns an expression if its name is not overloaded, returns null otherwise. */ - virtual Expr getExpressionForName(const std::string& name); - + virtual api::Term getExpressionForName(const std::string& name); + /** * Returns the expression that name should be interpreted as, based on the current binding. * * This is the same as above but where the name has been type cast to t. */ - virtual Expr getExpressionForNameAndType(const std::string& name, Type t); - + virtual api::Term getExpressionForNameAndType(const std::string& name, + api::Sort t); + /** * Returns the kind that should be used for applications of expression fun. * This is a generalization of ExprManager::operatorToKind that also @@ -379,19 +377,19 @@ public: * APPLY_UF if fun has function type, * APPLY_CONSTRUCTOR if fun has constructor type. */ - Kind getKindForFunction(Expr fun); - + api::Kind getKindForFunction(api::Term fun); + /** * Returns a sort, given a name. * @param sort_name the name to look up */ - Type getSort(const std::string& sort_name); + api::Sort getSort(const std::string& sort_name); /** * Returns a (parameterized) sort, given a name and args. */ - Type getSort(const std::string& sort_name, - const std::vector& params); + api::Sort getSort(const std::string& sort_name, + const std::vector& params); /** * Returns arity of a (parameterized) sort, given a name and args. @@ -434,28 +432,7 @@ public: * @throws ParserException if checks are enabled and fun is not * a function */ - void checkFunctionLike(Expr fun); - - /** - * Check that kind can accept numArgs arguments. - * @param kind the built-in operator to check - * @param numArgs the number of actual arguments - * @throws ParserException if checks are enabled and the operator - * kind cannot be applied to numArgs - * arguments. - */ - void checkArity(Kind kind, unsigned numArgs); - - /** - * Check that kind is a legal operator in the current - * logic and that it can accept numArgs arguments. - * - * @param kind the built-in operator to check - * @param numArgs the number of actual arguments - * @throws ParserException if the parser mode is strict and the - * operator kind has not been enabled - */ - void checkOperator(Kind kind, unsigned numArgs); + void checkFunctionLike(api::Term fun); /** Create a new CVC4 variable expression of the given type. * @@ -466,9 +443,10 @@ public: * then if doOverload is true, we create overloaded operators. * else if doOverload is false, the existing expression is shadowed by the new expression. */ - Expr mkVar(const std::string& name, const Type& type, - uint32_t flags = ExprManager::VAR_FLAG_NONE, - bool doOverload = false); + api::Term bindVar(const std::string& name, + const api::Sort& type, + uint32_t flags = ExprManager::VAR_FLAG_NONE, + bool doOverload = false); /** * Create a set of new CVC4 variable expressions of the given type. @@ -480,23 +458,23 @@ public: * then if doOverload is true, we create overloaded operators. * else if doOverload is false, the existing expression is shadowed by the new expression. */ - std::vector - mkVars(const std::vector names, const Type& type, - uint32_t flags = ExprManager::VAR_FLAG_NONE, - bool doOverload = false); + std::vector bindVars(const std::vector names, + const api::Sort& type, + uint32_t flags = ExprManager::VAR_FLAG_NONE, + bool doOverload = false); /** * Create a new CVC4 bound variable expression of the given type. This binds * the symbol name to that variable in the current scope. */ - Expr mkBoundVar(const std::string& name, const Type& type); + api::Term bindBoundVar(const std::string& name, const api::Sort& type); /** * Create a new CVC4 bound variable expressions of the given names and types. * Like the method above, this binds these names to those variables in the * current scope. */ - std::vector mkBoundVars( - std::vector >& sortedVarNames); + std::vector bindBoundVars( + std::vector >& sortedVarNames); /** * Create a set of new CVC4 bound variable expressions of the given type. @@ -508,7 +486,8 @@ public: * then if doOverload is true, we create overloaded operators. * else if doOverload is false, the existing expression is shadowed by the new expression. */ - std::vector mkBoundVars(const std::vector names, const Type& type); + std::vector bindBoundVars(const std::vector names, + const api::Sort& type); /** * Create a new CVC4 function expression of the given type, @@ -518,8 +497,9 @@ public: * flags specify information about the variable, e.g. whether it is global or defined * (see enum in expr_manager_template.h). */ - Expr mkAnonymousFunction(const std::string& prefix, const Type& type, - uint32_t flags = ExprManager::VAR_FLAG_NONE); + api::Term mkAnonymousFunction(const std::string& prefix, + const api::Sort& type, + uint32_t flags = ExprManager::VAR_FLAG_NONE); /** Create a new variable definition (e.g., from a let binding). * levelZero is set if the binding must be done at level 0. @@ -527,8 +507,10 @@ public: * then if doOverload is true, we create overloaded operators. * else if doOverload is false, the existing expression is shadowed by the new expression. */ - void defineVar(const std::string& name, const Expr& val, - bool levelZero = false, bool doOverload = false); + void defineVar(const std::string& name, + const api::Term& val, + bool levelZero = false, + bool doOverload = false); /** * Create a new type definition. @@ -539,7 +521,7 @@ public: * cannot be removed by poppoing the user context */ void defineType(const std::string& name, - const Type& type, + const api::Sort& type, bool levelZero = false); /** @@ -552,46 +534,44 @@ public: * cannot be removed by poppoing the user context */ void defineType(const std::string& name, - const std::vector& params, - const Type& type, + const std::vector& params, + const api::Sort& type, bool levelZero = false); /** Create a new type definition (e.g., from an SMT-LIBv2 define-sort). */ void defineParameterizedType(const std::string& name, - const std::vector& params, - const Type& type); + const std::vector& params, + const api::Sort& type); /** * Creates a new sort with the given name. */ - SortType mkSort(const std::string& name, - uint32_t flags = ExprManager::SORT_FLAG_NONE); + api::Sort mkSort(const std::string& name, + uint32_t flags = ExprManager::SORT_FLAG_NONE); /** * Creates a new sort constructor with the given name and arity. */ - SortConstructorType mkSortConstructor( - const std::string& name, - size_t arity, - uint32_t flags = ExprManager::SORT_FLAG_NONE); + api::Sort mkSortConstructor(const std::string& name, + size_t arity, + uint32_t flags = ExprManager::SORT_FLAG_NONE); /** * Creates a new "unresolved type," used only during parsing. */ - SortType mkUnresolvedType(const std::string& name); + api::Sort mkUnresolvedType(const std::string& name); /** * Creates a new unresolved (parameterized) type constructor of the given * arity. */ - SortConstructorType mkUnresolvedTypeConstructor(const std::string& name, - size_t arity); + api::Sort mkUnresolvedTypeConstructor(const std::string& name, size_t arity); /** * Creates a new unresolved (parameterized) type constructor given the type * parameters. */ - SortConstructorType mkUnresolvedTypeConstructor(const std::string& name, - const std::vector& params); + api::Sort mkUnresolvedTypeConstructor(const std::string& name, + const std::vector& params); /** * Returns true IFF name is an unresolved type. @@ -651,9 +631,9 @@ public: * where @ is (higher-order) application. In this example, z is added to * flattenVars. */ - Type mkFlatFunctionType(std::vector& sorts, - Type range, - std::vector& flattenVars); + api::Sort mkFlatFunctionType(std::vector& sorts, + api::Sort range, + std::vector& flattenVars); /** make flat function type * @@ -661,7 +641,7 @@ public: * This is used when the arguments of the function are not important (for * instance, if we are only using this type in a declare-fun). */ - Type mkFlatFunctionType(std::vector& sorts, Type range); + api::Sort mkFlatFunctionType(std::vector& sorts, api::Sort range); /** make higher-order apply * @@ -676,7 +656,7 @@ public: * for each i where 0 <= i < args.size(). If expr is not of this * type, the expression returned by this method will not be well typed. */ - Expr mkHoApply(Expr expr, std::vector& args); + api::Term mkHoApply(api::Term expr, const std::vector& args); /** Apply type ascription * @@ -702,12 +682,21 @@ public: */ api::Term applyTypeAscription(api::Term t, api::Sort s); + //!!!!!!!!!!! temporary + /** + * Make var, with flags required by the ExprManager, see ExprManager::mkVar. + */ + api::Term mkVar(const std::string& name, + const api::Sort& type, + uint32_t flags); + //!!!!!!!!!!! temporary + /** * Add an operator to the current legal set. * * @param kind the built-in operator to add */ - void addOperator(Kind kind); + void addOperator(api::Kind kind); /** * Preempt the next returned command with other ones; used to @@ -723,7 +712,7 @@ public: /** Is fun a function (or function-like thing)? * Currently this means its type is either a function, constructor, tester, or selector. */ - bool isFunctionLike(Expr fun); + bool isFunctionLike(api::Term fun); /** Is the symbol bound to a predicate? */ bool isPredicate(const std::string& name); @@ -864,25 +853,30 @@ public: //------------------------ operator overloading /** is this function overloaded? */ - bool isOverloadedFunction(Expr fun) { - return d_symtab->isOverloadedFunction(fun); + bool isOverloadedFunction(api::Term fun) + { + return d_symtab->isOverloadedFunction(fun.getExpr()); } - + /** Get overloaded constant for type. * If possible, it returns a defined symbol with name * that has type t. Otherwise returns null expression. */ - Expr getOverloadedConstantForType(const std::string& name, Type t) { - return d_symtab->getOverloadedConstantForType(name, t); + api::Term getOverloadedConstantForType(const std::string& name, api::Sort t) + { + return d_symtab->getOverloadedConstantForType(name, t.getType()); } - + /** * If possible, returns a defined function for a name * and a vector of expected argument types. Otherwise returns * null expression. */ - Expr getOverloadedFunctionForTypes(const std::string& name, std::vector< Type >& argTypes) { - return d_symtab->getOverloadedFunctionForTypes(name, argTypes); + api::Term getOverloadedFunctionForTypes(const std::string& name, + std::vector& argTypes) + { + return d_symtab->getOverloadedFunctionForTypes( + name, api::sortVectorToTypes(argTypes)); } //------------------------ end operator overloading };/* class Parser */ diff --git a/src/parser/smt2/Smt2.g b/src/parser/smt2/Smt2.g index 9ae9f7261..cd661364d 100644 --- a/src/parser/smt2/Smt2.g +++ b/src/parser/smt2/Smt2.g @@ -87,24 +87,26 @@ using namespace CVC4::parser; namespace CVC4 { class Expr; + namespace api { + class Term; + class Sort; + } + namespace parser { namespace smt2 { /** * Just exists to provide the uintptr_t constructor that ANTLR * requires. */ - struct myExpr : public CVC4::Expr { - myExpr() : CVC4::Expr() {} - myExpr(void*) : CVC4::Expr() {} - myExpr(const Expr& e) : CVC4::Expr(e) {} - myExpr(const myExpr& e) : CVC4::Expr(e) {} + struct myExpr : public CVC4::api::Term { + myExpr() : CVC4::api::Term() {} + myExpr(void*) : CVC4::api::Term() {} + myExpr(const Expr& e) : CVC4::api::Term(e) {} + myExpr(const myExpr& e) : CVC4::api::Term(e) {} };/* struct myExpr */ }/* CVC4::parser::smt2 namespace */ }/* CVC4::parser namespace */ - namespace api { - class Term; - } }/* CVC4 namespace */ }/* @parser::includes */ @@ -141,14 +143,10 @@ using namespace CVC4::parser; * PARSER would be undefined.) */ #undef PARSER_STATE #define PARSER_STATE ((Smt2*)PARSER->super) -#undef EXPR_MANAGER -#define EXPR_MANAGER PARSER_STATE->getExprManager() -#undef MK_EXPR -#define MK_EXPR EXPR_MANAGER->mkExpr -#undef MK_CONST -#define MK_CONST EXPR_MANAGER->mkConst #undef SOLVER #define SOLVER PARSER_STATE->getSolver() +#undef MK_TERM +#define MK_TERM SOLVER->mkTerm #define UNSUPPORTED PARSER_STATE->unimplementedFeature }/* parser::postinclude */ @@ -160,7 +158,7 @@ using namespace CVC4::parser; */ parseExpr returns [CVC4::parser::smt2::myExpr expr] @declarations { - Expr expr2; + CVC4::api::Term expr2; } : term[expr, expr2] | EOF @@ -225,12 +223,12 @@ command [std::unique_ptr* cmd] @declarations { std::string name; std::vector names; - Expr expr, expr2; - Type t; - std::vector terms; - std::vector sorts; - std::vector > sortedVarNames; - std::vector flattenVars; + CVC4::api::Term expr, expr2; + CVC4::api::Sort t; + std::vector terms; + std::vector sorts; + std::vector > sortedVarNames; + std::vector flattenVars; } : /* set the logic */ SET_LOGIC_TOK symbol[name,CHECK_NONE,SYM_SORT] @@ -267,11 +265,11 @@ command [std::unique_ptr* cmd] << "' arity=" << n << std::endl; unsigned arity = AntlrInput::tokenToUnsigned(n); if(arity == 0) { - Type type = PARSER_STATE->mkSort(name); - cmd->reset(new DeclareTypeCommand(name, 0, type)); + api::Sort type = PARSER_STATE->mkSort(name); + cmd->reset(new DeclareTypeCommand(name, 0, type.getType())); } else { - Type type = PARSER_STATE->mkSortConstructor(name, arity); - cmd->reset(new DeclareTypeCommand(name, arity, type)); + api::Sort type = PARSER_STATE->mkSortConstructor(name, arity); + cmd->reset(new DeclareTypeCommand(name, arity, type.getType())); } } | /* sort definition */ @@ -291,8 +289,9 @@ command [std::unique_ptr* cmd] { PARSER_STATE->popScope(); // Do NOT call mkSort, since that creates a new sort! // This name is not its own distinct sort, it's an alias. - PARSER_STATE->defineParameterizedType(name, sorts, t); - cmd->reset(new DefineTypeCommand(name, sorts, t)); + PARSER_STATE->defineParameterizedType(name, sorts, t.getType()); + cmd->reset(new DefineTypeCommand( + name, api::sortVectorToTypes(sorts), t.getType())); } | /* function declaration */ DECLARE_FUN_TOK { PARSER_STATE->checkThatLogicIsSet(); } @@ -315,8 +314,9 @@ command [std::unique_ptr* cmd] if (PARSER_STATE->sygus_v1()) { // it is a higher-order universal variable - Expr func = PARSER_STATE->mkBoundVar(name, t); - cmd->reset(new DeclareSygusFunctionCommand(name, func, t)); + api::Term func = PARSER_STATE->bindBoundVar(name, t); + cmd->reset( + new DeclareSygusFunctionCommand(name, func.getExpr(), t.getType())); } else if( PARSER_STATE->sygus() ) { @@ -325,8 +325,10 @@ command [std::unique_ptr* cmd] } else { - Expr func = PARSER_STATE->mkVar(name, t, ExprManager::VAR_FLAG_NONE, true); - cmd->reset(new DeclareFunctionCommand(name, func, t)); + api::Term func = + PARSER_STATE->bindVar(name, t, ExprManager::VAR_FLAG_NONE, true); + cmd->reset( + new DeclareFunctionCommand(name, func.getExpr(), t.getType())); } } | /* function definition */ @@ -339,7 +341,7 @@ command [std::unique_ptr* cmd] Debug("parser") << "define fun: '" << name << "'" << std::endl; if( sortedVarNames.size() > 0 ) { sorts.reserve(sortedVarNames.size()); - for(std::vector >::const_iterator i = + for(std::vector >::const_iterator i = sortedVarNames.begin(), iend = sortedVarNames.end(); i != iend; ++i) { @@ -348,7 +350,7 @@ command [std::unique_ptr* cmd] t = PARSER_STATE->mkFlatFunctionType(sorts, t, flattenVars); } PARSER_STATE->pushScope(true); - terms = PARSER_STATE->mkBoundVars(sortedVarNames); + terms = PARSER_STATE->bindBoundVars(sortedVarNames); } term[expr, expr2] { @@ -363,16 +365,17 @@ command [std::unique_ptr* cmd] // must not be extended with the name itself; no recursion // permitted) // we allow overloading for function definitions - Expr func = PARSER_STATE->mkVar(name, t, + api::Term func = PARSER_STATE->bindVar(name, t, ExprManager::VAR_FLAG_DEFINED, true); - cmd->reset(new DefineFunctionCommand(name, func, terms, expr)); + cmd->reset(new DefineFunctionCommand( + name, func.getExpr(), api::termVectorToExprs(terms), expr.getExpr())); } | DECLARE_DATATYPE_TOK datatypeDefCommand[false, cmd] | DECLARE_DATATYPES_TOK datatypesDefCommand[false, cmd] | /* value query */ GET_VALUE_TOK { PARSER_STATE->checkThatLogicIsSet(); } ( LPAREN_TOK termList[terms,expr] RPAREN_TOK - { cmd->reset(new GetValueCommand(terms)); } + { cmd->reset(new GetValueCommand(api::termVectorToExprs(terms))); } | ~LPAREN_TOK { PARSER_STATE->parseError("The get-value command expects a list of " "terms. Perhaps you forgot a pair of " @@ -387,11 +390,13 @@ command [std::unique_ptr* cmd] { PARSER_STATE->clearLastNamedTerm(); } term[expr, expr2] { bool inUnsatCore = PARSER_STATE->lastNamedTerm().first == expr; - cmd->reset(new AssertCommand(expr, inUnsatCore)); + cmd->reset(new AssertCommand(expr.getExpr(), inUnsatCore)); if(inUnsatCore) { // set the expression name, if there was a named term - std::pair namedTerm = PARSER_STATE->lastNamedTerm(); - Command* csen = new SetExpressionNameCommand(namedTerm.first, namedTerm.second); + std::pair namedTerm = + PARSER_STATE->lastNamedTerm(); + Command* csen = new SetExpressionNameCommand(namedTerm.first.getExpr(), + namedTerm.second); csen->setMuted(true); PARSER_STATE->preemptCommand(csen); } @@ -409,13 +414,15 @@ command [std::unique_ptr* cmd] "permitted while operating in strict compliance mode."); } } - | { expr = Expr(); } + | { expr = api::Term(); } ) - { cmd->reset(new CheckSatCommand(expr)); } + { cmd->reset(new CheckSatCommand(expr.getExpr())); } | /* check-sat-assuming */ CHECK_SAT_ASSUMING_TOK { PARSER_STATE->checkThatLogicIsSet(); } ( LPAREN_TOK termList[terms,expr] RPAREN_TOK - { cmd->reset(new CheckSatAssumingCommand(terms)); } + { + cmd->reset(new CheckSatAssumingCommand(api::termVectorToExprs(terms))); + } | ~LPAREN_TOK { PARSER_STATE->parseError("The check-sat-assuming command expects a " "list of terms. Perhaps you forgot a pair of " @@ -544,14 +551,14 @@ command [std::unique_ptr* cmd] sygusCommand returns [std::unique_ptr cmd] @declarations { - Expr expr, expr2; - Type t, range; + CVC4::api::Term expr, expr2; + CVC4::api::Sort t, range; std::vector names; - std::vector > sortedVarNames; + std::vector > sortedVarNames; std::unique_ptr synthFunFactory; std::string name, fun; bool isInv; - Type grammar; + CVC4::api::Sort grammar; } : /* declare-var */ DECLARE_VAR_TOK { PARSER_STATE->checkThatLogicIsSet(); } @@ -559,8 +566,8 @@ sygusCommand returns [std::unique_ptr cmd] { PARSER_STATE->checkUserSymbol(name); } sortSymbol[t,CHECK_DECLARED] { - Expr var = PARSER_STATE->mkBoundVar(name, t); - cmd.reset(new DeclareSygusVarCommand(name, var, t)); + api::Term var = PARSER_STATE->bindBoundVar(name, t); + cmd.reset(new DeclareSygusVarCommand(name, var.getExpr(), t.getType())); } | /* declare-primed-var */ DECLARE_PRIMED_VAR_TOK { PARSER_STATE->checkThatLogicIsSet(); } @@ -570,12 +577,12 @@ sygusCommand returns [std::unique_ptr cmd] { // spurious command, we do not need to create a variable. We only keep // track of the command for sanity checking / dumping - cmd.reset(new DeclareSygusPrimedVarCommand(name, t)); + cmd.reset(new DeclareSygusPrimedVarCommand(name, t.getType())); } | /* synth-fun */ ( SYNTH_FUN_V1_TOK { isInv = false; } - | SYNTH_INV_V1_TOK { isInv = true; range = EXPR_MANAGER->booleanType(); } + | SYNTH_INV_V1_TOK { isInv = true; range = SOLVER->getBooleanSort(); } ) { PARSER_STATE->checkThatLogicIsSet(); } symbol[fun,CHECK_UNDECLARED,SYM_VARIABLE] @@ -597,7 +604,7 @@ sygusCommand returns [std::unique_ptr cmd] } | /* synth-fun */ ( SYNTH_FUN_TOK { isInv = false; } - | SYNTH_INV_TOK { isInv = true; range = EXPR_MANAGER->booleanType(); } + | SYNTH_INV_TOK { isInv = true; range = SOLVER->getBooleanSort(); } ) { PARSER_STATE->checkThatLogicIsSet(); } symbol[fun,CHECK_UNDECLARED,SYM_VARIABLE] @@ -625,7 +632,7 @@ sygusCommand returns [std::unique_ptr cmd] } term[expr, expr2] { Debug("parser-sygus") << "...read constraint " << expr << std::endl; - cmd.reset(new SygusConstraintCommand(expr)); + cmd.reset(new SygusConstraintCommand(expr.getExpr())); } | /* inv-constraint */ INV_CONSTRAINT_TOK @@ -651,24 +658,24 @@ sygusCommand returns [std::unique_ptr cmd] * The argument fun is a unique identifier to avoid naming clashes for the * datatypes constructed by this call. */ -sygusGrammarV1[CVC4::Type & ret, - const std::vector& sygus_vars, +sygusGrammarV1[CVC4::api::Sort & ret, + const std::vector& sygus_vars, const std::string& fun] @declarations { - Type t; + CVC4::api::Sort t; std::string name; unsigned startIndex = 0; std::vector> sgts; std::vector datatypes; - std::vector sorts; + std::vector sorts; std::vector> ops; std::vector> cnames; - std::vector>> cargs; + std::vector>> cargs; std::vector allow_const; std::vector> unresolved_gterm_sym; - std::map sygus_to_builtin; - std::map sygus_to_builtin_expr; + std::map sygus_to_builtin; + std::map sygus_to_builtin_expr; } : LPAREN_TOK { PARSER_STATE->pushScope(); } (LPAREN_TOK @@ -688,7 +695,7 @@ sygusGrammarV1[CVC4::Type & ret, cargs, allow_const, unresolved_gterm_sym); - Type unres_t; + api::Sort unres_t; if (!PARSER_STATE->isUnresolvedType(name)) { // if not unresolved, must be undeclared @@ -724,7 +731,7 @@ sygusGrammarV1[CVC4::Type & ret, { for (unsigned j = 0, size = sgts[i].size(); j < size; j++) { - Type sub_ret; + api::Sort sub_ret; PARSER_STATE->processSygusGTerm(sgts[i][j], i, datatypes, @@ -748,10 +755,10 @@ sygusGrammarV1[CVC4::Type & ret, Debug("parser-sygus") << "..." << datatypes[i].getName() << " has builtin sort " << sorts[i] << std::endl; } - Expr bvl; + api::Term bvl; if (!sygus_vars.empty()) { - bvl = MK_EXPR(kind::BOUND_VAR_LIST, sygus_vars); + bvl = MK_TERM(api::BOUND_VAR_LIST, sygus_vars); } for (unsigned i = 0; i < ndatatypes; i++) { @@ -763,7 +770,8 @@ sygusGrammarV1[CVC4::Type & ret, "Internal error : could not infer " "builtin sort for nested gterm."); } - datatypes[i].setSygus(sorts[i], bvl, allow_const[i], false); + datatypes[i].setSygus( + sorts[i].getType(), bvl.getExpr(), allow_const[i], false); PARSER_STATE->mkSygusDatatype(datatypes[i], ops[i], cnames[i], @@ -796,10 +804,10 @@ sygusGrammarV1[CVC4::Type & ret, sygusGTerm[CVC4::SygusGTerm& sgt, const std::string& fun] @declarations { std::string name, name2; - Kind k; - Type t; + CVC4::api::Kind k; + CVC4::api::Sort t; std::string sname; - std::vector< Expr > let_vars; + std::vector< CVC4::api::Term > let_vars; std::string s; CVC4::api::Term atomTerm; } @@ -833,7 +841,7 @@ sygusGTerm[CVC4::SygusGTerm& sgt, const std::string& fun] Debug("parser-sygus") << "Sygus grammar " << fun << " : builtin op : " << name << std::endl; k = PARSER_STATE->getOperatorKind(name); - sgt.d_name = kind::kindToString(k); + sgt.d_name = api::kindToString(k); sgt.d_gterm_type = SygusGTerm::gterm_op; sgt.d_op.d_kind = k; }else{ @@ -886,7 +894,7 @@ sygusGTerm[CVC4::SygusGTerm& sgt, const std::string& fun] Debug("parser-sygus") << "Sygus grammar " << fun << " : unary minus integer literal " << name << std::endl; - sgt.d_op.d_expr = MK_CONST(Rational(name)); + sgt.d_op.d_expr = SOLVER->mkReal(name); sgt.d_name = name; sgt.d_gterm_type = SygusGTerm::gterm_op; }else if( PARSER_STATE->isDeclared(name,SYM_VARIABLE) ){ @@ -922,21 +930,21 @@ sygusGTerm[CVC4::SygusGTerm& sgt, const std::string& fun] * The argument fun is a unique identifier to avoid naming clashes for the * datatypes constructed by this call. */ -sygusGrammar[CVC4::Type & ret, - const std::vector& sygusVars, +sygusGrammar[CVC4::api::Sort & ret, + const std::vector& sygusVars, const std::string& fun] @declarations { // the pre-declaration - std::vector > sortedVarNames; + std::vector > sortedVarNames; // non-terminal symbols of the grammar - std::vector ntSyms; - Type t; + std::vector ntSyms; + CVC4::api::Sort t; std::string name; - Expr e, e2; + CVC4::api::Term e, e2; std::vector datatypes; - std::vector unresTypes; - std::map ntsToUnres; + std::vector unresTypes; + std::map ntsToUnres; unsigned dtProcessed = 0; std::unordered_set allowConst; } @@ -946,20 +954,20 @@ sygusGrammar[CVC4::Type & ret, { // non-terminal symbols in the pre-declaration are locally scoped PARSER_STATE->pushScope(true); - for (std::pair& i : sortedVarNames) + for (std::pair& i : sortedVarNames) { Trace("parser-sygus2") << "Declare datatype " << i.first << std::endl; // make the datatype, which encodes terms generated by this non-terminal std::string dname = i.first; - datatypes.push_back(Datatype(EXPR_MANAGER, dname)); + datatypes.push_back(Datatype(PARSER_STATE->getExprManager(), dname)); // make its unresolved type, used for referencing the final version of // the datatype PARSER_STATE->checkDeclaration(dname, CHECK_UNDECLARED, SYM_SORT); - Type urt = PARSER_STATE->mkUnresolvedType(dname); + api::Sort urt = PARSER_STATE->mkUnresolvedType(dname); unresTypes.push_back(urt); // make the non-terminal symbol, which will be parsed as an ordinary // free variable. - Expr nts = PARSER_STATE->mkBoundVar(i.first, i.second); + api::Term nts = PARSER_STATE->bindBoundVar(i.first, i.second); ntSyms.push_back(nts); ntsToUnres[nts] = urt; } @@ -1019,17 +1027,17 @@ sygusGrammar[CVC4::Type & ret, "Number of grouped rule listings does not match " "number of symbols in predeclaration."); } - Expr bvl; + api::Term bvl; if (!sygusVars.empty()) { - bvl = MK_EXPR(kind::BOUND_VAR_LIST, sygusVars); + bvl = MK_TERM(api::BOUND_VAR_LIST, sygusVars); } Trace("parser-sygus2") << "Process " << dtProcessed << " sygus datatypes..." << std::endl; for (unsigned i = 0; i < dtProcessed; i++) { bool aci = allowConst.find(i)!=allowConst.end(); - Type btt = sortedVarNames[i].second; - datatypes[i].setSygus(btt, bvl, aci, false); + api::Sort btt = sortedVarNames[i].second; + datatypes[i].setSygus(btt.getType(), bvl.getExpr(), aci, false); Trace("parser-sygus2") << "- " << datatypes[i].getName() << ", #cons= " << datatypes[i].getNumConstructors() << ", aci= " << aci << std::endl; @@ -1089,21 +1097,22 @@ smt25Command[std::unique_ptr* cmd] @declarations { std::string name; std::string fname; - Expr expr, expr2; - std::vector > sortedVarNames; + CVC4::api::Term expr, expr2; + std::vector > sortedVarNames; SExpr sexpr; - Type t; - Expr func; - std::vector bvs; - std::vector< std::vector > > sortedVarNamesList; - std::vector> flattenVarsList; - std::vector> formals; - std::vector funcs; - std::vector func_defs; - Expr aexpr; + CVC4::api::Sort t; + CVC4::api::Term func; + std::vector bvs; + std::vector>> + sortedVarNamesList; + std::vector> flattenVarsList; + std::vector> formals; + std::vector funcs; + std::vector func_defs; + CVC4::api::Term aexpr; std::unique_ptr seq; - std::vector sorts; - std::vector flattenVars; + std::vector sorts; + std::vector flattenVars; } /* declare-const */ : DECLARE_CONST_TOK { PARSER_STATE->checkThatLogicIsSet(); } @@ -1111,8 +1120,9 @@ smt25Command[std::unique_ptr* cmd] { PARSER_STATE->checkUserSymbol(name); } sortSymbol[t,CHECK_DECLARED] { // allow overloading here - Expr c = PARSER_STATE->mkVar(name, t, ExprManager::VAR_FLAG_NONE, true); - cmd->reset(new DeclareFunctionCommand(name, c, t)); } + api::Term c = + PARSER_STATE->bindVar(name, t, ExprManager::VAR_FLAG_NONE, true); + cmd->reset(new DeclareFunctionCommand(name, c.getExpr(), t.getType())); } /* get model */ | GET_MODEL_TOK { PARSER_STATE->checkThatLogicIsSet(); } @@ -1144,15 +1154,18 @@ smt25Command[std::unique_ptr* cmd] LPAREN_TOK sortedVarList[sortedVarNames] RPAREN_TOK sortSymbol[t,CHECK_DECLARED] { - func = PARSER_STATE->mkDefineFunRec(fname, sortedVarNames, t, flattenVars); - PARSER_STATE->pushDefineFunRecScope(sortedVarNames, func, flattenVars, bvs, true ); + func = + PARSER_STATE->bindDefineFunRec(fname, sortedVarNames, t, flattenVars); + PARSER_STATE->pushDefineFunRecScope( + sortedVarNames, func, flattenVars, bvs, true); } term[expr, expr2] { PARSER_STATE->popScope(); if( !flattenVars.empty() ){ expr = PARSER_STATE->mkHoApply( expr, flattenVars ); } - cmd->reset(new DefineFunctionRecCommand(func,bvs,expr)); + cmd->reset(new DefineFunctionRecCommand( + func.getExpr(), api::termVectorToExprs(bvs), expr.getExpr())); } | DEFINE_FUNS_REC_TOK { PARSER_STATE->checkThatLogicIsSet();} @@ -1164,7 +1177,8 @@ smt25Command[std::unique_ptr* cmd] sortSymbol[t,CHECK_DECLARED] { flattenVars.clear(); - func = PARSER_STATE->mkDefineFunRec( fname, sortedVarNames, t, flattenVars ); + func = PARSER_STATE->bindDefineFunRec( + fname, sortedVarNames, t, flattenVars); funcs.push_back( func ); // add to lists (need to remember for when parsing the bodies) @@ -1214,20 +1228,28 @@ smt25Command[std::unique_ptr* cmd] "Number of functions defined does not match number listed in " "define-funs-rec")); } - cmd->reset( new DefineFunctionRecCommand(funcs,formals,func_defs)); + std::vector> eformals; + for (unsigned i=0, fsize = formals.size(); ireset( + new DefineFunctionRecCommand(api::termVectorToExprs(funcs), + eformals, + api::termVectorToExprs(func_defs))); } ; extendedCommand[std::unique_ptr* cmd] @declarations { std::vector dts; - Expr e, e2; - Type t; + CVC4::api::Term e, e2; + CVC4::api::Sort t; std::string name; std::vector names; - std::vector terms; - std::vector sorts; - std::vector > sortedVarNames; + std::vector terms; + std::vector sorts; + std::vector > sortedVarNames; std::unique_ptr seq; } /* Extended SMT-LIB set of commands syntax, not permitted in @@ -1236,6 +1258,7 @@ extendedCommand[std::unique_ptr* cmd] | DECLARE_CODATATYPES_2_5_TOK datatypes_2_5_DefCommand[true, cmd] | DECLARE_CODATATYPE_TOK datatypeDefCommand[true, cmd] | DECLARE_CODATATYPES_TOK datatypesDefCommand[true, cmd] + /* Support some of Z3's extended SMT-LIB commands */ | DECLARE_SORTS_TOK { PARSER_STATE->checkThatLogicIsSet(); } @@ -1250,8 +1273,8 @@ extendedCommand[std::unique_ptr* cmd] LPAREN_TOK ( symbol[name,CHECK_UNDECLARED,SYM_SORT] { PARSER_STATE->checkUserSymbol(name); - Type type = PARSER_STATE->mkSort(name); - seq->addCommand(new DeclareTypeCommand(name, 0, type)); + api::Sort type = PARSER_STATE->mkSort(name); + seq->addCommand(new DeclareTypeCommand(name, 0, type.getType())); } )+ RPAREN_TOK @@ -1263,7 +1286,7 @@ extendedCommand[std::unique_ptr* cmd] ( LPAREN_TOK symbol[name,CHECK_UNDECLARED,SYM_VARIABLE] { PARSER_STATE->checkUserSymbol(name); } nonemptySortList[sorts] RPAREN_TOK - { Type tt; + { api::Sort tt; if(sorts.size() > 1) { if(!PARSER_STATE->isTheoryEnabled(Smt2::THEORY_UF)) { PARSER_STATE->parseError( @@ -1273,15 +1296,17 @@ extendedCommand[std::unique_ptr* cmd] + " unless option --uf-ho is used"); } // must flatten - Type range = sorts.back(); + api::Sort range = sorts.back(); sorts.pop_back(); tt = PARSER_STATE->mkFlatFunctionType(sorts, range); } else { tt = sorts[0]; } // allow overloading - Expr func = PARSER_STATE->mkVar(name, tt, ExprManager::VAR_FLAG_NONE, true); - seq->addCommand(new DeclareFunctionCommand(name, func, tt)); + api::Term func = + PARSER_STATE->bindVar(name, tt, ExprManager::VAR_FLAG_NONE, true); + seq->addCommand( + new DeclareFunctionCommand(name, func.getExpr(), tt.getType())); sorts.clear(); } )+ @@ -1293,7 +1318,7 @@ extendedCommand[std::unique_ptr* cmd] ( LPAREN_TOK symbol[name,CHECK_UNDECLARED,SYM_VARIABLE] { PARSER_STATE->checkUserSymbol(name); } sortList[sorts] RPAREN_TOK - { Type boolType = EXPR_MANAGER->booleanType(); + { t = SOLVER->getBooleanSort(); if(sorts.size() > 0) { if(!PARSER_STATE->isTheoryEnabled(Smt2::THEORY_UF)) { PARSER_STATE->parseError( @@ -1302,11 +1327,13 @@ extendedCommand[std::unique_ptr* cmd] + PARSER_STATE->getLogic().getLogicString() + " unless option --uf-ho is used"); } - boolType = EXPR_MANAGER->mkFunctionType(sorts, boolType); + t = SOLVER->mkFunctionSort(sorts, t); } // allow overloading - Expr func = PARSER_STATE->mkVar(name, boolType, ExprManager::VAR_FLAG_NONE, true); - seq->addCommand(new DeclareFunctionCommand(name, func, boolType)); + api::Term func = + PARSER_STATE->bindVar(name, t, ExprManager::VAR_FLAG_NONE, true); + seq->addCommand( + new DeclareFunctionCommand(name, func.getExpr(), t.getType())); sorts.clear(); } )+ @@ -1317,9 +1344,9 @@ extendedCommand[std::unique_ptr* cmd] ( symbol[name,CHECK_UNDECLARED,SYM_VARIABLE] { PARSER_STATE->checkUserSymbol(name); } term[e,e2] - { Expr func = PARSER_STATE->mkVar(name, e.getType(), + { api::Term func = PARSER_STATE->bindVar(name, e.getSort(), ExprManager::VAR_FLAG_DEFINED); - cmd->reset(new DefineFunctionCommand(name, func, e)); + cmd->reset(new DefineFunctionCommand(name, func.getExpr(), e.getExpr())); } | LPAREN_TOK symbol[name,CHECK_UNDECLARED,SYM_VARIABLE] @@ -1328,27 +1355,27 @@ extendedCommand[std::unique_ptr* cmd] { /* add variables to parser state before parsing term */ Debug("parser") << "define fun: '" << name << "'" << std::endl; PARSER_STATE->pushScope(true); - terms = PARSER_STATE->mkBoundVars(sortedVarNames); + terms = PARSER_STATE->bindBoundVars(sortedVarNames); } term[e,e2] { PARSER_STATE->popScope(); // declare the name down here (while parsing term, signature // must not be extended with the name itself; no recursion // permitted) - Type tt = e.getType(); + api::Sort tt = e.getSort(); if( sortedVarNames.size() > 0 ) { - std::vector types; - types.reserve(sortedVarNames.size()); - for(std::vector >::const_iterator + sorts.reserve(sortedVarNames.size()); + for(std::vector >::const_iterator i = sortedVarNames.begin(), iend = sortedVarNames.end(); i != iend; ++i) { - types.push_back((*i).second); + sorts.push_back((*i).second); } - tt = EXPR_MANAGER->mkFunctionType(types, tt); + tt = SOLVER->mkFunctionSort(sorts, tt); } - Expr func = PARSER_STATE->mkVar(name, tt, + api::Term func = PARSER_STATE->bindVar(name, tt, ExprManager::VAR_FLAG_DEFINED); - cmd->reset(new DefineFunctionCommand(name, func, terms, e)); + cmd->reset(new DefineFunctionCommand( + name, func.getExpr(), api::termVectorToExprs(terms), e.getExpr())); } ) | DEFINE_CONST_TOK { PARSER_STATE->checkThatLogicIsSet(); } @@ -1358,37 +1385,38 @@ extendedCommand[std::unique_ptr* cmd] { /* add variables to parser state before parsing term */ Debug("parser") << "define const: '" << name << "'" << std::endl; PARSER_STATE->pushScope(true); - terms = PARSER_STATE->mkBoundVars(sortedVarNames); + terms = PARSER_STATE->bindBoundVars(sortedVarNames); } term[e, e2] { PARSER_STATE->popScope(); // declare the name down here (while parsing term, signature // must not be extended with the name itself; no recursion // permitted) - Expr func = PARSER_STATE->mkVar(name, t, + api::Term func = PARSER_STATE->bindVar(name, t, ExprManager::VAR_FLAG_DEFINED); - cmd->reset(new DefineFunctionCommand(name, func, terms, e)); + cmd->reset(new DefineFunctionCommand( + name, func.getExpr(), api::termVectorToExprs(terms), e.getExpr())); } | SIMPLIFY_TOK { PARSER_STATE->checkThatLogicIsSet(); } term[e,e2] - { cmd->reset(new SimplifyCommand(e)); } + { cmd->reset(new SimplifyCommand(e.getExpr())); } | GET_QE_TOK { PARSER_STATE->checkThatLogicIsSet(); } term[e,e2] - { cmd->reset(new GetQuantifierEliminationCommand(e, true)); } + { cmd->reset(new GetQuantifierEliminationCommand(e.getExpr(), true)); } | GET_QE_DISJUNCT_TOK { PARSER_STATE->checkThatLogicIsSet(); } term[e,e2] - { cmd->reset(new GetQuantifierEliminationCommand(e, false)); } - | GET_ABDUCT_TOK { + { cmd->reset(new GetQuantifierEliminationCommand(e.getExpr(), false)); } + | GET_ABDUCT_TOK { PARSER_STATE->checkThatLogicIsSet(); } symbol[name,CHECK_UNDECLARED,SYM_VARIABLE] term[e,e2] ( sygusGrammar[t, terms, name] - )? + )? { - cmd->reset(new GetAbductCommand(name,e, t)); + cmd->reset(new GetAbductCommand(name,e.getExpr(), t.getType())); } | DECLARE_HEAP LPAREN_TOK sortSymbol[t, CHECK_DECLARED] @@ -1401,7 +1429,7 @@ extendedCommand[std::unique_ptr* cmd] | BLOCK_MODEL_VALUES_TOK { PARSER_STATE->checkThatLogicIsSet(); } ( LPAREN_TOK termList[terms,e] RPAREN_TOK - { cmd->reset(new BlockModelValuesCommand(terms)); } + { cmd->reset(new BlockModelValuesCommand(api::termVectorToExprs(terms))); } | ~LPAREN_TOK { PARSER_STATE->parseError("The block-model-value command expects a list " "of terms. Perhaps you forgot a pair of " @@ -1415,7 +1443,7 @@ datatypes_2_5_DefCommand[bool isCo, std::unique_ptr* cmd] @declarations { std::vector dts; std::string name; - std::vector sorts; + std::vector sorts; std::vector dnames; std::vector arities; } @@ -1424,7 +1452,9 @@ datatypes_2_5_DefCommand[bool isCo, std::unique_ptr* cmd] PARSER_STATE->pushScope(true); } LPAREN_TOK /* parametric sorts */ ( symbol[name,CHECK_UNDECLARED,SYM_SORT] - { sorts.push_back( PARSER_STATE->mkSort(name, ExprManager::SORT_FLAG_PLACEHOLDER) ); } + { + sorts.push_back(PARSER_STATE->mkSort(name, ExprManager::SORT_FLAG_PLACEHOLDER)); + } )* RPAREN_TOK LPAREN_TOK ( LPAREN_TOK datatypeDef[isCo, dts, sorts] RPAREN_TOK )+ RPAREN_TOK @@ -1483,7 +1513,7 @@ datatypesDef[bool isCo, @declarations { std::vector dts; std::string name; - std::vector params; + std::vector params; } : { PARSER_STATE->pushScope(true); } ( LPAREN_TOK { @@ -1495,7 +1525,8 @@ datatypesDef[bool isCo, } ( PAR_TOK { PARSER_STATE->pushScope(true); } LPAREN_TOK ( symbol[name,CHECK_UNDECLARED,SYM_SORT] - { params.push_back( PARSER_STATE->mkSort(name, ExprManager::SORT_FLAG_PLACEHOLDER) ); } + { + params.push_back( PARSER_STATE->mkSort(name, ExprManager::SORT_FLAG_PLACEHOLDER)); } )* RPAREN_TOK { // if the arity was fixed by prelude and is not equal to the number of parameters @@ -1503,7 +1534,7 @@ datatypesDef[bool isCo, PARSER_STATE->parseError("Wrong number of parameters for datatype."); } Debug("parser-dt") << params.size() << " parameters for " << dnames[dts.size()] << std::endl; - dts.push_back(Datatype(EXPR_MANAGER, dnames[dts.size()],params,isCo)); + dts.push_back(Datatype(PARSER_STATE->getExprManager(), dnames[dts.size()],api::sortVectorToTypes(params),isCo)); } LPAREN_TOK ( LPAREN_TOK constructorDef[dts.back()] RPAREN_TOK )+ @@ -1513,7 +1544,10 @@ datatypesDef[bool isCo, PARSER_STATE->parseError("No parameters given for datatype."); } Debug("parser-dt") << params.size() << " parameters for " << dnames[dts.size()] << std::endl; - dts.push_back(Datatype(EXPR_MANAGER, dnames[dts.size()],params,isCo)); + dts.push_back(Datatype(PARSER_STATE->getExprManager(), + dnames[dts.size()], + api::sortVectorToTypes(params), + isCo)); } ( LPAREN_TOK constructorDef[dts.back()] RPAREN_TOK )+ ) @@ -1586,12 +1620,12 @@ symbolicExpr[CVC4::SExpr& sexpr] * Matches a term. * @return the expression representing the term. */ -term[CVC4::Expr& expr, CVC4::Expr& expr2] +term[CVC4::api::Term& expr, CVC4::api::Term& expr2] @init { - Kind kind = kind::NULL_EXPR; - Expr f; + api::Kind kind = api::NULL_EXPR; + CVC4::api::Term f; std::string name; - Type type; + CVC4::api::Sort type; ParseOp p; } : termNonVariable[expr, expr2] @@ -1609,26 +1643,26 @@ term[CVC4::Expr& expr, CVC4::Expr& expr2] * @return the expression expr representing the term or formula, and expr2, an * optional annotation for expr (for instance, for attributed expressions). */ -termNonVariable[CVC4::Expr& expr, CVC4::Expr& expr2] +termNonVariable[CVC4::api::Term& expr, CVC4::api::Term& expr2] @init { Debug("parser") << "term: " << AntlrInput::tokenText(LT(1)) << std::endl; - Kind kind = kind::NULL_EXPR; + api::Kind kind = api::NULL_EXPR; std::string name; - std::vector args; - std::vector< std::pair > sortedVarNames; - Expr bvl; - Expr f, f2, f3; + std::vector args; + std::vector< std::pair > sortedVarNames; + CVC4::api::Term bvl; + CVC4::api::Term f, f2, f3; std::string attr; - Expr attexpr; - std::vector patexprs; - std::vector matchcases; + CVC4::api::Term attexpr; + std::vector patexprs; + std::vector matchcases; std::unordered_set names; - std::vector< std::pair > binders; - Type type; - Type type2; + std::vector< std::pair > binders; + CVC4::api::Sort type; + CVC4::api::Sort type2; api::Term atomTerm; ParseOp p; - std::vector argTypes; + std::vector argTypes; } : LPAREN_TOK quantOp[kind] { PARSER_STATE->pushScope(true); } @@ -1642,7 +1676,7 @@ termNonVariable[CVC4::Expr& expr, CVC4::Expr& expr2] if(! f2.isNull()){ args.push_back(f2); } - expr = MK_EXPR(kind, args); + expr = MK_TERM(kind, args); } | LPAREN_TOK COMPREHENSION_TOK { PARSER_STATE->pushScope(true); } @@ -1651,9 +1685,9 @@ termNonVariable[CVC4::Expr& expr, CVC4::Expr& expr2] args.push_back(bvl); } term[f, f2] { args.push_back(f); } - term[f, f2] { - args.push_back(f); - expr = MK_EXPR(CVC4::kind::COMPREHENSION, args); + term[f, f2] { + args.push_back(f); + expr = MK_TERM(api::COMPREHENSION, args); } RPAREN_TOK | LPAREN_TOK qualIdentifier[p] @@ -1697,7 +1731,7 @@ termNonVariable[CVC4::Expr& expr, CVC4::Expr& expr2] } binders.push_back(std::make_pair(name, expr)); } )+ ) { // now implement these bindings - for (const std::pair& binder : binders) + for (const std::pair& binder : binders) { { PARSER_STATE->defineVar(binder.first, binder.second); @@ -1710,7 +1744,7 @@ termNonVariable[CVC4::Expr& expr, CVC4::Expr& expr2] { PARSER_STATE->popScope(); } | /* match expression */ LPAREN_TOK MATCH_TOK term[expr, f2] { - if( !expr.getType().isDatatype() ){ + if( !expr.getSort().isDatatype() ){ PARSER_STATE->parseError("Cannot match on non-datatype term."); } } @@ -1721,17 +1755,19 @@ termNonVariable[CVC4::Expr& expr, CVC4::Expr& expr2] args.clear(); PARSER_STATE->pushScope(true); // f should be a constructor - type = f.getType(); + type = f.getSort(); Debug("parser-dt") << "Pattern head : " << f << " " << type << std::endl; if (!type.isConstructor()) { PARSER_STATE->parseError("Pattern must be application of a constructor or a variable."); } - if (Datatype::datatypeOf(f).isParametric()) + Expr ef = f.getExpr(); + if (Datatype::datatypeOf(ef).isParametric()) { - type = Datatype::datatypeOf(f)[Datatype::indexOf(f)].getSpecializedConstructorType(expr.getType()); + type = Datatype::datatypeOf(ef)[Datatype::indexOf(ef)] + .getSpecializedConstructorType(expr.getSort().getType()); } - argTypes = static_cast(type).getArgTypes(); + argTypes = type.getConstructorDomainSorts(); } // arguments of the pattern ( symbol[name,CHECK_NONE,SYM_VARIABLE] { @@ -1740,18 +1776,18 @@ termNonVariable[CVC4::Expr& expr, CVC4::Expr& expr2] PARSER_STATE->parseError("Too many arguments for pattern."); } //make of proper type - Expr arg = PARSER_STATE->mkBoundVar(name, argTypes[args.size()]); + api::Term arg = PARSER_STATE->bindBoundVar(name, argTypes[args.size()]); args.push_back( arg ); } )* RPAREN_TOK term[f3, f2] { // make the match case - std::vector cargs; + std::vector cargs; cargs.push_back(f); cargs.insert(cargs.end(),args.begin(),args.end()); - Expr c = MK_EXPR(kind::APPLY_CONSTRUCTOR,cargs); - Expr bvla = MK_EXPR(kind::BOUND_VAR_LIST,args); - Expr mc = MK_EXPR(kind::MATCH_BIND_CASE, bvla, c, f3); + api::Term c = MK_TERM(api::APPLY_CONSTRUCTOR,cargs); + api::Term bvla = MK_TERM(api::BOUND_VAR_LIST,args); + api::Term mc = MK_TERM(api::MATCH_BIND_CASE, bvla, c, f3); matchcases.push_back(mc); // now, pop the scope PARSER_STATE->popScope(); @@ -1762,31 +1798,31 @@ termNonVariable[CVC4::Expr& expr, CVC4::Expr& expr2] if (PARSER_STATE->isDeclared(name,SYM_VARIABLE)) { f = PARSER_STATE->getVariable(name); - type = f.getType(); - if (!type.isConstructor() || - !((ConstructorType)type).getArgTypes().empty()) + type = f.getSort(); + if (!type.isConstructor() || + !type.getConstructorDomainSorts().empty()) { PARSER_STATE->parseError("Must apply constructors of arity greater than 0 to arguments in pattern."); } // make nullary constructor application - f = MK_EXPR(kind::APPLY_CONSTRUCTOR, f); + f = MK_TERM(api::APPLY_CONSTRUCTOR, f); } else { // it has the type of the head expr - f = PARSER_STATE->mkBoundVar(name, expr.getType()); + f = PARSER_STATE->bindBoundVar(name, expr.getSort()); } } term[f3, f2] { - Expr mc; - if (f.getKind() == kind::BOUND_VARIABLE) + api::Term mc; + if (f.getKind() == api::VARIABLE) { - Expr bvlf = MK_EXPR(kind::BOUND_VAR_LIST, f); - mc = MK_EXPR(kind::MATCH_BIND_CASE, bvlf, f, f3); + api::Term bvlf = MK_TERM(api::BOUND_VAR_LIST, f); + mc = MK_TERM(api::MATCH_BIND_CASE, bvlf, f, f3); } else { - mc = MK_EXPR(kind::MATCH_CASE, f, f3); + mc = MK_TERM(api::MATCH_CASE, f, f3); } matchcases.push_back(mc); } @@ -1798,10 +1834,10 @@ termNonVariable[CVC4::Expr& expr, CVC4::Expr& expr2] { PARSER_STATE->parseError("Must have at least one case in match."); } - std::vector mchildren; + std::vector mchildren; mchildren.push_back(expr); mchildren.insert(mchildren.end(), matchcases.begin(), matchcases.end()); - expr = MK_EXPR(kind::MATCH, mchildren); + expr = MK_TERM(api::MATCH, mchildren); } /* attributed expressions */ @@ -1814,9 +1850,9 @@ termNonVariable[CVC4::Expr& expr, CVC4::Expr& expr2] )+ RPAREN_TOK { if(! patexprs.empty()) { - if( !f2.isNull() && f2.getKind()==kind::INST_PATTERN_LIST ){ + if( !f2.isNull() && f2.getKind()==api::INST_PATTERN_LIST ){ for( size_t i=0; ipopScope(); - expr = MK_EXPR(CVC4::kind::LAMBDA, args); + expr = MK_TERM(api::LAMBDA, args); } | LPAREN_TOK TUPLE_CONST_TOK termList[args,expr] RPAREN_TOK { std::vector sorts; std::vector terms; - for (const Expr& arg : args) + for (const api::Term& arg : args) { - sorts.emplace_back(arg.getType()); + sorts.emplace_back(arg.getSort()); terms.emplace_back(arg); } expr = SOLVER->mkTuple(sorts, terms).getExpr(); @@ -1881,7 +1917,7 @@ termNonVariable[CVC4::Expr& expr, CVC4::Expr& expr2] * - For declared functions f, we return (2). * - For indexed functions like testers (_ is C) and bitvector extract * (_ extract n m), we return (3) for the appropriate operator. - * - For tuple selectors (_ tupSel n), we return (1) and (3). Kind is set to + * - For tuple selectors (_ tupSel n), we return (1) and (3). api::Kind is set to * APPLY_SELECTOR, and expr is set to n, which is to be interpreted by the * caller as the n^th generic tuple selector. We do this since there is no * AST expression representing generic tuple select, and we do not have enough @@ -1910,16 +1946,16 @@ termNonVariable[CVC4::Expr& expr, CVC4::Expr& expr2] */ qualIdentifier[CVC4::ParseOp& p] @init { - Kind k; + api::Kind k; std::string baseName; - Expr f; - Type type; + CVC4::api::Term f; + CVC4::api::Sort type; } : identifier[p] | LPAREN_TOK AS_TOK ( CONST_TOK sortSymbol[type, CHECK_DECLARED] { - p.d_kind = kind::STORE_ALL; + p.d_kind = api::STORE_ALL; PARSER_STATE->parseOpApplyTypeAscription(p, type); } | identifier[p] @@ -1941,8 +1977,8 @@ qualIdentifier[CVC4::ParseOp& p] */ identifier[CVC4::ParseOp& p] @init { - Expr f; - Expr f2; + CVC4::api::Term f; + CVC4::api::Term f2; std::vector numerals; } : functionName[p.d_name, CHECK_NONE] @@ -1952,24 +1988,29 @@ identifier[CVC4::ParseOp& p] | LPAREN_TOK INDEX_TOK ( TESTER_TOK term[f, f2] { - if (f.getKind() == kind::APPLY_CONSTRUCTOR && f.getNumChildren() == 0) + if (f.getKind() == api::APPLY_CONSTRUCTOR && f.getNumChildren() == 1) { // for nullary constructors, must get the operator - f = f.getOperator(); + f = f[0]; } - if (!f.getType().isConstructor()) + if (!f.getSort().isConstructor()) { PARSER_STATE->parseError( "Bad syntax for test (_ is X), X must be a constructor."); } - p.d_expr = Datatype::datatypeOf(f)[Datatype::indexOf(f)].getTester(); + // get the datatype that f belongs to + api::Sort sf = f.getSort().getConstructorCodomainSort(); + api::Datatype d = sf.getDatatype(); + // lookup by name + api::DatatypeConstructor dc = d.getConstructor(f.toString()); + p.d_expr = dc.getTesterTerm(); } | TUPLE_SEL_TOK m=INTEGER_LITERAL { // we adopt a special syntax (_ tupSel n) - p.d_kind = CVC4::kind::APPLY_SELECTOR; + p.d_kind = api::APPLY_SELECTOR; // put m in expr so that the caller can deal with this case - p.d_expr = MK_CONST(Rational(AntlrInput::tokenToUnsigned($m))); + p.d_expr = SOLVER->mkReal(AntlrInput::tokenToUnsigned($m)); } | sym=SIMPLE_SYMBOL nonemptyNumeralList[numerals] { @@ -1985,8 +2026,8 @@ identifier[CVC4::ParseOp& p] */ termAtomic[CVC4::api::Term& atomTerm] @init { - Type type; - Type type2; + CVC4::api::Sort type; + CVC4::api::Sort type2; std::string s; std::vector numerals; } @@ -2054,18 +2095,17 @@ termAtomic[CVC4::api::Term& atomTerm] /** * Read attribute */ -attribute[CVC4::Expr& expr, CVC4::Expr& retExpr, std::string& attr] +attribute[CVC4::api::Term& expr, CVC4::api::Term& retExpr, std::string& attr] @init { SExpr sexpr; - Expr patexpr; - std::vector patexprs; - Expr e2; + CVC4::api::Term patexpr; + std::vector patexprs; + CVC4::api::Term e2; bool hasValue = false; } : KEYWORD ( simpleSymbolicExprNoKeyword[sexpr] { hasValue = true; } )? { attr = AntlrInput::tokenText($KEYWORD); - // EXPR_MANAGER->setNamedAttribute( expr, attr ); if(attr == ":rewrite-rule") { if(hasValue) { std::stringstream ss; @@ -2083,18 +2123,18 @@ attribute[CVC4::Expr& expr, CVC4::Expr& retExpr, std::string& attr] << " does not take a value (ignoring)"; PARSER_STATE->warning(ss.str()); } - Expr avar; + api::Term avar; bool success = true; std::string attr_name = attr; attr_name.erase( attr_name.begin() ); if( attr==":fun-def" ){ - if( expr.getKind()!=kind::EQUAL || expr[0].getKind()!=kind::APPLY_UF ){ + if( expr.getKind()!=api::EQUAL || expr[0].getKind()!=api::APPLY_UF ){ success = false; }else{ - FunctionType t = (FunctionType)expr[0].getOperator().getType(); + api::Sort t = expr[0].getOp().getSort(); for( unsigned i=0; ibooleanType(); - avar = PARSER_STATE->mkVar(attr_name, boolType); + api::Sort boolType = SOLVER->getBooleanSort(); + avar = PARSER_STATE->bindVar(attr_name, boolType); } if( success ){ //Will set the attribute on auxiliary var (preserves attribute on //formula through rewriting). - retExpr = MK_EXPR(kind::INST_ATTRIBUTE, avar); - Command* c = new SetUserAttributeCommand( attr_name, avar ); + retExpr = MK_TERM(api::INST_ATTRIBUTE, avar); + Command* c = new SetUserAttributeCommand( attr_name, avar.getExpr() ); c->setMuted(true); PARSER_STATE->preemptCommand(c); } @@ -2137,35 +2177,38 @@ attribute[CVC4::Expr& expr, CVC4::Expr& retExpr, std::string& attr] )+ RPAREN_TOK { attr = std::string(":pattern"); - retExpr = MK_EXPR(kind::INST_PATTERN, patexprs); + retExpr = MK_TERM(api::INST_PATTERN, patexprs); } | ATTRIBUTE_NO_PATTERN_TOK term[patexpr, e2] { attr = std::string(":no-pattern"); - retExpr = MK_EXPR(kind::INST_NO_PATTERN, patexpr); + retExpr = MK_TERM(api::INST_NO_PATTERN, patexpr); } - | tok=( ATTRIBUTE_INST_LEVEL | ATTRIBUTE_RR_PRIORITY ) INTEGER_LITERAL + | tok=( ATTRIBUTE_INST_LEVEL ) INTEGER_LITERAL { - Expr n = MK_CONST( AntlrInput::tokenToInteger($INTEGER_LITERAL) ); - std::vector values; + std::stringstream sIntLit; + sIntLit << $INTEGER_LITERAL; + api::Term n = SOLVER->mkReal(sIntLit.str()); + std::vector values; values.push_back( n ); std::string attr_name(AntlrInput::tokenText($tok)); attr_name.erase( attr_name.begin() ); - Type boolType = EXPR_MANAGER->booleanType(); - Expr avar = PARSER_STATE->mkVar(attr_name, boolType); - retExpr = MK_EXPR(kind::INST_ATTRIBUTE, avar); - Command* c = new SetUserAttributeCommand( attr_name, avar, values ); + api::Sort boolType = SOLVER->getBooleanSort(); + api::Term avar = PARSER_STATE->bindVar(attr_name, boolType); + retExpr = MK_TERM(api::INST_ATTRIBUTE, avar); + Command* c = new SetUserAttributeCommand( + attr_name, avar.getExpr(), api::termVectorToExprs(values)); c->setMuted(true); PARSER_STATE->preemptCommand(c); } | ATTRIBUTE_NAMED_TOK symbolicExpr[sexpr] { attr = std::string(":named"); - Expr func = PARSER_STATE->setNamedAttribute(expr, sexpr); + api::Term func = PARSER_STATE->setNamedAttribute(expr, sexpr); std::string name = sexpr.getValue(); // bind name to expr with define-fun - Command* c = - new DefineNamedFunctionCommand(name, func, std::vector(), expr); + Command* c = new DefineNamedFunctionCommand( + name, func.getExpr(), std::vector(), expr.getExpr()); c->setMuted(true); PARSER_STATE->preemptCommand(c); } @@ -2175,13 +2218,13 @@ attribute[CVC4::Expr& expr, CVC4::Expr& retExpr, std::string& attr] * Matches a sequence of terms and puts them into the formulas * vector. * @param formulas the vector to fill with terms - * @param expr an Expr reference for the elements of the sequence + * @param expr an CVC4::api::Term reference for the elements of the sequence */ -/* NOTE: We pass an Expr in here just to avoid allocating a fresh Expr every +/* NOTE: We pass an CVC4::api::Term in here just to avoid allocating a fresh CVC4::api::Term every * time through this rule. */ -termList[std::vector& formulas, CVC4::Expr& expr] +termList[std::vector& formulas, CVC4::api::Term& expr] @declarations { - Expr expr2; + CVC4::api::Term expr2; } : ( term[expr, expr2] { formulas.push_back(expr); } )+ ; @@ -2236,12 +2279,12 @@ str[std::string& s, bool fsmtlib] } ; -quantOp[CVC4::Kind& kind] +quantOp[CVC4::api::Kind& kind] @init { Debug("parser") << "quant: " << AntlrInput::tokenText(LT(1)) << std::endl; } - : EXISTS_TOK { $kind = CVC4::kind::EXISTS; } - | FORALL_TOK { $kind = CVC4::kind::FORALL; } + : EXISTS_TOK { $kind = api::EXISTS; } + | FORALL_TOK { $kind = api::FORALL; } ; /** @@ -2256,16 +2299,16 @@ functionName[std::string& name, CVC4::parser::DeclarationCheck check] * Matches a sequence of sort symbols and fills them into the given * vector. */ -sortList[std::vector& sorts] +sortList[std::vector& sorts] @declarations { - Type t; + CVC4::api::Sort t; } : ( sortSymbol[t,CHECK_DECLARED] { sorts.push_back(t); } )* ; -nonemptySortList[std::vector& sorts] +nonemptySortList[std::vector& sorts] @declarations { - Type t; + CVC4::api::Sort t; } : ( sortSymbol[t,CHECK_DECLARED] { sorts.push_back(t); } )+ ; @@ -2274,10 +2317,10 @@ nonemptySortList[std::vector& sorts] * Matches a sequence of (variable,sort) symbol pairs and fills them * into the given vector. */ -sortedVarList[std::vector >& sortedVars] +sortedVarList[std::vector >& sortedVars] @declarations { std::string name; - Type t; + CVC4::api::Sort t; } : ( LPAREN_TOK symbol[name,CHECK_NONE,SYM_VARIABLE] sortSymbol[t,CHECK_DECLARED] RPAREN_TOK @@ -2289,14 +2332,15 @@ sortedVarList[std::vector >& sortedVars] * Matches a sequence of (variable, sort) symbol pairs, registers them as bound * variables, and returns a term corresponding to the list of pairs. */ -boundVarList[CVC4::Expr& expr] +boundVarList[CVC4::api::Term& expr] @declarations { - std::vector> sortedVarNames; + std::vector> sortedVarNames; } : LPAREN_TOK sortedVarList[sortedVarNames] RPAREN_TOK { - std::vector args = PARSER_STATE->mkBoundVars(sortedVarNames); - expr = MK_EXPR(kind::BOUND_VAR_LIST, args); + std::vector args = + PARSER_STATE->bindBoundVars(sortedVarNames); + expr = MK_TERM(api::BOUND_VAR_LIST, args); } ; @@ -2308,10 +2352,10 @@ sortName[std::string& name, CVC4::parser::DeclarationCheck check] : symbol[name,check,SYM_SORT] ; -sortSymbol[CVC4::Type& t, CVC4::parser::DeclarationCheck check] +sortSymbol[CVC4::api::Sort& t, CVC4::parser::DeclarationCheck check] @declarations { std::string name; - std::vector args; + std::vector args; std::vector numerals; bool indexed = false; } @@ -2340,7 +2384,7 @@ sortSymbol[CVC4::Type& t, CVC4::parser::DeclarationCheck check] if(numerals.front() == 0) { PARSER_STATE->parseError("Illegal bitvector size: 0"); } - t = EXPR_MANAGER->mkBitVectorType(numerals.front()); + t = SOLVER->mkBitVectorSort(numerals.front()); } else if ( name == "FloatingPoint" ) { if( numerals.size() != 2 ) { PARSER_STATE->parseError("Illegal floating-point type."); @@ -2351,7 +2395,7 @@ sortSymbol[CVC4::Type& t, CVC4::parser::DeclarationCheck check] if(!validSignificandSize(numerals[1])) { PARSER_STATE->parseError("Illegal floating-point significand size"); } - t = EXPR_MANAGER->mkFloatingPointType(numerals[0],numerals[1]); + t = SOLVER->mkFloatingPointSort(numerals[0],numerals[1]); } else { std::stringstream ss; ss << "unknown indexed sort symbol `" << name << "'"; @@ -2373,15 +2417,15 @@ sortSymbol[CVC4::Type& t, CVC4::parser::DeclarationCheck check] if(args.size() != 2) { PARSER_STATE->parseError("Illegal array type."); } - t = EXPR_MANAGER->mkArrayType( args[0], args[1] ); + t = SOLVER->mkArraySort( args[0], args[1] ); } else if(name == "Set" && PARSER_STATE->isTheoryEnabled(Smt2::THEORY_SETS) ) { if(args.size() != 1) { PARSER_STATE->parseError("Illegal set type."); } - t = EXPR_MANAGER->mkSetType( args[0] ); + t = SOLVER->mkSetSort( args[0] ); } else if(name == "Tuple") { - t = EXPR_MANAGER->mkTupleType(args); + t = SOLVER->mkTupleSort(args); } else if(check == CHECK_DECLARED || PARSER_STATE->isDeclared(name, SYM_SORT)) { t = PARSER_STATE->getSort(name, args); @@ -2393,7 +2437,7 @@ sortSymbol[CVC4::Type& t, CVC4::parser::DeclarationCheck check] << std::endl; } else { t = PARSER_STATE->mkUnresolvedTypeConstructor(name,args); - t = SortConstructorType(t).instantiate( args ); + t = t.instantiate( args ); Debug("parser-param") << "param: make unres param type " << name << " " << args.size() << " " << PARSER_STATE->getArity( name ) << std::endl; @@ -2407,7 +2451,7 @@ sortSymbol[CVC4::Type& t, CVC4::parser::DeclarationCheck check] PARSER_STATE->parseError("Arrow types must have at least 2 arguments"); } //flatten the type - Type rangeType = args.back(); + api::Sort rangeType = args.back(); args.pop_back(); t = PARSER_STATE->mkFlatFunctionType( args, rangeType ); } @@ -2474,7 +2518,7 @@ nonemptyNumeralList[std::vector& numerals] * Parses a datatype definition */ datatypeDef[bool isCo, std::vector& datatypes, - std::vector< CVC4::Type >& params] + std::vector< CVC4::api::Sort >& params] @init { std::string id; } @@ -2483,11 +2527,11 @@ datatypeDef[bool isCo, std::vector& datatypes, * "defined" as an unresolved type; don't worry, we check * below. */ : symbol[id,CHECK_NONE,SYM_SORT] { PARSER_STATE->pushScope(true); } - { datatypes.push_back(Datatype(EXPR_MANAGER, id, params, isCo)); - if(!PARSER_STATE->isUnresolvedType(id)) { - // if not unresolved, must be undeclared - PARSER_STATE->checkDeclaration(id, CHECK_UNDECLARED, SYM_SORT); - } + { + datatypes.push_back(Datatype(PARSER_STATE->getExprManager(), + id, + api::sortVectorToTypes(params), + isCo)); } ( LPAREN_TOK constructorDef[datatypes.back()] RPAREN_TOK )+ { PARSER_STATE->popScope(); } @@ -2518,10 +2562,10 @@ constructorDef[CVC4::Datatype& type] selector[CVC4::DatatypeConstructor& ctor] @init { std::string id; - Type t, t2; + CVC4::api::Sort t, t2; } : symbol[id,CHECK_NONE,SYM_SORT] sortSymbol[t,CHECK_NONE] - { ctor.addArg(id, t); + { ctor.addArg(id, t.getType()); Debug("parser-idt") << "selector: " << id.c_str() << " of type " << t << std::endl; } diff --git a/src/parser/smt2/smt2.cpp b/src/parser/smt2/smt2.cpp index 15fdd8461..73be8910f 100644 --- a/src/parser/smt2/smt2.cpp +++ b/src/parser/smt2/smt2.cpp @@ -45,242 +45,236 @@ Smt2::Smt2(api::Solver* solver, Input* input, bool strictMode, bool parseOnly) } void Smt2::addArithmeticOperators() { - addOperator(kind::PLUS, "+"); - addOperator(kind::MINUS, "-"); - // kind::MINUS is converted to kind::UMINUS if there is only a single operand - Parser::addOperator(kind::UMINUS); - addOperator(kind::MULT, "*"); - addOperator(kind::LT, "<"); - addOperator(kind::LEQ, "<="); - addOperator(kind::GT, ">"); - addOperator(kind::GEQ, ">="); + addOperator(api::PLUS, "+"); + addOperator(api::MINUS, "-"); + // api::MINUS is converted to api::UMINUS if there is only a single operand + Parser::addOperator(api::UMINUS); + addOperator(api::MULT, "*"); + addOperator(api::LT, "<"); + addOperator(api::LEQ, "<="); + addOperator(api::GT, ">"); + addOperator(api::GEQ, ">="); if (!strictModeEnabled()) { // NOTE: this operator is non-standard - addOperator(kind::POW, "^"); + addOperator(api::POW, "^"); } } void Smt2::addTranscendentalOperators() { - addOperator(kind::EXPONENTIAL, "exp"); - addOperator(kind::SINE, "sin"); - addOperator(kind::COSINE, "cos"); - addOperator(kind::TANGENT, "tan"); - addOperator(kind::COSECANT, "csc"); - addOperator(kind::SECANT, "sec"); - addOperator(kind::COTANGENT, "cot"); - addOperator(kind::ARCSINE, "arcsin"); - addOperator(kind::ARCCOSINE, "arccos"); - addOperator(kind::ARCTANGENT, "arctan"); - addOperator(kind::ARCCOSECANT, "arccsc"); - addOperator(kind::ARCSECANT, "arcsec"); - addOperator(kind::ARCCOTANGENT, "arccot"); - addOperator(kind::SQRT, "sqrt"); + addOperator(api::EXPONENTIAL, "exp"); + addOperator(api::SINE, "sin"); + addOperator(api::COSINE, "cos"); + addOperator(api::TANGENT, "tan"); + addOperator(api::COSECANT, "csc"); + addOperator(api::SECANT, "sec"); + addOperator(api::COTANGENT, "cot"); + addOperator(api::ARCSINE, "arcsin"); + addOperator(api::ARCCOSINE, "arccos"); + addOperator(api::ARCTANGENT, "arctan"); + addOperator(api::ARCCOSECANT, "arccsc"); + addOperator(api::ARCSECANT, "arcsec"); + addOperator(api::ARCCOTANGENT, "arccot"); + addOperator(api::SQRT, "sqrt"); } void Smt2::addQuantifiersOperators() { if (!strictModeEnabled()) { - addOperator(kind::INST_CLOSURE, "inst-closure"); + addOperator(api::INST_CLOSURE, "inst-closure"); } } void Smt2::addBitvectorOperators() { - addOperator(kind::BITVECTOR_CONCAT, "concat"); - addOperator(kind::BITVECTOR_NOT, "bvnot"); - addOperator(kind::BITVECTOR_AND, "bvand"); - addOperator(kind::BITVECTOR_OR, "bvor"); - addOperator(kind::BITVECTOR_NEG, "bvneg"); - addOperator(kind::BITVECTOR_PLUS, "bvadd"); - addOperator(kind::BITVECTOR_MULT, "bvmul"); - addOperator(kind::BITVECTOR_UDIV, "bvudiv"); - addOperator(kind::BITVECTOR_UREM, "bvurem"); - addOperator(kind::BITVECTOR_SHL, "bvshl"); - addOperator(kind::BITVECTOR_LSHR, "bvlshr"); - addOperator(kind::BITVECTOR_ULT, "bvult"); - addOperator(kind::BITVECTOR_NAND, "bvnand"); - addOperator(kind::BITVECTOR_NOR, "bvnor"); - addOperator(kind::BITVECTOR_XOR, "bvxor"); - addOperator(kind::BITVECTOR_XNOR, "bvxnor"); - addOperator(kind::BITVECTOR_COMP, "bvcomp"); - addOperator(kind::BITVECTOR_SUB, "bvsub"); - addOperator(kind::BITVECTOR_SDIV, "bvsdiv"); - addOperator(kind::BITVECTOR_SREM, "bvsrem"); - addOperator(kind::BITVECTOR_SMOD, "bvsmod"); - addOperator(kind::BITVECTOR_ASHR, "bvashr"); - addOperator(kind::BITVECTOR_ULE, "bvule"); - addOperator(kind::BITVECTOR_UGT, "bvugt"); - addOperator(kind::BITVECTOR_UGE, "bvuge"); - addOperator(kind::BITVECTOR_SLT, "bvslt"); - addOperator(kind::BITVECTOR_SLE, "bvsle"); - addOperator(kind::BITVECTOR_SGT, "bvsgt"); - addOperator(kind::BITVECTOR_SGE, "bvsge"); - addOperator(kind::BITVECTOR_REDOR, "bvredor"); - addOperator(kind::BITVECTOR_REDAND, "bvredand"); - addOperator(kind::BITVECTOR_TO_NAT, "bv2nat"); - + addOperator(api::BITVECTOR_CONCAT, "concat"); + addOperator(api::BITVECTOR_NOT, "bvnot"); + addOperator(api::BITVECTOR_AND, "bvand"); + addOperator(api::BITVECTOR_OR, "bvor"); + addOperator(api::BITVECTOR_NEG, "bvneg"); + addOperator(api::BITVECTOR_PLUS, "bvadd"); + addOperator(api::BITVECTOR_MULT, "bvmul"); + addOperator(api::BITVECTOR_UDIV, "bvudiv"); + addOperator(api::BITVECTOR_UREM, "bvurem"); + addOperator(api::BITVECTOR_SHL, "bvshl"); + addOperator(api::BITVECTOR_LSHR, "bvlshr"); + addOperator(api::BITVECTOR_ULT, "bvult"); + addOperator(api::BITVECTOR_NAND, "bvnand"); + addOperator(api::BITVECTOR_NOR, "bvnor"); + addOperator(api::BITVECTOR_XOR, "bvxor"); + addOperator(api::BITVECTOR_XNOR, "bvxnor"); + addOperator(api::BITVECTOR_COMP, "bvcomp"); + addOperator(api::BITVECTOR_SUB, "bvsub"); + addOperator(api::BITVECTOR_SDIV, "bvsdiv"); + addOperator(api::BITVECTOR_SREM, "bvsrem"); + addOperator(api::BITVECTOR_SMOD, "bvsmod"); + addOperator(api::BITVECTOR_ASHR, "bvashr"); + addOperator(api::BITVECTOR_ULE, "bvule"); + addOperator(api::BITVECTOR_UGT, "bvugt"); + addOperator(api::BITVECTOR_UGE, "bvuge"); + addOperator(api::BITVECTOR_SLT, "bvslt"); + addOperator(api::BITVECTOR_SLE, "bvsle"); + addOperator(api::BITVECTOR_SGT, "bvsgt"); + addOperator(api::BITVECTOR_SGE, "bvsge"); + addOperator(api::BITVECTOR_REDOR, "bvredor"); + addOperator(api::BITVECTOR_REDAND, "bvredand"); + addOperator(api::BITVECTOR_TO_NAT, "bv2nat"); + + addIndexedOperator(api::BITVECTOR_EXTRACT, api::BITVECTOR_EXTRACT, "extract"); + addIndexedOperator(api::BITVECTOR_REPEAT, api::BITVECTOR_REPEAT, "repeat"); addIndexedOperator( - kind::BITVECTOR_EXTRACT, api::BITVECTOR_EXTRACT, "extract"); - addIndexedOperator(kind::BITVECTOR_REPEAT, api::BITVECTOR_REPEAT, "repeat"); + api::BITVECTOR_ZERO_EXTEND, api::BITVECTOR_ZERO_EXTEND, "zero_extend"); addIndexedOperator( - kind::BITVECTOR_ZERO_EXTEND, api::BITVECTOR_ZERO_EXTEND, "zero_extend"); + api::BITVECTOR_SIGN_EXTEND, api::BITVECTOR_SIGN_EXTEND, "sign_extend"); addIndexedOperator( - kind::BITVECTOR_SIGN_EXTEND, api::BITVECTOR_SIGN_EXTEND, "sign_extend"); + api::BITVECTOR_ROTATE_LEFT, api::BITVECTOR_ROTATE_LEFT, "rotate_left"); addIndexedOperator( - kind::BITVECTOR_ROTATE_LEFT, api::BITVECTOR_ROTATE_LEFT, "rotate_left"); - addIndexedOperator(kind::BITVECTOR_ROTATE_RIGHT, - api::BITVECTOR_ROTATE_RIGHT, - "rotate_right"); - addIndexedOperator(kind::INT_TO_BITVECTOR, api::INT_TO_BITVECTOR, "int2bv"); + api::BITVECTOR_ROTATE_RIGHT, api::BITVECTOR_ROTATE_RIGHT, "rotate_right"); + addIndexedOperator(api::INT_TO_BITVECTOR, api::INT_TO_BITVECTOR, "int2bv"); } void Smt2::addDatatypesOperators() { - Parser::addOperator(kind::APPLY_CONSTRUCTOR); - Parser::addOperator(kind::APPLY_TESTER); - Parser::addOperator(kind::APPLY_SELECTOR); - Parser::addOperator(kind::APPLY_SELECTOR_TOTAL); + Parser::addOperator(api::APPLY_CONSTRUCTOR); + Parser::addOperator(api::APPLY_TESTER); + Parser::addOperator(api::APPLY_SELECTOR); if (!strictModeEnabled()) { - addOperator(kind::DT_SIZE, "dt.size"); + addOperator(api::DT_SIZE, "dt.size"); } } void Smt2::addStringOperators() { - defineVar("re.all", - getSolver() - ->mkTerm(api::REGEXP_STAR, getSolver()->mkRegexpSigma()) - .getExpr()); - - addOperator(kind::STRING_CONCAT, "str.++"); - addOperator(kind::STRING_LENGTH, "str.len"); - addOperator(kind::STRING_SUBSTR, "str.substr" ); - addOperator(kind::STRING_STRCTN, "str.contains" ); - addOperator(kind::STRING_CHARAT, "str.at" ); - addOperator(kind::STRING_STRIDOF, "str.indexof" ); - addOperator(kind::STRING_STRREPL, "str.replace" ); + defineVar( + "re.all", + getSolver()->mkTerm(api::REGEXP_STAR, getSolver()->mkRegexpSigma())); + addOperator(api::STRING_CONCAT, "str.++"); + addOperator(api::STRING_LENGTH, "str.len"); + addOperator(api::STRING_SUBSTR, "str.substr"); + addOperator(api::STRING_STRCTN, "str.contains"); + addOperator(api::STRING_CHARAT, "str.at"); + addOperator(api::STRING_STRIDOF, "str.indexof"); + addOperator(api::STRING_STRREPL, "str.replace"); if (!strictModeEnabled()) { - addOperator(kind::STRING_TOLOWER, "str.tolower"); - addOperator(kind::STRING_TOUPPER, "str.toupper"); - addOperator(kind::STRING_REV, "str.rev"); - } - addOperator(kind::STRING_PREFIX, "str.prefixof" ); - addOperator(kind::STRING_SUFFIX, "str.suffixof" ); - addOperator(kind::STRING_FROM_CODE, "str.from_code"); - addOperator(kind::STRING_IS_DIGIT, "str.is_digit" ); - + addOperator(api::STRING_TOLOWER, "str.tolower"); + addOperator(api::STRING_TOUPPER, "str.toupper"); + addOperator(api::STRING_REV, "str.rev"); + } + addOperator(api::STRING_PREFIX, "str.prefixof"); + addOperator(api::STRING_SUFFIX, "str.suffixof"); + addOperator(api::STRING_FROM_CODE, "str.from_code"); + addOperator(api::STRING_IS_DIGIT, "str.is_digit"); // at the moment, we only use this syntax for smt2.6.1 if (getLanguage() == language::input::LANG_SMTLIB_V2_6_1 || getLanguage() == language::input::LANG_SYGUS_V2) { - addOperator(kind::STRING_ITOS, "str.from_int"); - addOperator(kind::STRING_STOI, "str.to_int"); - addOperator(kind::STRING_IN_REGEXP, "str.in_re"); - addOperator(kind::STRING_TO_REGEXP, "str.to_re"); - addOperator(kind::STRING_TO_CODE, "str.to_code"); - addOperator(kind::STRING_STRREPLALL, "str.replace_all"); + addOperator(api::STRING_ITOS, "str.from_int"); + addOperator(api::STRING_STOI, "str.to_int"); + addOperator(api::STRING_IN_REGEXP, "str.in_re"); + addOperator(api::STRING_TO_REGEXP, "str.to_re"); + addOperator(api::STRING_TO_CODE, "str.to_code"); + addOperator(api::STRING_STRREPLALL, "str.replace_all"); } else { - addOperator(kind::STRING_ITOS, "int.to.str"); - addOperator(kind::STRING_STOI, "str.to.int"); - addOperator(kind::STRING_IN_REGEXP, "str.in.re"); - addOperator(kind::STRING_TO_REGEXP, "str.to.re"); - addOperator(kind::STRING_TO_CODE, "str.code"); - addOperator(kind::STRING_STRREPLALL, "str.replaceall"); - } - - addOperator(kind::REGEXP_CONCAT, "re.++"); - addOperator(kind::REGEXP_UNION, "re.union"); - addOperator(kind::REGEXP_INTER, "re.inter"); - addOperator(kind::REGEXP_STAR, "re.*"); - addOperator(kind::REGEXP_PLUS, "re.+"); - addOperator(kind::REGEXP_OPT, "re.opt"); - addOperator(kind::REGEXP_RANGE, "re.range"); - addOperator(kind::REGEXP_LOOP, "re.loop"); - addOperator(kind::REGEXP_COMPLEMENT, "re.comp"); - addOperator(kind::REGEXP_DIFF, "re.diff"); - addOperator(kind::STRING_LT, "str.<"); - addOperator(kind::STRING_LEQ, "str.<="); + addOperator(api::STRING_ITOS, "int.to.str"); + addOperator(api::STRING_STOI, "str.to.int"); + addOperator(api::STRING_IN_REGEXP, "str.in.re"); + addOperator(api::STRING_TO_REGEXP, "str.to.re"); + addOperator(api::STRING_TO_CODE, "str.code"); + addOperator(api::STRING_STRREPLALL, "str.replaceall"); + } + + addOperator(api::REGEXP_CONCAT, "re.++"); + addOperator(api::REGEXP_UNION, "re.union"); + addOperator(api::REGEXP_INTER, "re.inter"); + addOperator(api::REGEXP_STAR, "re.*"); + addOperator(api::REGEXP_PLUS, "re.+"); + addOperator(api::REGEXP_OPT, "re.opt"); + addOperator(api::REGEXP_RANGE, "re.range"); + addOperator(api::REGEXP_LOOP, "re.loop"); + addOperator(api::REGEXP_COMPLEMENT, "re.comp"); + addOperator(api::REGEXP_DIFF, "re.diff"); + addOperator(api::STRING_LT, "str.<"); + addOperator(api::STRING_LEQ, "str.<="); } void Smt2::addFloatingPointOperators() { - addOperator(kind::FLOATINGPOINT_FP, "fp"); - addOperator(kind::FLOATINGPOINT_EQ, "fp.eq"); - addOperator(kind::FLOATINGPOINT_ABS, "fp.abs"); - addOperator(kind::FLOATINGPOINT_NEG, "fp.neg"); - addOperator(kind::FLOATINGPOINT_PLUS, "fp.add"); - addOperator(kind::FLOATINGPOINT_SUB, "fp.sub"); - addOperator(kind::FLOATINGPOINT_MULT, "fp.mul"); - addOperator(kind::FLOATINGPOINT_DIV, "fp.div"); - addOperator(kind::FLOATINGPOINT_FMA, "fp.fma"); - addOperator(kind::FLOATINGPOINT_SQRT, "fp.sqrt"); - addOperator(kind::FLOATINGPOINT_REM, "fp.rem"); - addOperator(kind::FLOATINGPOINT_RTI, "fp.roundToIntegral"); - addOperator(kind::FLOATINGPOINT_MIN, "fp.min"); - addOperator(kind::FLOATINGPOINT_MAX, "fp.max"); - addOperator(kind::FLOATINGPOINT_LEQ, "fp.leq"); - addOperator(kind::FLOATINGPOINT_LT, "fp.lt"); - addOperator(kind::FLOATINGPOINT_GEQ, "fp.geq"); - addOperator(kind::FLOATINGPOINT_GT, "fp.gt"); - addOperator(kind::FLOATINGPOINT_ISN, "fp.isNormal"); - addOperator(kind::FLOATINGPOINT_ISSN, "fp.isSubnormal"); - addOperator(kind::FLOATINGPOINT_ISZ, "fp.isZero"); - addOperator(kind::FLOATINGPOINT_ISINF, "fp.isInfinite"); - addOperator(kind::FLOATINGPOINT_ISNAN, "fp.isNaN"); - addOperator(kind::FLOATINGPOINT_ISNEG, "fp.isNegative"); - addOperator(kind::FLOATINGPOINT_ISPOS, "fp.isPositive"); - addOperator(kind::FLOATINGPOINT_TO_REAL, "fp.to_real"); - - addIndexedOperator(kind::FLOATINGPOINT_TO_FP_GENERIC, + addOperator(api::FLOATINGPOINT_FP, "fp"); + addOperator(api::FLOATINGPOINT_EQ, "fp.eq"); + addOperator(api::FLOATINGPOINT_ABS, "fp.abs"); + addOperator(api::FLOATINGPOINT_NEG, "fp.neg"); + addOperator(api::FLOATINGPOINT_PLUS, "fp.add"); + addOperator(api::FLOATINGPOINT_SUB, "fp.sub"); + addOperator(api::FLOATINGPOINT_MULT, "fp.mul"); + addOperator(api::FLOATINGPOINT_DIV, "fp.div"); + addOperator(api::FLOATINGPOINT_FMA, "fp.fma"); + addOperator(api::FLOATINGPOINT_SQRT, "fp.sqrt"); + addOperator(api::FLOATINGPOINT_REM, "fp.rem"); + addOperator(api::FLOATINGPOINT_RTI, "fp.roundToIntegral"); + addOperator(api::FLOATINGPOINT_MIN, "fp.min"); + addOperator(api::FLOATINGPOINT_MAX, "fp.max"); + addOperator(api::FLOATINGPOINT_LEQ, "fp.leq"); + addOperator(api::FLOATINGPOINT_LT, "fp.lt"); + addOperator(api::FLOATINGPOINT_GEQ, "fp.geq"); + addOperator(api::FLOATINGPOINT_GT, "fp.gt"); + addOperator(api::FLOATINGPOINT_ISN, "fp.isNormal"); + addOperator(api::FLOATINGPOINT_ISSN, "fp.isSubnormal"); + addOperator(api::FLOATINGPOINT_ISZ, "fp.isZero"); + addOperator(api::FLOATINGPOINT_ISINF, "fp.isInfinite"); + addOperator(api::FLOATINGPOINT_ISNAN, "fp.isNaN"); + addOperator(api::FLOATINGPOINT_ISNEG, "fp.isNegative"); + addOperator(api::FLOATINGPOINT_ISPOS, "fp.isPositive"); + addOperator(api::FLOATINGPOINT_TO_REAL, "fp.to_real"); + + addIndexedOperator(api::FLOATINGPOINT_TO_FP_GENERIC, api::FLOATINGPOINT_TO_FP_GENERIC, "to_fp"); - addIndexedOperator(kind::FLOATINGPOINT_TO_FP_UNSIGNED_BITVECTOR, + addIndexedOperator(api::FLOATINGPOINT_TO_FP_UNSIGNED_BITVECTOR, api::FLOATINGPOINT_TO_FP_UNSIGNED_BITVECTOR, "to_fp_unsigned"); addIndexedOperator( - kind::FLOATINGPOINT_TO_UBV, api::FLOATINGPOINT_TO_UBV, "fp.to_ubv"); + api::FLOATINGPOINT_TO_UBV, api::FLOATINGPOINT_TO_UBV, "fp.to_ubv"); addIndexedOperator( - kind::FLOATINGPOINT_TO_SBV, api::FLOATINGPOINT_TO_SBV, "fp.to_sbv"); + api::FLOATINGPOINT_TO_SBV, api::FLOATINGPOINT_TO_SBV, "fp.to_sbv"); if (!strictModeEnabled()) { - addIndexedOperator(kind::FLOATINGPOINT_TO_FP_IEEE_BITVECTOR, + addIndexedOperator(api::FLOATINGPOINT_TO_FP_IEEE_BITVECTOR, api::FLOATINGPOINT_TO_FP_IEEE_BITVECTOR, "to_fp_bv"); - addIndexedOperator(kind::FLOATINGPOINT_TO_FP_FLOATINGPOINT, + addIndexedOperator(api::FLOATINGPOINT_TO_FP_FLOATINGPOINT, api::FLOATINGPOINT_TO_FP_FLOATINGPOINT, "to_fp_fp"); - addIndexedOperator(kind::FLOATINGPOINT_TO_FP_REAL, + addIndexedOperator(api::FLOATINGPOINT_TO_FP_REAL, api::FLOATINGPOINT_TO_FP_REAL, "to_fp_real"); - addIndexedOperator(kind::FLOATINGPOINT_TO_FP_SIGNED_BITVECTOR, + addIndexedOperator(api::FLOATINGPOINT_TO_FP_SIGNED_BITVECTOR, api::FLOATINGPOINT_TO_FP_SIGNED_BITVECTOR, "to_fp_signed"); } } void Smt2::addSepOperators() { - addOperator(kind::SEP_STAR, "sep"); - addOperator(kind::SEP_PTO, "pto"); - addOperator(kind::SEP_WAND, "wand"); - addOperator(kind::SEP_EMP, "emp"); - Parser::addOperator(kind::SEP_STAR); - Parser::addOperator(kind::SEP_PTO); - Parser::addOperator(kind::SEP_WAND); - Parser::addOperator(kind::SEP_EMP); + addOperator(api::SEP_STAR, "sep"); + addOperator(api::SEP_PTO, "pto"); + addOperator(api::SEP_WAND, "wand"); + addOperator(api::SEP_EMP, "emp"); + Parser::addOperator(api::SEP_STAR); + Parser::addOperator(api::SEP_PTO); + Parser::addOperator(api::SEP_WAND); + Parser::addOperator(api::SEP_EMP); } void Smt2::addTheory(Theory theory) { switch(theory) { case THEORY_ARRAYS: - addOperator(kind::SELECT, "select"); - addOperator(kind::STORE, "store"); + addOperator(api::SELECT, "select"); + addOperator(api::STORE, "store"); break; case THEORY_BITVECTORS: @@ -288,145 +282,132 @@ void Smt2::addTheory(Theory theory) { break; case THEORY_CORE: - defineType("Bool", getExprManager()->booleanType()); - defineVar("true", getExprManager()->mkConst(true)); - defineVar("false", getExprManager()->mkConst(false)); - addOperator(kind::AND, "and"); - addOperator(kind::DISTINCT, "distinct"); - addOperator(kind::EQUAL, "="); - addOperator(kind::IMPLIES, "=>"); - addOperator(kind::ITE, "ite"); - addOperator(kind::NOT, "not"); - addOperator(kind::OR, "or"); - addOperator(kind::XOR, "xor"); + defineType("Bool", d_solver->getBooleanSort()); + defineVar("true", d_solver->mkTrue()); + defineVar("false", d_solver->mkFalse()); + addOperator(api::AND, "and"); + addOperator(api::DISTINCT, "distinct"); + addOperator(api::EQUAL, "="); + addOperator(api::IMPLIES, "=>"); + addOperator(api::ITE, "ite"); + addOperator(api::NOT, "not"); + addOperator(api::OR, "or"); + addOperator(api::XOR, "xor"); break; case THEORY_REALS_INTS: - defineType("Real", getExprManager()->realType()); - addOperator(kind::DIVISION, "/"); - addOperator(kind::TO_INTEGER, "to_int"); - addOperator(kind::IS_INTEGER, "is_int"); - addOperator(kind::TO_REAL, "to_real"); + defineType("Real", d_solver->getRealSort()); + addOperator(api::DIVISION, "/"); + addOperator(api::TO_INTEGER, "to_int"); + addOperator(api::IS_INTEGER, "is_int"); + addOperator(api::TO_REAL, "to_real"); // falling through on purpose, to add Ints part of Reals_Ints CVC4_FALLTHROUGH; case THEORY_INTS: - defineType("Int", getExprManager()->integerType()); + defineType("Int", d_solver->getIntegerSort()); addArithmeticOperators(); - addOperator(kind::INTS_DIVISION, "div"); - addOperator(kind::INTS_MODULUS, "mod"); - addOperator(kind::ABS, "abs"); - addIndexedOperator(kind::DIVISIBLE, api::DIVISIBLE, "divisible"); + addOperator(api::INTS_DIVISION, "div"); + addOperator(api::INTS_MODULUS, "mod"); + addOperator(api::ABS, "abs"); + addIndexedOperator(api::DIVISIBLE, api::DIVISIBLE, "divisible"); break; case THEORY_REALS: - defineType("Real", getExprManager()->realType()); + defineType("Real", d_solver->getRealSort()); addArithmeticOperators(); - addOperator(kind::DIVISION, "/"); + addOperator(api::DIVISION, "/"); if (!strictModeEnabled()) { - addOperator(kind::ABS, "abs"); + addOperator(api::ABS, "abs"); } break; case THEORY_TRANSCENDENTALS: - defineVar("real.pi", - getExprManager()->mkNullaryOperator(getExprManager()->realType(), - CVC4::kind::PI)); + defineVar("real.pi", d_solver->mkTerm(api::PI)); addTranscendentalOperators(); break; case THEORY_QUANTIFIERS: addQuantifiersOperators(); break; case THEORY_SETS: - defineVar("emptyset", - d_solver->mkEmptySet(d_solver->getNullSort()).getExpr()); + defineVar("emptyset", d_solver->mkEmptySet(d_solver->getNullSort())); // the Boolean sort is a placeholder here since we don't have type info // without type annotation - defineVar("univset", - d_solver->mkUniverseSet(d_solver->getBooleanSort()).getExpr()); - - addOperator(kind::UNION, "union"); - addOperator(kind::INTERSECTION, "intersection"); - addOperator(kind::SETMINUS, "setminus"); - addOperator(kind::SUBSET, "subset"); - addOperator(kind::MEMBER, "member"); - addOperator(kind::SINGLETON, "singleton"); - addOperator(kind::INSERT, "insert"); - addOperator(kind::CARD, "card"); - addOperator(kind::COMPLEMENT, "complement"); - addOperator(kind::JOIN, "join"); - addOperator(kind::PRODUCT, "product"); - addOperator(kind::TRANSPOSE, "transpose"); - addOperator(kind::TCLOSURE, "tclosure"); + defineVar("univset", d_solver->mkUniverseSet(d_solver->getBooleanSort())); + + addOperator(api::UNION, "union"); + addOperator(api::INTERSECTION, "intersection"); + addOperator(api::SETMINUS, "setminus"); + addOperator(api::SUBSET, "subset"); + addOperator(api::MEMBER, "member"); + addOperator(api::SINGLETON, "singleton"); + addOperator(api::INSERT, "insert"); + addOperator(api::CARD, "card"); + addOperator(api::COMPLEMENT, "complement"); + addOperator(api::JOIN, "join"); + addOperator(api::PRODUCT, "product"); + addOperator(api::TRANSPOSE, "transpose"); + addOperator(api::TCLOSURE, "tclosure"); break; case THEORY_DATATYPES: { - const std::vector types; - defineType("Tuple", getExprManager()->mkTupleType(types)); + const std::vector types; + defineType("Tuple", d_solver->mkTupleSort(types)); addDatatypesOperators(); break; } case THEORY_STRINGS: - defineType("String", getExprManager()->stringType()); - defineType("RegLan", getExprManager()->regExpType()); - defineType("Int", getExprManager()->integerType()); + defineType("String", d_solver->getStringSort()); + defineType("RegLan", d_solver->getRegExpSort()); + defineType("Int", d_solver->getIntegerSort()); if (getLanguage() == language::input::LANG_SMTLIB_V2_6_1) { - defineVar("re.none", d_solver->mkRegexpEmpty().getExpr()); + defineVar("re.none", d_solver->mkRegexpEmpty()); } else { - defineVar("re.nostr", d_solver->mkRegexpEmpty().getExpr()); + defineVar("re.nostr", d_solver->mkRegexpEmpty()); } - defineVar("re.allchar", d_solver->mkRegexpSigma().getExpr()); + defineVar("re.allchar", d_solver->mkRegexpSigma()); addStringOperators(); break; case THEORY_UF: - Parser::addOperator(kind::APPLY_UF); + Parser::addOperator(api::APPLY_UF); if (!strictModeEnabled() && d_logic.hasCardinalityConstraints()) { - addOperator(kind::CARDINALITY_CONSTRAINT, "fmf.card"); - addOperator(kind::CARDINALITY_VALUE, "fmf.card.val"); + addOperator(api::CARDINALITY_CONSTRAINT, "fmf.card"); + addOperator(api::CARDINALITY_VALUE, "fmf.card.val"); } break; case THEORY_FP: - defineType("RoundingMode", getExprManager()->roundingModeType()); - defineType("Float16", getExprManager()->mkFloatingPointType(5, 11)); - defineType("Float32", getExprManager()->mkFloatingPointType(8, 24)); - defineType("Float64", getExprManager()->mkFloatingPointType(11, 53)); - defineType("Float128", getExprManager()->mkFloatingPointType(15, 113)); - - defineVar( - "RNE", - d_solver->mkRoundingMode(api::ROUND_NEAREST_TIES_TO_EVEN).getExpr()); - defineVar( - "roundNearestTiesToEven", - d_solver->mkRoundingMode(api::ROUND_NEAREST_TIES_TO_EVEN).getExpr()); - defineVar( - "RNA", - d_solver->mkRoundingMode(api::ROUND_NEAREST_TIES_TO_AWAY).getExpr()); - defineVar( - "roundNearestTiesToAway", - d_solver->mkRoundingMode(api::ROUND_NEAREST_TIES_TO_AWAY).getExpr()); - defineVar("RTP", - d_solver->mkRoundingMode(api::ROUND_TOWARD_POSITIVE).getExpr()); + defineType("RoundingMode", d_solver->getRoundingmodeSort()); + defineType("Float16", d_solver->mkFloatingPointSort(5, 11)); + defineType("Float32", d_solver->mkFloatingPointSort(8, 24)); + defineType("Float64", d_solver->mkFloatingPointSort(11, 53)); + defineType("Float128", d_solver->mkFloatingPointSort(15, 113)); + + defineVar("RNE", d_solver->mkRoundingMode(api::ROUND_NEAREST_TIES_TO_EVEN)); + defineVar("roundNearestTiesToEven", + d_solver->mkRoundingMode(api::ROUND_NEAREST_TIES_TO_EVEN)); + defineVar("RNA", d_solver->mkRoundingMode(api::ROUND_NEAREST_TIES_TO_AWAY)); + defineVar("roundNearestTiesToAway", + d_solver->mkRoundingMode(api::ROUND_NEAREST_TIES_TO_AWAY)); + defineVar("RTP", d_solver->mkRoundingMode(api::ROUND_TOWARD_POSITIVE)); defineVar("roundTowardPositive", - d_solver->mkRoundingMode(api::ROUND_TOWARD_POSITIVE).getExpr()); - defineVar("RTN", - d_solver->mkRoundingMode(api::ROUND_TOWARD_NEGATIVE).getExpr()); + d_solver->mkRoundingMode(api::ROUND_TOWARD_POSITIVE)); + defineVar("RTN", d_solver->mkRoundingMode(api::ROUND_TOWARD_NEGATIVE)); defineVar("roundTowardNegative", - d_solver->mkRoundingMode(api::ROUND_TOWARD_NEGATIVE).getExpr()); - defineVar("RTZ", - d_solver->mkRoundingMode(api::ROUND_TOWARD_ZERO).getExpr()); + d_solver->mkRoundingMode(api::ROUND_TOWARD_NEGATIVE)); + defineVar("RTZ", d_solver->mkRoundingMode(api::ROUND_TOWARD_ZERO)); defineVar("roundTowardZero", - d_solver->mkRoundingMode(api::ROUND_TOWARD_ZERO).getExpr()); + d_solver->mkRoundingMode(api::ROUND_TOWARD_ZERO)); addFloatingPointOperators(); break; @@ -434,8 +415,7 @@ void Smt2::addTheory(Theory theory) { case THEORY_SEP: // the Boolean sort is a placeholder here since we don't have type info // without type annotation - defineVar("sep.nil", - d_solver->mkSepNil(d_solver->getBooleanSort()).getExpr()); + defineVar("sep.nil", d_solver->mkSepNil(d_solver->getBooleanSort())); addSepOperators(); break; @@ -447,14 +427,15 @@ void Smt2::addTheory(Theory theory) { } } -void Smt2::addOperator(Kind kind, const std::string& name) { +void Smt2::addOperator(api::Kind kind, const std::string& name) +{ Debug("parser") << "Smt2::addOperator( " << kind << ", " << name << " )" << std::endl; Parser::addOperator(kind); operatorKindMap[name] = kind; } -void Smt2::addIndexedOperator(Kind tKind, +void Smt2::addIndexedOperator(api::Kind tKind, api::Kind opKind, const std::string& name) { @@ -462,7 +443,8 @@ void Smt2::addIndexedOperator(Kind tKind, d_indexedOpKindMap[name] = opKind; } -Kind Smt2::getOperatorKind(const std::string& name) const { +api::Kind Smt2::getOperatorKind(const std::string& name) const +{ // precondition: isOperatorEnabled(name) return operatorKindMap.find(name)->second; } @@ -513,7 +495,9 @@ bool Smt2::logicIsSet() { return d_logicSet; } -Expr Smt2::getExpressionForNameAndType(const std::string& name, Type t) { +api::Term Smt2::getExpressionForNameAndType(const std::string& name, + api::Sort t) +{ if (isAbstractValue(name)) { return mkAbstractValue(name); @@ -581,40 +565,40 @@ api::Op Smt2::mkIndexedOp(const std::string& name, return api::Op(); } -Expr Smt2::mkDefineFunRec( +api::Term Smt2::bindDefineFunRec( const std::string& fname, - const std::vector >& sortedVarNames, - Type t, - std::vector& flattenVars) + const std::vector>& sortedVarNames, + api::Sort t, + std::vector& flattenVars) { - std::vector sorts; - for (const std::pair& svn : sortedVarNames) + std::vector sorts; + for (const std::pair& svn : sortedVarNames) { sorts.push_back(svn.second); } // make the flattened function type, add bound variables // to flattenVars if the defined function was given a function return type. - Type ft = mkFlatFunctionType(sorts, t, flattenVars); + api::Sort ft = mkFlatFunctionType(sorts, t, flattenVars); // allow overloading - return mkVar(fname, ft, ExprManager::VAR_FLAG_NONE, true); + return bindVar(fname, ft, ExprManager::VAR_FLAG_NONE, true); } void Smt2::pushDefineFunRecScope( - const std::vector >& sortedVarNames, - Expr func, - const std::vector& flattenVars, - std::vector& bvs, + const std::vector>& sortedVarNames, + api::Term func, + const std::vector& flattenVars, + std::vector& bvs, bool bindingLevel) { pushScope(bindingLevel); // bound variables are those that are explicitly named in the preamble // of the define-fun(s)-rec command, we define them here - for (const std::pair& svn : sortedVarNames) + for (const std::pair& svn : sortedVarNames) { - Expr v = mkBoundVar(svn.first, svn.second); + api::Term v = bindBoundVar(svn.first, svn.second); bvs.push_back(v); } @@ -626,7 +610,7 @@ void Smt2::reset() { d_seenSetLogic = false; d_logic = LogicInfo(); operatorKindMap.clear(); - d_lastNamedTerm = std::pair(); + d_lastNamedTerm = std::pair(); this->Parser::reset(); if( !strictModeEnabled() ) { @@ -645,8 +629,8 @@ Smt2::SynthFunFactory::SynthFunFactory( Smt2* smt2, const std::string& fun, bool isInv, - Type range, - std::vector>& sortedVarNames) + api::Sort range, + std::vector>& sortedVarNames) : d_smt2(smt2), d_fun(fun), d_isInv(isInv) { if (range.isNull()) @@ -657,38 +641,37 @@ Smt2::SynthFunFactory::SynthFunFactory( { smt2->parseError("Cannot use synth-fun with function return type."); } - std::vector varSorts; - for (const std::pair& p : sortedVarNames) + std::vector varSorts; + for (const std::pair& p : sortedVarNames) { varSorts.push_back(p.second); } Debug("parser-sygus") << "Define synth fun : " << fun << std::endl; - Type synthFunType = - varSorts.size() > 0 - ? d_smt2->getExprManager()->mkFunctionType(varSorts, range) - : range; + api::Sort synthFunType = + varSorts.size() > 0 ? d_smt2->getSolver()->mkFunctionSort(varSorts, range) + : range; // we do not allow overloading for synth fun - d_synthFun = d_smt2->mkBoundVar(fun, synthFunType); + d_synthFun = d_smt2->bindBoundVar(fun, synthFunType); // set the sygus type to be range by default, which is overwritten below // if a grammar is provided d_sygusType = range; d_smt2->pushScope(true); - d_sygusVars = d_smt2->mkBoundVars(sortedVarNames); + d_sygusVars = d_smt2->bindBoundVars(sortedVarNames); } Smt2::SynthFunFactory::~SynthFunFactory() { d_smt2->popScope(); } -std::unique_ptr Smt2::SynthFunFactory::mkCommand(Type grammar) +std::unique_ptr Smt2::SynthFunFactory::mkCommand(api::Sort grammar) { Debug("parser-sygus") << "...read synth fun " << d_fun << std::endl; - return std::unique_ptr( - new SynthFunCommand(d_fun, - d_synthFun, - grammar.isNull() ? d_sygusType : grammar, - d_isInv, - d_sygusVars)); + return std::unique_ptr(new SynthFunCommand( + d_fun, + d_synthFun.getExpr(), + grammar.isNull() ? d_sygusType.getType() : grammar.getType(), + d_isInv, + api::termVectorToExprs(d_sygusVars))); } std::unique_ptr Smt2::invConstraint( @@ -705,7 +688,7 @@ std::unique_ptr Smt2::invConstraint( "arguments."); } - std::vector terms; + std::vector terms; for (const std::string& name : names) { if (!isDeclared(name)) @@ -718,7 +701,8 @@ std::unique_ptr Smt2::invConstraint( terms.push_back(getVariable(name)); } - return std::unique_ptr(new SygusInvConstraintCommand(terms)); + return std::unique_ptr( + new SygusInvConstraintCommand(api::termVectorToExprs(terms))); } Command* Smt2::setLogic(std::string name, bool fromCommand) @@ -932,33 +916,32 @@ void Smt2::includeFile(const std::string& filename) { parseError("Couldn't open include file `" + path + "'"); } } - bool Smt2::isAbstractValue(const std::string& name) { return name.length() >= 2 && name[0] == '@' && name[1] != '0' && name.find_first_not_of("0123456789", 1) == std::string::npos; } -Expr Smt2::mkAbstractValue(const std::string& name) +api::Term Smt2::mkAbstractValue(const std::string& name) { assert(isAbstractValue(name)); // remove the '@' - return getExprManager()->mkConst(AbstractValue(Integer(name.substr(1)))); + return d_solver->mkAbstractValue(name.substr(1)); } -void Smt2::mkSygusConstantsForType( const Type& type, std::vector& ops ) { +void Smt2::mkSygusConstantsForType(const api::Sort& type, + std::vector& ops) +{ if( type.isInteger() ){ - ops.push_back(getExprManager()->mkConst(Rational(0))); - ops.push_back(getExprManager()->mkConst(Rational(1))); + ops.push_back(d_solver->mkReal(0)); + ops.push_back(d_solver->mkReal(1)); }else if( type.isBitVector() ){ - unsigned sz = ((BitVectorType)type).getSize(); - BitVector bval0(sz, (unsigned int)0); - ops.push_back( getExprManager()->mkConst(bval0) ); - BitVector bval1(sz, (unsigned int)1); - ops.push_back( getExprManager()->mkConst(bval1) ); + uint32_t sz = type.getBVSize(); + ops.push_back(d_solver->mkBitVector(sz, 0)); + ops.push_back(d_solver->mkBitVector(sz, 1)); }else if( type.isBoolean() ){ - ops.push_back(getExprManager()->mkConst(true)); - ops.push_back(getExprManager()->mkConst(false)); + ops.push_back(d_solver->mkTrue()); + ops.push_back(d_solver->mkFalse()); } //TODO : others? } @@ -969,36 +952,37 @@ void Smt2::processSygusGTerm( CVC4::SygusGTerm& sgt, int index, std::vector& datatypes, - std::vector& sorts, + std::vector& sorts, std::vector>& ops, std::vector>& cnames, - std::vector>>& cargs, + std::vector>>& cargs, std::vector& allow_const, std::vector>& unresolved_gterm_sym, - const std::vector& sygus_vars, - std::map& sygus_to_builtin, - std::map& sygus_to_builtin_expr, - CVC4::Type& ret, + const std::vector& sygus_vars, + std::map& sygus_to_builtin, + std::map& sygus_to_builtin_expr, + api::Sort& ret, bool isNested) { if (sgt.d_gterm_type == SygusGTerm::gterm_op) { Debug("parser-sygus") << "Add " << sgt.d_op << " to datatype " << index << std::endl; - Kind oldKind; - Kind newKind = kind::UNDEFINED_KIND; + api::Kind oldKind; + api::Kind newKind = api::UNDEFINED_KIND; //convert to UMINUS if one child of MINUS - if (sgt.d_children.size() == 1 && sgt.d_op.d_kind == kind::MINUS) + if (sgt.d_children.size() == 1 && sgt.d_op.d_kind == api::MINUS) { - oldKind = kind::MINUS; - newKind = kind::UMINUS; + oldKind = api::MINUS; + newKind = api::UMINUS; } - if( newKind!=kind::UNDEFINED_KIND ){ + if (newKind != api::UNDEFINED_KIND) + { Debug("parser-sygus") << "Replace " << sgt.d_op.d_kind << " with " << newKind << std::endl; sgt.d_op.d_kind = newKind; - std::string oldName = kind::kindToString(oldKind); - std::string newName = kind::kindToString(newKind); + std::string oldName = api::kindToString(oldKind); + std::string newName = api::kindToString(newKind); size_t pos = 0; if((pos = sgt.d_name.find(oldName, pos)) != std::string::npos){ sgt.d_name.replace(pos, oldName.length(), newName); @@ -1006,22 +990,32 @@ void Smt2::processSygusGTerm( } ops[index].push_back(sgt.d_op); cnames[index].push_back( sgt.d_name ); - cargs[index].push_back( std::vector< CVC4::Type >() ); + cargs[index].push_back(std::vector()); for( unsigned i=0; i consts; + std::vector consts; mkSygusConstantsForType( sgt.d_type, consts ); Debug("parser-sygus") << "...made " << consts.size() << " constants." << std::endl; for( unsigned i=0; i() ); + cargs[index].push_back(std::vector()); } allow_const[index] = true; } @@ -1053,7 +1047,8 @@ void Smt2::processSygusGTerm( } Debug("parser-sygus") << "...process " << sygus_vars.size() << " variables." << std::endl; for( unsigned i=0; i() ); + cargs[index].push_back(std::vector()); } } } @@ -1092,13 +1087,13 @@ void Smt2::processSygusGTerm( } bool Smt2::pushSygusDatatypeDef( - Type t, + api::Sort t, std::string& dname, std::vector& datatypes, - std::vector& sorts, + std::vector& sorts, std::vector>& ops, std::vector>& cnames, - std::vector>>& cargs, + std::vector>>& cargs, std::vector& allow_const, std::vector>& unresolved_gterm_sym) { @@ -1106,7 +1101,7 @@ bool Smt2::pushSygusDatatypeDef( datatypes.push_back(Datatype(getExprManager(), dname)); ops.push_back(std::vector()); cnames.push_back(std::vector()); - cargs.push_back(std::vector >()); + cargs.push_back(std::vector>()); allow_const.push_back(false); unresolved_gterm_sym.push_back(std::vector< std::string >()); return true; @@ -1114,10 +1109,10 @@ bool Smt2::pushSygusDatatypeDef( bool Smt2::popSygusDatatypeDef( std::vector& datatypes, - std::vector& sorts, + std::vector& sorts, std::vector>& ops, std::vector>& cnames, - std::vector>>& cargs, + std::vector>>& cargs, std::vector& allow_const, std::vector>& unresolved_gterm_sym) { @@ -1131,21 +1126,21 @@ bool Smt2::popSygusDatatypeDef( return true; } -Type Smt2::processSygusNestedGTerm( +api::Sort Smt2::processSygusNestedGTerm( int sub_dt_index, std::string& sub_dname, std::vector& datatypes, - std::vector& sorts, + std::vector& sorts, std::vector>& ops, std::vector>& cnames, - std::vector>>& cargs, + std::vector>>& cargs, std::vector& allow_const, std::vector>& unresolved_gterm_sym, - std::map& sygus_to_builtin, - std::map& sygus_to_builtin_expr, - Type sub_ret) + std::map& sygus_to_builtin, + std::map& sygus_to_builtin_expr, + api::Sort sub_ret) { - Type t = sub_ret; + api::Sort t = sub_ret; Debug("parser-sygus") << "Argument is "; if( t.isNull() ){ //then, it is the datatype we constructed, which should have a single constructor @@ -1156,13 +1151,16 @@ Type Smt2::processSygusNestedGTerm( parseError(std::string("Internal error : datatype for nested gterm does not have a constructor.")); } ParseOp op = ops[sub_dt_index][0]; - Type curr_t; + api::Sort curr_t; if (!op.d_expr.isNull() && (op.d_expr.isConst() || cargs[sub_dt_index][0].empty())) { - Expr sop = op.d_expr; - curr_t = sop.getType(); - Debug("parser-sygus") << ": it is constant/0-arg cons " << sop << " with type " << sop.getType() << ", debug=" << sop.isConst() << " " << cargs[sub_dt_index][0].size() << std::endl; + api::Term sop = op.d_expr; + curr_t = sop.getSort(); + Debug("parser-sygus") + << ": it is constant/0-arg cons " << sop << " with type " + << sop.getSort() << ", debug=" << sop.isConst() << " " + << cargs[sub_dt_index][0].size() << std::endl; // only cache if it is a singleton datatype (has unique expr) if (ops[sub_dt_index].size() == 1) { @@ -1176,24 +1174,29 @@ Type Smt2::processSygusNestedGTerm( } else { - std::vector< Expr > children; + std::vector children; for( unsigned i=0; i::iterator it = sygus_to_builtin_expr.find( cargs[sub_dt_index][0][i] ); + std::map::iterator it = + sygus_to_builtin_expr.find(cargs[sub_dt_index][0][i]); if( it==sygus_to_builtin_expr.end() ){ if( sygus_to_builtin.find( cargs[sub_dt_index][0][i] )==sygus_to_builtin.end() ){ std::stringstream ss; ss << "Missing builtin type for type " << cargs[sub_dt_index][0][i] << "!" << std::endl; ss << "Builtin types are currently : " << std::endl; - for( std::map< CVC4::Type, CVC4::Type >::iterator itb = sygus_to_builtin.begin(); itb != sygus_to_builtin.end(); ++itb ){ + for (std::map::iterator itb = + sygus_to_builtin.begin(); + itb != sygus_to_builtin.end(); + ++itb) + { ss << " " << itb->first << " -> " << itb->second << std::endl; } parseError(ss.str()); } - Type bt = sygus_to_builtin[cargs[sub_dt_index][0][i]]; + api::Sort bt = sygus_to_builtin[cargs[sub_dt_index][0][i]]; Debug("parser-sygus") << ": child " << i << " introduce type elem for " << cargs[sub_dt_index][0][i] << " " << bt << std::endl; std::stringstream ss; ss << t << "_x_" << i; - Expr bv = mkBoundVar(ss.str(), bt); + api::Term bv = bindBoundVar(ss.str(), bt); children.push_back( bv ); d_sygus_bound_var_type[bv] = cargs[sub_dt_index][0][i]; }else{ @@ -1201,9 +1204,10 @@ Type Smt2::processSygusNestedGTerm( children.push_back( it->second ); } } - Expr e = applyParseOp(op, children); - Debug("parser-sygus") << ": constructed " << e << ", which has type " << e.getType() << std::endl; - curr_t = e.getType(); + api::Term e = applyParseOp(op, children); + Debug("parser-sygus") << ": constructed " << e << ", which has type " + << e.getSort() << std::endl; + curr_t = e.getSort(); sygus_to_builtin_expr[t] = e; } sorts[sub_dt_index] = curr_t; @@ -1221,12 +1225,12 @@ Type Smt2::processSygusNestedGTerm( void Smt2::setSygusStartIndex(const std::string& fun, int startIndex, std::vector& datatypes, - std::vector& sorts, + std::vector& sorts, std::vector>& ops) { if( startIndex>0 ){ CVC4::Datatype tmp_dt = datatypes[0]; - Type tmp_sort = sorts[0]; + api::Sort tmp_sort = sorts[0]; std::vector tmp_ops; tmp_ops.insert( tmp_ops.end(), ops[0].begin(), ops[0].end() ); datatypes[0] = datatypes[startIndex]; @@ -1247,9 +1251,9 @@ void Smt2::setSygusStartIndex(const std::string& fun, void Smt2::mkSygusDatatype(CVC4::Datatype& dt, std::vector& ops, std::vector& cnames, - std::vector>& cargs, + std::vector>& cargs, std::vector& unresolved_gterm_sym, - std::map& sygus_to_builtin) + std::map& sygus_to_builtin) { Debug("parser-sygus") << "Making sygus datatype " << dt.getName() << std::endl; Debug("parser-sygus") << " add constructors..." << std::endl; @@ -1295,28 +1299,29 @@ void Smt2::mkSygusDatatype(CVC4::Datatype& dt, Debug("parser-sygus") << "--> Duplicate gterm operator : " << ops[i] << std::endl; // make into define-fun - std::vector ltypes; + std::vector ltypes; for (unsigned j = 0, size = cargs[i].size(); j < size; j++) { ltypes.push_back(sygus_to_builtin[cargs[i][j]]); } - std::vector largs; - Expr lbvl = makeSygusBoundVarList(dt, i, ltypes, largs); + std::vector largs; + api::Term lbvl = makeSygusBoundVarList(dt, i, ltypes, largs); // make the let_body - Expr body = applyParseOp(ops[i], largs); + api::Term body = applyParseOp(ops[i], largs); // replace by lambda ParseOp pLam; - pLam.d_expr = getExprManager()->mkExpr(kind::LAMBDA, lbvl, body); + pLam.d_expr = d_solver->mkTerm(api::LAMBDA, lbvl, body); ops[i] = pLam; Debug("parser-sygus") << " ...replace op : " << ops[i] << std::endl; // callback prints as the expression - spc = std::make_shared(body, largs); + spc = std::make_shared( + body.getExpr(), api::termVectorToExprs(largs)); } else { - Expr sop = ops[i].d_expr; - if (!sop.isNull() && sop.getType().isBitVector() && sop.isConst()) + api::Term sop = ops[i].d_expr; + if (!sop.isNull() && sop.getSort().isBitVector() && sop.isConst()) { Debug("parser-sygus") << "--> Bit-vector constant " << sop << " (" << cnames[i] << ")" << std::endl; @@ -1326,22 +1331,22 @@ void Smt2::mkSygusDatatype(CVC4::Datatype& dt, // the given name. spc = std::make_shared(cnames[i]); } - else if (!sop.isNull() && sop.getKind() == kind::VARIABLE) + else if (!sop.isNull() && sop.getKind() == api::VARIABLE) { Debug("parser-sygus") << "--> Defined function " << ops[i] << std::endl; // turn f into (lammbda (x) (f x)) // in a degenerate case, ops[i] may be a defined constant, // in which case we do not replace by a lambda. - if (sop.getType().isFunction()) + if (sop.getSort().isFunction()) { - std::vector ftypes = - static_cast(sop.getType()).getArgTypes(); - std::vector largs; - Expr lbvl = makeSygusBoundVarList(dt, i, ftypes, largs); + std::vector ftypes = + sop.getSort().getFunctionDomainSorts(); + std::vector largs; + api::Term lbvl = makeSygusBoundVarList(dt, i, ftypes, largs); largs.insert(largs.begin(), sop); - Expr body = getExprManager()->mkExpr(kind::APPLY_UF, largs); - ops[i].d_expr = getExprManager()->mkExpr(kind::LAMBDA, lbvl, body); + api::Term body = d_solver->mkTerm(api::APPLY_UF, largs); + ops[i].d_expr = d_solver->mkTerm(api::LAMBDA, lbvl, body); Debug("parser-sygus") << " ...replace op : " << ops[i] << std::endl; } @@ -1364,15 +1369,22 @@ void Smt2::mkSygusDatatype(CVC4::Datatype& dt, cnames[i] = ss.str(); Debug("parser-sygus") << " construct the datatype " << cnames[i] << "..." << std::endl; + // Add the sygus constructor, either using the expression operator of // ops[i], or the kind. if (!ops[i].d_expr.isNull()) { - dt.addSygusConstructor(ops[i].d_expr, cnames[i], cargs[i], spc); + dt.addSygusConstructor(ops[i].d_expr.getExpr(), + cnames[i], + api::sortVectorToTypes(cargs[i]), + spc); } - else if (ops[i].d_kind != kind::NULL_EXPR) + else if (ops[i].d_kind != api::NULL_EXPR) { - dt.addSygusConstructor(ops[i].d_kind, cnames[i], cargs[i], spc); + dt.addSygusConstructor(extToIntKind(ops[i].d_kind), + cnames[i], + api::sortVectorToTypes(cargs[i]), + spc); } else { @@ -1387,36 +1399,38 @@ void Smt2::mkSygusDatatype(CVC4::Datatype& dt, Debug("parser-sygus") << " add constructors for unresolved symbols..." << std::endl; if( !unresolved_gterm_sym.empty() ){ - std::vector< Type > types; + std::vector types; Debug("parser-sygus") << "...resolve " << unresolved_gterm_sym.size() << " symbols..." << std::endl; for( unsigned i=0; i lchildren; - lchildren.push_back( - getExprManager()->mkExpr(kind::BOUND_VAR_LIST, var)); + api::Term var = bindBoundVar(ss.str(), bt); + std::vector lchildren; + lchildren.push_back(d_solver->mkTerm(api::BOUND_VAR_LIST, var)); lchildren.push_back(var); - Expr id_op = getExprManager()->mkExpr(kind::LAMBDA, lchildren); + api::Term id_op = d_solver->mkTerm(api::LAMBDA, lchildren); // empty sygus callback (should not be printed) std::shared_ptr sepc = std::make_shared(); //make the sygus argument list - std::vector< Type > id_carg; + std::vector id_carg; id_carg.push_back( t ); - dt.addSygusConstructor(id_op, unresolved_gterm_sym[i], id_carg, sepc); + dt.addSygusConstructor(id_op.getExpr(), + unresolved_gterm_sym[i], + api::sortVectorToTypes(id_carg), + sepc); //add to operators ParseOp idOp; @@ -1432,31 +1446,30 @@ void Smt2::mkSygusDatatype(CVC4::Datatype& dt, } } -Expr Smt2::makeSygusBoundVarList(Datatype& dt, - unsigned i, - const std::vector& ltypes, - std::vector& lvars) +api::Term Smt2::makeSygusBoundVarList(CVC4::Datatype& dt, + unsigned i, + const std::vector& ltypes, + std::vector& lvars) { for (unsigned j = 0, size = ltypes.size(); j < size; j++) { std::stringstream ss; ss << dt.getName() << "_x_" << i << "_" << j; - Expr v = mkBoundVar(ss.str(), ltypes[j]); + api::Term v = bindBoundVar(ss.str(), ltypes[j]); lvars.push_back(v); } - return getExprManager()->mkExpr(kind::BOUND_VAR_LIST, lvars); + return d_solver->mkTerm(api::BOUND_VAR_LIST, lvars); } -void Smt2::addSygusConstructorTerm(Datatype& dt, - Expr term, - std::map& ntsToUnres) const +void Smt2::addSygusConstructorTerm( + Datatype& dt, + api::Term term, + std::map& ntsToUnres) const { Trace("parser-sygus2") << "Add sygus cons term " << term << std::endl; - // Ensure that we do type checking here to catch sygus constructors with - // malformed builtin operators. The argument "true" to getType here forces - // a recursive well-typedness check. - term.getType(true); - // purify each occurrence of a non-terminal symbol in term, replace by + // At this point, we should know that dt is well founded, and that its + // builtin sygus operators are well-typed. + // Now, purify each occurrence of a non-terminal symbol in term, replace by // free variables. These become arguments to constructors. Notice we must do // a tree traversal in this function, since unique paths to the same term // should be treated as distinct terms. @@ -1464,7 +1477,7 @@ void Smt2::addSygusConstructorTerm(Datatype& dt, // this does not lead to exponential behavior with respect to input size. std::vector args; std::vector cargs; - api::Term op = purifySygusGTerm(api::Term(term), ntsToUnres, args, cargs); + api::Term op = purifySygusGTerm(term, ntsToUnres, args, cargs); std::stringstream ssCName; ssCName << op.getKind(); Trace("parser-sygus2") << "Purified operator " << op @@ -1487,14 +1500,14 @@ void Smt2::addSygusConstructorTerm(Datatype& dt, } api::Term Smt2::purifySygusGTerm(api::Term term, - std::map& ntsToUnres, + std::map& ntsToUnres, std::vector& args, std::vector& cargs) const { Trace("parser-sygus2-debug") << "purifySygusGTerm: " << term << " #nchild=" << term.getExpr().getNumChildren() << std::endl; - std::map::iterator itn = ntsToUnres.find(term.getExpr()); + std::map::iterator itn = ntsToUnres.find(term); if (itn != ntsToUnres.end()) { api::Term ret = d_solver->mkVar(term.getSort()); @@ -1526,35 +1539,35 @@ api::Term Smt2::purifySygusGTerm(api::Term term, } void Smt2::addSygusConstructorVariables(Datatype& dt, - const std::vector& sygusVars, - Type type) const + const std::vector& sygusVars, + api::Sort type) const { // each variable of appropriate type becomes a sygus constructor in dt. for (unsigned i = 0, size = sygusVars.size(); i < size; i++) { - Expr v = sygusVars[i]; - if (v.getType() == type) + api::Term v = sygusVars[i]; + if (v.getSort() == type) { std::stringstream ss; ss << v; - std::vector cargs; - dt.addSygusConstructor(v, ss.str(), cargs); + std::vector cargs; + dt.addSygusConstructor( + v.getExpr(), ss.str(), api::sortVectorToTypes(cargs)); } } } InputLanguage Smt2::getLanguage() const { - ExprManager* em = getExprManager(); - return em->getOptions().getInputLanguage(); + return getExprManager()->getOptions().getInputLanguage(); } -void Smt2::parseOpApplyTypeAscription(ParseOp& p, Type type) +void Smt2::parseOpApplyTypeAscription(ParseOp& p, api::Sort type) { Debug("parser") << "parseOpApplyTypeAscription : " << p << " " << type << std::endl; // (as const (Array T1 T2)) - if (p.d_kind == kind::STORE_ALL) + if (p.d_kind == api::STORE_ALL) { if (!type.isArray()) { @@ -1576,6 +1589,7 @@ void Smt2::parseOpApplyTypeAscription(ParseOp& p, Type type) if (isDeclared(p.d_name, SYM_VARIABLE)) { p.d_expr = getExpressionForNameAndType(p.d_name, type); + p.d_name = std::string(""); } if (p.d_expr.isNull()) { @@ -1586,17 +1600,18 @@ void Smt2::parseOpApplyTypeAscription(ParseOp& p, Type type) } } Trace("parser-qid") << "Resolve ascription " << type << " on " << p.d_expr; - Trace("parser-qid") << " " << p.d_expr.getKind() << " " << p.d_expr.getType(); + Trace("parser-qid") << " " << p.d_expr.getKind() << " " << p.d_expr.getSort(); Trace("parser-qid") << std::endl; // otherwise, we process the type ascription p.d_expr = applyTypeAscription(api::Term(p.d_expr), api::Sort(type)).getExpr(); } -Expr Smt2::parseOpToExpr(ParseOp& p) +api::Term Smt2::parseOpToExpr(ParseOp& p) { - Expr expr; - if (p.d_kind != kind::NULL_EXPR || !p.d_type.isNull()) + Debug("parser") << "parseOpToExpr: " << p << std::endl; + api::Term expr; + if (p.d_kind != api::NULL_EXPR || !p.d_type.isNull()) { parseError( "Bad syntax for qualified identifier operator in term position."); @@ -1611,7 +1626,7 @@ Expr Smt2::parseOpToExpr(ParseOp& p) && p.d_name.find_first_not_of("0123456789", 1) == std::string::npos) { // allow unary minus in sygus version 1 - expr = getExprManager()->mkConst(Rational(p.d_name)); + expr = d_solver->mkReal(p.d_name); } else { @@ -1628,38 +1643,41 @@ Expr Smt2::parseOpToExpr(ParseOp& p) return expr; } -Expr Smt2::applyParseOp(ParseOp& p, std::vector& args) +api::Term Smt2::applyParseOp(ParseOp& p, std::vector& args) { bool isBuiltinOperator = false; // the builtin kind of the overall return expression - Kind kind = kind::NULL_EXPR; + api::Kind kind = api::NULL_EXPR; // First phase: process the operator if (Debug.isOn("parser")) { Debug("parser") << "applyParseOp: " << p << " to:" << std::endl; - for (std::vector::iterator i = args.begin(); i != args.end(); ++i) + for (std::vector::iterator i = args.begin(); i != args.end(); + ++i) { Debug("parser") << "++ " << *i << std::endl; } } api::Op op; - if (p.d_kind != kind::NULL_EXPR) + if (p.d_kind != api::NULL_EXPR) { // It is a special case, e.g. tupSel or array constant specification. // We have to wait until the arguments are parsed to resolve it. } else if (!p.d_expr.isNull()) { - // An explicit operator, e.g. an indexed symbol. - args.insert(args.begin(), p.d_expr); - Kind fkind = getKindForFunction(p.d_expr); - if (fkind != kind::UNDEFINED_KIND) + // An explicit operator, e.g. an apply function + api::Kind fkind = getKindForFunction(p.d_expr); + if (fkind != api::UNDEFINED_KIND) { // Some operators may require a specific kind. // Testers are handled differently than other indexed operators, // since they require a kind. kind = fkind; + Debug("parser") << "Got function kind " << kind << " for expression " + << std::endl; } + args.insert(args.begin(), p.d_expr); } else if (!p.d_op.isNull()) { @@ -1678,7 +1696,7 @@ Expr Smt2::applyParseOp(ParseOp& p, std::vector& args) { // A non-built-in function application, get the expression checkDeclaration(p.d_name, CHECK_DECLARED, SYM_VARIABLE); - Expr v = getVariable(p.d_name); + api::Term v = getVariable(p.d_name); if (!v.isNull()) { checkFunctionLike(v); @@ -1691,12 +1709,13 @@ Expr Smt2::applyParseOp(ParseOp& p, std::vector& args) // Could not find the expression. It may be an overloaded symbol, // in which case we may find it after knowing the types of its // arguments. - std::vector argTypes; - for (std::vector::iterator i = args.begin(); i != args.end(); ++i) + std::vector argTypes; + for (std::vector::iterator i = args.begin(); i != args.end(); + ++i) { - argTypes.push_back((*i).getType()); + argTypes.push_back((*i).getSort()); } - Expr fop = getOverloadedFunctionForTypes(p.d_name, argTypes); + api::Term fop = getOverloadedFunctionForTypes(p.d_name, argTypes); if (!fop.isNull()) { checkFunctionLike(fop); @@ -1715,13 +1734,13 @@ Expr Smt2::applyParseOp(ParseOp& p, std::vector& args) // Second phase: apply the arguments to the parse op ExprManager* em = getExprManager(); // handle special cases - if (p.d_kind == kind::STORE_ALL && !p.d_type.isNull()) + if (p.d_kind == api::STORE_ALL && !p.d_type.isNull()) { if (args.size() != 1) { parseError("Too many arguments to array constant."); } - Expr constVal = args[0]; + api::Term constVal = args[0]; if (!constVal.isConst()) { // To parse array constants taking reals whose values are specified by @@ -1732,12 +1751,13 @@ Expr Smt2::applyParseOp(ParseOp& p, std::vector& args) // like 5.0 which are converted to (/ 5 1) to distinguish them from // integer constants. We must ensure numerator and denominator are // constant and the denominator is non-zero. - if (constVal.getKind() == kind::DIVISION && constVal[0].isConst() + if (constVal.getKind() == api::DIVISION && constVal[0].isConst() && constVal[1].isConst() - && !constVal[1].getConst().isZero()) + && !constVal[1].getExpr().getConst().isZero()) { - constVal = em->mkConst(constVal[0].getConst() - / constVal[1].getConst()); + std::stringstream sdiv; + sdiv << constVal[0] << "/" << constVal[1]; + constVal = d_solver->mkReal(sdiv.str()); } if (!constVal.isConst()) { @@ -1748,47 +1768,52 @@ Expr Smt2::applyParseOp(ParseOp& p, std::vector& args) parseError(ss.str()); } } - ArrayType aqtype = static_cast(p.d_type); - if (!aqtype.getConstituentType().isComparableTo(constVal.getType())) + if (!p.d_type.getArrayElementSort().isComparableTo(constVal.getSort())) { std::stringstream ss; ss << "type mismatch inside array constant term:" << std::endl << "array type: " << p.d_type << std::endl - << "expected const type: " << aqtype.getConstituentType() << std::endl - << "computed const type: " << constVal.getType(); + << "expected const type: " << p.d_type.getArrayElementSort() + << std::endl + << "computed const type: " << constVal.getSort(); parseError(ss.str()); } - return em->mkConst(ArrayStoreAll(p.d_type, constVal)); + api::Term ret = d_solver->mkConstArray(p.d_type, constVal); + Debug("parser") << "applyParseOp: return store all " << ret << std::endl; + return ret; } - else if (p.d_kind == kind::APPLY_SELECTOR && !p.d_expr.isNull()) + else if (p.d_kind == api::APPLY_SELECTOR && !p.d_expr.isNull()) { // tuple selector case - Integer x = p.d_expr.getConst().getNumerator(); + Integer x = p.d_expr.getExpr().getConst().getNumerator(); if (!x.fitsUnsignedInt()) { parseError("index of tupSel is larger than size of unsigned int"); } unsigned int n = x.toUnsignedInt(); - if (args.size() > 1) + if (args.size() != 1) { - parseError("tupSel applied to more than one tuple argument"); + parseError("tupSel should only be applied to one tuple argument"); } - Type t = args[0].getType(); + api::Sort t = args[0].getSort(); if (!t.isTuple()) { parseError("tupSel applied to non-tuple"); } - size_t length = ((DatatypeType)t).getTupleLength(); + size_t length = t.getTupleLength(); if (n >= length) { std::stringstream ss; ss << "tuple is of length " << length << "; cannot access index " << n; parseError(ss.str()); } - const Datatype& dt = ((DatatypeType)t).getDatatype(); - return em->mkExpr(kind::APPLY_SELECTOR, dt[0][n].getSelector(), args); + const Datatype& dt = ((DatatypeType)t.getType()).getDatatype(); + api::Term ret = d_solver->mkTerm( + api::APPLY_SELECTOR, api::Term(dt[0][n].getSelector()), args[0]); + Debug("parser") << "applyParseOp: return selector " << ret << std::endl; + return ret; } - else if (p.d_kind != kind::NULL_EXPR) + else if (p.d_kind != api::NULL_EXPR) { // it should not have an expression or type specified at this point if (!p.d_expr.isNull() || !p.d_type.isNull()) @@ -1802,43 +1827,47 @@ Expr Smt2::applyParseOp(ParseOp& p, std::vector& args) } else if (isBuiltinOperator) { + Trace("ajr-temp") << "mkTerm builtin operator" << std::endl; if (!em->getOptions().getUfHo() - && (kind == kind::EQUAL || kind == kind::DISTINCT)) + && (kind == api::EQUAL || kind == api::DISTINCT)) { // need --uf-ho if these operators are applied over function args - for (std::vector::iterator i = args.begin(); i != args.end(); ++i) + for (std::vector::iterator i = args.begin(); i != args.end(); + ++i) { - if ((*i).getType().isFunction()) + if ((*i).getSort().isFunction()) { parseError( "Cannot apply equalty to functions unless --uf-ho is set."); } } } - if (!strictModeEnabled() && (kind == kind::AND || kind == kind::OR) + if (!strictModeEnabled() && (kind == api::AND || kind == api::OR) && args.size() == 1) { // Unary AND/OR can be replaced with the argument. + Debug("parser") << "applyParseOp: return unary " << args[0] << std::endl; return args[0]; } - else if (kind == kind::MINUS && args.size() == 1) + else if (kind == api::MINUS && args.size() == 1) { - return em->mkExpr(kind::UMINUS, args[0]); + api::Term ret = d_solver->mkTerm(api::UMINUS, args[0]); + Debug("parser") << "applyParseOp: return uminus " << ret << std::endl; + return ret; } - api::Term ret = - d_solver->mkTerm(intToExtKind(kind), api::exprVectorToTerms(args)); + api::Term ret = d_solver->mkTerm(kind, args); Debug("parser") << "applyParseOp: return default builtin " << ret << std::endl; - return ret.getExpr(); + return ret; } if (args.size() >= 2) { // may be partially applied function, in this case we use HO_APPLY - Type argt = args[0].getType(); + api::Sort argt = args[0].getSort(); if (argt.isFunction()) { - unsigned arity = static_cast(argt).getArity(); + unsigned arity = argt.getFunctionArity(); if (args.size() - 1 < arity) { if (!em->getOptions().getUfHo()) @@ -1848,26 +1877,33 @@ Expr Smt2::applyParseOp(ParseOp& p, std::vector& args) Debug("parser") << "Partial application of " << args[0]; Debug("parser") << " : #argTypes = " << arity; Debug("parser") << ", #args = " << args.size() - 1 << std::endl; + api::Term ret = d_solver->mkTerm(api::HO_APPLY, args); + Debug("parser") << "applyParseOp: return curry higher order " << ret + << std::endl; // must curry the partial application - return em->mkLeftAssociative(kind::HO_APPLY, args); + return ret; } } } if (!op.isNull()) { - api::Term ret = d_solver->mkTerm(op, api::exprVectorToTerms(args)); + api::Term ret = d_solver->mkTerm(op, args); Debug("parser") << "applyParseOp: return op : " << ret << std::endl; - return ret.getExpr(); + return ret; } - if (kind == kind::NULL_EXPR) + if (kind == api::NULL_EXPR) { - std::vector eargs(args.begin() + 1, args.end()); - return em->mkExpr(args[0], eargs); - } - return em->mkExpr(kind, args); + // should never happen in the new API + parseError("do not know how to process parse op"); + } + Debug("parser") << "Try default term construction for kind " << kind + << " #args = " << args.size() << "..." << std::endl; + api::Term ret = d_solver->mkTerm(kind, args); + Debug("parser") << "applyParseOp: return : " << ret << std::endl; + return ret; } -Expr Smt2::setNamedAttribute(Expr& expr, const SExpr& sexpr) +api::Term Smt2::setNamedAttribute(api::Term& expr, const SExpr& sexpr) { if (!sexpr.isKeyword()) { @@ -1876,7 +1912,7 @@ Expr Smt2::setNamedAttribute(Expr& expr, const SExpr& sexpr) std::string name = sexpr.getValue(); checkUserSymbol(name); // ensure expr is a closed subterm - if (expr.hasFreeVariable()) + if (expr.getExpr().hasFreeVariable()) { std::stringstream ss; ss << ":named annotations can only name terms that are closed"; @@ -1885,19 +1921,17 @@ Expr Smt2::setNamedAttribute(Expr& expr, const SExpr& sexpr) // check that sexpr is a fresh function symbol, and reserve it reserveSymbolAtAssertionLevel(name); // define it - Expr func = mkVar(name, expr.getType(), ExprManager::VAR_FLAG_DEFINED); + api::Term func = bindVar(name, expr.getSort(), ExprManager::VAR_FLAG_DEFINED); // remember the last term to have been given a :named attribute setLastNamedTerm(expr, name); return func; } -Expr Smt2::mkAnd(const std::vector& es) +api::Term Smt2::mkAnd(const std::vector& es) { - ExprManager* em = getExprManager(); - if (es.size() == 0) { - return em->mkConst(true); + return d_solver->mkTrue(); } else if (es.size() == 1) { @@ -1905,7 +1939,7 @@ Expr Smt2::mkAnd(const std::vector& es) } else { - return em->mkExpr(kind::AND, es); + return d_solver->mkTerm(api::AND, es); } } diff --git a/src/parser/smt2/smt2.h b/src/parser/smt2/smt2.h index 53ebf5929..afa60bf2f 100644 --- a/src/parser/smt2/smt2.h +++ b/src/parser/smt2/smt2.h @@ -72,15 +72,15 @@ class Smt2 : public Parser bool d_seenSetLogic; LogicInfo d_logic; - std::unordered_map operatorKindMap; + std::unordered_map operatorKindMap; /** * Maps indexed symbols to the kind of the operator (e.g. "extract" to * BITVECTOR_EXTRACT). */ std::unordered_map d_indexedOpKindMap; - std::pair d_lastNamedTerm; + std::pair d_lastNamedTerm; // for sygus - std::vector d_sygusVars, d_sygusVarPrimed, d_sygusConstraints, + std::vector d_sygusVars, d_sygusVarPrimed, d_sygusConstraints, d_sygusFunSymbols; protected: @@ -97,7 +97,7 @@ class Smt2 : public Parser */ void addTheory(Theory theory); - void addOperator(Kind k, const std::string& name); + void addOperator(api::Kind k, const std::string& name); /** * Registers an indexed function symbol. @@ -109,11 +109,11 @@ class Smt2 : public Parser * @param opKind The kind of the operator term (e.g. BITVECTOR_EXTRACT) * @param name The name of the symbol (e.g. "extract") */ - void addIndexedOperator(Kind tKind, + void addIndexedOperator(api::Kind tKind, api::Kind opKind, const std::string& name); - Kind getOperatorKind(const std::string& name) const; + api::Kind getOperatorKind(const std::string& name) const; bool isOperatorEnabled(const std::string& name) const; @@ -147,7 +147,8 @@ class Smt2 : public Parser /** * Returns the expression that name should be interpreted as. */ - Expr getExpressionForNameAndType(const std::string& name, Type t) override; + api::Term getExpressionForNameAndType(const std::string& name, + api::Sort t) override; /** Make function defined by a define-fun(s)-rec command. * @@ -163,11 +164,11 @@ class Smt2 : public Parser * added to flattenVars in this function if the function is given a function * range type. */ - Expr mkDefineFunRec( + api::Term bindDefineFunRec( const std::string& fname, - const std::vector >& sortedVarNames, - Type t, - std::vector& flattenVars); + const std::vector>& sortedVarNames, + api::Sort t, + std::vector& flattenVars); /** Push scope for define-fun-rec * @@ -187,10 +188,10 @@ class Smt2 : public Parser * that defined this definition and stores it in bvs. */ void pushDefineFunRecScope( - const std::vector >& sortedVarNames, - Expr func, - const std::vector& flattenVars, - std::vector& bvs, + const std::vector>& sortedVarNames, + api::Term func, + const std::vector& flattenVars, + std::vector& bvs, bool bindingLevel = false); void reset() override; @@ -218,11 +219,11 @@ class Smt2 : public Parser Smt2* smt2, const std::string& fun, bool isInv, - Type range, - std::vector>& sortedVarNames); + api::Sort range, + std::vector>& sortedVarNames); ~SynthFunFactory(); - const std::vector& getSygusVars() const { return d_sygusVars; } + const std::vector& getSygusVars() const { return d_sygusVars; } /** * Create an instance of `SynthFunCommand`. @@ -230,15 +231,15 @@ class Smt2 : public Parser * @param grammar Optional grammar associated with the synth-fun command * @return The instance of `SynthFunCommand` */ - std::unique_ptr mkCommand(Type grammar); + std::unique_ptr mkCommand(api::Sort grammar); private: Smt2* d_smt2; std::string d_fun; - Expr d_synthFun; - Type d_sygusType; + api::Term d_synthFun; + api::Sort d_sygusType; bool d_isInv; - std::vector d_sygusVars; + std::vector d_sygusVars; }; /** @@ -321,17 +322,16 @@ class Smt2 : public Parser void includeFile(const std::string& filename); - void setLastNamedTerm(Expr e, std::string name) { + void setLastNamedTerm(api::Term e, std::string name) + { d_lastNamedTerm = std::make_pair(e, name); } void clearLastNamedTerm() { - d_lastNamedTerm = std::make_pair(Expr(), ""); + d_lastNamedTerm = std::make_pair(api::Term(), ""); } - std::pair lastNamedTerm() { - return d_lastNamedTerm; - } + std::pair lastNamedTerm() { return d_lastNamedTerm; } /** Does name denote an abstract value? (of the form '@n' for numeral n). */ bool isAbstractValue(const std::string& name); @@ -341,58 +341,59 @@ class Smt2 : public Parser * Abstract values are used for processing get-value calls. The argument * name should be such that isAbstractValue(name) is true. */ - Expr mkAbstractValue(const std::string& name); + api::Term mkAbstractValue(const std::string& name); - void mkSygusConstantsForType( const Type& type, std::vector& ops ); + void mkSygusConstantsForType(const api::Sort& type, + std::vector& ops); void processSygusGTerm( CVC4::SygusGTerm& sgt, int index, std::vector& datatypes, - std::vector& sorts, + std::vector& sorts, std::vector>& ops, std::vector>& cnames, - std::vector>>& cargs, + std::vector>>& cargs, std::vector& allow_const, std::vector>& unresolved_gterm_sym, - const std::vector& sygus_vars, - std::map& sygus_to_builtin, - std::map& sygus_to_builtin_expr, - CVC4::Type& ret, + const std::vector& sygus_vars, + std::map& sygus_to_builtin, + std::map& sygus_to_builtin_expr, + api::Sort& ret, bool isNested = false); bool pushSygusDatatypeDef( - Type t, + api::Sort t, std::string& dname, std::vector& datatypes, - std::vector& sorts, + std::vector& sorts, std::vector>& ops, std::vector>& cnames, - std::vector>>& cargs, + std::vector>>& cargs, std::vector& allow_const, std::vector>& unresolved_gterm_sym); bool popSygusDatatypeDef( std::vector& datatypes, - std::vector& sorts, + std::vector& sorts, std::vector>& ops, std::vector>& cnames, - std::vector>>& cargs, + std::vector>>& cargs, std::vector& allow_const, std::vector>& unresolved_gterm_sym); void setSygusStartIndex(const std::string& fun, int startIndex, std::vector& datatypes, - std::vector& sorts, + std::vector& sorts, std::vector>& ops); void mkSygusDatatype(CVC4::Datatype& dt, std::vector& ops, std::vector& cnames, - std::vector>& cargs, + std::vector>& cargs, std::vector& unresolved_gterm_sym, - std::map& sygus_to_builtin); + std::map& sygus_to_builtin); /** * Adds a constructor to sygus datatype dt whose sygus operator is term. @@ -407,17 +408,18 @@ class Smt2 : public Parser * with bound variables via purifySygusGTerm, and binding these variables * via a lambda. */ - void addSygusConstructorTerm(Datatype& dt, - Expr term, - std::map& ntsToUnres) const; + void addSygusConstructorTerm( + Datatype& dt, + api::Term term, + std::map& ntsToUnres) const; /** * This adds constructors to dt for sygus variables in sygusVars whose * type is argument type. This method should be called when the sygus grammar * term (Variable type) is encountered. */ void addSygusConstructorVariables(Datatype& dt, - const std::vector& sygusVars, - Type type) const; + const std::vector& sygusVars, + api::Sort type) const; /** * Smt2 parser provides its own checkDeclaration, which does the @@ -446,40 +448,6 @@ class Smt2 : public Parser } this->Parser::checkDeclaration(name, check, type, notes); } - - void checkOperator(Kind kind, unsigned numArgs) - { - Parser::checkOperator(kind, numArgs); - // strict SMT-LIB mode enables extra checks for some bitvector operators - // that CVC4 permits as N-ary but the standard requires is binary - if(strictModeEnabled()) { - switch(kind) { - case kind::BITVECTOR_AND: - case kind::BITVECTOR_MULT: - case kind::BITVECTOR_OR: - case kind::BITVECTOR_PLUS: - case kind::BITVECTOR_XOR: - if (numArgs != 2 && !v2_6()) - { - parseError( - "Operator requires exactly 2 arguments in strict SMT-LIB " - "compliance mode (for versions <2.6): " - + kindToString(kind)); - } - break; - case kind::BITVECTOR_CONCAT: - if(numArgs != 2) { - parseError( - "Operator requires exactly 2 arguments in strict SMT-LIB " - "compliance mode: " - + kindToString(kind)); - } - break; - default: - break; /* no problem */ - } - } - } /** Set named attribute * * This is called when expression expr is annotated with a name, i.e. @@ -490,7 +458,7 @@ class Smt2 : public Parser * which is used later for tracking assertions in unsat cores. This * symbol is returned by this method. */ - Expr setNamedAttribute(Expr& expr, const SExpr& sexpr); + api::Term setNamedAttribute(api::Term& expr, const SExpr& sexpr); // Throw a ParserException with msg appended with the current logic. inline void parseErrorLogic(const std::string& msg) @@ -516,7 +484,7 @@ class Smt2 : public Parser * - If p's expression field is set, then we leave p unchanged, check if * that expression has the given type and throw a parse error otherwise. */ - void parseOpApplyTypeAscription(ParseOp& p, Type type); + void parseOpApplyTypeAscription(ParseOp& p, api::Sort type); /** * This converts a ParseOp to expression, assuming it is a standalone term. * @@ -526,7 +494,7 @@ class Smt2 : public Parser * of this class. * In other cases, a parse error is thrown. */ - Expr parseOpToExpr(ParseOp& p); + api::Term parseOpToExpr(ParseOp& p); /** * Apply parse operator to list of arguments, and return the resulting * expression. @@ -559,24 +527,24 @@ class Smt2 : public Parser * - If the overall expression is a partial application, then we process this * as a chain of HO_APPLY terms. */ - Expr applyParseOp(ParseOp& p, std::vector& args); + api::Term applyParseOp(ParseOp& p, std::vector& args); //------------------------- end processing parse operators private: - std::map< CVC4::Expr, CVC4::Type > d_sygus_bound_var_type; + std::map d_sygus_bound_var_type; - Type processSygusNestedGTerm( + api::Sort processSygusNestedGTerm( int sub_dt_index, std::string& sub_dname, std::vector& datatypes, - std::vector& sorts, + std::vector& sorts, std::vector>& ops, std::vector>& cnames, - std::vector>>& cargs, + std::vector>>& cargs, std::vector& allow_const, std::vector>& unresolved_gterm_sym, - std::map& sygus_to_builtin, - std::map& sygus_to_builtin_expr, - Type sub_ret); + std::map& sygus_to_builtin, + std::map& sygus_to_builtin_expr, + api::Sort sub_ret); /** make sygus bound var list * @@ -586,10 +554,10 @@ class Smt2 : public Parser * It appends a bound variable to lvars for each type in ltypes, and returns * a bound variable list whose children are lvars. */ - Expr makeSygusBoundVarList(Datatype& dt, - unsigned i, - const std::vector& ltypes, - std::vector& lvars); + api::Term makeSygusBoundVarList(CVC4::Datatype& dt, + unsigned i, + const std::vector& ltypes, + std::vector& lvars); /** Purify sygus grammar term * @@ -603,7 +571,7 @@ class Smt2 : public Parser * sygus constructor. */ api::Term purifySygusGTerm(api::Term term, - std::map& ntsToUnres, + std::map& ntsToUnres, std::vector& args, std::vector& cargs) const; @@ -632,7 +600,7 @@ class Smt2 : public Parser * @return True if `es` is empty, `e` if `es` consists of a single element * `e`, the conjunction of expressions otherwise. */ - Expr mkAnd(const std::vector& es); + api::Term mkAnd(const std::vector& es); }; /* class Smt2 */ }/* CVC4::parser namespace */ diff --git a/src/parser/smt2/smt2_input.cpp b/src/parser/smt2/smt2_input.cpp index 4e74eefb5..c0bece257 100644 --- a/src/parser/smt2/smt2_input.cpp +++ b/src/parser/smt2/smt2_input.cpp @@ -64,7 +64,7 @@ Command* Smt2Input::parseCommand() { api::Term Smt2Input::parseExpr() { - return api::Term(d_pSmt2Parser->parseExpr(d_pSmt2Parser)); + return d_pSmt2Parser->parseExpr(d_pSmt2Parser); } }/* CVC4::parser namespace */ diff --git a/src/parser/smt2/sygus_input.cpp b/src/parser/smt2/sygus_input.cpp index f0bed978e..a908bf4d5 100644 --- a/src/parser/smt2/sygus_input.cpp +++ b/src/parser/smt2/sygus_input.cpp @@ -65,7 +65,7 @@ Command* SygusInput::parseCommand() { api::Term SygusInput::parseExpr() { - return api::Term(d_pSmt2Parser->parseExpr(d_pSmt2Parser)); + return d_pSmt2Parser->parseExpr(d_pSmt2Parser); } }/* CVC4::parser namespace */ diff --git a/src/parser/tptp/Tptp.g b/src/parser/tptp/Tptp.g index afa072e6d..2568101c4 100644 --- a/src/parser/tptp/Tptp.g +++ b/src/parser/tptp/Tptp.g @@ -73,12 +73,12 @@ using namespace CVC4::parser; * by ANTLR *after* this section. (If they were functions, PARSER would be undefined.) */ #undef PARSER_STATE #define PARSER_STATE ((Tptp*)LEXER->super) -#undef EXPR_MANAGER -#define EXPR_MANAGER PARSER_STATE->getExprManager() -#undef MK_EXPR -#define MK_EXPR EXPR_MANAGER->mkExpr -#undef MK_CONST -#define MK_CONST EXPR_MANAGER->mkConst +#undef SOLVER +#define SOLVER PARSER_STATE->getSolver() +#undef MK_TERM +#define MK_TERM SOLVER->mkTerm +#undef MK_TERM +#define MK_TERM SOLVER->mkTerm #define UNSUPPORTED PARSER_STATE->unimplementedFeature }/* @lexer::postinclude */ @@ -101,6 +101,7 @@ using namespace CVC4::parser; #include #include +#include "api/cvc4cpp.h" #include "base/output.h" #include "expr/expr.h" #include "expr/kind.h" @@ -118,21 +119,18 @@ using namespace CVC4::parser; * by ANTLR *after* this section. (If they were functions, PARSER would be undefined.) */ #undef PARSER_STATE #define PARSER_STATE ((Tptp*)PARSER->super) -#undef EXPR_MANAGER -#define EXPR_MANAGER PARSER_STATE->getExprManager() -#undef MK_EXPR -#define MK_EXPR EXPR_MANAGER->mkExpr -#undef MK_EXPR_ASSOCIATIVE -#define MK_EXPR_ASSOCIATIVE EXPR_MANAGER->mkAssociative -#undef MK_CONST -#define MK_CONST EXPR_MANAGER->mkConst +#undef SOLVER +#define SOLVER PARSER_STATE->getSolver() +#undef MK_TERM +#define MK_TERM SOLVER->mkTerm #define UNSUPPORTED PARSER_STATE->unimplementedFeature }/* parser::postinclude */ /** * Parses an expression. - * @return the parsed expression, or the Null Expr if we've reached the end of the input + * @return the parsed expression, or the Null CVC4::api::Term if we've reached + * the end of the input */ parseExpr returns [CVC4::parser::tptp::myExpr expr] : cnfFormula[expr] @@ -145,7 +143,7 @@ parseExpr returns [CVC4::parser::tptp::myExpr expr] */ parseCommand returns [CVC4::Command* cmd = NULL] @declarations { - Expr expr; + CVC4::api::Term expr; Tptp::FormulaRole fr; std::string name, inclSymbol; ParseOp p; @@ -156,17 +154,17 @@ parseCommand returns [CVC4::Command* cmd = NULL] PARSER_STATE->pushScope(); } cnfFormula[expr] { PARSER_STATE->popScope(); - std::vector bvl = PARSER_STATE->getFreeVar(); + std::vector bvl = PARSER_STATE->getFreeVar(); if(!bvl.empty()) { - expr = MK_EXPR(kind::FORALL,MK_EXPR(kind::BOUND_VAR_LIST,bvl),expr); + expr = MK_TERM(api::FORALL,MK_TERM(api::BOUND_VAR_LIST,bvl),expr); }; } (COMMA_TOK anything*)? RPAREN_TOK DOT_TOK { - Expr aexpr = PARSER_STATE->getAssertionExpr(fr,expr); + CVC4::api::Term aexpr = PARSER_STATE->getAssertionExpr(fr,expr); if( !aexpr.isNull() ){ // set the expression name (e.g. used with unsat core printing) - Command* csen = new SetExpressionNameCommand(aexpr, name); + Command* csen = new SetExpressionNameCommand(aexpr.getExpr(), name); csen->setMuted(true); PARSER_STATE->preemptCommand(csen); } @@ -177,10 +175,10 @@ parseCommand returns [CVC4::Command* cmd = NULL] { PARSER_STATE->setCnf(false); PARSER_STATE->setFof(true); } fofFormula[expr] (COMMA_TOK anything*)? RPAREN_TOK DOT_TOK { - Expr aexpr = PARSER_STATE->getAssertionExpr(fr,expr); + CVC4::api::Term aexpr = PARSER_STATE->getAssertionExpr(fr,expr); if( !aexpr.isNull() ){ // set the expression name (e.g. used with unsat core printing) - Command* csen = new SetExpressionNameCommand(aexpr, name); + Command* csen = new SetExpressionNameCommand(aexpr.getExpr(), name); csen->setMuted(true); PARSER_STATE->preemptCommand(csen); } @@ -193,10 +191,10 @@ parseCommand returns [CVC4::Command* cmd = NULL] { PARSER_STATE->setCnf(false); PARSER_STATE->setFof(false); } tffFormula[expr] (COMMA_TOK anything*)? { - Expr aexpr = PARSER_STATE->getAssertionExpr(fr,expr); + CVC4::api::Term aexpr = PARSER_STATE->getAssertionExpr(fr,expr); if( !aexpr.isNull() ){ // set the expression name (e.g. used with unsat core printing) - Command* csen = new SetExpressionNameCommand(aexpr, name); + Command* csen = new SetExpressionNameCommand(aexpr.getExpr(), name); csen->setMuted(true); PARSER_STATE->preemptCommand(csen); } @@ -217,11 +215,11 @@ parseCommand returns [CVC4::Command* cmd = NULL] PARSER_STATE->parseError("Top level expression must be a formula"); } expr = p.d_expr; - Expr aexpr = PARSER_STATE->getAssertionExpr(fr, expr); + CVC4::api::Term aexpr = PARSER_STATE->getAssertionExpr(fr, expr); if (!aexpr.isNull()) { // set the expression name (e.g. used with unsat core printing) - Command* csen = new SetExpressionNameCommand(aexpr, name); + Command* csen = new SetExpressionNameCommand(aexpr.getExpr(), name); csen->setMuted(true); PARSER_STATE->preemptCommand(csen); } @@ -254,10 +252,10 @@ parseCommand returns [CVC4::Command* cmd = NULL] { CommandSequence* seq = new CommandSequence(); // assert that all distinct constants are distinct - Expr aexpr = PARSER_STATE->getAssertionDistinctConstants(); + CVC4::api::Term aexpr = PARSER_STATE->getAssertionDistinctConstants(); if( !aexpr.isNull() ) { - seq->addCommand(new AssertCommand(aexpr, false)); + seq->addCommand(new AssertCommand(aexpr.getExpr(), false)); } std::string filename = PARSER_STATE->getInput()->getInputStreamName(); @@ -270,7 +268,7 @@ parseCommand returns [CVC4::Command* cmd = NULL] } seq->addCommand(new SetInfoCommand("filename", SExpr(filename))); if(PARSER_STATE->hasConjecture()) { - seq->addCommand(new QueryCommand(MK_CONST(bool(false)))); + seq->addCommand(new QueryCommand(SOLVER->mkFalse().getExpr())); } else { seq->addCommand(new CheckSatCommand()); } @@ -308,33 +306,33 @@ formulaRole[CVC4::parser::Tptp::FormulaRole& role] /* It can parse a little more than the cnf grammar: false and true can appear. * Normally only false can appear and only at top level. */ -cnfFormula[CVC4::Expr& expr] +cnfFormula[CVC4::api::Term& expr] : LPAREN_TOK cnfDisjunction[expr] RPAREN_TOK | cnfDisjunction[expr] ; -cnfDisjunction[CVC4::Expr& expr] +cnfDisjunction[CVC4::api::Term& expr] @declarations { - std::vector args; + std::vector args; } : cnfLiteral[expr] { args.push_back(expr); } ( OR_TOK cnfLiteral[expr] { args.push_back(expr); } )* { if(args.size() > 1) { - expr = MK_EXPR_ASSOCIATIVE(kind::OR, args); + expr = MK_TERM(api::OR, args); } // else its already in the expr } ; -cnfLiteral[CVC4::Expr& expr] +cnfLiteral[CVC4::api::Term& expr] : atomicFormula[expr] - | NOT_TOK atomicFormula[expr] { expr = MK_EXPR(kind::NOT, expr); } + | NOT_TOK atomicFormula[expr] { expr = MK_TERM(api::NOT, expr); } ; -atomicFormula[CVC4::Expr& expr] +atomicFormula[CVC4::api::Term& expr] @declarations { - Expr expr2; + CVC4::api::Term expr2; std::string name; - std::vector args; + std::vector args; bool equal; ParseOp p; } @@ -346,15 +344,15 @@ atomicFormula[CVC4::Expr& expr] args.clear(); args.push_back(expr); args.push_back(expr2); - ParseOp p1(kind::EQUAL); + ParseOp p1(api::EQUAL); expr = PARSER_STATE->applyParseOp(p1, args); if (!equal) { - expr = MK_EXPR(kind::NOT, expr); + expr = MK_TERM(api::NOT, expr); } } | { // predicate - p.d_type = EXPR_MANAGER->booleanType(); + p.d_type = SOLVER->getBooleanSort(); expr = args.empty() ? PARSER_STATE->parseOpToExpr(p) : PARSER_STATE->applyParseOp(p, args); } @@ -368,11 +366,11 @@ atomicFormula[CVC4::Expr& expr] args.clear(); args.push_back(expr); args.push_back(expr2); - ParseOp p1(kind::EQUAL); + ParseOp p1(api::EQUAL); expr = PARSER_STATE->applyParseOp(p1, args); if (!equal) { - expr = MK_EXPR(kind::NOT, expr); + expr = MK_TERM(api::NOT, expr); } } ) @@ -382,17 +380,17 @@ atomicFormula[CVC4::Expr& expr] { // equality/disequality between terms args.push_back(expr); args.push_back(expr2); - p.d_kind = kind::EQUAL; + p.d_kind = api::EQUAL; expr = PARSER_STATE->applyParseOp(p, args); if (!equal) { - expr = MK_EXPR(kind::NOT, expr); + expr = MK_TERM(api::NOT, expr); } } )? | definedPred[p] (LPAREN_TOK arguments[args] RPAREN_TOK) { - p.d_type = EXPR_MANAGER->booleanType(); + p.d_type = SOLVER->getBooleanSort(); expr = PARSER_STATE->applyParseOp(p, args); } | definedProp[expr] @@ -400,9 +398,9 @@ atomicFormula[CVC4::Expr& expr] thfAtomicFormula[CVC4::ParseOp& p] @declarations { - Expr expr2; + CVC4::api::Term expr2; std::string name; - std::vector args; + std::vector args; bool equal; } : atomicWord[p.d_name] (LPAREN_TOK arguments[args] RPAREN_TOK)? @@ -419,11 +417,11 @@ thfAtomicFormula[CVC4::ParseOp& p] args.clear(); args.push_back(p.d_expr); args.push_back(expr2); - ParseOp p1(kind::EQUAL); + ParseOp p1(api::EQUAL); p.d_expr = PARSER_STATE->applyParseOp(p1, args); if (!equal) { - p.d_expr = MK_EXPR(kind::NOT, p.d_expr); + p.d_expr = MK_TERM(api::NOT, p.d_expr); } } )? @@ -432,7 +430,7 @@ thfAtomicFormula[CVC4::ParseOp& p] | conditionalTerm[p.d_expr] | thfDefinedPred[p] (LPAREN_TOK arguments[args] RPAREN_TOK)? { - p.d_type = EXPR_MANAGER->booleanType(); + p.d_type = SOLVER->getBooleanSort(); if (!args.empty()) { p.d_expr = PARSER_STATE->applyParseOp(p, args); @@ -444,130 +442,130 @@ thfAtomicFormula[CVC4::ParseOp& p] //%----Using removes a reduce/reduce ambiguity in lex/yacc. //%----Note: "defined" means a word starting with one $ and "system" means $$. -definedProp[CVC4::Expr& expr] - : TRUE_TOK { expr = MK_CONST(bool(true)); } - | FALSE_TOK { expr = MK_CONST(bool(false)); } +definedProp[CVC4::api::Term& expr] + : TRUE_TOK { expr = SOLVER->mkTrue(); } + | FALSE_TOK { expr = SOLVER->mkFalse(); } ; definedPred[CVC4::ParseOp& p] : '$less' { - p.d_kind = kind::LT; + p.d_kind = api::LT; } | '$lesseq' { - p.d_kind = kind::LEQ; + p.d_kind = api::LEQ; } | '$greater' { - p.d_kind = kind::GT; + p.d_kind = api::GT; } | '$greatereq' { - p.d_kind = kind::GEQ; + p.d_kind = api::GEQ; } | '$is_rat' // a real n is a rational if there exists q,r integers such that // to_real(q) = n*to_real(r), // where r is non-zero. { - Expr n = EXPR_MANAGER->mkBoundVar("N", EXPR_MANAGER->realType()); - Expr q = EXPR_MANAGER->mkBoundVar("Q", EXPR_MANAGER->integerType()); - Expr qr = MK_EXPR(kind::TO_REAL, q); - Expr r = EXPR_MANAGER->mkBoundVar("R", EXPR_MANAGER->integerType()); - Expr rr = MK_EXPR(kind::TO_REAL, r); - Expr body = - MK_EXPR(kind::AND, - MK_EXPR(kind::NOT, - MK_EXPR(kind::EQUAL, r, MK_CONST(Rational(0)))), - MK_EXPR(kind::EQUAL, qr, MK_EXPR(kind::MULT, n, rr))); - Expr bvl = MK_EXPR(kind::BOUND_VAR_LIST, q, r); - body = MK_EXPR(kind::EXISTS, bvl, body); - Expr lbvl = MK_EXPR(kind::BOUND_VAR_LIST, n); - p.d_kind = kind::LAMBDA; - p.d_expr = MK_EXPR(kind::LAMBDA, lbvl, body); + api::Term n = SOLVER->mkVar(SOLVER->getRealSort(), "N"); + api::Term q = SOLVER->mkVar(SOLVER->getIntegerSort(), "Q"); + api::Term qr = MK_TERM(api::TO_REAL, q); + api::Term r = SOLVER->mkVar(SOLVER->getIntegerSort(), "R"); + api::Term rr = MK_TERM(api::TO_REAL, r); + api::Term body = + MK_TERM(api::AND, + MK_TERM(api::NOT, + MK_TERM(api::EQUAL, r, SOLVER->mkReal(0))), + MK_TERM(api::EQUAL, qr, MK_TERM(api::MULT, n, rr))); + api::Term bvl = MK_TERM(api::BOUND_VAR_LIST, q, r); + body = MK_TERM(api::EXISTS, bvl, body); + api::Term lbvl = MK_TERM(api::BOUND_VAR_LIST, n); + p.d_kind = api::LAMBDA; + p.d_expr = MK_TERM(api::LAMBDA, lbvl, body); } | '$is_int' { - p.d_kind = kind::IS_INTEGER; + p.d_kind = api::IS_INTEGER; } | '$distinct' { - p.d_kind = kind::DISTINCT; + p.d_kind = api::DISTINCT; } | AND_TOK { - p.d_kind = kind::AND; + p.d_kind = api::AND; } | IMPLIES_TOK { - p.d_kind = kind::IMPLIES; + p.d_kind = api::IMPLIES; } | OR_TOK { - p.d_kind = kind::OR; + p.d_kind = api::OR; } ; thfDefinedPred[CVC4::ParseOp& p] : '$less' { - p.d_kind = kind::LT; + p.d_kind = api::LT; } | '$lesseq' { - p.d_kind = kind::LEQ; + p.d_kind = api::LEQ; } | '$greater' { - p.d_kind = kind::GT; + p.d_kind = api::GT; } | '$greatereq' { - p.d_kind = kind::GEQ; + p.d_kind = api::GEQ; } | '$is_rat' // a real n is a rational if there exists q,r integers such that // to_real(q) = n*to_real(r), // where r is non-zero. { - Expr n = EXPR_MANAGER->mkBoundVar("N", EXPR_MANAGER->realType()); - Expr q = EXPR_MANAGER->mkBoundVar("Q", EXPR_MANAGER->integerType()); - Expr qr = MK_EXPR(kind::TO_REAL, q); - Expr r = EXPR_MANAGER->mkBoundVar("R", EXPR_MANAGER->integerType()); - Expr rr = MK_EXPR(kind::TO_REAL, r); - Expr body = MK_EXPR( - kind::AND, - MK_EXPR(kind::NOT, - MK_EXPR(kind::EQUAL, r, MK_CONST(Rational(0)))), - MK_EXPR(kind::EQUAL, qr, MK_EXPR(kind::MULT, n, rr))); - Expr bvl = MK_EXPR(kind::BOUND_VAR_LIST, q, r); - body = MK_EXPR(kind::EXISTS, bvl, body); - Expr lbvl = MK_EXPR(kind::BOUND_VAR_LIST, n); - p.d_kind = kind::LAMBDA; - p.d_expr = MK_EXPR(kind::LAMBDA, lbvl, body); + api::Term n = SOLVER->mkVar(SOLVER->getRealSort(), "N"); + api::Term q = SOLVER->mkVar(SOLVER->getIntegerSort(), "Q"); + api::Term qr = MK_TERM(api::TO_REAL, q); + api::Term r = SOLVER->mkVar(SOLVER->getIntegerSort(), "R"); + api::Term rr = MK_TERM(api::TO_REAL, r); + api::Term body = MK_TERM( + api::AND, + MK_TERM(api::NOT, + MK_TERM(api::EQUAL, r, SOLVER->mkReal(0))), + MK_TERM(api::EQUAL, qr, MK_TERM(api::MULT, n, rr))); + api::Term bvl = MK_TERM(api::BOUND_VAR_LIST, q, r); + body = MK_TERM(api::EXISTS, bvl, body); + api::Term lbvl = MK_TERM(api::BOUND_VAR_LIST, n); + p.d_kind = api::LAMBDA; + p.d_expr = MK_TERM(api::LAMBDA, lbvl, body); } | '$is_int' { - p.d_kind = kind::IS_INTEGER; + p.d_kind = api::IS_INTEGER; } | '$distinct' { - p.d_kind = kind::DISTINCT; + p.d_kind = api::DISTINCT; } | LPAREN_TOK ( AND_TOK { - p.d_kind = kind::AND; + p.d_kind = api::AND; } | OR_TOK { - p.d_kind = kind::OR; + p.d_kind = api::OR; } | IMPLIES_TOK { - p.d_kind = kind::IMPLIES; + p.d_kind = api::IMPLIES; } ) RPAREN_TOK @@ -579,152 +577,152 @@ definedFun[CVC4::ParseOp& p] } : '$uminus' { - p.d_kind = kind::UMINUS; + p.d_kind = api::UMINUS; } | '$sum' { - p.d_kind = kind::PLUS; + p.d_kind = api::PLUS; } | '$difference' { - p.d_kind = kind::MINUS; + p.d_kind = api::MINUS; } | '$product' { - p.d_kind = kind::MULT; + p.d_kind = api::MULT; } | '$quotient' { - p.d_kind = kind::DIVISION; + p.d_kind = api::DIVISION; } | ( '$quotient_e' { remainder = false; } | '$remainder_e' { remainder = true; } ) { - Expr n = EXPR_MANAGER->mkBoundVar("N", EXPR_MANAGER->realType()); - Expr d = EXPR_MANAGER->mkBoundVar("D", EXPR_MANAGER->realType()); - Expr formals = MK_EXPR(kind::BOUND_VAR_LIST, n, d); - Expr expr = MK_EXPR(kind::DIVISION_TOTAL, n, d); - expr = MK_EXPR(kind::ITE, - MK_EXPR(kind::GEQ, d, MK_CONST(Rational(0))), - MK_EXPR(kind::TO_INTEGER, expr), - MK_EXPR(kind::UMINUS, - MK_EXPR(kind::TO_INTEGER, - MK_EXPR(kind::UMINUS, expr)))); + api::Term n = SOLVER->mkVar(SOLVER->getRealSort(), "N"); + api::Term d = SOLVER->mkVar(SOLVER->getRealSort(), "D"); + api::Term formals = MK_TERM(api::BOUND_VAR_LIST, n, d); + api::Term expr = MK_TERM(api::DIVISION, n, d); + expr = MK_TERM(api::ITE, + MK_TERM(api::GEQ, d, SOLVER->mkReal(0)), + MK_TERM(api::TO_INTEGER, expr), + MK_TERM(api::UMINUS, + MK_TERM(api::TO_INTEGER, + MK_TERM(api::UMINUS, expr)))); if (remainder) { - expr = MK_EXPR( - kind::TO_INTEGER, - MK_EXPR(kind::MINUS, n, MK_EXPR(kind::MULT, expr, d))); + expr = MK_TERM( + api::TO_INTEGER, + MK_TERM(api::MINUS, n, MK_TERM(api::MULT, expr, d))); } - p.d_kind = kind::LAMBDA; - p.d_expr = MK_EXPR(kind::LAMBDA, formals, expr); + p.d_kind = api::LAMBDA; + p.d_expr = MK_TERM(api::LAMBDA, formals, expr); } | ( '$quotient_t' { remainder = false; } | '$remainder_t' { remainder = true; } ) { - Expr n = EXPR_MANAGER->mkBoundVar("N", EXPR_MANAGER->realType()); - Expr d = EXPR_MANAGER->mkBoundVar("D", EXPR_MANAGER->realType()); - Expr formals = MK_EXPR(kind::BOUND_VAR_LIST, n, d); - Expr expr = MK_EXPR(kind::DIVISION_TOTAL, n, d); - expr = MK_EXPR(kind::ITE, - MK_EXPR(kind::GEQ, expr, MK_CONST(Rational(0))), - MK_EXPR(kind::TO_INTEGER, expr), - MK_EXPR(kind::UMINUS, - MK_EXPR(kind::TO_INTEGER, - MK_EXPR(kind::UMINUS, expr)))); + api::Term n = SOLVER->mkVar(SOLVER->getRealSort(), "N"); + api::Term d = SOLVER->mkVar(SOLVER->getRealSort(), "D"); + api::Term formals = MK_TERM(api::BOUND_VAR_LIST, n, d); + api::Term expr = MK_TERM(api::DIVISION, n, d); + expr = MK_TERM(api::ITE, + MK_TERM(api::GEQ, expr, SOLVER->mkReal(0)), + MK_TERM(api::TO_INTEGER, expr), + MK_TERM(api::UMINUS, + MK_TERM(api::TO_INTEGER, + MK_TERM(api::UMINUS, expr)))); if (remainder) { - expr = MK_EXPR( - kind::TO_INTEGER, - MK_EXPR(kind::MINUS, n, MK_EXPR(kind::MULT, expr, d))); + expr = MK_TERM( + api::TO_INTEGER, + MK_TERM(api::MINUS, n, MK_TERM(api::MULT, expr, d))); } - p.d_kind = kind::LAMBDA; - p.d_expr = MK_EXPR(kind::LAMBDA, formals, expr); + p.d_kind = api::LAMBDA; + p.d_expr = MK_TERM(api::LAMBDA, formals, expr); } | ( '$quotient_f' { remainder = false; } | '$remainder_f' { remainder = true; } ) { - Expr n = EXPR_MANAGER->mkBoundVar("N", EXPR_MANAGER->realType()); - Expr d = EXPR_MANAGER->mkBoundVar("D", EXPR_MANAGER->realType()); - Expr formals = MK_EXPR(kind::BOUND_VAR_LIST, n, d); - Expr expr = MK_EXPR(kind::DIVISION_TOTAL, n, d); - expr = MK_EXPR(kind::TO_INTEGER, expr); + api::Term n = SOLVER->mkVar(SOLVER->getRealSort(), "N"); + api::Term d = SOLVER->mkVar(SOLVER->getRealSort(), "D"); + api::Term formals = MK_TERM(api::BOUND_VAR_LIST, n, d); + api::Term expr = MK_TERM(api::DIVISION, n, d); + expr = MK_TERM(api::TO_INTEGER, expr); if (remainder) { - expr = MK_EXPR(kind::TO_INTEGER, - MK_EXPR(kind::MINUS, n, MK_EXPR(kind::MULT, expr, d))); + expr = MK_TERM(api::TO_INTEGER, + MK_TERM(api::MINUS, n, MK_TERM(api::MULT, expr, d))); } - p.d_kind = kind::LAMBDA; - p.d_expr = MK_EXPR(kind::LAMBDA, formals, expr); + p.d_kind = api::LAMBDA; + p.d_expr = MK_TERM(api::LAMBDA, formals, expr); } | '$floor' { - p.d_kind = kind::TO_INTEGER; + p.d_kind = api::TO_INTEGER; } | '$ceiling' { - Expr n = EXPR_MANAGER->mkBoundVar("N", EXPR_MANAGER->realType()); - Expr formals = MK_EXPR(kind::BOUND_VAR_LIST, n); - Expr expr = MK_EXPR(kind::UMINUS, - MK_EXPR(kind::TO_INTEGER, MK_EXPR(kind::UMINUS, n))); - p.d_kind = kind::LAMBDA; - p.d_expr = MK_EXPR(kind::LAMBDA, formals, expr); + api::Term n = SOLVER->mkVar(SOLVER->getRealSort(), "N"); + api::Term formals = MK_TERM(api::BOUND_VAR_LIST, n); + api::Term expr = MK_TERM(api::UMINUS, + MK_TERM(api::TO_INTEGER, MK_TERM(api::UMINUS, n))); + p.d_kind = api::LAMBDA; + p.d_expr = MK_TERM(api::LAMBDA, formals, expr); } | '$truncate' { - Expr n = EXPR_MANAGER->mkBoundVar("N", EXPR_MANAGER->realType()); - Expr formals = MK_EXPR(kind::BOUND_VAR_LIST, n); - Expr expr = - MK_EXPR(kind::ITE, - MK_EXPR(kind::GEQ, n, MK_CONST(Rational(0))), - MK_EXPR(kind::TO_INTEGER, n), - MK_EXPR(kind::UMINUS, - MK_EXPR(kind::TO_INTEGER, MK_EXPR(kind::UMINUS, n)))); - p.d_kind = kind::LAMBDA; - p.d_expr = MK_EXPR(kind::LAMBDA, formals, expr); + api::Term n = SOLVER->mkVar(SOLVER->getRealSort(), "N"); + api::Term formals = MK_TERM(api::BOUND_VAR_LIST, n); + api::Term expr = + MK_TERM(api::ITE, + MK_TERM(api::GEQ, n, SOLVER->mkReal(0)), + MK_TERM(api::TO_INTEGER, n), + MK_TERM(api::UMINUS, + MK_TERM(api::TO_INTEGER, MK_TERM(api::UMINUS, n)))); + p.d_kind = api::LAMBDA; + p.d_expr = MK_TERM(api::LAMBDA, formals, expr); } | '$round' { - Expr n = EXPR_MANAGER->mkBoundVar("N", EXPR_MANAGER->realType()); - Expr formals = MK_EXPR(kind::BOUND_VAR_LIST, n); - Expr decPart = MK_EXPR(kind::MINUS, n, MK_EXPR(kind::TO_INTEGER, n)); - Expr expr = MK_EXPR( - kind::ITE, - MK_EXPR(kind::LT, decPart, MK_CONST(Rational(1, 2))), + api::Term n = SOLVER->mkVar(SOLVER->getRealSort(), "N"); + api::Term formals = MK_TERM(api::BOUND_VAR_LIST, n); + api::Term decPart = MK_TERM(api::MINUS, n, MK_TERM(api::TO_INTEGER, n)); + api::Term expr = MK_TERM( + api::ITE, + MK_TERM(api::LT, decPart, SOLVER->mkReal(1, 2)), // if decPart < 0.5, round down - MK_EXPR(kind::TO_INTEGER, n), - MK_EXPR(kind::ITE, - MK_EXPR(kind::GT, decPart, MK_CONST(Rational(1, 2))), + MK_TERM(api::TO_INTEGER, n), + MK_TERM(api::ITE, + MK_TERM(api::GT, decPart, SOLVER->mkReal(1, 2)), // if decPart > 0.5, round up - MK_EXPR(kind::TO_INTEGER, - MK_EXPR(kind::PLUS, n, MK_CONST(Rational(1)))), + MK_TERM(api::TO_INTEGER, + MK_TERM(api::PLUS, n, SOLVER->mkReal(1))), // if decPart == 0.5, round to nearest even integer: // result is: to_int(n/2 + .5) * 2 - MK_EXPR(kind::MULT, - MK_EXPR(kind::TO_INTEGER, - MK_EXPR(kind::PLUS, - MK_EXPR(kind::DIVISION_TOTAL, + MK_TERM(api::MULT, + MK_TERM(api::TO_INTEGER, + MK_TERM(api::PLUS, + MK_TERM(api::DIVISION, n, - MK_CONST(Rational(2))), - MK_CONST(Rational(1, 2)))), - MK_CONST(Rational(2))))); - p.d_kind = kind::LAMBDA; - p.d_expr = MK_EXPR(kind::LAMBDA, formals, expr); + SOLVER->mkReal(2)), + SOLVER->mkReal(1, 2))), + SOLVER->mkReal(2)))); + p.d_kind = api::LAMBDA; + p.d_expr = MK_TERM(api::LAMBDA, formals, expr); } | '$to_int' { - p.d_kind = kind::TO_INTEGER; + p.d_kind = api::TO_INTEGER; } | '$to_rat' { - p.d_kind = kind::TO_REAL; + p.d_kind = api::TO_REAL; } | '$to_real' { - p.d_kind = kind::TO_REAL; + p.d_kind = api::TO_REAL; } ; @@ -736,16 +734,16 @@ equalOp[bool& equal] | DISEQUAL_TOK { equal = false; } ; -term[CVC4::Expr& expr] +term[CVC4::api::Term& expr] : functionTerm[expr] | conditionalTerm[expr] | simpleTerm[expr] | letTerm[expr] ; -letTerm[CVC4::Expr& expr] +letTerm[CVC4::api::Term& expr] @declarations { - CVC4::Expr lhs, rhs; + CVC4::api::Term lhs, rhs; } : '$let_ft' LPAREN_TOK { PARSER_STATE->pushScope(); } tffLetFormulaDefn[lhs, rhs] COMMA_TOK @@ -764,14 +762,14 @@ letTerm[CVC4::Expr& expr] ; /* Not an application */ -simpleTerm[CVC4::Expr& expr] +simpleTerm[CVC4::api::Term& expr] : variable[expr] | NUMBER { expr = PARSER_STATE->d_tmp_expr; } | DISTINCT_OBJECT { expr = PARSER_STATE->convertStrToUnsorted(AntlrInput::tokenText($DISTINCT_OBJECT)); } ; /* Not an application */ -thfSimpleTerm[CVC4::Expr& expr] +thfSimpleTerm[CVC4::api::Term& expr] : NUMBER { expr = PARSER_STATE->d_tmp_expr; } | DISTINCT_OBJECT { @@ -780,9 +778,9 @@ thfSimpleTerm[CVC4::Expr& expr] } ; -functionTerm[CVC4::Expr& expr] +functionTerm[CVC4::api::Term& expr] @declarations { - std::vector args; + std::vector args; ParseOp p; } : plainTerm[expr] @@ -792,18 +790,18 @@ functionTerm[CVC4::Expr& expr] } ; -conditionalTerm[CVC4::Expr& expr] +conditionalTerm[CVC4::api::Term& expr] @declarations { - CVC4::Expr expr2, expr3; + CVC4::api::Term expr2, expr3; } : '$ite_t' LPAREN_TOK tffLogicFormula[expr] COMMA_TOK term[expr2] COMMA_TOK term[expr3] RPAREN_TOK - { expr = EXPR_MANAGER->mkExpr(kind::ITE, expr, expr2, expr3); } + { expr = MK_TERM(api::ITE, expr, expr2, expr3); } ; -plainTerm[CVC4::Expr& expr] +plainTerm[CVC4::api::Term& expr] @declarations { std::string name; - std::vector args; + std::vector args; ParseOp p; } : atomicWord[p.d_name] (LPAREN_TOK arguments[args] RPAREN_TOK)? @@ -813,22 +811,22 @@ plainTerm[CVC4::Expr& expr] } ; -arguments[std::vector& args] +arguments[std::vector& args] @declarations { - Expr expr; + CVC4::api::Term expr; } : term[expr] { args.push_back(expr); } ( COMMA_TOK term[expr] { args.push_back(expr); } )* ; -variable[CVC4::Expr& expr] +variable[CVC4::api::Term& expr] : UPPER_WORD { std::string name = AntlrInput::tokenText($UPPER_WORD); if(!PARSER_STATE->cnf() || PARSER_STATE->isDeclared(name)) { expr = PARSER_STATE->getVariable(name); } else { - expr = PARSER_STATE->mkBoundVar(name, PARSER_STATE->d_unsorted); + expr = PARSER_STATE->bindBoundVar(name, PARSER_STATE->d_unsorted); if(PARSER_STATE->cnf()) PARSER_STATE->addFreeVar(expr); } } @@ -836,35 +834,35 @@ variable[CVC4::Expr& expr] /*******/ /* FOF */ -fofFormula[CVC4::Expr& expr] : fofLogicFormula[expr] ; +fofFormula[CVC4::api::Term& expr] : fofLogicFormula[expr] ; -fofLogicFormula[CVC4::Expr& expr] +fofLogicFormula[CVC4::api::Term& expr] @declarations { tptp::NonAssoc na; - std::vector< Expr > args; - Expr expr2; + std::vector< CVC4::api::Term > args; + CVC4::api::Term expr2; } : fofUnitaryFormula[expr] ( // Non-associative: <=> <~> ~& ~| ( fofBinaryNonAssoc[na] fofUnitaryFormula[expr2] { switch(na) { case tptp::NA_IFF: - expr = MK_EXPR(kind::EQUAL,expr,expr2); + expr = MK_TERM(api::EQUAL,expr,expr2); break; case tptp::NA_REVIFF: - expr = MK_EXPR(kind::XOR,expr,expr2); + expr = MK_TERM(api::XOR,expr,expr2); break; case tptp::NA_IMPLIES: - expr = MK_EXPR(kind::IMPLIES,expr,expr2); + expr = MK_TERM(api::IMPLIES,expr,expr2); break; case tptp::NA_REVIMPLIES: - expr = MK_EXPR(kind::IMPLIES,expr2,expr); + expr = MK_TERM(api::IMPLIES,expr2,expr); break; case tptp::NA_REVOR: - expr = MK_EXPR(kind::NOT,MK_EXPR(kind::OR,expr,expr2)); + expr = MK_TERM(api::NOT,MK_TERM(api::OR,expr,expr2)); break; case tptp::NA_REVAND: - expr = MK_EXPR(kind::NOT,MK_EXPR(kind::AND,expr,expr2)); + expr = MK_TERM(api::NOT,MK_TERM(api::AND,expr,expr2)); break; } } @@ -872,38 +870,38 @@ fofLogicFormula[CVC4::Expr& expr] | // N-ary and & ( { args.push_back(expr); } ( AND_TOK fofUnitaryFormula[expr] { args.push_back(expr); } )+ - { expr = MK_EXPR_ASSOCIATIVE(kind::AND, args); } + { expr = MK_TERM(api::AND, args); } ) | // N-ary or | ( { args.push_back(expr); } ( OR_TOK fofUnitaryFormula[expr] { args.push_back(expr); } )+ - { expr = MK_EXPR_ASSOCIATIVE(kind::OR, args); } + { expr = MK_TERM(api::OR, args); } ) )? ; -fofUnitaryFormula[CVC4::Expr& expr] +fofUnitaryFormula[CVC4::api::Term& expr] @declarations { - Kind kind; - std::vector< Expr > bv; + api::Kind kind; + std::vector< CVC4::api::Term > bv; } : atomicFormula[expr] | LPAREN_TOK fofLogicFormula[expr] RPAREN_TOK - | NOT_TOK fofUnitaryFormula[expr] { expr = MK_EXPR(kind::NOT,expr); } + | NOT_TOK fofUnitaryFormula[expr] { expr = MK_TERM(api::NOT,expr); } | // Quantified folQuantifier[kind] LBRACK_TOK {PARSER_STATE->pushScope();} ( bindvariable[expr] { bv.push_back(expr); } ( COMMA_TOK bindvariable[expr] { bv.push_back(expr); } )* ) RBRACK_TOK COLON_TOK fofUnitaryFormula[expr] { PARSER_STATE->popScope(); - expr = MK_EXPR(kind, MK_EXPR(kind::BOUND_VAR_LIST, bv), expr); + expr = MK_TERM(kind, MK_TERM(api::BOUND_VAR_LIST, bv), expr); } ; -bindvariable[CVC4::Expr& expr] +bindvariable[CVC4::api::Term& expr] : UPPER_WORD { std::string name = AntlrInput::tokenText($UPPER_WORD); - expr = PARSER_STATE->mkBoundVar(name, PARSER_STATE->d_unsorted); + expr = PARSER_STATE->bindBoundVar(name, PARSER_STATE->d_unsorted); } ; @@ -916,19 +914,19 @@ fofBinaryNonAssoc[CVC4::parser::tptp::NonAssoc& na] | REVIMPLIES_TOK { na = tptp::NA_REVIMPLIES; } ; -folQuantifier[CVC4::Kind& kind] - : FORALL_TOK { kind = kind::FORALL; } - | EXISTS_TOK { kind = kind::EXISTS; } +folQuantifier[CVC4::api::Kind& kind] + : FORALL_TOK { kind = api::FORALL; } + | EXISTS_TOK { kind = api::EXISTS; } ; /*******/ /* THF */ -thfQuantifier[CVC4::Kind& kind] - : FORALL_TOK { kind = kind::FORALL; } - | EXISTS_TOK { kind = kind::EXISTS; } - | LAMBDA_TOK { kind = kind::LAMBDA; } - | CHOICE_TOK { kind = kind::CHOICE; } +thfQuantifier[CVC4::api::Kind& kind] + : FORALL_TOK { kind = api::FORALL; } + | EXISTS_TOK { kind = api::EXISTS; } + | LAMBDA_TOK { kind = api::LAMBDA; } + | CHOICE_TOK { kind = api::CHOICE; } | DEF_DESC_TOK { UNSUPPORTED("Description quantifier"); @@ -942,8 +940,8 @@ thfQuantifier[CVC4::Kind& kind] thfAtomTyping[CVC4::Command*& cmd] // for now only supports mapping types (i.e. no applied types) @declarations { - CVC4::Expr expr; - CVC4::Type type; + CVC4::api::Term expr; + CVC4::api::Sort type; std::string name; } : LPAREN_TOK thfAtomTyping[cmd] RPAREN_TOK @@ -965,8 +963,8 @@ thfAtomTyping[CVC4::Command*& cmd] else { // as yet, it's undeclared - Type atype = PARSER_STATE->mkSort(name); - cmd = new DeclareTypeCommand(name, 0, atype); + api::Sort atype = PARSER_STATE->mkSort(name); + cmd = new DeclareTypeCommand(name, 0, atype.getType()); } } | parseThfType[type] @@ -980,7 +978,7 @@ thfAtomTyping[CVC4::Command*& cmd] } else if (PARSER_STATE->isDeclared(name, SYM_VARIABLE)) { - if (type == PARSER_STATE->getVariable(name).getType()) + if (type == PARSER_STATE->getVariable(name).getSort()) { // duplicate declaration is fine, they're compatible cmd = new EmptyCommand("compatible redeclaration of constant " @@ -997,16 +995,17 @@ thfAtomTyping[CVC4::Command*& cmd] else { // as of yet, it's undeclared - CVC4::Expr freshExpr; + CVC4::api::Term freshExpr; if (type.isFunction()) { - freshExpr = PARSER_STATE->mkVar(name, type); + freshExpr = PARSER_STATE->bindVar(name, type); } else { - freshExpr = PARSER_STATE->mkVar(name, type); + freshExpr = PARSER_STATE->bindVar(name, type); } - cmd = new DeclareFunctionCommand(name, freshExpr, type); + cmd = new DeclareFunctionCommand( + name, freshExpr.getExpr(), type.getType()); } } ) @@ -1015,9 +1014,9 @@ thfAtomTyping[CVC4::Command*& cmd] thfLogicFormula[CVC4::ParseOp& p] @declarations { tptp::NonAssoc na; - std::vector args; + std::vector args; std::vector p_args; - Expr expr2; + CVC4::api::Term expr2; bool equal; ParseOp p1; } @@ -1032,13 +1031,13 @@ thfLogicFormula[CVC4::ParseOp& p] { // make p.d_expr with a lambda of the same type as p1.d_expr p.d_expr = - PARSER_STATE->mkLambdaWrapper(p.d_kind, p1.d_expr.getType()); + PARSER_STATE->mkLambdaWrapper(p.d_kind, p1.d_expr.getSort()); } else if (p1.d_expr.isNull() && !p.d_expr.isNull()) { // make p1.d_expr with a lambda of the same type as p.d_expr p1.d_expr = - PARSER_STATE->mkLambdaWrapper(p1.d_kind, p.d_expr.getType()); + PARSER_STATE->mkLambdaWrapper(p1.d_kind, p.d_expr.getSort()); } else if (p.d_expr.isNull() && p1.d_expr.isNull()) { @@ -1048,10 +1047,10 @@ thfLogicFormula[CVC4::ParseOp& p] } args.push_back(p.d_expr); args.push_back(p1.d_expr); - p.d_expr = MK_EXPR(kind::EQUAL, args); + p.d_expr = MK_TERM(api::EQUAL, args); if (!equal) { - p.d_expr = MK_EXPR(kind::NOT, p.d_expr); + p.d_expr = MK_TERM(api::NOT, p.d_expr); } } | // Non-associative: <=> <~> ~& ~| @@ -1065,24 +1064,24 @@ thfLogicFormula[CVC4::ParseOp& p] switch (na) { case tptp::NA_IFF: - p.d_expr = MK_EXPR(kind::EQUAL, p.d_expr, p1.d_expr); + p.d_expr = MK_TERM(api::EQUAL, p.d_expr, p1.d_expr); break; case tptp::NA_REVIFF: - p.d_expr = MK_EXPR(kind::XOR, p.d_expr, p1.d_expr); + p.d_expr = MK_TERM(api::XOR, p.d_expr, p1.d_expr); break; case tptp::NA_IMPLIES: - p.d_expr = MK_EXPR(kind::IMPLIES, p.d_expr, p1.d_expr); + p.d_expr = MK_TERM(api::IMPLIES, p.d_expr, p1.d_expr); break; case tptp::NA_REVIMPLIES: - p.d_expr = MK_EXPR(kind::IMPLIES, p1.d_expr, p.d_expr); + p.d_expr = MK_TERM(api::IMPLIES, p1.d_expr, p.d_expr); break; case tptp::NA_REVOR: p.d_expr = - MK_EXPR(kind::NOT, MK_EXPR(kind::OR, p.d_expr, p1.d_expr)); + MK_TERM(api::NOT, MK_TERM(api::OR, p.d_expr, p1.d_expr)); break; case tptp::NA_REVAND: p.d_expr = - MK_EXPR(kind::NOT, MK_EXPR(kind::AND, p.d_expr, p1.d_expr)); + MK_TERM(api::NOT, MK_TERM(api::AND, p.d_expr, p1.d_expr)); break; } } @@ -1107,7 +1106,7 @@ thfLogicFormula[CVC4::ParseOp& p] } )+ { - p.d_expr = MK_EXPR_ASSOCIATIVE(kind::AND, args); + p.d_expr = MK_TERM(api::AND, args); } ) | // N-ary or | @@ -1131,7 +1130,7 @@ thfLogicFormula[CVC4::ParseOp& p] } )+ { - p.d_expr = MK_EXPR_ASSOCIATIVE(kind::OR, args); + p.d_expr = MK_TERM(api::OR, args); } ) | // N-ary @ | @@ -1191,19 +1190,19 @@ thfLogicFormula[CVC4::ParseOp& p] // lambda must have type ti args.push_back(PARSER_STATE->mkLambdaWrapper( p_args[i].d_kind, - (static_cast(p.d_expr.getType())) - .getArgTypes()[i - 1])); + p.d_expr.getSort() + .getFunctionDomainSorts()[i - 1])); } for (unsigned i = 0, size = args.size(); i < size; ++i) { - p.d_expr = MK_EXPR(kind::HO_APPLY, p.d_expr, args[i]); + p.d_expr = MK_TERM(api::HO_APPLY, p.d_expr, args[i]); } } } )? ; -thfTupleForm[std::vector& args] +thfTupleForm[std::vector& args] @declarations { ParseOp p; } @@ -1228,9 +1227,9 @@ thfTupleForm[std::vector& args] thfUnitaryFormula[CVC4::ParseOp& p] @declarations { - Kind kind; - std::vector< Expr > bv; - Expr expr; + api::Kind kind; + std::vector< CVC4::api::Term > bv; + CVC4::api::Term expr; bool equal; ParseOp p1; } @@ -1241,7 +1240,7 @@ thfUnitaryFormula[CVC4::ParseOp& p] RPAREN_TOK | NOT_TOK { - p.d_kind = kind::NOT; + p.d_kind = api::NOT; } ( thfUnitaryFormula[p1] @@ -1250,7 +1249,7 @@ thfUnitaryFormula[CVC4::ParseOp& p] { PARSER_STATE->parseError("NOT must be applied to a formula"); } - std::vector args{p1.d_expr}; + std::vector args{p1.d_expr}; p.d_expr = PARSER_STATE->applyParseOp(p, args); } )? @@ -1282,9 +1281,9 @@ thfUnitaryFormula[CVC4::ParseOp& p] // see documentation of mkFlatFunctionType for how it's done // // flatten body via flattening its type - std::vector sorts; - std::vector flattenVars; - PARSER_STATE->mkFlatFunctionType(sorts, expr.getType(), flattenVars); + std::vector sorts; + std::vector flattenVars; + PARSER_STATE->mkFlatFunctionType(sorts, expr.getSort(), flattenVars); if (!flattenVars.empty()) { // apply body of lambda to flatten vars @@ -1292,18 +1291,18 @@ thfUnitaryFormula[CVC4::ParseOp& p] // add variables to BOUND_VAR_LIST bv.insert(bv.end(), flattenVars.begin(), flattenVars.end()); } - p.d_expr = MK_EXPR(p.d_kind, MK_EXPR(kind::BOUND_VAR_LIST, bv), expr); + p.d_expr = MK_TERM(p.d_kind, MK_TERM(api::BOUND_VAR_LIST, bv), expr); } ; /*******/ /* TFF */ -tffFormula[CVC4::Expr& expr] : tffLogicFormula[expr]; +tffFormula[CVC4::api::Term& expr] : tffLogicFormula[expr]; tffTypedAtom[CVC4::Command*& cmd] @declarations { - CVC4::Expr expr; - CVC4::Type type; + CVC4::api::Term expr; + CVC4::api::Sort type; std::string name; } : LPAREN_TOK tffTypedAtom[cmd] RPAREN_TOK @@ -1317,8 +1316,8 @@ tffTypedAtom[CVC4::Command*& cmd] PARSER_STATE->parseError("Symbol `" + name + "' previously declared as a constant; cannot also be a sort"); } else { // as yet, it's undeclared - Type atype = PARSER_STATE->mkSort(name); - cmd = new DeclareTypeCommand(name, 0, atype); + api::Sort atype = PARSER_STATE->mkSort(name); + cmd = new DeclareTypeCommand(name, 0, atype.getType()); } } | parseType[type] @@ -1327,7 +1326,7 @@ tffTypedAtom[CVC4::Command*& cmd] PARSER_STATE->parseError("Symbol `" + name + "' previously declared as a sort"); cmd = new EmptyCommand("compatible redeclaration of sort " + name); } else if(PARSER_STATE->isDeclared(name, SYM_VARIABLE)) { - if(type == PARSER_STATE->getVariable(name).getType()) { + if(type == PARSER_STATE->getVariable(name).getSort()) { // duplicate declaration is fine, they're compatible cmd = new EmptyCommand("compatible redeclaration of constant " + name); } else { @@ -1336,40 +1335,41 @@ tffTypedAtom[CVC4::Command*& cmd] } } else { // as yet, it's undeclared - CVC4::Expr aexpr = PARSER_STATE->mkVar(name, type); - cmd = new DeclareFunctionCommand(name, aexpr, type); + CVC4::api::Term aexpr = PARSER_STATE->bindVar(name, type); + cmd = + new DeclareFunctionCommand(name, aexpr.getExpr(), type.getType()); } } ) ; -tffLogicFormula[CVC4::Expr& expr] +tffLogicFormula[CVC4::api::Term& expr] @declarations { tptp::NonAssoc na; - std::vector< Expr > args; - Expr expr2; + std::vector< CVC4::api::Term > args; + CVC4::api::Term expr2; } : tffUnitaryFormula[expr] ( // Non Assoc <=> <~> ~& ~| ( fofBinaryNonAssoc[na] tffUnitaryFormula[expr2] { switch(na) { case tptp::NA_IFF: - expr = MK_EXPR(kind::EQUAL,expr,expr2); + expr = MK_TERM(api::EQUAL,expr,expr2); break; case tptp::NA_REVIFF: - expr = MK_EXPR(kind::XOR,expr,expr2); + expr = MK_TERM(api::XOR,expr,expr2); break; case tptp::NA_IMPLIES: - expr = MK_EXPR(kind::IMPLIES,expr,expr2); + expr = MK_TERM(api::IMPLIES,expr,expr2); break; case tptp::NA_REVIMPLIES: - expr = MK_EXPR(kind::IMPLIES,expr2,expr); + expr = MK_TERM(api::IMPLIES,expr2,expr); break; case tptp::NA_REVOR: - expr = MK_EXPR(kind::NOT,MK_EXPR(kind::OR,expr,expr2)); + expr = MK_TERM(api::NOT,MK_TERM(api::OR,expr,expr2)); break; case tptp::NA_REVAND: - expr = MK_EXPR(kind::NOT,MK_EXPR(kind::AND,expr,expr2)); + expr = MK_TERM(api::NOT,MK_TERM(api::AND,expr,expr2)); break; } } @@ -1377,35 +1377,35 @@ tffLogicFormula[CVC4::Expr& expr] | // And & ( { args.push_back(expr); } ( AND_TOK tffUnitaryFormula[expr] { args.push_back(expr); } )+ - { expr = MK_EXPR(kind::AND,args); } + { expr = MK_TERM(api::AND,args); } ) | // Or | ( { args.push_back(expr); } ( OR_TOK tffUnitaryFormula[expr] { args.push_back(expr); } )+ - { expr = MK_EXPR(kind::OR,args); } + { expr = MK_TERM(api::OR,args); } ) )? ; -tffUnitaryFormula[CVC4::Expr& expr] +tffUnitaryFormula[CVC4::api::Term& expr] @declarations { - Kind kind; - std::vector< Expr > bv; - Expr lhs, rhs; + api::Kind kind; + std::vector< CVC4::api::Term > bv; + CVC4::api::Term lhs, rhs; } : atomicFormula[expr] | LPAREN_TOK tffLogicFormula[expr] RPAREN_TOK - | NOT_TOK tffUnitaryFormula[expr] { expr = MK_EXPR(kind::NOT,expr); } + | NOT_TOK tffUnitaryFormula[expr] { expr = MK_TERM(api::NOT,expr); } | // Quantified folQuantifier[kind] LBRACK_TOK {PARSER_STATE->pushScope();} ( tffbindvariable[expr] { bv.push_back(expr); } ( COMMA_TOK tffbindvariable[expr] { bv.push_back(expr); } )* ) RBRACK_TOK COLON_TOK tffUnitaryFormula[expr] { PARSER_STATE->popScope(); - expr = MK_EXPR(kind, MK_EXPR(kind::BOUND_VAR_LIST, bv), expr); + expr = MK_TERM(kind, MK_TERM(api::BOUND_VAR_LIST, bv), expr); } | '$ite_f' LPAREN_TOK tffLogicFormula[expr] COMMA_TOK tffLogicFormula[lhs] COMMA_TOK tffLogicFormula[rhs] RPAREN_TOK - { expr = EXPR_MANAGER->mkExpr(kind::ITE, expr, lhs, rhs); } + { expr = MK_TERM(api::ITE, expr, lhs, rhs); } | '$let_tf' LPAREN_TOK { PARSER_STATE->pushScope(); } tffLetTermDefn[lhs, rhs] COMMA_TOK tffFormula[expr] @@ -1422,79 +1422,88 @@ tffUnitaryFormula[CVC4::Expr& expr] RPAREN_TOK ; -tffLetTermDefn[CVC4::Expr& lhs, CVC4::Expr& rhs] +tffLetTermDefn[CVC4::api::Term& lhs, CVC4::api::Term& rhs] @declarations { - std::vector bvlist; + std::vector bvlist; } : (FORALL_TOK LBRACK_TOK tffVariableList[bvlist] RBRACK_TOK COLON_TOK)* tffLetTermBinding[bvlist, lhs, rhs] ; -tffLetTermBinding[std::vector& bvlist, CVC4::Expr& lhs, CVC4::Expr& rhs] +tffLetTermBinding[std::vector & bvlist, + CVC4::api::Term& lhs, + CVC4::api::Term& rhs] : term[lhs] EQUAL_TOK term[rhs] - { PARSER_STATE->checkLetBinding(bvlist, lhs, rhs, false); - rhs = MK_EXPR(kind::LAMBDA, MK_EXPR(kind::BOUND_VAR_LIST, lhs.getChildren()), rhs); - lhs = lhs.getOperator(); - } + { + PARSER_STATE->checkLetBinding(bvlist, lhs, rhs, false); + std::vector lchildren(++lhs.begin(), lhs.end()); + rhs = MK_TERM(api::LAMBDA, MK_TERM(api::BOUND_VAR_LIST, lchildren), rhs); + lhs = api::Term(lhs.getExpr().getOperator()); + } | LPAREN_TOK tffLetTermBinding[bvlist, lhs, rhs] RPAREN_TOK ; -tffLetFormulaDefn[CVC4::Expr& lhs, CVC4::Expr& rhs] +tffLetFormulaDefn[CVC4::api::Term& lhs, CVC4::api::Term& rhs] @declarations { - std::vector bvlist; + std::vector bvlist; } : (FORALL_TOK LBRACK_TOK tffVariableList[bvlist] RBRACK_TOK COLON_TOK)* tffLetFormulaBinding[bvlist, lhs, rhs] ; -tffLetFormulaBinding[std::vector& bvlist, CVC4::Expr& lhs, CVC4::Expr& rhs] +tffLetFormulaBinding[std::vector & bvlist, + CVC4::api::Term& lhs, + CVC4::api::Term& rhs] + : atomicFormula[lhs] IFF_TOK tffUnitaryFormula[rhs] - { PARSER_STATE->checkLetBinding(bvlist, lhs, rhs, true); - rhs = MK_EXPR(kind::LAMBDA, MK_EXPR(kind::BOUND_VAR_LIST, lhs.getChildren()), rhs); - lhs = lhs.getOperator(); - } + { + PARSER_STATE->checkLetBinding(bvlist, lhs, rhs, true); + std::vector lchildren(++lhs.begin(), lhs.end()); + rhs = MK_TERM(api::LAMBDA, MK_TERM(api::BOUND_VAR_LIST, lchildren), rhs); + lhs = api::Term(lhs.getExpr().getOperator()); + } | LPAREN_TOK tffLetFormulaBinding[bvlist, lhs, rhs] RPAREN_TOK ; -thfBindVariable[CVC4::Expr& expr] +thfBindVariable[CVC4::api::Term& expr] @declarations { std::string name; - CVC4::Type type = PARSER_STATE->d_unsorted; + CVC4::api::Sort type = PARSER_STATE->d_unsorted; } : UPPER_WORD { name = AntlrInput::tokenText($UPPER_WORD); } ( COLON_TOK parseThfType[type] )? { - expr = PARSER_STATE->mkBoundVar(name, type); + expr = PARSER_STATE->bindBoundVar(name, type); } ; -tffbindvariable[CVC4::Expr& expr] +tffbindvariable[CVC4::api::Term& expr] @declarations { - CVC4::Type type = PARSER_STATE->d_unsorted; + CVC4::api::Sort type = PARSER_STATE->d_unsorted; } : UPPER_WORD ( COLON_TOK parseType[type] )? { std::string name = AntlrInput::tokenText($UPPER_WORD); - expr = PARSER_STATE->mkBoundVar(name, type); + expr = PARSER_STATE->bindBoundVar(name, type); } ; // bvlist is accumulative; it can already contain elements // on the way in, which are left undisturbed -tffVariableList[std::vector& bvlist] +tffVariableList[std::vector& bvlist] @declarations { - CVC4::Expr e; + CVC4::api::Term e; } : tffbindvariable[e] { bvlist.push_back(e); } ( COMMA_TOK tffbindvariable[e] { bvlist.push_back(e); } )* ; -parseThfType[CVC4::Type& type] +parseThfType[CVC4::api::Sort& type] // assumes only mapping types (arrows), no tuple type @declarations { - std::vector sorts; + std::vector sorts; } : thfType[type] { sorts.push_back(type); } ( @@ -1507,24 +1516,24 @@ parseThfType[CVC4::Type& type] } else { - Type range = sorts.back(); + api::Sort range = sorts.back(); sorts.pop_back(); type = PARSER_STATE->mkFlatFunctionType(sorts, range); } } ; -thfType[CVC4::Type& type] +thfType[CVC4::api::Sort& type] // assumes only mapping types (arrows), no tuple type : simpleType[type] | LPAREN_TOK parseThfType[type] RPAREN_TOK | LBRACK_TOK { UNSUPPORTED("Tuple types"); } parseThfType[type] RBRACK_TOK ; -parseType[CVC4::Type & type] +parseType[CVC4::api::Sort & type] @declarations { - std::vector v; + std::vector v; } : simpleType[type] | ( simpleType[type] { v.push_back(type); } @@ -1533,23 +1542,22 @@ parseType[CVC4::Type & type] RPAREN_TOK ) ARROW_TOK simpleType[type] - { v.push_back(type); - type = EXPR_MANAGER->mkFunctionType(v); + { type = SOLVER->mkFunctionSort(v,type); } ; // non-function types -simpleType[CVC4::Type& type] +simpleType[CVC4::api::Sort& type] @declarations { std::string name; } : DEFINED_SYMBOL { std::string s = AntlrInput::tokenText($DEFINED_SYMBOL); if(s == "\$i") type = PARSER_STATE->d_unsorted; - else if(s == "\$o") type = EXPR_MANAGER->booleanType(); - else if(s == "\$int") type = EXPR_MANAGER->integerType(); - else if(s == "\$rat") type = EXPR_MANAGER->realType(); - else if(s == "\$real") type = EXPR_MANAGER->realType(); + else if(s == "\$o") type = SOLVER->getBooleanSort(); + else if(s == "\$int") type = SOLVER->getIntegerSort(); + else if(s == "\$rat") type = SOLVER->getRealSort(); + else if(s == "\$real") type = SOLVER->getRealSort(); else if(s == "\$tType") PARSER_STATE->parseError("Type of types `\$tType' cannot be used here"); else PARSER_STATE->parseError("unknown defined type `" + s + "'"); } @@ -1736,12 +1744,13 @@ NUMBER bool posE = true; } : ( SIGN[pos]? num=DECIMAL - { Integer i(AntlrInput::tokenText($num)); - Rational r = pos ? i : -i; - PARSER_STATE->d_tmp_expr = MK_CONST(r); + { std::stringstream ss; + ss << ( pos ? "" : "-" ) << AntlrInput::tokenText($num); + PARSER_STATE->d_tmp_expr = SOLVER->mkReal(ss.str()); } | SIGN[pos]? num=DECIMAL DOT den=DECIMAL (EXPONENT SIGN[posE]? e=DECIMAL)? - { std::string snum = AntlrInput::tokenText($num); + { + std::string snum = AntlrInput::tokenText($num); std::string sden = AntlrInput::tokenText($den); /* compute the numerator */ Integer inum(snum + sden); @@ -1758,12 +1767,14 @@ NUMBER else if(exp == dec) r = Rational(inum); else if(exp > dec) r = Rational(inum * Integer(10).pow(exp - dec)); else r = Rational(inum, Integer(10).pow(dec - exp)); - PARSER_STATE->d_tmp_expr = MK_CONST(r); + std::stringstream ss; + ss << r; + PARSER_STATE->d_tmp_expr = SOLVER->mkReal(ss.str()); } | SIGN[pos]? num=DECIMAL SLASH den=DECIMAL - { Integer inum(AntlrInput::tokenText($num)); - Integer iden(AntlrInput::tokenText($den)); - PARSER_STATE->d_tmp_expr = MK_CONST(Rational(pos ? inum : -inum, iden)); + { std::stringstream ss; + ss << AntlrInput::tokenText($num) << "/" << AntlrInput::tokenText($den); + PARSER_STATE->d_tmp_expr = SOLVER->mkReal(ss.str()); } ) { if(PARSER_STATE->cnf() || PARSER_STATE->fof()) { diff --git a/src/parser/tptp/tptp.cpp b/src/parser/tptp/tptp.cpp index d18e4a778..a21cc6785 100644 --- a/src/parser/tptp/tptp.cpp +++ b/src/parser/tptp/tptp.cpp @@ -75,21 +75,22 @@ void Tptp::addTheory(Theory theory) { //TPTP (CNF and FOF) is unsorted so we define this common type { std::string d_unsorted_name = "$$unsorted"; - d_unsorted = em->mkSort(d_unsorted_name); - preemptCommand( new DeclareTypeCommand(d_unsorted_name, 0, d_unsorted) ); + d_unsorted = api::Sort(em->mkSort(d_unsorted_name)); + preemptCommand( + new DeclareTypeCommand(d_unsorted_name, 0, d_unsorted.getType())); } // propositionnal defineType("Bool", em->booleanType()); defineVar("$true", em->mkConst(true)); defineVar("$false", em->mkConst(false)); - addOperator(kind::AND); - addOperator(kind::EQUAL); - addOperator(kind::IMPLIES); - //addOperator(kind::ITE); //only for tff thf - addOperator(kind::NOT); - addOperator(kind::OR); - addOperator(kind::XOR); - addOperator(kind::APPLY_UF); + addOperator(api::AND); + addOperator(api::EQUAL); + addOperator(api::IMPLIES); + // addOperator(api::ITE); //only for tff thf + addOperator(api::NOT); + addOperator(api::OR); + addOperator(api::XOR); + addOperator(api::APPLY_UF); //Add quantifiers? break; @@ -184,24 +185,32 @@ void Tptp::includeFile(std::string fileName) { } } -void Tptp::checkLetBinding(const std::vector& bvlist, Expr lhs, Expr rhs, - bool formula) { - if (lhs.getKind() != CVC4::kind::APPLY_UF) { +void Tptp::checkLetBinding(const std::vector& bvlist, + api::Term lhs, + api::Term rhs, + bool formula) +{ + if (lhs.getKind() != api::APPLY_UF) + { parseError("malformed let: LHS must be a flat function application"); } - const std::multiset vars{lhs.begin(), lhs.end()}; - if(formula && !lhs.getType().isBoolean()) { + const std::multiset vars{lhs.begin(), lhs.end()}; + if (formula && !lhs.getSort().isBoolean()) + { parseError("malformed let: LHS must be formula"); } - for (const CVC4::Expr& var : vars) { - if (var.hasOperator()) { + for (const CVC4::api::Term& var : vars) + { + if (var.hasOp()) + { parseError("malformed let: LHS must be flat, illegal child: " + var.toString()); } } // ensure all let-bound variables appear on the LHS, and appear only once - for (const Expr& bound_var : bvlist) { + for (const api::Term& bound_var : bvlist) + { const size_t count = vars.count(bound_var); if (count == 0) { parseError( @@ -215,76 +224,79 @@ void Tptp::checkLetBinding(const std::vector& bvlist, Expr lhs, Expr rhs, } } -Expr Tptp::parseOpToExpr(ParseOp& p) +api::Term Tptp::parseOpToExpr(ParseOp& p) { - Expr expr; + api::Term expr; if (!p.d_expr.isNull()) { return p.d_expr; } // if it has a kind, it's a builtin one and this function should not have been // called - assert(p.d_kind == kind::NULL_EXPR); + assert(p.d_kind == api::NULL_EXPR); if (isDeclared(p.d_name)) { // already appeared expr = getVariable(p.d_name); } else { - Type t = - p.d_type == getExprManager()->booleanType() ? p.d_type : d_unsorted; - expr = mkVar(p.d_name, t, ExprManager::VAR_FLAG_GLOBAL); // levelZero - preemptCommand(new DeclareFunctionCommand(p.d_name, expr, t)); + api::Sort t = + p.d_type == d_solver->getBooleanSort() ? p.d_type : d_unsorted; + expr = bindVar(p.d_name, t, ExprManager::VAR_FLAG_GLOBAL); // levelZero + preemptCommand( + new DeclareFunctionCommand(p.d_name, expr.getExpr(), t.getType())); } return expr; } -Expr Tptp::applyParseOp(ParseOp& p, std::vector& args) +api::Term Tptp::applyParseOp(ParseOp& p, std::vector& args) { if (Debug.isOn("parser")) { Debug("parser") << "applyParseOp: " << p << " to:" << std::endl; - for (std::vector::iterator i = args.begin(); i != args.end(); ++i) + for (std::vector::iterator i = args.begin(); i != args.end(); + ++i) { Debug("parser") << "++ " << *i << std::endl; } } assert(!args.empty()); - ExprManager* em = getExprManager(); // If operator already defined, just build application if (!p.d_expr.isNull()) { // this happens with some arithmetic kinds, which are wrapped around // lambdas. args.insert(args.begin(), p.d_expr); - return em->mkExpr(kind::APPLY_UF, args); + return d_solver->mkTerm(api::APPLY_UF, args); } bool isBuiltinKind = false; // the builtin kind of the overall return expression - Kind kind = kind::NULL_EXPR; + api::Kind kind = api::NULL_EXPR; // First phase: piece operator together - if (p.d_kind == kind::NULL_EXPR) + if (p.d_kind == api::NULL_EXPR) { // A non-built-in function application, get the expression - Expr v; + api::Term v; if (isDeclared(p.d_name)) { // already appeared v = getVariable(p.d_name); } else { - std::vector sorts(args.size(), d_unsorted); - Type t = p.d_type == em->booleanType() ? p.d_type : d_unsorted; - t = getExprManager()->mkFunctionType(sorts, t); - v = mkVar(p.d_name, t, ExprManager::VAR_FLAG_GLOBAL); // levelZero - preemptCommand(new DeclareFunctionCommand(p.d_name, v, t)); + std::vector sorts(args.size(), d_unsorted); + api::Sort t = + p.d_type == d_solver->getBooleanSort() ? p.d_type : d_unsorted; + t = d_solver->mkFunctionSort(sorts, t); + v = bindVar(p.d_name, t, ExprManager::VAR_FLAG_GLOBAL); // levelZero + preemptCommand( + new DeclareFunctionCommand(p.d_name, v.getExpr(), t.getType())); } // args might be rationals, in which case we need to create // distinct constants of the "unsorted" sort to represent them for (size_t i = 0; i < args.size(); ++i) { - if (args[i].getType().isReal() - && FunctionType(v.getType()).getArgTypes()[i] == d_unsorted) + if (args[i].getSort().isReal() + && v.getSort().getFunctionDomainSorts()[i] == d_unsorted) { args[i] = convertRatToUnsorted(args[i]); } @@ -299,44 +311,45 @@ Expr Tptp::applyParseOp(ParseOp& p, std::vector& args) kind = p.d_kind; isBuiltinKind = true; } - assert(kind != kind::NULL_EXPR); + assert(kind != api::NULL_EXPR); + ExprManager* em = getExprManager(); // Second phase: apply parse op to the arguments if (isBuiltinKind) { if (!em->getOptions().getUfHo() - && (kind == kind::EQUAL || kind == kind::DISTINCT)) + && (kind == api::EQUAL || kind == api::DISTINCT)) { // need --uf-ho if these operators are applied over function args - for (std::vector::iterator i = args.begin(); i != args.end(); ++i) + for (std::vector::iterator i = args.begin(); i != args.end(); + ++i) { - if ((*i).getType().isFunction()) + if ((*i).getSort().isFunction()) { parseError( "Cannot apply equalty to functions unless --uf-ho is set."); } } } - if (!strictModeEnabled() && (kind == kind::AND || kind == kind::OR) + if (!strictModeEnabled() && (kind == api::AND || kind == api::OR) && args.size() == 1) { // Unary AND/OR can be replaced with the argument. return args[0]; } - if (kind == kind::MINUS && args.size() == 1) + if (kind == api::MINUS && args.size() == 1) { - return em->mkExpr(kind::UMINUS, args[0]); + return d_solver->mkTerm(api::UMINUS, args[0]); } - return d_solver->mkTerm(intToExtKind(kind), api::exprVectorToTerms(args)) - .getExpr(); + return d_solver->mkTerm(kind, args); } // check if partially applied function, in this case we use HO_APPLY if (args.size() >= 2) { - Type argt = args[0].getType(); + api::Sort argt = args[0].getSort(); if (argt.isFunction()) { - unsigned arity = static_cast(argt).getArity(); + unsigned arity = argt.getFunctionArity(); if (args.size() - 1 < arity) { if (!em->getOptions().getUfHo()) @@ -347,12 +360,11 @@ Expr Tptp::applyParseOp(ParseOp& p, std::vector& args) Debug("parser") << " : #argTypes = " << arity; Debug("parser") << ", #args = " << args.size() - 1 << std::endl; // must curry the partial application - return d_solver->mkTerm(api::HO_APPLY, api::exprVectorToTerms(args)) - .getExpr(); + return d_solver->mkTerm(api::HO_APPLY, args); } } } - return em->mkExpr(kind, args); + return d_solver->mkTerm(kind, args); } void Tptp::forceLogic(const std::string& logic) @@ -361,79 +373,84 @@ void Tptp::forceLogic(const std::string& logic) preemptCommand(new SetBenchmarkLogicCommand(logic)); } -void Tptp::addFreeVar(Expr var) { +void Tptp::addFreeVar(api::Term var) +{ assert(cnf()); d_freeVar.push_back(var); } -std::vector Tptp::getFreeVar() { +std::vector Tptp::getFreeVar() +{ assert(cnf()); - std::vector r; + std::vector r; r.swap(d_freeVar); return r; } -Expr Tptp::convertRatToUnsorted(Expr expr) { - ExprManager* em = getExprManager(); - +api::Term Tptp::convertRatToUnsorted(api::Term expr) +{ // Create the conversion function If they doesn't exists if (d_rtu_op.isNull()) { - Type t; + api::Sort t; // Conversion from rational to unsorted - t = em->mkFunctionType(em->realType(), d_unsorted); - d_rtu_op = em->mkVar("$$rtu", t); - preemptCommand(new DeclareFunctionCommand("$$rtu", d_rtu_op, t)); + t = d_solver->mkFunctionSort(d_solver->getRealSort(), d_unsorted); + d_rtu_op = d_solver->mkConst(t, "$$rtu"); + preemptCommand( + new DeclareFunctionCommand("$$rtu", d_rtu_op.getExpr(), t.getType())); // Conversion from unsorted to rational - t = em->mkFunctionType(d_unsorted, em->realType()); - d_utr_op = em->mkVar("$$utr", t); - preemptCommand(new DeclareFunctionCommand("$$utr", d_utr_op, t)); + t = d_solver->mkFunctionSort(d_unsorted, d_solver->getRealSort()); + d_utr_op = d_solver->mkConst(t, "$$utr"); + preemptCommand( + new DeclareFunctionCommand("$$utr", d_utr_op.getExpr(), t.getType())); } // Add the inverse in order to show that over the elements that // appear in the problem there is a bijection between unsorted and // rational - Expr ret = em->mkExpr(kind::APPLY_UF, d_rtu_op, expr); + api::Term ret = d_solver->mkTerm(api::APPLY_UF, d_rtu_op, expr); if (d_r_converted.find(expr) == d_r_converted.end()) { d_r_converted.insert(expr); - Expr eq = em->mkExpr(kind::EQUAL, expr, - em->mkExpr(kind::APPLY_UF, d_utr_op, ret)); - preemptCommand(new AssertCommand(eq)); + api::Term eq = d_solver->mkTerm( + api::EQUAL, expr, d_solver->mkTerm(api::APPLY_UF, d_utr_op, ret)); + preemptCommand(new AssertCommand(eq.getExpr())); } - return ret; + return api::Term(ret); } -Expr Tptp::convertStrToUnsorted(std::string str) { - Expr& e = d_distinct_objects[str]; +api::Term Tptp::convertStrToUnsorted(std::string str) +{ + api::Term& e = d_distinct_objects[str]; if (e.isNull()) { - e = getExprManager()->mkVar(str, d_unsorted); + e = d_solver->mkConst(d_unsorted, str); } return e; } -Expr Tptp::mkLambdaWrapper(Kind k, Type argType) +api::Term Tptp::mkLambdaWrapper(api::Kind k, api::Sort argType) { Debug("parser") << "mkLambdaWrapper: kind " << k << " and type " << argType << "\n"; - std::vector lvars; - std::vector domainTypes = - (static_cast(argType)).getArgTypes(); - ExprManager* em = getExprManager(); + std::vector lvars; + std::vector domainTypes = argType.getFunctionDomainSorts(); for (unsigned i = 0, size = domainTypes.size(); i < size; ++i) { // the introduced variable is internal (not parsable) std::stringstream ss; ss << "_lvar_" << i; - Expr v = em->mkBoundVar(ss.str(), domainTypes[i]); + api::Term v = d_solver->mkVar(domainTypes[i], ss.str()); lvars.push_back(v); } // apply body of lambda to variables - Expr wrapper = em->mkExpr(kind::LAMBDA, - em->mkExpr(kind::BOUND_VAR_LIST, lvars), - em->mkExpr(k, lvars)); + api::Term wrapper = + d_solver->mkTerm(api::LAMBDA, + d_solver->mkTerm(api::BOUND_VAR_LIST, lvars), + d_solver->mkTerm(k, lvars)); + return wrapper; } -Expr Tptp::getAssertionExpr(FormulaRole fr, Expr expr) { +api::Term Tptp::getAssertionExpr(FormulaRole fr, api::Term expr) +{ switch (fr) { case FR_AXIOM: case FR_HYPOTHESIS: @@ -447,7 +464,7 @@ Expr Tptp::getAssertionExpr(FormulaRole fr, Expr expr) { return expr; case FR_CONJECTURE: // it should be negated when asserted - return getExprManager()->mkExpr(kind::NOT, expr); + return d_solver->mkTerm(api::NOT, expr); case FR_UNKNOWN: case FR_FI_DOMAIN: case FR_FI_FUNCTORS: @@ -461,21 +478,25 @@ Expr Tptp::getAssertionExpr(FormulaRole fr, Expr expr) { return d_nullExpr; } -Expr Tptp::getAssertionDistinctConstants() +api::Term Tptp::getAssertionDistinctConstants() { - std::vector constants; - for (std::pair& cs : d_distinct_objects) + std::vector constants; + for (std::pair& cs : d_distinct_objects) { constants.push_back(cs.second); } if (constants.size() > 1) { - return getExprManager()->mkExpr(kind::DISTINCT, constants); + return d_solver->mkTerm(api::DISTINCT, constants); } return d_nullExpr; } -Command* Tptp::makeAssertCommand(FormulaRole fr, Expr expr, bool cnf, bool inUnsatCore) { +Command* Tptp::makeAssertCommand(FormulaRole fr, + api::Term expr, + bool cnf, + bool inUnsatCore) +{ // For SZS ontology compliance. // if we're in cnf() though, conjectures don't result in "Theorem" or // "CounterSatisfiable". @@ -486,7 +507,7 @@ Command* Tptp::makeAssertCommand(FormulaRole fr, Expr expr, bool cnf, bool inUns if( expr.isNull() ){ return new EmptyCommand("Untreated role for expression"); }else{ - return new AssertCommand(expr, inUnsatCore); + return new AssertCommand(expr.getExpr(), inUnsatCore); } } diff --git a/src/parser/tptp/tptp.h b/src/parser/tptp/tptp.h index 23791ea0c..50557c95a 100644 --- a/src/parser/tptp/tptp.h +++ b/src/parser/tptp/tptp.h @@ -25,6 +25,7 @@ #include #include +#include "api/cvc4cpp.h" #include "parser/parse_op.h" #include "parser/parser.h" #include "smt/command.h" @@ -50,20 +51,20 @@ class Tptp : public Parser { void forceLogic(const std::string& logic) override; - void addFreeVar(Expr var); - std::vector< Expr > getFreeVar(); + void addFreeVar(api::Term var); + std::vector getFreeVar(); - Expr convertRatToUnsorted(Expr expr); + api::Term convertRatToUnsorted(api::Term expr); /** * Returns a free constant corresponding to the string str. We ensure that * these constants are one-to-one with str. We assert that all these free * constants are pairwise distinct before issuing satisfiability queries. */ - Expr convertStrToUnsorted(std::string str); + api::Term convertStrToUnsorted(std::string str); // CNF and FOF are unsorted so we define this common type. - // This is also the Type of $i in TFF. - Type d_unsorted; + // This is also the api::Sort of $i in TFF. + api::Sort d_unsorted; enum Theory { THEORY_CORE, @@ -109,14 +110,14 @@ class Tptp : public Parser { * expression * (lambda x1:t1,...,xn:tn . (k x1 ... xn)) : t */ - Expr mkLambdaWrapper(Kind k, Type argType); + api::Term mkLambdaWrapper(api::Kind k, api::Sort argType); /** get assertion expression, based on the formula role. * expr should have Boolean type. * This returns the expression that should be asserted, given the formula role fr. * For example, if the role is "conjecture", then the return value is the negation of expr. */ - Expr getAssertionExpr(FormulaRole fr, Expr expr); + api::Term getAssertionExpr(FormulaRole fr, api::Term expr); /** get assertion for distinct constants * @@ -124,26 +125,31 @@ class Tptp : public Parser { * are the distinct constants introduced by this parser (see * convertStrToUnsorted) if n>1, or null otherwise. */ - Expr getAssertionDistinctConstants(); + api::Term getAssertionDistinctConstants(); - /** returns the appropriate AssertCommand, given a role, expression expr to assert, - * and information about the assertion. - * The assertion expr is literally what should be asserted (it is already been processed - * with getAssertionExpr above). - * This may set a flag in the parser to mark that we have asserted a conjecture. - */ - Command* makeAssertCommand(FormulaRole fr, Expr expr, bool cnf, bool inUnsatCore); + /** returns the appropriate AssertCommand, given a role, expression expr to + * assert, and information about the assertion. The assertion expr is + * literally what should be asserted (it is already been processed with + * getAssertionExpr above). This may set a flag in the parser to mark + * that we have asserted a conjecture. + */ + Command* makeAssertCommand(FormulaRole fr, + api::Term expr, + bool cnf, + bool inUnsatCore); /** Ugly hack because I don't know how to return an expression from a token */ - Expr d_tmp_expr; + api::Term d_tmp_expr; /** Push a new stream in the lexer. When EOF is reached the previous stream is reused */ void includeFile(std::string fileName); /** Check a TPTP let binding for well-formedness. */ - void checkLetBinding(const std::vector& bvlist, Expr lhs, Expr rhs, + void checkLetBinding(const std::vector& bvlist, + api::Term lhs, + api::Term rhs, bool formula); /** * This converts a ParseOp to expression, assuming it is a standalone term. @@ -151,7 +157,7 @@ class Tptp : public Parser { * There are three cases in TPTP: either p already has an expression, in which * case this function just returns it, or p has just a name or a builtin kind. */ - Expr parseOpToExpr(ParseOp& p); + api::Term parseOpToExpr(ParseOp& p); /** * Apply parse operator to list of arguments, and return the resulting * expression. @@ -168,21 +174,21 @@ class Tptp : public Parser { * been previously declared, which leads to a more convoluted processing than * what is necessary in parsing SMT-LIB. */ - Expr applyParseOp(ParseOp& p, std::vector& args); + api::Term applyParseOp(ParseOp& p, std::vector& args); private: void addArithmeticOperators(); // In CNF variable are implicitly binded // d_freevar collect them - std::vector< Expr > d_freeVar; - Expr d_rtu_op; - Expr d_stu_op; - Expr d_utr_op; - Expr d_uts_op; + std::vector d_freeVar; + api::Term d_rtu_op; + api::Term d_stu_op; + api::Term d_utr_op; + api::Term d_uts_op; // The set of expression that already have a bridge - std::unordered_set d_r_converted; - std::unordered_map d_distinct_objects; + std::unordered_set d_r_converted; + std::unordered_map d_distinct_objects; std::vector< pANTLR3_INPUT_STREAM > d_in_created; @@ -191,7 +197,7 @@ class Tptp : public Parser { std::string d_tptpDir; // the null expression - Expr d_nullExpr; + api::Term d_nullExpr; // hack to make output SZS ontology-compliant bool d_hasConjecture; @@ -206,12 +212,13 @@ namespace tptp { * Just exists to provide the uintptr_t constructor that ANTLR * requires. */ -struct myExpr : public CVC4::Expr { - myExpr() : CVC4::Expr() {} - myExpr(void*) : CVC4::Expr() {} - myExpr(const Expr& e) : CVC4::Expr(e) {} - myExpr(const myExpr& e) : CVC4::Expr(e) {} -};/* struct myExpr */ +struct myExpr : public CVC4::api::Term +{ + myExpr() : CVC4::api::Term() {} + myExpr(void*) : CVC4::api::Term() {} + myExpr(const CVC4::api::Term& e) : CVC4::api::Term(e) {} + myExpr(const myExpr& e) : CVC4::api::Term(e) {} +}; /* struct myExpr*/ enum NonAssoc { NA_IFF, diff --git a/src/parser/tptp/tptp_input.cpp b/src/parser/tptp/tptp_input.cpp index 6a4ec0e79..741650150 100644 --- a/src/parser/tptp/tptp_input.cpp +++ b/src/parser/tptp/tptp_input.cpp @@ -66,7 +66,7 @@ Command* TptpInput::parseCommand() { api::Term TptpInput::parseExpr() { - return api::Term(d_pTptpParser->parseExpr(d_pTptpParser)); + return d_pTptpParser->parseExpr(d_pTptpParser); } }/* CVC4::parser namespace */ diff --git a/test/unit/parser/parser_black.h b/test/unit/parser/parser_black.h index e00016f45..85b379ac0 100644 --- a/test/unit/parser/parser_black.h +++ b/test/unit/parser/parser_black.h @@ -45,21 +45,21 @@ class ParserBlack /* Set up declaration context for expr inputs */ virtual void setupContext(Parser& parser) { /* a, b, c: BOOLEAN */ - parser.mkVar("a", d_solver->getExprManager()->booleanType()); - parser.mkVar("b", d_solver->getExprManager()->booleanType()); - parser.mkVar("c", d_solver->getExprManager()->booleanType()); + parser.bindVar("a", d_solver->getBooleanSort()); + parser.bindVar("b", d_solver->getBooleanSort()); + parser.bindVar("c", d_solver->getBooleanSort()); /* t, u, v: TYPE */ - Type t = parser.mkSort("t"); - Type u = parser.mkSort("u"); - Type v = parser.mkSort("v"); + api::Sort t = parser.mkSort("t"); + api::Sort u = parser.mkSort("u"); + api::Sort v = parser.mkSort("v"); /* f : t->u; g: u->v; h: v->t; */ - parser.mkVar("f", d_solver->getExprManager()->mkFunctionType(t, u)); - parser.mkVar("g", d_solver->getExprManager()->mkFunctionType(u, v)); - parser.mkVar("h", d_solver->getExprManager()->mkFunctionType(v, t)); + parser.bindVar("f", d_solver->mkFunctionSort(t, u)); + parser.bindVar("g", d_solver->mkFunctionSort(u, v)); + parser.bindVar("h", d_solver->mkFunctionSort(v, t)); /* x:t; y:u; z:v; */ - parser.mkVar("x",t); - parser.mkVar("y",u); - parser.mkVar("z",v); + parser.bindVar("x", t); + parser.bindVar("y", u); + parser.bindVar("z", v); } void tryGoodInput(const string goodInput)