您的位置:首页 > 编程语言

gcc源代码分析,finish_decl ()函数和rest_of_decl_compilation ()函数分析

2015-01-14 20:19 811 查看
int    printf            (const char *     , ... ) ;

本文探讨函数声明到tree到rtx的生成过程。

c-parse.y文件中有下面的一条规则,会调用start_decl ()函数和finish_decl ()函数。

initdcl:

      declarator maybeasm maybe_attribute '='

        { $<ttype>$ = start_decl ($1, current_declspecs, 1); }

      init

/* Note how the declaration of the variable is in effect while its init is parsed! */

        { finish_decl ($<ttype>5, $6, $2); }

    | declarator maybeasm maybe_attribute

        { tree d = start_decl ($1, current_declspecs, 0);

          finish_decl (d, NULL_TREE, $2); }

printf

 <identifier_node 95540 printf permanent

in build_pointer_type

 <integer_type 91130 char readonly permanent QI

    size <integer_cst 82638 type <integer_type 82848* unsigned int> literal permanent 1

    align 8 size_unit 8 sep_unit 8 symtab 0

    sep <integer_cst 82608 type <integer_type 825bc* char> literal permanent -128 precision 8 min <integer_cst 82608 -128>

    max <integer_cst 82620 type <integer_type 825bc* char> literal permanent 127

    pointer_to_this <pointer_type 9117c>

in finish_decl

in start_decl

 <call_expr 956c8 permanent

    arg 0 <identifier_node 95540 printf permanent

    arg 1 <tree_list 956b0 permanent

        purpose <parm_decl 941c0 type <pointer_type 9117c>

            unsigned SI file /usr/include/stdio.h line 214

            size <integer_cst 8254c literal permanent 4

            align 32 size_unit 8 offset 0 arguments <pointer_type 9117c>

        chain <tree_list 95698 permanent value <pointer_type 9117c> chain <tree_list 95698>(nil)

 <tree_list 95608 permanent

    value <identifier_node 82008 int permanent

        global <type_decl 82564 int type <integer_type 824d0* int>

            permanent VOID file (null) line 0

            align 1 size_unit 1 offset 0

in finish_decl

finish_decl 2

rest_of_decl_compilation

 <function_decl 95740 printf

    type <function_type 956e8

        type <integer_type 824d0 int permanent SI

            size <integer_cst 8254c literal permanent 4

            align 32 size_unit 8 sep_unit 32 symtab 0

            sep <integer_cst 8251c literal permanent -2147483648 precision 32 min <integer_cst 8251c -2147483648>

            max <integer_cst 82534 literal permanent 2147483647

            pointer_to_this <pointer_type 88b4c> chain <integer_type 825bc* char>

        permanent EP

        size <integer_cst 82dd8 literal permanent 8

        align 32 size_unit 8 sep_unit 0 symtab 0

        arg-types <tree_list 95698 permanent value <pointer_type 9117c>

    external public permanent QI file /usr/include/stdio.h line 214

    align 1 size_unit 1 offset 0 chain <function_decl 954d8 ungetc>

(symbol_ref:SI ("printf"))

(mem:QI (symbol_ref:SI ("printf")))

rest of decl 1

the end of rest_of_decl

finish_decl 3

/* Finish processing of a declaration;

   install its line number and initial value.

   If the length of an array type is not known before,

   it must be determined now, from the initial value, or it is an error.  */

void

finish_decl (decl, init, asmspec_tree)

     tree decl, init;

     tree asmspec_tree;

{

  if (TREE_CODE (decl) == VAR_DECL || TREE_CODE (decl) == FUNCTION_DECL)

    {

      if (flag_traditional && allocation_temporary_p ())

    {

      end_temporary_allocation ();

      rest_of_decl_compilation (decl, asmspec,

                    current_binding_level == global_binding_level,

                    0);

      resume_temporary_allocation ();

    }

      else

    rest_of_decl_compilation (decl, asmspec,

                  current_binding_level == global_binding_level,

                  0);

...

    }

...

}

/* This is called from finish_decl (within yyparse)

   for each declaration of a function or variable.

   This does nothing for automatic variables.

   Otherwise, it sets up the RTL and outputs any assembler code

   (label definition, storage allocation and initialization).

   DECL is the declaration.  If ASMSPEC is nonzero, it specifies

   the assembler symbol name to be used.  TOP_LEVEL is nonzero

   if this declaration is not within a function.  */

void
rest_of_decl_compilation (decl, asmspec, top_level, at_end)

     tree decl;

     char *asmspec;

     int top_level;

     int at_end;

{

  /* Declarations of variables, and of functions defined elsewhere.  */

  if (TREE_STATIC (decl) || TREE_EXTERNAL (decl))

    TIMEVAR (varconst_time,

         {

           make_decl_rtl (decl, asmspec, top_level);

           /* Don't output anything

          when a tentative file-scope definition is seen.

          But at end of compilation, do output code for them.  */

           if (! (! at_end && top_level

              && (DECL_INITIAL (decl) == 0

              || DECL_INITIAL (decl) == error_mark_node)))

         assemble_variable (decl, top_level, write_symbols, at_end);

         });

/* Create the DECL_RTL for a declaration for a static or external variable

   or static or external function.

   ASMSPEC, if not 0, is the string which the user specified

   as the assembler symbol name.

   TOP_LEVEL is nonzero if this is a file-scope variable.

   This is never called for PARM_DECL nodes.  */

void
make_decl_rtl (decl, asmspec, top_level)

     tree decl;

     char *asmspec;

     int top_level;

{

...

      DECL_RTL (decl) = gen_rtx (MEM, DECL_MODE (decl),

                     gen_rtx (SYMBOL_REF, Pmode, name));

<function_decl 95740 printf 已经生成。

在main函数里么再调用的时候就直接使用了。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  gcc 源代码 分析