Add lexer and parser sources
This commit is contained in:
50
boot/ast.cc
50
boot/ast.cc
@ -225,7 +225,7 @@ namespace elna::boot
|
||||
|
||||
variable_declaration::variable_declaration(const struct position position, identifier_definition identifier,
|
||||
std::shared_ptr<type_expression> variable_type)
|
||||
: definition(position, identifier), m_variable_type(variable_type)
|
||||
: declaration(position, identifier), m_variable_type(variable_type)
|
||||
{
|
||||
}
|
||||
|
||||
@ -239,28 +239,28 @@ namespace elna::boot
|
||||
return *m_variable_type;
|
||||
}
|
||||
|
||||
definition::definition(const struct position position, identifier_definition identifier)
|
||||
declaration::declaration(const struct position position, identifier_definition identifier)
|
||||
: node(position), identifier(identifier)
|
||||
{
|
||||
}
|
||||
|
||||
constant_definition::constant_definition(const struct position position, identifier_definition identifier,
|
||||
constant_declaration::constant_declaration(const struct position position, identifier_definition identifier,
|
||||
expression *body)
|
||||
: definition(position, identifier), m_body(body)
|
||||
: declaration(position, identifier), m_body(body)
|
||||
{
|
||||
}
|
||||
|
||||
void constant_definition::accept(parser_visitor *visitor)
|
||||
void constant_declaration::accept(parser_visitor *visitor)
|
||||
{
|
||||
visitor->visit(this);
|
||||
}
|
||||
|
||||
expression& constant_definition::body()
|
||||
expression& constant_declaration::body()
|
||||
{
|
||||
return *m_body;
|
||||
}
|
||||
|
||||
constant_definition::~constant_definition()
|
||||
constant_declaration::~constant_declaration()
|
||||
{
|
||||
delete m_body;
|
||||
}
|
||||
@ -307,55 +307,55 @@ namespace elna::boot
|
||||
return this;
|
||||
}
|
||||
|
||||
procedure_definition::procedure_definition(const struct position position, identifier_definition identifier,
|
||||
procedure_declaration::procedure_declaration(const struct position position, identifier_definition identifier,
|
||||
procedure_type_expression *heading, block&& body)
|
||||
: definition(position, identifier), m_heading(heading), body(std::move(body))
|
||||
: declaration(position, identifier), m_heading(heading), body(std::move(body))
|
||||
{
|
||||
}
|
||||
|
||||
procedure_definition::procedure_definition(const struct position position, identifier_definition identifier,
|
||||
procedure_declaration::procedure_declaration(const struct position position, identifier_definition identifier,
|
||||
procedure_type_expression *heading)
|
||||
: definition(position, identifier), m_heading(heading), body(std::nullopt)
|
||||
: declaration(position, identifier), m_heading(heading), body(std::nullopt)
|
||||
{
|
||||
}
|
||||
|
||||
void procedure_definition::accept(parser_visitor *visitor)
|
||||
void procedure_declaration::accept(parser_visitor *visitor)
|
||||
{
|
||||
visitor->visit(this);
|
||||
}
|
||||
|
||||
procedure_type_expression& procedure_definition::heading()
|
||||
procedure_type_expression& procedure_declaration::heading()
|
||||
{
|
||||
return *m_heading;
|
||||
}
|
||||
|
||||
procedure_definition::~procedure_definition()
|
||||
procedure_declaration::~procedure_declaration()
|
||||
{
|
||||
delete m_heading;
|
||||
}
|
||||
|
||||
type_definition::type_definition(const struct position position, identifier_definition identifier,
|
||||
type_declaration::type_declaration(const struct position position, identifier_definition identifier,
|
||||
type_expression *body)
|
||||
: definition(position, identifier), m_body(body)
|
||||
: declaration(position, identifier), m_body(body)
|
||||
{
|
||||
}
|
||||
|
||||
type_definition::~type_definition()
|
||||
type_declaration::~type_declaration()
|
||||
{
|
||||
delete m_body;
|
||||
}
|
||||
|
||||
void type_definition::accept(parser_visitor *visitor)
|
||||
void type_declaration::accept(parser_visitor *visitor)
|
||||
{
|
||||
visitor->visit(this);
|
||||
}
|
||||
|
||||
type_expression& type_definition::body()
|
||||
type_expression& type_declaration::body()
|
||||
{
|
||||
return *m_body;
|
||||
}
|
||||
|
||||
block::block(std::vector<constant_definition *>&& constants, std::vector<variable_declaration *>&& variables,
|
||||
block::block(std::vector<constant_declaration *>&& constants, std::vector<variable_declaration *>&& variables,
|
||||
std::vector<statement *>&& body)
|
||||
: m_variables(std::move(variables)), m_constants(std::move(constants)), m_body(std::move(body))
|
||||
{
|
||||
@ -381,7 +381,7 @@ namespace elna::boot
|
||||
return m_variables;
|
||||
}
|
||||
|
||||
const std::vector<constant_definition *>& block::constants()
|
||||
const std::vector<constant_declaration *>& block::constants()
|
||||
{
|
||||
return m_constants;
|
||||
}
|
||||
@ -401,7 +401,7 @@ namespace elna::boot
|
||||
{
|
||||
delete variable;
|
||||
}
|
||||
for (constant_definition *constant : this->constants())
|
||||
for (constant_declaration *constant : this->constants())
|
||||
{
|
||||
delete constant;
|
||||
}
|
||||
@ -419,7 +419,7 @@ namespace elna::boot
|
||||
|
||||
unit::~unit()
|
||||
{
|
||||
for (procedure_definition *procedure : this->procedures)
|
||||
for (procedure_declaration *procedure : this->procedures)
|
||||
{
|
||||
delete procedure;
|
||||
}
|
||||
@ -427,11 +427,11 @@ namespace elna::boot
|
||||
{
|
||||
delete variable;
|
||||
}
|
||||
for (type_definition *type : this->types)
|
||||
for (type_declaration *type : this->types)
|
||||
{
|
||||
delete type;
|
||||
}
|
||||
for (constant_definition *constant : this->constants)
|
||||
for (constant_declaration *constant : this->constants)
|
||||
{
|
||||
delete constant;
|
||||
}
|
||||
|
@ -133,8 +133,8 @@ along with GCC; see the file COPYING3. If not see
|
||||
%type <std::vector<elna::boot::expression *>> case_labels;
|
||||
%type <elna::boot::switch_case> switch_case;
|
||||
%type <std::vector<elna::boot::switch_case>> switch_cases;
|
||||
%type <elna::boot::constant_definition *> constant_definition;
|
||||
%type <std::vector<elna::boot::constant_definition *>> constant_part constant_definitions;
|
||||
%type <elna::boot::constant_declaration *> constant_declaration;
|
||||
%type <std::vector<elna::boot::constant_declaration *>> constant_part constant_declarations;
|
||||
%type <std::vector<elna::boot::variable_declaration *>> variable_declarations variable_part variable_declaration;
|
||||
%type <elna::boot::type_expression *> type_expression;
|
||||
%type <std::vector<elna::boot::type_expression *>> type_expressions;
|
||||
@ -148,12 +148,12 @@ along with GCC; see the file COPYING3. If not see
|
||||
%type <elna::boot::return_statement *> return_statement;
|
||||
%type <elna::boot::statement *> statement;
|
||||
%type <std::vector<elna::boot::statement *>> required_statements optional_statements statement_part;
|
||||
%type <elna::boot::procedure_definition *> procedure_definition;
|
||||
%type <elna::boot::procedure_declaration *> procedure_declaration;
|
||||
%type <std::pair<std::vector<std::string>, elna::boot::procedure_type_expression *>> procedure_heading;
|
||||
%type <elna::boot::procedure_type_expression::return_t> return_declaration;
|
||||
%type <std::vector<elna::boot::procedure_definition *>> procedure_definitions procedure_part;
|
||||
%type <elna::boot::type_definition *> type_definition;
|
||||
%type <std::vector<elna::boot::type_definition *>> type_definitions type_part;
|
||||
%type <std::vector<elna::boot::procedure_declaration *>> procedure_declarations procedure_part;
|
||||
%type <elna::boot::type_declaration *> type_declaration;
|
||||
%type <std::vector<elna::boot::type_declaration *>> type_declarations type_part;
|
||||
%type <std::unique_ptr<elna::boot::block>> block;
|
||||
%type <elna::boot::field_declaration> field_declaration formal_parameter;
|
||||
%type <std::vector<std::pair<std::string, elna::boot::type_expression *>>>
|
||||
@ -167,28 +167,28 @@ along with GCC; see the file COPYING3. If not see
|
||||
%type <std::vector<elna::boot::import_declaration *>> import_declarations import_part;
|
||||
%%
|
||||
program:
|
||||
"program" import_part constant_part type_part variable_part procedure_part "begin" optional_statements "end" "."
|
||||
"program" ";" import_part constant_part type_part variable_part procedure_part statement_part "end" "."
|
||||
{
|
||||
auto tree = new boot::program(boot::make_position(@7));
|
||||
auto tree = new boot::program(boot::make_position(@1));
|
||||
|
||||
std::swap(tree->imports, $2);
|
||||
std::swap(tree->constants, $3);
|
||||
std::swap(tree->types , $4);
|
||||
std::swap(tree->variables, $5);
|
||||
std::swap(tree->procedures, $6);
|
||||
std::swap(tree->imports, $3);
|
||||
std::swap(tree->constants, $4);
|
||||
std::swap(tree->types , $5);
|
||||
std::swap(tree->variables, $6);
|
||||
std::swap(tree->procedures, $7);
|
||||
std::swap(tree->body, $8);
|
||||
|
||||
driver.tree.reset(tree);
|
||||
}
|
||||
| "module" import_part constant_part type_part variable_part procedure_part "end" "."
|
||||
| "module" ";" import_part constant_part type_part variable_part procedure_part "end" "."
|
||||
{
|
||||
auto tree = new boot::program(boot::make_position(@7));
|
||||
auto tree = new boot::program(boot::make_position(@1));
|
||||
|
||||
std::swap(tree->imports, $2);
|
||||
std::swap(tree->constants, $3);
|
||||
std::swap(tree->types , $4);
|
||||
std::swap(tree->variables, $5);
|
||||
std::swap(tree->procedures, $6);
|
||||
std::swap(tree->imports, $3);
|
||||
std::swap(tree->constants, $4);
|
||||
std::swap(tree->types , $5);
|
||||
std::swap(tree->variables, $6);
|
||||
std::swap(tree->procedures, $7);
|
||||
|
||||
driver.tree.reset(tree);
|
||||
}
|
||||
@ -228,27 +228,27 @@ procedure_heading: formal_parameter_list return_declaration
|
||||
$$.second->parameters.push_back(type);
|
||||
}
|
||||
}
|
||||
procedure_definition:
|
||||
"proc" identifier_definition procedure_heading ";" block
|
||||
procedure_declaration:
|
||||
"proc" identifier_definition procedure_heading ";" block ";"
|
||||
{
|
||||
$$ = new boot::procedure_definition(boot::make_position(@1), std::move($2), $3.second, std::move(*$5));
|
||||
$$ = new boot::procedure_declaration(boot::make_position(@1), std::move($2), $3.second, std::move(*$5));
|
||||
std::swap($3.first, $$->parameter_names);
|
||||
}
|
||||
| "proc" identifier_definition procedure_heading ";" "extern"
|
||||
| "proc" identifier_definition procedure_heading ";" "extern" ";"
|
||||
{
|
||||
$$ = new boot::procedure_definition(boot::make_position(@1), std::move($2), $3.second);
|
||||
$$ = new boot::procedure_declaration(boot::make_position(@1), std::move($2), $3.second);
|
||||
std::swap($3.first, $$->parameter_names);
|
||||
}
|
||||
procedure_definitions:
|
||||
procedure_definition procedure_definitions
|
||||
procedure_declarations:
|
||||
procedure_declaration procedure_declarations
|
||||
{
|
||||
std::swap($$, $2);
|
||||
$$.emplace($$.cbegin(), std::move($1));
|
||||
}
|
||||
| procedure_definition { $$.emplace_back(std::move($1)); }
|
||||
| procedure_declaration { $$.emplace_back(std::move($1)); }
|
||||
procedure_part:
|
||||
/* no procedure definitions */ {}
|
||||
| procedure_definitions { std::swap($$, $1); }
|
||||
| procedure_declarations { std::swap($$, $1); }
|
||||
call_expression: designator_expression actual_parameter_list
|
||||
{
|
||||
$$ = new boot::procedure_call(boot::make_position(@1), $1);
|
||||
@ -454,9 +454,9 @@ optional_statements:
|
||||
field_declaration:
|
||||
IDENTIFIER ":" type_expression { $$ = std::make_pair($1, $3); }
|
||||
required_fields:
|
||||
field_declaration required_fields
|
||||
field_declaration ";" required_fields
|
||||
{
|
||||
std::swap($$, $2);
|
||||
std::swap($$, $3);
|
||||
$$.emplace($$.cbegin(), $1);
|
||||
}
|
||||
| field_declaration { $$.emplace_back($1); }
|
||||
@ -501,7 +501,7 @@ identifiers:
|
||||
$$.emplace($$.cbegin(), std::move($1));
|
||||
}
|
||||
| IDENTIFIER { $$.emplace_back(std::move($1)); }
|
||||
variable_declaration: identifier_definitions ":" type_expression
|
||||
variable_declaration: identifier_definitions ":" type_expression ";"
|
||||
{
|
||||
std::shared_ptr<boot::type_expression> shared_type{ $3 };
|
||||
|
||||
@ -523,12 +523,12 @@ variable_declarations:
|
||||
variable_part:
|
||||
/* no variable declarations */ {}
|
||||
| "var" variable_declarations { std::swap($$, $2); }
|
||||
constant_definition: identifier_definition ":=" expression
|
||||
constant_declaration: identifier_definition ":=" expression ";"
|
||||
{
|
||||
$$ = new boot::constant_definition(boot::make_position(@1), std::move($1), $3);
|
||||
$$ = new boot::constant_declaration(boot::make_position(@1), std::move($1), $3);
|
||||
}
|
||||
constant_definitions:
|
||||
constant_definition constant_definitions
|
||||
constant_declarations:
|
||||
constant_declaration constant_declarations
|
||||
{
|
||||
std::swap($$, $2);
|
||||
$$.insert($$.cbegin(), $1);
|
||||
@ -536,7 +536,7 @@ constant_definitions:
|
||||
| /* no constant definitions */ {}
|
||||
constant_part:
|
||||
/* no constant definitions */ {}
|
||||
| "const" constant_definitions { std::swap($$, $2); }
|
||||
| "const" constant_declarations { std::swap($$, $2); }
|
||||
import_declaration:
|
||||
IDENTIFIER "." import_declaration
|
||||
{
|
||||
@ -545,8 +545,7 @@ import_declaration:
|
||||
}
|
||||
| IDENTIFIER { $$.emplace_back(std::move($1)); }
|
||||
import_declarations:
|
||||
/* no import declarations */ {}
|
||||
| import_declaration "," import_declarations
|
||||
import_declaration "," import_declarations
|
||||
{
|
||||
std::swap($$, $3);
|
||||
$$.emplace($$.cbegin(), new boot::import_declaration(boot::make_position(@1), std::move($1)));
|
||||
@ -557,13 +556,13 @@ import_declarations:
|
||||
}
|
||||
import_part:
|
||||
/* no import declarations */ {}
|
||||
| "import" import_declarations { std::swap($$, $2); }
|
||||
type_definition: identifier_definition "=" type_expression
|
||||
| "import" import_declarations ";" { std::swap($$, $2); }
|
||||
type_declaration: identifier_definition "=" type_expression ";"
|
||||
{
|
||||
$$ = new boot::type_definition(boot::make_position(@1), std::move($1), $3);
|
||||
$$ = new boot::type_declaration(boot::make_position(@1), std::move($1), $3);
|
||||
}
|
||||
type_definitions:
|
||||
type_definition type_definitions
|
||||
type_declarations:
|
||||
type_declaration type_declarations
|
||||
{
|
||||
std::swap($$, $2);
|
||||
$$.insert($$.cbegin(), $1);
|
||||
@ -571,7 +570,7 @@ type_definitions:
|
||||
| /* no type definitions */ {}
|
||||
type_part:
|
||||
/* no type definitions */ {}
|
||||
| "type" type_definitions { std::swap($$, $2); }
|
||||
| "type" type_declarations { std::swap($$, $2); }
|
||||
formal_parameter:
|
||||
IDENTIFIER ":" type_expression { $$ = std::make_pair($1, $3); }
|
||||
formal_parameter_list:
|
||||
|
@ -83,7 +83,7 @@ namespace elna::boot
|
||||
}
|
||||
}
|
||||
|
||||
void declaration_visitor::visit(type_definition *definition)
|
||||
void declaration_visitor::visit(type_declaration *definition)
|
||||
{
|
||||
definition->body().accept(this);
|
||||
auto unresolved_declaration = this->unresolved.at(definition->identifier.identifier);
|
||||
@ -164,9 +164,12 @@ namespace elna::boot
|
||||
void declaration_visitor::visit(variable_declaration *declaration)
|
||||
{
|
||||
declaration->variable_type().accept(this);
|
||||
|
||||
this->symbols->enter(declaration->identifier.identifier,
|
||||
std::make_shared<variable_info>(this->current_type));
|
||||
}
|
||||
|
||||
void declaration_visitor::visit(constant_definition *definition)
|
||||
void declaration_visitor::visit(constant_declaration *definition)
|
||||
{
|
||||
definition->body().accept(this);
|
||||
|
||||
@ -174,7 +177,7 @@ namespace elna::boot
|
||||
std::make_shared<constant_info>(this->current_literal));
|
||||
}
|
||||
|
||||
void declaration_visitor::visit(procedure_definition *definition)
|
||||
void declaration_visitor::visit(procedure_declaration *definition)
|
||||
{
|
||||
std::shared_ptr<procedure_info> info = std::make_shared<procedure_info>(
|
||||
build_procedure(definition->heading()), definition->parameter_names);
|
||||
@ -184,7 +187,7 @@ namespace elna::boot
|
||||
|
||||
if (definition->body.has_value())
|
||||
{
|
||||
for (constant_definition *const constant : definition->body.value().constants())
|
||||
for (constant_declaration *const constant : definition->body.value().constants())
|
||||
{
|
||||
constant->accept(this);
|
||||
}
|
||||
@ -293,7 +296,7 @@ namespace elna::boot
|
||||
|
||||
void declaration_visitor::visit(unit *unit)
|
||||
{
|
||||
for (type_definition *const type : unit->types)
|
||||
for (type_declaration *const type : unit->types)
|
||||
{
|
||||
const std::string& type_identifier = type->identifier.identifier;
|
||||
|
||||
@ -303,7 +306,7 @@ namespace elna::boot
|
||||
add_error<already_declared_error>(type->identifier.identifier, this->input_file, type->position());
|
||||
}
|
||||
}
|
||||
for (type_definition *const type : unit->types)
|
||||
for (type_declaration *const type : unit->types)
|
||||
{
|
||||
type->accept(this);
|
||||
}
|
||||
@ -316,7 +319,7 @@ namespace elna::boot
|
||||
{
|
||||
variable->accept(this);
|
||||
}
|
||||
for (procedure_definition *const procedure : unit->procedures)
|
||||
for (procedure_declaration *const procedure : unit->procedures)
|
||||
{
|
||||
procedure->accept(this);
|
||||
}
|
||||
|
@ -332,8 +332,8 @@ namespace elna::boot
|
||||
return std::static_pointer_cast<constant_info>(shared_from_this());
|
||||
}
|
||||
|
||||
variable_info::variable_info(const std::string& name, const type symbol)
|
||||
: name(name), symbol(symbol)
|
||||
variable_info::variable_info(const type symbol)
|
||||
: symbol(symbol)
|
||||
{
|
||||
}
|
||||
|
||||
|
Reference in New Issue
Block a user