00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035 #include "config.h"
00036 #include "system.h"
00037 #include "coretypes.h"
00038 #include "tm.h"
00039 #include "tree.h"
00040 #include "rtl.h"
00041 #include "expr.h"
00042 #include "flags.h"
00043 #include "cp-tree.h"
00044 #include "decl.h"
00045 #include "output.h"
00046 #include "except.h"
00047 #include "toplev.h"
00048 #include "timevar.h"
00049 #include "cpplib.h"
00050 #include "target.h"
00051 #include "c-common.h"
00052 #include "tree-mudflap.h"
00053 #include "cgraph.h"
00054 #include "tree-inline.h"
00055 #include "c-pragma.h"
00056 #ifdef KEY
00057 #include "gspin-gcc-interface.h"
00058 #endif
00059
00060 extern cpp_reader *parse_in;
00061
00062
00063
00064 typedef struct priority_info_s {
00065
00066
00067 int initializations_p;
00068
00069
00070 int destructions_p;
00071 } *priority_info;
00072
00073 static void mark_vtable_entries (tree);
00074 static bool maybe_emit_vtables (tree);
00075 static bool acceptable_java_type (tree);
00076 static tree start_objects (int, int);
00077 static void finish_objects (int, int, tree);
00078 static tree start_static_storage_duration_function (unsigned);
00079 static void finish_static_storage_duration_function (tree);
00080 static priority_info get_priority_info (int);
00081 static void do_static_initialization (tree, tree);
00082 static void do_static_destruction (tree);
00083 static tree start_static_initialization_or_destruction (tree, int);
00084 static void finish_static_initialization_or_destruction (tree);
00085 static void generate_ctor_or_dtor_function (bool, int, location_t *);
00086 static int generate_ctor_and_dtor_functions_for_priority (splay_tree_node,
00087 void *);
00088 static tree prune_vars_needing_no_initialization (tree *);
00089 static void write_out_vars (tree);
00090 static void import_export_class (tree);
00091 static tree get_guard_bits (tree);
00092
00093
00094
00095
00096 static GTY(()) varray_type pending_statics;
00097 #define pending_statics_used \
00098 (pending_statics ? pending_statics->elements_used : 0)
00099
00100
00101
00102 static GTY(()) varray_type deferred_fns;
00103 #define deferred_fns_used \
00104 (deferred_fns ? deferred_fns->elements_used : 0)
00105
00106
00107
00108 extern int spew_debug;
00109
00110
00111
00112 int at_eof;
00113
00114
00115
00116 tree static_ctors;
00117 tree static_dtors;
00118
00119
00120
00121
00122
00123
00124
00125
00126 int
00127 grok_method_quals (tree ctype, tree function, cp_cv_quals quals)
00128 {
00129 tree fntype = TREE_TYPE (function);
00130 tree raises = TYPE_RAISES_EXCEPTIONS (fntype);
00131 int type_quals = TYPE_UNQUALIFIED;
00132 int this_quals = TYPE_UNQUALIFIED;
00133
00134 type_quals = quals & ~TYPE_QUAL_RESTRICT;
00135 this_quals = quals & TYPE_QUAL_RESTRICT;
00136
00137 ctype = cp_build_qualified_type (ctype, type_quals);
00138 fntype = build_method_type_directly (ctype, TREE_TYPE (fntype),
00139 (TREE_CODE (fntype) == METHOD_TYPE
00140 ? TREE_CHAIN (TYPE_ARG_TYPES (fntype))
00141 : TYPE_ARG_TYPES (fntype)));
00142 if (raises)
00143 fntype = build_exception_variant (fntype, raises);
00144
00145 TREE_TYPE (function) = fntype;
00146 return this_quals;
00147 }
00148
00149
00150
00151
00152 tree
00153 cp_build_parm_decl (tree name, tree type)
00154 {
00155 tree parm = build_decl (PARM_DECL, name, type);
00156
00157
00158 if (!processing_template_decl)
00159 DECL_ARG_TYPE (parm) = type_passed_as (type);
00160 return parm;
00161 }
00162
00163
00164
00165
00166 static tree
00167 build_artificial_parm (tree name, tree type)
00168 {
00169 tree parm = cp_build_parm_decl (name, type);
00170 DECL_ARTIFICIAL (parm) = 1;
00171
00172
00173 TREE_READONLY (parm) = 1;
00174 return parm;
00175 }
00176
00177
00178
00179
00180
00181
00182
00183
00184
00185
00186
00187
00188
00189
00190 void
00191 maybe_retrofit_in_chrg (tree fn)
00192 {
00193 tree basetype, arg_types, parms, parm, fntype;
00194
00195
00196 if (DECL_HAS_IN_CHARGE_PARM_P (fn))
00197 return;
00198
00199
00200
00201 if (processing_template_decl)
00202 return;
00203
00204
00205
00206 if (DECL_CONSTRUCTOR_P (fn)
00207 && !CLASSTYPE_VBASECLASSES (DECL_CONTEXT (fn)))
00208 return;
00209
00210 arg_types = TYPE_ARG_TYPES (TREE_TYPE (fn));
00211 basetype = TREE_TYPE (TREE_VALUE (arg_types));
00212 arg_types = TREE_CHAIN (arg_types);
00213
00214 parms = TREE_CHAIN (DECL_ARGUMENTS (fn));
00215
00216
00217
00218 if (CLASSTYPE_VBASECLASSES (DECL_CONTEXT (fn)))
00219 {
00220 parm = build_artificial_parm (vtt_parm_identifier, vtt_parm_type);
00221
00222
00223 TREE_CHAIN (parm) = parms;
00224 parms = parm;
00225
00226
00227 arg_types = hash_tree_chain (vtt_parm_type, arg_types);
00228
00229 DECL_HAS_VTT_PARM_P (fn) = 1;
00230 }
00231
00232
00233 parm = build_artificial_parm (in_charge_identifier, integer_type_node);
00234 TREE_CHAIN (parm) = parms;
00235 parms = parm;
00236 arg_types = hash_tree_chain (integer_type_node, arg_types);
00237
00238
00239 TREE_CHAIN (DECL_ARGUMENTS (fn)) = parms;
00240
00241
00242 fntype = build_method_type_directly (basetype, TREE_TYPE (TREE_TYPE (fn)),
00243 arg_types);
00244 if (TYPE_RAISES_EXCEPTIONS (TREE_TYPE (fn)))
00245 fntype = build_exception_variant (fntype,
00246 TYPE_RAISES_EXCEPTIONS (TREE_TYPE (fn)));
00247 TREE_TYPE (fn) = fntype;
00248
00249
00250 DECL_HAS_IN_CHARGE_PARM_P (fn) = 1;
00251 }
00252
00253
00254
00255
00256
00257
00258
00259
00260
00261
00262
00263
00264
00265
00266
00267
00268
00269
00270
00271
00272
00273 void
00274 grokclassfn (tree ctype, tree function, enum overload_flags flags,
00275 cp_cv_quals quals)
00276 {
00277 tree fn_name = DECL_NAME (function);
00278 cp_cv_quals this_quals = TYPE_UNQUALIFIED;
00279
00280
00281
00282 SET_DECL_LANGUAGE (function, lang_cplusplus);
00283
00284 if (fn_name == NULL_TREE)
00285 {
00286 error ("name missing for member function");
00287 fn_name = get_identifier ("<anonymous>");
00288 DECL_NAME (function) = fn_name;
00289 }
00290
00291 if (quals)
00292 this_quals = grok_method_quals (ctype, function, quals);
00293
00294 if (TREE_CODE (TREE_TYPE (function)) == METHOD_TYPE)
00295 {
00296
00297
00298
00299 tree type = TREE_VALUE (TYPE_ARG_TYPES (TREE_TYPE (function)));
00300 tree qual_type;
00301 tree parm;
00302
00303
00304
00305 this_quals |= TYPE_QUAL_CONST;
00306 qual_type = cp_build_qualified_type (type, this_quals);
00307 parm = build_artificial_parm (this_identifier, qual_type);
00308 cp_apply_type_quals_to_decl (this_quals, parm);
00309 TREE_CHAIN (parm) = DECL_ARGUMENTS (function);
00310 DECL_ARGUMENTS (function) = parm;
00311 }
00312
00313 DECL_CONTEXT (function) = ctype;
00314
00315 if (flags == DTOR_FLAG)
00316 DECL_DESTRUCTOR_P (function) = 1;
00317
00318 if (flags == DTOR_FLAG || DECL_CONSTRUCTOR_P (function))
00319 maybe_retrofit_in_chrg (function);
00320 }
00321
00322
00323
00324
00325 tree
00326 grok_array_decl (tree array_expr, tree index_exp)
00327 {
00328 tree type;
00329 tree expr;
00330 tree orig_array_expr = array_expr;
00331 tree orig_index_exp = index_exp;
00332
00333 if (error_operand_p (array_expr) || error_operand_p (index_exp))
00334 return error_mark_node;
00335
00336 if (processing_template_decl)
00337 {
00338 if (type_dependent_expression_p (array_expr)
00339 || type_dependent_expression_p (index_exp))
00340 return build_min_nt (ARRAY_REF, array_expr, index_exp,
00341 NULL_TREE, NULL_TREE);
00342 array_expr = build_non_dependent_expr (array_expr);
00343 index_exp = build_non_dependent_expr (index_exp);
00344 }
00345
00346 type = TREE_TYPE (array_expr);
00347 gcc_assert (type);
00348 type = non_reference (type);
00349
00350
00351 if (IS_AGGR_TYPE (type) || IS_AGGR_TYPE (TREE_TYPE (index_exp)))
00352 expr = build_new_op (ARRAY_REF, LOOKUP_NORMAL,
00353 array_expr, index_exp, NULL_TREE,
00354 NULL);
00355 else
00356 {
00357 tree p1, p2, i1, i2;
00358
00359
00360
00361
00362
00363 if (TREE_CODE (type) == ARRAY_TYPE)
00364 p1 = array_expr;
00365 else
00366 p1 = build_expr_type_conversion (WANT_POINTER, array_expr, false);
00367
00368 if (TREE_CODE (TREE_TYPE (index_exp)) == ARRAY_TYPE)
00369 p2 = index_exp;
00370 else
00371 p2 = build_expr_type_conversion (WANT_POINTER, index_exp, false);
00372
00373 i1 = build_expr_type_conversion (WANT_INT | WANT_ENUM, array_expr,
00374 false);
00375 i2 = build_expr_type_conversion (WANT_INT | WANT_ENUM, index_exp,
00376 false);
00377
00378 if ((p1 && i2) && (i1 && p2))
00379 error ("ambiguous conversion for array subscript");
00380
00381 if (p1 && i2)
00382 array_expr = p1, index_exp = i2;
00383 else if (i1 && p2)
00384 array_expr = p2, index_exp = i1;
00385 else
00386 {
00387 error ("invalid types %<%T[%T]%> for array subscript",
00388 type, TREE_TYPE (index_exp));
00389 return error_mark_node;
00390 }
00391
00392 if (array_expr == error_mark_node || index_exp == error_mark_node)
00393 error ("ambiguous conversion for array subscript");
00394
00395 expr = build_array_ref (array_expr, index_exp);
00396 }
00397 if (processing_template_decl && expr != error_mark_node)
00398 return build_min_non_dep (ARRAY_REF, expr, orig_array_expr, orig_index_exp,
00399 NULL_TREE, NULL_TREE);
00400 return expr;
00401 }
00402
00403
00404
00405
00406
00407
00408
00409
00410 tree
00411 delete_sanity (tree exp, tree size, bool doing_vec, int use_global_delete)
00412 {
00413 tree t, type;
00414
00415 if (exp == error_mark_node)
00416 return exp;
00417
00418 if (processing_template_decl)
00419 {
00420 t = build_min (DELETE_EXPR, void_type_node, exp, size);
00421 DELETE_EXPR_USE_GLOBAL (t) = use_global_delete;
00422 DELETE_EXPR_USE_VEC (t) = doing_vec;
00423 TREE_SIDE_EFFECTS (t) = 1;
00424 return t;
00425 }
00426
00427
00428 if (TREE_CODE (exp) == VAR_DECL
00429 && TREE_CODE (TREE_TYPE (exp)) == ARRAY_TYPE)
00430 warning ("deleting array %q#D", exp);
00431
00432 t = build_expr_type_conversion (WANT_POINTER, exp, true);
00433
00434 if (t == NULL_TREE || t == error_mark_node)
00435 {
00436 error ("type %q#T argument given to %<delete%>, expected pointer",
00437 TREE_TYPE (exp));
00438 return error_mark_node;
00439 }
00440
00441 type = TREE_TYPE (t);
00442
00443
00444
00445
00446 if (TREE_CODE (TREE_TYPE (type)) == FUNCTION_TYPE)
00447 {
00448 error ("cannot delete a function. Only pointer-to-objects are "
00449 "valid arguments to %<delete%>");
00450 return error_mark_node;
00451 }
00452
00453
00454 if (TREE_CODE (TREE_TYPE (type)) == VOID_TYPE)
00455 {
00456 warning ("deleting %qT is undefined", type);
00457 doing_vec = 0;
00458 }
00459
00460
00461 if (integer_zerop (t))
00462 return build1 (NOP_EXPR, void_type_node, t);
00463
00464 if (doing_vec)
00465 return build_vec_delete (t, NULL_TREE,
00466 sfk_deleting_destructor,
00467 use_global_delete);
00468 else
00469 return build_delete (type, t, sfk_deleting_destructor,
00470 LOOKUP_NORMAL, use_global_delete);
00471 }
00472
00473
00474
00475
00476 void
00477 check_member_template (tree tmpl)
00478 {
00479 tree decl;
00480
00481 gcc_assert (TREE_CODE (tmpl) == TEMPLATE_DECL);
00482 decl = DECL_TEMPLATE_RESULT (tmpl);
00483
00484 if (TREE_CODE (decl) == FUNCTION_DECL
00485 || (TREE_CODE (decl) == TYPE_DECL
00486 && IS_AGGR_TYPE (TREE_TYPE (decl))))
00487 {
00488 if (current_function_decl)
00489
00490
00491
00492 error ("invalid declaration of member template %q#D in local class",
00493 decl);
00494
00495 if (TREE_CODE (decl) == FUNCTION_DECL && DECL_VIRTUAL_P (decl))
00496 {
00497
00498
00499
00500 error
00501 ("invalid use of %<virtual%> in template declaration of %q#D",
00502 decl);
00503 DECL_VIRTUAL_P (decl) = 0;
00504 }
00505
00506
00507
00508 DECL_IGNORED_P (tmpl) = 1;
00509 }
00510 else
00511 error ("template declaration of %q#D", decl);
00512 }
00513
00514
00515
00516 static bool
00517 acceptable_java_type (tree type)
00518 {
00519 if (TREE_CODE (type) == VOID_TYPE || TYPE_FOR_JAVA (type))
00520 return 1;
00521 if (TREE_CODE (type) == POINTER_TYPE || TREE_CODE (type) == REFERENCE_TYPE)
00522 {
00523 type = TREE_TYPE (type);
00524 if (TREE_CODE (type) == RECORD_TYPE)
00525 {
00526 tree args; int i;
00527 if (! TYPE_FOR_JAVA (type))
00528 return false;
00529 if (! CLASSTYPE_TEMPLATE_INFO (type))
00530 return true;
00531 args = CLASSTYPE_TI_ARGS (type);
00532 i = TREE_VEC_LENGTH (args);
00533 while (--i >= 0)
00534 {
00535 type = TREE_VEC_ELT (args, i);
00536 if (TREE_CODE (type) == POINTER_TYPE)
00537 type = TREE_TYPE (type);
00538 if (! TYPE_FOR_JAVA (type))
00539 return false;
00540 }
00541 return true;
00542 }
00543 }
00544 return false;
00545 }
00546
00547
00548
00549
00550
00551 bool
00552 check_java_method (tree method)
00553 {
00554 bool jerr = false;
00555 tree arg_types = TYPE_ARG_TYPES (TREE_TYPE (method));
00556 tree ret_type = TREE_TYPE (TREE_TYPE (method));
00557
00558 if (!acceptable_java_type (ret_type))
00559 {
00560 error ("Java method %qD has non-Java return type %qT",
00561 method, ret_type);
00562 jerr = true;
00563 }
00564
00565 arg_types = TREE_CHAIN (arg_types);
00566 if (DECL_HAS_IN_CHARGE_PARM_P (method))
00567 arg_types = TREE_CHAIN (arg_types);
00568 if (DECL_HAS_VTT_PARM_P (method))
00569 arg_types = TREE_CHAIN (arg_types);
00570
00571 for (; arg_types != NULL_TREE; arg_types = TREE_CHAIN (arg_types))
00572 {
00573 tree type = TREE_VALUE (arg_types);
00574 if (!acceptable_java_type (type))
00575 {
00576 error ("Java method %qD has non-Java parameter type %qT",
00577 method, type);
00578 jerr = true;
00579 }
00580 }
00581 return !jerr;
00582 }
00583
00584
00585
00586
00587
00588
00589
00590
00591
00592
00593
00594 tree
00595 check_classfn (tree ctype, tree function, tree template_parms)
00596 {
00597 int ix;
00598 bool is_template;
00599
00600 if (DECL_USE_TEMPLATE (function)
00601 && !(TREE_CODE (function) == TEMPLATE_DECL
00602 && DECL_TEMPLATE_SPECIALIZATION (function))
00603 && DECL_MEMBER_TEMPLATE_P (DECL_TI_TEMPLATE (function)))
00604
00605
00606
00607
00608
00609
00610
00611
00612
00613
00614 return NULL_TREE;
00615
00616
00617
00618 if (TREE_CODE (function) == TEMPLATE_DECL)
00619 {
00620 gcc_assert (!template_parms
00621 || comp_template_parms (template_parms,
00622 DECL_TEMPLATE_PARMS (function)));
00623 template_parms = DECL_TEMPLATE_PARMS (function);
00624 }
00625
00626
00627 is_template = (template_parms != NULL_TREE);
00628
00629 ix = class_method_index_for_fn (complete_type (ctype), function);
00630 if (ix >= 0)
00631 {
00632 VEC(tree) *methods = CLASSTYPE_METHOD_VEC (ctype);
00633 tree fndecls, fndecl = 0;
00634 bool is_conv_op;
00635 tree pushed_scope;
00636 const char *format = NULL;
00637
00638 pushed_scope = push_scope (ctype);
00639 for (fndecls = VEC_index (tree, methods, ix);
00640 fndecls; fndecls = OVL_NEXT (fndecls))
00641 {
00642 tree p1, p2;
00643
00644 fndecl = OVL_CURRENT (fndecls);
00645 p1 = TYPE_ARG_TYPES (TREE_TYPE (function));
00646 p2 = TYPE_ARG_TYPES (TREE_TYPE (fndecl));
00647
00648
00649
00650
00651
00652
00653
00654
00655 if (DECL_STATIC_FUNCTION_P (fndecl)
00656 && TREE_CODE (TREE_TYPE (function)) == METHOD_TYPE)
00657 p1 = TREE_CHAIN (p1);
00658
00659
00660
00661 if (is_template != (TREE_CODE (fndecl) == TEMPLATE_DECL))
00662 continue;
00663
00664 if (same_type_p (TREE_TYPE (TREE_TYPE (function)),
00665 TREE_TYPE (TREE_TYPE (fndecl)))
00666 && compparms (p1, p2)
00667 && (!is_template
00668 || comp_template_parms (template_parms,
00669 DECL_TEMPLATE_PARMS (fndecl)))
00670 && (DECL_TEMPLATE_SPECIALIZATION (function)
00671 == DECL_TEMPLATE_SPECIALIZATION (fndecl))
00672 && (!DECL_TEMPLATE_SPECIALIZATION (function)
00673 || (DECL_TI_TEMPLATE (function)
00674 == DECL_TI_TEMPLATE (fndecl))))
00675 break;
00676 }
00677 if (pushed_scope)
00678 pop_scope (pushed_scope);
00679 if (fndecls)
00680 return OVL_CURRENT (fndecls);
00681 error ("prototype for %q#D does not match any in class %qT",
00682 function, ctype);
00683 is_conv_op = DECL_CONV_FN_P (fndecl);
00684
00685 if (is_conv_op)
00686 ix = CLASSTYPE_FIRST_CONVERSION_SLOT;
00687 fndecls = VEC_index (tree, methods, ix);
00688 while (fndecls)
00689 {
00690 fndecl = OVL_CURRENT (fndecls);
00691 fndecls = OVL_NEXT (fndecls);
00692
00693 if (!fndecls && is_conv_op)
00694 {
00695 if (VEC_length (tree, methods) > (size_t) ++ix)
00696 {
00697 fndecls = VEC_index (tree, methods, ix);
00698 if (!DECL_CONV_FN_P (OVL_CURRENT (fndecls)))
00699 {
00700 fndecls = NULL_TREE;
00701 is_conv_op = false;
00702 }
00703 }
00704 else
00705 is_conv_op = false;
00706 }
00707 if (format)
00708 format = " %#D";
00709 else if (fndecls)
00710 format = "candidates are: %#D";
00711 else
00712 format = "candidate is: %#D";
00713 cp_error_at (format, fndecl);
00714 }
00715 }
00716 else if (!COMPLETE_TYPE_P (ctype))
00717 cxx_incomplete_type_error (function, ctype);
00718 else
00719 error ("no %q#D member function declared in class %qT",
00720 function, ctype);
00721
00722
00723
00724
00725
00726 if (COMPLETE_TYPE_P (ctype))
00727 add_method (ctype, function, NULL_TREE);
00728 return NULL_TREE;
00729 }
00730
00731
00732
00733
00734
00735 void
00736 note_vague_linkage_fn (tree decl)
00737 {
00738 if (!DECL_DEFERRED_FN (decl))
00739 {
00740 DECL_DEFERRED_FN (decl) = 1;
00741 DECL_DEFER_OUTPUT (decl) = 1;
00742 if (!deferred_fns)
00743 VARRAY_TREE_INIT (deferred_fns, 32, "deferred_fns");
00744 VARRAY_PUSH_TREE (deferred_fns, decl);
00745 }
00746 }
00747
00748
00749
00750 static void
00751 note_vague_linkage_var (tree var)
00752 {
00753 if (!pending_statics)
00754 VARRAY_TREE_INIT (pending_statics, 32, "pending_statics");
00755 VARRAY_PUSH_TREE (pending_statics, var);
00756 }
00757
00758
00759
00760
00761
00762
00763 void
00764 finish_static_data_member_decl (tree decl, tree init, tree asmspec_tree,
00765 int flags)
00766 {
00767 gcc_assert (TREE_PUBLIC (decl));
00768
00769 DECL_CONTEXT (decl) = current_class_type;
00770
00771
00772
00773
00774
00775 if (!asmspec_tree && current_class_type)
00776 DECL_INITIAL (decl) = error_mark_node;
00777
00778 if (! processing_template_decl)
00779 note_vague_linkage_var (decl);
00780
00781 if (LOCAL_CLASS_P (current_class_type))
00782 pedwarn ("local class %q#T shall not have static data member %q#D",
00783 current_class_type, decl);
00784
00785
00786 if (init != NULL_TREE && TYPE_NEEDS_CONSTRUCTING (TREE_TYPE (decl)))
00787 {
00788 static int explained = 0;
00789
00790 error ("initializer invalid for static member with constructor");
00791 if (!explained)
00792 {
00793 error ("(an out of class initialization is required)");
00794 explained = 1;
00795 }
00796 init = NULL_TREE;
00797 }
00798
00799
00800 if (CP_TYPE_CONST_P (TREE_TYPE (decl)) && init == 0)
00801 TREE_USED (decl) = 1;
00802 DECL_INITIAL (decl) = init;
00803 DECL_IN_AGGR_P (decl) = 1;
00804
00805 cp_finish_decl (decl, init, asmspec_tree, flags);
00806 }
00807
00808
00809
00810
00811
00812
00813
00814
00815
00816
00817
00818
00819
00820
00821
00822
00823
00824
00825
00826 tree
00827 grokfield (const cp_declarator *declarator,
00828 cp_decl_specifier_seq *declspecs,
00829 tree init, tree asmspec_tree,
00830 tree attrlist)
00831 {
00832 tree value;
00833 const char *asmspec = 0;
00834 int flags = LOOKUP_ONLYCONVERTING;
00835
00836 if (!declspecs->any_specifiers_p
00837 && declarator->kind == cdk_id
00838 && declarator->u.id.qualifying_scope
00839 && TREE_CODE (declarator->u.id.unqualified_name) == IDENTIFIER_NODE)
00840
00841 return do_class_using_decl (declarator->u.id.qualifying_scope,
00842 declarator->u.id.unqualified_name);
00843
00844 if (init
00845 && TREE_CODE (init) == TREE_LIST
00846 && TREE_VALUE (init) == error_mark_node
00847 && TREE_CHAIN (init) == NULL_TREE)
00848 init = NULL_TREE;
00849
00850 value = grokdeclarator (declarator, declspecs, FIELD, init != 0, &attrlist);
00851 if (! value || error_operand_p (value))
00852
00853 return error_mark_node;
00854
00855 if (TREE_CODE (value) == TYPE_DECL && init)
00856 {
00857 error ("typedef %qD is initialized (use __typeof__ instead)", value);
00858 init = NULL_TREE;
00859 }
00860
00861
00862 if (value == void_type_node)
00863 return value;
00864
00865
00866 if ((TREE_CODE (value) == FUNCTION_DECL
00867 || TREE_CODE (value) == TEMPLATE_DECL)
00868 && DECL_CONTEXT (value) != current_class_type)
00869 return value;
00870
00871 if (DECL_NAME (value) != NULL_TREE
00872 && IDENTIFIER_POINTER (DECL_NAME (value))[0] == '_'
00873 && ! strcmp (IDENTIFIER_POINTER (DECL_NAME (value)), "_vptr"))
00874 error ("member %qD conflicts with virtual function table field name",
00875 value);
00876
00877
00878 if (TREE_CODE (value) == TYPE_DECL)
00879 {
00880 DECL_NONLOCAL (value) = 1;
00881 DECL_CONTEXT (value) = current_class_type;
00882
00883 if (processing_template_decl)
00884 value = push_template_decl (value);
00885
00886 if (attrlist)
00887 {
00888
00889
00890 tree type = TREE_TYPE (value);
00891 if (TREE_CODE (type) == TEMPLATE_TYPE_PARM
00892 || TREE_CODE (type) == BOUND_TEMPLATE_TEMPLATE_PARM)
00893 sorry ("applying attributes to template parameters is not implemented");
00894 else
00895 cplus_decl_attributes (&value, attrlist, 0);
00896 }
00897
00898 return value;
00899 }
00900
00901 if (DECL_IN_AGGR_P (value))
00902 {
00903 error ("%qD is already defined in %qT", value, DECL_CONTEXT (value));
00904 return void_type_node;
00905 }
00906
00907 if (asmspec_tree)
00908 asmspec = TREE_STRING_POINTER (asmspec_tree);
00909
00910 if (init)
00911 {
00912 if (TREE_CODE (value) == FUNCTION_DECL)
00913 {
00914
00915
00916 if (TREE_CODE (TREE_TYPE (value)) == METHOD_TYPE)
00917 {
00918 gcc_assert (error_operand_p (init) || integer_zerop (init));
00919 DECL_PURE_VIRTUAL_P (value) = 1;
00920 }
00921 else
00922 {
00923 gcc_assert (TREE_CODE (TREE_TYPE (value)) == FUNCTION_TYPE);
00924 error ("initializer specified for static member function %qD",
00925 value);
00926 }
00927 }
00928 else if (pedantic && TREE_CODE (value) != VAR_DECL)
00929
00930 init = NULL_TREE;
00931 else
00932 {
00933
00934
00935 if (TREE_CODE (init) == TREE_LIST)
00936 {
00937 if (TREE_CHAIN (init) == NULL_TREE)
00938 init = TREE_VALUE (init);
00939 else
00940 init = digest_init (TREE_TYPE (value), init, (tree *)0);
00941 }
00942
00943 if (!processing_template_decl)
00944 {
00945 if (TREE_CODE (init) == CONSTRUCTOR)
00946 init = digest_init (TREE_TYPE (value), init, (tree *)0);
00947 else
00948 init = integral_constant_value (init);
00949
00950 if (init != error_mark_node && ! TREE_CONSTANT (init))
00951 {
00952
00953
00954
00955 if (TREE_CODE (TREE_TYPE (value)) != REFERENCE_TYPE
00956 || (TREE_STATIC (init) == 0
00957 && (!DECL_P (init) || DECL_EXTERNAL (init) == 0)))
00958 {
00959 error ("field initializer is not constant");
00960 init = error_mark_node;
00961 }
00962 }
00963 }
00964 }
00965 }
00966
00967 if (processing_template_decl
00968 && (TREE_CODE (value) == VAR_DECL || TREE_CODE (value) == FUNCTION_DECL))
00969 {
00970 value = push_template_decl (value);
00971 if (error_operand_p (value))
00972 return error_mark_node;
00973 }
00974
00975 if (attrlist)
00976 cplus_decl_attributes (&value, attrlist, 0);
00977
00978 switch (TREE_CODE (value))
00979 {
00980 case VAR_DECL:
00981 finish_static_data_member_decl (value, init, asmspec_tree,
00982 flags);
00983 return value;
00984
00985 case FIELD_DECL:
00986 if (asmspec)
00987 error ("%<asm%> specifiers are not permitted on non-static data members");
00988 if (DECL_INITIAL (value) == error_mark_node)
00989 init = error_mark_node;
00990 cp_finish_decl (value, init, NULL_TREE, flags);
00991 DECL_INITIAL (value) = init;
00992 DECL_IN_AGGR_P (value) = 1;
00993 return value;
00994
00995 case FUNCTION_DECL:
00996 if (asmspec)
00997 set_user_assembler_name (value, asmspec);
00998 if (!DECL_FRIEND_P (value))
00999 grok_special_member_properties (value);
01000
01001 cp_finish_decl (value, init, asmspec_tree, flags);
01002
01003
01004 if (DECL_FRIEND_P (value))
01005 return void_type_node;
01006
01007 DECL_IN_AGGR_P (value) = 1;
01008 return value;
01009
01010 default:
01011 gcc_unreachable ();
01012 }
01013 return NULL_TREE;
01014 }
01015
01016
01017
01018
01019 tree
01020 grokbitfield (const cp_declarator *declarator,
01021 cp_decl_specifier_seq *declspecs, tree width)
01022 {
01023 tree value = grokdeclarator (declarator, declspecs, BITFIELD, 0, NULL);
01024
01025 if (! value) return NULL_TREE;
01026
01027
01028 if (TREE_CODE (value) == VOID_TYPE)
01029 return void_type_node;
01030
01031 if (TREE_CODE (value) == TYPE_DECL)
01032 {
01033 error ("cannot declare %qD to be a bit-field type", value);
01034 return NULL_TREE;
01035 }
01036
01037
01038
01039
01040
01041 if (TREE_CODE (value) == FUNCTION_DECL)
01042 {
01043 error ("cannot declare bit-field %qD with function type",
01044 DECL_NAME (value));
01045 return NULL_TREE;
01046 }
01047
01048 if (DECL_IN_AGGR_P (value))
01049 {
01050 error ("%qD is already defined in the class %qT", value,
01051 DECL_CONTEXT (value));
01052 return void_type_node;
01053 }
01054
01055 if (TREE_STATIC (value))
01056 {
01057 error ("static member %qD cannot be a bit-field", value);
01058 return NULL_TREE;
01059 }
01060 cp_finish_decl (value, NULL_TREE, NULL_TREE, 0);
01061
01062 if (width != error_mark_node)
01063 {
01064 constant_expression_warning (width);
01065 DECL_INITIAL (value) = width;
01066 SET_DECL_C_BIT_FIELD (value);
01067 }
01068
01069 DECL_IN_AGGR_P (value) = 1;
01070 return value;
01071 }
01072
01073
01074 void
01075 cplus_decl_attributes (tree *decl, tree attributes, int flags)
01076 {
01077 if (*decl == NULL_TREE || *decl == void_type_node)
01078 return;
01079
01080 if (TREE_CODE (*decl) == TEMPLATE_DECL)
01081 decl = &DECL_TEMPLATE_RESULT (*decl);
01082
01083 decl_attributes (decl, attributes, flags);
01084
01085 if (TREE_CODE (*decl) == TYPE_DECL)
01086 SET_IDENTIFIER_TYPE_VALUE (DECL_NAME (*decl), TREE_TYPE (*decl));
01087 }
01088
01089
01090
01091
01092
01093 static tree
01094 build_anon_union_vars (tree type, tree object)
01095 {
01096 tree main_decl = NULL_TREE;
01097 tree field;
01098
01099
01100
01101 if (TREE_CODE (type) != UNION_TYPE)
01102 error ("anonymous struct not inside named type");
01103
01104 for (field = TYPE_FIELDS (type);
01105 field != NULL_TREE;
01106 field = TREE_CHAIN (field))
01107 {
01108 tree decl;
01109 tree ref;
01110
01111 if (DECL_ARTIFICIAL (field))
01112 continue;
01113 if (TREE_CODE (field) != FIELD_DECL)
01114 {
01115 cp_pedwarn_at ("%q#D invalid; an anonymous union can only "
01116 "have non-static data members",
01117 field);
01118 continue;
01119 }
01120
01121 if (TREE_PRIVATE (field))
01122 cp_pedwarn_at ("private member %q#D in anonymous union", field);
01123 else if (TREE_PROTECTED (field))
01124 cp_pedwarn_at ("protected member %q#D in anonymous union", field);
01125
01126 if (processing_template_decl)
01127 ref = build_min_nt (COMPONENT_REF, object,
01128 DECL_NAME (field), NULL_TREE);
01129 else
01130 ref = build_class_member_access_expr (object, field, NULL_TREE,
01131 false);
01132
01133 if (DECL_NAME (field))
01134 {
01135 tree base;
01136
01137 decl = build_decl (VAR_DECL, DECL_NAME (field), TREE_TYPE (field));
01138
01139 base = get_base_address (object);
01140 TREE_PUBLIC (decl) = TREE_PUBLIC (base);
01141 TREE_STATIC (decl) = TREE_STATIC (base);
01142 DECL_EXTERNAL (decl) = DECL_EXTERNAL (base);
01143
01144 DECL_VALUE_EXPR (decl) = ref;
01145
01146 decl = pushdecl (decl);
01147 }
01148 else if (ANON_AGGR_TYPE_P (TREE_TYPE (field)))
01149 decl = build_anon_union_vars (TREE_TYPE (field), ref);
01150 else
01151 decl = 0;
01152
01153 if (main_decl == NULL_TREE)
01154 main_decl = decl;
01155 }
01156
01157 return main_decl;
01158 }
01159
01160
01161
01162
01163
01164 void
01165 finish_anon_union (tree anon_union_decl)
01166 {
01167 tree type;
01168 tree main_decl;
01169 bool public_p;
01170
01171 if (anon_union_decl == error_mark_node)
01172 return;
01173
01174 type = TREE_TYPE (anon_union_decl);
01175 public_p = TREE_PUBLIC (anon_union_decl);
01176
01177
01178 DECL_CONTEXT (anon_union_decl) = DECL_CONTEXT (TYPE_NAME (type));
01179
01180 if (TYPE_FIELDS (type) == NULL_TREE)
01181 return;
01182
01183 if (public_p)
01184 {
01185 error ("namespace-scope anonymous aggregates must be static");
01186 return;
01187 }
01188
01189 main_decl = build_anon_union_vars (type, anon_union_decl);
01190 if (main_decl == NULL_TREE)
01191 {
01192 warning ("anonymous union with no members");
01193 return;
01194 }
01195
01196 if (!processing_template_decl)
01197 {
01198
01199 DECL_NAME (anon_union_decl) = DECL_NAME (main_decl);
01200 mangle_decl (anon_union_decl);
01201 DECL_NAME (anon_union_decl) = NULL_TREE;
01202 }
01203
01204 pushdecl (anon_union_decl);
01205 if (building_stmt_tree ()
01206 && at_function_scope_p ())
01207 add_decl_expr (anon_union_decl);
01208 else if (!processing_template_decl)
01209 rest_of_decl_compilation (anon_union_decl,
01210 toplevel_bindings_p (), at_eof);
01211 }
01212
01213
01214
01215
01216
01217 tree
01218 coerce_new_type (tree type)
01219 {
01220 int e = 0;
01221 tree args = TYPE_ARG_TYPES (type);
01222
01223 gcc_assert (TREE_CODE (type) == FUNCTION_TYPE);
01224
01225 if (!same_type_p (TREE_TYPE (type), ptr_type_node))
01226 {
01227 e = 1;
01228 error ("%<operator new%> must return type %qT", ptr_type_node);
01229 }
01230
01231 if (!args || args == void_list_node
01232 || !same_type_p (TREE_VALUE (args), size_type_node))
01233 {
01234 e = 2;
01235 if (args && args != void_list_node)
01236 args = TREE_CHAIN (args);
01237 pedwarn ("%<operator new%> takes type %<size_t%> (%qT) "
01238 "as first parameter", size_type_node);
01239 }
01240 switch (e)
01241 {
01242 case 2:
01243 args = tree_cons (NULL_TREE, size_type_node, args);
01244
01245 case 1:
01246 type = build_exception_variant
01247 (build_function_type (ptr_type_node, args),
01248 TYPE_RAISES_EXCEPTIONS (type));
01249
01250 default:;
01251 }
01252 return type;
01253 }
01254
01255 tree
01256 coerce_delete_type (tree type)
01257 {
01258 int e = 0;
01259 tree args = TYPE_ARG_TYPES (type);
01260
01261 gcc_assert (TREE_CODE (type) == FUNCTION_TYPE);
01262
01263 if (!same_type_p (TREE_TYPE (type), void_type_node))
01264 {
01265 e = 1;
01266 error ("%<operator delete%> must return type %qT", void_type_node);
01267 }
01268
01269 if (!args || args == void_list_node
01270 || !same_type_p (TREE_VALUE (args), ptr_type_node))
01271 {
01272 e = 2;
01273 if (args && args != void_list_node)
01274 args = TREE_CHAIN (args);
01275 error ("%<operator delete%> takes type %qT as first parameter",
01276 ptr_type_node);
01277 }
01278 switch (e)
01279 {
01280 case 2:
01281 args = tree_cons (NULL_TREE, ptr_type_node, args);
01282
01283 case 1:
01284 type = build_exception_variant
01285 (build_function_type (void_type_node, args),
01286 TYPE_RAISES_EXCEPTIONS (type));
01287
01288 default:;
01289 }
01290
01291 return type;
01292 }
01293
01294 static void
01295 mark_vtable_entries (tree decl)
01296 {
01297 tree entries = CONSTRUCTOR_ELTS (DECL_INITIAL (decl));
01298
01299 for (; entries; entries = TREE_CHAIN (entries))
01300 {
01301 tree fnaddr = TREE_VALUE (entries);
01302 tree fn;
01303
01304 STRIP_NOPS (fnaddr);
01305
01306 if (TREE_CODE (fnaddr) != ADDR_EXPR
01307 && TREE_CODE (fnaddr) != FDESC_EXPR)
01308
01309
01310 continue;
01311
01312 fn = TREE_OPERAND (fnaddr, 0);
01313 TREE_ADDRESSABLE (fn) = 1;
01314
01315
01316
01317
01318 if (DECL_THUNK_P (fn))
01319 use_thunk (fn, 0);
01320 mark_used (fn);
01321 }
01322 }
01323
01324
01325
01326
01327 void
01328 comdat_linkage (tree decl)
01329 {
01330 if (flag_weak)
01331 make_decl_one_only (decl);
01332 else if (TREE_CODE (decl) == FUNCTION_DECL
01333 || (TREE_CODE (decl) == VAR_DECL && DECL_ARTIFICIAL (decl)))
01334
01335
01336
01337
01338
01339
01340
01341
01342
01343
01344
01345
01346
01347
01348
01349
01350 TREE_PUBLIC (decl) = 0;
01351 else
01352 {
01353
01354
01355 if (DECL_INITIAL (decl) == 0
01356 || DECL_INITIAL (decl) == error_mark_node)
01357 DECL_COMMON (decl) = 1;
01358 else if (EMPTY_CONSTRUCTOR_P (DECL_INITIAL (decl)))
01359 {
01360 DECL_COMMON (decl) = 1;
01361 DECL_INITIAL (decl) = error_mark_node;
01362 }
01363 else if (!DECL_EXPLICIT_INSTANTIATION (decl))
01364 {
01365
01366
01367 DECL_EXTERNAL (decl) = 1;
01368 DECL_NOT_REALLY_EXTERN (decl) = 0;
01369 }
01370 }
01371
01372 if (DECL_LANG_SPECIFIC (decl))
01373 DECL_COMDAT (decl) = 1;
01374 }
01375
01376
01377
01378
01379
01380
01381
01382 void
01383 maybe_make_one_only (tree decl)
01384 {
01385
01386
01387
01388
01389
01390
01391 if (! flag_weak)
01392 return;
01393
01394
01395
01396
01397
01398
01399 if (!TARGET_WEAK_NOT_IN_ARCHIVE_TOC
01400 || (! DECL_EXPLICIT_INSTANTIATION (decl)
01401 && ! DECL_TEMPLATE_SPECIALIZATION (decl)))
01402 {
01403 make_decl_one_only (decl);
01404
01405 if (TREE_CODE (decl) == VAR_DECL)
01406 {
01407 DECL_COMDAT (decl) = 1;
01408
01409 mark_decl_referenced (decl);
01410 }
01411 }
01412 }
01413
01414
01415
01416
01417 static void
01418 import_export_class (tree ctype)
01419 {
01420
01421 int import_export = 0;
01422
01423
01424
01425
01426
01427
01428 gcc_assert (at_eof);
01429
01430 if (CLASSTYPE_INTERFACE_KNOWN (ctype))
01431 return;
01432
01433
01434
01435
01436
01437
01438 if (CLASSTYPE_INTERFACE_ONLY (ctype))
01439 return;
01440
01441 if (lookup_attribute ("dllimport", TYPE_ATTRIBUTES (ctype)))
01442 import_export = -1;
01443 else if (lookup_attribute ("dllexport", TYPE_ATTRIBUTES (ctype)))
01444 import_export = 1;
01445 else if (CLASSTYPE_IMPLICIT_INSTANTIATION (ctype)
01446 && !flag_implicit_templates)
01447
01448
01449
01450
01451 import_export = repo_export_class_p (ctype) ? 1 : -1;
01452 else if (TYPE_POLYMORPHIC_P (ctype))
01453 {
01454
01455
01456 tree method = CLASSTYPE_KEY_METHOD (ctype);
01457
01458
01459
01460
01461
01462
01463 if (method && (flag_weak || ! DECL_DECLARED_INLINE_P (method)))
01464 import_export = (DECL_REALLY_EXTERN (method) ? -1 : 1);
01465 }
01466
01467
01468
01469 if (MULTIPLE_SYMBOL_SPACES && import_export == -1)
01470 import_export = 0;
01471
01472
01473 if (targetm.cxx.import_export_class)
01474 import_export = targetm.cxx.import_export_class (ctype, import_export);
01475
01476 if (import_export)
01477 {
01478 SET_CLASSTYPE_INTERFACE_KNOWN (ctype);
01479 CLASSTYPE_INTERFACE_ONLY (ctype) = (import_export < 0);
01480 }
01481 }
01482
01483
01484
01485 static bool
01486 var_finalized_p (tree var)
01487 {
01488 return cgraph_varpool_node (var)->finalized;
01489 }
01490
01491
01492
01493
01494 void
01495 mark_needed (tree decl)
01496 {
01497
01498
01499
01500 TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (decl)) = 1;
01501 mark_decl_referenced (decl);
01502 }
01503
01504
01505
01506
01507
01508
01509
01510 bool
01511 decl_needed_p (tree decl)
01512 {
01513 gcc_assert (TREE_CODE (decl) == VAR_DECL
01514 || TREE_CODE (decl) == FUNCTION_DECL);
01515
01516
01517
01518 gcc_assert (at_eof);
01519
01520
01521
01522 if (TREE_PUBLIC (decl) && !DECL_COMDAT (decl))
01523 return true;
01524
01525
01526 if (TREE_USED (decl)
01527 || (DECL_ASSEMBLER_NAME_SET_P (decl)
01528 && TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (decl))))
01529 return true;
01530
01531
01532 return false;
01533 }
01534
01535 #ifdef KEY
01536
01537
01538
01539
01540
01541
01542
01543
01544
01545
01546
01547
01548
01549
01550
01551 bool
01552 decl_maybe_needed_p (tree decl)
01553 {
01554 gcc_assert (TREE_CODE (decl) == VAR_DECL
01555 || TREE_CODE (decl) == FUNCTION_DECL);
01556
01557
01558
01559 gcc_assert (at_eof);
01560
01561
01562
01563 if (TREE_PUBLIC (decl) && !DECL_COMDAT (decl))
01564 return true;
01565
01566
01567 if (TREE_USED (decl)
01568 || (DECL_ASSEMBLER_NAME_SET_P (decl)
01569 ))
01570 return true;
01571
01572
01573 return false;
01574 }
01575 #endif
01576
01577
01578
01579
01580 static bool
01581 maybe_emit_vtables (tree ctype)
01582 {
01583 tree vtbl;
01584 tree primary_vtbl;
01585 int needed = 0;
01586
01587
01588
01589 primary_vtbl = CLASSTYPE_VTABLES (ctype);
01590 if (var_finalized_p (primary_vtbl))
01591 return false;
01592
01593 if (TREE_TYPE (primary_vtbl) == void_type_node)
01594 return false;
01595
01596
01597
01598
01599 if (!targetm.cxx.key_method_may_be_inline ())
01600 determine_key_method (ctype);
01601
01602
01603 for (vtbl = CLASSTYPE_VTABLES (ctype); vtbl; vtbl = TREE_CHAIN (vtbl))
01604 {
01605 import_export_decl (vtbl);
01606 if (DECL_NOT_REALLY_EXTERN (vtbl) && decl_needed_p (vtbl))
01607 needed = 1;
01608 }
01609 if (!needed)
01610 {
01611
01612
01613
01614 if (DECL_COMDAT (primary_vtbl)
01615 && CLASSTYPE_DEBUG_REQUESTED (ctype))
01616 note_debug_info_needed (ctype);
01617 return false;
01618 }
01619
01620
01621
01622 for (vtbl = CLASSTYPE_VTABLES (ctype); vtbl; vtbl = TREE_CHAIN (vtbl))
01623 {
01624
01625 mark_vtable_entries (vtbl);
01626
01627 if (TREE_TYPE (DECL_INITIAL (vtbl)) == 0)
01628 {
01629 tree expr = store_init_value (vtbl, DECL_INITIAL (vtbl));
01630
01631
01632 gcc_assert (!expr);
01633 }
01634
01635
01636 DECL_EXTERNAL (vtbl) = 0;
01637 rest_of_decl_compilation (vtbl, 1, 1);
01638
01639
01640
01641 if (flag_syntax_only)
01642 TREE_ASM_WRITTEN (vtbl) = 1;
01643 }
01644
01645
01646
01647 note_debug_info_needed (ctype);
01648
01649 return true;
01650 }
01651
01652
01653
01654
01655 void
01656 determine_visibility (tree decl)
01657 {
01658 tree class_type;
01659
01660
01661
01662
01663 gcc_assert (!DECL_CLONED_FUNCTION_P (decl));
01664
01665
01666 if (c_determine_visibility (decl))
01667 return;
01668
01669
01670
01671 if (DECL_CLASS_SCOPE_P (decl))
01672 class_type = DECL_CONTEXT (decl);
01673 else if (TREE_CODE (decl) == VAR_DECL
01674 && DECL_TINFO_P (decl)
01675 && CLASS_TYPE_P (TREE_TYPE (DECL_NAME (decl))))
01676 class_type = TREE_TYPE (DECL_NAME (decl));
01677 else
01678 {
01679
01680
01681 gcc_assert (TREE_CODE (decl) != VAR_DECL
01682 || !DECL_VTABLE_OR_VTT_P (decl));
01683
01684
01685 return;
01686 }
01687
01688
01689
01690 if (class_type)
01691 {
01692 if (TARGET_DLLIMPORT_DECL_ATTRIBUTES
01693 && lookup_attribute ("dllexport", TYPE_ATTRIBUTES (class_type)))
01694 {
01695 DECL_VISIBILITY (decl) = VISIBILITY_DEFAULT;
01696 DECL_VISIBILITY_SPECIFIED (decl) = 1;
01697 }
01698 else if (TREE_CODE (decl) == FUNCTION_DECL
01699 && DECL_DECLARED_INLINE_P (decl)
01700 && visibility_options.inlines_hidden)
01701 {
01702 DECL_VISIBILITY (decl) = VISIBILITY_HIDDEN;
01703 DECL_VISIBILITY_SPECIFIED (decl) = 1;
01704 }
01705 else if (CLASSTYPE_VISIBILITY_SPECIFIED (class_type))
01706 {
01707 DECL_VISIBILITY (decl) = CLASSTYPE_VISIBILITY (class_type);
01708 DECL_VISIBILITY_SPECIFIED (decl) = 1;
01709 }
01710
01711
01712
01713 else if (TREE_CODE (decl) == VAR_DECL
01714 && targetm.cxx.export_class_data ()
01715 && (DECL_TINFO_P (decl)
01716 || (DECL_VTABLE_OR_VTT_P (decl)
01717
01718
01719
01720
01721 && !DECL_CONSTRUCTION_VTABLE_P (decl))))
01722 DECL_VISIBILITY (decl) = VISIBILITY_DEFAULT;
01723 else
01724 {
01725 DECL_VISIBILITY (decl) = CLASSTYPE_VISIBILITY (class_type);
01726 DECL_VISIBILITY_SPECIFIED (decl) = 0;
01727 }
01728 }
01729 }
01730
01731
01732
01733
01734
01735
01736
01737
01738
01739
01740
01741
01742
01743 void
01744 import_export_decl (tree decl)
01745 {
01746 int emit_p;
01747 bool comdat_p;
01748 bool import_p;
01749
01750 if (DECL_INTERFACE_KNOWN (decl))
01751 return;
01752
01753
01754
01755
01756
01757
01758
01759
01760
01761 gcc_assert (at_eof);
01762
01763
01764
01765
01766
01767
01768
01769
01770
01771
01772
01773
01774
01775
01776
01777
01778
01779
01780
01781
01782
01783
01784 gcc_assert (TREE_CODE (decl) == FUNCTION_DECL
01785 || TREE_CODE (decl) == VAR_DECL);
01786
01787
01788 gcc_assert (TREE_PUBLIC (decl));
01789 if (TREE_CODE (decl) == FUNCTION_DECL)
01790 gcc_assert (DECL_IMPLICIT_INSTANTIATION (decl)
01791 || DECL_FRIEND_PSEUDO_TEMPLATE_INSTANTIATION (decl)
01792 || DECL_DECLARED_INLINE_P (decl));
01793 else
01794 gcc_assert (DECL_IMPLICIT_INSTANTIATION (decl)
01795 || DECL_VTABLE_OR_VTT_P (decl)
01796 || DECL_TINFO_P (decl));
01797
01798
01799 gcc_assert (!DECL_REALLY_EXTERN (decl));
01800
01801
01802 comdat_p = false;
01803
01804
01805 import_p = false;
01806
01807
01808
01809 emit_p = repo_emit_p (decl);
01810 if (emit_p == 0)
01811 import_p = true;
01812 else if (emit_p == 1)
01813 {
01814
01815
01816 if (TREE_CODE (decl) == VAR_DECL)
01817 mark_needed (decl);
01818 else if (DECL_MAYBE_IN_CHARGE_CONSTRUCTOR_P (decl)
01819 || DECL_MAYBE_IN_CHARGE_DESTRUCTOR_P (decl))
01820 {
01821 tree clone;
01822 FOR_EACH_CLONE (clone, decl)
01823 mark_needed (clone);
01824 }
01825 else
01826 mark_needed (decl);
01827
01828 DECL_EXTERNAL (decl) = 0;
01829 DECL_INTERFACE_KNOWN (decl) = 1;
01830 return;
01831 }
01832
01833 if (import_p)
01834
01835
01836 ;
01837 else if (TREE_CODE (decl) == VAR_DECL && DECL_VTABLE_OR_VTT_P (decl))
01838 {
01839 tree type = DECL_CONTEXT (decl);
01840 import_export_class (type);
01841 if (TYPE_FOR_JAVA (type))
01842 import_p = true;
01843 else if (CLASSTYPE_INTERFACE_KNOWN (type)
01844 && CLASSTYPE_INTERFACE_ONLY (type))
01845 import_p = true;
01846 else if ((!flag_weak || TARGET_WEAK_NOT_IN_ARCHIVE_TOC)
01847 && !CLASSTYPE_USE_TEMPLATE (type)
01848 && CLASSTYPE_KEY_METHOD (type)
01849 && !DECL_DECLARED_INLINE_P (CLASSTYPE_KEY_METHOD (type)))
01850
01851
01852
01853
01854
01855
01856
01857
01858
01859
01860 DECL_EXTERNAL (decl) = 0;
01861 else if (CLASSTYPE_INTERFACE_KNOWN (type))
01862 {
01863
01864
01865 if (!flag_weak && CLASSTYPE_EXPLICIT_INSTANTIATION (type))
01866
01867
01868
01869
01870
01871
01872
01873 DECL_EXTERNAL (decl) = 0;
01874 else
01875 {
01876
01877
01878
01879
01880 comdat_p = true;
01881 mark_needed (decl);
01882 }
01883 }
01884 else if (!flag_implicit_templates
01885 && CLASSTYPE_IMPLICIT_INSTANTIATION (type))
01886 import_p = true;
01887 else
01888 comdat_p = true;
01889 }
01890 else if (TREE_CODE (decl) == VAR_DECL && DECL_TINFO_P (decl))
01891 {
01892 tree type = TREE_TYPE (DECL_NAME (decl));
01893 if (CLASS_TYPE_P (type))
01894 {
01895 import_export_class (type);
01896 if (CLASSTYPE_INTERFACE_KNOWN (type)
01897 && TYPE_POLYMORPHIC_P (type)
01898 && CLASSTYPE_INTERFACE_ONLY (type)
01899
01900
01901
01902
01903 && flag_rtti)
01904 import_p = true;
01905 else
01906 {
01907 comdat_p = true;
01908 if (CLASSTYPE_INTERFACE_KNOWN (type)
01909 && !CLASSTYPE_INTERFACE_ONLY (type))
01910 {
01911 mark_needed (decl);
01912 if (!flag_weak)
01913 {
01914 comdat_p = false;
01915 DECL_EXTERNAL (decl) = 0;
01916 }
01917 }
01918 }
01919 }
01920 else
01921 comdat_p = true;
01922 }
01923 else if (DECL_TEMPLATE_INSTANTIATION (decl)
01924 || DECL_FRIEND_PSEUDO_TEMPLATE_INSTANTIATION (decl))
01925 {
01926
01927
01928 if (flag_implicit_templates
01929 || (flag_implicit_inline_templates
01930 && TREE_CODE (decl) == FUNCTION_DECL
01931 && DECL_DECLARED_INLINE_P (decl)))
01932 comdat_p = true;
01933 else
01934
01935
01936 import_p = true;
01937 }
01938 else if (DECL_FUNCTION_MEMBER_P (decl))
01939 {
01940 if (!DECL_DECLARED_INLINE_P (decl))
01941 {
01942 tree ctype = DECL_CONTEXT (decl);
01943 import_export_class (ctype);
01944 if (CLASSTYPE_INTERFACE_KNOWN (ctype))
01945 {
01946 DECL_NOT_REALLY_EXTERN (decl)
01947 = ! (CLASSTYPE_INTERFACE_ONLY (ctype)
01948 || (DECL_DECLARED_INLINE_P (decl)
01949 && ! flag_implement_inlines
01950 && !DECL_VINDEX (decl)));
01951
01952 if (!DECL_NOT_REALLY_EXTERN (decl))
01953 DECL_EXTERNAL (decl) = 1;
01954
01955
01956 if (DECL_ARTIFICIAL (decl) && flag_weak)
01957 comdat_p = true;
01958 else
01959 maybe_make_one_only (decl);
01960 }
01961 }
01962 else
01963 comdat_p = true;
01964 }
01965 else
01966 comdat_p = true;
01967
01968 if (import_p)
01969 {
01970
01971
01972 DECL_EXTERNAL (decl) = 1;
01973 DECL_NOT_REALLY_EXTERN (decl) = 0;
01974 }
01975 else if (comdat_p)
01976 {
01977
01978
01979 comdat_linkage (decl);
01980 }
01981
01982 DECL_INTERFACE_KNOWN (decl) = 1;
01983 }
01984
01985
01986
01987
01988
01989 tree
01990 build_cleanup (tree decl)
01991 {
01992 tree temp;
01993 tree type = TREE_TYPE (decl);
01994
01995
01996
01997 gcc_assert (!TYPE_HAS_TRIVIAL_DESTRUCTOR (type));
01998
01999
02000
02001 mark_used (decl);
02002
02003 if (TREE_CODE (type) == ARRAY_TYPE)
02004 temp = decl;
02005 else
02006 {
02007 cxx_mark_addressable (decl);
02008 temp = build1 (ADDR_EXPR, build_pointer_type (type), decl);
02009 }
02010 temp = build_delete (TREE_TYPE (temp), temp,
02011 sfk_complete_destructor,
02012 LOOKUP_NORMAL|LOOKUP_NONVIRTUAL|LOOKUP_DESTRUCTOR, 0);
02013 return temp;
02014 }
02015
02016
02017
02018
02019 tree
02020 get_guard (tree decl)
02021 {
02022 tree sname;
02023 tree guard;
02024
02025 sname = mangle_guard_variable (decl);
02026 guard = IDENTIFIER_GLOBAL_VALUE (sname);
02027 if (! guard)
02028 {
02029 tree guard_type;
02030
02031
02032
02033 guard_type = targetm.cxx.guard_type ();
02034 guard = build_decl (VAR_DECL, sname, guard_type);
02035
02036
02037 TREE_PUBLIC (guard) = TREE_PUBLIC (decl);
02038 TREE_STATIC (guard) = TREE_STATIC (decl);
02039 DECL_COMMON (guard) = DECL_COMMON (decl);
02040 DECL_ONE_ONLY (guard) = DECL_ONE_ONLY (decl);
02041 if (TREE_PUBLIC (decl))
02042 DECL_WEAK (guard) = DECL_WEAK (decl);
02043
02044 DECL_ARTIFICIAL (guard) = 1;
02045 DECL_IGNORED_P (guard) = 1;
02046 TREE_USED (guard) = 1;
02047 pushdecl_top_level_and_finish (guard, NULL_TREE);
02048 }
02049 return guard;
02050 }
02051
02052
02053
02054
02055 static tree
02056 get_guard_bits (tree guard)
02057 {
02058 if (!targetm.cxx.guard_mask_bit ())
02059 {
02060
02061
02062 guard = build1 (ADDR_EXPR,
02063 build_pointer_type (TREE_TYPE (guard)),
02064 guard);
02065 guard = build1 (NOP_EXPR,
02066 build_pointer_type (char_type_node),
02067 guard);
02068 guard = build1 (INDIRECT_REF, char_type_node, guard);
02069 }
02070
02071 return guard;
02072 }
02073
02074
02075
02076
02077 tree
02078 get_guard_cond (tree guard)
02079 {
02080 tree guard_value;
02081
02082
02083 guard = get_guard_bits (guard);
02084
02085
02086 if (targetm.cxx.guard_mask_bit ())
02087 {
02088 guard_value = integer_one_node;
02089 if (!same_type_p (TREE_TYPE (guard_value), TREE_TYPE (guard)))
02090 guard_value = convert (TREE_TYPE (guard), guard_value);
02091 guard = cp_build_binary_op (BIT_AND_EXPR, guard, guard_value);
02092 }
02093
02094 guard_value = integer_zero_node;
02095 if (!same_type_p (TREE_TYPE (guard_value), TREE_TYPE (guard)))
02096 guard_value = convert (TREE_TYPE (guard), guard_value);
02097 return cp_build_binary_op (EQ_EXPR, guard, guard_value);
02098 }
02099
02100
02101
02102
02103 tree
02104 set_guard (tree guard)
02105 {
02106 tree guard_init;
02107
02108
02109 guard = get_guard_bits (guard);
02110 guard_init = integer_one_node;
02111 if (!same_type_p (TREE_TYPE (guard_init), TREE_TYPE (guard)))
02112 guard_init = convert (TREE_TYPE (guard), guard_init);
02113 return build_modify_expr (guard, NOP_EXPR, guard_init);
02114 }
02115
02116
02117
02118
02119 static tree
02120 start_objects (int method_type, int initp)
02121 {
02122 tree body;
02123 tree fndecl;
02124 char type[10];
02125
02126
02127
02128 if (initp != DEFAULT_INIT_PRIORITY)
02129 {
02130 char joiner;
02131
02132 #ifdef JOINER
02133 joiner = JOINER;
02134 #else
02135 joiner = '_';
02136 #endif
02137
02138 sprintf (type, "%c%c%.5u", method_type, joiner, initp);
02139 }
02140 else
02141 sprintf (type, "%c", method_type);
02142
02143 fndecl = build_lang_decl (FUNCTION_DECL,
02144 get_file_function_name_long (type),
02145 build_function_type (void_type_node,
02146 void_list_node));
02147 start_preparsed_function (fndecl, NULL_TREE, SF_PRE_PARSED);
02148
02149
02150
02151 TREE_PUBLIC (current_function_decl) = ! targetm.have_ctors_dtors;
02152
02153
02154 TREE_USED (current_function_decl) = 1;
02155
02156
02157 if (method_type == 'I')
02158 DECL_GLOBAL_CTOR_P (current_function_decl) = 1;
02159 else
02160 DECL_GLOBAL_DTOR_P (current_function_decl) = 1;
02161 DECL_LANG_SPECIFIC (current_function_decl)->decl_flags.u2sel = 1;
02162
02163 body = begin_compound_stmt (BCS_FN_BODY);
02164
02165
02166
02167
02168
02169 DECL_INLINE (current_function_decl) = 0;
02170 DECL_UNINLINABLE (current_function_decl) = 1;
02171
02172 return body;
02173 }
02174
02175
02176
02177
02178 static void
02179 finish_objects (int method_type, int initp, tree body)
02180 {
02181 tree fn;
02182
02183
02184 finish_compound_stmt (body);
02185 fn = finish_function (0);
02186 expand_or_defer_fn (fn);
02187
02188
02189
02190
02191 if (flag_syntax_only)
02192 return;
02193
02194 if (targetm.have_ctors_dtors)
02195 {
02196 rtx fnsym = XEXP (DECL_RTL (fn), 0);
02197 if (method_type == 'I')
02198 (* targetm.asm_out.constructor) (fnsym, initp);
02199 else
02200 (* targetm.asm_out.destructor) (fnsym, initp);
02201 }
02202 }
02203
02204
02205
02206
02207 #define INITIALIZE_P_IDENTIFIER "__initialize_p"
02208 #define PRIORITY_IDENTIFIER "__priority"
02209
02210
02211
02212 #define SSDF_IDENTIFIER "__static_initialization_and_destruction"
02213
02214
02215 static GTY(()) tree initialize_p_decl;
02216
02217
02218 static GTY(()) tree priority_decl;
02219
02220
02221 static GTY(()) tree ssdf_decl;
02222
02223
02224
02225 static GTY(()) varray_type ssdf_decls;
02226
02227
02228
02229
02230 static splay_tree priority_info_map;
02231
02232
02233
02234
02235
02236
02237
02238
02239
02240
02241
02242
02243
02244 static tree
02245 start_static_storage_duration_function (unsigned count)
02246 {
02247 tree parm_types;
02248 tree type;
02249 tree body;
02250 char id[sizeof (SSDF_IDENTIFIER) + 1 + 32];
02251
02252
02253
02254 sprintf (id, "%s_%u", SSDF_IDENTIFIER, count);
02255
02256
02257 parm_types = void_list_node;
02258 parm_types = tree_cons (NULL_TREE, integer_type_node, parm_types);
02259 parm_types = tree_cons (NULL_TREE, integer_type_node, parm_types);
02260 type = build_function_type (void_type_node, parm_types);
02261
02262
02263 ssdf_decl = build_lang_decl (FUNCTION_DECL,
02264 get_identifier (id),
02265 type);
02266 TREE_PUBLIC (ssdf_decl) = 0;
02267 DECL_ARTIFICIAL (ssdf_decl) = 1;
02268
02269
02270
02271 if (!ssdf_decls)
02272 {
02273 VARRAY_TREE_INIT (ssdf_decls, 32, "ssdf_decls");
02274
02275
02276
02277 priority_info_map = splay_tree_new (splay_tree_compare_ints,
02278 0,
02279
02280 (splay_tree_delete_value_fn) &free);
02281
02282
02283
02284
02285
02286 get_priority_info (DEFAULT_INIT_PRIORITY);
02287 }
02288
02289 VARRAY_PUSH_TREE (ssdf_decls, ssdf_decl);
02290
02291
02292 initialize_p_decl = cp_build_parm_decl
02293 (get_identifier (INITIALIZE_P_IDENTIFIER), integer_type_node);
02294 DECL_CONTEXT (initialize_p_decl) = ssdf_decl;
02295 TREE_USED (initialize_p_decl) = 1;
02296 priority_decl = cp_build_parm_decl
02297 (get_identifier (PRIORITY_IDENTIFIER), integer_type_node);
02298 DECL_CONTEXT (priority_decl) = ssdf_decl;
02299 TREE_USED (priority_decl) = 1;
02300
02301 TREE_CHAIN (initialize_p_decl) = priority_decl;
02302 DECL_ARGUMENTS (ssdf_decl) = initialize_p_decl;
02303
02304
02305 pushdecl (ssdf_decl);
02306
02307
02308
02309
02310
02311
02312
02313
02314 start_preparsed_function (ssdf_decl,
02315 NULL_TREE,
02316 SF_PRE_PARSED);
02317
02318
02319 body = begin_compound_stmt (BCS_FN_BODY);
02320
02321
02322
02323 DECL_INLINE (ssdf_decl) = 0;
02324 DECL_UNINLINABLE (ssdf_decl) = 1;
02325
02326 return body;
02327 }
02328
02329
02330
02331
02332
02333 static void
02334 finish_static_storage_duration_function (tree body)
02335 {
02336
02337 finish_compound_stmt (body);
02338 expand_or_defer_fn (finish_function (0));
02339 }
02340
02341
02342
02343
02344
02345 static priority_info
02346 get_priority_info (int priority)
02347 {
02348 priority_info pi;
02349 splay_tree_node n;
02350
02351 n = splay_tree_lookup (priority_info_map,
02352 (splay_tree_key) priority);
02353 if (!n)
02354 {
02355
02356
02357 pi = xmalloc (sizeof (struct priority_info_s));
02358 pi->initializations_p = 0;
02359 pi->destructions_p = 0;
02360 splay_tree_insert (priority_info_map,
02361 (splay_tree_key) priority,
02362 (splay_tree_value) pi);
02363 }
02364 else
02365 pi = (priority_info) n->value;
02366
02367 return pi;
02368 }
02369
02370
02371
02372
02373
02374 static tree
02375 start_static_initialization_or_destruction (tree decl, int initp)
02376 {
02377 tree guard_if_stmt = NULL_TREE;
02378 int priority;
02379 tree cond;
02380 tree guard;
02381 tree init_cond;
02382 priority_info pi;
02383
02384
02385 priority = DECL_INIT_PRIORITY (decl);
02386 if (!priority)
02387 priority = DEFAULT_INIT_PRIORITY;
02388
02389
02390
02391 pi = get_priority_info (priority);
02392 if (initp)
02393 pi->initializations_p = 1;
02394 else
02395 pi->destructions_p = 1;
02396
02397
02398
02399
02400
02401 input_location = DECL_SOURCE_LOCATION (decl);
02402
02403
02404
02405
02406
02407
02408
02409
02410
02411
02412
02413
02414
02415 if (member_p (decl))
02416 {
02417 DECL_CONTEXT (current_function_decl) = DECL_CONTEXT (decl);
02418 DECL_STATIC_FUNCTION_P (current_function_decl) = 1;
02419 }
02420
02421
02422
02423 guard_if_stmt = begin_if_stmt ();
02424 cond = cp_build_binary_op (EQ_EXPR,
02425 priority_decl,
02426 build_int_cst (NULL_TREE, priority));
02427 init_cond = initp ? integer_one_node : integer_zero_node;
02428 init_cond = cp_build_binary_op (EQ_EXPR,
02429 initialize_p_decl,
02430 init_cond);
02431 cond = cp_build_binary_op (TRUTH_ANDIF_EXPR, cond, init_cond);
02432
02433
02434 guard = NULL_TREE;
02435
02436
02437
02438
02439 if (TREE_PUBLIC (decl) && (DECL_COMMON (decl)
02440 || DECL_ONE_ONLY (decl)
02441 || DECL_WEAK (decl)))
02442 {
02443 tree guard_cond;
02444
02445 guard = get_guard (decl);
02446
02447
02448
02449 if (flag_use_cxa_atexit)
02450 {
02451
02452
02453 gcc_assert (initp);
02454 guard_cond = get_guard_cond (guard);
02455 }
02456
02457
02458
02459
02460
02461
02462
02463 else if (initp)
02464 guard_cond
02465 = cp_build_binary_op (EQ_EXPR,
02466 build_unary_op (PREINCREMENT_EXPR,
02467 guard,
02468 1),
02469 integer_one_node);
02470 else
02471 guard_cond
02472 = cp_build_binary_op (EQ_EXPR,
02473 build_unary_op (PREDECREMENT_EXPR,
02474 guard,
02475 1),
02476 integer_zero_node);
02477
02478 cond = cp_build_binary_op (TRUTH_ANDIF_EXPR, cond, guard_cond);
02479 }
02480
02481 finish_if_stmt_cond (cond, guard_if_stmt);
02482
02483
02484
02485 if (guard && initp && flag_use_cxa_atexit)
02486 finish_expr_stmt (set_guard (guard));
02487
02488 return guard_if_stmt;
02489 }
02490
02491
02492
02493
02494
02495 static void
02496 finish_static_initialization_or_destruction (tree guard_if_stmt)
02497 {
02498 finish_then_clause (guard_if_stmt);
02499 finish_if_stmt (guard_if_stmt);
02500
02501
02502
02503 DECL_CONTEXT (current_function_decl) = NULL_TREE;
02504 DECL_STATIC_FUNCTION_P (current_function_decl) = 0;
02505 }
02506
02507
02508
02509
02510 static void
02511 do_static_initialization (tree decl, tree init)
02512 {
02513 tree guard_if_stmt;
02514
02515
02516 guard_if_stmt
02517 = start_static_initialization_or_destruction (decl,
02518 1);
02519
02520
02521 if (init)
02522 finish_expr_stmt (init);
02523
02524
02525
02526 if (flag_use_cxa_atexit)
02527 finish_expr_stmt (register_dtor_fn (decl));
02528
02529
02530 finish_static_initialization_or_destruction (guard_if_stmt);
02531 }
02532
02533
02534
02535
02536
02537
02538 static void
02539 do_static_destruction (tree decl)
02540 {
02541 tree guard_if_stmt;
02542
02543
02544
02545 gcc_assert (!flag_use_cxa_atexit);
02546
02547
02548 if (TYPE_HAS_TRIVIAL_DESTRUCTOR (TREE_TYPE (decl)))
02549 return;
02550
02551
02552 guard_if_stmt = start_static_initialization_or_destruction (decl,
02553 0);
02554 finish_expr_stmt (build_cleanup (decl));
02555 finish_static_initialization_or_destruction (guard_if_stmt);
02556 }
02557
02558
02559
02560
02561
02562
02563
02564
02565
02566 static tree
02567 prune_vars_needing_no_initialization (tree *vars)
02568 {
02569 tree *var = vars;
02570 tree result = NULL_TREE;
02571
02572 while (*var)
02573 {
02574 tree t = *var;
02575 tree decl = TREE_VALUE (t);
02576 tree init = TREE_PURPOSE (t);
02577
02578
02579 if (decl == error_mark_node)
02580 {
02581 var = &TREE_CHAIN (t);
02582 continue;
02583 }
02584
02585
02586 gcc_assert (TREE_CODE (decl) == VAR_DECL);
02587
02588
02589
02590 if (DECL_EXTERNAL (decl))
02591 {
02592 var = &TREE_CHAIN (t);
02593 continue;
02594 }
02595
02596
02597
02598 if (init && TREE_CODE (init) == TREE_LIST
02599 && value_member (error_mark_node, init))
02600 {
02601 var = &TREE_CHAIN (t);
02602 continue;
02603 }
02604
02605
02606
02607 *var = TREE_CHAIN (t);
02608 TREE_CHAIN (t) = result;
02609 result = t;
02610 }
02611
02612 return result;
02613 }
02614
02615
02616
02617
02618 static void
02619 write_out_vars (tree vars)
02620 {
02621 tree v;
02622
02623 for (v = vars; v; v = TREE_CHAIN (v))
02624 {
02625 tree var = TREE_VALUE (v);
02626 if (!var_finalized_p (var))
02627 {
02628 import_export_decl (var);
02629 rest_of_decl_compilation (var, 1, 1);
02630 }
02631 }
02632 }
02633
02634
02635
02636
02637
02638 static void
02639 generate_ctor_or_dtor_function (bool constructor_p, int priority,
02640 location_t *locus)
02641 {
02642 char function_key;
02643 tree arguments;
02644 tree fndecl;
02645 tree body;
02646 size_t i;
02647
02648 input_location = *locus;
02649 #ifdef USE_MAPPED_LOCATION
02650
02651 #else
02652 locus->line++;
02653 #endif
02654
02655
02656
02657 function_key = constructor_p ? 'I' : 'D';
02658
02659
02660
02661 body = NULL_TREE;
02662
02663
02664
02665 if (ssdf_decls)
02666 for (i = 0; i < ssdf_decls->elements_used; ++i)
02667 {
02668 fndecl = VARRAY_TREE (ssdf_decls, i);
02669
02670
02671 if (! (flags_from_decl_or_type (fndecl) & (ECF_CONST | ECF_PURE)))
02672 {
02673 if (! body)
02674 body = start_objects (function_key, priority);
02675
02676 arguments = tree_cons (NULL_TREE,
02677 build_int_cst (NULL_TREE, priority),
02678 NULL_TREE);
02679 arguments = tree_cons (NULL_TREE,
02680 build_int_cst (NULL_TREE, constructor_p),
02681 arguments);
02682 finish_expr_stmt (build_function_call (fndecl, arguments));
02683 }
02684 }
02685
02686
02687
02688
02689 if (priority == DEFAULT_INIT_PRIORITY)
02690 {
02691 tree fns;
02692
02693 for (fns = constructor_p ? static_ctors : static_dtors;
02694 fns;
02695 fns = TREE_CHAIN (fns))
02696 {
02697 fndecl = TREE_VALUE (fns);
02698
02699
02700 if (! (flags_from_decl_or_type (fndecl) & (ECF_CONST | ECF_PURE)))
02701 {
02702 if (! body)
02703 body = start_objects (function_key, priority);
02704 finish_expr_stmt (build_function_call (fndecl, NULL_TREE));
02705 }
02706 }
02707 }
02708
02709
02710 if (body)
02711 finish_objects (function_key, priority, body);
02712 }
02713
02714
02715
02716
02717 static int
02718 generate_ctor_and_dtor_functions_for_priority (splay_tree_node n, void * data)
02719 {
02720 location_t *locus = data;
02721 int priority = (int) n->key;
02722 priority_info pi = (priority_info) n->value;
02723
02724
02725
02726 if (pi->initializations_p
02727 || (priority == DEFAULT_INIT_PRIORITY && static_ctors))
02728 generate_ctor_or_dtor_function (true, priority, locus);
02729 if (pi->destructions_p
02730 || (priority == DEFAULT_INIT_PRIORITY && static_dtors))
02731 generate_ctor_or_dtor_function (false, priority, locus);
02732
02733
02734 return 0;
02735 }
02736
02737
02738
02739
02740
02741
02742
02743 tree
02744 cxx_callgraph_analyze_expr (tree *tp, int *walk_subtrees ATTRIBUTE_UNUSED,
02745 tree from ATTRIBUTE_UNUSED)
02746 {
02747 tree t = *tp;
02748
02749 switch (TREE_CODE (t))
02750 {
02751 case PTRMEM_CST:
02752 if (TYPE_PTRMEMFUNC_P (TREE_TYPE (t)))
02753 cgraph_mark_needed_node (cgraph_node (PTRMEM_CST_MEMBER (t)));
02754 break;
02755 case BASELINK:
02756 if (TREE_CODE (BASELINK_FUNCTIONS (t)) == FUNCTION_DECL)
02757 cgraph_mark_needed_node (cgraph_node (BASELINK_FUNCTIONS (t)));
02758 break;
02759 case VAR_DECL:
02760 if (DECL_VTABLE_OR_VTT_P (t))
02761 {
02762
02763
02764 tree vtbl;
02765 for (vtbl = CLASSTYPE_VTABLES (DECL_CONTEXT (t));
02766 vtbl;
02767 vtbl = TREE_CHAIN (vtbl))
02768 mark_decl_referenced (vtbl);
02769 }
02770 else if (DECL_CONTEXT (t)
02771 && TREE_CODE (DECL_CONTEXT (t)) == FUNCTION_DECL)
02772
02773
02774 mark_decl_referenced (DECL_CONTEXT (t));
02775 break;
02776 default:
02777 break;
02778 }
02779
02780 return NULL;
02781 }
02782
02783 #ifdef KEY
02784 extern int processing_global_namespace;
02785 #endif
02786
02787
02788
02789
02790
02791
02792 void
02793 cp_finish_file (void)
02794 {
02795 tree vars;
02796 bool reconsider;
02797 size_t i;
02798 location_t locus;
02799 unsigned ssdf_count = 0;
02800 int retries = 0;
02801
02802 locus = input_location;
02803 at_eof = 1;
02804
02805
02806 if (! global_bindings_p () || current_class_type || decl_namespace_list)
02807 return;
02808
02809 if (pch_file)
02810 c_common_write_pch ();
02811
02812 #ifdef USE_MAPPED_LOCATION
02813
02814 #else
02815
02816
02817 input_line -= 1;
02818 #endif
02819
02820
02821
02822
02823
02824
02825
02826
02827
02828
02829
02830
02831
02832
02833
02834
02835
02836 timevar_push (TV_VARCONST);
02837
02838 emit_support_tinfos ();
02839
02840 do
02841 {
02842 tree t;
02843
02844 reconsider = false;
02845
02846
02847
02848 instantiate_pending_templates (retries);
02849 ggc_collect ();
02850
02851
02852
02853
02854
02855
02856
02857 while (keyed_classes != NULL_TREE
02858 && maybe_emit_vtables (TREE_VALUE (keyed_classes)))
02859 {
02860 reconsider = true;
02861 keyed_classes = TREE_CHAIN (keyed_classes);
02862 }
02863
02864 t = keyed_classes;
02865 if (t != NULL_TREE)
02866 {
02867 tree next = TREE_CHAIN (t);
02868
02869 while (next)
02870 {
02871 if (maybe_emit_vtables (TREE_VALUE (next)))
02872 {
02873 reconsider = true;
02874 TREE_CHAIN (t) = TREE_CHAIN (next);
02875 }
02876 else
02877 t = next;
02878
02879 next = TREE_CHAIN (t);
02880 }
02881 }
02882
02883
02884
02885
02886
02887
02888 for (i = VEC_length (tree, unemitted_tinfo_decls);
02889 VEC_iterate (tree, unemitted_tinfo_decls, --i, t);)
02890 if (emit_tinfo_decl (t))
02891 {
02892 reconsider = true;
02893 VEC_unordered_remove (tree, unemitted_tinfo_decls, i);
02894 }
02895
02896
02897
02898
02899
02900
02901 vars = prune_vars_needing_no_initialization (&static_aggregates);
02902
02903 if (vars)
02904 {
02905 tree v;
02906
02907
02908
02909
02910
02911
02912
02913
02914 tree ssdf_body;
02915
02916
02917
02918 input_location = locus;
02919 ssdf_body = start_static_storage_duration_function (ssdf_count);
02920
02921
02922 write_out_vars (vars);
02923
02924
02925 for (v = vars; v; v = TREE_CHAIN (v))
02926 do_static_initialization (TREE_VALUE (v),
02927 TREE_PURPOSE (v));
02928
02929
02930
02931
02932
02933
02934
02935 if (!flag_use_cxa_atexit)
02936 {
02937 vars = nreverse (vars);
02938 for (v = vars; v; v = TREE_CHAIN (v))
02939 do_static_destruction (TREE_VALUE (v));
02940 }
02941 else
02942 vars = NULL_TREE;
02943
02944
02945
02946 input_location = locus;
02947 finish_static_storage_duration_function (ssdf_body);
02948
02949
02950
02951
02952 reconsider = true;
02953 ssdf_count++;
02954 #ifdef USE_MAPPED_LOCATION
02955
02956 #else
02957 locus.line++;
02958 #endif
02959 }
02960
02961
02962
02963
02964 for (i = 0; i < deferred_fns_used; ++i)
02965 {
02966 tree decl = VARRAY_TREE (deferred_fns, i);
02967
02968
02969 if (DECL_ARTIFICIAL (decl) && ! DECL_INITIAL (decl)
02970 && (! DECL_REALLY_EXTERN (decl) || DECL_INLINE (decl)))
02971 {
02972
02973
02974
02975
02976
02977 push_to_top_level ();
02978
02979
02980
02981 input_location = DECL_SOURCE_LOCATION (decl);
02982 synthesize_method (decl);
02983 pop_from_top_level ();
02984 reconsider = true;
02985 }
02986
02987 if (!DECL_SAVED_TREE (decl))
02988 continue;
02989
02990 import_export_decl (decl);
02991
02992
02993
02994
02995
02996
02997
02998
02999
03000
03001
03002 if (DECL_NOT_REALLY_EXTERN (decl)
03003 && DECL_INITIAL (decl)
03004 && decl_needed_p (decl))
03005 DECL_EXTERNAL (decl) = 0;
03006
03007 #ifdef KEY
03008 if (flag_spin_file && gspin_invoked(decl))
03009 gs_set_flag_value (decl, GS_DECL_EXTERNAL, DECL_EXTERNAL(decl));
03010 #endif
03011
03012
03013
03014
03015
03016 if (!DECL_EXTERNAL (decl)
03017 && decl_needed_p (decl)
03018 && !TREE_ASM_WRITTEN (decl)
03019 && !cgraph_node (decl)->local.finalized)
03020 {
03021
03022
03023 DECL_DEFER_OUTPUT (decl) = 0;
03024
03025
03026 expand_or_defer_fn (decl);
03027
03028
03029
03030 if (flag_syntax_only)
03031 TREE_ASM_WRITTEN (decl) = 1;
03032 reconsider = true;
03033 #ifdef KEY
03034
03035
03036 if (flag_spin_file)
03037 gspin_gxx_emits_decl (decl);
03038 #endif
03039 }
03040 }
03041
03042 if (walk_namespaces (wrapup_globals_for_namespace, 0))
03043 reconsider = true;
03044
03045
03046 for (i = 0; i < pending_statics_used; ++i)
03047 {
03048 tree decl = VARRAY_TREE (pending_statics, i);
03049 if (var_finalized_p (decl) || DECL_REALLY_EXTERN (decl))
03050 continue;
03051 import_export_decl (decl);
03052
03053
03054 if (DECL_NOT_REALLY_EXTERN (decl) && decl_needed_p (decl))
03055 DECL_EXTERNAL (decl) = 0;
03056 }
03057 if (pending_statics
03058 && wrapup_global_declarations (&VARRAY_TREE (pending_statics, 0),
03059 pending_statics_used))
03060 reconsider = true;
03061
03062
03063
03064
03065 if (cgraph_assemble_pending_functions ())
03066 reconsider = true;
03067 if (cgraph_varpool_assemble_pending_decls ())
03068 reconsider = true;
03069
03070 retries++;
03071 }
03072 while (reconsider);
03073
03074
03075 for (i = 0; i < deferred_fns_used; ++i)
03076 {
03077 tree decl = VARRAY_TREE (deferred_fns, i);
03078
03079 if (
03080 TREE_USED (decl) && DECL_DECLARED_INLINE_P (decl)
03081
03082 && DECL_REALLY_EXTERN (decl)
03083
03084
03085
03086
03087
03088
03089 && !flag_use_repository
03090
03091
03092
03093 && !DECL_EXPLICIT_INSTANTIATION (decl))
03094 {
03095 cp_warning_at ("inline function %qD used but never defined", decl);
03096
03097
03098
03099 TREE_PUBLIC (decl) = 1;
03100 }
03101 }
03102
03103
03104 push_lang_context (lang_name_c);
03105
03106
03107
03108 if (priority_info_map)
03109 splay_tree_foreach (priority_info_map,
03110 generate_ctor_and_dtor_functions_for_priority,
03111 &locus);
03112 else
03113 {
03114
03115 if (static_ctors)
03116 generate_ctor_or_dtor_function (true,
03117 DEFAULT_INIT_PRIORITY, &locus);
03118 if (static_dtors)
03119 generate_ctor_or_dtor_function (false,
03120 DEFAULT_INIT_PRIORITY, &locus);
03121 }
03122
03123
03124 if (priority_info_map)
03125 splay_tree_delete (priority_info_map);
03126
03127
03128 maybe_apply_pending_pragma_weaks ();
03129
03130
03131
03132 pop_lang_context ();
03133
03134 cgraph_finalize_compilation_unit ();
03135 cgraph_optimize ();
03136
03137
03138
03139 walk_namespaces (wrapup_globals_for_namespace, &reconsider);
03140 if (pending_statics)
03141 {
03142 check_global_declarations (&VARRAY_TREE (pending_statics, 0),
03143 pending_statics_used);
03144 emit_debug_global_declarations (&VARRAY_TREE (pending_statics, 0),
03145 pending_statics_used);
03146 }
03147
03148 finish_repo ();
03149
03150 #ifdef KEY
03151
03152 if (flag_spin_file)
03153 {
03154 static int spun_global_namespace = 0;
03155 if (!spun_global_namespace)
03156 {
03157 processing_global_namespace = 1;
03158 gspin (global_namespace);
03159
03160 processing_global_namespace = 0;
03161 spun_global_namespace = 1;
03162 }
03163 }
03164 #endif
03165
03166
03167
03168 {
03169 int flags;
03170 FILE *stream = dump_begin (TDI_tu, &flags);
03171
03172 if (stream)
03173 {
03174 dump_node (global_namespace, flags & ~TDF_SLIM, stream);
03175 dump_end (TDI_tu, stream);
03176 }
03177 }
03178
03179 timevar_pop (TV_VARCONST);
03180
03181 if (flag_detailed_statistics)
03182 {
03183 dump_tree_statistics ();
03184 dump_time_statistics ();
03185 }
03186 input_location = locus;
03187
03188 #ifdef ENABLE_CHECKING
03189 validate_conversion_obstack ();
03190 #endif
03191 }
03192
03193
03194
03195
03196
03197
03198 tree
03199 build_offset_ref_call_from_tree (tree fn, tree args)
03200 {
03201 tree orig_fn;
03202 tree orig_args;
03203 tree expr;
03204 tree object;
03205
03206 orig_fn = fn;
03207 orig_args = args;
03208 object = TREE_OPERAND (fn, 0);
03209
03210 if (processing_template_decl)
03211 {
03212 gcc_assert (TREE_CODE (fn) == DOTSTAR_EXPR
03213 || TREE_CODE (fn) == MEMBER_REF);
03214 if (type_dependent_expression_p (fn)
03215 || any_type_dependent_arguments_p (args))
03216 return build_min_nt (CALL_EXPR, fn, args, NULL_TREE);
03217
03218
03219
03220
03221 args = build_non_dependent_args (args);
03222 if (TREE_CODE (fn) == DOTSTAR_EXPR)
03223 object = build_unary_op (ADDR_EXPR, object, 0);
03224 object = build_non_dependent_expr (object);
03225 args = tree_cons (NULL_TREE, object, args);
03226
03227 fn = build_non_dependent_expr (fn);
03228 }
03229
03230
03231
03232
03233
03234
03235
03236 if (TREE_CODE (fn) == OFFSET_REF)
03237 {
03238 tree object_addr = build_unary_op (ADDR_EXPR, object, 0);
03239 fn = TREE_OPERAND (fn, 1);
03240 fn = get_member_function_from_ptrfunc (&object_addr, fn);
03241 args = tree_cons (NULL_TREE, object_addr, args);
03242 }
03243
03244 expr = build_function_call (fn, args);
03245 if (processing_template_decl && expr != error_mark_node)
03246 return build_min_non_dep (CALL_EXPR, expr, orig_fn, orig_args, NULL_TREE);
03247 return expr;
03248 }
03249
03250
03251 void
03252 check_default_args (tree x)
03253 {
03254 tree arg = TYPE_ARG_TYPES (TREE_TYPE (x));
03255 bool saw_def = false;
03256 int i = 0 - (TREE_CODE (TREE_TYPE (x)) == METHOD_TYPE);
03257 for (; arg && arg != void_list_node; arg = TREE_CHAIN (arg), ++i)
03258 {
03259 if (TREE_PURPOSE (arg))
03260 saw_def = true;
03261 else if (saw_def)
03262 {
03263 cp_error_at ("default argument missing for parameter %P of %q+#D",
03264 i, x);
03265 break;
03266 }
03267 }
03268 }
03269
03270
03271
03272
03273 void
03274 mark_used (tree decl)
03275 {
03276 HOST_WIDE_INT saved_processing_template_decl = 0;
03277
03278 TREE_USED (decl) = 1;
03279
03280 if (skip_evaluation)
03281 return;
03282
03283
03284
03285
03286 if (processing_template_decl)
03287 {
03288 if (TREE_CODE (decl) == VAR_DECL
03289 && DECL_INITIALIZED_BY_CONSTANT_EXPRESSION_P (decl)
03290 && DECL_CLASS_SCOPE_P (decl)
03291 && !dependent_type_p (DECL_CONTEXT (decl)))
03292 {
03293
03294
03295
03296 saved_processing_template_decl = processing_template_decl;
03297 processing_template_decl = 0;
03298 }
03299 else
03300 return;
03301 }
03302
03303 if (TREE_CODE (decl) == FUNCTION_DECL && DECL_DECLARED_INLINE_P (decl)
03304 && !TREE_ASM_WRITTEN (decl))
03305
03306 {
03307 if (DECL_DEFERRED_FN (decl))
03308 return;
03309
03310
03311
03312
03313 if (DECL_ARTIFICIAL (decl) && DECL_NONSTATIC_MEMBER_FUNCTION_P (decl)
03314 && !DECL_THUNK_P (decl))
03315 DECL_SOURCE_LOCATION (decl) = input_location;
03316
03317 note_vague_linkage_fn (decl);
03318 }
03319
03320 assemble_external (decl);
03321
03322
03323 if (TREE_CODE (decl) == FUNCTION_DECL
03324 && DECL_NONSTATIC_MEMBER_FUNCTION_P (decl)
03325 && DECL_ARTIFICIAL (decl)
03326 && !DECL_THUNK_P (decl)
03327 && ! DECL_INITIAL (decl)
03328
03329
03330
03331
03332 && current_function_decl)
03333 {
03334 synthesize_method (decl);
03335
03336
03337 return;
03338 }
03339
03340
03341
03342
03343
03344 if ((DECL_NON_THUNK_FUNCTION_P (decl) || TREE_CODE (decl) == VAR_DECL)
03345 && DECL_LANG_SPECIFIC (decl) && DECL_TEMPLATE_INFO (decl)
03346 && (!DECL_EXPLICIT_INSTANTIATION (decl)
03347 || (TREE_CODE (decl) == FUNCTION_DECL
03348 && DECL_INLINE (DECL_TEMPLATE_RESULT
03349 (template_for_substitution (decl))))
03350
03351
03352
03353 || (TREE_CODE (decl) == VAR_DECL
03354 && DECL_INITIALIZED_BY_CONSTANT_EXPRESSION_P (decl))))
03355
03356
03357
03358
03359 instantiate_decl (decl, true, 0);
03360
03361 processing_template_decl = saved_processing_template_decl;
03362 }
03363
03364 #include "gt-cp-decl2.h"