mirror of
https://github.com/krgamestudios/Toy.git
synced 2026-04-15 23:04:08 +10:00
Basically, all Toy varaibles, functions, etc. are prepended with "Toy_", and macros are prepended with "TOY_". This is to reduce namespace pollution, which was an issue pointed out to be - blame @GyroVorbis. I've also bumped the minor version number - theoretically I should bump the major number, but I'm not quite ready for 1.0 yet.
270 lines
7.8 KiB
C
270 lines
7.8 KiB
C
#pragma once
|
|
|
|
#include "toy_common.h"
|
|
#include "toy_literal.h"
|
|
#include "toy_opcodes.h"
|
|
#include "toy_token_types.h"
|
|
|
|
//nodes are the intermediaries between parsers and compilers
|
|
typedef union Toy_private_node Toy_ASTNode;
|
|
|
|
typedef enum Toy_ASTNodeType {
|
|
TOY_AST_NODE_ERROR,
|
|
TOY_AST_NODE_LITERAL, //a simple value
|
|
TOY_AST_NODE_UNARY, //one child + opcode
|
|
TOY_AST_NODE_BINARY, //two children, left and right + opcode
|
|
TOY_AST_NODE_TERNARY, //three children, condition, then path & else path
|
|
TOY_AST_NODE_GROUPING, //one child
|
|
TOY_AST_NODE_BLOCK, //contains a sub-node array
|
|
TOY_AST_NODE_COMPOUND, //contains a sub-node array
|
|
TOY_AST_NODE_PAIR, //contains a left and right
|
|
TOY_AST_NODE_INDEX, //index a variable
|
|
TOY_AST_NODE_VAR_DECL, //contains identifier literal, typenode, expression definition
|
|
TOY_AST_NODE_FN_DECL, //containd identifier literal, arguments node, returns node, block node
|
|
TOY_AST_NODE_FN_COLLECTION, //parts of a function
|
|
TOY_AST_NODE_FN_CALL, //call a function
|
|
TOY_AST_NODE_FN_RETURN, //for control flow
|
|
TOY_AST_NODE_IF, //for control flow
|
|
TOY_AST_NODE_WHILE, //for control flow
|
|
TOY_AST_NODE_FOR, //for control flow
|
|
TOY_AST_NODE_BREAK, //for control flow
|
|
TOY_AST_NODE_CONTINUE, //for control flow
|
|
TOY_AST_NODE_PREFIX_INCREMENT, //increment a variable
|
|
TOY_AST_NODE_POSTFIX_INCREMENT, //increment a variable
|
|
TOY_AST_NODE_PREFIX_DECREMENT, //decrement a variable
|
|
TOY_AST_NODE_POSTFIX_DECREMENT, //decrement a variable
|
|
TOY_AST_NODE_IMPORT, //import a library
|
|
} Toy_ASTNodeType;
|
|
|
|
//literals
|
|
void Toy_emitASTNodeLiteral(Toy_ASTNode** nodeHandle, Toy_Literal literal);
|
|
|
|
typedef struct Toy_NodeLiteral {
|
|
Toy_ASTNodeType type;
|
|
Toy_Literal literal;
|
|
} Toy_NodeLiteral;
|
|
|
|
//unary operator
|
|
void Toy_emitASTNodeUnary(Toy_ASTNode** nodeHandle, Toy_Opcode opcode, Toy_ASTNode* child);
|
|
|
|
typedef struct Toy_NodeUnary {
|
|
Toy_ASTNodeType type;
|
|
Toy_Opcode opcode;
|
|
Toy_ASTNode* child;
|
|
} Toy_NodeUnary;
|
|
|
|
//binary operator
|
|
void Toy_emitASTNodeBinary(Toy_ASTNode** nodeHandle, Toy_ASTNode* rhs, Toy_Opcode opcode); //handled node becomes lhs
|
|
|
|
typedef struct Toy_NodeBinary {
|
|
Toy_ASTNodeType type;
|
|
Toy_Opcode opcode;
|
|
Toy_ASTNode* left;
|
|
Toy_ASTNode* right;
|
|
} Toy_NodeBinary;
|
|
|
|
//ternary operator
|
|
void Toy_emitASTNodeTernary(Toy_ASTNode** nodeHandle, Toy_ASTNode* condition, Toy_ASTNode* thenPath, Toy_ASTNode* elsePath);
|
|
|
|
typedef struct Toy_NodeTernary {
|
|
Toy_ASTNodeType type;
|
|
Toy_ASTNode* condition;
|
|
Toy_ASTNode* thenPath;
|
|
Toy_ASTNode* elsePath;
|
|
} Toy_NodeTernary;
|
|
|
|
//grouping of other AST nodes
|
|
void Toy_emitASTNodeGrouping(Toy_ASTNode** nodeHandle);
|
|
|
|
typedef struct Toy_NodeGrouping {
|
|
Toy_ASTNodeType type;
|
|
Toy_ASTNode* child;
|
|
} Toy_NodeGrouping;
|
|
|
|
//block of statement nodes
|
|
void Toy_emitASTNodeBlock(Toy_ASTNode** nodeHandle);
|
|
|
|
typedef struct Toy_NodeBlock {
|
|
Toy_ASTNodeType type;
|
|
Toy_ASTNode* nodes;
|
|
int capacity;
|
|
int count;
|
|
} Toy_NodeBlock;
|
|
|
|
//compound literals (array, dictionary)
|
|
void Toy_emitASTNodeCompound(Toy_ASTNode** nodeHandle, Toy_LiteralType literalType);
|
|
|
|
typedef struct Toy_NodeCompound {
|
|
Toy_ASTNodeType type;
|
|
Toy_LiteralType literalType;
|
|
Toy_ASTNode* nodes;
|
|
int capacity;
|
|
int count;
|
|
} Toy_NodeCompound;
|
|
|
|
void Toy_setASTNodePair(Toy_ASTNode* node, Toy_ASTNode* left, Toy_ASTNode* right); //NOTE: this is a set function, not an emit function
|
|
|
|
typedef struct Toy_NodePair {
|
|
Toy_ASTNodeType type;
|
|
Toy_ASTNode* left;
|
|
Toy_ASTNode* right;
|
|
} Toy_NodePair;
|
|
|
|
void Toy_emitASTNodeIndex(Toy_ASTNode** nodeHandle, Toy_ASTNode* first, Toy_ASTNode* second, Toy_ASTNode* third);
|
|
|
|
typedef struct Toy_NodeIndex {
|
|
Toy_ASTNodeType type;
|
|
Toy_ASTNode* first;
|
|
Toy_ASTNode* second;
|
|
Toy_ASTNode* third;
|
|
} Toy_NodeIndex;
|
|
|
|
//variable declaration
|
|
void Toy_emitASTNodeVarDecl(Toy_ASTNode** nodeHandle, Toy_Literal identifier, Toy_Literal type, Toy_ASTNode* expression);
|
|
|
|
typedef struct Toy_NodeVarDecl {
|
|
Toy_ASTNodeType type;
|
|
Toy_Literal identifier;
|
|
Toy_Literal typeLiteral;
|
|
Toy_ASTNode* expression;
|
|
} Toy_NodeVarDecl;
|
|
|
|
//NOTE: fnCollection is used by fnDecl, fnCall and fnReturn
|
|
void Toy_emitASTNodeFnCollection(Toy_ASTNode** nodeHandle);
|
|
|
|
typedef struct Toy_NodeFnCollection {
|
|
Toy_ASTNodeType type;
|
|
Toy_ASTNode* nodes;
|
|
int capacity;
|
|
int count;
|
|
} Toy_NodeFnCollection;
|
|
|
|
//function declaration
|
|
void Toy_emitASTNodeFnDecl(Toy_ASTNode** nodeHandle, Toy_Literal identifier, Toy_ASTNode* arguments, Toy_ASTNode* returns, Toy_ASTNode* block);
|
|
|
|
typedef struct Toy_NodeFnDecl {
|
|
Toy_ASTNodeType type;
|
|
Toy_Literal identifier;
|
|
Toy_ASTNode* arguments;
|
|
Toy_ASTNode* returns;
|
|
Toy_ASTNode* block;
|
|
} Toy_NodeFnDecl;
|
|
|
|
//function call
|
|
void Toy_emitASTNodeFnCall(Toy_ASTNode** nodeHandle, Toy_ASTNode* arguments);
|
|
|
|
typedef struct Toy_NodeFnCall {
|
|
Toy_ASTNodeType type;
|
|
Toy_ASTNode* arguments;
|
|
int argumentCount; //NOTE: leave this, so it can be hacked by dottify()
|
|
} Toy_NodeFnCall;
|
|
|
|
//function return
|
|
void Toy_emitASTNodeFnReturn(Toy_ASTNode** nodeHandle, Toy_ASTNode* returns);
|
|
|
|
typedef struct Toy_NodeFnReturn {
|
|
Toy_ASTNodeType type;
|
|
Toy_ASTNode* returns;
|
|
} Toy_NodeFnReturn;
|
|
|
|
//control flow path - if-else, while, for, break, continue, return
|
|
void Toy_emitASTNodeIf(Toy_ASTNode** nodeHandle, Toy_ASTNode* condition, Toy_ASTNode* thenPath, Toy_ASTNode* elsePath);
|
|
void Toy_emitASTNodeWhile(Toy_ASTNode** nodeHandle, Toy_ASTNode* condition, Toy_ASTNode* thenPath);
|
|
void Toy_emitASTNodeFor(Toy_ASTNode** nodeHandle, Toy_ASTNode* preClause, Toy_ASTNode* condition, Toy_ASTNode* postClause, Toy_ASTNode* thenPath);
|
|
void Toy_emitASTNodeBreak(Toy_ASTNode** nodeHandle);
|
|
void Toy_emitASTNodeContinue(Toy_ASTNode** nodeHandle);
|
|
|
|
typedef struct Toy_NodeIf {
|
|
Toy_ASTNodeType type;
|
|
Toy_ASTNode* condition;
|
|
Toy_ASTNode* thenPath;
|
|
Toy_ASTNode* elsePath;
|
|
} Toy_NodeIf;
|
|
|
|
typedef struct Toy_NodeWhile {
|
|
Toy_ASTNodeType type;
|
|
Toy_ASTNode* condition;
|
|
Toy_ASTNode* thenPath;
|
|
} Toy_NodeWhile;
|
|
|
|
typedef struct Toy_NodeFor {
|
|
Toy_ASTNodeType type;
|
|
Toy_ASTNode* preClause;
|
|
Toy_ASTNode* condition;
|
|
Toy_ASTNode* postClause;
|
|
Toy_ASTNode* thenPath;
|
|
} Toy_NodeFor;
|
|
|
|
typedef struct Toy_NodeBreak {
|
|
Toy_ASTNodeType type;
|
|
} Toy_NodeBreak;
|
|
|
|
typedef struct Toy_NodeContinue {
|
|
Toy_ASTNodeType type;
|
|
} Toy_NodeContinue;
|
|
|
|
//pre-post increment/decrement
|
|
void Toy_emitASTNodePrefixIncrement(Toy_ASTNode** nodeHandle, Toy_Literal identifier);
|
|
void Toy_emitASTNodePrefixDecrement(Toy_ASTNode** nodeHandle, Toy_Literal identifier);
|
|
void Toy_emitASTNodePostfixIncrement(Toy_ASTNode** nodeHandle, Toy_Literal identifier);
|
|
void Toy_emitASTNodePostfixDecrement(Toy_ASTNode** nodeHandle, Toy_Literal identifier);
|
|
|
|
typedef struct Toy_NodePrefixIncrement {
|
|
Toy_ASTNodeType type;
|
|
Toy_Literal identifier;
|
|
} Toy_NodePrefixIncrement;
|
|
|
|
typedef struct Toy_NodePrefixDecrement {
|
|
Toy_ASTNodeType type;
|
|
Toy_Literal identifier;
|
|
} Toy_NodePrefixDecrement;
|
|
|
|
typedef struct Toy_NodePostfixIncrement {
|
|
Toy_ASTNodeType type;
|
|
Toy_Literal identifier;
|
|
} Toy_NodePostfixIncrement;
|
|
|
|
typedef struct Toy_NodePostfixDecrement {
|
|
Toy_ASTNodeType type;
|
|
Toy_Literal identifier;
|
|
} Toy_NodePostfixDecrement;
|
|
|
|
//import a library
|
|
void Toy_emitASTNodeImport(Toy_ASTNode** nodeHandle, Toy_Literal identifier, Toy_Literal alias);
|
|
|
|
typedef struct Toy_NodeImport {
|
|
Toy_ASTNodeType type;
|
|
Toy_Literal identifier;
|
|
Toy_Literal alias;
|
|
} Toy_NodeImport;
|
|
|
|
union Toy_private_node {
|
|
Toy_ASTNodeType type;
|
|
Toy_NodeLiteral atomic;
|
|
Toy_NodeUnary unary;
|
|
Toy_NodeBinary binary;
|
|
Toy_NodeTernary ternary;
|
|
Toy_NodeGrouping grouping;
|
|
Toy_NodeBlock block;
|
|
Toy_NodeCompound compound;
|
|
Toy_NodePair pair;
|
|
Toy_NodeIndex index;
|
|
Toy_NodeVarDecl varDecl;
|
|
Toy_NodeFnCollection fnCollection;
|
|
Toy_NodeFnDecl fnDecl;
|
|
Toy_NodeFnCall fnCall;
|
|
Toy_NodeFnReturn returns;
|
|
Toy_NodeIf pathIf;
|
|
Toy_NodeWhile pathWhile;
|
|
Toy_NodeFor pathFor;
|
|
Toy_NodeBreak pathBreak;
|
|
Toy_NodeContinue pathContinue;
|
|
Toy_NodePrefixIncrement prefixIncrement;
|
|
Toy_NodePrefixDecrement prefixDecrement;
|
|
Toy_NodePostfixIncrement postfixIncrement;
|
|
Toy_NodePostfixDecrement postfixDecrement;
|
|
Toy_NodeImport import;
|
|
};
|
|
|
|
TOY_API void Toy_freeASTNode(Toy_ASTNode* node);
|