Revert "Allow only one return"

This reverts commit 18602d00a1.
This commit is contained in:
2025-03-02 10:45:54 +01:00
parent 75561fd18a
commit 09f204bd16
10 changed files with 231 additions and 79 deletions

View File

@ -63,6 +63,7 @@ namespace boot
class assign_statement;
class if_statement;
class while_statement;
class return_statement;
class traits_expression;
class block;
class program;
@ -80,6 +81,7 @@ namespace boot
class dereference_expression;
template<typename T>
class number_literal;
class defer_statement;
/**
* Interface for AST visitors.
@ -96,6 +98,8 @@ namespace boot
virtual void visit(assign_statement *) = 0;
virtual void visit(if_statement *) = 0;
virtual void visit(while_statement *) = 0;
virtual void visit(return_statement *) = 0;
virtual void visit(defer_statement *) = 0;
virtual void visit(block *) = 0;
virtual void visit(program *) = 0;
virtual void visit(binary_expression *) = 0;
@ -134,6 +138,8 @@ namespace boot
virtual void visit(assign_statement *statement) override;
virtual void visit(if_statement *) override;
virtual void visit(while_statement *) override;
virtual void visit(return_statement *) override;
virtual void visit(defer_statement *defer) override;
virtual void visit(block *block) override;
virtual void visit(program *program) override;
virtual void visit(binary_expression *expression) override;
@ -360,11 +366,9 @@ namespace boot
public:
block *const body;
expression *const returning;
procedure_definition(const struct position position, const std::string& identifier,
const bool exported, std::shared_ptr<procedure_type> heading,
block *const body = nullptr, expression *const returning = nullptr);
const bool exported, std::shared_ptr<procedure_type> heading, block *body = nullptr);
virtual void accept(parser_visitor *visitor) override;
procedure_type& heading();
@ -435,6 +439,19 @@ namespace boot
virtual ~conditional_statements();
};
class return_statement : public statement
{
expression *m_return_expression{ nullptr };
public:
return_statement(const struct position position, expression *return_expression);
virtual void accept(parser_visitor *visitor) override;
expression *return_expression();
virtual ~return_statement() override;
};
class designator_expression : public expression
{
public:
@ -627,6 +644,17 @@ namespace boot
}
};
class defer_statement : public statement
{
public:
std::vector<statement *> statements;
defer_statement(const struct position position);
virtual void accept(parser_visitor *visitor) override;
virtual ~defer_statement() override;
};
class binary_expression : public expression
{
expression *m_lhs;

View File

@ -60,42 +60,43 @@ namespace gcc
void build_record_call(location_t call_location,
tree symbol, const std::vector<boot::expression *>& arguments);
void visit_statements(const std::vector<boot::statement *>& statements);
void visit_return(boot::expression *const return_expression);
public:
generic_visitor(std::shared_ptr<symbol_table> symbol_table);
virtual void visit(boot::program *program) override;
virtual void visit(boot::procedure_definition *definition) override;
virtual void visit(boot::procedure_call *call) override;
virtual void visit(boot::cast_expression *expression) override;
virtual void visit(boot::traits_expression *trait) override;
virtual void visit(boot::number_literal<std::int32_t> *literal) override;
virtual void visit(boot::number_literal<std::uint32_t> *literal) override;
virtual void visit(boot::number_literal<double> *literal) override;
virtual void visit(boot::number_literal<bool> *boolean) override;
virtual void visit(boot::number_literal<unsigned char> *character) override;
virtual void visit(boot::number_literal<std::nullptr_t> *) override;
virtual void visit(boot::number_literal<std::string> *string) override;
virtual void visit(boot::binary_expression *expression) override;
virtual void visit(boot::unary_expression *expression) override;
virtual void visit(boot::constant_definition *definition) override;
virtual void visit(boot::type_definition *definition) override;
virtual void visit(boot::variable_declaration *declaration) override;
virtual void visit(boot::variable_expression *expression) override;
virtual void visit(boot::array_access_expression *expression) override;
virtual void visit(boot::field_access_expression *expression) override;
virtual void visit(boot::dereference_expression *expression) override;
virtual void visit(boot::block *block) override;
virtual void visit(boot::assign_statement *statement) override;
virtual void visit(boot::if_statement *statement) override;
virtual void visit(boot::while_statement *statement) override;
virtual void visit(boot::basic_type *type) override;
virtual void visit(boot::array_type *type) override;
virtual void visit(boot::pointer_type *type) override;
virtual void visit(boot::record_type *type) override;
virtual void visit(boot::union_type *type) override;
virtual void visit(boot::procedure_type *type) override;
void visit(boot::program *program) override;
void visit(boot::procedure_definition *definition) override;
void visit(boot::procedure_call *call) override;
void visit(boot::cast_expression *expression) override;
void visit(boot::traits_expression *trait) override;
void visit(boot::number_literal<std::int32_t> *literal) override;
void visit(boot::number_literal<std::uint32_t> *literal) override;
void visit(boot::number_literal<double> *literal) override;
void visit(boot::number_literal<bool> *boolean) override;
void visit(boot::number_literal<unsigned char> *character) override;
void visit(boot::number_literal<std::nullptr_t> *) override;
void visit(boot::number_literal<std::string> *string) override;
void visit(boot::binary_expression *expression) override;
void visit(boot::unary_expression *expression) override;
void visit(boot::constant_definition *definition) override;
void visit(boot::type_definition *definition) override;
void visit(boot::variable_declaration *declaration) override;
void visit(boot::variable_expression *expression) override;
void visit(boot::array_access_expression *expression) override;
void visit(boot::field_access_expression *expression) override;
void visit(boot::dereference_expression *expression) override;
void visit(boot::block *block) override;
void visit(boot::assign_statement *statement) override;
void visit(boot::if_statement *statement) override;
void visit(boot::while_statement *statement) override;
void visit(boot::basic_type *type) override;
void visit(boot::array_type *type) override;
void visit(boot::pointer_type *type) override;
void visit(boot::record_type *type) override;
void visit(boot::union_type *type) override;
void visit(boot::procedure_type *type) override;
void visit(boot::return_statement *statement) override;
void visit(boot::defer_statement *statement) override;
};
}
}

View File

@ -72,6 +72,8 @@ namespace gcc
bool is_assignable_from(tree assignee, tree assignment);
void append_statement(tree statement_tree);
void defer(tree statement_tree);
tree chain_defer();
tree do_pointer_arithmetic(boot::binary_operator binary_operator, tree left, tree right);
tree build_binary_operation(bool condition, boot::binary_expression *expression,

View File

@ -58,6 +58,12 @@ struct GTY (()) lang_decl
{
};
struct GTY (()) defer_scope
{
tree defer_block;
tree try_statements;
};
struct GTY ((chain_next ("%h.level_chain"))) binding_level
{
// A block chain is needed to call defer statements beloning to each block.
@ -68,6 +74,9 @@ struct GTY ((chain_next ("%h.level_chain"))) binding_level
// Statements before the first defer has been seen.
tree statement_list;
// Defer statement coupled with statements following it.
vec<defer_scope, va_gc> *defers;
};
struct GTY (()) language_function