Replace ! with a function call writei

This commit is contained in:
2024-03-19 09:35:50 +01:00
parent bfabdb1d08
commit 263b868a45
25 changed files with 315 additions and 159 deletions

View File

@ -108,20 +108,18 @@ namespace elna::source
}
token::token(const token& that)
: m_type(that.of()), m_position(that.position())
{
*this = that;
}
token::token(token&& that)
: m_type(that.of()), m_position(that.position())
{
*this = std::move(that);
}
token::~token()
{
if (m_type == type::identifier || m_type == type::term_operator || m_type == type::factor_operator)
if (has_identifier())
{
m_value.identifier.~basic_string();
}
@ -129,11 +127,15 @@ namespace elna::source
token& token::operator=(const token& that)
{
if (has_identifier())
{
m_value.identifier.~basic_string();
}
m_type = that.of();
m_position = that.position();
if (that.has_identifier())
{
m_value.identifier = that.identifier();
new((void *) &m_value.identifier) std::string(that.identifier());
}
else if (that.is_numeric())
{
@ -148,11 +150,15 @@ namespace elna::source
token& token::operator=(token&& that)
{
if (has_identifier())
{
m_value.identifier.~basic_string();
}
m_type = that.of();
m_position = that.position();
if (that.has_identifier())
{
m_value.identifier = std::move(that.identifier());
new((void *) &m_value.identifier) std::string(std::move(that.identifier()));
}
else if (that.is_numeric())
{
@ -344,10 +350,6 @@ namespace elna::source
{
tokens.emplace_back(token::type::comma, iterator.position());
}
else if (*iterator == '!')
{
tokens.emplace_back(token::type::bang, iterator.position());
}
else if (*iterator == '?')
{
tokens.emplace_back(token::type::question_mark, iterator.position());

View File

@ -12,9 +12,9 @@ namespace elna::source
definition->body().accept(this);
}
void empty_visitor::visit(bang_statement *statement)
void empty_visitor::visit(call_statement *statement)
{
statement->body().accept(this);
statement->arguments().accept(this);
}
void empty_visitor::visit(question_mark_statement *statement)
@ -259,17 +259,22 @@ namespace elna::source
return m_operator;
}
bang_statement::bang_statement(std::unique_ptr<expression>&& body)
: m_body(std::move(body))
call_statement::call_statement(const std::string& name, std::unique_ptr<expression>&& body)
: m_name(name), m_body(std::move(body))
{
}
void bang_statement::accept(parser_visitor *visitor)
void call_statement::accept(parser_visitor *visitor)
{
visitor->visit(this);
}
expression& bang_statement::body()
std::string& call_statement::name() noexcept
{
return m_name;
}
expression& call_statement::arguments()
{
return *m_body;
}
@ -510,9 +515,9 @@ namespace elna::source
{
return parse_assign_statement();
}
else if (iterator.current(token::type::bang))
else if (iterator.current(token::type::identifier) && iterator.look_ahead(token::type::left_paren))
{
return parse_bang_statement();
return parse_call_statement();
}
else if (iterator.current(token::type::question_mark))
{
@ -534,17 +539,18 @@ namespace elna::source
return nullptr;
}
std::unique_ptr<bang_statement> parser::parse_bang_statement()
std::unique_ptr<call_statement> parser::parse_call_statement()
{
if (!iterator.advance(token::type::bang))
auto function_name = iterator.advance(token::type::identifier);
if (function_name.has_value() && !iterator.skip(token::type::left_paren))
{
return nullptr;
}
auto bang_body = parse_expression();
if (bang_body != nullptr)
if (bang_body != nullptr && iterator.skip(token::type::right_paren))
{
return std::make_unique<bang_statement>(std::move(bang_body));
return std::make_unique<call_statement>(function_name->get().identifier(), std::move(bang_body));
}
return nullptr;
}

View File

@ -27,6 +27,12 @@ namespace elna::source
return "Name '" + name + "' was already defined";
}
symbol_table::symbol_table()
{
enter("writei", std::make_shared<intrinsic_info>());
enter("writeb", std::make_shared<intrinsic_info>());
}
std::shared_ptr<info> symbol_table::lookup(const std::string& name)
{
auto entry = entries.find(name);
@ -84,4 +90,8 @@ namespace elna::source
{
this->local_stack_size = size;
}
intrinsic_info::~intrinsic_info()
{
}
}