2008-01-11 14:42:14 +01:00
/*
2013-06-12 16:42:09 +02:00
* Copyright ( C ) 2007 - 2013 Dynare Team
2008-01-11 14:42:14 +01:00
*
* 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/>.
*/
2010-06-09 18:35:03 +02:00
2008-06-28 13:20:45 +02:00
# include <cstring>
2009-08-25 11:43:01 +02:00
# include <sstream>
2009-12-16 18:18:38 +01:00
# include "Interpreter.hh"
2009-08-25 11:43:01 +02:00
# define BIG 1.0e+8;
# define SMALL 1.0e-5;
2013-03-22 15:44:34 +01:00
///#define DEBUG
2007-11-21 00:27:30 +01:00
2010-02-05 12:05:21 +01:00
Interpreter : : ~ Interpreter ( )
{
}
2009-09-18 18:34:11 +02:00
Interpreter : : Interpreter ( double * params_arg , double * y_arg , double * ya_arg , double * x_arg , double * steady_y_arg , double * steady_x_arg ,
2013-03-22 15:44:34 +01:00
double * direction_arg , size_t y_size_arg ,
size_t nb_row_x_arg , size_t nb_row_xd_arg , int periods_arg , int y_kmin_arg , int y_kmax_arg ,
int maxit_arg_ , double solve_tolf_arg , size_t size_of_direction_arg , double slowc_arg , int y_decal_arg , double markowitz_c_arg ,
2010-12-31 16:37:34 +01:00
string & filename_arg , int minimal_solving_periods_arg , int stack_solve_algo_arg , int solve_algo_arg ,
2013-03-22 15:44:34 +01:00
bool global_temporary_terms_arg , bool print_arg , bool print_error_arg , mxArray * GlobalTemporaryTerms_arg ,
bool steady_state_arg , bool print_it_arg
# ifdef CUDA
, const int CUDA_device_arg , cublasHandle_t cublas_handle_arg , cusparseHandle_t cusparse_handle_arg , cusparseMatDescr_t descr_arg
# endif
)
2013-06-10 16:45:57 +02:00
: dynSparseMatrix ( y_size_arg , y_kmin_arg , y_kmax_arg , print_it_arg , steady_state_arg , periods_arg , minimal_solving_periods_arg , slowc_arg
2013-03-22 15:44:34 +01:00
# ifdef CUDA
, CUDA_device_arg , cublas_handle_arg , cusparse_handle_arg , descr_arg
# endif
)
2007-11-21 00:27:30 +01:00
{
2009-12-16 18:18:38 +01:00
params = params_arg ;
y = y_arg ;
ya = ya_arg ;
x = x_arg ;
2009-09-18 18:34:11 +02:00
steady_y = steady_y_arg ;
steady_x = steady_x_arg ;
2009-12-16 18:18:38 +01:00
direction = direction_arg ;
2013-03-22 15:44:34 +01:00
//y_size = y_size_arg;
2009-12-16 18:18:38 +01:00
nb_row_x = nb_row_x_arg ;
nb_row_xd = nb_row_xd_arg ;
periods = periods_arg ;
2013-03-22 15:44:34 +01:00
//y_kmax = y_kmax_arg;
//y_kmin = y_kmin_arg;
2009-12-16 18:18:38 +01:00
maxit_ = maxit_arg_ ;
solve_tolf = solve_tolf_arg ;
size_of_direction = size_of_direction_arg ;
slowc = slowc_arg ;
2009-07-10 17:10:11 +02:00
slowc_save = slowc ;
2009-12-16 18:18:38 +01:00
y_decal = y_decal_arg ;
markowitz_c = markowitz_c_arg ;
filename = filename_arg ;
T = NULL ;
2009-10-18 17:18:16 +02:00
minimal_solving_periods = minimal_solving_periods_arg ;
2010-07-23 11:20:24 +02:00
stack_solve_algo = stack_solve_algo_arg ;
solve_algo = solve_algo_arg ;
2010-12-31 16:37:34 +01:00
global_temporary_terms = global_temporary_terms_arg ;
print = print_arg ;
2011-01-14 19:22:29 +01:00
GlobalTemporaryTerms = GlobalTemporaryTerms_arg ;
2011-06-17 16:37:36 +02:00
print_error = print_error_arg ;
2013-03-22 15:44:34 +01:00
//steady_state = steady_state_arg;
//print_it = print_it_arg;
2010-01-22 17:42:08 +01:00
2009-08-25 11:43:01 +02:00
}
2007-11-21 00:27:30 +01:00
void
2013-03-22 15:44:34 +01:00
Interpreter : : evaluate_a_block ( /*const int size, const int type, string bin_basename, int block_num,
2010-07-23 11:20:24 +02:00
const bool is_linear , const int symbol_table_endo_nbr , const int Block_List_Max_Lag ,
2013-03-22 15:44:34 +01:00
const int Block_List_Max_Lead , const int u_count_int , int block */ )
2009-09-11 19:06:54 +02:00
{
2009-10-16 18:34:27 +02:00
it_code_type begining ;
2011-02-04 16:53:12 +01:00
2009-09-11 19:06:54 +02:00
switch ( type )
{
2009-12-16 18:18:38 +01:00
case EVALUATE_FORWARD :
if ( steady_state )
2010-10-11 19:21:32 +02:00
{
2013-03-22 15:44:34 +01:00
compute_block_time ( 0 , true , /*block_num, size, steady_state, */ false ) ;
2010-10-11 19:21:32 +02:00
if ( block > = 0 )
for ( int j = 0 ; j < size ; j + + )
residual [ j ] = y [ Block_Contain [ j ] . Variable ] - ya [ Block_Contain [ j ] . Variable ] ;
2011-01-31 12:30:16 +01:00
else
for ( int j = 0 ; j < size ; j + + )
2013-03-22 15:44:34 +01:00
residual [ Block_Contain [ j ] . Equation ] = y [ Block_Contain [ j ] . Variable ] - ya [ Block_Contain [ j ] . Variable ] ;
2011-02-04 16:53:12 +01:00
}
2009-12-16 18:18:38 +01:00
else
{
begining = it_code ;
for ( it_ = y_kmin ; it_ < periods + y_kmin ; it_ + + )
{
it_code = begining ;
Per_y_ = it_ * y_size ;
2013-03-22 15:44:34 +01:00
compute_block_time ( 0 , true , /*block_num, size, steady_state, */ false ) ;
2010-10-11 19:21:32 +02:00
if ( block > = 0 )
for ( int j = 0 ; j < size ; j + + )
residual [ it_ * size + j ] = y [ it_ * y_size + Block_Contain [ j ] . Variable ] - ya [ it_ * y_size + Block_Contain [ j ] . Variable ] ;
2011-01-31 12:30:16 +01:00
else
for ( int j = 0 ; j < size ; j + + )
residual [ it_ * size + Block_Contain [ j ] . Equation ] = y [ it_ * y_size + Block_Contain [ j ] . Variable ] - ya [ it_ * y_size + Block_Contain [ j ] . Variable ] ;
2009-12-16 18:18:38 +01:00
}
}
break ;
case SOLVE_FORWARD_SIMPLE :
g1 = ( double * ) mxMalloc ( size * size * sizeof ( double ) ) ;
r = ( double * ) mxMalloc ( size * sizeof ( double ) ) ;
2013-03-22 15:44:34 +01:00
if ( steady_state )
{
compute_block_time ( 0 , true , /*block_num, size, steady_state,*/ false ) ;
if ( block < 0 )
for ( int j = 0 ; j < size ; j + + )
residual [ Block_Contain [ j ] . Equation ] = r [ j ] ;
2010-10-11 19:21:32 +02:00
else
2013-03-22 15:44:34 +01:00
for ( int j = 0 ; j < size ; j + + )
residual [ j ] = r [ j ] ;
2009-12-16 18:18:38 +01:00
}
else
{
begining = it_code ;
for ( it_ = y_kmin ; it_ < periods + y_kmin ; it_ + + )
{
it_code = begining ;
Per_y_ = it_ * y_size ;
2013-03-22 15:44:34 +01:00
compute_block_time ( 0 , true , /*block_num, size, steady_state,*/ false ) ;
2010-10-11 19:21:32 +02:00
if ( block < 0 )
2013-03-22 15:44:34 +01:00
for ( int j = 0 ; j < size ; j + + )
residual [ Per_y_ + Block_Contain [ j ] . Equation ] = r [ j ] ;
2010-10-11 19:21:32 +02:00
else
2013-03-22 15:44:34 +01:00
for ( int j = 0 ; j < size ; j + + )
residual [ it_ * size + j ] = r [ j ] ;
2009-12-16 18:18:38 +01:00
}
}
mxFree ( g1 ) ;
mxFree ( r ) ;
break ;
case SOLVE_FORWARD_COMPLETE :
fixe_u ( & u , u_count_int , u_count_int ) ;
2013-03-22 15:44:34 +01:00
Read_SparseMatrix ( bin_base_name , size , 1 , 0 , 0 , false , stack_solve_algo , solve_algo ) ;
2010-11-20 15:45:15 +01:00
# ifdef DEBUG
2011-02-04 16:53:12 +01:00
mexPrintf ( " in SOLVE_FORWARD_COMPLETE r = mxMalloc(%d*sizeof(double)) \n " , size ) ;
2010-11-20 15:45:15 +01:00
# endif
2009-12-16 18:18:38 +01:00
r = ( double * ) mxMalloc ( size * sizeof ( double ) ) ;
if ( steady_state )
{
2013-03-22 15:44:34 +01:00
compute_block_time ( 0 , true , /*block_num, size, steady_state,*/ false ) ;
2010-10-11 19:21:32 +02:00
if ( block < 0 )
for ( int j = 0 ; j < size ; j + + )
2013-03-22 15:44:34 +01:00
residual [ Block_Contain [ j ] . Equation ] = r [ j ] ;
2010-10-11 19:21:32 +02:00
else
for ( int j = 0 ; j < size ; j + + )
residual [ j ] = r [ j ] ;
2009-12-16 18:18:38 +01:00
}
else
{
begining = it_code ;
for ( it_ = y_kmin ; it_ < periods + y_kmin ; it_ + + )
{
it_code = begining ;
Per_y_ = it_ * y_size ;
2013-03-22 15:44:34 +01:00
compute_block_time ( 0 , true , /*block_num, size, steady_state,*/ false ) ;
2010-10-11 19:21:32 +02:00
if ( block < 0 )
for ( int j = 0 ; j < size ; j + + )
2013-03-22 15:44:34 +01:00
residual [ it_ * y_size + Block_Contain [ j ] . Equation ] = r [ j ] ;
2010-10-11 19:21:32 +02:00
else
for ( int j = 0 ; j < size ; j + + )
residual [ it_ * size + j ] = r [ j ] ;
2009-12-16 18:18:38 +01:00
}
}
mxFree ( r ) ;
break ;
case EVALUATE_BACKWARD :
if ( steady_state )
2011-01-31 12:30:16 +01:00
{
2013-03-22 15:44:34 +01:00
compute_block_time ( 0 , true , /*block_num, size, steady_state,*/ false ) ;
2011-01-31 12:30:16 +01:00
if ( block > = 0 )
2010-10-11 19:21:32 +02:00
for ( int j = 0 ; j < size ; j + + )
residual [ j ] = y [ Block_Contain [ j ] . Variable ] - ya [ Block_Contain [ j ] . Variable ] ;
2011-01-31 12:30:16 +01:00
else
for ( int j = 0 ; j < size ; j + + )
2013-03-22 15:44:34 +01:00
residual [ Block_Contain [ j ] . Equation ] = y [ Block_Contain [ j ] . Variable ] - ya [ Block_Contain [ j ] . Variable ] ;
2011-02-04 16:53:12 +01:00
}
2009-12-16 18:18:38 +01:00
else
{
begining = it_code ;
for ( it_ = periods + y_kmin - 1 ; it_ > = y_kmin ; it_ - - )
{
it_code = begining ;
Per_y_ = it_ * y_size ;
2013-03-22 15:44:34 +01:00
compute_block_time ( 0 , true , /*block_num, size, steady_state,*/ false ) ;
2010-10-11 19:21:32 +02:00
if ( block > = 0 )
for ( int j = 0 ; j < size ; j + + )
residual [ it_ * size + j ] = y [ it_ * y_size + Block_Contain [ j ] . Variable ] - ya [ it_ * y_size + Block_Contain [ j ] . Variable ] ;
2011-01-31 12:30:16 +01:00
else
for ( int j = 0 ; j < size ; j + + )
residual [ it_ * size + Block_Contain [ j ] . Equation ] = y [ it_ * y_size + Block_Contain [ j ] . Variable ] - ya [ it_ * y_size + Block_Contain [ j ] . Variable ] ;
2009-12-16 18:18:38 +01:00
}
}
break ;
case SOLVE_BACKWARD_SIMPLE :
g1 = ( double * ) mxMalloc ( size * size * sizeof ( double ) ) ;
r = ( double * ) mxMalloc ( size * sizeof ( double ) ) ;
if ( steady_state )
{
2013-03-22 15:44:34 +01:00
compute_block_time ( 0 , true , /*block_num, size, steady_state,*/ false ) ;
2010-10-11 19:21:32 +02:00
if ( block < 0 )
2013-03-22 15:44:34 +01:00
for ( int j = 0 ; j < size ; j + + )
residual [ Block_Contain [ j ] . Equation ] = r [ j ] ;
2010-10-11 19:21:32 +02:00
else
2013-03-22 15:44:34 +01:00
for ( int j = 0 ; j < size ; j + + )
residual [ j ] = r [ j ] ;
2009-12-16 18:18:38 +01:00
}
else
{
begining = it_code ;
for ( it_ = periods + y_kmin - 1 ; it_ > = y_kmin ; it_ - - )
{
it_code = begining ;
Per_y_ = it_ * y_size ;
2013-03-22 15:44:34 +01:00
compute_block_time ( 0 , true , /*block_num, size, steady_state,*/ false ) ;
2010-10-11 19:21:32 +02:00
if ( block < 0 )
2013-03-22 15:44:34 +01:00
for ( int j = 0 ; j < size ; j + + )
residual [ Per_y_ + Block_Contain [ j ] . Equation ] = r [ j ] ;
2010-10-11 19:21:32 +02:00
else
2013-03-22 15:44:34 +01:00
for ( int j = 0 ; j < size ; j + + )
residual [ it_ * size + j ] = r [ j ] ;
2009-12-16 18:18:38 +01:00
}
}
mxFree ( g1 ) ;
mxFree ( r ) ;
break ;
case SOLVE_BACKWARD_COMPLETE :
fixe_u ( & u , u_count_int , u_count_int ) ;
2013-03-22 15:44:34 +01:00
Read_SparseMatrix ( bin_base_name , size , 1 , 0 , 0 , false , stack_solve_algo , solve_algo ) ;
2009-12-16 18:18:38 +01:00
r = ( double * ) mxMalloc ( size * sizeof ( double ) ) ;
if ( steady_state )
{
2013-03-22 15:44:34 +01:00
compute_block_time ( 0 , true , /*block_num, size, steady_state,*/ false ) ;
2010-10-11 19:21:32 +02:00
if ( block < 0 )
for ( int j = 0 ; j < size ; j + + )
2013-03-22 15:44:34 +01:00
residual [ Block_Contain [ j ] . Equation ] = r [ j ] ;
2010-10-11 19:21:32 +02:00
else
for ( int j = 0 ; j < size ; j + + )
residual [ j ] = r [ j ] ;
2009-12-16 18:18:38 +01:00
}
else
{
begining = it_code ;
for ( it_ = periods + y_kmin - 1 ; it_ > = y_kmin ; it_ - - )
{
it_code = begining ;
Per_y_ = it_ * y_size ;
2013-03-22 15:44:34 +01:00
compute_block_time ( 0 , true , /*block_num, size, steady_state, */ false ) ;
2010-10-11 19:21:32 +02:00
if ( block < 0 )
for ( int j = 0 ; j < size ; j + + )
2013-03-22 15:44:34 +01:00
residual [ Per_y_ + Block_Contain [ j ] . Equation ] = r [ j ] ;
2010-10-11 19:21:32 +02:00
else
for ( int j = 0 ; j < size ; j + + )
residual [ it_ * size + j ] = r [ j ] ;
2009-12-16 18:18:38 +01:00
}
}
mxFree ( r ) ;
break ;
case SOLVE_TWO_BOUNDARIES_SIMPLE :
case SOLVE_TWO_BOUNDARIES_COMPLETE :
fixe_u ( & u , u_count_int , u_count_int ) ;
2013-03-22 15:44:34 +01:00
Read_SparseMatrix ( bin_base_name , size , periods , y_kmin , y_kmax , true , stack_solve_algo , solve_algo ) ;
2009-12-16 18:18:38 +01:00
u_count = u_count_int * ( periods + y_kmax + y_kmin ) ;
r = ( double * ) mxMalloc ( size * sizeof ( double ) ) ;
begining = it_code ;
for ( it_ = y_kmin ; it_ < periods + y_kmin ; it_ + + )
{
Per_u_ = ( it_ - y_kmin ) * u_count_int ;
Per_y_ = it_ * y_size ;
it_code = begining ;
2013-03-22 15:44:34 +01:00
compute_block_time ( Per_u_ , true , /*block_num, size, steady_state,*/ false ) ;
2010-10-11 19:21:32 +02:00
if ( block < 0 )
for ( int j = 0 ; j < size ; j + + )
2013-03-22 15:44:34 +01:00
residual [ it_ * y_size + Block_Contain [ j ] . Equation ] = r [ j ] ;
2010-10-11 19:21:32 +02:00
else
for ( int j = 0 ; j < size ; j + + )
residual [ it_ * size + j ] = r [ j ] ;
2009-12-16 18:18:38 +01:00
}
mxFree ( r ) ;
break ;
2009-09-11 19:06:54 +02:00
}
}
2012-03-06 11:03:13 +01:00
2010-09-24 12:52:58 +02:00
int
2013-03-22 15:44:34 +01:00
Interpreter : : simulate_a_block ( )
2007-11-21 00:27:30 +01:00
{
2009-10-16 18:34:27 +02:00
it_code_type begining ;
bool cvg ;
2007-11-21 00:27:30 +01:00
double * y_save ;
2010-07-23 11:20:24 +02:00
# ifdef DEBUG
2013-03-22 15:44:34 +01:00
mexPrintf ( " simulate_a_block type = %d, periods=%d, y_kmin=%d, y_kmax=%d \n " , type , periods , y_kmin , y_kmax ) ;
mexEvalString ( " drawnow; " ) ;
2010-07-23 11:20:24 +02:00
# endif
2007-11-21 00:27:30 +01:00
switch ( type )
{
2009-12-16 18:18:38 +01:00
case EVALUATE_FORWARD :
2010-07-23 11:20:24 +02:00
# ifdef DEBUG
mexPrintf ( " EVALUATE_FORWARD \n " ) ;
2013-03-22 15:44:34 +01:00
mexEvalString ( " drawnow; " ) ;
2010-07-23 11:20:24 +02:00
# endif
2013-03-22 15:44:34 +01:00
evaluate_over_periods ( true ) ;
2009-12-16 18:18:38 +01:00
break ;
case EVALUATE_BACKWARD :
2010-07-23 11:20:24 +02:00
# ifdef DEBUG
mexPrintf ( " EVALUATE_BACKWARD \n " ) ;
2013-03-22 15:44:34 +01:00
mexEvalString ( " drawnow; " ) ;
2010-07-23 11:20:24 +02:00
# endif
2013-03-22 15:44:34 +01:00
evaluate_over_periods ( false ) ;
2009-12-16 18:18:38 +01:00
break ;
case SOLVE_FORWARD_SIMPLE :
2010-07-23 11:20:24 +02:00
# ifdef DEBUG
2011-02-04 16:53:12 +01:00
mexPrintf ( " SOLVE_FORWARD_SIMPLE size=%d \n " , size ) ;
2013-03-22 15:44:34 +01:00
mexEvalString ( " drawnow; " ) ;
2010-07-23 11:20:24 +02:00
# endif
2013-03-22 15:44:34 +01:00
solve_simple_over_periods ( true ) ;
2009-12-16 18:18:38 +01:00
break ;
case SOLVE_BACKWARD_SIMPLE :
2010-07-23 11:20:24 +02:00
# ifdef DEBUG
mexPrintf ( " SOLVE_BACKWARD_SIMPLE \n " ) ;
2013-03-22 15:44:34 +01:00
mexEvalString ( " drawnow; " ) ;
2010-07-23 11:20:24 +02:00
# endif
2013-03-22 15:44:34 +01:00
solve_simple_over_periods ( false ) ;
2009-12-16 18:18:38 +01:00
break ;
case SOLVE_FORWARD_COMPLETE :
2010-07-23 11:20:24 +02:00
# ifdef DEBUG
mexPrintf ( " SOLVE_FORWARD_COMPLETE \n " ) ;
2013-03-22 15:44:34 +01:00
mexEvalString ( " drawnow; " ) ;
2010-07-23 11:20:24 +02:00
# endif
2009-12-16 18:18:38 +01:00
fixe_u ( & u , u_count_int , u_count_int ) ;
2013-03-22 15:44:34 +01:00
Read_SparseMatrix ( bin_base_name , size , 1 , 0 , 0 , false , stack_solve_algo , solve_algo ) ;
start_code = it_code ;
2009-12-16 18:18:38 +01:00
Per_u_ = 0 ;
2012-03-06 11:03:13 +01:00
2013-03-22 15:44:34 +01:00
Simulate_Newton_One_Boundary ( true ) ;
mxFree ( u ) ;
2009-12-16 18:18:38 +01:00
mxFree ( index_equa ) ;
mxFree ( index_vara ) ;
memset ( direction , 0 , size_of_direction ) ;
2013-03-22 15:44:34 +01:00
End_Solver ( ) ;
2009-12-16 18:18:38 +01:00
break ;
case SOLVE_BACKWARD_COMPLETE :
2010-07-23 11:20:24 +02:00
# ifdef DEBUG
mexPrintf ( " SOLVE_BACKWARD_COMPLETE \n " ) ;
2013-03-22 15:44:34 +01:00
mexEvalString ( " drawnow; " ) ;
2010-07-23 11:20:24 +02:00
# endif
2009-12-16 18:18:38 +01:00
fixe_u ( & u , u_count_int , u_count_int ) ;
2013-03-22 15:44:34 +01:00
Read_SparseMatrix ( bin_base_name , size , 1 , 0 , 0 , false , stack_solve_algo , solve_algo ) ;
start_code = it_code ;
Per_u_ = 0 ;
Simulate_Newton_One_Boundary ( false ) ;
2009-12-16 18:18:38 +01:00
mxFree ( index_equa ) ;
mxFree ( index_vara ) ;
memset ( direction , 0 , size_of_direction ) ;
mxFree ( u ) ;
2013-03-22 15:44:34 +01:00
End_Solver ( ) ;
2009-12-16 18:18:38 +01:00
break ;
case SOLVE_TWO_BOUNDARIES_SIMPLE :
case SOLVE_TWO_BOUNDARIES_COMPLETE :
2010-07-23 11:20:24 +02:00
# ifdef DEBUG
mexPrintf ( " SOLVE_TWO_BOUNDARIES \n " ) ;
2013-03-22 15:44:34 +01:00
mexEvalString ( " drawnow; " ) ;
2010-07-23 11:20:24 +02:00
# endif
2009-12-16 18:18:38 +01:00
if ( steady_state )
{
mexPrintf ( " SOLVE_TWO_BOUNDARIES in a steady state model: impossible case \n " ) ;
2010-09-24 12:52:58 +02:00
return ERROR_ON_EXIT ;
2009-12-16 18:18:38 +01:00
}
fixe_u ( & u , u_count_int , u_count_int ) ;
2013-03-22 15:44:34 +01:00
Read_SparseMatrix ( bin_base_name , size , periods , y_kmin , y_kmax , true , stack_solve_algo , solve_algo ) ;
2009-12-16 18:18:38 +01:00
u_count = u_count_int * ( periods + y_kmax + y_kmin ) ;
r = ( double * ) mxMalloc ( size * sizeof ( double ) ) ;
2013-03-22 15:44:34 +01:00
res = ( double * ) mxMalloc ( size * periods * sizeof ( double ) ) ;
2009-12-16 18:18:38 +01:00
y_save = ( double * ) mxMalloc ( y_size * sizeof ( double ) * ( periods + y_kmax + y_kmin ) ) ;
2013-03-22 15:44:34 +01:00
start_code = it_code ;
2009-12-16 18:18:38 +01:00
iter = 0 ;
if ( ! is_linear )
{
cvg = false ;
2010-02-06 15:07:56 +01:00
glambda2 = g0 = very_big ;
try_at_iteration = 0 ;
2009-12-16 18:18:38 +01:00
int u_count_saved = u_count ;
while ( ! ( cvg | | ( iter > maxit_ ) ) )
{
res2 = 0 ;
res1 = 0 ;
max_res = 0 ;
max_res_idx = 0 ;
memcpy ( y_save , y , y_size * sizeof ( double ) * ( periods + y_kmax + y_kmin ) ) ;
2013-03-22 15:44:34 +01:00
compute_complete_2b ( false , & res1 , & res2 , & max_res , & max_res_idx ) ;
end_code = it_code ;
if ( ! ( isnan ( res1 ) | | isinf ( res1 ) ) )
2009-12-16 18:18:38 +01:00
cvg = ( max_res < solve_tolf ) ;
2013-03-22 15:44:34 +01:00
if ( isnan ( res1 ) | | isinf ( res1 ) | | ( stack_solve_algo = = 4 & & iter > 0 ) )
memcpy ( y , y_save , y_size * sizeof ( double ) * ( periods + y_kmax + y_kmin ) ) ;
2009-12-16 18:18:38 +01:00
u_count = u_count_saved ;
2010-02-06 15:07:56 +01:00
int prev_iter = iter ;
2013-03-22 15:44:34 +01:00
Simulate_Newton_Two_Boundaries ( block_num , symbol_table_endo_nbr , y_kmin , y_kmax , size , periods , cvg , minimal_solving_periods , stack_solve_algo , endo_name_length , P_endo_names ) ;
2009-12-16 18:18:38 +01:00
iter + + ;
2010-02-06 15:07:56 +01:00
if ( iter > prev_iter )
{
g0 = res2 ;
gp0 = - res2 ;
try_at_iteration = 0 ;
2010-09-17 09:57:38 +02:00
slowc_save = slowc ;
2010-02-06 15:07:56 +01:00
}
2009-12-16 18:18:38 +01:00
}
if ( ! cvg )
{
2010-09-24 12:52:58 +02:00
ostringstream tmp ;
2013-03-22 15:44:34 +01:00
tmp < < " in Solve two boundaries, convergence not achieved in block " < < block_num + 1 < < " , after " < < iter < < " iterations \n " ;
2010-09-24 12:52:58 +02:00
throw FatalExceptionHandling ( tmp . str ( ) ) ;
2009-12-16 18:18:38 +01:00
}
}
else
{
2010-07-23 11:20:24 +02:00
res1 = 0 ;
res2 = 0 ;
max_res = 0 ; max_res_idx = 0 ;
2013-03-22 15:44:34 +01:00
compute_complete_2b ( false , & res1 , & res2 , & max_res , & max_res_idx ) ;
end_code = it_code ;
2009-12-16 18:18:38 +01:00
cvg = false ;
2013-03-22 15:44:34 +01:00
Simulate_Newton_Two_Boundaries ( block_num , symbol_table_endo_nbr , y_kmin , y_kmax , size , periods , cvg , minimal_solving_periods , stack_solve_algo , endo_name_length , P_endo_names ) ;
2009-12-16 18:18:38 +01:00
}
2013-03-22 15:44:34 +01:00
it_code = end_code ;
2009-12-16 18:18:38 +01:00
mxFree ( r ) ;
mxFree ( y_save ) ;
mxFree ( u ) ;
mxFree ( index_vara ) ;
mxFree ( index_equa ) ;
2013-03-22 15:44:34 +01:00
mxFree ( res ) ;
2009-12-16 18:18:38 +01:00
memset ( direction , 0 , size_of_direction ) ;
2013-03-22 15:44:34 +01:00
End_Solver ( ) ;
2009-12-16 18:18:38 +01:00
break ;
default :
2010-09-24 12:52:58 +02:00
ostringstream tmp ;
tmp < < " in simulate_a_block, Unknown type = " < < type < < " \n " ;
throw FatalExceptionHandling ( tmp . str ( ) ) ;
return ERROR_ON_EXIT ;
2007-11-21 00:27:30 +01:00
}
2010-09-24 12:52:58 +02:00
return NO_ERROR_ON_EXIT ;
2007-11-21 00:27:30 +01:00
}
2010-12-31 16:37:34 +01:00
void
2013-03-22 15:44:34 +01:00
Interpreter : : print_a_block ( )
2010-12-31 16:37:34 +01:00
{
it_code_type begining ;
2013-03-22 15:44:34 +01:00
if ( block < 0 )
mexPrintf ( " \n Block %d \n " , block_num + 1 ) ;
else
mexPrintf ( " \n Block %d \n " , block + 1 ) ;
2010-12-31 16:37:34 +01:00
mexPrintf ( " ---------- \n " ) ;
if ( steady_state )
residual = vector < double > ( size ) ;
else
residual = vector < double > ( size * ( periods + y_kmin ) ) ;
bool go_on = true ;
bool space = false ;
while ( go_on )
{
if ( it_code - > first = = FENDBLOCK )
{
go_on = false ;
it_code + + ;
}
else
{
string s = print_expression ( it_code , false , size , block_num , steady_state , Per_u_ , it_ , it_code , false ) ;
if ( s = = " if (evaluate) " | | s = = " else " )
space = false ;
2011-02-04 16:53:12 +01:00
if ( s . length ( ) > 0 )
2010-12-31 16:37:34 +01:00
{
if ( space )
2011-02-04 16:53:12 +01:00
mexPrintf ( " %s \n " , s . c_str ( ) ) ;
2010-12-31 16:37:34 +01:00
else
2011-02-04 16:53:12 +01:00
mexPrintf ( " %s \n " , s . c_str ( ) ) ;
2010-12-31 16:37:34 +01:00
mexEvalString ( " drawnow; " ) ;
}
if ( s = = " if (evaluate) " | | s = = " else " )
space = true ;
}
}
}
2009-08-25 11:43:01 +02:00
bool
2013-03-22 15:44:34 +01:00
Interpreter : : compute_blocks ( string file_name , string bin_basename , bool evaluate , int block , int & nb_blocks )
2007-11-21 00:27:30 +01:00
{
2009-08-25 11:43:01 +02:00
bool result = true ;
2009-12-16 18:18:38 +01:00
2009-08-29 18:04:06 +02:00
int var ;
2009-12-16 18:18:38 +01:00
if ( steady_state )
2009-08-25 11:43:01 +02:00
file_name + = " _static " ;
2009-12-16 18:18:38 +01:00
else
file_name + = " _dynamic " ;
CodeLoad code ;
//First read and store in memory the code
2009-10-16 18:34:27 +02:00
code_liste = code . get_op_code ( file_name ) ;
2010-01-22 17:42:08 +01:00
EQN_block_number = code . get_block_number ( ) ;
2009-10-16 18:34:27 +02:00
if ( ! code_liste . size ( ) )
2007-11-21 00:27:30 +01:00
{
2010-09-24 12:52:58 +02:00
ostringstream tmp ;
tmp < < " in compute_blocks, " < < file_name . c_str ( ) < < " cannot be opened \n " ;
throw FatalExceptionHandling ( tmp . str ( ) ) ;
2007-11-21 00:27:30 +01:00
}
2011-02-04 16:53:12 +01:00
if ( block > = ( int ) code . get_block_number ( ) )
2010-10-11 19:21:32 +02:00
{
ostringstream tmp ;
2012-11-16 17:39:03 +01:00
tmp < < " in compute_blocks, input argument block = " < < block + 1 < < " is greater than the number of blocks in the model ( " < < code . get_block_number ( ) < < " see M_.block_structure_stat.block) \n " ;
2010-10-11 19:21:32 +02:00
throw FatalExceptionHandling ( tmp . str ( ) ) ;
}
2007-11-21 00:27:30 +01:00
//The big loop on intructions
2009-12-16 18:18:38 +01:00
Block_Count = - 1 ;
bool go_on = true ;
2010-10-11 19:21:32 +02:00
2009-10-16 18:34:27 +02:00
it_code = code_liste . begin ( ) ;
2009-12-16 18:18:38 +01:00
it_code_type Init_Code = it_code ;
2011-01-31 12:30:16 +01:00
if ( block < 0 )
{
if ( steady_state )
residual = vector < double > ( y_size ) ;
else
residual = vector < double > ( y_size * ( periods + y_kmin ) ) ;
}
2011-02-04 16:53:12 +01:00
2007-11-21 00:27:30 +01:00
while ( go_on )
{
2009-10-16 18:34:27 +02:00
switch ( it_code - > first )
2007-11-21 00:27:30 +01:00
{
2009-12-16 18:18:38 +01:00
case FBEGINBLOCK :
Block_Count + + ;
2009-10-16 18:34:27 +02:00
# ifdef DEBUG
2010-10-11 19:21:32 +02:00
mexPrintf ( " --------------------------------------------------------- \n " ) ;
if ( block < 0 )
2011-02-02 00:31:37 +01:00
mexPrintf ( " FBEGINBLOCK Block_Count=%d \n " , Block_Count + 1 ) ;
2010-10-11 19:21:32 +02:00
else
2011-02-02 00:31:37 +01:00
mexPrintf ( " FBEGINBLOCK block=%d \n " , block + 1 ) ;
2009-10-16 18:34:27 +02:00
# endif
2009-12-16 18:18:38 +01:00
//it's a new block
{
FBEGINBLOCK_ * fb = ( FBEGINBLOCK_ * ) it_code - > second ;
Block_Contain = fb - > get_Block_Contain ( ) ;
2009-10-16 18:34:27 +02:00
it_code + + ;
2013-03-22 15:44:34 +01:00
set_block ( fb - > get_size ( ) , fb - > get_type ( ) , file_name , bin_basename , Block_Count , fb - > get_is_linear ( ) , fb - > get_endo_nbr ( ) , fb - > get_Max_Lag ( ) , fb - > get_Max_Lead ( ) , fb - > get_u_count_int ( ) , block ) ;
2010-12-31 16:37:34 +01:00
if ( print )
2013-03-22 15:44:34 +01:00
print_a_block ( ) ;
2010-12-31 16:37:34 +01:00
else if ( evaluate )
2010-07-23 11:20:24 +02:00
{
2010-11-20 15:45:15 +01:00
# ifdef DEBUG
2011-02-04 16:53:12 +01:00
mexPrintf ( " jacobian_block=mxCreateDoubleMatrix(%d, %d, mxREAL) \n " , fb - > get_size ( ) , fb - > get_nb_col_jacob ( ) ) ;
2010-11-20 15:45:15 +01:00
# endif
2011-02-04 16:53:12 +01:00
jacobian_block . push_back ( mxCreateDoubleMatrix ( fb - > get_size ( ) , fb - > get_nb_col_jacob ( ) , mxREAL ) ) ;
2010-07-23 11:20:24 +02:00
if ( ! steady_state )
{
2010-11-20 15:45:15 +01:00
# ifdef DEBUG
2011-02-04 16:53:12 +01:00
mexPrintf ( " allocates jacobian_exo_block( %d, %d, mxREAL) \n " , fb - > get_size ( ) , fb - > get_exo_size ( ) ) ;
2010-11-20 15:45:15 +01:00
# endif
2014-12-17 09:37:43 +01:00
jacobian_exo_block . push_back ( mxCreateDoubleMatrix ( fb - > get_size ( ) , fb - > get_nb_col_exo_jacob ( ) , mxREAL ) ) ;
jacobian_det_exo_block . push_back ( mxCreateDoubleMatrix ( fb - > get_size ( ) , fb - > get_nb_col_det_exo_jacob ( ) , mxREAL ) ) ;
2011-02-04 16:53:12 +01:00
jacobian_other_endo_block . push_back ( mxCreateDoubleMatrix ( fb - > get_size ( ) , fb - > get_nb_col_other_endo_jacob ( ) , mxREAL ) ) ;
2010-07-23 11:20:24 +02:00
}
2011-01-31 12:30:16 +01:00
if ( block > = 0 )
{
if ( steady_state )
residual = vector < double > ( fb - > get_size ( ) ) ;
else
residual = vector < double > ( fb - > get_size ( ) * ( periods + y_kmin ) ) ;
}
2013-03-22 15:44:34 +01:00
evaluate_a_block ( ) ;
2010-07-23 11:20:24 +02:00
}
2009-12-16 18:18:38 +01:00
else
2010-09-24 12:52:58 +02:00
{
2010-11-20 15:45:15 +01:00
# ifdef DEBUG
2014-12-17 09:37:43 +01:00
mexPrintf ( " endo in Block_Count=%d, block=%d, type=%d, steady_state=%d, print_it=%d, Block_Count=%d, fb->get_is_linear()=%d, fb->get_endo_nbr()=%d, fb->get_Max_Lag()=%d, fb->get_Max_Lead()=%d, fb->get_u_count_int()=%d \n " ,
Block_Count , fb - > get_size ( ) , fb - > get_type ( ) , steady_state , print_it , Block_Count , fb - > get_is_linear ( ) , fb - > get_endo_nbr ( ) , fb - > get_Max_Lag ( ) , fb - > get_Max_Lead ( ) , fb - > get_u_count_int ( ) ) ;
2010-11-20 15:45:15 +01:00
# endif
2013-03-22 15:44:34 +01:00
result = simulate_a_block ( ) ;
2010-09-24 12:52:58 +02:00
if ( result = = ERROR_ON_EXIT )
return ERROR_ON_EXIT ;
}
2009-12-16 18:18:38 +01:00
delete fb ;
}
2010-10-11 19:21:32 +02:00
if ( block > = 0 )
2010-12-17 17:17:40 +01:00
{
go_on = false ;
}
2009-12-16 18:18:38 +01:00
break ;
case FEND :
# ifdef DEBUG
mexPrintf ( " FEND \n " ) ;
# endif
go_on = false ;
it_code + + ;
break ;
case FDIMT :
# ifdef DEBUG
mexPrintf ( " FDIMT size=%d \n " , ( ( FDIMT_ * ) it_code - > second ) - > get_size ( ) ) ;
# endif
var = ( ( FDIMT_ * ) it_code - > second ) - > get_size ( ) ;
if ( T )
mxFree ( T ) ;
T = ( double * ) mxMalloc ( var * ( periods + y_kmin + y_kmax ) * sizeof ( double ) ) ;
2010-10-11 19:21:32 +02:00
if ( block > = 0 )
{
it_code = code_liste . begin ( ) + code . get_begin_block ( block ) ;
}
else
it_code + + ;
2009-12-16 18:18:38 +01:00
break ;
case FDIMST :
# ifdef DEBUG
2011-02-04 16:53:12 +01:00
mexPrintf ( " FDIMST size=%d \n " , ( ( FDIMST_ * ) it_code - > second ) - > get_size ( ) ) ;
2009-12-16 18:18:38 +01:00
# endif
var = ( ( FDIMST_ * ) it_code - > second ) - > get_size ( ) ;
if ( T )
mxFree ( T ) ;
2010-12-31 16:37:34 +01:00
if ( global_temporary_terms )
{
if ( GlobalTemporaryTerms = = NULL )
{
2011-02-04 16:53:12 +01:00
mexPrintf ( " GlobalTemporaryTerms is NULL \n " ) ; mexEvalString ( " drawnow; " ) ;
2010-12-31 16:37:34 +01:00
}
2011-02-04 16:53:12 +01:00
if ( var ! = ( int ) mxGetNumberOfElements ( GlobalTemporaryTerms ) )
2010-12-31 16:37:34 +01:00
GlobalTemporaryTerms = mxCreateDoubleMatrix ( var , 1 , mxREAL ) ;
T = mxGetPr ( GlobalTemporaryTerms ) ;
}
else
T = ( double * ) mxMalloc ( var * sizeof ( double ) ) ;
2011-01-14 19:22:29 +01:00
2010-10-11 19:21:32 +02:00
if ( block > = 0 )
it_code = code_liste . begin ( ) + code . get_begin_block ( block ) ;
else
it_code + + ;
2009-12-16 18:18:38 +01:00
break ;
default :
2010-09-24 12:52:58 +02:00
ostringstream tmp ;
2013-03-22 15:44:34 +01:00
tmp < < " in compute_blocks, unknown command " < < it_code - > first < < " (block= " < < Block_Count < < " ) \n " ;
2010-09-24 12:52:58 +02:00
throw FatalExceptionHandling ( tmp . str ( ) ) ;
2007-11-21 00:27:30 +01:00
}
}
2009-10-16 18:34:27 +02:00
mxFree ( Init_Code - > second ) ;
2010-07-23 11:20:24 +02:00
nb_blocks = Block_Count + 1 ;
2013-03-22 15:44:34 +01:00
if ( T & & ! global_temporary_terms )
2009-07-10 17:10:11 +02:00
mxFree ( T ) ;
2009-12-16 18:18:38 +01:00
return result ;
2007-11-21 00:27:30 +01:00
}