revamping...
This commit is contained in:
parent
385f2dd53e
commit
f8c17803c3
6
compiler/.vscode/settings.json
vendored
6
compiler/.vscode/settings.json
vendored
@ -1,7 +1,7 @@
|
||||
{
|
||||
"C_Cpp.default.includePath": [
|
||||
"${workspaceFolder}/include/",
|
||||
"/usr/include/antlr4-runtime",
|
||||
"${workspaceFolder}/build/antlr4_runtime/src/antlr4_runtime/runtime/Cpp/runtime/src",
|
||||
],
|
||||
"files.associations": {
|
||||
"*.embeddedhtml": "html",
|
||||
@ -77,6 +77,8 @@
|
||||
"typeinfo": "cpp",
|
||||
"valarray": "cpp",
|
||||
"variant": "cpp",
|
||||
"*.inc": "cpp"
|
||||
"*.inc": "cpp",
|
||||
"source_location": "cpp",
|
||||
"text_encoding": "cpp"
|
||||
}
|
||||
}
|
@ -17,7 +17,7 @@ list(APPEND CMAKE_MODULE_PATH ${CMAKE_SOURCE_DIR}/cmake)
|
||||
include(ExternalAntlr4Cpp)
|
||||
|
||||
find_package(
|
||||
Boost 1.84 REQUIRED
|
||||
Boost 1.83 REQUIRED
|
||||
COMPONENTS json
|
||||
)
|
||||
|
||||
|
@ -18,7 +18,7 @@ endif()
|
||||
|
||||
# Ensure that the include dir already exists at configure time (to avoid cmake erroring
|
||||
# on non-existent include dirs)
|
||||
file(MAKE_DIRECTORY "${ANTLR4_INCLUDE_DIRS}")
|
||||
file(MAKE_DIRECTORY ${ANTLR4_INCLUDE_DIRS})
|
||||
|
||||
if(${CMAKE_GENERATOR} MATCHES "Visual Studio.*")
|
||||
set(ANTLR4_OUTPUT_DIR ${ANTLR4_ROOT}/runtime/Cpp/runtime/$(Configuration))
|
||||
|
27
compiler/include/AST/AST.h
Normal file
27
compiler/include/AST/AST.h
Normal file
@ -0,0 +1,27 @@
|
||||
#pragma once
|
||||
|
||||
#include "Base.h"
|
||||
|
||||
#include "Expr/BinExpr.h"
|
||||
#include "Expr/CallExpr.h"
|
||||
#include "Expr/CastExpr.h"
|
||||
#include "Expr/Identifier.h"
|
||||
#include "Expr/LambdaExpr.h"
|
||||
#include "Expr/UnExpr.h"
|
||||
#include "Expr/Value.h"
|
||||
|
||||
#include "Module/Import.h"
|
||||
#include "Module/Module.h"
|
||||
|
||||
#include "Stmt/AssignStmt.h"
|
||||
#include "Stmt/ExprStmt.h"
|
||||
#include "Stmt/FnDecl.h"
|
||||
#include "Stmt/IfStmt.h"
|
||||
#include "Stmt/RetStmt.h"
|
||||
#include "Stmt/VarDecl.h"
|
||||
#include "Stmt/WhileStmt.h"
|
||||
|
||||
#include "Type/FunctionType.h"
|
||||
#include "Type/PrimitiveType.h"
|
||||
|
||||
#include "TypeName/PrimitiveTypeName.h"
|
@ -1,5 +1,6 @@
|
||||
#pragma once
|
||||
|
||||
#include <any>
|
||||
#include <boost/json/serialize.hpp>
|
||||
#include <exception>
|
||||
#include <functional>
|
||||
@ -11,42 +12,75 @@
|
||||
|
||||
#include <boost/json.hpp>
|
||||
|
||||
#define LOC_ARG const Location &location
|
||||
#define LOC_ARG const SourceRange &sourceRange
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
class Location {
|
||||
class BinExpr;
|
||||
class CallExpr;
|
||||
class CastExpr;
|
||||
class Identifier;
|
||||
class LambdaExpr;
|
||||
class UnExpr;
|
||||
class IntValue;
|
||||
class FloatValue;
|
||||
|
||||
class Import;
|
||||
class Module;
|
||||
|
||||
class AssignStmt;
|
||||
class ExprStmt;
|
||||
class FnParam;
|
||||
class FnDecl;
|
||||
class IfStmt;
|
||||
class RetStmt;
|
||||
class VarDecl;
|
||||
class WhileStmt;
|
||||
|
||||
class PrimitiveTypeName;
|
||||
|
||||
class ASTVisitor {
|
||||
public:
|
||||
Location(const std::string &file, std::pair<size_t, size_t> start,
|
||||
std::pair<size_t, size_t> end)
|
||||
: file(file), start(start), end(end) {}
|
||||
virtual ~ASTVisitor() = default;
|
||||
|
||||
const std::string file;
|
||||
const std::pair<size_t, size_t> start, end;
|
||||
virtual std::any visit(BinExpr &binExpr, std::any param) = 0;
|
||||
virtual std::any visit(CallExpr &callExpr, std::any param) = 0;
|
||||
virtual std::any visit(CastExpr &castExpr, std::any param) = 0;
|
||||
virtual std::any visit(Identifier &identifier, std::any param) = 0;
|
||||
virtual std::any visit(LambdaExpr &lambdaExpr, std::any param) = 0;
|
||||
virtual std::any visit(UnExpr &unExpr, std::any param) = 0;
|
||||
virtual std::any visit(IntValue &intValue, std::any param) = 0;
|
||||
virtual std::any visit(FloatValue &floatValue, std::any param) = 0;
|
||||
|
||||
static Location json() { return Location("<json>", {-1, -1}, {-1, -1}); };
|
||||
virtual std::any visit(Import &import, std::any param) = 0;
|
||||
virtual std::any visit(Module &module, std::any param) = 0;
|
||||
|
||||
virtual std::any visit(AssignStmt &assignStmt, std::any param) = 0;
|
||||
virtual std::any visit(ExprStmt &exprStmt, std::any param) = 0;
|
||||
virtual std::any visit(FnParam &fnParam, std::any param) = 0;
|
||||
virtual std::any visit(FnDecl &fnDecl, std::any param) = 0;
|
||||
virtual std::any visit(IfStmt &ifStmt, std::any param) = 0;
|
||||
virtual std::any visit(RetStmt &retStmt, std::any param) = 0;
|
||||
virtual std::any visit(VarDecl &varDecl, std::any param) = 0;
|
||||
virtual std::any visit(WhileStmt &whileStmt, std::any param) = 0;
|
||||
|
||||
virtual std::any visit(PrimitiveTypeName &primitiveTypeName,
|
||||
std::any param) = 0;
|
||||
};
|
||||
|
||||
class ASTNode {
|
||||
public:
|
||||
ASTNode(LOC_ARG) : location(location) {}
|
||||
virtual ~ASTNode() = default;
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
||||
|
||||
const Location location;
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
class Jsonable {
|
||||
public:
|
||||
virtual ~Jsonable() = default;
|
||||
|
||||
virtual boost::json::value toJson() = 0;
|
||||
|
||||
virtual std::string toJsonString() {
|
||||
return boost::json::serialize(toJson());
|
||||
}
|
||||
|
||||
static std::unique_ptr<ASTNode> fromJson(boost::json::value json);
|
||||
|
||||
virtual bool isExpr() { return false; }
|
||||
virtual bool isStmt() { return false; }
|
||||
virtual bool isType() { return false; }
|
||||
|
||||
protected:
|
||||
template <class CurrNode>
|
||||
static inline boost::json::value getJsonProperty(boost::json::value json,
|
||||
@ -88,7 +122,7 @@ protected:
|
||||
std::string property) {
|
||||
auto arr = getJsonProperty<CurrNode>(json, property).as_array();
|
||||
|
||||
std::vector<std::unique_ptr<SubNode>> result;
|
||||
std::vector<SubNode *> result;
|
||||
for (auto &el : arr) {
|
||||
result.push_back(SubNode::fromJson(el));
|
||||
}
|
||||
@ -97,31 +131,80 @@ protected:
|
||||
}
|
||||
};
|
||||
|
||||
class SourceRange {
|
||||
public:
|
||||
SourceRange(const std::string &file, const std::string &text,
|
||||
std::pair<size_t, size_t> start, std::pair<size_t, size_t> end)
|
||||
: file(file), text(text), start(start), end(end) {}
|
||||
|
||||
const std::string file, text;
|
||||
const std::pair<size_t, size_t> start, end;
|
||||
|
||||
static SourceRange unknown() {
|
||||
return SourceRange("<?>", "<?>", {-1, -1}, {-1, -1});
|
||||
};
|
||||
|
||||
static SourceRange json() {
|
||||
return SourceRange("<json>", "<?>", {-1, -1}, {-1, -1});
|
||||
};
|
||||
};
|
||||
|
||||
class ASTNode : public Jsonable {
|
||||
public:
|
||||
ASTNode(LOC_ARG) : Jsonable(), sourceRange(sourceRange) {}
|
||||
virtual ~ASTNode() = default;
|
||||
|
||||
const SourceRange sourceRange;
|
||||
|
||||
virtual std::string toJsonString() {
|
||||
return boost::json::serialize(toJson(), {});
|
||||
}
|
||||
|
||||
static ASTNode *fromJson(boost::json::value json);
|
||||
|
||||
virtual bool isExpr() { return false; }
|
||||
virtual bool isStmt() { return false; }
|
||||
virtual bool isTypeName() { return false; }
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) = 0;
|
||||
};
|
||||
|
||||
class Expr : public ASTNode {
|
||||
public:
|
||||
Expr(LOC_ARG) : ASTNode(location) {}
|
||||
Expr(LOC_ARG) : ASTNode(sourceRange) {}
|
||||
virtual ~Expr() = default;
|
||||
|
||||
static std::unique_ptr<Expr> fromJson(boost::json::value json);
|
||||
static Expr *fromJson(boost::json::value json);
|
||||
|
||||
virtual bool isExpr() override { return true; }
|
||||
};
|
||||
|
||||
class Stmt : public ASTNode {
|
||||
public:
|
||||
Stmt(LOC_ARG) : ASTNode(location) {}
|
||||
Stmt(LOC_ARG) : ASTNode(sourceRange) {}
|
||||
virtual ~Stmt() = default;
|
||||
|
||||
static std::unique_ptr<Stmt> fromJson(boost::json::value json);
|
||||
static Stmt *fromJson(boost::json::value json);
|
||||
|
||||
virtual bool isStmt() override { return true; }
|
||||
};
|
||||
|
||||
class Type : public ASTNode {
|
||||
class TypeName : public ASTNode {
|
||||
public:
|
||||
Type(LOC_ARG) : ASTNode(location) {}
|
||||
TypeName(LOC_ARG) : ASTNode(sourceRange) {}
|
||||
virtual ~TypeName() = default;
|
||||
|
||||
static std::unique_ptr<Type> fromJson(boost::json::value json);
|
||||
static TypeName *fromJson(boost::json::value json);
|
||||
|
||||
virtual bool isType() override { return true; }
|
||||
virtual bool isTypeName() override { return true; }
|
||||
};
|
||||
|
||||
class Type : public Jsonable {
|
||||
public:
|
||||
Type() : Jsonable() {}
|
||||
virtual ~Type() = default;
|
||||
|
||||
static Type *fromJson(boost::json::value json);
|
||||
};
|
||||
|
||||
} // namespace ast
|
||||
|
@ -1,29 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "Base.h"
|
||||
|
||||
#include "Expr/BinExpr.h"
|
||||
#include "Expr/Block.h"
|
||||
#include "Expr/Call.h"
|
||||
#include "Expr/Closure.h"
|
||||
#include "Expr/Identifier.h"
|
||||
#include "Expr/PropExpr.h"
|
||||
#include "Expr/Tuple.h"
|
||||
#include "Expr/UnaryExpr.h"
|
||||
#include "Expr/Value.h"
|
||||
|
||||
#include "Stmt/ExprStmt.h"
|
||||
#include "Stmt/FnDef.h"
|
||||
#include "Stmt/TraitAlias.h"
|
||||
#include "Stmt/TraitDef.h"
|
||||
#include "Stmt/TypeAlias.h"
|
||||
#include "Stmt/TypeDef.h"
|
||||
#include "Stmt/ValDecl.h"
|
||||
|
||||
#include "Type/Closure.h"
|
||||
#include "Type/Generic.h"
|
||||
#include "Type/Named.h"
|
||||
#include "Type/Tuple.h"
|
||||
|
||||
#include "Module/Import.h"
|
||||
#include "Module/Module.h"
|
@ -1,37 +1,44 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <iomanip>
|
||||
#include <memory>
|
||||
#include <sstream>
|
||||
#include <string>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
class BinExpr : public Expr {
|
||||
const std::string op;
|
||||
const std::unique_ptr<Expr> left, right;
|
||||
enum BinOp {
|
||||
ADD,
|
||||
SUB,
|
||||
MUL,
|
||||
DIV,
|
||||
MOD,
|
||||
|
||||
public:
|
||||
BinExpr(LOC_ARG, std::unique_ptr<Expr> &left, const std::string &op,
|
||||
std::unique_ptr<Expr> &right)
|
||||
: Expr(location), left(std::move(left)), op(op), right(std::move(right)) {
|
||||
}
|
||||
EQ,
|
||||
NE,
|
||||
GT,
|
||||
GE,
|
||||
LT,
|
||||
LE,
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<BinExpr> fromJson(boost::json::value json);
|
||||
AND,
|
||||
OR,
|
||||
};
|
||||
|
||||
class PrefExpr : public Expr {
|
||||
const std::unique_ptr<Expr> expr;
|
||||
class BinExpr : public Expr {
|
||||
const BinOp op;
|
||||
const std::shared_ptr<Expr> lhs, rhs;
|
||||
|
||||
public:
|
||||
PrefExpr(LOC_ARG, std::unique_ptr<Expr> &expr)
|
||||
: Expr(location), expr(std::move(expr)) {}
|
||||
BinExpr(LOC_ARG, const BinOp op, Expr *lhs, Expr *rhs)
|
||||
: Expr(sourceRange), op(op), lhs(lhs), rhs(rhs) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<PrefExpr> fromJson(boost::json::value json);
|
||||
static BinExpr *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace ast
|
||||
|
@ -1,25 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <sstream>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
class BlockExpr : public Expr {
|
||||
const std::vector<std::unique_ptr<Stmt>> stmts;
|
||||
const std::unique_ptr<Expr> result;
|
||||
|
||||
public:
|
||||
BlockExpr(LOC_ARG, std::vector<std::unique_ptr<Stmt>> &stmts,
|
||||
std::unique_ptr<Expr> &result)
|
||||
: Expr(location), stmts(std::move(stmts)), result(std::move(result)) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<BlockExpr> fromJson(boost::json::value json);
|
||||
};
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,25 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <sstream>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
class CallExpr : public Expr {
|
||||
const std::unique_ptr<Expr> callee;
|
||||
const std::vector<std::unique_ptr<Expr>> args;
|
||||
|
||||
public:
|
||||
CallExpr(LOC_ARG, std::unique_ptr<Expr> &callee,
|
||||
std::vector<std::unique_ptr<Expr>> &args)
|
||||
: Expr(location), callee(std::move(callee)), args(std::move(args)) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<CallExpr> fromJson(boost::json::value json);
|
||||
};
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
31
compiler/include/AST/Expr/CallExpr.h
Normal file
31
compiler/include/AST/Expr/CallExpr.h
Normal file
@ -0,0 +1,31 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
class CallExpr : public Expr {
|
||||
const std::shared_ptr<Expr> callee;
|
||||
std::vector<std::shared_ptr<Expr>> args;
|
||||
|
||||
public:
|
||||
CallExpr(LOC_ARG, Expr *callee, std::vector<Expr *> args)
|
||||
: Expr(sourceRange), callee(callee), args() {
|
||||
for (auto &arg : args) {
|
||||
this->args.push_back(std::shared_ptr<Expr>(arg));
|
||||
}
|
||||
}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static CallExpr *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
26
compiler/include/AST/Expr/CastExpr.h
Normal file
26
compiler/include/AST/Expr/CastExpr.h
Normal file
@ -0,0 +1,26 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <string>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
class CastExpr : public Expr {
|
||||
const std::shared_ptr<Expr> value;
|
||||
const std::shared_ptr<TypeName> typeName;
|
||||
|
||||
public:
|
||||
CastExpr(LOC_ARG, Expr *value, TypeName *typeName)
|
||||
: Expr(sourceRange), value(value), typeName(typeName) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static CastExpr *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,25 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <sstream>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class FnArg;
|
||||
|
||||
class Closure : public Expr {
|
||||
const std::vector<std::unique_ptr<FnArg>> args;
|
||||
const std::unique_ptr<Expr> body;
|
||||
|
||||
public:
|
||||
Closure(LOC_ARG, std::vector<std::unique_ptr<FnArg>> &args, std::unique_ptr<Expr> &body)
|
||||
: Expr(location), args(std::move(args)), body(std::move(body)) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<Closure> fromJson(boost::json::value json);
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -9,10 +9,15 @@ class Identifier : public Expr {
|
||||
const std::string name;
|
||||
|
||||
public:
|
||||
Identifier(LOC_ARG, const std::string &name) : Expr(location), name(name) {}
|
||||
Identifier(LOC_ARG, const std::string &name)
|
||||
: Expr(sourceRange), name(name) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<Identifier> fromJson(boost::json::value json);
|
||||
static Identifier *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace ast
|
||||
|
36
compiler/include/AST/Expr/LambdaExpr.h
Normal file
36
compiler/include/AST/Expr/LambdaExpr.h
Normal file
@ -0,0 +1,36 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class FnParam;
|
||||
|
||||
class LambdaExpr : public Expr {
|
||||
std::vector<std::shared_ptr<FnParam>> params;
|
||||
std::vector<std::shared_ptr<Expr>> body;
|
||||
|
||||
public:
|
||||
LambdaExpr(LOC_ARG, std::vector<FnParam *> params, std::vector<Expr *> body)
|
||||
: Expr(sourceRange), params(), body() {
|
||||
for (auto ¶m : params) {
|
||||
this->params.push_back(std::shared_ptr<FnParam>(param));
|
||||
}
|
||||
|
||||
for (auto &expr : body) {
|
||||
this->body.push_back(std::shared_ptr<Expr>(expr));
|
||||
}
|
||||
}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static LambdaExpr *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,22 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <sstream>
|
||||
#include <string>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class PropExpr : public Expr {
|
||||
const std::unique_ptr<Expr> expr;
|
||||
const std::string property;
|
||||
|
||||
public:
|
||||
PropExpr(LOC_ARG, std::unique_ptr<Expr> &expr, const std::string &property)
|
||||
: Expr(location), expr(std::move(expr)), property(property) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<PropExpr> fromJson(boost::json::value json);
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,23 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <sstream>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
class Tuple : public Expr {
|
||||
const std::vector<std::unique_ptr<Expr>> values;
|
||||
|
||||
public:
|
||||
Tuple(LOC_ARG, std::vector<std::unique_ptr<Expr>> &values)
|
||||
: Expr(location), values(std::move(values)) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<Tuple> fromJson(boost::json::value json);
|
||||
};
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
31
compiler/include/AST/Expr/UnExpr.h
Normal file
31
compiler/include/AST/Expr/UnExpr.h
Normal file
@ -0,0 +1,31 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <string>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
enum UnOp {
|
||||
NOT,
|
||||
POS,
|
||||
NEG,
|
||||
};
|
||||
|
||||
class UnExpr : public Expr {
|
||||
const UnOp op;
|
||||
const std::shared_ptr<Expr> expr;
|
||||
|
||||
public:
|
||||
UnExpr(LOC_ARG, const UnOp op, Expr *expr)
|
||||
: Expr(sourceRange), op(op), expr(expr) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static UnExpr *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,23 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <iomanip>
|
||||
#include <memory>
|
||||
#include <sstream>
|
||||
#include <string>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class UnaryExpr : public Expr {
|
||||
const std::string op;
|
||||
const std::unique_ptr<Expr> expr;
|
||||
|
||||
public:
|
||||
UnaryExpr(LOC_ARG, const std::string &op, std::unique_ptr<Expr> &expr)
|
||||
: Expr(location), op(op), expr(std::move(expr)) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<UnaryExpr> fromJson(boost::json::value json);
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,38 +1,47 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <string>
|
||||
#include <cstdint>
|
||||
#include <cfloat>
|
||||
#include <cstdint>
|
||||
#include <string>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class NullValue : public Expr {
|
||||
public:
|
||||
NullValue(LOC_ARG) : Expr(location) {}
|
||||
// class NullValue : public Expr {
|
||||
// public:
|
||||
// NullValue(LOC_ARG) : Expr(sourceRange) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<NullValue> fromJson(boost::json::value json);
|
||||
};
|
||||
// virtual boost::json::value toJson() override;
|
||||
// static std::unique_ptr<NullValue> fromJson(boost::json::value json);
|
||||
// };
|
||||
|
||||
class IntValue : public Expr {
|
||||
const std::int64_t value;
|
||||
|
||||
public:
|
||||
IntValue(LOC_ARG, int64_t value) : Expr(location), value(value) {}
|
||||
IntValue(LOC_ARG, int64_t value) : Expr(sourceRange), value(value) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<IntValue> fromJson(boost::json::value json);
|
||||
static IntValue *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
|
||||
class FloatValue : public Expr {
|
||||
const std::double_t value;
|
||||
|
||||
public:
|
||||
FloatValue(LOC_ARG, double value) : Expr(location), value(value) {}
|
||||
FloatValue(LOC_ARG, double value) : Expr(sourceRange), value(value) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<FloatValue> fromJson(boost::json::value json);
|
||||
static FloatValue *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
||||
|
@ -1,8 +1,6 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <iomanip>
|
||||
#include <sstream>
|
||||
#include <string>
|
||||
|
||||
namespace plsm {
|
||||
@ -12,10 +10,14 @@ class Import : public ASTNode {
|
||||
|
||||
public:
|
||||
Import(LOC_ARG, const std::string &moduleName)
|
||||
: ASTNode(location), moduleName(moduleName) {}
|
||||
: ASTNode(sourceRange), moduleName(moduleName) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<Import> fromJson(boost::json::value json);
|
||||
static Import *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
||||
|
@ -1,11 +1,8 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <cstddef>
|
||||
#include <iomanip>
|
||||
#include <memory>
|
||||
#include <vector>
|
||||
#include <sstream>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
@ -13,18 +10,28 @@ class Import;
|
||||
|
||||
class Module : public ASTNode {
|
||||
const std::string name;
|
||||
const std::vector<std::unique_ptr<Import>> imports;
|
||||
const std::vector<std::unique_ptr<Stmt>> stmts;
|
||||
std::vector<std::shared_ptr<Import>> imports;
|
||||
std::vector<std::shared_ptr<Stmt>> stmts;
|
||||
|
||||
public:
|
||||
Module(LOC_ARG, const std::string &name,
|
||||
std::vector<std::unique_ptr<Import>> &imports,
|
||||
std::vector<std::unique_ptr<Stmt>> &stmts)
|
||||
: ASTNode(location), name(name), imports(std::move(imports)),
|
||||
stmts(std::move(stmts)) {}
|
||||
Module(LOC_ARG, const std::string &name, const std::vector<Import *> &imports,
|
||||
const std::vector<Stmt *> &stmts)
|
||||
: ASTNode(sourceRange), name(name), imports(), stmts() {
|
||||
for (auto &import : imports) {
|
||||
this->imports.push_back(std::shared_ptr<Import>(import));
|
||||
}
|
||||
|
||||
for (auto &stmt : stmts) {
|
||||
this->stmts.push_back(std::shared_ptr<Stmt>(stmt));
|
||||
}
|
||||
}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<Module> fromJson(boost::json::value json);
|
||||
static Module *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
||||
|
27
compiler/include/AST/Stmt/AssignStmt.h
Normal file
27
compiler/include/AST/Stmt/AssignStmt.h
Normal file
@ -0,0 +1,27 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <string>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
class AssignStmt : public Stmt {
|
||||
const std::shared_ptr<Expr> lval;
|
||||
const std::shared_ptr<Expr> rval;
|
||||
|
||||
public:
|
||||
AssignStmt(LOC_ARG, Expr *lval, Expr *rval)
|
||||
: Stmt(sourceRange), lval(lval), rval(rval) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static AssignStmt *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -6,14 +6,17 @@
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class ExprStmt : public Stmt {
|
||||
const std::unique_ptr<Expr> expr;
|
||||
const std::shared_ptr<Expr> expr;
|
||||
|
||||
public:
|
||||
ExprStmt(LOC_ARG, std::unique_ptr<Expr> &expr)
|
||||
: Stmt(location), expr(std::move(expr)) {}
|
||||
ExprStmt(LOC_ARG, Expr *expr) : Stmt(sourceRange), expr(expr) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<ExprStmt> fromJson(boost::json::value json);
|
||||
static ExprStmt *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
||||
|
56
compiler/include/AST/Stmt/FnDecl.h
Normal file
56
compiler/include/AST/Stmt/FnDecl.h
Normal file
@ -0,0 +1,56 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
class FnParam : public ASTNode {
|
||||
const std::string name;
|
||||
const std::shared_ptr<TypeName> typeName;
|
||||
|
||||
public:
|
||||
FnParam(LOC_ARG, const std::string &name, TypeName *typeName)
|
||||
: ASTNode(sourceRange), name(name), typeName(typeName) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static FnParam *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
|
||||
class FnDecl : public Stmt {
|
||||
const std::string name;
|
||||
std::vector<std::shared_ptr<FnParam>> params;
|
||||
const std::shared_ptr<TypeName> returnTypeName;
|
||||
std::vector<std::shared_ptr<Stmt>> body;
|
||||
|
||||
public:
|
||||
FnDecl(LOC_ARG, const std::string &name, const std::vector<FnParam *> ¶ms,
|
||||
TypeName *returnTypeName, const std::vector<Stmt *> &body)
|
||||
: Stmt(sourceRange), name(name), params(), returnTypeName(returnTypeName),
|
||||
body() {
|
||||
for (auto ¶m : params) {
|
||||
this->params.push_back(std::shared_ptr<FnParam>(param));
|
||||
}
|
||||
|
||||
for (auto &stmt : body) {
|
||||
this->body.push_back(std::shared_ptr<Stmt>(stmt));
|
||||
}
|
||||
}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static FnDecl *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,41 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <iomanip>
|
||||
#include <memory>
|
||||
#include <sstream>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class FnArg : public ASTNode {
|
||||
const std::string name;
|
||||
const std::unique_ptr<Type> type;
|
||||
|
||||
public:
|
||||
FnArg(LOC_ARG, const std::string &name, std::unique_ptr<Type> &type)
|
||||
: ASTNode(location), name(name), type(std::move(type)) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<FnArg> fromJson(boost::json::value json);
|
||||
};
|
||||
|
||||
class FnDef : public Stmt {
|
||||
const std::string name;
|
||||
const std::vector<std::unique_ptr<FnArg>> args;
|
||||
const std::unique_ptr<Type> returnType;
|
||||
const std::unique_ptr<Expr> body;
|
||||
|
||||
public:
|
||||
FnDef(LOC_ARG, const std::string &name,
|
||||
std::vector<std::unique_ptr<FnArg>> &args,
|
||||
std::unique_ptr<Type> &returnType, std::unique_ptr<Expr> &body)
|
||||
: Stmt(location), name(name), args(std::move(args)),
|
||||
returnType(std::move(returnType)), body(std::move(body)) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<FnDef> fromJson(boost::json::value json);
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
36
compiler/include/AST/Stmt/IfStmt.h
Normal file
36
compiler/include/AST/Stmt/IfStmt.h
Normal file
@ -0,0 +1,36 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
class IfStmt : public Stmt {
|
||||
const std::shared_ptr<Expr> condition;
|
||||
std::vector<std::shared_ptr<Stmt>> ifBody, elseBody;
|
||||
|
||||
public:
|
||||
IfStmt(LOC_ARG, Expr *condition, const std::vector<Stmt *> &ifBody,
|
||||
const std::vector<Stmt *> &elseBody)
|
||||
: Stmt(sourceRange), condition(condition) {
|
||||
for (auto &stmt : ifBody) {
|
||||
this->ifBody.push_back(std::shared_ptr<Stmt>(stmt));
|
||||
}
|
||||
|
||||
for (auto &stmt : elseBody) {
|
||||
this->elseBody.push_back(std::shared_ptr<Stmt>(stmt));
|
||||
}
|
||||
}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static IfStmt *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
22
compiler/include/AST/Stmt/RetStmt.h
Normal file
22
compiler/include/AST/Stmt/RetStmt.h
Normal file
@ -0,0 +1,22 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class RetStmt : public Stmt {
|
||||
const std::shared_ptr<Expr> value;
|
||||
|
||||
public:
|
||||
RetStmt(LOC_ARG, Expr *value) : Stmt(sourceRange), value(value) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static RetStmt *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,24 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <iomanip>
|
||||
#include <memory>
|
||||
#include <sstream>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class TraitAlias : public Stmt {
|
||||
const std::string alias;
|
||||
const std::string aliased;
|
||||
|
||||
public:
|
||||
TraitAlias(LOC_ARG, const std::string &alias, const std::string &aliased)
|
||||
: Stmt(location), alias(alias), aliased(aliased) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<TraitAlias> fromJson(boost::json::value json);
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,26 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <iomanip>
|
||||
#include <memory>
|
||||
#include <sstream>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class FnDef;
|
||||
class TraitDef : public Stmt {
|
||||
const std::string name;
|
||||
const std::vector<std::unique_ptr<FnDef>> traits;
|
||||
|
||||
public:
|
||||
TraitDef(LOC_ARG, const std::string &name,
|
||||
std::vector<std::unique_ptr<FnDef>> &traits)
|
||||
: Stmt(location), name(name), traits(std::move(traits)) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<TraitDef> fromJson(boost::json::value json);
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,24 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <iomanip>
|
||||
#include <memory>
|
||||
#include <sstream>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class TypeAlias : public Stmt {
|
||||
const std::string alias;
|
||||
const std::unique_ptr<Type> type;
|
||||
|
||||
public:
|
||||
TypeAlias(LOC_ARG, const std::string &alias, std::unique_ptr<Type> &type)
|
||||
: Stmt(location), alias(alias), type(std::move(type)) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<TypeAlias> fromJson(boost::json::value json);
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,29 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class FnDef;
|
||||
class FnArg;
|
||||
|
||||
class TypeDef : public Stmt {
|
||||
const std::string name;
|
||||
const std::vector<std::unique_ptr<FnArg>> attrs;
|
||||
const std::vector<std::unique_ptr<FnDef>> members;
|
||||
|
||||
public:
|
||||
TypeDef(LOC_ARG, const std::string &name,
|
||||
std::vector<std::unique_ptr<FnArg>> &attrs,
|
||||
std::vector<std::unique_ptr<FnDef>> &members)
|
||||
: Stmt(location), name(name), attrs(std::move(attrs)),
|
||||
members(std::move(members)) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<TypeDef> fromJson(boost::json::value json);
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,24 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <string>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class ValDecl : public Stmt {
|
||||
const std::string name;
|
||||
const std::unique_ptr<Type> type;
|
||||
const std::unique_ptr<Expr> value;
|
||||
|
||||
public:
|
||||
ValDecl(LOC_ARG, const std::string &name, std::unique_ptr<Type> &type,
|
||||
std::unique_ptr<Expr> &value)
|
||||
: Stmt(location), name(name), type(std::move(type)),
|
||||
value(std::move(value)) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<ValDecl> fromJson(boost::json::value json);
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
26
compiler/include/AST/Stmt/VarDecl.h
Normal file
26
compiler/include/AST/Stmt/VarDecl.h
Normal file
@ -0,0 +1,26 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <string>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
class VarDecl : public Stmt {
|
||||
const std::string name;
|
||||
const std::shared_ptr<TypeName> typeName;
|
||||
|
||||
public:
|
||||
VarDecl(LOC_ARG, const std::string &name, TypeName *typeName)
|
||||
: Stmt(sourceRange), name(name), typeName(typeName) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static VarDecl *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
29
compiler/include/AST/Stmt/WhileStmt.h
Normal file
29
compiler/include/AST/Stmt/WhileStmt.h
Normal file
@ -0,0 +1,29 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class WhileStmt : public Stmt {
|
||||
const std::shared_ptr<Expr> condition;
|
||||
std::vector<std::shared_ptr<Stmt>> body;
|
||||
|
||||
public:
|
||||
WhileStmt(LOC_ARG, Expr *condition, const std::vector<Stmt *> &body)
|
||||
: Stmt(sourceRange), condition(condition) {
|
||||
for (auto &stmt : body) {
|
||||
this->body.push_back(std::shared_ptr<Stmt>(stmt));
|
||||
}
|
||||
}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static WhileStmt *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,23 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class ClosureType : public Type {
|
||||
const std::vector<std::unique_ptr<Type>> from;
|
||||
const std::unique_ptr<Type> to;
|
||||
|
||||
public:
|
||||
ClosureType(LOC_ARG, std::vector<std::unique_ptr<Type>> &from,
|
||||
std::unique_ptr<Type> &to)
|
||||
: Type(location), from(std::move(from)), to(std::move(to)) {}
|
||||
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<ClosureType> fromJson(boost::json::value json);
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
25
compiler/include/AST/Type/FunctionType.h
Normal file
25
compiler/include/AST/Type/FunctionType.h
Normal file
@ -0,0 +1,25 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class FunctionType : public Type {
|
||||
std::vector<std::unique_ptr<Type>> paramTypes;
|
||||
const std::unique_ptr<Type> returnType;
|
||||
|
||||
public:
|
||||
FunctionType(const std::vector<Type *> ¶mTypes, Type *returnType)
|
||||
: Type(), returnType(returnType) {
|
||||
for (auto ¶mType : paramTypes) {
|
||||
this->paramTypes.push_back(std::unique_ptr<Type>(paramType));
|
||||
}
|
||||
}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static FunctionType *fromJson(boost::json::value json);
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,23 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <memory>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class GenericType : public Type {
|
||||
const std::string name;
|
||||
const std::vector<std::unique_ptr<Type>> types;
|
||||
|
||||
public:
|
||||
GenericType(LOC_ARG, const std::string &name,
|
||||
std::vector<std::unique_ptr<Type>> &types)
|
||||
: Type(location), name(name), types(std::move(types)) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<GenericType> fromJson(boost::json::value json);
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,20 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
#include <string>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
class NamedType : public Type {
|
||||
const std::string name;
|
||||
|
||||
public:
|
||||
NamedType(LOC_ARG, const std::string &name) : Type(location), name(name) {}
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<NamedType> fromJson(boost::json::value json);
|
||||
};
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
22
compiler/include/AST/Type/PrimitiveType.h
Normal file
22
compiler/include/AST/Type/PrimitiveType.h
Normal file
@ -0,0 +1,22 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
class PrimitiveType : public Type {
|
||||
const std::string name;
|
||||
|
||||
public:
|
||||
PrimitiveType(const std::string &name) : Type(), name(name) {}
|
||||
|
||||
bool operator==(const PrimitiveType &other) { return name == other.name; }
|
||||
bool operator!=(const PrimitiveType &other) { return !(*this == other); }
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static PrimitiveType *fromJson(boost::json::value json);
|
||||
};
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,21 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Def.h"
|
||||
#include <memory>
|
||||
#include <vector>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
class TupleType : public Type {
|
||||
const std::vector<std::unique_ptr<Type>> types;
|
||||
|
||||
public:
|
||||
TupleType(LOC_ARG, std::vector<std::unique_ptr<Type>> &types)
|
||||
: Type(location), types(std::move(types)) {}
|
||||
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static std::unique_ptr<TupleType> fromJson(boost::json::value json);
|
||||
};
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
27
compiler/include/AST/TypeName/PrimitiveTypeName.h
Normal file
27
compiler/include/AST/TypeName/PrimitiveTypeName.h
Normal file
@ -0,0 +1,27 @@
|
||||
#pragma once
|
||||
|
||||
#include "AST/Base.h"
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
class PrimitiveTypeName : public TypeName {
|
||||
const std::string name;
|
||||
|
||||
public:
|
||||
PrimitiveTypeName(LOC_ARG, const std::string &name)
|
||||
: TypeName(sourceRange), name(name) {}
|
||||
|
||||
bool operator==(const PrimitiveTypeName &other) { return name == other.name; }
|
||||
bool operator!=(const PrimitiveTypeName &other) { return !(*this == other); }
|
||||
|
||||
virtual boost::json::value toJson() override;
|
||||
static PrimitiveTypeName *fromJson(boost::json::value json);
|
||||
|
||||
virtual std::any accept(ASTVisitor *visitor, std::any param) override {
|
||||
return visitor->visit(*this, param);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,12 +1,11 @@
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <stdexcept>
|
||||
#include <string>
|
||||
|
||||
#include "AST/Def.h"
|
||||
#include "AST/AST.h"
|
||||
|
||||
namespace plsm
|
||||
{
|
||||
std::unique_ptr<ast::Module> parse(const std::string &file, const std::string &input);
|
||||
namespace plsm {
|
||||
std::shared_ptr<ast::Module> parse(const std::string &file,
|
||||
const std::string &input);
|
||||
}
|
||||
|
||||
|
357
compiler/plsm.g4
357
compiler/plsm.g4
@ -1,84 +1,323 @@
|
||||
grammar plsm;
|
||||
|
||||
module: MODULE identifier ';' moduleImport* moduleStmt*;
|
||||
@parser::header {
|
||||
#include "AST/AST.h"
|
||||
|
||||
moduleImport: IMPORT importName ';';
|
||||
importName: identifier ('/' identifier)*;
|
||||
moduleStmt: let | fnDecl | fnDef | traitDef | typeDef;
|
||||
using namespace plsm::ast;
|
||||
}
|
||||
|
||||
traitDef: TRAIT identifier '=' identifier ';'
|
||||
| TRAIT identifier '=' '{' (fnDecl)* '}' ';';
|
||||
@parser::members {
|
||||
|
||||
typeDef: TYPE identifier '=' type ';'
|
||||
| TYPE identifier '=' ('(' fnDefArgs ')')? '{' (fnDecl | fnDef)* '}' ';';
|
||||
std::string filename;
|
||||
|
||||
fnDef: FN identifier '[' fnDefArgs? ']' type '=' expr ';';
|
||||
fnDefArgs: identifier type (',' identifier type)*;
|
||||
void setFileName(const std::string &filename) { this->filename = filename; }
|
||||
|
||||
fnDecl: FN identifier '[' fnDeclArgs? ']' type ';';
|
||||
fnDeclArgs: identifier? type (',' identifier? type)*;
|
||||
inline SourceRange getSourceRange(antlr4::ParserRuleContext *ctx) {
|
||||
if (!ctx->getStart() || !ctx->getStop()) {
|
||||
return SourceRange::unknown();
|
||||
}
|
||||
|
||||
let: LET identifier type? '=' expr ';';
|
||||
return SourceRange(
|
||||
filename, ctx->getText(),
|
||||
std::pair<size_t, size_t>(ctx->getStart()->getLine(),
|
||||
ctx->getStart()->getCharPositionInLine()),
|
||||
std::pair<size_t, size_t>(ctx->getStop()->getLine(),
|
||||
ctx->getStop()->getCharPositionInLine()));
|
||||
}
|
||||
|
||||
exprStmt: expr ';';
|
||||
}
|
||||
|
||||
type: type1; // novisit
|
||||
type1: type0
|
||||
| '(' type ')'
|
||||
| '(' tupleTypeList ')' // tuple
|
||||
| '[' typeList? ']' '->' type; // closure
|
||||
type0: identifier
|
||||
| identifier '{' typeList '}'; // generic
|
||||
module
|
||||
returns[Module *ast]: (stmts += topLevelStmt)* {
|
||||
std::vector<Stmt *> stmts;
|
||||
for (auto &stmt : $ctx->stmts) {
|
||||
stmts.push_back(stmt->ast);
|
||||
}
|
||||
|
||||
tupleTypeList: type (',' type)+;
|
||||
typeList: type (',' type)*;
|
||||
$ast = new Module(getSourceRange($ctx), "default", std::vector<Import *>(), stmts);
|
||||
};
|
||||
|
||||
topLevelStmt
|
||||
returns[Stmt *ast]:
|
||||
varDecl {
|
||||
$ast = $ctx->varDecl()->ast;
|
||||
}
|
||||
| fnDecl {
|
||||
$ast = $ctx->fnDecl()->ast;
|
||||
};
|
||||
|
||||
stmt
|
||||
returns[Stmt *ast]:
|
||||
exprStmt {
|
||||
$ast = $ctx->exprStmt()->ast;
|
||||
}
|
||||
| varDecl {
|
||||
$ast = $ctx->varDecl()->ast;
|
||||
}
|
||||
| retStmt {
|
||||
$ast = $ctx->retStmt()->ast;
|
||||
}
|
||||
| assignStmt {
|
||||
$ast = $ctx->assignStmt()->ast;
|
||||
}
|
||||
| implDeclAssignStmt {
|
||||
$ast = $ctx->implDeclAssignStmt()->ast;
|
||||
}
|
||||
| ifStmt {
|
||||
$ast = $ctx->ifStmt()->ast;
|
||||
}
|
||||
| whileStmt {
|
||||
$ast = $ctx->whileStmt()->ast;
|
||||
};
|
||||
|
||||
whileStmt
|
||||
returns[WhileStmt *ast]:
|
||||
'while' '(' condition = expr ')' (
|
||||
'{' (stmts += stmt)* '}'
|
||||
| singleStmt = stmt
|
||||
) {
|
||||
auto cond = $ctx->condition->ast;
|
||||
|
||||
std::vector<Stmt *> body;
|
||||
for (auto &stmt : $ctx->stmts) {
|
||||
body.push_back(stmt->ast);
|
||||
}
|
||||
if ($ctx->singleStmt) body.push_back($ctx->singleStmt->ast);
|
||||
|
||||
$ast = new WhileStmt(getSourceRange($ctx), cond, body);
|
||||
};
|
||||
|
||||
ifStmt
|
||||
returns[IfStmt *ast]:
|
||||
'if' '(' condition = expr ')' (
|
||||
'{' (ifStmts += stmt)* '}'
|
||||
| ifSingleStmt = stmt
|
||||
) (
|
||||
'else' (
|
||||
'{' (elseStmts += stmt)* '}'
|
||||
| elseSingleStmt = stmt
|
||||
)
|
||||
)? {
|
||||
auto cond = $ctx->condition->ast;
|
||||
|
||||
std::vector<Stmt *> ifBody;
|
||||
for (auto &stmt : $ctx->ifStmts) {
|
||||
ifBody.push_back(stmt->ast);
|
||||
}
|
||||
if ($ctx->ifSingleStmt) ifBody.push_back($ctx->ifSingleStmt->ast);
|
||||
|
||||
|
||||
expr: expr3; // novisit
|
||||
expr3: expr2
|
||||
| '[' fnDefArgs? ']' '->' expr // closure
|
||||
| '{' blockStmt* (expr ';') '}';
|
||||
expr2: expr1
|
||||
| expr2 operator expr1; // binary expr
|
||||
expr1: expr0
|
||||
| operator expr0; // unary expr
|
||||
expr0: literal
|
||||
| identifier
|
||||
| expr0 '[' exprList? ']' // fn call
|
||||
| '(' expr ')'
|
||||
| '(' tupleExprList ')' // tuple
|
||||
| expr0 '.' identifier; // property accessor
|
||||
std::vector<Stmt *> elseBody;
|
||||
for (auto &stmt : $ctx->elseStmts) {
|
||||
elseBody.push_back(stmt->ast);
|
||||
}
|
||||
if ($ctx->elseSingleStmt) elseBody.push_back($ctx->elseSingleStmt->ast);
|
||||
|
||||
blockStmt: let | exprStmt | fnDef;
|
||||
tupleExprList: expr (',' expr)+;
|
||||
exprList: expr (',' expr)*;
|
||||
$ast = new IfStmt(getSourceRange($ctx), cond, ifBody, elseBody);
|
||||
};
|
||||
|
||||
identifierList: identifier (',' identifier)*;
|
||||
implDeclAssignStmt
|
||||
returns[Stmt *ast]:
|
||||
IDENTIFIER ':=' expr {
|
||||
// TODO
|
||||
};
|
||||
|
||||
literal: NULL='null' | INT_LIT | FLOAT_LIT;
|
||||
assignStmt
|
||||
returns[AssignStmt *ast]:
|
||||
lval = expr '=' rval = expr {
|
||||
$ast = new AssignStmt(getSourceRange($ctx), $ctx->lval->ast, $ctx->rval->ast);
|
||||
};
|
||||
|
||||
operator: '=' | '->'
|
||||
| OPERATOR;
|
||||
retStmt
|
||||
returns[RetStmt *ast]:
|
||||
'ret' expr ';' {
|
||||
$ast = new RetStmt(getSourceRange($ctx), $ctx->expr()->ast);
|
||||
};
|
||||
|
||||
identifier: keyword | IDENTIFIER;
|
||||
keyword: BINOP | FN | IMPORT | LET | MODULE | NATIVE | TRAIT | TYPE | UNOP;
|
||||
fnDecl
|
||||
returns[FnDecl *ast]:
|
||||
'fun' name = IDENTIFIER '(' (
|
||||
params += fnParam (',' params += fnParam)*
|
||||
)? ')' typeName '{' (stmts += stmt)* '}' {
|
||||
auto name = $ctx->name->getText();
|
||||
|
||||
std::vector<FnParam *> params;
|
||||
for (auto ¶m : $ctx->params) {
|
||||
params.push_back(param->ast);
|
||||
}
|
||||
|
||||
INT_LIT: [0-9]+ | '0x' [0-9a-fA-F]+ | '0o' [0-7]+ | '0b' [01]+;
|
||||
FLOAT_LIT: [0-9]+ '.' | [0-9]* '.' [0-9]+;
|
||||
auto returnTypeName = $ctx->typeName()->ast;
|
||||
|
||||
OPERATOR: ('+'|'-'|'*'|'/'|'%'|'!'|'&'|'$'|'§'|'|'|'='|'<'|'>'|'?'|'~'|'#'|':'|'^'|'\\'|'.')+;
|
||||
std::vector<Stmt *> body;
|
||||
for (auto &stmt : $ctx->stmts) {
|
||||
body.push_back(stmt->ast);
|
||||
}
|
||||
|
||||
BINOP: 'binop';
|
||||
FN: 'fn';
|
||||
IMPORT: 'import';
|
||||
LET: 'let';
|
||||
MODULE: 'module';
|
||||
NATIVE: 'native';
|
||||
TRAIT: 'trait';
|
||||
TYPE: 'type';
|
||||
UNOP: 'unop';
|
||||
$ast = new FnDecl(getSourceRange($ctx), name, params, returnTypeName, body);
|
||||
};
|
||||
|
||||
fnParam
|
||||
returns[FnParam *ast]:
|
||||
IDENTIFIER typeName {
|
||||
$ast = new FnParam(getSourceRange($ctx), $ctx->IDENTIFIER()->getText(), $ctx->typeName()->ast);
|
||||
};
|
||||
|
||||
varDecl
|
||||
returns[VarDecl *ast]:
|
||||
'var' IDENTIFIER ':' typeName ';' {
|
||||
auto name = $ctx->IDENTIFIER()->getText();
|
||||
$ast = new VarDecl(getSourceRange($ctx), name, $ctx->typeName()->ast);
|
||||
};
|
||||
|
||||
exprStmt
|
||||
returns[ExprStmt *ast]:
|
||||
expr ';' {
|
||||
$ast = new ExprStmt(getSourceRange($ctx), $ctx->expr()->ast);
|
||||
};
|
||||
|
||||
expr
|
||||
returns[Expr *ast]:
|
||||
value = binaryExpr {
|
||||
$ast = $ctx->value->ast;
|
||||
};
|
||||
|
||||
binaryExpr
|
||||
returns[Expr *ast]:
|
||||
value = unaryExpr {
|
||||
$ast = $ctx->value->ast;
|
||||
}
|
||||
| lhs = binaryExpr op = ('*' | '/' | '%') rhs = binaryExpr {
|
||||
auto opText = $ctx->op->getText();
|
||||
|
||||
BinOp op;
|
||||
if (opText == "*") op = BinOp::MUL;
|
||||
if (opText == "/") op = BinOp::DIV;
|
||||
if (opText == "%") op = BinOp::MOD;
|
||||
|
||||
$ast = new BinExpr(getSourceRange($ctx), op, $ctx->lhs->ast, $ctx->rhs->ast);
|
||||
}
|
||||
| lhs = binaryExpr op = ('+' | '-') rhs = binaryExpr {
|
||||
auto opText = $ctx->op->getText();
|
||||
|
||||
BinOp op;
|
||||
if (opText == "+") op = BinOp::ADD;
|
||||
if (opText == "-") op = BinOp::SUB;
|
||||
|
||||
$ast = new BinExpr(getSourceRange($ctx), op, $ctx->lhs->ast, $ctx->rhs->ast);
|
||||
}
|
||||
| operand = binaryExpr 'as' typeName {
|
||||
$ast = new CastExpr(getSourceRange($ctx), $ctx->operand->ast, $ctx->typeName()->ast);
|
||||
}
|
||||
| lhs = binaryExpr op = (
|
||||
'=='
|
||||
| '!='
|
||||
| '>='
|
||||
| '<='
|
||||
| '>'
|
||||
| '<'
|
||||
) rhs = binaryExpr {
|
||||
auto opText = $ctx->op->getText();
|
||||
|
||||
BinOp op;
|
||||
if (opText == "==") op = BinOp::EQ;
|
||||
if (opText == "!=") op = BinOp::NE;
|
||||
if (opText == ">=") op = BinOp::GE;
|
||||
if (opText == "<=") op = BinOp::LE;
|
||||
if (opText == ">") op = BinOp::GT;
|
||||
if (opText == "<") op = BinOp::LT;
|
||||
|
||||
$ast = new BinExpr(getSourceRange($ctx), op, $ctx->lhs->ast, $ctx->rhs->ast);
|
||||
}
|
||||
| lhs = binaryExpr '&&' rhs = binaryExpr {
|
||||
$ast = new BinExpr(getSourceRange($ctx), BinOp::AND, $ctx->lhs->ast, $ctx->rhs->ast);
|
||||
}
|
||||
| lhs = binaryExpr '||' rhs = binaryExpr {
|
||||
$ast = new BinExpr(getSourceRange($ctx), BinOp::OR, $ctx->lhs->ast, $ctx->rhs->ast);
|
||||
};
|
||||
|
||||
unaryExpr
|
||||
returns[Expr *ast]:
|
||||
factorExpr {
|
||||
$ast = $ctx->factorExpr()->ast;
|
||||
}
|
||||
| functionCall {
|
||||
$ast = $ctx->functionCall()->ast;
|
||||
}
|
||||
| '!' unaryExpr {
|
||||
$ast = new UnExpr(getSourceRange($ctx), UnOp::NOT, $ctx->unaryExpr()->ast);
|
||||
}
|
||||
| '+' unaryExpr {
|
||||
$ast = new UnExpr(getSourceRange($ctx), UnOp::POS, $ctx->unaryExpr()->ast);
|
||||
}
|
||||
| '-' unaryExpr {
|
||||
$ast = new UnExpr(getSourceRange($ctx), UnOp::NEG, $ctx->unaryExpr()->ast);
|
||||
};
|
||||
|
||||
factorExpr
|
||||
returns[Expr *ast]:
|
||||
IDENTIFIER {
|
||||
$ast = new Identifier(getSourceRange($ctx), $ctx->IDENTIFIER()->getText());
|
||||
}
|
||||
| INT {
|
||||
auto text = $ctx->INT()->getText();
|
||||
|
||||
int64_t value;
|
||||
|
||||
if (!text.rfind("0x", 0))
|
||||
value = std::strtol(text.substr(2).data(), NULL, 16);
|
||||
|
||||
else if (!text.rfind("0o", 0))
|
||||
value = std::strtol(text.substr(2).data(), NULL, 8);
|
||||
|
||||
else if (!text.rfind("0b", 0))
|
||||
value = std::strtol(text.substr(2).data(), NULL, 2);
|
||||
|
||||
else
|
||||
value = std::strtol(text.data(), NULL, 10);
|
||||
|
||||
$ast = new IntValue(getSourceRange($ctx), value);
|
||||
}
|
||||
| FLOAT {
|
||||
auto text = $ctx->FLOAT()->getText();
|
||||
|
||||
if (text.at(text.size() - 1) == '.')
|
||||
text += "0";
|
||||
if (text.at(0) == '0')
|
||||
text = "0" + text;
|
||||
|
||||
double value = std::strtod(text.data(), NULL);
|
||||
$ast = new FloatValue(getSourceRange($ctx), value);
|
||||
}
|
||||
| BOOL {
|
||||
auto text = $ctx->BOOL()->getText();
|
||||
$ast = new IntValue(getSourceRange($ctx), text == "true" ? 1 : 0);
|
||||
}
|
||||
| '(' expr ')' {
|
||||
$ast = $ctx->expr()->ast;
|
||||
};
|
||||
|
||||
functionCall
|
||||
returns[Expr *ast]:
|
||||
callee = factorExpr '(' (args += expr (',' args += expr)*)? ')' {
|
||||
std::vector<Expr *> args;
|
||||
for (auto &arg : $ctx->args) {
|
||||
args.push_back(arg->ast);
|
||||
}
|
||||
|
||||
$ast = new CallExpr(getSourceRange($ctx), $ctx->callee->ast, args);
|
||||
};
|
||||
|
||||
typeName
|
||||
returns[TypeName *ast]:
|
||||
IDENTIFIER {
|
||||
auto text = $ctx->IDENTIFIER()->getText();
|
||||
$ast = new PrimitiveTypeName(getSourceRange($ctx), text);
|
||||
};
|
||||
|
||||
INT: [0-9]+ | '0x' [0-9a-fA-F]+ | '0o' [0-7]+ | '0b' [01]+;
|
||||
FLOAT: [0-9]+ '.' | [0-9]* '.' [0-9]+;
|
||||
BOOL: 'true' | 'false';
|
||||
|
||||
IDENTIFIER: [a-zA-Z_] [a-zA-Z0-9_]*;
|
||||
|
||||
WHITESPACE: [ \r\n\t]+ -> skip;
|
||||
WHITESPACE: [ \r\n\t]+ -> skip;
|
@ -1,23 +1,21 @@
|
||||
#include "AST/Def.h"
|
||||
#include "AST/Expr/BinExpr.h"
|
||||
#include "AST/Expr/Value.h"
|
||||
#include "AST/AST.h"
|
||||
|
||||
#include <map>
|
||||
#include <memory>
|
||||
#include <stdexcept>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
std::unique_ptr<ast::ASTNode> ast::ASTNode::fromJson(boost::json::value json) {
|
||||
if (json.is_null())
|
||||
return std::make_unique<NullValue>(ast::Location::json());
|
||||
ASTNode *ASTNode::fromJson(boost::json::value json) {
|
||||
// if (json.is_null())
|
||||
// return std::make_unique<NullValue>(Location::json());
|
||||
|
||||
if (json.is_int64())
|
||||
return std::make_unique<IntValue>(ast::Location::json(), json.as_int64());
|
||||
return new IntValue(SourceRange::json(), json.as_int64());
|
||||
|
||||
if (json.is_double())
|
||||
return std::make_unique<FloatValue>(ast::Location::json(),
|
||||
json.as_double());
|
||||
return new FloatValue(SourceRange::json(), json.as_double());
|
||||
|
||||
std::string type;
|
||||
try {
|
||||
@ -28,86 +26,93 @@ std::unique_ptr<ast::ASTNode> ast::ASTNode::fromJson(boost::json::value json) {
|
||||
}
|
||||
|
||||
if (type == "BinExpr")
|
||||
return ast::BinExpr::fromJson(json);
|
||||
if (type == "BlockExpr")
|
||||
return ast::BlockExpr::fromJson(json);
|
||||
return BinExpr::fromJson(json);
|
||||
if (type == "CallExpr")
|
||||
return ast::CallExpr::fromJson(json);
|
||||
if (type == "Closure")
|
||||
return ast::Closure::fromJson(json);
|
||||
return CallExpr::fromJson(json);
|
||||
if (type == "CastExpr")
|
||||
return CastExpr::fromJson(json);
|
||||
if (type == "Identifier")
|
||||
return ast::Identifier::fromJson(json);
|
||||
if (type == "PropExpr")
|
||||
return ast::PropExpr::fromJson(json);
|
||||
if (type == "Tuple")
|
||||
return ast::Tuple::fromJson(json);
|
||||
if (type == "UnaryExpr")
|
||||
return ast::UnaryExpr::fromJson(json);
|
||||
|
||||
if (type == "Import")
|
||||
return ast::Import::fromJson(json);
|
||||
if (type == "Module")
|
||||
return ast::Module::fromJson(json);
|
||||
return Identifier::fromJson(json);
|
||||
if (type == "LambdaExpr")
|
||||
return LambdaExpr::fromJson(json);
|
||||
if (type == "LambdaExpr")
|
||||
return LambdaExpr::fromJson(json);
|
||||
if (type == "UnExpr")
|
||||
return UnExpr::fromJson(json);
|
||||
|
||||
if (type == "AssignStmt")
|
||||
return AssignStmt::fromJson(json);
|
||||
if (type == "ExprStmt")
|
||||
return ast::ExprStmt::fromJson(json);
|
||||
if (type == "FnDef")
|
||||
return ast::FnDef::fromJson(json);
|
||||
if (type == "TraitAlias")
|
||||
return ast::TraitAlias::fromJson(json);
|
||||
if (type == "TraitDef")
|
||||
return ast::TraitDef::fromJson(json);
|
||||
if (type == "TypeAlias")
|
||||
return ast::TypeAlias::fromJson(json);
|
||||
if (type == "TypeDef")
|
||||
return ast::TypeDef::fromJson(json);
|
||||
if (type == "ValDecl")
|
||||
return ast::ValDecl::fromJson(json);
|
||||
return ExprStmt::fromJson(json);
|
||||
if (type == "FnParam")
|
||||
return FnParam::fromJson(json);
|
||||
if (type == "FnDecl")
|
||||
return FnDecl::fromJson(json);
|
||||
if (type == "IfStmt")
|
||||
return IfStmt::fromJson(json);
|
||||
if (type == "RetStmt")
|
||||
return RetStmt::fromJson(json);
|
||||
if (type == "VarDecl")
|
||||
return VarDecl::fromJson(json);
|
||||
if (type == "WhileStmt")
|
||||
return WhileStmt::fromJson(json);
|
||||
|
||||
if (type == "ClosureType")
|
||||
return ast::ClosureType::fromJson(json);
|
||||
if (type == "GenericType")
|
||||
return ast::GenericType::fromJson(json);
|
||||
if (type == "NamedType")
|
||||
return ast::NamedType::fromJson(json);
|
||||
if (type == "TupleType")
|
||||
return ast::TupleType::fromJson(json);
|
||||
if (type == "PrimitiveTypeName")
|
||||
return PrimitiveTypeName::fromJson(json);
|
||||
|
||||
throw std::runtime_error("json conversion for '" + type +
|
||||
"' not implemented");
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::Expr> ast::Expr::fromJson(boost::json::value json) {
|
||||
auto node = ast::ASTNode::fromJson(json);
|
||||
Expr *Expr::fromJson(boost::json::value json) {
|
||||
auto node = ASTNode::fromJson(json);
|
||||
|
||||
if (dynamic_cast<ast::Expr *>(node.get())) {
|
||||
return std::unique_ptr<ast::Expr>((ast::Expr *)node.release());
|
||||
if (dynamic_cast<Expr *>(node)) {
|
||||
return (Expr *)node;
|
||||
}
|
||||
|
||||
throw std::runtime_error(json.as_object().at("@type").as_string().c_str() +
|
||||
std::string(" is not of type 'Expr'"));
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::Type> ast::Type::fromJson(boost::json::value json) {
|
||||
auto node = ast::ASTNode::fromJson(json);
|
||||
TypeName *TypeName::fromJson(boost::json::value json) {
|
||||
auto node = ASTNode::fromJson(json);
|
||||
|
||||
if (dynamic_cast<ast::Type *>(node.get())) {
|
||||
return std::unique_ptr<ast::Type>((ast::Type *)node.release());
|
||||
if (dynamic_cast<TypeName *>(node)) {
|
||||
return (TypeName *)node;
|
||||
}
|
||||
|
||||
throw std::runtime_error(json.as_object().at("@type").as_string().c_str() +
|
||||
std::string(" is not of type 'Type'"));
|
||||
std::string(" is not of type 'TypeName'"));
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::Stmt> ast::Stmt::fromJson(boost::json::value json) {
|
||||
auto node = ast::ASTNode::fromJson(json);
|
||||
Stmt *Stmt::fromJson(boost::json::value json) {
|
||||
auto node = ASTNode::fromJson(json);
|
||||
|
||||
if (dynamic_cast<ast::Stmt *>(node.get())) {
|
||||
return std::unique_ptr<ast::Stmt>((ast::Stmt *)node.release());
|
||||
if (dynamic_cast<Stmt *>(node)) {
|
||||
return (Stmt *)node;
|
||||
}
|
||||
|
||||
throw std::runtime_error(json.as_object().at("@type").as_string().c_str() +
|
||||
std::string(" is not of type 'Stmt'"));
|
||||
}
|
||||
|
||||
} // namespace plsm
|
||||
Type *Type::fromJson(boost::json::value json) {
|
||||
std::string type;
|
||||
try {
|
||||
type = json.as_object().at("@type").as_string().c_str();
|
||||
} catch (...) {
|
||||
throw std::runtime_error("called Type::fromJson without @type constraint");
|
||||
}
|
||||
|
||||
if (type == "FunctionType")
|
||||
return FunctionType::fromJson(json);
|
||||
if (type == "PrimitiveType")
|
||||
return PrimitiveType::fromJson(json);
|
||||
|
||||
throw std::runtime_error("json conversion for '" + type +
|
||||
"' not implemented");
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,37 +1,41 @@
|
||||
#include "AST/Expr/BinExpr.h"
|
||||
#include "AST/Base.h"
|
||||
#include "AST/Def.h"
|
||||
#include "AST/AST.h"
|
||||
#include <memory>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
boost::json::value ast::BinExpr::toJson() {
|
||||
static const std::unordered_map<BinOp, std::string> binOpToString = {
|
||||
{BinOp::ADD, "+"}, {BinOp::SUB, "-"}, {BinOp::MUL, "*"}, {BinOp::DIV, "/"},
|
||||
{BinOp::MOD, "%"}, {BinOp::EQ, "=="}, {BinOp::NE, "!="}, {BinOp::LT, "<"},
|
||||
{BinOp::LE, "<="}, {BinOp::GT, ">"}, {BinOp::GE, ">="}, {BinOp::AND, "&&"},
|
||||
{BinOp::OR, "||"},
|
||||
};
|
||||
|
||||
static const std::unordered_map<std::string, BinOp> stringToBinOp = {
|
||||
{"+", BinOp::ADD}, {"-", BinOp::SUB}, {"*", BinOp::MUL}, {"/", BinOp::DIV},
|
||||
{"%", BinOp::MOD}, {"==", BinOp::EQ}, {"!=", BinOp::NE}, {"<", BinOp::LT},
|
||||
{"<=", BinOp::LE}, {">", BinOp::GT}, {">=", BinOp::GE}, {"&&", BinOp::AND},
|
||||
{"||", BinOp::OR},
|
||||
};
|
||||
|
||||
boost::json::value BinExpr::toJson() {
|
||||
return {
|
||||
{"@type", "BinExpr"},
|
||||
{"op", op},
|
||||
{"left", left->toJson()},
|
||||
{"right", right->toJson()},
|
||||
{"op", binOpToString.at(op)},
|
||||
{"lhs", lhs->toJson()},
|
||||
{"rhs", rhs->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::BinExpr> ast::BinExpr::fromJson(boost::json::value json) {
|
||||
auto op = getJsonValue<ast::BinExpr, std::string>(json, "op");
|
||||
auto left = fromJsonProperty<ast::BinExpr, ast::Expr>(json, "left");
|
||||
auto right = fromJsonProperty<ast::BinExpr, ast::Expr>(json, "right");
|
||||
return std::make_unique<ast::BinExpr>(ast::Location::json(), left, op, right);
|
||||
}
|
||||
|
||||
boost::json::value ast::PrefExpr::toJson() {
|
||||
return {
|
||||
{"@type", "PrefExpr"},
|
||||
{"expr", expr->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::PrefExpr>
|
||||
ast::PrefExpr::fromJson(boost::json::value json) {
|
||||
auto expr = fromJsonProperty<ast::PrefExpr, ast::Expr>(json, "expr");
|
||||
return std::make_unique<ast::PrefExpr>(ast::Location::json(), expr);
|
||||
BinExpr *BinExpr::fromJson(boost::json::value json) {
|
||||
auto opString = getJsonValue<BinExpr, std::string>(json, "op");
|
||||
auto op = stringToBinOp.at(opString);
|
||||
|
||||
auto lhs = fromJsonProperty<BinExpr, Expr>(json, "lhs");
|
||||
auto rhs = fromJsonProperty<BinExpr, Expr>(json, "rhs");
|
||||
|
||||
return new BinExpr(SourceRange::json(), op, lhs, rhs);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
||||
|
@ -1,25 +0,0 @@
|
||||
#include "AST/Expr/Block.h"
|
||||
#include "AST/Base.h"
|
||||
#include "AST/Def.h"
|
||||
#include "Utils.h"
|
||||
#include <algorithm>
|
||||
#include <memory>
|
||||
|
||||
namespace plsm {
|
||||
|
||||
boost::json::value ast::BlockExpr::toJson() {
|
||||
return {
|
||||
{"@type", "BlockExpr"},
|
||||
{"stmts", utils::mapToJson(stmts)},
|
||||
{"result", result->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::BlockExpr>
|
||||
ast::BlockExpr::fromJson(boost::json::value json) {
|
||||
auto stmts = fromJsonVector<ast::BlockExpr, ast::Stmt>(json, "stmts");
|
||||
auto result = fromJsonProperty<ast::BlockExpr, ast::Expr>(json, "result");
|
||||
return std::make_unique<ast::BlockExpr>(ast::Location::json(), stmts, result);
|
||||
}
|
||||
|
||||
} // namespace plsm
|
@ -1,22 +0,0 @@
|
||||
#include "AST/Expr/Call.h"
|
||||
#include "AST/Def.h"
|
||||
#include "Utils.h"
|
||||
|
||||
namespace plsm {
|
||||
|
||||
boost::json::value ast::CallExpr::toJson() {
|
||||
return {
|
||||
{"@type", "CallExpr"},
|
||||
{"callee", callee->toJson()},
|
||||
{"args", utils::mapToJson(args)},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::CallExpr>
|
||||
ast::CallExpr::fromJson(boost::json::value json) {
|
||||
auto callee = fromJsonProperty<ast::CallExpr, ast::Expr>(json, "callee");
|
||||
auto args = fromJsonVector<ast::CallExpr, ast::Expr>(json, "args");
|
||||
return std::make_unique<ast::CallExpr>(ast::Location::json(), callee, args);
|
||||
}
|
||||
|
||||
} // namespace plsm
|
22
compiler/src/AST/Expr/CallExpr.cpp
Normal file
22
compiler/src/AST/Expr/CallExpr.cpp
Normal file
@ -0,0 +1,22 @@
|
||||
#include "AST/AST.h"
|
||||
#include "Utils.h"
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
boost::json::value CallExpr::toJson() {
|
||||
return {
|
||||
{"@type", "CallExpr"},
|
||||
{"callee", callee->toJson()},
|
||||
{"args", utils::mapToJson(args)},
|
||||
};
|
||||
}
|
||||
|
||||
CallExpr *CallExpr::fromJson(boost::json::value json) {
|
||||
auto callee = fromJsonProperty<CallExpr, Expr>(json, "callee");
|
||||
auto args = fromJsonVector<CallExpr, Expr>(json, "args");
|
||||
return new CallExpr(SourceRange::json(), callee, args);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
22
compiler/src/AST/Expr/CastExpr.cpp
Normal file
22
compiler/src/AST/Expr/CastExpr.cpp
Normal file
@ -0,0 +1,22 @@
|
||||
#include "AST/AST.h"
|
||||
#include "Utils.h"
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
boost::json::value CastExpr::toJson() {
|
||||
return {
|
||||
{"@type", "CastExpr"},
|
||||
{"value", value->toJson()},
|
||||
{"typeName", typeName->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
CastExpr *CastExpr::fromJson(boost::json::value json) {
|
||||
auto value = fromJsonProperty<CastExpr, Expr>(json, "value");
|
||||
auto typeName = fromJsonProperty<CastExpr, TypeName>(json, "typeName");
|
||||
return new CastExpr(SourceRange::json(), value, typeName);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,20 +0,0 @@
|
||||
#include "AST/Def.h"
|
||||
#include "Utils.h"
|
||||
|
||||
namespace plsm {
|
||||
|
||||
boost::json::value ast::Closure::toJson() {
|
||||
return {
|
||||
{"@type", "Closure"},
|
||||
{"args", utils::mapToJson(args)},
|
||||
{"body", body->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::Closure> ast::Closure::fromJson(boost::json::value json) {
|
||||
auto args = fromJsonVector<ast::Closure, ast::FnArg>(json, "args");
|
||||
auto body = fromJsonProperty<ast::Closure, ast::Expr>(json, "body");
|
||||
return std::make_unique<ast::Closure>(ast::Location::json(), args, body);
|
||||
}
|
||||
|
||||
} // namespace plsm
|
@ -1,19 +1,19 @@
|
||||
#include "AST/Def.h"
|
||||
#include "AST/Expr/Identifier.h"
|
||||
#include "AST/AST.h"
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
boost::json::value ast::Identifier::toJson() {
|
||||
boost::json::value Identifier::toJson() {
|
||||
return {
|
||||
{"@type", "Identifier"},
|
||||
{"name", name},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::Identifier>
|
||||
ast::Identifier::fromJson(boost::json::value json) {
|
||||
auto name = getJsonValue<ast::Identifier, std::string>(json, "name");
|
||||
return std::make_unique<ast::Identifier>(ast::Location::json(), name);
|
||||
Identifier *Identifier::fromJson(boost::json::value json) {
|
||||
auto name = getJsonValue<Identifier, std::string>(json, "name");
|
||||
return new Identifier(SourceRange::json(), name);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
||||
|
22
compiler/src/AST/Expr/LambdaExpr.cpp
Normal file
22
compiler/src/AST/Expr/LambdaExpr.cpp
Normal file
@ -0,0 +1,22 @@
|
||||
#include "AST/AST.h"
|
||||
#include "Utils.h"
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
boost::json::value LambdaExpr::toJson() {
|
||||
return {
|
||||
{"@type", "LambdaExpr"},
|
||||
{"params", utils::mapToJson(params)},
|
||||
{"body", utils::mapToJson(body)},
|
||||
};
|
||||
}
|
||||
|
||||
LambdaExpr *LambdaExpr::fromJson(boost::json::value json) {
|
||||
auto params = fromJsonVector<LambdaExpr, FnParam>(json, "params");
|
||||
auto body = fromJsonVector<LambdaExpr, Expr>(json, "body");
|
||||
return new LambdaExpr(SourceRange::json(), params, body);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,21 +0,0 @@
|
||||
#include "AST/Def.h"
|
||||
#include <memory>
|
||||
|
||||
namespace plsm {
|
||||
|
||||
boost::json::value ast::PropExpr::toJson() {
|
||||
return {
|
||||
{"@type", "PropExpr"},
|
||||
{"expr", expr->toJson()},
|
||||
{"property", property},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::PropExpr>
|
||||
ast::PropExpr::fromJson(boost::json::value json) {
|
||||
auto expr = fromJsonProperty<ast::PropExpr, ast::Expr>(json, "expr");
|
||||
auto property = getJsonValue<ast::PropExpr, std::string>(json, "property");
|
||||
return std::make_unique<ast::PropExpr>(ast::Location::json(), expr, property);
|
||||
}
|
||||
|
||||
} // namespace plsm
|
@ -1,18 +0,0 @@
|
||||
#include "AST/Def.h"
|
||||
#include "Utils.h"
|
||||
|
||||
namespace plsm {
|
||||
|
||||
boost::json::value ast::Tuple::toJson() {
|
||||
return {
|
||||
{"@type", "Tuple"},
|
||||
{"values", utils::mapToJson(values)},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::Tuple> ast::Tuple::fromJson(boost::json::value json) {
|
||||
auto values = fromJsonVector<ast::Tuple, ast::Expr>(json, "values");
|
||||
return std::make_unique<ast::Tuple>(ast::Location::json(), values);
|
||||
}
|
||||
|
||||
} // namespace plsm
|
36
compiler/src/AST/Expr/UnExpr.cpp
Normal file
36
compiler/src/AST/Expr/UnExpr.cpp
Normal file
@ -0,0 +1,36 @@
|
||||
#include "AST/AST.h"
|
||||
#include <memory>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
static const std::unordered_map<UnOp, std::string> unOpToString = {
|
||||
{UnOp::POS, "+"},
|
||||
{UnOp::NEG, "-"},
|
||||
{UnOp::NOT, "!"},
|
||||
};
|
||||
|
||||
static const std::unordered_map<std::string, UnOp> stringToUnOp = {
|
||||
{"+", UnOp::POS},
|
||||
{"-", UnOp::NEG},
|
||||
{"!", UnOp::NOT},
|
||||
};
|
||||
|
||||
boost::json::value UnExpr::toJson() {
|
||||
return {
|
||||
{"@type", "UnExpr"},
|
||||
{"op", unOpToString.at(op)},
|
||||
{"expr", expr->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
UnExpr *UnExpr::fromJson(boost::json::value json) {
|
||||
auto opString = getJsonValue<UnExpr, std::string>(json, "op");
|
||||
auto op = stringToUnOp.at(opString);
|
||||
|
||||
auto expr = fromJsonProperty<UnExpr, Expr>(json, "expr");
|
||||
return new UnExpr(SourceRange::json(), op, expr);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,22 +0,0 @@
|
||||
#include "AST/Def.h"
|
||||
#include "AST/Expr/UnaryExpr.h"
|
||||
#include <memory>
|
||||
|
||||
namespace plsm {
|
||||
|
||||
boost::json::value ast::UnaryExpr::toJson() {
|
||||
return {
|
||||
{"@type", "UnaryExpr"},
|
||||
{"op", op},
|
||||
{"expr", expr->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::UnaryExpr>
|
||||
ast::UnaryExpr::fromJson(boost::json::value json) {
|
||||
auto op = getJsonValue<ast::UnaryExpr, std::string>(json, "op");
|
||||
auto expr = fromJsonProperty<ast::UnaryExpr, ast::Expr>(json, "expr");
|
||||
return std::make_unique<ast::UnaryExpr>(ast::Location::json(), op, expr);
|
||||
}
|
||||
|
||||
} // namespace plsm
|
@ -1,29 +1,26 @@
|
||||
#include "AST/Def.h"
|
||||
#include "AST/AST.h"
|
||||
#include <memory>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
// boost::json::value NullValue::toJson() { return nullptr; }
|
||||
|
||||
boost::json::value ast::NullValue::toJson() { return nullptr; }
|
||||
// std::unique_ptr<NullValue>
|
||||
// NullValue::fromJson(boost::json::value json) {
|
||||
// return std::make_unique<NullValue>(SourceRange::json());
|
||||
// }
|
||||
|
||||
std::unique_ptr<ast::NullValue>
|
||||
ast::NullValue::fromJson(boost::json::value json) {
|
||||
return std::make_unique<ast::NullValue>(ast::Location::json());
|
||||
boost::json::value IntValue::toJson() { return value; }
|
||||
|
||||
IntValue *IntValue::fromJson(boost::json::value json) {
|
||||
return new IntValue(SourceRange::json(), json.as_int64());
|
||||
}
|
||||
|
||||
boost::json::value ast::IntValue::toJson() { return value; }
|
||||
boost::json::value FloatValue::toJson() { return value; }
|
||||
|
||||
std::unique_ptr<ast::IntValue>
|
||||
ast::IntValue::fromJson(boost::json::value json) {
|
||||
return std::make_unique<ast::IntValue>(ast::Location::json(),
|
||||
json.as_int64());
|
||||
}
|
||||
|
||||
boost::json::value ast::FloatValue::toJson() { return value; }
|
||||
|
||||
std::unique_ptr<ast::FloatValue>
|
||||
ast::FloatValue::fromJson(boost::json::value json) {
|
||||
return std::make_unique<ast::FloatValue>(ast::Location::json(),
|
||||
json.as_double());
|
||||
FloatValue *FloatValue::fromJson(boost::json::value json) {
|
||||
return new FloatValue(SourceRange::json(), json.as_double());
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
||||
|
@ -1,19 +1,16 @@
|
||||
#include "AST/Def.h"
|
||||
#include "AST/AST.h"
|
||||
#include <memory>
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
boost::json::value ast::Import::toJson() {
|
||||
return {
|
||||
{"@type", "Import"},
|
||||
{"moduleName", moduleName}
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::Import>
|
||||
ast::Import::fromJson(boost::json::value json) {
|
||||
auto moduleName = getJsonValue<ast::Import, std::string>(json, "moduleName");
|
||||
return std::make_unique<ast::Import>(ast::Location::json(), moduleName);
|
||||
boost::json::value Import::toJson() {
|
||||
return {{"@type", "Import"}, {"moduleName", moduleName}};
|
||||
}
|
||||
Import *Import::fromJson(boost::json::value json) {
|
||||
auto moduleName = getJsonValue<Import, std::string>(json, "moduleName");
|
||||
return new Import(SourceRange::json(), moduleName);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
||||
|
@ -1,9 +1,10 @@
|
||||
#include "AST/Def.h"
|
||||
#include "AST/AST.h"
|
||||
#include "Utils.h"
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
boost::json::value ast::Module::toJson() {
|
||||
boost::json::value Module::toJson() {
|
||||
return {
|
||||
{"@type", "Module"},
|
||||
{"name", name},
|
||||
@ -12,11 +13,13 @@ boost::json::value ast::Module::toJson() {
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::Module> ast::Module::fromJson(boost::json::value json) {
|
||||
auto name = getJsonValue<ast::Module, std::string>(json, "name");
|
||||
auto imports = fromJsonVector<ast::Module, ast::Import>(json, "imports");
|
||||
auto stmts = fromJsonVector<ast::Module, ast::Stmt>(json, "stmts");
|
||||
return std::make_unique<ast::Module>(ast::Location::json(), name, imports, stmts);
|
||||
Module *Module::fromJson(boost::json::value json) {
|
||||
auto name = getJsonValue<Module, std::string>(json, "name");
|
||||
auto imports = fromJsonVector<Module, Import>(json, "imports");
|
||||
auto stmts = fromJsonVector<Module, Stmt>(json, "stmts");
|
||||
|
||||
return new Module(SourceRange::json(), name, imports, stmts);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
||||
|
21
compiler/src/AST/Stmt/AssignStmt.cpp
Normal file
21
compiler/src/AST/Stmt/AssignStmt.cpp
Normal file
@ -0,0 +1,21 @@
|
||||
#include "AST/AST.h"
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
boost::json::value AssignStmt::toJson() {
|
||||
return {
|
||||
{"@type", "AssignStmt"},
|
||||
{"lval", lval->toJson()},
|
||||
{"rval", rval->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
AssignStmt *AssignStmt::fromJson(boost::json::value json) {
|
||||
auto lval = fromJsonProperty<AssignStmt, Expr>(json, "lval");
|
||||
auto rval = fromJsonProperty<AssignStmt, Expr>(json, "rval");
|
||||
return new AssignStmt(SourceRange::json(), lval, rval);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,16 +1,19 @@
|
||||
#include "AST/Stmt/ExprStmt.h"
|
||||
#include "AST/Def.h"
|
||||
#include "AST/AST.h"
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
boost::json::value ast::ExprStmt::toJson() {
|
||||
return {{"@type", "ExprStmt"}, {"expr", expr->toJson()}};
|
||||
boost::json::value ExprStmt::toJson() {
|
||||
return {
|
||||
{"@type", "ExprStmt"},
|
||||
{"expr", expr->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::ExprStmt>
|
||||
ast::ExprStmt::fromJson(boost::json::value json) {
|
||||
auto expr = fromJsonProperty<ast::ExprStmt, ast::Expr>(json, "expr");
|
||||
return std::make_unique<ast::ExprStmt>(ast::Location::json(), expr);
|
||||
ExprStmt *ExprStmt::fromJson(boost::json::value json) {
|
||||
auto expr = fromJsonProperty<ExprStmt, Expr>(json, "expr");
|
||||
return new ExprStmt(SourceRange::json(), expr);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
||||
|
41
compiler/src/AST/Stmt/FnDecl.cpp
Normal file
41
compiler/src/AST/Stmt/FnDecl.cpp
Normal file
@ -0,0 +1,41 @@
|
||||
#include "AST/AST.h"
|
||||
#include "Utils.h"
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
boost::json::value FnParam::toJson() {
|
||||
return {
|
||||
{"@type", "FnParam"},
|
||||
{"name", name},
|
||||
{"typeName", typeName->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
FnParam *FnParam::fromJson(boost::json::value json) {
|
||||
auto name = getJsonValue<FnParam, std::string>(json, "name");
|
||||
auto typeName = fromJsonProperty<FnParam, TypeName>(json, "typeName");
|
||||
return new FnParam(SourceRange::json(), name, typeName);
|
||||
}
|
||||
|
||||
boost::json::value FnDecl::toJson() {
|
||||
return {
|
||||
{"@type", "FnDecl"},
|
||||
{"name", name},
|
||||
{"params", utils::mapToJson(params)},
|
||||
{"returnTypeName", returnTypeName->toJson()},
|
||||
{"body", utils::mapToJson(body)},
|
||||
};
|
||||
}
|
||||
|
||||
FnDecl *FnDecl::fromJson(boost::json::value json) {
|
||||
auto name = getJsonValue<FnDecl, std::string>(json, "name");
|
||||
auto params = fromJsonVector<FnDecl, FnParam>(json, "params");
|
||||
auto returnTypeName =
|
||||
fromJsonProperty<FnDecl, TypeName>(json, "returnTypeName");
|
||||
auto body = fromJsonVector<FnDecl, Stmt>(json, "body");
|
||||
return new FnDecl(SourceRange::json(), name, params, returnTypeName, body);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,39 +0,0 @@
|
||||
#include "AST/Def.h"
|
||||
#include "Utils.h"
|
||||
|
||||
namespace plsm {
|
||||
|
||||
boost::json::value ast::FnArg::toJson() {
|
||||
return {
|
||||
{"@type", "FnArg"},
|
||||
{"name", name},
|
||||
{"type", type->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::FnArg> ast::FnArg::fromJson(boost::json::value json) {
|
||||
auto name = getJsonValue<ast::FnArg, std::string>(json, "name");
|
||||
auto type = fromJsonProperty<ast::FnArg, ast::Type>(json, "type");
|
||||
return std::make_unique<ast::FnArg>(ast::Location::json(), name, type);
|
||||
}
|
||||
|
||||
boost::json::value ast::FnDef::toJson() {
|
||||
return {
|
||||
{"@type", "FnDef"},
|
||||
{"name", name},
|
||||
{"args", utils::mapToJson(args)},
|
||||
{"returnType", returnType->toJson()},
|
||||
{"body", body->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::FnDef> ast::FnDef::fromJson(boost::json::value json) {
|
||||
auto name = getJsonValue<ast::FnDef, std::string>(json, "name");
|
||||
auto args = fromJsonVector<ast::FnDef, ast::FnArg>(json, "args");
|
||||
auto returnType = fromJsonProperty<ast::FnDef, ast::Type>(json, "returnType");
|
||||
auto body = fromJsonProperty<ast::FnDef, ast::Expr>(json, "body");
|
||||
return std::make_unique<ast::FnDef>(ast::Location::json(), name, args,
|
||||
returnType, body);
|
||||
}
|
||||
|
||||
} // namespace plsm
|
24
compiler/src/AST/Stmt/IfStmt.cpp
Normal file
24
compiler/src/AST/Stmt/IfStmt.cpp
Normal file
@ -0,0 +1,24 @@
|
||||
#include "AST/AST.h"
|
||||
#include "Utils.h"
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
boost::json::value IfStmt::toJson() {
|
||||
return {
|
||||
{"@type", "IfStmt"},
|
||||
{"condition", condition->toJson()},
|
||||
{"ifBody", utils::mapToJson(ifBody)},
|
||||
{"elseBody", utils::mapToJson(elseBody)},
|
||||
};
|
||||
}
|
||||
|
||||
IfStmt *IfStmt::fromJson(boost::json::value json) {
|
||||
auto condition = fromJsonProperty<IfStmt, Expr>(json, "condition");
|
||||
auto ifBody = fromJsonVector<IfStmt, Stmt>(json, "ifBody");
|
||||
auto elseBody = fromJsonVector<IfStmt, Stmt>(json, "elseBody");
|
||||
return new IfStmt(SourceRange::json(), condition, ifBody, elseBody);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
19
compiler/src/AST/Stmt/RetStmt.cpp
Normal file
19
compiler/src/AST/Stmt/RetStmt.cpp
Normal file
@ -0,0 +1,19 @@
|
||||
#include "AST/AST.h"
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
boost::json::value RetStmt::toJson() {
|
||||
return {
|
||||
{"@type", "RetStmt"},
|
||||
{"value", value->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
RetStmt *RetStmt::fromJson(boost::json::value json) {
|
||||
auto value = fromJsonProperty<RetStmt, Expr>(json, "value");
|
||||
return new RetStmt(SourceRange::json(), value);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,22 +0,0 @@
|
||||
#include "AST/Stmt/TraitAlias.h"
|
||||
#include "AST/Def.h"
|
||||
|
||||
namespace plsm {
|
||||
|
||||
boost::json::value ast::TraitAlias::toJson() {
|
||||
return {
|
||||
{"@type", "TraitAlias"},
|
||||
{"alias", alias},
|
||||
{"aliased", aliased},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::TraitAlias>
|
||||
ast::TraitAlias::fromJson(boost::json::value json) {
|
||||
auto alias = getJsonValue<ast::TraitAlias, std::string>(json, "alias");
|
||||
auto aliased = getJsonValue<ast::TraitAlias, std::string>(json, "aliased");
|
||||
return std::make_unique<ast::TraitAlias>(ast::Location::json(), alias,
|
||||
aliased);
|
||||
}
|
||||
|
||||
} // namespace plsm
|
@ -1,23 +0,0 @@
|
||||
#include "AST/Def.h"
|
||||
#include "AST/Stmt/FnDef.h"
|
||||
#include "AST/Stmt/TraitDef.h"
|
||||
#include "Utils.h"
|
||||
|
||||
namespace plsm {
|
||||
|
||||
boost::json::value ast::TraitDef::toJson() {
|
||||
return {
|
||||
{"@type", "TraitDef"},
|
||||
{"name", name},
|
||||
{"traits", utils::mapToJson(traits)},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::TraitDef>
|
||||
ast::TraitDef::fromJson(boost::json::value json) {
|
||||
auto name = getJsonValue<ast::TraitDef, std::string>(json, "name");
|
||||
auto traits = fromJsonVector<ast::TraitDef, ast::FnDef>(json, "traits");
|
||||
return std::make_unique<ast::TraitDef>(ast::Location::json(), name, traits);
|
||||
}
|
||||
|
||||
} // namespace plsm
|
@ -1,18 +0,0 @@
|
||||
#include "AST/Def.h"
|
||||
|
||||
namespace plsm {
|
||||
|
||||
boost::json::value ast::TypeAlias::toJson() {
|
||||
return {
|
||||
{"@type", "TypeAlias"},
|
||||
{"alias", alias},
|
||||
{"type", type->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::TypeAlias>
|
||||
ast::TypeAlias::fromJson(boost::json::value json) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
} // namespace plsm
|
@ -1,25 +0,0 @@
|
||||
#include "AST/Def.h"
|
||||
#include "AST/Stmt/FnDef.h"
|
||||
#include "AST/Stmt/TypeDef.h"
|
||||
#include "Utils.h"
|
||||
#include <memory>
|
||||
|
||||
namespace plsm {
|
||||
|
||||
boost::json::value ast::TypeDef::toJson() {
|
||||
return {
|
||||
{"@type", "TypeDef"},
|
||||
{"name", name},
|
||||
{"attrs", utils::mapToJson(attrs)},
|
||||
{"members", utils::mapToJson(members)},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::TypeDef> ast::TypeDef::fromJson(boost::json::value json) {
|
||||
auto name = getJsonValue<ast::TypeDef, std::string>(json, "name");
|
||||
auto attrs = fromJsonVector<ast::TypeDef, ast::FnArg>(json, "attrs");
|
||||
auto members = fromJsonVector<ast::TypeDef, ast::FnDef>(json, "members");
|
||||
return std::make_unique<ast::TypeDef>(ast::Location::json(), name, attrs, members);
|
||||
}
|
||||
|
||||
} // namespace plsm
|
@ -1,21 +0,0 @@
|
||||
#include "AST/Def.h"
|
||||
|
||||
namespace plsm {
|
||||
|
||||
boost::json::value ast::ValDecl::toJson() {
|
||||
return {
|
||||
{"@type", "ValDecl"},
|
||||
{"name", name},
|
||||
{"type", type->toJson()},
|
||||
{"value", value->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::ValDecl> ast::ValDecl::fromJson(boost::json::value json) {
|
||||
auto name = getJsonValue<ast::ValDecl, std::string>(json, "name");
|
||||
auto type = fromJsonProperty<ast::ValDecl, ast::Type>(json, "type");
|
||||
auto value = fromJsonProperty<ast::ValDecl, ast::Expr>(json, "value");
|
||||
return std::make_unique<ast::ValDecl>(ast::Location::json(), name, type, value);
|
||||
}
|
||||
|
||||
} // namespace plsm
|
21
compiler/src/AST/Stmt/VarDecl.cpp
Normal file
21
compiler/src/AST/Stmt/VarDecl.cpp
Normal file
@ -0,0 +1,21 @@
|
||||
#include "AST/AST.h"
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
boost::json::value VarDecl::toJson() {
|
||||
return {
|
||||
{"@type", "VarDecl"},
|
||||
{"name", name},
|
||||
{"typeName", typeName->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
VarDecl *VarDecl::fromJson(boost::json::value json) {
|
||||
auto name = getJsonValue<VarDecl, std::string>(json, "name");
|
||||
auto typeName = fromJsonProperty<VarDecl, TypeName>(json, "typeName");
|
||||
return new VarDecl(SourceRange::json(), name, typeName);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
22
compiler/src/AST/Stmt/WhileStmt.cpp
Normal file
22
compiler/src/AST/Stmt/WhileStmt.cpp
Normal file
@ -0,0 +1,22 @@
|
||||
#include "AST/AST.h"
|
||||
#include "Utils.h"
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
boost::json::value WhileStmt::toJson() {
|
||||
return {
|
||||
{"@type", "WhileStmt"},
|
||||
{"condition", condition->toJson()},
|
||||
{"body", utils::mapToJson(body)},
|
||||
};
|
||||
}
|
||||
|
||||
WhileStmt *WhileStmt::fromJson(boost::json::value json) {
|
||||
auto condition = fromJsonProperty<WhileStmt, Expr>(json, "condition");
|
||||
auto body = fromJsonVector<WhileStmt, Stmt>(json, "body");
|
||||
return new WhileStmt(SourceRange::json(), condition, body);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,21 +0,0 @@
|
||||
#include "AST/Def.h"
|
||||
#include "Utils.h"
|
||||
|
||||
namespace plsm {
|
||||
|
||||
boost::json::value ast::ClosureType::toJson() {
|
||||
return {
|
||||
{"@type", "ClosureType"},
|
||||
{"from", utils::mapToJson(from)},
|
||||
{"to", to->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::ClosureType>
|
||||
ast::ClosureType::fromJson(boost::json::value json) {
|
||||
auto from = fromJsonVector<ast::ClosureType, ast::Type>(json, "from");
|
||||
auto to = fromJsonProperty<ast::ClosureType, ast::Type>(json, "to");
|
||||
return std::make_unique<ast::ClosureType>(ast::Location::json(), from, to);
|
||||
}
|
||||
|
||||
} // namespace plsm
|
22
compiler/src/AST/Type/FunctionType.cpp
Normal file
22
compiler/src/AST/Type/FunctionType.cpp
Normal file
@ -0,0 +1,22 @@
|
||||
#include "AST/AST.h"
|
||||
#include "Utils.h"
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
boost::json::value FunctionType::toJson() {
|
||||
return {
|
||||
{"@type", "FunctionType"},
|
||||
{"paramTypes", utils::mapToJson(paramTypes)},
|
||||
{"returnType", returnType->toJson()},
|
||||
};
|
||||
}
|
||||
|
||||
FunctionType *FunctionType::fromJson(boost::json::value json) {
|
||||
auto paramTypes = fromJsonVector<FunctionType, Type>(json, "paramTypes");
|
||||
auto returnType = fromJsonProperty<FunctionType, Type>(json, "returnType");
|
||||
return new FunctionType(paramTypes, returnType);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,22 +0,0 @@
|
||||
#include "AST/Def.h"
|
||||
#include "AST/Type/Generic.h"
|
||||
#include "Utils.h"
|
||||
|
||||
namespace plsm {
|
||||
|
||||
boost::json::value ast::GenericType::toJson() {
|
||||
return {
|
||||
{"@type", "GenericType"},
|
||||
{"name", name},
|
||||
{"types", utils::mapToJson(types)},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::GenericType>
|
||||
ast::GenericType::fromJson(boost::json::value json) {
|
||||
auto name = getJsonValue<ast::GenericType, std::string>(json, "name");
|
||||
auto types = fromJsonVector<ast::GenericType, ast::Type>(json, "types");
|
||||
return std::make_unique<ast::GenericType>(ast::Location::json(), name, types);
|
||||
}
|
||||
|
||||
} // namespace plsm
|
@ -1,19 +0,0 @@
|
||||
#include "AST/Def.h"
|
||||
#include "AST/Type/Named.h"
|
||||
|
||||
namespace plsm {
|
||||
|
||||
boost::json::value ast::NamedType::toJson() {
|
||||
return {
|
||||
{"@type", "NamedType"},
|
||||
{"name", name},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::NamedType>
|
||||
ast::NamedType::fromJson(boost::json::value json) {
|
||||
auto name = getJsonValue<ast::NamedType, std::string>(json, "name");
|
||||
return std::make_unique<ast::NamedType>(ast::Location::json(), name);
|
||||
}
|
||||
|
||||
} // namespace plsm
|
19
compiler/src/AST/Type/PrimitiveType.cpp
Normal file
19
compiler/src/AST/Type/PrimitiveType.cpp
Normal file
@ -0,0 +1,19 @@
|
||||
#include "AST/AST.h"
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
boost::json::value PrimitiveType::toJson() {
|
||||
return {
|
||||
{"@type", "PrimitiveType"},
|
||||
{"name", name},
|
||||
};
|
||||
}
|
||||
|
||||
PrimitiveType *PrimitiveType::fromJson(boost::json::value json) {
|
||||
auto name = getJsonValue<PrimitiveType, std::string>(json, "name");
|
||||
return new PrimitiveType(name);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,20 +0,0 @@
|
||||
#include "AST/Def.h"
|
||||
#include "AST/Type/Tuple.h"
|
||||
#include "Utils.h"
|
||||
|
||||
namespace plsm {
|
||||
|
||||
boost::json::value ast::TupleType::toJson() {
|
||||
return {
|
||||
{"@type", "TupleType"},
|
||||
{"types", utils::mapToJson(types)},
|
||||
};
|
||||
}
|
||||
|
||||
std::unique_ptr<ast::TupleType>
|
||||
ast::TupleType::fromJson(boost::json::value json) {
|
||||
auto types = fromJsonVector<ast::TupleType, ast::Type>(json, "types");
|
||||
return std::make_unique<ast::TupleType>(ast::Location::json(), types);
|
||||
}
|
||||
|
||||
} // namespace plsm
|
16
compiler/src/AST/TypeName/PrimitiveTypeName.cpp
Normal file
16
compiler/src/AST/TypeName/PrimitiveTypeName.cpp
Normal file
@ -0,0 +1,16 @@
|
||||
#include "AST/AST.h"
|
||||
|
||||
namespace plsm {
|
||||
namespace ast {
|
||||
|
||||
boost::json::value PrimitiveTypeName::toJson() {
|
||||
return {{"@type", "PrimitiveTypeName"}, {"name", name}};
|
||||
}
|
||||
|
||||
PrimitiveTypeName *PrimitiveTypeName::fromJson(boost::json::value json) {
|
||||
auto name = getJsonValue<PrimitiveTypeName, std::string>(json, "name");
|
||||
return new PrimitiveTypeName(SourceRange::json(), name);
|
||||
}
|
||||
|
||||
} // namespace ast
|
||||
} // namespace plsm
|
@ -1,21 +1,16 @@
|
||||
#include "Parser.h"
|
||||
|
||||
#include "AST/Def.h"
|
||||
|
||||
#include <any>
|
||||
#include <sstream>
|
||||
|
||||
#include "AST/Module/Module.h"
|
||||
#include "AST/AST.h"
|
||||
#include "plsmBaseVisitor.h"
|
||||
#include "plsmLexer.h"
|
||||
#include "plsmParser.h"
|
||||
|
||||
class ErrorListener : public antlr4::BaseErrorListener {
|
||||
class MyAntlr4ErrorListener : public antlr4::BaseErrorListener {
|
||||
std::string file;
|
||||
std::string *error;
|
||||
|
||||
public:
|
||||
ErrorListener(const std::string &file, std::string *error)
|
||||
MyAntlr4ErrorListener(const std::string &file, std::string *error)
|
||||
: file(file), error(error) {}
|
||||
|
||||
virtual void syntaxError(antlr4::Recognizer *recognizer,
|
||||
@ -30,423 +25,7 @@ public:
|
||||
|
||||
namespace plsm {
|
||||
|
||||
class Visitor : public plsmBaseVisitor {
|
||||
private:
|
||||
const std::string file;
|
||||
|
||||
public:
|
||||
Visitor(const std::string &file) : file(file) {}
|
||||
|
||||
inline ast::Location loc(antlr4::ParserRuleContext *ctx) {
|
||||
return ast::Location(
|
||||
file,
|
||||
std::pair<size_t, size_t>(ctx->getStart()->getLine(),
|
||||
ctx->getStart()->getCharPositionInLine()),
|
||||
std::pair<size_t, size_t>(ctx->getStop()->getLine(),
|
||||
ctx->getStop()->getCharPositionInLine()));
|
||||
}
|
||||
|
||||
template <typename T> inline T visitT(antlr4::tree::ParseTree *ctx) {
|
||||
return std::any_cast<T>(visit(ctx));
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
inline std::unique_ptr<T> visitU(antlr4::tree::ParseTree *ctx) {
|
||||
return std::unique_ptr<T>(visitT<T *>(ctx));
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
inline std::vector<std::unique_ptr<T>> visitVU(antlr4::tree::ParseTree *ctx) {
|
||||
std::vector<std::unique_ptr<T>> res;
|
||||
for (auto &el : visitT<std::vector<T *>>(ctx))
|
||||
res.push_back(std::unique_ptr<T>(el));
|
||||
return res;
|
||||
}
|
||||
|
||||
virtual std::any visitModule(plsmParser::ModuleContext *ctx) override {
|
||||
auto name = ctx->identifier()->getText();
|
||||
|
||||
std::vector<std::unique_ptr<ast::Import>> imports;
|
||||
for (auto &import : ctx->moduleImport())
|
||||
imports.push_back(visitU<ast::Import>(import));
|
||||
|
||||
std::vector<std::unique_ptr<ast::Stmt>> stmts;
|
||||
for (auto &stmt : ctx->moduleStmt())
|
||||
stmts.push_back(visitU<ast::Stmt>(stmt));
|
||||
|
||||
return std::any(new ast::Module(loc(ctx), name, imports, stmts));
|
||||
}
|
||||
|
||||
virtual std::any
|
||||
visitModuleImport(plsmParser::ModuleImportContext *ctx) override {
|
||||
return std::any(
|
||||
new ast::Import(loc(ctx), visitT<std::string>(ctx->importName())));
|
||||
}
|
||||
|
||||
virtual std::any
|
||||
visitImportName(plsmParser::ImportNameContext *ctx) override {
|
||||
auto name = ctx->identifier(0)->getText();
|
||||
|
||||
for (size_t i = 1; i < ctx->identifier().size(); i++)
|
||||
name = name + "/" + ctx->identifier(i)->getText();
|
||||
|
||||
return std::any(name);
|
||||
}
|
||||
|
||||
virtual std::any
|
||||
visitModuleStmt(plsmParser::ModuleStmtContext *ctx) override {
|
||||
ast::Stmt *stmt;
|
||||
|
||||
if (ctx->let())
|
||||
stmt = (ast::Stmt *)visitT<ast::ValDecl *>(ctx->let());
|
||||
if (ctx->fnDecl())
|
||||
stmt = (ast::Stmt *)visitT<ast::FnDef *>(ctx->fnDecl());
|
||||
if (ctx->fnDef())
|
||||
stmt = (ast::Stmt *)visitT<ast::FnDef *>(ctx->fnDef());
|
||||
if (ctx->traitDef())
|
||||
stmt = (ast::Stmt *)visitT<ast::Stmt *>(ctx->traitDef());
|
||||
if (ctx->typeDef())
|
||||
stmt = (ast::Stmt *)visitT<ast::Stmt *>(ctx->typeDef());
|
||||
|
||||
return std::any(stmt);
|
||||
}
|
||||
|
||||
virtual std::any visitTraitDef(plsmParser::TraitDefContext *ctx) override {
|
||||
auto name = ctx->identifier(0)->getText();
|
||||
|
||||
if (ctx->identifier(1)) {
|
||||
auto aliased = ctx->identifier(1)->getText();
|
||||
return std::any(
|
||||
(ast::Stmt *)new ast::TraitAlias(loc(ctx), name, aliased));
|
||||
}
|
||||
|
||||
std::vector<std::unique_ptr<ast::FnDef>> fns;
|
||||
for (auto &decl : ctx->fnDecl())
|
||||
fns.push_back(visitU<ast::FnDef>(decl));
|
||||
|
||||
return std::any((ast::Stmt *)new ast::TraitDef(loc(ctx), name, fns));
|
||||
}
|
||||
|
||||
virtual std::any visitTypeDef(plsmParser::TypeDefContext *ctx) override {
|
||||
auto name = ctx->identifier()->getText();
|
||||
|
||||
if (ctx->type()) {
|
||||
auto gen = visitU<ast::Type>(ctx->type());
|
||||
return std::any((ast::Stmt *)new ast::TypeAlias(loc(ctx), name, gen));
|
||||
}
|
||||
|
||||
std::vector<std::unique_ptr<ast::FnArg>> attrs;
|
||||
if (ctx->fnDefArgs())
|
||||
attrs = visitVU<ast::FnArg>(ctx->fnDefArgs());
|
||||
|
||||
std::vector<std::unique_ptr<ast::FnDef>> members;
|
||||
for (auto &def : ctx->fnDef())
|
||||
members.push_back(visitU<ast::FnDef>(def));
|
||||
for (auto &decl : ctx->fnDecl())
|
||||
members.push_back(visitU<ast::FnDef>(decl));
|
||||
|
||||
return std::any(
|
||||
(ast::Stmt *)new ast::TypeDef(loc(ctx), name, attrs, members));
|
||||
}
|
||||
|
||||
virtual std::any visitFnDef(plsmParser::FnDefContext *ctx) override {
|
||||
auto name = ctx->identifier()->getText();
|
||||
|
||||
std::vector<std::unique_ptr<ast::FnArg>> args;
|
||||
if (ctx->fnDefArgs())
|
||||
args = std::move(visitVU<ast::FnArg>(ctx->fnDefArgs()));
|
||||
|
||||
auto returnType = visitU<ast::Type>(ctx->type());
|
||||
auto body = visitU<ast::Expr>(ctx->expr());
|
||||
|
||||
return std::any(new ast::FnDef(loc(ctx), name, args, returnType, body));
|
||||
}
|
||||
|
||||
virtual std::any visitFnDefArgs(plsmParser::FnDefArgsContext *ctx) override {
|
||||
std::vector<ast::FnArg *> args;
|
||||
|
||||
for (size_t i = 0; i < ctx->children.size(); i += 3) {
|
||||
auto name = ctx->children[i]->getText();
|
||||
auto type = visitU<ast::Type>(ctx->children[i + 1]);
|
||||
args.push_back(new ast::FnArg(loc(ctx), name, type));
|
||||
}
|
||||
|
||||
return std::any(args);
|
||||
}
|
||||
|
||||
virtual std::any visitFnDecl(plsmParser::FnDeclContext *ctx) override {
|
||||
auto name = ctx->identifier()->getText();
|
||||
|
||||
std::vector<std::unique_ptr<ast::FnArg>> args;
|
||||
if (ctx->fnDeclArgs())
|
||||
args = visitVU<ast::FnArg>(ctx->fnDeclArgs());
|
||||
|
||||
auto returnType = visitU<ast::Type>(ctx->type());
|
||||
auto body = std::unique_ptr<ast::Expr>(nullptr);
|
||||
|
||||
return std::any(new ast::FnDef(loc(ctx), name, args, returnType, body));
|
||||
}
|
||||
|
||||
virtual std::any
|
||||
visitFnDeclArgs(plsmParser::FnDeclArgsContext *ctx) override {
|
||||
std::vector<ast::FnArg *> args;
|
||||
|
||||
for (size_t i = 0; i < ctx->children.size(); i++) {
|
||||
std::string name;
|
||||
if (dynamic_cast<plsmParser::IdentifierContext *>(ctx->children[i]))
|
||||
name = ctx->children[i++]->getText();
|
||||
|
||||
auto type = visitU<ast::Type>(ctx->children[i++]);
|
||||
|
||||
args.push_back(new ast::FnArg(loc(ctx), name, type));
|
||||
}
|
||||
|
||||
return std::any(args);
|
||||
}
|
||||
|
||||
virtual std::any visitLet(plsmParser::LetContext *ctx) override {
|
||||
auto name = ctx->identifier()->getText();
|
||||
|
||||
std::unique_ptr<ast::Type> type(nullptr);
|
||||
if (ctx->type())
|
||||
type = visitU<ast::Type>(ctx->type());
|
||||
|
||||
auto expr = visitU<ast::Expr>(ctx->expr());
|
||||
|
||||
return std::any(new ast::ValDecl(loc(ctx), name, type, expr));
|
||||
}
|
||||
|
||||
virtual std::any visitExprStmt(plsmParser::ExprStmtContext *ctx) override {
|
||||
auto expr = visitU<ast::Expr>(ctx->expr());
|
||||
return std::any(new ast::ExprStmt(loc(ctx), expr));
|
||||
}
|
||||
|
||||
virtual std::any visitType1(plsmParser::Type1Context *ctx) override {
|
||||
if (ctx->type0())
|
||||
return visit(ctx->type0());
|
||||
|
||||
if (ctx->children[0]->getText() == "(") {
|
||||
if (ctx->type())
|
||||
return visit(ctx->type());
|
||||
|
||||
if (ctx->tupleTypeList()) {
|
||||
auto types = visitVU<ast::Type>(ctx->tupleTypeList());
|
||||
return std::any((ast::Type *)new ast::TupleType(loc(ctx), types));
|
||||
}
|
||||
}
|
||||
|
||||
if (ctx->children[0]->getText() == "[") {
|
||||
std::vector<std::unique_ptr<ast::Type>> args;
|
||||
if (ctx->typeList())
|
||||
args = visitVU<ast::Type>(ctx->typeList());
|
||||
|
||||
auto returnType = visitU<ast::Type>(ctx->type());
|
||||
|
||||
return std::any(
|
||||
(ast::Type *)new ast::ClosureType(loc(ctx), args, returnType));
|
||||
}
|
||||
|
||||
throw std::logic_error("type2 not implemented");
|
||||
}
|
||||
|
||||
virtual std::any visitType0(plsmParser::Type0Context *ctx) override {
|
||||
auto name = ctx->identifier()->getText();
|
||||
|
||||
if (ctx->typeList()) {
|
||||
auto types = visitVU<ast::Type>(ctx->typeList());
|
||||
return std::any((ast::Type *)new ast::GenericType(loc(ctx), name, types));
|
||||
}
|
||||
|
||||
return std::any((ast::Type *)new ast::NamedType(loc(ctx), name));
|
||||
}
|
||||
|
||||
virtual std::any
|
||||
visitTupleTypeList(plsmParser::TupleTypeListContext *ctx) override {
|
||||
std::vector<ast::Type *> types;
|
||||
for (auto &type : ctx->type())
|
||||
types.push_back(visitT<ast::Type *>(type));
|
||||
|
||||
return std::any(types);
|
||||
}
|
||||
|
||||
virtual std::any visitTypeList(plsmParser::TypeListContext *ctx) override {
|
||||
std::vector<ast::Type *> types;
|
||||
for (auto &type : ctx->type())
|
||||
types.push_back(visitT<ast::Type *>(type));
|
||||
|
||||
return std::any(types);
|
||||
}
|
||||
|
||||
virtual std::any visitExpr3(plsmParser::Expr3Context *ctx) override {
|
||||
if (ctx->expr2())
|
||||
return visit(ctx->expr2());
|
||||
|
||||
// closure
|
||||
if (ctx->children[0]->getText() == "[") {
|
||||
std::vector<std::unique_ptr<ast::FnArg>> args;
|
||||
if (ctx->fnDefArgs())
|
||||
args = visitVU<ast::FnArg>(ctx->fnDefArgs());
|
||||
|
||||
auto body = visitU<ast::Expr>(ctx->expr());
|
||||
|
||||
return std::any((ast::Expr *)new ast::Closure(loc(ctx), args, body));
|
||||
}
|
||||
|
||||
// block
|
||||
if (ctx->children[0]->getText() == "{") {
|
||||
std::vector<std::unique_ptr<ast::Stmt>> stmts;
|
||||
for (auto &stmt : ctx->blockStmt())
|
||||
stmts.push_back(visitU<ast::Stmt>(stmt));
|
||||
|
||||
auto result = visitU<ast::Expr>(ctx->expr());
|
||||
|
||||
return std::any((ast::Expr *)new ast::BlockExpr(loc(ctx), stmts, result));
|
||||
}
|
||||
|
||||
throw std::logic_error("expr3 not implemented");
|
||||
}
|
||||
|
||||
virtual std::any visitExpr2(plsmParser::Expr2Context *ctx) override {
|
||||
if (ctx->expr2()) {
|
||||
auto left = visitU<ast::Expr>(ctx->expr2());
|
||||
auto op = ctx->operator_()->getText();
|
||||
auto right = visitU<ast::Expr>(ctx->expr1());
|
||||
return std::any((ast::Expr *)new ast::BinExpr(loc(ctx), left, op, right));
|
||||
}
|
||||
|
||||
return visit(ctx->expr1());
|
||||
}
|
||||
|
||||
virtual std::any visitExpr1(plsmParser::Expr1Context *ctx) override {
|
||||
if (ctx->operator_()) {
|
||||
auto op = ctx->operator_()->getText();
|
||||
auto expr = visitU<ast::Expr>(ctx->expr0());
|
||||
return std::any((ast::Expr *)new ast::UnaryExpr(loc(ctx), op, expr));
|
||||
}
|
||||
|
||||
return visit(ctx->expr0());
|
||||
}
|
||||
|
||||
virtual std::any visitExpr0(plsmParser::Expr0Context *ctx) override {
|
||||
if (ctx->literal())
|
||||
return visit(ctx->literal());
|
||||
|
||||
if (ctx->expr()) {
|
||||
auto expr = visitU<ast::Expr>(ctx->expr());
|
||||
return std::any((ast::Expr *)new ast::PrefExpr(loc(ctx), expr));
|
||||
}
|
||||
|
||||
if (ctx->expr0()) {
|
||||
auto expr = visitU<ast::Expr>(ctx->expr0());
|
||||
|
||||
// property accessor
|
||||
if (ctx->identifier()) {
|
||||
auto name = ctx->identifier()->getText();
|
||||
return std::any((ast::Expr *)new ast::PropExpr(loc(ctx), expr, name));
|
||||
}
|
||||
|
||||
// function/closure call
|
||||
std::vector<std::unique_ptr<ast::Expr>> args;
|
||||
if (ctx->exprList())
|
||||
args = visitVU<ast::Expr>(ctx->exprList());
|
||||
|
||||
return std::any((ast::Expr *)new ast::CallExpr(loc(ctx), expr, args));
|
||||
}
|
||||
|
||||
// tuple
|
||||
if (ctx->tupleExprList()) {
|
||||
auto values = visitVU<ast::Expr>(ctx->tupleExprList());
|
||||
return std::any((ast::Expr *)new ast::Tuple(loc(ctx), values));
|
||||
}
|
||||
|
||||
// identifier
|
||||
if (ctx->identifier()) {
|
||||
auto name = ctx->identifier()->getText();
|
||||
return std::any((ast::Expr *)new ast::Identifier(loc(ctx), name));
|
||||
}
|
||||
|
||||
throw std::logic_error("expr0 not implemented");
|
||||
}
|
||||
|
||||
virtual std::any visitBlockStmt(plsmParser::BlockStmtContext *ctx) override {
|
||||
ast::Stmt *stmt;
|
||||
|
||||
if (ctx->let())
|
||||
stmt = (ast::Stmt *)visitT<ast::ValDecl *>(ctx->let());
|
||||
if (ctx->exprStmt())
|
||||
stmt = (ast::Stmt *)visitT<ast::ExprStmt *>(ctx->exprStmt());
|
||||
if (ctx->fnDef())
|
||||
stmt = (ast::Stmt *)visitT<ast::FnDef *>(ctx->fnDef());
|
||||
|
||||
return std::any(stmt);
|
||||
}
|
||||
|
||||
virtual std::any
|
||||
visitTupleExprList(plsmParser::TupleExprListContext *ctx) override {
|
||||
std::vector<ast::Expr *> exprs;
|
||||
for (auto &expr : ctx->expr())
|
||||
exprs.push_back(visitT<ast::Expr *>(expr));
|
||||
|
||||
return std::any(exprs);
|
||||
}
|
||||
|
||||
virtual std::any visitExprList(plsmParser::ExprListContext *ctx) override {
|
||||
std::vector<ast::Expr *> exprs;
|
||||
for (auto &expr : ctx->expr())
|
||||
exprs.push_back(visitT<ast::Expr *>(expr));
|
||||
|
||||
return std::any(exprs);
|
||||
}
|
||||
|
||||
virtual std::any
|
||||
visitIdentifierList(plsmParser::IdentifierListContext *ctx) override {
|
||||
std::vector<std::string> identifiers;
|
||||
for (auto &identifier : ctx->identifier())
|
||||
identifiers.push_back(visitT<std::string>(identifier));
|
||||
|
||||
return std::any(identifiers);
|
||||
}
|
||||
|
||||
virtual std::any visitLiteral(plsmParser::LiteralContext *ctx) override {
|
||||
if (ctx->NULL_)
|
||||
return std::any((ast::Expr *)new ast::NullValue(loc(ctx)));
|
||||
|
||||
if (ctx->INT_LIT()) {
|
||||
auto text = ctx->INT_LIT()->getText();
|
||||
|
||||
int64_t value;
|
||||
|
||||
if (!text.rfind("0x", 0))
|
||||
value = std::strtol(text.substr(2).data(), NULL, 16);
|
||||
|
||||
else if (!text.rfind("0o", 0))
|
||||
value = std::strtol(text.substr(2).data(), NULL, 8);
|
||||
|
||||
else if (!text.rfind("0b", 0))
|
||||
value = std::strtol(text.substr(2).data(), NULL, 2);
|
||||
|
||||
else value = std::strtol(text.data(), NULL, 10);
|
||||
|
||||
return std::any((ast::Expr *)new ast::IntValue(loc(ctx), value));
|
||||
}
|
||||
|
||||
if (ctx->FLOAT_LIT()) {
|
||||
auto text = ctx->FLOAT_LIT()->getText();
|
||||
|
||||
if (text.at(text.size() - 1) == '.')
|
||||
text += "0";
|
||||
if (text.at(0) == '0')
|
||||
text = "0" + text;
|
||||
|
||||
double value = std::strtod(text.data(), NULL);
|
||||
return std::any((ast::Expr *)new ast::FloatValue(loc(ctx), value));
|
||||
}
|
||||
|
||||
throw std::logic_error("literal not implemented");
|
||||
}
|
||||
};
|
||||
|
||||
std::unique_ptr<ast::Module> parse(const std::string &file,
|
||||
std::shared_ptr<ast::Module> parse(const std::string &file,
|
||||
const std::string &input) {
|
||||
auto istream = antlr4::ANTLRInputStream(input);
|
||||
auto lexer = plsmLexer(&istream);
|
||||
@ -454,17 +33,12 @@ std::unique_ptr<ast::Module> parse(const std::string &file,
|
||||
auto parser = plsmParser(&tokens);
|
||||
|
||||
std::string error;
|
||||
ErrorListener listener(file, &error);
|
||||
MyAntlr4ErrorListener listener(file, &error);
|
||||
parser.removeErrorListeners();
|
||||
parser.addErrorListener(&listener);
|
||||
|
||||
auto tree = parser.module();
|
||||
|
||||
if (error.size())
|
||||
throw std::runtime_error(error);
|
||||
|
||||
auto module = std::any_cast<ast::Module *>(Visitor(file).visitModule(tree));
|
||||
return std::unique_ptr<ast::Module>(module);
|
||||
return std::shared_ptr<Module>(tree->ast);
|
||||
}
|
||||
|
||||
} // namespace plsm
|
||||
|
@ -1,12 +1,11 @@
|
||||
#include <iostream>
|
||||
#include <fstream>
|
||||
#include <iostream>
|
||||
#include <istream>
|
||||
#include <sstream>
|
||||
|
||||
#include "Parser.h"
|
||||
|
||||
static std::string readFile(const std::string &path)
|
||||
{
|
||||
static std::string readFile(const std::string &path) {
|
||||
std::ifstream f(path);
|
||||
auto data = (std::stringstream() << f.rdbuf()).str();
|
||||
f.close();
|
||||
@ -14,10 +13,8 @@ static std::string readFile(const std::string &path)
|
||||
return data;
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
if (argc != 2)
|
||||
{
|
||||
int main(int argc, char *argv[]) {
|
||||
if (argc != 2) {
|
||||
std::cout << "Usage:" << std::endl
|
||||
<< "\t" << argv[0] << " <path/to/file>" << std::endl;
|
||||
exit(EXIT_FAILURE);
|
||||
@ -25,19 +22,17 @@ int main(int argc, char *argv[])
|
||||
|
||||
auto input = readFile(argv[1]);
|
||||
|
||||
std::cout << input << std::endl;
|
||||
// std::cout << input << std::endl;
|
||||
|
||||
try
|
||||
{
|
||||
try {
|
||||
auto module = plsm::parse(argv[1], input);
|
||||
std::cout << module->toJsonString() << std::endl;
|
||||
|
||||
std::cout << "\n\n";
|
||||
// std::cout << "\n\n";
|
||||
|
||||
std::cout << plsm::ast::Module::fromJson(module->toJson())->toJson() << std::endl;
|
||||
}
|
||||
catch (std::runtime_error &err)
|
||||
{
|
||||
// std::cout << plsm::ast::Module::fromJson(module->toJson())->toJson() <<
|
||||
// std::endl;
|
||||
} catch (std::runtime_error &err) {
|
||||
std::cerr << err.what() << std::endl;
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
142
compiler/test.json
Normal file
142
compiler/test.json
Normal file
@ -0,0 +1,142 @@
|
||||
{
|
||||
"@type": "Module",
|
||||
"name": "default",
|
||||
"imports": [],
|
||||
"stmts": [
|
||||
{
|
||||
"@type": "FnDecl",
|
||||
"name": "main",
|
||||
"params": [],
|
||||
"returnTypeName": {
|
||||
"@type": "PrimitiveTypeName",
|
||||
"name": "i64"
|
||||
},
|
||||
"body": [
|
||||
{
|
||||
"@type": "VarDecl",
|
||||
"name": "asdf",
|
||||
"typeName": {
|
||||
"@type": "PrimitiveTypeName",
|
||||
"name": "int"
|
||||
}
|
||||
},
|
||||
{
|
||||
"@type": "AssignStmt",
|
||||
"lval": {
|
||||
"@type": "Identifier",
|
||||
"name": "asdf"
|
||||
},
|
||||
"rval": 100
|
||||
},
|
||||
{
|
||||
"@type": "IfStmt",
|
||||
"condition": {
|
||||
"@type": "BinExpr",
|
||||
"op": ">",
|
||||
"lhs": {
|
||||
"@type": "Identifier",
|
||||
"name": "asdf"
|
||||
},
|
||||
"rhs": 1000
|
||||
},
|
||||
"ifBody": [
|
||||
{
|
||||
"@type": "AssignStmt",
|
||||
"lval": {
|
||||
"@type": "Identifier",
|
||||
"name": "a"
|
||||
},
|
||||
"rval": 1
|
||||
}
|
||||
],
|
||||
"elseBody": [
|
||||
{
|
||||
"@type": "IfStmt",
|
||||
"condition": {
|
||||
"@type": "BinExpr",
|
||||
"op": ">",
|
||||
"lhs": {
|
||||
"@type": "Identifier",
|
||||
"name": "asdf"
|
||||
},
|
||||
"rhs": 500
|
||||
},
|
||||
"ifBody": [
|
||||
{
|
||||
"@type": "AssignStmt",
|
||||
"lval": {
|
||||
"@type": "Identifier",
|
||||
"name": "a"
|
||||
},
|
||||
"rval": 2
|
||||
}
|
||||
],
|
||||
"elseBody": [
|
||||
{
|
||||
"@type": "AssignStmt",
|
||||
"lval": {
|
||||
"@type": "Identifier",
|
||||
"name": "a"
|
||||
},
|
||||
"rval": 3
|
||||
}
|
||||
]
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"@type": "WhileStmt",
|
||||
"condition": {
|
||||
"@type": "BinExpr",
|
||||
"op": "<",
|
||||
"lhs": {
|
||||
"@type": "Identifier",
|
||||
"name": "a"
|
||||
},
|
||||
"rhs": 10
|
||||
},
|
||||
"body": [
|
||||
{
|
||||
"@type": "AssignStmt",
|
||||
"lval": {
|
||||
"@type": "Identifier",
|
||||
"name": "a"
|
||||
},
|
||||
"rval": {
|
||||
"@type": "Identifier",
|
||||
"name": "a"
|
||||
}
|
||||
},
|
||||
{
|
||||
"@type": "ExprStmt",
|
||||
"expr": {
|
||||
"@type": "UnExpr",
|
||||
"op": "+",
|
||||
"expr": 1
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"@type": "RetStmt",
|
||||
"value": {
|
||||
"@type": "BinExpr",
|
||||
"op": "+",
|
||||
"lhs": {
|
||||
"@type": "BinExpr",
|
||||
"op": "*",
|
||||
"lhs": 3,
|
||||
"rhs": 10
|
||||
},
|
||||
"rhs": {
|
||||
"@type": "BinExpr",
|
||||
"op": "*",
|
||||
"lhs": 21,
|
||||
"rhs": 2
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
18
examples/new.plsm
Normal file
18
examples/new.plsm
Normal file
@ -0,0 +1,18 @@
|
||||
fun main() i64 {
|
||||
var asdf : int;
|
||||
asdf = 100;
|
||||
|
||||
if (asdf > 1000) {
|
||||
a = 1;
|
||||
} else if (asdf > 500) {
|
||||
a = 2;
|
||||
} else {
|
||||
a = 3;
|
||||
}
|
||||
|
||||
while (a < 10) {
|
||||
a = a + 1;
|
||||
}
|
||||
|
||||
ret 3 * 10 + 21.0 * 2;
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user