some progress
This commit is contained in:
parent
055a2c0ef7
commit
99ac38be63
@ -11,9 +11,12 @@
|
|||||||
|
|
||||||
#include "Stmt/ExprStmt.h"
|
#include "Stmt/ExprStmt.h"
|
||||||
#include "Stmt/FnDecl.h"
|
#include "Stmt/FnDecl.h"
|
||||||
|
#include "Stmt/TraitDecl.h"
|
||||||
|
#include "Stmt/TypeDecl.h"
|
||||||
#include "Stmt/ValDecl.h"
|
#include "Stmt/ValDecl.h"
|
||||||
|
|
||||||
#include "Type/Function.h"
|
#include "Type/Function.h"
|
||||||
|
#include "Type/Generic.h"
|
||||||
#include "Type/Named.h"
|
#include "Type/Named.h"
|
||||||
#include "Type/Tuple.h"
|
#include "Type/Tuple.h"
|
||||||
|
|
||||||
|
@ -13,6 +13,7 @@ namespace ast
|
|||||||
|
|
||||||
~CallExpr()
|
~CallExpr()
|
||||||
{
|
{
|
||||||
|
delete callee;
|
||||||
for (auto &arg : args)
|
for (auto &arg : args)
|
||||||
delete arg;
|
delete arg;
|
||||||
}
|
}
|
||||||
|
19
compiler/include/AST/Expr/Closure.h
Normal file
19
compiler/include/AST/Expr/Closure.h
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "AST/Base.h"
|
||||||
|
#include <string>
|
||||||
|
#include <vector>
|
||||||
|
|
||||||
|
namespace ast
|
||||||
|
{
|
||||||
|
class Closure : public Expr
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
Closure(const std::vector<std::string> &args, const Expr *body)
|
||||||
|
: args(std::move(args)), body(body) {}
|
||||||
|
~Closure() { delete body; }
|
||||||
|
|
||||||
|
const std::vector<std::string> args;
|
||||||
|
const Expr *body;
|
||||||
|
};
|
||||||
|
}
|
25
compiler/include/AST/Stmt/TraitDecl.h
Normal file
25
compiler/include/AST/Stmt/TraitDecl.h
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "AST/Base.h"
|
||||||
|
#include <vector>
|
||||||
|
#include <string>
|
||||||
|
|
||||||
|
namespace ast
|
||||||
|
{
|
||||||
|
class FnDecl;
|
||||||
|
|
||||||
|
class TraitDecl : public Stmt
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
TraitDecl(const std::string &name, const std::vector<FnDecl *> &traits)
|
||||||
|
: name(name), traits(std::move(traits)) {}
|
||||||
|
~TraitDecl()
|
||||||
|
{
|
||||||
|
for (auto &trait : traits)
|
||||||
|
delete trait;
|
||||||
|
}
|
||||||
|
|
||||||
|
const std::string name;
|
||||||
|
const std::vector<FnDecl *> traits;
|
||||||
|
};
|
||||||
|
}
|
31
compiler/include/AST/Stmt/TypeDecl.h
Normal file
31
compiler/include/AST/Stmt/TypeDecl.h
Normal file
@ -0,0 +1,31 @@
|
|||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "AST/Base.h"
|
||||||
|
#include <vector>
|
||||||
|
#include <string>
|
||||||
|
|
||||||
|
namespace ast
|
||||||
|
{
|
||||||
|
class FnDecl;
|
||||||
|
|
||||||
|
typedef std::pair<std::string, Type *> TypeAttr;
|
||||||
|
|
||||||
|
class TypeDecl : public Stmt
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
TypeDecl(const std::string &name, const std::vector<TypeAttr> &attrs, const std::vector<FnDecl *> &members)
|
||||||
|
: name(name), attrs(std::move(attrs)), members(std::move(members)) {}
|
||||||
|
~TypeDecl()
|
||||||
|
{
|
||||||
|
for (auto &attr : attrs)
|
||||||
|
delete attr.second;
|
||||||
|
|
||||||
|
for (auto &member : members)
|
||||||
|
delete member;
|
||||||
|
}
|
||||||
|
|
||||||
|
const std::string name;
|
||||||
|
const std::vector<TypeAttr> attrs;
|
||||||
|
const std::vector<FnDecl *> members;
|
||||||
|
};
|
||||||
|
}
|
24
compiler/include/AST/Type/Generic.h
Normal file
24
compiler/include/AST/Type/Generic.h
Normal file
@ -0,0 +1,24 @@
|
|||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "AST/Base.h"
|
||||||
|
#include <string>
|
||||||
|
#include <vector>
|
||||||
|
|
||||||
|
namespace ast
|
||||||
|
{
|
||||||
|
class GenericType : public Type
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
GenericType(const std::string &name, const std::vector<Type *> &types)
|
||||||
|
: name(name), types(std::move(types)) {}
|
||||||
|
|
||||||
|
~GenericType()
|
||||||
|
{
|
||||||
|
for (auto &type : types)
|
||||||
|
delete type;
|
||||||
|
}
|
||||||
|
|
||||||
|
const std::string name;
|
||||||
|
const std::vector<Type *> types;
|
||||||
|
};
|
||||||
|
}
|
18
compiler/include/Parser.h
Normal file
18
compiler/include/Parser.h
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <string>
|
||||||
|
|
||||||
|
#include "AST/Def.h"
|
||||||
|
#include "parser.gen.h"
|
||||||
|
|
||||||
|
class Parser
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
Parser() {}
|
||||||
|
|
||||||
|
ast::Module *parse(const std::string &file, const std::stringstream &input);
|
||||||
|
|
||||||
|
std::string file;
|
||||||
|
yy::location location;
|
||||||
|
ast::Module *module;
|
||||||
|
};
|
@ -1,25 +0,0 @@
|
|||||||
#pragma once
|
|
||||||
|
|
||||||
#include <string>
|
|
||||||
|
|
||||||
#include "AST/Def.h"
|
|
||||||
#include "parser.gen.h"
|
|
||||||
|
|
||||||
class ParserDriver
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
ParserDriver() {}
|
|
||||||
~ParserDriver() { delete module; }
|
|
||||||
|
|
||||||
int parse(const std::string &input);
|
|
||||||
|
|
||||||
void startLexer();
|
|
||||||
void stopLexer();
|
|
||||||
|
|
||||||
std::string file;
|
|
||||||
yy::location location;
|
|
||||||
ast::Module *module;
|
|
||||||
};
|
|
||||||
|
|
||||||
#define YY_DECL yy::parser::symbol_type yylex(ParserDriver &driver)
|
|
||||||
YY_DECL;
|
|
@ -1,6 +1,9 @@
|
|||||||
%{
|
%{
|
||||||
#include "parser.gen.h"
|
#include "parser.gen.h"
|
||||||
#include "ParserDriver.h"
|
#include "Parser.h"
|
||||||
|
|
||||||
|
#undef YY_DECL
|
||||||
|
#define YY_DECL yy::parser::symbol_type yylex(Parser &driver)
|
||||||
|
|
||||||
#define yyterminate() yy::parser::make_END(yy::location())
|
#define yyterminate() yy::parser::make_END(yy::location())
|
||||||
|
|
||||||
@ -16,7 +19,7 @@ hexdigit [0-9a-fA-F]
|
|||||||
|
|
||||||
letter [a-zA-Z]
|
letter [a-zA-Z]
|
||||||
|
|
||||||
opchar ("+"|"-"|"*"|"/"|"%"|"!"|"&"|"$"|"§"|"|"|"="|"<"|">"|"?"|"~"|"#"|":"|"^"|"\\")
|
opchar ("+"|"-"|"*"|"/"|"%"|"!"|"&"|"$"|"§"|"|"|"="|"<"|">"|"?"|"~"|"#"|":"|"^"|"\\"|".")
|
||||||
|
|
||||||
whitespace [ \n\t\r\v]+
|
whitespace [ \n\t\r\v]+
|
||||||
|
|
||||||
@ -33,9 +36,9 @@ whitespace [ \n\t\r\v]+
|
|||||||
{opchar}+ { std::string text = yytext;
|
{opchar}+ { std::string text = yytext;
|
||||||
if (text == "=") return _token(EQUALS);
|
if (text == "=") return _token(EQUALS);
|
||||||
if (text == "->") return _token(RARR);
|
if (text == "->") return _token(RARR);
|
||||||
|
if (text == ".") return _token(DOT);
|
||||||
return _token(OPERATOR); }
|
return _token(OPERATOR); }
|
||||||
|
|
||||||
"." { return _token(DOT); }
|
|
||||||
"," { return _token(COMMA); }
|
"," { return _token(COMMA); }
|
||||||
";" { return _token(SEMI); }
|
";" { return _token(SEMI); }
|
||||||
"(" { return _token(LPAREN); }
|
"(" { return _token(LPAREN); }
|
||||||
@ -62,9 +65,3 @@ whitespace [ \n\t\r\v]+
|
|||||||
{whitespace} { ; }
|
{whitespace} { ; }
|
||||||
|
|
||||||
%%
|
%%
|
||||||
|
|
||||||
void ParserDriver::startLexer() {
|
|
||||||
yy_scan_string(this->file.data());
|
|
||||||
}
|
|
||||||
|
|
||||||
void ParserDriver::stopLexer() {}
|
|
||||||
|
@ -19,14 +19,15 @@
|
|||||||
|
|
||||||
%code requires {
|
%code requires {
|
||||||
#include "AST/Def.h"
|
#include "AST/Def.h"
|
||||||
class ParserDriver;
|
class Parser;
|
||||||
}
|
}
|
||||||
|
|
||||||
%lex-param { ParserDriver &driver }
|
%lex-param { Parser &driver }
|
||||||
%parse-param { ParserDriver &driver }
|
%parse-param { Parser &driver }
|
||||||
|
|
||||||
%code {
|
%code {
|
||||||
#include "ParserDriver.h"
|
#include "Parser.h"
|
||||||
|
yy::parser::symbol_type yylex(Parser &driver);
|
||||||
}
|
}
|
||||||
|
|
||||||
%token <long> INT "integer literal"
|
%token <long> INT "integer literal"
|
||||||
@ -70,7 +71,8 @@ class ParserDriver;
|
|||||||
blockStmt
|
blockStmt
|
||||||
;
|
;
|
||||||
|
|
||||||
%type <ast::FnDecl *> extFnDecl fnDecl;
|
%type <std::vector<ast::FnDecl *>> fnDecls fnDecls0;
|
||||||
|
%type <ast::FnDecl *> fnDecl fnDef;
|
||||||
%type <ast::ValDecl *> valDecl;
|
%type <ast::ValDecl *> valDecl;
|
||||||
|
|
||||||
%type <std::vector<ast::Type *>>
|
%type <std::vector<ast::Type *>>
|
||||||
@ -79,14 +81,9 @@ class ParserDriver;
|
|||||||
fnTypeArgs
|
fnTypeArgs
|
||||||
;
|
;
|
||||||
|
|
||||||
%type <ast::Type *>
|
%type <ast::Type *> type type1;
|
||||||
type
|
|
||||||
;
|
|
||||||
|
|
||||||
%type <std::vector<ast::Expr *>>
|
%type <std::vector<ast::Expr *>> exprs args;
|
||||||
exprs
|
|
||||||
args
|
|
||||||
;
|
|
||||||
|
|
||||||
%type <ast::Expr *>
|
%type <ast::Expr *>
|
||||||
expr
|
expr
|
||||||
@ -98,10 +95,7 @@ class ParserDriver;
|
|||||||
;
|
;
|
||||||
|
|
||||||
%type <ast::FnArg> fnArg;
|
%type <ast::FnArg> fnArg;
|
||||||
%type <std::vector<ast::FnArg>>
|
%type <std::vector<ast::FnArg>> fnArgs fnArgs0;
|
||||||
fnArgs
|
|
||||||
fnArgs0
|
|
||||||
;
|
|
||||||
|
|
||||||
%type <std::vector<std::string>>
|
%type <std::vector<std::string>>
|
||||||
lambdaArgs
|
lambdaArgs
|
||||||
@ -110,6 +104,7 @@ class ParserDriver;
|
|||||||
|
|
||||||
%type <std::string>
|
%type <std::string>
|
||||||
moduleName
|
moduleName
|
||||||
|
type0
|
||||||
operator
|
operator
|
||||||
identifier
|
identifier
|
||||||
keyword
|
keyword
|
||||||
@ -121,11 +116,14 @@ class ParserDriver;
|
|||||||
imports
|
imports
|
||||||
;
|
;
|
||||||
|
|
||||||
|
%type <ast::TraitDecl *> traitDecl;
|
||||||
|
%type <ast::TypeDecl *> typeDecl;
|
||||||
|
|
||||||
%start module
|
%start module
|
||||||
|
|
||||||
%%
|
%%
|
||||||
|
|
||||||
module: imports topLevelStmts { driver.module = new ast::Module($2); }
|
module: imports topLevelStmts { driver.module = new ast::Module($1, $2); }
|
||||||
;
|
;
|
||||||
|
|
||||||
|
|
||||||
@ -144,14 +142,15 @@ moduleName: identifier { $$ = $1; }
|
|||||||
| moduleName "." identifier { $$ = $1 + $2 + $3; }
|
| moduleName "." identifier { $$ = $1 + $2 + $3; }
|
||||||
;
|
;
|
||||||
|
|
||||||
|
|
||||||
topLevelStmts: topLevelStmt { $$.push_back($1); }
|
topLevelStmts: topLevelStmt { $$.push_back($1); }
|
||||||
| topLevelStmts topLevelStmt { $1.push_back($2); $$ = std::move($1); }
|
| topLevelStmts topLevelStmt { $1.push_back($2); $$ = std::move($1); }
|
||||||
;
|
;
|
||||||
|
|
||||||
topLevelStmt: fnDecl { $$ = $1; }
|
topLevelStmt: fnDef { $$ = $1; }
|
||||||
| extFnDecl { $$ = $1; }
|
| fnDecl { $$ = $1; }
|
||||||
| valDecl { $$ = $1; }
|
| valDecl { $$ = $1; }
|
||||||
|
| typeDecl { $$ = $1; }
|
||||||
|
| traitDecl { $$ = $1; }
|
||||||
;
|
;
|
||||||
|
|
||||||
blockStmts: blockStmt { $$.push_back($1); }
|
blockStmts: blockStmt { $$.push_back($1); }
|
||||||
@ -159,19 +158,33 @@ blockStmts: blockStmt { $$.push_back($1); }
|
|||||||
;
|
;
|
||||||
|
|
||||||
blockStmt: valDecl { $$ = $1; }
|
blockStmt: valDecl { $$ = $1; }
|
||||||
| fnDecl { $$ = $1; }
|
| fnDef { $$ = $1; }
|
||||||
| expr ";" { $$ = new ast::ExprStmt($1); }
|
| expr ";" { $$ = new ast::ExprStmt($1); }
|
||||||
;
|
;
|
||||||
|
|
||||||
|
traitDecl: TRAIT identifier "=" "{" fnDecls "}" { $$ = new ast::TraitDecl($2, $5); }
|
||||||
|
;
|
||||||
|
|
||||||
|
typeDecl: TYPE identifier "=" "(" fnArgs ")" "{" fnDecls "}" { $$ = new ast::TypeDecl($2, $5, $8); }
|
||||||
|
;
|
||||||
|
|
||||||
|
fnDecls: %empty { ; }
|
||||||
|
| fnDecls0 { $$ = std::move($1); }
|
||||||
|
;
|
||||||
|
|
||||||
|
fnDecls0: fnDecl { $$.push_back($1); }
|
||||||
|
| fnDecls0 fnDecl { $1.push_back($2); $$ = std::move($1); }
|
||||||
|
;
|
||||||
|
|
||||||
valDecl: VAL identifier "=" expr ";" { $$ = new ast::ValDecl($2, nullptr, $4); }
|
valDecl: VAL identifier "=" expr ";" { $$ = new ast::ValDecl($2, nullptr, $4); }
|
||||||
| VAL identifier type "=" expr ";" { $$ = new ast::ValDecl($2, $3, $5); }
|
| VAL identifier type "=" expr ";" { $$ = new ast::ValDecl($2, $3, $5); }
|
||||||
;
|
;
|
||||||
|
|
||||||
fnDecl: FN identifier "[" fnArgs "]" type "=" expr ";" { $$ = new ast::FnDecl($2, $4, $6, $8); }
|
fnDef : FN identifier "[" fnArgs "]" type "=" expr ";" { $$ = new ast::FnDecl($2, $4, $6, $8); }
|
||||||
;
|
;
|
||||||
|
|
||||||
extFnDecl: DECLARE FN identifier "[" fnArgs "]" type ";" { $$ = new ast::FnDecl($3, $5, $7, nullptr); }
|
fnDecl: FN identifier "[" fnArgs "]" type ";" { $$ = new ast::FnDecl($2, $4, $6, nullptr); }
|
||||||
;
|
;
|
||||||
|
|
||||||
fnArgs: %empty { ; }
|
fnArgs: %empty { ; }
|
||||||
| fnArgs0 { $$ = std::move($1); }
|
| fnArgs0 { $$ = std::move($1); }
|
||||||
@ -188,12 +201,18 @@ types: type { $$.push_back($1); }
|
|||||||
| types "," type { $1.push_back($3); $$ = std::move($1); }
|
| types "," type { $1.push_back($3); $$ = std::move($1); }
|
||||||
;
|
;
|
||||||
|
|
||||||
type: identifier { $$ = new ast::NamedType($1); }
|
type: type1
|
||||||
| "(" type ")" { $$ = $2; }
|
| "(" type ")" { $$ = $2; }
|
||||||
| "(" tupleTypes ")" { $$ = new ast::TupleType($2); }
|
| "(" tupleTypes ")" { $$ = new ast::TupleType($2); }
|
||||||
| "[" fnTypeArgs "]" "->" type { $$ = new ast::FunctionType($2, $5); }
|
| "[" fnTypeArgs "]" "->" type { $$ = new ast::FunctionType($2, $5); }
|
||||||
;
|
;
|
||||||
|
|
||||||
|
type1: type0 { $$ = new ast::NamedType($1); }
|
||||||
|
| type0 "{" types "}" { $$ = new ast::GenericType($1, $3); }
|
||||||
|
;
|
||||||
|
|
||||||
|
type0: identifier;
|
||||||
|
|
||||||
tupleTypes: type "," type { $$.push_back($1); $$.push_back($3); }
|
tupleTypes: type "," type { $$.push_back($1); $$.push_back($3); }
|
||||||
| tupleTypes "," type { $1.push_back($3); $$ = std::move($1); }
|
| tupleTypes "," type { $1.push_back($3); $$ = std::move($1); }
|
||||||
;
|
;
|
||||||
@ -210,8 +229,8 @@ expr: expr3 { $$ = $1; }
|
|||||||
;
|
;
|
||||||
|
|
||||||
expr3: expr2 { $$ = $1; }
|
expr3: expr2 { $$ = $1; }
|
||||||
| "[" lambdaArgs "]" "->" expr { $$ = NULL; }
|
| "[" lambdaArgs "]" "->" expr { $$ = nullptr; }
|
||||||
| "{" blockStmts "}" { $$ = new ast::BlockExpr($2); }
|
| "{" blockStmts "}" { $$ = new ast::BlockExpr($2); }
|
||||||
;
|
;
|
||||||
|
|
||||||
expr2: expr1 { $$ = $1; }
|
expr2: expr1 { $$ = $1; }
|
||||||
@ -226,6 +245,7 @@ expr0: literal { $$ = $1; }
|
|||||||
| identifier { $$ = new ast::Identifier($1); }
|
| identifier { $$ = new ast::Identifier($1); }
|
||||||
| expr0 "[" args "]" { $$ = new ast::CallExpr($1, $3); }
|
| expr0 "[" args "]" { $$ = new ast::CallExpr($1, $3); }
|
||||||
| "(" expr ")" { $$ = new ast::PrefExpr($2); }
|
| "(" expr ")" { $$ = new ast::PrefExpr($2); }
|
||||||
|
| expr0 "." identifier { $$ = $1; }
|
||||||
;
|
;
|
||||||
|
|
||||||
lambdaArgs: %empty { ; }
|
lambdaArgs: %empty { ; }
|
||||||
|
20
compiler/src/Parser.cpp
Normal file
20
compiler/src/Parser.cpp
Normal file
@ -0,0 +1,20 @@
|
|||||||
|
#include "Parser.h"
|
||||||
|
|
||||||
|
#include <sstream>
|
||||||
|
#include <fstream>
|
||||||
|
|
||||||
|
void yy_scan_string(const char *);
|
||||||
|
|
||||||
|
ast::Module *Parser::parse(const std::string &file, const std::stringstream &input)
|
||||||
|
{
|
||||||
|
module = nullptr;
|
||||||
|
|
||||||
|
this->file = file;
|
||||||
|
location.initialize(&file);
|
||||||
|
|
||||||
|
yy_scan_string(input.str().data());
|
||||||
|
|
||||||
|
int res = yy::parser(*this)();
|
||||||
|
|
||||||
|
return module;
|
||||||
|
}
|
@ -1,14 +0,0 @@
|
|||||||
#include "ParserDriver.h"
|
|
||||||
|
|
||||||
int ParserDriver::parse(const std::string &input)
|
|
||||||
{
|
|
||||||
file = input;
|
|
||||||
location.initialize(&file);
|
|
||||||
|
|
||||||
startLexer();
|
|
||||||
yy::parser parse(*this);
|
|
||||||
int res = parse();
|
|
||||||
stopLexer();
|
|
||||||
|
|
||||||
return res;
|
|
||||||
}
|
|
@ -1,10 +1,10 @@
|
|||||||
#include "ParserDriver.h"
|
#include "Parser.h"
|
||||||
|
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
#include <fstream>
|
#include <fstream>
|
||||||
#include <sstream>
|
#include <sstream>
|
||||||
|
|
||||||
std::stringstream readFile(const std::string &path)
|
static std::stringstream readFile(const std::string &path)
|
||||||
{
|
{
|
||||||
std::ifstream t(path);
|
std::ifstream t(path);
|
||||||
std::stringstream buffer;
|
std::stringstream buffer;
|
||||||
@ -21,10 +21,10 @@ int main(int argc, char *argv[])
|
|||||||
exit(EXIT_FAILURE);
|
exit(EXIT_FAILURE);
|
||||||
}
|
}
|
||||||
|
|
||||||
auto buf = readFile(argv[1]);
|
auto module = Parser().parse(argv[1], readFile(argv[1]));
|
||||||
auto parser = ParserDriver();
|
|
||||||
parser.parse(buf.str());
|
|
||||||
|
|
||||||
auto fn = (ast::FnDecl *)parser.module->stmts.at(0);
|
auto fn = (ast::FnDecl *)module->stmts.at(0);
|
||||||
std::cout << fn->name << std::endl;
|
std::cout << fn->name << std::endl;
|
||||||
|
|
||||||
|
delete module;
|
||||||
}
|
}
|
||||||
|
@ -3,7 +3,9 @@ import test.test;
|
|||||||
fn main[] Int = 42;
|
fn main[] Int = 42;
|
||||||
|
|
||||||
fn test[b Int] Int = {
|
fn test[b Int] Int = {
|
||||||
fn helper[] Int = 10;
|
fn helper[] Int = b;
|
||||||
20 * b;
|
20 * helper[];
|
||||||
};
|
};
|
||||||
|
|
||||||
|
fn size[vals List{Int}] Int = vals.size[];
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include "int.h"
|
#include "int.h"
|
||||||
#include "bool.h"
|
#include "bool.h"
|
||||||
|
Loading…
x
Reference in New Issue
Block a user