aboutsummaryrefslogtreecommitdiff
path: root/boot/parser.yy
diff options
context:
space:
mode:
authorEugen Wissner <belka@caraus.de>2026-07-14 18:08:44 +0200
committerEugen Wissner <belka@caraus.de>2026-07-14 18:08:44 +0200
commita32a61813ebaecf0c1e69fd1481bf09d8c8b1420 (patch)
treeecfb6140075e3c46b599755e220dbf560de2e31d /boot/parser.yy
parent51e2f98e33ae10fc3052335cc6847bc93d0784fa (diff)
downloadelna-a32a61813ebaecf0c1e69fd1481bf09d8c8b1420.tar.gz
Support more floating point literals
Diffstat (limited to 'boot/parser.yy')
-rw-r--r--boot/parser.yy210
1 files changed, 101 insertions, 109 deletions
diff --git a/boot/parser.yy b/boot/parser.yy
index 4ef2de4..ef887ab 100644
--- a/boot/parser.yy
+++ b/boot/parser.yy
@@ -60,6 +60,10 @@ along with GCC; see the file COPYING3. If not see
%define api.token.raw
%define api.token.constructor
%define api.value.type variant
+%define api.value.automove
+%define parse.error detailed
+%define parse.lac full
+%expect 0 // Assert zero shift/reduce conflicts.
%parse-param {elna::boot::lexer& lexer}
%param {elna::boot::driver& driver}
@@ -76,7 +80,7 @@ along with GCC; see the file COPYING3. If not see
%token <std::string> TRAIT
%token <std::int32_t> INTEGER
%token <std::uint32_t> WORD
-%token <float> FLOAT
+%token <double> FLOAT
%token <std::string> CHARACTER
%token <std::string> STRING
%token <bool> BOOLEAN
@@ -162,78 +166,70 @@ along with GCC; see the file COPYING3. If not see
program:
import_part constant_part type_part variable_part procedure_part statement_part return_statement "end" "."
{
- boot::unit *tree = new boot::unit(boot::make_position(@1),
- std::move($1), std::move($2), std::move($3), std::move($4), std::move($5),
- std::move($6), $7);
+ boot::unit *tree = new boot::unit(boot::make_position(@$), $1, $2, $3, $4, $5, $6, $7);
driver.tree.reset(tree);
}
procedure_body:
constant_part variable_part statement_part return_statement "end"
- {
- $$ = std::make_unique<boot::procedure_body>(std::move($1), std::move($2), std::move($3), $4);
- }
+ { $$ = std::make_unique<boot::procedure_body>($1, $2, $3, $4); }
statement_part:
/* no statements */ {}
- | "begin" statements { std::swap($$, $2); }
+ | "begin" statements { $$ = $2; }
identifier_definition:
IDENTIFIER "*" { $$ = boot::identifier_definition{ $1, true }; }
| IDENTIFIER { $$ = boot::identifier_definition{ $1, false }; }
identifier_definitions:
identifier_definition "," identifier_definitions
{
- std::swap($$, $3);
+ $$ = $3;
$$.emplace($$.cbegin(), $1);
}
- | identifier_definition { $$.emplace_back(std::move($1)); }
+ | identifier_definition { $$.emplace_back($1); }
return_declaration:
/* proper procedure */ {}
| ":" "!" { $$ = boot::procedure_type_expression::return_t(std::monostate{}); }
| ":" type_expression { $$ = boot::procedure_type_expression::return_t($2); }
procedure_heading: "(" optional_fields ")" return_declaration
- {
- $$ = new boot::procedure_type_expression(boot::make_position(@1), std::move($2), std::move($4));
- }
+ { $$ = new boot::procedure_type_expression(boot::make_position(@$), $2, $4); }
procedure_declaration:
"proc" identifier_definition procedure_heading procedure_body
{
- $$ = new boot::procedure_declaration(boot::make_position(@1), std::move($2), $3,
- std::move(*$4));
+ $$ = new boot::procedure_declaration(boot::make_position(@$), $2, $3, std::move(*$4));
}
| "proc" identifier_definition procedure_heading "extern"
{
- $$ = new boot::procedure_declaration(boot::make_position(@1), std::move($2), $3);
+ $$ = new boot::procedure_declaration(boot::make_position(@$), $2, $3);
}
procedure_part:
/* no procedure declarations */ {}
| procedure_declaration procedure_part
{
- std::swap($$, $2);
- $$.emplace($$.cbegin(), std::move($1));
+ $$ = $2;
+ $$.emplace($$.cbegin(), $1);
}
call_expression: designator_expression actual_parameter_list
{
- $$ = new boot::procedure_call(boot::make_position(@1), $1);
- std::swap($$->arguments, $2);
+ $$ = new boot::procedure_call(boot::make_position(@$), $1, $2);
}
cast_expression: "cast" "(" expression ":" type_expression ")"
- { $$ = new boot::cast_expression(boot::make_position(@1), $5, $3); }
+ { $$ = new boot::cast_expression(boot::make_position(@$), $5, $3); }
elsif_do_statements:
"elsif" expression "do" statements elsif_do_statements
{
- boot::conditional_statements *branch = new boot::conditional_statements($2, std::move($4));
- std::swap($5, $$);
+ boot::conditional_statements *branch = new boot::conditional_statements($2, $4);
+ $$ = $5;
$$.emplace($$.begin(), branch);
}
| /* no branches */ {}
else_statements:
- "else" statements { $$ = new std::vector<boot::statement *>(std::move($2)); }
+ "else" statements { $$ = new std::vector<boot::statement *>($2); }
| { $$ = nullptr; }
elsif_then_statements:
"elsif" expression "then" statements elsif_then_statements
{
- boot::conditional_statements *branch = new boot::conditional_statements($2, std::move($4));
- std::swap($5, $$);
+ boot::conditional_statements *branch = new boot::conditional_statements($2, $4);
+ $$ = $5;
$$.emplace($$.begin(), branch);
}
| /* no branches */ {}
@@ -241,18 +237,17 @@ return_statement:
"return" expression { $$ = $2; }
| /* no return statement */ { $$ = nullptr; }
literal:
- INTEGER { $$ = new boot::literal<std::int32_t>(boot::make_position(@1), $1); }
- | WORD { $$ = new boot::literal<std::uint32_t>(boot::make_position(@1), $1); }
- | FLOAT { $$ = new boot::literal<double>(boot::make_position(@1), $1); }
- | BOOLEAN { $$ = new boot::literal<bool>(boot::make_position(@1), $1); }
- | CHARACTER { $$ = new boot::literal<unsigned char>(boot::make_position(@1), $1.at(0)); }
- | "nil" { $$ = new boot::literal<std::nullptr_t>(boot::make_position(@1), nullptr); }
- | STRING { $$ = new boot::literal<std::string>(boot::make_position(@1), $1); }
+ INTEGER { $$ = new boot::literal<std::int32_t>(boot::make_position(@$), $1); }
+ | WORD { $$ = new boot::literal<std::uint32_t>(boot::make_position(@$), $1); }
+ | FLOAT { $$ = new boot::literal<double>(boot::make_position(@$), $1); }
+ | BOOLEAN { $$ = new boot::literal<bool>(boot::make_position(@$), $1); }
+ | CHARACTER { $$ = new boot::literal<unsigned char>(boot::make_position(@$), $1.at(0)); }
+ | "nil" { $$ = new boot::literal<std::nullptr_t>(boot::make_position(@$), nullptr); }
+ | STRING { $$ = new boot::literal<std::string>(boot::make_position(@$), $1); }
traits_expression:
TRAIT "(" type_expressions ")"
{
- $$ = new boot::traits_expression(boot::make_position(@1), $1);
- std::swap($3, $$->parameters);
+ $$ = new boot::traits_expression(boot::make_position(@$), $1, $3);
}
simple_expression:
literal { $$ = $1; }
@@ -263,11 +258,11 @@ simple_expression:
| "(" expression ")" { $$ = $2; }
| IDENTIFIER "{" field_initializers "}"
{
- $$ = new boot::record_constructor_expression(boot::make_position(@1), std::move($1), std::move($3));
+ $$ = new boot::record_constructor_expression(boot::make_position(@$), $1, $3);
}
| "[" INTEGER "]" type_expression "{" expressions "}"
{
- $$ = new boot::array_constructor_expression(boot::make_position(@1), $2, $4, std::move($6));
+ $$ = new boot::array_constructor_expression(boot::make_position(@$), $2, $4, $6);
}
operand:
unary_expression { $$ = $1; }
@@ -278,185 +273,183 @@ expression:
binary_expression:
expression "*" expression
{
- $$ = new boot::binary_expression(boot::make_position(@2), $1, $3, boot::binary_operator::multiplication);
+ $$ = new boot::binary_expression(boot::make_position(@$), $1, $3, boot::binary_operator::multiplication);
}
| expression "/" expression
{
- $$ = new boot::binary_expression(boot::make_position(@2), $1, $3, boot::binary_operator::division);
+ $$ = new boot::binary_expression(boot::make_position(@$), $1, $3, boot::binary_operator::division);
}
| expression "%" expression
{
- $$ = new boot::binary_expression(boot::make_position(@2), $1, $3, boot::binary_operator::remainder);
+ $$ = new boot::binary_expression(boot::make_position(@$), $1, $3, boot::binary_operator::remainder);
}
| expression "+" expression
{
- $$ = new boot::binary_expression(boot::make_position(@2), $1, $3, boot::binary_operator::sum);
+ $$ = new boot::binary_expression(boot::make_position(@$), $1, $3, boot::binary_operator::sum);
}
| expression "-" expression
{
- $$ = new boot::binary_expression(boot::make_position(@2), $1, $3, boot::binary_operator::subtraction);
+ $$ = new boot::binary_expression(boot::make_position(@$), $1, $3, boot::binary_operator::subtraction);
}
| expression "=" expression
{
- $$ = new boot::binary_expression(boot::make_position(@2), $1, $3, boot::binary_operator::equals);
+ $$ = new boot::binary_expression(boot::make_position(@$), $1, $3, boot::binary_operator::equals);
}
| expression "<>" expression
{
- $$ = new boot::binary_expression(boot::make_position(@2), $1, $3, boot::binary_operator::not_equals);
+ $$ = new boot::binary_expression(boot::make_position(@$), $1, $3, boot::binary_operator::not_equals);
}
| expression "<" expression
{
- $$ = new boot::binary_expression(boot::make_position(@2), $1, $3, boot::binary_operator::less);
+ $$ = new boot::binary_expression(boot::make_position(@$), $1, $3, boot::binary_operator::less);
}
| expression ">" expression
{
- $$ = new boot::binary_expression(boot::make_position(@2), $1, $3, boot::binary_operator::greater);
+ $$ = new boot::binary_expression(boot::make_position(@$), $1, $3, boot::binary_operator::greater);
}
| expression "<=" expression
{
- $$ = new boot::binary_expression(boot::make_position(@2), $1, $3,
- boot::binary_operator::less_equal);
+ $$ = new boot::binary_expression(boot::make_position(@$), $1, $3, boot::binary_operator::less_equal);
}
| expression ">=" expression
{
- $$ = new boot::binary_expression(boot::make_position(@2), $1, $3, boot::binary_operator::greater_equal);
+ $$ = new boot::binary_expression(boot::make_position(@$), $1, $3, boot::binary_operator::greater_equal);
}
| expression "&" expression
{
- $$ = new boot::binary_expression(boot::make_position(@2), $1, $3, boot::binary_operator::conjunction);
+ $$ = new boot::binary_expression(boot::make_position(@$), $1, $3, boot::binary_operator::conjunction);
}
| expression "or" expression
{
- $$ = new boot::binary_expression(boot::make_position(@2), $1, $3, boot::binary_operator::disjunction);
+ $$ = new boot::binary_expression(boot::make_position(@$), $1, $3, boot::binary_operator::disjunction);
}
| expression "xor" expression
{
- $$ = new boot::binary_expression(boot::make_position(@2), $1, $3,
- boot::binary_operator::exclusive_disjunction);
+ $$ = new boot::binary_expression(boot::make_position(@$), $1, $3, boot::binary_operator::exclusive_disjunction);
}
| expression "<<" expression
{
- $$ = new boot::binary_expression(boot::make_position(@2), $1, $3, boot::binary_operator::shift_left);
+ $$ = new boot::binary_expression(boot::make_position(@$), $1, $3, boot::binary_operator::shift_left);
}
| expression ">>" expression
{
- $$ = new boot::binary_expression(boot::make_position(@2), $1, $3, boot::binary_operator::shift_right);
+ $$ = new boot::binary_expression(boot::make_position(@$), $1, $3, boot::binary_operator::shift_right);
}
unary_expression:
"@" operand
{
- $$ = new boot::unary_expression(boot::make_position(@1), $2, boot::unary_operator::reference);
+ $$ = new boot::unary_expression(boot::make_position(@$), $2, boot::unary_operator::reference);
}
| "~" operand
{
- $$ = new boot::unary_expression(boot::make_position(@1), $2, boot::unary_operator::negation);
+ $$ = new boot::unary_expression(boot::make_position(@$), $2, boot::unary_operator::negation);
}
| "-" operand
{
- $$ = new boot::unary_expression(boot::make_position(@1), $2, boot::unary_operator::minus);
+ $$ = new boot::unary_expression(boot::make_position(@$), $2, boot::unary_operator::minus);
}
expressions:
expression "," expressions
{
- std::swap($$, $3);
+ $$ = $3;
$$.emplace($$.cbegin(), $1);
}
| expression { $$.push_back($1); }
type_expressions:
type_expression "," type_expressions
{
- std::swap($$, $3);
+ $$ = $3;
$$.emplace($$.cbegin(), $1);
}
| type_expression { $$.push_back($1); }
designator_expression:
simple_expression "[" expression "]"
- { $$ = new boot::array_access_expression(boot::make_position(@2), $1, $3); }
+ { $$ = new boot::array_access_expression(boot::make_position(@$), $1, $3); }
| simple_expression "." IDENTIFIER
- { $$ = new boot::field_access_expression(boot::make_position(@2), $1, $3); }
+ { $$ = new boot::field_access_expression(boot::make_position(@$), $1, $3); }
| simple_expression "^"
- { $$ = new boot::dereference_expression(boot::make_position(@1), $1); }
+ { $$ = new boot::dereference_expression(boot::make_position(@$), $1); }
| IDENTIFIER
- { $$ = new boot::named_expression(boot::make_position(@1), $1); }
+ { $$ = new boot::named_expression(boot::make_position(@$), $1); }
statement:
designator_expression ":=" expression
- { $$ = new boot::assign_statement(boot::make_position(@1), $1, $3); }
+ { $$ = new boot::assign_statement(boot::make_position(@$), $1, $3); }
| "while" expression "do" statements elsif_do_statements "end"
{
- boot::conditional_statements *body = new boot::conditional_statements($2, std::move($4));
- $$ = new boot::while_statement(boot::make_position(@1), body, std::move($5));
+ boot::conditional_statements *body = new boot::conditional_statements($2, $4);
+ $$ = new boot::while_statement(boot::make_position(@$), body, $5);
}
| "if" expression "then" statements elsif_then_statements else_statements "end"
{
- boot::conditional_statements *then = new boot::conditional_statements($2, std::move($4));
- $$ = new boot::if_statement(boot::make_position(@1), then, std::move($5), $6);
+ boot::conditional_statements *then = new boot::conditional_statements($2, $4);
+ $$ = new boot::if_statement(boot::make_position(@$), then, $5, $6);
}
| call_expression { $$ = $1; }
| "defer" statements "end"
- { $$ = new boot::defer_statement(boot::make_position(@1), std::move($2)); }
+ { $$ = new boot::defer_statement(boot::make_position(@$), $2); }
| "case" expression "of" switch_cases else_statements "end"
- { $$ = new boot::case_statement(boot::make_position(@1), $2, std::move($4), $5); }
+ { $$ = new boot::case_statement(boot::make_position(@$), $2, $4, $5); }
| { $$ = new boot::empty_statement(boot::make_position(@$)); }
switch_case: case_labels ":" statements
- { $$ = { .labels = std::move($1), .statements = std::move($3) }; }
+ { $$ = { .labels = $1, .statements = $3 }; }
switch_cases:
switch_case "|" switch_cases
{
- std::swap($$, $3);
+ $$ = $3;
$$.emplace($$.cbegin(), $1);
}
| switch_case { $$.push_back($1); }
case_labels:
expression "," case_labels
{
- std::swap($$, $3);
+ $$ = $3;
$$.emplace($$.cbegin(), $1);
}
| expression { $$.push_back($1); }
statements:
statements ";" statement
{
- std::swap($$, $1);
+ $$ = $1;
$$.insert($$.cend(), $3);
}
| statement { $$.push_back($1); }
field_declaration:
- identifiers ":" type_expression { $$ = std::make_pair(std::move($1), std::shared_ptr<boot::type_expression>($3)); }
+ identifiers ":" type_expression { $$ = std::make_pair($1, std::shared_ptr<boot::type_expression>($3)); }
required_fields:
field_declaration ";" required_fields
{
- std::swap($$, $3);
+ $$ = $3;
$$.emplace($$.cbegin(), $1);
}
| field_declaration { $$.emplace_back($1); }
optional_fields:
- required_fields { std::swap($$, $1); }
+ required_fields { $$ = $1; }
| /* no fields */ {}
field_initializer:
- IDENTIFIER ":" expression { $$.name = std::move($1); $$.value = $3; }
+ IDENTIFIER ":" expression { $$.name = $1; $$.value = $3; }
field_initializers:
field_initializer "," field_initializers
{
- std::swap($$, $3);
+ $$ = $3;
$$.emplace($$.cbegin(), $1);
}
| field_initializer { $$.push_back($1); }
type_expression:
"[" INTEGER "]" type_expression
{
- $$ = new boot::array_type_expression(boot::make_position(@1), $4, $2);
+ $$ = new boot::array_type_expression(boot::make_position(@$), $4, $2);
}
| "^" type_expression
{
- $$ = new boot::pointer_type_expression(boot::make_position(@1), $2);
+ $$ = new boot::pointer_type_expression(boot::make_position(@$), $2);
}
| "record" optional_fields "end"
{
- $$ = new boot::record_type_expression(boot::make_position(@1), std::move($2));
+ $$ = new boot::record_type_expression(boot::make_position(@$), $2);
}
| "record" "(" IDENTIFIER ")" optional_fields "end"
{
- $$ = new boot::record_type_expression(boot::make_position(@1), std::move($5), std::move($3));
+ $$ = new boot::record_type_expression(boot::make_position(@$), $5, $3);
}
| "proc" procedure_heading
{
@@ -464,97 +457,96 @@ type_expression:
}
| "(" identifiers ")"
{
- $$ = new boot::enumeration_type_expression(boot::make_position(@1), std::move($2));
+ $$ = new boot::enumeration_type_expression(boot::make_position(@$), $2);
}
| IDENTIFIER
{
- $$ = new boot::named_expression(boot::make_position(@1), $1);
+ $$ = new boot::named_expression(boot::make_position(@$), $1);
}
identifiers:
IDENTIFIER "," identifiers
{
- std::swap($$, $3);
- $$.emplace($$.cbegin(), std::move($1));
+ $$ = $3;
+ $$.emplace($$.cbegin(), $1);
}
- | IDENTIFIER { $$.emplace_back(std::move($1)); }
+ | IDENTIFIER { $$.emplace_back($1); }
variable_declaration:
identifier_definitions ":" type_expression
{
std::shared_ptr<boot::type_expression> shared_type{ $3 };
- $$ = new boot::variable_declaration( boot::make_position(@2), std::move($1), shared_type);
+ $$ = new boot::variable_declaration( boot::make_position(@$), $1, shared_type);
}
| identifier_definitions ":" type_expression ":=" "extern"
{
std::shared_ptr<boot::type_expression> shared_type{ $3 };
- $$ = new boot::variable_declaration( boot::make_position(@2), std::move($1), shared_type,
- std::monostate{});
+ $$ = new boot::variable_declaration( boot::make_position(@$), $1, shared_type, std::monostate{});
}
| identifier_definitions ":" type_expression ":=" expression
{
std::shared_ptr<boot::type_expression> shared_type{ $3 };
- $$ = new boot::variable_declaration( boot::make_position(@2), std::move($1), shared_type, $5);
+ $$ = new boot::variable_declaration( boot::make_position(@$), $1, shared_type, $5);
}
variable_declarations:
/* no variable declarations */ {}
| variable_declaration variable_declarations
{
- std::swap($$, $2);
+ $$ = $2;
$$.insert(std::cbegin($$), $1);
}
variable_part:
/* no variable declarations */ {}
- | "var" variable_declarations { std::swap($$, $2); }
+ | "var" variable_declarations { $$ = $2; }
constant_declaration: identifier_definition ":=" expression
{
- $$ = new boot::constant_declaration(boot::make_position(@1), std::move($1), $3);
+ $$ = new boot::constant_declaration(boot::make_position(@$), $1, $3);
}
constant_declarations:
constant_declaration constant_declarations
{
- std::swap($$, $2);
+ $$ = $2;
$$.insert(std::cbegin($$), $1);
}
| /* no constant definitions */ {}
constant_part:
/* no constant definitions */ {}
- | "const" constant_declarations { std::swap($$, $2); }
+ | "const" constant_declarations { $$ = $2; }
import_declaration:
IDENTIFIER "." import_declaration
{
- std::swap($$, $3);
- $$.emplace($$.cbegin(), std::move($1));
+ $$ = $3;
+ $$.emplace($$.cbegin(), $1);
}
- | IDENTIFIER { $$.emplace_back(std::move($1)); }
+ | IDENTIFIER { $$.emplace_back($1); }
import_declarations:
import_declaration "," import_declarations
{
- std::swap($$, $3);
- $$.emplace($$.cbegin(), new boot::import_declaration(boot::make_position(@1), std::move($1)));
+ $$ = $3;
+ $$.emplace($$.cbegin(), new boot::import_declaration(boot::make_position(@$), $1));
}
| import_declaration
{
- $$.emplace_back(new boot::import_declaration(boot::make_position(@1), std::move($1)));
+ $$.emplace_back(new boot::import_declaration(boot::make_position(@$), $1));
}
import_part:
/* no import declarations */ {}
- | "import" import_declarations { std::swap($$, $2); }
+ | "import" import_declarations { $$ = $2; }
type_declaration: identifier_definition "=" type_expression
{
- $$ = new boot::type_declaration(boot::make_position(@1), std::move($1), $3);
+ $$ = new boot::type_declaration(boot::make_position(@$), $1, $3);
}
type_declarations:
type_declaration type_declarations
{
- std::swap($$, $2);
+ $$ = $2;
$$.insert($$.cbegin(), $1);
}
| /* no type definitions */ {}
type_part:
/* no type definitions */ {}
- | "type" type_declarations { std::swap($$, $2); }
+ | "type" type_declarations { $$ = $2; }
actual_parameter_list:
"(" ")" {}
- | "(" expressions ")" { std::swap($$, $2); }
+ | "(" expressions ")" { $$ = $2; }
%%
void yy::parser::error(const location_type& loc, const std::string& message)