forked from PuqiAR/Fig-TreeWalker
[Feat] 详细区分左值(LvObject)与右值(RvObject -> ObjectPtr)
[Impl] 重构evaluator.cpp + hpp 全部 [Feat] 增加对于IndexExpr的解析 [Fix][Impl] 现在点运算符不由BinaryExpr负责,增加MemberExpr,单独实现解析 [Impl] 项目目录全部翻修, src/目录下单独文件夹放置每一个模块
This commit is contained in:
23
src/Ast/AccessModifier.hpp
Normal file
23
src/Ast/AccessModifier.hpp
Normal file
@@ -0,0 +1,23 @@
|
||||
#pragma once
|
||||
|
||||
#include <cstdint>
|
||||
namespace Fig
|
||||
{
|
||||
enum class AccessModifier : uint8_t
|
||||
{
|
||||
Normal,
|
||||
Const,
|
||||
Public,
|
||||
PublicConst,
|
||||
};
|
||||
|
||||
inline bool isAccessPublic(AccessModifier am)
|
||||
{
|
||||
return am == AccessModifier::Public || am == AccessModifier::PublicConst;
|
||||
}
|
||||
|
||||
inline bool isAccessConst(AccessModifier am)
|
||||
{
|
||||
return am == AccessModifier::Const || am == AccessModifier::PublicConst;
|
||||
}
|
||||
};
|
||||
29
src/Ast/Expressions/BinaryExpr.hpp
Normal file
29
src/Ast/Expressions/BinaryExpr.hpp
Normal file
@@ -0,0 +1,29 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
class BinaryExprAst final : public ExpressionAst
|
||||
{
|
||||
public:
|
||||
Operator op;
|
||||
Expression lexp, rexp;
|
||||
|
||||
BinaryExprAst()
|
||||
{
|
||||
type = AstType::BinaryExpr;
|
||||
}
|
||||
BinaryExprAst(Expression _lexp, Operator _op, Expression _rexp)
|
||||
{
|
||||
type = AstType::BinaryExpr;
|
||||
|
||||
lexp = _lexp;
|
||||
op = _op;
|
||||
rexp = _rexp;
|
||||
}
|
||||
};
|
||||
|
||||
using BinaryExpr = std::shared_ptr<BinaryExprAst>;
|
||||
|
||||
}; // namespace Fig
|
||||
65
src/Ast/Expressions/ContainerInitExprs.hpp
Normal file
65
src/Ast/Expressions/ContainerInitExprs.hpp
Normal file
@@ -0,0 +1,65 @@
|
||||
|
||||
// Container Data Types --- Tuple/List/Map...
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
|
||||
#include <map>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
class ListExprAst final : public ExpressionAst
|
||||
{
|
||||
public:
|
||||
std::vector<Expression> val;
|
||||
|
||||
ListExprAst()
|
||||
{
|
||||
type = AstType::ListExpr;
|
||||
}
|
||||
|
||||
ListExprAst(std::vector<Expression> _val) :
|
||||
val(std::move(_val))
|
||||
{
|
||||
type = AstType::ListExpr;
|
||||
}
|
||||
};
|
||||
using ListExpr = std::shared_ptr<ListExprAst>;
|
||||
|
||||
class TupleExprAst final : public ExpressionAst
|
||||
{
|
||||
public:
|
||||
std::vector<Expression> val;
|
||||
|
||||
TupleExprAst()
|
||||
{
|
||||
type = AstType::TupleExpr;
|
||||
}
|
||||
|
||||
TupleExprAst(std::vector<Expression> _val) :
|
||||
val(std::move(_val))
|
||||
{
|
||||
type = AstType::TupleExpr;
|
||||
}
|
||||
};
|
||||
using TupleExpr = std::shared_ptr<TupleExprAst>;
|
||||
|
||||
class MapExprAst final : public ExpressionAst
|
||||
{
|
||||
public:
|
||||
std::map<FString, Expression> val;
|
||||
|
||||
MapExprAst()
|
||||
{
|
||||
type = AstType::MapExpr;
|
||||
}
|
||||
|
||||
MapExprAst(std::map<FString, Expression> _val) :
|
||||
val(std::move(_val))
|
||||
{
|
||||
type = AstType::MapExpr;
|
||||
}
|
||||
};
|
||||
using MapExpr = std::shared_ptr<MapExprAst>;
|
||||
}; // namespace Fig::Ast
|
||||
54
src/Ast/Expressions/FunctionCall.hpp
Normal file
54
src/Ast/Expressions/FunctionCall.hpp
Normal file
@@ -0,0 +1,54 @@
|
||||
// include/Ast/FunctionCall.hpp
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
#include <Value/value.hpp>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
struct FunctionArguments
|
||||
{
|
||||
std::vector<Expression> argv;
|
||||
size_t getLength() const { return argv.size(); }
|
||||
};
|
||||
|
||||
struct FunctionCallArgs final
|
||||
{
|
||||
std::vector<ObjectPtr> argv;
|
||||
size_t getLength() const { return argv.size(); }
|
||||
};
|
||||
|
||||
class FunctionCallExpr final : public ExpressionAst
|
||||
{
|
||||
public:
|
||||
Expression callee;
|
||||
FunctionArguments arg;
|
||||
|
||||
FunctionCallExpr()
|
||||
{
|
||||
type = AstType::FunctionCall;
|
||||
}
|
||||
|
||||
FunctionCallExpr(Expression _callee, FunctionArguments _arg) :
|
||||
callee(std::move(_callee)), arg(std::move(_arg))
|
||||
{
|
||||
type = AstType::FunctionCall;
|
||||
}
|
||||
|
||||
virtual FString toString() override
|
||||
{
|
||||
FString s = callee->toString();
|
||||
s += u8"(";
|
||||
for (size_t i = 0; i < arg.argv.size(); ++i)
|
||||
{
|
||||
s += arg.argv[i]->toString();
|
||||
if (i + 1 < arg.argv.size())
|
||||
s += u8", ";
|
||||
}
|
||||
s += u8")";
|
||||
return s;
|
||||
}
|
||||
};
|
||||
|
||||
using FunctionCall = std::shared_ptr<FunctionCallExpr>;
|
||||
}; // namespace Fig
|
||||
47
src/Ast/Expressions/FunctionLiteralExpr.hpp
Normal file
47
src/Ast/Expressions/FunctionLiteralExpr.hpp
Normal file
@@ -0,0 +1,47 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
#include <Ast/functionParameters.hpp>
|
||||
#include <Core/fig_string.hpp>
|
||||
#include <variant>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
class FunctionLiteralExprAst final : public ExpressionAst
|
||||
{
|
||||
public:
|
||||
FunctionParameters paras;
|
||||
std::variant<BlockStatement, Expression> body;
|
||||
|
||||
FunctionLiteralExprAst(FunctionParameters _paras, BlockStatement _body) :
|
||||
paras(std::move(_paras)), body(std::move(_body))
|
||||
{
|
||||
type = AstType::FunctionLiteralExpr;
|
||||
}
|
||||
|
||||
FunctionLiteralExprAst(FunctionParameters _paras, Expression _exprBody) :
|
||||
paras(std::move(_paras)), body(std::move(_exprBody))
|
||||
{
|
||||
type = AstType::FunctionLiteralExpr;
|
||||
}
|
||||
|
||||
bool isExprMode() const
|
||||
{
|
||||
return std::holds_alternative<Expression>(body);
|
||||
}
|
||||
|
||||
BlockStatement &getBlockBody()
|
||||
{
|
||||
return std::get<BlockStatement>(body);
|
||||
}
|
||||
|
||||
Expression &getExprBody()
|
||||
{
|
||||
return std::get<Expression>(body);
|
||||
}
|
||||
|
||||
~FunctionLiteralExprAst() = default;
|
||||
};
|
||||
|
||||
using FunctionLiteralExpr = std::shared_ptr<FunctionLiteralExprAst>;
|
||||
} // namespace Fig::Ast
|
||||
42
src/Ast/Expressions/InitExpr.hpp
Normal file
42
src/Ast/Expressions/InitExpr.hpp
Normal file
@@ -0,0 +1,42 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
class InitExprAst final : public ExpressionAst
|
||||
{
|
||||
public:
|
||||
FString structName;
|
||||
|
||||
std::vector<std::pair<FString, Expression>> args;
|
||||
|
||||
enum class InitMode
|
||||
{
|
||||
Positional = 1,
|
||||
Named,
|
||||
Shorthand
|
||||
} initMode;
|
||||
|
||||
/*
|
||||
3 ways of calling constructor
|
||||
.1 Person {"Fig", 1, "IDK"};
|
||||
.2 Person {name: "Fig", age: 1, sex: "IDK"}; // can be unordered
|
||||
.3 Person {name, age, sex};
|
||||
*/
|
||||
|
||||
InitExprAst()
|
||||
{
|
||||
type = AstType::InitExpr;
|
||||
}
|
||||
|
||||
InitExprAst(FString _structName, std::vector<std::pair<FString, Expression>> _args, InitMode _initMode) :
|
||||
structName(std::move(_structName)), args(std::move(_args)), initMode(_initMode)
|
||||
{
|
||||
type = AstType::InitExpr;
|
||||
}
|
||||
};
|
||||
|
||||
using InitExpr = std::shared_ptr<InitExprAst>;
|
||||
|
||||
}; // namespace Fig::Ast
|
||||
49
src/Ast/Expressions/PostfixExprs.hpp
Normal file
49
src/Ast/Expressions/PostfixExprs.hpp
Normal file
@@ -0,0 +1,49 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
// actually, function call is postfix, too
|
||||
// but it's too long, so use a single file (FunctionCall.hpp)
|
||||
|
||||
class MemberExprAst final : public ExpressionAst
|
||||
{
|
||||
public:
|
||||
Expression base;
|
||||
FString member;
|
||||
|
||||
MemberExprAst()
|
||||
{
|
||||
type = AstType::MemberExpr;
|
||||
}
|
||||
|
||||
MemberExprAst(Expression _base, FString _member) :
|
||||
base(std::move(_base)), member(std::move(_member))
|
||||
{
|
||||
type = AstType::MemberExpr;
|
||||
}
|
||||
};
|
||||
|
||||
using MemberExpr = std::shared_ptr<MemberExprAst>;
|
||||
|
||||
class IndexExprAst final : public ExpressionAst
|
||||
{
|
||||
public:
|
||||
Expression base;
|
||||
Expression index;
|
||||
|
||||
IndexExprAst()
|
||||
{
|
||||
type = AstType::IndexExpr;
|
||||
}
|
||||
|
||||
IndexExprAst(Expression _base, Expression _index) :
|
||||
base(std::move(_base)), index(std::move(_index))
|
||||
{
|
||||
type = AstType::IndexExpr;
|
||||
}
|
||||
};
|
||||
|
||||
using IndexExpr = std::shared_ptr<IndexExprAst>;
|
||||
}; // namespace Fig::Ast
|
||||
29
src/Ast/Expressions/TernaryExpr.hpp
Normal file
29
src/Ast/Expressions/TernaryExpr.hpp
Normal file
@@ -0,0 +1,29 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
// condition ? val_true : val_false
|
||||
class TernaryExprAst final : public ExpressionAst
|
||||
{
|
||||
public:
|
||||
Expression condition;
|
||||
Expression valueT;
|
||||
Expression valueF;
|
||||
|
||||
TernaryExprAst()
|
||||
{
|
||||
type = AstType::TernaryExpr;
|
||||
}
|
||||
TernaryExprAst(Expression _condition, Expression _valueT, Expression _valueF)
|
||||
{
|
||||
type = AstType::TernaryExpr;
|
||||
|
||||
condition = std::move(_condition);
|
||||
valueT = std::move(_valueT);
|
||||
valueF = std::move(_valueF);
|
||||
}
|
||||
};
|
||||
using TernaryExpr = std::shared_ptr<TernaryExprAst>;
|
||||
} // namespace Fig
|
||||
27
src/Ast/Expressions/UnaryExpr.hpp
Normal file
27
src/Ast/Expressions/UnaryExpr.hpp
Normal file
@@ -0,0 +1,27 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
class UnaryExprAst final : public ExpressionAst
|
||||
{
|
||||
public:
|
||||
Operator op;
|
||||
Expression exp;
|
||||
|
||||
UnaryExprAst()
|
||||
{
|
||||
type = AstType::UnaryExpr;
|
||||
}
|
||||
UnaryExprAst(Operator _op, Expression _exp)
|
||||
{
|
||||
type = AstType::UnaryExpr;
|
||||
|
||||
op = _op;
|
||||
exp = std::move(_exp);
|
||||
}
|
||||
};
|
||||
|
||||
using UnaryExpr = std::shared_ptr<UnaryExprAst>;
|
||||
} // namespace Fig
|
||||
26
src/Ast/Expressions/ValueExpr.hpp
Normal file
26
src/Ast/Expressions/ValueExpr.hpp
Normal file
@@ -0,0 +1,26 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
|
||||
#include <Value/value.hpp>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
class ValueExprAst final : public ExpressionAst
|
||||
{
|
||||
public:
|
||||
ObjectPtr val;
|
||||
|
||||
ValueExprAst()
|
||||
{
|
||||
type = AstType::ValueExpr;
|
||||
}
|
||||
ValueExprAst(ObjectPtr _val)
|
||||
{
|
||||
type = AstType::ValueExpr;
|
||||
val = std::move(_val);
|
||||
}
|
||||
};
|
||||
|
||||
using ValueExpr = std::shared_ptr<ValueExprAst>;
|
||||
};
|
||||
24
src/Ast/Expressions/VarExpr.hpp
Normal file
24
src/Ast/Expressions/VarExpr.hpp
Normal file
@@ -0,0 +1,24 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
class VarExprAst final : public ExpressionAst
|
||||
{
|
||||
public:
|
||||
const FString name;
|
||||
VarExprAst() :
|
||||
name(u8"")
|
||||
{
|
||||
type = AstType::VarExpr;
|
||||
}
|
||||
VarExprAst(FString _name) :
|
||||
name(std::move(_name))
|
||||
{
|
||||
type = AstType::VarExpr;
|
||||
}
|
||||
};
|
||||
|
||||
using VarExpr = std::shared_ptr<VarExprAst>;
|
||||
}; // namespace Fig
|
||||
46
src/Ast/Statements/ControlSt.hpp
Normal file
46
src/Ast/Statements/ControlSt.hpp
Normal file
@@ -0,0 +1,46 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
class ReturnSt final : public StatementAst
|
||||
{
|
||||
public:
|
||||
Expression retValue;
|
||||
|
||||
ReturnSt()
|
||||
{
|
||||
type = AstType::ReturnSt;
|
||||
}
|
||||
ReturnSt(Expression _retValue) :
|
||||
retValue(_retValue)
|
||||
{
|
||||
type = AstType::ReturnSt;
|
||||
}
|
||||
};
|
||||
|
||||
using Return = std::shared_ptr<ReturnSt>;
|
||||
|
||||
class BreakSt final : public StatementAst
|
||||
{
|
||||
public:
|
||||
BreakSt()
|
||||
{
|
||||
type = AstType::BreakSt;
|
||||
}
|
||||
};
|
||||
|
||||
using Break = std::shared_ptr<BreakSt>;
|
||||
|
||||
class ContinueSt final : public StatementAst
|
||||
{
|
||||
public:
|
||||
ContinueSt()
|
||||
{
|
||||
type = AstType::ContinueSt;
|
||||
}
|
||||
};
|
||||
|
||||
using Continue = std::shared_ptr<ContinueSt>;
|
||||
};
|
||||
21
src/Ast/Statements/ExpressionStmt.hpp
Normal file
21
src/Ast/Statements/ExpressionStmt.hpp
Normal file
@@ -0,0 +1,21 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
class ExpressionStmtAst final : public StatementAst
|
||||
{
|
||||
public:
|
||||
Expression exp;
|
||||
ExpressionStmtAst()
|
||||
{
|
||||
type = AstType::ExpressionStmt;
|
||||
}
|
||||
ExpressionStmtAst(Expression _exp) : exp(std::move(_exp))
|
||||
{
|
||||
type = AstType::ExpressionStmt;
|
||||
}
|
||||
};
|
||||
using ExpressionStmt = std::shared_ptr<ExpressionStmtAst>;
|
||||
}
|
||||
30
src/Ast/Statements/ForSt.hpp
Normal file
30
src/Ast/Statements/ForSt.hpp
Normal file
@@ -0,0 +1,30 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
class ForSt final : public StatementAst
|
||||
{
|
||||
public:
|
||||
Statement initSt;
|
||||
Expression condition;
|
||||
Statement incrementSt;
|
||||
BlockStatement body;
|
||||
|
||||
ForSt()
|
||||
{
|
||||
type = AstType::ForSt;
|
||||
}
|
||||
ForSt(Statement _initSt, Expression _condition, Statement _incrementSt, BlockStatement _body) :
|
||||
initSt(std::move(_initSt)),
|
||||
condition(std::move(_condition)),
|
||||
incrementSt(std::move(_incrementSt)),
|
||||
body(std::move(_body))
|
||||
{
|
||||
type = AstType::ForSt;
|
||||
}
|
||||
};
|
||||
|
||||
using For = std::shared_ptr<ForSt>;
|
||||
};
|
||||
45
src/Ast/Statements/FunctionDefSt.hpp
Normal file
45
src/Ast/Statements/FunctionDefSt.hpp
Normal file
@@ -0,0 +1,45 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
#include <Ast/functionParameters.hpp>
|
||||
|
||||
#include <Value/value.hpp>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
/*
|
||||
func greet(greeting, name:String, age:Int, split:String=":") -> Null
|
||||
{
|
||||
io.println("{}, {}{}{}", greeting, name, split, age);
|
||||
}
|
||||
|
||||
`greeting`, `name`, `age` -> positional parameters
|
||||
`split` -> default parameter
|
||||
*/
|
||||
|
||||
class FunctionDefSt final : public StatementAst // for definition
|
||||
{
|
||||
public:
|
||||
FString name;
|
||||
FunctionParameters paras;
|
||||
bool isPublic;
|
||||
FString retType;
|
||||
BlockStatement body;
|
||||
FunctionDefSt() :
|
||||
retType(ValueType::Null.name)
|
||||
{
|
||||
type = AstType::FunctionDefSt;
|
||||
}
|
||||
FunctionDefSt(FString _name, FunctionParameters _paras, bool _isPublic, FString _retType, BlockStatement _body)
|
||||
{
|
||||
type = AstType::FunctionDefSt;
|
||||
|
||||
name = std::move(_name);
|
||||
paras = std::move(_paras);
|
||||
isPublic = _isPublic;
|
||||
retType = std::move(_retType);
|
||||
body = std::move(_body);
|
||||
}
|
||||
};
|
||||
using FunctionDef = std::shared_ptr<FunctionDefSt>;
|
||||
}; // namespace Fig
|
||||
68
src/Ast/Statements/IfSt.hpp
Normal file
68
src/Ast/Statements/IfSt.hpp
Normal file
@@ -0,0 +1,68 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
class ElseSt final : public StatementAst
|
||||
{
|
||||
public:
|
||||
BlockStatement body;
|
||||
ElseSt()
|
||||
{
|
||||
type = AstType::ElseSt;
|
||||
}
|
||||
ElseSt(BlockStatement _body) :
|
||||
body(_body)
|
||||
{
|
||||
type = AstType::ElseSt;
|
||||
}
|
||||
virtual FString toString() override
|
||||
{
|
||||
return FString(std::format("<Else Ast at {}:{}>", aai.line, aai.column));
|
||||
}
|
||||
};
|
||||
using Else = std::shared_ptr<ElseSt>;
|
||||
class ElseIfSt final : public StatementAst
|
||||
{
|
||||
public:
|
||||
Expression condition;
|
||||
BlockStatement body;
|
||||
ElseIfSt()
|
||||
{
|
||||
type = AstType::ElseIfSt;
|
||||
}
|
||||
ElseIfSt(Expression _condition,
|
||||
BlockStatement _body) :
|
||||
condition(_condition), body(_body)
|
||||
{
|
||||
type = AstType::ElseIfSt;
|
||||
}
|
||||
virtual FString toString() override
|
||||
{
|
||||
return FString(std::format("<ElseIf Ast at {}:{}>", aai.line, aai.column));
|
||||
}
|
||||
};
|
||||
using ElseIf = std::shared_ptr<ElseIfSt>;
|
||||
class IfSt final : public StatementAst
|
||||
{
|
||||
public:
|
||||
Expression condition;
|
||||
BlockStatement body;
|
||||
std::vector<ElseIf> elifs;
|
||||
Else els;
|
||||
IfSt()
|
||||
{
|
||||
type = AstType::IfSt;
|
||||
}
|
||||
IfSt(Expression _condition,
|
||||
BlockStatement _body,
|
||||
std::vector<ElseIf> _elifs,
|
||||
Else _els) :
|
||||
condition(_condition), body(_body), elifs(_elifs), els(_els)
|
||||
{
|
||||
type = AstType::IfSt;
|
||||
}
|
||||
};
|
||||
using If = std::shared_ptr<IfSt>;
|
||||
}; // namespace Fig
|
||||
0
src/Ast/Statements/ImplementSt.hpp
Normal file
0
src/Ast/Statements/ImplementSt.hpp
Normal file
44
src/Ast/Statements/StructDefSt.hpp
Normal file
44
src/Ast/Statements/StructDefSt.hpp
Normal file
@@ -0,0 +1,44 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
#include <Ast/AccessModifier.hpp>
|
||||
|
||||
#include <vector>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
|
||||
struct StructDefField
|
||||
{
|
||||
AccessModifier am;
|
||||
FString fieldName;
|
||||
FString tiName;
|
||||
Expression defaultValueExpr;
|
||||
|
||||
StructDefField() {}
|
||||
StructDefField(AccessModifier _am, FString _fieldName, FString _tiName, Expression _defaultValueExpr) :
|
||||
am(std::move(_am)), fieldName(std::move(_fieldName)), tiName(std::move(_tiName)), defaultValueExpr(std::move(_defaultValueExpr))
|
||||
{
|
||||
}
|
||||
};
|
||||
class StructDefSt final : public StatementAst
|
||||
{
|
||||
public:
|
||||
bool isPublic;
|
||||
const FString name;
|
||||
const std::vector<StructDefField> fields; // field name (:type name = default value expression)
|
||||
// name / name: String / name: String = "Fig"
|
||||
const BlockStatement body;
|
||||
StructDefSt()
|
||||
{
|
||||
type = AstType::StructSt;
|
||||
}
|
||||
StructDefSt(bool _isPublic, FString _name, std::vector<StructDefField> _fields, BlockStatement _body) :
|
||||
isPublic(std::move(_isPublic)), name(std::move(_name)), fields(std::move(_fields)), body(std::move(_body))
|
||||
{
|
||||
type = AstType::StructSt;
|
||||
}
|
||||
};
|
||||
|
||||
using StructDef = std::shared_ptr<StructDefSt>;
|
||||
}; // namespace Fig
|
||||
34
src/Ast/Statements/VarDef.hpp
Normal file
34
src/Ast/Statements/VarDef.hpp
Normal file
@@ -0,0 +1,34 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
#include <Value/Type.hpp>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
class VarDefAst final : public StatementAst
|
||||
{
|
||||
public:
|
||||
bool isPublic;
|
||||
bool isConst;
|
||||
FString name;
|
||||
FString typeName;
|
||||
Expression expr;
|
||||
|
||||
VarDefAst() :
|
||||
typeName(ValueType::Any.name)
|
||||
{
|
||||
type = AstType::VarDefSt;
|
||||
}
|
||||
VarDefAst(bool _isPublic, bool _isConst, FString _name, FString _info, Expression _expr) :
|
||||
typeName(std::move(_info))
|
||||
{
|
||||
type = AstType::VarDefSt;
|
||||
isPublic = _isPublic;
|
||||
isConst = _isConst;
|
||||
name = std::move(_name);
|
||||
expr = std::move(_expr);
|
||||
}
|
||||
};
|
||||
|
||||
using VarDef = std::shared_ptr<VarDefAst>;
|
||||
} // namespace Fig
|
||||
26
src/Ast/Statements/WhileSt.hpp
Normal file
26
src/Ast/Statements/WhileSt.hpp
Normal file
@@ -0,0 +1,26 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
class WhileSt final : public StatementAst
|
||||
{
|
||||
public:
|
||||
Expression condition;
|
||||
BlockStatement body;
|
||||
|
||||
WhileSt()
|
||||
{
|
||||
type = AstType::WhileSt;
|
||||
}
|
||||
|
||||
WhileSt(Expression _condition, BlockStatement _body)
|
||||
: condition(_condition), body(_body)
|
||||
{
|
||||
type = AstType::WhileSt;
|
||||
}
|
||||
};
|
||||
|
||||
using While = std::shared_ptr<WhileSt>;
|
||||
};
|
||||
26
src/Ast/ast.hpp
Normal file
26
src/Ast/ast.hpp
Normal file
@@ -0,0 +1,26 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
#include <Ast/AccessModifier.hpp>
|
||||
#include <Ast/functionParameters.hpp>
|
||||
|
||||
#include <Ast/Expressions/BinaryExpr.hpp>
|
||||
#include <Ast/Expressions/ContainerInitExprs.hpp>
|
||||
#include <Ast/Expressions/FunctionCall.hpp>
|
||||
#include <Ast/Expressions/FunctionLiteralExpr.hpp>
|
||||
#include <Ast/Expressions/InitExpr.hpp>
|
||||
#include <Ast/Expressions/PostfixExprs.hpp>
|
||||
#include <Ast/Expressions/TernaryExpr.hpp>
|
||||
#include <Ast/Expressions/UnaryExpr.hpp>
|
||||
#include <Ast/Expressions/ValueExpr.hpp>
|
||||
#include <Ast/Expressions/VarExpr.hpp>
|
||||
|
||||
#include <Ast/Statements/VarDef.hpp>
|
||||
#include <Ast/Statements/WhileSt.hpp>
|
||||
#include <Ast/Statements/StructDefSt.hpp>
|
||||
#include <Ast/Statements/IfSt.hpp>
|
||||
#include <Ast/Statements/ImplementSt.hpp>
|
||||
#include <Ast/Statements/FunctionDefSt.hpp>
|
||||
#include <Ast/Statements/ControlSt.hpp>
|
||||
#include <Ast/Statements/ExpressionStmt.hpp>
|
||||
#include <Ast/Statements/ForSt.hpp>
|
||||
344
src/Ast/astBase.hpp
Normal file
344
src/Ast/astBase.hpp
Normal file
@@ -0,0 +1,344 @@
|
||||
#pragma once
|
||||
|
||||
#include <Token/token.hpp>
|
||||
#include <Core/fig_string.hpp>
|
||||
|
||||
#include <format>
|
||||
#include <unordered_map>
|
||||
#include <memory>
|
||||
#include <cstdint>
|
||||
#include <unordered_set>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
enum class AstType : uint8_t
|
||||
{
|
||||
/* Base Class */
|
||||
_AstBase,
|
||||
StatementBase,
|
||||
ExpressionBase,
|
||||
/* Expression */
|
||||
ValueExpr,
|
||||
VarExpr,
|
||||
LambdaExpr,
|
||||
UnaryExpr,
|
||||
BinaryExpr,
|
||||
TernaryExpr,
|
||||
|
||||
/* Postfix */
|
||||
MemberExpr, // a.b
|
||||
IndexExpr, // a[b]
|
||||
FunctionCall, // a()
|
||||
|
||||
/* Literals */
|
||||
ListExpr, // [1, "2", 3
|
||||
TupleExpr, // (1, 2, 3)
|
||||
MapExpr, // {a: 1}
|
||||
InitExpr, // struct{"123", 456}
|
||||
FunctionLiteralExpr,
|
||||
|
||||
/* Statement */
|
||||
BlockStatement,
|
||||
ExpressionStmt,
|
||||
|
||||
VarDefSt,
|
||||
FunctionDefSt,
|
||||
StructSt,
|
||||
ImplementSt,
|
||||
|
||||
IfSt,
|
||||
ElseSt,
|
||||
ElseIfSt,
|
||||
|
||||
VarAssignSt,
|
||||
WhileSt,
|
||||
ForSt,
|
||||
ReturnSt,
|
||||
BreakSt,
|
||||
ContinueSt,
|
||||
};
|
||||
|
||||
// static const std::unordered_map<AstType, FString> astTypeToString{
|
||||
// /* Base Class */
|
||||
// {AstType::_AstBase, FString(u8"Ast")},
|
||||
// {AstType::StatementBase, FString(u8"Statement")},
|
||||
// {AstType::ExpressionBase, FString(u8"Expression")},
|
||||
// /* Expression */
|
||||
// {AstType::ValueExpr, FString(u8"ValueExpr")},
|
||||
// {AstType::LambdaExpr, FString(u8"LambdaExpr")},
|
||||
// {AstType::UnaryExpr, FString(u8"UnaryExpr")},
|
||||
// {AstType::BinaryExpr, FString(u8"BinaryExpr")},
|
||||
// {AstType::TernaryExpr, FString(u8"TernaryExpr")},
|
||||
|
||||
// {AstType::InitExpr, FString(u8"InitExpr")},
|
||||
|
||||
// /* Statement */
|
||||
// {AstType::BlockStatement, FString(u8"BlockStatement")},
|
||||
|
||||
// {AstType::VarDefSt, FString(u8"VarSt")},
|
||||
// {AstType::FunctionDefSt, FString(u8"FunctionDefSt")},
|
||||
// {AstType::StructSt, FString(u8"StructSt")},
|
||||
// {AstType::ImplementSt, FString(u8"ImplementSt")},
|
||||
|
||||
// {AstType::IfSt, FString(u8"IfSt")},
|
||||
// {AstType::ElseSt, FString(u8"ElseSt")},
|
||||
// {AstType::ElseIfSt, FString(u8"ElseIfSt")},
|
||||
// {AstType::VarAssignSt, FString(u8"VarAssignSt")},
|
||||
// {AstType::WhileSt, FString(u8"WhileSt")},
|
||||
// {AstType::ReturnSt, FString(u8"ReturnSt")},
|
||||
// {AstType::BreakSt, FString(u8"BreakSt")},
|
||||
// {AstType::ContinueSt, FString(u8"ContinueSt")},
|
||||
// };
|
||||
|
||||
struct AstAddressInfo
|
||||
{
|
||||
size_t line, column;
|
||||
};
|
||||
|
||||
class _AstBase
|
||||
{
|
||||
protected:
|
||||
AstType type;
|
||||
AstAddressInfo aai;
|
||||
|
||||
public:
|
||||
_AstBase(const _AstBase &) = default;
|
||||
_AstBase(_AstBase &&) = default;
|
||||
|
||||
_AstBase &operator=(const _AstBase &) = default;
|
||||
_AstBase &operator=(_AstBase &&) = default;
|
||||
|
||||
_AstBase() {}
|
||||
|
||||
void setAAI(AstAddressInfo _aai)
|
||||
{
|
||||
aai = std::move(_aai);
|
||||
}
|
||||
|
||||
virtual FString typeName()
|
||||
{
|
||||
return FString::fromStringView(
|
||||
FStringView::fromBasicStringView(magic_enum::enum_name(type)));
|
||||
}
|
||||
virtual FString toString()
|
||||
{
|
||||
return FString(std::format("<Base Ast '{}' at {}:{}>", typeName().toBasicString(), aai.line, aai.column));
|
||||
}
|
||||
|
||||
AstAddressInfo getAAI()
|
||||
{
|
||||
return aai;
|
||||
}
|
||||
|
||||
AstType getType()
|
||||
{
|
||||
return type;
|
||||
}
|
||||
};
|
||||
|
||||
class StatementAst : public _AstBase
|
||||
{
|
||||
public:
|
||||
using _AstBase::_AstBase;
|
||||
using _AstBase::operator=;
|
||||
StatementAst()
|
||||
{
|
||||
type = AstType::StatementBase;
|
||||
}
|
||||
|
||||
virtual FString toString() override
|
||||
{
|
||||
return FString(std::format("<Stmt Ast '{}' at {}:{}>", typeName().toBasicString(), aai.line, aai.column));
|
||||
}
|
||||
};
|
||||
|
||||
class EofStmt final : public StatementAst
|
||||
{
|
||||
public:
|
||||
EofStmt()
|
||||
{
|
||||
type = AstType::StatementBase;
|
||||
}
|
||||
|
||||
virtual FString toString() override
|
||||
{
|
||||
return FString(std::format("<EOF Stmt at {}:{}>", aai.line, aai.column));
|
||||
}
|
||||
};
|
||||
|
||||
class ExpressionAst : public _AstBase
|
||||
{
|
||||
public:
|
||||
using _AstBase::_AstBase;
|
||||
using _AstBase::operator=;
|
||||
ExpressionAst()
|
||||
{
|
||||
type = AstType::ExpressionBase;
|
||||
}
|
||||
|
||||
virtual FString toString() override
|
||||
{
|
||||
return FString(std::format("<Expr Ast '{}' at {}:{}>", typeName().toBasicString(), aai.line, aai.column));
|
||||
}
|
||||
};
|
||||
enum class Operator : uint8_t
|
||||
{
|
||||
LeftParen,
|
||||
RightParen,
|
||||
|
||||
// 算术
|
||||
Add, // +
|
||||
Subtract, // -
|
||||
Multiply, // *
|
||||
Divide, // /
|
||||
Modulo, // %
|
||||
Power, // **
|
||||
|
||||
// 逻辑
|
||||
And, // and / &&
|
||||
Or, // or / ||
|
||||
Not, // not / !
|
||||
|
||||
// 比较
|
||||
Equal, // ==
|
||||
NotEqual, // !=
|
||||
Less, // <
|
||||
LessEqual, // <=
|
||||
Greater, // >
|
||||
GreaterEqual, // >=
|
||||
|
||||
// 三目
|
||||
TernaryCond,
|
||||
|
||||
// 位运算
|
||||
BitAnd, // &
|
||||
BitOr, // |
|
||||
BitXor, // ^
|
||||
BitNot, // ~
|
||||
ShiftLeft, // <<
|
||||
ShiftRight, // >>
|
||||
|
||||
// 赋值表达式
|
||||
Assign, // =
|
||||
// Walrus, // :=
|
||||
};
|
||||
|
||||
static const std::unordered_set<Operator> unaryOps{
|
||||
Operator::Not,
|
||||
Operator::Subtract,
|
||||
Operator::BitNot,
|
||||
};
|
||||
static const std::unordered_set<Operator> binaryOps{
|
||||
Operator::Add,
|
||||
Operator::Subtract,
|
||||
Operator::Multiply,
|
||||
Operator::Divide,
|
||||
Operator::Modulo,
|
||||
Operator::Power,
|
||||
Operator::And,
|
||||
Operator::Or,
|
||||
|
||||
Operator::Equal,
|
||||
Operator::NotEqual,
|
||||
Operator::Less,
|
||||
Operator::LessEqual,
|
||||
Operator::Greater,
|
||||
Operator::GreaterEqual,
|
||||
|
||||
Operator::BitAnd,
|
||||
Operator::BitOr,
|
||||
Operator::BitXor,
|
||||
Operator::BitNot,
|
||||
Operator::ShiftLeft,
|
||||
Operator::ShiftRight,
|
||||
|
||||
// Operator::Walrus,
|
||||
// Operator::Dot
|
||||
};
|
||||
static const std::unordered_set<Operator> ternaryOps{Operator::TernaryCond};
|
||||
|
||||
static const std::unordered_map<TokenType, Operator> TokenToOp{
|
||||
// 算术
|
||||
{TokenType::Plus, Operator::Add},
|
||||
{TokenType::Minus, Operator::Subtract},
|
||||
{TokenType::Asterisk, Operator::Multiply},
|
||||
{TokenType::Slash, Operator::Divide},
|
||||
{TokenType::Percent, Operator::Modulo},
|
||||
{TokenType::Power, Operator::Power},
|
||||
|
||||
// 逻辑
|
||||
{TokenType::And, Operator::And},
|
||||
{TokenType::DoubleAmpersand, Operator::And},
|
||||
{TokenType::Or, Operator::Or},
|
||||
{TokenType::DoublePipe, Operator::Or},
|
||||
{TokenType::Not, Operator::Not},
|
||||
|
||||
// 比较
|
||||
{TokenType::Equal, Operator::Equal},
|
||||
{TokenType::NotEqual, Operator::NotEqual},
|
||||
{TokenType::Less, Operator::Less},
|
||||
{TokenType::LessEqual, Operator::LessEqual},
|
||||
{TokenType::Greater, Operator::Greater},
|
||||
{TokenType::GreaterEqual, Operator::GreaterEqual},
|
||||
|
||||
// 三目
|
||||
{TokenType::Question, Operator::TernaryCond},
|
||||
|
||||
// 位运算
|
||||
{TokenType::Ampersand, Operator::BitAnd},
|
||||
{TokenType::Pipe, Operator::BitOr},
|
||||
{TokenType::Caret, Operator::BitXor},
|
||||
{TokenType::Tilde, Operator::BitNot},
|
||||
{TokenType::ShiftLeft, Operator::ShiftLeft},
|
||||
{TokenType::ShiftRight, Operator::ShiftRight},
|
||||
|
||||
// 赋值表达式
|
||||
{TokenType::Assign, Operator::Assign},
|
||||
// {TokenType::Walrus, Operator::Walrus},
|
||||
}; // :=
|
||||
|
||||
inline bool isOpUnary(Operator op)
|
||||
{
|
||||
return unaryOps.contains(op);
|
||||
}
|
||||
inline bool isOpBinary(Operator op)
|
||||
{
|
||||
return binaryOps.contains(op);
|
||||
}
|
||||
inline bool isOpTernary(Operator op)
|
||||
{
|
||||
return ternaryOps.contains(op);
|
||||
}
|
||||
|
||||
using AstBase = std::shared_ptr<_AstBase>;
|
||||
using Statement = std::shared_ptr<StatementAst>;
|
||||
using Expression = std::shared_ptr<ExpressionAst>;
|
||||
using Eof = std::shared_ptr<EofStmt>;
|
||||
|
||||
class BlockStatementAst : public StatementAst
|
||||
{
|
||||
public:
|
||||
std::vector<Statement> stmts;
|
||||
BlockStatementAst()
|
||||
{
|
||||
type = AstType::BlockStatement;
|
||||
}
|
||||
BlockStatementAst(std::vector<Statement> _stmts) :
|
||||
stmts(std::move(_stmts))
|
||||
{
|
||||
type = AstType::BlockStatement;
|
||||
}
|
||||
virtual FString typeName() override
|
||||
{
|
||||
return FString(u8"BlockStatement");
|
||||
}
|
||||
virtual FString toString() override
|
||||
{
|
||||
return FString(std::format("<StmtAst '{}' at {}:{}>", typeName().toBasicString(), aai.line, aai.column));
|
||||
}
|
||||
virtual ~BlockStatementAst() = default;
|
||||
};
|
||||
|
||||
using BlockStatement = std::shared_ptr<BlockStatementAst>;
|
||||
// static BlockStatement builtinEmptyBlockSt(new BlockStatementAst());
|
||||
}; // namespace Fig::Ast
|
||||
39
src/Ast/functionParameters.hpp
Normal file
39
src/Ast/functionParameters.hpp
Normal file
@@ -0,0 +1,39 @@
|
||||
#pragma once
|
||||
|
||||
#include <Ast/astBase.hpp>
|
||||
#include <Value/Type.hpp>
|
||||
#include <Core/fig_string.hpp>
|
||||
|
||||
namespace Fig::Ast
|
||||
{
|
||||
struct FunctionParameters // for define
|
||||
{
|
||||
/*
|
||||
Positional Parameters:
|
||||
fun test(pp1, pp2: Int)
|
||||
Default Parameters:
|
||||
fun test2(dp1 = 10, dp2:String = "default parameter 2")
|
||||
*/
|
||||
|
||||
using PosParasType = std::vector<std::pair<FString, FString>>;
|
||||
using DefParasType = std::vector<std::pair<FString, std::pair<FString, Expression>>>;
|
||||
|
||||
PosParasType posParas;
|
||||
DefParasType defParas; // default parameters
|
||||
|
||||
FunctionParameters()
|
||||
{
|
||||
|
||||
}
|
||||
FunctionParameters(PosParasType _posParas, DefParasType _defParas)
|
||||
{
|
||||
posParas = std::move(_posParas);
|
||||
defParas = std::move(_defParas);
|
||||
}
|
||||
|
||||
size_t size() const
|
||||
{
|
||||
return posParas.size() + defParas.size();
|
||||
}
|
||||
};
|
||||
}
|
||||
Reference in New Issue
Block a user