stage1 支持defer 支持null 支持指针运算 支持*any指针
This commit is contained in:
1 parent
983746c797
commit
be41a82d55
4 files changed
+98
-34
No files matched your search
+34
-9
@@ -544,6 +544,23 @@ static spl_ir_node_ref_t emit_expr_raw(spl_ast2ir_t *a, spl_ast_node_ref_t ref)
|
||||
spl_ir_node_ref_t r = emit_expr(a, n->binary.right);
|
||||
if (!l || !r)
|
||||
return 0;
|
||||
|
||||
spl_ast_node_t *ln = spl_ast_node(a->sema->ast, n->binary.left);
|
||||
spl_lang_type_id_t lt = node_lang(a, ln);
|
||||
spl_lang_type_node_t *lln = spl_lang_type_node(a->sema->type, lt);
|
||||
|
||||
if (lln && lln->kind == SPL_LANG_TYPE_PTR && (op == SPL_OP_ADD || op == SPL_OP_SUB)) {
|
||||
spl_lang_type_id_t elem_lang = lln->extra.elem;
|
||||
spl_type_id_t elem_ir = to_ir_type(a, elem_lang);
|
||||
spl_type_id_t rt_ir = node_ir(a, spl_ast_node(a->sema->ast, n->binary.right));
|
||||
|
||||
spl_ir_node_ref_t off = r;
|
||||
if (op == SPL_OP_SUB)
|
||||
off = spl_ir_builder_arith_neg(a->ir, rt_ir, r);
|
||||
|
||||
return spl_ir_builder_mem_offset(a->ir, elem_ir, l, off);
|
||||
}
|
||||
|
||||
spl_type_id_t t = node_ir(a, n);
|
||||
switch (op) {
|
||||
case SPL_OP_ADD:
|
||||
@@ -899,17 +916,20 @@ static void emit_stmt(spl_ast2ir_t *a, spl_ast_node_ref_t ref) {
|
||||
|
||||
switch (n->kind) {
|
||||
case SPL_AST_STATEMENT_RET: {
|
||||
while (vec_size(a->defer_stack) > 0) {
|
||||
spl_type_id_t ret_ir = to_ir_type(a, a->cur_ret_lang);
|
||||
|
||||
/* 先求值 ret 表达式,结果保存在 v 中 */
|
||||
spl_ir_node_ref_t v = 0;
|
||||
if (n->statement_ret.expr)
|
||||
v = emit_expr(a, n->statement_ret.expr);
|
||||
|
||||
/* 再执行 defer(LIFO),只清空当前函数注册的 defer */
|
||||
while (vec_size(a->defer_stack) > a->cur_defer_base) {
|
||||
spl_ast_node_ref_t d = vec_pop(a->defer_stack);
|
||||
emit_stmt(a, d);
|
||||
}
|
||||
spl_type_id_t ret_ir = to_ir_type(a, a->cur_ret_lang);
|
||||
if (n->statement_ret.expr) {
|
||||
spl_ir_node_ref_t v = emit_expr(a, n->statement_ret.expr);
|
||||
spl_ir_builder_control_ret(a->ir, ret_ir, v);
|
||||
} else {
|
||||
spl_ir_builder_control_ret(a->ir, ret_ir, 0);
|
||||
}
|
||||
|
||||
spl_ir_builder_control_ret(a->ir, ret_ir, v);
|
||||
return;
|
||||
}
|
||||
case SPL_AST_STATEMENT_DEFER:
|
||||
@@ -1244,7 +1264,10 @@ static void emit_fn_body(spl_ast2ir_t *a, spl_ast_node_t *n) {
|
||||
spl_lang_type_id_t saved_ret = a->cur_ret_lang;
|
||||
a->cur_ret_lang = ret_lang;
|
||||
|
||||
usize defer_base = vec_size(a->defer_stack);
|
||||
usize saved_defer_base = a->cur_defer_base;
|
||||
a->cur_defer_base = vec_size(a->defer_stack);
|
||||
|
||||
usize defer_base = a->cur_defer_base;
|
||||
usize loop_base = vec_size(a->loop_stack);
|
||||
|
||||
spl_ir_builder_block_begin(a->ir);
|
||||
@@ -1301,6 +1324,7 @@ static void emit_fn_body(spl_ast2ir_t *a, spl_ast_node_t *n) {
|
||||
}
|
||||
|
||||
a->cur_ret_lang = saved_ret;
|
||||
a->cur_defer_base = saved_defer_base;
|
||||
|
||||
spl_ir_builder_block_end(a->ir);
|
||||
spl_ir_builder_fn_end(a->ir);
|
||||
@@ -1455,6 +1479,7 @@ void spl_ast2ir_init(spl_ast2ir_t *ast2ir, spl_ir_builder_t *ir, const spl_sema_
|
||||
vec_init(ast2ir->defer_stack);
|
||||
ast2ir->err_count = 0;
|
||||
ast2ir->cur_ret_lang = 0;
|
||||
ast2ir->cur_defer_base = 0;
|
||||
}
|
||||
|
||||
void spl_ast2ir_drop(spl_ast2ir_t *ast2ir) {
|
||||
|
||||
Reference in new issue
Block a user