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 /boot/parser.yy | |
| parent | b575036fe804f14b78da74897a74b010cc94f730 (diff) | |
| download | elna-dc9d03915c4b169fec749081b45d56f722105813.tar.gz | |
Allow block-local variables
Diffstat (limited to 'boot/parser.yy')
| -rw-r--r-- | boot/parser.yy | 67 |
1 files changed, 38 insertions, 29 deletions
diff --git a/boot/parser.yy b/boot/parser.yy index eaf1a7c..01dfa80 100644 --- a/boot/parser.yy +++ b/boot/parser.yy @@ -135,7 +135,7 @@ along with GCC; see the file COPYING3. If not see %type <elna::boot::switch_case> switch_case; %type <std::vector<elna::boot::switch_case>> switch_cases; %type <elna::boot::variable_declaration *> variable_declaration; -%type <std::vector<elna::boot::variable_declaration *>> variable_declarations; +%type <std::vector<elna::boot::variable_declaration *>> variable_declarations variable_part; %type <elna::boot::type_expression *> type_expression; %type <std::vector<elna::boot::type_expression *>> type_expressions; %type <elna::boot::expression *> expression operand simple_expression procedure_return unary_expression; @@ -145,6 +145,7 @@ along with GCC; see the file COPYING3. If not see %type <std::unique_ptr<elna::boot::procedure_call>> call_expression; %type <elna::boot::statement *> statement; %type <std::vector<elna::boot::statement *>> statements statement_part; +%type <elna::boot::block> block; %type <elna::boot::procedure_declaration *> procedure_declaration; %type <std::unique_ptr<elna::boot::procedure_type_expression>> procedure_heading; %type <elna::boot::procedure_type_expression::return_t> return_declaration; @@ -157,7 +158,7 @@ along with GCC; see the file COPYING3. If not see %type <std::unique_ptr<elna::boot::field_initializer>> field_initializer; %type <std::vector<elna::boot::field_initializer>> field_initializers; %type <std::vector<elna::boot::conditional_statements *>> elsif_then_statements elsif_do_statements; -%type <std::vector<elna::boot::statement *> *> else_statements; +%type <elna::boot::block *> else_statements; %type <std::unique_ptr<elna::boot::identifier>> identifier with_counter; %type <std::unique_ptr<elna::boot::identifier_definition>> identifier_definition attributed_identifier; %type <std::vector<elna::boot::identifier_definition>> identifier_definitions; @@ -188,9 +189,9 @@ program: } module_declaration: "type" type_declarations { $$ = $2; } - | "var" variable_declarations + | variable_part { - std::vector<boot::variable_declaration *> variables = $2; + std::vector<boot::variable_declaration *> variables = $1; $$.insert($$.end(), variables.begin(), variables.end()); } @@ -215,12 +216,19 @@ module_declarations: $$.insert($$.end(), appendix.begin(), appendix.end()); } procedure_body: - "var" variable_declarations statement_part procedure_return - { $$ = std::make_unique<boot::procedure_body>($2, $3, $4); } - | statement_part procedure_return - { - $$ = std::make_unique<boot::procedure_body>(std::vector<boot::variable_declaration *>(), $1, $2); - } + block procedure_return + { $$ = std::make_unique<boot::procedure_body>(std::move($1), $2); } + +variable_part: + "var" variable_declarations { $$ = $2; } + +block: + variable_part statement_part + { $$ = boot::block(std::move($1), std::move($2)); } + | "begin" statements + { $$ = boot::block(std::vector<boot::variable_declaration *>(), std::move($2)); } + | statements + { $$ = boot::block(std::vector<boot::variable_declaration *>(), std::move($1)); } statement_part: %empty {} @@ -284,20 +292,20 @@ with_counter: "with" identifier { $$ = $2; } | %empty { $$ = nullptr; } elsif_do_statements: - "elsif" expression "do" statements elsif_do_statements + "elsif" expression "do" block elsif_do_statements { - boot::conditional_statements *branch = new boot::conditional_statements($2, $4); + boot::conditional_statements *branch = new boot::conditional_statements($2, std::move($4)); $$ = $5; $$.emplace($$.begin(), branch); } | %empty {} else_statements: - "else" statements { $$ = new std::vector<boot::statement *>($2); } + "else" block { $$ = new boot::block(std::move($2)); } | %empty { $$ = nullptr; } elsif_then_statements: - "elsif" expression "then" statements elsif_then_statements + "elsif" expression "then" block elsif_then_statements { - boot::conditional_statements *branch = new boot::conditional_statements($2, $4); + boot::conditional_statements *branch = new boot::conditional_statements($2, std::move($4)); $$ = $5; $$.emplace($$.begin(), branch); } @@ -563,36 +571,37 @@ name_reference: statement: designator_expression ":=" expression { $$ = new boot::assign_statement(boot::make_position(@$), $1, $3); } - | "while" expression "do" statements elsif_do_statements "end" + | "while" expression "do" block elsif_do_statements "end" { - boot::conditional_statements *body = new boot::conditional_statements($2, $4); + boot::conditional_statements *body = new boot::conditional_statements($2, std::move($4)); $$ = new boot::while_statement(boot::make_position(@$), body, $5); } - | "repeat" statements "until" expression + | "repeat" block "until" expression { - $$ = new boot::repeat_statement(boot::make_position(@$), $2, $4); + $$ = new boot::repeat_statement(boot::make_position(@$), std::move($2), $4); } - | "for" identifier "of" expression with_counter "do" statements "end" + | "for" identifier "of" expression with_counter "do" block "end" { - $$ = new boot::for_statement(boot::make_position(@$), std::move(*$2), $4, $7, $5.release()); + $$ = new boot::for_statement(boot::make_position(@$), std::move(*$2), $4, + std::move($7), $5.release()); } - | "if" expression "then" statements elsif_then_statements else_statements "end" + | "if" expression "then" block elsif_then_statements else_statements "end" { - boot::conditional_statements *then = new boot::conditional_statements($2, $4); + boot::conditional_statements *then = new boot::conditional_statements($2, std::move($4)); $$ = new boot::if_statement(boot::make_position(@$), then, $5, $6); } | call_expression { $$ = $1.release(); } - | "defer" statements "end" - { $$ = new boot::defer_statement(boot::make_position(@$), $2); } - | "block" identifier statements "end" - { $$ = new boot::block_statement(boot::make_position(@$), std::move(*$2), $3); } + | "defer" block "end" + { $$ = new boot::defer_statement(boot::make_position(@$), std::move($2)); } + | "block" identifier block "end" + { $$ = new boot::block_statement(boot::make_position(@$), std::move(*$2), std::move($3)); } | "break" identifier { $$ = new boot::break_statement(boot::make_position(@$), std::move(*$2)); } | "case" expression "of" switch_cases else_statements "end" { $$ = new boot::case_statement(boot::make_position(@$), $2, $4, $5); } | %empty { $$ = new boot::empty_statement(boot::make_position(@$)); } -switch_case: case_labels ":" statements - { $$ = { .labels = $1, .statements = $3 }; } +switch_case: case_labels ":" block + { $$ = { .labels = $1, .body = std::move($3) }; } switch_cases: switch_case "|" switch_cases { |
