From 9ae440c769563e79055f8b21f66fe9bae9b6823a Mon Sep 17 00:00:00 2001 From: "yu.dongliang" <18588496441@163.com> Date: Wed, 16 Sep 2026 16:58:27 +0800 Subject: [PATCH] 1, self compile files of lex module, only compile ok!! 2, fix: data wrong caused by 'struct assign' with memcpy(). 3, fix: loop analysis error for '__lex_pop_word()' in ../lex/scf_lex.c, 4, fix: include path not end with '/', 5, fix: parse enum of .h error when include multi times. --- core/scf_ast.c | 2 +- core/scf_basic_block.c | 10 +- core/scf_dag.c | 5 + core/scf_node.h | 23 ++-- core/scf_optimizer.c | 6 +- core/scf_optimizer_loop.c | 145 ++++++++++++++++++-------- core/scf_variable.c | 4 +- examples/struct_assign.c | 15 +++ native/x64/scf_x64_inst.c | 2 +- native/x64/scf_x64_inst_binary.c | 10 +- native/x64/scf_x64_reg.c | 2 +- parse/main.c | 3 +- parse/scf_dfa.c | 4 +- parse/scf_dfa_call.c | 8 +- parse/scf_dfa_enum.c | 11 +- parse/scf_dfa_expr.c | 102 +++++++++++------- parse/scf_dfa_function.c | 43 +++++--- parse/scf_dfa_identity.c | 2 + parse/scf_dfa_sizeof.c | 2 +- parse/scf_operator_handler_const.c | 11 ++ parse/scf_operator_handler_semantic.c | 12 ++- parse/scf_parse.h | 3 - util/scf_string.c | 24 ++++- 23 files changed, 315 insertions(+), 134 deletions(-) create mode 100644 examples/struct_assign.c diff --git a/core/scf_ast.c b/core/scf_ast.c index f823bde..c747a8b 100644 --- a/core/scf_ast.c +++ b/core/scf_ast.c @@ -354,7 +354,7 @@ int scf_ast_find_global_typedef(scf_variable_t** pv, scf_ast_t* ast, char* name) if (!vec) return -ENOMEM; - int ret = scf_node_search_bfs((scf_node_t*)ast->root_block, name, vec, -1, _find_type_by_name); + int ret = scf_node_search_bfs((scf_node_t*)ast->root_block, name, vec, -1, _find_typedef_by_name); if (ret < 0) { scf_vector_free(vec); return ret; diff --git a/core/scf_basic_block.c b/core/scf_basic_block.c index b229f16..45a2daf 100644 --- a/core/scf_basic_block.c +++ b/core/scf_basic_block.c @@ -843,9 +843,13 @@ static int _bb_init_array_index(scf_3ac_code_t* c, scf_basic_block_t* bb, scf_li } while (SCF_OP_ARRAY_INDEX == dn_base->type - || SCF_OP_POINTER == dn_base->type) { + || SCF_OP_POINTER == dn_base->type + || SCF_OP_DEREFERENCE == dn_base->type) { - dn_index = dn_base->childs->data[1]; + if (SCF_OP_DEREFERENCE == dn_base->type) + dn_index = dn_base->childs->data[0]; + else + dn_index = dn_base->childs->data[1]; ret = scf_dn_status_index(ds, dn_index, dn_base->type); if (ret < 0) { @@ -853,7 +857,7 @@ static int _bb_init_array_index(scf_3ac_code_t* c, scf_basic_block_t* bb, scf_li return ret; } - dn_base = dn_base->childs->data[0]; + dn_base = dn_base->childs->data[0]; } assert(scf_type_is_var(dn_base->type)); diff --git a/core/scf_dag.c b/core/scf_dag.c index 0fe3b59..38b504d 100644 --- a/core/scf_dag.c +++ b/core/scf_dag.c @@ -836,6 +836,10 @@ static int _dn_status_index(scf_vector_t* indexes, scf_dag_node_t* dn_index, int di->index = -1; di->dn = dn_index; + } else if (SCF_OP_DEREFERENCE == type) { + di->index = 0; + di->dn = dn_index; + } else if (SCF_OP_POINTER == type) { di->member = dn_index->var; di->dn = dn_index; @@ -849,6 +853,7 @@ static int _dn_status_index(scf_vector_t* indexes, scf_dag_node_t* dn_index, int scf_dn_index_free(di); return ret; } + return 0; } diff --git a/core/scf_node.h b/core/scf_node.h index 58e143b..d4a063d 100644 --- a/core/scf_node.h +++ b/core/scf_node.h @@ -13,27 +13,30 @@ #define SCF_OP_ASSOCIATIVITY_RIGHT 1 struct scf_node_s { - int type; // node type + int type; // node type - scf_node_t* parent; // parent node - int nb_nodes; // children nodes count - scf_node_t** nodes; // children nodes + scf_node_t* parent; // parent node + int nb_nodes; // children nodes count + scf_node_t** nodes; // children nodes union { scf_variable_t* var; scf_lex_word_t* w; }; - scf_lex_word_t* debug_w; + scf_lex_word_t* debug_w; - int priority; - scf_operator_t* op; + int priority; + scf_operator_t* op; - scf_variable_t* result; + scf_variable_t* result; scf_vector_t* result_nodes; scf_node_t* split_parent; // split from the parent - int pause_flag; // ++ when followed by a '(' of function call(), sizeof(), etc... only for expr. + int pause_flag; // 'pause_flag++' when followed by a '(' of function call(), sizeof(), etc... only for expr. + + int n_lps; + int n_rps; uint32_t root_flag :1; // set when node is root block uint32_t file_flag :1; // set when node is a file block @@ -48,6 +51,8 @@ struct scf_node_s { uint32_t _3ac_done :1; // set when node's 3ac code is made uint32_t semi_flag :1; // set when followed by a ';' + + uint32_t op_comma_flag :1; // save status: enable/disable comma operator ',' }; struct scf_label_s { diff --git a/core/scf_optimizer.c b/core/scf_optimizer.c index 5f839d9..f991f59 100644 --- a/core/scf_optimizer.c +++ b/core/scf_optimizer.c @@ -100,15 +100,15 @@ int scf_optimize(scf_ast_t* ast, scf_vector_t* functions) } } -#if 0 +#if 1 for (i = 0; i < functions->size; i++) { f = functions->data[i]; if (!f->node.define_flag) continue; -// if (strcmp(f->node.w->text->data, "main")) -// continue; + if (strcmp(f->node.w->text->data, "main")) + continue; printf("\n"); scf_logi("------- %s() ------\n", f->node.w->text->data); diff --git a/core/scf_optimizer_loop.c b/core/scf_optimizer_loop.c index c72c65b..a8f7a36 100644 --- a/core/scf_optimizer_loop.c +++ b/core/scf_optimizer_loop.c @@ -325,13 +325,8 @@ static void _bb_loop_sort(scf_vector_t* loops) static int __bb_loop_layers(scf_function_t* f) { - scf_basic_block_t* entry; - scf_basic_block_t* exit; - scf_basic_block_t* bb; - scf_bb_group_t* loop0; - scf_bb_group_t* loop1; - - int ret; + scf_bb_group_t* loop0; + scf_bb_group_t* loop1; int i; int j; @@ -348,27 +343,27 @@ static int __bb_loop_layers(scf_function_t* f) break; } - if (k < loop0->body->size) - continue; + if (k >= loop0->body->size) { - if (!loop0->loop_parent || loop0->loop_parent->body->size > loop1->body->size) - loop0 ->loop_parent = loop1; + if (!loop1->loop_childs) { + loop1->loop_childs = scf_vector_alloc(); + if (!loop1->loop_childs) + return -ENOMEM; + } - if (loop1->loop_layers <= loop0->loop_layers + 1) - loop1->loop_layers = loop0->loop_layers + 1; + int ret = scf_vector_add(loop1->loop_childs, loop0); + if (ret < 0) + return ret; - if (!loop1->loop_childs) { - loop1->loop_childs = scf_vector_alloc(); - if (!loop1->loop_childs) - return -ENOMEM; - } + if (loop1->loop_layers < loop0->loop_layers + 1) + loop1->loop_layers = loop0->loop_layers + 1; - ret = scf_vector_add_unique(loop1->loop_childs, loop0); - if (ret < 0) - return ret; + loop0->loop_parent = loop1; + break; + } } - if (loop0->loop_parent) + if (j < f->bb_loops->size) assert(0 == scf_vector_del(f->bb_loops, loop0)); else i++; @@ -377,13 +372,83 @@ static int __bb_loop_layers(scf_function_t* f) return 0; } -static int _bb_loop_layers(scf_function_t* f) +static int __bb_loop_unique_entry(scf_bb_group_t* loop) { - scf_basic_block_t* entry; - scf_bb_group_t* loop; + scf_basic_block_t* bb0 = loop->body->data[0]; + scf_basic_block_t* entry; + scf_basic_block_t* old; int i; int j; + entry = scf_basic_block_alloc(); + if (!entry) + return -ENOMEM; + + scf_list_add_tail(&bb0->list, &entry->list); + + int ret = scf_vector_add(entry->nexts, bb0); + if (ret < 0) + return ret; + + ret = scf_vector_add(bb0->prevs, entry); + if (ret < 0) + return ret; + + for (i = 0; i < loop->entries->size; i++) { + old = loop->entries->data[i]; + + if (scf_vector_find(loop->body, old)) + continue; + + assert(scf_vector_find(old->nexts, bb0)); + + for (j = 0; j < old->nexts->size; j++) { + if (old->nexts->data[j] == bb0) + old->nexts->data[j] = entry; + } + + ret = scf_vector_add(entry->prevs, old); + if (ret < 0) + return ret; + + ret = scf_vector_del(bb0->prevs, old); + if (ret < 0) + return ret; + + scf_basic_block_t* jmp; + scf_3ac_operand_t* dst; + scf_3ac_code_t* c; + scf_list_t* l; + scf_list_t* l2; + + for (l = scf_list_next(&old->list); l != &entry->list; l = scf_list_next(l)) { + jmp = scf_list_data(l, scf_basic_block_t, list); + + if (!jmp->jmp_flag) + break; + + l2 = scf_list_head(&jmp->code_list_head); + c = scf_list_data(l2, scf_3ac_code_t, list); + + assert(c->dsts && 1 == c->dsts->size); + + dst = c->dsts->data[0]; + if (dst->bb == bb0) + dst->bb = entry; + } + } + + loop->entries->data[0] = entry; + loop->entries->size = 1; + return 0; +} + +static int _bb_loop_layers(scf_function_t* f) +{ + scf_basic_block_t* entry; + scf_bb_group_t* loop; + int i; + int ret = __bb_loop_layers(f); if (ret < 0) return ret; @@ -394,14 +459,14 @@ static int _bb_loop_layers(scf_function_t* f) _bb_loop_sort(f->bb_loops); - for (i = 0; i < f->bb_loops->size; i++) { loop = f->bb_loops->data[i]; - for (j = 0; j < loop->entries->size; j++) { - entry = loop->entries->data[j]; + if (loop->entries->size > 1) { - scf_logi("loop: %p, j: %d, entry: %p\n", loop, j, entry); + ret = __bb_loop_unique_entry(loop); + if (ret < 0) + return ret; } assert(1 == loop->entries->size); @@ -415,15 +480,14 @@ static int _bb_loop_layers(scf_function_t* f) static int _bb_loop_add_pre_post(scf_function_t* f) { - scf_bb_group_t* bbg; - scf_basic_block_t* bb; - scf_basic_block_t* jmp; - scf_basic_block_t* exit; - scf_basic_block_t* pre; - scf_basic_block_t* post; - scf_basic_block_t* first; - - scf_list_t* sentinel = scf_list_sentinel(&f->basic_block_list_head); + scf_bb_group_t* bbg; + scf_basic_block_t* bb; + scf_basic_block_t* jmp; + scf_basic_block_t* exit; + scf_basic_block_t* pre; + scf_basic_block_t* post; + scf_basic_block_t* first; + scf_list_t* sentinel = scf_list_sentinel(&f->basic_block_list_head); int i; int j; @@ -734,11 +798,6 @@ static int _optimize_loop(scf_ast_t* ast, scf_function_t* f, scf_vector_t* funct if (scf_list_empty(bb_list_head)) return 0; - if (!strcmp(f->node.w->text->data, "__parse_macro_include")) { - scf_logi("------- %s() ------\n", f->node.w->text->data); - scf_basic_block_print_list(&f->basic_block_list_head); - } - scf_vector_clear(f->bb_loops, ( void (*)(void*) )scf_bb_group_free); scf_vector_clear(f->bb_groups, ( void (*)(void*) )scf_bb_group_free); diff --git a/core/scf_variable.c b/core/scf_variable.c index d7cd25a..785c52f 100644 --- a/core/scf_variable.c +++ b/core/scf_variable.c @@ -394,8 +394,10 @@ int scf_variable_type_like(scf_variable_t* v0, scf_variable_t* v1) if (!v1) return 0; - if (v0->type != v1->type) + if (v0->type != v1->type) { + scf_loge("v0->type: %d, v1->type: %d\n", v0->type, v1->type); return 0; + } if (scf_variable_nb_pointers(v0) != scf_variable_nb_pointers(v1)) return 0; diff --git a/examples/struct_assign.c b/examples/struct_assign.c new file mode 100644 index 0000000..7ea4f9f --- /dev/null +++ b/examples/struct_assign.c @@ -0,0 +1,15 @@ +int printf(const char* fmt, ...); + +typedef struct { + float real; + float imag; +} complex_t; + +int main() +{ + complex_t s = {2.71, 3.14}; + complex_t d = s; + + printf("d: %lg + %lg\n", d.real, d.imag); + return 0; +} diff --git a/native/x64/scf_x64_inst.c b/native/x64/scf_x64_inst.c index 6e74c02..adaa82d 100644 --- a/native/x64/scf_x64_inst.c +++ b/native/x64/scf_x64_inst.c @@ -511,7 +511,7 @@ static int _x64_inst_call_handler(scf_native_t* ctx, scf_3ac_code_t* c) if (ret < 0) return ret; - uint32_t imm = ret > 0; + uint32_t imm = ret; mov = x64_find_OpCode(SCF_X64_MOV, 4,4, SCF_X64_I2G); inst = x64_make_inst_I2G(mov, eax, (uint8_t*)&imm, sizeof(imm)); diff --git a/native/x64/scf_x64_inst_binary.c b/native/x64/scf_x64_inst_binary.c index 29b6da9..7b09b6b 100644 --- a/native/x64/scf_x64_inst_binary.c +++ b/native/x64/scf_x64_inst_binary.c @@ -316,7 +316,8 @@ int x64_assign_pointer(scf_native_t* ctx, scf_3ac_code_t* c) assert(dsize <= vsize); - if (0 == src->dag_node->color) + intptr_t color = src->dag_node->color; + if (0 == color) src->dag_node->color = -1; X64_SELECT_REG_CHECK(&rs, src->dag_node, c, f, 1); @@ -388,6 +389,13 @@ int x64_assign_pointer(scf_native_t* ctx, scf_3ac_code_t* c) else inst = x64_make_inst_G2P(mov, sib.base, sib.disp, rs); X64_INST_ADD_CHECK(c, inst, NULL); + + if (0 == color) { + scf_vector_del(rs->dag_nodes, src->dag_node); + + src->dag_node->color = 0; + src->dag_node->loaded = 0; + } return 0; } diff --git a/native/x64/scf_x64_reg.c b/native/x64/scf_x64_reg.c index 5988fd3..f050267 100644 --- a/native/x64/scf_x64_reg.c +++ b/native/x64/scf_x64_reg.c @@ -364,7 +364,7 @@ int x64_save_var2(scf_dag_node_t* dn, scf_register_t* r, scf_3ac_code_t* c, scf_ assert(var_size == r->bytes); - if (scf_variable_const(v)) { + if (scf_variable_const(v) || scf_variable_is_struct(v)) { if (v->w) scf_logd("const literal var: v_%s_%d_%d not save\n", v->w->text->data, v->w->line, v->w->pos); else diff --git a/parse/main.c b/parse/main.c index 1f04712..7248531 100644 --- a/parse/main.c +++ b/parse/main.c @@ -9,7 +9,8 @@ "uint8_t* optr;" \ "intptr_t ireg;" \ "intptr_t freg;" \ -"};" +"}; " \ +"void *memcpy(void *dest, const void *src, uintptr_t n);" static scf_string_t __builtin_h = { diff --git a/parse/scf_dfa.c b/parse/scf_dfa.c index ef1cd4c..c93d3b6 100644 --- a/parse/scf_dfa.c +++ b/parse/scf_dfa.c @@ -381,7 +381,7 @@ static int _scf_dfa_node_parse_word(scf_dfa_t* dfa, scf_dfa_node_t* node, scf_ve printf("\n"); #endif - if (!pre_hook_flag) { +// if (!pre_hook_flag) { scf_dfa_hook_t* hook = scf_dfa_find_hook(dfa, &(dfa->hooks[SCF_DFA_HOOK_POST]), w); if (hook && !hook->disable_flag) { @@ -405,7 +405,7 @@ static int _scf_dfa_node_parse_word(scf_dfa_t* dfa, scf_dfa_node_t* node, scf_ve } } } - } +// } if (SCF_DFA_OK == ret) { scf_dfa_hook_t** pp = &(dfa->hooks[SCF_DFA_HOOK_END]); diff --git a/parse/scf_dfa_call.c b/parse/scf_dfa_call.c index 57000c0..b3b8a29 100644 --- a/parse/scf_dfa_call.c +++ b/parse/scf_dfa_call.c @@ -166,7 +166,7 @@ static int _call_action_rp(scf_dfa_t* dfa, scf_vector_t* words, void* data) cd->nb_rps++; - scf_logd("cd->nb_lps: %d, cd->nb_rps: %d\n", cd->nb_lps, cd->nb_rps); + scf_logi("cd->nb_lps: %d, cd->nb_rps: %d\n", cd->nb_lps, cd->nb_rps); if (cd->nb_rps < cd->nb_lps) { @@ -174,14 +174,14 @@ static int _call_action_rp(scf_dfa_t* dfa, scf_vector_t* words, void* data) SCF_DFA_PUSH_HOOK(scf_dfa_find_node(dfa, "call_comma"), SCF_DFA_HOOK_POST); SCF_DFA_PUSH_HOOK(scf_dfa_find_node(dfa, "call_lp_stat"), SCF_DFA_HOOK_POST); - scf_logd("d->expr: %p\n", d->expr); + scf_logi("d->expr: %p\n", d->expr); return SCF_DFA_NEXT_WORD; } assert(cd->nb_rps == cd->nb_lps); scf_stack_pop(s); - scf_logd("cd->parent_expr: %p, d->expr: %p\n", cd->parent_expr, d->expr); + scf_logi("cd->parent_expr: %p, d->expr: %p\n", cd->parent_expr, d->expr); if (cd->parent_expr) { if (cd->func) @@ -216,7 +216,7 @@ static int _call_action_rp(scf_dfa_t* dfa, scf_vector_t* words, void* data) d->expr_local_flag--; d->op_comma_flag = cd->op_comma_flag; - scf_logd("d->expr: %p\n", d->expr); + scf_logi("d->expr: %p\n", d->expr); scf_expr_t* grand = scf_stack_top(d->lp_exprs); if (grand) { diff --git a/parse/scf_dfa_enum.c b/parse/scf_dfa_enum.c index d0bdafd..071a8db 100644 --- a/parse/scf_dfa_enum.c +++ b/parse/scf_dfa_enum.c @@ -109,7 +109,16 @@ static int _enum_action_var(scf_dfa_t* dfa, scf_vector_t* words, void* data) v = scf_block_find_variable(parse->ast->root_block, w->text->data); if (v) { - scf_loge("repeated declared enum var '%s', 1st in file: %s, line: %d\n", w->text->data, v->w->file->data, v->w->line); + if (!scf_string_cmp(v->w->file, w->file)) { + md->current_v = v; + return SCF_DFA_NEXT_WORD; + } + + scf_loge("%s:%d:%d, repeated declared enum var '%s', 1st in %s:%d:%d\n", + w->file->data, w->line, w->pos, + w->text->data, + v->w->file->data, v->w->line, v->w->pos); + return SCF_DFA_ERROR; } diff --git a/parse/scf_dfa_expr.c b/parse/scf_dfa_expr.c index fac9cca..162efb4 100644 --- a/parse/scf_dfa_expr.c +++ b/parse/scf_dfa_expr.c @@ -13,8 +13,8 @@ typedef struct { scf_lex_word_t* op_comma; - int n_lps; - int n_rps; +// int n_lps; +// int n_rps; int n_lss; int n_rss; @@ -393,17 +393,19 @@ static int _expr_action_lp(scf_dfa_t* dfa, scf_vector_t* words, void* data) dfa_data_t* d = data; expr_module_data_t* md = d->module_datas[dfa_module_expr.index]; - md->n_lps++; - - d->op_comma_flag = 1; - scf_expr_t* e = scf_expr_alloc(); if (!e) { scf_loge("\n"); return SCF_DFA_ERROR; } - scf_logi("d->expr: %p, e: %p, d->op_comma_flag: %d\n", d->expr, e, d->op_comma_flag); + e->op_comma_flag = d->op_comma_flag; + d->op_comma_flag = 1; + +// md->n_lps++; + e->n_lps++; + + scf_logi("d->expr: %p, e: %p, d->op_comma_flag: %d, e->op_comma_flag: %d\n", d->expr, e, d->op_comma_flag, e->op_comma_flag); scf_stack_push(d->lp_exprs, d->expr); d->expr = e; @@ -423,31 +425,34 @@ static int _expr_action_rp_cast(scf_dfa_t* dfa, scf_vector_t* words, void* data) expr_module_data_t* md = d->module_datas[dfa_module_expr.index]; dfa_identity_t* id = scf_stack_top(d->current_identities); - md->n_rps++; +// md->n_rps++; + if (d->expr) { + d->expr->n_rps++; - if (md->n_rps >= md->n_lps) { - md->n_rps = 0; - md->n_lps = 0; + if (d->expr->n_rps >= d->expr->n_lps) { + // md->n_rps = 0; + // md->n_lps = 0; - assert(!md->op_comma); + assert(!md->op_comma); - d->op_comma_flag = 0; + d ->op_comma_flag = d->expr->op_comma_flag; + d->expr->op_comma_flag = 0; + } } scf_logi("d->op_comma_flag: %d\n", d->op_comma_flag); - if (!id) { - scf_loge("\n"); - return SCF_DFA_ERROR; - } + if (id) { + if (!id->type) { + if (_type_find_type(dfa, id) < 0) + return SCF_DFA_ERROR; + } - if (!id->type) { - if (_type_find_type(dfa, id) < 0) { + if (!id->type || !id->type_w) { scf_loge("\n"); return SCF_DFA_ERROR; } - } - if (!id->type || !id->type_w) { + } else if (!d->current_var) { scf_loge("\n"); return SCF_DFA_ERROR; } @@ -471,18 +476,34 @@ static int _expr_action_rp_cast(scf_dfa_t* dfa, scf_vector_t* words, void* data) scf_node_t* cast = NULL; scf_expr_t* e = NULL; - var = SCF_VAR_ALLOC_BY_TYPE(id->type_w, id->type, id->const_flag, id->nb_pointers, id->func_ptr); - if (!var) - return SCF_DFA_ERROR; + if (id) { + var = SCF_VAR_ALLOC_BY_TYPE(id->type_w, id->type, id->const_flag, id->nb_pointers, id->func_ptr); + if (!var) + return SCF_DFA_ERROR; - node = scf_node_alloc(NULL, var->type, var); + node = scf_node_alloc(NULL, var->type, var); - scf_variable_free(var); - var = NULL; - if (!node) - return SCF_DFA_ERROR; + scf_variable_free(var); + var = NULL; + if (!node) + return SCF_DFA_ERROR; + + cast = scf_node_alloc(id->type_w, SCF_OP_TYPE_CAST, NULL); + + scf_stack_pop(d->current_identities); + free(id); + id = NULL; + + } else if (d->current_var) { + node = scf_node_alloc(NULL, d->current_var->type, d->current_var); + if (!node) + return SCF_DFA_ERROR; + + cast = scf_node_alloc(d->current_var->w, SCF_OP_TYPE_CAST, NULL); + + d->current_var = NULL; + } - cast = scf_node_alloc(id->type_w, SCF_OP_TYPE_CAST, NULL); if (!cast) { scf_node_free(node); return SCF_DFA_ERROR; @@ -518,8 +539,6 @@ static int _expr_action_rp_cast(scf_dfa_t* dfa, scf_vector_t* words, void* data) assert(md->current_struct); } - scf_stack_pop(d->current_identities); - free(id); return SCF_DFA_NEXT_WORD; } @@ -530,11 +549,13 @@ static int _expr_action_rp(scf_dfa_t* dfa, scf_vector_t* words, void* data) expr_module_data_t* md = d->module_datas[dfa_module_expr.index]; dfa_identity_t* id = scf_stack_top(d->current_identities); - md->n_rps++; + assert(d->expr); +// md->n_rps++; + d->expr->n_rps++; - if (md->n_rps >= md->n_lps) { - md->n_rps = 0; - md->n_lps = 0; + if (d->expr->n_rps >= d->expr->n_lps) { +// md->n_rps = 0; +// md->n_lps = 0; if (md->op_comma) { scf_dfa_enable_hook_w(dfa, SCF_DFA_HOOK_PRE, md->op_comma); @@ -543,7 +564,8 @@ static int _expr_action_rp(scf_dfa_t* dfa, scf_vector_t* words, void* data) md->op_comma = NULL; } - d->op_comma_flag = 0; + d ->op_comma_flag = d->expr->op_comma_flag; + d->expr->op_comma_flag = 0; } scf_logi("d->op_comma_flag: %d, d->expr: %p\n", d->op_comma_flag, d->expr); @@ -803,7 +825,7 @@ int _expr_multi_rets(scf_expr_t* e) int _expr_fini_expr(scf_parse_t* parse, dfa_data_t* d, int semi_flag) { - scf_logd("d->expr: %p\n", d->expr); + scf_logi("d->expr: %p\n", d->expr); if (d->expr) { while (d->expr->parent) @@ -836,7 +858,7 @@ int _expr_fini_expr(scf_parse_t* parse, dfa_data_t* d, int semi_flag) d->expr = NULL; } - scf_logd("d->expr: %p, d->expr_local_flag: %d\n", d->expr, d->expr_local_flag); + scf_logi("d->expr: %p, d->expr_local_flag: %d\n", d->expr, d->expr_local_flag); } return SCF_DFA_OK; @@ -866,7 +888,7 @@ static int _expr_action_comma(scf_dfa_t* dfa, scf_vector_t* words, void* data) scf_logi("d->op_comma_flag: %d\n", d->op_comma_flag); - if (md->n_lps > 0 && d->op_comma_flag) { + if (d->expr && d->expr->n_lps > 0 && d->op_comma_flag) { scf_loge("op: '%s', %d:%d\n", w->text->data, w->line, w->pos); diff --git a/parse/scf_dfa_function.c b/parse/scf_dfa_function.c index 23195df..0baa30c 100644 --- a/parse/scf_dfa_function.c +++ b/parse/scf_dfa_function.c @@ -604,23 +604,38 @@ static int _function_action_rp(scf_dfa_t* dfa, scf_vector_t* words, void* data) fprev = scf_scope_find_function(b->scope, f->node.w->text->data); - if (!fprev && !f->static_flag) { + if (fprev) { + if (!scf_function_same(fprev, f)) { + + scf_loge("%s:%d:%d, repeated declare function '%s', first in %s:%d:%d, function overloading only can do in class\n", + f->node.w->file->data, f->node.w->line, f->node.w->pos, + f->node.w->text->data, + fprev->node.w->file->data, fprev->node.w->line, fprev->node.w->pos); + + scf_function_free(f); + f = NULL; + return SCF_DFA_ERROR; + } +/* + } else if (!f->static_flag) { int ret = scf_ast_find_global_function(&fprev, ast, f->node.w->text->data); if (ret < 0) return ret; - } - if (fprev && !scf_function_same(fprev, f)) { + if (fprev + && !scf_function_same(fprev, f) + && scf_string_cmp(fprev->node.w->file, f->node.w->file)) { - scf_loge("%s:%d:%d, repeated declare function '%s', first in %s:%d:%d, function overloading only can do in class\n", - f->node.w->file->data, f->node.w->line, f->node.w->pos, - f->node.w->text->data, - fprev->node.w->file->data, fprev->node.w->line, fprev->node.w->pos); + scf_loge("%s:%d:%d, repeated declare function '%s', first in %s:%d:%d, linker don't know use which\n", + f->node.w->file->data, f->node.w->line, f->node.w->pos, + f->node.w->text->data, + fprev->node.w->file->data, fprev->node.w->line, fprev->node.w->pos); - scf_function_free(f); - f = NULL; - return SCF_DFA_ERROR; + scf_function_free(f); + f = NULL; + return SCF_DFA_ERROR; + } */ } } @@ -688,9 +703,10 @@ static int _function_action_rp(scf_dfa_t* dfa, scf_vector_t* words, void* data) d->current_var = fd->v_pf; fd->v_pf = NULL; - scf_logd("fd->f: %s(), d->current_var: %p\n", fd->f->node.w->text->data, d->current_var); - scf_stack_pop(s); + + scf_logi("s->size: %d, fd->f: %s(), d->current_var: %p\n", s->size, fd->f->node.w->text->data, d->current_var); + free(fd); fd = scf_stack_top(s); @@ -788,6 +804,8 @@ static int _dfa_init_syntax_function(scf_dfa_t* dfa) SCF_DFA_GET_MODULE_NODE(dfa, type, identity, identity); SCF_DFA_GET_MODULE_NODE(dfa, block, entry, block); + SCF_DFA_GET_MODULE_NODE(dfa, expr, rp_cast, rp_cast); + SCF_DFA_GET_MODULE_NODE(dfa, var, ls, ls); SCF_DFA_GET_MODULE_NODE(dfa, var, rs, rs); SCF_DFA_GET_MODULE_NODE(dfa, var, assign, assign); @@ -848,6 +866,7 @@ static int _dfa_init_syntax_function(scf_dfa_t* dfa) scf_dfa_node_add_child(vargs, rp); // function body + scf_dfa_node_add_child(rp, rp_cast); scf_dfa_node_add_child(rp, block); return 0; diff --git a/parse/scf_dfa_identity.c b/parse/scf_dfa_identity.c index 1c461b9..a0d7c3c 100644 --- a/parse/scf_dfa_identity.c +++ b/parse/scf_dfa_identity.c @@ -47,10 +47,12 @@ static int _identity_action_identity(scf_dfa_t* dfa, scf_vector_t* words, void* id->identity = w; id->const_flag = d->const_flag; id->extern_flag = d->extern_flag; + id->static_flag = d->static_flag; id->volatile_flag = d->volatile_flag; d->const_flag = 0; d->extern_flag = 0; + d->static_flag = 0; d->volatile_flag = 0; return SCF_DFA_NEXT_WORD; diff --git a/parse/scf_dfa_sizeof.c b/parse/scf_dfa_sizeof.c index 5d90f9f..3b523d6 100644 --- a/parse/scf_dfa_sizeof.c +++ b/parse/scf_dfa_sizeof.c @@ -192,7 +192,7 @@ static int _sizeof_action_rp(scf_dfa_t* dfa, scf_vector_t* words, void* data) if (grand) { assert(--grand->pause_flag >= 0); - scf_logi("grand: %p, grand->pause_flag: %d\n", grand, grand->pause_flag); + scf_logi("d->expr: %p, grand: %p, grand->pause_flag: %d\n", d->expr, grand, grand->pause_flag); } free(sd); diff --git a/parse/scf_operator_handler_const.c b/parse/scf_operator_handler_const.c index a630b82..2bafdfe 100644 --- a/parse/scf_operator_handler_const.c +++ b/parse/scf_operator_handler_const.c @@ -573,6 +573,17 @@ static int _scf_op_const_address_of(scf_ast_t* ast, scf_node_t** nodes, int nb_n scf_logd("type->data.p: %p, type->data_size: %d, member->data.u64: %ld, r->data.p: %p\n", type->data.p, type->data_size, member->data.u64, r->data.p); } + + } else if (SCF_OP_DEREFERENCE == child->type) { + assert(1 == child->nb_nodes); + + scf_node_t* tmp = child->nodes[0]; + + child->nodes[0] = NULL; + + scf_node_free_data(parent); + scf_node_move_data(parent, tmp); + scf_node_free(tmp); } return 0; diff --git a/parse/scf_operator_handler_semantic.c b/parse/scf_operator_handler_semantic.c index 137847b..61ddb6c 100644 --- a/parse/scf_operator_handler_semantic.c +++ b/parse/scf_operator_handler_semantic.c @@ -1033,7 +1033,7 @@ static int _scf_op_semantic_return(scf_ast_t* ast, scf_node_t** nodes, int nb_no } if (nb_nodes > f->rets->size) { - scf_loge("\n"); + scf_loge("nb_nodes: %d, f->rets->size: %d\n", nb_nodes, f->rets->size); return -1; } @@ -2658,22 +2658,22 @@ static int _scf_op_semantic_assign(scf_ast_t* ast, scf_node_t** nodes, int nb_no if (scf_variable_same_type(v0, v1)) { scf_function_t* f = NULL; - ret = scf_ast_find_function(&f, ast, "scf__memcpy"); + ret = scf_ast_find_function(&f, ast, "memcpy"); if (ret < 0) return ret; if (!f) { - scf_loge("semantic do overloaded error: default 'scf__memcpy' NOT found\n"); + scf_loge("semantic do overloaded error: default 'memcpy' NOT found\n"); return -1; } - scf_type_t* t = scf_block_find_type_type(ast->current_block, SCF_VAR_INTPTR); + scf_type_t* t = scf_block_find_type_type(ast->current_block, SCF_VAR_UINTPTR); scf_variable_t* v = SCF_VAR_ALLOC_BY_TYPE(NULL, t, 1, 0, NULL); if (!v) { scf_loge("var alloc failed\n"); return -ENOMEM; } - v->data.i64 = size; + v->data.u64 = size; scf_node_t* node_size = scf_node_alloc(NULL, v->type, v); if (!node_size) { @@ -3180,6 +3180,8 @@ int scf_function_semantic_analysis(scf_ast_t* ast, scf_function_t* f) { scf_handler_data_t d = {0}; + scf_logi("----%s()----\n", f->node.w->text->data); + int ret = __scf_op_semantic_call(ast, f, &d); if (ret < 0) { diff --git a/parse/scf_parse.h b/parse/scf_parse.h index 15da040..334556f 100644 --- a/parse/scf_parse.h +++ b/parse/scf_parse.h @@ -124,9 +124,6 @@ struct dfa_data_s { int nb_lss; int nb_rss; - -// int nb_lps; -// int nb_rps; }; int scf_parse_dfa_init(scf_parse_t* parse); diff --git a/util/scf_string.c b/util/scf_string.c index 24cfc8d..59152b7 100644 --- a/util/scf_string.c +++ b/util/scf_string.c @@ -402,13 +402,29 @@ int scf_file_path(uint8_t** path, const scf_string_t* base, const scf_string_t* if ('/' == file->data[0] || '~' == file->data[0]) return 0; + int k = -1; int i; int j; + for (i = base->len - 1; i >= 0; i--) { if ('/' == base->data[i]) break; + + if (k < 0 && '.' == base->data[i]) + k = i; + + // 1, if 'base' is a file path, it has a '.' for extent, such as .c .h + + // 2, if 'base' end by '..' or '.', k == base->len - 1 + + // 3, if 'base' like '../core', k == -1 because loop exit at '/' + + // 4, if 'base' like '../core/', k == -1 because loop exit at the last '/' } + if (k < 0 || k == base->len - 1) // for above 2, 3, 4, the dir is the whole path 'base' + i = base->len - 1; + if (i < 0) return 0; @@ -420,11 +436,15 @@ int scf_file_path(uint8_t** path, const scf_string_t* base, const scf_string_t* if (j == i && (j <= 0 || !strncmp(base->data, file->data, j))) return 0; - uint8_t* p = malloc(i + 1 + file->len + 1); + uint8_t* p = malloc(i + 1 + file->len + 2); if (!p) return -ENOMEM; - memcpy(p, base->data, i + 1); + memcpy(p, base->data, i + 1); + + if ('/' != base->data[i]) + p[++i] = '/'; + memcpy(p + i + 1, file->data, file->len + 1); *path = p; -- 2.25.1