Unify the build_type function

This commit is contained in:
2025-03-06 22:59:41 +01:00
parent dbeaca7cbf
commit dc5760394b
8 changed files with 261 additions and 175 deletions

View File

@ -38,112 +38,41 @@ namespace elna
{
namespace gcc
{
declaration_visitor::declaration_visitor(std::shared_ptr<symbol_table> symbol_table)
: symbols(symbol_table)
static tree get_inner_alias(std::shared_ptr<symbol_table> symbol_table, const boot::type& type)
{
this->symbols->enter("Int", elna_int_type_node);
this->symbols->enter("Word", elna_word_type_node);
this->symbols->enter("Char", elna_char_type_node);
this->symbols->enter("Bool", elna_bool_type_node);
this->symbols->enter("Byte", elna_byte_type_node);
this->symbols->enter("Float", elna_float_type_node);
this->symbols->enter("String", elna_string_type_node);
}
tree declaration_visitor::get_inner_alias(const boot::alias_type& t)
{
if (t.reference == nullptr)
if (auto reference = type.get<boot::primitive_type>())
{
return NULL_TREE;
return symbol_table->lookup(reference->identifier);
}
else if (auto reference = t.reference->is_primitive())
{
return this->symbols->lookup(reference->identifier);
}
else if (auto reference = t.reference->is_alias())
{
return get_inner_alias(*reference);
}
else if (auto reference = t.reference->is_record())
else if (auto reference = type.get<boot::record_type>())
{
return make_node(RECORD_TYPE);
}
else if (auto reference = t.reference->is_union())
else if (auto reference = type.get<boot::union_type>())
{
return make_node(UNION_TYPE);
}
return NULL_TREE;
else if (auto reference = type.get<boot::pointer_type>())
{
return build_pointer_type_for_mode(get_inner_alias(symbol_table, reference->base), VOIDmode, true);
}
else if (auto reference = type.get<boot::alias_type>())
{
return get_inner_alias(symbol_table, reference->reference);
}
return error_mark_node;
}
boot::type *declaration_visitor::build_type(boot::type_expression *type_expression)
void do_semantic_analysis(std::shared_ptr<symbol_table> symbols, std::unique_ptr<boot::program>& ast)
{
if (auto alias_node = type_expression->is_primitive())
{
return this->unresolved.at(alias_node->name);
}
else if (auto alias_node = type_expression->is_record())
{
return build_record(alias_node.get());
}
else if (auto alias_node = type_expression->is_union())
{
return build_union(alias_node.get());
}
return nullptr;
}
boot::declaration_visitor declaration_visitor;
boot::record_type *declaration_visitor::build_record(boot::record_type_expression *type_expression)
{
return new boot::record_type();
}
boot::union_type *declaration_visitor::build_union(boot::union_type_expression *type_expression)
{
return new boot::union_type();
}
void declaration_visitor::visit(boot::program *program)
{
for (boot::type_definition *const type : program->types)
declaration_visitor.visit(ast.get());
for (auto unresolved : declaration_visitor.unresolved)
{
type->accept(this);
auto inner_alias = elna::gcc::get_inner_alias(symbols, boot::type(unresolved.second));
symbols->enter(unresolved.first, inner_alias);
}
for (boot::type_definition *const type : program->types)
{
auto unresolved_declaration = this->unresolved.at(type->identifier);
if (auto alias_node = type->body().is_primitive())
{
auto unresolved_alias = this->unresolved.find(alias_node->name);
if (unresolved_alias != this->unresolved.end())
{
unresolved_declaration->reference = unresolved_alias->second;
}
else
{
unresolved_declaration->reference = new boot::primitive_type(alias_node->name);
}
}
else if (auto alias_node = type->body().is_record())
{
unresolved_declaration->reference = build_record(alias_node.get());
}
else if (auto alias_node = type->body().is_union())
{
unresolved_declaration->reference = build_union(alias_node.get());
}
}
for (auto unresolved : this->unresolved)
{
auto inner_alias = get_inner_alias(*unresolved.second);
this->symbols->enter(unresolved.first, inner_alias);
}
}
void declaration_visitor::visit(boot::type_definition *definition)
{
this->unresolved.insert({ definition->identifier, new boot::alias_type() });
}
generic_visitor::generic_visitor(std::shared_ptr<symbol_table> symbol_table)