ModFile.cc 7.17 KB
Newer Older
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
/*
 * Copyright (C) 2006-2008 Dynare Team
 *
 * This file is part of Dynare.
 *
 * Dynare is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 *
 * Dynare is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with Dynare.  If not, see <http://www.gnu.org/licenses/>.
 */

20
#include <cstdlib>
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
#include <iostream>
#include <fstream>

#include "ModFile.hh"

ModFile::ModFile() : expressions_tree(symbol_table, num_constants),
                     model_tree(symbol_table, num_constants),
                     linear(false)
{
}

ModFile::~ModFile()
{
  for(vector<Statement *>::iterator it = statements.begin();
      it != statements.end(); it++)
    delete (*it);
}

void
ModFile::addStatement(Statement *st)
{
  statements.push_back(st);
}

void
ModFile::checkPass()
{
  for(vector<Statement *>::iterator it = statements.begin();
      it != statements.end(); it++)
    (*it)->checkPass(mod_file_struct);

52
53
54
55
  // If order option has not been set, default to 2
  if (!mod_file_struct.order_option)
    mod_file_struct.order_option = 2;

sebastien's avatar
sebastien committed
56
57
58
59
60
61
  bool stochastic_statement_present = mod_file_struct.stoch_simul_present
    || mod_file_struct.estimation_present
    || mod_file_struct.forecast_present
    || mod_file_struct.osr_present
    || mod_file_struct.ramsey_policy_present;

62
63
64
65
  // Allow empty model only when doing a standalone BVAR estimation
  if (model_tree.equation_number() == 0
      && (mod_file_struct.check_present
          || mod_file_struct.simul_present
sebastien's avatar
sebastien committed
66
67
68
          || stochastic_statement_present))
    {
      cerr << "ERROR: At least one model equation must be declared!" << endl;
69
      exit(EXIT_FAILURE);
sebastien's avatar
sebastien committed
70
71
    }

ferhat's avatar
ferhat committed
72
  if (mod_file_struct.simul_present && stochastic_statement_present && model_tree.mode==0)
73
    {
sebastien's avatar
sebastien committed
74
      cerr << "ERROR: A .mod file cannot contain both a simul command and one of {stoch_simul, estimation, forecast, osr, ramsey_policy}" << endl;
75
      exit(EXIT_FAILURE);
76
77
    }

78
79
80
81
82
83
84
85
86
  /*
    Enforce the same number of equations and endogenous, except in two cases:
    - ramsey_policy is used
    - a BVAR command is used and there is no equation (standalone BVAR estimation)
  */
  if (!mod_file_struct.ramsey_policy_present
      && !((mod_file_struct.bvar_density_present || mod_file_struct.bvar_forecast_present)
           && model_tree.equation_number() == 0)
      && (model_tree.equation_number() != symbol_table.endo_nbr))
87
    {
sebastien's avatar
sebastien committed
88
      cerr << "ERROR: There are " << model_tree.equation_number() << " equations but " << symbol_table.endo_nbr << " endogenous variables!" << endl;
89
      exit(EXIT_FAILURE);
90
91
92
93
    }
}

void
94
ModFile::computingPass(bool no_tmp_terms)
95
96
97
98
99
100
101
102
103
104
105
106
{
  // Mod file may have no equation (for example in a standalone BVAR estimation)
  if (model_tree.equation_number() > 0)
    {
      // Set things to compute
      if (mod_file_struct.simul_present)
        model_tree.computeJacobian = true;
      else
        {
          if (mod_file_struct.order_option < 1 || mod_file_struct.order_option > 3)
            {
              cerr << "Incorrect order option..." << endl;
107
              exit(EXIT_FAILURE);
108
109
110
111
112
113
114
115
            }
          model_tree.computeJacobianExo = true;
          if (mod_file_struct.order_option >= 2)
            model_tree.computeHessian = true;
          if (mod_file_struct.order_option == 3)
            model_tree.computeThirdDerivatives = true;
        }

116
      model_tree.computingPass(global_eval_context, no_tmp_terms);
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
    }

  for(vector<Statement *>::iterator it = statements.begin();
      it != statements.end(); it++)
    (*it)->computingPass();
}

void
ModFile::writeOutputFiles(const string &basename, bool clear_all) const
{
  ofstream mOutputFile;

  if (basename.size())
    {
      string fname(basename);
sebastien's avatar
sebastien committed
132
      fname += ".m";
133
134
135
      mOutputFile.open(fname.c_str(), ios::out | ios::binary);
      if (!mOutputFile.is_open())
        {
sebastien's avatar
sebastien committed
136
          cerr << "ERROR: Can't open file " << fname
137
               << " for writing" << endl;
138
          exit(EXIT_FAILURE);
139
140
141
142
        }
    }
  else
    {
sebastien's avatar
sebastien committed
143
      cerr << "ERROR: Missing file name" << endl;
144
      exit(EXIT_FAILURE);
145
146
    }

sebastien's avatar
sebastien committed
147
148
149
150
151
  mOutputFile << "%" << endl
              << "% Status : main Dynare file " << endl
              << "%" << endl
              << "% Warning : this file is generated automatically by Dynare" << endl
              << "%           from model file (.mod)" << endl << endl;
152
153
154
155
156
157
158
159
160

  if (clear_all)
    mOutputFile << "clear all" << endl;
  mOutputFile << "tic;" << endl;
  mOutputFile << "global M_ oo_ exedet_ exdet_ recur_ recurs_ " << endl;
  mOutputFile << "global options_ endval_" << endl;
  mOutputFile << "global ys0_ recurs0_ ex0_ ct_" << endl;
  mOutputFile << "options_ = [];" << endl;
  mOutputFile << "M_.fname = '" << basename << "';" << endl;
sebastien's avatar
sebastien committed
161
162
163
  mOutputFile << "%" << endl;
  mOutputFile << "% Some global variables initialization" << endl;
  mOutputFile << "%" << endl;
164
  mOutputFile << "global_initialization;" << endl;
165
166
167
168
169
  mOutputFile << "diary off;" << endl
              << "warning_old_state = warning;" << endl
              << "warning off;" << endl
              << "delete " << basename << ".log;" << endl
              << "warning warning_old_state" << endl;
170
  mOutputFile << "logname_ = '" << basename << ".log';" << endl;
171
  mOutputFile << "diary " << basename << ".log" << endl;
172
  mOutputFile << "options_.model_mode = " << model_tree.mode << ";\n";
173
174
175
176
177
178


  if (model_tree.equation_number() > 0)
    {
      if (model_tree.mode == eDLLMode)
        {
sebastien's avatar
sebastien committed
179
          mOutputFile << "if exist('" << basename << "_static.c')" << endl;
180
          mOutputFile << "   clear " << basename << "_static" << endl;
sebastien's avatar
sebastien committed
181
          mOutputFile << "   mex -O " << basename << "_static.c" << endl;
182
          mOutputFile << "end" << endl;
sebastien's avatar
sebastien committed
183
          mOutputFile << "if exist('" << basename << "_dynamic.c')" << endl;
184
          mOutputFile << "   clear " << basename << "_dynamic" << endl;
sebastien's avatar
sebastien committed
185
          mOutputFile << "   mex -O " << basename << "_dynamic.c" << endl;
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
          mOutputFile << "end" << endl;
        }
      else
        {
          mOutputFile << "erase_compiled_function('" + basename +"_static');" << endl;
          mOutputFile << "erase_compiled_function('" + basename +"_dynamic');" << endl;
        }
    }

  cout << "Processing outputs ..." << endl;

  symbol_table.writeOutput(mOutputFile);

  if (linear == 1)
    mOutputFile << "options_.linear = 1;" << endl;

  if (model_tree.equation_number() > 0)
    {
      model_tree.writeOutput(mOutputFile);
      model_tree.writeStaticFile(basename);
      model_tree.writeDynamicFile(basename);
    }

  // Print statements
  for(vector<Statement *>::const_iterator it = statements.begin();
      it != statements.end(); it++)
    (*it)->writeOutput(mOutputFile, basename);

214
  mOutputFile << "save('" << basename << "_results.mat', 'oo_');" << endl;
215
216
  mOutputFile << "diary off" << endl;

217
  mOutputFile << endl << "disp(['Total computing time : ' dynsec2hms(toc) ]);" << endl;
218
219
  mOutputFile.close();
}