350 lines
11 KiB
Plaintext
350 lines
11 KiB
Plaintext
|
%code requires {
|
||
|
#include "../src/stack.h"
|
||
|
}
|
||
|
|
||
|
%{
|
||
|
#include <stdio.h>
|
||
|
#include "../src/ast.h"
|
||
|
#include "../src/stack.h"
|
||
|
|
||
|
void yyerror(FILE *fp, Stack *stack, char *s)
|
||
|
{
|
||
|
fprintf (stderr, "%s\n", s);
|
||
|
}
|
||
|
|
||
|
extern char *yytext;
|
||
|
extern int yylex (void);
|
||
|
extern FILE *yyin;
|
||
|
|
||
|
extern Node *rootNode;
|
||
|
%}
|
||
|
|
||
|
%define api.value.type {struct Node*}
|
||
|
|
||
|
%token VOID
|
||
|
%token INT
|
||
|
%token UINT
|
||
|
%token FLOAT
|
||
|
%token DOUBLE
|
||
|
%token STRING
|
||
|
%token BOOL
|
||
|
%token STRUCT
|
||
|
%token RETURN
|
||
|
%token STATIC
|
||
|
%token REFERENCE
|
||
|
%token ALLOC
|
||
|
%token NUMBER
|
||
|
%token ID
|
||
|
%token STRING_LITERAL
|
||
|
%token PLUS
|
||
|
%token MINUS
|
||
|
%token STAR
|
||
|
%token SLASH
|
||
|
%token PERCENT
|
||
|
%token EQUAL
|
||
|
%token LESS_THAN
|
||
|
%token GREATER_THAN
|
||
|
%token QUOTE
|
||
|
%token BANG
|
||
|
%token BAR
|
||
|
%token AMPERSAND
|
||
|
%token POINT
|
||
|
%token COMMA
|
||
|
%token SEMICOLON
|
||
|
%token COLON
|
||
|
%token QUESTION
|
||
|
%token LEFT_PAREN
|
||
|
%token RIGHT_PAREN
|
||
|
%token LEFT_BRACE
|
||
|
%token RIGHT_BRACE
|
||
|
%token LEFT_BRACKET
|
||
|
%token RIGHT_BRACKET
|
||
|
%token COMMENT
|
||
|
%token NEWLINE
|
||
|
|
||
|
%parse-param { FILE* fp } { Stack *stack }
|
||
|
|
||
|
%define parse.error verbose
|
||
|
|
||
|
%left PLUS MINUS
|
||
|
%left BANG
|
||
|
%left LEFT_PAREN RIGHT_PAREN
|
||
|
|
||
|
%%
|
||
|
Program : TopLevelDeclarations
|
||
|
{
|
||
|
Node **declarations;
|
||
|
Node *declarationSequence;
|
||
|
uint32_t declarationCount;
|
||
|
|
||
|
declarations = GetNodes(stack, &declarationCount);
|
||
|
declarationSequence = MakeDeclarationSequenceNode(declarations, declarationCount);
|
||
|
|
||
|
PopStackFrame(stack);
|
||
|
|
||
|
rootNode = declarationSequence;
|
||
|
}
|
||
|
|
||
|
BaseType : VOID
|
||
|
{
|
||
|
$$ = MakePrimitiveTypeNode(Void);
|
||
|
}
|
||
|
| INT
|
||
|
{
|
||
|
$$ = MakePrimitiveTypeNode(Int);
|
||
|
}
|
||
|
| UINT
|
||
|
{
|
||
|
$$ = MakePrimitiveTypeNode(UInt);
|
||
|
}
|
||
|
| FLOAT
|
||
|
{
|
||
|
$$ = MakePrimitiveTypeNode(Float);
|
||
|
}
|
||
|
| DOUBLE
|
||
|
{
|
||
|
$$ = MakePrimitiveTypeNode(Double);
|
||
|
}
|
||
|
| STRING
|
||
|
{
|
||
|
$$ = MakePrimitiveTypeNode(String);
|
||
|
}
|
||
|
| BOOL
|
||
|
{
|
||
|
$$ = MakePrimitiveTypeNode(Bool);
|
||
|
}
|
||
|
| Identifier
|
||
|
{
|
||
|
$$ = MakeCustomTypeNode(yytext);
|
||
|
}
|
||
|
| REFERENCE LESS_THAN Type GREATER_THAN
|
||
|
{
|
||
|
$$ = MakeReferenceTypeNode($3);
|
||
|
}
|
||
|
;
|
||
|
|
||
|
Type : BaseType
|
||
|
{
|
||
|
$$ = MakeTypeNode($1);
|
||
|
}
|
||
|
|
||
|
Identifier : ID
|
||
|
{
|
||
|
$$ = MakeIdentifierNode(yytext);
|
||
|
}
|
||
|
|
||
|
HeapAllocation : ALLOC Type
|
||
|
{
|
||
|
$$ = MakeAllocNode($2);
|
||
|
}
|
||
|
|
||
|
AccessExpression : Identifier POINT AccessExpression
|
||
|
{
|
||
|
$$ = MakeAccessExpressionNode($1, $3);
|
||
|
}
|
||
|
| Identifier
|
||
|
{
|
||
|
$$ = $1;
|
||
|
}
|
||
|
|
||
|
PrimaryExpression : NUMBER
|
||
|
{
|
||
|
$$ = MakeNumberNode(yytext);
|
||
|
}
|
||
|
| STRING
|
||
|
{
|
||
|
$$ = MakeStringNode(yytext);
|
||
|
}
|
||
|
| LEFT_PAREN Expression RIGHT_PAREN
|
||
|
{
|
||
|
$$ = $2;
|
||
|
}
|
||
|
| FunctionCallExpression
|
||
|
| AccessExpression
|
||
|
;
|
||
|
|
||
|
UnaryExpression : BANG Expression
|
||
|
{
|
||
|
$$ = MakeUnaryNode(Negate, $2);
|
||
|
}
|
||
|
|
||
|
BinaryExpression : Expression PLUS Expression
|
||
|
{
|
||
|
$$ = MakeBinaryNode(Add, $1, $3);
|
||
|
}
|
||
|
| Expression MINUS Expression
|
||
|
{
|
||
|
$$ = MakeBinaryNode(Subtract, $1, $3);
|
||
|
}
|
||
|
| Expression STAR Expression
|
||
|
{
|
||
|
$$ = MakeBinaryNode(Multiply, $1, $3);
|
||
|
}
|
||
|
|
||
|
Expression : PrimaryExpression
|
||
|
| UnaryExpression
|
||
|
| BinaryExpression
|
||
|
| HeapAllocation
|
||
|
;
|
||
|
|
||
|
VariableDeclaration : Identifier COLON Type
|
||
|
{
|
||
|
$$ = MakeDeclarationNode($3, $1);
|
||
|
}
|
||
|
|
||
|
AssignmentStatement : VariableDeclaration EQUAL Expression
|
||
|
{
|
||
|
$$ = MakeAssignmentNode($1, $3);
|
||
|
}
|
||
|
| AccessExpression EQUAL Expression
|
||
|
{
|
||
|
$$ = MakeAssignmentNode($1, $3);
|
||
|
}
|
||
|
| Identifier EQUAL Expression
|
||
|
{
|
||
|
$$ = MakeAssignmentNode($1, $3);
|
||
|
}
|
||
|
|
||
|
ReturnStatement : RETURN Expression
|
||
|
{
|
||
|
$$ = MakeReturnStatementNode($2);
|
||
|
}
|
||
|
| RETURN
|
||
|
{
|
||
|
$$ = MakeReturnVoidStatementNode();
|
||
|
}
|
||
|
|
||
|
FunctionCallExpression : AccessExpression LEFT_PAREN Arguments RIGHT_PAREN
|
||
|
{
|
||
|
Node **arguments;
|
||
|
uint32_t argumentCount;
|
||
|
|
||
|
arguments = GetNodes(stack, &argumentCount);
|
||
|
$$ = MakeFunctionCallExpressionNode($1, MakeFunctionArgumentSequenceNode(arguments, argumentCount));
|
||
|
|
||
|
PopStackFrame(stack);
|
||
|
}
|
||
|
|
||
|
PartialStatement : FunctionCallExpression
|
||
|
| AssignmentStatement
|
||
|
| VariableDeclaration
|
||
|
| ReturnStatement
|
||
|
;
|
||
|
|
||
|
Statement : PartialStatement SEMICOLON;
|
||
|
|
||
|
Statements : Statement Statements
|
||
|
{
|
||
|
AddNode(stack, $1);
|
||
|
}
|
||
|
|
|
||
|
{
|
||
|
PushStackFrame(stack);
|
||
|
}
|
||
|
|
||
|
Arguments : PrimaryExpression COMMA Arguments
|
||
|
{
|
||
|
AddNode(stack, $1);
|
||
|
}
|
||
|
| PrimaryExpression
|
||
|
{
|
||
|
PushStackFrame(stack);
|
||
|
AddNode(stack, $1);
|
||
|
}
|
||
|
|
|
||
|
{
|
||
|
PushStackFrame(stack);
|
||
|
}
|
||
|
;
|
||
|
|
||
|
SignatureArguments : VariableDeclaration COMMA SignatureArguments
|
||
|
{
|
||
|
AddNode(stack, $1);
|
||
|
}
|
||
|
| VariableDeclaration
|
||
|
{
|
||
|
PushStackFrame(stack);
|
||
|
AddNode(stack, $1);
|
||
|
}
|
||
|
|
|
||
|
;
|
||
|
|
||
|
Body : LEFT_BRACE Statements RIGHT_BRACE
|
||
|
{
|
||
|
Node **statements;
|
||
|
Node *statementSequence;
|
||
|
uint32_t statementCount;
|
||
|
|
||
|
statements = GetNodes(stack, &statementCount);
|
||
|
statementSequence = MakeStatementSequenceNode(statements, statementCount);
|
||
|
$$ = MakeStatementSequenceNode(statements, statementCount);
|
||
|
|
||
|
PopStackFrame(stack);
|
||
|
}
|
||
|
|
||
|
FunctionSignature : Identifier LEFT_PAREN SignatureArguments RIGHT_PAREN COLON Type
|
||
|
{
|
||
|
Node **declarations;
|
||
|
uint32_t declarationCount;
|
||
|
|
||
|
declarations = GetNodes(stack, &declarationCount);
|
||
|
$$ = MakeFunctionSignatureNode($1, $6, MakeFunctionSignatureArgumentsNode(declarations, declarationCount), MakeFunctionModifiersNode(NULL, 0));
|
||
|
|
||
|
PopStackFrame(stack);
|
||
|
}
|
||
|
| STATIC Identifier LEFT_PAREN SignatureArguments RIGHT_PAREN COLON Type
|
||
|
{
|
||
|
Node **declarations;
|
||
|
uint32_t declarationCount;
|
||
|
Node *modifier = MakeStaticNode();
|
||
|
|
||
|
declarations = GetNodes(stack, &declarationCount);
|
||
|
$$ = MakeFunctionSignatureNode($2, $7, MakeFunctionSignatureArgumentsNode(declarations, declarationCount), MakeFunctionModifiersNode(&modifier, 1));
|
||
|
|
||
|
PopStackFrame(stack);
|
||
|
}
|
||
|
|
||
|
FunctionDeclaration : FunctionSignature Body
|
||
|
{
|
||
|
$$ = MakeFunctionDeclarationNode($1, $2);
|
||
|
}
|
||
|
|
||
|
StructDeclaration : STRUCT Identifier LEFT_BRACE Declarations RIGHT_BRACE
|
||
|
{
|
||
|
Node **declarations;
|
||
|
Node *declarationSequence;
|
||
|
uint32_t declarationCount;
|
||
|
|
||
|
declarations = GetNodes(stack, &declarationCount);
|
||
|
declarationSequence = MakeDeclarationSequenceNode(declarations, declarationCount);
|
||
|
$$ = MakeStructDeclarationNode($2, declarationSequence);
|
||
|
|
||
|
PopStackFrame(stack);
|
||
|
}
|
||
|
|
||
|
|
||
|
Declaration : FunctionDeclaration
|
||
|
| VariableDeclaration SEMICOLON
|
||
|
;
|
||
|
|
||
|
Declarations : Declaration Declarations
|
||
|
{
|
||
|
AddNode(stack, $1);
|
||
|
}
|
||
|
|
|
||
|
{
|
||
|
PushStackFrame(stack);
|
||
|
}
|
||
|
|
||
|
TopLevelDeclaration : StructDeclaration;
|
||
|
|
||
|
TopLevelDeclarations : TopLevelDeclaration TopLevelDeclarations
|
||
|
{
|
||
|
AddNode(stack, $1);
|
||
|
}
|
||
|
|
|
||
|
{
|
||
|
PushStackFrame(stack);
|
||
|
}
|
||
|
%%
|