Skip to content
This repository has been archived by the owner on Jun 29, 2024. It is now read-only.

Commit

Permalink
Add function body
Browse files Browse the repository at this point in the history
  • Loading branch information
Gashmob committed Aug 6, 2023
1 parent c580b3c commit 3878de6
Show file tree
Hide file tree
Showing 5 changed files with 46 additions and 12 deletions.
6 changes: 5 additions & 1 deletion src/lib/ast/AST.h
Original file line number Diff line number Diff line change
Expand Up @@ -334,18 +334,22 @@ namespace filc::ast {

class Function : public AbstractExpression {
public:
Function(Identifier *name, const std::vector<FunctionParameter *> &parameters, AbstractType *return_type);
Function(Identifier *name, const std::vector<FunctionParameter *> &parameters, AbstractType *return_type,
const std::vector<AbstractExpression *> &body);

[[nodiscard]] auto getName() const -> Identifier *;

[[nodiscard]] auto getParameters() const -> const std::vector<FunctionParameter *> &;

[[nodiscard]] auto getReturnType() const -> AbstractType *;

[[nodiscard]] auto getBody() const -> const std::vector<AbstractExpression *> &;

private:
Identifier *_name;
std::vector<FunctionParameter *> _parameters;
AbstractType *_return_type;
std::vector<AbstractExpression *> _body;
};

class FunctionParameter {
Expand Down
9 changes: 7 additions & 2 deletions src/lib/ast/Function.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -24,8 +24,9 @@
#include "AST.h"

namespace filc::ast {
Function::Function(Identifier *name, const std::vector<FunctionParameter *> &parameters, AbstractType *return_type)
: AbstractExpression(), _name(name), _parameters(parameters), _return_type(return_type) {}
Function::Function(Identifier *name, const std::vector<FunctionParameter *> &parameters, AbstractType *return_type,
const std::vector<AbstractExpression *> &body)
: AbstractExpression(), _name(name), _parameters(parameters), _return_type(return_type), _body(body) {}

auto Function::getName() const -> Identifier * {
return _name;
Expand All @@ -38,4 +39,8 @@ namespace filc::ast {
auto Function::getReturnType() const -> AbstractType * {
return _return_type;
}

auto Function::getBody() const -> const std::vector<AbstractExpression *> & {
return _body;
}
}
29 changes: 21 additions & 8 deletions src/lib/grammar/FilParser.g4
Original file line number Diff line number Diff line change
Expand Up @@ -289,8 +289,8 @@ binary_operator returns[filc::ast::Operator *tree]
};

function returns[filc::ast::Function *tree]
: fd=function_declaration function_body {
$tree = new filc::ast::Function($fd.identifier, $fd.parameters, $fd.return_type);
: fd=function_declaration fb=function_body {
$tree = new filc::ast::Function($fd.identifier, $fd.parameters, $fd.return_type, $fb.tree);
};

function_declaration returns[filc::ast::Identifier *identifier, std::vector<filc::ast::FunctionParameter *> parameters, filc::ast::AbstractType *return_type]
Expand Down Expand Up @@ -355,14 +355,27 @@ function_type returns[filc::ast::AbstractType *tree]
$tree = $t.tree;
};

function_body
: assignation | parenthesis_body | block_body;
function_body returns[std::vector<filc::ast::AbstractExpression *> tree]
: a=assignation {
$tree = std::vector<filc::ast::AbstractExpression *>({$a.tree});
} | pb=parenthesis_body {
$tree = $pb.tree;
} | bb=block_body {
$tree = $bb.tree;
};

parenthesis_body
: LPAREN expression RPAREN;
parenthesis_body returns[std::vector<filc::ast::AbstractExpression *> tree]
: LPAREN e=expression {
$tree = std::vector<filc::ast::AbstractExpression *>({$e.tree});
} RPAREN;

block_body
: LBRACE expression* RBRACE;
block_body returns[std::vector<filc::ast::AbstractExpression *> tree]
@init {
$tree = std::vector<filc::ast::AbstractExpression *>();
}
: LBRACE (e=expression {
$tree.push_back($e.tree);
})* RBRACE;

lambda
: LPAREN function_parameters? RPAREN function_type ARROW (expression | parenthesis_body | block_body);
Expand Down
4 changes: 3 additions & 1 deletion tests/unit/ast/FunctionTest.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -32,9 +32,11 @@ TEST(Function, constructor) {
filc::ast::Function fun1(
new filc::ast::Identifier("fact"),
{},
new filc::ast::Type(new filc::ast::Identifier("int"))
new filc::ast::Type(new filc::ast::Identifier("int")),
{}
);
ASSERT_IDENTIFIER("fact", fun1.getName());
ASSERT_THAT(fun1.getParameters(), IsEmpty());
ASSERT_TYPE("int", fun1.getReturnType());
ASSERT_THAT(fun1.getBody(), IsEmpty());
}
10 changes: 10 additions & 0 deletions tests/unit/grammar/ParserTest.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -318,6 +318,11 @@ TEST(Parser, Function) {
ASSERT_IDENTIFIER("b", parameter1_2->getName());
ASSERT_TYPE("int", parameter1_1->getType());
ASSERT_TYPE("int", parameter1_2->getType());
ASSERT_THAT(expression1->getBody(), SizeIs(1));
auto *body1 = static_cast<filc::ast::BinaryCalcul *>(expression1->getBody()[0]);
ASSERT_IDENTIFIER("a", body1->getLeftExpression());
ASSERT_IDENTIFIER("b", body1->getRightExpression());
ASSERT_CLASSIC_OPERATOR(filc::ast::ClassicOperator::MINUS, body1->getOperator());

filc::grammar::Parser parser2(FIXTURES_PATH "/function2.fil");
auto *program2 = parser2.getProgram();
Expand All @@ -333,4 +338,9 @@ TEST(Parser, Function) {
ASSERT_IDENTIFIER("b", parameter2_2->getName());
ASSERT_TYPE("float", parameter2_1->getType());
ASSERT_TYPE("float", parameter2_2->getType());
ASSERT_THAT(expression2->getBody(), SizeIs(1));
auto *body2 = static_cast<filc::ast::BinaryCalcul *>(expression2->getBody()[0]);
ASSERT_IDENTIFIER("a", body2->getLeftExpression());
ASSERT_IDENTIFIER("b", body2->getRightExpression());
ASSERT_CLASSIC_OPERATOR(filc::ast::ClassicOperator::EQEQ, body2->getOperator());
}

0 comments on commit 3878de6

Please sign in to comment.