diff options
| author | Eugen Wissner <belka@caraus.de> | 2026-09-18 12:19:13 +0200 |
|---|---|---|
| committer | Eugen Wissner <belka@caraus.de> | 2026-09-18 12:19:13 +0200 |
| commit | dc9d03915c4b169fec749081b45d56f722105813 (patch) | |
| tree | 0a0719bc95f942b675fb52865d9c5bac9e105767 /gcc | |
| parent | b575036fe804f14b78da74897a74b010cc94f730 (diff) | |
| download | elna-dc9d03915c4b169fec749081b45d56f722105813.tar.gz | |
Allow block-local variables
Diffstat (limited to 'gcc')
| -rw-r--r-- | gcc/gcc/elna-generic.cc | 39 |
1 files changed, 25 insertions, 14 deletions
diff --git a/gcc/gcc/elna-generic.cc b/gcc/gcc/elna-generic.cc index 60ed82b..f4cb3c3 100644 --- a/gcc/gcc/elna-generic.cc +++ b/gcc/gcc/elna-generic.cc @@ -980,7 +980,7 @@ namespace elna::gcc if (statement->alternative != nullptr) { enter_scope(); - visit_statements(*statement->alternative); + visit_block(*statement->alternative); result = leave_scope(); } @@ -1001,7 +1001,7 @@ namespace elna::gcc tree condition = this->current_expression; enter_scope(); - visit_statements(branch.statements); + visit_block(branch.body); if (goto_append != NULL_TREE) { append_statement(goto_append); @@ -1032,7 +1032,7 @@ namespace elna::gcc append_statement(build1(LABEL_EXPR, void_type_node, loop_label)); enter_scope(); - visit_statements(statement->body); + visit_block(statement->body); tree repeat_binding = leave_scope(); append_statement(repeat_binding); @@ -1077,7 +1077,7 @@ namespace elna::gcc enter_scope(); // Declare control variable with the unqualified type. The constant_type wrapper // is for semantic checking only, because GENERIC needs to modify the control variable. - auto control_variable_info = statement->symbols->lookup(statement->control_variable.name()); + auto control_variable_info = statement->body.symbols->lookup(statement->control_variable.name()); const boot::variable_info unqualified_info( boot::resolve_underlying_type(control_variable_info->is_variable()->symbol), control_variable_info->is_variable()->is_extern); @@ -1087,7 +1087,7 @@ namespace elna::gcc tree counter_declaration{ NULL_TREE }; if (statement->counter != nullptr) { - auto counter_info = statement->symbols->lookup(statement->counter->name()); + auto counter_info = statement->body.symbols->lookup(statement->counter->name()); counter_declaration = declare_local_variable(*statement->counter, *counter_info->is_variable(), elna_word_one_node); } @@ -1097,7 +1097,7 @@ namespace elna::gcc // The body gets its own scope, so that defer statements in it are run on // every iteration and not once for the whole loop. enter_scope(); - visit_statements(statement->body); + visit_block(statement->body); tree body_binding = leave_scope(); append_statement(body_binding); @@ -1158,10 +1158,21 @@ namespace elna::gcc } } + void generic_visitor::visit_block(boot::block& body) + { + this->bag.enter(body.symbols); + for (boot::variable_declaration *const variable : body.variables) + { + variable->accept(this); + } + visit_statements(body.statements); + this->bag.leave(); + } + void generic_visitor::visit(boot::defer_statement *statement) { enter_scope(); - visit_statements(statement->statements); + visit_block(statement->body); defer(leave_scope()); } @@ -1172,7 +1183,7 @@ namespace elna::gcc enter_scope(); this->symbols->enter(statement->name.name(), end_label); - visit_statements(statement->statements); + visit_block(statement->body); append_statement(leave_scope()); // The label sits outside the binding, so that a break leaving the block @@ -1216,7 +1227,7 @@ namespace elna::gcc tree end_label_declaration = create_artificial_label(get_location(&statement->position())); tree switch_statements = alloc_stmt_list(); - for (const boot::switch_case& case_block : statement->cases) + for (boot::switch_case& case_block : statement->cases) { for (boot::expression *const case_label : case_block.labels) { @@ -1230,7 +1241,7 @@ namespace elna::gcc append_to_statement_list(case_expression, &switch_statements); } enter_scope(); - visit_statements(case_block.statements); + visit_block(case_block.body); append_to_statement_list(leave_scope(), &switch_statements); tree goto_end = build1(GOTO_EXPR, void_type_node, end_label_declaration); @@ -1245,7 +1256,7 @@ namespace elna::gcc append_to_statement_list(case_expression, &switch_statements); enter_scope(); - visit_statements(*statement->alternative); + visit_block(*statement->alternative); append_to_statement_list(leave_scope(), &switch_statements); TREE_USED(end_label_declaration) = 1; @@ -1267,10 +1278,10 @@ namespace elna::gcc if (statement->alternative != nullptr) { enter_scope(); - visit_statements(*statement->alternative); + visit_block(*statement->alternative); result = leave_scope(); } - for (const boot::switch_case& case_block : statement->cases | std::views::reverse) + for (boot::switch_case& case_block : statement->cases | std::views::reverse) { tree case_condition = boolean_false_node; for (boot::expression *const case_label : case_block.labels) @@ -1285,7 +1296,7 @@ namespace elna::gcc } enter_scope(); - visit_statements(case_block.statements); + visit_block(case_block.body); tree then_body = leave_scope(); result = build3(COND_EXPR, void_type_node, case_condition, then_body, result); |
