Studying note of GCC-3.4.6 source (29)

4.1.2. Set up flags controlling lexer

Below, flag_inline_trees, it is 0 if we should not perform inlining, 1 if we should expand functions calls inline at the tree level, and 2 if we should consider all functions to be inline candidates.

And flag_inline_functions if nonzero, the compiler is allowed to select certain simple functions to be expanded in line at the point of the function call. This variable is automatically set by -O3 unless the -fno-inline-functions flag is specified. Next, flag_no_inline if nonzero, causes the compiler to ignore the inline keyword. Further flag_really_no_inline, if nonzero, means that we don't want inlining by virtue of -fno-inline, not just because the tree inliner turned us off.

Obvious, if flag_really_no_inline is nonzero, unless using attribute “always_inline”, inline functions won’t be expanded. But if lag_no_inline and flag_inline_functions both are nonzero, the compiler will determine which to be expanded.

 

c_common_post_option (continue)

 

1087   flag_inline_trees = 1;

1088

1089   /* Use tree inlining if possible. Function instrumentation is only

1090     done in the RTL level, so we disable tree inlining.  */

1091   if (flag_instrument_function_entry_exit)

1092   {

1093     flag_no_inline = 1;

1094     flag_really_no_inline = 1;

1095   }

1096   else

1097   {

1098     if (!flag_no_inline)

1099       flag_no_inline = 1;

1100     if (flag_inline_functions)

1101     {

1102       flag_inline_trees = 2;

1103       flag_inline_functions = 0;

1104     }

1105   }

1106

1107   /* -Wextra implies -Wsign-compare, but not if explicitly

1108     overridden.  */

1109   if (warn_sign_compare == -1)

1110     warn_sign_compare = extra_warnings;

1111

1112   /* Special format checking options don't work without -Wformat; warn if

1113     they are used.  */

1114   if (warn_format_y2k && !warn_format)

1115     warning ("-Wformat-y2k ignored without -Wformat");

1116   if (warn_format_extra_args && ! warn_format)

1117     warning ("-Wformat-extra-args ignored without -Wformat");

1118   if (warn_format_zero_length && ! warn_format)

1119     warning ("-Wformat-zero-length ignored without -Wformat");

1120   if (warn_format_nonliteral && ! warn_format)

1121     warning ("-Wformat-nonliteral ignored without -Wformat");

1122   if (warn_format_security && ! warn_format)

1123     warning ("-Wformat-security ignored without -Wformat");

1124   if (warn_missing_format_attribute && ! warn_format)

1125     warning ("-Wmissing-format-attribute ignored without -Wformat");

1126

1127   if (flag_preprocess_only)

1128   {

1129     /* Open the output now. We must do so even if flag_no_output is

1130       on, because there may be other output than from the actual

1131       preprocessing (e.g. from -dM).  */

1132     if (out_fname [0] == '/0')

1133       out_fname = stdout;

1134     else

1135       out_fname = fopen (out_fname, "w");

1136

1137     if (out_fname == NULL)

1138     {

1139       fatal_error ("opening output file %s: %m", out_fname);

1140       return false;

1141     }

1142

1143     if (num_in_fnames > 1)

1144       error ("too many filenames given. Type %s --help for usage",

1145             progname);

1146

1147     init_pp_output (out_fname);

1148   }

1149   else

1150   {

1151     init_c_lex ();

1152

1153     /* Yuk.  WTF is this? I do know ObjC relies on it somewhere.  */

1154     input_line = 0;

1155   }

1156

1157   cb = cpp_get_callbacks (parse_in);

1158   cb->file_change = cb_file_change;

1159   cb->dir_change = cb_dir_change;

1160   cpp_post_options (parse_in);

 

If we don’t require just preprocessing and then stop, thus line 1151 above does the initialization related to lex stage.

 

77    void

78    init_c_lex (void)                                                                                        in c-lex.c

79    {

80      struct cpp_callbacks *cb;

81      struct c_fileinfo *toplevel;

82   

83      /* Set up filename timing. Must happen before cpp_read_main_file.  */

84      file_info_tree = splay_tree_new ((splay_tree_compare_fn)strcmp,

85                            0,

86                            (splay_tree_delete_value_fn)free);

87      toplevel = get_fileinfo ("<top level>");

88      if (flag_detailed_statistics)

89      {

90        header_time = 0;

91        body_time = get_run_time ();

92        toplevel->time = body_time;

93      }

94   

95      cb = cpp_get_callbacks (parse_in);

96   

97      cb->line_change = cb_line_change;

98      cb->ident = cb_ident;

99      cb->def_pragma = cb_def_pragma;

100    cb->valid_pch = c_common_valid_pch;

101    cb->read_pch = c_common_read_pch;

102 

103    /* Set the debug callbacks if we can use them.  */

104    if (debug_info_level == DINFO_LEVEL_VERBOSE

105        && (write_symbols == DWARF_DEBUG || write_symbols == DWARF2_DEBUG

106            || write_symbols == VMS_AND_DWARF2_DEBUG))

107    {

108      cb->define = cb_define;

109      cb->undef = cb_undef;

110     }

111   }

 

Above, at line 84, creates a root node for splay-tree (self adjusting binary searching tree). This tree is used to records time of file in compiling.

cpp_get_callbacks, at line 95 above, fetches the address of cb field of cpp_reader, which bundles language dependent handlers here.

We have seen the definition of cpp_options, it is the collection of flags that controls the behavior of the lexer. At line 1161 in c_common_post_option, cpp_post_options adjusts these flags.

 

441    void

442    cpp_post_options (cpp_reader *pfile)                                                        in cpppinit.c

443    {

444      sanity_checks (pfile);

445   

446      post_options (pfile);

447   

448      /* Mark named operators before handling command line macros.  */

449      if (CPP_OPTION (pfile, cplusplus) && CPP_OPTION (pfile, operator_names))

450        mark_named_operators (pfile);

451    }

 

 

Below at line 623, field traditional in cpp_reader is set by option -traditional-cpp (default value is 0), if nonzero, means using traditional preprocessor.

 

605    static void

606    post_options (cpp_reader *pfile)                                                                in cpppinit.c

607    {

608      /* -Wtraditional is not useful in C++ mode.  */

609      if (CPP_OPTION (pfile, cplusplus))

610        CPP_OPTION (pfile, warn_traditional) = 0;

611    

612      /* Permanently disable macro expansion if we are rescanning

613        preprocessed text. Read preprocesed source in ISO mode.  */

614      if (CPP_OPTION (pfile, preprocessed))

615      {

616        pfile->state.prevent_expansion = 1;

617        CPP_OPTION (pfile, traditional) = 0;

618      }

619   

620      if (CPP_OPTION (pfile, warn_trigraphs) == 2)

621        CPP_OPTION (pfile, warn_trigraphs) = !CPP_OPTION (pfile, trigraphs);

622   

623      if (CPP_OPTION (pfile, traditional))

624      {

625        CPP_OPTION (pfile, cplusplus_comments) = 0;

626   

627        /* Traditional CPP does not accurately track column information.  */

628        CPP_OPTION (pfile, show_column) = 0;

629        CPP_OPTION (pfile, trigraphs) = 0;

630        CPP_OPTION (pfile, warn_trigraphs) = 0;

631      }

632    }

 

As long as using C++, operator_names will also be set, mark_named_operators inserts C++ operators into hash_table of cpp_reader.

 

320    static void

321    mark_named_operators (cpp_reader *pfile)                                                in cpppinit.c

322    {

323      const struct builtin *b;

324   

325      for (b = operator_array;

326           b < (operator_array + ARRAY_SIZE (operator_array));

327           b++)

328      {

329        cpp_hashnode *hp = cpp_lookup (pfile, b->name, b->len);

330        hp->flags |= NODE_OPERATOR;

331        hp->is_directive = 0;

332        hp->directive_index = b->value;

333      }

334    }

 

Above at line 325, operator_array is of type builtin which is just records the literal name of the builtin funciton and its enum value associated. The builtin operators of C++ are: and, and_eq, bitand, bitor, compl, not, not_eq, or, or_eq, xor, xor_eq. The value of builtin is defined in TTYPE_TABLE, which is the identifer for the builtin object.

 

281    struct builtin                                                                                            in cpppinit.c

282    {

283      const uchar *name;

284      unsigned short len;

285      unsigned short value;

286    };

 

288    #define B(n, t)    { DSC(n), t }

 

303    static const struct builtin operator_array[] =

304    {

305      B("and",   CPP_AND_AND),

306      B("and_eq",     CPP_AND_EQ),

307      B("bitand",      CPP_AND),

308      B("bitor", CPP_OR),

309      B("compl",      CPP_COMPL),

310      B("not",   CPP_NOT),

311       B("not_eq",     CPP_NOT_EQ),

312      B("or",     CPP_OR_OR),

313      B("or_eq",       CPP_OR_EQ),

314      B("xor",   CPP_XOR),

315      B("xor_eq",     CPP_XOR_EQ)

316    };

317    #undef B

 

Above cpp_lookup at line 329 will insert the node into hash_table of cpp_reader which has element of type ht_identifier (but cpp_hashnode indeed).

 

你可能感兴趣的:(struct,tree,compiler,output,initialization,filenames)