1 /*
2  * Copyright © 2007-2019 Dynare Team
3  *
4  * This file is part of Dynare.
5  *
6  * Dynare is free software: you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation, either version 3 of the License, or
9  * (at your option) any later version.
10  *
11  * Dynare is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with Dynare.  If not, see <http://www.gnu.org/licenses/>.
18  */
19 
20 #ifndef _CODEINTERPRETER_HH
21 #define _CODEINTERPRETER_HH
22 //#define DEBUGL
23 
24 #include <fstream>
25 #include <cstring>
26 #include <utility>
27 #include <vector>
28 #ifdef LINBCG
29 # include "linbcg.hh"
30 #endif
31 #ifdef BYTE_CODE
32 # ifndef DEBUG_EX
33 #  include "mex.h"
34 # else
35 #  include "mex_interface.hh"
36 # endif
37 #endif
38 
39 using namespace std;
40 
41 const double near_zero{1e-12};
42 
43 /**
44  * \enum Tags
45  * \brief The differents flags of the bytecode
46  */
47 enum Tags
48   {
49    FLDZ, //!< Stores zero in the stack - 0 (0)
50    FLDC, //!< Stores a constant term in the stack - 1 (1)
51 
52    FDIMT, //!< Defines the number of temporary terms - dynamic context (the period has to be indicated) - 2 (2)
53    FDIMST, //!< Defines the number of temporary terms - static context (the period hasn't to be indicated) - 3  (3)
54    FLDT, //!< Stores a temporary term in the stack - dynamic context (the period has to be indicated) - 4 (4)
55    FLDST, //!< Stores a temporary term in the stack - static context (the period hasn't to be indicated) - 5 (5)
56    FSTPT, //!< Loads a temporary term from the stack - dynamic context (the period has to be indicated) - 6 (6)
57    FSTPST, //!< Loads a temporary term from the stack - static context (the period hasn't to be indicated) - 7 (7)
58 
59    FLDU, //!< Stores an element of the vector U in the stack - dynamic context (the period has to be indicated) - 8 (8)
60    FLDSU, //!< Stores an element of the vector U in the stack - static context (the period hasn't to be indicated) - 9 (9)
61    FSTPU, //!< Loads an element of the vector U from the stack - dynamic context (the period has to be indicated) - A (10)
62    FSTPSU, //!< Loads an element of the vector U from the stack - static context (the period hasn't to be indicated) - B (11)
63 
64    FLDV, //!< Stores a variable (described in SymbolType) in the stack - dynamic context (the period has to be indicated) - C (12)
65    FLDSV, //!< Stores a variable (described in SymbolType) in the stack - static context (the period hasn't to be indicated) - D (13)
66    FLDVS, //!< Stores a variable (described in SymbolType) in the stack - dynamic context but inside the STEADYSTATE function (the period hasn't to be indicated) - E (14)
67    FSTPV, //!< Loads a variable (described in SymbolType) from the stack - dynamic context (the period has to be indicated) - F (15)
68    FSTPSV, //!< Loads a variable (described in SymbolType) from the stack - static context (the period hasn't to be indicated) - 10 (16)
69 
70    FLDR, //!< Stores a residual in the stack - 11 (17)
71    FSTPR, //!< Loads a residual from the stack - 12 (18)
72 
73    FSTPG, //!< Loads a derivative from the stack - 13 (19)
74    FSTPG2, //!< Loads a derivative matrix for static model from the stack - 14 (20)
75    FSTPG3, //!< Loads a derivative matrix for a dynamic model from the stack - 15 (21)
76    FSTPG4, //!< Loads a second order derivative matrix for a dynamic model from the stack - 16 (22)
77 
78    FUNARY, //!< A Unary operator - 17 (23)
79    FBINARY, //!< A binary operator - 18 (24)
80    FTRINARY, //!< A trinary operator - 19 (25)
81 
82    FCUML, //!< Cumulates the result - 1A (26)
83 
84    FJMPIFEVAL, //!< Jump if evaluate = true - 1B (27)
85    FJMP, //!< Jump - 1C (28)
86 
87    FBEGINBLOCK, //!< Defines the begining of a model block - 1D (29)
88    FENDBLOCK, //!< Defines the end of a model block - 1E (30)
89    FENDEQU, //!< Defines the last equation of the block. For block that has to be solved, the derivatives appear just after this flag - 1F (31)
90    FEND, //!< Defines the end of the model code - 20 (32)
91 
92    FOK, //!< Used for debugging purpose - 21 (33)
93 
94    FNUMEXPR, //!< Store the expression type and references - 22 (34)
95 
96    FCALL, //!< Call an external function - 23 (35)
97    FPUSH, //!< Push a double in the stack - 24 (36)
98    FPOP, //!< Pop a double from the stack - 25 (37)
99    FLDTEF, //!< Stores the result of an external function in the stack - 26 (38)
100    FSTPTEF, //!< Loads the result of an external function from the stack- 27 (39)
101    FLDTEFD, //!< Stores the result of an external function in the stack - 28 (40)
102    FSTPTEFD, //!< Loads the result of an external function from the stack- 29 (41)
103    FLDTEFDD, //!< Stores the result of an external function in the stack - 28 (42)
104    FSTPTEFDD //!< Loads the result of an external function from the stack- 29 (43)
105 
106   };
107 
108 enum BlockType
109   {
110    SIMULTANS, //!< Simultaneous time separable block
111    PROLOGUE, //!< Prologue block (one equation at the beginning, later merged)
112    EPILOGUE, //!< Epilogue block (one equation at the beginning, later merged)
113    SIMULTAN //!< Simultaneous time unseparable block
114   };
115 
116 enum EquationType
117   {
118    E_UNKNOWN, //!< Unknown equation type
119    E_EVALUATE, //!< Simple evaluation, normalized variable on left-hand side
120    E_EVALUATE_S, //!< Simple evaluation, normalize using the first order derivative
121    E_SOLVE //!< No simple evaluation of the equation, it has to be solved
122   };
123 
124 enum BlockSimulationType
125   {
126    UNKNOWN, //!< Unknown simulation type
127    EVALUATE_FORWARD, //!< Simple evaluation, normalized variable on left-hand side, forward
128    EVALUATE_BACKWARD, //!< Simple evaluation, normalized variable on left-hand side, backward
129    SOLVE_FORWARD_SIMPLE, //!< Block of one equation, newton solver needed, forward
130    SOLVE_BACKWARD_SIMPLE, //!< Block of one equation, newton solver needed, backward
131    SOLVE_TWO_BOUNDARIES_SIMPLE, //!< Block of one equation, newton solver needed, forward & ackward
132    SOLVE_FORWARD_COMPLETE, //!< Block of several equations, newton solver needed, forward
133    SOLVE_BACKWARD_COMPLETE, //!< Block of several equations, newton solver needed, backward
134    SOLVE_TWO_BOUNDARIES_COMPLETE //!< Block of several equations, newton solver needed, forward and backwar
135   };
136 
137 //! Enumeration of possible symbol types
138 /*! Warning: do not to change existing values for 0 to 4: the values matter for homotopy_setup command */
139 enum class SymbolType
140   {
141    endogenous = 0, //!< Endogenous
142    exogenous = 1, //!< Exogenous
143    exogenousDet = 2, //!< Exogenous deterministic
144    parameter = 4, //!< Parameter
145    modelLocalVariable = 10, //!< Local variable whose scope is model (pound expression)
146    modFileLocalVariable = 11, //!< Local variable whose scope is mod file (model excluded)
147    externalFunction = 12, //!< External (user-defined) function
148    trend = 13, //!< Trend variable
149    statementDeclaredVariable = 14, //!< Local variable assigned within a Statement (see subsample statement for example)
150    logTrend = 15, //!< Log-trend variable
151    unusedEndogenous = 16, //!< Type to mark unused endogenous variables when `nostrict` option is passed
152    endogenousVAR = 17, //!< Variables declared in a var_model statement
153    epilogue = 18, //!< Variables created in epilogue block
154    excludedVariable = 19 //!< Type to use when an equation is excluded via include/exclude_eqs and the LHS variable is not used elsewhere in the model
155   };
156 
157 enum ExpressionType
158   {
159    TemporaryTerm,
160    ModelEquation,
161    FirstEndoDerivative,
162    FirstOtherEndoDerivative,
163    FirstExoDerivative,
164    FirstExodetDerivative,
165    FirstParamDerivative,
166    SecondEndoDerivative,
167    SecondExoDerivative,
168    SecondExodetDerivative,
169    SecondParamDerivative,
170    ThirdEndoDerivative,
171    ThirdExoDerivative,
172    ThirdExodetDerivative,
173    ThirdParamDerivative
174   };
175 
176 enum class UnaryOpcode
177   {
178    uminus,
179    exp,
180    log,
181    log10,
182    cos,
183    sin,
184    tan,
185    acos,
186    asin,
187    atan,
188    cosh,
189    sinh,
190    tanh,
191    acosh,
192    asinh,
193    atanh,
194    sqrt,
195    cbrt,
196    abs,
197    sign,
198    steadyState,
199    steadyStateParamDeriv, // for the derivative of the STEADY_STATE operator w.r.t. to a parameter
200    steadyStateParam2ndDeriv, // for the 2nd derivative of the STEADY_STATE operator w.r.t. to a parameter
201    expectation,
202    erf,
203    diff,
204    adl
205   };
206 
207 enum class BinaryOpcode
208   {
209    plus,
210    minus,
211    times,
212    divide,
213    power,
214    powerDeriv, // for the derivative of the power function (see trac ticket #78)
215    equal,
216    max,
217    min,
218    less,
219    greater,
220    lessEqual,
221    greaterEqual,
222    equalEqual,
223    different
224   };
225 
226 enum class TrinaryOpcode
227   {
228    normcdf,
229    normpdf
230   };
231 
232 enum class ExternalFunctionType
233   {
234    withoutDerivative,
235    withFirstDerivative,
236    withFirstAndSecondDerivative,
237    numericalFirstDerivative,
238    firstDerivative,
239    numericalSecondDerivative,
240    secondDerivative
241   };
242 
243 enum class PriorDistributions
244   {
245    noShape = 0,
246    beta = 1,
247    gamma = 2,
248    normal = 3,
249    invGamma = 4,
250    invGamma1 = 4,
251    uniform = 5,
252    invGamma2 = 6,
253    dirichlet = 7,
254    weibull = 8
255   };
256 
257 struct Block_contain_type
258 {
259   int Equation, Variable, Own_Derivative;
260 };
261 
262 #pragma pack(push, 1)
263 class TagWithoutArgument
264 {
265 protected:
266   uint8_t op_code;
267 public:
268   inline explicit
TagWithoutArgument(uint8_t op_code_arg)269   TagWithoutArgument(uint8_t op_code_arg) : op_code{op_code_arg}
270   {
271   };
272   inline void
write(ostream & CompileCode,unsigned int & instruction_number)273   write(ostream &CompileCode, unsigned int &instruction_number)
274   {
275     CompileCode.write(reinterpret_cast<char *>(this), sizeof(*this));
276     instruction_number++;
277   };
278 };
279 
280 template<typename T1>
281 class TagWithOneArgument
282 {
283 protected:
284   uint8_t op_code;
285   T1 arg1;
286 public:
287   inline explicit
TagWithOneArgument(uint8_t op_code_arg)288   TagWithOneArgument(uint8_t op_code_arg) : op_code{op_code_arg}
289   {
290   };
291   inline
TagWithOneArgument(uint8_t op_code_arg,T1 arg_arg1)292   TagWithOneArgument(uint8_t op_code_arg, T1 arg_arg1) : op_code{op_code_arg}, arg1{arg_arg1}
293   {
294   };
295   inline void
write(ostream & CompileCode,unsigned int & instruction_number)296   write(ostream &CompileCode, unsigned int &instruction_number)
297   {
298     CompileCode.write(reinterpret_cast<char *>(this), sizeof(TagWithOneArgument));
299     instruction_number++;
300   };
301 };
302 
303 template<typename T1, typename T2>
304 class TagWithTwoArguments
305 {
306 protected:
307   uint8_t op_code;
308   T1 arg1;
309   T2 arg2;
310 public:
311   inline explicit
TagWithTwoArguments(uint8_t op_code_arg)312   TagWithTwoArguments(uint8_t op_code_arg) : op_code{op_code_arg}
313   {
314   };
315   inline
TagWithTwoArguments(uint8_t op_code_arg,T1 arg_arg1,T2 arg_arg2)316   TagWithTwoArguments(uint8_t op_code_arg, T1 arg_arg1, T2 arg_arg2) : op_code{op_code_arg}, arg1{arg_arg1}, arg2{arg_arg2}
317   {
318   };
319   inline void
write(ostream & CompileCode,unsigned int & instruction_number)320   write(ostream &CompileCode, unsigned int &instruction_number)
321   {
322     CompileCode.write(reinterpret_cast<char *>(this), sizeof(*this));
323     instruction_number++;
324   };
325 };
326 
327 template<typename T1, typename T2, typename T3>
328 class TagWithThreeArguments
329 {
330 protected:
331   uint8_t op_code;
332   T1 arg1;
333   T2 arg2;
334   T3 arg3;
335 public:
336   inline explicit
TagWithThreeArguments(uint8_t op_code_arg)337   TagWithThreeArguments(uint8_t op_code_arg) : op_code{op_code_arg}
338   {
339   };
340   inline
TagWithThreeArguments(uint8_t op_code_arg,T1 arg_arg1,T2 arg_arg2,T3 arg_arg3)341   TagWithThreeArguments(uint8_t op_code_arg, T1 arg_arg1, T2 arg_arg2, T3 arg_arg3) : op_code{op_code_arg}, arg1{arg_arg1}, arg2{arg_arg2}, arg3{arg_arg3}
342   {
343   };
344   inline void
write(ostream & CompileCode,unsigned int & instruction_number)345   write(ostream &CompileCode, unsigned int &instruction_number)
346   {
347     CompileCode.write(reinterpret_cast<char *>(this), sizeof(*this));
348     instruction_number++;
349   };
350 };
351 
352 template<typename T1, typename T2, typename T3, typename T4>
353 class TagWithFourArguments
354 {
355 protected:
356   uint8_t op_code;
357   T1 arg1;
358   T2 arg2;
359   T3 arg3;
360   T4 arg4;
361 public:
362   inline explicit
TagWithFourArguments(uint8_t op_code_arg)363   TagWithFourArguments(uint8_t op_code_arg) : op_code{op_code_arg}
364   {
365   };
366   inline
TagWithFourArguments(uint8_t op_code_arg,T1 arg_arg1,T2 arg_arg2,T3 arg_arg3,T4 arg_arg4)367   TagWithFourArguments(uint8_t op_code_arg, T1 arg_arg1, T2 arg_arg2, T3 arg_arg3, T4 arg_arg4) : op_code{op_code_arg}, arg1{arg_arg1}, arg2{arg_arg2}, arg3{move(arg_arg3)}, arg4{arg_arg4}
368   {
369   };
370   inline void
write(ostream & CompileCode,unsigned int & instruction_number)371   write(ostream &CompileCode, unsigned int &instruction_number)
372   {
373     CompileCode.write(reinterpret_cast<char *>(this), sizeof(*this));
374     instruction_number++;
375   };
376 };
377 
378 class FLDZ_ : public TagWithoutArgument
379 {
380 public:
381   inline
FLDZ_()382   FLDZ_() : TagWithoutArgument{FLDZ}
383   {
384   };
385 };
386 
387 class FEND_ : public TagWithoutArgument
388 {
389 public:
390   inline
FEND_()391   FEND_() : TagWithoutArgument{FEND}
392   {
393   };
394 };
395 
396 class FENDBLOCK_ : public TagWithoutArgument
397 {
398 public:
399   inline
FENDBLOCK_()400   FENDBLOCK_() : TagWithoutArgument{FENDBLOCK}
401   {
402   };
403 };
404 
405 class FENDEQU_ : public TagWithoutArgument
406 {
407 public:
408   inline
FENDEQU_()409   FENDEQU_() : TagWithoutArgument{FENDEQU}
410   {
411   };
412 };
413 
414 class FCUML_ : public TagWithoutArgument
415 {
416 public:
417   inline
FCUML_()418   FCUML_() : TagWithoutArgument{FCUML}
419   {
420   };
421 };
422 
423 class FPUSH_ : public TagWithoutArgument
424 {
425 public:
426   inline
FPUSH_()427   FPUSH_() : TagWithoutArgument{FPUSH}
428   {
429   };
430 };
431 
432 class FPOP_ : public TagWithoutArgument
433 {
434 public:
435   inline
FPOP_()436   FPOP_() : TagWithoutArgument{FPOP}
437   {
438   };
439 };
440 
441 class FDIMT_ : public TagWithOneArgument<unsigned int>
442 {
443 public:
444   inline
FDIMT_()445   FDIMT_() : TagWithOneArgument<unsigned int>::TagWithOneArgument{FDIMT}
446   {
447   };
448   inline explicit
FDIMT_(unsigned int size_arg)449   FDIMT_(unsigned int size_arg) : TagWithOneArgument<unsigned int>::TagWithOneArgument{FDIMT, size_arg}
450   {
451   };
452   inline unsigned int
get_size()453   get_size()
454   {
455     return arg1;
456   };
457 };
458 
459 class FDIMST_ : public TagWithOneArgument<unsigned int>
460 {
461 public:
462   inline
FDIMST_()463   FDIMST_() : TagWithOneArgument<unsigned int>::TagWithOneArgument{FDIMST}
464   {
465   };
466   inline explicit
FDIMST_(const unsigned int size_arg)467   FDIMST_(const unsigned int size_arg) : TagWithOneArgument<unsigned int>::TagWithOneArgument{FDIMST, size_arg}
468   {
469   };
470   inline unsigned int
get_size()471   get_size()
472   {
473     return arg1;
474   };
475 };
476 
477 class FLDC_ : public TagWithOneArgument<double>
478 {
479 public:
480   inline
FLDC_()481   FLDC_() : TagWithOneArgument<double>::TagWithOneArgument{FLDC}
482   {
483   };
484   inline explicit
FLDC_(double value_arg)485   FLDC_(double value_arg) : TagWithOneArgument<double>::TagWithOneArgument{FLDC, value_arg}
486   {
487   };
488   inline double
get_value()489   get_value()
490   {
491     return arg1;
492   };
493 };
494 
495 class FLDU_ : public TagWithOneArgument<unsigned int>
496 {
497 public:
498   inline
FLDU_()499   FLDU_() : TagWithOneArgument<unsigned int>::TagWithOneArgument{FLDU}
500   {
501   };
502   inline explicit
FLDU_(unsigned int pos_arg)503   FLDU_(unsigned int pos_arg) : TagWithOneArgument<unsigned int>::TagWithOneArgument{FLDU, pos_arg}
504   {
505   };
506   inline unsigned int
get_pos()507   get_pos()
508   {
509     return arg1;
510   };
511 };
512 
513 class FLDSU_ : public TagWithOneArgument<unsigned int>
514 {
515 public:
516   inline
FLDSU_()517   FLDSU_() : TagWithOneArgument<unsigned int>::TagWithOneArgument{FLDSU}
518   {
519   };
520   inline explicit
FLDSU_(unsigned int pos_arg)521   FLDSU_(unsigned int pos_arg) : TagWithOneArgument<unsigned int>::TagWithOneArgument{FLDSU, pos_arg}
522   {
523   };
524   inline unsigned int
get_pos()525   get_pos()
526   {
527     return arg1;
528   };
529 };
530 
531 class FLDR_ : public TagWithOneArgument<unsigned int>
532 {
533 public:
534   inline
FLDR_()535   FLDR_() : TagWithOneArgument<unsigned int>::TagWithOneArgument{FLDR}
536   {
537   };
538   inline explicit
FLDR_(unsigned int pos_arg)539   FLDR_(unsigned int pos_arg) : TagWithOneArgument<unsigned int>::TagWithOneArgument{FLDR, pos_arg}
540   {
541   };
542   inline unsigned int
get_pos()543   get_pos()
544   {
545     return arg1;
546   };
547 };
548 
549 class FLDT_ : public TagWithOneArgument<unsigned int>
550 {
551 public:
552   inline
FLDT_()553   FLDT_() : TagWithOneArgument<unsigned int>::TagWithOneArgument{FLDT}
554   {
555   };
556   inline explicit
FLDT_(unsigned int pos_arg)557   FLDT_(unsigned int pos_arg) : TagWithOneArgument<unsigned int>::TagWithOneArgument{FLDT, pos_arg}
558   {
559   };
560   inline unsigned int
get_pos()561   get_pos()
562   {
563     return arg1;
564   };
565 };
566 
567 class FLDST_ : public TagWithOneArgument<unsigned int>
568 {
569 public:
570   inline
FLDST_()571   FLDST_() : TagWithOneArgument<unsigned int>::TagWithOneArgument{FLDST}
572   {
573   };
574   inline explicit
FLDST_(unsigned int pos_arg)575   FLDST_(unsigned int pos_arg) : TagWithOneArgument<unsigned int>::TagWithOneArgument{FLDST, pos_arg}
576   {
577   };
578   inline unsigned int
get_pos()579   get_pos()
580   {
581     return arg1;
582   };
583 };
584 
585 class FSTPT_ : public TagWithOneArgument<unsigned int>
586 {
587 public:
588   inline
FSTPT_()589   FSTPT_() : TagWithOneArgument<unsigned int>::TagWithOneArgument{FSTPT}
590   {
591   };
592   inline explicit
FSTPT_(unsigned int pos_arg)593   FSTPT_(unsigned int pos_arg) : TagWithOneArgument<unsigned int>::TagWithOneArgument{FSTPT, pos_arg}
594   {
595   };
596   inline unsigned int
get_pos()597   get_pos()
598   {
599     return arg1;
600   };
601 };
602 
603 class FSTPST_ : public TagWithOneArgument<unsigned int>
604 {
605 public:
606   inline
FSTPST_()607   FSTPST_() : TagWithOneArgument<unsigned int>::TagWithOneArgument{FSTPST}
608   {
609   };
610   inline explicit
FSTPST_(unsigned int pos_arg)611   FSTPST_(unsigned int pos_arg) : TagWithOneArgument<unsigned int>::TagWithOneArgument{FSTPST, pos_arg}
612   {
613   };
614   inline unsigned int
get_pos()615   get_pos()
616   {
617     return arg1;
618   };
619 };
620 
621 class FSTPR_ : public TagWithOneArgument<unsigned int>
622 {
623 public:
624   inline
FSTPR_()625   FSTPR_() : TagWithOneArgument<unsigned int>::TagWithOneArgument{FSTPR}
626   {
627   };
628   inline explicit
FSTPR_(unsigned int pos_arg)629   FSTPR_(unsigned int pos_arg) : TagWithOneArgument<unsigned int>::TagWithOneArgument{FSTPR, pos_arg}
630   {
631   };
632   inline unsigned int
get_pos()633   get_pos()
634   {
635     return arg1;
636   };
637 };
638 
639 class FSTPU_ : public TagWithOneArgument<unsigned int>
640 {
641 public:
642   inline
FSTPU_()643   FSTPU_() : TagWithOneArgument<unsigned int>::TagWithOneArgument{FSTPU}
644   {
645   };
646   inline explicit
FSTPU_(unsigned int pos_arg)647   FSTPU_(unsigned int pos_arg) : TagWithOneArgument<unsigned int>::TagWithOneArgument{FSTPU, pos_arg}
648   {
649   };
650   inline unsigned int
get_pos()651   get_pos()
652   {
653     return arg1;
654   };
655 };
656 
657 class FSTPSU_ : public TagWithOneArgument<unsigned int>
658 {
659 public:
660   inline
FSTPSU_()661   FSTPSU_() : TagWithOneArgument<unsigned int>::TagWithOneArgument{FSTPSU}
662   {
663   };
664   inline explicit
FSTPSU_(unsigned int pos_arg)665   FSTPSU_(unsigned int pos_arg) : TagWithOneArgument<unsigned int>::TagWithOneArgument{FSTPSU, pos_arg}
666   {
667   };
668   inline unsigned int
get_pos()669   get_pos()
670   {
671     return arg1;
672   };
673 };
674 
675 class FSTPG_ : public TagWithOneArgument<unsigned int>
676 {
677 public:
678   inline
FSTPG_()679   FSTPG_() : TagWithOneArgument<unsigned int>::TagWithOneArgument{FSTPG, 0}
680   {
681   };
682   inline explicit
FSTPG_(unsigned int pos_arg)683   FSTPG_(unsigned int pos_arg) : TagWithOneArgument<unsigned int>::TagWithOneArgument{FSTPG, pos_arg}
684   {
685   };
686   inline unsigned int
get_pos()687   get_pos()
688   {
689     return arg1;
690   };
691 };
692 
693 class FSTPG2_ : public TagWithTwoArguments<unsigned int, unsigned int>
694 {
695 public:
696   inline
FSTPG2_()697   FSTPG2_() : TagWithTwoArguments<unsigned int, unsigned int>::TagWithTwoArguments{FSTPG2, 0, 0}
698   {
699   };
700   inline
FSTPG2_(unsigned int pos_arg1,unsigned int pos_arg2)701   FSTPG2_(unsigned int pos_arg1, unsigned int pos_arg2) : TagWithTwoArguments<unsigned int, unsigned int>::TagWithTwoArguments{FSTPG2, pos_arg1, pos_arg2}
702   {
703   };
704   inline unsigned int
get_row()705   get_row()
706   {
707     return arg1;
708   };
709   inline unsigned int
get_col()710   get_col()
711   {
712     return arg2;
713   };
714 };
715 
716 class FSTPG3_ : public TagWithFourArguments<unsigned int, unsigned int, int, unsigned int>
717 {
718 public:
719   inline
FSTPG3_()720   FSTPG3_() : TagWithFourArguments<unsigned int, unsigned int, int, unsigned int>::TagWithFourArguments{FSTPG3, 0, 0, 0, 0}
721   {
722   };
723   inline
FSTPG3_(unsigned int pos_arg1,unsigned int pos_arg2,int pos_arg3,unsigned int pos_arg4)724   FSTPG3_(unsigned int pos_arg1, unsigned int pos_arg2, int pos_arg3, unsigned int pos_arg4) : TagWithFourArguments<unsigned int, unsigned int, int, unsigned int>::TagWithFourArguments{FSTPG3, pos_arg1, pos_arg2, pos_arg3, pos_arg4}
725   {
726   };
727   inline unsigned int
get_row()728   get_row()
729   {
730     return arg1;
731   };
732   inline unsigned int
get_col()733   get_col()
734   {
735     return arg2;
736   };
737   inline int
get_lag()738   get_lag()
739   {
740     return arg2;
741   };
742   inline unsigned int
get_col_pos()743   get_col_pos()
744   {
745     return arg4;
746   };
747 };
748 
749 class FUNARY_ : public TagWithOneArgument<uint8_t>
750 {
751 public:
752   inline
FUNARY_()753   FUNARY_() : TagWithOneArgument<uint8_t>::TagWithOneArgument{FUNARY}
754   {
755   };
756   inline explicit
FUNARY_(uint8_t op_type_arg)757   FUNARY_(uint8_t op_type_arg) : TagWithOneArgument<uint8_t>::TagWithOneArgument{FUNARY, op_type_arg}
758   {
759   };
760   inline uint8_t
get_op_type()761   get_op_type()
762   {
763     return arg1;
764   };
765 };
766 
767 class FBINARY_ : public TagWithOneArgument<uint8_t>
768 {
769 public:
770   inline
FBINARY_()771   FBINARY_() : TagWithOneArgument<uint8_t>::TagWithOneArgument{FBINARY}
772   {
773   };
774   inline explicit
FBINARY_(int op_type_arg)775   FBINARY_(int op_type_arg) : TagWithOneArgument<uint8_t>::TagWithOneArgument{FBINARY, static_cast<uint8_t>(op_type_arg)}
776   {
777   };
778   inline uint8_t
get_op_type()779   get_op_type()
780   {
781     return arg1;
782   };
783 };
784 
785 class FTRINARY_ : public TagWithOneArgument<uint8_t>
786 {
787 public:
788   inline
FTRINARY_()789   FTRINARY_() : TagWithOneArgument<uint8_t>::TagWithOneArgument{FTRINARY}
790   {
791   };
792   inline explicit
FTRINARY_(int op_type_arg)793   FTRINARY_(int op_type_arg) : TagWithOneArgument<uint8_t>::TagWithOneArgument{FTRINARY, static_cast<uint8_t>(op_type_arg)}
794   {
795   };
796   inline uint8_t
get_op_type()797   get_op_type()
798   {
799     return arg1;
800   };
801 };
802 
803 class FOK_ : public TagWithOneArgument<int>
804 {
805 public:
806   inline
FOK_()807   FOK_() : TagWithOneArgument<int>::TagWithOneArgument{FOK}
808   {
809   };
810   inline explicit
FOK_(int arg_arg)811   FOK_(int arg_arg) : TagWithOneArgument<int>::TagWithOneArgument{FOK, arg_arg}
812   {
813   };
814   inline int
get_arg()815   get_arg()
816   {
817     return arg1;
818   };
819 };
820 
821 class FJMPIFEVAL_ : public TagWithOneArgument<unsigned int>
822 {
823 public:
824   inline
FJMPIFEVAL_()825   FJMPIFEVAL_() : TagWithOneArgument<unsigned int>::TagWithOneArgument{FJMPIFEVAL}
826   {
827   };
828   inline explicit
FJMPIFEVAL_(unsigned int arg_pos)829   FJMPIFEVAL_(unsigned int arg_pos) : TagWithOneArgument<unsigned int>::TagWithOneArgument{FJMPIFEVAL, arg_pos}
830   {
831   };
832   inline unsigned int
get_pos()833   get_pos()
834   {
835     return arg1;
836   }
837 };
838 
839 class FJMP_ : public TagWithOneArgument<unsigned int>
840 {
841 public:
842   inline
FJMP_()843   FJMP_() : TagWithOneArgument<unsigned int>::TagWithOneArgument{FJMP}
844   {
845   };
846   inline explicit
FJMP_(unsigned int arg_pos)847   FJMP_(unsigned int arg_pos) : TagWithOneArgument<unsigned int>::TagWithOneArgument{FJMP, arg_pos}
848   {
849   };
850   inline unsigned int
get_pos()851   get_pos()
852   {
853     return arg1;
854   }
855 };
856 
857 class FLDTEF_ : public TagWithOneArgument<unsigned int>
858 {
859 public:
860   inline
FLDTEF_()861   FLDTEF_() : TagWithOneArgument<unsigned int>::TagWithOneArgument{FLDTEF}
862   {
863   };
864   inline explicit
FLDTEF_(unsigned int number)865   FLDTEF_(unsigned int number) : TagWithOneArgument<unsigned int>::TagWithOneArgument{FLDTEF, number}
866   {
867   };
868   inline unsigned int
get_number()869   get_number()
870   {
871     return arg1;
872   }
873 };
874 
875 class FSTPTEF_ : public TagWithOneArgument<unsigned int>
876 {
877 public:
878   inline
FSTPTEF_()879   FSTPTEF_() : TagWithOneArgument<unsigned int>::TagWithOneArgument{FSTPTEF}
880   {
881   };
882   inline explicit
FSTPTEF_(unsigned int number)883   FSTPTEF_(unsigned int number) : TagWithOneArgument<unsigned int>::TagWithOneArgument{FSTPTEF, number}
884   {
885   };
886   inline unsigned int
get_number()887   get_number()
888   {
889     return arg1;
890   }
891 };
892 
893 class FLDTEFD_ : public TagWithTwoArguments<unsigned int, unsigned int>
894 {
895 public:
896   inline
FLDTEFD_()897   FLDTEFD_() : TagWithTwoArguments<unsigned int, unsigned int>::TagWithTwoArguments{FLDTEFD}
898   {
899   };
900   inline
FLDTEFD_(unsigned int indx,unsigned int row)901   FLDTEFD_(unsigned int indx, unsigned int row) : TagWithTwoArguments<unsigned int, unsigned int>::TagWithTwoArguments{FLDTEFD, indx, row}
902   {
903   };
904   inline unsigned int
get_indx()905   get_indx()
906   {
907     return arg1;
908   };
909   inline unsigned int
get_row()910   get_row()
911   {
912     return arg2;
913   };
914 };
915 
916 class FSTPTEFD_ : public TagWithTwoArguments<unsigned int, unsigned int>
917 {
918 public:
919   inline
FSTPTEFD_()920   FSTPTEFD_() : TagWithTwoArguments<unsigned int, unsigned int>::TagWithTwoArguments{FSTPTEFD}
921   {
922   };
923   inline
FSTPTEFD_(unsigned int indx,unsigned int row)924   FSTPTEFD_(unsigned int indx, unsigned int row) : TagWithTwoArguments<unsigned int, unsigned int>::TagWithTwoArguments{FSTPTEFD, indx, row}
925   {
926   };
927   inline unsigned int
get_indx()928   get_indx()
929   {
930     return arg1;
931   };
932   inline unsigned int
get_row()933   get_row()
934   {
935     return arg2;
936   };
937 };
938 
939 class FLDTEFDD_ : public TagWithThreeArguments<unsigned int, unsigned int, unsigned int>
940 {
941 public:
942   inline
FLDTEFDD_()943   FLDTEFDD_() : TagWithThreeArguments<unsigned int, unsigned int, unsigned int>::TagWithThreeArguments{FLDTEFDD}
944   {
945   };
946   inline
FLDTEFDD_(unsigned int indx,unsigned int row,unsigned int col)947   FLDTEFDD_(unsigned int indx, unsigned int row, unsigned int col) : TagWithThreeArguments<unsigned int, unsigned int, unsigned int>::TagWithThreeArguments{FLDTEFDD, indx, row, col}
948   {
949   };
950   inline unsigned int
get_indx()951   get_indx()
952   {
953     return arg1;
954   };
955   inline unsigned int
get_row()956   get_row()
957   {
958     return arg2;
959   };
960   inline unsigned int
get_col()961   get_col()
962   {
963     return arg3;
964   };
965 };
966 
967 class FSTPTEFDD_ : public TagWithThreeArguments<unsigned int, unsigned int, unsigned int>
968 {
969 public:
970   inline
FSTPTEFDD_()971   FSTPTEFDD_() : TagWithThreeArguments<unsigned int, unsigned int, unsigned int>::TagWithThreeArguments{FSTPTEFDD}
972   {
973   };
974   inline
FSTPTEFDD_(unsigned int indx,unsigned int row,unsigned int col)975   FSTPTEFDD_(unsigned int indx, unsigned int row, unsigned int col) : TagWithThreeArguments<unsigned int, unsigned int, unsigned int>::TagWithThreeArguments{FSTPTEF, indx, row, col}
976   {
977   };
978   inline unsigned int
get_indx()979   get_indx()
980   {
981     return arg1;
982   };
983   inline unsigned int
get_row()984   get_row()
985   {
986     return arg2;
987   };
988   inline unsigned int
get_col()989   get_col()
990   {
991     return arg3;
992   };
993 };
994 
995 class FLDVS_ : public TagWithTwoArguments<uint8_t, unsigned int>
996 {
997 public:
998   inline
FLDVS_()999   FLDVS_() : TagWithTwoArguments<uint8_t, unsigned int>::TagWithTwoArguments{FLDVS}
1000   {
1001   };
1002   inline
FLDVS_(uint8_t type_arg,unsigned int pos_arg)1003   FLDVS_(uint8_t type_arg, unsigned int pos_arg) : TagWithTwoArguments<uint8_t, unsigned int>::TagWithTwoArguments{FLDVS, type_arg, pos_arg}
1004   {
1005   };
1006   inline uint8_t
get_type()1007   get_type()
1008   {
1009     return arg1;
1010   };
1011   inline unsigned int
get_pos()1012   get_pos()
1013   {
1014     return arg2;
1015   };
1016 };
1017 
1018 class FLDSV_ : public TagWithTwoArguments<uint8_t, unsigned int>
1019 {
1020 public:
1021   inline
FLDSV_()1022   FLDSV_() : TagWithTwoArguments<uint8_t, unsigned int>::TagWithTwoArguments{FLDSV}
1023   {
1024   };
1025   inline
FLDSV_(uint8_t type_arg,unsigned int pos_arg)1026   FLDSV_(uint8_t type_arg, unsigned int pos_arg) :
1027     TagWithTwoArguments<uint8_t, unsigned int>::TagWithTwoArguments{FLDSV, type_arg, pos_arg}
1028   {
1029   };
1030   inline uint8_t
get_type()1031   get_type()
1032   {
1033     return arg1;
1034   };
1035   inline unsigned int
get_pos()1036   get_pos()
1037   {
1038     return arg2;
1039   };
1040 };
1041 
1042 class FSTPSV_ : public TagWithTwoArguments<uint8_t, unsigned int>
1043 {
1044 public:
1045   inline
FSTPSV_()1046   FSTPSV_() : TagWithTwoArguments<uint8_t, unsigned int>::TagWithTwoArguments{FSTPSV}
1047   {
1048   };
1049   inline
FSTPSV_(uint8_t type_arg,unsigned int pos_arg)1050   FSTPSV_(uint8_t type_arg, unsigned int pos_arg) :
1051     TagWithTwoArguments<uint8_t, unsigned int>::TagWithTwoArguments{FSTPSV, type_arg, pos_arg}
1052   {
1053   };
1054   inline uint8_t
get_type()1055   get_type()
1056   {
1057     return arg1;
1058   };
1059   inline unsigned int
get_pos()1060   get_pos()
1061   {
1062     return arg2;
1063   };
1064 };
1065 
1066 class FLDV_ : public TagWithThreeArguments<uint8_t, unsigned int, int>
1067 {
1068 public:
1069   inline
FLDV_()1070   FLDV_() : TagWithThreeArguments<uint8_t, unsigned int, int>::TagWithThreeArguments{FLDV}
1071   {
1072   };
1073   inline
FLDV_(int type_arg,unsigned int pos_arg)1074   FLDV_(int type_arg, unsigned int pos_arg) :
1075     TagWithThreeArguments<uint8_t, unsigned int, int>::TagWithThreeArguments{FLDV, static_cast<uint8_t>(type_arg), pos_arg, 0}
1076   {
1077   };
1078   inline
FLDV_(int type_arg,unsigned int pos_arg,int lead_lag_arg)1079   FLDV_(int type_arg, unsigned int pos_arg, int lead_lag_arg) :
1080     TagWithThreeArguments<uint8_t, unsigned int, int>::TagWithThreeArguments{FLDV, static_cast<uint8_t>(type_arg), pos_arg, lead_lag_arg}
1081   {
1082   };
1083   inline uint8_t
get_type()1084   get_type()
1085   {
1086     return arg1;
1087   };
1088   inline unsigned int
get_pos()1089   get_pos()
1090   {
1091     return arg2;
1092   };
1093   inline int
get_lead_lag()1094   get_lead_lag()
1095   {
1096     return arg3;
1097   };
1098 };
1099 
1100 class FSTPV_ : public TagWithThreeArguments<uint8_t, unsigned int, int>
1101 {
1102 public:
1103   inline
FSTPV_()1104   FSTPV_() : TagWithThreeArguments<uint8_t, unsigned int, int>::TagWithThreeArguments{FSTPV}
1105   {
1106   };
1107   inline
FSTPV_(int type_arg,unsigned int pos_arg)1108   FSTPV_(int type_arg, unsigned int pos_arg) :
1109     TagWithThreeArguments<uint8_t, unsigned int, int>::TagWithThreeArguments{FSTPV, static_cast<uint8_t>(type_arg), pos_arg, 0}
1110   {
1111   };
1112   inline
FSTPV_(int type_arg,unsigned int pos_arg,int lead_lag_arg)1113   FSTPV_(int type_arg, unsigned int pos_arg, int lead_lag_arg) :
1114     TagWithThreeArguments<uint8_t, unsigned int, int>::TagWithThreeArguments{FSTPV, static_cast<uint8_t>(type_arg), pos_arg, lead_lag_arg}
1115   {
1116   };
1117   inline uint8_t
get_type()1118   get_type()
1119   {
1120     return arg1;
1121   };
1122   inline unsigned int
get_pos()1123   get_pos()
1124   {
1125     return arg2;
1126   };
1127   inline int
get_lead_lag()1128   get_lead_lag()
1129   {
1130     return arg3;
1131   };
1132 };
1133 
1134 class FCALL_ : public TagWithFourArguments<unsigned int, unsigned int, string, unsigned int>
1135 {
1136   string func_name;
1137   string arg_func_name;
1138   unsigned int add_input_arguments, row, col;
1139   ExternalFunctionType function_type;
1140 public:
1141   inline
FCALL_()1142   FCALL_() : TagWithFourArguments<unsigned int, unsigned int, string, unsigned int>::TagWithFourArguments{FCALL},
1143     add_input_arguments{0},
1144     row{0},
1145     col{0},
1146     function_type{ExternalFunctionType::withoutDerivative}
1147   {
1148   };
1149   inline
FCALL_(unsigned int nb_output_arguments,unsigned int nb_input_arguments,string f_name,unsigned int indx)1150   FCALL_(unsigned int nb_output_arguments, unsigned int nb_input_arguments, string f_name, unsigned int indx) :
1151     TagWithFourArguments<unsigned int, unsigned int, string, unsigned int>::TagWithFourArguments{FCALL, nb_output_arguments, nb_input_arguments, f_name, indx},
1152     func_name{f_name},
1153     add_input_arguments{0},
1154     row{0},
1155     col{0},
1156     function_type{ExternalFunctionType::withoutDerivative}
1157   {
1158   };
1159   inline string
get_function_name()1160   get_function_name()
1161   {
1162     //printf("get_function_name => func_name=%s\n",func_name.c_str());fflush(stdout);
1163     return func_name;
1164   };
1165   inline unsigned int
get_nb_output_arguments()1166   get_nb_output_arguments()
1167   {
1168     return arg1;
1169   };
1170   inline unsigned int
get_nb_input_arguments()1171   get_nb_input_arguments()
1172   {
1173     return arg2;
1174   };
1175   inline unsigned int
get_indx()1176   get_indx()
1177   {
1178     return arg4;
1179   };
1180   inline void
set_arg_func_name(string arg_arg_func_name)1181   set_arg_func_name(string arg_arg_func_name)
1182   {
1183     arg_func_name = arg_arg_func_name;
1184   };
1185   inline string
get_arg_func_name()1186   get_arg_func_name()
1187   {
1188     return arg_func_name;
1189   };
1190   inline void
set_nb_add_input_arguments(unsigned int arg_add_input_arguments)1191   set_nb_add_input_arguments(unsigned int arg_add_input_arguments)
1192   {
1193     add_input_arguments = arg_add_input_arguments;
1194   };
1195   inline unsigned int
get_nb_add_input_arguments()1196   get_nb_add_input_arguments()
1197   {
1198     return add_input_arguments;
1199   };
1200   inline void
set_row(unsigned int arg_row)1201   set_row(unsigned int arg_row)
1202   {
1203     row = arg_row;
1204   };
1205   inline unsigned int
get_row()1206   get_row()
1207   {
1208     return row;
1209   }
1210   inline void
set_col(unsigned int arg_col)1211   set_col(unsigned int arg_col)
1212   {
1213     col = arg_col;
1214   };
1215   inline unsigned int
get_col()1216   get_col()
1217   {
1218     return col;
1219   };
1220   inline void
set_function_type(ExternalFunctionType arg_function_type)1221   set_function_type(ExternalFunctionType arg_function_type)
1222   {
1223     function_type = arg_function_type;
1224   };
1225   inline ExternalFunctionType
get_function_type()1226   get_function_type()
1227   {
1228     return (function_type);
1229   }
1230   inline void
write(ostream & CompileCode,unsigned int & instruction_number)1231   write(ostream &CompileCode, unsigned int &instruction_number)
1232   {
1233     CompileCode.write(reinterpret_cast<char *>(&op_code), sizeof(op_code));
1234     CompileCode.write(reinterpret_cast<char *>(&arg1), sizeof(arg1));
1235     CompileCode.write(reinterpret_cast<char *>(&arg2), sizeof(arg2));
1236     CompileCode.write(reinterpret_cast<char *>(&arg4), sizeof(arg4));
1237     CompileCode.write(reinterpret_cast<char *>(&add_input_arguments), sizeof(add_input_arguments));
1238     CompileCode.write(reinterpret_cast<char *>(&row), sizeof(row));
1239     CompileCode.write(reinterpret_cast<char *>(&col), sizeof(col));
1240     CompileCode.write(reinterpret_cast<char *>(&function_type), sizeof(function_type));
1241     size_t size = func_name.size();
1242     CompileCode.write(reinterpret_cast<char *>(&size), sizeof(int));
1243     const char *name = func_name.c_str();
1244     CompileCode.write(reinterpret_cast<const char *>(name), func_name.size());
1245     size = arg_func_name.size();
1246     CompileCode.write(reinterpret_cast<char *>(&size), sizeof(int));
1247     name = arg_func_name.c_str();
1248     CompileCode.write(reinterpret_cast<const char *>(name), arg_func_name.size());
1249     instruction_number++;
1250   };
1251 #ifdef BYTE_CODE
1252 
1253   inline uint8_t *
load(uint8_t * code)1254   load(uint8_t *code)
1255   {
1256     op_code = FCALL; code += sizeof(op_code);
1257     memcpy(&arg1, code, sizeof(arg1)); code += sizeof(arg1);
1258     memcpy(&arg2, code, sizeof(arg2)); code += sizeof(arg2);
1259     memcpy(&arg4, code, sizeof(arg4)); code += sizeof(arg4);
1260     memcpy(&add_input_arguments, code, sizeof(add_input_arguments)); code += sizeof(add_input_arguments);
1261     memcpy(&row, code, sizeof(row)); code += sizeof(row);
1262     memcpy(&col, code, sizeof(col)); code += sizeof(col);
1263     memcpy(&function_type, code, sizeof(function_type)); code += sizeof(function_type);
1264     int size;
1265     memcpy(&size, code, sizeof(size)); code += sizeof(size);
1266     char *name = static_cast<char *>(mxMalloc((size+1)*sizeof(char)));
1267     memcpy(name, code, size); code += size;
1268     name[size] = 0;
1269     func_name = name;
1270     mxFree(name);
1271     memcpy(&size, code, sizeof(size)); code += sizeof(size);
1272     name = static_cast<char *>(mxMalloc((size+1)*sizeof(char)));
1273     memcpy(name, code, size); code += size;
1274     name[size] = 0;
1275     arg_func_name = name;
1276     mxFree(name);
1277     return code;
1278   }
1279 #endif
1280 };
1281 
1282 class FNUMEXPR_ : public TagWithOneArgument<ExpressionType>
1283 {
1284 private:
1285   unsigned int equation;
1286   uint16_t dvariable1, dvariable2, dvariable3;
1287   int8_t lag1, lag2, lag3;
1288 public:
1289   inline
FNUMEXPR_()1290   FNUMEXPR_() : TagWithOneArgument<ExpressionType>::TagWithOneArgument{FNUMEXPR}
1291   {
1292   };
1293   inline
FNUMEXPR_(const ExpressionType expression_type,unsigned int equation_arg)1294   FNUMEXPR_(const ExpressionType expression_type, unsigned int equation_arg) :
1295     TagWithOneArgument<ExpressionType>::TagWithOneArgument{FNUMEXPR, expression_type},
1296     equation{equation_arg},
1297     dvariable1{0}, dvariable2{0}, dvariable3{0},
1298     lag1{0}, lag2{0}, lag3{0}
1299   {
1300   };
1301   inline
FNUMEXPR_(const ExpressionType expression_type,unsigned int equation_arg,unsigned int dvariable1_arg)1302   FNUMEXPR_(const ExpressionType expression_type, unsigned int equation_arg, unsigned int dvariable1_arg) :
1303     TagWithOneArgument<ExpressionType>::TagWithOneArgument{FNUMEXPR, expression_type},
1304     equation{equation_arg},
1305     dvariable1{static_cast<uint16_t>(dvariable1_arg)}, dvariable2{0}, dvariable3{0},
1306     lag1{0}, lag2{0}, lag3{0}
1307   {
1308   };
1309   inline
FNUMEXPR_(const ExpressionType expression_type,unsigned int equation_arg,unsigned int dvariable1_arg,int lag1_arg)1310   FNUMEXPR_(const ExpressionType expression_type, unsigned int equation_arg, unsigned int dvariable1_arg, int lag1_arg) :
1311     TagWithOneArgument<ExpressionType>::TagWithOneArgument{FNUMEXPR, expression_type},
1312     equation{equation_arg},
1313     dvariable1{static_cast<uint16_t>(dvariable1_arg)}, dvariable2{0}, dvariable3{0},
1314     lag1{static_cast<int8_t>(lag1_arg)}, lag2{0}, lag3{0}
1315   {
1316   };
1317   inline
FNUMEXPR_(const ExpressionType expression_type,unsigned int equation_arg,unsigned int dvariable1_arg,unsigned int dvariable2_arg)1318   FNUMEXPR_(const ExpressionType expression_type, unsigned int equation_arg, unsigned int dvariable1_arg, unsigned int dvariable2_arg) :
1319     TagWithOneArgument<ExpressionType>::TagWithOneArgument{FNUMEXPR, expression_type},
1320     equation{equation_arg},
1321     dvariable1{static_cast<uint16_t>(dvariable1_arg)},
1322     dvariable2{static_cast<uint16_t>(dvariable2_arg)},
1323     dvariable3{0},
1324     lag1{0}, lag2{0}, lag3{0}
1325   {
1326   };
1327   inline
FNUMEXPR_(const ExpressionType expression_type,unsigned int equation_arg,unsigned int dvariable1_arg,int lag1_arg,unsigned int dvariable2_arg,int lag2_arg)1328   FNUMEXPR_(const ExpressionType expression_type, unsigned int equation_arg, unsigned int dvariable1_arg, int lag1_arg, unsigned int dvariable2_arg, int lag2_arg) :
1329     TagWithOneArgument<ExpressionType>::TagWithOneArgument{FNUMEXPR, expression_type},
1330     equation{equation_arg},
1331     dvariable1{static_cast<uint16_t>(dvariable1_arg)},
1332     dvariable2{static_cast<uint16_t>(dvariable2_arg)},
1333     dvariable3{0},
1334     lag1{static_cast<int8_t>(lag1_arg)},
1335     lag2{static_cast<int8_t>(lag2_arg)},
1336     lag3{0}
1337   {
1338   };
1339   inline
FNUMEXPR_(const ExpressionType expression_type,unsigned int equation_arg,unsigned int dvariable1_arg,unsigned int dvariable2_arg,unsigned int dvariable3_arg)1340   FNUMEXPR_(const ExpressionType expression_type, unsigned int equation_arg, unsigned int dvariable1_arg, unsigned int dvariable2_arg, unsigned int dvariable3_arg) :
1341     TagWithOneArgument<ExpressionType>::TagWithOneArgument{FNUMEXPR, expression_type},
1342     equation{equation_arg},
1343     dvariable1{static_cast<uint16_t>(dvariable1_arg)},
1344     dvariable2{static_cast<uint16_t>(dvariable2_arg)},
1345     dvariable3{static_cast<uint16_t>(dvariable3_arg)},
1346     lag1{0}, lag2{0}, lag3{0}
1347   {
1348   };
1349   inline
FNUMEXPR_(const ExpressionType expression_type,unsigned int equation_arg,unsigned int dvariable1_arg,int lag1_arg,unsigned int dvariable2_arg,int lag2_arg,unsigned int dvariable3_arg,int lag3_arg)1350   FNUMEXPR_(const ExpressionType expression_type, unsigned int equation_arg, unsigned int dvariable1_arg, int lag1_arg, unsigned int dvariable2_arg, int lag2_arg, unsigned int dvariable3_arg, int lag3_arg) :
1351     TagWithOneArgument<ExpressionType>::TagWithOneArgument{FNUMEXPR, expression_type},
1352     equation{equation_arg},
1353     dvariable1{static_cast<uint16_t>(dvariable1_arg)},
1354     dvariable2{static_cast<uint16_t>(dvariable2_arg)},
1355     dvariable3{static_cast<uint16_t>(dvariable3_arg)},
1356     lag1{static_cast<int8_t>(lag1_arg)},
1357     lag2{static_cast<int8_t>(lag2_arg)},
1358     lag3{static_cast<int8_t>(lag3_arg)}
1359   {
1360   };
1361   inline ExpressionType
get_expression_type()1362   get_expression_type()
1363   {
1364     return arg1;
1365   }
1366   inline unsigned int
get_equation()1367   get_equation()
1368   {
1369     return equation;
1370   };
1371   inline unsigned int
get_dvariable1()1372   get_dvariable1()
1373   {
1374     return dvariable1;
1375   };
1376   inline int
get_lag1()1377   get_lag1()
1378   {
1379     return lag1;
1380   };
1381   inline unsigned int
get_dvariable2()1382   get_dvariable2()
1383   {
1384     return dvariable2;
1385   };
1386   inline int
get_lag2()1387   get_lag2()
1388   {
1389     return lag2;
1390   };
1391   inline unsigned int
get_dvariable3()1392   get_dvariable3()
1393   {
1394     return dvariable3;
1395   };
1396   inline int
get_lag3()1397   get_lag3()
1398   {
1399     return lag3;
1400   };
1401   inline void
write(ostream & CompileCode,unsigned int & instruction_number)1402   write(ostream &CompileCode, unsigned int &instruction_number)
1403   {
1404     CompileCode.write(reinterpret_cast<char *>(this), sizeof(FNUMEXPR_));
1405     instruction_number++;
1406   };
1407 };
1408 
1409 class FBEGINBLOCK_
1410 {
1411 private:
1412   uint8_t op_code{FBEGINBLOCK};
1413   int size;
1414   uint8_t type;
1415   vector<int> variable;
1416   vector<int> equation;
1417   vector<unsigned int> other_endogenous;
1418   vector<unsigned int> exogenous;
1419   vector<unsigned int> det_exogenous;
1420   bool is_linear;
1421   vector<Block_contain_type> Block_Contain_;
1422   int endo_nbr;
1423   int Max_Lag;
1424   int Max_Lead;
1425   int u_count_int;
1426   int nb_col_jacob;
1427   unsigned int det_exo_size, exo_size, other_endo_size;
1428   unsigned int nb_col_det_exo_jacob, nb_col_exo_jacob, nb_col_other_endo_jacob;
1429 public:
1430   inline
FBEGINBLOCK_()1431   FBEGINBLOCK_() : size{0}, type{UNKNOWN},
1432                    is_linear{false}, endo_nbr{0}, Max_Lag{0}, Max_Lead{0}, u_count_int{0}, nb_col_jacob{0}
1433   {
1434   }
1435   inline
FBEGINBLOCK_(unsigned int size_arg,BlockSimulationType type_arg,int unsigned first_element,int unsigned block_size,const vector<int> & variable_arg,const vector<int> & equation_arg,bool is_linear_arg,int endo_nbr_arg,int Max_Lag_arg,int Max_Lead_arg,int & u_count_int_arg,int nb_col_jacob_arg,unsigned int det_exo_size_arg,unsigned int nb_col_det_exo_jacob_arg,unsigned int exo_size_arg,unsigned int nb_col_exo_jacob_arg,unsigned int other_endo_size_arg,unsigned int nb_col_other_endo_jacob_arg,const vector<unsigned int> & det_exogenous_arg,const vector<unsigned int> & exogenous_arg,const vector<unsigned int> & other_endogenous_arg)1436   FBEGINBLOCK_(unsigned int size_arg, BlockSimulationType type_arg, int unsigned first_element, int unsigned block_size,
1437                const vector<int> &variable_arg, const vector<int> &equation_arg,
1438                bool is_linear_arg, int endo_nbr_arg, int Max_Lag_arg, int Max_Lead_arg, int &u_count_int_arg, int nb_col_jacob_arg,
1439                unsigned int det_exo_size_arg, unsigned int nb_col_det_exo_jacob_arg, unsigned int exo_size_arg, unsigned int nb_col_exo_jacob_arg, unsigned int other_endo_size_arg, unsigned int nb_col_other_endo_jacob_arg,
1440                const vector<unsigned int> &det_exogenous_arg, const vector<unsigned int> &exogenous_arg, const vector<unsigned int> &other_endogenous_arg) :
1441     size{static_cast<int>(size_arg)},
1442     type{static_cast<uint8_t>(type_arg)},
1443     variable{variable_arg.begin()+first_element, variable_arg.begin()+(first_element+block_size)},
1444     equation{equation_arg.begin()+first_element, equation_arg.begin()+(first_element+block_size)},
1445     other_endogenous{other_endogenous_arg},
1446     exogenous{exogenous_arg},
1447     det_exogenous{det_exogenous_arg},
1448     is_linear{is_linear_arg},
1449     endo_nbr{endo_nbr_arg},
1450     Max_Lag{Max_Lag_arg},
1451     Max_Lead{Max_Lead_arg},
1452     u_count_int{u_count_int_arg},
1453     nb_col_jacob{nb_col_jacob_arg},
1454     det_exo_size{det_exo_size_arg},
1455     exo_size{exo_size_arg},
1456     other_endo_size{other_endo_size_arg},
1457     nb_col_det_exo_jacob{nb_col_det_exo_jacob_arg},
1458     nb_col_exo_jacob{nb_col_exo_jacob_arg},
1459     nb_col_other_endo_jacob{nb_col_other_endo_jacob_arg}
1460   {
1461   }
1462   inline
FBEGINBLOCK_(unsigned int size_arg,BlockSimulationType type_arg,int unsigned first_element,int unsigned block_size,const vector<int> & variable_arg,const vector<int> & equation_arg,bool is_linear_arg,int endo_nbr_arg,int Max_Lag_arg,int Max_Lead_arg,int & u_count_int_arg,int nb_col_jacob_arg)1463   FBEGINBLOCK_(unsigned int size_arg, BlockSimulationType type_arg, int unsigned first_element, int unsigned block_size,
1464                const vector<int> &variable_arg, const vector<int> &equation_arg,
1465                bool is_linear_arg, int endo_nbr_arg, int Max_Lag_arg, int Max_Lead_arg, int &u_count_int_arg, int nb_col_jacob_arg) :
1466     size{static_cast<int>(size_arg)},
1467     type{static_cast<uint8_t>(type_arg)},
1468     variable{variable_arg.begin()+first_element, variable_arg.begin()+(first_element+block_size)},
1469     equation{equation_arg.begin()+first_element, equation_arg.begin()+(first_element+block_size)},
1470     is_linear{is_linear_arg},
1471     endo_nbr{endo_nbr_arg},
1472     Max_Lag{Max_Lag_arg},
1473     Max_Lead{Max_Lead_arg},
1474     u_count_int{u_count_int_arg},
1475     nb_col_jacob{nb_col_jacob_arg},
1476     det_exo_size{0},
1477     exo_size{0},
1478     other_endo_size{0},
1479     nb_col_det_exo_jacob{0},
1480     nb_col_exo_jacob{0},
1481     nb_col_other_endo_jacob{0}
1482   {
1483   }
1484   inline unsigned int
get_size()1485   get_size()
1486   {
1487     return size;
1488   };
1489   inline uint8_t
get_type()1490   get_type()
1491   {
1492     return type;
1493   };
1494   inline bool
get_is_linear()1495   get_is_linear()
1496   {
1497     return is_linear;
1498   };
1499   inline int
get_endo_nbr()1500   get_endo_nbr()
1501   {
1502     return endo_nbr;
1503   };
1504   inline int
get_Max_Lag()1505   get_Max_Lag()
1506   {
1507     return Max_Lag;
1508   };
1509   inline int
get_Max_Lead()1510   get_Max_Lead()
1511   {
1512     return Max_Lead;
1513   };
1514   inline int
get_u_count_int()1515   get_u_count_int()
1516   {
1517     return u_count_int;
1518   };
1519   inline vector<Block_contain_type>
get_Block_Contain()1520   get_Block_Contain()
1521   {
1522     return Block_Contain_;
1523   };
1524   inline int
get_nb_col_jacob()1525   get_nb_col_jacob()
1526   {
1527     return nb_col_jacob;
1528   };
1529   inline unsigned int
get_exo_size()1530   get_exo_size()
1531   {
1532     return exo_size;
1533   };
1534   inline unsigned int
get_nb_col_exo_jacob()1535   get_nb_col_exo_jacob()
1536   {
1537     return nb_col_exo_jacob;
1538   };
1539   inline unsigned int
get_det_exo_size()1540   get_det_exo_size()
1541   {
1542     return det_exo_size;
1543   };
1544   inline unsigned int
get_nb_col_det_exo_jacob()1545   get_nb_col_det_exo_jacob()
1546   {
1547     return nb_col_det_exo_jacob;
1548   };
1549   inline unsigned int
get_other_endo_size()1550   get_other_endo_size()
1551   {
1552     return other_endo_size;
1553   };
1554   inline unsigned int
get_nb_col_other_endo_jacob()1555   get_nb_col_other_endo_jacob()
1556   {
1557     return nb_col_other_endo_jacob;
1558   };
1559   inline vector<int>
get_endogenous()1560   get_endogenous()
1561   {
1562     return variable;
1563   }
1564   inline vector<unsigned int>
get_exogenous()1565   get_exogenous()
1566   {
1567     return exogenous;
1568   }
1569   inline void
write(ostream & CompileCode,unsigned int & instruction_number)1570   write(ostream &CompileCode, unsigned int &instruction_number)
1571   {
1572     CompileCode.write(reinterpret_cast<char *>(&op_code), sizeof(op_code));
1573     CompileCode.write(reinterpret_cast<char *>(&size), sizeof(size));
1574     CompileCode.write(reinterpret_cast<char *>(&type), sizeof(type));
1575     for (int i = 0; i < size; i++)
1576       {
1577         CompileCode.write(reinterpret_cast<char *>(&variable[i]), sizeof(variable[0]));
1578         CompileCode.write(reinterpret_cast<char *>(&equation[i]), sizeof(equation[0]));
1579       }
1580     if (type == SOLVE_TWO_BOUNDARIES_SIMPLE || type == SOLVE_TWO_BOUNDARIES_COMPLETE
1581         || type == SOLVE_BACKWARD_COMPLETE || type == SOLVE_FORWARD_COMPLETE)
1582       {
1583         CompileCode.write(reinterpret_cast<char *>(&is_linear), sizeof(is_linear));
1584         CompileCode.write(reinterpret_cast<char *>(&endo_nbr), sizeof(endo_nbr));
1585         CompileCode.write(reinterpret_cast<char *>(&Max_Lag), sizeof(Max_Lag));
1586         CompileCode.write(reinterpret_cast<char *>(&Max_Lead), sizeof(Max_Lead));
1587         CompileCode.write(reinterpret_cast<char *>(&u_count_int), sizeof(u_count_int));
1588       }
1589     CompileCode.write(reinterpret_cast<char *>(&nb_col_jacob), sizeof(nb_col_jacob));
1590     CompileCode.write(reinterpret_cast<char *>(&det_exo_size), sizeof(det_exo_size));
1591     CompileCode.write(reinterpret_cast<char *>(&nb_col_det_exo_jacob), sizeof(nb_col_det_exo_jacob));
1592     CompileCode.write(reinterpret_cast<char *>(&exo_size), sizeof(exo_size));
1593     CompileCode.write(reinterpret_cast<char *>(&nb_col_exo_jacob), sizeof(nb_col_exo_jacob));
1594     CompileCode.write(reinterpret_cast<char *>(&other_endo_size), sizeof(other_endo_size));
1595     CompileCode.write(reinterpret_cast<char *>(&nb_col_other_endo_jacob), sizeof(nb_col_other_endo_jacob));
1596 
1597     for (unsigned int i = 0; i < det_exo_size; i++)
1598       CompileCode.write(reinterpret_cast<char *>(&det_exogenous[i]), sizeof(det_exogenous[0]));
1599     for (unsigned int i = 0; i < exo_size; i++)
1600       CompileCode.write(reinterpret_cast<char *>(&exogenous[i]), sizeof(exogenous[0]));
1601     for (unsigned int i = 0; i < other_endo_size; i++)
1602       CompileCode.write(reinterpret_cast<char *>(&other_endogenous[i]), sizeof(other_endogenous[0]));
1603     instruction_number++;
1604   };
1605 #ifdef BYTE_CODE
1606 
1607   inline uint8_t *
load(uint8_t * code)1608   load(uint8_t *code)
1609   {
1610     op_code = FBEGINBLOCK; code += sizeof(op_code);
1611     memcpy(&size, code, sizeof(size)); code += sizeof(size);
1612     memcpy(&type, code, sizeof(type)); code += sizeof(type);
1613     for (int i = 0; i < size; i++)
1614       {
1615         Block_contain_type bc;
1616         memcpy(&bc.Variable, code, sizeof(bc.Variable)); code += sizeof(bc.Variable);
1617         memcpy(&bc.Equation, code, sizeof(bc.Equation)); code += sizeof(bc.Equation);
1618         Block_Contain_.push_back(bc);
1619       }
1620     if (type == SOLVE_TWO_BOUNDARIES_SIMPLE || type == SOLVE_TWO_BOUNDARIES_COMPLETE
1621         || type == SOLVE_BACKWARD_COMPLETE || type == SOLVE_FORWARD_COMPLETE)
1622       {
1623         memcpy(&is_linear, code, sizeof(is_linear)); code += sizeof(is_linear);
1624         memcpy(&endo_nbr, code, sizeof(endo_nbr)); code += sizeof(endo_nbr);
1625         memcpy(&Max_Lag, code, sizeof(Max_Lag)); code += sizeof(Max_Lag);
1626         memcpy(&Max_Lead, code, sizeof(Max_Lead)); code += sizeof(Max_Lead);
1627         memcpy(&u_count_int, code, sizeof(u_count_int)); code += sizeof(u_count_int);
1628       }
1629     memcpy(&nb_col_jacob, code, sizeof(nb_col_jacob)); code += sizeof(nb_col_jacob);
1630     memcpy(&det_exo_size, code, sizeof(det_exo_size)); code += sizeof(det_exo_size);
1631     memcpy(&nb_col_det_exo_jacob, code, sizeof(nb_col_det_exo_jacob)); code += sizeof(nb_col_det_exo_jacob);
1632     memcpy(&exo_size, code, sizeof(exo_size)); code += sizeof(exo_size);
1633     memcpy(&nb_col_exo_jacob, code, sizeof(nb_col_exo_jacob)); code += sizeof(nb_col_exo_jacob);
1634     memcpy(&other_endo_size, code, sizeof(other_endo_size)); code += sizeof(other_endo_size);
1635     memcpy(&nb_col_other_endo_jacob, code, sizeof(nb_col_other_endo_jacob)); code += sizeof(nb_col_other_endo_jacob);
1636 
1637     for (unsigned int i = 0; i < det_exo_size; i++)
1638       {
1639         unsigned int tmp_i;
1640         memcpy(&tmp_i, code, sizeof(tmp_i)); code += sizeof(tmp_i);
1641         det_exogenous.push_back(tmp_i);
1642       }
1643     for (unsigned int i = 0; i < exo_size; i++)
1644       {
1645         unsigned int tmp_i;
1646         memcpy(&tmp_i, code, sizeof(tmp_i)); code += sizeof(tmp_i);
1647         exogenous.push_back(tmp_i);
1648       }
1649     for (unsigned int i = 0; i < other_endo_size; i++)
1650       {
1651         unsigned int tmp_i;
1652         memcpy(&tmp_i, code, sizeof(tmp_i)); code += sizeof(tmp_i);
1653         other_endogenous.push_back(tmp_i);
1654       }
1655     return code;
1656   };
1657 #endif
1658 };
1659 
1660 #ifdef BYTE_CODE
1661 using tags_liste_t = vector<pair<Tags, void * >>;
1662 class CodeLoad
1663 {
1664 private:
1665   uint8_t *code;
1666   unsigned int nb_blocks;
1667   vector<size_t> begin_block;
1668 public:
1669 
1670   inline unsigned int
get_block_number()1671   get_block_number()
1672   {
1673     return nb_blocks;
1674   };
1675 
1676   size_t inline
get_begin_block(int block)1677   get_begin_block(int block)
1678   {
1679     return begin_block[block];
1680   }
1681   inline void *
get_current_code()1682   get_current_code()
1683   {
1684     return code;
1685   };
1686   inline tags_liste_t
get_op_code(string file_name)1687   get_op_code(string file_name)
1688   {
1689     tags_liste_t tags_liste;
1690     ifstream CompiledCode;
1691     streamoff Code_Size;
1692     CompiledCode.open(file_name + ".cod", std::ios::in | std::ios::binary| std::ios::ate);
1693     if (!CompiledCode.is_open())
1694       {
1695         return tags_liste;
1696       }
1697     Code_Size = CompiledCode.tellg();
1698     CompiledCode.seekg(std::ios::beg);
1699     code = static_cast<uint8_t *>(mxMalloc(Code_Size));
1700     CompiledCode.seekg(0);
1701     CompiledCode.read(reinterpret_cast<char *>(code), Code_Size);
1702     CompiledCode.close();
1703     nb_blocks = 0;
1704     bool done = false;
1705     int instruction = 0;
1706     while (!done)
1707       {
1708         switch (*code)
1709           {
1710           case FLDZ:
1711 # ifdef DEBUGL
1712             mexPrintf("FLDZ = %d size = %d\n", FLDZ, sizeof(FLDZ_));
1713 # endif
1714             tags_liste.emplace_back(FLDZ, code);
1715             code += sizeof(FLDZ_);
1716             break;
1717           case FEND:
1718 # ifdef DEBUGL
1719             mexPrintf("FEND\n");
1720 # endif
1721             tags_liste.emplace_back(FEND, code);
1722             code += sizeof(FEND_);
1723             done = true;
1724             break;
1725           case FENDBLOCK:
1726 # ifdef DEBUGL
1727             mexPrintf("FENDBLOCK\n");
1728 # endif
1729             tags_liste.emplace_back(FENDBLOCK, code);
1730             code += sizeof(FENDBLOCK_);
1731             break;
1732           case FENDEQU:
1733 # ifdef DEBUGL
1734             mexPrintf("FENDEQU\n");
1735 # endif
1736             tags_liste.emplace_back(FENDEQU, code);
1737             code += sizeof(FENDEQU_);
1738             break;
1739           case FCUML:
1740 # ifdef DEBUGL
1741             mexPrintf("FCUML\n");
1742 # endif
1743             tags_liste.emplace_back(FCUML, code);
1744             code += sizeof(FCUML_);
1745             break;
1746           case FDIMT:
1747 # ifdef DEBUGL
1748             mexPrintf("FDIMT = %d size = %d\n", FDIMT, sizeof(FDIMT_));
1749 # endif
1750             tags_liste.emplace_back(FDIMT, code);
1751             code += sizeof(FDIMT_);
1752             break;
1753           case FDIMST:
1754 # ifdef DEBUGL
1755             mexPrintf("FDIMST\n");
1756 # endif
1757             tags_liste.emplace_back(FDIMST, code);
1758             code += sizeof(FDIMST_);
1759             break;
1760           case FNUMEXPR:
1761 # ifdef DEBUGL
1762             mexPrintf("FNUMEXPR\n");
1763 # endif
1764             tags_liste.emplace_back(FNUMEXPR, code);
1765             code += sizeof(FNUMEXPR_);
1766             break;
1767           case FLDC:
1768 # ifdef DEBUGL
1769             mexPrintf("FLDC\n");
1770 # endif
1771             tags_liste.emplace_back(FLDC, code);
1772             code += sizeof(FLDC_);
1773             break;
1774           case FLDU:
1775 # ifdef DEBUGL
1776             mexPrintf("FLDU\n");
1777 # endif
1778             tags_liste.emplace_back(FLDU, code);
1779             code += sizeof(FLDU_);
1780             break;
1781           case FLDSU:
1782 # ifdef DEBUGL
1783             mexPrintf("FLDSU\n");
1784 # endif
1785             tags_liste.emplace_back(FLDSU, code);
1786             code += sizeof(FLDSU_);
1787             break;
1788           case FLDR:
1789 # ifdef DEBUGL
1790             mexPrintf("FLDR\n");
1791 # endif
1792             tags_liste.emplace_back(FLDR, code);
1793             code += sizeof(FLDR_);
1794             break;
1795           case FLDT:
1796 # ifdef DEBUGL
1797             mexPrintf("FLDT\n");
1798 # endif
1799             tags_liste.emplace_back(FLDT, code);
1800             code += sizeof(FLDT_);
1801             break;
1802           case FLDST:
1803 # ifdef DEBUGL
1804             mexPrintf("FLDST\n");
1805 # endif
1806             tags_liste.emplace_back(FLDST, code);
1807             code += sizeof(FLDST_);
1808             break;
1809           case FSTPT:
1810 # ifdef DEBUGL
1811             mexPrintf("FSTPT = %d size = %d\n", FSTPT, sizeof(FSTPT_));
1812 # endif
1813             tags_liste.emplace_back(FSTPT, code);
1814             code += sizeof(FSTPT_);
1815             break;
1816           case FSTPST:
1817 # ifdef DEBUGL
1818             mexPrintf("FSTPST\n");
1819 # endif
1820             tags_liste.emplace_back(FSTPST, code);
1821             code += sizeof(FSTPST_);
1822             break;
1823           case FSTPR:
1824 # ifdef DEBUGL
1825             mexPrintf("FSTPR\n");
1826 # endif
1827             tags_liste.emplace_back(FSTPR, code);
1828             code += sizeof(FSTPR_);
1829             break;
1830           case FSTPU:
1831 # ifdef DEBUGL
1832             mexPrintf("FSTPU\n");
1833 # endif
1834             tags_liste.emplace_back(FSTPU, code);
1835             code += sizeof(FSTPU_);
1836             break;
1837           case FSTPSU:
1838 # ifdef DEBUGL
1839             mexPrintf("FSTPSU\n");
1840 # endif
1841             tags_liste.emplace_back(FSTPSU, code);
1842             code += sizeof(FSTPSU_);
1843             break;
1844           case FSTPG:
1845 # ifdef DEBUGL
1846             mexPrintf("FSTPG\n");
1847 # endif
1848             tags_liste.emplace_back(FSTPG, code);
1849             code += sizeof(FSTPG_);
1850             break;
1851           case FSTPG2:
1852 # ifdef DEBUGL
1853             mexPrintf("FSTPG2\n");
1854 # endif
1855             tags_liste.emplace_back(FSTPG2, code);
1856             code += sizeof(FSTPG2_);
1857             break;
1858           case FSTPG3:
1859 # ifdef DEBUGL
1860             mexPrintf("FSTPG3\n");
1861 # endif
1862             tags_liste.emplace_back(FSTPG3, code);
1863             code += sizeof(FSTPG3_);
1864             break;
1865           case FUNARY:
1866 # ifdef DEBUGL
1867             mexPrintf("FUNARY\n");
1868 # endif
1869             tags_liste.emplace_back(FUNARY, code);
1870             code += sizeof(FUNARY_);
1871             break;
1872           case FBINARY:
1873 # ifdef DEBUGL
1874             mexPrintf("FBINARY\n");
1875 # endif
1876             tags_liste.emplace_back(FBINARY, code);
1877             code += sizeof(FBINARY_);
1878             break;
1879           case FTRINARY:
1880 # ifdef DEBUGL
1881             mexPrintf("FTRINARY\n");
1882 # endif
1883             tags_liste.emplace_back(FTRINARY, code);
1884             code += sizeof(FTRINARY_);
1885             break;
1886           case FOK:
1887 # ifdef DEBUGL
1888             mexPrintf("FOK\n");
1889 # endif
1890             tags_liste.emplace_back(FOK, code);
1891             code += sizeof(FOK_);
1892             break;
1893           case FLDVS:
1894 # ifdef DEBUGL
1895             mexPrintf("FLDVS\n");
1896 # endif
1897             tags_liste.emplace_back(FLDVS, code);
1898             code += sizeof(FLDVS_);
1899             break;
1900           case FLDSV:
1901 # ifdef DEBUGL
1902             mexPrintf("FLDSV\n");
1903 # endif
1904             tags_liste.emplace_back(FLDSV, code);
1905             code += sizeof(FLDSV_);
1906             break;
1907           case FSTPSV:
1908 # ifdef DEBUGL
1909             mexPrintf("FSTPSV\n");
1910 # endif
1911             tags_liste.emplace_back(FSTPSV, code);
1912             code += sizeof(FSTPSV_);
1913             break;
1914           case FLDV:
1915 # ifdef DEBUGL
1916             mexPrintf("FLDV\n");
1917 # endif
1918             tags_liste.emplace_back(FLDV, code);
1919             code += sizeof(FLDV_);
1920             break;
1921           case FSTPV:
1922 # ifdef DEBUGL
1923             mexPrintf("FSTPV\n");
1924 # endif
1925             tags_liste.emplace_back(FSTPV, code);
1926             code += sizeof(FSTPV_);
1927             break;
1928           case FBEGINBLOCK:
1929 # ifdef DEBUGL
1930             mexPrintf("FBEGINBLOCK\n");
1931 # endif
1932             {
1933               FBEGINBLOCK_ *fbegin_block = new FBEGINBLOCK_;
1934 
1935               code = fbegin_block->load(code);
1936 
1937               begin_block.push_back(tags_liste.size());
1938               tags_liste.emplace_back(FBEGINBLOCK, fbegin_block);
1939               nb_blocks++;
1940             }
1941             break;
1942           case FJMPIFEVAL:
1943 # ifdef DEBUGL
1944             mexPrintf("FJMPIFEVAL\n");
1945 # endif
1946             tags_liste.emplace_back(FJMPIFEVAL, code);
1947             code += sizeof(FJMPIFEVAL_);
1948             break;
1949           case FJMP:
1950 # ifdef DEBUGL
1951             mexPrintf("FJMP\n");
1952 # endif
1953             tags_liste.emplace_back(FJMP, code);
1954             code += sizeof(FJMP_);
1955             break;
1956           case FCALL:
1957             {
1958 # ifdef DEBUGL
1959               mexPrintf("FCALL\n");
1960 # endif
1961               FCALL_ *fcall = new FCALL_;
1962 
1963               code = fcall->load(code);
1964 
1965               tags_liste.emplace_back(FCALL, fcall);
1966 # ifdef DEBUGL
1967               mexPrintf("FCALL finish\n"); mexEvalString("drawnow;");
1968               mexPrintf("-- *code=%d\n", *code); mexEvalString("drawnow;");
1969 # endif
1970             }
1971             break;
1972           case FPUSH:
1973 # ifdef DEBUGL
1974             mexPrintf("FPUSH\n");
1975 # endif
1976             tags_liste.emplace_back(FPUSH, code);
1977             code += sizeof(FPUSH_);
1978             break;
1979           case FPOP:
1980 # ifdef DEBUGL
1981             mexPrintf("FPOP\n");
1982 # endif
1983             tags_liste.emplace_back(FPOP, code);
1984             code += sizeof(FPOP_);
1985             break;
1986           case FLDTEF:
1987 # ifdef DEBUGL
1988             mexPrintf("FLDTEF\n");
1989 # endif
1990             tags_liste.emplace_back(FLDTEF, code);
1991             code += sizeof(FLDTEF_);
1992             break;
1993           case FSTPTEF:
1994 # ifdef DEBUGL
1995             mexPrintf("FSTPTEF\n");
1996 # endif
1997             tags_liste.emplace_back(FSTPTEF, code);
1998             code += sizeof(FSTPTEF_);
1999             break;
2000           case FLDTEFD:
2001 # ifdef DEBUGL
2002             mexPrintf("FLDTEFD\n");
2003 # endif
2004             tags_liste.emplace_back(FLDTEFD, code);
2005             code += sizeof(FLDTEFD_);
2006             break;
2007           case FSTPTEFD:
2008 # ifdef DEBUGL
2009             mexPrintf("FSTPTEFD\n");
2010 # endif
2011             tags_liste.emplace_back(FSTPTEFD, code);
2012             code += sizeof(FSTPTEFD_);
2013             break;
2014           case FLDTEFDD:
2015 # ifdef DEBUGL
2016             mexPrintf("FLDTEFDD\n");
2017 # endif
2018             tags_liste.emplace_back(FLDTEFDD, code);
2019             code += sizeof(FLDTEFDD_);
2020             break;
2021           case FSTPTEFDD:
2022 # ifdef DEBUGL
2023             mexPrintf("FSTPTEFDD\n");
2024 # endif
2025             tags_liste.emplace_back(FSTPTEFDD, code);
2026             code += sizeof(FSTPTEFDD_);
2027             break;
2028           default:
2029             mexPrintf("Unknown Tag value=%d code=%x\n", *code, code);
2030             done = true;
2031           }
2032         instruction++;
2033       }
2034     return tags_liste;
2035   };
2036 };
2037 #endif
2038 #pragma pack(pop)
2039 #endif
2040