Named function args
This commit is contained in:
477
new_ast.c
477
new_ast.c
@@ -1,6 +1,129 @@
|
||||
|
||||
typedef struct Expr Expr;
|
||||
typedef struct Note Note;
|
||||
typedef struct Decl Decl;
|
||||
typedef struct Stmt Stmt;
|
||||
typedef struct Stmt_If Stmt_If;
|
||||
typedef struct Typespec Typespec;
|
||||
typedef struct Decl_Enum_Child Decl_Enum_Child;
|
||||
typedef struct Decl_Function_Arg Decl_Function_Arg;
|
||||
typedef struct Expr_Compound_Field Expr_Compound_Field;
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// Expressions
|
||||
//-----------------------------------------------------------------------------
|
||||
typedef enum Expr_Sizeof_Kind{
|
||||
SIZEOF_Expr,
|
||||
SIZEOF_Type,
|
||||
}Expr_Sizeof_Kind;
|
||||
|
||||
typedef enum Expr_Kind{
|
||||
EK_None,
|
||||
EK_Int,
|
||||
EK_String,
|
||||
EK_Identifier,
|
||||
EK_Compound,
|
||||
EK_Paren,
|
||||
EK_PostfixUnary,
|
||||
EK_Unary,
|
||||
EK_Binary,
|
||||
EK_Ternary,
|
||||
EK_Cast,
|
||||
EK_Field,
|
||||
EK_Call,
|
||||
EK_Index,
|
||||
EK_SizeType,
|
||||
EK_SizeExpr,
|
||||
} Expr_Kind;
|
||||
|
||||
typedef enum Expr_Compound_Kind{
|
||||
COMPOUND_None,
|
||||
COMPOUND_Default,
|
||||
COMPOUND_Named,
|
||||
COMPOUND_Index,
|
||||
}Expr_Compound_Kind;
|
||||
|
||||
struct Expr_Compound_Field{
|
||||
Expr_Compound_Field *next;
|
||||
Expr_Compound_Kind kind;
|
||||
Token *pos;
|
||||
Expr *init;
|
||||
union{
|
||||
Expr *index;
|
||||
Intern_String name;
|
||||
};
|
||||
};
|
||||
|
||||
struct Expr {
|
||||
Expr_Kind kind;
|
||||
Token *token;
|
||||
Expr *next;
|
||||
union {
|
||||
U64 int_val;
|
||||
Intern_String intern_val;
|
||||
double float_val;
|
||||
struct {
|
||||
Expr *expr;
|
||||
} paren;
|
||||
struct {
|
||||
Typespec *typespec;
|
||||
Expr* expr;
|
||||
} cast;
|
||||
struct{
|
||||
Intern_String name;
|
||||
Expr *expr;
|
||||
}field;
|
||||
|
||||
struct{
|
||||
Typespec *typespec;
|
||||
Expr_Compound_Field *first;
|
||||
Expr_Compound_Field *last;
|
||||
}compound;
|
||||
|
||||
struct {
|
||||
Expr *atom;
|
||||
Expr_Compound_Field *first;
|
||||
Expr_Compound_Field *last;
|
||||
} call;
|
||||
struct{
|
||||
|
||||
}arg;
|
||||
struct {
|
||||
Expr *atom;
|
||||
Expr *index;
|
||||
} index;
|
||||
|
||||
struct {
|
||||
Token_Kind op;
|
||||
Expr* expr;
|
||||
} unary;
|
||||
struct {
|
||||
Token_Kind op;
|
||||
Expr *expr;
|
||||
} postfix_unary;
|
||||
struct {
|
||||
Token_Kind op;
|
||||
Expr* left;
|
||||
Expr* right;
|
||||
} binary;
|
||||
struct {
|
||||
Expr* cond;
|
||||
Expr* on_true;
|
||||
Expr* on_false;
|
||||
} ternary;
|
||||
|
||||
struct{
|
||||
Typespec *typespec;
|
||||
} size_type;
|
||||
|
||||
struct{
|
||||
Expr *expr;
|
||||
} size_expr;
|
||||
};
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// Type specifiers
|
||||
//-----------------------------------------------------------------------------
|
||||
typedef enum Typespec_Kind{
|
||||
TS_None,
|
||||
TS_Name,
|
||||
@@ -29,92 +152,127 @@ struct Typespec{
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// Expressions
|
||||
// Declarations
|
||||
//-----------------------------------------------------------------------------
|
||||
typedef enum Expr_Sizeof_Kind{
|
||||
SIZEOF_Expr,
|
||||
SIZEOF_Type,
|
||||
}Expr_Sizeof_Kind;
|
||||
typedef enum Decl_Kind{
|
||||
DECL_None,
|
||||
DECL_Struct,
|
||||
DECL_Union,
|
||||
DECL_Enum,
|
||||
DECL_Variable,
|
||||
DECL_Typedef,
|
||||
DECL_Function,
|
||||
DECL_List,
|
||||
}Decl_Kind;
|
||||
|
||||
typedef enum Expr_Kind{
|
||||
EK_None,
|
||||
EK_Int,
|
||||
EK_String,
|
||||
EK_Identifier,
|
||||
EK_Paren,
|
||||
EK_PostfixUnary,
|
||||
EK_Unary,
|
||||
EK_Binary,
|
||||
EK_Ternary,
|
||||
EK_Cast,
|
||||
EK_Field,
|
||||
EK_Call,
|
||||
EK_Index,
|
||||
EK_Sizeof,
|
||||
} Expr_Kind;
|
||||
struct Note{
|
||||
Token *pos;
|
||||
Intern_String name;
|
||||
Expr *expr;
|
||||
Note *next;
|
||||
Note *first;
|
||||
Note *last;
|
||||
};
|
||||
|
||||
struct Expr {
|
||||
Expr_Kind kind;
|
||||
Token *token;
|
||||
Expr *next;
|
||||
union {
|
||||
U64 int_val;
|
||||
Intern_String intern_val;
|
||||
double float_val;
|
||||
struct {
|
||||
Expr *expr;
|
||||
} paren;
|
||||
|
||||
struct {
|
||||
struct Decl{
|
||||
Decl_Kind kind;
|
||||
Decl *next;
|
||||
B32 is_incomplete;
|
||||
|
||||
Decl *prev; // Doubly linked list?
|
||||
Decl *parent; // ?
|
||||
|
||||
Intern_String name;
|
||||
Token *pos;
|
||||
|
||||
Note *first_note;
|
||||
Note *last_note;
|
||||
union{
|
||||
struct{
|
||||
Decl_Enum_Child *first;
|
||||
Decl_Enum_Child *last;
|
||||
Typespec *typespec;
|
||||
}enum_decl;
|
||||
struct{
|
||||
Decl *first;
|
||||
Decl *last;
|
||||
}struct_decl;
|
||||
struct{
|
||||
Typespec *type;
|
||||
Expr* expr;
|
||||
} cast;
|
||||
|
||||
struct{
|
||||
Intern_String name;
|
||||
Expr *expr;
|
||||
}field;
|
||||
|
||||
struct {
|
||||
Expr *atom;
|
||||
Expr *first;
|
||||
Expr *last;
|
||||
} call;
|
||||
struct {
|
||||
Expr *atom;
|
||||
Expr *index;
|
||||
} index;
|
||||
struct {
|
||||
Token_Kind op;
|
||||
Expr* expr;
|
||||
} unary;
|
||||
struct {
|
||||
Token_Kind op;
|
||||
Expr *expr;
|
||||
} postfix_unary;
|
||||
struct {
|
||||
Token_Kind op;
|
||||
Expr* left;
|
||||
Expr* right;
|
||||
} binary;
|
||||
struct {
|
||||
Expr* cond;
|
||||
Expr* on_true;
|
||||
Expr* on_false;
|
||||
} ternary;
|
||||
|
||||
}var_decl;
|
||||
struct{
|
||||
Expr_Sizeof_Kind kind;
|
||||
union{
|
||||
Typespec *type;
|
||||
Expr *expr;
|
||||
};
|
||||
} size_of;
|
||||
Typespec *type;
|
||||
}typedef_decl;
|
||||
struct{
|
||||
Decl_Function_Arg *first;
|
||||
Decl_Function_Arg *last;
|
||||
Typespec *ret;
|
||||
//Stmt *body;
|
||||
}func_decl;
|
||||
struct{
|
||||
Decl *first;
|
||||
Decl *last;
|
||||
}list_decl;
|
||||
};
|
||||
};
|
||||
|
||||
struct Decl_Function_Arg{
|
||||
Decl_Function_Arg *next;
|
||||
Token *pos;
|
||||
Intern_String name;
|
||||
Typespec *typespec;
|
||||
};
|
||||
|
||||
struct Decl_Enum_Child{
|
||||
Decl_Enum_Child *next;
|
||||
Intern_String name;
|
||||
Token *pos;
|
||||
Expr *expr;
|
||||
Note *first_note;
|
||||
Note *last_note;
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// Expr
|
||||
// Statements
|
||||
//-----------------------------------------------------------------------------
|
||||
typedef enum Stmt_Kind{
|
||||
STMT_None,
|
||||
STMT_Decl,
|
||||
STMT_Expr,
|
||||
STMT_List,
|
||||
STMT_Return,
|
||||
STMT_If,
|
||||
STMT_For,
|
||||
}Stmt_Kind;
|
||||
|
||||
struct Stmt_If{
|
||||
Stmt_If *next;
|
||||
Expr *cond;
|
||||
Stmt *body;
|
||||
};
|
||||
|
||||
struct Stmt{
|
||||
Stmt_Kind kind;
|
||||
Stmt *next;
|
||||
Token *pos;
|
||||
union{
|
||||
Stmt_If stmt_if;
|
||||
Decl *decl;
|
||||
Expr *expr;
|
||||
struct{
|
||||
Stmt *first;
|
||||
Stmt *last;
|
||||
}list;
|
||||
struct{
|
||||
Expr *expr;
|
||||
}ret;
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// Expression constructors
|
||||
//-----------------------------------------------------------------------------
|
||||
function Expr *
|
||||
expr_new(Arena *p, Expr_Kind kind, Token *token){
|
||||
@@ -216,28 +374,171 @@ expr_index(Arena *p, Token *token, Expr *atom, Expr *index){
|
||||
function Expr *
|
||||
expr_cast(Arena *p, Token *token, Typespec *type, Expr *exp){
|
||||
Expr *expr = expr_new(p, EK_Cast, token);
|
||||
expr->cast.type = type;
|
||||
expr->cast.typespec = type;
|
||||
expr->cast.expr = exp;
|
||||
return expr;
|
||||
}
|
||||
|
||||
function Expr *
|
||||
expr_sizeof_type(Arena *p, Token *token, Typespec *type){
|
||||
Expr *expr = expr_new(p, EK_Sizeof, token);
|
||||
expr->size_of.kind = SIZEOF_Type;
|
||||
expr->size_of.type = type;
|
||||
expr_size_type(Arena *p, Token *token, Typespec *type){
|
||||
Expr *expr = expr_new(p, EK_SizeType, token);
|
||||
expr->size_type.typespec = type;
|
||||
return expr;
|
||||
}
|
||||
|
||||
function Expr *
|
||||
expr_sizeof_expr(Arena *p, Token *token, Expr *in_expr){
|
||||
Expr *expr = expr_new(p, EK_Sizeof, token);
|
||||
expr->size_of.kind = SIZEOF_Expr;
|
||||
expr->size_of.expr = in_expr;
|
||||
Expr *expr = expr_new(p, EK_SizeExpr, token);
|
||||
expr->size_expr.expr = in_expr;
|
||||
return expr;
|
||||
}
|
||||
|
||||
function void
|
||||
expr_call_push(Expr *list, Expr *expr){
|
||||
SLLQueuePush(list->call.first, list->call.last, expr);
|
||||
function Expr *
|
||||
expr_compound(Arena *arena, Token *pos, Typespec *typespec){
|
||||
Expr *result = expr_new(arena, EK_Compound, pos);
|
||||
result->compound.typespec = typespec;
|
||||
return result;
|
||||
}
|
||||
|
||||
function Expr_Compound_Field *
|
||||
expr_compound_new(Arena *arena, Expr_Compound_Kind kind, Token *pos, Expr *init){
|
||||
Expr_Compound_Field *result = arena_push_struct(arena, Expr_Compound_Field);
|
||||
result->kind = kind;
|
||||
result->pos = pos;
|
||||
result->init = init;
|
||||
return result;
|
||||
}
|
||||
|
||||
function Expr_Compound_Field *
|
||||
expr_compound_default(Arena *arena, Token *pos, Expr *init){
|
||||
Expr_Compound_Field *result = expr_compound_new(arena, COMPOUND_Default, pos, init);
|
||||
return result;
|
||||
}
|
||||
|
||||
function Expr_Compound_Field *
|
||||
expr_compound_named(Arena *arena, Token *pos, Intern_String name, Expr *init){
|
||||
Expr_Compound_Field *result = expr_compound_new(arena, COMPOUND_Named, pos, init);
|
||||
result->name = name;
|
||||
return result;
|
||||
}
|
||||
|
||||
function Expr_Compound_Field *
|
||||
expr_compound_index(Arena *arena, Token *pos, Expr *index, Expr *init){
|
||||
Expr_Compound_Field *result = expr_compound_new(arena, COMPOUND_Index, pos, init);
|
||||
result->index = index;
|
||||
return result;
|
||||
}
|
||||
|
||||
function void
|
||||
expr_call_push(Expr *list, Expr_Compound_Field *field){
|
||||
SLLQueuePush(list->call.first, list->call.last, field);
|
||||
}
|
||||
|
||||
function void
|
||||
expr_compound_push(Expr *list, Expr_Compound_Field *field){
|
||||
SLLQueuePush(list->compound.first, list->compound.last, field);
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// Double linked list
|
||||
//-----------------------------------------------------------------------------
|
||||
function void
|
||||
decl_list_push(Decl *l, Decl *node){
|
||||
if(l->list_decl.first == 0){
|
||||
l->list_decl.first = l->list_decl.last = node;
|
||||
node->prev = 0;
|
||||
node->next = 0;
|
||||
}
|
||||
else{
|
||||
l->list_decl.last->next = node;
|
||||
node->prev = l->list_decl.last;
|
||||
node->next = 0;
|
||||
l->list_decl.last = node;
|
||||
}
|
||||
node->parent = l;
|
||||
}
|
||||
|
||||
function void
|
||||
decl_list_push_front(Decl *l, Decl *node){
|
||||
if(l->list_decl.first == 0){
|
||||
l->list_decl.first = l->list_decl.last = node;
|
||||
node->prev = 0;
|
||||
node->next = 0;
|
||||
}
|
||||
else{
|
||||
node->next = l->list_decl.first;
|
||||
l->list_decl.first->prev = node;
|
||||
node->prev = 0;
|
||||
l->list_decl.first = node;
|
||||
}
|
||||
node->parent = l;
|
||||
}
|
||||
|
||||
function void
|
||||
decl_list_remove(Decl *l, Decl *node){
|
||||
if(l->list_decl.first == l->list_decl.last){
|
||||
assert(node == l->list_decl.last);
|
||||
l->list_decl.first = l->list_decl.last = 0;
|
||||
}
|
||||
else if(l->list_decl.last == node){
|
||||
l->list_decl.last = l->list_decl.last->prev;
|
||||
l->list_decl.last->next = 0;
|
||||
}
|
||||
else if(l->list_decl.first == node){
|
||||
l->list_decl.first = l->list_decl.first->next;
|
||||
l->list_decl.first->prev = 0;
|
||||
}
|
||||
else{
|
||||
node->prev->next = node->next;
|
||||
node->next->prev = node->prev;
|
||||
}
|
||||
|
||||
node->parent = 0;
|
||||
node->prev = 0;
|
||||
node->next = 0;
|
||||
}
|
||||
|
||||
function void
|
||||
list_print(Decl *decls){
|
||||
|
||||
printf("next:");
|
||||
for(Decl *n = decls[0].list_decl.first; n; n=n->next){
|
||||
printf("%d", n->kind);
|
||||
}
|
||||
printf("prev:");
|
||||
for(Decl *n = decls[0].list_decl.last; n; n=n->prev){
|
||||
printf("%d", n->kind);
|
||||
}
|
||||
printf("parent:");
|
||||
for(Decl *n = decls[0].list_decl.first; n; n=n->next){
|
||||
printf("%d", n->parent->kind);
|
||||
}
|
||||
}
|
||||
|
||||
function void
|
||||
ast_test(){
|
||||
Decl decls[16] = {0};
|
||||
decls[0].kind = 9;
|
||||
decls[1].kind = 1;
|
||||
decls[2].kind = 2;
|
||||
decls[3].kind = 3;
|
||||
decls[4].kind = 4;
|
||||
decl_list_push(decls, decls+1);
|
||||
decl_list_push(decls, decls+2);
|
||||
decl_list_push(decls, decls+3);
|
||||
decl_list_push_front(decls, decls+4);
|
||||
|
||||
//list_print(decls);
|
||||
decl_list_remove(decls, decls+1);
|
||||
//list_print(decls);
|
||||
decl_list_remove(decls, decls+2);
|
||||
//list_print(decls);
|
||||
decl_list_remove(decls, decls+3);
|
||||
//list_print(decls);
|
||||
decl_list_remove(decls, decls+4);
|
||||
//list_print(decls);
|
||||
assert(decls[0].list_decl.first == 0);
|
||||
assert(decls[0].list_decl.last == 0);
|
||||
}
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user