wraith-lang/wraith.y

256 lines
7.3 KiB
Plaintext

%{
#include <stdio.h>
#include "ast.h"
#include "stack.h"
#define YYSTYPE struct Node*
void yyerror(FILE *fp, char *s)
{
fprintf (stderr, "%s\n", s);
}
Stack *stack;
#define YYDEBUG 1
int yydebug=1;
%}
%token NUMBER
%token INT
%token UINT
%token FLOAT
%token DOUBLE
%token STRING
%token BOOL
%token STRUCT
%token RETURN
%token ID
%token STRING_LITERAL
%token PLUS
%token MINUS
%token MULTIPLY
%token DIVIDE
%token MOD
%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 }
%left PLUS MINUS
%left BANG
%left LEFT_PAREN RIGHT_PAREN
%%
Program : Declarations
{
Node **declarations;
Node *declarationSequence;
uint32_t declarationCount;
declarations = GetDeclarations(stack, &declarationCount);
declarationSequence = MakeDeclarationSequenceNode(declarations, declarationCount);
PopStackFrame(stack);
PrintTree(declarationSequence, 0);
}
Type : INT
{
$$ = MakeTypeNode(Int);
}
| UINT
{
$$ = MakeTypeNode(UInt);
}
| FLOAT
{
$$ = MakeTypeNode(Float);
}
| DOUBLE
{
$$ = MakeTypeNode(Double);
}
| STRING
{
$$ = MakeTypeNode(String);
}
| BOOL
{
$$ = MakeTypeNode(Bool);
}
;
Identifier : ID
{
$$ = MakeIdentifierNode(yytext);
}
PrimaryExpression : Identifier
| NUMBER
{
$$ = MakeNumberNode(yytext);
}
| STRING
{
$$ = MakeStringNode(yytext);
}
| LEFT_PAREN Expression RIGHT_PAREN
{
$$ = $2;
}
;
UnaryExpression : BANG Expression
{
$$ = MakeUnaryNode(Negate, $2);
}
BinaryExpression : Expression PLUS Expression
{
$$ = MakeBinaryNode(Add, $1, $3);
}
| Expression MINUS Expression
{
$$ = MakeBinaryNode(Subtract, $1, $3);
}
Expression : PrimaryExpression
| UnaryExpression
| BinaryExpression
;
VariableDeclaration : Type Identifier
{
$$ = MakeDeclarationNode($1, $2);
}
AssignmentStatement : VariableDeclaration EQUAL Expression
{
$$ = MakeAssignmentNode($1, $3);
}
| Identifier EQUAL Expression
{
$$ = MakeAssignmentNode($1, $3);
}
ReturnStatement : RETURN Expression
{
$$ = MakeReturnStatementNode($2);
}
PartialStatement : AssignmentStatement
| VariableDeclaration
| ReturnStatement
;
Statement : PartialStatement SEMICOLON;
Statements : Statement Statements
{
AddStatement(stack, $1);
}
|
{
PushStackFrame(stack);
}
Arguments : Arguments COMMA VariableDeclaration
| VariableDeclaration
;
Body : LEFT_BRACE Statements RIGHT_BRACE
{
Node **statements;
Node *statementSequence;
uint32_t statementCount;
statements = GetStatements(stack, &statementCount);
statementSequence = MakeStatementSequenceNode(statements, statementCount);
$$ = MakeStatementSequenceNode(statements, statementCount);
PopStackFrame(stack);
}
FunctionSignature : Type Identifier LEFT_PAREN Arguments RIGHT_PAREN
{
$$ = MakeFunctionSignatureNode($2, $1, $4);
}
FunctionDeclaration : FunctionSignature Body
{
$$ = MakeFunctionDeclarationNode($1, $2);
}
VariableDeclarations : VariableDeclaration SEMICOLON VariableDeclarations
{
AddDeclaration(stack, $1);
}
|
{
PushStackFrame(stack);
}
StructDeclaration : STRUCT Identifier LEFT_BRACE VariableDeclarations RIGHT_BRACE
{
Node **declarations;
Node *declarationSequence;
uint32_t declarationCount;
declarations = GetDeclarations(stack, &declarationCount);
declarationSequence = MakeDeclarationSequenceNode(declarations, declarationCount);
$$ = MakeStructDeclarationNode($2, declarationSequence);
PopStackFrame(stack);
}
Declaration : StructDeclaration
| FunctionDeclaration
;
Declarations : Declaration Declarations
{
AddDeclaration(stack, $1);
}
|
{
PushStackFrame(stack);
}
%%
#include "lex.yy.c"
int main(int argc, char *argv[])
{
if (argc < 2)
{
printf("Please provide a file.\n");
return 1;
}
stack = CreateStack();
FILE *fp = fopen(argv[1], "r");
yyin = fp;
yyparse(fp);
fclose(fp);
return 0;
}