]> git.xonotic.org Git - xonotic/gmqcc.git/commitdiff
A new ast-test, now using some macros to make them easier to write...
authorWolfgang (Blub) Bumiller <blub@speed.at>
Fri, 4 May 2012 10:28:35 +0000 (12:28 +0200)
committerWolfgang (Blub) Bumiller <blub@speed.at>
Fri, 4 May 2012 10:28:35 +0000 (12:28 +0200)
test/ast-macros.h [new file with mode: 0644]
test/ast-test.c

diff --git a/test/ast-macros.h b/test/ast-macros.h
new file mode 100644 (file)
index 0000000..2f91d1f
--- /dev/null
@@ -0,0 +1,95 @@
+#ifndef TEST_AST_MACROS_HDR
+#define TEST_AST_MACROS_HDR
+
+#if 0
+VAR(TYPE_FLOAT, i);
+VAR(TYPE_FLOAT, x);
+
+VAR(TYPE_FLOAT, f0);
+VAR(TYPE_FLOAT, f1);
+VAR(TYPE_FLOAT, f5);
+
+MKCONSTFLOAT(f0, 0.0);
+MKCONSTFLOAT(f1, 1.0);
+MKCONSTFLOAT(f5, 5.0);
+
+STATE(ASSIGN(STORE_F, i, f0));
+WHILE(BIN(LT, i, f5));
+STATE(ASSIGN(STORE_F, x, BIN(MUL_F, i, f5)));
+STATE(ASSIGN(STORE_F, i, BIN(ADD_F, i, f1)));
+ENDWHILE();
+#endif
+
+#define TESTVARS()   \
+ast_block *curblock; \
+lex_ctx    ctx
+
+#define TESTINIT()   \
+ctx.file = NULL;     \
+ctx.line = 1;
+
+#define DEFVAR(name) \
+ast_value *name
+
+#define VAR(type, name) \
+name = ast_value_new(ctx, #name, type)
+
+#define MKGLOBAL(name) \
+assert(globals_add(name) >= 0)
+
+#define MKCONSTFLOAT(name, value)  \
+do {                               \
+    name->isconst = true;          \
+    name->constval.vfloat = value; \
+    MKGLOBAL(name);                \
+} while(0)
+
+#define STATE(a)                                 \
+do {                                             \
+    ast_expression *exp = (ast_expression*)(a);  \
+    assert(ast_block_exprs_add(curblock, exp)); \
+} while(0)
+
+#define ASSIGN(op, a, b) \
+(ast_expression*)ast_store_new(ctx, INSTR_##op, (a), (ast_expression*)(b))
+
+#define BIN(op, a, b) \
+(ast_expression*)ast_binary_new(ctx, INSTR_##op, (ast_expression*)(a), (ast_expression*)(b))
+
+#define WHILE(cond)                                    \
+do {                                                   \
+    ast_expression *wh_cond = (ast_expression*)(cond); \
+    ast_block *wh_body = ast_block_new(ctx);           \
+    ast_block *oldcur = curblock;                      \
+    ast_loop  *loop;                                   \
+    curblock = wh_body;
+
+#define ENDWHILE()                                             \
+    curblock = oldcur;                                         \
+    loop = ast_loop_new(ctx, NULL, (ast_expression*)wh_cond,   \
+                        NULL, NULL, (ast_expression*)wh_body); \
+    assert(loop);                                              \
+    STATE(loop);                                               \
+} while(0)
+
+#define FUNCTION(name)                                          \
+do {                                                            \
+    ast_function *func_##name;                                  \
+    ast_block    *my_funcblock;                                 \
+    DEFVAR(var_##name);                                         \
+    VAR(TYPE_FUNCTION, var_##name);                             \
+    MKGLOBAL(var_##name);                                       \
+    func_##name = ast_function_new(ctx, #name, var_##name);     \
+    assert(functions_add(func_##name) >= 0);                    \
+    my_funcblock = ast_block_new(ctx);                          \
+    assert(my_funcblock);                                       \
+    assert(ast_function_blocks_add(func_##name, my_funcblock)); \
+    curblock = my_funcblock;
+    
+#define MKLOCAL(var) \
+    assert(ast_block_locals_add(curblock, var))
+
+#define ENDFUNCTION(name) \
+} while(0)
+
+#endif
index 1f8a7f6a0c6df533eeeae669bb3fe187d2e9d17c..eb4e1e9c65f30bccebd51b393764b58c902ef56a 100644 (file)
@@ -12,6 +12,7 @@
 VECTOR_MAKE(ast_value*, globals);
 VECTOR_MAKE(ast_function*, functions);
 
+#if 0
 int main()
 {
     /* AST */
@@ -124,6 +125,94 @@ int main()
             assert(!"finalize on function failed...");
     }
 
+    /* dump */
+    ir_builder_dump(ir, printf);
+
+    /* ir cleanup */
+    ir_builder_delete(ir);
+
+    /* cleanup */
+    /* Functions must be deleted FIRST since their expressions
+     * reference global variables.
+     */
+    for (i = 0; i < functions_elements; ++i) {
+        ast_function_delete(functions_data[i]);
+    }
+    if (functions_data)
+        mem_d(functions_data);
+
+    /* We must delete not only globals, but also the functions'
+     * ast_values (their type and name), that's why we added them to the globals vector.
+     */
+    for (i = 0; i < globals_elements; ++i) {
+        ast_value_delete(globals_data[i]);
+    }
+    if (globals_data)
+        mem_d(globals_data);
+    return 0;
+}
+#endif
+
+#include "ast-macros.h"
+
+int main()
+{
+    size_t i;
+
+    ir_builder     *ir;
+
+    TESTVARS();
+
+    DEFVAR(vi);
+    DEFVAR(vx);
+    DEFVAR(f0);
+    DEFVAR(f1);
+    DEFVAR(f5);
+    
+    TESTINIT();
+VAR(TYPE_FLOAT, f0);
+VAR(TYPE_FLOAT, f1);
+VAR(TYPE_FLOAT, f5);
+MKCONSTFLOAT(f0, 0.0);
+MKCONSTFLOAT(f1, 1.0);
+MKCONSTFLOAT(f5, 5.0);
+
+FUNCTION(main);
+
+VAR(TYPE_FLOAT, vi);
+VAR(TYPE_FLOAT, vx);
+
+MKLOCAL(vi);
+MKLOCAL(vx);
+
+STATE(ASSIGN(STORE_F, vi, f0));
+WHILE(BIN(LT, vi, f5));
+STATE(ASSIGN(STORE_F, vx, BIN(MUL_F, vi, f5)));
+STATE(ASSIGN(STORE_F, vi, BIN(ADD_F, vi, f1)));
+ENDWHILE();
+
+ENDFUNCTION(main);
+    
+    ir = ir_builder_new("ast_test");
+    assert(ir);
+
+    /* gen globals */
+    for (i = 0; i < globals_elements; ++i) {
+        if (!ast_global_codegen(globals_data[i], ir)) {
+            assert(!"failed to generate global");
+        }
+    }
+
+    /* gen functions */
+    for (i = 0; i < functions_elements; ++i) {
+        if (!ast_function_codegen(functions_data[i], ir)) {
+            assert(!"failed to generate function");
+        }
+        if (!ir_function_finalize(functions_data[i]->ir_func))
+            assert(!"finalize on function failed...");
+    }
+
+
     /* dump */
     ir_builder_dump(ir, printf);