]> git.xonotic.org Git - xonotic/gmqcc.git/blobdiff - intrin.cpp
add another test that we just didn't have anywhere else yet
[xonotic/gmqcc.git] / intrin.cpp
index 291636703e4a2ae93ea4620f4ae201db6a35a13a..cc6250be7cd1194986ba31d3001dca24204337ac 100644 (file)
@@ -1,11 +1,14 @@
 #include <string.h>
+
+#include "ast.h"
+#include "fold.h"
 #include "parser.h"
 
 lex_ctx_t intrin::ctx() const {
     return parser_ctx(m_parser);
 }
 
-ast_function *intrin::value(ast_value **out, const char *name, qcint_t vtype) {
+ast_function *intrin::value(ast_value **out, const char *name, qc_type vtype) {
     ast_value *value = nullptr;
     ast_function *func  = nullptr;
     char buffer[1024];
@@ -15,10 +18,10 @@ ast_function *intrin::value(ast_value **out, const char *name, qcint_t vtype) {
     util_snprintf(stype,  sizeof(stype),   "<%s>",        type_name[vtype]);
 
     value = ast_value_new(ctx(), buffer, TYPE_FUNCTION);
-    value->intrinsic = true;
-    value->expression.next = (ast_expression*)ast_value_new(ctx(), stype, vtype);
+    value->m_intrinsic = true;
+    value->m_next = (ast_expression*)ast_value_new(ctx(), stype, vtype);
     func = ast_function_new(ctx(), buffer, value);
-    value->expression.flags |= AST_FLAG_ERASEABLE;
+    value->m_flags |= AST_FLAG_ERASEABLE;
 
     *out = value;
     return func;
@@ -52,16 +55,16 @@ ast_expression *intrin::isfinite_() {
     ast_block    *block     = ast_block_new(ctx());
 
     /* float x; */
-    val->expression.params.push_back(x);
+    val->m_type_params.push_back(x);
 
     /* <callisnan> = isnan(x); */
-    callisnan->params.push_back((ast_expression*)x);
+    callisnan->m_params.push_back((ast_expression*)x);
 
     /* <callisinf> = isinf(x); */
-    callisinf->params.push_back((ast_expression*)x);
+    callisinf->m_params.push_back((ast_expression*)x);
 
     /* return (!<callisnan> || <callisinf>); */
-    block->exprs.push_back(
+    block->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)ast_unary_new(
@@ -77,7 +80,7 @@ ast_expression *intrin::isfinite_() {
         )
     );
 
-    func->blocks.push_back(block);
+    func->m_blocks.emplace_back(block);
     reg(val, func);
 
     return (ast_expression*)val;;
@@ -94,7 +97,7 @@ ast_expression *intrin::isinf_() {
     ast_block *body = ast_block_new(ctx());
     ast_function *func = value(&val, "isinf", TYPE_FLOAT);
 
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)ast_binary_new(
@@ -104,7 +107,7 @@ ast_expression *intrin::isinf_() {
                     ctx(),
                     INSTR_NE_F,
                     (ast_expression*)x,
-                    (ast_expression*)m_fold->imm_float[0]
+                    (ast_expression*)m_fold->m_imm_float[0]
                 ),
                 (ast_expression*)ast_binary_new(
                     ctx(),
@@ -121,8 +124,8 @@ ast_expression *intrin::isinf_() {
         )
     );
 
-    val->expression.params.push_back(x);
-    func->blocks.push_back(body);
+    val->m_type_params.push_back(x);
+    func->m_blocks.emplace_back(body);
 
     reg(val, func);
 
@@ -144,8 +147,8 @@ ast_expression *intrin::isnan_() {
     ast_block *body  = ast_block_new(ctx());
     ast_function *func = value(&val, "isnan", TYPE_FLOAT);
 
-    body->locals.push_back(local);
-    body->exprs.push_back(
+    body->m_locals.push_back(local);
+    body->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
@@ -154,7 +157,7 @@ ast_expression *intrin::isnan_() {
         )
     );
 
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)ast_binary_new(
@@ -166,8 +169,8 @@ ast_expression *intrin::isnan_() {
         )
     );
 
-    val->expression.params.push_back(arg1);
-    func->blocks.push_back(body);
+    val->m_type_params.push_back(arg1);
+    func->m_blocks.emplace_back(body);
 
     reg(val, func);
 
@@ -186,18 +189,18 @@ ast_expression *intrin::isnormal_() {
     ast_block *body = ast_block_new(ctx());
     ast_function *func = value(&val, "isnormal", TYPE_FLOAT);
 
-    val->expression.params.push_back(x);
-    callisfinite->params.push_back((ast_expression*)x);
+    val->m_type_params.push_back(x);
+    callisfinite->m_params.push_back((ast_expression*)x);
 
     /* return <callisfinite> */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)callisfinite
         )
     );
 
-    func->blocks.push_back(body);
+    func->m_blocks.emplace_back(body);
     reg(val, func);
     return (ast_expression*)val;
 }
@@ -213,10 +216,10 @@ ast_expression *intrin::signbit_() {
     ast_block *body = ast_block_new(ctx());
     ast_function *func = value(&val, "signbit", TYPE_FLOAT);
 
-    val->expression.params.push_back(x);
+    val->m_type_params.push_back(x);
 
     /* return (x < 0); */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)ast_ternary_new(
@@ -225,15 +228,15 @@ ast_expression *intrin::signbit_() {
                     ctx(),
                     INSTR_LT,
                     (ast_expression*)x,
-                    (ast_expression*)m_fold->imm_float[0]
+                    (ast_expression*)m_fold->m_imm_float[0]
                 ),
-                (ast_expression*)m_fold->imm_float[1],
-                (ast_expression*)m_fold->imm_float[0]
+                (ast_expression*)m_fold->m_imm_float[1],
+                (ast_expression*)m_fold->m_imm_float[0]
             )
         )
     );
 
-    func->blocks.push_back(body);
+    func->m_blocks.emplace_back(body);
     reg(val, func);
     return (ast_expression*)val;
 }
@@ -251,10 +254,10 @@ ast_expression *intrin::acosh_() {
     ast_block    *body     = ast_block_new(ctx());
     ast_function *func     = value(&val, "acosh", TYPE_FLOAT);
 
-    val->expression.params.push_back(x);
+    val->m_type_params.push_back(x);
 
     /* <callsqrt> = sqrt((x * x) - 1); */
-    callsqrt->params.push_back(
+    callsqrt->m_params.push_back(
         (ast_expression*)ast_binary_new(
             ctx(),
             INSTR_SUB_F,
@@ -264,12 +267,12 @@ ast_expression *intrin::acosh_() {
                 (ast_expression*)x,
                 (ast_expression*)x
             ),
-            (ast_expression*)m_fold->imm_float[1]
+            (ast_expression*)m_fold->m_imm_float[1]
         )
     );
 
     /* <calllog> = log(x + <callsqrt>); */
-    calllog->params.push_back(
+    calllog->m_params.push_back(
         (ast_expression*)ast_binary_new(
             ctx(),
             INSTR_ADD_F,
@@ -279,14 +282,14 @@ ast_expression *intrin::acosh_() {
     );
 
     /* return <calllog>; */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)calllog
         )
     );
 
-    func->blocks.push_back(body);
+    func->m_blocks.emplace_back(body);
     reg(val, func);
     return (ast_expression*)val;
 }
@@ -304,10 +307,10 @@ ast_expression *intrin::asinh_() {
     ast_block *body = ast_block_new(ctx());
     ast_function *func = value(&val, "asinh", TYPE_FLOAT);
 
-    val->expression.params.push_back(x);
+    val->m_type_params.push_back(x);
 
     /* <callsqrt> = sqrt((x * x) + 1); */
-    callsqrt->params.push_back(
+    callsqrt->m_params.push_back(
         (ast_expression*)ast_binary_new(
             ctx(),
             INSTR_ADD_F,
@@ -317,12 +320,12 @@ ast_expression *intrin::asinh_() {
                 (ast_expression*)x,
                 (ast_expression*)x
             ),
-            (ast_expression*)m_fold->imm_float[1]
+            (ast_expression*)m_fold->m_imm_float[1]
         )
     );
 
     /* <calllog> = log(x + <callsqrt>); */
-    calllog->params.push_back(
+    calllog->m_params.push_back(
         (ast_expression*)ast_binary_new(
             ctx(),
             INSTR_ADD_F,
@@ -332,14 +335,14 @@ ast_expression *intrin::asinh_() {
     );
 
     /* return <calllog>; */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)calllog
         )
     );
 
-    func->blocks.push_back(body);
+    func->m_blocks.emplace_back(body);
     reg(val, func);
     return (ast_expression*)val;
 }
@@ -356,39 +359,39 @@ ast_expression *intrin::atanh_() {
     ast_block    *body    = ast_block_new(ctx());
     ast_function *func    = value(&val, "atanh", TYPE_FLOAT);
 
-    val->expression.params.push_back(x);
+    val->m_type_params.push_back(x);
 
     /* <callog> = log((1 + x) / (1 - x)); */
-    calllog->params.push_back(
+    calllog->m_params.push_back(
         (ast_expression*)ast_binary_new(
             ctx(),
             INSTR_DIV_F,
             (ast_expression*)ast_binary_new(
                 ctx(),
                 INSTR_ADD_F,
-                (ast_expression*)m_fold->imm_float[1],
+                (ast_expression*)m_fold->m_imm_float[1],
                 (ast_expression*)x
             ),
             (ast_expression*)ast_binary_new(
                 ctx(),
                 INSTR_SUB_F,
-                (ast_expression*)m_fold->imm_float[1],
+                (ast_expression*)m_fold->m_imm_float[1],
                 (ast_expression*)x
             )
         )
     );
 
     /* return 0.5 * <calllog>; */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_binary_new(
             ctx(),
             INSTR_MUL_F,
-            (ast_expression*)fold_constgen_float(m_fold, 0.5, false),
+            (ast_expression*)m_fold->constgen_float(0.5, false),
             (ast_expression*)calllog
         )
     );
 
-    func->blocks.push_back(body);
+    func->m_blocks.emplace_back(body);
     reg(val, func);
     return (ast_expression*)val;
 }
@@ -413,29 +416,29 @@ ast_expression *intrin::exp_() {
     ast_block *body = ast_block_new(ctx());
     ast_function *func = value(&val, "exp", TYPE_FLOAT);
 
-    val->expression.params.push_back(x);
+    val->m_type_params.push_back(x);
 
-    body->locals.push_back(sum);
-    body->locals.push_back(acc);
-    body->locals.push_back(i);
+    body->m_locals.push_back(sum);
+    body->m_locals.push_back(acc);
+    body->m_locals.push_back(i);
 
     /* sum = 1.0; */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
             (ast_expression*)sum,
-            (ast_expression*)m_fold->imm_float[1]
+            (ast_expression*)m_fold->m_imm_float[1]
         )
     );
 
     /* acc = 1.0; */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
             (ast_expression*)acc,
-            (ast_expression*)m_fold->imm_float[1]
+            (ast_expression*)m_fold->m_imm_float[1]
         )
     );
 
@@ -443,7 +446,7 @@ ast_expression *intrin::exp_() {
      * for (i = 1; i < 200; ++i)
      *     sum += (acc *= x / i);
      */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_loop_new(
             ctx(),
             /* i = 1; */
@@ -451,14 +454,14 @@ ast_expression *intrin::exp_() {
                 ctx(),
                 INSTR_STORE_F,
                 (ast_expression*)i,
-                (ast_expression*)m_fold->imm_float[1]
+                (ast_expression*)m_fold->m_imm_float[1]
             ),
             /* i < 200; */
             (ast_expression*)ast_binary_new(
                 ctx(),
                 INSTR_LT,
                 (ast_expression*)i,
-                (ast_expression*)fold_constgen_float(m_fold, 200.0f, false)
+                (ast_expression*)m_fold->constgen_float(200.0f, false)
             ),
             false,
             nullptr,
@@ -469,7 +472,7 @@ ast_expression *intrin::exp_() {
                 INSTR_STORE_F,
                 INSTR_ADD_F,
                 (ast_expression*)i,
-                (ast_expression*)m_fold->imm_float[1]
+                (ast_expression*)m_fold->m_imm_float[1]
             ),
             /* sum += (acc *= (x / i)) */
             (ast_expression*)ast_binstore_new(
@@ -494,14 +497,14 @@ ast_expression *intrin::exp_() {
     );
 
     /* return sum; */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)sum
         )
     );
 
-    func->blocks.push_back(body);
+    func->m_blocks.emplace_back(body);
     reg(val, func);
     return (ast_expression*)val;
 }
@@ -518,20 +521,20 @@ ast_expression *intrin::exp2_() {
     ast_block *body = ast_block_new(ctx());
     ast_function *func = value(&val, "exp2", TYPE_FLOAT);
 
-    val->expression.params.push_back(arg1);
+    val->m_type_params.push_back(arg1);
 
-    callpow->params.push_back((ast_expression*)m_fold->imm_float[3]);
-    callpow->params.push_back((ast_expression*)arg1);
+    callpow->m_params.push_back((ast_expression*)m_fold->m_imm_float[3]);
+    callpow->m_params.push_back((ast_expression*)arg1);
 
     /* return <callpow> */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)callpow
         )
     );
 
-    func->blocks.push_back(body);
+    func->m_blocks.emplace_back(body);
     reg(val, func);
     return (ast_expression*)val;
 }
@@ -548,25 +551,25 @@ ast_expression *intrin::expm1_() {
     ast_block *body = ast_block_new(ctx());
     ast_function *func = value(&val, "expm1", TYPE_FLOAT);
 
-    val->expression.params.push_back(x);
+    val->m_type_params.push_back(x);
 
     /* <callexp> = exp(x); */
-    callexp->params.push_back((ast_expression*)x);
+    callexp->m_params.push_back((ast_expression*)x);
 
     /* return <callexp> - 1; */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)ast_binary_new(
                 ctx(),
                 INSTR_SUB_F,
                 (ast_expression*)callexp,
-                (ast_expression*)m_fold->imm_float[1]
+                (ast_expression*)m_fold->m_imm_float[1]
             )
         )
     );
 
-    func->blocks.push_back(body);
+    func->m_blocks.emplace_back(body);
     reg(val, func);
     return (ast_expression*)val;
 }
@@ -649,32 +652,32 @@ ast_expression *intrin::pow_() {
     ast_value *square     = ast_value_new(ctx(), "square",     TYPE_FLOAT);
     ast_value *accumulate = ast_value_new(ctx(), "accumulate", TYPE_FLOAT);
     ast_value *mid        = ast_value_new(ctx(), "mid",        TYPE_FLOAT);
-    body->locals.push_back(result);
-    body->locals.push_back(low);
-    body->locals.push_back(high);
-    body->locals.push_back(square);
-    body->locals.push_back(accumulate);
-    body->locals.push_back(mid);
+    body->m_locals.push_back(result);
+    body->m_locals.push_back(low);
+    body->m_locals.push_back(high);
+    body->m_locals.push_back(square);
+    body->m_locals.push_back(accumulate);
+    body->m_locals.push_back(mid);
 
-    val->expression.params.push_back(base);
-    val->expression.params.push_back(exp);
+    val->m_type_params.push_back(base);
+    val->m_type_params.push_back(exp);
 
     /*
      * if (exp == 0.0)
      *     return 1;
      */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_ifthen_new(
             ctx(),
             (ast_expression*)ast_binary_new(
                 ctx(),
                 INSTR_EQ_F,
                 (ast_expression*)exp,
-                (ast_expression*)m_fold->imm_float[0]
+                (ast_expression*)m_fold->m_imm_float[0]
             ),
             (ast_expression*)ast_return_new(
                 ctx(),
-                (ast_expression*)m_fold->imm_float[1]
+                (ast_expression*)m_fold->m_imm_float[1]
             ),
             nullptr
         )
@@ -684,14 +687,14 @@ ast_expression *intrin::pow_() {
      * if (exp == 1.0)
      *     return base;
      */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_ifthen_new(
             ctx(),
             (ast_expression*)ast_binary_new(
                 ctx(),
                 INSTR_EQ_F,
                 (ast_expression*)exp,
-                (ast_expression*)m_fold->imm_float[1]
+                (ast_expression*)m_fold->m_imm_float[1]
             ),
             (ast_expression*)ast_return_new(
                 ctx(),
@@ -702,8 +705,8 @@ ast_expression *intrin::pow_() {
     );
 
     /* <callpow1> = pow(base, -exp) */
-    callpow1->params.push_back((ast_expression*)base);
-    callpow1->params.push_back(
+    callpow1->m_params.push_back((ast_expression*)base);
+    callpow1->m_params.push_back(
         (ast_expression*)ast_unary_new(
             ctx(),
             VINSTR_NEG_F,
@@ -715,21 +718,21 @@ ast_expression *intrin::pow_() {
      * if (exp < 0)
      *     return 1.0 / <callpow1>;
      */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_ifthen_new(
             ctx(),
             (ast_expression*)ast_binary_new(
                 ctx(),
                 INSTR_LT,
                 (ast_expression*)exp,
-                (ast_expression*)m_fold->imm_float[0]
+                (ast_expression*)m_fold->m_imm_float[0]
             ),
             (ast_expression*)ast_return_new(
                 ctx(),
                 (ast_expression*)ast_binary_new(
                     ctx(),
                     INSTR_DIV_F,
-                    (ast_expression*)m_fold->imm_float[1],
+                    (ast_expression*)m_fold->m_imm_float[1],
                     (ast_expression*)callpow1
                 )
             ),
@@ -738,13 +741,13 @@ ast_expression *intrin::pow_() {
     );
 
     /* <callpow2> = pow(base, exp / 2) */
-    callpow2->params.push_back((ast_expression*)base);
-    callpow2->params.push_back(
+    callpow2->m_params.push_back((ast_expression*)base);
+    callpow2->m_params.push_back(
         (ast_expression*)ast_binary_new(
             ctx(),
             INSTR_DIV_F,
             (ast_expression*)exp,
-            (ast_expression*)m_fold->imm_float[3] /* 2.0f */
+            (ast_expression*)m_fold->m_imm_float[3] /* 2.0f */
         )
     );
 
@@ -754,7 +757,7 @@ ast_expression *intrin::pow_() {
      *     return result * result;
      * }
      */
-    expgt1->exprs.push_back(
+    expgt1->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
@@ -762,7 +765,7 @@ ast_expression *intrin::pow_() {
             (ast_expression*)callpow2
         )
     );
-    expgt1->exprs.push_back(
+    expgt1->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)ast_binary_new(
@@ -779,14 +782,14 @@ ast_expression *intrin::pow_() {
      *     <expgt1>
      * }
      */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_ifthen_new(
             ctx(),
             (ast_expression*)ast_binary_new(
                 ctx(),
                 INSTR_GE,
                 (ast_expression*)exp,
-                (ast_expression*)m_fold->imm_float[1]
+                (ast_expression*)m_fold->m_imm_float[1]
             ),
             (ast_expression*)expgt1,
             nullptr
@@ -796,7 +799,7 @@ ast_expression *intrin::pow_() {
     /*
      * <callsqrt1> = sqrt(base)
      */
-    callsqrt1->params.push_back((ast_expression*)base);
+    callsqrt1->m_params.push_back((ast_expression*)base);
 
     /*
      * low        = 0.0f;
@@ -805,23 +808,23 @@ ast_expression *intrin::pow_() {
      * accumulate = square;
      * mid        = high / 2.0f;
      */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_store_new(ctx(),
             INSTR_STORE_F,
             (ast_expression*)low,
-            (ast_expression*)m_fold->imm_float[0]
+            (ast_expression*)m_fold->m_imm_float[0]
         )
     );
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
             (ast_expression*)high,
-            (ast_expression*)m_fold->imm_float[1]
+            (ast_expression*)m_fold->m_imm_float[1]
         )
     );
 
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
@@ -830,7 +833,7 @@ ast_expression *intrin::pow_() {
         )
     );
 
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
@@ -838,7 +841,7 @@ ast_expression *intrin::pow_() {
             (ast_expression*)square
         )
     );
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
@@ -847,7 +850,7 @@ ast_expression *intrin::pow_() {
                 ctx(),
                 INSTR_DIV_F,
                 (ast_expression*)high,
-                (ast_expression*)m_fold->imm_float[3] /* 2.0f */
+                (ast_expression*)m_fold->m_imm_float[3] /* 2.0f */
             )
         )
     );
@@ -858,7 +861,7 @@ ast_expression *intrin::pow_() {
      *     accumulate *= square;
      * }
      */
-    midltexp->exprs.push_back(
+    midltexp->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
@@ -866,7 +869,7 @@ ast_expression *intrin::pow_() {
             (ast_expression*)mid
         )
     );
-    midltexp->exprs.push_back(
+    midltexp->m_exprs.push_back(
         (ast_expression*)ast_binstore_new(
             ctx(),
             INSTR_STORE_F,
@@ -882,7 +885,7 @@ ast_expression *intrin::pow_() {
      *     accumulate *= (1.0 / square);
      * }
      */
-    midltexpelse->exprs.push_back(
+    midltexpelse->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
@@ -890,7 +893,7 @@ ast_expression *intrin::pow_() {
             (ast_expression*)mid
         )
     );
-    midltexpelse->exprs.push_back(
+    midltexpelse->m_exprs.push_back(
         (ast_expression*)ast_binstore_new(
             ctx(),
             INSTR_STORE_F,
@@ -899,7 +902,7 @@ ast_expression *intrin::pow_() {
             (ast_expression*)ast_binary_new(
                 ctx(),
                 INSTR_DIV_F,
-                (ast_expression*)m_fold->imm_float[1],
+                (ast_expression*)m_fold->m_imm_float[1],
                 (ast_expression*)square
             )
         )
@@ -908,7 +911,7 @@ ast_expression *intrin::pow_() {
     /*
      * <callsqrt2> = sqrt(square)
      */
-    callsqrt2->params.push_back((ast_expression*)square);
+    callsqrt2->m_params.push_back((ast_expression*)square);
 
     /*
      * <whileblock> = {
@@ -921,7 +924,7 @@ ast_expression *intrin::pow_() {
      *     mid = (low + high) / 2;
      * }
      */
-    whileblock->exprs.push_back(
+    whileblock->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
@@ -929,7 +932,7 @@ ast_expression *intrin::pow_() {
             (ast_expression*)callsqrt2
         )
     );
-    whileblock->exprs.push_back(
+    whileblock->m_exprs.push_back(
         (ast_expression*)ast_ifthen_new(
             ctx(),
             (ast_expression*)ast_binary_new(
@@ -942,7 +945,7 @@ ast_expression *intrin::pow_() {
             (ast_expression*)midltexpelse
         )
     );
-    whileblock->exprs.push_back(
+    whileblock->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
@@ -956,7 +959,7 @@ ast_expression *intrin::pow_() {
                     (ast_expression*)low,
                     (ast_expression*)high
                 ),
-                (ast_expression*)m_fold->imm_float[3] /* 2.0f */
+                (ast_expression*)m_fold->m_imm_float[3] /* 2.0f */
             )
         )
     );
@@ -964,7 +967,7 @@ ast_expression *intrin::pow_() {
     /*
      * <callabs> = fabs(mid - exp)
      */
-    callfabs->params.push_back(
+    callfabs->m_params.push_back(
         (ast_expression*)ast_binary_new(
             ctx(),
             INSTR_SUB_F,
@@ -977,7 +980,7 @@ ast_expression *intrin::pow_() {
      * while (<callfabs>  > epsilon)
      *     <whileblock>
      */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_loop_new(
             ctx(),
             /* init */
@@ -987,7 +990,7 @@ ast_expression *intrin::pow_() {
                 ctx(),
                 INSTR_GT,
                 (ast_expression*)callfabs,
-                (ast_expression*)fold_constgen_float(m_fold, QC_POW_EPSILON, false)
+                (ast_expression*)m_fold->constgen_float(QC_POW_EPSILON, false)
             ),
             /* pre not */
             false,
@@ -1003,7 +1006,7 @@ ast_expression *intrin::pow_() {
     );
 
     /* return accumulate */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)accumulate
@@ -1011,7 +1014,7 @@ ast_expression *intrin::pow_() {
     );
 
     /* } */
-    func->blocks.push_back(body);
+    func->m_blocks.emplace_back(body);
     reg(val, func);
     return (ast_expression*)val;
 }
@@ -1033,14 +1036,14 @@ ast_expression *intrin::mod_() {
     ast_block    *body  = ast_block_new(ctx());
     ast_function *func  = value(&val, "mod", TYPE_FLOAT);
 
-    val->expression.params.push_back(a);
-    val->expression.params.push_back(b);
+    val->m_type_params.push_back(a);
+    val->m_type_params.push_back(b);
 
-    body->locals.push_back(div);
-    body->locals.push_back(sign);
+    body->m_locals.push_back(div);
+    body->m_locals.push_back(sign);
 
     /* div = a / b; */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
@@ -1055,7 +1058,7 @@ ast_expression *intrin::mod_() {
     );
 
     /* sign = (div < 0.0f) ? -1 : 1; */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
@@ -1066,16 +1069,16 @@ ast_expression *intrin::mod_() {
                     ctx(),
                     INSTR_LT,
                     (ast_expression*)div,
-                    (ast_expression*)m_fold->imm_float[0]
+                    (ast_expression*)m_fold->m_imm_float[0]
                 ),
-                (ast_expression*)m_fold->imm_float[2],
-                (ast_expression*)m_fold->imm_float[1]
+                (ast_expression*)m_fold->m_imm_float[2],
+                (ast_expression*)m_fold->m_imm_float[1]
             )
         )
     );
 
     /* floor(sign * div) */
-    call->params.push_back(
+    call->m_params.push_back(
         (ast_expression*)ast_binary_new(
             ctx(),
             INSTR_MUL_F,
@@ -1085,7 +1088,7 @@ ast_expression *intrin::mod_() {
     );
 
     /* return a - b * sign * <call> */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)ast_binary_new(
@@ -1107,7 +1110,7 @@ ast_expression *intrin::mod_() {
         )
     );
 
-    func->blocks.push_back(body);
+    func->m_blocks.emplace_back(body);
     reg(val, func);
     return (ast_expression*)val;
 }
@@ -1123,7 +1126,7 @@ ast_expression *intrin::fabs_() {
     ast_block    *body   = ast_block_new(ctx());
     ast_function *func   = value(&val, "fabs", TYPE_FLOAT);
 
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)ast_ternary_new(
@@ -1132,7 +1135,7 @@ ast_expression *intrin::fabs_() {
                     ctx(),
                     INSTR_LE,
                     (ast_expression*)arg1,
-                    (ast_expression*)m_fold->imm_float[0]
+                    (ast_expression*)m_fold->m_imm_float[0]
                 ),
                 (ast_expression*)ast_unary_new(
                     ctx(),
@@ -1144,9 +1147,9 @@ ast_expression *intrin::fabs_() {
         )
     );
 
-    val->expression.params.push_back(arg1);
+    val->m_type_params.push_back(arg1);
 
-    func->blocks.push_back(body);
+    func->m_blocks.emplace_back(body);
     reg(val, func);
     return (ast_expression*)val;
 }
@@ -1164,19 +1167,19 @@ ast_expression *intrin::epsilon_() {
     ast_block    *body   = ast_block_new(ctx());
     ast_function *func   = value(&val, "epsilon", TYPE_FLOAT);
 
-    body->locals.push_back(eps);
+    body->m_locals.push_back(eps);
 
     /* eps = 1.0f; */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
             (ast_expression*)eps,
-            (ast_expression*)m_fold->imm_float[0]
+            (ast_expression*)m_fold->m_imm_float[0]
         )
     );
 
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_loop_new(
             ctx(),
             nullptr,
@@ -1188,15 +1191,15 @@ ast_expression *intrin::epsilon_() {
                 (ast_expression*)ast_binary_new(
                     ctx(),
                     INSTR_ADD_F,
-                    (ast_expression*)m_fold->imm_float[1],
+                    (ast_expression*)m_fold->m_imm_float[1],
                     (ast_expression*)ast_binary_new(
                         ctx(),
                         INSTR_MUL_F,
                         (ast_expression*)eps,
-                        (ast_expression*)m_fold->imm_float[3] /* 2.0f */
+                        (ast_expression*)m_fold->m_imm_float[3] /* 2.0f */
                     )
                 ),
-                (ast_expression*)m_fold->imm_float[1]
+                (ast_expression*)m_fold->m_imm_float[1]
             ),
             false,
             nullptr,
@@ -1205,20 +1208,20 @@ ast_expression *intrin::epsilon_() {
                 INSTR_STORE_F,
                 INSTR_DIV_F,
                 (ast_expression*)eps,
-                (ast_expression*)m_fold->imm_float[3] /* 2.0f */
+                (ast_expression*)m_fold->m_imm_float[3] /* 2.0f */
             )
         )
     );
 
     /* return eps; */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)eps
         )
     );
 
-    func->blocks.push_back(body);
+    func->m_blocks.emplace_back(body);
     reg(val, func);
     return (ast_expression*)val;
 }
@@ -1235,18 +1238,18 @@ ast_expression *intrin::nan_() {
     ast_function *func   = value(&val, "nan", TYPE_FLOAT);
     ast_block    *block  = ast_block_new(ctx());
 
-    block->locals.push_back(x);
+    block->m_locals.push_back(x);
 
-    block->exprs.push_back(
+    block->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
             (ast_expression*)x,
-            (ast_expression*)m_fold->imm_float[0]
+            (ast_expression*)m_fold->m_imm_float[0]
         )
     );
 
-    block->exprs.push_back(
+    block->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)ast_binary_new(
@@ -1258,7 +1261,7 @@ ast_expression *intrin::nan_() {
         )
     );
 
-    func->blocks.push_back(block);
+    func->m_blocks.emplace_back(block);
     reg(val, func);
     return (ast_expression*)val;
 }
@@ -1278,22 +1281,22 @@ ast_expression *intrin::inf_() {
     ast_block    *block  = ast_block_new(ctx());
     size_t        i;
 
-    block->locals.push_back(x);
-    block->locals.push_back(y);
+    block->m_locals.push_back(x);
+    block->m_locals.push_back(y);
 
     /* to keep code size down */
     for (i = 0; i <= 1; i++) {
-        block->exprs.push_back(
+        block->m_exprs.push_back(
             (ast_expression*)ast_store_new(
                 ctx(),
                 INSTR_STORE_F,
                 (ast_expression*)((i == 0) ? x : y),
-                (ast_expression*)m_fold->imm_float[i]
+                (ast_expression*)m_fold->m_imm_float[i]
             )
         );
     }
 
-    block->exprs.push_back(
+    block->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)ast_binary_new(
@@ -1305,7 +1308,7 @@ ast_expression *intrin::inf_() {
         )
     );
 
-    func->blocks.push_back(block);
+    func->m_blocks.emplace_back(block);
     reg(val, func);
     return (ast_expression*)val;
 }
@@ -1403,30 +1406,30 @@ ast_expression *intrin::ln_() {
     ast_function *func = value(&val, "ln", TYPE_FLOAT);
     size_t i;
 
-    val->expression.params.push_back(power);
-    val->expression.params.push_back(base);
+    val->m_type_params.push_back(power);
+    val->m_type_params.push_back(base);
 
-    block->locals.push_back(whole);
-    block->locals.push_back(nth);
-    block->locals.push_back(sign);
-    block->locals.push_back(eps);
-    block->locals.push_back(A_i);
-    block->locals.push_back(B_i);
-    block->locals.push_back(A_iminus1);
-    block->locals.push_back(B_iminus1);
+    block->m_locals.push_back(whole);
+    block->m_locals.push_back(nth);
+    block->m_locals.push_back(sign);
+    block->m_locals.push_back(eps);
+    block->m_locals.push_back(A_i);
+    block->m_locals.push_back(B_i);
+    block->m_locals.push_back(A_iminus1);
+    block->m_locals.push_back(B_iminus1);
 
     /* sign = 1.0f; */
-    block->exprs.push_back(
+    block->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
             (ast_expression*)sign,
-            (ast_expression*)m_fold->imm_float[1]
+            (ast_expression*)m_fold->m_imm_float[1]
         )
     );
 
     /* eps = __builtin_epsilon(); */
-    block->exprs.push_back(
+    block->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
@@ -1447,13 +1450,13 @@ ast_expression *intrin::ln_() {
     for (i = 0; i <= 1; i++) {
         int j;
         for (j = 1; j >= 0; j--) {
-            block->exprs.push_back(
+            block->m_exprs.push_back(
                 (ast_expression*)ast_store_new(
                     ctx(),
                     INSTR_STORE_F,
                     (ast_expression*)((j) ? ((i) ? B_iminus1 : A_i)
                                           : ((i) ? A_iminus1 : B_i)),
-                    (ast_expression*)m_fold->imm_float[j]
+                    (ast_expression*)m_fold->m_imm_float[j]
                 )
             );
         }
@@ -1470,7 +1473,7 @@ ast_expression *intrin::ln_() {
      * }
      */
     for (i = 0; i <= 1; i++) {
-        ((i) ? blt1 : plt1)->exprs.push_back(
+        ((i) ? blt1 : plt1)->m_exprs.push_back(
             (ast_expression*)ast_store_new(
                 ctx(),
                 INSTR_STORE_F,
@@ -1478,18 +1481,18 @@ ast_expression *intrin::ln_() {
                 (ast_expression*)ast_binary_new(
                     ctx(),
                     INSTR_DIV_F,
-                    (ast_expression*)m_fold->imm_float[1],
+                    (ast_expression*)m_fold->m_imm_float[1],
                     (ast_expression*)((i) ? base : power)
                 )
             )
         );
-        plt1->exprs.push_back(
+        plt1->m_exprs.push_back(
             (ast_expression*)ast_binstore_new(
                 ctx(),
                 INSTR_STORE_F,
                 INSTR_MUL_F,
                 (ast_expression*)sign,
-                (ast_expression*)m_fold->imm_float[2]
+                (ast_expression*)m_fold->m_imm_float[2]
             )
         );
     }
@@ -1504,7 +1507,7 @@ ast_expression *intrin::ln_() {
      *         <blt1>
      * }
      */
-    plt1orblt1->exprs.push_back(
+    plt1orblt1->m_exprs.push_back(
         (ast_expression*)ast_ifthen_new(
             ctx(),
             (ast_expression*)ast_binary_new(
@@ -1514,13 +1517,13 @@ ast_expression *intrin::ln_() {
                     ctx(),
                     INSTR_LE,
                     (ast_expression*)power,
-                    (ast_expression*)m_fold->imm_float[0]
+                    (ast_expression*)m_fold->m_imm_float[0]
                 ),
                 (ast_expression*)ast_binary_new(
                     ctx(),
                     INSTR_LE,
                     (ast_expression*)base,
-                    (ast_expression*)m_fold->imm_float[0]
+                    (ast_expression*)m_fold->m_imm_float[0]
                 )
             ),
             (ast_expression*)ast_return_new(
@@ -1535,14 +1538,14 @@ ast_expression *intrin::ln_() {
     );
 
     for (i = 0; i <= 1; i++) {
-        plt1orblt1->exprs.push_back(
+        plt1orblt1->m_exprs.push_back(
             (ast_expression*)ast_ifthen_new(
                 ctx(),
                 (ast_expression*)ast_binary_new(
                     ctx(),
                     INSTR_LT,
                     (ast_expression*)((i) ? base : power),
-                    (ast_expression*)m_fold->imm_float[1]
+                    (ast_expression*)m_fold->m_imm_float[1]
                 ),
                 (ast_expression*)((i) ? blt1 : plt1),
                 nullptr
@@ -1550,11 +1553,11 @@ ast_expression *intrin::ln_() {
         );
     }
 
-    block->exprs.push_back((ast_expression*)plt1orblt1);
+    block->m_exprs.push_back((ast_expression*)plt1orblt1);
 
 
     /* whole = power; */
-    forloop->exprs.push_back(
+    forloop->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
@@ -1564,17 +1567,17 @@ ast_expression *intrin::ln_() {
     );
 
     /* nth = 0.0f; */
-    forloop->exprs.push_back(
+    forloop->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
             (ast_expression*)nth,
-            (ast_expression*)m_fold->imm_float[0]
+            (ast_expression*)m_fold->m_imm_float[0]
         )
     );
 
     /* base2 = base; */
-    whileloop->exprs.push_back(
+    whileloop->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
@@ -1584,17 +1587,17 @@ ast_expression *intrin::ln_() {
     );
 
     /* n2 = 1.0f; */
-    whileloop->exprs.push_back(
+    whileloop->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
             (ast_expression*)n2,
-            (ast_expression*)m_fold->imm_float[1]
+            (ast_expression*)m_fold->m_imm_float[1]
         )
     );
 
     /* newbase2 = base2 * base2; */
-    whileloop->exprs.push_back(
+    whileloop->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
@@ -1609,12 +1612,12 @@ ast_expression *intrin::ln_() {
     );
 
     /* while loop locals */
-    whileloop->locals.push_back(base2);
-    whileloop->locals.push_back(n2);
-    whileloop->locals.push_back(newbase2);
+    whileloop->m_locals.push_back(base2);
+    whileloop->m_locals.push_back(n2);
+    whileloop->m_locals.push_back(newbase2);
 
     /* base2 = newbase2; */
-    nestwhile->exprs.push_back(
+    nestwhile->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
@@ -1624,18 +1627,18 @@ ast_expression *intrin::ln_() {
     );
 
     /* n2 *= 2; */
-    nestwhile->exprs.push_back(
+    nestwhile->m_exprs.push_back(
         (ast_expression*)ast_binstore_new(
             ctx(),
             INSTR_STORE_F,
             INSTR_MUL_F,
             (ast_expression*)n2,
-            (ast_expression*)m_fold->imm_float[3] /* 2.0f */
+            (ast_expression*)m_fold->m_imm_float[3] /* 2.0f */
         )
     );
 
     /* newbase2 *= newbase2; */
-    nestwhile->exprs.push_back(
+    nestwhile->m_exprs.push_back(
         (ast_expression*)ast_binstore_new(
             ctx(),
             INSTR_STORE_F,
@@ -1646,7 +1649,7 @@ ast_expression *intrin::ln_() {
     );
 
     /* while (whole >= newbase2) */
-    whileloop->exprs.push_back(
+    whileloop->m_exprs.push_back(
         (ast_expression*)ast_loop_new(
             ctx(),
             nullptr,
@@ -1665,7 +1668,7 @@ ast_expression *intrin::ln_() {
     );
 
     /* whole /= base2; */
-    whileloop->exprs.push_back(
+    whileloop->m_exprs.push_back(
         (ast_expression*)ast_binstore_new(
             ctx(),
             INSTR_STORE_F,
@@ -1676,7 +1679,7 @@ ast_expression *intrin::ln_() {
     );
 
     /* nth += n2; */
-    whileloop->exprs.push_back(
+    whileloop->m_exprs.push_back(
         (ast_expression*)ast_binstore_new(
             ctx(),
             INSTR_STORE_F,
@@ -1687,7 +1690,7 @@ ast_expression *intrin::ln_() {
     );
 
     /* while (whole >= base) */
-    forloop->exprs.push_back(
+    forloop->m_exprs.push_back(
         (ast_expression*)ast_loop_new(
             ctx(),
             nullptr,
@@ -1705,12 +1708,12 @@ ast_expression *intrin::ln_() {
         )
     );
 
-    forloop->locals.push_back(b_iplus1);
-    forloop->locals.push_back(A_iplus1);
-    forloop->locals.push_back(B_iplus1);
+    forloop->m_locals.push_back(b_iplus1);
+    forloop->m_locals.push_back(A_iplus1);
+    forloop->m_locals.push_back(B_iplus1);
 
     /* b_iplus1 = nth; */
-    forloop->exprs.push_back(
+    forloop->m_exprs.push_back(
         (ast_expression*)ast_store_new(
             ctx(),
             INSTR_STORE_F,
@@ -1724,7 +1727,7 @@ ast_expression *intrin::ln_() {
      * B_iplus1 = b_iplus1 * B_i + B_iminus1;
      */
     for (i = 0; i <= 1; i++) {
-        forloop->exprs.push_back(
+        forloop->m_exprs.push_back(
             (ast_expression*)ast_store_new(
                 ctx(),
                 INSTR_STORE_F,
@@ -1749,7 +1752,7 @@ ast_expression *intrin::ln_() {
      * B_iminus1 = B_i;
      */
     for (i = 0; i <= 1; i++) {
-        forloop->exprs.push_back(
+        forloop->m_exprs.push_back(
             (ast_expression*)ast_store_new(
                 ctx(),
                 INSTR_STORE_F,
@@ -1764,7 +1767,7 @@ ast_expression *intrin::ln_() {
      * B_i = B_iplus1;
      */
     for (i = 0; i <= 1; i++) {
-        forloop->exprs.push_back(
+        forloop->m_exprs.push_back(
             (ast_expression*)ast_store_new(
                 ctx(),
                 INSTR_STORE_F,
@@ -1778,7 +1781,7 @@ ast_expression *intrin::ln_() {
      * if (whole <= 1.0f + eps)
      *     break;
      */
-    forloop->exprs.push_back(
+    forloop->m_exprs.push_back(
         (ast_expression*)ast_ifthen_new(
             ctx(),
             (ast_expression*)ast_binary_new(
@@ -1788,7 +1791,7 @@ ast_expression *intrin::ln_() {
                 (ast_expression*)ast_binary_new(
                     ctx(),
                     INSTR_ADD_F,
-                    (ast_expression*)m_fold->imm_float[1],
+                    (ast_expression*)m_fold->m_imm_float[1],
                     (ast_expression*)eps
                 )
             ),
@@ -1806,7 +1809,7 @@ ast_expression *intrin::ln_() {
      * base  = whole;
      */
     for (i = 0; i <= 1; i++) {
-        forloop->exprs.push_back(
+        forloop->m_exprs.push_back(
             (ast_expression*)ast_store_new(
                 ctx(),
                 INSTR_STORE_F,
@@ -1817,12 +1820,12 @@ ast_expression *intrin::ln_() {
     }
 
     /* add the for loop block */
-    block->exprs.push_back(
+    block->m_exprs.push_back(
         (ast_expression*)ast_loop_new(
             ctx(),
             nullptr,
             /* for(; 1; ) ?? (can this be nullptr too?) */
-            (ast_expression*)m_fold->imm_float[1],
+            (ast_expression*)m_fold->m_imm_float[1],
             false,
             nullptr,
             false,
@@ -1832,7 +1835,7 @@ ast_expression *intrin::ln_() {
     );
 
     /* return sign * A_i / B_il */
-    block->exprs.push_back(
+    block->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)ast_binary_new(
@@ -1849,7 +1852,7 @@ ast_expression *intrin::ln_() {
         )
     );
 
-    func->blocks.push_back(block);
+    func->m_blocks.emplace_back(block);
     reg(val, func);
     return (ast_expression*)val;
 }
@@ -1861,19 +1864,19 @@ ast_expression *intrin::log_variant(const char *name, float base) {
     ast_block *body = ast_block_new(ctx());
     ast_function *func = value(&val, name, TYPE_FLOAT);
 
-    val->expression.params.push_back(arg1);
+    val->m_type_params.push_back(arg1);
 
-    callln->params.push_back((ast_expression*)arg1);
-    callln->params.push_back((ast_expression*)fold_constgen_float(m_fold, base, false));
+    callln->m_params.push_back((ast_expression*)arg1);
+    callln->m_params.push_back((ast_expression*)m_fold->constgen_float(base, false));
 
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)callln
         )
     );
 
-    func->blocks.push_back(body);
+    func->m_blocks.emplace_back(body);
     reg(val, func);
     return (ast_expression*)val;
 }
@@ -1905,15 +1908,15 @@ ast_expression *intrin::shift_variant(const char *name, size_t instr) {
     ast_block *body = ast_block_new(ctx());
     ast_function *func = value(&val, name, TYPE_FLOAT);
 
-    val->expression.params.push_back(a);
-    val->expression.params.push_back(b);
+    val->m_type_params.push_back(a);
+    val->m_type_params.push_back(b);
 
     /* <callpow> = pow(2, b) */
-    callpow->params.push_back((ast_expression*)m_fold->imm_float[3]);
-    callpow->params.push_back((ast_expression*)b);
+    callpow->m_params.push_back((ast_expression*)m_fold->m_imm_float[3]);
+    callpow->m_params.push_back((ast_expression*)b);
 
     /* <callfloor> = floor(a [instr] <callpow>) */
-    callfloor->params.push_back(
+    callfloor->m_params.push_back(
         (ast_expression*)ast_binary_new(
             ctx(),
             instr,
@@ -1923,14 +1926,14 @@ ast_expression *intrin::shift_variant(const char *name, size_t instr) {
     );
 
     /* return <callfloor> */
-    body->exprs.push_back(
+    body->m_exprs.push_back(
         (ast_expression*)ast_return_new(
             ctx(),
             (ast_expression*)callfloor
         )
     );
 
-    func->blocks.push_back(body);
+    func->m_blocks.emplace_back(body);
     reg(val, func);
     return (ast_expression*)val;
 }
@@ -1957,7 +1960,7 @@ ast_expression *intrin::debug_typestring() {
 
 intrin::intrin(parser_t *parser)
     : m_parser(parser)
-    , m_fold(parser->fold)
+    , m_fold(&parser->m_fold)
 {
     static const intrin_func_t intrinsics[] = {
         {&intrin::isfinite_,        "__builtin_isfinite",         "isfinite", 1},
@@ -1994,15 +1997,15 @@ intrin::intrin(parser_t *parser)
     }
 }
 
-ast_expression *intrin::fold(ast_value *val, ast_expression **exprs) {
-    if (!val || !val->name)
+ast_expression *intrin::do_fold(ast_value *val, ast_expression **exprs) {
+    if (!val || !val->m_name)
         return nullptr;
     static constexpr size_t kPrefixLength = 10; // "__builtin_"
     for (auto &it : m_intrinsics) {
-        if (!strcmp(val->name, it.name))
+        if (!strcmp(val->m_name, it.name))
             return (vec_size(exprs) != it.args)
                         ? nullptr
-                        : fold_intrin(m_fold, val->name + kPrefixLength, exprs);
+                        : m_fold->intrinsic(val->m_name + kPrefixLength, exprs);
     }
     return nullptr;
 }
@@ -2022,9 +2025,9 @@ ast_expression *intrin::func_try(size_t offset, const char *compare) {
 ast_expression *intrin::func_self(const char *name, const char *from) {
     ast_expression *find;
     /* try current first */
-    if ((find = parser_find_global(m_parser, name)) && ((ast_value*)find)->expression.vtype == TYPE_FUNCTION)
+    if ((find = parser_find_global(m_parser, name)) && ((ast_value*)find)->m_vtype == TYPE_FUNCTION)
         for (auto &it : m_parser->functions)
-            if (((ast_value*)find)->name && !strcmp(it->name, ((ast_value*)find)->name) && it->builtin < 0)
+            if (((ast_value*)find)->m_name && !strcmp(it->m_name, ((ast_value*)find)->m_name) && it->m_builtin < 0)
                 return find;
     /* try name second */
     if ((find = func_try(offsetof(intrin_func_t, name),  name)))