Move bytecode stuff into a dedicated namespace, for better code separation
parent
1c10a3acbf
commit
22709f8225
|
@ -24,7 +24,10 @@
|
||||||
|
|
||||||
#include "Bytecode.hh"
|
#include "Bytecode.hh"
|
||||||
|
|
||||||
BytecodeWriter::BytecodeWriter(const filesystem::path& filename)
|
namespace Bytecode
|
||||||
|
{
|
||||||
|
|
||||||
|
Writer::Writer(const filesystem::path& filename)
|
||||||
{
|
{
|
||||||
open(filename, ios::out | ios::binary);
|
open(filename, ios::out | ios::binary);
|
||||||
if (!is_open())
|
if (!is_open())
|
||||||
|
@ -35,8 +38,8 @@ BytecodeWriter::BytecodeWriter(const filesystem::path& filename)
|
||||||
}
|
}
|
||||||
|
|
||||||
template<>
|
template<>
|
||||||
BytecodeWriter&
|
Writer&
|
||||||
operator<<(BytecodeWriter& code_file, const FCALL_& instr)
|
operator<<(Writer& code_file, const FCALL_& instr)
|
||||||
{
|
{
|
||||||
code_file.instructions_positions.push_back(code_file.tellp());
|
code_file.instructions_positions.push_back(code_file.tellp());
|
||||||
|
|
||||||
|
@ -65,8 +68,8 @@ operator<<(BytecodeWriter& code_file, const FCALL_& instr)
|
||||||
}
|
}
|
||||||
|
|
||||||
template<>
|
template<>
|
||||||
BytecodeWriter&
|
Writer&
|
||||||
operator<<(BytecodeWriter& code_file, const FBEGINBLOCK_& instr)
|
operator<<(Writer& code_file, const FBEGINBLOCK_& instr)
|
||||||
{
|
{
|
||||||
code_file.instructions_positions.push_back(code_file.tellp());
|
code_file.instructions_positions.push_back(code_file.tellp());
|
||||||
|
|
||||||
|
@ -99,3 +102,5 @@ operator<<(BytecodeWriter& code_file, const FBEGINBLOCK_& instr)
|
||||||
|
|
||||||
return code_file;
|
return code_file;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
|
@ -31,7 +31,10 @@
|
||||||
|
|
||||||
using namespace std;
|
using namespace std;
|
||||||
|
|
||||||
// The different opcodes of bytecode
|
namespace Bytecode
|
||||||
|
{
|
||||||
|
|
||||||
|
// The different tags encoding a bytecode instruction
|
||||||
enum class Tags
|
enum class Tags
|
||||||
{
|
{
|
||||||
FLDZ, // Loads a zero onto the stack
|
FLDZ, // Loads a zero onto the stack
|
||||||
|
@ -124,12 +127,12 @@ struct Block_contain_type
|
||||||
int Equation, Variable, Own_Derivative;
|
int Equation, Variable, Own_Derivative;
|
||||||
};
|
};
|
||||||
|
|
||||||
class BytecodeWriter;
|
class Writer;
|
||||||
|
|
||||||
struct BytecodeInstruction
|
struct Instruction
|
||||||
{
|
{
|
||||||
const Tags op_code;
|
const Tags op_code;
|
||||||
explicit BytecodeInstruction(Tags op_code_arg) : op_code {op_code_arg}
|
explicit Instruction(Tags op_code_arg) : op_code {op_code_arg}
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -139,28 +142,27 @@ protected:
|
||||||
would no longer be POD; its memory representation would also include
|
would no longer be POD; its memory representation would also include
|
||||||
runtime type information, and our crude serialization technique (copying the
|
runtime type information, and our crude serialization technique (copying the
|
||||||
whole object from memory) would thus not work. */
|
whole object from memory) would thus not work. */
|
||||||
~BytecodeInstruction() = default;
|
~Instruction() = default;
|
||||||
};
|
};
|
||||||
|
|
||||||
template<typename T1>
|
template<typename T1>
|
||||||
class TagWithOneArgument : public BytecodeInstruction
|
class TagWithOneArgument : public Instruction
|
||||||
{
|
{
|
||||||
protected:
|
protected:
|
||||||
T1 arg1;
|
T1 arg1;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
TagWithOneArgument(Tags op_code_arg, T1 arg_arg1) :
|
TagWithOneArgument(Tags op_code_arg, T1 arg_arg1) : Instruction {op_code_arg}, arg1 {arg_arg1}
|
||||||
BytecodeInstruction {op_code_arg}, arg1 {arg_arg1}
|
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
// See BytecodeInstruction destructor for the rationale
|
// See Instruction destructor for the rationale
|
||||||
~TagWithOneArgument() = default;
|
~TagWithOneArgument() = default;
|
||||||
};
|
};
|
||||||
|
|
||||||
template<typename T1, typename T2>
|
template<typename T1, typename T2>
|
||||||
class TagWithTwoArguments : public BytecodeInstruction
|
class TagWithTwoArguments : public Instruction
|
||||||
{
|
{
|
||||||
protected:
|
protected:
|
||||||
T1 arg1;
|
T1 arg1;
|
||||||
|
@ -168,17 +170,17 @@ protected:
|
||||||
|
|
||||||
public:
|
public:
|
||||||
TagWithTwoArguments(Tags op_code_arg, T1 arg_arg1, T2 arg_arg2) :
|
TagWithTwoArguments(Tags op_code_arg, T1 arg_arg1, T2 arg_arg2) :
|
||||||
BytecodeInstruction {op_code_arg}, arg1 {arg_arg1}, arg2 {arg_arg2}
|
Instruction {op_code_arg}, arg1 {arg_arg1}, arg2 {arg_arg2}
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
// See BytecodeInstruction destructor for the rationale
|
// See Instruction destructor for the rationale
|
||||||
~TagWithTwoArguments() = default;
|
~TagWithTwoArguments() = default;
|
||||||
};
|
};
|
||||||
|
|
||||||
template<typename T1, typename T2, typename T3>
|
template<typename T1, typename T2, typename T3>
|
||||||
class TagWithThreeArguments : public BytecodeInstruction
|
class TagWithThreeArguments : public Instruction
|
||||||
{
|
{
|
||||||
protected:
|
protected:
|
||||||
T1 arg1;
|
T1 arg1;
|
||||||
|
@ -187,17 +189,17 @@ protected:
|
||||||
|
|
||||||
public:
|
public:
|
||||||
TagWithThreeArguments(Tags op_code_arg, T1 arg_arg1, T2 arg_arg2, T3 arg_arg3) :
|
TagWithThreeArguments(Tags op_code_arg, T1 arg_arg1, T2 arg_arg2, T3 arg_arg3) :
|
||||||
BytecodeInstruction {op_code_arg}, arg1 {arg_arg1}, arg2 {arg_arg2}, arg3 {arg_arg3}
|
Instruction {op_code_arg}, arg1 {arg_arg1}, arg2 {arg_arg2}, arg3 {arg_arg3}
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
// See BytecodeInstruction destructor for the rationale
|
// See Instruction destructor for the rationale
|
||||||
~TagWithThreeArguments() = default;
|
~TagWithThreeArguments() = default;
|
||||||
};
|
};
|
||||||
|
|
||||||
template<typename T1, typename T2, typename T3, typename T4>
|
template<typename T1, typename T2, typename T3, typename T4>
|
||||||
class TagWithFourArguments : public BytecodeInstruction
|
class TagWithFourArguments : public Instruction
|
||||||
{
|
{
|
||||||
protected:
|
protected:
|
||||||
T1 arg1;
|
T1 arg1;
|
||||||
|
@ -207,7 +209,7 @@ protected:
|
||||||
|
|
||||||
public:
|
public:
|
||||||
TagWithFourArguments(Tags op_code_arg, T1 arg_arg1, T2 arg_arg2, T3 arg_arg3, T4 arg_arg4) :
|
TagWithFourArguments(Tags op_code_arg, T1 arg_arg1, T2 arg_arg2, T3 arg_arg3, T4 arg_arg4) :
|
||||||
BytecodeInstruction {op_code_arg},
|
Instruction {op_code_arg},
|
||||||
arg1 {arg_arg1},
|
arg1 {arg_arg1},
|
||||||
arg2 {arg_arg2},
|
arg2 {arg_arg2},
|
||||||
arg3 {move(arg_arg3)},
|
arg3 {move(arg_arg3)},
|
||||||
|
@ -216,38 +218,38 @@ public:
|
||||||
}
|
}
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
// See BytecodeInstruction destructor for the rationale
|
// See Instruction destructor for the rationale
|
||||||
~TagWithFourArguments() = default;
|
~TagWithFourArguments() = default;
|
||||||
};
|
};
|
||||||
|
|
||||||
class FLDZ_ final : public BytecodeInstruction
|
class FLDZ_ final : public Instruction
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FLDZ_() : BytecodeInstruction {Tags::FLDZ}
|
FLDZ_() : Instruction {Tags::FLDZ}
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
class FEND_ final : public BytecodeInstruction
|
class FEND_ final : public Instruction
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FEND_() : BytecodeInstruction {Tags::FEND}
|
FEND_() : Instruction {Tags::FEND}
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
class FENDBLOCK_ final : public BytecodeInstruction
|
class FENDBLOCK_ final : public Instruction
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FENDBLOCK_() : BytecodeInstruction {Tags::FENDBLOCK}
|
FENDBLOCK_() : Instruction {Tags::FENDBLOCK}
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
class FENDEQU_ final : public BytecodeInstruction
|
class FENDEQU_ final : public Instruction
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FENDEQU_() : BytecodeInstruction {Tags::FENDEQU}
|
FENDEQU_() : Instruction {Tags::FENDEQU}
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
@ -768,10 +770,10 @@ public:
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
class FCALL_ final : public BytecodeInstruction
|
class FCALL_ final : public Instruction
|
||||||
{
|
{
|
||||||
template<typename B>
|
template<typename B>
|
||||||
friend BytecodeWriter& operator<<(BytecodeWriter& code_file, const B& instr);
|
friend Writer& operator<<(Writer& code_file, const B& instr);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
int nb_output_arguments, nb_input_arguments, indx;
|
int nb_output_arguments, nb_input_arguments, indx;
|
||||||
|
@ -783,7 +785,7 @@ private:
|
||||||
public:
|
public:
|
||||||
FCALL_(int nb_output_arguments_arg, int nb_input_arguments_arg, string func_name_arg,
|
FCALL_(int nb_output_arguments_arg, int nb_input_arguments_arg, string func_name_arg,
|
||||||
int indx_arg, ExternalFunctionCallType call_type_arg) :
|
int indx_arg, ExternalFunctionCallType call_type_arg) :
|
||||||
BytecodeInstruction {Tags::FCALL},
|
Instruction {Tags::FCALL},
|
||||||
nb_output_arguments {nb_output_arguments_arg},
|
nb_output_arguments {nb_output_arguments_arg},
|
||||||
nb_input_arguments {nb_input_arguments_arg},
|
nb_input_arguments {nb_input_arguments_arg},
|
||||||
indx {indx_arg},
|
indx {indx_arg},
|
||||||
|
@ -793,7 +795,7 @@ public:
|
||||||
}
|
}
|
||||||
/* Deserializing constructor.
|
/* Deserializing constructor.
|
||||||
Updates the code pointer to point beyond the bytes read. */
|
Updates the code pointer to point beyond the bytes read. */
|
||||||
FCALL_(char*& code) : BytecodeInstruction {Tags::FCALL}
|
FCALL_(char*& code) : Instruction {Tags::FCALL}
|
||||||
{
|
{
|
||||||
code += sizeof(op_code);
|
code += sizeof(op_code);
|
||||||
|
|
||||||
|
@ -888,7 +890,7 @@ public:
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
class FNUMEXPR_ final : public BytecodeInstruction
|
class FNUMEXPR_ final : public Instruction
|
||||||
{
|
{
|
||||||
private:
|
private:
|
||||||
ExpressionType expression_type;
|
ExpressionType expression_type;
|
||||||
|
@ -898,7 +900,7 @@ private:
|
||||||
int lag1; // For derivatives, lead/lag of the derivation variable
|
int lag1; // For derivatives, lead/lag of the derivation variable
|
||||||
public:
|
public:
|
||||||
FNUMEXPR_(const ExpressionType expression_type_arg, int equation_arg) :
|
FNUMEXPR_(const ExpressionType expression_type_arg, int equation_arg) :
|
||||||
BytecodeInstruction {Tags::FNUMEXPR},
|
Instruction {Tags::FNUMEXPR},
|
||||||
expression_type {expression_type_arg},
|
expression_type {expression_type_arg},
|
||||||
equation {equation_arg},
|
equation {equation_arg},
|
||||||
dvariable1 {0},
|
dvariable1 {0},
|
||||||
|
@ -906,7 +908,7 @@ public:
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
FNUMEXPR_(const ExpressionType expression_type_arg, int equation_arg, int dvariable1_arg) :
|
FNUMEXPR_(const ExpressionType expression_type_arg, int equation_arg, int dvariable1_arg) :
|
||||||
BytecodeInstruction {Tags::FNUMEXPR},
|
Instruction {Tags::FNUMEXPR},
|
||||||
expression_type {expression_type_arg},
|
expression_type {expression_type_arg},
|
||||||
equation {equation_arg},
|
equation {equation_arg},
|
||||||
dvariable1 {dvariable1_arg},
|
dvariable1 {dvariable1_arg},
|
||||||
|
@ -915,7 +917,7 @@ public:
|
||||||
}
|
}
|
||||||
FNUMEXPR_(const ExpressionType expression_type_arg, int equation_arg, int dvariable1_arg,
|
FNUMEXPR_(const ExpressionType expression_type_arg, int equation_arg, int dvariable1_arg,
|
||||||
int lag1_arg) :
|
int lag1_arg) :
|
||||||
BytecodeInstruction {Tags::FNUMEXPR},
|
Instruction {Tags::FNUMEXPR},
|
||||||
expression_type {expression_type_arg},
|
expression_type {expression_type_arg},
|
||||||
equation {equation_arg},
|
equation {equation_arg},
|
||||||
dvariable1 {dvariable1_arg},
|
dvariable1 {dvariable1_arg},
|
||||||
|
@ -944,10 +946,10 @@ public:
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
class FBEGINBLOCK_ final : public BytecodeInstruction
|
class FBEGINBLOCK_ final : public Instruction
|
||||||
{
|
{
|
||||||
template<typename B>
|
template<typename B>
|
||||||
friend BytecodeWriter& operator<<(BytecodeWriter& code_file, const B& instr);
|
friend Writer& operator<<(Writer& code_file, const B& instr);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
int size {0};
|
int size {0};
|
||||||
|
@ -970,7 +972,7 @@ public:
|
||||||
const vector<int>& variable_arg, const vector<int>& equation_arg, bool is_linear_arg,
|
const vector<int>& variable_arg, const vector<int>& equation_arg, bool is_linear_arg,
|
||||||
int u_count_int_arg, int nb_col_jacob_arg, int det_exo_size_arg, int exo_size_arg,
|
int u_count_int_arg, int nb_col_jacob_arg, int det_exo_size_arg, int exo_size_arg,
|
||||||
vector<int> det_exogenous_arg, vector<int> exogenous_arg) :
|
vector<int> det_exogenous_arg, vector<int> exogenous_arg) :
|
||||||
BytecodeInstruction {Tags::FBEGINBLOCK},
|
Instruction {Tags::FBEGINBLOCK},
|
||||||
size {size_arg},
|
size {size_arg},
|
||||||
type {type_arg},
|
type {type_arg},
|
||||||
variable {variable_arg.begin() + first_element,
|
variable {variable_arg.begin() + first_element,
|
||||||
|
@ -990,7 +992,7 @@ public:
|
||||||
FBEGINBLOCK_(int size_arg, BlockSimulationType type_arg, int first_element, int block_size,
|
FBEGINBLOCK_(int size_arg, BlockSimulationType type_arg, int first_element, int block_size,
|
||||||
const vector<int>& variable_arg, const vector<int>& equation_arg, bool is_linear_arg,
|
const vector<int>& variable_arg, const vector<int>& equation_arg, bool is_linear_arg,
|
||||||
int u_count_int_arg, int nb_col_jacob_arg) :
|
int u_count_int_arg, int nb_col_jacob_arg) :
|
||||||
BytecodeInstruction {Tags::FBEGINBLOCK},
|
Instruction {Tags::FBEGINBLOCK},
|
||||||
size {size_arg},
|
size {size_arg},
|
||||||
type {type_arg},
|
type {type_arg},
|
||||||
variable {variable_arg.begin() + first_element,
|
variable {variable_arg.begin() + first_element,
|
||||||
|
@ -1006,7 +1008,7 @@ public:
|
||||||
}
|
}
|
||||||
/* Deserializing constructor.
|
/* Deserializing constructor.
|
||||||
Updates the code pointer to point beyond the bytes read. */
|
Updates the code pointer to point beyond the bytes read. */
|
||||||
FBEGINBLOCK_(char*& code) : BytecodeInstruction {Tags::FBEGINBLOCK}
|
FBEGINBLOCK_(char*& code) : Instruction {Tags::FBEGINBLOCK}
|
||||||
{
|
{
|
||||||
code += sizeof(op_code);
|
code += sizeof(op_code);
|
||||||
|
|
||||||
|
@ -1103,17 +1105,17 @@ public:
|
||||||
};
|
};
|
||||||
|
|
||||||
// Superclass of std::ofstream for writing a sequence of bytecode instructions
|
// Superclass of std::ofstream for writing a sequence of bytecode instructions
|
||||||
class BytecodeWriter : private ofstream
|
class Writer : private ofstream
|
||||||
{
|
{
|
||||||
template<typename B>
|
template<typename B>
|
||||||
friend BytecodeWriter& operator<<(BytecodeWriter& code_file, const B& instr);
|
friend Writer& operator<<(Writer& code_file, const B& instr);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
// Stores the positions of all instructions in the byte stream
|
// Stores the positions of all instructions in the byte stream
|
||||||
vector<pos_type> instructions_positions;
|
vector<pos_type> instructions_positions;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
BytecodeWriter(const filesystem::path& filename);
|
Writer(const filesystem::path& filename);
|
||||||
// Returns the number of the next instruction to be written
|
// Returns the number of the next instruction to be written
|
||||||
int
|
int
|
||||||
getInstructionCounter() const
|
getInstructionCounter() const
|
||||||
|
@ -1137,8 +1139,8 @@ public:
|
||||||
// Overloads of operator<< for writing bytecode instructions
|
// Overloads of operator<< for writing bytecode instructions
|
||||||
|
|
||||||
template<typename B>
|
template<typename B>
|
||||||
BytecodeWriter&
|
Writer&
|
||||||
operator<<(BytecodeWriter& code_file, const B& instr)
|
operator<<(Writer& code_file, const B& instr)
|
||||||
{
|
{
|
||||||
code_file.instructions_positions.push_back(code_file.tellp());
|
code_file.instructions_positions.push_back(code_file.tellp());
|
||||||
code_file.write(reinterpret_cast<const char*>(&instr), sizeof(B));
|
code_file.write(reinterpret_cast<const char*>(&instr), sizeof(B));
|
||||||
|
@ -1146,9 +1148,11 @@ operator<<(BytecodeWriter& code_file, const B& instr)
|
||||||
}
|
}
|
||||||
|
|
||||||
template<>
|
template<>
|
||||||
BytecodeWriter& operator<<(BytecodeWriter& code_file, const FCALL_& instr);
|
Writer& operator<<(Writer& code_file, const FCALL_& instr);
|
||||||
|
|
||||||
template<>
|
template<>
|
||||||
BytecodeWriter& operator<<(BytecodeWriter& code_file, const FBEGINBLOCK_& instr);
|
Writer& operator<<(Writer& code_file, const FBEGINBLOCK_& instr);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -164,11 +164,11 @@ DynamicModel::writeDynamicBytecode(const string& basename) const
|
||||||
writeBytecodeBinFile(basename + "/model/bytecode/dynamic.bin",
|
writeBytecodeBinFile(basename + "/model/bytecode/dynamic.bin",
|
||||||
simulation_type == BlockSimulationType::solveTwoBoundariesComplete)};
|
simulation_type == BlockSimulationType::solveTwoBoundariesComplete)};
|
||||||
|
|
||||||
BytecodeWriter code_file {basename + "/model/bytecode/dynamic.cod"};
|
Bytecode::Writer code_file {basename + "/model/bytecode/dynamic.cod"};
|
||||||
|
|
||||||
// Declare temporary terms
|
// Declare temporary terms
|
||||||
code_file << FDIMT_ {static_cast<int>(temporary_terms_derivatives[0].size()
|
code_file << Bytecode::FDIMT_ {static_cast<int>(temporary_terms_derivatives[0].size()
|
||||||
+ temporary_terms_derivatives[1].size())};
|
+ temporary_terms_derivatives[1].size())};
|
||||||
|
|
||||||
// Declare the (single) block
|
// Declare the (single) block
|
||||||
vector<int> exo(symbol_table.exo_nbr()), exo_det(symbol_table.exo_det_nbr());
|
vector<int> exo(symbol_table.exo_nbr()), exo_det(symbol_table.exo_det_nbr());
|
||||||
|
@ -183,19 +183,19 @@ DynamicModel::writeDynamicBytecode(const string& basename) const
|
||||||
vector<int> endo_idx(symbol_table.endo_nbr());
|
vector<int> endo_idx(symbol_table.endo_nbr());
|
||||||
iota(endo_idx.begin(), endo_idx.end(), 0);
|
iota(endo_idx.begin(), endo_idx.end(), 0);
|
||||||
|
|
||||||
code_file << FBEGINBLOCK_ {symbol_table.endo_nbr(),
|
code_file << Bytecode::FBEGINBLOCK_ {symbol_table.endo_nbr(),
|
||||||
simulation_type,
|
simulation_type,
|
||||||
0,
|
0,
|
||||||
symbol_table.endo_nbr(),
|
symbol_table.endo_nbr(),
|
||||||
endo_idx,
|
endo_idx,
|
||||||
eq_idx,
|
eq_idx,
|
||||||
false,
|
false,
|
||||||
u_count_int,
|
u_count_int,
|
||||||
jacobian_ncols_endo,
|
jacobian_ncols_endo,
|
||||||
symbol_table.exo_det_nbr(),
|
symbol_table.exo_det_nbr(),
|
||||||
symbol_table.exo_nbr(),
|
symbol_table.exo_nbr(),
|
||||||
exo_det,
|
exo_det,
|
||||||
exo};
|
exo};
|
||||||
|
|
||||||
writeBytecodeHelper<true>(code_file);
|
writeBytecodeHelper<true>(code_file);
|
||||||
}
|
}
|
||||||
|
@ -203,7 +203,7 @@ DynamicModel::writeDynamicBytecode(const string& basename) const
|
||||||
void
|
void
|
||||||
DynamicModel::writeDynamicBlockBytecode(const string& basename) const
|
DynamicModel::writeDynamicBlockBytecode(const string& basename) const
|
||||||
{
|
{
|
||||||
BytecodeWriter code_file {basename + "/model/bytecode/block/dynamic.cod"};
|
Bytecode::Writer code_file {basename + "/model/bytecode/block/dynamic.cod"};
|
||||||
|
|
||||||
const filesystem::path bin_filename {basename + "/model/bytecode/block/dynamic.bin"};
|
const filesystem::path bin_filename {basename + "/model/bytecode/block/dynamic.bin"};
|
||||||
ofstream bin_file {bin_filename, ios::out | ios::binary};
|
ofstream bin_file {bin_filename, ios::out | ios::binary};
|
||||||
|
@ -214,7 +214,7 @@ DynamicModel::writeDynamicBlockBytecode(const string& basename) const
|
||||||
}
|
}
|
||||||
|
|
||||||
// Temporary variables declaration
|
// Temporary variables declaration
|
||||||
code_file << FDIMT_ {static_cast<int>(blocks_temporary_terms_idxs.size())};
|
code_file << Bytecode::FDIMT_ {static_cast<int>(blocks_temporary_terms_idxs.size())};
|
||||||
|
|
||||||
temporary_terms_t temporary_terms_written;
|
temporary_terms_t temporary_terms_written;
|
||||||
|
|
||||||
|
@ -231,19 +231,19 @@ DynamicModel::writeDynamicBlockBytecode(const string& basename) const
|
||||||
? writeBlockBytecodeBinFile(bin_file, block)
|
? writeBlockBytecodeBinFile(bin_file, block)
|
||||||
: 0};
|
: 0};
|
||||||
|
|
||||||
code_file << FBEGINBLOCK_ {blocks[block].mfs_size,
|
code_file << Bytecode::FBEGINBLOCK_ {blocks[block].mfs_size,
|
||||||
simulation_type,
|
simulation_type,
|
||||||
blocks[block].first_equation,
|
blocks[block].first_equation,
|
||||||
blocks[block].size,
|
blocks[block].size,
|
||||||
endo_idx_block2orig,
|
endo_idx_block2orig,
|
||||||
eq_idx_block2orig,
|
eq_idx_block2orig,
|
||||||
blocks[block].linear,
|
blocks[block].linear,
|
||||||
u_count,
|
u_count,
|
||||||
static_cast<int>(blocks_jacob_cols_endo[block].size())};
|
static_cast<int>(blocks_jacob_cols_endo[block].size())};
|
||||||
|
|
||||||
writeBlockBytecodeHelper<true>(code_file, block, temporary_terms_written);
|
writeBlockBytecodeHelper<true>(code_file, block, temporary_terms_written);
|
||||||
}
|
}
|
||||||
code_file << FEND_ {};
|
code_file << Bytecode::FEND_ {};
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
|
122
src/ExprNode.cc
122
src/ExprNode.cc
|
@ -144,7 +144,7 @@ ExprNode::checkIfTemporaryTermThenWrite(ostream& output, ExprNodeOutputType outp
|
||||||
|
|
||||||
bool
|
bool
|
||||||
ExprNode::checkIfTemporaryTermThenWriteBytecode(
|
ExprNode::checkIfTemporaryTermThenWriteBytecode(
|
||||||
BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs) const
|
const temporary_terms_idxs_t& temporary_terms_idxs) const
|
||||||
{
|
{
|
||||||
|
@ -163,10 +163,10 @@ ExprNode::checkIfTemporaryTermThenWriteBytecode(
|
||||||
was initially not called with steady_dynamic=true). */
|
was initially not called with steady_dynamic=true). */
|
||||||
return false;
|
return false;
|
||||||
case ExprNodeBytecodeOutputType::dynamicModel:
|
case ExprNodeBytecodeOutputType::dynamicModel:
|
||||||
code_file << FLDT_ {it2->second};
|
code_file << Bytecode::FLDT_ {it2->second};
|
||||||
break;
|
break;
|
||||||
case ExprNodeBytecodeOutputType::staticModel:
|
case ExprNodeBytecodeOutputType::staticModel:
|
||||||
code_file << FLDST_ {it2->second};
|
code_file << Bytecode::FLDST_ {it2->second};
|
||||||
break;
|
break;
|
||||||
case ExprNodeBytecodeOutputType::dynamicAssignmentLHS:
|
case ExprNodeBytecodeOutputType::dynamicAssignmentLHS:
|
||||||
case ExprNodeBytecodeOutputType::staticAssignmentLHS:
|
case ExprNodeBytecodeOutputType::staticAssignmentLHS:
|
||||||
|
@ -267,7 +267,7 @@ ExprNode::writeJsonExternalFunctionOutput([[maybe_unused]] vector<string>& efout
|
||||||
|
|
||||||
void
|
void
|
||||||
ExprNode::writeBytecodeExternalFunctionOutput(
|
ExprNode::writeBytecodeExternalFunctionOutput(
|
||||||
[[maybe_unused]] BytecodeWriter& code_file,
|
[[maybe_unused]] Bytecode::Writer& code_file,
|
||||||
[[maybe_unused]] ExprNodeBytecodeOutputType output_type,
|
[[maybe_unused]] ExprNodeBytecodeOutputType output_type,
|
||||||
[[maybe_unused]] const temporary_terms_t& temporary_terms,
|
[[maybe_unused]] const temporary_terms_t& temporary_terms,
|
||||||
[[maybe_unused]] const temporary_terms_idxs_t& temporary_terms_idxs,
|
[[maybe_unused]] const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
|
@ -556,7 +556,8 @@ NumConstNode::eval([[maybe_unused]] const eval_context_t& eval_context) const no
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
NumConstNode::writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
NumConstNode::writeBytecodeOutput(Bytecode::Writer& code_file,
|
||||||
|
ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
[[maybe_unused]] const deriv_node_temp_terms_t& tef_terms) const
|
[[maybe_unused]] const deriv_node_temp_terms_t& tef_terms) const
|
||||||
|
@ -564,7 +565,7 @@ NumConstNode::writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOut
|
||||||
assert(!isAssignmentLHSBytecodeOutput(output_type));
|
assert(!isAssignmentLHSBytecodeOutput(output_type));
|
||||||
if (!checkIfTemporaryTermThenWriteBytecode(code_file, output_type, temporary_terms,
|
if (!checkIfTemporaryTermThenWriteBytecode(code_file, output_type, temporary_terms,
|
||||||
temporary_terms_idxs))
|
temporary_terms_idxs))
|
||||||
code_file << FLDC_ {datatree.num_constants.getDouble(id)};
|
code_file << Bytecode::FLDC_ {datatree.num_constants.getDouble(id)};
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
@ -1431,7 +1432,8 @@ VariableNode::eval(const eval_context_t& eval_context) const noexcept(false)
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
VariableNode::writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
VariableNode::writeBytecodeOutput(Bytecode::Writer& code_file,
|
||||||
|
ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const
|
const deriv_node_temp_terms_t& tef_terms) const
|
||||||
|
@ -1450,19 +1452,19 @@ VariableNode::writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOut
|
||||||
switch (output_type)
|
switch (output_type)
|
||||||
{
|
{
|
||||||
case ExprNodeBytecodeOutputType::dynamicModel:
|
case ExprNodeBytecodeOutputType::dynamicModel:
|
||||||
code_file << FLDV_ {type, tsid, lag};
|
code_file << Bytecode::FLDV_ {type, tsid, lag};
|
||||||
break;
|
break;
|
||||||
case ExprNodeBytecodeOutputType::staticModel:
|
case ExprNodeBytecodeOutputType::staticModel:
|
||||||
code_file << FLDSV_ {type, tsid};
|
code_file << Bytecode::FLDSV_ {type, tsid};
|
||||||
break;
|
break;
|
||||||
case ExprNodeBytecodeOutputType::dynamicSteadyStateOperator:
|
case ExprNodeBytecodeOutputType::dynamicSteadyStateOperator:
|
||||||
code_file << FLDVS_ {type, tsid};
|
code_file << Bytecode::FLDVS_ {type, tsid};
|
||||||
break;
|
break;
|
||||||
case ExprNodeBytecodeOutputType::dynamicAssignmentLHS:
|
case ExprNodeBytecodeOutputType::dynamicAssignmentLHS:
|
||||||
code_file << FSTPV_ {type, tsid, lag};
|
code_file << Bytecode::FSTPV_ {type, tsid, lag};
|
||||||
break;
|
break;
|
||||||
case ExprNodeBytecodeOutputType::staticAssignmentLHS:
|
case ExprNodeBytecodeOutputType::staticAssignmentLHS:
|
||||||
code_file << FSTPSV_ {type, tsid};
|
code_file << Bytecode::FSTPSV_ {type, tsid};
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -3160,7 +3162,7 @@ UnaryOpNode::writeJsonExternalFunctionOutput(vector<string>& efout,
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
UnaryOpNode::writeBytecodeExternalFunctionOutput(BytecodeWriter& code_file,
|
UnaryOpNode::writeBytecodeExternalFunctionOutput(Bytecode::Writer& code_file,
|
||||||
ExprNodeBytecodeOutputType output_type,
|
ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
|
@ -3250,7 +3252,8 @@ UnaryOpNode::eval(const eval_context_t& eval_context) const noexcept(false)
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
UnaryOpNode::writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
UnaryOpNode::writeBytecodeOutput(Bytecode::Writer& code_file,
|
||||||
|
ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const
|
const deriv_node_temp_terms_t& tef_terms) const
|
||||||
|
@ -3283,7 +3286,7 @@ UnaryOpNode::writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOutp
|
||||||
{
|
{
|
||||||
arg->writeBytecodeOutput(code_file, output_type, temporary_terms, temporary_terms_idxs,
|
arg->writeBytecodeOutput(code_file, output_type, temporary_terms, temporary_terms_idxs,
|
||||||
tef_terms);
|
tef_terms);
|
||||||
code_file << FUNARY_ {op_code};
|
code_file << Bytecode::FUNARY_ {op_code};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -4547,7 +4550,8 @@ BinaryOpNode::eval(const eval_context_t& eval_context) const noexcept(false)
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
BinaryOpNode::writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
BinaryOpNode::writeBytecodeOutput(Bytecode::Writer& code_file,
|
||||||
|
ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const
|
const deriv_node_temp_terms_t& tef_terms) const
|
||||||
|
@ -4558,12 +4562,12 @@ BinaryOpNode::writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOut
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (op_code == BinaryOpcode::powerDeriv)
|
if (op_code == BinaryOpcode::powerDeriv)
|
||||||
code_file << FLDC_ {static_cast<double>(powerDerivOrder)};
|
code_file << Bytecode::FLDC_ {static_cast<double>(powerDerivOrder)};
|
||||||
arg1->writeBytecodeOutput(code_file, output_type, temporary_terms, temporary_terms_idxs,
|
arg1->writeBytecodeOutput(code_file, output_type, temporary_terms, temporary_terms_idxs,
|
||||||
tef_terms);
|
tef_terms);
|
||||||
arg2->writeBytecodeOutput(code_file, output_type, temporary_terms, temporary_terms_idxs,
|
arg2->writeBytecodeOutput(code_file, output_type, temporary_terms, temporary_terms_idxs,
|
||||||
tef_terms);
|
tef_terms);
|
||||||
code_file << FBINARY_ {op_code};
|
code_file << Bytecode::FBINARY_ {op_code};
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
|
@ -5009,7 +5013,7 @@ BinaryOpNode::writeJsonExternalFunctionOutput(vector<string>& efout,
|
||||||
|
|
||||||
void
|
void
|
||||||
BinaryOpNode::writeBytecodeExternalFunctionOutput(
|
BinaryOpNode::writeBytecodeExternalFunctionOutput(
|
||||||
BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
deriv_node_temp_terms_t& tef_terms) const
|
deriv_node_temp_terms_t& tef_terms) const
|
||||||
{
|
{
|
||||||
|
@ -6288,7 +6292,7 @@ TrinaryOpNode::eval(const eval_context_t& eval_context) const noexcept(false)
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
TrinaryOpNode::writeBytecodeOutput(BytecodeWriter& code_file,
|
TrinaryOpNode::writeBytecodeOutput(Bytecode::Writer& code_file,
|
||||||
ExprNodeBytecodeOutputType output_type,
|
ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
|
@ -6305,7 +6309,7 @@ TrinaryOpNode::writeBytecodeOutput(BytecodeWriter& code_file,
|
||||||
tef_terms);
|
tef_terms);
|
||||||
arg3->writeBytecodeOutput(code_file, output_type, temporary_terms, temporary_terms_idxs,
|
arg3->writeBytecodeOutput(code_file, output_type, temporary_terms, temporary_terms_idxs,
|
||||||
tef_terms);
|
tef_terms);
|
||||||
code_file << FTRINARY_ {op_code};
|
code_file << Bytecode::FTRINARY_ {op_code};
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
|
@ -6484,7 +6488,7 @@ TrinaryOpNode::writeJsonExternalFunctionOutput(vector<string>& efout,
|
||||||
|
|
||||||
void
|
void
|
||||||
TrinaryOpNode::writeBytecodeExternalFunctionOutput(
|
TrinaryOpNode::writeBytecodeExternalFunctionOutput(
|
||||||
BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
deriv_node_temp_terms_t& tef_terms) const
|
deriv_node_temp_terms_t& tef_terms) const
|
||||||
{
|
{
|
||||||
|
@ -6940,7 +6944,7 @@ AbstractExternalFunctionNode::computeChainRuleDerivative(
|
||||||
|
|
||||||
void
|
void
|
||||||
AbstractExternalFunctionNode::writeBytecodeExternalFunctionArguments(
|
AbstractExternalFunctionNode::writeBytecodeExternalFunctionArguments(
|
||||||
BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const
|
const deriv_node_temp_terms_t& tef_terms) const
|
||||||
{
|
{
|
||||||
|
@ -7437,7 +7441,7 @@ ExternalFunctionNode::composeDerivatives(const vector<expr_t>& dargs)
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
ExternalFunctionNode::writeBytecodeOutput(BytecodeWriter& code_file,
|
ExternalFunctionNode::writeBytecodeOutput(Bytecode::Writer& code_file,
|
||||||
ExprNodeBytecodeOutputType output_type,
|
ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
|
@ -7456,14 +7460,14 @@ ExternalFunctionNode::writeBytecodeOutput(BytecodeWriter& code_file,
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (!isAssignmentLHSBytecodeOutput(output_type))
|
if (!isAssignmentLHSBytecodeOutput(output_type))
|
||||||
code_file << FLDTEF_ {getIndxInTefTerms(symb_id, tef_terms)};
|
code_file << Bytecode::FLDTEF_ {getIndxInTefTerms(symb_id, tef_terms)};
|
||||||
else
|
else
|
||||||
code_file << FSTPTEF_ {getIndxInTefTerms(symb_id, tef_terms)};
|
code_file << Bytecode::FSTPTEF_ {getIndxInTefTerms(symb_id, tef_terms)};
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
ExternalFunctionNode::writeBytecodeExternalFunctionOutput(
|
ExternalFunctionNode::writeBytecodeExternalFunctionOutput(
|
||||||
BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
deriv_node_temp_terms_t& tef_terms) const
|
deriv_node_temp_terms_t& tef_terms) const
|
||||||
{
|
{
|
||||||
|
@ -7485,26 +7489,26 @@ ExternalFunctionNode::writeBytecodeExternalFunctionOutput(
|
||||||
temporary_terms_idxs, tef_terms);
|
temporary_terms_idxs, tef_terms);
|
||||||
|
|
||||||
int nb_output_arguments;
|
int nb_output_arguments;
|
||||||
ExternalFunctionCallType call_type;
|
Bytecode::ExternalFunctionCallType call_type;
|
||||||
if (symb_id == first_deriv_symb_id && symb_id == second_deriv_symb_id)
|
if (symb_id == first_deriv_symb_id && symb_id == second_deriv_symb_id)
|
||||||
{
|
{
|
||||||
nb_output_arguments = 3;
|
nb_output_arguments = 3;
|
||||||
call_type = ExternalFunctionCallType::levelWithFirstAndSecondDerivative;
|
call_type = Bytecode::ExternalFunctionCallType::levelWithFirstAndSecondDerivative;
|
||||||
}
|
}
|
||||||
else if (symb_id == first_deriv_symb_id)
|
else if (symb_id == first_deriv_symb_id)
|
||||||
{
|
{
|
||||||
nb_output_arguments = 2;
|
nb_output_arguments = 2;
|
||||||
call_type = ExternalFunctionCallType::levelWithFirstDerivative;
|
call_type = Bytecode::ExternalFunctionCallType::levelWithFirstDerivative;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
nb_output_arguments = 1;
|
nb_output_arguments = 1;
|
||||||
call_type = ExternalFunctionCallType::levelWithoutDerivative;
|
call_type = Bytecode::ExternalFunctionCallType::levelWithoutDerivative;
|
||||||
}
|
}
|
||||||
|
|
||||||
code_file << FCALL_ {nb_output_arguments, static_cast<int>(arguments.size()),
|
code_file << Bytecode::FCALL_ {nb_output_arguments, static_cast<int>(arguments.size()),
|
||||||
datatree.symbol_table.getName(symb_id), indx, call_type}
|
datatree.symbol_table.getName(symb_id), indx, call_type}
|
||||||
<< FSTPTEF_ {indx};
|
<< Bytecode::FSTPTEF_ {indx};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -7815,7 +7819,7 @@ FirstDerivExternalFunctionNode::writeOutput(ostream& output, ExprNodeOutputType
|
||||||
|
|
||||||
void
|
void
|
||||||
FirstDerivExternalFunctionNode::writeBytecodeOutput(
|
FirstDerivExternalFunctionNode::writeBytecodeOutput(
|
||||||
BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const
|
const deriv_node_temp_terms_t& tef_terms) const
|
||||||
{
|
{
|
||||||
|
@ -7835,9 +7839,9 @@ FirstDerivExternalFunctionNode::writeBytecodeOutput(
|
||||||
assert(first_deriv_symb_id != ExternalFunctionsTable::IDSetButNoNameProvided);
|
assert(first_deriv_symb_id != ExternalFunctionsTable::IDSetButNoNameProvided);
|
||||||
|
|
||||||
if (!isAssignmentLHSBytecodeOutput(output_type))
|
if (!isAssignmentLHSBytecodeOutput(output_type))
|
||||||
code_file << FLDTEFD_ {getIndxInTefTerms(symb_id, tef_terms), inputIndex};
|
code_file << Bytecode::FLDTEFD_ {getIndxInTefTerms(symb_id, tef_terms), inputIndex};
|
||||||
else
|
else
|
||||||
code_file << FSTPTEFD_ {getIndxInTefTerms(symb_id, tef_terms), inputIndex};
|
code_file << Bytecode::FSTPTEFD_ {getIndxInTefTerms(symb_id, tef_terms), inputIndex};
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
@ -7972,7 +7976,7 @@ FirstDerivExternalFunctionNode::writeJsonExternalFunctionOutput(
|
||||||
|
|
||||||
void
|
void
|
||||||
FirstDerivExternalFunctionNode::writeBytecodeExternalFunctionOutput(
|
FirstDerivExternalFunctionNode::writeBytecodeExternalFunctionOutput(
|
||||||
BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
deriv_node_temp_terms_t& tef_terms) const
|
deriv_node_temp_terms_t& tef_terms) const
|
||||||
{
|
{
|
||||||
|
@ -8000,12 +8004,12 @@ FirstDerivExternalFunctionNode::writeBytecodeExternalFunctionOutput(
|
||||||
{
|
{
|
||||||
int nb_input_arguments {0};
|
int nb_input_arguments {0};
|
||||||
int nb_output_arguments {1};
|
int nb_output_arguments {1};
|
||||||
FCALL_ fcall {nb_output_arguments, nb_input_arguments, "jacob_element", indx,
|
Bytecode::FCALL_ fcall {nb_output_arguments, nb_input_arguments, "jacob_element", indx,
|
||||||
ExternalFunctionCallType::numericalFirstDerivative};
|
Bytecode::ExternalFunctionCallType::numericalFirstDerivative};
|
||||||
fcall.set_arg_func_name(datatree.symbol_table.getName(symb_id));
|
fcall.set_arg_func_name(datatree.symbol_table.getName(symb_id));
|
||||||
fcall.set_row(inputIndex);
|
fcall.set_row(inputIndex);
|
||||||
fcall.set_nb_add_input_arguments(static_cast<int>(arguments.size()));
|
fcall.set_nb_add_input_arguments(static_cast<int>(arguments.size()));
|
||||||
code_file << fcall << FSTPTEFD_ {indx, inputIndex};
|
code_file << fcall << Bytecode::FSTPTEFD_ {indx, inputIndex};
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -8015,10 +8019,11 @@ FirstDerivExternalFunctionNode::writeBytecodeExternalFunctionOutput(
|
||||||
|
|
||||||
int nb_output_arguments {1};
|
int nb_output_arguments {1};
|
||||||
|
|
||||||
code_file << FCALL_ {nb_output_arguments, static_cast<int>(arguments.size()),
|
code_file << Bytecode::
|
||||||
datatree.symbol_table.getName(first_deriv_symb_id), indx,
|
FCALL_ {nb_output_arguments, static_cast<int>(arguments.size()),
|
||||||
ExternalFunctionCallType::separatelyProvidedFirstDerivative}
|
datatree.symbol_table.getName(first_deriv_symb_id), indx,
|
||||||
<< FSTPTEFD_ {indx, inputIndex};
|
Bytecode::ExternalFunctionCallType::separatelyProvidedFirstDerivative}
|
||||||
|
<< Bytecode::FSTPTEFD_ {indx, inputIndex};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -8319,7 +8324,7 @@ SecondDerivExternalFunctionNode::computeXrefs(EquationInfo& ei) const
|
||||||
|
|
||||||
void
|
void
|
||||||
SecondDerivExternalFunctionNode::writeBytecodeOutput(
|
SecondDerivExternalFunctionNode::writeBytecodeOutput(
|
||||||
BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const
|
const deriv_node_temp_terms_t& tef_terms) const
|
||||||
{
|
{
|
||||||
|
@ -8339,14 +8344,16 @@ SecondDerivExternalFunctionNode::writeBytecodeOutput(
|
||||||
assert(second_deriv_symb_id != ExternalFunctionsTable::IDSetButNoNameProvided);
|
assert(second_deriv_symb_id != ExternalFunctionsTable::IDSetButNoNameProvided);
|
||||||
|
|
||||||
if (!isAssignmentLHSBytecodeOutput(output_type))
|
if (!isAssignmentLHSBytecodeOutput(output_type))
|
||||||
code_file << FLDTEFDD_ {getIndxInTefTerms(symb_id, tef_terms), inputIndex1, inputIndex2};
|
code_file << Bytecode::FLDTEFDD_ {getIndxInTefTerms(symb_id, tef_terms), inputIndex1,
|
||||||
|
inputIndex2};
|
||||||
else
|
else
|
||||||
code_file << FSTPTEFDD_ {getIndxInTefTerms(symb_id, tef_terms), inputIndex1, inputIndex2};
|
code_file << Bytecode::FSTPTEFDD_ {getIndxInTefTerms(symb_id, tef_terms), inputIndex1,
|
||||||
|
inputIndex2};
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
SecondDerivExternalFunctionNode::writeBytecodeExternalFunctionOutput(
|
SecondDerivExternalFunctionNode::writeBytecodeExternalFunctionOutput(
|
||||||
BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
deriv_node_temp_terms_t& tef_terms) const
|
deriv_node_temp_terms_t& tef_terms) const
|
||||||
{
|
{
|
||||||
|
@ -8372,22 +8379,23 @@ SecondDerivExternalFunctionNode::writeBytecodeExternalFunctionOutput(
|
||||||
if (int indx = getIndxInTefTerms(symb_id, tef_terms);
|
if (int indx = getIndxInTefTerms(symb_id, tef_terms);
|
||||||
second_deriv_symb_id == ExternalFunctionsTable::IDNotSet)
|
second_deriv_symb_id == ExternalFunctionsTable::IDNotSet)
|
||||||
{
|
{
|
||||||
FCALL_ fcall {1, 0, "hess_element", indx,
|
Bytecode::FCALL_ fcall {1, 0, "hess_element", indx,
|
||||||
ExternalFunctionCallType::numericalSecondDerivative};
|
Bytecode::ExternalFunctionCallType::numericalSecondDerivative};
|
||||||
fcall.set_arg_func_name(datatree.symbol_table.getName(symb_id));
|
fcall.set_arg_func_name(datatree.symbol_table.getName(symb_id));
|
||||||
fcall.set_row(inputIndex1);
|
fcall.set_row(inputIndex1);
|
||||||
fcall.set_col(inputIndex2);
|
fcall.set_col(inputIndex2);
|
||||||
fcall.set_nb_add_input_arguments(static_cast<int>(arguments.size()));
|
fcall.set_nb_add_input_arguments(static_cast<int>(arguments.size()));
|
||||||
code_file << fcall << FSTPTEFDD_ {indx, inputIndex1, inputIndex2};
|
code_file << fcall << Bytecode::FSTPTEFDD_ {indx, inputIndex1, inputIndex2};
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
tef_terms[{second_deriv_symb_id, arguments}] = static_cast<int>(tef_terms.size());
|
tef_terms[{second_deriv_symb_id, arguments}] = static_cast<int>(tef_terms.size());
|
||||||
|
|
||||||
code_file << FCALL_ {1, static_cast<int>(arguments.size()),
|
code_file << Bytecode::
|
||||||
datatree.symbol_table.getName(second_deriv_symb_id), indx,
|
FCALL_ {1, static_cast<int>(arguments.size()),
|
||||||
ExternalFunctionCallType::separatelyProvidedSecondDerivative}
|
datatree.symbol_table.getName(second_deriv_symb_id), indx,
|
||||||
<< FSTPTEFDD_ {indx, inputIndex1, inputIndex2};
|
Bytecode::ExternalFunctionCallType::separatelyProvidedSecondDerivative}
|
||||||
|
<< Bytecode::FSTPTEFDD_ {indx, inputIndex1, inputIndex2};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -8610,7 +8618,7 @@ SubModelNode::collectDynamicVariables([[maybe_unused]] SymbolType type_arg,
|
||||||
|
|
||||||
void
|
void
|
||||||
SubModelNode::writeBytecodeOutput(
|
SubModelNode::writeBytecodeOutput(
|
||||||
[[maybe_unused]] BytecodeWriter& code_file,
|
[[maybe_unused]] Bytecode::Writer& code_file,
|
||||||
[[maybe_unused]] ExprNodeBytecodeOutputType output_type,
|
[[maybe_unused]] ExprNodeBytecodeOutputType output_type,
|
||||||
[[maybe_unused]] const temporary_terms_t& temporary_terms,
|
[[maybe_unused]] const temporary_terms_t& temporary_terms,
|
||||||
[[maybe_unused]] const temporary_terms_idxs_t& temporary_terms_idxs,
|
[[maybe_unused]] const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
|
|
|
@ -321,7 +321,7 @@ protected:
|
||||||
|
|
||||||
// Same as above, for the bytecode case
|
// Same as above, for the bytecode case
|
||||||
bool
|
bool
|
||||||
checkIfTemporaryTermThenWriteBytecode(BytecodeWriter& code_file,
|
checkIfTemporaryTermThenWriteBytecode(Bytecode::Writer& code_file,
|
||||||
ExprNodeBytecodeOutputType output_type,
|
ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs) const;
|
const temporary_terms_idxs_t& temporary_terms_idxs) const;
|
||||||
|
@ -488,7 +488,7 @@ public:
|
||||||
bool isdynamic = true) const;
|
bool isdynamic = true) const;
|
||||||
|
|
||||||
virtual void writeBytecodeExternalFunctionOutput(
|
virtual void writeBytecodeExternalFunctionOutput(
|
||||||
BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_t& temporary_terms, const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
deriv_node_temp_terms_t& tef_terms) const;
|
deriv_node_temp_terms_t& tef_terms) const;
|
||||||
|
|
||||||
|
@ -537,7 +537,7 @@ public:
|
||||||
[[nodiscard]] virtual double eval(const eval_context_t& eval_context) const noexcept(false) = 0;
|
[[nodiscard]] virtual double eval(const eval_context_t& eval_context) const noexcept(false) = 0;
|
||||||
|
|
||||||
// Write output to bytecode file
|
// Write output to bytecode file
|
||||||
virtual void writeBytecodeOutput(BytecodeWriter& code_file,
|
virtual void writeBytecodeOutput(Bytecode::Writer& code_file,
|
||||||
ExprNodeBytecodeOutputType output_type,
|
ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
|
@ -995,7 +995,7 @@ public:
|
||||||
void collectVARLHSVariable(set<expr_t>& result) const override;
|
void collectVARLHSVariable(set<expr_t>& result) const override;
|
||||||
void collectDynamicVariables(SymbolType type_arg, set<pair<int, int>>& result) const override;
|
void collectDynamicVariables(SymbolType type_arg, set<pair<int, int>>& result) const override;
|
||||||
[[nodiscard]] double eval(const eval_context_t& eval_context) const noexcept(false) override;
|
[[nodiscard]] double eval(const eval_context_t& eval_context) const noexcept(false) override;
|
||||||
void writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
void writeBytecodeOutput(Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const override;
|
const deriv_node_temp_terms_t& tef_terms) const override;
|
||||||
|
@ -1095,7 +1095,7 @@ public:
|
||||||
void collectVARLHSVariable(set<expr_t>& result) const override;
|
void collectVARLHSVariable(set<expr_t>& result) const override;
|
||||||
void collectDynamicVariables(SymbolType type_arg, set<pair<int, int>>& result) const override;
|
void collectDynamicVariables(SymbolType type_arg, set<pair<int, int>>& result) const override;
|
||||||
[[nodiscard]] double eval(const eval_context_t& eval_context) const noexcept(false) override;
|
[[nodiscard]] double eval(const eval_context_t& eval_context) const noexcept(false) override;
|
||||||
void writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
void writeBytecodeOutput(Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const override;
|
const deriv_node_temp_terms_t& tef_terms) const override;
|
||||||
|
@ -1231,7 +1231,7 @@ public:
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
deriv_node_temp_terms_t& tef_terms,
|
deriv_node_temp_terms_t& tef_terms,
|
||||||
bool isdynamic) const override;
|
bool isdynamic) const override;
|
||||||
void writeBytecodeExternalFunctionOutput(BytecodeWriter& code_file,
|
void writeBytecodeExternalFunctionOutput(Bytecode::Writer& code_file,
|
||||||
ExprNodeBytecodeOutputType output_type,
|
ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
|
@ -1240,7 +1240,7 @@ public:
|
||||||
void collectDynamicVariables(SymbolType type_arg, set<pair<int, int>>& result) const override;
|
void collectDynamicVariables(SymbolType type_arg, set<pair<int, int>>& result) const override;
|
||||||
static double eval_opcode(UnaryOpcode op_code, double v) noexcept(false);
|
static double eval_opcode(UnaryOpcode op_code, double v) noexcept(false);
|
||||||
[[nodiscard]] double eval(const eval_context_t& eval_context) const noexcept(false) override;
|
[[nodiscard]] double eval(const eval_context_t& eval_context) const noexcept(false) override;
|
||||||
void writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
void writeBytecodeOutput(Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const override;
|
const deriv_node_temp_terms_t& tef_terms) const override;
|
||||||
|
@ -1376,7 +1376,7 @@ public:
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
deriv_node_temp_terms_t& tef_terms,
|
deriv_node_temp_terms_t& tef_terms,
|
||||||
bool isdynamic) const override;
|
bool isdynamic) const override;
|
||||||
void writeBytecodeExternalFunctionOutput(BytecodeWriter& code_file,
|
void writeBytecodeExternalFunctionOutput(Bytecode::Writer& code_file,
|
||||||
ExprNodeBytecodeOutputType output_type,
|
ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
|
@ -1386,7 +1386,7 @@ public:
|
||||||
static double eval_opcode(double v1, BinaryOpcode op_code, double v2,
|
static double eval_opcode(double v1, BinaryOpcode op_code, double v2,
|
||||||
int derivOrder) noexcept(false);
|
int derivOrder) noexcept(false);
|
||||||
[[nodiscard]] double eval(const eval_context_t& eval_context) const noexcept(false) override;
|
[[nodiscard]] double eval(const eval_context_t& eval_context) const noexcept(false) override;
|
||||||
void writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
void writeBytecodeOutput(Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const override;
|
const deriv_node_temp_terms_t& tef_terms) const override;
|
||||||
|
@ -1569,7 +1569,7 @@ public:
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
deriv_node_temp_terms_t& tef_terms,
|
deriv_node_temp_terms_t& tef_terms,
|
||||||
bool isdynamic) const override;
|
bool isdynamic) const override;
|
||||||
void writeBytecodeExternalFunctionOutput(BytecodeWriter& code_file,
|
void writeBytecodeExternalFunctionOutput(Bytecode::Writer& code_file,
|
||||||
ExprNodeBytecodeOutputType output_type,
|
ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
|
@ -1578,7 +1578,7 @@ public:
|
||||||
void collectDynamicVariables(SymbolType type_arg, set<pair<int, int>>& result) const override;
|
void collectDynamicVariables(SymbolType type_arg, set<pair<int, int>>& result) const override;
|
||||||
static double eval_opcode(double v1, TrinaryOpcode op_code, double v2, double v3) noexcept(false);
|
static double eval_opcode(double v1, TrinaryOpcode op_code, double v2, double v3) noexcept(false);
|
||||||
[[nodiscard]] double eval(const eval_context_t& eval_context) const noexcept(false) override;
|
[[nodiscard]] double eval(const eval_context_t& eval_context) const noexcept(false) override;
|
||||||
void writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
void writeBytecodeOutput(Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const override;
|
const deriv_node_temp_terms_t& tef_terms) const override;
|
||||||
|
@ -1694,7 +1694,7 @@ protected:
|
||||||
void writeJsonExternalFunctionArguments(ostream& output, const temporary_terms_t& temporary_terms,
|
void writeJsonExternalFunctionArguments(ostream& output, const temporary_terms_t& temporary_terms,
|
||||||
const deriv_node_temp_terms_t& tef_terms,
|
const deriv_node_temp_terms_t& tef_terms,
|
||||||
bool isdynamic) const;
|
bool isdynamic) const;
|
||||||
void writeBytecodeExternalFunctionArguments(BytecodeWriter& code_file,
|
void writeBytecodeExternalFunctionArguments(Bytecode::Writer& code_file,
|
||||||
ExprNodeBytecodeOutputType output_type,
|
ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
|
@ -1737,7 +1737,7 @@ public:
|
||||||
deriv_node_temp_terms_t& tef_terms,
|
deriv_node_temp_terms_t& tef_terms,
|
||||||
bool isdynamic = true) const override
|
bool isdynamic = true) const override
|
||||||
= 0;
|
= 0;
|
||||||
void writeBytecodeExternalFunctionOutput(BytecodeWriter& code_file,
|
void writeBytecodeExternalFunctionOutput(Bytecode::Writer& code_file,
|
||||||
ExprNodeBytecodeOutputType output_type,
|
ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
|
@ -1746,7 +1746,7 @@ public:
|
||||||
void collectVARLHSVariable(set<expr_t>& result) const override;
|
void collectVARLHSVariable(set<expr_t>& result) const override;
|
||||||
void collectDynamicVariables(SymbolType type_arg, set<pair<int, int>>& result) const override;
|
void collectDynamicVariables(SymbolType type_arg, set<pair<int, int>>& result) const override;
|
||||||
[[nodiscard]] double eval(const eval_context_t& eval_context) const noexcept(false) override;
|
[[nodiscard]] double eval(const eval_context_t& eval_context) const noexcept(false) override;
|
||||||
void writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
void writeBytecodeOutput(Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const override
|
const deriv_node_temp_terms_t& tef_terms) const override
|
||||||
|
@ -1842,12 +1842,12 @@ public:
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
deriv_node_temp_terms_t& tef_terms,
|
deriv_node_temp_terms_t& tef_terms,
|
||||||
bool isdynamic) const override;
|
bool isdynamic) const override;
|
||||||
void writeBytecodeExternalFunctionOutput(BytecodeWriter& code_file,
|
void writeBytecodeExternalFunctionOutput(Bytecode::Writer& code_file,
|
||||||
ExprNodeBytecodeOutputType output_type,
|
ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
deriv_node_temp_terms_t& tef_terms) const override;
|
deriv_node_temp_terms_t& tef_terms) const override;
|
||||||
void writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
void writeBytecodeOutput(Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const override;
|
const deriv_node_temp_terms_t& tef_terms) const override;
|
||||||
|
@ -1877,7 +1877,7 @@ public:
|
||||||
void writeJsonAST(ostream& output) const override;
|
void writeJsonAST(ostream& output) const override;
|
||||||
void writeJsonOutput(ostream& output, const temporary_terms_t& temporary_terms,
|
void writeJsonOutput(ostream& output, const temporary_terms_t& temporary_terms,
|
||||||
const deriv_node_temp_terms_t& tef_terms, bool isdynamic) const override;
|
const deriv_node_temp_terms_t& tef_terms, bool isdynamic) const override;
|
||||||
void writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
void writeBytecodeOutput(Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const override;
|
const deriv_node_temp_terms_t& tef_terms) const override;
|
||||||
|
@ -1889,7 +1889,7 @@ public:
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
deriv_node_temp_terms_t& tef_terms,
|
deriv_node_temp_terms_t& tef_terms,
|
||||||
bool isdynamic) const override;
|
bool isdynamic) const override;
|
||||||
void writeBytecodeExternalFunctionOutput(BytecodeWriter& code_file,
|
void writeBytecodeExternalFunctionOutput(Bytecode::Writer& code_file,
|
||||||
ExprNodeBytecodeOutputType output_type,
|
ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
|
@ -1922,7 +1922,7 @@ public:
|
||||||
void writeJsonAST(ostream& output) const override;
|
void writeJsonAST(ostream& output) const override;
|
||||||
void writeJsonOutput(ostream& output, const temporary_terms_t& temporary_terms,
|
void writeJsonOutput(ostream& output, const temporary_terms_t& temporary_terms,
|
||||||
const deriv_node_temp_terms_t& tef_terms, bool isdynamic) const override;
|
const deriv_node_temp_terms_t& tef_terms, bool isdynamic) const override;
|
||||||
void writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
void writeBytecodeOutput(Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const override;
|
const deriv_node_temp_terms_t& tef_terms) const override;
|
||||||
|
@ -1934,7 +1934,7 @@ public:
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
deriv_node_temp_terms_t& tef_terms,
|
deriv_node_temp_terms_t& tef_terms,
|
||||||
bool isdynamic) const override;
|
bool isdynamic) const override;
|
||||||
void writeBytecodeExternalFunctionOutput(BytecodeWriter& code_file,
|
void writeBytecodeExternalFunctionOutput(Bytecode::Writer& code_file,
|
||||||
ExprNodeBytecodeOutputType output_type,
|
ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
|
@ -1994,7 +1994,7 @@ public:
|
||||||
expr_t substituteUnaryOpNodes(const lag_equivalence_table_t& nodes, subst_table_t& subst_table,
|
expr_t substituteUnaryOpNodes(const lag_equivalence_table_t& nodes, subst_table_t& subst_table,
|
||||||
vector<BinaryOpNode*>& neweqs) const override;
|
vector<BinaryOpNode*>& neweqs) const override;
|
||||||
BinaryOpNode* normalizeEquationHelper(const set<expr_t>& contain_var, expr_t rhs) const override;
|
BinaryOpNode* normalizeEquationHelper(const set<expr_t>& contain_var, expr_t rhs) const override;
|
||||||
void writeBytecodeOutput(BytecodeWriter& code_file, ExprNodeBytecodeOutputType output_type,
|
void writeBytecodeOutput(Bytecode::Writer& code_file, ExprNodeBytecodeOutputType output_type,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const temporary_terms_idxs_t& temporary_terms_idxs,
|
const temporary_terms_idxs_t& temporary_terms_idxs,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const override;
|
const deriv_node_temp_terms_t& tef_terms) const override;
|
||||||
|
|
159
src/ModelTree.hh
159
src/ModelTree.hh
|
@ -294,9 +294,10 @@ protected:
|
||||||
const string& concat) const;
|
const string& concat) const;
|
||||||
//! Writes temporary terms in bytecode
|
//! Writes temporary terms in bytecode
|
||||||
template<ExprNodeBytecodeOutputType output_type>
|
template<ExprNodeBytecodeOutputType output_type>
|
||||||
void
|
void writeBytecodeTemporaryTerms(const temporary_terms_t& tt,
|
||||||
writeBytecodeTemporaryTerms(const temporary_terms_t& tt, temporary_terms_t& temporary_terms_union,
|
temporary_terms_t& temporary_terms_union,
|
||||||
BytecodeWriter& code_file, deriv_node_temp_terms_t& tef_terms) const;
|
Bytecode::Writer& code_file,
|
||||||
|
deriv_node_temp_terms_t& tef_terms) const;
|
||||||
/* Adds information for (non-block) bytecode simulation in a separate .bin
|
/* Adds information for (non-block) bytecode simulation in a separate .bin
|
||||||
file.
|
file.
|
||||||
Returns the number of first derivatives w.r.t. endogenous variables */
|
Returns the number of first derivatives w.r.t. endogenous variables */
|
||||||
|
@ -343,11 +344,11 @@ protected:
|
||||||
|
|
||||||
// Helper for writing bytecode (without block decomposition)
|
// Helper for writing bytecode (without block decomposition)
|
||||||
template<bool dynamic>
|
template<bool dynamic>
|
||||||
void writeBytecodeHelper(BytecodeWriter& code_file) const;
|
void writeBytecodeHelper(Bytecode::Writer& code_file) const;
|
||||||
|
|
||||||
// Helper for writing blocks in bytecode
|
// Helper for writing blocks in bytecode
|
||||||
template<bool dynamic>
|
template<bool dynamic>
|
||||||
void writeBlockBytecodeHelper(BytecodeWriter& code_file, int block,
|
void writeBlockBytecodeHelper(Bytecode::Writer& code_file, int block,
|
||||||
temporary_terms_t& temporary_terms_union) const;
|
temporary_terms_t& temporary_terms_union) const;
|
||||||
|
|
||||||
// Helper for writing sparse derivatives indices in MATLAB/Octave driver file
|
// Helper for writing sparse derivatives indices in MATLAB/Octave driver file
|
||||||
|
@ -387,7 +388,7 @@ protected:
|
||||||
|
|
||||||
//! Writes model equations in bytecode
|
//! Writes model equations in bytecode
|
||||||
template<ExprNodeBytecodeOutputType output_type>
|
template<ExprNodeBytecodeOutputType output_type>
|
||||||
void writeBytecodeModelEquations(BytecodeWriter& code_file,
|
void writeBytecodeModelEquations(Bytecode::Writer& code_file,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const;
|
const deriv_node_temp_terms_t& tef_terms) const;
|
||||||
|
|
||||||
|
@ -1518,7 +1519,7 @@ template<ExprNodeBytecodeOutputType output_type>
|
||||||
void
|
void
|
||||||
ModelTree::writeBytecodeTemporaryTerms(const temporary_terms_t& tt,
|
ModelTree::writeBytecodeTemporaryTerms(const temporary_terms_t& tt,
|
||||||
temporary_terms_t& temporary_terms_union,
|
temporary_terms_t& temporary_terms_union,
|
||||||
BytecodeWriter& code_file,
|
Bytecode::Writer& code_file,
|
||||||
deriv_node_temp_terms_t& tef_terms) const
|
deriv_node_temp_terms_t& tef_terms) const
|
||||||
{
|
{
|
||||||
for (auto it : tt)
|
for (auto it : tt)
|
||||||
|
@ -1528,16 +1529,16 @@ ModelTree::writeBytecodeTemporaryTerms(const temporary_terms_t& tt,
|
||||||
temporary_terms_idxs, tef_terms);
|
temporary_terms_idxs, tef_terms);
|
||||||
|
|
||||||
int idx {temporary_terms_idxs.at(it)};
|
int idx {temporary_terms_idxs.at(it)};
|
||||||
code_file << FNUMEXPR_ {ExpressionType::TemporaryTerm, idx};
|
code_file << Bytecode::FNUMEXPR_ {Bytecode::ExpressionType::TemporaryTerm, idx};
|
||||||
it->writeBytecodeOutput(code_file, output_type, temporary_terms_union, temporary_terms_idxs,
|
it->writeBytecodeOutput(code_file, output_type, temporary_terms_union, temporary_terms_idxs,
|
||||||
tef_terms);
|
tef_terms);
|
||||||
|
|
||||||
static_assert(output_type == ExprNodeBytecodeOutputType::dynamicModel
|
static_assert(output_type == ExprNodeBytecodeOutputType::dynamicModel
|
||||||
|| output_type == ExprNodeBytecodeOutputType::staticModel);
|
|| output_type == ExprNodeBytecodeOutputType::staticModel);
|
||||||
if constexpr (output_type == ExprNodeBytecodeOutputType::dynamicModel)
|
if constexpr (output_type == ExprNodeBytecodeOutputType::dynamicModel)
|
||||||
code_file << FSTPT_ {idx};
|
code_file << Bytecode::FSTPT_ {idx};
|
||||||
else
|
else
|
||||||
code_file << FSTPST_ {idx};
|
code_file << Bytecode::FSTPST_ {idx};
|
||||||
|
|
||||||
temporary_terms_union.insert(it);
|
temporary_terms_union.insert(it);
|
||||||
}
|
}
|
||||||
|
@ -1545,7 +1546,7 @@ ModelTree::writeBytecodeTemporaryTerms(const temporary_terms_t& tt,
|
||||||
|
|
||||||
template<ExprNodeBytecodeOutputType output_type>
|
template<ExprNodeBytecodeOutputType output_type>
|
||||||
void
|
void
|
||||||
ModelTree::writeBytecodeModelEquations(BytecodeWriter& code_file,
|
ModelTree::writeBytecodeModelEquations(Bytecode::Writer& code_file,
|
||||||
const temporary_terms_t& temporary_terms,
|
const temporary_terms_t& temporary_terms,
|
||||||
const deriv_node_temp_terms_t& tef_terms) const
|
const deriv_node_temp_terms_t& tef_terms) const
|
||||||
{
|
{
|
||||||
|
@ -1553,7 +1554,7 @@ ModelTree::writeBytecodeModelEquations(BytecodeWriter& code_file,
|
||||||
{
|
{
|
||||||
BinaryOpNode* eq_node {equations[eq]};
|
BinaryOpNode* eq_node {equations[eq]};
|
||||||
expr_t lhs {eq_node->arg1}, rhs {eq_node->arg2};
|
expr_t lhs {eq_node->arg1}, rhs {eq_node->arg2};
|
||||||
code_file << FNUMEXPR_ {ExpressionType::ModelEquation, eq};
|
code_file << Bytecode::FNUMEXPR_ {Bytecode::ExpressionType::ModelEquation, eq};
|
||||||
// Test if the right hand side of the equation is empty.
|
// Test if the right hand side of the equation is empty.
|
||||||
double vrhs {1.0};
|
double vrhs {1.0};
|
||||||
try
|
try
|
||||||
|
@ -1571,20 +1572,20 @@ ModelTree::writeBytecodeModelEquations(BytecodeWriter& code_file,
|
||||||
rhs->writeBytecodeOutput(code_file, output_type, temporary_terms, temporary_terms_idxs,
|
rhs->writeBytecodeOutput(code_file, output_type, temporary_terms, temporary_terms_idxs,
|
||||||
tef_terms);
|
tef_terms);
|
||||||
|
|
||||||
code_file << FBINARY_ {BinaryOpcode::minus} << FSTPR_ {eq};
|
code_file << Bytecode::FBINARY_ {BinaryOpcode::minus} << Bytecode::FSTPR_ {eq};
|
||||||
}
|
}
|
||||||
else // The right hand side of the equation is empty ⇒ residual=lhs
|
else // The right hand side of the equation is empty ⇒ residual=lhs
|
||||||
{
|
{
|
||||||
lhs->writeBytecodeOutput(code_file, output_type, temporary_terms, temporary_terms_idxs,
|
lhs->writeBytecodeOutput(code_file, output_type, temporary_terms, temporary_terms_idxs,
|
||||||
tef_terms);
|
tef_terms);
|
||||||
code_file << FSTPR_ {eq};
|
code_file << Bytecode::FSTPR_ {eq};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
template<bool dynamic>
|
template<bool dynamic>
|
||||||
void
|
void
|
||||||
ModelTree::writeBytecodeHelper(BytecodeWriter& code_file) const
|
ModelTree::writeBytecodeHelper(Bytecode::Writer& code_file) const
|
||||||
{
|
{
|
||||||
constexpr ExprNodeBytecodeOutputType output_type {
|
constexpr ExprNodeBytecodeOutputType output_type {
|
||||||
dynamic ? ExprNodeBytecodeOutputType::dynamicModel : ExprNodeBytecodeOutputType::staticModel};
|
dynamic ? ExprNodeBytecodeOutputType::dynamicModel : ExprNodeBytecodeOutputType::staticModel};
|
||||||
|
@ -1596,7 +1597,7 @@ ModelTree::writeBytecodeHelper(BytecodeWriter& code_file) const
|
||||||
code_file, tef_terms);
|
code_file, tef_terms);
|
||||||
writeBytecodeModelEquations<output_type>(code_file, temporary_terms_union, tef_terms);
|
writeBytecodeModelEquations<output_type>(code_file, temporary_terms_union, tef_terms);
|
||||||
|
|
||||||
code_file << FENDEQU_ {};
|
code_file << Bytecode::FENDEQU_ {};
|
||||||
|
|
||||||
// Temporary terms for the Jacobian
|
// Temporary terms for the Jacobian
|
||||||
writeBytecodeTemporaryTerms<output_type>(temporary_terms_derivatives[1], temporary_terms_union,
|
writeBytecodeTemporaryTerms<output_type>(temporary_terms_derivatives[1], temporary_terms_union,
|
||||||
|
@ -1604,7 +1605,7 @@ ModelTree::writeBytecodeHelper(BytecodeWriter& code_file) const
|
||||||
|
|
||||||
// Get the current code_file position and jump if “evaluate” mode
|
// Get the current code_file position and jump if “evaluate” mode
|
||||||
int pos_jmpifeval {code_file.getInstructionCounter()};
|
int pos_jmpifeval {code_file.getInstructionCounter()};
|
||||||
code_file << FJMPIFEVAL_ {0}; // Use 0 as jump offset for the time being
|
code_file << Bytecode::FJMPIFEVAL_ {0}; // Use 0 as jump offset for the time being
|
||||||
|
|
||||||
// The Jacobian in “simulate” mode
|
// The Jacobian in “simulate” mode
|
||||||
vector<vector<tuple<int, int, int>>> my_derivatives(symbol_table.endo_nbr());
|
vector<vector<tuple<int, int, int>>> my_derivatives(symbol_table.endo_nbr());
|
||||||
|
@ -1618,49 +1619,53 @@ ModelTree::writeBytecodeHelper(BytecodeWriter& code_file) const
|
||||||
int tsid {getTypeSpecificIDByDerivID(deriv_id)};
|
int tsid {getTypeSpecificIDByDerivID(deriv_id)};
|
||||||
int lag {getLagByDerivID(deriv_id)};
|
int lag {getLagByDerivID(deriv_id)};
|
||||||
if constexpr (dynamic)
|
if constexpr (dynamic)
|
||||||
code_file << FNUMEXPR_ {ExpressionType::FirstEndoDerivative, eq, tsid, lag};
|
code_file << Bytecode::FNUMEXPR_ {Bytecode::ExpressionType::FirstEndoDerivative, eq,
|
||||||
|
tsid, lag};
|
||||||
else
|
else
|
||||||
code_file << FNUMEXPR_ {ExpressionType::FirstEndoDerivative, eq, tsid};
|
code_file << Bytecode::FNUMEXPR_ {Bytecode::ExpressionType::FirstEndoDerivative, eq,
|
||||||
|
tsid};
|
||||||
if (!my_derivatives[eq].size())
|
if (!my_derivatives[eq].size())
|
||||||
my_derivatives[eq].clear();
|
my_derivatives[eq].clear();
|
||||||
my_derivatives[eq].emplace_back(tsid, lag, count_u);
|
my_derivatives[eq].emplace_back(tsid, lag, count_u);
|
||||||
d1->writeBytecodeOutput(code_file, output_type, temporary_terms_union,
|
d1->writeBytecodeOutput(code_file, output_type, temporary_terms_union,
|
||||||
temporary_terms_idxs, tef_terms);
|
temporary_terms_idxs, tef_terms);
|
||||||
if constexpr (dynamic)
|
if constexpr (dynamic)
|
||||||
code_file << FSTPU_ {count_u};
|
code_file << Bytecode::FSTPU_ {count_u};
|
||||||
else
|
else
|
||||||
code_file << FSTPSU_ {count_u};
|
code_file << Bytecode::FSTPSU_ {count_u};
|
||||||
count_u++;
|
count_u++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
for (int i {0}; i < symbol_table.endo_nbr(); i++)
|
for (int i {0}; i < symbol_table.endo_nbr(); i++)
|
||||||
{
|
{
|
||||||
code_file << FLDR_ {i};
|
code_file << Bytecode::FLDR_ {i};
|
||||||
if (my_derivatives[i].size())
|
if (my_derivatives[i].size())
|
||||||
{
|
{
|
||||||
for (bool first_term {true}; const auto& [tsid, lag, uidx] : my_derivatives[i])
|
for (bool first_term {true}; const auto& [tsid, lag, uidx] : my_derivatives[i])
|
||||||
{
|
{
|
||||||
if constexpr (dynamic)
|
if constexpr (dynamic)
|
||||||
code_file << FLDU_ {uidx} << FLDV_ {SymbolType::endogenous, tsid, lag};
|
code_file << Bytecode::FLDU_ {uidx}
|
||||||
|
<< Bytecode::FLDV_ {SymbolType::endogenous, tsid, lag};
|
||||||
else
|
else
|
||||||
code_file << FLDSU_ {uidx} << FLDSV_ {SymbolType::endogenous, tsid};
|
code_file << Bytecode::FLDSU_ {uidx}
|
||||||
code_file << FBINARY_ {BinaryOpcode::times};
|
<< Bytecode::FLDSV_ {SymbolType::endogenous, tsid};
|
||||||
|
code_file << Bytecode::FBINARY_ {BinaryOpcode::times};
|
||||||
if (!exchange(first_term, false))
|
if (!exchange(first_term, false))
|
||||||
code_file << FBINARY_ {BinaryOpcode::plus};
|
code_file << Bytecode::FBINARY_ {BinaryOpcode::plus};
|
||||||
}
|
}
|
||||||
code_file << FBINARY_ {BinaryOpcode::minus};
|
code_file << Bytecode::FBINARY_ {BinaryOpcode::minus};
|
||||||
}
|
}
|
||||||
if constexpr (dynamic)
|
if constexpr (dynamic)
|
||||||
code_file << FSTPU_ {i};
|
code_file << Bytecode::FSTPU_ {i};
|
||||||
else
|
else
|
||||||
code_file << FSTPSU_ {i};
|
code_file << Bytecode::FSTPSU_ {i};
|
||||||
}
|
}
|
||||||
|
|
||||||
// Jump unconditionally after the block
|
// Jump unconditionally after the block
|
||||||
int pos_jmp {code_file.getInstructionCounter()};
|
int pos_jmp {code_file.getInstructionCounter()};
|
||||||
code_file << FJMP_ {0}; // Use 0 as jump offset for the time being
|
code_file << Bytecode::FJMP_ {0}; // Use 0 as jump offset for the time being
|
||||||
// Update jump offset for previous JMPIFEVAL
|
// Update jump offset for previous JMPIFEVAL
|
||||||
code_file.overwriteInstruction(pos_jmpifeval, FJMPIFEVAL_ {pos_jmp - pos_jmpifeval});
|
code_file.overwriteInstruction(pos_jmpifeval, Bytecode::FJMPIFEVAL_ {pos_jmp - pos_jmpifeval});
|
||||||
|
|
||||||
// The Jacobian in “evaluate” mode
|
// The Jacobian in “evaluate” mode
|
||||||
for (const auto& [indices, d1] : derivatives[1])
|
for (const auto& [indices, d1] : derivatives[1])
|
||||||
|
@ -1672,28 +1677,29 @@ ModelTree::writeBytecodeHelper(BytecodeWriter& code_file) const
|
||||||
|
|
||||||
if constexpr (dynamic)
|
if constexpr (dynamic)
|
||||||
{
|
{
|
||||||
ExpressionType expr_type;
|
Bytecode::ExpressionType expr_type;
|
||||||
switch (type)
|
switch (type)
|
||||||
{
|
{
|
||||||
case SymbolType::endogenous:
|
case SymbolType::endogenous:
|
||||||
expr_type = ExpressionType::FirstEndoDerivative;
|
expr_type = Bytecode::ExpressionType::FirstEndoDerivative;
|
||||||
break;
|
break;
|
||||||
case SymbolType::exogenous:
|
case SymbolType::exogenous:
|
||||||
expr_type = ExpressionType::FirstExoDerivative;
|
expr_type = Bytecode::ExpressionType::FirstExoDerivative;
|
||||||
break;
|
break;
|
||||||
case SymbolType::exogenousDet:
|
case SymbolType::exogenousDet:
|
||||||
expr_type = ExpressionType::FirstExodetDerivative;
|
expr_type = Bytecode::ExpressionType::FirstExodetDerivative;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
assert(false);
|
assert(false);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
code_file << FNUMEXPR_ {expr_type, eq, tsid, lag};
|
code_file << Bytecode::FNUMEXPR_ {expr_type, eq, tsid, lag};
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
assert(type == SymbolType::endogenous);
|
assert(type == SymbolType::endogenous);
|
||||||
code_file << FNUMEXPR_ {ExpressionType::FirstEndoDerivative, eq, tsid};
|
code_file << Bytecode::FNUMEXPR_ {Bytecode::ExpressionType::FirstEndoDerivative, eq,
|
||||||
|
tsid};
|
||||||
}
|
}
|
||||||
|
|
||||||
d1->writeBytecodeOutput(code_file, output_type, temporary_terms_union, temporary_terms_idxs,
|
d1->writeBytecodeOutput(code_file, output_type, temporary_terms_union, temporary_terms_idxs,
|
||||||
|
@ -1702,22 +1708,22 @@ ModelTree::writeBytecodeHelper(BytecodeWriter& code_file) const
|
||||||
{
|
{
|
||||||
// Bytecode MEX uses a separate matrix for exogenous and exodet Jacobians
|
// Bytecode MEX uses a separate matrix for exogenous and exodet Jacobians
|
||||||
int jacob_col {type == SymbolType::endogenous ? getJacobianCol(deriv_id, false) : tsid};
|
int jacob_col {type == SymbolType::endogenous ? getJacobianCol(deriv_id, false) : tsid};
|
||||||
code_file << FSTPG3_ {eq, tsid, lag, jacob_col};
|
code_file << Bytecode::FSTPG3_ {eq, tsid, lag, jacob_col};
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
code_file << FSTPG2_ {eq, tsid};
|
code_file << Bytecode::FSTPG2_ {eq, tsid};
|
||||||
}
|
}
|
||||||
|
|
||||||
// Update jump offset for previous JMP
|
// Update jump offset for previous JMP
|
||||||
int pos_end_block {code_file.getInstructionCounter()};
|
int pos_end_block {code_file.getInstructionCounter()};
|
||||||
code_file.overwriteInstruction(pos_jmp, FJMP_ {pos_end_block - pos_jmp - 1});
|
code_file.overwriteInstruction(pos_jmp, Bytecode::FJMP_ {pos_end_block - pos_jmp - 1});
|
||||||
|
|
||||||
code_file << FENDBLOCK_ {} << FEND_ {};
|
code_file << Bytecode::FENDBLOCK_ {} << Bytecode::FEND_ {};
|
||||||
}
|
}
|
||||||
|
|
||||||
template<bool dynamic>
|
template<bool dynamic>
|
||||||
void
|
void
|
||||||
ModelTree::writeBlockBytecodeHelper(BytecodeWriter& code_file, int block,
|
ModelTree::writeBlockBytecodeHelper(Bytecode::Writer& code_file, int block,
|
||||||
temporary_terms_t& temporary_terms_union) const
|
temporary_terms_t& temporary_terms_union) const
|
||||||
{
|
{
|
||||||
constexpr ExprNodeBytecodeOutputType output_type {
|
constexpr ExprNodeBytecodeOutputType output_type {
|
||||||
|
@ -1740,13 +1746,14 @@ ModelTree::writeBlockBytecodeHelper(BytecodeWriter& code_file, int block,
|
||||||
it->writeBytecodeExternalFunctionOutput(code_file, output_type, temporary_terms_union,
|
it->writeBytecodeExternalFunctionOutput(code_file, output_type, temporary_terms_union,
|
||||||
blocks_temporary_terms_idxs, tef_terms);
|
blocks_temporary_terms_idxs, tef_terms);
|
||||||
|
|
||||||
code_file << FNUMEXPR_ {ExpressionType::TemporaryTerm, blocks_temporary_terms_idxs.at(it)};
|
code_file << Bytecode::FNUMEXPR_ {Bytecode::ExpressionType::TemporaryTerm,
|
||||||
|
blocks_temporary_terms_idxs.at(it)};
|
||||||
it->writeBytecodeOutput(code_file, output_type, temporary_terms_union,
|
it->writeBytecodeOutput(code_file, output_type, temporary_terms_union,
|
||||||
blocks_temporary_terms_idxs, tef_terms);
|
blocks_temporary_terms_idxs, tef_terms);
|
||||||
if constexpr (dynamic)
|
if constexpr (dynamic)
|
||||||
code_file << FSTPT_ {blocks_temporary_terms_idxs.at(it)};
|
code_file << Bytecode::FSTPT_ {blocks_temporary_terms_idxs.at(it)};
|
||||||
else
|
else
|
||||||
code_file << FSTPST_ {blocks_temporary_terms_idxs.at(it)};
|
code_file << Bytecode::FSTPST_ {blocks_temporary_terms_idxs.at(it)};
|
||||||
temporary_terms_union.insert(it);
|
temporary_terms_union.insert(it);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
@ -1772,7 +1779,8 @@ ModelTree::writeBlockBytecodeHelper(BytecodeWriter& code_file, int block,
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
assert(equ_type == EquationType::evaluate);
|
assert(equ_type == EquationType::evaluate);
|
||||||
code_file << FNUMEXPR_ {ExpressionType::ModelEquation, getBlockEquationID(block, i)};
|
code_file << Bytecode::FNUMEXPR_ {Bytecode::ExpressionType::ModelEquation,
|
||||||
|
getBlockEquationID(block, i)};
|
||||||
rhs->writeBytecodeOutput(code_file, output_type, temporary_terms_union,
|
rhs->writeBytecodeOutput(code_file, output_type, temporary_terms_union,
|
||||||
blocks_temporary_terms_idxs, tef_terms);
|
blocks_temporary_terms_idxs, tef_terms);
|
||||||
lhs->writeBytecodeOutput(code_file, assignment_lhs_output_type, temporary_terms_union,
|
lhs->writeBytecodeOutput(code_file, assignment_lhs_output_type, temporary_terms_union,
|
||||||
|
@ -1787,12 +1795,14 @@ ModelTree::writeBlockBytecodeHelper(BytecodeWriter& code_file, int block,
|
||||||
[[fallthrough]];
|
[[fallthrough]];
|
||||||
case BlockSimulationType::solveBackwardSimple:
|
case BlockSimulationType::solveBackwardSimple:
|
||||||
case BlockSimulationType::solveForwardSimple:
|
case BlockSimulationType::solveForwardSimple:
|
||||||
code_file << FNUMEXPR_ {ExpressionType::ModelEquation, getBlockEquationID(block, i)};
|
code_file << Bytecode::FNUMEXPR_ {Bytecode::ExpressionType::ModelEquation,
|
||||||
|
getBlockEquationID(block, i)};
|
||||||
lhs->writeBytecodeOutput(code_file, output_type, temporary_terms_union,
|
lhs->writeBytecodeOutput(code_file, output_type, temporary_terms_union,
|
||||||
blocks_temporary_terms_idxs, tef_terms);
|
blocks_temporary_terms_idxs, tef_terms);
|
||||||
rhs->writeBytecodeOutput(code_file, output_type, temporary_terms_union,
|
rhs->writeBytecodeOutput(code_file, output_type, temporary_terms_union,
|
||||||
blocks_temporary_terms_idxs, tef_terms);
|
blocks_temporary_terms_idxs, tef_terms);
|
||||||
code_file << FBINARY_ {BinaryOpcode::minus} << FSTPR_ {i - block_recursive};
|
code_file << Bytecode::FBINARY_ {BinaryOpcode::minus}
|
||||||
|
<< Bytecode::FSTPR_ {i - block_recursive};
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1807,11 +1817,11 @@ ModelTree::writeBlockBytecodeHelper(BytecodeWriter& code_file, int block,
|
||||||
be needed in subsequent blocks. */
|
be needed in subsequent blocks. */
|
||||||
write_eq_tt(blocks[block].size);
|
write_eq_tt(blocks[block].size);
|
||||||
|
|
||||||
code_file << FENDEQU_ {};
|
code_file << Bytecode::FENDEQU_ {};
|
||||||
|
|
||||||
// Get the current code_file position and jump if evaluating
|
// Get the current code_file position and jump if evaluating
|
||||||
int pos_jmpifeval {code_file.getInstructionCounter()};
|
int pos_jmpifeval {code_file.getInstructionCounter()};
|
||||||
code_file << FJMPIFEVAL_ {0}; // Use 0 as jump offset for the time being
|
code_file << Bytecode::FJMPIFEVAL_ {0}; // Use 0 as jump offset for the time being
|
||||||
|
|
||||||
/* Write the derivatives for the “simulate” mode (not needed if the block
|
/* Write the derivatives for the “simulate” mode (not needed if the block
|
||||||
is of type “evaluate backward/forward”) */
|
is of type “evaluate backward/forward”) */
|
||||||
|
@ -1825,15 +1835,16 @@ ModelTree::writeBlockBytecodeHelper(BytecodeWriter& code_file, int block,
|
||||||
{
|
{
|
||||||
int eqr {getBlockEquationID(block, 0)};
|
int eqr {getBlockEquationID(block, 0)};
|
||||||
int varr {getBlockVariableID(block, 0)};
|
int varr {getBlockVariableID(block, 0)};
|
||||||
code_file << FNUMEXPR_ {ExpressionType::FirstEndoDerivative, eqr, varr, 0};
|
code_file << Bytecode::FNUMEXPR_ {Bytecode::ExpressionType::FirstEndoDerivative, eqr,
|
||||||
|
varr, 0};
|
||||||
// Get contemporaneous derivative of the single variable in the block
|
// Get contemporaneous derivative of the single variable in the block
|
||||||
if (auto it {blocks_derivatives[block].find({0, 0, 0})};
|
if (auto it {blocks_derivatives[block].find({0, 0, 0})};
|
||||||
it != blocks_derivatives[block].end())
|
it != blocks_derivatives[block].end())
|
||||||
it->second->writeBytecodeOutput(code_file, output_type, temporary_terms_union,
|
it->second->writeBytecodeOutput(code_file, output_type, temporary_terms_union,
|
||||||
blocks_temporary_terms_idxs, tef_terms);
|
blocks_temporary_terms_idxs, tef_terms);
|
||||||
else
|
else
|
||||||
code_file << FLDZ_ {};
|
code_file << Bytecode::FLDZ_ {};
|
||||||
code_file << FSTPG_ {0};
|
code_file << Bytecode::FSTPG_ {0};
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
@ -1858,13 +1869,14 @@ ModelTree::writeBlockBytecodeHelper(BytecodeWriter& code_file, int block,
|
||||||
&& (simulation_type == BlockSimulationType::solveForwardComplete
|
&& (simulation_type == BlockSimulationType::solveForwardComplete
|
||||||
|| simulation_type == BlockSimulationType::solveBackwardComplete))
|
|| simulation_type == BlockSimulationType::solveBackwardComplete))
|
||||||
continue;
|
continue;
|
||||||
code_file << FNUMEXPR_ {ExpressionType::FirstEndoDerivative, eqr, varr, lag};
|
code_file << Bytecode::FNUMEXPR_ {Bytecode::ExpressionType::FirstEndoDerivative,
|
||||||
|
eqr, varr, lag};
|
||||||
d1->writeBytecodeOutput(code_file, output_type, temporary_terms_union,
|
d1->writeBytecodeOutput(code_file, output_type, temporary_terms_union,
|
||||||
blocks_temporary_terms_idxs, tef_terms);
|
blocks_temporary_terms_idxs, tef_terms);
|
||||||
if constexpr (dynamic)
|
if constexpr (dynamic)
|
||||||
code_file << FSTPU_ {count_u};
|
code_file << Bytecode::FSTPU_ {count_u};
|
||||||
else
|
else
|
||||||
code_file << FSTPSU_ {count_u};
|
code_file << Bytecode::FSTPSU_ {count_u};
|
||||||
Uf[eqr].emplace_back(count_u, varr, lag);
|
Uf[eqr].emplace_back(count_u, varr, lag);
|
||||||
count_u++;
|
count_u++;
|
||||||
}
|
}
|
||||||
|
@ -1872,22 +1884,25 @@ ModelTree::writeBlockBytecodeHelper(BytecodeWriter& code_file, int block,
|
||||||
for (int i {0}; i < block_size; i++)
|
for (int i {0}; i < block_size; i++)
|
||||||
if (i >= block_recursive)
|
if (i >= block_recursive)
|
||||||
{
|
{
|
||||||
code_file << FLDR_ {i - block_recursive} << FLDZ_ {};
|
code_file << Bytecode::FLDR_ {i - block_recursive} << Bytecode::FLDZ_ {};
|
||||||
|
|
||||||
int eqr {getBlockEquationID(block, i)};
|
int eqr {getBlockEquationID(block, i)};
|
||||||
for (const auto& [index_u, var, lag] : Uf[eqr])
|
for (const auto& [index_u, var, lag] : Uf[eqr])
|
||||||
{
|
{
|
||||||
if constexpr (dynamic)
|
if constexpr (dynamic)
|
||||||
code_file << FLDU_ {index_u} << FLDV_ {SymbolType::endogenous, var, lag};
|
code_file << Bytecode::FLDU_ {index_u}
|
||||||
|
<< Bytecode::FLDV_ {SymbolType::endogenous, var, lag};
|
||||||
else
|
else
|
||||||
code_file << FLDSU_ {index_u} << FLDSV_ {SymbolType::endogenous, var};
|
code_file << Bytecode::FLDSU_ {index_u}
|
||||||
code_file << FBINARY_ {BinaryOpcode::times} << FBINARY_ {BinaryOpcode::plus};
|
<< Bytecode::FLDSV_ {SymbolType::endogenous, var};
|
||||||
|
code_file << Bytecode::FBINARY_ {BinaryOpcode::times}
|
||||||
|
<< Bytecode::FBINARY_ {BinaryOpcode::plus};
|
||||||
}
|
}
|
||||||
code_file << FBINARY_ {BinaryOpcode::minus};
|
code_file << Bytecode::FBINARY_ {BinaryOpcode::minus};
|
||||||
if constexpr (dynamic)
|
if constexpr (dynamic)
|
||||||
code_file << FSTPU_ {i - block_recursive};
|
code_file << Bytecode::FSTPU_ {i - block_recursive};
|
||||||
else
|
else
|
||||||
code_file << FSTPSU_ {i - block_recursive};
|
code_file << Bytecode::FSTPSU_ {i - block_recursive};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -1898,9 +1913,9 @@ ModelTree::writeBlockBytecodeHelper(BytecodeWriter& code_file, int block,
|
||||||
|
|
||||||
// Jump unconditionally after the block
|
// Jump unconditionally after the block
|
||||||
int pos_jmp {code_file.getInstructionCounter()};
|
int pos_jmp {code_file.getInstructionCounter()};
|
||||||
code_file << FJMP_ {0}; // Use 0 as jump offset for the time being
|
code_file << Bytecode::FJMP_ {0}; // Use 0 as jump offset for the time being
|
||||||
// Update jump offset for previous JMPIFEVAL
|
// Update jump offset for previous JMPIFEVAL
|
||||||
code_file.overwriteInstruction(pos_jmpifeval, FJMPIFEVAL_ {pos_jmp - pos_jmpifeval});
|
code_file.overwriteInstruction(pos_jmpifeval, Bytecode::FJMPIFEVAL_ {pos_jmp - pos_jmpifeval});
|
||||||
|
|
||||||
// Write the derivatives for the “evaluate” mode
|
// Write the derivatives for the “evaluate” mode
|
||||||
for (const auto& [indices, d] : blocks_derivatives[block])
|
for (const auto& [indices, d] : blocks_derivatives[block])
|
||||||
|
@ -1908,22 +1923,24 @@ ModelTree::writeBlockBytecodeHelper(BytecodeWriter& code_file, int block,
|
||||||
const auto& [eq, var, lag] {indices};
|
const auto& [eq, var, lag] {indices};
|
||||||
int eqr {getBlockEquationID(block, eq)};
|
int eqr {getBlockEquationID(block, eq)};
|
||||||
int varr {getBlockVariableID(block, var)};
|
int varr {getBlockVariableID(block, var)};
|
||||||
code_file << FNUMEXPR_ {ExpressionType::FirstEndoDerivative, eqr, varr, lag};
|
code_file << Bytecode::FNUMEXPR_ {Bytecode::ExpressionType::FirstEndoDerivative, eqr, varr,
|
||||||
|
lag};
|
||||||
d->writeBytecodeOutput(code_file, output_type, temporary_terms_union,
|
d->writeBytecodeOutput(code_file, output_type, temporary_terms_union,
|
||||||
blocks_temporary_terms_idxs, tef_terms);
|
blocks_temporary_terms_idxs, tef_terms);
|
||||||
assert(eq >= block_recursive);
|
assert(eq >= block_recursive);
|
||||||
if constexpr (dynamic)
|
if constexpr (dynamic)
|
||||||
code_file << FSTPG3_ {eq - block_recursive, var, lag,
|
code_file << Bytecode::FSTPG3_ {eq - block_recursive, var, lag,
|
||||||
getBlockJacobianEndoCol(block, var, lag)};
|
getBlockJacobianEndoCol(block, var, lag)};
|
||||||
else
|
else
|
||||||
code_file << FSTPG2_ {eq - block_recursive, getBlockJacobianEndoCol(block, var, lag)};
|
code_file << Bytecode::FSTPG2_ {eq - block_recursive,
|
||||||
|
getBlockJacobianEndoCol(block, var, lag)};
|
||||||
}
|
}
|
||||||
|
|
||||||
// Update jump offset for previous JMP
|
// Update jump offset for previous JMP
|
||||||
int pos_end_block {code_file.getInstructionCounter()};
|
int pos_end_block {code_file.getInstructionCounter()};
|
||||||
code_file.overwriteInstruction(pos_jmp, FJMP_ {pos_end_block - pos_jmp - 1});
|
code_file.overwriteInstruction(pos_jmp, Bytecode::FJMP_ {pos_end_block - pos_jmp - 1});
|
||||||
|
|
||||||
code_file << FENDBLOCK_ {};
|
code_file << Bytecode::FENDBLOCK_ {};
|
||||||
}
|
}
|
||||||
|
|
||||||
template<bool dynamic>
|
template<bool dynamic>
|
||||||
|
|
|
@ -131,24 +131,24 @@ StaticModel::writeStaticBytecode(const string& basename) const
|
||||||
// First write the .bin file
|
// First write the .bin file
|
||||||
int u_count_int {writeBytecodeBinFile(basename + "/model/bytecode/static.bin", false)};
|
int u_count_int {writeBytecodeBinFile(basename + "/model/bytecode/static.bin", false)};
|
||||||
|
|
||||||
BytecodeWriter code_file {basename + "/model/bytecode/static.cod"};
|
Bytecode::Writer code_file {basename + "/model/bytecode/static.cod"};
|
||||||
vector<int> eq_idx(equations.size());
|
vector<int> eq_idx(equations.size());
|
||||||
iota(eq_idx.begin(), eq_idx.end(), 0);
|
iota(eq_idx.begin(), eq_idx.end(), 0);
|
||||||
vector<int> endo_idx(symbol_table.endo_nbr());
|
vector<int> endo_idx(symbol_table.endo_nbr());
|
||||||
iota(endo_idx.begin(), endo_idx.end(), 0);
|
iota(endo_idx.begin(), endo_idx.end(), 0);
|
||||||
|
|
||||||
// Declare temporary terms and the (single) block
|
// Declare temporary terms and the (single) block
|
||||||
code_file << FDIMST_ {static_cast<int>(temporary_terms_derivatives[0].size()
|
code_file << Bytecode::FDIMST_ {static_cast<int>(temporary_terms_derivatives[0].size()
|
||||||
+ temporary_terms_derivatives[1].size())}
|
+ temporary_terms_derivatives[1].size())}
|
||||||
<< FBEGINBLOCK_ {symbol_table.endo_nbr(),
|
<< Bytecode::FBEGINBLOCK_ {symbol_table.endo_nbr(),
|
||||||
BlockSimulationType::solveForwardComplete,
|
BlockSimulationType::solveForwardComplete,
|
||||||
0,
|
0,
|
||||||
symbol_table.endo_nbr(),
|
symbol_table.endo_nbr(),
|
||||||
endo_idx,
|
endo_idx,
|
||||||
eq_idx,
|
eq_idx,
|
||||||
false,
|
false,
|
||||||
u_count_int,
|
u_count_int,
|
||||||
symbol_table.endo_nbr()};
|
symbol_table.endo_nbr()};
|
||||||
|
|
||||||
writeBytecodeHelper<false>(code_file);
|
writeBytecodeHelper<false>(code_file);
|
||||||
}
|
}
|
||||||
|
@ -156,7 +156,7 @@ StaticModel::writeStaticBytecode(const string& basename) const
|
||||||
void
|
void
|
||||||
StaticModel::writeStaticBlockBytecode(const string& basename) const
|
StaticModel::writeStaticBlockBytecode(const string& basename) const
|
||||||
{
|
{
|
||||||
BytecodeWriter code_file {basename + "/model/bytecode/block/static.cod"};
|
Bytecode::Writer code_file {basename + "/model/bytecode/block/static.cod"};
|
||||||
|
|
||||||
const filesystem::path bin_filename {basename + "/model/bytecode/block/static.bin"};
|
const filesystem::path bin_filename {basename + "/model/bytecode/block/static.bin"};
|
||||||
ofstream bin_file {bin_filename, ios::out | ios::binary};
|
ofstream bin_file {bin_filename, ios::out | ios::binary};
|
||||||
|
@ -167,7 +167,7 @@ StaticModel::writeStaticBlockBytecode(const string& basename) const
|
||||||
}
|
}
|
||||||
|
|
||||||
// Temporary variables declaration
|
// Temporary variables declaration
|
||||||
code_file << FDIMST_ {static_cast<int>(blocks_temporary_terms_idxs.size())};
|
code_file << Bytecode::FDIMST_ {static_cast<int>(blocks_temporary_terms_idxs.size())};
|
||||||
|
|
||||||
temporary_terms_t temporary_terms_written;
|
temporary_terms_t temporary_terms_written;
|
||||||
|
|
||||||
|
@ -181,19 +181,19 @@ StaticModel::writeStaticBlockBytecode(const string& basename) const
|
||||||
? writeBlockBytecodeBinFile(bin_file, block)
|
? writeBlockBytecodeBinFile(bin_file, block)
|
||||||
: 0};
|
: 0};
|
||||||
|
|
||||||
code_file << FBEGINBLOCK_ {blocks[block].mfs_size,
|
code_file << Bytecode::FBEGINBLOCK_ {blocks[block].mfs_size,
|
||||||
simulation_type,
|
simulation_type,
|
||||||
blocks[block].first_equation,
|
blocks[block].first_equation,
|
||||||
block_size,
|
block_size,
|
||||||
endo_idx_block2orig,
|
endo_idx_block2orig,
|
||||||
eq_idx_block2orig,
|
eq_idx_block2orig,
|
||||||
blocks[block].linear,
|
blocks[block].linear,
|
||||||
u_count,
|
u_count,
|
||||||
block_size};
|
block_size};
|
||||||
|
|
||||||
writeBlockBytecodeHelper<false>(code_file, block, temporary_terms_written);
|
writeBlockBytecodeHelper<false>(code_file, block, temporary_terms_written);
|
||||||
}
|
}
|
||||||
code_file << FEND_ {};
|
code_file << Bytecode::FEND_ {};
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
|
Loading…
Reference in New Issue