Skip to content
Snippets Groups Projects
Commit 246d8a38 authored by Stéphane Del Pino's avatar Stéphane Del Pino
Browse files

Add missing tests for BinaryExpressionProcessor

parent b5786502
No related branches found
No related tags found
1 merge request!116Add tests for EmbeddedIDiscreteFunctionUtils
......@@ -232,7 +232,7 @@ struct BinaryExpressionProcessor<BinaryOpT, std::shared_ptr<ValueT>, std::shared
return this->_eval(m_node.children[0]->execute(exec_policy), m_node.children[1]->execute(exec_policy));
}
catch (const NormalError& error) {
throw ParseError(error.what(), m_node.begin());
throw ParseError(error.what(), m_node.begin()); // LCOV_EXCL_LINE
}
}
......@@ -269,7 +269,7 @@ struct BinaryExpressionProcessor<BinaryOpT, std::shared_ptr<ValueT>, A_DataT, st
return this->_eval(m_node.children[0]->execute(exec_policy), m_node.children[1]->execute(exec_policy));
}
catch (const NormalError& error) {
throw ParseError(error.what(), m_node.begin());
throw ParseError(error.what(), m_node.begin()); // LCOV_EXCL_LINE
}
}
......@@ -306,7 +306,7 @@ struct BinaryExpressionProcessor<BinaryOpT, std::shared_ptr<ValueT>, std::shared
return this->_eval(m_node.children[0]->execute(exec_policy), m_node.children[1]->execute(exec_policy));
}
catch (const NormalError& error) {
throw ParseError(error.what(), m_node.begin());
throw ParseError(error.what(), m_node.begin()); // LCOV_EXCL_LINE
}
}
......
#include <catch2/catch_test_macros.hpp>
#include <catch2/matchers/catch_matchers_all.hpp>
#include <language/utils/ASTNodeDataTypeTraits.hpp>
#include <language/utils/BasicAffectationRegistrerFor.hpp>
#include <language/utils/BinaryOperatorProcessorBuilder.hpp>
#include <language/utils/DataHandler.hpp>
#include <language/utils/OperatorRepository.hpp>
#include <language/utils/TypeDescriptor.hpp>
#include <test_BinaryExpressionProcessor_utils.hpp>
// clazy:excludeall=non-pod-global-static
template <>
inline ASTNodeDataType ast_node_data_type_from<std::shared_ptr<const double>> =
ASTNodeDataType::build<ASTNodeDataType::type_id_t>("builtin_t");
const auto builtin_data_type = ast_node_data_type_from<std::shared_ptr<const double>>;
inline std::shared_ptr<const double>
operator+(const std::shared_ptr<const double>& p_a, const std::shared_ptr<const double>& p_b)
{
return std::make_shared<double>(*p_a + *p_b);
}
inline std::shared_ptr<const double>
operator/(const std::shared_ptr<const double>&, const std::shared_ptr<const double>&)
{
throw std::runtime_error("runtime error both");
}
inline std::shared_ptr<const double>
operator/(const std::shared_ptr<const double>&, double)
{
throw std::runtime_error("runtime error lhs");
}
inline std::shared_ptr<const double>
operator/(double, const std::shared_ptr<const double>&)
{
throw std::runtime_error("runtime error rhs");
}
inline std::shared_ptr<const double>
operator+(const std::shared_ptr<const double>& p_a, double b)
{
return std::make_shared<double>(*p_a + b);
}
inline std::shared_ptr<const double>
operator+(double a, const std::shared_ptr<const double>& p_b)
{
return std::make_shared<double>(a + *p_b);
}
TEST_CASE("BinaryExpressionProcessor arithmetic", "[language]")
{
SECTION("+")
......@@ -151,4 +199,186 @@ TEST_CASE("BinaryExpressionProcessor arithmetic", "[language]")
CHECK_BINARY_EXPRESSION_RESULT(R"(let r:R, r = -1.2 / 2.3;)", "r", (-1.2 / 2.3));
}
}
SECTION("binary operator [builtin]")
{
#define CHECK_BUILTIN_BINARY_EXPRESSION_RESULT(data, result) \
{ \
TAO_PEGTL_NAMESPACE::string_input input{data, "test.pgs"}; \
auto ast = ASTBuilder::build(input); \
\
ASTModulesImporter{*ast}; \
\
BasicAffectationRegisterFor<EmbeddedData>{ASTNodeDataType::build<ASTNodeDataType::type_id_t>("builtin_t")}; \
\
OperatorRepository& repository = OperatorRepository::instance(); \
\
repository.addBinaryOperator<language::plus_op>( \
std::make_shared< \
BinaryOperatorProcessorBuilder<language::plus_op, std::shared_ptr<const double>, \
std::shared_ptr<const double>, std::shared_ptr<const double>>>()); \
\
repository.addBinaryOperator<language::plus_op>( \
std::make_shared<BinaryOperatorProcessorBuilder<language::plus_op, std::shared_ptr<const double>, \
std::shared_ptr<const double>, double>>()); \
\
repository.addBinaryOperator<language::plus_op>( \
std::make_shared<BinaryOperatorProcessorBuilder<language::plus_op, std::shared_ptr<const double>, double, \
std::shared_ptr<const double>>>()); \
\
SymbolTable& symbol_table = *ast->m_symbol_table; \
auto [i_symbol, success] = symbol_table.add(builtin_data_type.nameOfTypeId(), ast->begin()); \
if (not success) { \
throw UnexpectedError("cannot add '" + builtin_data_type.nameOfTypeId() + "' type for testing"); \
} \
\
i_symbol->attributes().setDataType(ASTNodeDataType::build<ASTNodeDataType::type_name_id_t>()); \
i_symbol->attributes().setIsInitialized(); \
i_symbol->attributes().value() = symbol_table.typeEmbedderTable().size(); \
symbol_table.typeEmbedderTable().add(std::make_shared<TypeDescriptor>(builtin_data_type.nameOfTypeId())); \
\
auto [i_symbol_bt_a, success_bt_a] = symbol_table.add("bt_a", ast->begin()); \
if (not success_bt_a) { \
throw UnexpectedError("cannot add 'bt_a' of type builtin_t for testing"); \
} \
i_symbol_bt_a->attributes().setDataType(ast_node_data_type_from<std::shared_ptr<const double>>); \
i_symbol_bt_a->attributes().setIsInitialized(); \
i_symbol_bt_a->attributes().value() = \
EmbeddedData(std::make_shared<DataHandler<const double>>(std::make_shared<double>(3.2))); \
\
auto [i_symbol_bt_b, success_bt_b] = symbol_table.add("bt_b", ast->begin()); \
if (not success_bt_b) { \
throw UnexpectedError("cannot add 'bt_b' of type builtin_t for testing"); \
} \
i_symbol_bt_b->attributes().setDataType(ast_node_data_type_from<std::shared_ptr<const double>>); \
i_symbol_bt_b->attributes().setIsInitialized(); \
i_symbol_bt_b->attributes().value() = \
EmbeddedData(std::make_shared<DataHandler<const double>>(std::make_shared<double>(5.3))); \
\
ASTNodeTypeCleaner<language::import_instruction>{*ast}; \
\
ASTSymbolTableBuilder{*ast}; \
ASTNodeDataTypeBuilder{*ast}; \
\
ASTNodeDeclarationToAffectationConverter{*ast}; \
ASTNodeTypeCleaner<language::var_declaration>{*ast}; \
\
ASTNodeExpressionBuilder{*ast}; \
ExecutionPolicy exec_policy; \
ast->execute(exec_policy); \
\
using namespace TAO_PEGTL_NAMESPACE; \
position use_position{internal::iterator{"fixture"}, "fixture"}; \
use_position.byte = 10000; \
auto [symbol, found] = symbol_table.find("r", use_position); \
\
auto attributes = symbol->attributes(); \
auto embedded_value = std::get<EmbeddedData>(attributes.value()); \
\
double value = *dynamic_cast<const DataHandler<const double>&>(embedded_value.get()).data_ptr(); \
REQUIRE(value == expected); \
}
SECTION("builtin both side")
{
std::string_view data = R"(let r:builtin_t, r = bt_a + bt_b;)";
const double expected = double{3.2} + double{5.3};
CHECK_BUILTIN_BINARY_EXPRESSION_RESULT(data, expected);
}
SECTION("builtin lhs")
{
std::string_view data = R"(let r:builtin_t, r = bt_a + 5.;)";
const double expected = double{3.2} + double{5};
CHECK_BUILTIN_BINARY_EXPRESSION_RESULT(data, expected);
}
SECTION("builtin rhs")
{
std::string_view data = R"(let r:builtin_t, r = 5. + bt_a;)";
const double expected = double{3.2} + double{5};
CHECK_BUILTIN_BINARY_EXPRESSION_RESULT(data, expected);
}
#define CHECK_BUILTIN_BINARY_EXPRESSION_ERROR(data, error_msg) \
{ \
TAO_PEGTL_NAMESPACE::string_input input{data, "test.pgs"}; \
auto ast = ASTBuilder::build(input); \
\
ASTModulesImporter{*ast}; \
\
BasicAffectationRegisterFor<EmbeddedData>{ASTNodeDataType::build<ASTNodeDataType::type_id_t>("builtin_t")}; \
\
OperatorRepository& repository = OperatorRepository::instance(); \
\
repository.addBinaryOperator<language::divide_op>( \
std::make_shared< \
BinaryOperatorProcessorBuilder<language::divide_op, std::shared_ptr<const double>, \
std::shared_ptr<const double>, std::shared_ptr<const double>>>()); \
\
repository.addBinaryOperator<language::divide_op>( \
std::make_shared<BinaryOperatorProcessorBuilder<language::divide_op, std::shared_ptr<const double>, \
std::shared_ptr<const double>, double>>()); \
\
repository.addBinaryOperator<language::divide_op>( \
std::make_shared<BinaryOperatorProcessorBuilder<language::divide_op, std::shared_ptr<const double>, double, \
std::shared_ptr<const double>>>()); \
\
SymbolTable& symbol_table = *ast->m_symbol_table; \
auto [i_symbol, success] = symbol_table.add(builtin_data_type.nameOfTypeId(), ast->begin()); \
if (not success) { \
throw UnexpectedError("cannot add '" + builtin_data_type.nameOfTypeId() + "' type for testing"); \
} \
\
i_symbol->attributes().setDataType(ASTNodeDataType::build<ASTNodeDataType::type_name_id_t>()); \
i_symbol->attributes().setIsInitialized(); \
i_symbol->attributes().value() = symbol_table.typeEmbedderTable().size(); \
symbol_table.typeEmbedderTable().add(std::make_shared<TypeDescriptor>(builtin_data_type.nameOfTypeId())); \
\
auto [i_symbol_bt_a, success_bt_a] = symbol_table.add("bt_a", ast->begin()); \
if (not success_bt_a) { \
throw UnexpectedError("cannot add 'bt_a' of type builtin_t for testing"); \
} \
i_symbol_bt_a->attributes().setDataType(ast_node_data_type_from<std::shared_ptr<const double>>); \
i_symbol_bt_a->attributes().setIsInitialized(); \
i_symbol_bt_a->attributes().value() = \
EmbeddedData(std::make_shared<DataHandler<const double>>(std::make_shared<double>(3.2))); \
\
auto [i_symbol_bt_b, success_bt_b] = symbol_table.add("bt_b", ast->begin()); \
if (not success_bt_b) { \
throw UnexpectedError("cannot add 'bt_b' of type builtin_t for testing"); \
} \
i_symbol_bt_b->attributes().setDataType(ast_node_data_type_from<std::shared_ptr<const double>>); \
i_symbol_bt_b->attributes().setIsInitialized(); \
i_symbol_bt_b->attributes().value() = \
EmbeddedData(std::make_shared<DataHandler<const double>>(std::make_shared<double>(5.3))); \
\
ASTNodeTypeCleaner<language::import_instruction>{*ast}; \
\
ASTSymbolTableBuilder{*ast}; \
ASTNodeDataTypeBuilder{*ast}; \
\
ASTNodeDeclarationToAffectationConverter{*ast}; \
ASTNodeTypeCleaner<language::var_declaration>{*ast}; \
\
ASTNodeExpressionBuilder{*ast}; \
ExecutionPolicy exec_policy; \
REQUIRE_THROWS_WITH(ast->execute(exec_policy), error_msg); \
}
SECTION("runtime error")
{
std::string_view data_both = R"(let r:builtin_t, r = bt_a / bt_b;)";
CHECK_BUILTIN_BINARY_EXPRESSION_ERROR(data_both, "runtime error both");
std::string_view data_lhs = R"(let r:builtin_t, r = bt_a / 2.3;)";
CHECK_BUILTIN_BINARY_EXPRESSION_ERROR(data_lhs, "runtime error lhs");
std::string_view data_rhs = R"(let r:builtin_t, r = 2.3/ bt_a;)";
CHECK_BUILTIN_BINARY_EXPRESSION_ERROR(data_rhs, "runtime error rhs");
}
}
}
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment