From 3f73d6ef90458b45bbbb33ef4c2b174d4662a22d Mon Sep 17 00:00:00 2001 From: Jing Yu Date: Wed, 15 Feb 2012 15:40:16 -0800 Subject: Sync down FSF r184235@google/gcc-4_6_2-mobile branch 1) Get mostly new patches from FSF gcc-4.6 branch 2) Fix PR52129 3) Insert GNU-stack note for all ARM targets Change-Id: I2b9926981210e517e4021242908074319a91d6bd --- gcc-4.6/gcc/cp/ChangeLog | 285 ++++++++++++++++++++++++++++++++++++ gcc-4.6/gcc/cp/ChangeLog.google-4_6 | 82 +++++++++++ gcc-4.6/gcc/cp/call.c | 50 ++++--- gcc-4.6/gcc/cp/class.c | 87 +++++++++-- gcc-4.6/gcc/cp/cp-tree.h | 1 + gcc-4.6/gcc/cp/decl.c | 83 ++++++++--- gcc-4.6/gcc/cp/error.c | 20 +-- gcc-4.6/gcc/cp/init.c | 38 +++-- gcc-4.6/gcc/cp/mangle.c | 11 +- gcc-4.6/gcc/cp/method.c | 5 +- gcc-4.6/gcc/cp/name-lookup.c | 5 +- gcc-4.6/gcc/cp/parser.c | 50 +++---- gcc-4.6/gcc/cp/pt.c | 204 +++++++++++++++----------- gcc-4.6/gcc/cp/semantics.c | 61 ++++++-- gcc-4.6/gcc/cp/tree.c | 12 +- gcc-4.6/gcc/cp/typeck.c | 22 ++- gcc-4.6/gcc/cp/typeck2.c | 12 +- 17 files changed, 817 insertions(+), 211 deletions(-) (limited to 'gcc-4.6/gcc/cp') diff --git a/gcc-4.6/gcc/cp/ChangeLog b/gcc-4.6/gcc/cp/ChangeLog index 229fc8ec4..1909c6961 100644 --- a/gcc-4.6/gcc/cp/ChangeLog +++ b/gcc-4.6/gcc/cp/ChangeLog @@ -1,8 +1,293 @@ +2011-12-20 Dodji Seketeli + + PR debug/49951 + * decl.c (cxx_maybe_build_cleanup): Don't set location of the call + to the destructor. + +2011-12-16 Jason Merrill + + PR c++/51416 + * init.c (build_value_init_noctor): Check for incomplete type. + +2011-12-16 Jason Merrill + + PR c++/51331 + * class.c (convert_to_base_statically): Just call + build_simple_base_path. + (build_simple_base_path): Check field offset. + +2011-12-14 Jason Merrill + + PR c++/51248 + * decl.c (copy_type_enum): Also update variants. + (finish_enum): Allow variants of complete enums. + +2011-12-13 Jason Merrill + + PR c++/51406 + PR c++/51161 + * typeck.c (build_static_cast_1): Fix cast of lvalue to + base rvalue reference. + +2011-11-22 Paolo Carlini + + PR c++/51265 + * semantics.c (finish_decltype_type): Handle PTRMEM_CST. + +2011-11-18 Paolo Carlini + + PR c++/51150 + * pt.c (tsubst_copy_and_build): Handle FIX_TRUNC_EXPR. + +2011-11-07 Jason Merrill + + PR c++/50870 + * pt.c (tsubst_copy): Handle NAMESPACE_DECL. + (tsubst_copy_and_build) [COMPONENT_REF]: Handle a still-dependent + object. + +2011-11-04 Eric Botcazou + + PR c++/50608 + * semantics.c (finish_offsetof): Adjust call to fold_offsetof. + * typeck.c (cp_build_addr_expr_1): Call fold_offsetof_1. + +2011-10-29 Paolo Carlini + + PR c++/50901 + * call.c (build_new_op_1): Handle ABS_EXPR together with the + other unary EXPR. + +2011-10-26 Release Manager + + * GCC 4.6.2 released. + +2011-10-19 Jason Merrill + + PR c++/50793 + * tree.c (bot_manip): Propagate AGGR_INIT_ZERO_FIRST. + +2011-10-19 Jason Merrill + + PR c++/50787 + * parser.c (cp_parser_initializer_clause): Don't call + maybe_constant_value here. + +2011-10-18 Jason Merrill + + PR c++/50531 + * pt.c (instantiate_decl): Recognize when a function defaulted + outside the class is already instantiated. + +2011-10-15 Nicola Pero + + Backport from mainline + 2011-06-06 Nicola Pero , + + PR obj-c++/48275 + * parser.c (cp_parser_objc_at_property_declaration): Allow setter + and getter names to use all the allowed method names. + +2011-10-13 Jason Merrill + + PR c++/50618 + * init.c (expand_aggr_init_1): Don't zero-initialize virtual + bases of a base subobject. + +2011-10-11 Jason Merrill + + PR c++/49216 + * init.c (build_vec_init): Avoid crash on new int[1]{}. + +2011-10-11 Janis Johnson + + PR c++/44473 + * mangle.c (write_type): Handle CV qualifiers for decimal classes. + +2011-10-11 Paolo Carlini + + PR c++/50611 + * pt.c (tsubst_copy_and_build): If (complain & tf_error) is false + do not call unqualified_name_lookup_error. + +2011-10-09 Jakub Jelinek + Diego Novillo + + * pt.c (reregister_specialization): Use htab_find instead of + htab_find_slot with INSERT. + +2011-09-26 Jason Merrill + + PR c++/46105 + * typeck.c (structural_comptypes): Ignore cv-quals on typename scope. + + PR c++/50508 + * semantics.c (cxx_eval_logical_expression): Use tree_int_cst_equal + rather than ==. + +2011-09-23 Jason Merrill + + Core 253 - allow const objects with no initializer or + user-provided default constructor if the defaulted constructor + initializes all the subobjects. + PR c++/20039 + PR c++/42844 + * class.c (default_init_uninitialized_part): New. + * cp-tree.h: Declare it. + * decl.c (check_for_uninitialized_const_var): Use it. + * init.c (perform_member_init): Likewise. + (build_new_1): Likewise. + * method.c (walk_field_subobs): Likewise. + +2011-09-22 Paolo Carlini + + PR c++/50491 + * semantics.c (potential_constant_expression_1): Handle USING_DECL. + +2011-09-17 Jason Merrill + + PR c++/50442 + Revert: + PR c++/49267 + * call.c (compare_ics): rvaluedness_matches_p can differ + based on the source type, not just target. + +2011-09-16 Jason Merrill + + PR c++/50424 + * tree.c (bot_manip): Set cp_function_chain->can_throw. + +2011-09-13 Dodji Seketeli + + PR c++/48320 + * pt.c (template_parameter_pack_p): Support TEMPLATE_PARM_INDEX + nodes. Add a comment. + (arg_from_parm_pack_p): New static function, factorized out from + tsubst_pack_expansion and extended to support non-type parameter + packs represented with TEMPLATE_PARM_INDEX nodes. + (tsubst_pack_expansion): Use arg_from_parm_pack_p. + +2011-09-08 Jakub Jelinek + + PR c++/50255 + * method.c (use_thunk): If emitting thunk into the same section + as function, use the same DECL_COMDAT_GROUP as well. + +2011-09-07 Paolo Carlini + + PR c++/50309 + * decl.c (grokdeclarator): Check u.function.exception_specification + for error_mark_node. + +2011-09-04 Jason Merrill + + PR c++/49267 + * call.c (compare_ics): rvaluedness_matches_p can differ + based on the source type, not just target. + +2011-08-29 Jakub Jelinek + Jason Merrill + + PR c++/50207 + * class.c (finish_struct_1): Complain if the first field is + artificial. + +2011-08-30 Jason Merrill + + PR c++/50089 + * semantics.c (finish_id_expression): Use + current_nonlambda_class_type for qualified-ids. + + PR c++/50220 + * semantics.c (add_capture): Call complete_type for copy. + + PR c++/50234 + * semantics.c (cxx_eval_component_reference): Handle + value-initialization for omitted initializers. + +2011-08-29 Jason Merrill + + PR c++/50224 + * semantics.c (finish_id_expression): Mark captured variables used. + +2011-08-25 Jason Merrill + + PR c++/50157 + * call.c (convert_like_real): Exit early if bad and !tf_error. + +2011-08-23 Jason Merrill + + PR c++/50024 + * semantics.c (maybe_constant_value): Don't try to fold { }. + * pt.c (build_non_dependent_expr): Don't wrap { }. + * init.c (build_value_init): Allow scalar value-init in templates. + +2011-08-23 Jakub Jelinek + + PR c++/46862 + * class.c (finish_struct_1): If TYPE_TRANSPARENT_AGGR is set on a type + which doesn't have any fields, clear it and diagnose. + +2011-08-16 Jason Merrill + + PR c++/50086 + * pt.c (unify_pack_expansion): Correct overloaded unification + logic. + + PR c++/50054 + * typeck2.c (cxx_incomplete_type_diagnostic): Handle + init_list_type_node. + +2011-08-12 David Li + + * class.c (update_vtable_entry_for_fn): Set + LOST_PRIMARY bit properly. + +2011-08-05 Jason Merrill + + PR c++/48993 + * semantics.c (potential_constant_expression_1) [CALL_EXPR]: Sorry + on 'this' in a constructor. + + PR c++/49921 + * semantics.c (finish_decltype_type): Call invalid_nonstatic_memfn_p. + + PR c++/49669 + * init.c (perform_member_init): Handle invalid array initializer. + + PR c++/49988 + * semantics.c (cxx_eval_array_reference): Handle failure to + reduce the array operand to something we can work with. + +2011-08-02 Jason Merrill + + PR c++/43886 + * parser.c (cp_parser_lambda_body): Clear local_variables_forbidden_p. + + PR c++/49593 + * pt.c (find_parameter_packs_r): Handle CONSTRUCTOR. + + PR c++/49803 + * init.c (sort_mem_initializers): Initialize uses_unions_p here. + (build_field_list): Not here. + + PR c++/49924 + * semantics.c (cxx_eval_vec_init_1): Fix logic. + + PR c++/49260 + * call.c (build_call_a): Set cp_function_chain->can_throw here. + (build_cxx_call): Not here. + 2011-07-27 Jeffrey Yasskin * pt.c (build_template_decl): Copy the function_decl's source location to the new template_decl. +2011-07-19 Jason Merrill + + PR c++/49785 + * pt.c (coerce_template_parms): Handle non-pack after pack. + 2011-07-11 Jason Merrill PR c++/49672 diff --git a/gcc-4.6/gcc/cp/ChangeLog.google-4_6 b/gcc-4.6/gcc/cp/ChangeLog.google-4_6 index 6f863d432..0137c1ba6 100644 --- a/gcc-4.6/gcc/cp/ChangeLog.google-4_6 +++ b/gcc-4.6/gcc/cp/ChangeLog.google-4_6 @@ -1,3 +1,85 @@ +2011-12-19 Sterling Augustine + + Backport from google/main + + * error.c (dump_decl): Reformat return value to "(anonymous namespace)". + (lang_decl_name): Return "(anonymous namespace)" when appropriate. + +2011-12-17 Easwaran Raman + Backport r182443 from google/main. + + 2011-12-17 Easwaran Raman + + * decl.c (cxx_init_decl_processing): Specify a function that + takes a void* and size_t for DELETE_EXPR. + * call.c (build_op_delete_call): If fsized-delete is used, use + the variant that takes size_t as the second parameter except + when deleteting a pointer of type void *. + +2011-12-06 Jeffrey Yasskin + + Backport from rev 180707 + + 2011-10-31 Jason Merrill + + PR c++/50920 + * class.c (check_field_decl): Change c++0x in diags to c++11. + * error.c (maybe_warn_cpp0x): Likewise. + * parser.c (cp_parser_diagnose_invalid_type_name): Likewise. + * pt.c (check_default_tmpl_args): Likewise. + +2011-11-18 Paolo Carlini + + PR c++/51150 + * pt.c (tsubst_copy_and_build): Handle FIX_TRUNC_EXPR. + +2011-11-02 Jeffrey Yasskin + + Backport from rev 176665 + + 2011-07-22 Jason Merrill + + PR c++/49793 + * typeck2.c (check_narrowing): Downgrade permerror to pedwarn. + Make conditional on -Wnarrowing. + +2011-10-28 Jeffrey Yasskin + + google ref 5514746; backport of r179121 + + Modified locally to only block static const literals in -pedantic + mode. + + 2011-09-23 Paolo Carlini + + PR c++/50258 + * decl.c (check_static_variable_definition): Allow in-class + initialization of static data member of non-integral type in + permissive mode. + +2011-09-29 DeLesley Hutchins + + * cp/parser.c (cp_parser_late_parsing_attribute_arg_lists) + fixed case where the potential clone is a template. + +2011-09-22 Paolo Carlini + + Backport r179110 from gcc-4_6-branch. + + * semantics.c (potential_constant_expression_1): Handle USING_DECL. + +2011-9-13 DeLesley Hutchins + + * class.c (cp_get_virtual_function_decl): bugfix where + type is uknown + +2011-08-18 Diego Novillo + + * name-lookup.c (lookup_arg_dependent): Use conditional + timevars. + * decl.c (xref_tag): Likewise. + * call.c (build_op_call): Likewise. + 2011-08-12 Xinliang David Li * class.c (update_vtable_entry_for_fn): Set lost_primary diff --git a/gcc-4.6/gcc/cp/call.c b/gcc-4.6/gcc/cp/call.c index 700e2d655..b292f26e1 100644 --- a/gcc-4.6/gcc/cp/call.c +++ b/gcc-4.6/gcc/cp/call.c @@ -355,6 +355,9 @@ build_call_a (tree function, int n, tree *argarray) nothrow = ((decl && TREE_NOTHROW (decl)) || TYPE_NOTHROW_P (TREE_TYPE (TREE_TYPE (function)))); + if (!nothrow && at_function_scope_p () && cfun && cp_function_chain) + cp_function_chain->can_throw = 1; + if (decl && TREE_THIS_VOLATILE (decl) && cfun && cp_function_chain) current_function_returns_abnormally = 1; @@ -3965,9 +3968,10 @@ tree build_op_call (tree obj, VEC(tree,gc) **args, tsubst_flags_t complain) { tree ret; - timevar_start (TV_OVERLOAD); + bool subtime; + subtime = timevar_cond_start (TV_OVERLOAD); ret = build_op_call_1 (obj, args, complain); - timevar_stop (TV_OVERLOAD); + timevar_cond_stop (TV_OVERLOAD, subtime); return ret; } @@ -5075,6 +5079,7 @@ build_new_op_1 (enum tree_code code, int flags, tree arg1, tree arg2, tree arg3, case POSTDECREMENT_EXPR: case REALPART_EXPR: case IMAGPART_EXPR: + case ABS_EXPR: return cp_build_unary_op (code, arg1, candidates != 0, complain); case ARRAY_REF: @@ -5259,8 +5264,22 @@ build_op_delete_call (enum tree_code code, tree addr, tree size, usual deallocation function." So (void*) beats (void*, size_t). */ - if (FUNCTION_ARG_CHAIN (fn) == void_list_node) - break; + /* If type is not void, pick (void*, size_t) version (which comes + first). */ + if (!flag_sized_delete || TREE_CODE (type) == VOID_TYPE ) + { + /* If -fsized-delete is not passed or if a void * is deleted, + prefer delete (void *) version. */ + if (FUNCTION_ARG_CHAIN (fn) == void_list_node) + break; + } + else + { + /* If -fsized-delete is passed and it is not a void *, + prefer delete (void *, size_t) version. */ + if (FUNCTION_ARG_CHAIN (fn) != void_list_node) + break; + } } } @@ -5427,6 +5446,9 @@ convert_like_real (conversion *convs, tree expr, tree fn, int argnum, diagnostic_t diag_kind; int flags; + if (convs->bad_p && !(complain & tf_error)) + return error_mark_node; + if (convs->bad_p && convs->kind != ck_user && convs->kind != ck_list @@ -5462,15 +5484,12 @@ convert_like_real (conversion *convs, tree expr, tree fn, int argnum, else if (t->kind == ck_identity) break; } - if (complain & tf_error) - { - permerror (input_location, "invalid conversion from %qT to %qT", TREE_TYPE (expr), totype); - if (fn) - permerror (DECL_SOURCE_LOCATION (fn), - " initializing argument %P of %qD", argnum, fn); - } - else - return error_mark_node; + + permerror (input_location, "invalid conversion from %qT to %qT", + TREE_TYPE (expr), totype); + if (fn) + permerror (DECL_SOURCE_LOCATION (fn), + " initializing argument %P of %qD", argnum, fn); return cp_convert (totype, expr); } @@ -6588,11 +6607,6 @@ build_cxx_call (tree fn, int nargs, tree *argarray) /* If this call might throw an exception, note that fact. */ fndecl = get_callee_fndecl (fn); - if ((!fndecl || !TREE_NOTHROW (fndecl)) - && at_function_scope_p () - && cfun - && cp_function_chain) - cp_function_chain->can_throw = 1; /* Check that arguments to builtin functions match the expectations. */ if (fndecl diff --git a/gcc-4.6/gcc/cp/class.c b/gcc-4.6/gcc/cp/class.c index a3d010203..9f2a7c1ef 100644 --- a/gcc-4.6/gcc/cp/class.c +++ b/gcc-4.6/gcc/cp/class.c @@ -1,6 +1,6 @@ /* Functions related to building classes and their related objects. Copyright (C) 1987, 1992, 1993, 1994, 1995, 1996, 1997, 1998, - 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2007, 2008, 2009, 2010 + 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2007, 2008, 2009, 2010, 2011 Free Software Foundation, Inc. Contributed by Michael Tiemann (tiemann@cygnus.com) @@ -464,7 +464,14 @@ build_simple_base_path (tree expr, tree binfo) /* Is this the base field created by build_base_field? */ if (TREE_CODE (field) == FIELD_DECL && DECL_FIELD_IS_BASE (field) - && TREE_TYPE (field) == type) + && TREE_TYPE (field) == type + /* If we're looking for a field in the most-derived class, + also check the field offset; we can have two base fields + of the same type if one is an indirect virtual base and one + is a direct non-virtual base. */ + && (BINFO_INHERITANCE_CHAIN (d_binfo) + || tree_int_cst_equal (byte_position (field), + BINFO_OFFSET (binfo)))) { /* We don't use build_class_member_access_expr here, as that has unnecessary checks, and more importantly results in @@ -541,6 +548,10 @@ convert_to_base_statically (tree expr, tree base) { tree pointer_type; + /* If this is a non-empty base, use a COMPONENT_REF. */ + if (!is_empty_class (BINFO_TYPE (base))) + return build_simple_base_path (expr, base); + pointer_type = build_pointer_type (expr_type); /* We use fold_build2 and fold_convert below to simplify the trees @@ -2295,10 +2306,7 @@ update_vtable_entry_for_fn (tree t, tree binfo, tree fn, tree* virtuals, else BV_VCALL_INDEX (*virtuals) = NULL_TREE; - if (lost) - BV_LOST_PRIMARY (*virtuals) = true; - else - BV_LOST_PRIMARY (*virtuals) = false; + BV_LOST_PRIMARY (*virtuals) = lost; } /* Called from modify_all_vtables via dfs_walk. */ @@ -2917,7 +2925,7 @@ check_field_decl (tree field, if (!warned && errorcount > oldcount) { inform (DECL_SOURCE_LOCATION (field), "unrestricted unions " - "only available with -std=c++0x or -std=gnu++0x"); + "only available with -std=c++11 or -std=gnu++11"); warned = true; } } @@ -4349,6 +4357,40 @@ type_has_user_provided_default_constructor (tree t) return false; } +/* If default-initialization leaves part of TYPE uninitialized, returns + a DECL for the field or TYPE itself (DR 253). */ + +tree +default_init_uninitialized_part (tree type) +{ + tree t, r, binfo; + int i; + + type = strip_array_types (type); + if (!CLASS_TYPE_P (type)) + return type; + if (type_has_user_provided_default_constructor (type)) + return NULL_TREE; + for (binfo = TYPE_BINFO (type), i = 0; + BINFO_BASE_ITERATE (binfo, i, t); ++i) + { + r = default_init_uninitialized_part (BINFO_TYPE (t)); + if (r) + return r; + } + for (t = TYPE_FIELDS (type); t; t = DECL_CHAIN (t)) + if (TREE_CODE (t) == FIELD_DECL + && !DECL_ARTIFICIAL (t) + && !DECL_INITIAL (t)) + { + r = default_init_uninitialized_part (TREE_TYPE (t)); + if (r) + return DECL_P (r) ? r : t; + } + + return NULL_TREE; +} + /* Returns true iff for class T, a synthesized default constructor would be constexpr. */ @@ -5706,6 +5748,27 @@ finish_struct_1 (tree t) /* Finish debugging output for this type. */ rest_of_type_compilation (t, ! LOCAL_CLASS_P (t)); + + if (TYPE_TRANSPARENT_AGGR (t)) + { + tree field = first_field (t); + if (field == NULL_TREE || error_operand_p (field)) + { + error ("type transparent class %qT does not have any fields", t); + TYPE_TRANSPARENT_AGGR (t) = 0; + } + else if (DECL_ARTIFICIAL (field)) + { + if (DECL_FIELD_IS_BASE (field)) + error ("type transparent class %qT has base classes", t); + else + { + gcc_checking_assert (DECL_VIRTUAL_P (field)); + error ("type transparent class %qT has virtual functions", t); + } + TYPE_TRANSPARENT_AGGR (t) = 0; + } + } } /* When T was built up, the member declarations were added in reverse @@ -8384,9 +8447,15 @@ cp_get_virtual_function_decl (tree ref, tree known_type) { HOST_WIDE_INT index = tree_low_cst (OBJ_TYPE_REF_TOKEN (ref), 1); HOST_WIDE_INT i = 0; - tree v = BINFO_VIRTUALS (TYPE_BINFO (known_type)); + tree binfo = TYPE_BINFO (known_type); + tree v; tree fndecl; - + + if (!binfo) + return NULL_TREE; + + v = BINFO_VIRTUALS (TYPE_BINFO (known_type)); + while (v && i != index) { i += (TARGET_VTABLE_USES_DESCRIPTORS diff --git a/gcc-4.6/gcc/cp/cp-tree.h b/gcc-4.6/gcc/cp/cp-tree.h index 9745797a4..daf4714bf 100644 --- a/gcc-4.6/gcc/cp/cp-tree.h +++ b/gcc-4.6/gcc/cp/cp-tree.h @@ -4723,6 +4723,7 @@ extern tree in_class_defaulted_default_constructor (tree); extern bool user_provided_p (tree); extern bool type_has_user_provided_constructor (tree); extern bool type_has_user_provided_default_constructor (tree); +extern tree default_init_uninitialized_part (tree); extern bool synthesized_default_constructor_is_constexpr (tree); extern bool type_has_constexpr_default_constructor (tree); extern bool type_has_virtual_destructor (tree); diff --git a/gcc-4.6/gcc/cp/decl.c b/gcc-4.6/gcc/cp/decl.c index aa20497b5..ff3baa54b 100644 --- a/gcc-4.6/gcc/cp/decl.c +++ b/gcc-4.6/gcc/cp/decl.c @@ -3519,6 +3519,7 @@ cxx_init_decl_processing (void) { tree void_ftype; tree void_ftype_ptr; + tree void_ftype_ptr_sizetype; build_common_tree_nodes (flag_signed_char); @@ -3584,8 +3585,14 @@ cxx_init_decl_processing (void) void_ftype = build_function_type_list (void_type_node, NULL_TREE); void_ftype_ptr = build_function_type_list (void_type_node, ptr_type_node, NULL_TREE); + void_ftype_ptr_sizetype = build_function_type_list (void_type_node, + ptr_type_node, + size_type_node, + NULL_TREE); void_ftype_ptr = build_exception_variant (void_ftype_ptr, empty_except_spec); + void_ftype_ptr_sizetype + = build_exception_variant (void_ftype_ptr_sizetype, empty_except_spec); /* C++ extensions */ @@ -3635,7 +3642,7 @@ cxx_init_decl_processing (void) current_lang_name = lang_name_cplusplus; { - tree newtype, deltype; + tree newtype, deltype, deltype2; tree ptr_ftype_sizetype; tree new_eh_spec; @@ -3664,8 +3671,10 @@ cxx_init_decl_processing (void) newtype = build_exception_variant (ptr_ftype_sizetype, new_eh_spec); deltype = build_exception_variant (void_ftype_ptr, empty_except_spec); + deltype2 = build_exception_variant (void_ftype_ptr_sizetype, empty_except_spec); push_cp_library_fn (NEW_EXPR, newtype); push_cp_library_fn (VEC_NEW_EXPR, newtype); + push_cp_library_fn (DELETE_EXPR, deltype2); global_delete_fndecl = push_cp_library_fn (DELETE_EXPR, deltype); push_cp_library_fn (VEC_DELETE_EXPR, deltype); @@ -4877,15 +4886,16 @@ check_for_uninitialized_const_var (tree decl) if (TREE_CODE (decl) == VAR_DECL && TREE_CODE (type) != REFERENCE_TYPE && CP_TYPE_CONST_P (type) - && (!TYPE_NEEDS_CONSTRUCTING (type) - || !type_has_user_provided_default_constructor (type)) && !DECL_INITIAL (decl)) { + tree field = default_init_uninitialized_part (type); + if (!field) + return; + permerror (DECL_SOURCE_LOCATION (decl), "uninitialized const %qD", decl); - if (CLASS_TYPE_P (type) - && !type_has_user_provided_default_constructor (type)) + if (CLASS_TYPE_P (type)) { tree defaulted_ctor; @@ -4896,6 +4906,8 @@ check_for_uninitialized_const_var (tree decl) inform (DECL_SOURCE_LOCATION (defaulted_ctor), "constructor is not user-provided because it is " "explicitly defaulted in the class body"); + inform (0, "and the implicitly-defined constructor does not " + "initialize %q+#D", field); } } } @@ -7505,8 +7517,18 @@ check_static_variable_definition (tree decl, tree type) else if (cxx_dialect >= cxx0x && !INTEGRAL_OR_ENUMERATION_TYPE_P (type)) { if (literal_type_p (type)) - error ("% needed for in-class initialization of static " - "data member %q#D of non-integral type", decl); + { + /* FIXME google: This local modification allows us to + transition from C++98 to C++11 without moving static + const floats out of the class during the transition. It + should not be forward-ported to a 4.7 branch, since by + then we should be able to just fix the code to use + constexpr. */ + pedwarn (input_location, OPT_pedantic, + "% needed for in-class initialization of " + "static data member %q#D of non-integral type", decl); + return 0; + } else error ("in-class initialization of static data member %q#D of " "non-literal type", decl); @@ -8796,6 +8818,10 @@ grokdeclarator (const cp_declarator *declarator, /* Pick up the exception specifications. */ raises = declarator->u.function.exception_specification; + /* If the exception-specification is ill-formed, let's pretend + there wasn't one. */ + if (raises == error_mark_node) + raises = NULL_TREE; /* Say it's a definition only for the CALL_EXPR closest to the identifier. */ @@ -11354,9 +11380,10 @@ xref_tag (enum tag_types tag_code, tree name, tag_scope scope, bool template_header_p) { tree ret; - timevar_start (TV_NAME_LOOKUP); + bool subtime; + subtime = timevar_cond_start (TV_NAME_LOOKUP); ret = xref_tag_1 (tag_code, name, scope, template_header_p); - timevar_stop (TV_NAME_LOOKUP); + timevar_cond_stop (TV_NAME_LOOKUP, subtime); return ret; } @@ -11592,15 +11619,19 @@ xref_basetypes (tree ref, tree base_list) static void copy_type_enum (tree dst, tree src) { - TYPE_MIN_VALUE (dst) = TYPE_MIN_VALUE (src); - TYPE_MAX_VALUE (dst) = TYPE_MAX_VALUE (src); - TYPE_SIZE (dst) = TYPE_SIZE (src); - TYPE_SIZE_UNIT (dst) = TYPE_SIZE_UNIT (src); - SET_TYPE_MODE (dst, TYPE_MODE (src)); - TYPE_PRECISION (dst) = TYPE_PRECISION (src); - TYPE_ALIGN (dst) = TYPE_ALIGN (src); - TYPE_USER_ALIGN (dst) = TYPE_USER_ALIGN (src); - TYPE_UNSIGNED (dst) = TYPE_UNSIGNED (src); + tree t; + for (t = dst; t; t = TYPE_NEXT_VARIANT (t)) + { + TYPE_MIN_VALUE (t) = TYPE_MIN_VALUE (src); + TYPE_MAX_VALUE (t) = TYPE_MAX_VALUE (src); + TYPE_SIZE (t) = TYPE_SIZE (src); + TYPE_SIZE_UNIT (t) = TYPE_SIZE_UNIT (src); + SET_TYPE_MODE (dst, TYPE_MODE (src)); + TYPE_PRECISION (t) = TYPE_PRECISION (src); + TYPE_ALIGN (t) = TYPE_ALIGN (src); + TYPE_USER_ALIGN (t) = TYPE_USER_ALIGN (src); + TYPE_UNSIGNED (t) = TYPE_UNSIGNED (src); + } } /* Begin compiling the definition of an enumeration type. @@ -11955,9 +11986,12 @@ finish_enum (tree enumtype) return; } - /* Here there should not be any variants of this type. */ + /* If this is a forward declaration, there should not be any variants, + though we can get a variant in the middle of an enum-specifier with + wacky code like 'enum E { e = sizeof(const E*) };' */ gcc_assert (enumtype == TYPE_MAIN_VARIANT (enumtype) - && !TYPE_NEXT_VARIANT (enumtype)); + && (TYPE_VALUES (enumtype) + || !TYPE_NEXT_VARIANT (enumtype))); } /* Build and install a CONST_DECL for an enumeration constant of the @@ -13408,8 +13442,17 @@ cxx_maybe_build_cleanup (tree decl) cleanup = call; } + /* build_delete sets the location of the destructor call to the + current location, even though the destructor is going to be + called later, at the end of the current scope. This can lead to + a "jumpy" behaviour for users of debuggers when they step around + the end of the block. So let's unset the location of the + destructor call instead. */ + if (cleanup != NULL && EXPR_P (cleanup)) + SET_EXPR_LOCATION (cleanup, UNKNOWN_LOCATION); return cleanup; } + /* When a stmt has been parsed, this function is called. */ diff --git a/gcc-4.6/gcc/cp/error.c b/gcc-4.6/gcc/cp/error.c index f2a450a08..809c87c50 100644 --- a/gcc-4.6/gcc/cp/error.c +++ b/gcc-4.6/gcc/cp/error.c @@ -974,7 +974,7 @@ dump_decl (tree t, int flags) dump_scope (CP_DECL_CONTEXT (t), flags); flags &= ~TFF_UNQUALIFIED_NAME; if (DECL_NAME (t) == NULL_TREE) - pp_cxx_ws_string (cxx_pp, M_("{anonymous}")); + pp_cxx_ws_string (cxx_pp, M_("(anonymous namespace)")); else pp_cxx_tree_identifier (cxx_pp, DECL_NAME (t)); } @@ -2494,6 +2494,8 @@ lang_decl_name (tree decl, int v, bool translate) if (TREE_CODE (decl) == FUNCTION_DECL) dump_function_name (decl, TFF_PLAIN_IDENTIFIER); + else if (DECL_NAME (decl) == NULL && TREE_CODE (decl) == NAMESPACE_DECL) + pp_string (cxx_pp, M_("(anonymous namespace)")); else dump_decl (DECL_NAME (decl), TFF_PLAIN_IDENTIFIER); @@ -3144,40 +3146,40 @@ maybe_warn_cpp0x (cpp0x_warn_str str) case CPP0X_INITIALIZER_LISTS: pedwarn (input_location, 0, "extended initializer lists " - "only available with -std=c++0x or -std=gnu++0x"); + "only available with -std=c++11 or -std=gnu++11"); break; case CPP0X_EXPLICIT_CONVERSION: pedwarn (input_location, 0, "explicit conversion operators " - "only available with -std=c++0x or -std=gnu++0x"); + "only available with -std=c++11 or -std=gnu++11"); break; case CPP0X_VARIADIC_TEMPLATES: pedwarn (input_location, 0, "variadic templates " - "only available with -std=c++0x or -std=gnu++0x"); + "only available with -std=c++11 or -std=gnu++11"); break; case CPP0X_LAMBDA_EXPR: pedwarn (input_location, 0, "lambda expressions " - "only available with -std=c++0x or -std=gnu++0x"); + "only available with -std=c++11 or -std=gnu++11"); break; case CPP0X_AUTO: pedwarn (input_location, 0, - "C++0x auto only available with -std=c++0x or -std=gnu++0x"); + "C++0x auto only available with -std=c++11 or -std=gnu++11"); break; case CPP0X_SCOPED_ENUMS: pedwarn (input_location, 0, - "scoped enums only available with -std=c++0x or -std=gnu++0x"); + "scoped enums only available with -std=c++11 or -std=gnu++11"); break; case CPP0X_DEFAULTED_DELETED: pedwarn (input_location, 0, "defaulted and deleted functions " - "only available with -std=c++0x or -std=gnu++0x"); + "only available with -std=c++11 or -std=gnu++11"); break; case CPP0X_INLINE_NAMESPACES: pedwarn (input_location, OPT_pedantic, "inline namespaces " - "only available with -std=c++0x or -std=gnu++0x"); + "only available with -std=c++11 or -std=gnu++11"); break; default: gcc_unreachable(); diff --git a/gcc-4.6/gcc/cp/init.c b/gcc-4.6/gcc/cp/init.c index 40caa599a..8b4c4f01a 100644 --- a/gcc-4.6/gcc/cp/init.c +++ b/gcc-4.6/gcc/cp/init.c @@ -141,7 +141,9 @@ initialize_vtbl_ptrs (tree addr) zero-initialization does not simply mean filling the storage with zero bytes. FIELD_SIZE, if non-NULL, is the bit size of the field, subfields with bit positions at or above that bit size shouldn't - be added. */ + be added. Note that this only works when the result is assigned + to a base COMPONENT_REF; if we only have a pointer to the base subobject, + expand_assignment will end up clearing the full size of TYPE. */ static tree build_zero_init_1 (tree type, tree nelts, bool static_storage_p, @@ -332,7 +334,7 @@ build_value_init (tree type, tsubst_flags_t complain) constructor. */ /* The AGGR_INIT_EXPR tweaking below breaks in templates. */ - gcc_assert (!processing_template_decl); + gcc_assert (!processing_template_decl || SCALAR_TYPE_P (type)); if (CLASS_TYPE_P (type)) { @@ -368,6 +370,12 @@ build_value_init (tree type, tsubst_flags_t complain) tree build_value_init_noctor (tree type, tsubst_flags_t complain) { + if (!COMPLETE_TYPE_P (type)) + { + if (complain & tf_error) + error ("value-initialization of incomplete type %qT", type); + return error_mark_node; + } if (CLASS_TYPE_P (type)) { gcc_assert (!TYPE_NEEDS_CONSTRUCTING (type)); @@ -526,8 +534,10 @@ perform_member_init (tree member, tree init) { if (init) { - gcc_assert (TREE_CHAIN (init) == NULL_TREE); - init = TREE_VALUE (init); + if (TREE_CHAIN (init)) + init = error_mark_node; + else + init = TREE_VALUE (init); if (BRACE_ENCLOSED_INITIALIZER_P (init)) init = digest_init (type, init); } @@ -549,7 +559,7 @@ perform_member_init (tree member, tree init) flags |= LOOKUP_DEFAULTED; if (CP_TYPE_CONST_P (type) && init == NULL_TREE - && !type_has_user_provided_default_constructor (type)) + && default_init_uninitialized_part (type)) /* TYPE_NEEDS_CONSTRUCTING can be set just because we have a vtable; still give this diagnostic. */ permerror (DECL_SOURCE_LOCATION (current_function_decl), @@ -633,8 +643,6 @@ build_field_list (tree t, tree list, int *uses_unions_p) { tree fields; - *uses_unions_p = 0; - /* Note whether or not T is a union. */ if (TREE_CODE (t) == UNION_TYPE) *uses_unions_p = 1; @@ -688,7 +696,7 @@ sort_mem_initializers (tree t, tree mem_inits) tree next_subobject; VEC(tree,gc) *vbases; int i; - int uses_unions_p; + int uses_unions_p = 0; /* Build up a list of initializations. The TREE_PURPOSE of entry will be the subobject (a FIELD_DECL or BINFO) to initialize. The @@ -1567,7 +1575,12 @@ expand_aggr_init_1 (tree binfo, tree true_exp, tree exp, tree init, int flags, zero out the object first. */ else if (TYPE_NEEDS_CONSTRUCTING (type)) { - init = build_zero_init (type, NULL_TREE, /*static_storage_p=*/false); + tree field_size = NULL_TREE; + if (exp != true_exp && CLASSTYPE_AS_BASE (type) != type) + /* Don't clobber already initialized virtual bases. */ + field_size = TYPE_SIZE (CLASSTYPE_AS_BASE (type)); + init = build_zero_init_1 (type, NULL_TREE, /*static_storage_p=*/false, + field_size); init = build2 (INIT_EXPR, type, exp, init); finish_expr_stmt (init); /* And then call the constructor. */ @@ -2090,7 +2103,7 @@ build_new_1 (VEC(tree,gc) **placement, tree type, tree nelts, } if (CP_TYPE_CONST_P (elt_type) && *init == NULL - && !type_has_user_provided_default_constructor (elt_type)) + && default_init_uninitialized_part (elt_type)) { if (complain & tf_error) error ("uninitialized const in % of %q#T", elt_type); @@ -3073,8 +3086,9 @@ build_vec_init (tree base, tree maxindex, tree init, unsigned HOST_WIDE_INT idx; tree field, elt; /* Should we try to create a constant initializer? */ - bool try_const = (literal_type_p (inner_elt_type) - || TYPE_HAS_CONSTEXPR_CTOR (inner_elt_type)); + bool try_const = (TREE_CODE (atype) == ARRAY_TYPE + && (literal_type_p (inner_elt_type) + || TYPE_HAS_CONSTEXPR_CTOR (inner_elt_type))); bool saw_non_const = false; bool saw_const = false; /* If we're initializing a static array, we want to do static diff --git a/gcc-4.6/gcc/cp/mangle.c b/gcc-4.6/gcc/cp/mangle.c index 9e9ced648..3f9996b64 100644 --- a/gcc-4.6/gcc/cp/mangle.c +++ b/gcc-4.6/gcc/cp/mangle.c @@ -1790,11 +1790,6 @@ write_type (tree type) if (find_substitution (type)) return; - /* According to the C++ ABI, some library classes are passed the - same as the scalar type of their single member and use the same - mangling. */ - if (TREE_CODE (type) == RECORD_TYPE && TYPE_TRANSPARENT_AGGR (type)) - type = TREE_TYPE (first_field (type)); if (write_CV_qualifiers_for_type (type) > 0) /* If TYPE was CV-qualified, we just wrote the qualifiers; now @@ -1814,6 +1809,12 @@ write_type (tree type) /* See through any typedefs. */ type = TYPE_MAIN_VARIANT (type); + /* According to the C++ ABI, some library classes are passed the + same as the scalar type of their single member and use the same + mangling. */ + if (TREE_CODE (type) == RECORD_TYPE && TYPE_TRANSPARENT_AGGR (type)) + type = TREE_TYPE (first_field (type)); + if (TYPE_PTRMEM_P (type)) write_pointer_to_member_type (type); else diff --git a/gcc-4.6/gcc/cp/method.c b/gcc-4.6/gcc/cp/method.c index a6932229b..f7198d590 100644 --- a/gcc-4.6/gcc/cp/method.c +++ b/gcc-4.6/gcc/cp/method.c @@ -360,6 +360,8 @@ use_thunk (tree thunk_fndecl, bool emit_p) /* Output the thunk into the same section as function. */ DECL_SECTION_NAME (thunk_fndecl) = DECL_SECTION_NAME (function); + if (DECL_COMDAT_GROUP (function)) + make_decl_one_only (thunk_fndecl, DECL_COMDAT_GROUP (function)); } } @@ -1007,8 +1009,7 @@ walk_field_subobs (tree fields, tree fnname, special_function_kind sfk, { bool bad = true; if (CP_TYPE_CONST_P (mem_type) - && (!CLASS_TYPE_P (mem_type) - || !type_has_user_provided_default_constructor (mem_type))) + && default_init_uninitialized_part (mem_type)) { if (msg) error ("uninitialized non-static const member %q#D", diff --git a/gcc-4.6/gcc/cp/name-lookup.c b/gcc-4.6/gcc/cp/name-lookup.c index 8753f1491..85caafe34 100644 --- a/gcc-4.6/gcc/cp/name-lookup.c +++ b/gcc-4.6/gcc/cp/name-lookup.c @@ -5441,9 +5441,10 @@ lookup_arg_dependent (tree name, tree fns, VEC(tree,gc) *args, bool include_std) { tree ret; - timevar_start (TV_NAME_LOOKUP); + bool subtime; + subtime = timevar_cond_start (TV_NAME_LOOKUP); ret = lookup_arg_dependent_1 (name, fns, args, include_std); - timevar_stop (TV_NAME_LOOKUP); + timevar_cond_stop (TV_NAME_LOOKUP, subtime); return ret; } diff --git a/gcc-4.6/gcc/cp/parser.c b/gcc-4.6/gcc/cp/parser.c index f5eb09966..12cfacf38 100644 --- a/gcc-4.6/gcc/cp/parser.c +++ b/gcc-4.6/gcc/cp/parser.c @@ -2759,8 +2759,8 @@ cp_parser_diagnose_invalid_type_name (cp_parser *parser, The user should have said "typename A::X". */ if (cxx_dialect < cxx0x && id == ridpointers[(int)RID_CONSTEXPR]) - inform (location, "C++0x % only available with " - "-std=c++0x or -std=gnu++0x"); + inform (location, "C++11 % only available with " + "-std=c++11 or -std=gnu++11"); else if (processing_template_decl && current_class_type && TYPE_BINFO (current_class_type)) { @@ -8049,8 +8049,11 @@ static void cp_parser_lambda_body (cp_parser* parser, tree lambda_expr) { bool nested = (current_function_decl != NULL_TREE); + bool local_variables_forbidden_p = parser->local_variables_forbidden_p; if (nested) push_function_context (); + /* Clear this in case we're in the middle of a default argument. */ + parser->local_variables_forbidden_p = false; /* Finish the function call operator - class_specifier @@ -8137,6 +8140,7 @@ cp_parser_lambda_body (cp_parser* parser, tree lambda_expr) expand_or_defer_fn (finish_function (/*inline*/2)); } + parser->local_variables_forbidden_p = local_variables_forbidden_p; if (nested) pop_function_context(); } @@ -16708,16 +16712,6 @@ cp_parser_initializer_clause (cp_parser* parser, bool* non_constant_p) = cp_parser_constant_expression (parser, /*allow_non_constant_p=*/true, non_constant_p); - if (!*non_constant_p) - { - /* We only want to fold if this is really a constant - expression. FIXME Actually, we don't want to fold here, but in - cp_finish_decl. */ - tree folded = fold_non_dependent_expr (initializer); - folded = maybe_constant_value (folded); - if (TREE_CONSTANT (folded)) - initializer = folded; - } } else initializer = cp_parser_braced_list (parser, non_constant_p); @@ -19275,6 +19269,7 @@ cp_parser_late_parsing_attribute_arg_lists (cp_parser* parser) cp_token_cache *tokens = (cp_token_cache *) TREE_VALUE (artificial_node); tree ctype; VEC(tree,gc) *vec; + tree clone; gcc_assert (tokens); gcc_assert (decl && decl != error_mark_node); @@ -19318,16 +19313,9 @@ cp_parser_late_parsing_attribute_arg_lists (cp_parser* parser) /* If decl has clones (when it is a ctor or a dtor), we need to modify the clones' attributes as well. */ - if (TREE_CODE (decl) == FUNCTION_DECL - && (DECL_CONSTRUCTOR_P (decl) || DECL_DESTRUCTOR_P (decl))) - { - tree clone; - for (clone = TREE_CHAIN (decl); clone; clone = TREE_CHAIN (clone)) - { - if (DECL_CLONED_FUNCTION (clone) == decl) - DECL_ATTRIBUTES (clone) = DECL_ATTRIBUTES (decl); - } - } + FOR_EACH_CLONE (clone, decl) + if (DECL_CLONED_FUNCTION (clone) == decl) + DECL_ATTRIBUTES (clone) = DECL_ATTRIBUTES (decl); pop_nested_class (); @@ -23530,7 +23518,7 @@ cp_parser_objc_at_property_declaration (cp_parser *parser) break; } cp_lexer_consume_token (parser->lexer); /* eat the = */ - if (cp_lexer_next_token_is_not (parser->lexer, CPP_NAME)) + if (!cp_parser_objc_selector_p (cp_lexer_peek_token (parser->lexer)->type)) { cp_parser_error (parser, "expected identifier"); syntax_error = true; @@ -23539,10 +23527,12 @@ cp_parser_objc_at_property_declaration (cp_parser *parser) if (keyword == RID_SETTER) { if (property_setter_ident != NULL_TREE) - cp_parser_error (parser, "the % attribute may only be specified once"); + { + cp_parser_error (parser, "the % attribute may only be specified once"); + cp_lexer_consume_token (parser->lexer); + } else - property_setter_ident = cp_lexer_peek_token (parser->lexer)->u.value; - cp_lexer_consume_token (parser->lexer); + property_setter_ident = cp_parser_objc_selector (parser); if (cp_lexer_next_token_is_not (parser->lexer, CPP_COLON)) cp_parser_error (parser, "setter name must terminate with %<:%>"); else @@ -23551,10 +23541,12 @@ cp_parser_objc_at_property_declaration (cp_parser *parser) else { if (property_getter_ident != NULL_TREE) - cp_parser_error (parser, "the % attribute may only be specified once"); + { + cp_parser_error (parser, "the % attribute may only be specified once"); + cp_lexer_consume_token (parser->lexer); + } else - property_getter_ident = cp_lexer_peek_token (parser->lexer)->u.value; - cp_lexer_consume_token (parser->lexer); + property_getter_ident = cp_parser_objc_selector (parser); } break; default: diff --git a/gcc-4.6/gcc/cp/pt.c b/gcc-4.6/gcc/cp/pt.c index 770aca8cc..f2459f901 100644 --- a/gcc-4.6/gcc/cp/pt.c +++ b/gcc-4.6/gcc/cp/pt.c @@ -225,6 +225,7 @@ static void append_type_to_template_for_access_check_1 (tree, tree, tree, static tree listify (tree); static tree listify_autos (tree, tree); static tree template_parm_to_arg (tree t); +static bool arg_from_parm_pack_p (tree, tree); static tree current_template_args (void); static tree fixup_template_type_parm_type (tree, int); static tree fixup_template_parm_index (tree, tree, int); @@ -1660,19 +1661,19 @@ iterative_hash_template_arg (tree arg, hashval_t val) bool reregister_specialization (tree spec, tree tinfo, tree new_spec) { - spec_entry **slot; + spec_entry *entry; spec_entry elt; elt.tmpl = most_general_template (TI_TEMPLATE (tinfo)); elt.args = TI_ARGS (tinfo); elt.spec = NULL_TREE; - slot = (spec_entry **) htab_find_slot (decl_specializations, &elt, INSERT); - if (*slot) + entry = (spec_entry *) htab_find (decl_specializations, &elt); + if (entry != NULL) { - gcc_assert ((*slot)->spec == spec || (*slot)->spec == new_spec); + gcc_assert (entry->spec == spec || entry->spec == new_spec); gcc_assert (new_spec != NULL_TREE); - (*slot)->spec = new_spec; + entry->spec = new_spec; return 1; } @@ -2763,12 +2764,15 @@ template_parameter_pack_p (const_tree parm) if (TREE_CODE (parm) == PARM_DECL) return (DECL_TEMPLATE_PARM_P (parm) && TEMPLATE_PARM_PARAMETER_PACK (DECL_INITIAL (parm))); + if (TREE_CODE (parm) == TEMPLATE_PARM_INDEX) + return TEMPLATE_PARM_PARAMETER_PACK (parm); /* If this is a list of template parameters, we could get a TYPE_DECL or a TEMPLATE_DECL. */ if (TREE_CODE (parm) == TYPE_DECL || TREE_CODE (parm) == TEMPLATE_DECL) parm = TREE_TYPE (parm); + /* Otherwise it must be a type template parameter. */ return ((TREE_CODE (parm) == TEMPLATE_TYPE_PARM || TREE_CODE (parm) == TEMPLATE_TEMPLATE_PARM) && TEMPLATE_TYPE_PARAMETER_PACK (parm)); @@ -3047,6 +3051,7 @@ find_parameter_packs_r (tree *tp, int *walk_subtrees, void* data) *walk_subtrees = 0; return NULL_TREE; + case CONSTRUCTOR: case TEMPLATE_DECL: cp_walk_tree (&TREE_TYPE (t), &find_parameter_packs_r, ppd, ppd->visited); @@ -4036,6 +4041,63 @@ template_parm_to_arg (tree t) return t; } +/* This function returns TRUE if PARM_PACK is a template parameter + pack and if ARG_PACK is what template_parm_to_arg returned when + passed PARM_PACK. */ + +static bool +arg_from_parm_pack_p (tree arg_pack, tree parm_pack) +{ + /* For clarity in the comments below let's use the representation + argument_pack' to denote an argument pack and its + elements. + + In the 'if' block below, we want to detect cases where + ARG_PACK is argument_pack. I.e, we want to + check if ARG_PACK is an argument pack which sole element is + the expansion of PARM_PACK. That argument pack is typically + created by template_parm_to_arg when passed a parameter + pack. */ + + if (arg_pack + && TREE_VEC_LENGTH (ARGUMENT_PACK_ARGS (arg_pack)) == 1 + && PACK_EXPANSION_P (TREE_VEC_ELT (ARGUMENT_PACK_ARGS (arg_pack), 0))) + { + tree expansion = TREE_VEC_ELT (ARGUMENT_PACK_ARGS (arg_pack), 0); + tree pattern = PACK_EXPANSION_PATTERN (expansion); + /* So we have an argument_pack. We want to test if P + is actually PARM_PACK. We will not use cp_tree_equal to + test P and PARM_PACK because during type fixup (by + fixup_template_parm) P can be a pre-fixup version of a + type and PARM_PACK be its post-fixup version. + cp_tree_equal would consider them as different even + though we would want to consider them compatible for our + precise purpose here. + + Thus we are going to consider that P and PARM_PACK are + compatible if they have the same DECL. */ + if ((/* If ARG_PACK is a type parameter pack named by the + same DECL as parm_pack ... */ + (TYPE_P (pattern) + && TYPE_P (parm_pack) + && TYPE_NAME (pattern) == TYPE_NAME (parm_pack)) + /* ... or if PARM_PACK is a non-type parameter named by the + same DECL as ARG_PACK. Note that PARM_PACK being a + non-type parameter means it's either a PARM_DECL or a + TEMPLATE_PARM_INDEX. */ + || (TREE_CODE (pattern) == TEMPLATE_PARM_INDEX + && ((TREE_CODE (parm_pack) == PARM_DECL + && (TEMPLATE_PARM_DECL (pattern) + == TEMPLATE_PARM_DECL (DECL_INITIAL (parm_pack)))) + || (TREE_CODE (parm_pack) == TEMPLATE_PARM_INDEX + && (TEMPLATE_PARM_DECL (pattern) + == TEMPLATE_PARM_DECL (parm_pack)))))) + && template_parameter_pack_p (pattern)) + return true; + } + return false; +} + /* Within the declaration of a template, return all levels of template parameters that apply. The template parameters are represented as a TREE_VEC, in the form documented in cp-tree.h for template @@ -4613,7 +4675,7 @@ check_default_tmpl_args (tree decl, tree parms, int is_primary, "friend declarations"); else if (TREE_CODE (decl) == FUNCTION_DECL && (cxx_dialect == cxx98)) msg = G_("default template arguments may not be used in function templates " - "without -std=c++0x or -std=gnu++0x"); + "without -std=c++11 or -std=gnu++11"); else if (is_partial) msg = G_("default template arguments may not be used in " "partial specializations"); @@ -6340,6 +6402,7 @@ coerce_template_parms (tree parms, subtract it from nparms to get the number of non-variadic parameters. */ int variadic_p = 0; + int post_variadic_parms = 0; if (args == error_mark_node) return error_mark_node; @@ -6350,19 +6413,22 @@ coerce_template_parms (tree parms, for (parm_idx = 0; parm_idx < nparms; ++parm_idx) { tree tparm = TREE_VALUE (TREE_VEC_ELT (parms, parm_idx)); + if (variadic_p) + ++post_variadic_parms; if (template_parameter_pack_p (tparm)) ++variadic_p; } inner_args = INNERMOST_TEMPLATE_ARGS (args); - /* If there are 0 or 1 parameter packs, we need to expand any argument - packs so that we can deduce a parameter pack from some non-packed args - followed by an argument pack, as in variadic85.C. If there are more - than that, we need to leave argument packs intact so the arguments are - assigned to the right parameter packs. This should only happen when - dealing with a nested class inside a partial specialization of a class - template, as in variadic92.C. */ - if (variadic_p <= 1) + /* If there are no parameters that follow a parameter pack, we need to + expand any argument packs so that we can deduce a parameter pack from + some non-packed args followed by an argument pack, as in variadic85.C. + If there are such parameters, we need to leave argument packs intact + so the arguments are assigned properly. This can happen when dealing + with a nested class inside a partial specialization of a class + template, as in variadic92.C, or when deducing a template parameter pack + from a sub-declarator, as in variadic114.C. */ + if (!post_variadic_parms) inner_args = expand_template_argument_pack (inner_args); nargs = inner_args ? NUM_TMPL_ARGS (inner_args) : 0; @@ -8873,53 +8939,13 @@ tsubst_pack_expansion (tree t, tree args, tsubst_flags_t complain, return result; } - /* For clarity in the comments below let's use the - representation 'argument_pack' to denote an - argument pack and its elements. - - In the 'if' block below, we want to detect cases where - ARG_PACK is argument_pack. I.e, we want to - check if ARG_PACK is an argument pack which sole element is - the expansion of PARM_PACK. That argument pack is typically - created by template_parm_to_arg when passed a parameter - pack. */ - if (arg_pack - && TREE_VEC_LENGTH (ARGUMENT_PACK_ARGS (arg_pack)) == 1 - && PACK_EXPANSION_P (TREE_VEC_ELT (ARGUMENT_PACK_ARGS (arg_pack), 0))) - { - tree expansion = TREE_VEC_ELT (ARGUMENT_PACK_ARGS (arg_pack), 0); - tree pattern = PACK_EXPANSION_PATTERN (expansion); - /* So we have an argument_pack. We want to test if P - is actually PARM_PACK. We will not use cp_tree_equal to - test P and PARM_PACK because during type fixup (by - fixup_template_parm) P can be a pre-fixup version of a - type and PARM_PACK be its post-fixup version. - cp_tree_equal would consider them as different even - though we would want to consider them compatible for our - precise purpose here. - - Thus we are going to consider that P and PARM_PACK are - compatible if they have the same DECL. */ - if ((/* If ARG_PACK is a type parameter pack named by the - same DECL as parm_pack ... */ - (TYPE_P (pattern) - && TYPE_P (parm_pack) - && TYPE_NAME (pattern) == TYPE_NAME (parm_pack)) - /* ... or if ARG_PACK is a non-type parameter - named by the same DECL as parm_pack ... */ - || (TREE_CODE (pattern) == TEMPLATE_PARM_INDEX - && TREE_CODE (parm_pack) == PARM_DECL - && TEMPLATE_PARM_DECL (pattern) - == TEMPLATE_PARM_DECL (DECL_INITIAL (parm_pack)))) - && template_parameter_pack_p (pattern)) - /* ... then the argument pack that the parameter maps to - is just an expansion of the parameter itself, such as - one would find in the implicit typedef of a class - inside the class itself. Consider this parameter - "unsubstituted", so that we will maintain the outer - pack expansion. */ - arg_pack = NULL_TREE; - } + if (arg_from_parm_pack_p (arg_pack, parm_pack)) + /* The argument pack that the parameter maps to is just an + expansion of the parameter itself, such as one would find + in the implicit typedef of a class inside the class itself. + Consider this parameter "unsubstituted", so that we will + maintain the outer pack expansion. */ + arg_pack = NULL_TREE; if (arg_pack) { @@ -11549,6 +11575,9 @@ tsubst_copy (tree t, tree args, tsubst_flags_t complain, tree in_decl) mark_used (t); return t; + case NAMESPACE_DECL: + return t; + case OVERLOAD: /* An OVERLOAD will always be a non-dependent overload set; an overload set from function scope will just be represented with an @@ -12702,7 +12731,11 @@ tsubst_copy_and_build (tree t, if (parsing_lock_attribute && func_decl_params) decl = lookup_name_in_func_params (func_decl_params, decl); else - decl = unqualified_name_lookup_error (decl); + { + if (complain & tf_error) + unqualified_name_lookup_error (decl); + decl = error_mark_node; + } } return decl; } @@ -12810,6 +12843,10 @@ tsubst_copy_and_build (tree t, return build_x_unary_op (TREE_CODE (t), RECUR (TREE_OPERAND (t, 0)), complain); + case FIX_TRUNC_EXPR: + return cp_build_unary_op (FIX_TRUNC_EXPR, RECUR (TREE_OPERAND (t, 0)), + 0, complain); + case ADDR_EXPR: op1 = TREE_OPERAND (t, 0); if (TREE_CODE (op1) == LABEL_DECL) @@ -13285,7 +13322,9 @@ tsubst_copy_and_build (tree t, if (member == error_mark_node) return error_mark_node; - if (object_type && !CLASS_TYPE_P (object_type)) + if (type_dependent_expression_p (object)) + /* We can't do much here. */; + else if (!CLASS_TYPE_P (object_type)) { if (SCALAR_TYPE_P (object_type)) { @@ -14950,7 +14989,6 @@ unify_pack_expansion (tree tparms, tree targs, tree packed_parms, tree arg = TREE_VEC_ELT (packed_args, i); tree arg_expr = NULL_TREE; int arg_strict = strict; - bool skip_arg_p = false; if (call_args_p) { @@ -14993,19 +15031,15 @@ unify_pack_expansion (tree tparms, tree targs, tree packed_parms, if (resolve_overloaded_unification (tparms, targs, parm, arg, (unification_kind_t) strict, - sub_strict) - != 0) - return 1; - skip_arg_p = true; + sub_strict)) + goto unified; + return 1; } - if (!skip_arg_p) - { - arg_expr = arg; - arg = unlowered_expr_type (arg); - if (arg == error_mark_node) - return 1; - } + arg_expr = arg; + arg = unlowered_expr_type (arg); + if (arg == error_mark_node) + return 1; } arg_strict = sub_strict; @@ -15016,16 +15050,14 @@ unify_pack_expansion (tree tparms, tree targs, tree packed_parms, &parm, &arg, arg_expr); } - if (!skip_arg_p) - { - /* For deduction from an init-list we need the actual list. */ - if (arg_expr && BRACE_ENCLOSED_INITIALIZER_P (arg_expr)) - arg = arg_expr; - if (unify (tparms, targs, parm, arg, arg_strict)) - return 1; - } + /* For deduction from an init-list we need the actual list. */ + if (arg_expr && BRACE_ENCLOSED_INITIALIZER_P (arg_expr)) + arg = arg_expr; + if (unify (tparms, targs, parm, arg, arg_strict)) + return 1; } + unified: /* For each parameter pack, collect the deduced value. */ for (pack = packs; pack; pack = TREE_CHAIN (pack)) { @@ -17359,6 +17391,8 @@ instantiate_decl (tree d, int defer_ok, d = DECL_CLONED_FUNCTION (d); if (DECL_TEMPLATE_INSTANTIATED (d) + || (TREE_CODE (d) == FUNCTION_DECL + && DECL_DEFAULTED_FN (d) && DECL_INITIAL (d)) || DECL_TEMPLATE_SPECIALIZATION (d)) /* D has already been instantiated or explicitly specialized, so there's nothing for us to do here. @@ -19072,6 +19106,10 @@ build_non_dependent_expr (tree expr) if (TREE_CODE (expr) == THROW_EXPR) return expr; + /* Don't wrap an initializer list, we need to be able to look inside. */ + if (BRACE_ENCLOSED_INITIALIZER_P (expr)) + return expr; + if (TREE_CODE (expr) == COND_EXPR) return build3 (COND_EXPR, TREE_TYPE (expr), diff --git a/gcc-4.6/gcc/cp/semantics.c b/gcc-4.6/gcc/cp/semantics.c index 1816e0520..6a2c81863 100644 --- a/gcc-4.6/gcc/cp/semantics.c +++ b/gcc-4.6/gcc/cp/semantics.c @@ -2911,6 +2911,9 @@ finish_id_expression (tree id_expression, tree lambda_expr = NULL_TREE; tree initializer = convert_from_reference (decl); + /* Mark it as used now even if the use is ill-formed. */ + mark_used (decl); + /* Core issue 696: "[At the July 2009 meeting] the CWG expressed support for an approach in which a reference to a local [constant] automatic variable in a nested class or lambda body @@ -3217,7 +3220,7 @@ finish_id_expression (tree id_expression, if (scope) { decl = (adjust_result_of_qualified_name_lookup - (decl, scope, current_class_type)); + (decl, scope, current_nonlambda_class_type())); if (TREE_CODE (decl) == FUNCTION_DECL) mark_used (decl); @@ -3359,7 +3362,7 @@ finish_offsetof (tree expr) } if (TREE_CODE (expr) == INDIRECT_REF && REFERENCE_REF_P (expr)) expr = TREE_OPERAND (expr, 0); - return fold_offsetof (expr, NULL_TREE); + return fold_offsetof (expr); } /* Replace the AGGR_INIT_EXPR at *TP with an equivalent CALL_EXPR. This @@ -4859,6 +4862,9 @@ finish_decltype_type (tree expr, bool id_expression_or_member_access_p, expr = resolve_nondeduced_context (expr); + if (invalid_nonstatic_memfn_p (expr, complain)) + return error_mark_node; + /* To get the size of a static data member declared as an array of unknown bound, we need to instantiate it. */ if (TREE_CODE (expr) == VAR_DECL @@ -4945,8 +4951,9 @@ finish_decltype_type (tree expr, bool id_expression_or_member_access_p, gcc_unreachable (); case INTEGER_CST: + case PTRMEM_CST: /* We can get here when the id-expression refers to an - enumerator. */ + enumerator or non-type template parameter. */ type = TREE_TYPE (expr); break; @@ -6324,12 +6331,22 @@ cxx_eval_array_reference (const constexpr_call *call, tree t, elem_type = TREE_TYPE (TREE_TYPE (ary)); if (TREE_CODE (ary) == CONSTRUCTOR) len = CONSTRUCTOR_NELTS (ary); - else + else if (TREE_CODE (ary) == STRING_CST) { elem_nchars = (TYPE_PRECISION (elem_type) / TYPE_PRECISION (char_type_node)); len = (unsigned) TREE_STRING_LENGTH (ary) / elem_nchars; } + else + { + /* We can't do anything with other tree codes, so use + VERIFY_CONSTANT to complain and fail. */ + VERIFY_CONSTANT (ary); + /* This should be unreachable, but be more fault-tolerant on the + release branch. */ + *non_constant_p = true; + return t; + } if (compare_tree_int (index, len) >= 0) { if (tree_int_cst_lt (index, array_type_nelts_top (TREE_TYPE (ary)))) @@ -6399,7 +6416,8 @@ cxx_eval_component_reference (const constexpr_call *call, tree t, if (field == part) return value; } - if (TREE_CODE (TREE_TYPE (whole)) == UNION_TYPE) + if (TREE_CODE (TREE_TYPE (whole)) == UNION_TYPE + && CONSTRUCTOR_NELTS (whole) > 0) { /* FIXME Mike Miller wants this to be OK. */ if (!allow_non_constant) @@ -6408,8 +6426,12 @@ cxx_eval_component_reference (const constexpr_call *call, tree t, *non_constant_p = true; return t; } - gcc_unreachable(); - return error_mark_node; + + /* If there's no explicit init for this field, it's value-initialized. */ + value = build_value_init (TREE_TYPE (t), tf_warning_or_error); + return cxx_eval_constant_expression (call, value, + allow_non_constant, addr, + non_constant_p); } /* Subroutine of cxx_eval_constant_expression. @@ -6506,9 +6528,9 @@ cxx_eval_logical_expression (const constexpr_call *call, tree t, allow_non_constant, addr, non_constant_p); VERIFY_CONSTANT (lhs); - if (lhs == bailout_value) + if (tree_int_cst_equal (lhs, bailout_value)) return lhs; - gcc_assert (lhs == continue_value); + gcc_assert (tree_int_cst_equal (lhs, continue_value)); r = cxx_eval_constant_expression (call, TREE_OPERAND (t, 1), allow_non_constant, addr, non_constant_p); VERIFY_CONSTANT (r); @@ -6613,6 +6635,7 @@ cxx_eval_vec_init_1 (const constexpr_call *call, tree atype, tree init, tree elttype = TREE_TYPE (atype); int max = tree_low_cst (array_type_nelts (atype), 0); VEC(constructor_elt,gc) *n = VEC_alloc (constructor_elt, gc, max + 1); + bool default_init = false; int i; /* For the default constructor, build up a call to the default @@ -6631,6 +6654,7 @@ cxx_eval_vec_init_1 (const constexpr_call *call, tree atype, tree init, release_tree_vector (argvec); init = cxx_eval_constant_expression (call, init, allow_non_constant, addr, non_constant_p); + default_init = true; } if (*non_constant_p && !allow_non_constant) @@ -6658,7 +6682,7 @@ cxx_eval_vec_init_1 (const constexpr_call *call, tree atype, tree init, eltinit = cxx_eval_constant_expression (call, eltinit, allow_non_constant, addr, non_constant_p); } - else if (TREE_CODE (init) == CONSTRUCTOR) + else if (default_init) { /* Initializing an element using the call to the default constructor we just built above. */ @@ -7310,6 +7334,7 @@ maybe_constant_value (tree t) if (type_dependent_expression_p (t) || type_unknown_p (t) + || BRACE_ENCLOSED_INITIALIZER_P (t) || !potential_constant_expression (t) || value_dependent_expression_p (t)) return t; @@ -7468,6 +7493,7 @@ potential_constant_expression_1 (tree t, bool want_rval, tsubst_flags_t flags) case IDENTIFIER_NODE: /* We can see a FIELD_DECL in a pointer-to-member expression. */ case FIELD_DECL: + case USING_DECL: return true; case PARM_DECL: @@ -7516,7 +7542,17 @@ potential_constant_expression_1 (tree t, bool want_rval, tsubst_flags_t flags) { tree x = get_nth_callarg (t, 0); if (is_this_parameter (x)) - /* OK. */; + { + if (DECL_CONSTRUCTOR_P (DECL_CONTEXT (x))) + { + if (flags & tf_error) + sorry ("calling a member function of the " + "object being constructed in a constant " + "expression"); + return false; + } + /* Otherwise OK. */; + } else if (!potential_constant_expression_1 (x, rval, flags)) { if (flags & tf_error) @@ -8283,6 +8319,9 @@ add_capture (tree lambda, tree id, tree initializer, bool by_reference_p, if (!real_lvalue_p (initializer)) error ("cannot capture %qE by reference", initializer); } + else + /* Capture by copy requires a complete type. */ + type = complete_type (type); /* Make member variable. */ member = build_lang_decl (FIELD_DECL, id, type); diff --git a/gcc-4.6/gcc/cp/tree.c b/gcc-4.6/gcc/cp/tree.c index 1fa32a015..6a39cc9e4 100644 --- a/gcc-4.6/gcc/cp/tree.c +++ b/gcc-4.6/gcc/cp/tree.c @@ -1840,7 +1840,11 @@ bot_manip (tree* tp, int* walk_subtrees, void* data) tree u; if (TREE_CODE (TREE_OPERAND (t, 1)) == AGGR_INIT_EXPR) - u = build_cplus_new (TREE_TYPE (t), TREE_OPERAND (t, 1)); + { + u = build_cplus_new (TREE_TYPE (t), TREE_OPERAND (t, 1)); + if (AGGR_INIT_ZERO_FIRST (TREE_OPERAND (t, 1))) + AGGR_INIT_ZERO_FIRST (TREE_OPERAND (u, 1)) = true; + } else u = build_target_expr_with_type (TREE_OPERAND (t, 1), TREE_TYPE (t)); @@ -1861,7 +1865,11 @@ bot_manip (tree* tp, int* walk_subtrees, void* data) } /* Make a copy of this node. */ - return copy_tree_r (tp, walk_subtrees, NULL); + t = copy_tree_r (tp, walk_subtrees, NULL); + if (TREE_CODE (*tp) == CALL_EXPR && !TREE_NOTHROW (*tp) + && cfun && cp_function_chain) + cp_function_chain->can_throw = 1; + return t; } /* Replace all remapped VAR_DECLs in T with their new equivalents. diff --git a/gcc-4.6/gcc/cp/typeck.c b/gcc-4.6/gcc/cp/typeck.c index eaed39067..a8cac768c 100644 --- a/gcc-4.6/gcc/cp/typeck.c +++ b/gcc-4.6/gcc/cp/typeck.c @@ -1299,7 +1299,9 @@ structural_comptypes (tree t1, tree t2, int strict) if (!cp_tree_equal (TYPENAME_TYPE_FULLNAME (t1), TYPENAME_TYPE_FULLNAME (t2))) return false; - if (!same_type_p (TYPE_CONTEXT (t1), TYPE_CONTEXT (t2))) + /* Qualifiers don't matter on scopes. */ + if (!same_type_ignoring_top_level_qualifiers_p (TYPE_CONTEXT (t1), + TYPE_CONTEXT (t2))) return false; break; @@ -4838,9 +4840,7 @@ cp_build_addr_expr_1 (tree arg, bool strict_lvalue, tsubst_flags_t complain) && TREE_CONSTANT (TREE_OPERAND (val, 0))) { tree type = build_pointer_type (argtype); - tree op0 = fold_convert (type, TREE_OPERAND (val, 0)); - tree op1 = fold_convert (sizetype, fold_offsetof (arg, val)); - return fold_build2 (POINTER_PLUS_EXPR, type, op0, op1); + return fold_convert (type, fold_offsetof_1 (arg)); } /* Handle complex lvalues (when permitted) @@ -5775,8 +5775,18 @@ build_static_cast_1 (tree type, tree expr, bool c_cast_p, && reference_related_p (TREE_TYPE (type), intype) && (c_cast_p || at_least_as_qualified_p (TREE_TYPE (type), intype))) { - expr = build_typed_address (expr, type); - return convert_from_reference (expr); + /* Handle the lvalue case here by casting to lvalue reference and + then changing it to an rvalue reference. Casting an xvalue to + rvalue reference will be handled by the main code path. */ + tree lref = cp_build_reference_type (TREE_TYPE (type), false); + result = (perform_direct_initialization_if_possible + (lref, expr, c_cast_p, complain)); + result = cp_fold_convert (type, result); + /* Make sure we don't fold back down to a named rvalue reference, + because that would be an lvalue. */ + if (DECL_P (result)) + result = build1 (NON_LVALUE_EXPR, type, result); + return convert_from_reference (result); } /* Resolve overloaded address here rather than once in diff --git a/gcc-4.6/gcc/cp/typeck2.c b/gcc-4.6/gcc/cp/typeck2.c index 480f442ee..7662e209c 100644 --- a/gcc-4.6/gcc/cp/typeck2.c +++ b/gcc-4.6/gcc/cp/typeck2.c @@ -452,6 +452,12 @@ cxx_incomplete_type_diagnostic (const_tree value, const_tree type, break; case LANG_TYPE: + if (type == init_list_type_node) + { + emit_diagnostic (diag_kind, input_location, 0, + "invalid use of brace-enclosed initializer list"); + break; + } gcc_assert (type == unknown_type_node); if (value && TREE_CODE (value) == COMPONENT_REF) goto bad_member; @@ -727,7 +733,7 @@ check_narrowing (tree type, tree init) bool ok = true; REAL_VALUE_TYPE d; - if (!ARITHMETIC_TYPE_P (type)) + if (!warn_narrowing || !ARITHMETIC_TYPE_P (type)) return; init = maybe_constant_value (init); @@ -775,8 +781,8 @@ check_narrowing (tree type, tree init) } if (!ok) - permerror (input_location, "narrowing conversion of %qE from %qT to %qT inside { }", - init, ftype, type); + pedwarn (input_location, OPT_Wnarrowing, "narrowing conversion of %qE " + "from %qT to %qT inside { }", init, ftype, type); } /* Process the initializer INIT for a variable of type TYPE, emitting -- cgit v1.2.3