]> git.xonotic.org Git - xonotic/gmqcc.git/blob - test/ast-test.c
44a9c0daf3487448d1e422eac2f4da0385005a81
[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 BUILTIN(print, TYPE_VOID, -1);
35 PARAM(TYPE_STRING, text);
36 ENDBUILTIN();
37
38     TESTINIT();
39 VAR(TYPE_FLOAT, f0);
40 VAR(TYPE_FLOAT, f1);
41 VAR(TYPE_FLOAT, f5);
42 MKCONSTFLOAT(f0, 0.0);
43 MKCONSTFLOAT(f1, 1.0);
44 MKCONSTFLOAT(f5, 5.0);
45
46 FUNCTION(foo, TYPE_VOID);
47 ENDFUNCTION(foo);
48
49 FUNCTION(main, TYPE_VOID);
50
51     VAR(TYPE_FLOAT, vi);
52     VAR(TYPE_FLOAT, vx);
53
54     MKLOCAL(vi);
55     MKLOCAL(vx);
56
57     STATE(ASSIGN(STORE_F, vi, f0));
58     WHILE(BIN(LT, vi, f5));
59         STATE(ASSIGN(STORE_F, vx, BIN(MUL_F, vi, f5)));
60         STATE(ASSIGN(STORE_F, vi, BIN(ADD_F, vi, f1)));
61     ENDWHILE();
62
63 ENDFUNCTION(main);
64
65     ir = ir_builder_new("ast_test");
66     assert(ir);
67
68     /* gen globals */
69     for (i = 0; i < globals_elements; ++i) {
70         if (!ast_global_codegen(globals_data[i], ir)) {
71             assert(!"failed to generate global");
72         }
73     }
74
75     /* gen functions */
76     for (i = 0; i < functions_elements; ++i) {
77         if (!ast_function_codegen(functions_data[i], ir)) {
78             assert(!"failed to generate function");
79         }
80         if (!ir_function_finalize(functions_data[i]->ir_func))
81             assert(!"finalize on function failed...");
82     }
83
84
85     /* dump */
86     ir_builder_dump(ir, printf);
87
88     /* Now create a file */
89     if (!ir_builder_generate(ir, "test_ast.dat"))
90         printf("*** failed to generate code\n");
91
92     /* ir cleanup */
93     ir_builder_delete(ir);
94
95     /* cleanup */
96     /* Functions must be deleted FIRST since their expressions
97      * reference global variables.
98      */
99     for (i = 0; i < functions_elements; ++i) {
100         ast_function_delete(functions_data[i]);
101     }
102     if (functions_data)
103         mem_d(functions_data);
104
105     /* We must delete not only globals, but also the functions'
106      * ast_values (their type and name), that's why we added them to the globals vector.
107      */
108     for (i = 0; i < globals_elements; ++i) {
109         ast_value_delete(globals_data[i]);
110     }
111     if (globals_data)
112         mem_d(globals_data);
113     return 0;
114 }