Implement elsif

This commit is contained in:
2025-01-27 01:16:27 +01:00
parent 1f7c1b4cb8
commit 18d8ded239
6 changed files with 115 additions and 155 deletions

View File

@ -898,7 +898,10 @@ namespace source
if_statement::~if_statement()
{
delete m_body;
for (const auto branch : branches)
{
delete branch;
}
if (m_alternative != nullptr)
{
delete m_alternative;

View File

@ -96,6 +96,7 @@
%type <elna::source::block *> block;
%type <std::pair<std::string, elna::source::type_expression *>> field_declaration;
%type <std::vector<std::pair<std::string, elna::source::type_expression *>>> field_list;
%type <std::vector<elna::source::conditional_statements *>> elsif_statement_list;
%%
program:
type_part constant_part procedure_part variable_part BEGIN_BLOCK optional_statements END_BLOCK DOT
@ -121,7 +122,7 @@ program:
{
*value_definition++ = variable;
}
auto tree = new elna::source::program(elna::source::position{},
auto tree = new elna::source::program(elna::source::make_position(@5),
std::move(definitions), std::move(value_definitions), std::move($6));
driver.tree.reset(tree);
@ -139,28 +140,28 @@ block: constant_part variable_part BEGIN_BLOCK optional_statements END_BLOCK
{
*definition++ = variable;
}
$$ = new elna::source::block(elna::source::position{},
$$ = new elna::source::block(elna::source::make_position(@3),
std::move(definitions), std::move($4));
}
procedure_definition:
PROCEDURE IDENTIFIER formal_parameter_list SEMICOLON block SEMICOLON
{
$$ = new elna::source::procedure_definition(elna::source::position{},
$$ = new elna::source::procedure_definition(elna::source::make_position(@1),
$2, std::move($3), nullptr, $5);
}
| PROCEDURE IDENTIFIER formal_parameter_list SEMICOLON EXTERN SEMICOLON
{
$$ = new elna::source::procedure_definition(elna::source::position{},
$$ = new elna::source::procedure_definition(elna::source::make_position(@1),
$2, std::move($3), nullptr, nullptr);
}
| PROCEDURE IDENTIFIER formal_parameter_list COLON type_expression SEMICOLON block SEMICOLON
{
$$ = new elna::source::procedure_definition(elna::source::position{},
$$ = new elna::source::procedure_definition(elna::source::make_position(@1),
$2, std::move($3), $5, $7);
}
| PROCEDURE IDENTIFIER formal_parameter_list COLON type_expression SEMICOLON EXTERN SEMICOLON
{
$$ = new elna::source::procedure_definition(elna::source::position{},
$$ = new elna::source::procedure_definition(elna::source::make_position(@1),
$2, std::move($3), $5, nullptr);
}
procedure_definitions:
@ -188,19 +189,30 @@ while_statement: WHILE expression DO optional_statements END_BLOCK
std::swap($4, body->statements);
$$ = new elna::source::while_statement(elna::source::make_position(@1), body);
}
elsif_statement_list:
ELSIF expression THEN optional_statements elsif_statement_list
{
elna::source::conditional_statements *branch = new elna::source::conditional_statements($2);
std::swap(branch->statements, $4);
std::swap($5, $$);
$$.emplace($$.begin(), branch);
}
| {}
if_statement:
IF expression THEN optional_statements END_BLOCK
IF expression THEN optional_statements elsif_statement_list END_BLOCK
{
auto then = new elna::source::conditional_statements($2);
std::swap($4, then->statements);
$$ = new elna::source::if_statement(elna::source::make_position(@1), then);
std::swap($5, $$->branches);
}
| IF expression THEN optional_statements ELSE optional_statements END_BLOCK
| IF expression THEN optional_statements elsif_statement_list ELSE optional_statements END_BLOCK
{
auto then = new elna::source::conditional_statements($2);
std::swap($4, then->statements);
auto _else = new std::vector<elna::source::statement *>(std::move($6));
auto _else = new std::vector<elna::source::statement *>(std::move($7));
$$ = new elna::source::if_statement(elna::source::make_position(@1), then, _else);
std::swap($5, $$->branches);
}
return_statement:
RETURN expression