Select Git revision
BuiltinFunctionProcessor.hpp
-
Stéphane Del Pino authored
- code is now generic (even if more testing remains). - data types are now check accordingly to catch error in a clean way In some cases (generally?) data types can only be checked at runtime. This is the case for instance if function definition depends on the dimension (which is likely to happen in many cases). Thus a special procedure has been developed to indicate where the semantic error occurs at runtime. (this is in some way related to issue #19)
Stéphane Del Pino authored- code is now generic (even if more testing remains). - data types are now check accordingly to catch error in a clean way In some cases (generally?) data types can only be checked at runtime. This is the case for instance if function definition depends on the dimension (which is likely to happen in many cases). Thus a special procedure has been developed to indicate where the semantic error occurs at runtime. (this is in some way related to issue #19)
ASTNodeExpressionBuilder.cpp 7.18 KiB
#include <language/ast/ASTNodeExpressionBuilder.hpp>
#include <language/PEGGrammar.hpp>
#include <language/ast/ASTNodeAffectationExpressionBuilder.hpp>
#include <language/ast/ASTNodeArraySubscriptExpressionBuilder.hpp>
#include <language/ast/ASTNodeBinaryOperatorExpressionBuilder.hpp>
#include <language/ast/ASTNodeFunctionEvaluationExpressionBuilder.hpp>
#include <language/ast/ASTNodeIncDecExpressionBuilder.hpp>
#include <language/ast/ASTNodeListAffectationExpressionBuilder.hpp>
#include <language/ast/ASTNodeUnaryOperatorExpressionBuilder.hpp>
#include <language/node_processor/ASTNodeExpressionListProcessor.hpp>
#include <language/node_processor/ASTNodeListProcessor.hpp>
#include <language/node_processor/BreakProcessor.hpp>
#include <language/node_processor/ContinueProcessor.hpp>
#include <language/node_processor/DoWhileProcessor.hpp>
#include <language/node_processor/FakeProcessor.hpp>
#include <language/node_processor/ForProcessor.hpp>
#include <language/node_processor/IfProcessor.hpp>
#include <language/node_processor/LocalNameProcessor.hpp>
#include <language/node_processor/NameProcessor.hpp>
#include <language/node_processor/OStreamProcessor.hpp>
#include <language/node_processor/TupleToTinyVectorProcessor.hpp>
#include <language/node_processor/TupleToVectorProcessor.hpp>
#include <language/node_processor/ValueProcessor.hpp>
#include <language/node_processor/WhileProcessor.hpp>
#include <language/utils/ParseError.hpp>
void
ASTNodeExpressionBuilder::_buildExpression(ASTNode& n)
{
if (n.is_type<language::block>()) {
n.m_node_processor = std::make_unique<ASTNodeListProcessor>(n);
} else if ((n.is_type<language::eq_op>() or n.is_type<language::multiplyeq_op>() or
n.is_type<language::divideeq_op>() or n.is_type<language::pluseq_op>() or
n.is_type<language::minuseq_op>())) {
if (n.children[0]->is_type<language::name_list>() or n.children[0]->is_type<language::lvalue_list>()) {
ASTNodeListAffectationExpressionBuilder{n};
} else {
ASTNodeAffectationExpressionBuilder{n};
}
} else if (n.is_type<language::tuple_expression>()) {
n.m_node_processor = std::make_unique<TupleToVectorProcessor<ASTNodeExpressionListProcessor>>(n);
} else if (n.is_type<language::function_definition>()) {
n.m_node_processor = std::make_unique<FakeProcessor>();
} else if (n.is_type<language::function_evaluation>()) {
ASTNodeFunctionEvaluationExpressionBuilder{n};
} else if (n.is_type<language::subscript_expression>()) {
ASTNodeArraySubscriptExpressionBuilder{n};
} else if (n.is_type<language::real>()) {
n.m_node_processor = std::make_unique<ValueProcessor>(n);
} else if (n.is_type<language::integer>()) {
n.m_node_processor = std::make_unique<ValueProcessor>(n);
} else if (n.is_type<language::literal>()) {
n.m_node_processor = std::make_unique<ValueProcessor>(n);
} else if (n.is_type<language::true_kw>()) {
n.m_node_processor = std::make_unique<ValueProcessor>(n);
} else if (n.is_type<language::false_kw>()) {
n.m_node_processor = std::make_unique<ValueProcessor>(n);
} else if ((n.is_type<language::function_argument_list>()) or (n.is_type<language::expression_list>())) {
n.m_node_processor = std::make_unique<ASTNodeExpressionListProcessor>(n);
} else if (n.is_type<language::name_list>() or n.is_type<language::lvalue_list>()) {
n.m_node_processor = std::make_unique<FakeProcessor>();
} else if (n.is_type<language::name>()) {
// Dealing with contexts
auto [i_symbol, success] = n.m_symbol_table->find(n.string(), n.begin());
if (i_symbol->attributes().hasLocalContext()) {
n.m_node_processor = std::make_unique<LocalNameProcessor>(n);
} else {
n.m_node_processor = std::make_unique<NameProcessor>(n);
}
} else if (n.is_type<language::unary_minus>() or n.is_type<language::unary_not>()) {
ASTNodeUnaryOperatorExpressionBuilder{n};
} else if (n.is_type<language::unary_minusminus>() or n.is_type<language::unary_plusplus>() or
n.is_type<language::post_minusminus>() or n.is_type<language::post_plusplus>()) {
ASTNodeIncDecExpressionBuilder{n};
} else if (n.is_type<language::multiply_op>() or n.is_type<language::divide_op>() or n.is_type<language::plus_op>() or
n.is_type<language::minus_op>() or n.is_type<language::or_op>() or n.is_type<language::and_op>() or
n.is_type<language::xor_op>() or n.is_type<language::greater_op>() or
n.is_type<language::greater_or_eq_op>() or n.is_type<language::lesser_op>() or
n.is_type<language::lesser_or_eq_op>() or n.is_type<language::eqeq_op>() or
n.is_type<language::not_eq_op>()) {
ASTNodeBinaryOperatorExpressionBuilder{n};
} else if (n.is_type<language::cout_kw>()) {
n.m_node_processor = std::make_unique<OStreamProcessor>(n, std::cout);
} else if (n.is_type<language::cerr_kw>()) {
n.m_node_processor = std::make_unique<OStreamProcessor>(n, std::cerr);
} else if (n.is_type<language::clog_kw>()) {
n.m_node_processor = std::make_unique<OStreamProcessor>(n, std::clog);
} else if (n.is_type<language::if_statement>()) {
n.m_node_processor = std::make_unique<IfProcessor>(n);
} else if (n.is_type<language::statement_block>()) {
n.m_node_processor = std::make_unique<ASTNodeListProcessor>(n);
} else if (n.is_type<language::do_while_statement>()) {
n.m_node_processor = std::make_unique<DoWhileProcessor>(n);
} else if (n.is_type<language::while_statement>()) {
n.m_node_processor = std::make_unique<WhileProcessor>(n);
} else if (n.is_type<language::for_statement>()) {
n.m_node_processor = std::make_unique<ForProcessor>(n);
} else if (n.is_type<language::for_statement_block>()) {
n.m_node_processor = std::make_unique<ASTNodeListProcessor>(n);
} else if (n.is_type<language::for_init>()) {
n.m_node_processor = std::make_unique<FakeProcessor>();
} else if (n.is_type<language::for_post>()) {
n.m_node_processor = std::make_unique<FakeProcessor>();
} else if (n.is_type<language::for_test>()) {
n.m_node_processor = std::make_unique<ValueProcessor>(n);
} else if (n.is_type<language::break_kw>()) {
n.m_node_processor = std::make_unique<BreakProcessor>();
} else if (n.is_type<language::continue_kw>()) {
n.m_node_processor = std::make_unique<ContinueProcessor>();
} else {
std::ostringstream error_message;
error_message << "undefined node processor type '" << rang::fgB::red << n.name() << rang::fg::reset << "'";
throw ParseError{error_message.str(), std::vector{n.begin()}};
}
for (auto& child : n.children) {
this->_buildExpression(*child);
}
}
ASTNodeExpressionBuilder::ASTNodeExpressionBuilder(ASTNode& node)
{
Assert(node.is_root());
node.m_node_processor = std::make_unique<ASTNodeListProcessor>(node);
for (auto& child : node.children) {
this->_buildExpression(*child);
}
// Build expressions of functions
FunctionTable& function_table = node.m_symbol_table->functionTable();
for (size_t function_id = 0; function_id < function_table.size(); ++function_id) {
FunctionDescriptor& function_descriptor = function_table[function_id];
ASTNode& function_expression = function_descriptor.definitionNode();
this->_buildExpression(function_expression);
}
}