summaryrefslogtreecommitdiff
path: root/ast.c
blob: fda03d383809780b359fe1640d1deadf1cfc55f8 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
#include "ast.h"
#include <stdlib.h>
#include <stddef.h>
#include <stdio.h>
#include <assert.h>

AstVec astvec_new() {
	AstNode *vals = malloc(2 * sizeof(AstNode));
	return (AstVec){
		.len = 0,
		.cap = 2,
		vals = vals
	};
}

void astvec_append(AstVec *v, AstNode val) {
	if (v->len == v->cap) {
		size_t newcap = v->cap * 2;
		// printf("%ld to %ld\n", v->cap, newcap);
		v->vals = realloc(v->vals, newcap * sizeof(AstNode));
		v->cap = newcap;
	}
	v->vals[v->len] = val;
	v->len ++;
}

void astnode_append(AstNode *l, AstNode val) {
	// printf("   astnode_append: %d\n",l->ty);
	assert(l->ty == AST_LIST);
	astvec_append(&l->as.list, val);
}

AstNode astnode_new_num(int n) {
	return (AstNode){
		.ty = AST_NUM,
		.as = {
			.num = n,
		},
	};
}

AstNode astnode_new_list() {
	return (AstNode){
		.ty = AST_LIST,
		.as = {
			.list = astvec_new()
		}
	};
}

AstNode astnode_new_ident(char *s) {
	return (AstNode){
		.ty =AST_IDENT,
		.as = {
			.str = s
		}
	};
}

AstNode astnode_new_string(char *s) {
	return (AstNode){
		.ty =AST_STRING,
		.as = {
			.str = s
		}
	};
}

void astnode_disp(AstNode *a) {
	switch (a->ty) {
	case AST_NUM:
		printf("%s:%d ",ast_ty_to_str(a->ty),a->as.num);
		break;
	case AST_LIST:;
		AstVec *v = &a->as.list;
		printf("%s:(",ast_ty_to_str(a->ty));
		for (int i = 0; i < v->len; i++) {
			astnode_disp(&v->vals[i]);
		}
		printf(")");
		break;
	case AST_IDENT:
	case AST_STRING:
		printf("%s:%s ",ast_ty_to_str(a->ty), a->as.str);
		break;

	}
}

const char* ty_names[] = {
	"list", "num", "ident", "string"
};
const char *ast_ty_to_str(AstTy ty) {
	return ty_names[ty];
}