📄 kgram.y
字号:
| '(' declarator ')' {$$ = $2;} | declarator2 '[' ']' {modify_type ($1,IS_ARRAY_OF,NO_STYLE,(token_ptr)NULL);} | declarator2 '[' constant_expr ']' {modify_type ($1,IS_ARRAY_OF,NO_STYLE,(token_ptr)NULL);} | declarator2 parms_next '(' ')' {modify_type ($1,IS_FUNC_RET,OLD_STYLE_VOID,(token_ptr)NULL); in_parms = 0;} | declarator2 parms_next '(' parameter_type_list ')' {modify_type ($1,IS_FUNC_RET,NEW_STYLE,$4); in_parms = 0;} | declarator2 parms_next '(' parameter_identifier_list ')' {modify_type ($1,IS_FUNC_RET,OLD_STYLE,$4); in_parms = 0;} ;pointer : '*' {$$ = (token_ptr)1;} | '*' type_qualifier_list {$$ = (token_ptr)1;} | '*' pointer {$$ = (token_ptr)((int)$2 + 1);} | '*' type_qualifier_list pointer {$$ = (token_ptr)((int)$3 + 1);} ;type_qualifier : CONST {make_decl ($1, FLAG_TYPE_CONST);} | VOLATILE {make_decl ($1, FLAG_TYPE_VOLATILE);} ;type_qualifier_list : type_qualifier | type_qualifier_list type_qualifier ;/*type_specifier_list : type_specifier | type_specifier_list type_specifier { $1->desc.decl->decl_flags |= $2->desc.decl->decl_flags; if ($1->desc.decl->tag == NULL) $1->desc.decl->tag = $2->desc.decl->tag; if ($1->desc.decl->vars == NULL) $1->desc.decl->vars = $2->desc.decl->vars; if ($1->desc.decl->members == NULL) $1->desc.decl->members = $2->desc.decl->members; if ($1->desc.decl->member_ste == NULL) $1->desc.decl->member_ste = $2->desc.decl->member_ste; } ; */parameter_identifier_list : identifier_list /* | identifier_list ',' ELIPSIS */ ;identifier_list : identifier | identifier_list ',' identifier { token_ptr t; if ($1){ t = $1; while (t->next) t = t->next; t->next = $3; } else $$ = $3; } ;parameter_type_list : parameter_list | parameter_list ',' ELIPSIS ;parameter_list : parameter_declaration | parameter_list ',' parameter_declaration { token_ptr t; if ($1){ t = $1; while (t->next) t = t->next; t->next = $3; } else $$ = $3; } ;parameter_declaration : declaration_specifiers declarator/* : type_specifier_list declarator */ { /* : declaration_specifiers declarator */ $1->desc.decl->vars = $2; } /* | REGISTER type_specifier_list declarator { $2->desc.decl->vars = $3; $$ = $2; } | type_name */ | declaration_specifiers abstract_declarator | declaration_specifiers ;type_name /* : type_specifier_list | type_specifier_list abstract_declarator */ : specifier_qual_list | specifier_qual_list abstract_declarator { $1->desc.type_desc = (type_ptr) $2; } ;abstract_declarator : pointer { int i; type_ptr old = NULL,new; for (i = 0; i < (int)$1; i++){ new = make_abstract_type ( IS_PTR_TO,NO_STYLE,(token_ptr)NULL); if (!old) old = new; else merge_abstract_type (old,new); } $$ = (token_ptr)old; } | abstract_declarator2 | pointer abstract_declarator2 { int i; type_ptr old = NULL,new; if ($2) old = (type_ptr)$2; for (i = 0; i < (int)$1; i++){ new = make_abstract_type ( IS_PTR_TO,NO_STYLE,(token_ptr)NULL); if (!old) old = new; else merge_abstract_type (old,new); } $$ = (token_ptr)old; } ;abstract_declarator2 : '(' abstract_declarator ')' {$$ = $2;} | '[' ']' {$$ = (token_ptr) make_abstract_type (IS_ARRAY_OF,NO_STYLE,NULL);} | '[' constant_expr ']' {$$ = (token_ptr) make_abstract_type (IS_ARRAY_OF,NO_STYLE,NULL);} | abstract_declarator2 '[' ']' {type_ptr new; new = make_abstract_type (IS_ARRAY_OF,NO_STYLE,NULL); if ($1){ merge_abstract_type ($1,new); } else $$ = (token_ptr) new; } | abstract_declarator2 '[' constant_expr ']' {type_ptr new; new = make_abstract_type (IS_ARRAY_OF,NO_STYLE,NULL); if ($1){ merge_abstract_type ($1,new); } else $$ = (token_ptr) new; } | '(' ')' {$$ = NULL;} | '(' parameter_type_list ')' {$$ = NULL;} | abstract_declarator2 parms_next '(' ')' | abstract_declarator2 parms_next '(' parameter_type_list ')' ;initializer : assignment_expr { $$ = NULL;} | '{' initializer_list '}' {$$ = NULL;} | '{' initializer_list ',' '}' {$$ = NULL;} ;initializer_list : initializer | initializer_list ',' initializer ;statement : labeled_statement | compound_statement | expression_statement | selection_statement | iteration_statement | jump_statement ;labeled_statement : identifier ':' statement {$$ = stmt_label($1,$3);} | CASE constant_expr ':' statement {$$ = case_stmt ($1,$3,$4,False);} | DEFAULT ':' statement {$$ = case_stmt ($1,$2,$3,True);} ;decl_end : declaration_list { end_local_decl(); } ;decl_start : /* empty */ { open_scope(); start_local_decl(); } ;compound_statement : '{' '}' {$$ = brace_stmt ($1,(token_ptr)NULL,$2);} | '{' statement_list '}' {$$ = brace_stmt ($1,$2,$3);} | '{' decl_start decl_end '}' { close_scope(); $$ = brace_stmt ($1,(token_ptr)NULL,$4); } | '{' decl_start decl_end statement_list '}' { close_scope(); $$ = brace_stmt ($1,$4,$5); } ;declaration_list : declaration | declaration_list declaration { if ($1){ $1->next = $2; } else $$ = $2; } ;statement_list : statement | statement_list statement { $$ = join_stmt ($1,$2);} ;expression_statement : ';' { int node; node = get_stmt_no(); source_map (node,$1,$1); $$ = make_stmt (node,node,node,node); } | expr ';' {int from_node,to_node; int node_id; node_id = xpr_gen ($1, &from_node,&to_node); $$ = make_stmt (node_id,stmtno,from_node,to_node); source_map (node_id,leftmost($1),$2); } ;selection_statement : IF '(' expr ')' statement {$$ = if_stmt ($1,$3,$4,$5,(token_ptr)NULL,(stmt_ptr)NULL);} | IF '(' expr ')' statement ELSE statement {$$ = if_stmt ($1,$3,$4,$5,$6,$7);} | SWITCH '(' expr ')' statement {$$ = switch_stmt ($1,$3,$4,$5);} ;oexpr : /* optional */ {$$ = NULL;} | expr ;iteration_statement : WHILE '(' expr ')' statement {$$ = while_stmt ($1,$3,$4,$5);} | DO statement WHILE '(' expr ')' ';' {$$ = do_stmt($1,$2,$3,$5,$7);} | FOR '(' oexpr ';' oexpr ';' oexpr ')' statement {$$ = for_stmt ($1,$2,$3,$4,$5,$6,$7,$8,$9);} /* | FOR '(' ';' ';' ')' statement | FOR '(' ';' ';' expr ')' statement | FOR '(' ';' expr ';' ')' statement | FOR '(' ';' expr ';' expr ')' statement | FOR '(' expr ';' ';' ')' statement | FOR '(' expr ';' ';' expr ')' statement | FOR '(' expr ';' expr ';' ')' statement | FOR '(' expr ';' expr ';' expr ')' statement */ ;jump_statement : GOTO identifier ';' { $$ = goto_stmt ($1,$2,$3); } | CONTINUE ';' {$$ = continue_stmt ($1,$2);} | BREAK ';' {$$ = break_stmt ($1,$2);} | RETURN ';' {$$ = return_stmt ($1,(tree_ptr)NULL,$2);} | RETURN expr ';' {$$ = return_stmt ($1,$2,$3);} ;program : {$$ = NULL;} | file { close_scope(); } ;file : external_definition | file external_definition ;external_definition : function_definition | declaration | ";" /* | IDENTIFIER "(" ")" ";" */ ;function_start : /* empty */ { token_ptr tk,parm; type_ptr t; $$ = fun_stmt ($<token>-1); open_scope(); start_local_decls(); tk = $<token>-1; /*printf ("Start Fundtion %s",tk->text); */ t = tk->desc.type_desc; while (t){ /*printf ("(mod %d style %d)", t->is,t->style); */ if ((t->is == IS_FUNC_RET) && (t->style == NEW_STYLE)){ parm = t->formals; while (parm){ decl (parm, parm->desc.decl->vars,False); parm = parm->next; } } t=t->next; } /*printf ("\n"); */ clear_type_flag(); } ;function_definition : declarator { } function_start ";" | declarator { } function_start function_body { int end_stmt; end_stmt = $4->exit; do_returns (end_stmt); connect_nodes ($3->exit,$4->entry); gen_require ($4->entry,$3->exit,$3->exit); if (current_proc){ current_proc->exit_node = $4->exit; current_proc->n_locals = current_local(); } close_scope(); fprintf (outfile,"%d(%d",LIF_PROC_END,$4->exit); if (current_proc->has_return_xpr) fprintf (outfile,",R"); fprintf (outfile,")"); if (z_opt)fprintf (outfile," end function %s", $1->text); fprintf (outfile,"\n"); } | declaration_specifiers declarator { decl ($1,NULL,False); } function_start function_body { int is_static = 0; do_returns ($5->exit); connect_nodes ($4->exit,$5->entry); gen_require ($5->entry,$4->exit,$4->exit); close_scope(); fprintf (outfile,"%d(%d",LIF_PROC_END,$5->exit); if($1->desc.decl->decl_flags & FLAG_SC_STATIC){ fprintf (outfile,",S"); is_static = 1; } if (current_proc->has_return_xpr) fprintf (outfile,",R"); fprintf (outfile,")"); if (z_opt)fprintf (outfile," end %sfunction %s", is_static?"static ":"", $2->text); fprintf (outfile,"\n"); if (current_proc){ if (is_static) current_proc->static_or_extern = 'S'; current_proc->type_decl = $1; current_proc->exit_node = $5->exit; current_proc->n_locals = current_local(); } } ;function_body : compound_statement {$$ = $1;} | declaration_list { token_ptr fun,parm; type_ptr t; int pn,level; var_ste_ptr v; $$ = NULL; fun = $<token>-2; /* printf ("\tOld Fundtion body %s: ",$<token>-1->text); */ t = fun->desc.type_desc; while (t){ /* printf ("(mod %d style %d)", t->is,t->style); */ if ((t->is == IS_FUNC_RET) && (t->style == OLD_STYLE)){ parm = t->formals; pn = 1; while (parm){ /* printf ("%s(%d) ",parm->text,pn); */ v = look_up_id (NULL,parm->text,&level); if (!v || (level != 2)){ /* printf ("not a parm "); */ insert_var_decl (parm); v = look_up_id (NULL,parm->text,&level); } /* if(v)printf ("[%d] ",v->id) */; if (v->id != pn) v->id = pn; pn++; parm = parm->next; } } t=t->next; } /* printf ("\n"); */ } compound_statement {$$ = $3;} /* | declaration_list compound_statement */ /* ^ */ /* | */ /* +--- insert check of decl_list vs declarator */ ;identifier : IDENTIFIER ;%%print_flags (flags) int flags;{ static char *flag_names[] = { "char", "short", "int", "long", "signed", "unsigned", "float", "double", "const", "volatile", "void", "u/s", "enum", "user type", "typedef", "extern", "static", "auto", "register", "struct", "union"}; int i = 0; while (flags){ if (flags & 1) printf ("%s ",flag_names[i]); i++; flags = flags >> 1; }}print_decl (type_spec,var_specs) token_ptr type_spec,var_specs;{ token_ptr s,t; type_ptr ty; printf ("Declaration: "); if (type_spec) { printf ("%8x ",type_spec->desc.decl->decl_flags); print_flags (type_spec->desc.decl->decl_flags); if (type_spec->desc.decl->decl_flags & FLAG_TYPE_US){ printf ("\n Struct/union: "); if (type_spec){ if (type_spec->desc.decl->tag){ printf ("(%s) ", type_spec->desc.decl->tag->text); } s = type_spec->desc.decl->members; while (s){ if (s->desc.decl)print_decl (s,s->desc.decl->vars); s = s->next; } } printf ("\n End Struct/union: "); } t = var_specs; while (t) { if(t->text)printf (" %s",t->text); if (ty = t->desc.type_desc){ printf (" ("); while(ty){ if (ty->is == IS_FUNC_RET) printf (" function returning"); else if (ty->is == IS_ARRAY_OF) printf (" array of"); else if (ty->is == IS_PTR_TO) printf (" pointer to"); ty = ty -> next; } printf (")"); } t = t -> next; if(t)printf ("\n%21s",""); } } printf ("\n");}print_token(t) token_ptr t;{ printf ("TOKEN:"); if (t){ printf (" addr %d",t); if (t->text) printf (" (%s)",t->text); printf (" at %d(%d)-%d(%d)", t->at.line_start, t->at.col_start, t->at.line_end, t->at.col_end); } else printf (" is null"); printf ("\n");}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -