From 54f73e0864577001049d6337d236b1a68bba44a6 Mon Sep 17 00:00:00 2001 From: Houtan Bastani Date: Mon, 23 Dec 2019 16:22:23 +0100 Subject: [PATCH] Symbol List check pass: allow caller to specify the valid types of variables in a Symbol List dynare#1355 --- src/ComputingTasks.cc | 94 +++++++++++++++++++++++++++++++++++-------- src/ComputingTasks.hh | 3 +- src/SymbolList.cc | 75 ++++++++++++++++++++++++++++++++-- src/SymbolList.hh | 2 +- 4 files changed, 151 insertions(+), 23 deletions(-) diff --git a/src/ComputingTasks.cc b/src/ComputingTasks.cc index 5b8eaf55..86c712e9 100644 --- a/src/ComputingTasks.cc +++ b/src/ComputingTasks.cc @@ -646,7 +646,8 @@ StochSimulStatement::checkPass(ModFileStructure &mod_file_struct, WarningConsoli try { - symbol_list.checkPass(warnings); + const vector valid_symbol_list_types { SymbolType::endogenous }; + symbol_list.checkPass(warnings, valid_symbol_list_types); } catch (SymbolList::SymbolListException &e) { @@ -699,7 +700,8 @@ ForecastStatement::checkPass(ModFileStructure &mod_file_struct, WarningConsolida { try { - symbol_list.checkPass(warnings); + const vector valid_symbol_list_types { SymbolType::endogenous }; + symbol_list.checkPass(warnings, valid_symbol_list_types); } catch (SymbolList::SymbolListException &e) { @@ -989,7 +991,8 @@ RamseyPolicyStatement::checkPass(ModFileStructure &mod_file_struct, WarningConso try { - symbol_list.checkPass(warnings); + const vector valid_symbol_list_types { SymbolType::endogenous }; + symbol_list.checkPass(warnings, valid_symbol_list_types); } catch (SymbolList::SymbolListException &e) { @@ -1093,7 +1096,8 @@ DiscretionaryPolicyStatement::checkPass(ModFileStructure &mod_file_struct, Warni try { - symbol_list.checkPass(warnings); + const vector valid_symbol_list_types { SymbolType::endogenous }; + symbol_list.checkPass(warnings, valid_symbol_list_types); } catch (SymbolList::SymbolListException &e) { @@ -1214,7 +1218,8 @@ EstimationStatement::checkPass(ModFileStructure &mod_file_struct, WarningConsoli try { - symbol_list.checkPass(warnings); + const vector valid_symbol_list_types { SymbolType::endogenous }; + symbol_list.checkPass(warnings, valid_symbol_list_types); } catch (SymbolList::SymbolListException &e) { @@ -1318,6 +1323,22 @@ RplotStatement::RplotStatement(SymbolList symbol_list_arg) : { } +void +RplotStatement::checkPass(ModFileStructure &mod_file_struct, WarningConsolidation &warnings) +{ + try + { + const vector valid_symbol_list_types { SymbolType::endogenous, + SymbolType::exogenous}; + symbol_list.checkPass(warnings, valid_symbol_list_types); + } + catch (SymbolList::SymbolListException &e) + { + cerr << "ERROR: rplot: " << e.message << endl; + exit(EXIT_FAILURE); + } +} + void RplotStatement::writeOutput(ostream &output, const string &basename, bool minimal_workspace) const { @@ -1886,6 +1907,17 @@ OsrParamsStatement::checkPass(ModFileStructure &mod_file_struct, WarningConsolid if (mod_file_struct.osr_params_present) cerr << "WARNING: You have more than one osr_params statement in the .mod file." << endl; mod_file_struct.osr_params_present = true; + + try + { + const vector valid_symbol_list_types { SymbolType::parameter }; + symbol_list.checkPass(warnings, valid_symbol_list_types); + } + catch (SymbolList::SymbolListException &e) + { + cerr << "ERROR: osr: " << e.message << endl; + exit(EXIT_FAILURE); + } } void @@ -1994,7 +2026,8 @@ OsrStatement::checkPass(ModFileStructure &mod_file_struct, WarningConsolidation try { - symbol_list.checkPass(warnings); + const vector valid_symbol_list_types { SymbolType::endogenous }; + symbol_list.checkPass(warnings, valid_symbol_list_types); } catch (SymbolList::SymbolListException &e) { @@ -2120,7 +2153,8 @@ DynaSaveStatement::checkPass(ModFileStructure &mod_file_struct, WarningConsolida { try { - symbol_list.checkPass(warnings); + const vector valid_symbol_list_types { SymbolType::endogenous }; + symbol_list.checkPass(warnings, valid_symbol_list_types); } catch (SymbolList::SymbolListException &e) { @@ -2162,7 +2196,8 @@ DynaTypeStatement::checkPass(ModFileStructure &mod_file_struct, WarningConsolida { try { - symbol_list.checkPass(warnings); + const vector valid_symbol_list_types { SymbolType::endogenous }; + symbol_list.checkPass(warnings, valid_symbol_list_types); } catch (SymbolList::SymbolListException &e) { @@ -2561,7 +2596,8 @@ MSSBVARIrfStatement::checkPass(ModFileStructure &mod_file_struct, WarningConsoli try { - symbol_list.checkPass(warnings); + const vector valid_symbol_list_types { SymbolType::endogenous }; + symbol_list.checkPass(warnings, valid_symbol_list_types); } catch (SymbolList::SymbolListException &e) { @@ -2838,7 +2874,8 @@ ShockDecompositionStatement::checkPass(ModFileStructure &mod_file_struct, Warnin try { - symbol_list.checkPass(warnings); + const vector valid_symbol_list_types { SymbolType::endogenous }; + symbol_list.checkPass(warnings, valid_symbol_list_types); } catch (SymbolList::SymbolListException &e) { @@ -2888,7 +2925,8 @@ RealtimeShockDecompositionStatement::checkPass(ModFileStructure &mod_file_struct try { - symbol_list.checkPass(warnings); + const vector valid_symbol_list_types { SymbolType::endogenous }; + symbol_list.checkPass(warnings, valid_symbol_list_types); } catch (SymbolList::SymbolListException &e) { @@ -2929,6 +2967,22 @@ PlotShockDecompositionStatement::PlotShockDecompositionStatement(SymbolList symb { } +void +PlotShockDecompositionStatement::checkPass(ModFileStructure &mod_file_struct, WarningConsolidation &warnings) +{ + try + { + const vector valid_symbol_list_types { SymbolType::endogenous, + SymbolType::epilogue }; + symbol_list.checkPass(warnings, valid_symbol_list_types); + } + catch (SymbolList::SymbolListException &e) + { + cerr << "ERROR: plot_shock_decomposition: " << e.message << endl; + exit(EXIT_FAILURE); + } +} + void PlotShockDecompositionStatement::writeOutput(ostream &output, const string &basename, bool minimal_workspace) const { @@ -2971,7 +3025,8 @@ InitialConditionDecompositionStatement::checkPass(ModFileStructure &mod_file_str try { - symbol_list.checkPass(warnings); + const vector valid_symbol_list_types { SymbolType::endogenous }; + symbol_list.checkPass(warnings, valid_symbol_list_types); } catch (SymbolList::SymbolListException &e) { @@ -3017,7 +3072,8 @@ SqueezeShockDecompositionStatement::checkPass(ModFileStructure &mod_file_struct, { try { - symbol_list.checkPass(warnings); + const vector valid_symbol_list_types { SymbolType::endogenous }; + symbol_list.checkPass(warnings, valid_symbol_list_types); } catch (SymbolList::SymbolListException &e) { @@ -3096,7 +3152,8 @@ PlotConditionalForecastStatement::checkPass(ModFileStructure &mod_file_struct, { try { - symbol_list.checkPass(warnings); + const vector valid_symbol_list_types { SymbolType::endogenous }; + symbol_list.checkPass(warnings, valid_symbol_list_types); } catch (SymbolList::SymbolListException &e) { @@ -4670,7 +4727,8 @@ CalibSmootherStatement::checkPass(ModFileStructure &mod_file_struct, WarningCons mod_file_struct.calib_smoother_present = true; try { - symbol_list.checkPass(warnings); + const vector valid_symbol_list_types { SymbolType::endogenous }; + symbol_list.checkPass(warnings, valid_symbol_list_types); } catch (SymbolList::SymbolListException &e) { @@ -4802,7 +4860,8 @@ GMMEstimationStatement::checkPass(ModFileStructure &mod_file_struct, WarningCons { try { - symbol_list.checkPass(warnings); + const vector valid_symbol_list_types { SymbolType::endogenous }; + symbol_list.checkPass(warnings, valid_symbol_list_types); } catch (SymbolList::SymbolListException &e) { @@ -4849,7 +4908,8 @@ SMMEstimationStatement::checkPass(ModFileStructure &mod_file_struct, WarningCons { try { - symbol_list.checkPass(warnings); + const vector valid_symbol_list_types { SymbolType::endogenous }; + symbol_list.checkPass(warnings, valid_symbol_list_types); } catch (SymbolList::SymbolListException &e) { diff --git a/src/ComputingTasks.hh b/src/ComputingTasks.hh index 4c0be196..09d2fef8 100644 --- a/src/ComputingTasks.hh +++ b/src/ComputingTasks.hh @@ -248,7 +248,6 @@ public: SymbolList symbol_list_arg, OptionsList options_list_arg); void checkPass(ModFileStructure &mod_file_struct, WarningConsolidation &warnings) override; - void checkRamseyPolicyList(); void writeOutput(ostream &output, const string &basename, bool minimal_workspace) const override; void writeJsonOutput(ostream &output) const override; }; @@ -279,6 +278,7 @@ private: const SymbolList symbol_list; public: explicit RplotStatement(SymbolList symbol_list_arg); + void checkPass(ModFileStructure &mod_file_struct, WarningConsolidation &warnings) override; void writeOutput(ostream &output, const string &basename, bool minimal_workspace) const override; void writeJsonOutput(ostream &output) const override; }; @@ -747,6 +747,7 @@ private: public: PlotShockDecompositionStatement(SymbolList symbol_list_arg, OptionsList options_list_arg); + void checkPass(ModFileStructure &mod_file_struct, WarningConsolidation &warnings) override; void writeOutput(ostream &output, const string &basename, bool minimal_workspace) const override; void writeJsonOutput(ostream &output) const override; }; diff --git a/src/SymbolList.cc b/src/SymbolList.cc index 52044a51..d21bf929 100644 --- a/src/SymbolList.cc +++ b/src/SymbolList.cc @@ -34,10 +34,21 @@ SymbolList::addSymbol(const string &symbol) } void -SymbolList::checkPass(WarningConsolidation &warnings) const noexcept(false) +SymbolList::checkPass(WarningConsolidation &warnings, + const vector &types) const noexcept(false) { + if (types.empty()) + return; + smatch m; - regex re("^(AUX_EXPECT_|AUX_ENDO_|MULT_)"); + string regex_str = "AUX_EXPECT_|MULT_"; + for (auto type : types) + if (type == SymbolType::endogenous) + { + regex_str += "|AUX_ENDO_"; + break; + } + regex re("^(" + regex_str +")"); for (const auto &symbol : symbols) { if (!symbol_table->exists(symbol)) @@ -53,8 +64,64 @@ SymbolList::checkPass(WarningConsolidation &warnings) const noexcept(false) throw SymbolListException{"Variable " + symbol + " was not declared."}; } - if (symbol_table->getType(symbol) != SymbolType::endogenous) - throw SymbolListException{"Variable " + symbol + " is not endogenous."}; + bool type_found = false; + for (auto type : types) + if (symbol_table->getType(symbol) == type) + { + type_found = true; + break; + } + if (!type_found) + { + string valid_types; + for (auto type : types) + switch(type) + { + case SymbolType::endogenous: + valid_types += "endogenous, "; + break; + case SymbolType::exogenous: + valid_types += "exogenous, "; + break; + case SymbolType::epilogue: + valid_types += "epilogue, "; + break; + case SymbolType::parameter: + valid_types += "parameter, "; + break; + case SymbolType::exogenousDet: + valid_types += "exogenousDet, "; + break; + case SymbolType::trend: + valid_types += "trend, "; + break; + case SymbolType::logTrend: + valid_types += "logTrend, "; + break; + case SymbolType::modFileLocalVariable: + valid_types += "modFileLocalVariable, "; + break; + case SymbolType::modelLocalVariable: + valid_types += "modelLocalVariable, "; + break; + case SymbolType::externalFunction: + valid_types += "externalFunction, "; + break; + case SymbolType::statementDeclaredVariable: + valid_types += "statementDeclaredVariable, "; + break; + case SymbolType::unusedEndogenous: + valid_types += "unusedEndogenous, "; + break; + case SymbolType::endogenousVAR: + valid_types += "endogenousVAR, "; + break; + case SymbolType::excludedVariable: + valid_types += "excludedVariable, "; + } + valid_types = valid_types.erase(valid_types.size()-2, 2); + throw SymbolListException{"Variable " + symbol + " is not one of {" + valid_types + "}"}; + } } } diff --git a/src/SymbolList.hh b/src/SymbolList.hh index 63c45e74..8b53cc37 100644 --- a/src/SymbolList.hh +++ b/src/SymbolList.hh @@ -54,7 +54,7 @@ public: //! Removed duplicate symbols void removeDuplicates(const string &dynare_command, WarningConsolidation &warnings); //! Check symbols to ensure variables have been declared and are endogenous - void checkPass(WarningConsolidation &warnings) const noexcept(false); + void checkPass(WarningConsolidation &warnings, const vector &types) const noexcept(false); //! Output content in Matlab format /*! Creates a string array for Matlab, stored in variable "varname" */ void writeOutput(const string &varname, ostream &output) const;