aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
Diffstat (limited to 'gcc')
-rw-r--r--gcc/gcc/elna-builtins.cc20
-rw-r--r--gcc/gcc/elna-diagnostic.cc4
-rw-r--r--gcc/gcc/elna-generic.cc388
-rw-r--r--gcc/gcc/elna-tree.cc36
4 files changed, 154 insertions, 294 deletions
diff --git a/gcc/gcc/elna-builtins.cc b/gcc/gcc/elna-builtins.cc
index 141b34f..77ffb1c 100644
--- a/gcc/gcc/elna-builtins.cc
+++ b/gcc/gcc/elna-builtins.cc
@@ -38,17 +38,6 @@ namespace elna::gcc
elna_bool_false_node = boolean_false_node;
elna_pointer_nil_node = null_pointer_node;
-
- elna_string_type_node = make_node(RECORD_TYPE);
- tree string_ptr_type = build_pointer_type(elna_char_type_node);
-
- elna_string_length_field_node = build_field(UNKNOWN_LOCATION,
- elna_string_type_node, "length", build_qualified_type(elna_word_type_node, TYPE_QUAL_CONST));
- elna_string_ptr_field_node = build_field(UNKNOWN_LOCATION,
- elna_string_type_node, "ptr", build_qualified_type(string_ptr_type, TYPE_QUAL_CONST));
-
- TYPE_FIELDS(elna_string_type_node) = chainon(elna_string_ptr_field_node, elna_string_length_field_node);
- layout_type(elna_string_type_node);
}
static
@@ -73,10 +62,6 @@ namespace elna::gcc
declare_builtin_type(builtin_table, "Pointer", elna_pointer_type_node);
declare_builtin_type(builtin_table, "Float", elna_float_type_node);
- tree string_declaration = declare_builtin_type(builtin_table, "String", elna_string_type_node);
- TYPE_NAME(elna_string_type_node) = DECL_NAME(string_declaration);
- TYPE_STUB_DECL(elna_string_type_node) = string_declaration;
-
return builtin_table;
}
@@ -165,7 +150,7 @@ namespace elna::gcc
TYPE_FIELDS(slice_record) = chainon(ptr_field, length_field);
layout_type(slice_record);
- return slice_record;
+ return type_hash_canon(type_hash_canon_hash(slice_record), slice_record);
}
else if (auto reference = type.get<boot::procedure_type>())
{
@@ -175,7 +160,8 @@ namespace elna::gcc
}
else if (auto reference = type.get<boot::constant_type>())
{
- return get_inner_alias(reference->unqualified, symbols);
+ tree unqualified = get_inner_alias(reference->unqualified, symbols);
+ return build_qualified_type(unqualified, TYPE_QUAL_CONST);
}
else if (auto reference = type.get<boot::alias_type>())
{
diff --git a/gcc/gcc/elna-diagnostic.cc b/gcc/gcc/elna-diagnostic.cc
index 3769ee4..630db0c 100644
--- a/gcc/gcc/elna-diagnostic.cc
+++ b/gcc/gcc/elna-diagnostic.cc
@@ -108,10 +108,6 @@ namespace elna::gcc
{
return "Char";
}
- else if (unqualified_type == elna_string_type_node)
- {
- return "String";
- }
else if (is_void_type(unqualified_type)) // For procedures without a return type.
{
return "()";
diff --git a/gcc/gcc/elna-generic.cc b/gcc/gcc/elna-generic.cc
index ea209df..c2c59aa 100644
--- a/gcc/gcc/elna-generic.cc
+++ b/gcc/gcc/elna-generic.cc
@@ -126,18 +126,7 @@ namespace elna::gcc
? this->current_expression
: TREE_TYPE(this->current_expression);
- if (TREE_CODE(expression_type) == RECORD_TYPE
- && TYPE_NAME(expression_type) == get_identifier("String"))
- {
- vec<constructor_elt, va_gc> *elms = nullptr;
-
- call->arguments.at(0)->accept(this);
- CONSTRUCTOR_APPEND_ELT(elms, elna_string_ptr_field_node, this->current_expression);
- call->arguments.at(1)->accept(this);
- CONSTRUCTOR_APPEND_ELT(elms, elna_string_length_field_node, this->current_expression);
- this->current_expression = build_constructor(elna_string_type_node, elms);
- }
- else if (TREE_CODE(expression_type) == FUNCTION_TYPE)
+ if (TREE_CODE(expression_type) == FUNCTION_TYPE)
{
this->current_expression = build1(ADDR_EXPR,
build_pointer_type(expression_type), this->current_expression);
@@ -230,28 +219,31 @@ namespace elna::gcc
tree base = this->current_expression;
tree base_type = TREE_TYPE(base);
- expression->offset().accept(this);
- tree offset = fold_convert(elna_word_type_node, this->current_expression);
- offset = build2(MINUS_EXPR, elna_word_type_node, offset, size_one_node);
+ expression->start().accept(this);
+ tree start_index = fold_convert(elna_word_type_node, this->current_expression);
+ tree zero_based_offset = build2(MINUS_EXPR, elna_word_type_node,
+ start_index, size_one_node);
tree slice_ptr;
if (TREE_CODE(base_type) == ARRAY_TYPE)
{
+ // Elna arrays are 1-indexed in TYPE_DOMAIN. Pass the raw
+ // (1-based) start index — GCC handles the 1→0 conversion
+ // via the domain lower bound. No -1 adjustment needed here.
slice_ptr = build4_loc(location, ARRAY_REF, TREE_TYPE(base_type),
- base, offset, size_one_node, NULL_TREE);
+ base, start_index, size_one_node, NULL_TREE);
slice_ptr = build1(ADDR_EXPR, build_pointer_type(TREE_TYPE(base_type)), slice_ptr);
}
else
{
tree ptr = build3_loc(location, COMPONENT_REF, TREE_TYPE(ptr_field),
base, ptr_field, NULL_TREE);
- slice_ptr = do_pointer_arithmetic(boot::binary_operator::sum, ptr, offset, location);
+ slice_ptr = do_pointer_arithmetic(boot::binary_operator::sum,
+ ptr, zero_based_offset, location);
}
- expression->length().accept(this);
+ expression->end().accept(this);
tree end_index = fold_convert(elna_word_type_node, this->current_expression);
- expression->offset().accept(this);
- tree start_index = fold_convert(elna_word_type_node, this->current_expression);
tree slice_length = build2(MINUS_EXPR, elna_word_type_node,
end_index, start_index);
slice_length = build2(PLUS_EXPR, elna_word_type_node, slice_length, size_one_node);
@@ -288,10 +280,7 @@ namespace elna::gcc
DECL_CONTEXT(resdecl) = fndecl;
DECL_RESULT(fndecl) = resdecl;
- push_struct_function(fndecl, false);
- DECL_STRUCT_FUNCTION(fndecl)->language = ggc_cleared_alloc<language_function>();
-
- enter_scope();
+ begin_function(fndecl);
tree parameter_type = TYPE_ARG_TYPES(declaration_type);
for (const char *argument_name : std::array<const char *, 2>{ "count", "parameters" })
@@ -311,18 +300,9 @@ namespace elna::gcc
tree return_stmt = build1(RETURN_EXPR, void_type_node, set_result);
append_statement(return_stmt);
this->current_expression = NULL_TREE;
- tree mapping = leave_scope();
-
- BLOCK_SUPERCONTEXT(BIND_EXPR_BLOCK(mapping)) = fndecl;
- DECL_INITIAL(fndecl) = BIND_EXPR_BLOCK(mapping);
- DECL_SAVED_TREE(fndecl) = mapping;
DECL_EXTERNAL(fndecl) = 0;
- DECL_PRESERVE_P(fndecl) = 1;
-
- pop_cfun();
- gimplify_function_tree(fndecl);
- cgraph_node::finalize_function(fndecl, true);
+ finish_function(fndecl);
}
}
@@ -334,10 +314,7 @@ namespace elna::gcc
{
return;
}
- push_struct_function(fndecl, false);
- DECL_STRUCT_FUNCTION(fndecl)->language = ggc_cleared_alloc<language_function>();
-
- enter_scope();
+ begin_function(fndecl);
this->bag.enter(this->bag.lookup(declaration->identifier.name())->is_procedure()->scope);
tree argument_chain = DECL_ARGUMENTS(fndecl);
@@ -369,18 +346,8 @@ namespace elna::gcc
this->current_expression = NULL_TREE;
}
- tree mapping = leave_scope();
this->bag.leave();
-
- BLOCK_SUPERCONTEXT(BIND_EXPR_BLOCK(mapping)) = fndecl;
- DECL_INITIAL(fndecl) = BIND_EXPR_BLOCK(mapping);
- DECL_SAVED_TREE(fndecl) = mapping;
-
- DECL_PRESERVE_P(fndecl) = 1;
-
- pop_cfun();
- gimplify_function_tree(fndecl);
- cgraph_node::finalize_function(fndecl, true);
+ finish_function(fndecl);
}
void generic_visitor::enter_scope()
@@ -416,14 +383,72 @@ namespace elna::gcc
return bind_expr;
}
+ void generic_visitor::begin_function(tree fndecl)
+ {
+ push_struct_function(fndecl, false);
+ DECL_STRUCT_FUNCTION(fndecl)->language = ggc_cleared_alloc<language_function>();
+ enter_scope();
+ }
+
+ void generic_visitor::finish_function(tree fndecl)
+ {
+ tree mapping = leave_scope();
+
+ BLOCK_SUPERCONTEXT(BIND_EXPR_BLOCK(mapping)) = fndecl;
+ DECL_INITIAL(fndecl) = BIND_EXPR_BLOCK(mapping);
+ DECL_SAVED_TREE(fndecl) = mapping;
+
+ DECL_PRESERVE_P(fndecl) = 1;
+
+ pop_cfun();
+ gimplify_function_tree(fndecl);
+ cgraph_node::finalize_function(fndecl, true);
+ }
+
+ static tree constant_to_tree(const boot::constant_value& constant_value)
+ {
+ if (std::holds_alternative<std::int32_t>(constant_value))
+ {
+ return build_int_cst(elna_int_type_node, std::get<std::int32_t>(constant_value));
+ }
+ else if (std::holds_alternative<std::uint32_t>(constant_value))
+ {
+ return build_int_cstu(elna_word_type_node, std::get<std::uint32_t>(constant_value));
+ }
+
+ else if (std::holds_alternative<double>(constant_value))
+ {
+ auto real_value = std::get<double>(constant_value);
+ REAL_VALUE_TYPE real;
+ HOST_WIDE_INT target_bits[(sizeof(double) + sizeof(HOST_WIDE_INT) - 1)
+ / sizeof(HOST_WIDE_INT)];
+ std::memcpy(target_bits, &real_value, sizeof(real_value));
+ real_from_target(&real, target_bits, REAL_MODE_FORMAT(TYPE_MODE(elna_float_type_node)));
+ return build_real(elna_float_type_node, real);
+ }
+ else if (std::holds_alternative<bool>(constant_value))
+ {
+ return std::get<bool>(constant_value) ? boolean_true_node : boolean_false_node;
+ }
+ else if (std::holds_alternative<unsigned char>(constant_value))
+ {
+ return build_int_cstu(elna_char_type_node, std::get<unsigned char>(constant_value));
+ }
+ else if (std::holds_alternative<std::nullptr_t>(constant_value))
+ {
+ return elna_pointer_nil_node;
+ }
+ return NULL_TREE;
+ }
+
void generic_visitor::visit(boot::literal<std::int32_t> *literal)
{
- this->current_expression = build_int_cst(elna_int_type_node, literal->value);
+ this->current_expression = constant_to_tree(boot::constant_value{ literal->value });
}
void generic_visitor::visit(boot::literal<std::uint32_t> *literal)
{
- this->current_expression = build_int_cstu(elna_word_type_node, literal->value);
+ this->current_expression = constant_to_tree(boot::constant_value{ literal->value });
}
void generic_visitor::visit(boot::literal<double> *literal)
@@ -443,97 +468,43 @@ namespace elna::gcc
void generic_visitor::visit(boot::literal<bool> *boolean)
{
- this->current_expression = boolean->value ? boolean_true_node : boolean_false_node;
+ this->current_expression = constant_to_tree(boot::constant_value{ boolean->value });
}
void generic_visitor::visit(boot::literal<unsigned char> *character)
{
- this->current_expression = build_int_cstu(elna_char_type_node, character->value);
+ this->current_expression = constant_to_tree(boot::constant_value{ character->value });
}
void generic_visitor::visit(boot::literal<std::nullptr_t> *)
{
- this->current_expression = elna_pointer_nil_node;
+ this->current_expression = constant_to_tree(boot::constant_value{ std::nullptr_t{} });
}
void generic_visitor::visit(boot::literal<std::string> *string)
{
tree index_constant = build_int_cstu(elna_word_type_node, string->value.size());
- tree string_type = build_array_type(elna_char_type_node, build_index_type(index_constant));
+ tree char_array_type = build_array_type(elna_char_type_node, build_index_type(index_constant));
tree string_literal = build_string(string->value.size(), string->value.c_str());
- TREE_TYPE(string_literal) = string_type;
+ TREE_TYPE(string_literal) = char_array_type;
TREE_CONSTANT(string_literal) = 1;
TREE_READONLY(string_literal) = 1;
TREE_STATIC(string_literal) = 1;
- string_type = TREE_TYPE(elna_string_ptr_field_node);
+ tree slice_type = get_inner_alias(string->type_decoration, this->symbols);
+ tree ptr_field = TYPE_FIELDS(slice_type);
+
+ tree ptr_type = TREE_TYPE(ptr_field);
string_literal = build4(ARRAY_REF, elna_char_type_node,
string_literal, integer_zero_node, NULL_TREE, NULL_TREE);
- string_literal = build1(ADDR_EXPR, string_type, string_literal);
+ string_literal = build1(ADDR_EXPR, ptr_type, string_literal);
vec<constructor_elt, va_gc> *elms = nullptr;
- CONSTRUCTOR_APPEND_ELT(elms, elna_string_ptr_field_node, string_literal);
- CONSTRUCTOR_APPEND_ELT(elms, elna_string_length_field_node, index_constant);
-
- this->current_expression = build_constructor(elna_string_type_node, elms);
- }
-
- tree generic_visitor::build_arithmetic_operation(boot::binary_expression *expression,
- tree_code operator_code, tree left, tree right)
- {
- return build_binary_operation(is_numeric_type(TREE_TYPE(left)),
- expression, operator_code, left, right, TREE_TYPE(left));
- }
-
- tree generic_visitor::build_comparison_operation(boot::binary_expression *expression,
- tree_code operator_code, tree left, tree right)
- {
- return build_binary_operation(is_numeric_type(TREE_TYPE(left)) || POINTER_TYPE_P(TREE_TYPE(left)),
- expression, operator_code, left, right, elna_bool_type_node);
- }
+ CONSTRUCTOR_APPEND_ELT(elms, ptr_field, string_literal);
+ CONSTRUCTOR_APPEND_ELT(elms, TREE_CHAIN(ptr_field), index_constant);
- tree generic_visitor::build_bit_logic_operation(boot::binary_expression *expression, tree left, tree right)
- {
- location_t expression_location = get_location(&expression->position());
- tree left_type = TREE_TYPE(left);
- tree right_type = TREE_TYPE(right);
- tree_code logical_code, bit_code;
-
- if (expression->operation() == boot::binary_operator::conjunction)
- {
- bit_code = BIT_AND_EXPR;
- logical_code = TRUTH_ANDIF_EXPR;
- }
- else if (expression->operation() == boot::binary_operator::disjunction)
- {
- bit_code = BIT_IOR_EXPR;
- logical_code = TRUTH_ORIF_EXPR;
- }
- else if (expression->operation() == boot::binary_operator::exclusive_disjunction)
- {
- bit_code = BIT_XOR_EXPR;
- logical_code = TRUTH_XOR_EXPR;
- }
- else
- {
- gcc_unreachable();
- }
- if (left_type == elna_bool_type_node)
- {
- return build2_loc(expression_location, logical_code, elna_bool_type_node, left, right);
- }
- else if (is_integral_type(left_type))
- {
- return build2_loc(expression_location, bit_code, left_type, left, right);
- }
- else
- {
- error_at(expression_location, "Invalid operands of type '%s' and '%s' for operator %s",
- print_type(left_type).c_str(), print_type(right_type).c_str(),
- boot::print_binary_operator(expression->operation()));
- return error_mark_node;
- }
+ this->current_expression = build_constructor(slice_type, elms);
}
tree generic_visitor::build_equality_operation(boot::binary_expression *expression, tree left, tree right)
@@ -555,26 +526,7 @@ namespace elna::gcc
{
gcc_unreachable();
}
- if (TREE_TYPE(left) == elna_string_type_node)
- {
- tree lhs_length = build3(COMPONENT_REF, TREE_TYPE(elna_string_length_field_node),
- left, elna_string_length_field_node, NULL_TREE);
- tree lhs_ptr = build3(COMPONENT_REF, TREE_TYPE(elna_string_ptr_field_node),
- left, elna_string_ptr_field_node, NULL_TREE);
-
- tree rhs_length = build3(COMPONENT_REF, TREE_TYPE(elna_string_length_field_node),
- right, elna_string_length_field_node, NULL_TREE);
- tree rhs_ptr = build3(COMPONENT_REF, TREE_TYPE(elna_string_ptr_field_node),
- right, elna_string_ptr_field_node, NULL_TREE);
-
- tree length_equality = build2(equality_code, elna_bool_type_node, lhs_length, rhs_length);
- tree memcmp_call = call_built_in(UNKNOWN_LOCATION, "__builtin_memcmp", integer_type_node,
- lhs_ptr, rhs_ptr, lhs_length);
- tree equals_zero = build2(equality_code, elna_bool_type_node, memcmp_call, integer_zero_node);
-
- return build2(combination_code, elna_bool_type_node, length_equality, equals_zero);
- }
- else if (expression->lhs().type_decoration.get<boot::slice_type>() != nullptr)
+ if (expression->lhs().type_decoration.get<boot::slice_type>() != nullptr)
{
tree lhs_ptr_field = TYPE_FIELDS(TREE_TYPE(left));
tree lhs_length_field = TREE_CHAIN(lhs_ptr_field);
@@ -600,7 +552,8 @@ namespace elna::gcc
return build2(combination_code, elna_bool_type_node, length_equality, equals_zero);
}
- else if (TREE_CODE(TREE_TYPE(left)) == RECORD_TYPE)
+ else if (expression->lhs().type_decoration.get<boot::record_type>() != nullptr
+ || expression->lhs().type_decoration.get<boot::array_type>() != nullptr)
{
tree size = fold_convert(elna_word_type_node,
size_in_bytes(TREE_TYPE(left)));
@@ -636,84 +589,90 @@ namespace elna::gcc
{
this->current_expression = do_pointer_arithmetic(expression->operation(),
left, right, expression_location);
- if (this->current_expression == error_mark_node)
- {
- error_at(expression_location,
- "invalid operation %s on a pointer and an integral type",
- boot::print_binary_operator(expression->operation()));
- }
- else if (TREE_TYPE(this->current_expression) == ssizetype)
+ if (TREE_TYPE(this->current_expression) == ssizetype)
{
this->current_expression = fold_convert(elna_int_type_node, this->current_expression);
}
return;
}
- if (left_type != right_type
- && !are_compatible_pointers(left_type, right)
- && !are_compatible_pointers(right_type, left)
- && !(is_integral_type(left_type) && right_type == elna_word_type_node))
- {
- error_at(expression_location,
- "invalid operands of type '%s' and '%s' for operator %s",
- print_type(left_type).c_str(), print_type(right_type).c_str(),
- boot::print_binary_operator(expression->operation()));
- this->current_expression = error_mark_node;
- return;
- }
switch (expression->operation())
{
using enum boot::binary_operator;
case sum:
- this->current_expression = build_arithmetic_operation(expression, PLUS_EXPR, left, right);
+ this->current_expression = fold_build2_loc(expression_location,
+ PLUS_EXPR, left_type, left, right);
break;
case subtraction:
- this->current_expression = build_arithmetic_operation(expression, MINUS_EXPR, left, right);
+ this->current_expression = fold_build2_loc(expression_location,
+ MINUS_EXPR, left_type, left, right);
break;
case division:
- this->current_expression = build_arithmetic_operation(expression, TRUNC_DIV_EXPR, left, right);
+ this->current_expression = fold_build2_loc(expression_location,
+ TRUNC_DIV_EXPR, left_type, left, right);
break;
case remainder:
- this->current_expression = build_arithmetic_operation(expression, TRUNC_MOD_EXPR, left, right);
+ this->current_expression = fold_build2_loc(expression_location,
+ TRUNC_MOD_EXPR, left_type, left, right);
break;
case multiplication:
- this->current_expression = build_arithmetic_operation(expression, MULT_EXPR, left, right);
+ this->current_expression = fold_build2_loc(expression_location,
+ MULT_EXPR, left_type, left, right);
break;
case less:
- this->current_expression = build_comparison_operation(expression, LT_EXPR, left, right);
+ this->current_expression = fold_build2_loc(expression_location,
+ LT_EXPR, elna_bool_type_node, left, right);
break;
case greater:
- this->current_expression = build_comparison_operation(expression, GT_EXPR, left, right);
+ this->current_expression = fold_build2_loc(expression_location,
+ GT_EXPR, elna_bool_type_node, left, right);
break;
case less_equal:
- this->current_expression = build_comparison_operation(expression, LE_EXPR, left, right);
+ this->current_expression = fold_build2_loc(expression_location,
+ LE_EXPR, elna_bool_type_node, left, right);
break;
case greater_equal:
- this->current_expression = build_comparison_operation(expression, GE_EXPR, left, right);
+ this->current_expression = fold_build2_loc(expression_location,
+ GE_EXPR, elna_bool_type_node, left, right);
break;
case conjunction:
- this->current_expression = build_bit_logic_operation(expression, left, right);
- break;
case disjunction:
- this->current_expression = build_bit_logic_operation(expression, left, right);
- break;
case exclusive_disjunction:
- this->current_expression = build_bit_logic_operation(expression, left, right);
+ gcc_unreachable();
+ case logical_conjunction:
+ this->current_expression = build2_loc(expression_location,
+ TRUTH_ANDIF_EXPR, elna_bool_type_node, left, right);
break;
- case equals:
- this->current_expression = build_equality_operation(expression, left, right);
+ case logical_disjunction:
+ this->current_expression = build2_loc(expression_location,
+ TRUTH_ORIF_EXPR, elna_bool_type_node, left, right);
break;
+ case logical_exclusive_disjunction:
+ this->current_expression = build2_loc(expression_location,
+ TRUTH_XOR_EXPR, elna_bool_type_node, left, right);
+ break;
+ case bitwise_conjunction:
+ this->current_expression = build2_loc(expression_location,
+ BIT_AND_EXPR, left_type, left, right);
+ break;
+ case bitwise_disjunction:
+ this->current_expression = build2_loc(expression_location,
+ BIT_IOR_EXPR, left_type, left, right);
+ break;
+ case bitwise_exclusive_disjunction:
+ this->current_expression = build2_loc(expression_location,
+ BIT_XOR_EXPR, left_type, left, right);
+ break;
+ case equals:
case not_equals:
this->current_expression = build_equality_operation(expression, left, right);
break;
case shift_left:
- this->current_expression = build_binary_operation(
- is_numeric_type(left_type) && right_type == elna_word_type_node,
- expression, LSHIFT_EXPR, left, right, left_type);
+ this->current_expression = fold_build2_loc(expression_location,
+ LSHIFT_EXPR, left_type, left, right);
break;
case shift_right:
- this->current_expression = build_binary_operation(
- is_numeric_type(left_type) && right_type == elna_word_type_node,
- expression, RSHIFT_EXPR, left, right, left_type);
+ this->current_expression = fold_build2_loc(expression_location,
+ RSHIFT_EXPR, left_type, left, right);
break;
}
}
@@ -734,22 +693,14 @@ namespace elna::gcc
build_pointer_type(TREE_TYPE(this->current_expression)));
TREE_NO_TRAMPOLINE(this->current_expression) = 1;
break;
- case negation:
- {
- tree operand_type = TREE_TYPE(this->current_expression);
-
- if (operand_type == elna_bool_type_node)
- {
- this->current_expression = build1_loc(location, TRUTH_NOT_EXPR,
- boolean_type_node, this->current_expression);
- }
- else
- {
- this->current_expression = build1_loc(location, BIT_NOT_EXPR,
- operand_type, this->current_expression);
- }
+ case bitwise_negation:
+ this->current_expression = build1_loc(location, BIT_NOT_EXPR,
+ TREE_TYPE(this->current_expression), this->current_expression);
+ break;
+ case logical_negation:
+ this->current_expression = build1_loc(location, TRUTH_NOT_EXPR,
+ boolean_type_node, this->current_expression);
break;
- }
case minus:
{
tree operand_type = TREE_TYPE(this->current_expression);
@@ -761,45 +712,11 @@ namespace elna::gcc
case plus:
// Identity: operand already in current_expression.
break;
+ default:
+ gcc_unreachable();
}
}
- static tree constant_to_tree(const boot::constant_value& constant_value)
- {
- if (std::holds_alternative<std::int32_t>(constant_value))
- {
- return build_int_cst(elna_int_type_node, std::get<std::int32_t>(constant_value));
- }
- else if (std::holds_alternative<std::uint32_t>(constant_value))
- {
- return build_int_cst(elna_word_type_node, std::get<std::uint32_t>(constant_value));
- }
-
- else if (std::holds_alternative<double>(constant_value))
- {
- auto real_value = std::get<double>(constant_value);
- REAL_VALUE_TYPE real;
- HOST_WIDE_INT target_bits[(sizeof(double) + sizeof(HOST_WIDE_INT) - 1)
- / sizeof(HOST_WIDE_INT)];
- std::memcpy(target_bits, &real_value, sizeof(real_value));
- real_from_target(&real, target_bits, REAL_MODE_FORMAT(TYPE_MODE(elna_float_type_node)));
- return build_real(elna_float_type_node, real);
- }
- else if (std::holds_alternative<bool>(constant_value))
- {
- return std::get<bool>(constant_value) ? boolean_true_node : boolean_false_node;
- }
- else if (std::holds_alternative<unsigned char>(constant_value))
- {
- return build_int_cst(elna_char_type_node, std::get<unsigned char>(constant_value));
- }
- else if (std::holds_alternative<std::nullptr_t>(constant_value))
- {
- return elna_pointer_nil_node;
- }
- return NULL_TREE;
- }
-
void generic_visitor::visit(boot::variable_declaration *declaration)
{
for (const auto& variable_identifier : declaration->identifiers)
@@ -865,7 +782,7 @@ namespace elna::gcc
DECL_CONTEXT(declaration_tree) = current_function_decl;
f_names = chainon(f_names, declaration_tree);
- auto declaration_statement = build1_loc(declaration_location, DECL_EXPR,
+ auto *declaration_statement = build1_loc(declaration_location, DECL_EXPR,
void_type_node, declaration_tree);
append_statement(declaration_statement);
}
@@ -909,12 +826,9 @@ namespace elna::gcc
this->current_expression = build4_loc(location,
ARRAY_REF, element_type, designator, offset, size_one_node, NULL_TREE);
}
- else if (TREE_TYPE(designator) == elna_string_type_node
- || expression->base().type_decoration.get<boot::slice_type>() != nullptr)
+ else if (expression->base().type_decoration.get<boot::slice_type>() != nullptr)
{
- tree ptr_field = (TREE_TYPE(designator) == elna_string_type_node)
- ? elna_string_ptr_field_node
- : TYPE_FIELDS(TREE_TYPE(designator));
+ tree ptr_field = TYPE_FIELDS(TREE_TYPE(designator));
offset = build2(MINUS_EXPR, elna_word_type_node, offset, size_one_node);
tree slice_ptr = build3_loc(location, COMPONENT_REF, TREE_TYPE(ptr_field),
designator, ptr_field, NULL_TREE);
diff --git a/gcc/gcc/elna-tree.cc b/gcc/gcc/elna-tree.cc
index 0227433..ab7363f 100644
--- a/gcc/gcc/elna-tree.cc
+++ b/gcc/gcc/elna-tree.cc
@@ -53,15 +53,6 @@ namespace elna::gcc
return INTEGRAL_TYPE_P(type) || POINTER_TYPE_P(type) || TREE_CODE(type) == REAL_TYPE;
}
- bool are_compatible_pointers(tree lhs_type, tree rhs)
- {
- gcc_assert(TYPE_P(lhs_type));
- tree rhs_type = TREE_TYPE(rhs);
-
- return (POINTER_TYPE_P(lhs_type) && rhs == elna_pointer_nil_node)
- || (POINTER_TYPE_P(lhs_type) && lhs_type == rhs_type);
- }
-
tree prepare_rvalue(tree rvalue)
{
if (DECL_P(rvalue) && TREE_CODE(TREE_TYPE(rvalue)) == FUNCTION_TYPE)
@@ -74,12 +65,6 @@ namespace elna::gcc
}
}
- bool is_assignable_from(tree assignee, tree assignment)
- {
- return get_qualified_type(TREE_TYPE(assignment), TYPE_UNQUALIFIED) == assignee
- || are_compatible_pointers(assignee, assignment);
- }
-
void append_statement(tree statement_tree)
{
if (!vec_safe_is_empty(f_binding_level->defers))
@@ -187,27 +172,6 @@ namespace elna::gcc
gcc_unreachable();
}
- tree build_binary_operation(bool condition, boot::binary_expression *expression,
- tree_code operator_code, tree left, tree right, tree target_type)
- {
- location_t expression_location = get_location(&expression->position());
- tree left_type = get_qualified_type(TREE_TYPE(left), TYPE_UNQUALIFIED);
- tree right_type = get_qualified_type(TREE_TYPE(right), TYPE_UNQUALIFIED);
-
- if (condition)
- {
- return fold_build2_loc(expression_location, operator_code, target_type, left, right);
- }
- else
- {
- error_at(expression_location,
- "invalid operands of type '%s' and '%s' for operator %s",
- print_type(left_type).c_str(), print_type(right_type).c_str(),
- boot::print_binary_operator(expression->operation()));
- return error_mark_node;
- }
- }
-
tree find_field_by_name(location_t expression_location, tree type, const std::string& field_name)
{
if (type == error_mark_node)