forked from KPGPMC/furlang
@@ -36,6 +36,8 @@ public:
|
|||||||
|
|
||||||
front::token name() const { return m_name; }
|
front::token name() const { return m_name; }
|
||||||
public:
|
public:
|
||||||
|
void accept(visitor& visitor) const override;
|
||||||
|
|
||||||
std::ostream& print(std::ostream& os) const override;
|
std::ostream& print(std::ostream& os) const override;
|
||||||
protected:
|
protected:
|
||||||
bool equal(const node& rhs) const override;
|
bool equal(const node& rhs) const override;
|
||||||
@@ -65,6 +67,8 @@ public:
|
|||||||
|
|
||||||
const function_body_h& body() const { return m_body; }
|
const function_body_h& body() const { return m_body; }
|
||||||
public:
|
public:
|
||||||
|
void accept(visitor& visitor) const override;
|
||||||
|
|
||||||
std::ostream& print(std::ostream& os) const override;
|
std::ostream& print(std::ostream& os) const override;
|
||||||
protected:
|
protected:
|
||||||
bool equal(const node& rhs) const override;
|
bool equal(const node& rhs) const override;
|
||||||
|
|||||||
@@ -36,6 +36,8 @@ public:
|
|||||||
handle<std::string_view>&& move_name() { return std::move(m_name); }
|
handle<std::string_view>&& move_name() { return std::move(m_name); }
|
||||||
public:
|
public:
|
||||||
expression_node_t expression_type() const override { return expression_node_t::VarRead; }
|
expression_node_t expression_type() const override { return expression_node_t::VarRead; }
|
||||||
|
public:
|
||||||
|
void accept(visitor& visitor) const override;
|
||||||
|
|
||||||
std::ostream& print(std::ostream& os) const override;
|
std::ostream& print(std::ostream& os) const override;
|
||||||
protected:
|
protected:
|
||||||
@@ -66,6 +68,8 @@ public:
|
|||||||
expression_node_h&& move_node() { return std::move(m_node); }
|
expression_node_h&& move_node() { return std::move(m_node); }
|
||||||
public:
|
public:
|
||||||
expression_node_t expression_type() const override { return expression_node_t::Unaryop; }
|
expression_node_t expression_type() const override { return expression_node_t::Unaryop; }
|
||||||
|
public:
|
||||||
|
void accept(visitor& visitor) const override;
|
||||||
|
|
||||||
std::ostream& print(std::ostream& os) const override;
|
std::ostream& print(std::ostream& os) const override;
|
||||||
protected:
|
protected:
|
||||||
@@ -105,6 +109,8 @@ public:
|
|||||||
expression_node_h&& move_rhs() { return std::move(m_rhs); };
|
expression_node_h&& move_rhs() { return std::move(m_rhs); };
|
||||||
public:
|
public:
|
||||||
expression_node_t expression_type() const override { return expression_node_t::Binop; }
|
expression_node_t expression_type() const override { return expression_node_t::Binop; }
|
||||||
|
public:
|
||||||
|
void accept(visitor& visitor) const override;
|
||||||
|
|
||||||
std::ostream& print(std::ostream& os) const override;
|
std::ostream& print(std::ostream& os) const override;
|
||||||
protected:
|
protected:
|
||||||
@@ -128,6 +134,8 @@ public:
|
|||||||
const expression_node_h& rhs() const { return m_rhs; }
|
const expression_node_h& rhs() const { return m_rhs; }
|
||||||
public:
|
public:
|
||||||
expression_node_t expression_type() const override { return expression_node_t::VarAssign; }
|
expression_node_t expression_type() const override { return expression_node_t::VarAssign; }
|
||||||
|
public:
|
||||||
|
void accept(visitor& visitor) const override;
|
||||||
|
|
||||||
std::ostream& print(std::ostream& os) const override;
|
std::ostream& print(std::ostream& os) const override;
|
||||||
protected:
|
protected:
|
||||||
|
|||||||
@@ -10,8 +10,8 @@ namespace ast {
|
|||||||
|
|
||||||
class node;
|
class node;
|
||||||
|
|
||||||
template <typename T, typename Error = std::string>
|
template <typename T>
|
||||||
using node_handle = handle<T*, Error>;
|
using node_handle = handle<T*, std::string>;
|
||||||
|
|
||||||
class literal_node;
|
class literal_node;
|
||||||
using literal_node_h = node_handle<literal_node>;
|
using literal_node_h = node_handle<literal_node>;
|
||||||
|
|||||||
@@ -33,6 +33,8 @@ public:
|
|||||||
|
|
||||||
const handle<std::string_view>& value() const { return m_value; }
|
const handle<std::string_view>& value() const { return m_value; }
|
||||||
public:
|
public:
|
||||||
|
void accept(visitor& visitor) const override;
|
||||||
|
|
||||||
std::ostream& print(std::ostream& os) const override;
|
std::ostream& print(std::ostream& os) const override;
|
||||||
protected:
|
protected:
|
||||||
bool equal(const node& rhs) const override;
|
bool equal(const node& rhs) const override;
|
||||||
@@ -51,6 +53,8 @@ public:
|
|||||||
|
|
||||||
bool operator==(front::integer_token integer) const { return m_value == integer; }
|
bool operator==(front::integer_token integer) const { return m_value == integer; }
|
||||||
public:
|
public:
|
||||||
|
void accept(visitor& visitor) const override;
|
||||||
|
|
||||||
std::ostream& print(std::ostream& os) const override;
|
std::ostream& print(std::ostream& os) const override;
|
||||||
protected:
|
protected:
|
||||||
bool equal(const node& rhs) const override;
|
bool equal(const node& rhs) const override;
|
||||||
|
|||||||
@@ -2,6 +2,7 @@
|
|||||||
#define FURC_AST_NODE_HPP
|
#define FURC_AST_NODE_HPP
|
||||||
|
|
||||||
#include "furc/ast/fwd.hpp"
|
#include "furc/ast/fwd.hpp"
|
||||||
|
#include "furc/ast/visitor.hpp"
|
||||||
|
|
||||||
namespace furc {
|
namespace furc {
|
||||||
namespace ast {
|
namespace ast {
|
||||||
@@ -39,6 +40,8 @@ public:
|
|||||||
bool operator==(const node& rhs) const { return category() == rhs.category() && equal(rhs); }
|
bool operator==(const node& rhs) const { return category() == rhs.category() && equal(rhs); }
|
||||||
bool operator!=(const node& rhs) const { return !this->operator==(rhs); }
|
bool operator!=(const node& rhs) const { return !this->operator==(rhs); }
|
||||||
public:
|
public:
|
||||||
|
virtual void accept(visitor& visitor) const = 0;
|
||||||
|
|
||||||
virtual std::ostream& print(std::ostream& os) const = 0;
|
virtual std::ostream& print(std::ostream& os) const = 0;
|
||||||
|
|
||||||
friend std::ostream& operator<<(std::ostream& os, const node& node) { return node.print(os); }
|
friend std::ostream& operator<<(std::ostream& os, const node& node) { return node.print(os); }
|
||||||
|
|||||||
@@ -19,6 +19,8 @@ public:
|
|||||||
|
|
||||||
const std::vector<node_handle<declaration_node>>& declarations() const { return m_declarations; }
|
const std::vector<node_handle<declaration_node>>& declarations() const { return m_declarations; }
|
||||||
public:
|
public:
|
||||||
|
void accept(visitor& visitor) const override;
|
||||||
|
|
||||||
std::ostream& print(std::ostream& os) const override;
|
std::ostream& print(std::ostream& os) const override;
|
||||||
protected:
|
protected:
|
||||||
bool equal(const node& rhs) const override;
|
bool equal(const node& rhs) const override;
|
||||||
|
|||||||
@@ -31,6 +31,8 @@ public:
|
|||||||
node_handle<expression_node> value() const { return m_value; }
|
node_handle<expression_node> value() const { return m_value; }
|
||||||
public:
|
public:
|
||||||
statement_node_t statement_type() const override { return statement_node_t::Return; }
|
statement_node_t statement_type() const override { return statement_node_t::Return; }
|
||||||
|
public:
|
||||||
|
void accept(visitor& visitor) const override;
|
||||||
|
|
||||||
std::ostream& print(std::ostream& os) const override;
|
std::ostream& print(std::ostream& os) const override;
|
||||||
protected:
|
protected:
|
||||||
|
|||||||
@@ -0,0 +1,34 @@
|
|||||||
|
#ifndef FURC_AST_VISITOR_HPP
|
||||||
|
#define FURC_AST_VISITOR_HPP
|
||||||
|
|
||||||
|
#include "furc/ast/fwd.hpp"
|
||||||
|
|
||||||
|
namespace furc {
|
||||||
|
namespace ast {
|
||||||
|
|
||||||
|
class visitor {
|
||||||
|
public:
|
||||||
|
virtual ~visitor() = default;
|
||||||
|
|
||||||
|
visitor(visitor&&) = default;
|
||||||
|
visitor& operator=(visitor&&) = default;
|
||||||
|
visitor(const visitor&) = default;
|
||||||
|
visitor& operator=(const visitor&) = default;
|
||||||
|
public:
|
||||||
|
virtual void visit_string_literal_node(const string_literal_node&) {}
|
||||||
|
virtual void visit_integer_literal_node(const integer_literal_node&) {}
|
||||||
|
virtual void visit_var_read_expression_node(const var_read_expression_node&) {}
|
||||||
|
virtual void visit_unaryop_expression_node(const unaryop_expression_node&) {}
|
||||||
|
virtual void visit_binop_expression_node(const binop_expression_node&) {}
|
||||||
|
virtual void visit_var_assign_expression_node(const var_assign_expression_node&) {}
|
||||||
|
virtual void visit_function_declaration_node(const function_declaration_node&) {}
|
||||||
|
virtual void visit_function_definition_node(const function_definition_node&) {}
|
||||||
|
virtual void visit_return_statement_node(const return_statement_node&) {}
|
||||||
|
|
||||||
|
virtual void visit_error(const node_handle<node>& handle) {}
|
||||||
|
};
|
||||||
|
|
||||||
|
} // namespace ast
|
||||||
|
} // namespace furc
|
||||||
|
|
||||||
|
#endif // FURC_AST_VISITOR_HPP
|
||||||
+55
-9
@@ -12,13 +12,8 @@ bool literal_node::equal(const node& rhs) const {
|
|||||||
return literal_type() == reinterpret_cast<const literal_node&>(rhs).literal_type();
|
return literal_type() == reinterpret_cast<const literal_node&>(rhs).literal_type();
|
||||||
}
|
}
|
||||||
|
|
||||||
std::ostream& integer_literal_node::print(std::ostream& os) const {
|
void string_literal_node::accept(visitor& visitor) const {
|
||||||
if (m_value.has_error()) return os << m_value.error();
|
visitor.visit_string_literal_node(*this);
|
||||||
return os << *m_value;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool integer_literal_node::equal(const node& rhs) const {
|
|
||||||
return literal_node::equal(rhs) && m_value == reinterpret_cast<const integer_literal_node&>(rhs).m_value;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
std::ostream& string_literal_node::print(std::ostream& os) const {
|
std::ostream& string_literal_node::print(std::ostream& os) const {
|
||||||
@@ -30,10 +25,27 @@ bool string_literal_node::equal(const node& rhs) const {
|
|||||||
return literal_node::equal(rhs) && m_value == reinterpret_cast<const string_literal_node&>(rhs).m_value;
|
return literal_node::equal(rhs) && m_value == reinterpret_cast<const string_literal_node&>(rhs).m_value;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void integer_literal_node::accept(visitor& visitor) const {
|
||||||
|
visitor.visit_integer_literal_node(*this);
|
||||||
|
}
|
||||||
|
|
||||||
|
std::ostream& integer_literal_node::print(std::ostream& os) const {
|
||||||
|
if (m_value.has_error()) return os << m_value.error();
|
||||||
|
return os << *m_value;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool integer_literal_node::equal(const node& rhs) const {
|
||||||
|
return literal_node::equal(rhs) && m_value == reinterpret_cast<const integer_literal_node&>(rhs).m_value;
|
||||||
|
}
|
||||||
|
|
||||||
bool expression_node::equal(const node& rhs) const {
|
bool expression_node::equal(const node& rhs) const {
|
||||||
return expression_type() == reinterpret_cast<const expression_node&>(rhs).expression_type();
|
return expression_type() == reinterpret_cast<const expression_node&>(rhs).expression_type();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void var_read_expression_node::accept(visitor& visitor) const {
|
||||||
|
visitor.visit_var_read_expression_node(*this);
|
||||||
|
}
|
||||||
|
|
||||||
std::ostream& var_read_expression_node::print(std::ostream& os) const {
|
std::ostream& var_read_expression_node::print(std::ostream& os) const {
|
||||||
if (m_name.present()) return os << *m_name;
|
if (m_name.present()) return os << *m_name;
|
||||||
return os << m_name.error();
|
return os << m_name.error();
|
||||||
@@ -56,6 +68,10 @@ std::ostream& operator<<(std::ostream& os, unaryop_expression_node_t type) {
|
|||||||
return os;
|
return os;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void unaryop_expression_node::accept(visitor& visitor) const {
|
||||||
|
visitor.visit_unaryop_expression_node(*this);
|
||||||
|
}
|
||||||
|
|
||||||
std::ostream& unaryop_expression_node::print(std::ostream& os) const {
|
std::ostream& unaryop_expression_node::print(std::ostream& os) const {
|
||||||
switch (m_type) {
|
switch (m_type) {
|
||||||
case unaryop_expression_node_t::Positive:
|
case unaryop_expression_node_t::Positive:
|
||||||
@@ -91,6 +107,10 @@ std::ostream& operator<<(std::ostream& os, binop_expression_node_t type) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void binop_expression_node::accept(visitor& visitor) const {
|
||||||
|
visitor.visit_binop_expression_node(*this);
|
||||||
|
}
|
||||||
|
|
||||||
std::ostream& binop_expression_node::print(std::ostream& os) const {
|
std::ostream& binop_expression_node::print(std::ostream& os) const {
|
||||||
if (m_type == binop_expression_node_t::None) return os;
|
if (m_type == binop_expression_node_t::None) return os;
|
||||||
return os << '(' << *m_lhs << ' ' << m_type << ' ' << *m_rhs << ')';
|
return os << '(' << *m_lhs << ' ' << m_type << ' ' << *m_rhs << ')';
|
||||||
@@ -101,6 +121,10 @@ bool binop_expression_node::equal(const node& rhsNode) const {
|
|||||||
return expression_node::equal(rhsNode) && m_type == rhs.m_type && m_lhs == rhs.m_lhs && m_rhs == rhs.m_rhs;
|
return expression_node::equal(rhsNode) && m_type == rhs.m_type && m_lhs == rhs.m_lhs && m_rhs == rhs.m_rhs;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void var_assign_expression_node::accept(visitor& visitor) const {
|
||||||
|
visitor.visit_var_assign_expression_node(*this);
|
||||||
|
}
|
||||||
|
|
||||||
std::ostream& var_assign_expression_node::print(std::ostream& os) const {
|
std::ostream& var_assign_expression_node::print(std::ostream& os) const {
|
||||||
return os << '(' << *m_lhs << ' ' << m_compound << "= " << *m_rhs << ')';
|
return os << '(' << *m_lhs << ' ' << m_compound << "= " << *m_rhs << ')';
|
||||||
}
|
}
|
||||||
@@ -114,6 +138,10 @@ bool declaration_node::equal(const node& rhs) const {
|
|||||||
return declaration_type() == reinterpret_cast<const declaration_node&>(rhs).declaration_type();
|
return declaration_type() == reinterpret_cast<const declaration_node&>(rhs).declaration_type();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void function_declaration_node::accept(visitor& visitor) const {
|
||||||
|
visitor.visit_function_declaration_node(*this);
|
||||||
|
}
|
||||||
|
|
||||||
std::ostream& function_declaration_node::print(std::ostream& os) const {
|
std::ostream& function_declaration_node::print(std::ostream& os) const {
|
||||||
return os << "function " << m_name->string << " declaration";
|
return os << "function " << m_name->string << " declaration";
|
||||||
}
|
}
|
||||||
@@ -122,6 +150,10 @@ bool function_declaration_node::equal(const node& rhs) const {
|
|||||||
return declaration_node::equal(rhs) && m_name == reinterpret_cast<const function_declaration_node&>(rhs).m_name;
|
return declaration_node::equal(rhs) && m_name == reinterpret_cast<const function_declaration_node&>(rhs).m_name;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void function_definition_node::accept(visitor& visitor) const {
|
||||||
|
visitor.visit_function_definition_node(*this);
|
||||||
|
}
|
||||||
|
|
||||||
std::ostream& function_definition_node::print(std::ostream& os) const {
|
std::ostream& function_definition_node::print(std::ostream& os) const {
|
||||||
function_declaration_node::print(os);
|
function_declaration_node::print(os);
|
||||||
os << ':';
|
os << ':';
|
||||||
@@ -142,6 +174,10 @@ bool statement_node::equal(const node& rhs) const {
|
|||||||
return statement_type() == reinterpret_cast<const statement_node&>(rhs).statement_type();
|
return statement_type() == reinterpret_cast<const statement_node&>(rhs).statement_type();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void return_statement_node::accept(visitor& visitor) const {
|
||||||
|
visitor.visit_return_statement_node(*this);
|
||||||
|
}
|
||||||
|
|
||||||
std::ostream& return_statement_node::print(std::ostream& os) const {
|
std::ostream& return_statement_node::print(std::ostream& os) const {
|
||||||
os << "return statement";
|
os << "return statement";
|
||||||
if (m_value.present()) return os << ' ' << *m_value;
|
if (m_value.present()) return os << ' ' << *m_value;
|
||||||
@@ -152,8 +188,14 @@ bool return_statement_node::equal(const node& rhs) const {
|
|||||||
return statement_node::equal(rhs) && m_value == reinterpret_cast<const return_statement_node&>(rhs).m_value;
|
return statement_node::equal(rhs) && m_value == reinterpret_cast<const return_statement_node&>(rhs).m_value;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool program_node::equal(const node& rhs) const {
|
void program_node::accept(visitor& visitor) const {
|
||||||
return m_declarations == reinterpret_cast<const program_node&>(rhs).m_declarations;
|
for (const auto& decl : m_declarations) {
|
||||||
|
if (decl.has_error()) {
|
||||||
|
visitor.visit_error(decl);
|
||||||
|
} else {
|
||||||
|
decl->accept(visitor);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
std::ostream& program_node::print(std::ostream& os) const {
|
std::ostream& program_node::print(std::ostream& os) const {
|
||||||
@@ -164,4 +206,8 @@ std::ostream& program_node::print(std::ostream& os) const {
|
|||||||
return os;
|
return os;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool program_node::equal(const node& rhs) const {
|
||||||
|
return m_declarations == reinterpret_cast<const program_node&>(rhs).m_declarations;
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace furc::ast
|
} // namespace furc::ast
|
||||||
Reference in New Issue
Block a user