]> git.xonotic.org Git - xonotic/gmqcc.git/blob - test/ast-test.c
add AINSTR_END to the end of functions so the debug-printing knows when to end...
[xonotic/gmqcc.git] / test / ast-test.c
1 #include "gmqcc.h"
2 #include "ast.h"
3
4 /* NOTE: it's a test - I'll abort() on epic-failure */
5
6 #ifdef assert
7 #   undef assert
8 #endif
9 /* (note: 'do {} while(0)' forces the need for a semicolon after assert() */
10 #define assert(x) do { if ( !(x) ) { printf("Assertion failed: %s\n", #x); abort(); } } while(0)
11
12 VECTOR_MAKE(ast_value*, globals);
13 VECTOR_MAKE(ast_function*, functions);
14
15 #include "ast-macros.h"
16
17 int main()
18 {
19     size_t i;
20
21     ir_builder     *ir;
22
23     TESTVARS();
24
25     DEFVAR(vi);
26     DEFVAR(vx);
27     DEFVAR(f0);
28     DEFVAR(f1);
29     DEFVAR(f5);
30     DEFVAR(print);
31
32     /* opts_debug = true; */
33
34 #if 0
35     BUILTIN(print, TYPE_VOID, -1);
36     PARAM(TYPE_STRING, text);
37     ENDBUILTIN();
38 #endif
39
40     TESTINIT();
41 VAR(TYPE_FLOAT, f0);
42 VAR(TYPE_FLOAT, f1);
43 VAR(TYPE_FLOAT, f5);
44 MKCONSTFLOAT(f0, 0.0);
45 MKCONSTFLOAT(f1, 1.0);
46 MKCONSTFLOAT(f5, 5.0);
47
48 FUNCTION(foo, TYPE_VOID);
49 ENDFUNCTION(foo);
50
51 FUNCTION(main, TYPE_VOID);
52
53     VAR(TYPE_FLOAT, vi);
54     VAR(TYPE_FLOAT, vx);
55
56     MKLOCAL(vi);
57     MKLOCAL(vx);
58
59     STATE(ASSIGN(STORE_F, vi, f0));
60     WHILE(BIN(LT, vi, f5));
61         STATE(ASSIGN(STORE_F, vx, BIN(MUL_F, vi, f5)));
62         STATE(ASSIGN(STORE_F, vi, BIN(ADD_F, vi, f1)));
63     ENDWHILE();
64
65 ENDFUNCTION(main);
66
67     ir = ir_builder_new("ast_test");
68     assert(ir);
69
70     /* gen globals */
71     for (i = 0; i < globals_elements; ++i) {
72         if (!ast_global_codegen(globals_data[i], ir)) {
73             assert(!"failed to generate global");
74         }
75     }
76
77     /* gen functions */
78     for (i = 0; i < functions_elements; ++i) {
79         if (!ast_function_codegen(functions_data[i], ir)) {
80             assert(!"failed to generate function");
81         }
82         if (!ir_function_finalize(functions_data[i]->ir_func))
83             assert(!"finalize on function failed...");
84     }
85
86
87     /* dump */
88     ir_builder_dump(ir, printf);
89
90     /* Now create a file */
91     if (!ir_builder_generate(ir, "test_ast.dat"))
92         printf("*** failed to generate code\n");
93
94     /* ir cleanup */
95     ir_builder_delete(ir);
96
97     /* cleanup */
98     /* Functions must be deleted FIRST since their expressions
99      * reference global variables.
100      */
101     for (i = 0; i < functions_elements; ++i) {
102         ast_function_delete(functions_data[i]);
103     }
104     if (functions_data)
105         mem_d(functions_data);
106
107     /* We must delete not only globals, but also the functions'
108      * ast_values (their type and name), that's why we added them to the globals vector.
109      */
110     for (i = 0; i < globals_elements; ++i) {
111         ast_value_delete(globals_data[i]);
112     }
113     if (globals_data)
114         mem_d(globals_data);
115     return 0;
116 }