* parser.c (cp_parser_postfix_expression): Allow non-constant
expressions as arguments to __builtin_constant_p.
* tree.c (builtin_valid_in_constant_expr_p): Use
- DECL_IS_BUILTIN_CONSTANT_P.
+ DECL_IS_BUILTIN_CONSTANT_P.
2005-06-03 Mark Mitchell <mark@codesourcery.com>
Mike Stump <mrs@apple.com>
Yet more Objective-C++...
-
+
* cp-objcp-common.h (cxx_get_alias_set): Move from
here...
(cxx_warn_unused_global_decl): Likewise.
* typeck.c (build_unary_op): Do not resort to address arithmetic
when taking the address of a COMPONENT_REF.
-
+
2005-05-08 Kazu Hirata <kazu@cs.umass.edu>
* class.c (vtbl_init_data_s): Change the type of fns to
* decl2.c (check_classfn): Adjust.
* init.c (sort_mem_initializers, push_base_cleanups): Adjust.
* method.c (do_build_copy_constructor): Adjust.
- * name-lookup.c (new_class_binding, store_binding,
+ * name-lookup.c (new_class_binding, store_binding,
store_bindings, store_class_bindings): Adjust.
* name-lookup.h: Define VEC(cxx_saved_binding,gc),
VEC(cp_class_binding,gc).
* typeck.c (cxx_sizeof_or_alignof_type): Check whether the type to
which sizeof/alignof is dependent, rather than just whether we are
processing_template_decl.
-
+
2005-04-17 Kazu Hirata <kazu@cs.umass.edu>
* cp-tree.h (LOOKUP_GLOBAL): Remove.
* decl2.c (determine_visibility): Don't use export_class_data.
(import_export_decl): Honor TARGET_CXX_CLASS_DATA_ALWAYS_WEAK and
- TARGET_CXX_DETERMINE_CLASS_DATA_VISIBILITY.
+ TARGET_CXX_DETERMINE_CLASS_DATA_VISIBILITY.
2005-04-09 Kazu Hirata <kazu@cs.umass.edu>
(cp_parser_type_specifier_seq): In a condition, do not allow
invalid type-specifier combinations.
(cp_parser_exception_declaration): Adjust call to
- cp_parser_type_specifier_seq.
+ cp_parser_type_specifier_seq.
* cp-tree.def (TINST_LEVEL): Document TINST_IN_SYSTEM_HEADER_P.
* cp-tree.h (struct tinst_level): Add in_system_header_p.
(lookup_template_class, instantiate_class_template): Adjust call
to pushtag.
* semantics.c (begin_class_definition): Likewise.
- * rtti.c (init_rtti_processing, build_dynamic_cast_1,
+ * rtti.c (init_rtti_processing, build_dynamic_cast_1,
tinfo_base_init, emit_support_tinfos): Use ts_current instead of
ts_global.
2005-03-13 Mark Mitchell <mark@codesourcery.com>
PR c++/20157
- * pt.c (determine_specialization): Reject non-specializations.
+ * pt.c (determine_specialization): Reject non-specializations.
2005-03-11 Per Bothner <per@bothner.com>
2005-03-09 Paolo Carlini <pcarlini@suse.de>
- PR c++/16859
+ PR c++/16859
* decl.c (complete_array_type): In pedantic mode, return
3 for an empty initializer list as the initializer for an
array of unknown bound (8.5.1/4).
(cp_finish_decl): Remove dead code.
* init.c (build_vec_init): When determining whether or not the
element type has an asignment operator, look through all array
- dimensions.
+ dimensions.
* typeck.c (target_type): Remove.
2005-03-07 Mark Mitchell <mark@codesourcery.com>
PR c++/20232
* class.c (update_vtable_entry_for_fn): Don't crash on invalid
- covariancy.
+ covariancy.
* cp-tree.g (THUNK_TARGET): Expand comment.
* method.c (use_thunk): Make sure we also use the target, if that
PR c++/20152
* parser.c (cp_parser_class_head): Check for redefintions here.
* semantics.c (begin_class_definition): Not here.
-
+
PR c++/20153
* decl2.c (build_anon_union_vars): Add type parameter.
(finish_anon_union): Pass it.
* parser.c (cp_parser_direct_declarator): Always complain about
non-constant array bounds when in a function scope.
* semantics.c (finish_id_expression): Do not mark dependent names
- as non-constant.
+ as non-constant.
2005-02-21 Douglas Gregor <dgregor@cs.indiana.edu>
-
+
PR c++/19076
PR c++/6628
* cp-tree.h (cp_apply_type_quals_to_decl): Declared.
* decl.c (grokdeclarator): Pedwarn about qualifying a function
- type.
+ type.
Add qualifiers when declaring a typedef of a function type.
Member function pointers pick up the qualifiers of the typedef
used to declare them.
(start_preparsed_function): Use cp_apply_type_quals_to_decl.
(grokclassfn): Use cp_apply_type_quals_to_decl.
* error.c (dump_type_suffix): Print qualifiers for function
- types.
+ types.
* pt.c (tsubst_decl): Use cp_apply_type_quals_to_decl.
(tsubst): When substituting a function type into a member
pointer type, pass along the qualifiers.
push_c_function_context.
(pop_cp_function_context): Similarly.
(finish_function): Reverse order of poplevel and pop_nested_class so
- that current_class_decl is restored properly.
+ that current_class_decl is restored properly.
(start_function): Likewise.
(finish_function): Add parameter 'nested'. Don't call
permanent_allocation if (nested).
(determine_primary_base): ... this. Simplify.
(create_vtable_ptr): Tweak accordingly.
(finish_struct_1): Simplify.
-
+
* cp-tree.h (CLASSTYPE_VBASECLASSES): Update documentation.
(CLASSTYPE_N_BASECLASSES): Likewise.
(BINFO_FOR_VBASE): New macro.
(get_vbase_types): Don't return a value. Set
CLASSTYPE_VBASECLASSES here.
* typeck.c (get_delta_difference): Use BINFO_FOR_VBASE.
-
+
1999-12-30 Mark Mitchell <mark@codesourcery.com>
* class.c (fixup_inline_methods): Clear CLASSTYPE_INLINE_FRIENDS.
(fixup_inline_methods): New function.
* method.c (fixup_pending_inline): Remove.
(do_inline_function_hair): Likewise.
-
+
* decl.c (BOOL_TYPE_SIZE): Bools always have size `1' under the
new ABI.
-
+
* cp-tree.h (lang_type): Replace abstract_virtuals with pure_virtuals.
(CLASSTYPE_ABSTRACT_VIRTUALS): Rename to ...
(CLASSTYPE_PURE_VIRTUALS): ... this.
* typeck2.c (abstract_virtuals_error): Likewise.
* xref.c (GNU_xref_member): Likewise.
* search.c (get_abstract_virtuals): Rename to get_pure_virtuals.
-
+
1999-12-26 Zack Weinberg <zack@wolery.cumb.org>
* cp-tree.h: Replace ENABLE_CHECKING with ENABLE_TREE_CHECKING
DECL_RESULT, not the mode of DECL_RESULT itself.
* semantics.c (finish_named_return_value): Set DECL_UNINLINABLE
for functions that used named return values.
-
+
1999-12-24 Mark Mitchell <mark@codesourcery.com>
* semantics.c (expand_body): Use
the first field in the class.
* tree.c (layout_basetypes): Use CLASSTYPE_N_BASECLASSES. Handle
seeing TYPE_VFIELD as the first field in the class.
-
+
* cp-tree.h (TYPE_VIRTUAL_P): Rename to ...
(TYPE_POLYMORPHIC_P): ... this.
(TYPE_USES_COMPLEX_INHERITANCE): Rename to ...
* typeck.c (build_component_ref): Likewise.
(build_component_addr): Likewise.
* typeck2.c (process_init_constructor): Likewise.
-
+
1999-12-20 Nathan Sidwell <nathan@acm.org>
* typeck.c (strip_all_pointer_quals): New static function.
(avoid_overlap): Moved here from tree.c.
(build_base_fields): Likewise.
(check_bases): New function, split out from finish_base_struct.
- (check_bases_and_members): New function, split out from
+ (check_bases_and_members): New function, split out from
finish_struct_1.
(struct base_info): Remove cant_have_default_ctor,
cant_have_const_ctor, cant_have_asn_ref.
(build_base_fields): Don't declare.
* tree.c (avoid_overlap): Remove.
(build_base_fields): Likewise.
-
+
* optimize.c (struct inline_data): Remove scope_stmt.
(remap_block): Don't use insert_block_after_note. Don't update
scope_stmt.
* method.c (fixup_pending_inline): New function, split out from ...
(do_inline_function_hair): ... here.
* tree.c (build_vbase_pointer_fields): Remove.
-
+
1999-12-15 Jason Merrill <jason@casey.cygnus.com>
* tree.c (walk_tree): Walk operand subtrees in forward order.
(expand_body): Use it.
* tree.c (walk_tree): Special-case TARGET_EXPRs since they
sometimes present the same sub-tree twice.
-
+
* dump.c (dequeue_and_dump): Abbreviate `class' as `cls', not
`csl'.
* typeck.c (c_expand_start_case): Here.
* semantics.c (do_poplevel): Remove unused variable.
-
+
1999-12-06 Mark Mitchell <mark@codesourcery.com>
* tree.c (walk_tree): Don't recurse into DECL_INITIAL or DECL_SIZE
parameters of the inlined function.
(optimize_function): Prevent recursion into partially complete
functions.
-
+
* cp-tree.def (SCOPE_STMT): Take one operand.
* cp-tree.h (SCOPE_STMT_BLOCK): New macro.
(SCOPE_NULLIFIED_P): Redefine.
* tree.c (copy_tree_r): Clear SCOPE_STMT_BLOCK rather than setting
SCOPE_NULLIFIED_P.
* Makefile.in (semantics.o): Depend on RTL_H.
-
+
* decl2.c (pending_statics_used): Make it a macro.
(saved_inlines_used): Likewise.
(finish_static_data_member_decl): Use VARRAY_PUSH_TREE.
(ssdf_decls_used): Remove.
(start_static_storage_duration_function): Use VARRAY_PUSH_TREE.
(generate_ctor_or_dtor_function): Adjust accordingly.
-
+
1999-11-24 Geoffrey Keating <geoffk@cygnus.com>
Greg McGary <gkm@gnu.org>
* typeck.c (build_component_ref): Don't use scratch_ovl_cons.
(build_x_function_call): Likewise.
(build_c_cast): Don't use min_tree_cons.
-
+
1999-11-29 Mark Mitchell <mark@codesourcery.com>
* pt.c (tsubst_decl): Robustify.
1999-11-25 Mark Mitchell <mark@codesourcery.com>
- * Make-lang.in (CXX_SRCS): Add optimize.c.
+ * Make-lang.in (CXX_SRCS): Add optimize.c.
* Makefile.in (CXX_OBJS): Add optimize.o.
(CXX_TREE_H): Add splay-tree.h, system.h, and $(CONFIG_H).
(spew.o, lex.o, decl.o, decl2.o, typeck2.o, typeck.o): Adjust.
(search.o, tree.o, ptree.o, rtti.o, except.o, expr.o): Likewise.
(xref.o, pt.o, error.o, errfn.o, repo.o, semantics.o): Likewise.
(dump.o): Likewise.
- (optimize.o): New target.
+ (optimize.o): New target.
* class.c: Don't include splay-tree.h.
- * cp-tree.def (CTOR_COMPLETE): Rename to CTOR_STMT.
+ * cp-tree.def (CTOR_COMPLETE): Rename to CTOR_STMT.
* cp-tree.h: Include splay-tree.h.
(DECL_UNINLINABLE): New macro.
(CTOR_BEGIN_P, CTOR_END_P): New macros.
(optimize_function): Likewise.
(cplus_unsave_expr_now): Remove.
(copy_tree_r): Declare.
- (remap_save_expr): Likewise.
+ (remap_save_expr): Likewise.
* decl.c (local_variable_p): Don't
make it static.
(local_variable_p_walkfn): New function.
(start_function): Set the DECL_CONTEXT for automatically generated
labels.
(finish_constructor_body): Use CTOR_STMT to mark the end of a
- constructor.
+ constructor.
* decl2.c: Don't include splay-tree.h.
- (flag_inline_trees): Define.
+ (flag_inline_trees): Define.
* dump.c: Don't include
- splay-tree.h.
+ splay-tree.h.
* except.c (expand_end_catch_block): Fix comment formatting.
(expand_end_eh_spec): Set DECL_CONTEXT on temporary variables.
- (expand_throw): Tidy comment.
- * init.c (build_vec_delete_1): Use create_temporary_var.
+ (expand_throw): Tidy comment.
+ * init.c (build_vec_delete_1): Use create_temporary_var.
* lex.c (cplus_tree_code_type): Make it static.
(cplus_tree_code_length): Likewise.
- (cplus_tree_code_name): Likewise.
- * optimize.c: New file.
+ (cplus_tree_code_name): Likewise.
+ * optimize.c: New file.
* semantics.c (finish_goto_stmt): Set DECL_UNLINABLE for functions
with computed gotos.
(setup_vtbl_ptr): Mark the beginnings of constructors with
(init_tree): Set lang_unsave to cp_unsave.
(remap_save_expr): Define.
* ir.texi: Document CTOR_STMT.
-
+
1999-11-24 Jason Merrill <jason@casey.cygnus.com>
* search.c (note_debug_info_needed): Do perform this optimization
- for dwarf2.
+ for dwarf2.
(maybe_suppress_debug_info): Likewise. Start by clearing
TYPE_DECL_SUPPRESS_DEBUG.
(finish_function): Don't call end_protect_partials here.
* ir.texi (CTOR_COMPLETE): Document it.
* semantics.c (expand_stmt): Handle it.
-
+
* cp-tree.def (FUNCTION_NAME): New tree node.
* cp-tree.h (current_function_name_declared): Tweak documentation.
(lang_decl_flags): Add pretty_function_p, adjust dummy.
even in template functions.
(setup_vtbl_ptr): Don't declare __PRETTY_FUNCTION in the
conditional scope at the top of a destructor.
-
+
* error.c (dump_function_decl): Use `[ with ... ]' syntax for
specializations too.
1999-11-15 Jason Merrill <jason@casey.cygnus.com>
* cp-tree.h, decl.c (compute_array_index_type): Make nonstatic.
- * pt.c (tsubst, case INTEGER_TYPE): Call it.
+ * pt.c (tsubst, case INTEGER_TYPE): Call it.
Check uses_template_parms.
* class.c (finish_struct): If we're a local class in a template
* cp-tree.h: Declare it.
* decl2.c (finish_vtable_vardecl): Override TYPE_DECL_SUPPRESS_DEBUG
if we're writing out the vtable.
- * decl.c, search.c (dfs_debug_mark, dfs_debug_unmarked_p,
+ * decl.c, search.c (dfs_debug_mark, dfs_debug_unmarked_p,
note_debug_info_needed): #if 0 out.
1999-11-14 Mark Mitchell <mark@codesourcery.com>
TREE_PERMANENT.
* decl.c (pushdecl): Set DECL_LOCAL_FUNCTION_P.
* decl2.c (lookup_arg_dependent): Use it.
-
+
* cp-tree.h (cp_finish_decl): Change prototype.
(finish_static_data_member_decl): Likewise.
(push_permanent_obstack): Remove declaration.
(push_expression_obstack): Remove.
(push_permanent_obstack): Likewise.
* typeck.c (mark_addressable): Likewise.
-
+
1999-11-13 Mark Mitchell <mark@codesourcery.com>
* call.c (build_conditional_expr): Use build_target_expr_with_type.
(structsp): Adjust.
* parse.c: Regenerated.
* pt.c (tsubst_enum): Adjust according to build_enumerator changes.
-
+
Wed Nov 10 12:43:21 1999 Philippe De Muyter <phdm@macqel.be>
Kaveh R. Ghazi <ghazi@caip.rutgers.edu>
* pt.c (tsubst_expr): Don't suspend_momentary or resume_momentary.
* semantics.c (begin_new_placement): Remove.
(finish_new_placement): Likewise.
-
+
1999-11-05 Martin v. Löwis <loewis@informatik.hu-berlin.de>
* cp-tree.h (VAR_TEMPL_TYPE_OR_FUNCTION_DECL_CHECK): New macro.
* pt.c (tinst_level_tick): Make it static.
(last_template_error_tick): Likewise.
-
+
* cp-tree.h (mapcar): Remove declaration.
(search_tree): Likewise.
(walk_tree_fn): New typedef.
(check_default_argument): Use walk_tree.
* pt.c (for_each_template_parm_r): New function, split out from ...
(for_each_template_parm): Here. Use it, via walk_tree.
-
+
1999-11-03 Mark Mitchell <mark@codesourcery.com>
* class.c (check_bitfield_decl): New function, split out from
anonymous structs.
(finish_struct_1): Use them.
* cp-tree.h (ANON_UNION_TYPE_P): New macro.
-
+
1999-11-02 Mark Mitchell <mark@codesourcery.com>
* decl.c (grokfndecl): Remove dead code.
function. Clear DECL_SAVED_TREE after generating RTL for a
function.
* Makefile.in (semantics.o): Depend on ggc.h.
-
+
1999-10-29 Mark Mitchell <mark@codesourcery.com>
* cp-tree.h (make_typename_type): Change prototype.
* pt.c (convert_template_argument): Pass complain to
make_typename_type.
(tsubst): Likewise.
-
+
1999-10-28 Mark Mitchell <mark@codesourcery.com>
* semantics.c (finish_handler): End the scope of the handler
(do_pushlevel): Likewise.
(do_poplevel): Likewise.
* tree.c (make_temp_vec): Remove.
-
+
* dump.c (dequeue_and_dump): Dump HANDLERs and SAVE_EXPRs. Dump
CLEANUP_P for a TRY_BLOCK.
* ir.texi: Document SAVE_EXPR.
* call.c (build_over_call): Check that the built-in function is
of class BUILT_IN_NORMAL before trying to recongize it as BUILT_IN_ABS.
- * typeck.c (build_function_call_real): Similarly.
+ * typeck.c (build_function_call_real): Similarly.
1999-10-26 Mark Mitchell <mark@codesourcery.com>
1999-10-24 Mark Mitchell <mark@codesourcery.com>
* decl.c (push_overloaded_decl_1): Use pushdecl.
-
+
* decl.c (auto_function): Replace #ifdef'd __inline with just
plain inline.
* lex.c (my_get_run_time): Likeise.
(issue_ktype): Likewise.
* parse.y (empty_parms): Likewise.
* parse.c: Regenerated.
-
+
1999-10-21 Mark Mitchell <mark@codesourcery.com>
* dump.c (dequeue_and_dump): Replace several uses of
(do_pushlevel): Use it.
(do_poplevel): Use it.
(expand_stmt): Check SCOPE_PARTIAL_P.
-
+
* cp-tree.def (EMPTY_CLASS_EXPR): New tree node.
* call.c (build_call): Use EMPTY_CLASS_EXPR instead of RTL_EXPR.
* expr.c (cplus_expand_expr): Expand it.
* ir.texi: Document EMPTY_CLASS_EXPR.
-
+
1999-10-20 Mark Mitchell <mark@codesourcery.com>
* cp-tree.h (DECL_NAMESPACE_SCOPE_P): Don't treat template
* dump.c (dequeue_and_dump): Handle CLEANUP_POINT_EXPR.
* ir.texi: Clean up documentation of RETURN_INIT.
-
+
1999-10-15 Greg McGary <gkm@gnu.org>
* lex.c (lang_init_options): Set flag_bounds_check as "unspecified".
* cp-tree.h (build_x_va_arg): Prototype new function.
* call.c (build_x_va_arg): Define it.
* parse.y (unary_expr): Call build_x_va_arg.
-
+
* cp-tree.h (convert_type_from_ellipsis): Prototype new function.
* call.c (convert_type_from_ellipsis): Define it.
* decl.c (init_decl_processing): Set lang_type_promotes_to.
1999-10-09 Mark Mitchell <mark@codesourcery.com>
- * cp-tree.h (make_rtl_for_local_static): New function.
+ * cp-tree.h (make_rtl_for_local_static): New function.
* decl.c (make_rtl_for_nonlocal_decl): Move code to create RTL for
local statics ...
(make_rtl_for_local_static): Here.
* semantics.c (expand_stmt): Use make_rtl_for_local_static.
-
+
1999-10-08 Kaveh R. Ghazi <ghazi@caip.rutgers.edu>
* method.c: Include tm_p.h.
* cp-tree.h (cp_make_lake_type): Renamed from make_lang_type.
* lex.c (cp_make_lake_type): Likewise.
* tree.c (init_tree): Init make_lang_type_fn.
-
+
1999-10-07 Mark Mitchell <mark@codesourcery.com>
* pt.c (tsubst_expr): Set DECL_TEMPLATE_INSTANTIATED for a catch
parameter.
-
+
* semantics.c (expand_stmt): Don't pretend to have asmspecs for
local statics if we don't really have them.
(expand_upcast_fixups): Likewise.
* typeck.c (build_component_ref): Likewise.
(build_binary_op_nodefault): Likewise.
-
+
* dump.c (dqueue_and_dump): Dump TYPE_VFIELD.
* ir.texi: Document TYPE_VFIELD.
(dequeue_and_dump): Unconditionally print children. Adjust calls
to functions mentioned above.
(dump_node): Pass DUMP_NONE, instead of DUMP_CHILDREN to queue.
-
+
* ir.texi: Document BIND_EXPR, LOOP_EXPR, and EXIT_EXPR.
* dump.c (dequeue_and_dump): Dump them.
-
+
* method.c (synthesize_method): Call setup_vtbl_ptr for destructors.
* decl.c (start_function): Set current_in_charge_parm for
constructors, too, where appropriate.
* search.c (fixup_all_virtual_upcast_offsets): New function.
(expand_indirect_vtbls_init): Use it.
-
+
1999-10-04 Nathan Sidwell <nathan@acm.org>
* decl2.c (grok_alignof): Don't decay lvalues.
-
+
* init.c (build_new): Remove unused variable.
1999-10-04 Mark Mitchell <mark@codesourcery.com>
(static_labelno): Remove macro.
* method.c (build_overload_nested_name): Make static_labelno
static here.
-
+
* pt.c (instantiate_decl): Use DECL_SAVED_TREE, not DECL_INITIAL,
to decide whether or not a function is defined.
(building_stmt_tree): Simplify.
* decl.c (mark_stmt_tree): New function.
(mark_saved_scope): Use it.
- (start_function): Rearrange slightly to call begin_stmt_tree
+ (start_function): Rearrange slightly to call begin_stmt_tree
earlier.
(save_function_data): Tweak.
(finish_function): Adjust call to finish_stmt_tree.
(finish_stmt_tree): Likewise.
* tree.c (search_tree): Don't handle VEC_INIT_EXPR.
(mapcar): Likewise.
-
+
* parse.y (simple_stmt): Don't call finish_stmt unnecessarily.
* parse.c: Regenerated.
-
+
* dump.c (dqueue_and_dump): Dump bitfieldness.
-
+
* tree.c (lvalue_p_1): Use DECL_C_BIT_FIELD to check for
bitfields, rather than DECL_BIT_FIELD.
* ir.texi: Document how to tell whether or not a field is a
bitfield.
-
+
* lex.c (make_lang_type): Fix typo in comment.
1999-10-01 Jason Merrill <jason@yorick.cygnus.com>
(DECL_GLOBAL_CTOR_P, DECL_GLOBAL_DTOR_P): New macros.
(GLOBAL_INIT_PRIORITY): Likewise.
* decl.c (lang_mark_tree): Adjust accordingly.
- (start_objects): Set DECL_GLOBAL_CTOR_P, DECL_GLOBAL_DTOR_P,
+ (start_objects): Set DECL_GLOBAL_CTOR_P, DECL_GLOBAL_DTOR_P,
and GLOBAL_INIT_PRIORITY.
* dump.c (dequeue_and_dump): Print them.
* ir.texi: Document them.
(prune_vars_needing_no_initialization): New function.
(write_out_vars): Likewise.
(finish_file): Use the various new functions instead of the old.
-
+
Thu Sep 30 00:13:27 1999 Dirk Zoller <duz@rtsffm.com>
* cp-tree.h (warn_float_equal): Declare.
(TMPL_ARG, SET_TMPL_ARG, NUM_TMPL_ARGS, TMPL_PARMS_DEPTH): Likewise.
(tsubst_copy): Clarify variable name.
(most_general_template): Robustify.
-
+
1999-09-29 Nathan Sidwell <nathan@acm.org>
* error.c (dump_template_parms): Don't use TS_PEDANTIC_NAME
* semantics.c: Include flags.h.
(expand_body): Don't do RTL generation if -fsyntax-only.
* Makefile.in (semantics.o): Depends on flags.h.
-
+
1999-09-28 Gabriel Dos Reis <gdr@codesourcery.com>
* pt.c (most_general_template): Adjust declaration.
(cplus_expand_expr): Don't call expand_throw here.
* Makefile.in (expr.o): Depend on except.h.
* ir.texi: Update documentation for THROW_EXPR.
-
+
* decl.c (start_function): Set x_dont_save_pending_sizes rather
than calling get_pending_sizes.
* init.c (build_new): Don't save and restore
function split out from c_expand_return.
(check_return_expr): Likewise.
(c_expand_return): Just generate the RTL for the return.
-
+
1999-09-24 Mark Mitchell <mark@codesourcery.com>
* cp-tree.h (CPTI_CLEANUP_TYPE): New macro.
(make_rtl_for_nonlocal_decl): Don't fuss with obstacks. Simplify.
Don't accidentally make RTL for local declarations.
(emit_local_var): Handle declarations with asm-specifiers here.
-
+
1999-09-23 Mark Mitchell <mark@codesourcery.com>
* ir.texi: Improve documentation for TARGET_EXPRs. Discuss
in function-at-a-time mode.
(finish_objects): Likewise.
(generate_ctor_or_dtor_function): Adjust accordingly.
-
+
* cp-tree.h (DECL_ANON_UNION_ELEMS): New macro.
* decl2.c (finish_anon_union): Set DECL_ANON_UNION_ELEMS.
Don't call expand_anon_union_decl here
* semantics.c (exapnd_stmt): Call it here, instead.
* typeck.c (mark_addressable): Addressed variables are implicitly
used.
-
+
1999-09-23 Martin v. Löwis <loewis@informatik.hu-berlin.de>
* cp-tree.h (VAR_OR_FUNCTION_DECL_CHECK): New macro.
(RECORD_OR_UNION_TYPE_CHECK, LANG_IDENTIFIER_CAST): Likewise.
(DEFARG_NODE_CHECK): Remove; replace with DEFAULT_ARG_CHECK.
* cp-tree.h: Add tree checking macros to various tree access
- macros.
+ macros.
* ptree.c (print_lang_decl): Test for function or variable
before accessing template info.
* lang-specs.h: If -fshort-wchar, override __WCHAR_TYPE__.
* decl2.c (lang_f_options): Add -fshort-wchar.
* cp-tree.h: Declare flag_short_wchar.
- * decl.c (init_decl_processing): If -fshort-wchar, use 'short unsigned
+ * decl.c (init_decl_processing): If -fshort-wchar, use 'short unsigned
int' for wchar_t.
1999-09-23 Martin v. Löwis <loewis@informatik.hu-berlin.de>
* typeck.c (build_modify_expr): Don't check for assignments to
this.
(c_expand_return): Don't suggest assigning to `this'.
-
+
* Makefile.in (decl.o): Depend on RTL_H.
(decl2.o): Likewise.
(class.o): Likewise.
* ir.texi (CTOR_INITIALIZER): Remove mention. Fix typo. Add
detail about the statement-tree.
-
+
1999-09-20 Nathan Sidwell <nathan@acm.org>
* parse.y (primary): Use build_functional_cast for CV_QUALIFIER.
1999-09-18 Paul Burchard <burchard@pobox.com>
* gxxint.texi: G++ now implements namespaces.
-
+
1999-09-18 Mark Mitchell <mark@codesourcery.com>
* decl.c (pop_label): Don't warn about unused labels more than
1999-09-17 Mark Mitchell <mark@codesourcery.com>
- Turn on function-at-a-time processing.
+ Turn on function-at-a-time processing.
* cp-tree.h (doing_semantic_analysis_p): New macro.
(SF_DEFAULT): Define to zero, not SF_EXPAND.
(start_handler_parms): Change prototype.
(begin_catch_block): Declare.
(finish_handler): Change prototype.
(do_pushlevel): Declare.
- (do_poplevel): Likewise.
+ (do_poplevel): Likewise.
* decl.c (pushlevel): Don't create
binding levels when not doing semantic analysis.
(poplevel): Don't pop them.
(push_cp_function_context): Don't expand functions without an
explicit call to expand_body.
(mark_lang_function): Make eh_spec_try_block and
- x_scope_stmt_stack.
+ x_scope_stmt_stack.
* except.c (expand_end_eh_spec): Don't
declare.
(process_start_catch_block): Likewise.
(expand_exception_blocks): Simplify.
(start_anon_func): Use do_pushlevel.
(end_anon_func): Use do_poplvel. Call expand_body for the
- function.
- * expr.c (do_case): Don't call define_case_label.
+ function.
+ * expr.c (do_case): Don't call define_case_label.
* init.c (create_temporary_var): Set DECL_CONTEXT for local
- variables.
+ variables.
* method.c (emit_thunk): Call expand_body for the
thunk.
- (sythesize_method): Likewise.
+ (sythesize_method): Likewise.
* parse.y (handler_args): Give it ttype.
(eat_saved_input): Call expand_body.
(base_init): Use do_pushlevel.
(handler_args): Don't call expand_start_catch_block. Return the
catch parameter. * pt.c (tsubst_expr): Adjust HANDLER handling.
* parse.c: Regenerated.
- * rtti.c (synthesize_tinfo_fn): Call finish_function.
+ * rtti.c (synthesize_tinfo_fn): Call finish_function.
* semantics.c (do_pushlevel): Give it external linkage. Build
SCOPE_STMTs.
(do_poplevel): Likewise.
HANDLERs. Handle SCOPE_STMT, CTOR_INITIALIZER, and RETURN_INIT.
(expand_body): Let expand_stmt handle CTOR_INITIALIZER,
RETURN_INIT and function try blocks.
-
+
* cp-tree.h (language_function): Add x_eh_spec_try_block. Add
x_scope_stmt_stack. Add x_in_charge_parm.
(current_eh_spec_try_block): New macro.
* Makefile.in (CONFLICTS): Adjust.
1999-09-17 Gabriel Dos Reis <gdr@codesourcery.com>
-
+
* error.c: Reduce code duplication.
(dump_template_value): New function.
(dump_type_real): Use it.
problems with extern "C" functions redeclared as static.
(duplicate_decls): When a builtin is redeclared static, make the
new function have internal linkage.
-
+
1999-09-15 Mark Mitchell <mark@codesourcery.com>
* decl2.c (build_expr_from_tree): Handle VA_ARG_EXPR.
1999-09-14 Mark Mitchell <mark@codesourcery.com>
- * decl.c (build_target_expr): Set TREE_SIDE_EFFECTS on the
+ * decl.c (build_target_expr): Set TREE_SIDE_EFFECTS on the
TARGET_EXPR.
* call.c (build_over_call): Don't set TREE_SIDE_EFFECTS on
the TARGET_EXPR.
* cvt.c (build_up_reference): Likewise.
* tree.c (build_cplus_new): Likewise.
(get_target_expr): Likewise.
-
+
Tue Sep 14 01:45:10 1999 Marc Espie <espie@cvs.openbsd.org>
* Makefile.in: Prepend $(SHELL) to move-if-change calls.
* error.c (dump_expr): Handle OVERLOADs.
* spew.c (probe_obstack): Remove.
* typeck.c (condition_conversion): Use perform_implicit_conversion.
-
+
1999-09-12 Bernd Schmidt <bernds@cygnus.co.uk>
* cp-tree.h (auto_function, define_function): Adjust prototypes.
non-permanent CONSTANTs and STRINGs.
* tree.c (build_cplus_array_type_1): Don't fuss with
TREE_PERMANENT on ARRAY_TYPEs.
-
+
* cp-tree.def (CLEANUP_STMT): New node.
* cp-tree.h (language_function): Add name_declared.
(current_function_name_declared): New macro.
* semantics.c (begin_compound_stmt): Call declare_function_name,
if appropriate.
(finish_decl_cleanup): New function.
- (expand_stmt): Use emit_local_var to output variables.
+ (expand_stmt): Use emit_local_var to output variables.
(expand_body): Set current_function_name_declared.
-
+
1999-09-10 Mark Mitchell <mark@codesourcery.com>
* cp-tree.h (finish_cleanup_try_block): New function.
(finish_do_stmt): Likewise.
(finish_for_cond): Likewise.
(expand_cond): Adjust.
-
+
* cp-tree.h (FN_TRY_BLOCK_P): New macro.
* init.c (perform_member_init): Remove obstack machinations.
(expand_cleanup_for_base): Likewise.
* pt.c (tsubst_expr): Handle various kinds of try blocks.
* semantics.c (expand_stmts): Remove.
(begin_function_try_block): Set FN_TRY_BLOCK_P.
- (finish_function_try_block): Be careful rechaining
+ (finish_function_try_block): Be careful rechaining
function try blocks.
(expand_stmt): Loop through all the statements at a given level.
(exapnd_body): Be careful with line-numbers here too. Prepare for
* semantics.c (RECHAIN_STMTS): Remove `last' parameter.
(RECHAIN_STMTS_FROM_LAST): Remove. Replace all uses with
- RECHAIN_STMTS.
+ RECHAIN_STMTS.
(RECHAIN_STMST_FROM_CHAIN): Likewise.
* parse.y (simple_stmt): Fix typo in last change.
(finish_stmt_tree): Tweak line-number handling.
(prep_stmt): New function.
(expand_stmt): Use it.
-
+
* cp-tree.h (begin_switch_stmt): Adjust prototype.
(finish_switch_cond): Likewise.
* parse.y (simple_stmt): Adjust accordingly.
(language_function): Rename binding_level to bindings.
(cp_function_chain): Use the current_function, not the
outer_function_chain.
- (current_class_ptr): Make it work, even when there's no
+ (current_class_ptr): Make it work, even when there's no
current function.
(current_class_ref): Likewise.
- (SF_DEFAULT, SF_PRE_PARSED, SF_INCLASS_INLINE, SF_EXPAND): New
+ (SF_DEFAULT, SF_PRE_PARSED, SF_INCLASS_INLINE, SF_EXPAND): New
macros.
(clear_temp_name): Remove.
* decl.c (check_function_type): New function, broken out from
* decl2.c (clear_temp_name): Remove.
(start_objects): Use SF flags to start_function.
(start_static_storage_duration_function): Likewise.
- * except.c (start_anon_func): Remove redundant calls to
+ * except.c (start_anon_func): Remove redundant calls to
push_function_context_to. Use SF flags to start function.
(end_anon_func): Remove redundant call to pop_function_context
from.
- * lex.c (reinit_parse_for_function): Don't initialize per-function
+ * lex.c (reinit_parse_for_function): Don't initialize per-function
data.
* method.c (emit_thunk): Clear current_function after calling
assemble_end_function. Use SF flags for start_function.
* rtti.c (sythesize_tinfo_fn): Use SF flags to start_function.
* semantics.c (begin_function_definition): Likewise.
(expand_body): Likewise.
-
+
1999-09-09 Nathan Sidwell <nathan@acm.org>
* cp-tree.h (convert_to_void): Prototype new function.
(build_static_cast): Likewise.
(build_c_cast): Likewise.
* semantics.c (finish_expr_stmt): Do not decay full expressions.
-
+
* typeck.c (build_x_compound_expr): Add FIXME.
1999-09-08 Mark Mitchell <mark@codesourcery.com>
* typeck.c: Likewise.
* parse.c: Regenerated.
* tree.c (build_srcloc): Simplify.
-
+
1999-09-08 Bruce Korb autogen@linuxbox.com
* Makefile.in: Give the gperf user a hint about why "gperf -F" fails.
(retrofit_lang_decl): Likewise.
(copy_lang_decl): Likewise.
- * cp-tree.h (saved_scope): Remove old_binding_level and
+ * cp-tree.h (saved_scope): Remove old_binding_level and
function_decl. Tidy up.
* decl.c (mark_saved_scope): Don't set them.
(maybe_push_to_top_level): Clear memory.
(grokvardecl): Don't complete types here.
* decl.c (start_function): Clear last_dtor_insn and
- last_parm_cleanup_insn.
+ last_parm_cleanup_insn.
(push_cp_function_context): Just copy over a little of
the old context, not all of it.
* typeckc.c (build_static_cast): Likewise.
(build_reinterpret_cast): Likewise.
(build_const_cast): Likewise.
-
+
1999-09-07 Mark Mitchell <mark@codesourcery.com>
* decl.c (ggc_p): Set it to 1.
(binding_init): Remove.
(init_cplus_unsave): Rename to ...
(init_tree): This. Add GC roots.
-
+
1999-09-05 Mark Mitchell <mark@codesourcery.com>
Get ready for garbage collection.
(cp_global_trees): Add access_default, access_public,
access_protected, access_private, access_default_virtual,
access_public_virtual, access_protected_virtual,
- access_private_virtual, ctor_identifier, delta2_identifier,
+ access_private_virtual, ctor_identifier, delta2_identifier,
delta_identifier, dtor_identifier, in_charge_identifier,
index_identifier, nelts_identifier, this_identifier,
pfn_identifier, pfn_or_delta2_identifier, vptr_identifier,
* decl2.c: Don't include varray.h.
(current_namespace): Remove.
(init_decl2): Add GC roots.
- * except.c (Terminate): Remove.
+ * except.c (Terminate): Remove.
(init_exception_processing): Use terminate_node instead.
(build_terminate_handler): Likewise.
* init.c (nc_nelts_field_id): Remove.
(expand_indirect_vtbls_init): Remove redundant declaration of
in_charge_identifier.
(init_search_processing): Use vptr_identifier.
-
+
1999-09-05 Richard Henderson <rth@cygnus.com>
Bernd Schmidt <bernds@cygnus.co.uk>
Mark Mitchell <mark@codesourcery.com>
(init_init_processing): Add GC roots.
* parse.y: Include ggc.h.
(cp_parse_init): New function.
-
+
1999-09-04 Mark Mitchell <mark@codesourcery.com>
* decl.c (init_decl_processing): Set mark_lang_status.
x_base_init_list, x_member_init_list, x_base_init_expr,
x_current_class_ptr, x_current_class_ref, x_last_tree,
x_last_expr_type, x_last_dtor_insn, x_last_parm_cleanup_insn, and
- x_result_rtx.
+ x_result_rtx.
(dtor_label, ctor_label, current_base_init_list,
current_member_init_list, base_init_expr, current_class_ptr,
current_class_ref, last_tree, last_expr_type): Adjust accordingly.
(mark_false_label_stack): Likewise.
(lang_mark_tree): Likewise.
(lang_cleanup_tree): Likewise.
-
+
1999-09-03 Mark Mitchell <mark@codesourcery.com>
* Makefile.in (CXX_TREE_H): Include function.h.
pop_cp_function_context.
* init.c: Don't include function.h.
* lex.c (begin_definition_of_inclass_inline): Call
- push_function_context_to, not push_cp_function_context.
+ push_function_context_to, not push_cp_function_context.
(process_next_inline): Call pop_function_context_from, not
pop_cp_function_context.
* method.c: Don't include function.h.
push_cp_function_context. Call pop_function_context_from, not
pop_cp_function_context.
* typeck.c: Don't include function.h.
-
+
* decl.c (expand_static_init): Tweak handling of static
initializations for objects without constructors.
(last_expr_type): Likewise.
* typeck.c (dtor_label): Likewise.
(ctor_label): Likewise.
-
+
1999-09-01 Alex Samuel <samuel@codesourcery.com>
* decl2.c (arg_assoc_template_arg): New prototype. New function.
(arg_assoc_class): Use arg_assoc_template_arg for template
- arguments.
+ arguments.
(arg_assoc): Likewise.
* pt.c (mangle_class_name_for_template): Allow member template
template arguments.
(tsubst_expr): Adjust calls to expand_start_catch_block
appropriately.
* semantics.c (expand_stmt): Likewise.
-
+
1999-08-29 Alex Samuel <samuel@codesourcery.com>
* pt.c (push_template_decl_real): Use template declaration from
* pt.c (tsbust_expr): Fix indentation. Call cp_finish_decl here.
* semantics.c (expand_stmt): Don't call cp_finish_decl here. Just
call initialize_local_var to generate initialization code.
-
+
1999-08-29 Kaveh R. Ghazi <ghazi@caip.rutgers.edu>
* cp-tree.h (fndecl_as_string, type_as_string,
(make_rtl_for_nonlocal_decl): Likewise.
(cp_finish_decl): Use them.
* typeck.c (strip_array_types): New function.
-
+
* cp-tree.def (LABEL_STMT): New tree node.
* cp-tree.h (LABEL_STMT_LABEL): New macro.
(shadow_label): Remove.
building_stmt_tree.
(finish_label_decl): New function.
(expand_stmt): Handle LABEL_STMTs and local label declarations.
-
+
1999-08-26 Mark Mitchell <mark@codesourcery.com>
* decl.c (lookup_label): Build labels on the permanent obstack
(expand_stmt): Adjust accordingly.
* pt.c (tsubst_expr); Likewise.
(do_decl_instantiation): Robustify.
-
+
* cp-tree.h (AGGR_INIT_VIA_CTOR_P): New macro.
* tree.c (build_cplus_new): Set it.
* expr.c (cplus_expand_expr): Use it.
* dump.c (deque_and_dump): Handle AGGR_INIT_EXPR.
-
+
* decl.c (store_parm_decls): Reset immediate_size_expand.
(finish_function): Likewise.
-
+
* tree.c (cplus_unsave_expr_now): Don't return a value.
* semantics.c (do_poplevel): Always initialize the return value.
* typeck.c (build_modify_expr): Don't build an RTL_EXPR.
* typeck2.c (store_init_value): Change expand_aggr_init to
build_aggr_init in comment.
-
+
1999-08-25 Mark Mitchell <mark@codesourcery.com>
* dump.c (dequeue_and_dump): Dump TARGET_EXPRs.
* dump.c (dump_next_stmt): New function.
(dequeue_and_dump): Use it.
-
+
* pt.c (tsubst_copy): Make sure to initialize return value for a
STMT_EXPR, even when processing_template_decl.
* semantics.c (finish_stmt_expr): A statement-expression whose
- last statement is not an expression-statement has type `void'.
-
+ last statement is not an expression-statement has type `void'.
+
1999-08-20 Mark Mitchell <mark@codesourcery.com>
* semantics.c (finish_stmt_expr): Fix typo in comment.
BIND_EXPR permanent.
* pt.c (register_specialization): Don't register a specialization
more than once.
-
+
1999-08-18 Andrew Haley <aph@cygnus.com>
* method.c (process_overload_item): Call build_mangled_C9x_name ()
(tsubst_copy): Likewise.
* tree.c (search_tree): Likewise.
* semantics.c (finish_pseudo_destructor_call): Create it.
-
+
1999-08-18 Mark Mitchell <mark@codesourcery.com>
* search.c (setup_class_bindings): Robustify.
(build_lang_field_decl): Likewise.
(copy_lang_decl): Use CAN_HAVE_FULLLANG_DECL_P to decide how much
to copy.
-
+
* cp-tree.def (STMT_EXPR): New tree node.
* cp-tree.h (STMT_EXPR_STMT): New macro.
(store_return_init): Change prototype.
sorry, if an unsupported node is encountered.
* typeck.c (require_complete_type_in_void): Handle BIND_EXPR.
(c_expand_return): Don't call add_tree here.
-
+
1999-08-15 Mark Mitchell <mark@codesourcery.com>
* pt.c (check_default_tmpl_args): Don't check in local scopes.
obstack. Clear DECL_DEAD_FOR_LOCAL when making a copy of a local
variable.
(tsubst_expr): Adjust now that DECL_STMTs really contain DECLs.
-
+
1999-08-14 Jason Merrill <jason@yorick.cygnus.com>
Speed up Koenig lookup.
to return namespaces we've looked at.
* decl2.c (lookup_using_namespace): Likewise.
(add_function): Don't call ovl_member.
- (lookup_arg_dependent): Initialize k.namespaces to the list of
+ (lookup_arg_dependent): Initialize k.namespaces to the list of
namespaces seen in unqualified lookup.
* call.c (equal_functions): Move here from tree.c.
(joust): Use it to handle duplicate candidates.
(push_permanent_obstack): Define.
(mark_addressable): Use it.
* typeck.c (mark_addressable): Likewise.
-
+
1999-08-13 Gavin Romig-Koch <gavin@cygnus.com>
* cp-tree.h (init_cplus_unsave): New.
* dump.c (queue): Be careful when computing bitmasks.
(dequeue_and_dump): Describe binfos as binfos, not as
vectors.
-
+
* parse.y (pedantic): Give it itype. Adjust usage accordingly
- throughout.
+ throughout.
* parse.c: Regenerated.
-
+
* Make-lang.in (CXX_SRCS): Remove sig.c.
* Makefile.in (CXX_OBJS): Remove sig.o.
(sig.o): Remove.
* hash.h: Regenerated.
* init.c (build_new_1): Remove support for signatures.
* lang-options.h: Remove -fhandle-signatures,
- -fno-handle-signatures.
+ -fno-handle-signatures.
* lex.c (init_parse): Remove support for signatures.
(yyprint): Likewise.
* lex.h (rid): Remove RID_SIGNATURE.
* method.c (build_decl_overload_real): Remove support for
- signatures.
+ signatures.
(hack_identifier): Likewise.
* parse.y (base_class): Likewise.
(base_class.1): Likewise.
(build_x_arrow): Likewise.
(build_functional_cast): Likewise.
* xref.c (GNU_xref_decl): Likewise.
-
+
1999-08-10 Martin v. Loewis <martin@mira.isdn.cs.tu-berlin.de>
* lex.c (do_identifier): Remove unnecessary lookup of class field.
* search.c (binfo_from_vbase): New fn.
* cp-tree.h: Declare it.
* cvt.c (cp_convert_to_pointer): Use it to diagnose conversion
- from pointer to member of virtual base.
+ from pointer to member of virtual base.
* typeck.c (get_delta_difference): Likewise.
1999-08-06 Alexandre Oliva <oliva@dcc.unicamp.br>
`1', `2', and `<'; handle them generically. Don't be sorry about
"unrecognized tree codes"; just abort.
(no_linkage_check): Don't do linkage checks for templates.
-
+
* tree.c (cp_build_qualified_type_real): Handle
pointer-to-member-function types correctly.
1999-08-05 Jason Merrill <jason@yorick.cygnus.com>
- * decl.c (pushdecl): Only give an error for shadowing a parm
+ * decl.c (pushdecl): Only give an error for shadowing a parm
from *this* function.
Thu Aug 5 02:40:42 1999 Jeffrey A Law (law@cygnus.com)
specifiers.
(comptypes): Adjust for comp_except_specs.
* typeck2.c (add_exception_specifier): New global function.
-
+
* class.c (check_for_override): Reword error message.
1999-08-03 Nathan Sidwell <nathan@acm.org>
(tsubst_expr): Use STMT_LINENO.
* semantics.c (finish_asm_stmt): Eliminate duplicate code. Check
for invalid cv-qualifiers even while building templates.
-
+
1999-08-02 Richard Henderson <rth@cygnus.com>
* call.c: Include defaults.h instead of expr.h.
(build_conditional_expr): Tweak.
(convert_like): Some BASE_CONVs really do require the generation
of code.
-
+
* init.c (perform_member_init): Don't go through build_modify_expr
for simple initializations.
* tree.c (debug_binfo): Likewise.
* decl2.c (mark_vtable_entries): Don't bash abstract virtuals to
__pure_virtual here.
-
+
1999-07-26 Mark Mitchell <mark@codesourcery.com>
* tree.c (build_cplus_new): Adjust call to abstract_virtuals_error
(build_binary_op_nodefault): Use null_ptr_cst_p.
(build_conditional_expr): Remove.
(convert_for_assignment): Use new conversion functions.
-
+
* cp-tree.h (abstract_virtuals_error): Change declaration.
* typeck2.c (abstract_virtuals_error): Check to see if an error
occurred, and return a boolean value accordingly.
* pt.c (unify): Don't get confused by pointers-to-member functions.
* search.c (build_cplus_new): Robustify.
-
+
1999-07-24 Richard Henderson <rth@cygnus.com>
* gxx.gperf (__builtin_va_arg): New.
(lvalue_p): Likewise.
(build_cplus_new): Don't allow the creation of an abstract class.
* typeck.c (convert_for_initialization): Use initialize_reference.
-
+
1999-07-21 Gavin Romig-Koch <gavin@cygnus.com>
* lex.c (real_yylex) : Correct the test for overflow when lexing
* Makefile.in (INTERFACE): Bump to 2.
1999-07-17 Alexandre Oliva <oliva@dcc.unicamp.br>
-
+
* typeck2.c (my_friendly_abort): Updated URL with bug reporting
instructions to gcc.gnu.org. Removed e-mail address.
* class.c (method_name_cmp): New function.
(finish_struct_methods): Modified to support sorting and searching
methods.
- (finish_struct_anon): Changed code in inner loop to use ELT rather
+ (finish_struct_anon): Changed code in inner loop to use ELT rather
than UELT (which required an extra indirection for every reference).
(field_decl_cmp): New function to support sorting FIELD_DECLs.
(finish_struct_1): Sort fields.
initial declaration, then don't save the inline info and by all
means don't mark the function as a builtin function.
- * decl.c (lookup_name_real): Set NONCLASS to 1 if
+ * decl.c (lookup_name_real): Set NONCLASS to 1 if
CURRENT_CLASS_TYPE is 0.
* class.c (duplicate_tag_error): Set TYPE_NONCOPIED_PARTS to
(init_decl_processing): Handle/use the two new types.
* lex.c (real_yylex): Same.
* typeck.c (unsigned_type,signed_type,signed_or_unsigned_type) :
- Same.
+ Same.
1999-07-01 Mark Mitchell <mark@codesourcery.com>
* error.c (dump_type_real): Handle TREE_LIST again.
- * typeck.c (comp_target_parms): Don't complain about
+ * typeck.c (comp_target_parms): Don't complain about
converting from () to (...) if !flag_strict_prototype.
* decl.c (grokdeclarator): Update the names of all variants when
1999-06-21 Mark Mitchell <mark@codesourcery.com>
* init.c (expand_aggr_vbase_init): Rename to
- construct_virtual_bases. Conditionalize construction here,
+ construct_virtual_bases. Conditionalize construction here,
rather than ...
(emit_base_init): Here.
* error.c (dump_expr): Handle BIND_EXPR, LOOP_EXPR, and
EXIT_EXPR.
-
+
1999-06-18 Mark Mitchell <mark@codesourcery.com>
* init.c (expand_aggr_vbase_init): Add flag parameter.
(build_partial_cleanup_for): Remove, inlining into ..
(expand_cleanup_for_base): ... here. Take flag parameter.
(emit_base_init): Pass the in_chrg parameter to
- emit_aggr_vbase_init.
+ emit_aggr_vbase_init.
(emit_aggr_vbase_init): Pass it to expand_cleanup_for_base.
-
+
1999-06-16 Mark Mitchell <mark@codesourcery.com>
* decl2.c (import_export_decl): Use same_type_p, rather than
(push_class_level_binding): Use push_cache_obstack, not
maybe_push_cache_obstack.
* search.c (push_class_decls): Likewise.
-
+
1999-06-14 Martin von Löwis <loewis@informatik.hu-berlin.de>
* pt.c (tsubst_friend_function): Push into namespace of friend
* tree.c (build_cplus_array_type_1): Use push_obstacks_nochange
and friends rather than messing with current_obstack directly.
(cp_build_qualified_type_real): Rework ARRAY_TYPE
- allocation to match practice throughout the rest of the
+ allocation to match practice throughout the rest of the
compiler.
1999-05-30 Mark Mitchell <mark@codesourcery.com>
(DECL_SAVED_TREE): Document.
(DECL_TEMPLATE_INJECT): Remove.
* class.c (finish_struct): Remove code to deal with
- DECL_TEMPLATE_INJECT.
+ DECL_TEMPLATE_INJECT.
* decl.c (maybe_process_template_type_declaration): Handle all new
types in templates uniformly.
forward-declarations.
(instantiate_class_template): Remove code processing
DECL_TEMPLATE_INJECT.
-
+
* pt.c (lookup_template_class): Tweak lookup to find member
templates.
ASM_CV_QUAL.
* semantics.c (finish_asm_stmt): Make strings permanent if they're
used in a template.
-
+
1999-05-25 Jason Merrill <jason@yorick.cygnus.com>
* typeck.c (casts_away_constness, casts_away_constness_r): Strip both
* decl2.c (mark_vtable_entries): Don't make a copy of a function,
and then make it look like `abort'. Just use `abort' instead.
-
+
* typeck.c (build_static_cast): Don't allow static_casts that cast
away constness.
(casts_away_constness_r): New function.
* lex.c (is_global): A template parameter isn't global.
* parse.y (class_head): Robustify.
* parse.c: Regenerated.
-
+
1999-05-22 Mark Mitchell <mark@codesourcery.com>
* pt.c (for_each_template_parm): Walk into TYPENAME_TYPEs,
INDIRECT_REFs, and COMPONENT_REFs. Handle FIELD_DECLs.
-
+
* cp-tree.h (push_nested_namespace): Declare.
(pop_nested_namespace): Likewise.
* decl.c (push_nested_namespace): New function.
1999-05-21 Mark Mitchell <mark@codesourcery.com>
Nathan Sidwell <nathan@acm.org>
-
+
* Make-lang.in (cc1plus): Make it depend on gxx.gperf.
* cp-tree.h: Fix typo in documentation on pointers-to-members.
(cp_build_qualified_type): Make it a macro.
(cp_build_qualified_type): Rename to ...
(cp_build_qualified_type_real): Add additional COMPLAIN parameter
and modify appropriately.
-
+
* typeck.c (build_ptrmemfunc): Handle PTRMEM_CSTs carefully to
reveal optimization opportunities.
* search.c (marked_pushdecls_p): Don't descend into
TEMPLATE_TYPE_PARMs and the like.
(unmarked_pushdecls_p): Likewise.
-
+
* call.c (build_over_call): Don't throw away
initializations/copies of empty classes; use MODIFY_EXPR and
INIT_EXPR as for non-empty classes.
convert_for_initialization): Likewise.
* class.c (instantiate_type): Handle seeing a baselink under an
OFFSET_REF.
- * error.c (dump_expr): Likewise.
+ * error.c (dump_expr): Likewise.
* pt.c (for_each_template_parm): Likewise.
(resolve_overloaded_unification): Likewise.
* tree.c (is_overloaded_fn, really_overloaded_fn): Likewise.
TREE_LIST for ambiguous lookups.
(setup_class_bindings): Adjust accordingly.
(push_class_decls): Revise out-of-date comments.
-
+
* typeck.c (build_const_cast): Tighten checks for legality.
1999-05-02 Martin von Löwis <loewis@informatik.hu-berlin.de>
other parsing fails.
(cp_parser_enclosed_template_argument_list): If the argument list is
parsed correctly, but the next token is '>>', emit a diagnostic.
- (cp_parser_next_token_ends_template_argument): Accept '>>' as
+ (cp_parser_next_token_ends_template_argument): Accept '>>' as
delimiter of template argument, it will be later detected as a typo.
2003-12-17 Kelley Cook <kcook@gcc.gnu.org>
PR c/13134
* decl.c (duplicate_decls): Copy visibility flag when appropriate.
-
+
2003-12-09 Giovanni Bajo <giovannibajo@gcc.gnu.org>
* init.c (build_new_1): Deal with an OVERLOAD set when
PR c++/11929
* call.c (magic_varargs_p): New fn.
- (build_over_call): Do no ellipsis conversions for arguments to
+ (build_over_call): Do no ellipsis conversions for arguments to
functions with magic varargs.
* name-lookup.c, init.c, except.c: Revert Giovanni's patch from
PR c++/13305
* parser.c (cp_parser_elaborated_type_specifier): Accept
attributes.
-
+
2003-12-05 Mark Mitchell <mark@codesourcery.com>
PR c++/13314
2003-12-02 Richard Henderson <rth@redhat.com>
* name-lookup.h (struct cp_binding_level): Use ENUM_BITFIELD.
- * parser.c (struct cp_token): Likewise.
+ * parser.c (struct cp_token): Likewise.
(struct cp_parser_token_tree_map_node): Likewise.
* lex.c (struct resword): Move const after ENUM_BITFIELD.
* decl.c (duplicate_decls): copy DECL_VISIBILITY field.
* method.c (use_thunk): give thunk same visibility as function.
* optimize.c (maybe_clone_body): copy DECL_VISIBILITY field.
-
+
2003-11-05 Kriang Lerdsuwanakij <lerdsuwa@users.sourceforge.net>
PR c++/11616
mangle a non-existant middle operator to the ?: operator.
2003-10-21 Robert Bowdidge <bowdidge@apple.com>
- * decl.c (cp_finish_decl): Remove clause intended for asm directives
+
+ * decl.c (cp_finish_decl): Remove clause intended for asm directives
in struct or class fields: this code is never executed.
2003-10-22 Kriang Lerdsuwanakij <lerdsuwa@users.sourceforge.net>
2003-10-13 Gabriel Dos Reis <gdr@integrable-solutions.net>
- Break out decl.c (2/n)
+ Break out decl.c (2/n)
* name-lookup.c: Include diagnostic.h
(cxx_binding_free): Make static.
(cxx_binding_make): Likewise.
(maybe_process_template_type_declaration): Likewise.
(pop_binding): Likewise.
* cp-tree.h: Move corresponding declarations to name-lookup.h
-
+
2003-10-12 Steven Bosscher <steven@gcc.gnu.org>
* cvt.c (ocp_convert): Move warning to C common code.
pp_cxx_flag_qualified_id and pp_cxx_flag_global_scope.
* cxx-pretty-print.c (pp_cxx_id_expression): Always display
qualified entities using qualified names.
-
+
PR c++/12337
* init.c (build_new_1): Make sure that the expression returned is
not an lvalue.
2003-10-03 Gabriel Dos Reis <gdr@integrable-solutions.net>
* name-lookup.c (binding_entry_free): Nullify name and type
- fields.
+ fields.
2003-10-02 Mark Mitchell <mark@codesourcery.com>
2003-09-30 Gabriel Dos Reis <gdr@integrable-solutions.net>
* decl.c (pop_binding): Don't mess with nullifying binding->scope
- here.
+ here.
* name-lookup.c: Re-format.
(cxx_binding_free): Nullify binding->scope.
2003-09-19 Gabriel Dos Reis <gdr@integrable-solutions.net>
* decl.c (cxx_scope_descriptor): Fix thinko.
- (struct cp_binding_level): Adjust type of binding_depth field.
+ (struct cp_binding_level): Adjust type of binding_depth field.
2003-09-18 Danny Smith <dannysmith@users.sourceforge.net>
2003-09-18 Gabriel Dos Reis <gdr@integrable-solutions.net>
* error.c (dump_type): Simplify. Use pp_type_specifier_seq for
- "C" types.
+ "C" types.
* cxx-pretty-print.c (pp_cxx_type_specifier_seq): Fix thinko.
2003-09-17 Richard Henderson <rth@redhat.com>
the various flags.
(set_block): Remove check for doing_semantic_analysis_p.
(pushlevel_class): Use "kind" field in binding_level, not
- the various flags.
+ the various flags.
(poplevel_class): Likewise.
(initial_push_namespace_scope): Likewise.
(maybe_push_to_top_level): Likewise.
(save_function-data): Do not set expanding_p.
(cxx_push_function_context): Do not clear expanding_p.
* semantics.c (cxx_expand_function_start): Do not set expanding_p.
-
+
2003-09-14 Mark Mitchell <mark@codesourcery.com>
* class.c (layout_class_type): Make DECL_MODE match TYPE_MODE for
2003-09-09 Richard Henderson <rth@redhat.com>
- * semantics.c (expand_or_defer_fn): Update call to
+ * semantics.c (expand_or_defer_fn): Update call to
cgraph_finalize_function.
* semantics.c (expand_or_defer_fn): Use cgraph_finalize_function
* error.c (dump_decl): Handle namespace-alias-definition.
* decl.c (warn_extern_redeclared_static): There is no point in
checking changes in storage class specifier for a namespace
- declaration.
+ declaration.
(duplicate_decls): Tidy diagnostic message.
* cxx-pretty-print.c (pp_cxx_left_brace): New macro.
(pp_cxx_right_brace): Likewise.
(push_class_binding): Likewise.
(set_identifier_type_value_with_scope): Likewise.
* name-lookup.c (supplement_binding): Rename from add_binding.
- Return a bool. Improve documentation.
+ Return a bool. Improve documentation.
(set_namespace_binding): Adjust.
* Make-lang.in (cp/name-lookup.o): Depend on toplev.h
PR c++/11811
* cxx-pretty-print.c (pp_cxx_canonical_template_parameter): New
- function.
+ function.
* cxx-pretty-print.h: Declare.
* error.c (dump_template_parameter): Use it.
(dump_type): Likewise.
* init.c (build_vec_delete_1): Convert 2nd argument to NE_EXPR to
the proper type.
-
+
2004-02-24 Jason Merrill <jason@redhat.com>
PR c++/13944
* call.c, cvt.c, init.c, typeck.c: Use TREE_NO_WARNING instead
of TREE_NO_UNUSED_WARNING.
* cvt.c (convert_to_void): Also use it for "has no effect" warning.
-
+
2004-01-30 Frank Ch. Eigler <fche@redhat.com>
* cp-mudflap.c (mflang_flush_calls): Mark static ctor as TREE_USED.
* cp-lang.c (LANG_HOOKS_CALLGRAPH_ANALYZE_EXPR): Kill.
* cp-tree.h (cxx_callgraph_analyze_expr): Kill.
* decl2.c (cxx_callgraph_analyze_expr): Kill.
-
+
2003-12-14 Jan Hubicka <jh@suse.cz>
* cp-lang.c (LANG_HOOKS_CALLGRAPH_ANALYZE_EXPR): Kill.
$(INCLUDES) $(srcdir)/cp/g++spec.c)
# Create the compiler driver for g++.
-GXX_OBJS = gcc.o g++spec.o intl.o prefix.o version.o
+GXX_OBJS = gcc.o g++spec.o intl.o prefix.o version.o
g++$(exeext): $(GXX_OBJS) $(EXTRA_GCC_OBJS) $(LIBDEPS)
$(CC) $(ALL_CFLAGS) $(LDFLAGS) -o $@ \
$(GXX_OBJS) $(EXTRA_GCC_OBJS) $(LIBS)
doc/g++.1: doc/gcc.1
cp doc/gcc.1 doc/g++.1
-c++.install-man: $(DESTDIR)$(man1dir)/$(GXX_INSTALL_NAME)$(man1ext)
+c++.install-man: $(DESTDIR)$(man1dir)/$(GXX_INSTALL_NAME)$(man1ext)
$(DESTDIR)$(man1dir)/$(GXX_INSTALL_NAME)$(man1ext): doc/g++.1 installdirs
-rm -f $@
* G++ no longer allows in-class initializations of static data members
that do not have arithmetic or enumeration type. For example:
- struct S {
+ struct S {
static const char* const p = "abc";
};
- is no longer accepted.
+ is no longer accepted.
Use the standards-conformant form:
- struct S {
+ struct S {
static const char* const p;
};
pointer to cv-qualified member function types.
* The C++ ABI has been changed to correctly handle this code:
-
+
struct A {
void operator delete[] (void *, size_t);
};
- struct B : public A {
+ struct B : public A {
};
new B[10];
The amount of storage allocated for the array will be greater than
it was in 3.0, in order to store the number of elements in the
array, so that the correct size can be passed to `operator delete[]'
- when the array is deleted. Previously, the value passed to
+ when the array is deleted. Previously, the value passed to
`operator delete[]' was unpredictable.
This change will only affect code that declares a two-argument
`operator delete[]' with a second parameter of type `size_t'
- in a base class, and does not override that definition in a
+ in a base class, and does not override that definition in a
derived class.
* The C++ ABI has been changed so that:
- struct A {
+ struct A {
void operator delete[] (void *, size_t);
void operator delete[] (void *);
};
are those whose types involve non-type template arguments whose
mangled representations require more than one digit.
-* Support for assignment to `this' has been removed. This idiom
+* Support for assignment to `this' has been removed. This idiom
was used in the very early days of C++, before users were allowed
to overload `operator new'; it is no longer allowed by the C++
standard.
* G++ previously allowed `sizeof (X::Y)' where Y was a non-static
member of X, even if the `sizeof' expression occurred outside
- of a non-static member function of X (or one of its derived classes,
+ of a non-static member function of X (or one of its derived classes,
or a member-initializer for X or one of its derived classes.) This
extension has been removed.
-* G++ no longer allows you to overload the conditional operator (i.e.,
+* G++ no longer allows you to overload the conditional operator (i.e.,
the `?:' operator.)
* The "named return value" extension:
-
+
int f () return r { r = 3; }
has been deprecated, and will be removed in a future version of G++.
*** Changes in EGCS 1.1:
-* Namespaces are fully supported. The library has not yet been converted
+* Namespaces are fully supported. The library has not yet been converted
to use namespace std, however, and the old std-faking code is still on by
default. To turn it off, you can use -fhonor-std.
http://www.cygnus.com/misc/wp/dec96pub/template.html#temp.res
- + Guiding declarations are no longer supported. Function declarations,
+ + Guiding declarations are no longer supported. Function declarations,
including friend declarations, do not refer to template instantiations.
You can restore the old behavior with -fguiding-decls until you fix
your code.
converting from a bound member function pointer to function
pointer).
- + A flag -Weffc++ has been added for violations of some of the style
+ + A flag -Weffc++ has been added for violations of some of the style
guidelines in Scott Meyers' _Effective C++_ books.
+ -Woverloaded-virtual now warns if a virtual function in a base
* __FUNCTION__ and __PRETTY_FUNCTION__ are now treated as variables by the
parser; previously they were treated as string constants. So code like
- `printf (__FUNCTION__ ": foo")' must be rewritten to
+ `printf (__FUNCTION__ ": foo")' must be rewritten to
`printf ("%s: foo", __FUNCTION__)'. This is necessary for templates.
* local static variables in extern inline functions will be shared between
translation units.
-* -fvtable-thunks is supported for all targets, and is the default for
+* -fvtable-thunks is supported for all targets, and is the default for
Linux with glibc 2.x (also called libc 6.x).
* bool is now always the same size as another built-in type. Previously,
* Joe Buck <jbuck@synopsys.com>, the maintainer of the g++ FAQ.
* Brendan Kehoe <brendan@cygnus.com>, who coordinates testing of g++.
* Jason Merrill <jason@cygnus.com>, the g++ maintainer.
-* Mark Mitchell <mmitchell@usa.net>, who implemented member function
+* Mark Mitchell <mmitchell@usa.net>, who implemented member function
templates and explicit qualification of function templates.
* Mike Stump <mrs@wrs.com>, the previous g++ maintainer, who did most of
the exception handling work.
/* Functions related to invoking methods and overloaded functions.
- Copyright (C) 1987, 1992, 1993, 1994, 1995, 1996, 1997, 1998,
+ Copyright (C) 1987, 1992, 1993, 1994, 1995, 1996, 1997, 1998,
1999, 2000, 2001, 2002, 2003, 2004, 2005 Free Software Foundation, Inc.
Contributed by Michael Tiemann (tiemann@cygnus.com) and
modified by Brendan Kehoe (brendan@cygnus.com).
/* The various kinds of conversion. */
-typedef enum conversion_kind {
+typedef enum conversion_kind {
ck_identity,
ck_lvalue,
ck_qual,
used. */
BOOL_BITFIELD check_copy_constructor_p : 1;
/* If KIND is ck_ptr or ck_pmem, true to indicate that a conversion
- from a pointer-to-derived to pointer-to-base is being performed. */
+ from a pointer-to-derived to pointer-to-base is being performed. */
BOOL_BITFIELD base_p : 1;
/* The type of the expression resulting from the conversion. */
tree type;
static struct z_candidate *splice_viable (struct z_candidate *, bool, bool *);
static bool any_strictly_viable (struct z_candidate *);
static struct z_candidate *add_template_candidate
- (struct z_candidate **, tree, tree, tree, tree, tree,
+ (struct z_candidate **, tree, tree, tree, tree, tree,
tree, tree, int, unification_kind_t);
static struct z_candidate *add_template_candidate_real
- (struct z_candidate **, tree, tree, tree, tree, tree,
+ (struct z_candidate **, tree, tree, tree, tree, tree,
tree, tree, int, tree, unification_kind_t);
-static struct z_candidate *add_template_conv_candidate
+static struct z_candidate *add_template_conv_candidate
(struct z_candidate **, tree, tree, tree, tree, tree, tree);
static void add_builtin_candidates
(struct z_candidate **, enum tree_code, enum tree_code,
(struct z_candidate **, enum tree_code, enum tree_code,
tree, tree, tree, tree *, tree *, int);
static bool is_complete (tree);
-static void build_builtin_candidate
+static void build_builtin_candidate
(struct z_candidate **, tree, tree, tree, tree *, tree *,
int);
-static struct z_candidate *add_conv_candidate
+static struct z_candidate *add_conv_candidate
(struct z_candidate **, tree, tree, tree, tree, tree);
-static struct z_candidate *add_function_candidate
+static struct z_candidate *add_function_candidate
(struct z_candidate **, tree, tree, tree, tree, tree, int);
static conversion *implicit_conversion (tree, tree, tree, int);
static conversion *standard_conversion (tree, tree, tree, int);
static bool is_subseq (conversion *, conversion *);
static tree maybe_handle_ref_bind (conversion **);
static void maybe_handle_implicit_object (conversion **);
-static struct z_candidate *add_candidate
- (struct z_candidate **, tree, tree, size_t,
+static struct z_candidate *add_candidate
+ (struct z_candidate **, tree, tree, size_t,
conversion **, tree, tree, int);
static tree source_type (conversion *);
static void add_warning (struct z_candidate *, struct z_candidate *);
else
{
/* In the case of:
-
+
template <class T> struct S { ~S(); };
int i;
i.~S();
-
+
NAME will be a class template. */
gcc_assert (DECL_CLASS_TEMPLATE_P (name));
return false;
function = build3 (CALL_EXPR, result_type, function, parms, NULL_TREE);
TREE_HAS_CONSTRUCTOR (function) = is_constructor;
TREE_NOTHROW (function) = nothrow;
-
+
return function;
}
validate_conversion_obstack (void)
{
if (conversion_obstack_initialized)
- gcc_assert ((obstack_next_free (&conversion_obstack)
+ gcc_assert ((obstack_next_free (&conversion_obstack)
== obstack_base (&conversion_obstack)));
}
build_identity_conv (tree type, tree expr)
{
conversion *c;
-
+
c = alloc_conversion (ck_identity);
c->type = type;
c->u.expr = expr;
conversion. */
conversion *part_conv = standard_conversion
(TREE_TYPE (to), TREE_TYPE (from), NULL_TREE, flags);
-
+
if (part_conv)
{
conv = build_conv (part_conv->kind, to, conv);
&& TREE_CODE (TREE_TYPE (from)) != FUNCTION_TYPE)
{
from = build_pointer_type
- (cp_build_qualified_type (void_type_node,
+ (cp_build_qualified_type (void_type_node,
cp_type_quals (TREE_TYPE (from))));
conv = build_conv (ck_ptr, from, conv);
}
(TYPE_PTRMEM_POINTED_TO_TYPE (from),
TYPE_PTRMEM_POINTED_TO_TYPE (to))))
{
- from = build_ptrmem_type (tbase,
+ from = build_ptrmem_type (tbase,
TYPE_PTRMEM_POINTED_TO_TYPE (from));
conv = build_conv (ck_pmem, from, conv);
}
else if (IS_AGGR_TYPE (TREE_TYPE (from))
&& IS_AGGR_TYPE (TREE_TYPE (to))
/* [conv.ptr]
-
+
An rvalue of type "pointer to cv D," where D is a
class type, can be converted to an rvalue of type
"pointer to cv B," where B is a base class (clause
access or uniqueness. */
&& DERIVED_FROM_P (TREE_TYPE (to), TREE_TYPE (from)))
{
- from =
+ from =
cp_build_qualified_type (TREE_TYPE (to),
cp_type_quals (TREE_TYPE (from)));
from = build_pointer_type (from);
return 0;
from = cp_build_qualified_type (tbase, cp_type_quals (fbase));
- from = build_method_type_directly (from,
+ from = build_method_type_directly (from,
TREE_TYPE (fromfn),
TREE_CHAIN (TYPE_ARG_TYPES (fromfn)));
from = build_ptrmemfunc_type (build_pointer_type (from));
conv = build_conv (ck_std, to, conv);
if (fcode == POINTER_TYPE
|| TYPE_PTRMEM_P (from)
- || (TYPE_PTRMEMFUNC_P (from)
+ || (TYPE_PTRMEMFUNC_P (from)
&& conv->rank < cr_pbool))
conv->rank = cr_pbool;
return conv;
}
-
+
return NULL;
}
/* We don't check for ENUMERAL_TYPE here because there are no standard
{
tree f = OVL_CURRENT (fns);
tree t2 = TREE_TYPE (TREE_TYPE (f));
-
+
cand = NULL;
/* If this is a template function, try to get an exact
TREE_PURPOSE (conversions),
LOOKUP_NORMAL,
DEDUCE_CONV);
-
+
if (cand)
{
/* Now, see if the conversion function really returns
}
else if (TREE_CODE (t2) == REFERENCE_TYPE
&& reference_compatible_p (t, TREE_TYPE (t2)))
- cand = add_function_candidate (&candidates, f, s, arglist,
- TYPE_BINFO (s),
+ cand = add_function_candidate (&candidates, f, s, arglist,
+ TYPE_BINFO (s),
TREE_PURPOSE (conversions),
LOOKUP_NORMAL);
-
+
if (cand)
{
conversion *identity_conv;
/* Build a standard conversion sequence indicating the
binding from the reference type returned by the
function to the desired REFERENCE_TYPE. */
- identity_conv
- = build_identity_conv (TREE_TYPE (TREE_TYPE
+ identity_conv
+ = build_identity_conv (TREE_TYPE (TREE_TYPE
(TREE_TYPE (cand->fn))),
NULL_TREE);
cand->second_conv
- = (direct_reference_binding
+ = (direct_reference_binding
(reference_type, identity_conv));
cand->second_conv->bad_p |= cand->convs[0]->bad_p;
}
if (cand->viable == -1)
conv->bad_p = true;
-
+
return cand->second_conv;
}
t = TREE_TYPE (type);
- /* [over.ics.rank]
-
+ /* [over.ics.rank]
+
When a parameter of reference type binds directly
(_dcl.init.ref_) to an argument expression, the implicit
conversion sequence is the identity conversion, unless the
argument expression has a type that is a derived class of the
parameter type, in which case the implicit conversion sequence is
a derived-to-base Conversion.
-
+
If the parameter binds directly to the result of applying a
conversion function to the argument expression, the implicit
conversion sequence is a user-defined conversion sequence
{
/* [dcl.init.ref]
- If the initializer expression
-
+ If the initializer expression
+
-- is an lvalue (but not an lvalue for a bit-field), and "cv1 T1"
is reference-compatible with "cv2 T2,"
-
+
the reference is bound directly to the initializer expression
lvalue. */
conv = build_identity_conv (from, expr);
a temporary, so we just issue an error when the conversion
actually occurs. */
conv->need_temporary_p = true;
-
+
return conv;
}
else if (CLASS_TYPE_P (from) && !(flags & LOOKUP_NO_CONVERSION))
"cv1 T1" is reference-compatible with "cv3 T3". (this
conversion is selected by enumerating the applicable
conversion functions (_over.match.ref_) and choosing the
- best one through overload resolution. (_over.match_).
+ best one through overload resolution. (_over.match_).
the reference is bound to the lvalue result of the conversion
in the second case. */
return NULL;
/* [over.ics.rank]
-
+
When a parameter of reference type is not bound directly to an
argument expression, the conversion sequence is the one required
to convert the argument expression to the underlying type of the
return NULL;
/* [dcl.init.ref]
-
+
If the initializer expression is an rvalue, with T2 a class type,
and "cv1 T1" is reference-compatible with "cv2 T2", the reference
is bound in one of the following ways:
-
+
-- The reference is bound to the object represented by the rvalue
- or to a sub-object within that object.
+ or to a sub-object within that object.
-- ...
-
+
We use the first alternative. The implicit conversion sequence
is supposed to be same as we would obtain by generating a
temporary. Fortunately, if the types are reference compatible,
functions. */
static struct z_candidate *
-add_candidate (struct z_candidate **candidates,
- tree fn, tree args,
- size_t num_convs, conversion **convs,
- tree access_path, tree conversion_path,
+add_candidate (struct z_candidate **candidates,
+ tree fn, tree args,
+ size_t num_convs, conversion **convs,
+ tree access_path, tree conversion_path,
int viable)
{
- struct z_candidate *cand
+ struct z_candidate *cand
= conversion_obstack_alloc (sizeof (struct z_candidate));
cand->fn = fn;
comes from for purposes of overload resolution. */
static struct z_candidate *
-add_function_candidate (struct z_candidate **candidates,
- tree fn, tree ctype, tree arglist,
+add_function_candidate (struct z_candidate **candidates,
+ tree fn, tree ctype, tree arglist,
tree access_path, tree conversion_path,
int flags)
{
orig_arglist = arglist;
arglist = skip_artificial_parms_for (fn, arglist);
}
- else
+ else
orig_arglist = arglist;
len = list_length (arglist);
}
out:
- return add_candidate (candidates, fn, orig_arglist, len, convs,
+ return add_candidate (candidates, fn, orig_arglist, len, convs,
access_path, conversion_path, viable);
}
if (!sufficient_parms_p (parmnode))
viable = 0;
- return add_candidate (candidates, totype, arglist, len, convs,
+ return add_candidate (candidates, totype, arglist, len, convs,
access_path, conversion_path, viable);
}
convs[0] = t;
else
viable = 0;
- }
+ }
- add_candidate (candidates, fnname, /*args=*/NULL_TREE,
- num_convs, convs,
+ add_candidate (candidates, fnname, /*args=*/NULL_TREE,
+ num_convs, convs,
/*access_path=*/NULL_TREE,
/*conversion_path=*/NULL_TREE,
viable);
/* Create any builtin operator overload candidates for the operator in
question given the converted operand types TYPE1 and TYPE2. The other
args are passed through from add_builtin_candidates to
- build_builtin_candidate.
-
- TYPE1 and TYPE2 may not be permissible, and we must filter them.
+ build_builtin_candidate.
+
+ TYPE1 and TYPE2 may not be permissible, and we must filter them.
If CODE is requires candidates operands of the same type of the kind
of which TYPE1 and TYPE2 are, we add both candidates
CODE (TYPE1, TYPE1) and CODE (TYPE2, TYPE2). */
&& (TYPE_PTROB_P (type1)
|| TREE_CODE (TREE_TYPE (type1)) == FUNCTION_TYPE))
break;
- return;
+ return;
/* 9 For every type T, there exist candidate operator functions of the form
T* operator+(T*);
/* [over.built]
For every pair of promoted arithmetic types L and R, there
- exist candidate operator functions of the form
+ exist candidate operator functions of the form
- LR operator?(bool, L, R);
+ LR operator?(bool, L, R);
where LR is the result of the usual arithmetic conversions
between types L and R.
if (!(TYPE_PTR_P (type1) || TYPE_PTR_TO_MEMBER_P (type1))
|| !(TYPE_PTR_P (type2) || TYPE_PTR_TO_MEMBER_P (type2)))
return;
-
+
/* We don't check that the two types are the same; the logic
below will actually create two candidates; one in which both
parameter types are TYPE1, and one in which both parameter
one of the input types converts to.
3) arithmetic candidates. According to the standard, we should generate
all of these, but I'm trying not to...
-
+
Here we generate a superset of the possible candidates for this particular
case. That is a subset of the full set the standard defines, plus some
other cases which the standard disallows. add_builtin_candidate will
case GE_EXPR:
enum_p = 1;
/* Fall through. */
-
+
default:
ref1 = 0;
}
/* In [class.copy]:
A member function template is never instantiated to perform the
- copy of a class object to an object of its class type.
+ copy of a class object to an object of its class type.
It's a little unclear what this means; the standard explicitly
does allow a template to be used to copy a class. For example,
};
const A f ();
void g () { A a (f ()); }
-
+
the member template will be used to make the copy. The section
quoted above appears in the paragraph that forbids constructors
whose only parameter is (a possibly cv-qualified variant of) the
class type, and a logical interpretation is that the intent was
to forbid the instantiation of member templates which would then
have that form. */
- if (DECL_CONSTRUCTOR_P (fn) && list_length (arglist) == 2)
+ if (DECL_CONSTRUCTOR_P (fn) && list_length (arglist) == 2)
{
tree arg_types = FUNCTION_FIRST_USER_PARMTYPE (fn);
if (arg_types && same_type_p (TYPE_MAIN_VARIANT (TREE_VALUE (arg_types)),
conversion_path, arglist);
else
cand = add_function_candidate (candidates, fn, ctype,
- arglist, access_path,
+ arglist, access_path,
conversion_path, flags);
if (DECL_TI_TEMPLATE (fn) != tmpl)
/* This situation can occur if a member template of a template
tree access_path, tree conversion_path, int flags,
unification_kind_t strict)
{
- return
+ return
add_template_candidate_real (candidates, tmpl, ctype,
- explicit_targs, arglist, return_type,
+ explicit_targs, arglist, return_type,
access_path, conversion_path,
flags, NULL_TREE, strict);
}
tree obj, tree arglist, tree return_type,
tree access_path, tree conversion_path)
{
- return
+ return
add_template_candidate_real (candidates, tmpl, NULL_TREE, NULL_TREE,
arglist, return_type, access_path,
conversion_path, 0, obj, DEDUCE_CONV);
last_viable = &viable;
*any_viable_p = false;
- cand = &cands;
- while (*cand)
+ cand = &cands;
+ while (*cand)
{
struct z_candidate *c = *cand;
if (strict_p ? c->viable == 1 : c->viable)
gcc_assert (user_seq->kind == ck_user);
/* Find the end of the second conversion sequence. */
- t = &(std_seq);
+ t = &(std_seq);
while ((*t)->kind != ck_identity)
t = &((*t)->u.next);
if (DECL_NONCONVERTING_P (ctor))
continue;
- if (TREE_CODE (ctor) == TEMPLATE_DECL)
+ if (TREE_CODE (ctor) == TEMPLATE_DECL)
cand = add_template_candidate (&candidates, ctor, totype,
- NULL_TREE, args, NULL_TREE,
+ NULL_TREE, args, NULL_TREE,
TYPE_BINFO (totype),
TYPE_BINFO (totype),
flags,
DEDUCE_CALL);
- else
+ else
cand = add_function_candidate (&candidates, ctor, totype,
- args, TYPE_BINFO (totype),
+ args, TYPE_BINFO (totype),
TYPE_BINFO (totype),
- flags);
+ flags);
if (cand)
cand->second_conv = build_identity_conv (totype, NULL_TREE);
look for a temporary binding. */
if (TREE_CODE (totype) == REFERENCE_TYPE)
convflags |= LOOKUP_NO_TEMP_BIND;
-
+
for (fns = TREE_VALUE (conv_fns); fns; fns = OVL_NEXT (fns))
{
tree fn = OVL_CURRENT (fns);
-
+
/* [over.match.funcs] For conversion functions, the function
is considered to be a member of the class of the implicit
object argument for the purpose of defining the type of
So we pass fromtype as CTYPE to add_*_candidate. */
if (TREE_CODE (fn) == TEMPLATE_DECL)
- cand = add_template_candidate (&candidates, fn, fromtype,
+ cand = add_template_candidate (&candidates, fn, fromtype,
NULL_TREE,
- args, totype,
- TYPE_BINFO (fromtype),
+ args, totype,
+ TYPE_BINFO (fromtype),
conversion_path,
flags,
DEDUCE_CONV);
- else
+ else
cand = add_function_candidate (&candidates, fn, fromtype,
args,
TYPE_BINFO (fromtype),
conversion_path,
- flags);
+ flags);
if (cand)
{
conversion *ics
- = implicit_conversion (totype,
+ = implicit_conversion (totype,
TREE_TYPE (TREE_TYPE (cand->fn)),
0, convflags);
cand->second_conv = ics;
-
+
if (!ics)
cand->viable = 0;
else if (candidates->viable == 1 && ics->bad_p)
for (t = args; t; t = TREE_CHAIN (t))
{
tree arg = TREE_VALUE (t);
-
+
if (arg == error_mark_node)
return error_mark_node;
else if (VOID_TYPE_P (TREE_TYPE (arg)))
that overload resolution fails, *CANDIDATES will be the set of
candidates considered, and ANY_VIABLE_P will be set to true or
false to indicate whether or not any of the candidates were
- viable.
+ viable.
The ARGS should already have gone through RESOLVE_ARGS before this
function is called. */
static struct z_candidate *
-perform_overload_resolution (tree fn,
- tree args,
+perform_overload_resolution (tree fn,
+ tree args,
struct z_candidate **candidates,
bool *any_viable_p)
{
*any_viable_p = true;
/* Check FN and ARGS. */
- gcc_assert (TREE_CODE (fn) == FUNCTION_DECL
+ gcc_assert (TREE_CODE (fn) == FUNCTION_DECL
|| TREE_CODE (fn) == TEMPLATE_DECL
|| TREE_CODE (fn) == OVERLOAD
|| TREE_CODE (fn) == TEMPLATE_ID_EXPR);
/* Return an expression for a call to FN (a namespace-scope function,
or a static member function) with the ARGS. */
-
+
tree
build_new_function_call (tree fn, tree args)
{
/* Figure out what function is being called. */
cand = perform_overload_resolution (fns, args, &candidates, &any_viable_p);
-
+
/* If no suitable function could be found, issue an error message
and give up. */
if (!cand)
/* Skip the size_t parameter. */
arg_types = TREE_CHAIN (arg_types);
/* Check the remaining parameters (if any). */
- if (arg_types
+ if (arg_types
&& TREE_CHAIN (arg_types) == void_list_node
&& same_type_p (TREE_VALUE (arg_types),
ptr_type_node))
tree fn = OVL_CURRENT (fns);
if (TREE_CODE (fn) == TEMPLATE_DECL)
add_template_candidate (&candidates, fn, base, NULL_TREE,
- mem_args, NULL_TREE,
+ mem_args, NULL_TREE,
TYPE_BINFO (type),
TYPE_BINFO (type),
LOOKUP_NORMAL, DEDUCE_CALL);
for (; fns; fns = OVL_NEXT (fns))
{
tree fn = OVL_CURRENT (fns);
- if (TREE_CODE (fn) == TEMPLATE_DECL)
- add_template_conv_candidate
+ if (TREE_CODE (fn) == TEMPLATE_DECL)
+ add_template_conv_candidate
(&candidates, fn, obj, args, totype,
/*access_path=*/NULL_TREE,
/*conversion_path=*/NULL_TREE);
error ("%s for ternary %<operator?:%> in %<%E ? %E : %E%>",
problem, arg1, arg2, arg3);
break;
-
+
case POSTINCREMENT_EXPR:
case POSTDECREMENT_EXPR:
error ("%s for %<operator%s%> in %<%E%s%>", problem, opname, arg1, opname);
break;
-
+
case ARRAY_REF:
error ("%s for %<operator[]%> in %<%E[%E]%>", problem, arg1, arg2);
break;
case IMAGPART_EXPR:
error ("%s for %qs in %<%s %E%>", problem, opname, opname, arg1);
break;
-
+
default:
if (arg2)
error ("%s for %<operator%s%> in %<%E %s %E%>",
reference must bind directly (_dcl.init.ref_) to E1. */
if (real_lvalue_p (e2))
{
- conv = implicit_conversion (build_reference_type (t2),
+ conv = implicit_conversion (build_reference_type (t2),
t1,
e1,
LOOKUP_NO_TEMP_BIND);
if (good_base && at_least_as_qualified_p (t2, t1))
{
conv = build_identity_conv (t1, e1);
- if (!same_type_p (TYPE_MAIN_VARIANT (t1),
+ if (!same_type_p (TYPE_MAIN_VARIANT (t1),
TYPE_MAIN_VARIANT (t2)))
conv = build_conv (ck_base, t2, conv);
else
}
/* [expr.cond]
-
+
The first expr ession is implicitly converted to bool (clause
_conv_). */
arg1 = perform_implicit_conversion (boolean_type_node, arg1);
type of the other and is an rvalue.
--Both the second and the third operands have type void; the
- result is of type void and is an rvalue.
+ result is of type void and is an rvalue.
We must avoid calling force_rvalue for expressions of type
"void" because it will complain that their value is being
used. */
- if (TREE_CODE (arg2) == THROW_EXPR
+ if (TREE_CODE (arg2) == THROW_EXPR
&& TREE_CODE (arg3) != THROW_EXPR)
{
if (!VOID_TYPE_P (arg3_type))
arg3_type = TREE_TYPE (arg3);
result_type = arg3_type;
}
- else if (TREE_CODE (arg2) != THROW_EXPR
+ else if (TREE_CODE (arg2) != THROW_EXPR
&& TREE_CODE (arg3) == THROW_EXPR)
{
if (!VOID_TYPE_P (arg2_type))
{
conversion *conv2;
conversion *conv3;
-
+
/* Get the high-water mark for the CONVERSION_OBSTACK. */
p = conversion_obstack_alloc (0);
/* If, after the conversion, both operands have class type,
treat the cv-qualification of both operands as if it were the
- union of the cv-qualification of the operands.
+ union of the cv-qualification of the operands.
The standard is not clear about what to do in this
circumstance. For example, if the first operand has type
if ((conv2 || conv3)
&& CLASS_TYPE_P (arg2_type)
&& TYPE_QUALS (arg2_type) != TYPE_QUALS (arg3_type))
- arg2_type = arg3_type =
+ arg2_type = arg3_type =
cp_build_qualified_type (arg2_type,
TYPE_QUALS (arg2_type)
| TYPE_QUALS (arg3_type));
If the second and third operands are lvalues and have the same
type, the result is of that type and is an lvalue. */
- if (real_lvalue_p (arg2)
- && real_lvalue_p (arg3)
+ if (real_lvalue_p (arg2)
+ && real_lvalue_p (arg3)
&& same_type_p (arg2_type, arg3_type))
{
result_type = arg2_type;
args[0] = arg2;
args[1] = arg3;
args[2] = arg1;
- add_builtin_candidates (&candidates,
- COND_EXPR,
+ add_builtin_candidates (&candidates,
+ COND_EXPR,
NOP_EXPR,
ansi_opname (COND_EXPR),
args,
if (arg2 == error_mark_node || arg3 == error_mark_node)
return error_mark_node;
-
+
/* [expr.cond]
-
+
After those conversions, one of the following shall hold:
--The second and third operands have the same type; the result is of
--The second and third operands have arithmetic or enumeration
type; the usual arithmetic conversions are performed to bring
them to a common type, and the result is of that type. */
- else if ((ARITHMETIC_TYPE_P (arg2_type)
+ else if ((ARITHMETIC_TYPE_P (arg2_type)
|| TREE_CODE (arg2_type) == ENUMERAL_TYPE)
&& (ARITHMETIC_TYPE_P (arg3_type)
|| TREE_CODE (arg3_type) == ENUMERAL_TYPE))
{
/* In this case, there is always a common type. */
- result_type = type_after_usual_arithmetic_conversions (arg2_type,
+ result_type = type_after_usual_arithmetic_conversions (arg2_type,
arg3_type);
-
+
if (TREE_CODE (arg2_type) == ENUMERAL_TYPE
&& TREE_CODE (arg3_type) == ENUMERAL_TYPE)
warning (0, "enumeral mismatch in conditional expression: %qT vs %qT",
|| (TREE_CODE (arg3_type) == ENUMERAL_TYPE
&& !same_type_p (arg2_type, type_promotes_to (arg3_type)))))
warning (0, "enumeral and non-enumeral type in conditional expression");
-
+
arg2 = perform_implicit_conversion (result_type, arg2);
arg3 = perform_implicit_conversion (result_type, arg3);
}
them to a common type, whose cv-qualification shall match the
cv-qualification of either the second or the third operand.
The result is of the common type. */
- else if ((null_ptr_cst_p (arg2)
+ else if ((null_ptr_cst_p (arg2)
&& (TYPE_PTR_P (arg3_type) || TYPE_PTR_TO_MEMBER_P (arg3_type)))
- || (null_ptr_cst_p (arg3)
+ || (null_ptr_cst_p (arg3)
&& (TYPE_PTR_P (arg2_type) || TYPE_PTR_TO_MEMBER_P (arg2_type)))
|| (TYPE_PTR_P (arg2_type) && TYPE_PTR_P (arg3_type))
|| (TYPE_PTRMEM_P (arg2_type) && TYPE_PTRMEM_P (arg3_type))
}
valid_operands:
- result = fold_if_not_in_template (build3 (COND_EXPR, result_type, arg1,
+ result = fold_if_not_in_template (build3 (COND_EXPR, result_type, arg1,
arg2, arg3));
/* We can't use result_type below, as fold might have returned a
throw_expr. */
sometimes wrap them in NOP_EXPRs so the test would fail. */
if (!lvalue_p && CLASS_TYPE_P (TREE_TYPE (result)))
result = get_target_expr (result);
-
+
/* If this expression is an rvalue, but might be mistaken for an
lvalue, we must add a NON_LVALUE_EXPR. */
if (!lvalue_p && real_lvalue_p (result))
ACCESS_PATH, and FLAGS are as for add_function_candidate. */
static void
-add_candidates (tree fns, tree args,
+add_candidates (tree fns, tree args,
tree explicit_targs, bool template_only,
tree conversion_path, tree access_path,
int flags,
/* Delay creating the implicit this parameter until it is needed. */
non_static_args = NULL_TREE;
- while (fns)
+ while (fns)
{
tree fn;
tree fn_args;
fn_args = args;
if (TREE_CODE (fn) == TEMPLATE_DECL)
- add_template_candidate (candidates,
- fn,
+ add_template_candidate (candidates,
+ fn,
ctype,
explicit_targs,
fn_args,
bool strict_p;
bool any_viable_p;
- if (error_operand_p (arg1)
- || error_operand_p (arg2)
+ if (error_operand_p (arg1)
+ || error_operand_p (arg2)
|| error_operand_p (arg3))
return error_mark_node;
fnname = ansi_opname (code);
arg1 = prep_operand (arg1);
-
+
switch (code)
{
case NEW_EXPR:
arg2 = prep_operand (arg2);
arg3 = prep_operand (arg3);
-
+
if (code == COND_EXPR)
{
if (arg2 == NULL_TREE
goto user_defined_result_ready;
}
if (fns)
- add_candidates (BASELINK_FUNCTIONS (fns), arglist,
+ add_candidates (BASELINK_FUNCTIONS (fns), arglist,
NULL_TREE, false,
BASELINK_BINFO (fns),
TYPE_BINFO (TREE_TYPE (arg1)),
default:
strict_p = pedantic;
break;
- }
+ }
candidates = splice_viable (candidates, strict_p, &any_viable_p);
if (!any_viable_p)
if (flags & LOOKUP_COMPLAIN)
pedwarn ("no %<%D(int)%> declared for postfix %qs, "
"trying prefix operator instead",
- fnname,
+ fnname,
operator_name_info[code].name);
if (code == POSTINCREMENT_EXPR)
code = PREINCREMENT_EXPR;
else
- code = PREDECREMENT_EXPR;
+ code = PREDECREMENT_EXPR;
result = build_new_op (code, flags, arg1, NULL_TREE, NULL_TREE,
overloaded_p);
break;
case LE_EXPR:
case EQ_EXPR:
case NE_EXPR:
- if (TREE_CODE (TREE_TYPE (arg1)) == ENUMERAL_TYPE
- && TREE_CODE (TREE_TYPE (arg2)) == ENUMERAL_TYPE
+ if (TREE_CODE (TREE_TYPE (arg1)) == ENUMERAL_TYPE
+ && TREE_CODE (TREE_TYPE (arg2)) == ENUMERAL_TYPE
&& (TYPE_MAIN_VARIANT (TREE_TYPE (arg1))
!= TYPE_MAIN_VARIANT (TREE_TYPE (arg2))))
{
- warning (0, "comparison between %q#T and %q#T",
+ warning (0, "comparison between %q#T and %q#T",
TREE_TYPE (arg1), TREE_TYPE (arg2));
}
break;
fnname = ansi_opname (code);
- if (CLASS_TYPE_P (type)
+ if (CLASS_TYPE_P (type)
&& COMPLETE_TYPE_P (complete_type (type))
&& !global_p)
/* In [class.free]
If the result of the lookup is ambiguous or inaccessible, or if
the lookup selects a placement deallocation function, the
program is ill-formed.
-
+
Therefore, we ask lookup_fnfields to complain about ambiguity. */
{
fns = lookup_fnfields (TYPE_BINFO (type), fnname, 1);
the first pass, we look for a one-operator (or placement)
operator delete. If we're not doing placement delete, then on
the second pass we look for a two-argument delete. */
- for (pass = 0; pass < (placement ? 1 : 2); ++pass)
+ for (pass = 0; pass < (placement ? 1 : 2); ++pass)
{
/* Go through the `operator delete' functions looking for one
with a matching type. */
- for (fn = BASELINK_P (fns) ? BASELINK_FUNCTIONS (fns) : fns;
- fn;
+ for (fn = BASELINK_P (fns) ? BASELINK_FUNCTIONS (fns) : fns;
+ fn;
fn = OVL_NEXT (fn))
{
tree t;
if (pass == 0)
args = tree_cons (NULL_TREE, addr, args);
else
- args = tree_cons (NULL_TREE, addr,
+ args = tree_cons (NULL_TREE, addr,
build_tree_list (NULL_TREE, size));
if (placement)
enforce_access (tree basetype_path, tree decl)
{
gcc_assert (TREE_CODE (basetype_path) == TREE_BINFO);
-
+
if (!accessible_p (basetype_path, decl, true))
{
if (TREE_PRIVATE (decl))
{
build_special_member_call (NULL_TREE,
complete_ctor_identifier,
- build_tree_list (NULL_TREE, expr),
+ build_tree_list (NULL_TREE, expr),
type,
LOOKUP_NORMAL | LOOKUP_ONLYCONVERTING
| LOOKUP_NO_CONVERSION
to NULL. */
static tree
-build_temp (tree expr, tree type, int flags,
+build_temp (tree expr, tree type, int flags,
void (**diagnostic_fn)(const char *, ...))
{
int savew, savee;
-
+
savew = warningcount, savee = errorcount;
expr = build_special_member_call (NULL_TREE,
complete_ctor_identifier,
- build_tree_list (NULL_TREE, expr),
+ build_tree_list (NULL_TREE, expr),
type, flags);
if (warningcount > savew)
*diagnostic_fn = warning0;
*diagnostic_fn = NULL;
return expr;
}
-
+
/* Perform the conversions in CONVS on the expression EXPR. FN and
ARGNUM are used for diagnostics. ARGNUM is zero based, -1
conversions to inaccessible bases are permitted. */
static tree
-convert_like_real (conversion *convs, tree expr, tree fn, int argnum,
+convert_like_real (conversion *convs, tree expr, tree fn, int argnum,
int inner, bool issue_conversion_warnings,
bool c_cast_p)
{
pedwarn (" initializing argument %P of %qD", argnum, fn);
return cp_convert (totype, expr);
}
-
+
if (issue_conversion_warnings)
{
tree t = non_reference (totype);
variable. */
else if (TYPE_UNSIGNED (t) && TREE_CODE (t) != BOOLEAN_TYPE)
{
- if (TREE_CODE (expr) == INTEGER_CST && TREE_NEGATED_INT (expr))
+ if (TREE_CODE (expr) == INTEGER_CST && TREE_NEGATED_INT (expr))
{
if (fn)
warning (0, "passing negative value %qE for argument %P to %qD",
else
warning (0, "converting negative value %qE to %qT", expr, t);
}
-
+
overflow_warning (expr);
}
}
if (IS_AGGR_TYPE (totype)
&& (inner >= 0 || !lvalue_p (expr)))
{
- expr = (build_temp
- (expr, totype,
+ expr = (build_temp
+ (expr, totype,
/* Core issue 84, now a DR, says that we don't
allow UDCs for these args (which deliberately
breaks copy-init of an auto_ptr<Base> from an
auto_ptr<Derived>). */
LOOKUP_NORMAL|LOOKUP_ONLYCONVERTING|LOOKUP_NO_CONVERSION,
&diagnostic_fn));
-
+
if (diagnostic_fn)
{
if (fn)
- diagnostic_fn
+ diagnostic_fn
(" initializing argument %P of %qD from result of %qD",
argnum, fn, convfn);
else
- diagnostic_fn
+ diagnostic_fn
(" initializing temporary from result of %qD", convfn);
}
expr = build_cplus_new (totype, expr);
copy constructor, and we'll end up with an infinite
loop. If we can use a bitwise copy, then we'll be
OK. */
- if ((lvalue & clk_packed)
- && CLASS_TYPE_P (type)
+ if ((lvalue & clk_packed)
+ && CLASS_TYPE_P (type)
&& !TYPE_HAS_TRIVIAL_INIT_REF (type))
{
error ("cannot bind packed field %qE to %qT",
/* Convert it to a pointer to the type referred to by the
reference. This will adjust the pointer if a derived to
base conversion is being performed. */
- expr = cp_convert (build_pointer_type (TREE_TYPE (ref_type)),
+ expr = cp_convert (build_pointer_type (TREE_TYPE (ref_type)),
expr);
/* Convert the pointer to the desired reference type. */
return build_nop (ref_type, expr);
arg = perform_integral_promotions (arg);
arg = require_complete_type (arg);
-
+
if (arg != error_mark_node
&& !pod_type_p (TREE_TYPE (arg)))
{
/* Undefined behavior [expr.call] 5.2.2/7. We used to just warn
here and do a bitwise copy, but now cp_expr_size will abort if we
- try to do that.
- If the call appears in the context of a sizeof expression,
- there is no need to emit a warning, since the expression won't be
+ try to do that.
+ If the call appears in the context of a sizeof expression,
+ there is no need to emit a warning, since the expression won't be
evaluated. We keep the builtin_trap just as a safety check. */
if (!skip_evaluation)
warning (0, "cannot pass objects of non-POD type %q#T through %<...%>; "
{
if (processing_template_decl)
return build_min (VA_ARG_EXPR, type, expr);
-
+
type = complete_type_or_else (type, NULL_TREE);
if (expr == error_mark_node || !type)
return error_mark_node;
-
+
if (! pod_type_p (type))
{
/* Undefined behavior [expr.call] 5.2.2/7. */
expr = build_indirect_ref (expr, NULL);
return expr;
}
-
+
return build_va_arg (expr, type);
}
promote = type_promotes_to (type);
if (same_type_p (type, promote))
promote = type;
-
+
return promote;
}
parm = TREE_CHAIN (parm);
/* We should never try to call the abstract constructor. */
gcc_assert (!DECL_HAS_IN_CHARGE_PARM_P (fn));
-
+
if (DECL_HAS_VTT_PARM_P (fn))
{
converted_args = tree_cons
arg = TREE_CHAIN (arg);
parm = TREE_CHAIN (parm);
}
- }
+ }
/* Bypass access control for 'this' parameter. */
else if (TREE_CODE (TREE_TYPE (fn)) == METHOD_TYPE)
{
tree argtype = TREE_TYPE (TREE_VALUE (arg));
tree converted_arg;
tree base_binfo;
-
+
if (convs[i]->bad_p)
pedwarn ("passing %qT as %<this%> argument of %q#D discards qualifiers",
TREE_TYPE (argtype), fn);
cand->conversion_path,
1);
/* Check that the base class is accessible. */
- if (!accessible_base_p (TREE_TYPE (argtype),
+ if (!accessible_base_p (TREE_TYPE (argtype),
BINFO_TYPE (cand->conversion_path), true))
error ("%qT is not an accessible base of %qT",
BINFO_TYPE (cand->conversion_path),
TREE_TYPE (parmtype), ba_unique, NULL);
converted_arg = build_base_path (PLUS_EXPR, converted_arg,
base_binfo, 1);
-
+
converted_args = tree_cons (NULL_TREE, converted_arg, converted_args);
parm = TREE_CHAIN (parm);
arg = TREE_CHAIN (arg);
/* Default arguments */
for (; parm && parm != void_list_node; parm = TREE_CHAIN (parm), i++)
- converted_args
- = tree_cons (NULL_TREE,
- convert_default_arg (TREE_VALUE (parm),
+ converted_args
+ = tree_cons (NULL_TREE,
+ convert_default_arg (TREE_VALUE (parm),
TREE_PURPOSE (parm),
fn, i - is_method),
converted_args);
if (TREE_CODE (targ) == ADDR_EXPR)
{
targ = TREE_OPERAND (targ, 0);
- if (!same_type_ignoring_top_level_qualifiers_p
+ if (!same_type_ignoring_top_level_qualifiers_p
(TREE_TYPE (TREE_TYPE (arg)), TREE_TYPE (targ)))
targ = NULL_TREE;
}
t = convert (TREE_TYPE (TREE_VALUE (args)), t);
val = build_indirect_ref (t, 0);
}
-
+
return val;
}
DECL_CONTEXT (fn),
ba_any, NULL);
gcc_assert (binfo && binfo != error_mark_node);
-
+
*p = build_base_path (PLUS_EXPR, *p, binfo, 1);
if (TREE_SIDE_EFFECTS (*p))
*p = save_expr (*p);
/* If this call might throw an exception, note that fact. */
fndecl = get_callee_fndecl (fn);
- if ((!fndecl || !TREE_NOTHROW (fndecl))
+ if ((!fndecl || !TREE_NOTHROW (fndecl))
&& at_function_scope_p ()
&& cfun)
cp_function_chain->can_throw = 1;
tree lookup_args, lookup_fn, method, idx;
tree klass_ref, iface, iface_ref;
int i;
-
+
if (!java_iface_lookup_fn)
{
tree endlink = build_void_list_node ();
tree_cons (NULL_TREE, ptr_type_node,
tree_cons (NULL_TREE, java_int_type_node,
endlink)));
- java_iface_lookup_fn
+ java_iface_lookup_fn
= builtin_function ("_Jv_LookupInterfaceMethodIdx",
build_function_type (ptr_type_node, t),
0, NOT_BUILT_IN, NULL, NULL_TREE);
}
- /* Look up the pointer to the runtime java.lang.Class object for `instance'.
+ /* Look up the pointer to the runtime java.lang.Class object for `instance'.
This is the first entry in the vtable. */
- klass_ref = build_vtbl_ref (build_indirect_ref (instance, 0),
+ klass_ref = build_vtbl_ref (build_indirect_ref (instance, 0),
integer_zero_node);
/* Get the java.lang.Class pointer for the interface being called. */
if (!iface_ref || TREE_CODE (iface_ref) != VAR_DECL
|| DECL_CONTEXT (iface_ref) != iface)
{
- error ("could not find class$ field in java interface type %qT",
+ error ("could not find class$ field in java interface type %qT",
iface);
return error_mark_node;
}
iface_ref = build_address (iface_ref);
iface_ref = convert (build_pointer_type (iface), iface_ref);
-
+
/* Determine the itable index of FN. */
i = 1;
for (method = TYPE_METHODS (iface); method; method = TREE_CHAIN (method))
}
idx = build_int_cst (NULL_TREE, i);
- lookup_args = tree_cons (NULL_TREE, klass_ref,
+ lookup_args = tree_cons (NULL_TREE, klass_ref,
tree_cons (NULL_TREE, iface_ref,
build_tree_list (NULL_TREE, idx)));
- lookup_fn = build1 (ADDR_EXPR,
+ lookup_fn = build1 (ADDR_EXPR,
build_pointer_type (TREE_TYPE (java_iface_lookup_fn)),
java_iface_lookup_fn);
return build3 (CALL_EXPR, ptr_type_node, lookup_fn, lookup_args, NULL_TREE);
/* Returns the value to use for the in-charge parameter when making a
call to a function with the indicated NAME.
-
+
FIXME:Can't we find a neater way to do this mapping? */
tree
store the newly constructed object into a VAR_DECL. */
tree
-build_special_member_call (tree instance, tree name, tree args,
+build_special_member_call (tree instance, tree name, tree args,
tree binfo, int flags)
{
tree fns;
binfo = TYPE_BINFO (binfo);
}
-
+
gcc_assert (binfo != NULL_TREE);
class_type = BINFO_TYPE (binfo);
}
else
{
- if (name == complete_dtor_identifier
+ if (name == complete_dtor_identifier
|| name == base_dtor_identifier
|| name == deleting_dtor_identifier)
gcc_assert (args == NULL_TREE);
/* Convert to the base class, if necessary. */
- if (!same_type_ignoring_top_level_qualifiers_p
+ if (!same_type_ignoring_top_level_qualifiers_p
(TREE_TYPE (instance), BINFO_TYPE (binfo)))
{
if (name != ansi_assopname (NOP_EXPR))
binfo, /*nonnull=*/1);
}
}
-
+
gcc_assert (instance != NULL_TREE);
fns = lookup_fnfields (binfo, name, 1);
-
+
/* When making a call to a constructor or destructor for a subobject
that uses virtual base classes, pass down a pointer to a VTT for
the subobject. */
args = tree_cons (NULL_TREE, sub_vtt, args);
}
- return build_new_method_call (instance, fns, args,
- TYPE_BINFO (BINFO_TYPE (binfo)),
+ return build_new_method_call (instance, fns, args,
+ TYPE_BINFO (BINFO_TYPE (binfo)),
flags);
}
/* Return the NAME, as a C string. The NAME indicates a function that
is a member of TYPE. *FREE_P is set to true if the caller must
- free the memory returned.
+ free the memory returned.
Rather than go through all of this, we should simply set the names
of constructors and destructors appropriately, and dispense with
/* Constructors and destructors are special. */
if (IDENTIFIER_CTOR_OR_DTOR_P (name))
{
- pretty_name
+ pretty_name
= (char *) IDENTIFIER_POINTER (constructor_name (type));
/* For a destructor, add the '~'. */
if (name == complete_dtor_identifier
/* Build a call to "INSTANCE.FN (ARGS)". */
tree
-build_new_method_call (tree instance, tree fns, tree args,
+build_new_method_call (tree instance, tree fns, tree args,
tree conversion_path, int flags)
{
struct z_candidate *candidates = 0, *cand;
gcc_assert (instance != NULL_TREE);
- if (error_operand_p (instance)
+ if (error_operand_p (instance)
|| error_operand_p (fns)
|| args == error_mark_node)
return error_mark_node;
if (TREE_CODE (t) == TEMPLATE_DECL)
/* A member template. */
- add_template_candidate (&candidates, t,
+ add_template_candidate (&candidates, t,
class_type,
explicit_targs,
this_arglist, optype,
- access_binfo,
+ access_binfo,
conversion_path,
flags,
DEDUCE_CALL);
else if (! template_only)
- add_function_candidate (&candidates, t,
+ add_function_candidate (&candidates, t,
class_type,
this_arglist,
access_binfo,
|| DECL_DESTRUCTOR_P (current_function_decl)))
/* This is not an error, it is runtime undefined
behavior. */
- warning (0, (DECL_CONSTRUCTOR_P (current_function_decl) ?
+ warning (0, (DECL_CONSTRUCTOR_P (current_function_decl) ?
"abstract virtual %q#D called from constructor"
: "abstract virtual %q#D called from destructor"),
cand->fn);
-
+
if (TREE_CODE (TREE_TYPE (cand->fn)) == METHOD_TYPE
&& is_dummy_object (instance_ptr))
{
- error ("cannot call member function %qD without object",
+ error ("cannot call member function %qD without object",
cand->fn);
call = error_mark_node;
}
out to be a static member function, `a' is
none-the-less evaluated. */
if (TREE_CODE (TREE_TYPE (cand->fn)) != METHOD_TYPE
- && !is_dummy_object (instance_ptr)
+ && !is_dummy_object (instance_ptr)
&& TREE_SIDE_EFFECTS (instance))
- call = build2 (COMPOUND_EXPR, TREE_TYPE (call),
+ call = build2 (COMPOUND_EXPR, TREE_TYPE (call),
instance, call);
}
}
if (ics2->kind == ics1->kind
&& same_type_p (ics2->type, ics1->type)
- && same_type_p (ics2->u.next->type,
+ && same_type_p (ics2->u.next->type,
ics1->u.next->type))
return true;
}
if ((*ics)->this_p)
{
/* [over.match.funcs]
-
+
For non-static member functions, the type of the
implicit object parameter is "reference to cv X"
where X is the class of which the function is a
if (t->kind == ck_ptr)
t = t->u.next;
t = build_identity_conv (TREE_TYPE (t->type), NULL_TREE);
- t = direct_reference_binding (reference_type, t);
+ t = direct_reference_binding (reference_type, t);
*ics = t;
}
}
--a standard conversion sequence (_over.ics.scs_) is a better
conversion sequence than a user-defined conversion sequence
or an ellipsis conversion sequence, and
-
+
--a user-defined conversion sequence (_over.ics.user_) is a
better conversion sequence than an ellipsis conversion sequence
(_over.ics.ellipsis_). */
rank1 = CONVERSION_RANK (ics1);
rank2 = CONVERSION_RANK (ics2);
-
+
if (rank1 > rank2)
return -1;
else if (rank1 < rank2)
conversion *t1;
conversion *t2;
- /* We're dealing with two standard conversion sequences.
+ /* We're dealing with two standard conversion sequences.
[over.ics.rank]
-
+
Standard conversion sequence S1 is a better conversion
sequence than standard conversion sequence S2 if
-
+
--S1 is a proper subsequence of S2 (comparing the conversion
sequences in the canonical form defined by _over.ics.scs_,
excluding any Lvalue Transformation; the identity
conversion sequence is considered to be a subsequence of
any non-identity conversion sequence */
-
+
t1 = ics1;
while (t1->kind != ck_identity)
t1 = t1->u.next;
from_type1 = t1->type;
-
+
t2 = ics2;
while (t2->kind != ck_identity)
t2 = t2->u.next;
--A conversion that is not a conversion of a pointer, or pointer
to member, to bool is better than another conversion that is such
- a conversion.
+ a conversion.
The ICS_STD_RANK automatically handles the pointer-to-bool rule,
so that we do not have to check it explicitly. */
&& IS_AGGR_TYPE_CODE (TREE_CODE (deref_from_type1))
&& IS_AGGR_TYPE_CODE (TREE_CODE (deref_from_type2)))
{
- /* This was one of the pointer or pointer-like conversions.
+ /* This was one of the pointer or pointer-like conversions.
[over.ics.rank]
-
+
--If class B is derived directly or indirectly from class A,
conversion of B* to A* is better than conversion of B* to
void*, and conversion of A* to void* is better than
--If class B is derived directly or indirectly from class A
and class C is derived directly or indirectly from B,
-
+
--conversion of C* to B* is better than conversion of C* to
- A*,
-
+ A*,
+
--conversion of B* to A* is better than conversion of C* to
A* */
if (same_type_p (deref_from_type1, deref_from_type2))
tree from = non_reference (from_type1);
/* [over.ics.rank]
-
+
--binding of an expression of type C to a reference of type
B& is better than binding an expression of type C to a
reference of type A&
--binding of an expression of type B to a reference of type
A& is better than binding an expression of type C to a
- reference of type A&,
+ reference of type A&,
--conversion of B to A is better than conversion of C to A */
if (is_properly_derived_from (from_type1, to)
return comp_cv_qual_signature (to_type1, to_type2);
/* [over.ics.rank]
-
+
--S1 and S2 are reference bindings (_dcl.init.ref_), and the
types to which the references refer are the same type except for
top-level cv-qualifiers, and the type to which the reference
initialized by S2 refers is more cv-qualified than the type to
which the reference initialized by S1 refers */
-
+
if (target_type1 && target_type2
&& same_type_ignoring_top_level_qualifiers_p (to_type1, to_type2))
return comp_cv_qualification (target_type2, target_type1);
int static_2 = DECL_STATIC_FUNCTION_P (cand2->fn);
gcc_assert (static_1 != static_2);
-
+
if (static_1)
off2 = 1;
else
{
struct z_candidate *w, *l;
bool give_warning = false;
-
+
if (winner == 1)
w = cand1, l = cand2;
else
w = cand2, l = cand1;
-
+
/* We don't want to complain about `X::operator T1 ()'
beating `X::operator T2 () const', when T2 is a no less
cv-qualified version of T1. */
{
tree t = TREE_TYPE (TREE_TYPE (l->fn));
tree f = TREE_TYPE (TREE_TYPE (w->fn));
-
+
if (TREE_CODE (t) == TREE_CODE (f) && POINTER_TYPE_P (t))
{
t = TREE_TYPE (t);
}
else
give_warning = true;
-
+
if (!give_warning)
/*NOP*/;
else if (warn)
/* or, if not that,
F1 is a non-template function and F2 is a template function
specialization. */
-
+
if (!cand1->template_decl && cand2->template_decl)
return 1;
else if (cand1->template_decl && !cand2->template_decl)
return -1;
-
+
/* or, if not that,
F1 and F2 are template functions and the function template for F1 is
more specialized than the template for F2 according to the partial
ordering rules. */
-
+
if (cand1->template_decl && cand2->template_decl)
{
winner = more_specialized_fn
if (winner)
return winner;
}
-
+
/* Check whether we can discard a builtin candidate, either because we
have two identical ones or matching builtin and non-builtin candidates.
(Pedantically in the latter case the builtin which matched the user
function should not be added to the overload set, but we spot it here.
-
+
[over.match.oper]
... the builtin candidates include ...
- do not have the same parameter type list as any non-template
non-member candidate. */
-
+
if (TREE_CODE (cand1->fn) == IDENTIFIER_NODE
|| TREE_CODE (cand2->fn) == IDENTIFIER_NODE)
{
if (DECL_P (cand1->fn) && DECL_P (cand2->fn)
&& equal_functions (cand1->fn, cand2->fn))
return 1;
-
+
tweak:
/* Extension: If the worst conversion for one candidate is worse than the
/* Make sure the champ is better than all the candidates it hasn't yet
been compared to. */
- for (challenger = candidates;
- challenger != champ
+ for (challenger = candidates;
+ challenger != champ
&& !(champ_compared_to_predecessor && challenger->next == champ);
challenger = challenger->next)
{
cast. */
tree
-perform_direct_initialization_if_possible (tree type,
+perform_direct_initialization_if_possible (tree type,
tree expr,
bool c_cast_p)
{
if (!conv || conv->bad_p)
expr = NULL_TREE;
else
- expr = convert_like_real (conv, expr, NULL_TREE, 0, 0,
+ expr = convert_like_real (conv, expr, NULL_TREE, 0, 0,
/*issue_conversion_warnings=*/false,
c_cast_p);
with the indicated TYPE; this variable will store the value to
which the reference is bound. */
-tree
+tree
make_temporary_var_for_ref_to_temp (tree decl, tree type)
{
tree var;
type, TREE_TYPE (expr));
else
error ("invalid initialization of reference of type "
- "%qT from expression of type %qT", type,
+ "%qT from expression of type %qT", type,
TREE_TYPE (expr));
return error_mark_node;
}
full-expression in which they are created.
In that case, we store the converted expression into a new
- VAR_DECL in a new scope.
+ VAR_DECL in a new scope.
However, we want to be careful not to create temporaries when
they are not required. For example, given:
- struct B {};
+ struct B {};
struct D : public B {};
D f();
const B& b = f();
/* Use its address to initialize the reference variable. */
expr = build_address (var);
if (base_conv_type)
- expr = convert_to_base (expr,
+ expr = convert_to_base (expr,
build_pointer_type (base_conv_type),
/*check_access=*/true,
/*nonnull=*/true);
expr = build_unary_op (ADDR_EXPR, expr, 0);
/* If a BASE_CONV was required, perform it now. */
if (base_conv_type)
- expr = (perform_implicit_conversion
+ expr = (perform_implicit_conversion
(build_pointer_type (base_conv_type), expr));
expr = build_nop (type, expr);
}
&& SAME_BINFO_TYPE_P (BINFO_TYPE (binfo), probe))
|| (code == PLUS_EXPR
&& SAME_BINFO_TYPE_P (BINFO_TYPE (d_binfo), probe)));
-
+
if (binfo == d_binfo)
/* Nothing to do. */
return expr;
else
v_offset = build_vfield_ref (build_indirect_ref (expr, NULL),
TREE_TYPE (TREE_TYPE (expr)));
-
+
v_offset = build2 (PLUS_EXPR, TREE_TYPE (v_offset),
v_offset, BINFO_VPTR_FIELD (v_binfo));
- v_offset = build1 (NOP_EXPR,
+ v_offset = build1 (NOP_EXPR,
build_pointer_type (ptrdiff_type_node),
v_offset);
v_offset = build_indirect_ref (v_offset, NULL);
TREE_INVARIANT (v_offset) = 1;
offset = convert_to_integer (ptrdiff_type_node,
- size_diffop (offset,
+ size_diffop (offset,
BINFO_OFFSET (v_binfo)));
if (!integer_zerop (offset))
}
target_type = code == PLUS_EXPR ? BINFO_TYPE (binfo) : BINFO_TYPE (d_binfo);
-
+
target_type = cp_build_qualified_type
(target_type, cp_type_quals (TREE_TYPE (TREE_TYPE (expr))));
ptr_target_type = build_pointer_type (target_type);
if (want_pointer)
target_type = ptr_target_type;
-
+
expr = build1 (NOP_EXPR, ptr_target_type, expr);
if (!integer_zerop (offset))
expr = build2 (code, ptr_target_type, expr, offset);
else
null_test = NULL;
-
+
if (!want_pointer)
expr = build_indirect_ref (expr, NULL);
if (d_binfo == NULL_TREE)
{
tree temp;
-
+
gcc_assert (TYPE_MAIN_VARIANT (TREE_TYPE (expr)) == type);
-
+
/* Transform `(a, b).x' into `(*(a, &b)).x', `(a ? b : c).x'
into `(*(a ? &b : &c)).x', and so on. A COND_EXPR is only
an lvalue in the frontend; only _DECLs and _REFs are lvalues
cp_build_qualified_type (type, type_quals),
expr, field, NULL_TREE);
expr = fold_if_not_in_template (expr);
-
+
/* Mark the expression const or volatile, as appropriate.
Even though we've dealt with the type above, we still have
to mark the expression itself. */
TREE_READONLY (expr) = 1;
if (type_quals & TYPE_QUAL_VOLATILE)
TREE_THIS_VOLATILE (expr) = 1;
-
+
return expr;
}
object_type = TREE_TYPE (object);
binfo = lookup_base (object_type, type,
- check_access ? ba_check : ba_unique,
+ check_access ? ba_check : ba_unique,
NULL);
if (!binfo || binfo == error_mark_node)
return error_mark_node;
pointer_type = build_pointer_type (expr_type);
expr = build_unary_op (ADDR_EXPR, expr, /*noconvert=*/1);
if (!integer_zerop (BINFO_OFFSET (base)))
- expr = build2 (PLUS_EXPR, pointer_type, expr,
+ expr = build2 (PLUS_EXPR, pointer_type, expr,
build_nop (pointer_type, BINFO_OFFSET (base)));
expr = build_nop (build_pointer_type (BINFO_TYPE (base)), expr);
expr = build1 (INDIRECT_REF, BINFO_TYPE (base), expr);
if (!vtbl)
vtbl = build_vfield_ref (instance, basetype);
-
+
assemble_external (vtbl);
aref = build_array_ref (vtbl, idx);
is rather important that such things be ignored because any
effort to actually generate DWARF for them will run into
trouble when/if we encounter code like:
-
+
#pragma interface
struct S { virtual void member (); };
-
+
because the artificial declaration of the vtable itself (as
manufactured by the g++ front end) will say that the vtable is
a static member of `S' but only *after* the debug output for
impossible to actually build the vtable, but is useful to get at those
which are known to exist in the runtime. */
-tree
+tree
get_vtable_decl (tree type, int complete)
{
tree decl;
if (CLASSTYPE_VTABLES (type))
return CLASSTYPE_VTABLES (type);
-
+
decl = build_vtable (type, get_vtable_name (type), vtbl_type_node);
CLASSTYPE_VTABLES (type) = decl;
tree virtuals;
decl = get_vtable_decl (type, /*complete=*/0);
-
+
if (binfo)
{
if (BINFO_NEW_VTABLE_MARKED (binfo))
/* We have already created a vtable for this base, so there's
no need to do it again. */
return 0;
-
+
virtuals = copy_list (BINFO_VIRTUALS (binfo));
TREE_TYPE (decl) = TREE_TYPE (get_vtbl_decl_for_binfo (binfo));
DECL_SIZE (decl) = TYPE_SIZE (TREE_TYPE (decl));
/* Remember that we've created a vtable for this BINFO, so that we
don't try to do so again. */
SET_BINFO_NEW_VTABLE_MARKED (binfo);
-
+
/* Make fresh virtual list, so we can smash it later. */
BINFO_VIRTUALS (binfo) = copy_list (BINFO_VIRTUALS (binfo));
static void
modify_vtable_entry (tree t,
- tree binfo,
- tree fndecl,
- tree delta,
+ tree binfo,
+ tree fndecl,
+ tree delta,
tree *virtuals)
{
tree v;
else if (DECL_MAYBE_IN_CHARGE_DESTRUCTOR_P (method))
{
slot = CLASSTYPE_DESTRUCTOR_SLOT;
-
+
if (TYPE_FOR_JAVA (type))
{
if (!DECL_ARTIFICIAL (method))
insert_p = true;
/* See if we already have an entry with this name. */
- for (slot = CLASSTYPE_FIRST_CONVERSION_SLOT;
+ for (slot = CLASSTYPE_FIRST_CONVERSION_SLOT;
VEC_iterate (tree, method_vec, slot, m);
++slot)
{
}
}
current_fns = insert_p ? NULL_TREE : VEC_index (tree, method_vec, slot);
-
+
if (processing_template_decl)
/* TYPE is a template class. Don't issue any errors now; wait
until instantiation time to complain. */
&& (TYPE_QUALS (TREE_TYPE (TREE_VALUE (parms1)))
!= TYPE_QUALS (TREE_TYPE (TREE_VALUE (parms2)))))
same = 0;
-
+
/* For templates, the template parms must be identical. */
if (TREE_CODE (fn) == TEMPLATE_DECL
&& !comp_template_parms (DECL_TEMPLATE_PARMS (fn),
DECL_TEMPLATE_PARMS (method)))
same = 0;
-
+
if (! DECL_STATIC_FUNCTION_P (fn))
parms1 = TREE_CHAIN (parms1);
if (! DECL_STATIC_FUNCTION_P (method))
parms2 = TREE_CHAIN (parms2);
- if (same && compparms (parms1, parms2)
- && (!DECL_CONV_FN_P (fn)
+ if (same && compparms (parms1, parms2)
+ && (!DECL_CONV_FN_P (fn)
|| same_type_p (TREE_TYPE (TREE_TYPE (fn)),
TREE_TYPE (TREE_TYPE (method)))))
{
cp_error_at ("%q#D cannot be overloaded", method);
cp_error_at ("with %q#D", fn);
}
-
+
/* We don't call duplicate_decls here to merge the
declarations because that will confuse things if the
methods have inline definitions. In particular, we
}
}
- /* Add the new binding. */
+ /* Add the new binding. */
overload = build_overload (method, current_fns);
-
+
if (!conv_p && slot >= CLASSTYPE_FIRST_CONVERSION_SLOT && !complete_p)
push_class_level_binding (DECL_NAME (method), overload);
tree old_value;
gcc_assert (!processing_template_decl && decl);
-
+
old_value = lookup_member (t, name, /*protect=*/0, /*want_type=*/false);
if (old_value)
{
else
old_value = NULL_TREE;
}
-
+
cp_emit_debug_info_for_using (decl, current_class_type);
-
+
if (is_overloaded_fn (decl))
flist = decl;
cp_error_at (" because of local member %q#D with same name", old_value);
return;
}
-
+
/* Make type T see field decl FDECL with access ACCESS. */
if (flist)
for (; flist; flist = OVL_NEXT (flist))
tree basetype = TREE_TYPE (base_binfo);
gcc_assert (COMPLETE_TYPE_P (basetype));
-
+
/* Effective C++ rule 14. We only need to check TYPE_POLYMORPHIC_P
here because the case of virtual functions but non-virtual
dtor is handled in finish_struct_1. */
/* A lot of properties from the bases also apply to the derived
class. */
TYPE_NEEDS_CONSTRUCTING (t) |= TYPE_NEEDS_CONSTRUCTING (basetype);
- TYPE_HAS_NONTRIVIAL_DESTRUCTOR (t)
+ TYPE_HAS_NONTRIVIAL_DESTRUCTOR (t)
|= TYPE_HAS_NONTRIVIAL_DESTRUCTOR (basetype);
- TYPE_HAS_COMPLEX_ASSIGN_REF (t)
+ TYPE_HAS_COMPLEX_ASSIGN_REF (t)
|= TYPE_HAS_COMPLEX_ASSIGN_REF (basetype);
TYPE_HAS_COMPLEX_INIT_REF (t) |= TYPE_HAS_COMPLEX_INIT_REF (basetype);
TYPE_POLYMORPHIC_P (t) |= TYPE_POLYMORPHIC_P (basetype);
- CLASSTYPE_CONTAINS_EMPTY_CLASS_P (t)
+ CLASSTYPE_CONTAINS_EMPTY_CLASS_P (t)
|= CLASSTYPE_CONTAINS_EMPTY_CLASS_P (basetype);
}
}
{
tree parent = BINFO_INHERITANCE_CHAIN (base_binfo);
tree parent_primary = CLASSTYPE_PRIMARY_BINFO (BINFO_TYPE (parent));
-
+
if (parent_primary
&& SAME_BINFO_TYPE_P (BINFO_TYPE (base_binfo),
BINFO_TYPE (parent_primary)))
else
{
tree delta;
-
+
BINFO_PRIMARY_P (this_primary) = 1;
BINFO_INHERITANCE_CHAIN (this_primary) = base_binfo;
-
+
/* A virtual binfo might have been copied from within
another hierarchy. As we're about to use it as a
primary base, make sure the offsets match. */
BINFO_OFFSET (base_binfo)),
convert (ssizetype,
BINFO_OFFSET (this_primary)));
-
+
propagate_binfo_offsets (this_primary, delta);
}
}
/* Remember the first candidate. */
primary = base_binfo;
}
-
+
found:
/* If we've got a primary base, use it. */
if (primary)
{
tree basetype = BINFO_TYPE (primary);
-
+
CLASSTYPE_PRIMARY_BINFO (t) = primary;
if (BINFO_PRIMARY_P (primary))
/* We are stealing a primary base. */
base, make sure the offsets match. */
delta = size_diffop (ssize_int (0),
convert (ssizetype, BINFO_OFFSET (primary)));
-
+
propagate_binfo_offsets (primary, delta);
}
-
+
primary = TYPE_BINFO (basetype);
-
+
TYPE_VFIELD (t) = TYPE_VFIELD (basetype);
BINFO_VTABLE (type_binfo) = BINFO_VTABLE (primary);
BINFO_VIRTUALS (type_binfo) = BINFO_VIRTUALS (primary);
finish_struct_bits (tree t)
{
tree variants;
-
+
/* Fix up variants (if any). */
for (variants = TYPE_NEXT_VARIANT (t);
variants;
the TYPE_LANG_SPECIFIC component, so they are not shared. */
TYPE_HAS_CONSTRUCTOR (variants) = TYPE_HAS_CONSTRUCTOR (t);
TYPE_NEEDS_CONSTRUCTING (variants) = TYPE_NEEDS_CONSTRUCTING (t);
- TYPE_HAS_NONTRIVIAL_DESTRUCTOR (variants)
+ TYPE_HAS_NONTRIVIAL_DESTRUCTOR (variants)
= TYPE_HAS_NONTRIVIAL_DESTRUCTOR (t);
TYPE_POLYMORPHIC_P (variants) = TYPE_POLYMORPHIC_P (t);
-
+
TYPE_BINFO (variants) = TYPE_BINFO (t);
/* Copy whatever these are holding today. */
recalculate what's really an abstract virtual at this point (by
looking in the vtables). */
get_pure_virtuals (t);
-
+
/* If this type has a copy constructor or a destructor, force its
mode to be BLKmode, and force its TREE_ADDRESSABLE bit to be
nonzero. This will cause it to be passed by invisible reference
}
/* Issue warnings about T having private constructors, but no friends,
- and so forth.
+ and so forth.
HAS_NONPRIVATE_METHOD is nonzero if T has any non-private methods or
static members. HAS_NONPRIVATE_STATIC_FN is nonzero if T has any
/* We will have warned when the template was declared; there's
no need to warn on every instantiation. */
|| CLASSTYPE_TEMPLATE_INSTANTIATION (t))
- /* There's no reason to even consider warning about this
+ /* There's no reason to even consider warning about this
class. */
return;
-
+
/* We only issue one warning, if more than one applies, because
otherwise, on code like:
for (fn = TYPE_METHODS (t); fn; fn = TREE_CHAIN (fn))
/* We're not interested in compiler-generated methods; they don't
provide any way to call private members. */
- if (!DECL_ARTIFICIAL (fn))
+ if (!DECL_ARTIFICIAL (fn))
{
if (!TREE_PRIVATE (fn))
{
- if (DECL_STATIC_FUNCTION_P (fn))
+ if (DECL_STATIC_FUNCTION_P (fn))
/* A non-private static member function is just like a
friend; it can create and invoke private member
functions, and be accessed without a class
instance. */
return;
-
+
has_nonprivate_method = 1;
/* Keep searching for a static member function. */
}
else if (!DECL_CONSTRUCTOR_P (fn) && !DECL_DESTRUCTOR_P (fn))
has_member_fn = 1;
- }
+ }
- if (!has_nonprivate_method && has_member_fn)
+ if (!has_nonprivate_method && has_member_fn)
{
/* There are no non-private methods, and there's at least one
private member function that isn't a constructor or
constructors/destructors.) */
unsigned i;
tree binfo = TYPE_BINFO (t);
-
+
for (i = 0; i != BINFO_N_BASE_BINFOS (binfo); i++)
if (BINFO_BASE_ACCESS (binfo, i) != access_private_node)
{
has_nonprivate_method = 1;
break;
}
- if (!has_nonprivate_method)
+ if (!has_nonprivate_method)
{
warning (0, "all member functions in class %qT are private", t);
return;
if (TYPE_HAS_CONSTRUCTOR (t))
{
int nonprivate_ctor = 0;
-
+
/* If a non-template class does not define a copy
constructor, one is defined for it, enabling it to avoid
this warning. For a template class, this does not
happen, and so we would normally get a warning on:
- template <class T> class C { private: C(); };
-
+ template <class T> class C { private: C(); };
+
To avoid this asymmetry, we check TYPE_HAS_INIT_REF. All
complete non-template or fully instantiated classes have this
flag set. */
if (!TYPE_HAS_INIT_REF (t))
nonprivate_ctor = 1;
- else
- for (fn = CLASSTYPE_CONSTRUCTORS (t); fn; fn = OVL_NEXT (fn))
+ else
+ for (fn = CLASSTYPE_CONSTRUCTORS (t); fn; fn = OVL_NEXT (fn))
{
tree ctor = OVL_CURRENT (fn);
/* Ideally, we wouldn't count copy constructors (or, in
{
const tree *const m1 = m1_p;
const tree *const m2 = m2_p;
-
+
if (*m1 == NULL_TREE && *m2 == NULL_TREE)
return 0;
if (*m1 == NULL_TREE)
/* Resort TYPE_METHOD_VEC because pointers have been reordered. */
-void
+void
resort_type_method_vec (void* obj,
void* orig_obj ATTRIBUTE_UNUSED ,
gt_pointer_operator new_value,
len = VEC_length (tree, method_vec);
/* Clear DECL_IN_AGGR_P for all functions. */
- for (fn_fields = TYPE_METHODS (t); fn_fields;
+ for (fn_fields = TYPE_METHODS (t); fn_fields;
fn_fields = TREE_CHAIN (fn_fields))
DECL_IN_AGGR_P (fn_fields) = 0;
tree atype;
tree vtable;
- atype = build_cplus_array_type (vtable_entry_type,
+ atype = build_cplus_array_type (vtable_entry_type,
build_index_type (size_int (n - 1)));
layout_type (atype);
/* Returns TRUE if DERIVED is a binfo containing the binfo BASE as a
subobject. */
-
+
static bool
base_derived_from (tree derived, tree base)
{
Returns true if an overrider was found; false otherwise. */
static bool
-dfs_find_final_overrider_1 (tree binfo,
+dfs_find_final_overrider_1 (tree binfo,
find_final_overrider_data *ffod,
unsigned depth)
{
if (method)
{
tree *candidate = &ffod->candidates;
-
+
/* Remove any candidates overridden by this new function. */
while (*candidate)
{
else
candidate = &TREE_CHAIN (*candidate);
}
-
+
/* Add the new function. */
ffod->candidates = tree_cons (method, binfo, ffod->candidates);
return true;
struct T { virtual void f (); };
struct U : public S, public T { };
- even though calling `f' in `U' is ambiguous. But,
+ even though calling `f' in `U' is ambiguous. But,
struct R { virtual void f(); };
struct S : virtual public R { virtual void f (); };
struct U : public S, public T { };
is not -- there's no way to decide whether to put `S::f' or
- `T::f' in the vtable for `R'.
-
+ `T::f' in the vtable for `R'.
+
The solution is to look at all paths to BINFO. If we find
different overriders along any two, then there is a problem. */
if (DECL_THUNK_P (fn))
dfs_find_final_overrider_post, &ffod);
VEC_free (tree, heap, ffod.path);
-
+
/* If there was no winner, issue an error message. */
if (!ffod.candidates || TREE_CHAIN (ffod.candidates))
{
- error ("no unique final overrider for %qD in %qT", fn,
+ error ("no unique final overrider for %qD in %qT", fn,
BINFO_TYPE (derived));
return error_mark_node;
}
if (overrider == error_mark_node)
return;
overrider_target = overrider_fn = TREE_PURPOSE (overrider);
-
+
/* Check for adjusting covariant return types. */
over_return = TREE_TYPE (TREE_TYPE (overrider_target));
base_return = TREE_TYPE (TREE_TYPE (target_fn));
-
+
if (POINTER_TYPE_P (over_return)
&& TREE_CODE (over_return) == TREE_CODE (base_return)
&& CLASS_TYPE_P (TREE_TYPE (over_return))
over_return = TREE_TYPE (over_return);
base_return = TREE_TYPE (base_return);
-
+
if (DECL_THUNK_P (fn))
{
gcc_assert (DECL_RESULT_THUNK_P (fn));
if (SAME_BINFO_TYPE_P (BINFO_TYPE (thunk_binfo),
BINFO_TYPE (base_binfo)))
break;
-
+
/* See if virtual inheritance is involved. */
for (virtual_offset = thunk_binfo;
virtual_offset;
virtual_offset = BINFO_INHERITANCE_CHAIN (virtual_offset))
if (BINFO_VIRTUAL_P (virtual_offset))
break;
-
+
if (virtual_offset
|| (thunk_binfo && !BINFO_OFFSET_ZEROP (thunk_binfo)))
{
fixed_offset = offset;
}
}
-
+
if (fixed_offset || virtual_offset)
/* Replace the overriding function with a covariant thunk. We
will emit the overriding function in its own slot as
}
else
gcc_assert (!DECL_THUNK_P (fn));
-
+
/* Assume that we will produce a thunk that convert all the way to
the final overrider, and not to an intermediate virtual base. */
virtual_base = NULL_TREE;
&& (unsigned) list_length (BINFO_VIRTUALS (probe)) > ix)
if (BINFO_VIRTUAL_P (probe))
virtual_base = probe;
-
+
if (virtual_base)
/* Even if we find a virtual base, the correct delta is
between the overrider and the binfo we're building a vtable
for. */
goto virtual_covariant;
}
-
+
/* Compute the constant adjustment to the `this' pointer. The
`this' pointer, when this function is called, will point at BINFO
(or one of its primary bases, which are at the same offset). */
modify_vtable_entry (t, binfo, overrider_fn, delta, virtuals);
if (virtual_base)
- BV_VCALL_INDEX (*virtuals)
+ BV_VCALL_INDEX (*virtuals)
= get_vcall_index (overrider_target, BINFO_TYPE (virtual_base));
else
BV_VCALL_INDEX (*virtuals) = NULL_TREE;
/* A base without a vtable needs no modification, and its bases
are uninteresting. */
return dfs_skip_bases;
-
+
if (SAME_BINFO_TYPE_P (BINFO_TYPE (binfo), t)
&& !CLASSTYPE_HAS_PRIMARY_BASE_P (t))
/* Don't do the primary vtable, if it's new. */
return NULL_TREE;
make_new_vtable (t, binfo);
-
+
/* Now, go through each of the virtual functions in the virtual
function table for BINFO. Find the final overrider, and update
the BINFO_VIRTUALS list appropriately. */
virtuals;
ix++, virtuals = TREE_CHAIN (virtuals),
old_virtuals = TREE_CHAIN (old_virtuals))
- update_vtable_entry_for_fn (t,
- binfo,
+ update_vtable_entry_for_fn (t,
+ binfo,
BV_FN (old_virtuals),
&virtuals, ix);
size_t i;
/* We go through each separately named virtual function. */
- for (i = CLASSTYPE_FIRST_CONVERSION_SLOT;
+ for (i = CLASSTYPE_FIRST_CONVERSION_SLOT;
VEC_iterate (tree, method_vec, i, fns);
++i)
{
if (DECL_VINDEX (fndecl))
{
tree *prev = &base_fndecls;
-
- while (*prev)
+
+ while (*prev)
/* If the method from the base class has the same
signature as the method from the derived class, it
has been overridden. */
/* Now give a warning for all base functions without overriders,
as they are hidden. */
- while (base_fndecls)
+ while (base_fndecls)
{
/* Here we know it is a hider, and no overrider exists. */
cp_warning_at ("%qD was hidden", TREE_VALUE (base_fndecls));
though, so we explicitly tolerate that. We use
TYPE_ANONYMOUS_P rather than ANON_AGGR_TYPE_P so that
we also allow unnamed types used for defining fields. */
- if (DECL_ARTIFICIAL (elt)
+ if (DECL_ARTIFICIAL (elt)
&& (!DECL_IMPLICIT_TYPEDEF_P (elt)
|| TYPE_ANONYMOUS_P (TREE_TYPE (elt))))
continue;
will be used later during class template instantiation.
When FRIEND_P is zero, T can be a static member data (VAR_DECL),
a non-static member data (FIELD_DECL), a member function
- (FUNCTION_DECL), a nested type (RECORD_TYPE, ENUM_TYPE),
+ (FUNCTION_DECL), a nested type (RECORD_TYPE, ENUM_TYPE),
a typedef (TYPE_DECL) or a member class template (TEMPLATE_DECL)
When FRIEND_P is nonzero, T is either a friend class
(RECORD_TYPE, TEMPLATE_DECL) or a friend function
a const reference, respectively. */
static void
-add_implicitly_declared_members (tree t,
+add_implicitly_declared_members (tree t,
int cant_have_const_cctor,
int cant_have_const_assignment)
{
}
/* If we can't get away with being lazy, generate the destructor
- now. */
+ now. */
if (!lazy_p)
lazily_declare_fn (sfk_destructor, t);
}
cp_warning_at ("%qD is too small to hold all values of %q#T",
field, type);
}
-
+
/* Remove the bit-field width indicator so that the rest of the
compiler does not treat that value as an initializer. */
DECL_INITIAL (field) = NULL_TREE;
/* Never let anything with uninheritable virtuals
make it through without complaint. */
abstract_virtuals_error (field, type);
-
+
if (TREE_CODE (t) == UNION_TYPE)
{
if (TYPE_NEEDS_CONSTRUCTING (type))
else
{
TYPE_NEEDS_CONSTRUCTING (t) |= TYPE_NEEDS_CONSTRUCTING (type);
- TYPE_HAS_NONTRIVIAL_DESTRUCTOR (t)
+ TYPE_HAS_NONTRIVIAL_DESTRUCTOR (t)
|= TYPE_HAS_NONTRIVIAL_DESTRUCTOR (type);
TYPE_HAS_COMPLEX_ASSIGN_REF (t) |= TYPE_HAS_COMPLEX_ASSIGN_REF (type);
TYPE_HAS_COMPLEX_INIT_REF (t) |= TYPE_HAS_COMPLEX_INIT_REF (type);
/* If one of the data members contains an empty class,
so does T. */
element_type = strip_array_types (type);
- if (CLASS_TYPE_P (element_type)
+ if (CLASS_TYPE_P (element_type)
&& CLASSTYPE_CONTAINS_EMPTY_CLASS_P (element_type))
CLASSTYPE_CONTAINS_EMPTY_CLASS_P (t) = 1;
}
if (type == error_mark_node)
continue;
-
+
if (TREE_CODE (x) == CONST_DECL || TREE_CODE (x) == VAR_DECL)
continue;
-- Warn only if there is a non-trivial destructor. We assume that the
user at least implemented the cleanup correctly, and a destructor
is needed to free dynamic memory.
-
+
This seems enough for practical purposes. */
if (warn_ecpp
&& has_pointers
&& !(TYPE_HAS_INIT_REF (t) && TYPE_HAS_ASSIGN_REF (t)))
{
warning (0, "%q#T has pointer data members", t);
-
+
if (! TYPE_HAS_INIT_REF (t))
{
warning (0, " but does not override %<%T(const %T&)%>", t, t);
/* Record the location of this empty object in OFFSETS. */
n = splay_tree_lookup (offsets, (splay_tree_key) offset);
if (!n)
- n = splay_tree_insert (offsets,
+ n = splay_tree_insert (offsets,
(splay_tree_key) offset,
(splay_tree_value) NULL_TREE);
- n->value = ((splay_tree_value)
+ n->value = ((splay_tree_value)
tree_cons (NULL_TREE,
type,
(tree) n->value));
is returned. Otherwise, returns zero. */
static int
-walk_subobject_offsets (tree type,
- subobject_offset_fn f,
- tree offset,
- splay_tree offsets,
- tree max_offset,
+walk_subobject_offsets (tree type,
+ subobject_offset_fn f,
+ tree offset,
+ splay_tree offsets,
+ tree max_offset,
int vbases_p)
{
int r = 0;
if (max_offset && INT_CST_LT (max_offset, offset))
return 0;
- if (!TYPE_P (type))
+ if (!TYPE_P (type))
{
if (abi_version_at_least (2))
type_binfo = type;
{
tree binfo_offset;
- if (abi_version_at_least (2)
+ if (abi_version_at_least (2)
&& BINFO_VIRTUAL_P (binfo))
continue;
- if (!vbases_p
- && BINFO_VIRTUAL_P (binfo)
+ if (!vbases_p
+ && BINFO_VIRTUAL_P (binfo)
&& !BINFO_PRIMARY_P (binfo))
continue;
class yet, but the offsets for direct non-virtual
bases can be calculated by going back to the TYPE. */
orig_binfo = BINFO_BASE_BINFO (TYPE_BINFO (type), i);
- binfo_offset = size_binop (PLUS_EXPR,
+ binfo_offset = size_binop (PLUS_EXPR,
offset,
BINFO_OFFSET (orig_binfo));
}
binfo_offset,
offsets,
max_offset,
- (abi_version_at_least (2)
+ (abi_version_at_least (2)
? /*vbases_p=*/0 : vbases_p));
if (r)
return r;
virtual. (If it is non-virtual, then it was walked
above.) */
tree vbase = get_primary_binfo (type_binfo);
-
+
if (vbase && BINFO_VIRTUAL_P (vbase)
&& BINFO_PRIMARY_P (vbase)
&& BINFO_INHERITANCE_CHAIN (vbase) == type_binfo)
{
- r = (walk_subobject_offsets
+ r = (walk_subobject_offsets
(vbase, f, offset,
offsets, max_offset, /*vbases_p=*/0));
if (r)
/* Step through each of the elements in the array. */
for (index = size_zero_node;
/* G++ 3.2 had an off-by-one error here. */
- (abi_version_at_least (2)
+ (abi_version_at_least (2)
? !INT_CST_LT (TYPE_MAX_VALUE (domain), index)
: INT_CST_LT (index, TYPE_MAX_VALUE (domain)));
index = size_binop (PLUS_EXPR, index, size_one_node))
/*vbases_p=*/1);
if (r)
return r;
- offset = size_binop (PLUS_EXPR, offset,
+ offset = size_binop (PLUS_EXPR, offset,
TYPE_SIZE_UNIT (TREE_TYPE (type)));
/* If this new OFFSET is bigger than the MAX_OFFSET, then
there's no point in iterating through the remaining
examined. */
static void
-record_subobject_offsets (tree type,
- tree offset,
- splay_tree offsets,
+record_subobject_offsets (tree type,
+ tree offset,
+ splay_tree offsets,
int vbases_p)
{
walk_subobject_offsets (type, record_subobject_offset, offset,
static int
layout_conflict_p (tree type,
- tree offset,
- splay_tree offsets,
+ tree offset,
+ splay_tree offsets,
int vbases_p)
{
splay_tree_node max_node;
the position of the DECL. */
static void
-layout_nonempty_base_or_field (record_layout_info rli,
- tree decl,
- tree binfo,
+layout_nonempty_base_or_field (record_layout_info rli,
+ tree decl,
+ tree binfo,
splay_tree offsets)
{
tree offset = NULL_TREE;
bool field_p;
tree type;
-
+
if (binfo)
{
/* For the purposes of determining layout conflicts, we want to
/* We have to check to see whether or not there is already
something of the same type at the offset we're about to use.
For example, consider:
-
+
struct S {};
struct T : public S { int i; };
struct U : public S, public T {};
-
+
Here, we put S at offset zero in U. Then, we can't put T at
offset zero -- its S component would be at the same address
as the S we already allocated. So, we have to skip ahead.
virtual base. */
if (!abi_version_at_least (2) && binfo && BINFO_VIRTUAL_P (binfo))
break;
- if (layout_conflict_p (field_p ? type : binfo, offset,
+ if (layout_conflict_p (field_p ? type : binfo, offset,
offsets, field_p))
{
/* Strip off the size allocated to this field. That puts us
/* Bump up by the alignment required for the type. */
rli->bitpos
- = size_binop (PLUS_EXPR, rli->bitpos,
- bitsize_int (binfo
+ = size_binop (PLUS_EXPR, rli->bitpos,
+ bitsize_int (binfo
? CLASSTYPE_ALIGN (type)
: TYPE_ALIGN (type)));
normalize_rli (rli);
this point because their BINFO_OFFSET is copied from another
hierarchy. Therefore, we may not need to add the entire
OFFSET. */
- propagate_binfo_offsets (binfo,
+ propagate_binfo_offsets (binfo,
size_diffop (convert (ssizetype, offset),
- convert (ssizetype,
+ convert (ssizetype,
BINFO_OFFSET (binfo))));
}
"change in a future version of GCC",
BINFO_TYPE (binfo));
}
-
+
/* This is an empty base class. We first try to put it at offset
zero. */
if (layout_conflict_p (binfo,
BINFO_OFFSET (binfo),
- offsets,
+ offsets,
/*vbases_p=*/0))
{
/* That didn't work. Now, we move forward from the next
available spot in the class. */
atend = true;
propagate_binfo_offsets (binfo, convert (ssizetype, eoc));
- while (1)
+ while (1)
{
if (!layout_conflict_p (binfo,
- BINFO_OFFSET (binfo),
+ BINFO_OFFSET (binfo),
offsets,
/*vbases_p=*/0))
/* We finally found a spot where there's no overlap. */
any base class. OFFSETS gives the location of empty base
subobjects. T is the most derived type. Return nonzero if the new
object cannot be nearly-empty. A new FIELD_DECL is inserted at
- *NEXT_FIELD, unless BINFO is for an empty base class.
+ *NEXT_FIELD, unless BINFO is for an empty base class.
Returns the location at which the next field should be inserted. */
/* This error is now reported in xref_tag, thus giving better
location information. */
return next_field;
-
+
/* Place the base class. */
if (!is_empty_class (basetype))
{
/* The containing class is non-empty because it has a non-empty
base class. */
CLASSTYPE_EMPTY_P (t) = 0;
-
+
/* Create the FIELD_DECL. */
decl = build_decl (FIELD_DECL, NULL_TREE, CLASSTYPE_AS_BASE (basetype));
DECL_ARTIFICIAL (decl) = 1;
/* The check above (used in G++ 3.2) is insufficient because
an empty class placed at offset zero might itself have an
empty base at a nonzero offset. */
- else if (walk_subobject_offsets (basetype,
+ else if (walk_subobject_offsets (basetype,
empty_base_at_nonzero_offset_p,
size_zero_node,
/*offsets=*/NULL,
"future version of GCC", t);
}
}
-
+
/* We do not create a FIELD_DECL for empty base classes because
it might overlap some other field. We want to be able to
create CONSTRUCTORs for the class by iterating over the
/* Record the offsets of BINFO and its base subobjects. */
record_subobject_offsets (binfo,
BINFO_OFFSET (binfo),
- offsets,
+ offsets,
/*vbases_p=*/0);
return next_field;
parmtypes = TREE_CHAIN (parmtypes);
/* If this is subobject constructor or destructor, add the vtt
parameter. */
- TREE_TYPE (clone)
+ TREE_TYPE (clone)
= build_method_type_directly (basetype,
TREE_TYPE (TREE_TYPE (clone)),
parmtypes);
if (exceptions)
TREE_TYPE (clone) = build_exception_variant (TREE_TYPE (clone),
exceptions);
- TREE_TYPE (clone)
+ TREE_TYPE (clone)
= cp_build_type_attribute_variant (TREE_TYPE (clone),
TYPE_ATTRIBUTES (TREE_TYPE (fn)));
}
/* Create the RTL for this function. */
SET_DECL_RTL (clone, NULL_RTX);
rest_of_decl_compilation (clone, /*top_level=*/1, at_eof);
-
+
/* Make it easy to find the CLONE given the FN. */
TREE_CHAIN (clone) = TREE_CHAIN (fn);
TREE_CHAIN (fn) = clone;
{
tree result;
- DECL_TEMPLATE_RESULT (clone)
+ DECL_TEMPLATE_RESULT (clone)
= build_clone (DECL_TEMPLATE_RESULT (clone), name);
result = DECL_TEMPLATE_RESULT (clone);
DECL_TEMPLATE_INFO (result) = copy_node (DECL_TEMPLATE_INFO (result));
version. We clone the deleting version first because that
means it will go second on the TYPE_METHODS list -- and that
corresponds to the correct layout order in the virtual
- function table.
+ function table.
For a non-virtual destructor, we do not build a deleting
destructor. */
adjust_clone_args (tree decl)
{
tree clone;
-
+
for (clone = TREE_CHAIN (decl); clone && DECL_CLONED_FUNCTION (clone);
clone = TREE_CHAIN (clone))
{
tree decl_parms, clone_parms;
clone_parms = orig_clone_parms;
-
+
/* Skip the 'this' parameter. */
orig_clone_parms = TREE_CHAIN (orig_clone_parms);
orig_decl_parms = TREE_CHAIN (orig_decl_parms);
orig_decl_parms = TREE_CHAIN (orig_decl_parms);
if (DECL_HAS_VTT_PARM_P (decl))
orig_decl_parms = TREE_CHAIN (orig_decl_parms);
-
+
clone_parms = orig_clone_parms;
if (DECL_HAS_VTT_PARM_P (clone))
clone_parms = TREE_CHAIN (clone_parms);
-
+
for (decl_parms = orig_decl_parms; decl_parms;
decl_parms = TREE_CHAIN (decl_parms),
clone_parms = TREE_CHAIN (clone_parms))
{
gcc_assert (same_type_p (TREE_TYPE (decl_parms),
TREE_TYPE (clone_parms)));
-
+
if (TREE_PURPOSE (decl_parms) && !TREE_PURPOSE (clone_parms))
{
/* A default parameter has been added. Adjust the
if (exceptions)
type = build_exception_variant (type, exceptions);
TREE_TYPE (clone) = type;
-
+
clone_parms = NULL_TREE;
break;
}
{
tree *fieldsp;
- fieldsp = &TYPE_FIELDS (t);
+ fieldsp = &TYPE_FIELDS (t);
while (*fieldsp)
{
if (TREE_CODE (*fieldsp) == FIELD_DECL
- && DECL_C_BIT_FIELD (*fieldsp)
+ && DECL_C_BIT_FIELD (*fieldsp)
&& DECL_INITIAL (*fieldsp))
*fieldsp = TREE_CHAIN (*fieldsp);
else
argument is of type `size_t', then we have to pass the size of
the array to the deallocation function, so we will need to store
a cookie. */
- fns = lookup_fnfields (TYPE_BINFO (type),
+ fns = lookup_fnfields (TYPE_BINFO (type),
ansi_opname (VEC_DELETE_EXPR),
/*protect=*/0);
/* If there are no `operator []' members, or the lookup is
CLASSTYPE_NON_AGGREGATE (t)
|= (TYPE_HAS_CONSTRUCTOR (t) || TYPE_POLYMORPHIC_P (t));
CLASSTYPE_NON_POD_P (t)
- |= (CLASSTYPE_NON_AGGREGATE (t)
+ |= (CLASSTYPE_NON_AGGREGATE (t)
|| TYPE_HAS_NONTRIVIAL_DESTRUCTOR (t)
|| TYPE_HAS_ASSIGN_REF (t));
TYPE_HAS_COMPLEX_ASSIGN_REF (t)
&& TREE_CODE (DECL_VINDEX (fn)) != INTEGER_CST)
{
tree new_virtual = make_node (TREE_LIST);
-
+
BV_FN (new_virtual) = fn;
BV_DELTA (new_virtual) = integer_zero_node;
BV_VCALL_INDEX (new_virtual) = NULL_TREE;
TREE_CHAIN (new_virtual) = *virtuals_p;
*virtuals_p = new_virtual;
}
-
+
/* If we couldn't find an appropriate base class, create a new field
here. Even if there weren't any new virtual functions, we might need a
new virtual function table if we're supposed to include vptrs in
the derived class vtable pointer, since they have different
types. Thus, in a derived class destructor, where the base
class constructor was inlined, we could generate bad code for
- setting up the vtable pointer.
+ setting up the vtable pointer.
Therefore, we use one type for all vtable pointers. We still
use a type-correct type; it's just doesn't indicate the array
DECL_ARTIFICIAL (field) = 1;
DECL_FIELD_CONTEXT (field) = t;
DECL_FCONTEXT (field) = t;
-
+
TYPE_VFIELD (t) = field;
-
+
/* This class is non-empty. */
CLASSTYPE_EMPTY_P (t) = 0;
/* Update BINFO's offset. */
BINFO_OFFSET (binfo)
- = convert (sizetype,
+ = convert (sizetype,
size_binop (PLUS_EXPR,
convert (ssizetype, BINFO_OFFSET (binfo)),
offset));
if (primary_binfo && BINFO_INHERITANCE_CHAIN (primary_binfo) == binfo)
propagate_binfo_offsets (primary_binfo, offset);
-
+
/* Scan all of the bases, pushing the BINFO_OFFSET adjust
downwards. */
for (i = 0; BINFO_BASE_ITERATE (binfo, i, base_binfo); ++i)
the results which is not particularly tractable. */
if (warn_abi
&& first_vbase
- && (tree_int_cst_lt
+ && (tree_int_cst_lt
(size_binop (CEIL_DIV_EXPR,
round_up (CLASSTYPE_SIZE (t),
CLASSTYPE_ALIGN (basetype)),
/* If there are no repeated bases, nothing can be ambiguous. */
if (!CLASSTYPE_REPEATED_BASE_P (t))
return;
-
+
/* Check direct bases. */
for (binfo = TYPE_BINFO (t), i = 0;
BINFO_BASE_ITERATE (binfo, i, base_binfo); ++i)
VEC_iterate (tree, vbases, i, binfo); i++)
{
basetype = BINFO_TYPE (binfo);
-
+
if (!lookup_base (t, basetype, ba_unique | ba_quiet, NULL))
warning (0, "virtual base %qT inaccessible in %qT due to ambiguity",
basetype, t);
because we are willing to overlay multiple bases at the same
offset. However, now we need to make sure that RLI is big enough
to reflect the entire class. */
- eoc = end_of_class (rli->t,
+ eoc = end_of_class (rli->t,
CLASSTYPE_AS_BASE (rli->t) != NULL_TREE);
rli_size = rli_size_unit_so_far (rli);
if (TREE_CODE (rli_size) == INTEGER_CST
/* The size should have been rounded to a whole byte. */
gcc_assert (tree_int_cst_equal
(rli->bitpos, round_down (rli->bitpos, BITS_PER_UNIT)));
- rli->bitpos
- = size_binop (PLUS_EXPR,
+ rli->bitpos
+ = size_binop (PLUS_EXPR,
rli->bitpos,
size_binop (MULT_EXPR,
convert (bitsizetype,
next_field = &TYPE_FIELDS (t);
/* Build FIELD_DECLs for all of the non-virtual base-types. */
- empty_base_offsets = splay_tree_new (splay_tree_compare_integer_csts,
+ empty_base_offsets = splay_tree_new (splay_tree_compare_integer_csts,
NULL, NULL);
build_base_fields (rli, empty_base_offsets, next_field);
-
+
/* Layout the non-static data members. */
for (field = non_static_data_members; field; field = TREE_CHAIN (field))
{
{
place_field (rli, field);
/* If the static data member has incomplete type, keep track
- of it so that it can be completed later. (The handling
+ of it so that it can be completed later. (The handling
of pending statics in finish_record_layout is
insufficient; consider:
struct S1;
struct S2 { static S1 s1; };
-
+
At this point, finish_record_layout will be called, but
S1 is still incomplete.) */
if (TREE_CODE (field) == VAR_DECL)
}
type = TREE_TYPE (field);
-
+
padding = NULL_TREE;
/* If this field is a bit-field whose width is greater than its
of the field. Then, we are supposed to use the left over
bits as additional padding. */
for (itk = itk_char; itk != itk_none; ++itk)
- if (INT_CST_LT (DECL_SIZE (field),
+ if (INT_CST_LT (DECL_SIZE (field),
TYPE_SIZE (integer_types[itk])))
break;
if (warn_abi && TREE_CODE (t) == UNION_TYPE)
warning (0, "size assigned to %qT may not be "
"ABI-compliant and may change in a future "
- "version of GCC",
+ "version of GCC",
t);
padding = size_binop (MINUS_EXPR, DECL_SIZE (field),
TYPE_SIZE (integer_type));
/* Remember the location of any empty classes in FIELD. */
if (abi_version_at_least (2))
- record_subobject_offsets (TREE_TYPE (field),
+ record_subobject_offsets (TREE_TYPE (field),
byte_position(field),
empty_base_offsets,
/*vbases_p=*/1);
and yet it starts in the middle of a byte, we have failed to
comply with the ABI. */
if (warn_abi
- && DECL_C_BIT_FIELD (field)
+ && DECL_C_BIT_FIELD (field)
/* The TREE_NO_WARNING flag gets set by Objective-C when
laying out an Objective-C class. The ObjC ABI differs
from the C++ ABI, and so we do not want a warning
DECL_FIELD_BIT_OFFSET (field),
bitsize_unit_node)))
cp_warning_at ("offset of %qD is not ABI-compliant and may "
- "change in a future version of GCC",
+ "change in a future version of GCC",
field);
/* G++ used to use DECL_FIELD_OFFSET as if it were the byte
offset of the field. */
- if (warn_abi
+ if (warn_abi
&& !tree_int_cst_equal (DECL_FIELD_OFFSET (field),
byte_position (field))
&& contains_empty_class_p (TREE_TYPE (field)))
{
tree padding_field;
- padding_field = build_decl (FIELD_DECL,
+ padding_field = build_decl (FIELD_DECL,
NULL_TREE,
- char_type_node);
+ char_type_node);
DECL_BIT_FIELD (padding_field) = 1;
DECL_SIZE (padding_field) = padding;
DECL_CONTEXT (padding_field) = t;
DECL_ARTIFICIAL (padding_field) = 1;
DECL_IGNORED_P (padding_field) = 1;
layout_nonempty_base_or_field (rli, padding_field,
- NULL_TREE,
+ NULL_TREE,
empty_base_offsets);
}
if (CLASSTYPE_NON_POD_P (t) || CLASSTYPE_EMPTY_P (t))
{
base_t = make_node (TREE_CODE (t));
-
+
/* Set the size and alignment for the new type. In G++ 3.2, all
empty classes were considered to have size zero when used as
base classes. */
rli_size_so_far, rather than rli_size_unit_so_far, is
used to compute TYPE_SIZE_UNIT. */
eoc = end_of_class (t, /*include_virtuals_p=*/0);
- TYPE_SIZE_UNIT (base_t)
+ TYPE_SIZE_UNIT (base_t)
= size_binop (MAX_EXPR,
convert (sizetype,
size_binop (CEIL_DIV_EXPR,
rli_size_so_far (rli),
bitsize_int (BITS_PER_UNIT))),
eoc);
- TYPE_SIZE (base_t)
+ TYPE_SIZE (base_t)
= size_binop (MAX_EXPR,
rli_size_so_far (rli),
size_binop (MULT_EXPR,
if (TREE_CODE (field) == FIELD_DECL)
{
*next_field = build_decl (FIELD_DECL,
- DECL_NAME (field),
+ DECL_NAME (field),
TREE_TYPE (field));
DECL_CONTEXT (*next_field) = base_t;
DECL_FIELD_OFFSET (*next_field) = DECL_FIELD_OFFSET (field);
base subobject fields. */
layout_virtual_bases (rli, empty_base_offsets);
- /* Make sure that empty classes are reflected in RLI at this
+ /* Make sure that empty classes are reflected in RLI at this
point. */
include_empty_classes(rli);
/* Make sure not to create any structures with zero size. */
if (integer_zerop (rli_size_unit_so_far (rli)) && CLASSTYPE_EMPTY_P (t))
- place_field (rli,
+ place_field (rli,
build_decl (FIELD_DECL, NULL_TREE, char_type_node));
/* Let the back-end lay out the type. */
CLASSTYPE_PRIMARY_BINFO (t) = NULL_TREE;
fixup_inline_methods (t);
-
+
/* Make assumptions about the class; we'll reset the flags if
necessary. */
CLASSTYPE_EMPTY_P (t) = 1;
= chainon (BINFO_VIRTUALS (TYPE_BINFO (t)), virtuals);
/* Set DECL_VINDEX for all functions declared in this class. */
- for (vindex = 0, fn = BINFO_VIRTUALS (TYPE_BINFO (t));
- fn;
- fn = TREE_CHAIN (fn),
+ for (vindex = 0, fn = BINFO_VIRTUALS (TYPE_BINFO (t));
+ fn;
+ fn = TREE_CHAIN (fn),
vindex += (TARGET_VTABLE_USES_DESCRIPTORS
? TARGET_VTABLE_USES_DESCRIPTORS : 1))
{
/* Make the rtl for any new vtables we have created, and unmark
the base types we marked. */
finish_vtbls (t);
-
+
/* Build the VTT for T. */
build_vtt (t);
if it were virtual, we would have created it by now. */
!dtor
|| (!DECL_VINDEX (dtor)
- && (!TREE_PRIVATE (dtor)
- || CLASSTYPE_FRIEND_CLASSES (t)
+ && (!TREE_PRIVATE (dtor)
+ || CLASSTYPE_FRIEND_CLASSES (t)
|| DECL_FRIENDLIST (TYPE_MAIN_DECL (t)))))
- warning (0, "%q#T has virtual functions but non-virtual destructor",
+ warning (0, "%q#T has virtual functions but non-virtual destructor",
t);
}
maybe_suppress_debug_info (t);
dump_class_hierarchy (t);
-
+
/* Finish debugging output for this type. */
rest_of_type_compilation (t, ! LOCAL_CLASS_P (t));
}
/* Actually, for the TYPE_FIELDS, only the non TYPE_DECLs are in
reverse order, so we can't just use nreverse. */
prev = NULL_TREE;
- for (x = TYPE_FIELDS (t);
- x && TREE_CODE (x) != TYPE_DECL;
+ for (x = TYPE_FIELDS (t);
+ x && TREE_CODE (x) != TYPE_DECL;
x = next)
{
next = TREE_CHAIN (x);
{
if (nonnull)
*nonnull = 1;
-
+
/* if we're in a ctor or dtor, we know our type. */
if (DECL_LANG_SPECIFIC (current_function_decl)
&& (DECL_CONSTRUCTOR_P (current_function_decl)
/* Reference variables should be references to objects. */
if (nonnull)
*nonnull = 1;
-
+
/* DECL_VAR_MARKED_P is used to prevent recursion; a
variable's initializer may refer to the variable
itself. */
- if (TREE_CODE (instance) == VAR_DECL
+ if (TREE_CODE (instance) == VAR_DECL
&& DECL_INITIAL (instance)
&& !DECL_VAR_MARKED_P (instance))
{
{
tree t = TREE_TYPE (instance);
int cdtorp = 0;
-
+
tree fixed = fixed_type_or_null (instance, nonnull, &cdtorp);
if (fixed == NULL_TREE)
return 0;
{
current_class_depth = 0;
current_class_stack_size = 10;
- current_class_stack
+ current_class_stack
= xmalloc (current_class_stack_size * sizeof (struct class_stack_node));
local_classes = VEC_alloc (tree, gc, 8);
push_binding_level (previous_class_level);
class_binding_level = previous_class_level;
/* Restore IDENTIFIER_TYPE_VALUE. */
- for (type = class_binding_level->type_shadowed;
- type;
+ for (type = class_binding_level->type_shadowed;
+ type;
type = TREE_CHAIN (type))
SET_IDENTIFIER_TYPE_VALUE (TREE_PURPOSE (type), TREE_TYPE (type));
}
type = TYPE_MAIN_VARIANT (type);
/* Make sure there is enough room for the new entry on the stack. */
- if (current_class_depth + 1 >= current_class_stack_size)
+ if (current_class_depth + 1 >= current_class_stack_size)
{
current_class_stack_size *= 2;
current_class_stack
/* By default, things in classes are private, while things in
structures or unions are public. */
- current_access_specifier = (CLASSTYPE_DECLARED_CLASS (type)
- ? access_private_node
+ current_access_specifier = (CLASSTYPE_DECLARED_CLASS (type)
+ ? access_private_node
: access_public_node);
if (previous_class_level
invalidate_class_lookup_cache ();
}
- if (!previous_class_level
+ if (!previous_class_level
|| type != previous_class_level->this_entity
|| current_class_depth > 1)
pushlevel_class ();
{
previous_class_level = NULL;
}
-
+
/* Get out of the current class scope. If we were in a class scope
previously, that is the one popped to. */
tree context;
/* A namespace might be passed in error cases, like A::B:C. */
- if (type == NULL_TREE
- || type == error_mark_node
+ if (type == NULL_TREE
+ || type == error_mark_node
|| TREE_CODE (type) == NAMESPACE_DECL
|| ! IS_AGGR_TYPE (type)
|| TREE_CODE (type) == TEMPLATE_TYPE_PARM
|| TREE_CODE (type) == BOUND_TEMPLATE_TEMPLATE_PARM)
return;
-
+
context = DECL_CONTEXT (TYPE_MAIN_DECL (type));
if (context && CLASS_TYPE_P (context))
else
error ("language string %<\"%E\"%> not recognized", name);
}
-
+
/* Get out of the current language scope. */
void
template arguments. */
static tree
-resolve_address_of_overloaded_function (tree target_type,
+resolve_address_of_overloaded_function (tree target_type,
tree overload,
tsubst_flags_t flags,
bool template_only,
tree explicit_targs)
{
/* Here's what the standard says:
-
+
[over.over]
If the name is a function template, template argument deduction
|| TREE_CODE (TREE_TYPE (target_type)) != METHOD_TYPE);
gcc_assert (is_overloaded_fn (overload));
-
+
/* Check that the TARGET_TYPE is reasonable. */
if (TYPE_PTRFN_P (target_type))
/* This is OK. */;
target_type = build_reference_type (target_type);
is_reference = 1;
}
- else
+ else
{
if (flags & tf_error)
error ("cannot resolve overloaded function %qD based on"
- " conversion to type %qT",
+ " conversion to type %qT",
DECL_NAME (OVL_FUNCTION (overload)), target_type);
return error_mark_node;
}
-
+
/* If we can find a non-template function that matches, we can just
use it. There's no point in generating template instantiations
if we're just going to throw them out anyhow. But, of course, we
/* Now, if we've already got a match (or matches), there's no need
to proceed to the template functions. But, if we don't have a
match we need to look at them, too. */
- if (!matches)
+ if (!matches)
{
tree target_fn_type;
tree target_arg_types;
/* Never do unification on the 'this' parameter. */
if (TREE_CODE (target_fn_type) == METHOD_TYPE)
target_arg_types = TREE_CHAIN (target_arg_types);
-
+
for (fns = overload; fns; fns = OVL_NEXT (fns))
{
tree fn = OVL_CURRENT (fns);
/* See if there's a match. */
instantiation_type = TREE_TYPE (instantiation);
if (is_ptrmem)
- instantiation_type =
+ instantiation_type =
build_ptrmemfunc_type (build_pointer_type (instantiation_type));
else if (!is_reference)
instantiation_type = build_pointer_type (instantiation_type);
/* There were *no* matches. */
if (flags & tf_error)
{
- error ("no matches converting function %qD to type %q#T",
+ error ("no matches converting function %qD to type %q#T",
DECL_NAME (OVL_FUNCTION (overload)),
target_type);
for (; overload; overload = OVL_NEXT (overload))
matches = tree_cons (NULL_TREE, OVL_CURRENT (overload),
matches);
-
+
print_candidates (matches);
}
return error_mark_node;
{
tree match;
- error ("converting overloaded function %qD to type %q#T is ambiguous",
+ error ("converting overloaded function %qD to type %q#T is ambiguous",
DECL_NAME (OVL_FUNCTION (overload)),
target_type);
print_candidates (matches);
}
-
+
return error_mark_node;
}
&& !(flags & tf_ptrmem_ok) && !flag_ms_extensions)
{
static int explained;
-
+
if (!(flags & tf_error))
return error_mark_node;
we complain on errors. If we are not complaining, never modify rhs,
as overload resolution wants to try many possible instantiations, in
the hope that at least one will work.
-
+
For non-recursive calls, LHSTYPE should be a function, pointer to
function, or a pointer to member function. */
instantiate_type (tree lhstype, tree rhs, tsubst_flags_t flags)
{
tsubst_flags_t flags_in = flags;
-
+
flags &= ~tf_ptrmem_ok;
-
+
if (TREE_CODE (lhstype) == UNKNOWN_TYPE)
{
if (flags & tf_error)
{
if (same_type_p (lhstype, TREE_TYPE (rhs)))
return rhs;
- if (flag_ms_extensions
+ if (flag_ms_extensions
&& TYPE_PTRMEMFUNC_P (lhstype)
&& !TYPE_PTRMEMFUNC_P (TREE_TYPE (rhs)))
/* Microsoft allows `A::f' to be resolved to a
case OVERLOAD:
case FUNCTION_DECL:
- return
+ return
resolve_address_of_overloaded_function (lhstype, rhs, flags_in,
/*template_only=*/false,
/*explicit_targs=*/NULL_TREE);
TREE_TYPE (rhs) = lhstype;
return rhs;
-
+
case ADDR_EXPR:
{
if (PTRMEM_OK_P (rhs))
flags |= tf_ptrmem_ok;
-
+
return instantiate_type (lhstype, TREE_OPERAND (rhs, 0), flags);
}
|| !TYPE_CONTAINS_VPTR_P (BINFO_TYPE (base_binfo)))
break;
}
-
+
type = BINFO_TYPE (binfo);
buf = alloca (sizeof (VFIELD_NAME_FORMAT) + TYPE_NAME_LENGTH (type) + 2);
sprintf (buf, VFIELD_NAME_FORMAT,
if (!(innermost_scope_kind() == sk_class
&& TYPE_BEING_DEFINED (current_class_type)))
return;
-
+
/* If there's already a binding for this NAME, then we don't have
anything to worry about. */
- if (lookup_member (current_class_type, name,
+ if (lookup_member (current_class_type, name,
/*protect=*/0, /*want_type=*/false))
return;
names_used = current_class_stack[current_class_depth - 1].names_used;
splay_tree_insert (names_used,
- (splay_tree_key) name,
+ (splay_tree_key) name,
(splay_tree_value) decl);
}
splay_tree_node n;
/* Look to see if we ever used this name. */
- names_used
+ names_used
= current_class_stack[current_class_depth - 1].names_used;
if (!names_used)
return;
if (n)
{
/* [basic.scope.class]
-
+
A name N used in a class S shall refer to the same declaration
in its context and when re-evaluated in the completed scope of
S. */
error ("declaration of %q#D", decl);
- cp_error_at ("changes meaning of %qD from %q+#D",
+ cp_error_at ("changes meaning of %qD from %q+#D",
DECL_NAME (OVL_CURRENT (decl)),
(tree) n->value);
}
{
tree primary_base;
tree result;
-
+
primary_base = CLASSTYPE_PRIMARY_BINFO (BINFO_TYPE (binfo));
if (!primary_base)
return NULL_TREE;
int indented = 0;
tree base_binfo;
int i;
-
+
indented = maybe_indent_hierarchy (stream, indent, 0);
fprintf (stream, "%s (0x%lx) ",
type_as_string (BINFO_TYPE (binfo), TFF_PLAIN_IDENTIFIER),
return igo;
}
igo = TREE_CHAIN (binfo);
-
+
fprintf (stream, HOST_WIDE_INT_PRINT_DEC,
tree_low_cst (BINFO_OFFSET (binfo), 0));
if (is_empty_class (BINFO_TYPE (binfo)))
if (!(flags & TDF_SLIM))
{
int indented = 0;
-
+
if (BINFO_SUBVTT_INDEX (binfo))
{
indented = maybe_indent_hierarchy (stream, indent + 3, indented);
expr_as_string (BINFO_VTABLE (binfo),
TFF_PLAIN_IDENTIFIER));
}
-
+
if (indented)
fprintf (stream, "\n");
}
for (i = 0; BINFO_BASE_ITERATE (binfo, i, base_binfo); i++)
igo = dump_class_hierarchy_r (stream, flags, base_binfo, igo, indent + 2);
-
+
return igo;
}
if (!(flags & TDF_SLIM))
{
int ctor_vtbl_p = TYPE_BINFO (t) != binfo;
-
+
fprintf (stream, "%s for %s",
ctor_vtbl_p ? "Construction vtable" : "Vtable",
type_as_string (BINFO_TYPE (binfo), TFF_PLAIN_IDENTIFIER));
dump_array (stream, vtable);
fprintf (stream, "\n");
}
-
+
dump_end (TDI_class, stream);
}
dump_array (stream, vtt);
fprintf (stream, "\n");
}
-
+
dump_end (TDI_class, stream);
}
static const char spaces[] = " ";
tree name = DECL_NAME (thunk);
tree thunks;
-
+
fprintf (stream, "%.*s%p %s %s", indent, spaces,
(void *)thunk,
!DECL_THUNK_P (thunk) ? "function"
list = build_tree_list (BINFO_VTABLE (TYPE_BINFO (t)), NULL_TREE);
accumulate_vtbl_inits (TYPE_BINFO (t), TYPE_BINFO (t),
TYPE_BINFO (t), t, list);
-
+
/* Then come the virtual bases, also in inheritance graph order. */
for (vbase = TYPE_BINFO (t); vbase; vbase = TREE_CHAIN (vbase))
{
/* Build the VTT (virtual table table) for T.
A class requires a VTT if it has virtual bases.
-
+
This holds
1 - primary virtual pointer for complete object T
2 - secondary VTTs for each direct non-virtual base of T which requires a
3 - secondary virtual pointers for each direct or indirect base of T which
has virtual bases or is reachable via a virtual path from T.
4 - secondary VTTs for each direct or indirect virtual base of T.
-
+
Secondary VTTs look like complete object VTTs without part 4. */
static void
/* Figure out the type of the VTT. */
type = build_index_type (size_int (list_length (inits) - 1));
type = build_cplus_array_type (const_ptr_type_node, type);
-
+
/* Now, build the VTT object itself. */
vtt = build_vtable (t, get_vtt_name (t), type);
initialize_artificial_var (vtt, inits);
BINFO_VPTR_INDEX (binfo) = *index;
}
*index = size_binop (PLUS_EXPR, *index, TYPE_SIZE_UNIT (ptr_type_node));
-
+
/* Recursively add the secondary VTTs for non-virtual bases. */
for (i = 0; BINFO_BASE_ITERATE (binfo, i, b); ++i)
if (!BINFO_VIRTUAL_P (b))
inits = build_vtt_inits (b, t, inits, index);
-
+
/* Add secondary virtual pointers for all subobjects of BINFO with
either virtual bases or reachable along a virtual path, except
subobjects that are non-virtual primary bases. */
data.index = *index;
data.inits = NULL;
data.type_being_constructed = BINFO_TYPE (binfo);
-
+
dfs_walk_once (binfo, dfs_build_secondary_vptr_vtt_inits, NULL, &data);
*index = data.index;
{
if (!BINFO_VIRTUAL_P (b))
continue;
-
+
inits = build_vtt_inits (b, t, inits, index);
}
else
if (!(CLASSTYPE_VBASECLASSES (BINFO_TYPE (binfo))
|| binfo_via_virtual (binfo, data->type_being_constructed)))
return dfs_skip_bases;
-
+
/* We're not interested in non-virtual primary bases. */
if (!BINFO_VIRTUAL_P (binfo) && BINFO_PRIMARY_P (binfo))
return NULL_TREE;
-
+
/* Record the index where this secondary vptr can be found. */
if (data->top_level_p)
{
binfo = BINFO_INHERITANCE_CHAIN (binfo);
}
}
-
+
/* Add the initializer for the secondary vptr itself. */
data->inits = tree_cons (NULL_TREE, binfo_ctor_vtable (binfo), data->inits);
if (!TYPE_CONTAINS_VPTR_P (BINFO_TYPE (binfo)))
/* If this class has no vtable, none of its bases do. */
return dfs_skip_bases;
-
+
if (!vtable)
/* This might be a primary base, so have no vtable in this
hierarchy. */
return NULL_TREE;
-
+
/* If we scribbled the construction vtable vptr into BINFO, clear it
out now. */
if (TREE_CODE (vtable) == TREE_LIST
/* Add the vtables for each of our virtual bases using the vbase in T
binfo. */
- for (vbase = TYPE_BINFO (BINFO_TYPE (binfo));
- vbase;
+ for (vbase = TYPE_BINFO (BINFO_TYPE (binfo));
+ vbase;
vbase = TREE_CHAIN (vbase))
{
tree b;
if (!BINFO_VIRTUAL_P (vbase))
continue;
b = copied_binfo (vbase, binfo);
-
+
accumulate_vtbl_inits (b, vbase, binfo, t, list);
}
inits = TREE_VALUE (list);
/* If it doesn't have a vptr, we don't do anything. */
if (!TYPE_CONTAINS_VPTR_P (BINFO_TYPE (binfo)))
return;
-
+
/* If we're building a construction vtable, we're not interested in
subobjects that don't require construction vtables. */
- if (ctor_vtbl_p
+ if (ctor_vtbl_p
&& !CLASSTYPE_VBASECLASSES (BINFO_TYPE (binfo))
&& !binfo_via_virtual (orig_binfo, BINFO_TYPE (rtti_binfo)))
return;
/* Build the initializers for the BINFO-in-T vtable. */
- TREE_VALUE (inits)
+ TREE_VALUE (inits)
= chainon (TREE_VALUE (inits),
dfs_accumulate_vtbl_inits (binfo, orig_binfo,
rtti_binfo, t, inits));
-
+
/* Walk the BINFO and its bases. We walk in preorder so that as we
initialize each vtable we can figure out at what offset the
secondary vtable lies from the primary vtable. We can't use
primary, we still need a VTT entry for the vtable, but it
should point to the ctor vtable for the base it is a
primary for within the sub-hierarchy of RTTI_BINFO.
-
+
There are three possible cases:
-
+
1) We are in the same place.
2) We are a primary base within a lost primary virtual base of
RTTI_BINFO.
3) We are primary to something not a base of RTTI_BINFO. */
-
+
tree b;
tree last = NULL_TREE;
if (BINFO_VIRTUAL_P (b) || b == rtti_binfo)
break;
found:
-
+
/* If we found RTTI_BINFO, this is case 1. If we found a virtual
base B and it is a base of RTTI_BINFO, this is case 2. In
either case, we share our vtable with LAST, i.e. the
The value returned is a TREE_LIST suitable for wrapping in a
CONSTRUCTOR to use as the DECL_INITIAL for a vtable. If
NON_FN_ENTRIES_P is not NULL, *NON_FN_ENTRIES_P is set to the
- number of non-function entries in the vtable.
+ number of non-function entries in the vtable.
It might seem that this function should never be called with a
BINFO for which BINFO_PRIMARY_P holds, the vtable for such a
unsigned ix;
tree vbinfo;
VEC(tree,gc) *vbases;
-
+
/* Initialize VID. */
memset (&vid, 0, sizeof (vid));
vid.binfo = binfo;
vid.fns = VEC_alloc (tree, gc, 32);
/* Add the vcall and vbase offset entries. */
build_vcall_and_vbase_vtbl_entries (binfo, &vid);
-
+
/* Clear BINFO_VTABLE_PATH_MARKED; it's set by
build_vbase_offset_vtbl_entries. */
for (vbases = CLASSTYPE_VBASECLASSES (t), ix = 0;
tree vcall_index;
tree fn, fn_original;
tree init = NULL_TREE;
-
+
fn = BV_FN (v);
fn_original = fn;
if (DECL_THUNK_P (fn))
}
fn_original = THUNK_TARGET (fn);
}
-
+
/* If the only definition of this function signature along our
primary base chain is from a lost primary, this vtable slot will
never be used, so just zero it out. This is important to avoid
/* The initializers for virtual functions were built up in reverse
order; straighten them out now. */
vfun_inits = nreverse (vfun_inits);
-
+
/* The negative offset initializers are also in reverse order. */
vid.inits = nreverse (vid.inits);
return;
t = vid->derived;
-
+
/* We might be a primary base class. Go up the inheritance hierarchy
until we find the most derived class of which we are a primary base:
it is the offset of that which we need to use. */
{
tree b;
tree delta;
-
+
if (!BINFO_VIRTUAL_P (vbase))
continue;
BINFO_VTABLE_PATH_MARKED (b) = 1;
/* Figure out where we can find this vbase offset. */
- delta = size_binop (MULT_EXPR,
+ delta = size_binop (MULT_EXPR,
vid->index,
convert (ssizetype,
TYPE_SIZE_UNIT (vtable_entry_type)));
we are walking in inheritance graph order so these end up in
the right order. */
delta = size_diffop (BINFO_OFFSET (b), BINFO_OFFSET (non_primary_binfo));
-
- *vid->last_init
+
+ *vid->last_init
= build_tree_list (NULL_TREE,
- fold_build1 (NOP_EXPR,
+ fold_build1 (NOP_EXPR,
vtable_entry_type,
delta));
vid->last_init = &TREE_CHAIN (*vid->last_init);
through the recursion in build_vcall_and_vbase_vtbl_entries. */
if (BINFO_VIRTUAL_P (binfo) && vid->vbase != binfo)
return;
-
+
/* If BINFO has a primary base, process it first. */
primary_binfo = get_primary_binfo (binfo);
if (primary_binfo)
where rtti_binfo is the most derived type. */
non_primary_binfo
= original_binfo (non_primary_binfo, vid->rtti_binfo);
-
+
for (base_virtuals = BINFO_VIRTUALS (binfo),
derived_virtuals = BINFO_VIRTUALS (non_primary_binfo),
orig_virtuals = BINFO_VIRTUALS (TYPE_BINFO (BINFO_TYPE (binfo)));
signature as FN, then we do not need a second vcall offset.
Check the list of functions already present in the derived
class vtable. */
- for (i = 0; VEC_iterate (tree, vid->fns, i, derived_entry); ++i)
+ for (i = 0; VEC_iterate (tree, vid->fns, i, derived_entry); ++i)
{
if (same_signature_p (derived_entry, orig_fn)
/* We only use one vcall offset for virtual destructors,
elt->purpose = orig_fn;
elt->value = vid->index;
}
-
+
/* The next vcall offset will be found at a more negative
offset. */
vid->index = size_binop (MINUS_EXPR, vid->index,
decl = build_address (get_tinfo_decl (t));
else
decl = integer_zero_node;
-
+
/* Convert the declaration to a type that can be stored in the
vtable. */
init = build_nop (vfunc_ptr_type_node, decl);
CLEANUP_EXPR (stmt));
pointer_set_insert (p_set, *stmt_p);
-
+
return NULL;
}
the result. Since the "s" subobject is never
constructed, this is a valid transformation. */
|| CP_AGGREGATE_TYPE_P (type));
-
+
/* This would be wrong for a type with virtual bases, but they are
caught by the assert above. */
return (is_empty_class (type)
/* This file contains the definitions and documentation for the
additional tree codes used in the GNU C++ compiler (see tree.def
for the standard codes).
- Copyright (C) 1987, 1988, 1990, 1993, 1997, 1998, 2003, 2004, 2005,
+ Copyright (C) 1987, 1988, 1990, 1993, 1997, 1998, 2003, 2004, 2005,
1999, 2000, 2001, 2002, 2003, 2004, 2005 Free Software Foundation, Inc.
Hacked by Michael Tiemann (tiemann@cygnus.com)
the Free Software Foundation, 59 Temple Place - Suite 330,
Boston, MA 02111-1307, USA. */
-
+
/* An OFFSET_REF is used in two situations:
1. An expression of the form `A::m' where `A' is a class and `m' is
The expression is a pointer-to-member if its address is taken,
but simply denotes a member of the object if its address is not
taken.
-
+
This form is only used during the parsing phase; once semantic
analysis has taken place they are eliminated.
functions. BASELINK_BINFO gives the base from which the functions
come, i.e., the base to which the `this' pointer must be converted
before the functions are called. BASELINK_ACCESS_BINFO gives the
- base used to name the functions.
+ base used to name the functions.
A BASELINK is an expression; the TREE_TYPE of the BASELINK gives
the type of the expression. This type is either a FUNCTION_TYPE,
gives the level (from 1) of the parameter.
Here's an example:
-
+
template <class T> // Index 0, Level 1.
struct S
{
template <class U, // Index 0, Level 2.
class V> // Index 1, Level 2.
void f();
- };
+ };
The DESCENDANTS will be a chain of TEMPLATE_PARM_INDEXs descended
from this one. The first descendant will have the same IDX, but
class V> // Index 1, Level 1, Orig Level 2
void f();
};
-
+
The LEVEL is the level of the parameter when we are worrying about
the types of things; the ORIG_LEVEL is the level when we are
worrying about instantiating things. */
DEFTREECODE (TEMPLATE_PARM_INDEX, "template_parm_index", tcc_exceptional, 0)
/* Index into a template parameter list for template template parameters.
- This parameter must be a type. The TYPE_FIELDS value will be a
+ This parameter must be a type. The TYPE_FIELDS value will be a
TEMPLATE_PARM_INDEX.
- It is used without template arguments like TT in C<TT>,
+ It is used without template arguments like TT in C<TT>,
TEMPLATE_TEMPLATE_PARM_TEMPLATE_INFO is NULL_TREE
and TYPE_NAME is a TEMPLATE_DECL. */
DEFTREECODE (TEMPLATE_TEMPLATE_PARM, "template_template_parm", tcc_type, 0)
macros in tree.h. Changing the order will degrade the speed of the
compiler. TEMPLATE_TYPE_PARM, TYPENAME_TYPE, TYPEOF_TYPE,
BOUND_TEMPLATE_TEMPLATE_PARM. */
-
+
/* Index into a template parameter list. This parameter must be a type.
The type.value field will be a TEMPLATE_PARM_INDEX. */
DEFTREECODE (TEMPLATE_TYPE_PARM, "template_type_parm", tcc_type, 0)
expression in question. */
DEFTREECODE (TYPEOF_TYPE, "typeof_type", tcc_type, 0)
-/* Like TEMPLATE_TEMPLATE_PARM it is used with bound template arguments
+/* Like TEMPLATE_TEMPLATE_PARM it is used with bound template arguments
like TT<int>.
In this case, TEMPLATE_TEMPLATE_PARM_TEMPLATE_INFO contains the
template name and its bound arguments. TYPE_NAME is a TYPE_DECL. */
not an alias, but is later expanded into multiple aliases. */
DEFTREECODE (USING_DECL, "using_decl", tcc_declaration, 0)
-/* A using directive. The operand is USING_STMT_NAMESPACE. */
+/* A using directive. The operand is USING_STMT_NAMESPACE. */
DEFTREECODE (USING_STMT, "using_directive", tcc_statement, 1)
/* An un-parsed default argument. Holds a vector of input tokens and
member template, the template may be an IDENTIFIER_NODE. */
DEFTREECODE (TEMPLATE_ID_EXPR, "template_id_expr", tcc_expression, 2)
-/* A list-like node for chaining overloading candidates. TREE_TYPE is
+/* A list-like node for chaining overloading candidates. TREE_TYPE is
the original name, and the parameter is the FUNCTION_DECL. */
DEFTREECODE (OVERLOAD, "overload", tcc_exceptional, 0)
"OBJECT.SCOPE::~DESTRUCTOR. The first operand is the OBJECT. The
second operand (if non-NULL) is the SCOPE. The third operand is
the TYPE node corresponding to the DESTRUCTOR. The type of the
- first operand will always be a scalar type.
+ first operand will always be a scalar type.
The type of a PSEUDO_DTOR_EXPR is always "void", even though it can
be used as if it were a zero-argument function. We handle the
function-call case specially, and giving it "void" type prevents it
- being used in expressions in ways that are not permitted. */
+ being used in expressions in ways that are not permitted. */
DEFTREECODE (PSEUDO_DTOR_EXPR, "pseudo_dtor_expr", tcc_expression, 3)
/* A whole bunch of tree codes for the initial, superficial parsing of
/* Represents an 'if' statement. The operands are IF_COND,
THEN_CLAUSE, and ELSE_CLAUSE, respectively. */
-/* ??? It is currently still necessary to distinguish between IF_STMT
+/* ??? It is currently still necessary to distinguish between IF_STMT
and COND_EXPR for the benefit of templates. */
DEFTREECODE (IF_STMT, "if_stmt", tcc_statement, 3)
unsigned java_interface : 1;
unsigned debug_requested : 1;
unsigned fields_readonly : 1;
-
+
unsigned use_template : 2;
unsigned ptrmemfunc_flag : 1;
unsigned was_anonymous : 1;
it has not yet been declared. */
#define CLASSTYPE_LAZY_DESTRUCTOR(NODE) \
(LANG_TYPE_CLASS_CHECK (NODE)->lazy_destructor)
-
+
/* Nonzero means that this _CLASSTYPE node overloads operator=(X&). */
#define TYPE_HAS_ASSIGN_REF(NODE) (LANG_TYPE_CLASS_CHECK (NODE)->has_assign_ref)
unsigned initialized_in_class : 1;
unsigned assignment_operator_p : 1;
unsigned u1sel : 1;
-
+
unsigned u2sel : 1;
unsigned can_be_full : 1;
unsigned thunk_p : 1;
unsigned u3sel : 1;
unsigned pending_inline_p : 1;
unsigned spare : 22;
-
+
/* For a non-thunk function decl, this is a tree list of
friendly classes. For a thunk function decl, it is the
thunked to function decl. */
/* In a non-thunk FUNCTION_DECL or TEMPLATE_DECL, this is
DECL_CLONED_FUNCTION. */
tree GTY ((tag ("0"))) cloned_function;
-
+
/* In a FUNCTION_DECL for which THUNK_P holds this is the
THUNK_FIXED_OFFSET. */
HOST_WIDE_INT GTY ((tag ("1"))) fixed_offset;
} GTY ((desc ("%0.decl_flags.thunk_p"))) u5;
-
+
union lang_decl_u3
{
struct sorted_fields_type * GTY ((tag ("0"), reorder ("resort_sorted_fields")))
(TREE_CODE (NODE) == FUNCTION_DECL \
&& DECL_LANG_SPECIFIC (NODE) \
&& DECL_LANG_SPECIFIC (NODE)->decl_flags.thunk_p)
-
+
/* Set DECL_THUNK_P for node. */
#define SET_DECL_THUNK_P(NODE, THIS_ADJUSTING) \
(DECL_LANG_SPECIFIC (NODE)->decl_flags.thunk_p = 1, \
intype_class = TREE_TYPE (intype);
type_class = TREE_TYPE (type);
- same_p = same_type_p (TYPE_MAIN_VARIANT (intype_class),
+ same_p = same_type_p (TYPE_MAIN_VARIANT (intype_class),
TYPE_MAIN_VARIANT (type_class));
binfo = NULL_TREE;
/* Try derived to base conversion. */
}
else if (TYPE_PTRMEM_P (type) && TYPE_PTRMEM_P (intype))
{
- tree b1;
+ tree b1;
tree b2;
tree binfo;
enum tree_code code = PLUS_EXPR;
expr = cplus_expand_constant (expr);
if (binfo && !integer_zerop (BINFO_OFFSET (binfo)))
- expr = size_binop (code,
+ expr = size_binop (code,
build_nop (sizetype, expr),
BINFO_OFFSET (binfo));
return build_nop (type, expr);
}
else
expr = build_int_cst (type, 0);
-
+
return expr;
}
else if (TYPE_PTR_TO_MEMBER_P (type) && INTEGRAL_CODE_P (form))
as a pointer. */
gcc_assert (GET_MODE_SIZE (TYPE_MODE (TREE_TYPE (expr)))
== GET_MODE_SIZE (TYPE_MODE (type)));
-
+
return convert_to_pointer (type, expr);
}
{
tree intype = TREE_TYPE (expr);
enum tree_code form = TREE_CODE (intype);
-
+
if (form == POINTER_TYPE)
{
intype = TYPE_MAIN_VARIANT (intype);
/* Process the initializer for the declaration. */
DECL_INITIAL (arg) = targ;
- cp_finish_decl (arg, targ, NULL_TREE,
+ cp_finish_decl (arg, targ, NULL_TREE,
LOOKUP_ONLYCONVERTING|DIRECT_BIND);
}
else if (!(flags & DIRECT_BIND) && ! lvalue_p (arg))
/* Subroutine of convert_to_reference. REFTYPE is the target reference type.
INTYPE is the original rvalue type and DECL is an optional _DECL node
for diagnostics.
-
+
[dcl.init.ref] says that if an rvalue is used to
initialize a reference, then the reference must be to a
non-volatile const type. */
warn_ref_binding (tree reftype, tree intype, tree decl)
{
tree ttl = TREE_TYPE (reftype);
-
+
if (!CP_TYPE_CONST_NON_VOLATILE_P (ttl))
{
const char *msg;
tree rval_as_conversion = NULL_TREE;
bool can_convert_intype_to_type;
- if (TREE_CODE (type) == FUNCTION_TYPE
+ if (TREE_CODE (type) == FUNCTION_TYPE
&& TREE_TYPE (expr) == unknown_type_node)
- expr = instantiate_type (type, expr,
+ expr = instantiate_type (type, expr,
(flags & LOOKUP_COMPLAIN)
? tf_error | tf_warning : tf_none);
if (! real_lvalue_p (expr))
warn_ref_binding (reftype, intype, decl);
-
+
if (! (convtype & CONV_CONST)
&& !at_least_as_qualified_p (ttl, ttr))
pedwarn ("conversion from %qT to %qT discards qualifiers",
COMPARE_BASE | COMPARE_DERIVED)))
warning (0, "casting %qT to %qT does not dereference pointer",
intype, reftype);
-
+
rval = build_unary_op (ADDR_EXPR, expr, 0);
if (rval != error_mark_node)
rval = convert_force (build_pointer_type (TREE_TYPE (reftype)),
{
tree t = canonical_type_variant (TREE_TYPE (TREE_TYPE (val)));
tree ref = build1 (INDIRECT_REF, t, val);
-
+
/* We *must* set TREE_READONLY when dereferencing a pointer to const,
so that we get the proper error message if the result is used
to assign to. Also, &* is supposed to be a no-op. */
REFERENCE_REF_P (ref) = 1;
val = ref;
}
-
+
return val;
}
the target with the temp (see [dcl.init]). */
ctor = build_user_type_conversion (type, ctor, flags);
else
- ctor = build_special_member_call (NULL_TREE,
+ ctor = build_special_member_call (NULL_TREE,
complete_ctor_identifier,
build_tree_list (NULL_TREE, ctor),
type, flags);
volatile references we do not do this interpretation, because that would
make it impossible to ignore the reference return value from functions. We
issue warnings in the confusing cases.
-
+
IMPLICIT is tells us the context of an implicit void conversion. */
tree
convert_to_void (tree expr, const char *implicit)
{
- if (expr == error_mark_node
+ if (expr == error_mark_node
|| TREE_TYPE (expr) == error_mark_node)
return error_mark_node;
if (!TREE_TYPE (expr))
tree new_op2 = convert_to_void
(op2, (implicit && !TREE_SIDE_EFFECTS (op1)
? "third operand of conditional" : NULL));
-
+
expr = build3 (COND_EXPR, TREE_TYPE (new_op1),
TREE_OPERAND (expr, 0), new_op1, new_op2);
break;
}
-
+
case COMPOUND_EXPR:
{
/* The second part of a compound expr contains the value. */
tree new_op1 = convert_to_void
(op1, (implicit && !TREE_NO_WARNING (expr)
? "right-hand operand of comma" : NULL));
-
+
if (new_op1 != op1)
{
tree t = build2 (COMPOUND_EXPR, TREE_TYPE (new_op1),
break;
}
-
+
case NON_LVALUE_EXPR:
case NOP_EXPR:
/* These have already decayed to rvalue. */
break;
-
+
case CALL_EXPR: /* We have a special meaning for volatile void fn(). */
break;
-
+
case INDIRECT_REF:
{
tree type = TREE_TYPE (expr);
== REFERENCE_TYPE;
int is_volatile = TYPE_VOLATILE (type);
int is_complete = COMPLETE_TYPE_P (complete_type (type));
-
+
if (is_volatile && !is_complete)
warning (0, "object of incomplete type %qT will not be accessed in %s",
type, implicit ? implicit : "void context");
implicit ? implicit : "void context");
if (is_reference || !is_volatile || !is_complete)
expr = TREE_OPERAND (expr, 0);
-
+
break;
}
-
+
case VAR_DECL:
{
/* External variables might be incomplete. */
tree type = TREE_TYPE (expr);
int is_complete = COMPLETE_TYPE_P (complete_type (type));
-
+
if (TYPE_VOLATILE (type) && !is_complete)
warning (0, "object %qE of incomplete type %qT will not be accessed in %s",
expr, type, implicit ? implicit : "void context");
}
{
tree probe = expr;
-
+
if (TREE_CODE (probe) == ADDR_EXPR)
probe = TREE_OPERAND (expr, 0);
if (type_unknown_p (probe))
warning (0, "%s is a reference, not call, to function %qE",
implicit, expr);
}
-
+
if (expr != error_mark_node && !VOID_TYPE_P (TREE_TYPE (expr)))
{
if (implicit && warn_unused_value && !TREE_NO_WARNING (expr))
been explicitly cast to void, so we must do so here. */
if (!TREE_SIDE_EFFECTS (expr))
warning (0, "%s has no effect", implicit);
- else
- {
+ else
+ {
tree e;
enum tree_code code;
enum tree_code_class class;
-
+
e = expr;
/* We might like to warn about (say) "(int) f()", as the
cast has no effect, but the compiler itself will
class = TREE_CODE_CLASS (code);
if (class == tcc_comparison
|| class == tcc_unary
- || (class == tcc_binary
+ || (class == tcc_binary
&& !(code == MODIFY_EXPR
|| code == INIT_EXPR
|| code == PREDECREMENT_EXPR
enum tree_code code = TREE_CODE (type);
if (code == REFERENCE_TYPE)
- return (fold_if_not_in_template
+ return (fold_if_not_in_template
(convert_to_reference (type, e, CONV_C_CAST, LOOKUP_COMPLAIN,
NULL_TREE)));
tree conv = NULL_TREE;
tree winner = NULL_TREE;
- if (expr == null_node
- && (desires & WANT_INT)
+ if (expr == null_node
+ && (desires & WANT_INT)
&& !(desires & WANT_NULL))
warning (0, "converting NULL to non-pointer type");
-
+
basetype = TREE_TYPE (expr);
if (basetype == error_mark_node)
return (desires & WANT_FLOAT) ? expr : NULL_TREE;
case POINTER_TYPE:
return (desires & WANT_POINTER) ? expr : NULL_TREE;
-
+
case FUNCTION_TYPE:
case ARRAY_TYPE:
return (desires & WANT_POINTER) ? decay_conversion (expr)
}
else if (type == float_type_node)
type = double_type_node;
-
+
return type;
}
to TYPE. Return the resulting expression, or error_mark_node if
the conversion was impossible. */
-tree
+tree
perform_qualification_conversions (tree type, tree expr)
{
tree expr_type;
break;
case OVERLOAD:
- t = OVL_CURRENT (t);
+ t = OVL_CURRENT (t);
case VAR_DECL:
case PARM_DECL:
case CONST_DECL:
case USING_DECL:
case TEMPLATE_DECL:
t = DECL_NAME (t);
-
+
case IDENTIFIER_NODE:
if (t == NULL)
pp_cxx_identifier (pp, "<unnamed>");
pp_cxx_postfix_expression (cxx_pretty_printer *pp, tree t)
{
enum tree_code code = TREE_CODE (t);
-
+
switch (code)
{
case AGGR_INIT_EXPR:
tree object = code == AGGR_INIT_EXPR && AGGR_INIT_VIA_CTOR_P (t)
? TREE_OPERAND (t, 2)
: TREE_VALUE (args);
-
+
while (TREE_CODE (object) == NOP_EXPR)
object = TREE_OPERAND (object, 0);
if (TREE_CODE (object) == ADDR_EXPR)
object = TREE_OPERAND (object, 0);
-
+
if (TREE_CODE (TREE_TYPE (object)) != POINTER_TYPE)
{
pp_cxx_postfix_expression (pp, object);
pp_cxx_dot (pp);
}
- else
+ else
{
pp_cxx_postfix_expression (pp, object);
pp_cxx_arrow (pp);
pp_right_bracket (pp);
}
pp_c_cast_expression (pp_c_base (pp), TREE_OPERAND (t, 0));
- break;
-
+ break;
+
default:
pp_unsupported_tree (pp, t);
}
case VEC_DELETE_EXPR:
pp_cxx_delete_expression (pp, t);
break;
-
+
case SIZEOF_EXPR:
case ALIGNOF_EXPR:
pp_cxx_identifier (pp, code == SIZEOF_EXPR ? "sizeof" : "__alignof__");
pp_cxx_unqualified_id (pp, t);
break;
-#if 0
+#if 0
case OFFSET_REF:
-#endif
+#endif
case SCOPE_REF:
case PTRMEM_CST:
pp_cxx_qualified_id (pp, t);
case STATIC_CAST_EXPR:
case REINTERPRET_CAST_EXPR:
case CONST_CAST_EXPR:
-#if 0
+#if 0
case MEMBER_REF:
-#endif
+#endif
case EMPTY_CLASS_EXPR:
case TYPEID_EXPR:
case PSEUDO_DTOR_EXPR:
default:
pp_c_expression (pp_c_base (pp), t);
- break;
+ break;
}
}
pp_cxx_storage_class_specifier (pp, t);
pp_cxx_decl_specifier_seq (pp, TREE_TYPE (t));
break;
-
+
case TYPE_DECL:
pp_cxx_identifier (pp, "typedef");
pp_cxx_decl_specifier_seq (pp, TREE_TYPE (t));
pp_cxx_parameter_declaration_clause (cxx_pretty_printer *pp, tree t)
{
tree args = TYPE_P (t) ? NULL : FUNCTION_FIRST_USER_PARM (t);
- tree types =
+ tree types =
TYPE_P (t) ? TYPE_ARG_TYPES (t) : FUNCTION_FIRST_USER_PARMTYPE (t);
const bool abstract = args == NULL
|| pp_c_base (pp)->flags & pp_c_flag_abstract;
}
pp_cxx_abstract_declarator (pp, TREE_TYPE (t));
break;
-
+
case FUNCTION_DECL:
pp_cxx_space_for_pointer_operator (pp, TREE_TYPE (TREE_TYPE (t)));
pp_cxx_id_expression (pp, t);
pp_cxx_parameter_declaration_clause (pp, t);
-
+
if (DECL_NONSTATIC_MEMBER_FUNCTION_P (t))
{
pp_base (pp)->padding = pp_before;
default:
pp_c_direct_abstract_declarator (pp_c_base (pp), t);
- break;
+ break;
}
}
handler handler-seq(opt)
handler:
- catch ( exception-declaration ) compound-statement
+ catch ( exception-declaration ) compound-statement
exception-declaration:
type-specifier-seq declarator
if (code == TEMPLATE_TYPE_PARM || code == TEMPLATE_TEMPLATE_PARM
|| code == BOUND_TEMPLATE_TEMPLATE_PARM)
parm = TEMPLATE_TYPE_PARM_INDEX (parm);
-
+
pp_cxx_begin_template_argument_list (pp);
pp_cxx_identifier (pp, "template-parameter-");
pp_wide_integer (pp, TEMPLATE_PARM_LEVEL (parm));
case 1:
pp_cxx_template_declaration (pp, t);
break;
-
+
case 2:
pp_cxx_explicit_specialization (pp, t);
break;
case TYPE_DECL:
pp_cxx_simple_declaration (pp, t);
break;
-
+
case FUNCTION_DECL:
if (DECL_SAVED_TREE (t))
pp_cxx_function_definition (pp, t);
{
/* Ask for an qualified-id. */
pp_cxx_flag_default_argument = 1 << pp_c_flag_last_bit
-
+
} cxx_pretty_printer_flags;
typedef struct
else
{
tree name;
-
+
/* Remove the binding. */
decl = link;
if (TREE_CODE (decl) == TREE_LIST)
decl = TREE_VALUE (decl);
name = decl;
-
+
if (TREE_CODE (name) == OVERLOAD)
name = OVL_FUNCTION (name);
else if (TREE_CODE (newdecl) == NAMESPACE_DECL)
{
/* In [namespace.alias] we have:
-
+
In a declarative region, a namespace-alias-definition can be
used to redefine a namespace-alias declared in that declarative
region to refer only to the namespace to which it already
refers.
-
+
Therefore, if we encounter a second alias directive for the same
alias, we can just ignore the second directive. */
if (DECL_NAMESPACE_ALIAS (newdecl)
- && (DECL_NAMESPACE_ALIAS (newdecl)
+ && (DECL_NAMESPACE_ALIAS (newdecl)
== DECL_NAMESPACE_ALIAS (olddecl)))
return olddecl;
/* [namespace.alias]
DECL_COMDAT (newdecl) |= DECL_COMDAT (olddecl);
DECL_TEMPLATE_INSTANTIATED (newdecl)
|= DECL_TEMPLATE_INSTANTIATED (olddecl);
-
+
/* If the OLDDECL is an instantiation and/or specialization,
then the NEWDECL must be too. But, it may not yet be marked
as such if the caller has created NEWDECL, but has not yet
figured out that it is a redeclaration. */
if (!DECL_USE_TEMPLATE (newdecl))
DECL_USE_TEMPLATE (newdecl) = DECL_USE_TEMPLATE (olddecl);
-
+
/* Don't really know how much of the language-specific
values we should copy from old to new. */
DECL_IN_AGGR_P (newdecl) = DECL_IN_AGGR_P (olddecl);
COPY_DECL_ASSEMBLER_NAME (olddecl, newdecl);
/* Warn about conflicting visibility specifications. */
- if (DECL_VISIBILITY_SPECIFIED (olddecl)
+ if (DECL_VISIBILITY_SPECIFIED (olddecl)
&& DECL_VISIBILITY_SPECIFIED (newdecl)
&& DECL_VISIBILITY (newdecl) != DECL_VISIBILITY (olddecl))
{
with that from NEWDECL below. */
if (DECL_LANG_SPECIFIC (olddecl))
{
- gcc_assert (DECL_LANG_SPECIFIC (olddecl)
+ gcc_assert (DECL_LANG_SPECIFIC (olddecl)
!= DECL_LANG_SPECIFIC (newdecl));
ggc_free (DECL_LANG_SPECIFIC (olddecl));
}
/* Build a TYPENAME_TYPE. If the type is `typename T::t', CONTEXT is
the type of `T', NAME is the IDENTIFIER_NODE for `t'.
-
+
Returns the new TYPENAME_TYPE. */
static GTY ((param_is (union tree_node))) htab_t typename_htab;
typename_htab = htab_create_ggc (61, &typename_hash,
&typename_compare, NULL);
- ti.scope = FROB_CONTEXT (context);
+ ti.scope = FROB_CONTEXT (context);
ti.name = name;
ti.template_id = fullname;
ti.enum_p = tag_type == enum_type;
TYPENAME_TYPE_FULLNAME (t) = ti.template_id;
TYPENAME_IS_ENUM_P (t) = ti.enum_p;
TYPENAME_IS_CLASS_P (t) = ti.class_p;
-
+
/* Build the corresponding TYPE_DECL. */
d = build_decl (TYPE_DECL, name, t);
TYPE_NAME (TREE_TYPE (d)) = d;
/* Store it in the hash table. */
*e = t;
}
-
+
return t;
}
}
/* Resolve `CONTEXT::template NAME'. Returns a TEMPLATE_DECL if the name
- can be resolved or an UNBOUND_CLASS_TEMPLATE, unless an error occurs,
+ can be resolved or an UNBOUND_CLASS_TEMPLATE, unless an error occurs,
in which case error_mark_node is returned.
If PARM_LIST is non-NULL, also make sure that the template parameter
cp_decl_specifier_seq *declspecs,
int initialized,
tree attributes,
- tree prefix_attributes,
+ tree prefix_attributes,
tree *pushed_scope_p)
{
tree decl;
tree context;
*pushed_scope_p = NULL_TREE;
-
+
/* This should only be done once on the top most decl. */
if (have_extern_spec)
{
if (context)
{
*pushed_scope_p = push_scope (context);
-
+
/* We are only interested in class contexts, later. */
if (TREE_CODE (context) == NAMESPACE_DECL)
context = NULL_TREE;
/* Do not mark DECL as an explicit specialization if it was not
already marked as an instantiation; a declaration should
never be marked as a specialization unless we know what
- template is being specialized. */
+ template is being specialized. */
if (DECL_LANG_SPECIFIC (decl) && DECL_USE_TEMPLATE (decl))
{
SET_DECL_TEMPLATE_SPECIALIZATION (decl);
-
+
/* [temp.expl.spec] An explicit specialization of a static data
member of a template is a definition if the declaration
includes an initializer; otherwise, it is a declaration.
-
+
We check for processing_specialization so this only applies
to the new specialization syntax. */
if (!DECL_INITIAL (decl)
}
/* If there are more initializers than necessary, issue a
- diagnostic. */
+ diagnostic. */
if (*initp)
{
if (brace_enclosed_p)
&& !DECL_PRETTY_FUNCTION_P (decl)
&& !dependent_type_p (TREE_TYPE (decl)))
maybe_deduce_size_from_array_init (decl, init);
-
+
goto finish_end;
}
}
/* A reference will be modified here, as it is initialized. */
- if (! DECL_EXTERNAL (decl)
+ if (! DECL_EXTERNAL (decl)
&& TREE_READONLY (decl)
&& TREE_CODE (type) == REFERENCE_TYPE)
{
DECL_INITIALIZED_IN_CLASS_P (decl) = 0;
init = NULL_TREE;
}
-
+
/* Handle:
[dcl.init]
else if (!TREE_STATIC (decl))
initialize_local_var (decl, init);
}
-
+
/* If a variable is defined, and then a subsequent
definition with external linkage is encountered, we will
get here twice for the same variable. We want to avoid
initializer. It is not legal to redeclare a static data
member, so this issue does not arise in that case. */
if (var_definition_p && TREE_STATIC (decl))
- expand_static_init (decl, init);
- }
+ expand_static_init (decl, init);
+ }
}
/* If a CLEANUP_STMT was created to destroy a temporary bound to a
[stmt.dcl]
- If the initialization exits by throwing an exception, the
+ If the initialization exits by throwing an exception, the
initialization is not complete, so it will be tried again
the next time control enters the declaration.
(processing_template_decl
> template_class_depth (ctype))
? current_template_parms
- : NULL_TREE);
+ : NULL_TREE);
if (old_decl && TREE_CODE (old_decl) == TEMPLATE_DECL)
/* Because grokfndecl is always supposed to return a
error ("variable or field declared void");
type = integer_type_node;
}
-
+
return type;
}
error ("declaration of %qD as non-function", decl);
return error_mark_node;
}
- else if (!qualifying_scope
+ else if (!qualifying_scope
&& !(current_class_type && at_class_scope_p ()))
{
error ("declaration of %qD as non-member", decl);
return error_mark_node;
}
-
+
type = TREE_OPERAND (decl, 0);
name = IDENTIFIER_POINTER (constructor_name (type));
}
error ("qualifiers are not allowed on declaration of %<operator %T%>",
ctor_return_type);
- if (TREE_CODE (type) == FUNCTION_TYPE
+ if (TREE_CODE (type) == FUNCTION_TYPE
&& type_quals != TYPE_UNQUALIFIED)
{
/* This was an error in C++98 (cv-qualifiers cannot be added to
|| (quals && TREE_CODE (type) == METHOD_TYPE)))
{
tree dummy;
-
+
/* If the type is a FUNCTION_TYPE, pick up the
qualifiers from that function type. No other
qualifiers may be supplied. */
if (!current_function_decl)
DECL_CONTEXT (decl) = FROB_CONTEXT (current_namespace);
else if (DECL_MAYBE_IN_CHARGE_CONSTRUCTOR_P (current_function_decl)
- || (DECL_MAYBE_IN_CHARGE_DESTRUCTOR_P
+ || (DECL_MAYBE_IN_CHARGE_DESTRUCTOR_P
(current_function_decl)))
/* The TYPE_DECL is "abstract" because there will be
clones of this constructor/destructor, and there will
if (decl_context != TYPENAME)
{
/* A cv-qualifier-seq shall only be part of the function type
- for a non-static member function. [8.3.5/4 dcl.fct] */
+ for a non-static member function. [8.3.5/4 dcl.fct] */
if (cp_type_quals (type) != TYPE_UNQUALIFIED
&& (current_class_type == NULL_TREE || staticp) )
{
(staticp? "static member" : "free"));
type = TYPE_MAIN_VARIANT (type);
}
-
+
/* The qualifiers on the function type become the qualifiers on
the non-static member function. */
quals |= cp_type_quals (type);
/* Check that the name used for a destructor makes sense. */
if (sfk == sfk_destructor
- && !same_type_p (TREE_OPERAND
+ && !same_type_p (TREE_OPERAND
(id_declarator->u.id.unqualified_name, 0),
ctype))
{
- error ("declaration of %qD as member of %qT",
+ error ("declaration of %qD as member of %qT",
id_declarator->u.id.unqualified_name,
ctype);
return error_mark_node;
unqualified_id,
virtualp, flags, quals, raises,
friendp ? -1 : 0, friendp, 1, 0, sfk,
- funcdef_flag, template_count, in_namespace,
- attrlist);
+ funcdef_flag, template_count, in_namespace,
+ attrlist);
if (decl == NULL_TREE)
return NULL_TREE;
}
gcc_assert (DECL_FUNCTION_MEMBER_P (d));
- if (DECL_TEMPLATE_INFO (d)
+ if (DECL_TEMPLATE_INFO (d)
&& DECL_MEMBER_TEMPLATE_P (DECL_TI_TEMPLATE (d)))
/* Instantiations of template member functions are never copy
functions. Note that member functions of templated classes are
return;
/* Warn about conversion operators that will never be used. */
- if (IDENTIFIER_TYPENAME_P (name)
+ if (IDENTIFIER_TYPENAME_P (name)
&& ! DECL_TEMPLATE_INFO (decl)
&& warn_conversion
/* Warn only declaring the function; there is no need to
CLASSTYPE_REPEATED_BASE_P (ref)
|= CLASSTYPE_REPEATED_BASE_P (basetype);
}
-
+
/* We must do this test after we've seen through a typedef
type. */
if (TYPE_MARKED_P (basetype))
/* Do not clobber shared ints. */
value = copy_node (value);
-
+
TREE_TYPE (value) = enumtype;
DECL_INITIAL (decl) = value;
TREE_VALUE (values) = value;
DECL_NOT_REALLY_EXTERN (decl1) = 0;
DECL_INTERFACE_KNOWN (decl1) = 1;
/* If this function is in an interface implemented in this file,
- make sure that the backend knows to emit this function
+ make sure that the backend knows to emit this function
here. */
if (!DECL_EXTERNAL (decl1))
mark_needed (decl1);
};
/* We need this in here to get the decl_context definition. */
-extern tree grokdeclarator (const cp_declarator *,
- const cp_decl_specifier_seq *,
+extern tree grokdeclarator (const cp_declarator *,
+ const cp_decl_specifier_seq *,
enum decl_context, int, tree*);
QUALS are the qualifiers for the this pointer. */
void
-grokclassfn (tree ctype, tree function, enum overload_flags flags,
+grokclassfn (tree ctype, tree function, enum overload_flags flags,
cp_cv_quals quals)
{
tree fn_name = DECL_NAME (function);
else
p2 = build_expr_type_conversion (WANT_POINTER, index_exp, false);
- i1 = build_expr_type_conversion (WANT_INT | WANT_ENUM, array_expr,
+ i1 = build_expr_type_conversion (WANT_INT | WANT_ENUM, array_expr,
false);
- i2 = build_expr_type_conversion (WANT_INT | WANT_ENUM, index_exp,
+ i2 = build_expr_type_conversion (WANT_INT | WANT_ENUM, index_exp,
false);
if ((p1 && i2) && (i1 && p2))
return build1 (NOP_EXPR, void_type_node, t);
if (doing_vec)
- return build_vec_delete (t, /*maxindex=*/NULL_TREE,
+ return build_vec_delete (t, /*maxindex=*/NULL_TREE,
sfk_deleting_destructor,
use_global_delete);
else
{
if (current_function_decl)
/* 14.5.2.2 [temp.mem]
-
+
A local class shall not have member templates. */
error ("invalid declaration of member template %q#D in local class",
decl);
-
+
if (TREE_CODE (decl) == FUNCTION_DECL && DECL_VIRTUAL_P (decl))
{
/* 14.5.2.3 [temp.mem]
A member function template shall not be virtual. */
- error
+ error
("invalid use of %<virtual%> in template declaration of %q#D",
decl);
DECL_VIRTUAL_P (decl) = 0;
}
/* The debug-information generating code doesn't know what to do
- with member templates. */
+ with member templates. */
DECL_IGNORED_P (tmpl) = 1;
- }
+ }
else
error ("template declaration of %q#D", decl);
}
arg_types = TREE_CHAIN (arg_types);
if (DECL_HAS_VTT_PARM_P (method))
arg_types = TREE_CHAIN (arg_types);
-
+
for (; arg_types != NULL_TREE; arg_types = TREE_CHAIN (arg_types))
{
tree type = TREE_VALUE (arg_types);
/* Sanity check: report error if this function FUNCTION is not
really a member of the class (CTYPE) it is supposed to belong to.
TEMPLATE_PARMS is used to specify the template parameters of a member
- template passed as FUNCTION_DECL. If the member template is passed as a
+ template passed as FUNCTION_DECL. If the member template is passed as a
TEMPLATE_DECL, it can be NULL since the parameters can be extracted
from the declaration. If the function is not a function template, it
must be NULL.
{
int ix;
bool is_template;
-
+
if (DECL_USE_TEMPLATE (function)
&& !(TREE_CODE (function) == TEMPLATE_DECL
&& DECL_TEMPLATE_SPECIALIZATION (function))
/* Since this is a specialization of a member template,
we're not going to find the declaration in the class.
For example, in:
-
+
struct S { template <typename T> void f(T); };
template <> void S::f(int);
-
+
we're not going to find `S::f(int)', but there's no
reason we should, either. We let our callers know we didn't
find the method, but we don't complain. */
either were not passed, or they are the same of DECL_TEMPLATE_PARMS. */
if (TREE_CODE (function) == TEMPLATE_DECL)
{
- gcc_assert (!template_parms
- || comp_template_parms (template_parms,
+ gcc_assert (!template_parms
+ || comp_template_parms (template_parms,
DECL_TEMPLATE_PARMS (function)));
template_parms = DECL_TEMPLATE_PARMS (function);
}
bool is_conv_op;
tree pushed_scope;
const char *format = NULL;
-
+
pushed_scope = push_scope (ctype);
for (fndecls = VEC_index (tree, methods, ix);
fndecls; fndecls = OVL_NEXT (fndecls))
{
tree p1, p2;
-
+
fndecl = OVL_CURRENT (fndecls);
p1 = TYPE_ARG_TYPES (TREE_TYPE (function));
p2 = TYPE_ARG_TYPES (TREE_TYPE (fndecl));
/* We cannot simply call decls_match because this doesn't
work for static member functions that are pretending to
be methods, and because the name may have been changed by
- asm("new_name"). */
-
+ asm("new_name"). */
+
/* Get rid of the this parameter on functions that become
static. */
if (DECL_STATIC_FUNCTION_P (fndecl)
declaration. */
if (is_template != (TREE_CODE (fndecl) == TEMPLATE_DECL))
continue;
-
+
if (same_type_p (TREE_TYPE (TREE_TYPE (function)),
TREE_TYPE (TREE_TYPE (fndecl)))
&& compparms (p1, p2)
&& (!is_template
- || comp_template_parms (template_parms,
+ || comp_template_parms (template_parms,
DECL_TEMPLATE_PARMS (fndecl)))
&& (DECL_TEMPLATE_SPECIALIZATION (function)
== DECL_TEMPLATE_SPECIALIZATION (fndecl))
&& (!DECL_TEMPLATE_SPECIALIZATION (function)
- || (DECL_TI_TEMPLATE (function)
+ || (DECL_TI_TEMPLATE (function)
== DECL_TI_TEMPLATE (fndecl))))
break;
}
if (init != NULL_TREE && TYPE_NEEDS_CONSTRUCTING (TREE_TYPE (decl)))
{
static int explained = 0;
-
+
error ("initializer invalid for static member with constructor");
if (!explained)
{
CHANGES TO CODE IN `start_method'. */
tree
-grokfield (const cp_declarator *declarator,
- cp_decl_specifier_seq *declspecs,
+grokfield (const cp_declarator *declarator,
+ cp_decl_specifier_seq *declspecs,
tree init, tree asmspec_tree,
tree attrlist)
{
if (!declspecs->any_specifiers_p
&& declarator->kind == cdk_id
- && declarator->u.id.qualifying_scope
+ && declarator->u.id.qualifying_scope
&& TREE_CODE (declarator->u.id.unqualified_name) == IDENTIFIER_NODE)
/* Access declaration */
return do_class_using_decl (declarator->u.id.qualifying_scope,
init = digest_init (TREE_TYPE (value), init, (tree *)0);
else
init = integral_constant_value (init);
-
+
if (init != error_mark_node && ! TREE_CONSTANT (init))
{
/* We can allow references to things that are effectively
switch (TREE_CODE (value))
{
case VAR_DECL:
- finish_static_data_member_decl (value, init, asmspec_tree,
+ finish_static_data_member_decl (value, init, asmspec_tree,
flags);
return value;
set_user_assembler_name (value, asmspec);
if (!DECL_FRIEND_P (value))
grok_special_member_properties (value);
-
+
cp_finish_decl (value, init, asmspec_tree, flags);
/* Pass friends back this way. */
DECL_IN_AGGR_P (value) = 1;
return value;
-
+
default:
gcc_unreachable ();
}
WIDTH is non-NULL for bit fields only, and is an INTEGER_CST node. */
tree
-grokbitfield (const cp_declarator *declarator,
+grokbitfield (const cp_declarator *declarator,
cp_decl_specifier_seq *declspecs, tree width)
{
tree value = grokdeclarator (declarator, declspecs, BITFIELD, 0, NULL);
if (TREE_CODE (type) != UNION_TYPE)
error ("anonymous struct not inside named type");
- for (field = TYPE_FIELDS (type);
- field != NULL_TREE;
+ for (field = TYPE_FIELDS (type);
+ field != NULL_TREE;
field = TREE_CHAIN (field))
{
tree decl;
if (DECL_NAME (field))
{
decl = build_decl (ALIAS_DECL, DECL_NAME (field), TREE_TYPE (field));
- DECL_INITIAL (decl) = ref;
+ DECL_INITIAL (decl) = ref;
TREE_PUBLIC (decl) = 0;
TREE_STATIC (decl) = 0;
DECL_EXTERNAL (decl) = 1;
/* The VAR_DECL's context is the same as the TYPE's context. */
DECL_CONTEXT (anon_union_decl) = DECL_CONTEXT (TYPE_NAME (type));
-
+
if (TYPE_FIELDS (type) == NULL_TREE)
return;
tree args = TYPE_ARG_TYPES (type);
gcc_assert (TREE_CODE (type) == FUNCTION_TYPE);
-
+
if (!same_type_p (TREE_TYPE (type), ptr_type_node))
{
e = 1;
{
int e = 0;
tree args = TYPE_ARG_TYPES (type);
-
+
gcc_assert (TREE_CODE (type) == FUNCTION_TYPE);
if (!same_type_p (TREE_TYPE (type), void_type_node))
we output the vtables that contain them. With vcall offsets,
we know all the thunks we'll need when we emit a virtual
function, so we emit the thunks there instead. */
- if (DECL_THUNK_P (fn))
+ if (DECL_THUNK_P (fn))
use_thunk (fn, /*emit_p=*/0);
mark_used (fn);
}
{
if (flag_weak)
make_decl_one_only (decl);
- else if (TREE_CODE (decl) == FUNCTION_DECL
+ else if (TREE_CODE (decl) == FUNCTION_DECL
|| (TREE_CODE (decl) == VAR_DECL && DECL_ARTIFICIAL (decl)))
/* We can just emit function and compiler-generated variables
statically; having multiple copies is (for the most part) only
- a waste of space.
+ a waste of space.
There are two correctness issues, however: the address of a
template instantiation with external linkage should be the
same, independent of what translation unit asks for the
address, and this will not hold when we emit multiple copies of
- the function. However, there's little else we can do.
+ the function. However, there's little else we can do.
Also, by default, the typeinfo implementation assumes that
there will be only one copy of the string used as the name for
/* For win32 we also want to put explicit instantiations in
linkonce sections, so that they will be merged with implicit
- instantiations; otherwise we get duplicate symbol errors.
- For Darwin we do not want explicit instantiations to be
+ instantiations; otherwise we get duplicate symbol errors.
+ For Darwin we do not want explicit instantiations to be
linkonce. */
void
return true;
/* If this entity was used, let the back-end see it; it will decide
whether or not to emit it into the object file. */
- if (TREE_USED (decl)
+ if (TREE_USED (decl)
|| (DECL_ASSEMBLER_NAME_SET_P (decl)
&& TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (decl))))
return true;
/* If the references to this class' vtables are optimized away,
still emit the appropriate debugging information. See
dfs_debug_mark. */
- if (DECL_COMDAT (primary_vtbl)
+ if (DECL_COMDAT (primary_vtbl)
&& CLASSTYPE_DEBUG_REQUESTED (ctype))
note_debug_info_needed (ctype);
return false;
if (TREE_TYPE (DECL_INITIAL (vtbl)) == 0)
{
tree expr = store_init_value (vtbl, DECL_INITIAL (vtbl));
-
+
/* It had better be all done at compile-time. */
gcc_assert (!expr);
}
else if (CLASSTYPE_INTERFACE_KNOWN (class_type))
{
/* CLASS_TYPE is being exported from this translation unit,
- so DECL should be defined here. */
+ so DECL should be defined here. */
if (!flag_weak && CLASSTYPE_EXPLICIT_INSTANTIATION (class_type))
/* If a class is declared in a header with the "extern
template" extension, then it will not be instantiated,
wherever it is used. */
&& flag_rtti)
import_p = true;
- else
+ else
{
if (CLASSTYPE_INTERFACE_KNOWN (type)
&& !CLASSTYPE_INTERFACE_ONLY (type))
data member. */
if (flag_implicit_templates
|| (flag_implicit_inline_templates
- && TREE_CODE (decl) == FUNCTION_DECL
+ && TREE_CODE (decl) == FUNCTION_DECL
&& DECL_DECLARED_INLINE_P (decl)))
comdat_p = true;
else
{
DECL_NOT_REALLY_EXTERN (decl)
= ! (CLASSTYPE_INTERFACE_ONLY (ctype)
- || (DECL_DECLARED_INLINE_P (decl)
+ || (DECL_DECLARED_INLINE_P (decl)
&& ! flag_implement_inlines
&& !DECL_VINDEX (decl)));
&& DECL_VISIBILITY_SPECIFIED (decl)
&& (!class_type || !CLASSTYPE_VISIBILITY_SPECIFIED (class_type)))
targetm.cxx.determine_class_data_visibility (decl);
-
+
DECL_INTERFACE_KNOWN (decl) = 1;
}
as an integer counter. */
guard_type = targetm.cxx.guard_type ();
guard = build_decl (VAR_DECL, sname, guard_type);
-
+
/* The guard should have the same linkage as what it guards. */
TREE_PUBLIC (guard) = TREE_PUBLIC (decl);
TREE_STATIC (guard) = TREE_STATIC (decl);
DECL_ONE_ONLY (guard) = DECL_ONE_ONLY (decl);
if (TREE_PUBLIC (decl))
DECL_WEAK (guard) = DECL_WEAK (decl);
-
+
DECL_ARTIFICIAL (guard) = 1;
DECL_IGNORED_P (guard) = 1;
TREE_USED (guard) = 1;
{
/* We only set the first byte of the guard, in order to leave room
for a mutex in the high-order bits. */
- guard = build1 (ADDR_EXPR,
+ guard = build1 (ADDR_EXPR,
build_pointer_type (TREE_TYPE (guard)),
guard);
- guard = build1 (NOP_EXPR,
- build_pointer_type (char_type_node),
+ guard = build1 (NOP_EXPR,
+ build_pointer_type (char_type_node),
guard);
guard = build1 (INDIRECT_REF, char_type_node, guard);
}
else
sprintf (type, "%c", method_type);
- fndecl = build_lang_decl (FUNCTION_DECL,
+ fndecl = build_lang_decl (FUNCTION_DECL,
get_file_function_name_long (type),
build_function_type (void_type_node,
void_list_node));
nonzero, it performs initializations. Otherwise, it performs
destructions. It only performs those initializations or
destructions with the indicated __PRIORITY. The generated function
- returns no value.
+ returns no value.
It is assumed that this function will only be called once per
translation unit. */
type = build_function_type (void_type_node, parm_types);
/* Create the FUNCTION_DECL itself. */
- ssdf_decl = build_lang_decl (FUNCTION_DECL,
+ ssdf_decl = build_lang_decl (FUNCTION_DECL,
get_identifier (id),
type);
TREE_PUBLIC (ssdf_decl) = 0;
function as:
static void __ssdf (int __initialize_p, init __priority_p);
-
+
It is static because we only need to call this function from the
various constructor and destructor functions for this module. */
start_preparsed_function (ssdf_decl,
priority_info pi;
splay_tree_node n;
- n = splay_tree_lookup (priority_info_map,
+ n = splay_tree_lookup (priority_info_map,
(splay_tree_key) priority);
if (!n)
{
the conversion functions, or the destructor called to
create and destroy a static data member is performed as
if these calls appeared in the scope of the member's
- class.
+ class.
we pretend we are in a static member function of the class of
which the DECL is a member. */
DECL_CONTEXT (current_function_decl) = DECL_CONTEXT (decl);
DECL_STATIC_FUNCTION_P (current_function_decl) = 1;
}
-
+
/* Conditionalize this initialization on being in the right priority
and being initializing/finalizing appropriately. */
guard_if_stmt = begin_if_stmt ();
might be initialized in more than one place. (For example, a
static data member of a template, when the data member requires
construction.) */
- if (TREE_PUBLIC (decl) && (DECL_COMMON (decl)
+ if (TREE_PUBLIC (decl) && (DECL_COMMON (decl)
|| DECL_ONE_ONLY (decl)
|| DECL_WEAK (decl)))
{
destructions only if the GUARD is one, i.e., if we are the
last to destroy the variable. */
else if (initp)
- guard_cond
+ guard_cond
= cp_build_binary_op (EQ_EXPR,
build_unary_op (PREINCREMENT_EXPR,
guard,
/*noconvert=*/1),
integer_one_node);
else
- guard_cond
+ guard_cond
= cp_build_binary_op (EQ_EXPR,
build_unary_op (PREDECREMENT_EXPR,
guard,
/* Also, if the initializer already contains errors, we can bail
out now. */
- if (init && TREE_CODE (init) == TREE_LIST
+ if (init && TREE_CODE (init) == TREE_LIST
&& value_member (error_mark_node, init))
{
var = &TREE_CHAIN (t);
#else
locus->line++;
#endif
-
+
/* We use `I' to indicate initialization and `D' to indicate
destruction. */
function_key = constructor_p ? 'I' : 'D';
/* Call the static storage duration function with appropriate
arguments. */
- for (i = 0; VEC_iterate (tree, ssdf_decls, i, fndecl); ++i)
+ for (i = 0; VEC_iterate (tree, ssdf_decls, i, fndecl); ++i)
{
/* Calls to pure or const functions will expand to nothing. */
if (! (flags_from_decl_or_type (fndecl) & (ECF_CONST | ECF_PURE)))
body = start_objects (function_key, priority);
arguments = tree_cons (NULL_TREE,
- build_int_cst (NULL_TREE, priority),
+ build_int_cst (NULL_TREE, priority),
NULL_TREE);
arguments = tree_cons (NULL_TREE,
build_int_cst (NULL_TREE, constructor_p),
{
tree fns;
- for (fns = constructor_p ? static_ctors : static_dtors;
+ for (fns = constructor_p ? static_ctors : static_dtors;
fns;
fns = TREE_CHAIN (fns))
{
vtbl = TREE_CHAIN (vtbl))
mark_decl_referenced (vtbl);
}
- else if (DECL_CONTEXT (t)
+ else if (DECL_CONTEXT (t)
&& TREE_CODE (DECL_CONTEXT (t)) == FUNCTION_DECL)
/* If we need a static variable in a function, then we
need the containing function. */
static storage duration. (Local objects with static storage
duration are initialized when their scope is first entered,
and are cleaned up via atexit.)
- o Virtual function tables.
+ o Virtual function tables.
All of these may cause others to be needed. For example,
instantiating one function may cause another to be needed, and
emit_support_tinfos ();
- do
+ do
{
tree t;
tree decl;
reconsider = true;
keyed_classes = TREE_CHAIN (keyed_classes);
}
-
+
t = keyed_classes;
if (t != NULL_TREE)
{
tree next = TREE_CHAIN (t);
-
+
while (next)
{
if (maybe_emit_vtables (TREE_VALUE (next)))
}
else
t = next;
-
+
next = TREE_CHAIN (t);
}
}
locus.line++;
#endif
}
-
+
/* Go through the set of inline functions whose bodies have not
been emitted yet. If out-of-line copies of these functions
are required, emit them. */
reconsider = true;
/* Static data members are just like namespace-scope globals. */
- for (i = 0; VEC_iterate (tree, pending_statics, i, decl); ++i)
+ for (i = 0; VEC_iterate (tree, pending_statics, i, decl); ++i)
{
if (var_finalized_p (decl) || DECL_REALLY_EXTERN (decl))
continue;
reconsider = true;
retries++;
- }
+ }
while (reconsider);
/* All used inline functions must have a definition at this point. */
TREE_PUBLIC (decl) = 1;
}
}
-
+
/* We give C linkage to static constructors and destructors. */
push_lang_context (lang_name_c);
/* Generate initialization and destruction functions for all
priorities for which they are required. */
if (priority_info_map)
- splay_tree_foreach (priority_info_map,
+ splay_tree_foreach (priority_info_map,
generate_ctor_and_dtor_functions_for_priority,
/*data=*/&locus);
else
{
-
+
if (static_ctors)
generate_ctor_or_dtor_function (/*constructor_p=*/true,
DEFAULT_INIT_PRIORITY, &locus);
dump_end (TDI_tu, stream);
}
}
-
+
timevar_pop (TV_VARCONST);
if (flag_detailed_statistics)
return build_min_non_dep (CALL_EXPR, expr, orig_fn, orig_args, NULL_TREE);
return expr;
}
-
+
void
check_default_args (tree x)
{
if (DECL_DEFERRED_FN (decl))
return;
-
+
/* Remember the current location for a function we will end up
synthesizing. Then we can inform the user where it was
required in the case of error. */
if (DECL_ARTIFICIAL (decl) && DECL_NONSTATIC_MEMBER_FUNCTION_P (decl)
&& !DECL_THUNK_P (decl))
DECL_SOURCE_LOCATION (decl) = input_location;
-
+
note_vague_linkage_fn (decl);
}
-
+
assemble_external (decl);
/* Is it a synthesized method that needs to be synthesized? */
if (TREE_CODE (decl) == FUNCTION_DECL
&& DECL_NONSTATIC_MEMBER_FUNCTION_P (decl)
- && DECL_ARTIFICIAL (decl)
+ && DECL_ARTIFICIAL (decl)
&& !DECL_THUNK_P (decl)
&& ! DECL_INITIAL (decl)
/* Kludge: don't synthesize for default args. Unfortunately this
if ((DECL_NON_THUNK_FUNCTION_P (decl) || TREE_CODE (decl) == VAR_DECL)
&& DECL_LANG_SPECIFIC (decl) && DECL_TEMPLATE_INFO (decl)
&& (!DECL_EXPLICIT_INSTANTIATION (decl)
- || (TREE_CODE (decl) == FUNCTION_DECL
- && DECL_INLINE (DECL_TEMPLATE_RESULT
+ || (TREE_CODE (decl) == FUNCTION_DECL
+ && DECL_INLINE (DECL_TEMPLATE_RESULT
(template_for_substitution (decl))))))
/* We put off instantiating functions in order to improve compile
times. Maintaining a stack of active functions is expensive,
dump_string (di, "subs");
break;
case POSTINCREMENT_EXPR:
- dump_string (di, "postinc");
+ dump_string (di, "postinc");
break;
case POSTDECREMENT_EXPR:
dump_string (di, "postdec");
dump_child ("bfld", TYPE_CONTEXT (t));
return true;
}
-
+
if (! IS_AGGR_TYPE (t))
break;
int i;
tree binfo;
tree base_binfo;
-
+
for (binfo = TYPE_BINFO (t), i = 0;
BINFO_BASE_ITERATE (binfo, i, base_binfo); ++i)
{
dump_child ("base", BINFO_TYPE (base_binfo));
- if (BINFO_VIRTUAL_P (base_binfo))
+ if (BINFO_VIRTUAL_P (base_binfo))
dump_string (di, "virtual");
dump_access (di, base_binfo);
}
dump_access (di, t);
if (TREE_STATIC (t) && !TREE_PUBLIC (t))
dump_string (di, "static");
- break;
+ break;
case FUNCTION_DECL:
if (!DECL_THUNK_P (t))
dump_string (di, "operator");
dump_op (di, t);
}
- if (DECL_FUNCTION_MEMBER_P (t))
+ if (DECL_FUNCTION_MEMBER_P (t))
{
dump_string (di, "member");
dump_access (di, t);
else
{
tree virt = THUNK_VIRTUAL_OFFSET (t);
-
+
dump_string (di, "thunk");
if (DECL_THIS_THUNK_P (t))
dump_string (di, "this adjusting");
dump_child ("args", TREE_OPERAND (t, 1));
dump_child ("decl", TREE_OPERAND (t, 2));
break;
-
+
case HANDLER:
dump_stmt (di, t);
dump_child ("parm", HANDLER_PARMS (t));
}
case TYPENAME_TYPE:
pp_cxx_cv_qualifier_seq (cxx_pp, t);
- pp_cxx_identifier (cxx_pp,
- TYPENAME_IS_ENUM_P (t) ? "enum"
+ pp_cxx_identifier (cxx_pp,
+ TYPENAME_IS_ENUM_P (t) ? "enum"
: TYPENAME_IS_CLASS_P (t) ? "class"
: "typename");
dump_typename (t, flags);
Arrays must also do this for DECL nodes, like int a[], and for things like
int *[]&. */
-static void
+static void
dump_type_prefix (tree t, int flags)
{
if (TYPE_PTRMEMFUNC_P (t))
&& TREE_CODE (TREE_TYPE (t)) == TEMPLATE_TYPE_PARM)
/* Say `class T' not just `T'. */
pp_cxx_identifier (cxx_pp, "class");
-
+
dump_type (TREE_TYPE (t), flags);
break;
}
dump_decl (DECL_NAME (t), flags);
break;
}
-
+
/* If there's only one function, just treat it like an ordinary
FUNCTION_DECL. */
t = OVL_CURRENT (t);
case TEMPLATE_ID_EXPR:
{
tree name = TREE_OPERAND (t, 0);
-
+
if (is_overloaded_fn (name))
name = DECL_NAME (get_first_fn (name));
dump_decl (name, flags);
if (TMPL_ARGS_HAVE_MULTIPLE_LEVELS (args))
args = TREE_VEC_ELT (args, TREE_VEC_LENGTH (args) - 1);
-
+
len = TREE_VEC_LENGTH (args);
for (ix = 0; ix != len; ix++)
if (ix)
pp_separate_with_comma (cxx_pp);
-
+
if (!arg)
pp_identifier (cxx_pp, "<template parameter error>");
else
{
if (t == 0)
return;
-
+
switch (TREE_CODE (t))
{
case VAR_DECL:
if (PAREN_STRING_LITERAL_P (t))
pp_cxx_right_paren (cxx_pp);
break;
-
+
case INTEGER_CST:
case REAL_CST:
pp_c_constant (pp_c_base (cxx_pp), t);
case CONVERT_EXPR:
{
tree op = TREE_OPERAND (t, 0);
-
+
if (!same_type_p (TREE_TYPE (op), TREE_TYPE (t)))
{
/* It is a cast, but we cannot tell whether it is a
dump_expr (op, flags);
break;
}
-
+
case CONSTRUCTOR:
if (TREE_TYPE (t) && TYPE_PTRMEMFUNC_P (TREE_TYPE (t)))
{
dump_expr_list (CONSTRUCTOR_ELTS (t), flags);
pp_cxx_right_brace (cxx_pp);
}
-
+
break;
case OFFSET_REF:
/* A::f */
dump_expr (t, flags | TFF_EXPR_IN_PARENS);
else if (BASELINK_P (t))
- dump_expr (OVL_CURRENT (BASELINK_FUNCTIONS (t)),
+ dump_expr (OVL_CURRENT (BASELINK_FUNCTIONS (t)),
flags | TFF_EXPR_IN_PARENS);
else
dump_decl (t, flags);
t = TYPE_MAIN_DECL (t);
else if (TREE_CODE (t) == OVERLOAD)
t = OVL_FUNCTION (t);
-
+
return DECL_SOURCE_LOCATION (t);
}
{
tree p = current_instantiation ();
location_t location = input_location;
-
+
if (p)
{
if (current_function_decl != TINST_DECL (p)
case 'Q': result = assop_to_string (next_tcode); break;
case 'T': result = type_to_string (next_tree, verbose); break;
case 'V': result = cv_to_string (next_tree, verbose); break;
-
+
default:
return false;
}
When the destruction of an object during stack unwinding exits
using an exception ... void terminate(); is called. */
return build_call (terminate_node, NULL_TREE);
-}
+}
static tree
prepare_eh_type (tree type)
/* Initialize the catch parameter DECL. */
-static void
+static void
initialize_handler_parm (tree decl, tree exp)
{
tree init;
TREE_USED (decl) = 1;
/* Figure out the type that the initializer is. Pointers are returned
- adjusted by value from __cxa_begin_catch. Others are returned by
+ adjusted by value from __cxa_begin_catch. Others are returned by
reference. */
init_type = TREE_TYPE (decl);
if (!POINTER_TYPE_P (init_type))
tree tmp = tree_cons (NULL_TREE, size_type_node, void_list_node);
fn = push_library_fn (fn, build_function_type (ptr_type_node, tmp));
}
-
+
return build_function_call (fn, tree_cons (NULL_TREE, size_in_bytes (type),
NULL_TREE));
}
if (exp == null_node)
warning (0, "throwing NULL, which has integral, not pointer type");
-
+
if (exp != NULL_TREE)
{
if (!is_admissible_throw_operand (exp))
tmp = build_function_type (void_type_node, tmp);
cleanup_type = build_pointer_type (tmp);
}
-
+
fn = get_identifier ("__cxa_throw");
if (!get_global_value_if_present (fn, &fn))
{
tmp = build_function_type (void_type_node, tmp);
fn = push_throw_library_fn (fn, tmp);
}
-
+
/* throw expression */
/* First, decay it. */
exp = decay_conversion (exp);
}
else
cleanup = build_int_cst (cleanup_type, 0);
-
+
tmp = tree_cons (NULL_TREE, cleanup, NULL_TREE);
tmp = tree_cons (NULL_TREE, throw_type, tmp);
tmp = tree_cons (NULL_TREE, ptr, tmp);
}
/* ??? Indicate that this function call allows exceptions of the type
- of the enclosing catch block (if known). */
+ of the enclosing catch block (if known). */
exp = build_function_call (fn, NULL_TREE);
}
complete_ptr_ref_or_void_ptr_p (tree type, tree from)
{
int is_ptr;
-
+
/* Check complete. */
type = complete_type_or_else (type, from);
if (!type)
return 0;
-
+
/* Or a pointer or ref to one, or cv void *. */
is_ptr = TREE_CODE (type) == POINTER_TYPE;
if (is_ptr || TREE_CODE (type) == REFERENCE_TYPE)
{
tree core = TREE_TYPE (type);
-
+
if (is_ptr && VOID_TYPE_P (core))
/* OK */;
else if (!complete_type_or_else (core, from))
{
tree type = TREE_TYPE (cst);
tree member;
-
+
/* Find the member. */
member = PTRMEM_CST_MEMBER (cst);
- if (TREE_CODE (member) == FIELD_DECL)
+ if (TREE_CODE (member) == FIELD_DECL)
{
/* Find the offset for the field. */
cst = byte_position (member);
context = TYPE_CONTEXT (context))
if (type == context)
return 1;
-
+
list = CLASSTYPE_FRIEND_CLASSES (TREE_TYPE (TYPE_MAIN_DECL (type)));
for (; list ; list = TREE_CHAIN (list))
{
tree t = TREE_VALUE (list);
- if (TREE_CODE (t) == TEMPLATE_DECL ?
+ if (TREE_CODE (t) == TEMPLATE_DECL ?
is_specialization_of_friend (TYPE_MAIN_DECL (supplicant), t) :
same_type_p (supplicant, t))
return 1;
}
- }
+ }
if (declp && DECL_FUNCTION_MEMBER_P (supplicant))
context = DECL_CONTEXT (supplicant);
= tree_cons (DECL_NAME (decl), build_tree_list (NULL_TREE, decl),
DECL_FRIENDLIST (typedecl));
if (!uses_template_parms (type))
- DECL_BEFRIENDING_CLASSES (decl)
+ DECL_BEFRIENDING_CLASSES (decl)
= tree_cons (NULL_TREE, type,
DECL_BEFRIENDING_CLASSES (decl));
}
}
}
}
-
- if (!classes)
+
+ if (!classes)
{
maybe_add_class_template_decl_list (type, friend_type, /*friend_p=*/1);
friend_type = TREE_TYPE (friend_type);
if (!uses_template_parms (type))
CLASSTYPE_BEFRIENDING_CLASSES (friend_type)
- = tree_cons (NULL_TREE, type,
- CLASSTYPE_BEFRIENDING_CLASSES (friend_type));
+ = tree_cons (NULL_TREE, type,
+ CLASSTYPE_BEFRIENDING_CLASSES (friend_type));
}
}
-/* Main friend processor.
+/* Main friend processor.
CTYPE is the class this friend belongs to.
tree
do_friend (tree ctype, tree declarator, tree decl,
- tree attrlist, enum overload_flags flags,
+ tree attrlist, enum overload_flags flags,
cp_cv_quals quals,
int funcdef_flag)
{
validity of the declaration later. */
decl = push_template_decl_real (decl, /*is_friend=*/1);
else
- decl = check_classfn (ctype, decl,
- template_member_p
+ decl = check_classfn (ctype, decl,
+ template_member_p
? current_template_parms
: NULL_TREE);
general, such a declaration depends on template
parameters. Instead, we call pushdecl when the class
is instantiated. */
- decl = push_template_decl_real (decl, /*is_friend=*/1);
+ decl = push_template_decl_real (decl, /*is_friend=*/1);
else if (current_function_decl)
/* This must be a local class, so pushdecl will be ok, and
insert an unqualified friend into the local scope
unqualified friend decl into the template parameter
scope, rather than the namespace containing it. */
tree ns = decl_namespace_context (decl);
-
+
push_nested_namespace (ns);
decl = pushdecl_namespace_level (decl);
pop_nested_namespace (ns);
if (decl == error_mark_node)
return error_mark_node;
-
- add_friend (current_class_type,
+
+ add_friend (current_class_type,
is_friend_template ? DECL_TI_TEMPLATE (decl) : decl,
/*complain=*/true);
DECL_FRIEND_P (decl) = 1;
cause a warning. */
library = -1;
}
- else if (strcmp (argv[i], "-static-libgcc") == 0
+ else if (strcmp (argv[i], "-static-libgcc") == 0
|| strcmp (argv[i], "-static") == 0)
shared_libgcc = 0;
else if (DEFAULT_WORD_SWITCH_TAKES_ARG (&argv[i][1]))
}
else
{
- int len;
+ int len;
if (saw_speclang)
{
But not if a specified -x option is currently active. */
len = strlen (argv[i]);
if (len > 2
- && (argv[i][len - 1] == 'c'
+ && (argv[i][len - 1] == 'c'
|| argv[i][len - 1] == 'i'
|| argv[i][len - 1] == 'h')
&& argv[i][len - 2] == '.')
args[i] |= LANGSPEC;
added += 2;
}
-
+
/* If we don't know that this is a header file, we might
need to be linking in the libraries. */
if (library == 0)
i = 0;
j = 0;
-
+
/* Copy the 0th argument, i.e., the name of the program itself. */
arglist[i++] = argv[j++];
/* Number of extra output files that lang_specific_pre_link may generate. */
int lang_specific_extra_outfiles = 0; /* Not used for C++. */
-/* Table of language-specific spec functions. */
+/* Table of language-specific spec functions. */
const struct spec_function lang_specific_spec_functions[] =
{
{ 0, 0 }
begin_init_stmts (tree *stmt_expr_p, tree *compound_stmt_p)
{
bool is_global = !building_stmt_tree ();
-
+
*stmt_expr_p = begin_stmt_expr ();
*compound_stmt_p = begin_compound_stmt (BCS_NO_SCOPE);
static tree
finish_init_stmts (bool is_global, tree stmt_expr, tree compound_stmt)
-{
+{
finish_compound_stmt (compound_stmt);
-
+
stmt_expr = finish_stmt_expr (stmt_expr, true);
gcc_assert (!building_stmt_tree () == is_global);
-
+
return stmt_expr;
}
{
if (!TYPE_CONTAINS_VPTR_P (BINFO_TYPE (binfo)))
return dfs_skip_bases;
-
+
if (!BINFO_PRIMARY_P (binfo) || BINFO_VIRTUAL_P (binfo))
{
tree base_ptr = TREE_VALUE ((tree) data);
over TYPE_FIELDs will result in correct initialization of
all of the subobjects. */
if (static_storage_p && !zero_init_p (TREE_TYPE (field)))
- inits = tree_cons (field,
+ inits = tree_cons (field,
build_zero_init (TREE_TYPE (field),
/*nelts=*/NULL_TREE,
static_storage_p),
/*nelts=*/NULL_TREE,
static_storage_p);
tree range;
-
+
/* If this is a one element array, we just use a regular init. */
if (tree_int_cst_equal (size_zero_node, max_index))
range = size_zero_node;
else
range = build2 (RANGE_EXPR, sizetype, size_zero_node, max_index);
-
+
inits = tree_cons (range, elt_init, inits);
}
-
+
CONSTRUCTOR_ELTS (init) = nreverse (inits);
}
else
a class with a pointer-to-data member as a non-static data member
does not have TYPE_NEEDS_CONSTRUCTING set.) Therefore, we end up
passing non-PODs to build_zero_init below, which is contrary to
- the semantics quoted above from [dcl.init].
+ the semantics quoted above from [dcl.init].
It happens, however, that the behavior of the constructor the
standard says we should have generated would be precisely the
if (TYPE_NEEDS_CONSTRUCTING (type)
|| (nelts && TREE_CODE (nelts) != INTEGER_CST))
return NULL_TREE;
-
+
/* At this point, TYPE is either a POD class type, an array of POD
classes, or something even more innocuous. */
return build_zero_init (type, nelts, /*static_storage_p=*/false);
/* Returns a TREE_LIST containing (as the TREE_PURPOSE of each node) all
the FIELD_DECLs on the TYPE_FIELDS list for T, in reverse order. */
-static tree
+static tree
build_field_list (tree t, tree list, int *uses_unions_p)
{
tree fields;
/* Skip CONST_DECLs for enumeration constants and so forth. */
if (TREE_CODE (fields) != FIELD_DECL || DECL_ARTIFICIAL (fields))
continue;
-
+
/* Keep track of whether or not any fields are unions. */
if (TREE_CODE (TREE_TYPE (fields)) == UNION_TYPE)
*uses_unions_p = 1;
initialize the entire aggregate. */
list = tree_cons (fields, NULL_TREE, list);
/* And now add the fields in the anonymous aggregate. */
- list = build_field_list (TREE_TYPE (fields), list,
+ list = build_field_list (TREE_TYPE (fields), list,
uses_unions_p);
}
/* Add this field. */
TREE_VALUE will be the constructor arguments, or NULL if no
explicit initialization was provided. */
sorted_inits = NULL_TREE;
-
+
/* Process the virtual bases. */
for (vbases = CLASSTYPE_VBASECLASSES (t), i = 0;
VEC_iterate (tree, vbases, i, base); i++)
sorted_inits = tree_cons (base, NULL_TREE, sorted_inits);
-
+
/* Process the direct bases. */
for (binfo = TYPE_BINFO (t), i = 0;
BINFO_BASE_ITERATE (binfo, i, base_binfo); ++i)
subobject = TREE_PURPOSE (init);
/* If the explicit initializers are in sorted order, then
- SUBOBJECT will be NEXT_SUBOBJECT, or something following
+ SUBOBJECT will be NEXT_SUBOBJECT, or something following
it. */
- for (subobject_init = next_subobject;
- subobject_init;
+ for (subobject_init = next_subobject;
+ subobject_init;
subobject_init = TREE_CHAIN (subobject_init))
if (TREE_PURPOSE (subobject_init) == subobject)
break;
while (TREE_PURPOSE (subobject_init) != subobject)
subobject_init = TREE_CHAIN (subobject_init);
}
-
+
/* It is invalid to initialize the same subobject more than
once. */
if (TREE_VALUE (subobject_init))
error ("%Jmultiple initializations given for %qD",
current_function_decl, subobject);
else
- error ("%Jmultiple initializations given for base %qT",
+ error ("%Jmultiple initializations given for base %qT",
current_function_decl, subobject);
}
int done;
/* Skip uninitialized members and base classes. */
- if (!TREE_VALUE (init)
+ if (!TREE_VALUE (init)
|| TREE_CODE (TREE_PURPOSE (init)) != FIELD_DECL)
continue;
/* See if this field is a member of a union, or a member of a
last_field_type = TYPE_CONTEXT (last_field_type);
}
-
+
/* If we've reached the outermost class, then we're
done. */
if (same_type_p (field_type, t))
the type is incomplete. */
if (!COMPLETE_TYPE_P (current_class_type))
return;
-
+
/* Sort the mem-initializers into the order in which the
initializations should be performed. */
mem_inits = sort_mem_initializers (current_class_type, mem_inits);
in_base_initializer = 1;
-
+
/* Initialize base classes. */
- while (mem_inits
+ while (mem_inits
&& TREE_CODE (TREE_PURPOSE (mem_inits)) != FIELD_DECL)
{
tree subobject = TREE_PURPOSE (mem_inits);
/* If these initializations are taking place in a copy
constructor, the base class should probably be explicitly
initialized. */
- if (extra_warnings && !arguments
+ if (extra_warnings && !arguments
&& DECL_COPY_CONSTRUCTOR_P (current_function_decl)
&& TYPE_NEEDS_CONSTRUCTING (BINFO_TYPE (subobject)))
warning (0, "%Jbase class %q#T should be explicitly initialized in the "
else
{
tree base_addr;
-
+
base_addr = build_base_path (PLUS_EXPR, current_class_ptr,
subobject, 1);
expand_aggr_init_1 (subobject, NULL_TREE,
- build_indirect_ref (base_addr, NULL),
+ build_indirect_ref (base_addr, NULL),
arguments,
LOOKUP_NORMAL);
expand_cleanup_for_base (subobject, NULL_TREE);
/* Initialize the vptrs. */
initialize_vtbl_ptrs (current_class_ptr);
-
+
/* Initialize the data members. */
while (mem_inits)
{
/* Compute the value to use, when there's a VTT. */
vtt_parm = current_vtt_parm;
- vtbl2 = build2 (PLUS_EXPR,
- TREE_TYPE (vtt_parm),
+ vtbl2 = build2 (PLUS_EXPR,
+ TREE_TYPE (vtt_parm),
vtt_parm,
vtt_index);
vtbl2 = build_indirect_ref (vtbl2, NULL);
/* The actual initializer is the VTT value only in the subobject
constructor. In maybe_clone_body we'll substitute NULL for
the vtt_parm in the case of the non-subobject constructor. */
- vtbl = build3 (COND_EXPR,
- TREE_TYPE (vtbl),
+ vtbl = build3 (COND_EXPR,
+ TREE_TYPE (vtbl),
build2 (EQ_EXPR, boolean_type_node,
current_in_charge_parm, integer_zero_node),
- vtbl2,
+ vtbl2,
vtbl);
}
return;
/* Call the destructor. */
- expr = build_special_member_call (current_class_ref,
+ expr = build_special_member_call (current_class_ref,
base_dtor_identifier,
NULL_TREE,
binfo,
{
tree inner_if_stmt;
tree exp;
- tree flag;
+ tree flag;
/* If there are virtual base classes with destructors, we need to
emit cleanups to destroy them if an exception is thrown during
we already know where it is. */
exp = convert_to_base_statically (current_class_ref, vbase);
- expand_aggr_init_1 (vbase, current_class_ref, exp, arguments,
+ expand_aggr_init_1 (vbase, current_class_ref, exp, arguments,
LOOKUP_COMPLAIN);
finish_then_clause (inner_if_stmt);
finish_if_stmt (inner_if_stmt);
is erroneous. FIELD is the member we decided to initialize.
TYPE is the type for which the initialization is being performed.
FIELD must be a member of TYPE.
-
+
MEMBER_NAME is the name of the member. */
static int
virtual_binfo = binfo_for_vbase (basetype, current_class_type);
/* [class.base.init]
-
+
If a mem-initializer-id is ambiguous because it designates
both a direct non-virtual base class and an inherited virtual
base class, the mem-initializer is ill-formed. */
if (type == NULL_TREE)
return error_mark_node;
-
+
/* Handle namespace names fully here. */
if (TREE_CODE (type) == NAMESPACE_DECL)
{
else
{
member = lookup_member (basebinfo, name, 1, 0);
-
+
if (member == error_mark_node)
return error_mark_node;
}
t = build2 (TEMPLATE_ID_EXPR, TREE_TYPE (t), t,
TREE_OPERAND (orig_name, 1));
t = build2 (OFFSET_REF, unknown_type_node, decl, t);
-
+
PTRMEM_OK_P (t) = 1;
-
+
return t;
}
PTRMEM_OK_P (member) = 1;
return build_unary_op (ADDR_EXPR, member, 0);
}
- error ("invalid use of non-static member function %qD",
+ error ("invalid use of non-static member function %qD",
TREE_OPERAND (member, 1));
return member;
}
then re-evaluating it could give different results. */
&& TREE_CONSTANT (DECL_INITIAL (decl)))
return DECL_INITIAL (decl);
-
+
return decl;
}
\f
explicitly wrote "::new" rather than just "new". */
tree
-build_new (tree placement, tree type, tree nelts, tree init,
+build_new (tree placement, tree type, tree nelts, tree init,
int use_global_new)
{
tree rval;
if (processing_template_decl)
{
- rval = build_min (NEW_EXPR, build_pointer_type (type),
+ rval = build_min (NEW_EXPR, build_pointer_type (type),
placement, type, nelts, init);
NEW_EXPR_USE_GLOBAL (rval) = use_global_new;
TREE_SIDE_EFFECTS (rval) = 1;
tree placement, init;
tree size, rval;
/* True iff this is a call to "operator new[]" instead of just
- "operator new". */
+ "operator new". */
bool array_p = false;
/* True iff ARRAY_P is true and the bound of the array type is
not necessarily a compile time constant. For example, VLA_P is
true for "new int[f()]". */
bool vla_p = false;
- /* The type being allocated. If ARRAY_P is true, this will be an
+ /* The type being allocated. If ARRAY_P is true, this will be an
ARRAY_TYPE. */
tree full_type;
/* If ARRAY_P is true, the element type of the array. This is an
outer_nelts = nelts;
array_p = true;
- /* ??? The middle-end will error on us for building a VLA outside a
+ /* ??? The middle-end will error on us for building a VLA outside a
function context. Methinks that's not it's purvey. So we'll do
our own VLA layout later. */
vla_p = true;
for (elt_type = type;
TREE_CODE (elt_type) == ARRAY_TYPE;
elt_type = TREE_TYPE (elt_type))
- nelts = cp_build_binary_op (MULT_EXPR, nelts,
+ nelts = cp_build_binary_op (MULT_EXPR, nelts,
array_type_nelts_top (elt_type));
if (!complete_type_or_else (elt_type, exp))
use_java_new = 1;
alloc_decl = NULL;
- if (!get_global_value_if_present (get_identifier (alloc_name),
+ if (!get_global_value_if_present (get_identifier (alloc_name),
&alloc_decl))
{
error ("call to Java constructor with %qs undefined", alloc_name);
fnname = ansi_opname (array_p ? VEC_NEW_EXPR : NEW_EXPR);
- if (!globally_qualified_p
+ if (!globally_qualified_p
&& CLASS_TYPE_P (elt_type)
&& (array_p
? TYPE_HAS_ARRAY_NEW_OPERATOR (elt_type)
else
cookie_size = NULL_TREE;
- alloc_call = build_operator_new_call (fnname, placement,
+ alloc_call = build_operator_new_call (fnname, placement,
&size, &cookie_size);
}
}
alloc_node = TARGET_EXPR_SLOT (alloc_expr);
/* Strip any COMPOUND_EXPRs from ALLOC_CALL. */
- while (TREE_CODE (alloc_call) == COMPOUND_EXPR)
+ while (TREE_CODE (alloc_call) == COMPOUND_EXPR)
alloc_call = TREE_OPERAND (alloc_call, 1);
alloc_fn = get_callee_fndecl (alloc_call);
gcc_assert (alloc_fn != NULL_TREE);
there is no explicit placement argument. If there is more than
one argument, or there are variable arguments, then this is a
placement allocation function. */
- placement_allocation_fn_p
- = (type_num_arguments (TREE_TYPE (alloc_fn)) > 1
+ placement_allocation_fn_p
+ = (type_num_arguments (TREE_TYPE (alloc_fn)) > 1
|| varargs_function_p (alloc_fn));
/* Preevaluate the placement args so that we don't reevaluate them for a
}
else if (TYPE_NEEDS_CONSTRUCTING (type))
{
- init_expr = build_special_member_call (init_expr,
+ init_expr = build_special_member_call (init_expr,
complete_ctor_identifier,
init, elt_type,
LOOKUP_NORMAL);
/* The Standard is unclear here, but the right thing to do
is to use the same method for finding deallocation
functions that we use for finding allocation functions. */
- cleanup = build_op_delete_call (dcode, alloc_node, size,
+ cleanup = build_op_delete_call (dcode, alloc_node, size,
globally_qualified_p,
- (placement_allocation_fn_p
+ (placement_allocation_fn_p
? alloc_call : NULL_TREE));
if (!cleanup)
build2 (COMPOUND_EXPR, void_type_node, init_expr,
end));
}
-
+
}
}
else
tree cookie_size;
cookie_size = targetm.cxx.get_cookie_size (type);
- base_tbd
+ base_tbd
= cp_convert (ptype,
cp_build_binary_op (MINUS_EXPR,
- cp_convert (string_type_node,
+ cp_convert (string_type_node,
base),
cookie_size));
/* True size with header. */
body = deallocate_expr;
else
body = build_compound_expr (body, deallocate_expr);
-
+
if (!body)
body = integer_zero_node;
-
+
/* Outermost wrapper: If pointer is null, punt. */
body = fold_build3 (COND_EXPR, void_type_node,
fold_build2 (NE_EXPR, boolean_type_node, base,
return convert_to_void (body, /*implicit=*/NULL);
}
-/* Create an unnamed variable of the indicated TYPE. */
+/* Create an unnamed variable of the indicated TYPE. */
tree
create_temporary_var (tree type)
{
tree decl;
-
+
decl = build_decl (VAR_DECL, NULL_TREE, type);
TREE_USED (decl) = 1;
DECL_ARTIFICIAL (decl) = 1;
decl = create_temporary_var (type);
add_decl_expr (decl);
-
+
finish_expr_stmt (build_modify_expr (decl, INIT_EXPR, init));
return decl;
tree atype = TREE_TYPE (base);
/* The type of an element in the array. */
tree type = TREE_TYPE (atype);
- /* The element type reached after removing all outer array
+ /* The element type reached after removing all outer array
types. */
tree inner_elt_type;
/* The type of a pointer to an element in the array. */
tree try_block = NULL_TREE;
int num_initialized_elts = 0;
bool is_global;
-
+
if (TYPE_DOMAIN (atype))
maxindex = array_type_nelts (atype);
inner_elt_type = strip_array_types (atype);
if (init
&& (from_array == 2
- ? (!CLASS_TYPE_P (inner_elt_type)
+ ? (!CLASS_TYPE_P (inner_elt_type)
|| !TYPE_HAS_COMPLEX_ASSIGN_REF (inner_elt_type))
: !TYPE_NEEDS_CONSTRUCTING (type))
&& ((TREE_CODE (init) == CONSTRUCTOR
}
rval;
})
-
+
We can omit the try and catch blocks if we know that the
initialization will never throw an exception, or if the array
elements do not have destructors. We can omit the loop completely if
- the elements of the array do not have constructors.
+ the elements of the array do not have constructors.
We actually wrap the entire body of the above in a STMT_EXPR, for
- tidiness.
+ tidiness.
When copying from array to another, when the array elements have
only trivial copy constructors, we should use __builtin_memcpy
{
/* If initializing one array from another, initialize element by
element. We rely upon the below calls the do argument
- checking. */
+ checking. */
if (init)
{
base2 = decay_conversion (init);
0, 0, 0);
}
else
- elt_init = build_aggr_init (build1 (INDIRECT_REF, type, base),
+ elt_init = build_aggr_init (build1 (INDIRECT_REF, type, base),
init, 0);
-
+
current_stmt_tree ()->stmts_are_full_exprs_p = 1;
finish_expr_stmt (elt_init);
current_stmt_tree ()->stmts_are_full_exprs_p = 0;
array_type_nelts_total (type));
finish_cleanup_try_block (try_block);
- e = build_vec_delete_1 (rval, m,
+ e = build_vec_delete_1 (rval, m,
inner_elt_type, sfk_base_destructor,
/*use_global_delete=*/0);
finish_cleanup (e, try_block);
atype = build_pointer_type (atype);
stmt_expr = build1 (NOP_EXPR, atype, stmt_expr);
stmt_expr = build_indirect_ref (stmt_expr, NULL);
-
+
current_stmt_tree ()->stmts_are_full_exprs_p = destroy_temps;
return stmt_expr;
}
int use_vec_delete = !!(which_delete & 2);
enum tree_code code = use_vec_delete ? VEC_DELETE_EXPR : DELETE_EXPR;
- return build_op_delete_call (code, addr, virtual_size, use_global_delete,
+ return build_op_delete_call (code, addr, virtual_size, use_global_delete,
NULL_TREE);
}
gcc_unreachable ();
}
fn = lookup_fnfields (TREE_TYPE (exp), name, /*protect=*/2);
- return build_new_method_call (exp, fn,
+ return build_new_method_call (exp, fn,
/*args=*/NULL_TREE,
/*conversion_path=*/NULL_TREE,
flags);
else if (TREE_CODE (type) == ARRAY_TYPE)
{
handle_array:
-
+
if (TYPE_DOMAIN (type) == NULL_TREE)
{
error ("unknown array size in delete");
{
if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (BINFO_TYPE (base_binfo)))
{
- expr = build_special_member_call (current_class_ref,
+ expr = build_special_member_call (current_class_ref,
base_dtor_identifier,
NULL_TREE,
base_binfo,
- (LOOKUP_NORMAL
+ (LOOKUP_NORMAL
| LOOKUP_NONVIRTUAL));
expr = build3 (COND_EXPR, void_type_node, cond,
expr, void_zero_node);
|| BINFO_VIRTUAL_P (base_binfo))
continue;
- expr = build_special_member_call (current_class_ref,
+ expr = build_special_member_call (current_class_ref,
base_dtor_identifier,
- NULL_TREE, base_binfo,
+ NULL_TREE, base_binfo,
LOOKUP_NORMAL | LOOKUP_NONVIRTUAL);
finish_decl_cleanup (NULL_TREE, expr);
}
continue;
if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (TREE_TYPE (member)))
{
- tree this_member = (build_class_member_access_expr
- (current_class_ref, member,
+ tree this_member = (build_class_member_access_expr
+ (current_class_ref, member,
/*access_path=*/NULL_TREE,
/*preserve_reference=*/false));
tree this_type = TREE_TYPE (member);
declaration of "f" is available. Historically, G++ and most
other compilers accepted that usage since they deferred all name
lookup until instantiation time rather than doing unqualified
- name lookup at template definition time; explain to the user what
+ name lookup at template definition time; explain to the user what
is going wrong.
Note that we have the exact wording of the following message in
the manual (trouble.texi, node "Name lookup"), so they need to
be kept in synch. */
pedwarn ("there are no arguments to %qD that depend on a template "
- "parameter, so a declaration of %qD must be available",
+ "parameter, so a declaration of %qD must be available",
name, name);
-
+
if (!flag_permissive)
{
static bool hint;
/* All nesting of C++ functions is lexical; there is never a "static
chain" in the sense of GNU C nested functions. */
- if (code == FUNCTION_DECL)
+ if (code == FUNCTION_DECL)
DECL_NO_STATIC_CHAIN (t) = 1;
return t;
*template_info = TYPE_TEMPLATE_INFO (type);
return 1;
}
- }
+ }
else
{
/* Check if this is a primary template. */
else if (TYPE_NAME (el))
name = IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (el)));
fprintf (stderr, " S%d_ = ", i - 1);
- if (TYPE_P (el) &&
- (CP_TYPE_RESTRICT_P (el)
- || CP_TYPE_VOLATILE_P (el)
+ if (TYPE_P (el) &&
+ (CP_TYPE_RESTRICT_P (el)
+ || CP_TYPE_VOLATILE_P (el)
|| CP_TYPE_CONST_P (el)))
fprintf (stderr, "CV-");
- fprintf (stderr, "%s (%s at %p)\n",
+ fprintf (stderr, "%s (%s at %p)\n",
name, tree_code_name[TREE_CODE (el)], (void *) el);
}
}
tree c;
if (DEBUG_MANGLE)
- fprintf (stderr, " ++ add_substitution (%s at %10p)\n",
+ fprintf (stderr, " ++ add_substitution (%s at %10p)\n",
tree_code_name[TREE_CODE (node)], (void *) node);
/* Get the canonicalized substitution candidate for NODE. */
for (i = 0; VEC_iterate (tree, G.substitutions, i, candidate); i++)
{
gcc_assert (!(DECL_P (node) && node == candidate));
- gcc_assert (!(TYPE_P (node) && TYPE_P (candidate)
+ gcc_assert (!(TYPE_P (node) && TYPE_P (candidate)
&& same_type_p (node, candidate)));
}
}
which may be a decl or a CLASS_TYPE, is a template-id with template
name of substitution_index[INDEX] in the ::std namespace. */
-static inline int
+static inline int
is_std_substitution (const tree node,
const substitution_identifier_index_t index)
{
type = node;
decl = TYPE_NAME (node);
}
- else
+ else
/* These are not the droids you're looking for. */
return 0;
return (DECL_NAMESPACE_STD_P (CP_DECL_CONTEXT (decl))
- && TYPE_LANG_SPECIFIC (type)
+ && TYPE_LANG_SPECIFIC (type)
&& TYPE_TEMPLATE_INFO (type)
- && (DECL_NAME (TYPE_TI_TEMPLATE (type))
+ && (DECL_NAME (TYPE_TI_TEMPLATE (type))
== subst_identifiers[index]));
}
return 0;
/* Figure out its template args. */
if (DECL_P (node))
- args = DECL_TI_ARGS (node);
+ args = DECL_TI_ARGS (node);
else if (CLASS_TYPE_P (node))
args = CLASSTYPE_TI_ARGS (node);
else
/* Oops, not a template. */
return 0;
/* NODE's template arg list should be <char>. */
- return
+ return
TREE_VEC_LENGTH (args) == 1
&& TREE_VEC_ELT (args, 0) == char_type_node;
}
First, check standard special-case substitutions.
- <substitution> ::= St
+ <substitution> ::= St
# ::std
- ::= Sa
+ ::= Sa
# ::std::allocator
- ::= Sb
+ ::= Sb
# ::std::basic_string
- ::= Ss
+ ::= Ss
# ::std::basic_string<char,
::std::char_traits<char>,
::std::allocator<char> >
- ::= Si
+ ::= Si
# ::std::basic_istream<char, ::std::char_traits<char> >
- ::= So
+ ::= So
# ::std::basic_ostream<char, ::std::char_traits<char> >
- ::= Sd
- # ::std::basic_iostream<char, ::std::char_traits<char> >
+ ::= Sd
+ # ::std::basic_iostream<char, ::std::char_traits<char> >
Then examine the stack of currently available substitution
candidates for entities appearing earlier in the same mangling
type = TYPE_P (node) ? node : TREE_TYPE (node);
/* Check for std::allocator. */
- if (decl
+ if (decl
&& is_std_substitution (decl, SUBID_ALLOCATOR)
&& !CLASSTYPE_USE_TEMPLATE (TREE_TYPE (decl)))
{
{
if (TYPE_P (node))
{
- /* If this is a type (i.e. a fully-qualified template-id),
- check for
+ /* If this is a type (i.e. a fully-qualified template-id),
+ check for
std::basic_string <char,
std::char_traits<char>,
std::allocator<char> > . */
&& CLASSTYPE_USE_TEMPLATE (type)
&& CLASSTYPE_TEMPLATE_INFO (type) != NULL)
{
- /* First, check for the template
+ /* First, check for the template
args <char, std::char_traits<char> > . */
tree args = CLASSTYPE_TI_ARGS (type);
if (TREE_VEC_LENGTH (args) == 2
/* TOP_LEVEL is true, if this is being called at outermost level of
mangling. It should be false when mangling a decl appearing in an
expression within some other mangling.
-
+
<mangled-name> ::= _Z <encoding> */
static void
&& !DECL_OVERLOADED_OPERATOR_P (decl))
{
unmangled_name:;
-
+
if (top_level)
write_string (IDENTIFIER_POINTER (DECL_NAME (decl)));
else
d = decl;
}
- write_bare_function_type (fn_type,
+ write_bare_function_type (fn_type,
(!DECL_CONSTRUCTOR_P (decl)
&& !DECL_DESTRUCTOR_P (decl)
&& !DECL_CONV_FN_P (decl)
/* <name> ::= <unscoped-name>
::= <unscoped-template-name> <template-args>
::= <nested-name>
- ::= <local-name>
+ ::= <local-name>
If IGNORE_LOCAL_SCOPE is nonzero, this production of <name> is
called from <local-name>, which mangles the enclosing scope
latter with a special substitution. Also, a name that is
directly in a local function scope is also mangled with
<unscoped-name> rather than a full <nested-name>. */
- if (context == NULL
- || context == global_namespace
+ if (context == NULL
+ || context == global_namespace
|| DECL_NAMESPACE_STD_P (context)
|| (ignore_local_scope && TREE_CODE (context) == FUNCTION_DECL))
{
{
/* If not, it should be either in the global namespace, or directly
in a local function scope. */
- gcc_assert (context == global_namespace
+ gcc_assert (context == global_namespace
|| context == NULL
|| TREE_CODE (context) == FUNCTION_DECL);
-
+
write_unqualified_name (decl);
}
}
/* Write the nested name, including CV-qualifiers, of DECL.
- <nested-name> ::= N [<CV-qualifiers>] <prefix> <unqualified-name> E
+ <nested-name> ::= N [<CV-qualifiers>] <prefix> <unqualified-name> E
::= N [<CV-qualifiers>] <template-prefix> <template-args> E
<CV-qualifiers> ::= [r] [V] [K] */
MANGLE_TRACE_TREE ("nested-name", decl);
write_char ('N');
-
+
/* Write CV-qualifiers, if this is a member function. */
- if (TREE_CODE (decl) == FUNCTION_DECL
+ if (TREE_CODE (decl) == FUNCTION_DECL
&& DECL_NONSTATIC_MEMBER_FUNCTION_P (decl))
{
if (DECL_VOLATILE_MEMFUNC_P (decl))
}
/* In G++ 3.2, the name of the template parameter was used. */
- if (TREE_CODE (node) == TEMPLATE_TYPE_PARM
+ if (TREE_CODE (node) == TEMPLATE_TYPE_PARM
&& !abi_version_at_least (2))
G.need_abi_warning = true;
else
{
gcc_assert (CLASSTYPE_TEMPLATE_ID_P (type));
-
+
template = TYPE_TI_TEMPLATE (type);
}
}
/* We don't need to handle thunks, vtables, or VTTs here. Those are
- mangled through special entry points.
+ mangled through special entry points.
<unqualified-name> ::= <operator-name>
- ::= <special-name>
+ ::= <special-name>
::= <source-name> */
static void
write_special_name_destructor (decl);
else if (DECL_NAME (decl) == NULL_TREE)
write_source_name (DECL_ASSEMBLER_NAME (decl));
- else if (DECL_CONV_FN_P (decl))
+ else if (DECL_CONV_FN_P (decl))
{
- /* Conversion operator. Handle it right here.
+ /* Conversion operator. Handle it right here.
<operator> ::= cv <type> */
tree type;
if (decl_is_template_id (decl, NULL))
oni = assignment_operator_name_info;
else
oni = operator_name_info;
-
+
write_string (oni[DECL_OVERLOADED_OPERATOR_P (decl)].mangled_name);
}
else
write_type (type);
}
-/* Non-terminal <source-name>. IDENTIFIER is an IDENTIFIER_NODE.
+/* Non-terminal <source-name>. IDENTIFIER is an IDENTIFIER_NODE.
<source-name> ::= </length/ number> <identifier> */
{
static const char base_digits[] = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ";
unsigned digits = 0;
-
+
while (number)
{
unsigned HOST_WIDE_INT d = number / base;
-
+
*--buffer = base_digits[number - d * base];
digits++;
number = d;
representable. */
chunk = 1000000000;
chunk_digits = 9;
-
+
if (sizeof (HOST_WIDE_INT) >= 8)
{
/* It is at least 64 bits, so 10^18 is representable. */
chunk_digits = 18;
chunk *= chunk;
}
-
+
type = c_common_signed_or_unsigned_type (1, TREE_TYPE (cst));
base = build_int_cstu (type, chunk);
n = build_int_cst_wide (type,
while (!done);
write_chars (ptr, count);
}
- else
+ else
{
/* A small num. */
unsigned HOST_WIDE_INT low = TREE_INT_CST_LOW (cst);
-
+
if (sign < 0)
{
write_char ('n');
}
}
-/* Write out a floating-point literal.
-
+/* Write out a floating-point literal.
+
"Floating-point literals are encoded using the bit pattern of the
target processor's internal representation of that number, as a
fixed-length lowercase hexadecimal string, high-order bytes first
format for REAL_VALUE_TYPE. */
size_t i;
for (i = 0; i < sizeof (TREE_REAL_CST (value)); ++i)
- write_number (((unsigned char *) &TREE_REAL_CST (value))[i],
+ write_number (((unsigned char *) &TREE_REAL_CST (value))[i],
/*unsigned_p*/ 1,
/*base*/ 16);
G.need_abi_warning = 1;
}
/* Handle constructor productions of non-terminal <special-name>.
- CTOR is a constructor FUNCTION_DECL.
+ CTOR is a constructor FUNCTION_DECL.
<special-name> ::= C1 # complete object constructor
::= C2 # base object constructor
::= C3 # complete object allocating constructor
- Currently, allocating constructors are never used.
+ Currently, allocating constructors are never used.
We also need to provide mangled names for the maybe-in-charge
constructor, so we treat it here too. mangle_decl_string will
}
/* Handle destructor productions of non-terminal <special-name>.
- DTOR is a destructor FUNCTION_DECL.
+ DTOR is a destructor FUNCTION_DECL.
<special-name> ::= D0 # deleting (in-charge) destructor
::= D1 # complete object (in-charge) destructor
else if (TREE_CODE (entity) == TYPE_DECL)
{
int ix;
-
+
/* Scan the list of local classes. */
entity = TREE_TYPE (entity);
for (ix = 0; ; ix++)
&& TYPE_CONTEXT (type) == TYPE_CONTEXT (entity))
++discriminator;
}
- }
+ }
return discriminator;
}
return 0;
}
-/* <discriminator> := _ <number>
+/* <discriminator> := _ <number>
The discriminator is used only for the second and later occurrences
of the same name within a single function. In this case <number> is
if (TREE_CODE (entity) == STRING_CST)
{
write_char ('s');
- write_discriminator (discriminator_for_string_literal (function,
+ write_discriminator (discriminator_for_string_literal (function,
entity));
}
else
}
}
-/* Non-terminals <type> and <CV-qualifier>.
+/* Non-terminals <type> and <CV-qualifier>.
<type> ::= <builtin-type>
::= <function-type>
::= R <type> # reference-to
::= C <type> # complex pair (C 2000)
::= G <type> # imaginary (C 2000) [not supported]
- ::= U <source-name> <type> # vendor extended type qualifier
+ ::= U <source-name> <type> # vendor extended type qualifier
TYPE is a type node. */
-static void
+static void
write_type (tree type)
{
/* This gets set to nonzero if TYPE turns out to be a (possibly
if (find_substitution (type))
return;
-
+
if (write_CV_qualifiers_for_type (type) > 0)
/* If TYPE was CV-qualified, we just wrote the qualifiers; now
mangle the unqualified type. The recursive call is needed here
case BOUND_TEMPLATE_TEMPLATE_PARM:
write_template_template_param (type);
- write_template_args
+ write_template_args
(TI_ARGS (TEMPLATE_TEMPLATE_PARM_TEMPLATE_INFO (type)));
break;
"In cases where multiple order-insensitive qualifiers are
present, they should be ordered 'K' (closest to the base type),
- 'V', 'r', and 'U' (farthest from the base type) ..."
+ 'V', 'r', and 'U' (farthest from the base type) ..."
Note that we do not use cp_type_quals below; given "const
int[3]", the "const" is emitted with the "int", not with the
return num_qualifiers;
}
-/* Non-terminal <builtin-type>.
+/* Non-terminal <builtin-type>.
- <builtin-type> ::= v # void
+ <builtin-type> ::= v # void
::= b # bool
::= w # wchar_t
::= c # char
::= l # long
::= m # unsigned long
::= x # long long, __int64
- ::= y # unsigned long long, __int64
+ ::= y # unsigned long long, __int64
::= n # __int128
::= o # unsigned __int128
::= f # float
::= d # double
- ::= e # long double, __float80
+ ::= e # long double, __float80
::= g # __float128 [not supported]
::= u <source-name> # vendor extended type */
-static void
+static void
write_builtin_type (tree type)
{
switch (TREE_CODE (type))
extern "C" function_t f; // Vice versa.
See [dcl.link]. */
- write_bare_function_type (type, /*include_return_type_p=*/1,
+ write_bare_function_type (type, /*include_return_type_p=*/1,
/*decl=*/NULL);
write_char ('E');
}
write_type (TREE_TYPE (type));
/* Now mangle the types of the arguments. */
- write_method_parms (TYPE_ARG_TYPES (type),
+ write_method_parms (TYPE_ARG_TYPES (type),
TREE_CODE (type) == METHOD_TYPE,
decl);
}
int varargs_p = 1;
/* If this is a member function, skip the first arg, which is the
- this pointer.
+ this pointer.
"Member functions do not encode the type of their implicit this
- parameter."
-
+ parameter."
+
Similarly, there's no need to mangle artificial parameters, like
the VTT parameters for constructors and destructors. */
if (method_p)
}
}
- for (first_parm_type = parm_types;
- parm_types;
+ for (first_parm_type = parm_types;
+ parm_types;
parm_types = TREE_CHAIN (parm_types))
{
tree parm = TREE_VALUE (parm_types);
/* <class-enum-type> ::= <name> */
-static void
+static void
write_class_enum_type (const tree type)
{
write_name (TYPE_NAME (type), /*ignore_local_scope=*/0);
{
int i;
int length = TREE_VEC_LENGTH (args);
-
+
MANGLE_TRACE_TREE ("template-args", args);
write_char ('I');
}
for (i = 0; i < length; ++i)
write_template_arg (TREE_VEC_ELT (args, i));
-
+
write_char ('E');
}
<expr-primary> ::= <template-param>
::= L <type> <value number> E # literal
- ::= L <mangled-name> E # external name
+ ::= L <mangled-name> E # external name
::= sr <type> <unqualified-name>
::= sr <type> <unqualified-name> <template-args> */
}
/* Handle template parameters. */
- if (code == TEMPLATE_TYPE_PARM
+ if (code == TEMPLATE_TYPE_PARM
|| code == TEMPLATE_TEMPLATE_PARM
|| code == BOUND_TEMPLATE_TEMPLATE_PARM
|| code == TEMPLATE_PARM_INDEX)
write_mangled_name (expr, false);
write_char ('E');
}
- else if (TREE_CODE (expr) == SIZEOF_EXPR
+ else if (TREE_CODE (expr) == SIZEOF_EXPR
&& TYPE_P (TREE_OPERAND (expr, 0)))
{
write_string ("st");
else if (assignment_operator_name_info[i].identifier
== member)
{
- mangled_name
+ mangled_name
= assignment_operator_name_info[i].mangled_name;
break;
}
write_expression (TREE_OPERAND (expr, 0));
break;
-
+
/* Handle pointers-to-members specially. */
case SCOPE_REF:
write_type (TREE_OPERAND (expr, 0));
}
}
-/* Literal subcase of non-terminal <template-arg>.
+/* Literal subcase of non-terminal <template-arg>.
"Literal arguments, e.g. "A<42L>", are encoded with their type
and value. Negative integer values are preceded with "n"; for
case CONST_DECL:
write_integer_cst (DECL_INITIAL (value));
break;
-
+
case INTEGER_CST:
gcc_assert (!same_type_p (TREE_TYPE (value), boolean_type_node)
|| integer_zerop (value) || integer_onep (value));
default:
gcc_unreachable ();
}
-
+
write_char ('E');
}
-/* Non-terminal <template-arg>.
+/* Non-terminal <template-arg>.
<template-arg> ::= <type> # type
::= L <type> </value/ number> E # literal
code = TREE_CODE (node);
}
}
-
+
if (TREE_CODE (node) == NOP_EXPR
&& TREE_CODE (TREE_TYPE (node)) == REFERENCE_TYPE)
{
else if (DECL_P (node))
{
/* Until ABI version 2, non-type template arguments of
- enumeration type were mangled using their names. */
+ enumeration type were mangled using their names. */
if (code == CONST_DECL && !abi_version_at_least (2))
G.need_abi_warning = 1;
write_char ('L');
}
-/* Non-terminal <array-type>. TYPE is an ARRAY_TYPE.
+/* Non-terminal <array-type>. TYPE is an ARRAY_TYPE.
- <array-type> ::= A [</dimension/ number>] _ </element/ type>
+ <array-type> ::= A [</dimension/ number>] _ </element/ type>
::= A <expression> _ </element/ type>
"Array types encode the dimension (number of elements) and the
}
write_expression (max);
}
-
+
}
write_char ('_');
write_type (TREE_TYPE (type));
}
/* <template-template-param>
- ::= <template-param>
+ ::= <template-param>
::= <substitution> */
static void
only the template. */
if (TREE_CODE (parm) == BOUND_TEMPLATE_TEMPLATE_PARM)
{
- template
+ template
= TI_TEMPLATE (TEMPLATE_TEMPLATE_PARM_TEMPLATE_INFO (parm));
if (find_substitution (template))
return;
add_substitution (template);
}
-/* Non-terminal <substitution>.
+/* Non-terminal <substitution>.
<substitution> ::= S <seq-id> _
::= S_ */
{
G.entity = entity;
G.need_abi_warning = false;
- if (!ident_p)
+ if (!ident_p)
{
obstack_free (&name_obstack, name_base);
mangle_obstack = &name_obstack;
write_type (TREE_TYPE (decl));
else
write_mangled_name (decl, true);
-
+
result = finish_mangling (/*warn=*/true);
if (DEBUG_MANGLE)
fprintf (stderr, "mangle_decl_string = '%s'\n\n", result);
static inline tree
get_identifier_nocopy (const char *name)
{
- hashnode ht_node = ht_lookup (ident_hash, (const unsigned char *) name,
+ hashnode ht_node = ht_lookup (ident_hash, (const unsigned char *) name,
strlen (name), HT_ALLOCED);
return HT_IDENT_TO_GCC_IDENT (ht_node);
}
void
mangle_decl (const tree decl)
{
- SET_DECL_ASSEMBLER_NAME (decl,
+ SET_DECL_ASSEMBLER_NAME (decl,
get_identifier_nocopy (mangle_decl_string (decl)));
}
/* Return an identifier for a construction vtable group. TYPE is
the most derived class in the hierarchy; BINFO is the base
- subobject for which this construction vtable group will be used.
+ subobject for which this construction vtable group will be used.
This mangling isn't part of the ABI specification; in the ABI
specification, the vtable group is dumped in the same COMDAT as the
main vtable, and is referenced only from that vtable, so it doesn't
need an external name. For binary formats without COMDAT sections,
- though, we need external names for the vtable groups.
+ though, we need external names for the vtable groups.
We use the production
}
/* Mangle a this pointer or result pointer adjustment.
-
+
<call-offset> ::= h <fixed offset number> _
::= v <fixed offset number> _ <virtual offset number> _ */
-
+
static void
mangle_call_offset (const tree fixed_offset, const tree virtual_offset)
{
tree virtual_offset)
{
const char *result;
-
+
start_mangling (fn_decl, /*ident_p=*/true);
write_string ("_Z");
write_char ('T');
-
+
if (!this_adjusting)
{
/* Covariant thunk with no this adjustment */
void **slot;
tree identifier;
- if (conv_type_names == NULL)
+ if (conv_type_names == NULL)
conv_type_names = htab_create_ggc (31, &hash_type, &compare_type, NULL);
- slot = htab_find_slot_with_hash (conv_type_names, type,
+ slot = htab_find_slot_with_hash (conv_type_names, type,
(hashval_t) TYPE_UID (type), INSERT);
identifier = (tree)*slot;
if (!identifier)
{
char buffer[64];
-
+
/* Create a unique name corresponding to TYPE. */
sprintf (buffer, "operator %lu",
(unsigned long) htab_elements (conv_type_names));
IDENTIFIER_OPNAME_P (identifier) = 1;
IDENTIFIER_TYPENAME_P (identifier) = 1;
}
-
+
return identifier;
}
/* Handle the hair of processing (but not expanding) inline functions.
Also manage function and variable name overloading.
- Copyright (C) 1987, 1989, 1992, 1993, 1994, 1995, 1996, 1997, 1998,
+ Copyright (C) 1987, 1989, 1992, 1993, 1994, 1995, 1996, 1997, 1998,
1999, 2000, 2001, 2002, 2003, 2004, 2005 Free Software Foundation, Inc.
Contributed by Michael Tiemann (tiemann@cygnus.com)
This file is part of GCC.
-
+
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2, or (at your option)
{
HOST_WIDE_INT d;
tree thunk;
-
+
gcc_assert (TREE_CODE (function) == FUNCTION_DECL);
/* We can have this thunks to covariant thunks, but not vice versa. */
gcc_assert (!DECL_THIS_THUNK_P (function));
gcc_assert (!DECL_RESULT_THUNK_P (function) || this_adjusting);
-
+
/* Scale the VIRTUAL_OFFSET to be in terms of bytes. */
if (this_adjusting && virtual_offset)
- virtual_offset
+ virtual_offset
= size_binop (MULT_EXPR,
virtual_offset,
convert (ssizetype,
TYPE_SIZE_UNIT (vtable_entry_type)));
-
+
d = tree_low_cst (fixed_offset, 0);
-
+
/* See if we already have the thunk in question. For this_adjusting
thunks VIRTUAL_OFFSET will be an INTEGER_CST, for covariant thunks it
will be a BINFO. */
virtual_offset)
: THUNK_VIRTUAL_OFFSET (thunk) == virtual_offset)))
return thunk;
-
+
/* All thunks must be created before FUNCTION is actually emitted;
the ABI requires that all thunks be emitted together with the
function to which they transfer control. */
DECL_LANG_SPECIFIC (thunk) = DECL_LANG_SPECIFIC (function);
cxx_dup_lang_specific_decl (thunk);
DECL_THUNKS (thunk) = NULL_TREE;
-
+
DECL_CONTEXT (thunk) = DECL_CONTEXT (function);
TREE_READONLY (thunk) = TREE_READONLY (function);
TREE_THIS_VOLATILE (thunk) = TREE_THIS_VOLATILE (function);
THUNK_FIXED_OFFSET (thunk) = d;
THUNK_VIRTUAL_OFFSET (thunk) = virtual_offset;
THUNK_ALIAS (thunk) = NULL_TREE;
-
+
/* The thunk itself is not a constructor or destructor, even if
the thing it is thunking to is. */
DECL_INTERFACE_KNOWN (thunk) = 1;
DECL_DECLARED_INLINE_P (thunk) = 0;
/* Nor has it been deferred. */
DECL_DEFERRED_FN (thunk) = 0;
-
+
/* Add it to the list of thunks associated with FUNCTION. */
TREE_CHAIN (thunk) = DECL_THUNKS (function);
DECL_THUNKS (function) = thunk;
break;
}
}
-
+
DECL_NAME (thunk) = name;
SET_DECL_ASSEMBLER_NAME (thunk, name);
}
ptr = save_expr (ptr);
/* The vptr is always at offset zero in the object. */
vtable = build1 (NOP_EXPR,
- build_pointer_type (build_pointer_type
+ build_pointer_type (build_pointer_type
(vtable_entry_type)),
ptr);
/* Form the vtable address. */
/* Adjust the `this' pointer. */
ptr = fold_build2 (PLUS_EXPR, TREE_TYPE (ptr), ptr, vtable);
}
-
+
if (!this_adjusting)
/* Adjust the pointer by the constant. */
ptr = fold_build2 (PLUS_EXPR, TREE_TYPE (ptr), ptr,
if (TREE_ASM_WRITTEN (thunk_fndecl))
return;
-
+
function = THUNK_TARGET (thunk_fndecl);
if (DECL_RESULT (thunk_fndecl))
/* We already turned this thunk into an ordinary function.
if (DECL_THUNK_P (function))
/* The target is itself a thunk, process it now. */
use_thunk (function, emit_p);
-
+
/* Thunks are always addressable; they only appear in vtables. */
TREE_ADDRESSABLE (thunk_fndecl) = 1;
}
else
virtual_value = 0;
-
+
/* And, if we need to emit the thunk, it's used. */
mark_used (thunk_fndecl);
/* This thunk is actually defined. */
rewrite. */
TREE_PUBLIC (thunk_fndecl) = TREE_PUBLIC (function);
DECL_VISIBILITY (thunk_fndecl) = DECL_VISIBILITY (function);
- DECL_VISIBILITY_SPECIFIED (thunk_fndecl)
+ DECL_VISIBILITY_SPECIFIED (thunk_fndecl)
= DECL_VISIBILITY_SPECIFIED (function);
if (flag_weak && TREE_PUBLIC (thunk_fndecl))
comdat_linkage (thunk_fndecl);
a = nreverse (t);
DECL_ARGUMENTS (thunk_fndecl) = a;
BLOCK_VARS (DECL_INITIAL (thunk_fndecl)) = a;
-
+
if (this_adjusting
&& targetm.asm_out.can_output_mi_thunk (thunk_fndecl, fixed_offset,
virtual_value, alias))
if (this_adjusting)
t = thunk_adjust (t, /*this_adjusting=*/1,
fixed_offset, virtual_offset);
-
+
/* Build up the call to the real function. */
t = tree_cons (NULL_TREE, t, NULL_TREE);
for (a = TREE_CHAIN (a); a; a = TREE_CHAIN (a))
t = nreverse (t);
t = build_call (alias, t);
CALL_FROM_THUNK_P (t) = 1;
-
+
if (VOID_TYPE_P (TREE_TYPE (t)))
finish_expr_stmt (t);
else
t = save_expr (t);
cond = cp_convert (boolean_type_node, t);
}
-
+
t = thunk_adjust (t, /*this_adjusting=*/0,
fixed_offset, virtual_offset);
if (cond)
for (vbases = CLASSTYPE_VBASECLASSES (current_class_type), i = 0;
VEC_iterate (tree, vbases, i, binfo); i++)
{
- member_init_list
+ member_init_list
= tree_cons (binfo,
build_tree_list (NULL_TREE,
build_base_path (PLUS_EXPR, parm,
BINFO_BASE_ITERATE (binfo, i, base_binfo); i++)
{
if (BINFO_VIRTUAL_P (base_binfo))
- continue;
+ continue;
- member_init_list
+ member_init_list
= tree_cons (base_binfo,
build_tree_list (NULL_TREE,
build_base_path (PLUS_EXPR, parm,
if (TREE_CODE (expr_type) != REFERENCE_TYPE)
{
int quals = cvquals;
-
+
if (DECL_MUTABLE_P (field))
quals &= ~TYPE_QUAL_CONST;
expr_type = cp_build_qualified_type (expr_type, quals);
}
-
+
init = build3 (COMPONENT_REF, expr_type, init, field, NULL_TREE);
init = build_tree_list (NULL_TREE, init);
explicitly since the base class may be ambiguous. */
converted_parm = build_base_path (PLUS_EXPR, parm, base_binfo, 1);
/* Call the base class assignment operator. */
- finish_expr_stmt
- (build_special_member_call (current_class_ref,
+ finish_expr_stmt
+ (build_special_member_call (current_class_ref,
ansi_assopname (NOP_EXPR),
- build_tree_list (NULL_TREE,
+ build_tree_list (NULL_TREE,
converted_parm),
base_binfo,
LOOKUP_NORMAL | LOOKUP_NONVIRTUAL));
}
/* Assign to each of the non-static data members. */
- for (fields = TYPE_FIELDS (current_class_type);
- fields;
+ for (fields = TYPE_FIELDS (current_class_type);
+ fields;
fields = TREE_CHAIN (fields))
{
tree comp = current_class_ref;
continue;
expr_type = TREE_TYPE (field);
-
+
if (CP_TYPE_CONST_P (expr_type))
{
error ("non-static const member %q#D, can't use default "
continue;
comp = build3 (COMPONENT_REF, expr_type, comp, field, NULL_TREE);
-
+
/* Compute the type of init->field */
quals = cvquals;
if (DECL_MUTABLE_P (field))
quals &= ~TYPE_QUAL_CONST;
expr_type = cp_build_qualified_type (expr_type, quals);
-
+
init = build3 (COMPONENT_REF, expr_type, init, field, NULL_TREE);
if (DECL_NAME (field))
deferred, and thus have saved where we were first needed. */
DECL_SOURCE_LOCATION (fndecl)
= DECL_SOURCE_LOCATION (TYPE_NAME (DECL_CONTEXT (fndecl)));
-
+
/* If we've been asked to synthesize a clone, just synthesize the
cloned function instead. Doing so will automatically fill in the
body for the clone. */
if (fn)
{
tree fn_raises = TYPE_RAISES_EXCEPTIONS (TREE_TYPE (fn));
-
+
raises = merge_exception_specifiers (raises, fn_raises);
}
}
{
tree type = TREE_TYPE (fields);
tree fn;
-
+
if (TREE_CODE (fields) != FIELD_DECL || DECL_ARTIFICIAL (fields))
continue;
while (TREE_CODE (type) == ARRAY_TYPE)
type = TREE_TYPE (type);
if (TREE_CODE (type) != RECORD_TYPE)
continue;
-
+
fn = (*extractor) (type, client);
if (fn)
{
tree fn_raises = TYPE_RAISES_EXCEPTIONS (TREE_TYPE (fn));
-
+
raises = merge_exception_specifiers (raises, fn_raises);
}
}
locate_ctor (tree type, void *client ATTRIBUTE_UNUSED)
{
tree fns;
-
+
if (!TYPE_HAS_DEFAULT_CONSTRUCTOR (type))
return NULL_TREE;
{
tree fn = OVL_CURRENT (fns);
tree parms = TYPE_ARG_TYPES (TREE_TYPE (fn));
-
+
if (sufficient_parms_p (TREE_CHAIN (parms)))
return fn;
}
tree fns;
tree best = NULL_TREE;
bool excess_p = false;
-
+
if (client->name)
{
int ix;
tree src_type;
int excess;
int quals;
-
+
parms = TREE_CHAIN (parms);
if (!parms)
continue;
case sfk_assignment_operator:
{
struct copy_data data;
-
+
data.name = NULL;
data.quals = 0;
if (kind == sfk_assignment_operator)
/* Add it to CLASSTYPE_METHOD_VEC. */
add_method (type, fn, NULL_TREE);
/* Add it to TYPE_METHODS. */
- if (sfk == sfk_destructor
+ if (sfk == sfk_destructor
&& DECL_VIRTUAL_P (fn)
&& abi_version_at_least (2))
/* The ABI requires that a virtual destructor go at the end of the
{
/* G++ 3.2 put the implicit destructor at the *beginning* of the
TYPE_METHODS list, which cause the destructor to be emitted
- in an incorrect location in the vtable. */
+ in an incorrect location in the vtable. */
if (warn_abi && DECL_VIRTUAL_P (fn))
warning (0, "vtable layout for class %qT may not be ABI-compliant"
"and may change in a future version of GCC due to "
{
cp_class_binding *cb;
cxx_binding *binding;
-
+
if (VEC_length (cp_class_binding, scope->class_shadowed))
{
cp_class_binding *old_base;
{
/* Fixup the current bindings, as they might have moved. */
size_t i;
-
+
for (i = 0;
VEC_iterate (cp_class_binding, scope->class_shadowed, i, cb);
i++)
}
else
cb = VEC_safe_push (cp_class_binding, gc, scope->class_shadowed, NULL);
-
+
cb->identifier = name;
binding = &cb->base;
binding->scope = scope;
}
else
binding = new_class_binding (id, decl, /*type=*/NULL_TREE, level);
-
+
/* Now, fill in the binding information. */
binding->previous = IDENTIFIER_BINDING (id);
INHERITED_VALUE_BINDING_P (binding) = 0;
else if (/* BVAL is null when push_class_level_binding moves an
inherited type-binding out of the way to make room for a
new value binding. */
- !bval
+ !bval
/* BVAL is error_mark_node when DECL's name has been used
in a non-class scope prior declaration. In that case,
we should have already issued a diagnostic; for graceful
In a given scope, a typedef specifier can be used to redefine
the name of any type declared in that scope to refer to the
- type to which it already refers.
+ type to which it already refers.
However, in class scopes, this rule does not apply due to the
stricter language in [class.mem] prohibiting redeclarations of
&& DECL_NAMESPACE_ALIAS (bval)
&& ORIGINAL_NAMESPACE (bval) == ORIGINAL_NAMESPACE (decl))
/* [namespace.alias]
-
+
In a declarative region, a namespace-alias-definition can be
used to redefine a namespace-alias declared in that declarative
region to refer only to the namespace to which it already
static void
add_decl_to_level (tree decl, cxx_scope *b)
{
- if (TREE_CODE (decl) == NAMESPACE_DECL
+ if (TREE_CODE (decl) == NAMESPACE_DECL
&& !DECL_NAMESPACE_ALIAS (decl))
{
TREE_CHAIN (decl) = b->namespaces;
TREE_CHAIN (decl) = b->vtables;
b->vtables = decl;
}
- else
+ else
{
/* We build up the list in reverse order, and reverse it later if
necessary. */
b->names_size++;
/* If appropriate, add decl to separate list of statics. We
- include extern variables because they might turn out to be
+ include extern variables because they might turn out to be
static later. It's OK for this list to contain a few false
positives. */
if (b->kind == sk_namespace)
else
{
tree olddecl = duplicate_decls (x, t);
-
+
/* If the redeclaration failed, we can stop at this
point. */
if (olddecl == error_mark_node)
{
/* A redeclaration of main, but not a duplicate of the
previous one.
-
+
[basic.start.main]
-
+
This function shall not be overloaded. */
cp_error_at ("invalid redeclaration of %qD", t);
error ("as %qD", x);
/*want_type=*/false);
else
member = NULL_TREE;
-
+
if (member && !TREE_STATIC (member))
{
/* Location of previous decl is not useful in this case. */
begin_scope (scope_kind kind, tree entity)
{
cxx_scope *scope;
-
+
/* Reuse or create a struct for this binding level. */
if (!ENABLE_SCOPE_CHECKING && free_binding_level)
{
case sk_cleanup:
scope->keep = true;
break;
-
+
case sk_template_spec:
scope->explicit_spec_p = true;
kind = sk_template_parms;
/* We cannot leave a scope, if there are none left. */
if (NAMESPACE_LEVEL (global_namespace))
gcc_assert (!global_scope_p (scope));
-
+
if (ENABLE_SCOPE_CHECKING)
{
indent (--binding_depth);
size_t i;
cp_class_binding *b;
fprintf (stderr, " class-shadowed:");
- for (i = 0;
+ for (i = 0;
VEC_iterate(cp_class_binding, lvl->class_shadowed, i, b);
- ++i)
+ ++i)
fprintf (stderr, " %s ", IDENTIFIER_POINTER (b->identifier));
fprintf (stderr, "\n");
}
supplement_binding (binding, decl);
else
binding->value = decl;
-
+
/* Store marker instead of real type. */
type = global_type_node;
}
if (!name)
return false;
-
+
if (TREE_CODE (name) != IDENTIFIER_NODE)
return false;
-
+
ctor_name = constructor_name_full (type);
if (name == ctor_name)
return true;
return get_identifier (buf);
}
-/* Return (from the stack of) the BINDING, if any, established at SCOPE. */
+/* Return (from the stack of) the BINDING, if any, established at SCOPE. */
static inline cxx_binding *
find_binding (cxx_scope *scope, cxx_binding *binding)
/* It is impossible to overload a built-in function; any explicit
declaration eliminates the built-in declaration. So, if OLDVAL
is a built-in, then we can just pretend it isn't there. */
- if (oldval
+ if (oldval
&& TREE_CODE (oldval) == FUNCTION_DECL
&& DECL_ANTICIPATED (oldval))
oldval = NULL_TREE;
scope. */
if (tmp1)
continue;
-
+
/* If we are adding to an existing OVERLOAD, then we no
longer know the type of the set of functions. */
if (*newval && TREE_CODE (*newval) == OVERLOAD)
OVL_USED (*newval) = 1;
}
}
- else
+ else
{
*newval = decls.value;
if (oldval && !decls_match (*newval, oldval))
term = OVL_FUNCTION (oldval);
else
term = oldval;
- for (fn = newval; fn && OVL_CURRENT (fn) != term;
+ for (fn = newval; fn && OVL_CURRENT (fn) != term;
fn = OVL_NEXT (fn))
- push_overloaded_decl (OVL_CURRENT (fn),
+ push_overloaded_decl (OVL_CURRENT (fn),
PUSH_LOCAL | PUSH_USING);
}
else
|| CLASS_TYPE_P (root)));
gcc_assert ((TREE_CODE (child) == NAMESPACE_DECL
|| CLASS_TYPE_P (child)));
-
+
/* The global namespace encloses everything. */
if (root == global_namespace)
return true;
pushing name into scope. In case a template parameter scope is present,
namespace is pushed under the template parameter scope according to
name lookup rule in 14.6.1/6.
-
+
Return the former current scope suitable for pop_inner_scope. */
tree
;
else if (value_binding)
{
- if (TREE_CODE (value_binding) == TREE_LIST
+ if (TREE_CODE (value_binding) == TREE_LIST
&& TREE_TYPE (value_binding) == error_mark_node)
/* NAME is ambiguous. */
;
new binding object. */
if (type_binding || value_binding)
{
- binding = new_class_binding (name,
- value_binding,
+ binding = new_class_binding (name,
+ value_binding,
type_binding,
scope);
/* This is a class-scope binding, not a block-scope binding. */
return binding;
}
-
+
/* Make the declaration(s) of X appear in CLASS scope under the name
NAME. Returns true if the binding is valid. */
/* We could have been passed a tree list if this is an ambiguous
declaration. If so, pull the declaration out because
check_template_shadow will not handle a TREE_LIST. */
- if (TREE_CODE (decl) == TREE_LIST
+ if (TREE_CODE (decl) == TREE_LIST
&& TREE_TYPE (decl) == error_mark_node)
decl = TREE_VALUE (decl);
tree value, decl, binfo;
base_kind b_kind;
bool dependent_p;
-
+
if (!scope || !TYPE_P (scope))
{
error ("using-declaration for non-member at class scope");
else
b_kind = bk_proper_base;
}
-
+
if (b_kind < bk_proper_base)
{
error_not_base_type (scope, current_class_type);
return NULL_TREE;
}
-
+
/* Make sure the name is not invalid */
if (TREE_CODE (name) == BIT_NOT_EXPR)
{
if (!dependent_p)
{
decl = lookup_member (binfo, name, 0, false);
-
+
if (!decl)
{
error ("no members matching %<%T::%D%> in %q#T", scope, name, scope);
set_decl_namespace (tree decl, tree scope, bool friendp)
{
tree old;
-
+
/* Get rid of namespace aliases. */
scope = ORIGINAL_NAMESPACE (scope);
-
+
/* It is ok for friends to be qualified in parallel space. */
if (!friendp && !is_ancestor (current_namespace, scope))
error ("declaration of %qD not in a namespace surrounding %qD",
decl, scope);
DECL_CONTEXT (decl) = FROB_CONTEXT (scope);
- /* Writing "int N::i" to declare a variable within "N" is invalid. */
- if (scope == current_namespace)
+ /* Writing "int N::i" to declare a variable within "N" is invalid. */
+ if (scope == current_namespace)
{
if (at_namespace_scope_p ())
error ("explicit qualification in declaration of `%D'",
return;
complain:
error ("%qD should have been declared inside %qD", decl, scope);
-}
+}
/* Return the namespace where the current declaration is declared. */
result = decl_namespace_context (current_class_type);
else if (current_function_decl)
result = decl_namespace_context (current_function_decl);
- else
+ else
result = current_namespace;
return result;
}
bool anon = !name;
timevar_push (TV_NAME_LOOKUP);
-
+
/* We should not get here if the global_namespace is not yet constructed
nor if NAME designates the global namespace: The global scope is
constructed elsewhere. */
decl_namespace_list = TREE_CHAIN (decl_namespace_list);
}
-/* Return the namespace that is the common ancestor
+/* Return the namespace that is the common ancestor
of two given namespaces. */
static tree
namespace = ORIGINAL_NAMESPACE (namespace);
/* Build the alias. */
- alias = build_lang_decl (NAMESPACE_DECL, alias, void_type_node);
+ alias = build_lang_decl (NAMESPACE_DECL, alias, void_type_node);
DECL_NAMESPACE_ALIAS (alias) = namespace;
DECL_EXTERNAL (alias) = 1;
DECL_CONTEXT (alias) = FROB_CONTEXT (current_scope ());
/* Insert USED into the using list of USER. Set INDIRECT_flag if this
directive is not directly from the source. Also find the common
ancestor and let our users know about the new namespace */
-static void
+static void
add_using_namespace (tree user, tree used, bool indirect)
{
tree t;
}
/* Add used to the user's using list. */
- DECL_NAMESPACE_USING (user)
- = tree_cons (used, namespace_ancestor (user, used),
+ DECL_NAMESPACE_USING (user)
+ = tree_cons (used, namespace_ancestor (user, used),
DECL_NAMESPACE_USING (user));
TREE_INDIRECT_USING (DECL_NAMESPACE_USING (user)) = indirect;
decl = validate_nonmember_using_decl (decl, scope, name);
if (decl == NULL_TREE)
return;
-
+
binding = binding_for_name (NAMESPACE_LEVEL (current_namespace), name);
oldval = binding->value;
if (building_stmt_tree ())
add_stmt (build_stmt (USING_STMT, namespace));
-
+
/* using namespace A::B::C; */
if (TREE_CODE (namespace) == SCOPE_REF)
namespace = TREE_OPERAND (namespace, 1);
if (current_namespace != global_namespace)
context = current_namespace;
}
-
+
/* Emit debugging info. */
if (!processing_template_decl)
(*debug_hooks->imported_module_or_decl) (namespace, context);
need to add it again. For `extern "C"' functions, we
might have two FUNCTION_DECLs for the same function, in
different namespaces; again, we only need one of them. */
- if (fn1 == fn2
+ if (fn1 == fn2
|| (DECL_EXTERN_C_P (fn1) && DECL_EXTERN_C_P (fn2)
&& DECL_NAME (fn1) == DECL_NAME (fn2)))
break;
}
-
+
/* If we exhausted all of the functions in S1, FN2 is new. */
if (!fns1)
s1 = build_overload (fn2, s1);
if (LOOKUP_QUALIFIERS_ONLY (flags))
val = NULL_TREE;
}
-
+
if (!old->value)
old->value = val;
else if (val && val != old->value)
return true;
}
-/* Given a lookup that returned VAL, decide if we want to ignore it or
+/* Given a lookup that returned VAL, decide if we want to ignore it or
not based on DECL_ANTICIPATED_P. */
bool
if (binding->type && (!val || (flags & LOOKUP_PREFER_TYPES)))
val = binding->type;
/* Don't return non-types if we really prefer types. */
- else if (val && LOOKUP_TYPES_ONLY (flags)
+ else if (val && LOOKUP_TYPES_ONLY (flags)
&& ! DECL_DECLARES_TYPE_P (val))
val = NULL_TREE;
/* Look up NAME (an IDENTIFIER_NODE) in SCOPE (either a NAMESPACE_DECL
or a class TYPE). If IS_TYPE_P is TRUE, then ignore non-type
- bindings.
+ bindings.
Returns a DECL (or OVERLOAD, or BASELINK) representing the
declaration found. If no suitable declaration can be found,
CLASS_P is false, then class bindings are ignored. */
cxx_binding *
-outer_binding (tree name,
+outer_binding (tree name,
cxx_binding *binding,
bool class_p)
{
if (class_p)
while (scope && scope != outer_scope && scope->kind != sk_namespace)
{
- if (scope->kind == sk_class)
+ if (scope->kind == sk_class)
{
cxx_binding *class_binding;
-
+
class_binding = get_class_binding (name, scope);
if (class_binding)
{
/* Conversion operators are handled specially because ordinary
unqualified name lookup will not find template conversion
operators. */
- if (IDENTIFIER_TYPENAME_P (name))
+ if (IDENTIFIER_TYPENAME_P (name))
{
struct cp_binding_level *level;
- for (level = current_binding_level;
+ for (level = current_binding_level;
level && level->kind != sk_namespace;
level = level->level_chain)
{
tree class_type;
tree operators;
-
- /* A conversion operator can only be declared in a class
+
+ /* A conversion operator can only be declared in a class
scope. */
if (level->kind != sk_class)
continue;
-
+
/* Lookup the conversion operator in the class. */
class_type = level->this_entity;
operators = lookup_fnfields (class_type, name, /*protect=*/0);
iter = outer_binding (name, iter, !nonclass))
{
tree binding;
-
+
/* Skip entities we don't want. */
if (LOCAL_BINDING_P (iter) ? !block_p : nonclass)
continue;
-
+
/* If this is the kind of thing we're looking for, we're done. */
if (qualify_lookup (iter->value, flags)
&& !hidden_name_p (iter->value))
binding = iter->type;
else
binding = NULL_TREE;
-
+
if (binding)
{
val = binding;
tree
lookup_function_nonclass (tree name, tree args, bool block_p)
{
- return
- lookup_arg_dependent (name,
- lookup_name_real (name, 0, 1, block_p, 0,
+ return
+ lookup_arg_dependent (name,
+ lookup_name_real (name, 0, 1, block_p, 0,
LOOKUP_COMPLAIN),
args);
}
tree
lookup_name (tree name, int prefer_type)
{
- return lookup_name_real (name, prefer_type, 0, /*block_p=*/true,
+ return lookup_name_real (name, prefer_type, 0, /*block_p=*/true,
0, LOOKUP_COMPLAIN);
}
Unlike lookup_name_real, we make sure that NAME is actually
declared in the desired scope, not from inheritance, nor using
directive. For using declaration, there is DR138 still waiting
- to be resolved. Hidden name coming from earlier an friend
+ to be resolved. Hidden name coming from earlier an friend
declaration is also returned.
A TYPE_DECL best matching the NAME is returned. Catching error
for (; iter; iter = outer_binding (name, iter, /*class_p=*/ true))
{
/* Check if this is the kind of thing we're looking for.
- If SCOPE is TS_CURRENT, also make sure it doesn't come from
+ If SCOPE is TS_CURRENT, also make sure it doesn't come from
base class. For ITER->VALUE, we can simply use
- INHERITED_VALUE_BINDING_P. For ITER->TYPE, we have to use
+ INHERITED_VALUE_BINDING_P. For ITER->TYPE, we have to use
our own check.
We check ITER->TYPE before ITER->VALUE in order to handle
else if (qualify_lookup (iter->value, LOOKUP_PREFER_TYPES))
val = iter->value;
}
-
+
}
/* Type found, check if it is in the allowed scopes, ignoring cleanup
case. */
/* We must find only functions, or exactly one non-function. */
- if (!k->functions)
+ if (!k->functions)
k->functions = fn;
else if (fn == k->functions)
;
value = TREE_CHAIN (value))
if (arg_assoc_namespace (k, TREE_PURPOSE (value)))
return true;
-
+
value = namespace_binding (k->name, scope);
if (!value)
return false;
for (; value; value = OVL_NEXT (value))
if (add_function (k, OVL_CURRENT (value)))
return true;
-
+
return false;
}
if (TREE_CODE (ctx) == NAMESPACE_DECL)
return arg_assoc_namespace (k, ctx);
/* Otherwise, it must be member template. */
- else
+ else
return arg_assoc_class (k, ctx);
}
/* It's not a template template argument, but it is a type template
{
tree list, friends, context;
int i;
-
+
/* Backend build structures, such as __builtin_va_list, aren't
affected by all this. */
if (!CLASS_TYPE_P (type))
if (purpose_member (type, k->classes))
return false;
k->classes = tree_cons (type, NULL_TREE, k->classes);
-
+
context = decl_namespace_context (type);
if (arg_assoc_namespace (k, context))
return true;
{
/* Process baseclasses. */
tree binfo, base_binfo;
-
+
for (binfo = TYPE_BINFO (type), i = 0;
BINFO_BASE_ITERATE (binfo, i, base_binfo); i++)
if (arg_assoc_class (k, BINFO_TYPE (base_binfo)))
return true;
}
-
+
/* Process friends. */
- for (list = DECL_FRIENDLIST (TYPE_MAIN_DECL (type)); list;
+ for (list = DECL_FRIENDLIST (TYPE_MAIN_DECL (type)); list;
list = TREE_CHAIN (list))
if (k->name == FRIEND_NAME (list))
- for (friends = FRIEND_DECLS (list); friends;
+ for (friends = FRIEND_DECLS (list); friends;
friends = TREE_CHAIN (friends))
{
tree fn = TREE_VALUE (friends);
}
/* Process template arguments. */
- if (CLASSTYPE_TEMPLATE_INFO (type)
+ if (CLASSTYPE_TEMPLATE_INFO (type)
&& PRIMARY_TEMPLATE_P (CLASSTYPE_TI_TEMPLATE (type)))
{
list = INNERMOST_TEMPLATE_ARGS (CLASSTYPE_TI_ARGS (type));
- for (i = 0; i < TREE_VEC_LENGTH (list); ++i)
+ for (i = 0; i < TREE_VEC_LENGTH (list); ++i)
arg_assoc_template_arg (k, TREE_VEC_ELT (list, i));
}
if (TREE_CODE (template) == COMPONENT_REF)
template = TREE_OPERAND (template, 1);
-
+
/* First, the template. There may actually be more than one if
this is an overloaded function template. But, in that case,
we only need the first; all the functions will be in the same
template = OVL_CURRENT (template);
ctx = CP_DECL_CONTEXT (template);
-
+
if (TREE_CODE (ctx) == NAMESPACE_DECL)
{
if (arg_assoc_namespace (k, ctx) == 1)
should be visible during argument-dependent lookup. */
if (fns)
fn = OVL_CURRENT (fns);
- if (fn && TREE_CODE (fn) == FUNCTION_DECL
+ if (fn && TREE_CODE (fn) == FUNCTION_DECL
&& (CP_DECL_CONTEXT (fn) != current_decl_namespace ()
|| DECL_LOCAL_FUNCTION_P (fn)))
k.namespaces = NULL_TREE;
context = current_namespace;
if (b->kind == sk_class
- || (b->kind == sk_template_parms
+ || (b->kind == sk_template_parms
&& b->level_chain->kind == sk_class))
in_class = 1;
if (IDENTIFIER_MARKED (id))
return;
-
+
IDENTIFIER_MARKED (id) = 1;
saved = VEC_safe_push (cxx_saved_binding, gc, *old_bindings, NULL);
objects, rather than a TREE_LIST. */
static void
-store_class_bindings (VEC(cp_class_binding,gc) *names,
+store_class_bindings (VEC(cp_class_binding,gc) *names,
VEC(cxx_saved_binding,gc) **old_bindings)
{
size_t i;
cxx_saved_binding *saved;
size_t i;
- timevar_push (TV_NAME_LOOKUP);
+ timevar_push (TV_NAME_LOOKUP);
/* Clear out class-level bindings cache. */
if (previous_class_level)
invalidate_class_lookup_cache ();
}
/* Emit debugging information for using declarations and directives.
- If input tree is overloaded fn then emit debug info for all
+ If input tree is overloaded fn then emit debug info for all
candidates. */
void
cp_emit_debug_info_for_using (tree t, tree context)
{
- /* Ignore this FUNCTION_DECL if it refers to a builtin declaration
+ /* Ignore this FUNCTION_DECL if it refers to a builtin declaration
of a builtin function. */
- if (TREE_CODE (t) == FUNCTION_DECL
+ if (TREE_CODE (t) == FUNCTION_DECL
&& DECL_EXTERNAL (t)
&& DECL_BUILT_IN (t))
return;
it is a global namespace. */
if (context == global_namespace)
context = NULL_TREE;
-
+
if (BASELINK_P (t))
t = BASELINK_FUNCTIONS (t);
-
+
/* FIXME: Handle TEMPLATE_DECLs. */
for (t = OVL_CURRENT (t); t; t = OVL_NEXT (t))
if (TREE_CODE (t) != TEMPLATE_DECL)
VEC(tree,gc) *static_decls;
/* A chain of VTABLE_DECL nodes. */
- tree vtables;
+ tree vtables;
/* A list of USING_DECL nodes. */
tree usings;
/* -*-C-*-
-
+
This file contains definitions of the various C++ operators,
including both overloadable operators (like `+') and
- non-overloadable operators (like the `?:' ternary operator).
+ non-overloadable operators (like the `?:' ternary operator).
Written by Mark Mitchell <mark@codesourcery.com>
Copyright (C) 2000, 2001, 2002, 2003, 2005 Free Software Foundation, Inc.
preceding `operator'. This is the name that would be given in
the source program. For `operator +', for example, this would be
`+'.
-
+
CODE
The tree_code for this operator. For `operator +', for example,
would be "pl".
ARITY
-
+
The arity of the operator, or -1 if any arity is allowed. (As
for `operator ()'.) Postincrement and postdecrement operators
are marked as binary.
A boolean value. If nonzero, this is an assignment operator.
Before including this file, you should define DEFOPERATOR
- to take these arguments.
+ to take these arguments.
There is code (such as in grok_op_properties) that depends on the
order the operators are presented in this file. In particular,
unary operators must precede binary operators. */
-
+
/* Use DEF_SIMPLE_OPERATOR to define a non-assignment operator. Its
arguments are as for DEF_OPERATOR, but there is no need to provide
an ASSIGNMENT_P argument; it is always zero. */
/* The definition might have different constness. */
TREE_READONLY (cloned_parm) = TREE_READONLY (parm);
-
+
TREE_USED (cloned_parm) = TREE_USED (parm);
-
+
/* The name may have changed from the declaration. */
DECL_NAME (cloned_parm) = DECL_NAME (parm);
DECL_SOURCE_LOCATION (cloned_parm) = DECL_SOURCE_LOCATION (parm);
/* If the lexer owns the buffer, this is the number of tokens in the
buffer. */
size_t buffer_length;
-
+
/* A pointer just past the last available token. The tokens
in this lexer are [buffer, last_token). */
cp_token_position GTY ((skip)) last_token;
/* Allocate the memory. */
lexer = GGC_CNEW (cp_lexer);
-#ifdef ENABLE_CHECKING
+#ifdef ENABLE_CHECKING
/* Initially we are not debugging. */
lexer->debugging_p = false;
#endif /* ENABLE_CHECKING */
lexer->saved_tokens = VEC_alloc (cp_token_position, heap,
CP_SAVED_TOKEN_STACK);
-
+
/* Create the buffer. */
alloc = CP_LEXER_BUFFER_SIZE;
buffer = ggc_alloc (alloc * sizeof (cp_token));
space = alloc;
pos = buffer;
*pos = first_token;
-
+
/* Get the remaining tokens from the preprocessor. */
while (pos->type != CPP_EOF)
{
lexer->buffer_length = 0;
lexer->next_token = first == last ? (cp_token *)&eof_token : first;
lexer->last_token = last;
-
+
lexer->saved_tokens = VEC_alloc (cp_token_position, heap,
CP_SAVED_TOKEN_STACK);
cp_lexer_token_position (cp_lexer *lexer, bool previous_p)
{
gcc_assert (!previous_p || lexer->next_token != &eof_token);
-
+
return lexer->next_token - previous_p;
}
= c_lex_with_flags (&token->value, &token->location, &token->flags);
token->in_system_header = in_system_header;
- /* On some systems, some header files are surrounded by an
+ /* On some systems, some header files are surrounded by an
implicit extern "C" block. Set a flag in the token if it
comes from such a header. */
is_extern_c += pending_lang_change;
token = (cp_token *)&eof_token;
break;
}
-
+
if (token->type != CPP_PURGED)
--n;
}
cp_token *token = lexer->next_token;
gcc_assert (token != &eof_token);
-
+
do
{
lexer->next_token++;
lexer->next_token = (cp_token *)&eof_token;
break;
}
-
+
}
while (lexer->next_token->type == CPP_PURGED);
-
+
cp_lexer_set_source_position_from_token (token);
-
+
/* Provide debugging output. */
if (cp_lexer_debugging_p (lexer))
{
cp_lexer_print_token (cp_lexer_debug_stream, token);
putc ('\n', cp_lexer_debug_stream);
}
-
+
return token;
}
cp_lexer_purge_token (cp_lexer *lexer)
{
cp_token *tok = lexer->next_token;
-
+
gcc_assert (tok != &eof_token);
tok->type = CPP_PURGED;
tok->location = UNKNOWN_LOCATION;
if (peek == &eof_token)
peek = lexer->last_token;
-
+
gcc_assert (tok < peek);
for ( tok += 1; tok != peek; tok += 1)
"NESTED_NAME_SPECIFIER",
"PURGED"
};
-
+
/* If we have a name for the token, print it out. Otherwise, we
simply give the numeric code. */
gcc_assert (token->type < ARRAY_SIZE(token_names));
(cp_parser *);
static tree cp_parser_objc_encode_expression
(cp_parser *);
-static tree cp_parser_objc_defs_expression
+static tree cp_parser_objc_defs_expression
(cp_parser *);
static tree cp_parser_objc_protocol_expression
(cp_parser *);
cp_lexer_set_source_position_from_token (token);
if (token->type == CPP_PRAGMA)
{
- error ("%<#pragma%> is not allowed here");
+ error ("%<#pragma%> is not allowed here");
cp_lexer_purge_token (parser->lexer);
return;
}
parser->scope, name);
else if (parser->scope == global_namespace)
error ("%<::%D%> has not been declared", name);
- else if (parser->object_scope
+ else if (parser->object_scope
&& !CLASS_TYPE_P (parser->object_scope))
error ("request for member %qD in non-class type %qT",
name, parser->object_scope);
else if (parser->object_scope)
- error ("%<%T::%D%> has not been declared",
+ error ("%<%T::%D%> has not been declared",
parser->object_scope, name);
else
error ("%qD has not been declared", name);
/* If parsing an integral constant-expression, issue an error message
about the fact that THING appeared and return true. Otherwise,
return false. In either case, set
- PARSER->NON_INTEGRAL_CONSTANT_EXPRESSION_P. */
+ PARSER->NON_INTEGRAL_CONSTANT_EXPRESSION_P. */
static bool
cp_parser_non_integral_constant_expression (cp_parser *parser,
while (nesting_depth >= 0)
{
cp_token *token = cp_lexer_peek_token (parser->lexer);
-
+
if (token->type == CPP_EOF)
break;
if (!nesting_depth)
nesting_depth = -1;
break;
-
+
case CPP_OPEN_BRACE:
/* Nest. */
nesting_depth++;
default:
break;
}
-
+
/* Consume the token. */
cp_lexer_consume_token (parser->lexer);
-
+
}
}
checked at that point. If we are not within a cast, then
this code is invalid. */
if (!cast_p)
- cp_parser_non_integral_constant_expression
+ cp_parser_non_integral_constant_expression
(parser, "floating-point literal");
}
return token->value;
/* Anything else is an error. */
default:
/* ...unless we have an Objective-C++ message or string literal, that is. */
- if (c_dialect_objc ()
+ if (c_dialect_objc ()
&& (token->type == CPP_OPEN_SQUARE || token->type == CPP_OBJC_STRING))
return cp_parser_objc_expression (parser);
look up names in "X<T>::I" in order to determine that "Y" is
a template. So, if we have a typename at this point, we make
an effort to look through it. */
- if (is_declaration
+ if (is_declaration
&& !typename_keyword_p
- && parser->scope
+ && parser->scope
&& TREE_CODE (parser->scope) == TYPENAME_TYPE)
- parser->scope = resolve_typename_type (parser->scope,
+ parser->scope = resolve_typename_type (parser->scope,
/*only_current_p=*/false);
/* Parse the qualifying entity. */
new_scope
if (success && start)
{
cp_token *token = cp_lexer_token_at (parser->lexer, start);
-
+
/* Reset the contents of the START token. */
token->type = CPP_NESTED_NAME_SPECIFIER;
token->value = build_tree_list (access_check, parser->scope);
TREE_TYPE (token->value) = parser->qualifying_scope;
token->keyword = RID_MAX;
-
+
/* Purge all subsequent tokens. */
cp_lexer_purge_tokens_after (parser->lexer, start);
}
If ADDRESS_P is true, the postfix expression is the operand of the
`&' operator. CAST_P is true if this expression is the target of a
- cast.
+ cast.
Returns a representation of the expression. */
bool saved_non_integral_constant_expression_p = false;
tree args;
- is_builtin_constant_p
+ is_builtin_constant_p
= DECL_IS_BUILTIN_CONSTANT_P (postfix_expression);
if (is_builtin_constant_p)
{
parser->integral_constant_expression_p = false;
}
args = (cp_parser_parenthesized_expression_list
- (parser, /*is_attribute_list=*/false,
+ (parser, /*is_attribute_list=*/false,
/*cast_p=*/false,
/*non_constant_p=*/NULL));
if (is_builtin_constant_p)
token = cp_lexer_consume_token (parser->lexer);
/* Parse the cast-expression. */
cast_expression
- = cp_parser_cast_expression (parser,
+ = cp_parser_cast_expression (parser,
unary_operator == ADDR_EXPR,
/*cast_p=*/false);
/* Now, build an appropriate representation. */
*nelts = declarator->u.array.bounds;
if (*nelts == error_mark_node)
*nelts = integer_one_node;
-
+
if (outer_declarator)
outer_declarator->declarator = declarator->declarator;
else
ctor of T, but looks like a cast to function returning T
without a dependent expression. */
if (!cp_parser_error_occurred (parser))
- expr = cp_parser_cast_expression (parser,
+ expr = cp_parser_cast_expression (parser,
/*address_p=*/false,
/*cast_p=*/true);
relational-expression >= shift-expression
GNU Extension:
-
+
relational-expression:
relational-expression <? shift-expression
relational-expression >? shift-expression
- either we found a token which is not an operator (`>' where it is not
an operator, or prec == PREC_NOT_OPERATOR), in which case popping
will happen repeatedly;
- - or, we found an operator which has lower priority. This is the case
+ - or, we found an operator which has lower priority. This is the case
where the recursive descent *ascends*, as in `3 * 4 + 5' after
parsing `3 * 4'. */
if (new_prec <= prec)
pop:
/* If the stack is not empty, we have parsed into LHS the right side
(`4' in the example above) of an expression we had suspended.
- We can use the information on the stack to recover the LHS (`3')
+ We can use the information on the stack to recover the LHS (`3')
from the stack together with the tree code (`MULT_EXPR'), and
the precedence of the higher level subexpression
(`PREC_ADDITIVE_EXPRESSION'). TOKEN is the CPP_PLUS token,
least one of the operands is of enumeration type. */
if (overloaded_p
- && (cp_parser_non_integral_constant_expression
+ && (cp_parser_non_integral_constant_expression
(parser, "calls to overloaded operators")))
return error_mark_node;
}
constant. */
expression = cp_parser_assignment_expression (parser, /*cast_p=*/false);
/* Restore the old settings. */
- parser->integral_constant_expression_p
+ parser->integral_constant_expression_p
= saved_integral_constant_expression_p;
parser->allow_non_integral_constant_expression_p
= saved_allow_non_integral_constant_expression_p;
*non_constant_p = parser->non_integral_constant_expression_p;
else if (parser->non_integral_constant_expression_p)
expression = error_mark_node;
- parser->non_integral_constant_expression_p
+ parser->non_integral_constant_expression_p
= saved_non_integral_constant_expression_p;
return expression;
for sure. */
if (cp_parser_parse_definitely (parser))
{
- tree pushed_scope;
+ tree pushed_scope;
/* Create the declaration. */
decl = start_decl (declarator, &type_specifiers,
/* Give up. */
goto done;
}
-
+
/* If we have seen at least one decl-specifier, and the next token
is not a parenthesis, then we must be looking at a declaration.
(After "int (" we might be looking at a functional cast.) */
- if (decl_specifiers.any_specifiers_p
+ if (decl_specifiers.any_specifiers_p
&& cp_lexer_next_token_is_not (parser->lexer, CPP_OPEN_PAREN))
cp_parser_commit_to_tentative_parse (parser);
if (start_of_id)
{
cp_token *token = cp_lexer_token_at (parser->lexer, start_of_id);
-
+
/* Reset the contents of the START_OF_ID token. */
token->type = CPP_TEMPLATE_ID;
token->value = build_tree_list (access_check, template_id);
token->keyword = RID_MAX;
-
+
/* Purge all subsequent tokens. */
cp_lexer_purge_tokens_after (parser->lexer, start_of_id);
&& !constructor_name_p (identifier, parser->scope))
{
cp_token_position start = 0;
-
+
/* Explain what went wrong. */
error ("non-template %qD used as template", identifier);
inform ("use %<%T::template %D%> to indicate that it is a template",
gcc_assert (REFERENCE_REF_P (argument));
argument = TREE_OPERAND (argument, 0);
}
-
+
if (qualifying_class)
argument = finish_qualified_id_expr (qualifying_class,
argument,
}
cp_parser_check_for_invalid_template_id (parser, TREE_TYPE (type));
- }
+ }
return type;
}
/* See if this is an Objective-C type. */
tree protos = cp_parser_objc_protocol_refs_opt (parser);
tree type = objc_get_protocol_qualified_type (identifier, protos);
- if (type)
+ if (type)
type_decl = TYPE_NAME (type);
}
}
/* For a `typename', we needn't call xref_tag. */
- if (tag_type == typename_type
+ if (tag_type == typename_type
&& TREE_CODE (parser->scope) != NAMESPACE_DECL)
return cp_parser_make_typename_type (parser, parser->scope,
identifier);
if (TREE_CODE (decl) != TYPE_DECL)
{
- cp_parser_diagnose_invalid_type_name (parser,
+ cp_parser_diagnose_invalid_type_name (parser,
parser->scope,
identifier);
return error_mark_node;
tree temp = asm_stmt;
if (TREE_CODE (temp) == CLEANUP_POINT_EXPR)
temp = TREE_OPERAND (temp, 0);
-
+
ASM_INPUT_P (temp) = 1;
}
}
expression, not a declaration.)
If PARENTHESIZED_P is non-NULL, *PARENTHESIZED_P is set to true iff
- the declarator is a direct-declarator of the form "(...)".
+ the declarator is a direct-declarator of the form "(...)".
MEMBER_P is true iff this declarator is a member-declarator. */
bounds = fold_non_dependent_expr (bounds);
/* Normally, the array bound must be an integral constant
expression. However, as an extension, we allow VLAs
- in function scopes. */
+ in function scopes. */
else if (!at_function_scope_p ())
{
error ("array bound is not an integer constant");
if (!cp_parser_parse_definitely (parser))
unqualified_name = error_mark_node;
else if (qualifying_scope
- || (TREE_CODE (unqualified_name)
+ || (TREE_CODE (unqualified_name)
!= IDENTIFIER_NODE))
{
cp_parser_error (parser, "expected unqualified-id");
specialized, then this `i' will not be used, so there
is no harm in resolving the types here. */
tree type;
-
+
/* Resolve the TYPENAME_TYPE. */
type = resolve_typename_type (qualifying_scope,
/*only_current_p=*/false);
qualifying_scope = type;
}
- declarator = make_id_declarator (qualifying_scope,
+ declarator = make_id_declarator (qualifying_scope,
unqualified_name);
declarator->id_loc = token->location;
if (unqualified_name)
&& (constructor_name_p (unqualified_name,
class_type)
|| (TREE_CODE (unqualified_name) == TYPE_DECL
- && (same_type_p
+ && (same_type_p
(TREE_TYPE (unqualified_name),
class_type)))))
declarator->u.id.sfk = sfk_constructor;
/* The standard says that a condition can be:
type-specifier-seq declarator = assignment-expression
-
+
However, given:
struct S {};
then add a semantic restriction that if any decl-specifiers
that are not type-specifiers appear, the program is invalid. */
if (is_condition && !is_cv_qualifier)
- flags |= CP_PARSER_FLAGS_NO_USER_DEFINED_TYPES;
+ flags |= CP_PARSER_FLAGS_NO_USER_DEFINED_TYPES;
}
return;
= parser->local_variables_forbidden_p;
parser->local_variables_forbidden_p = true;
/* Parse the assignment-expression. */
- default_argument
+ default_argument
= cp_parser_assignment_expression (parser, /*cast_p=*/false);
/* Restore saved state. */
parser->greater_than_is_operator_p
involving a nested-name-specifier was used, and FALSE otherwise.
Returns error_mark_node if this is not a class-head.
-
+
Returns NULL_TREE if the class-head is syntactically valid, but
semantically invalid in a way that means we should skip the entire
body of the class. */
goto done;
}
}
-
+
type = TREE_TYPE (type);
*nested_name_specifier_p = true;
}
token = cp_lexer_consume_token (parser->lexer);
/* Save away the identifier that indicates which attribute
- this is. */
+ this is. */
identifier = token->value;
attribute = build_tree_list (identifier, NULL_TREE);
tree arguments;
arguments = (cp_parser_parenthesized_expression_list
- (parser, true, /*cast_p=*/false,
+ (parser, true, /*cast_p=*/false,
/*non_constant_p=*/NULL));
/* Save the identifier and arguments away. */
TREE_VALUE (attribute) = arguments;
are ignored.
If CHECK_DEPENDENCY is TRUE, names are not looked up in dependent
- types.
+ types.
If AMBIGUOUS_P is non-NULL, it is set to true if name-lookup
results in an ambiguity, and false otherwise. */
may be instantiated during name lookup. In that case,
errors may be issued. Even if we rollback the current
tentative parse, those errors are valid. */
- decl = lookup_qualified_name (parser->scope, name,
- tag_type != none_type,
+ decl = lookup_qualified_name (parser->scope, name,
+ tag_type != none_type,
/*complain=*/true);
if (pushed_scope)
pop_scope (pushed_scope);
parse, those errors are valid. */
object_decl = lookup_member (object_type,
name,
- /*protect=*/0,
+ /*protect=*/0,
tag_type != none_type);
/* Look it up in the enclosing context, too. */
- decl = lookup_name_real (name, tag_type != none_type,
+ decl = lookup_name_real (name, tag_type != none_type,
/*nonclass=*/0,
/*block_p=*/true, is_namespace,
/*flags=*/0);
}
else
{
- decl = lookup_name_real (name, tag_type != none_type,
+ decl = lookup_name_real (name, tag_type != none_type,
/*nonclass=*/0,
/*block_p=*/true, is_namespace,
/*flags=*/0);
scope = TYPE_CONTEXT (scope);
}
}
- else if (TREE_CODE (declarator->u.id.unqualified_name)
+ else if (TREE_CODE (declarator->u.id.unqualified_name)
== TEMPLATE_ID_EXPR)
/* If the DECLARATOR has the form `X<y>' then it uses one
additional level of template parameters. */
tokens = DECL_PENDING_INLINE_INFO (member_function);
DECL_PENDING_INLINE_INFO (member_function) = NULL;
DECL_PENDING_INLINE_P (member_function) = 0;
-
+
/* If this is a local class, enter the scope of the containing
function. */
function_scope = current_function_decl;
if (function_scope)
push_function_context_to (function_scope);
-
+
/* Push the body of the function onto the lexer stack. */
cp_parser_push_lexer_for_tokens (parser, tokens);
/* Don't do access checking if it is a templated function. */
if (processing_template_decl)
push_deferring_access_checks (dk_no_check);
-
+
/* Now, parse the body of the function. */
cp_parser_function_definition_after_declarator (parser,
/*inline_p=*/true);
if (processing_template_decl)
pop_deferring_access_checks ();
-
+
/* Leave the scope of the containing function. */
if (function_scope)
pop_function_context_from (function_scope);
VEC(tree,gc) *insts;
tree copy;
unsigned ix;
-
+
if (!default_arg)
continue;
/* The restrictions on constant-expressions do not apply inside
sizeof expressions. */
- saved_integral_constant_expression_p
+ saved_integral_constant_expression_p
= parser->integral_constant_expression_p;
saved_non_integral_constant_expression_p
= parser->non_integral_constant_expression_p;
free ((char *) parser->type_definition_forbidden_message);
/* And restore the old one. */
parser->type_definition_forbidden_message = saved_message;
- parser->integral_constant_expression_p
+ parser->integral_constant_expression_p
= saved_integral_constant_expression_p;
parser->non_integral_constant_expression_p
= saved_non_integral_constant_expression_p;
objc-encode-expression:
@encode objc-typename
-
+
Returns an encoded representation of the type argument. */
static tree
while (sep->type == CPP_COMMA)
{
cp_lexer_consume_token (parser->lexer); /* Eat ','. */
- list = chainon (list,
+ list = chainon (list,
build_tree_list (NULL_TREE,
cp_parser_identifier (parser)));
sep = cp_lexer_peek_token (parser->lexer);
}
-
+
return list;
}
cp_parser_objc_selector (cp_parser* parser)
{
cp_token *token = cp_lexer_consume_token (parser->lexer);
-
+
if (!cp_parser_objc_selector_p (token->type))
{
error ("invalid Objective-C++ selector name");
params
= chainon (params,
- objc_build_keyword_decl (selector,
+ objc_build_keyword_decl (selector,
typename,
identifier));
parmdecl = cp_parser_parameter_declaration (parser, false, NULL);
parm = grokdeclarator (parmdecl->declarator,
&parmdecl->decl_specifiers,
- PARM, /*initialized=*/0,
+ PARM, /*initialized=*/0,
/*attrlist=*/NULL);
chainon (params, build_tree_list (NULL_TREE, parm));
else
{
/* Parse the declarator. */
- declarator
+ declarator
= cp_parser_declarator (parser, CP_PARSER_DECLARATOR_NAMED,
&ctor_dtor_or_conv_p,
/*parenthesized_p=*/NULL,
else
decl = grokfield (declarator, &declspecs, NULL_TREE,
NULL_TREE, attributes);
-
+
/* Add the instance variable. */
objc_add_instance_variable (decl);
/* See if we have a forward declaration or a definition. */
tok = cp_lexer_peek_nth_token (parser->lexer, 2);
-
+
/* Try a forward declaration first. */
if (tok->type == CPP_COMMA || tok->type == CPP_SEMICOLON)
{
objc_declare_protocols (cp_parser_objc_identifier_list (parser));
- finish:
+ finish:
cp_parser_consume_semicolon_at_end_of_statement (parser);
- }
+ }
/* Ok, we got a full-fledged definition (or at least should). */
else
stmt = push_stmt_list ();
cp_parser_compound_statement (parser, NULL, false);
objc_begin_try_stmt (location, pop_stmt_list (stmt));
-
+
while (cp_lexer_next_token_is_keyword (parser->lexer, RID_AT_CATCH))
{
cp_parameter_declarator *parmdecl;
parmdecl = cp_parser_parameter_declaration (parser, false, NULL);
parm = grokdeclarator (parmdecl->declarator,
&parmdecl->decl_specifiers,
- PARM, /*initialized=*/0,
+ PARM, /*initialized=*/0,
/*attrlist=*/NULL);
cp_parser_require (parser, CPP_CLOSE_PAREN, "`)'");
objc_begin_catch_clause (parm);
static tree add_to_template_args (tree, tree);
static tree add_outermost_template_args (tree, tree);
static bool check_instantiated_args (tree, tree, tsubst_flags_t);
-static int maybe_adjust_types_for_deduction (unification_kind_t, tree*, tree*);
+static int maybe_adjust_types_for_deduction (unification_kind_t, tree*, tree*);
static int type_unification_real (tree, tree, tree, tree,
int, unification_kind_t, int);
static void note_template_header (int);
push_nested_class (DECL_CONTEXT (t));
else
push_to_top_level ();
-
+
if (TREE_CODE (t) == FUNCTION_DECL)
{
saved_access_scope = tree_cons
tree type;
type = TREE_TYPE (decl);
- if (IS_AGGR_TYPE (type)
+ if (IS_AGGR_TYPE (type)
&& CLASSTYPE_TEMPLATE_INFO (type)
&& !CLASSTYPE_TEMPLATE_SPECIALIZATION (type))
{
}
else
return decl;
- }
+ }
else
error ("invalid member template declaration %qD", decl);
}
/* Returns the template nesting level of the indicated class TYPE.
-
+
For example, in:
template <class T>
struct A
struct B {};
};
- A<T>::B<U> has depth two, while A<T> has depth one.
+ A<T>::B<U> has depth two, while A<T> has depth one.
Both A<T>::B<int> and A<int>::B<U> have depth one, if
COUNT_SPECIALIZATIONS is 0 or if they are instantiations, not
- specializations.
+ specializations.
This function is guaranteed to return 0 if passed NULL_TREE so
that, for example, `template_class_depth (current_class_type)' is
always safe. */
-static int
+static int
template_class_depth_real (tree type, int count_specializations)
{
int depth;
- for (depth = 0;
+ for (depth = 0;
type && TREE_CODE (type) != NAMESPACE_DECL;
- type = (TREE_CODE (type) == FUNCTION_DECL)
+ type = (TREE_CODE (type) == FUNCTION_DECL)
? CP_DECL_CONTEXT (type) : TYPE_CONTEXT (type))
{
if (TREE_CODE (type) != FUNCTION_DECL)
|| uses_template_parms (CLASSTYPE_TI_ARGS (type))))
++depth;
}
- else
+ else
{
if (DECL_TEMPLATE_INFO (type)
&& PRIMARY_TEMPLATE_P (DECL_TI_TEMPLATE (type))
Like template_class_depth_real, but instantiations do not count in
the depth. */
-int
+int
template_class_depth (tree type)
{
return template_class_depth_real (type, /*count_specializations=*/0);
begin_scope (TREE_VEC_LENGTH (parms) ? sk_template_parms : sk_template_spec,
NULL);
- for (i = 0; i < TREE_VEC_LENGTH (parms); ++i)
+ for (i = 0; i < TREE_VEC_LENGTH (parms); ++i)
{
tree parm = TREE_VALUE (TREE_VEC_ELT (parms, i));
gcc_assert (DECL_P (parm));
/* Undo the effects of maybe_begin_member_template_processing. */
-void
+void
maybe_end_member_template_processing (void)
{
int i;
return;
--inline_parm_levels_used;
- for (i = 0;
+ for (i = 0;
i < VARRAY_INT (inline_parm_levels, inline_parm_levels_used);
- ++i)
+ ++i)
{
--processing_template_decl;
current_template_parms = TREE_CHAIN (current_template_parms);
for (j = 1; j <= extra_depth; ++j, ++i)
SET_TMPL_ARGS_LEVEL (new_args, i, TMPL_ARGS_LEVEL (extra_args, j));
-
+
return new_args;
}
/* For the moment, we make ARGS look like it contains fewer levels. */
TREE_VEC_LENGTH (args) -= TMPL_ARGS_DEPTH (extra_args);
-
+
new_args = add_to_template_args (args, extra_args);
/* Now, we restore ARGS to its full dimensions. */
/* If N is 1, just return the innermost set of template arguments. */
if (n == 1)
return TMPL_ARGS_LEVEL (args, TMPL_ARGS_DEPTH (args));
-
+
/* If we're not removing anything, just return the arguments we were
given. */
extra_levels = TMPL_ARGS_DEPTH (args) - n;
/* Make a new set of arguments, not containing the outer arguments. */
new_args = make_tree_vec (n);
for (i = 1; i <= n; ++i)
- SET_TMPL_ARGS_LEVEL (new_args, i,
+ SET_TMPL_ARGS_LEVEL (new_args, i,
TMPL_ARGS_LEVEL (args, i + extra_levels));
return new_args;
e.g.:
template <class T> struct S1 {
- template <class T> struct S2 {};
+ template <class T> struct S2 {};
};
pushtag contains special code to call pushdecl_with_scope on the
{
tree scope = current_scope ();
- /* [temp.expl.spec]
-
+ /* [temp.expl.spec]
+
An explicit specialization shall be declared in the namespace of
which the template is a member, or, for member templates, in the
namespace of which the enclosing class or enclosing class
if (scope && TREE_CODE (scope) != NAMESPACE_DECL)
error ("explicit specialization in non-namespace scope %qD", scope);
- /* [temp.expl.spec]
+ /* [temp.expl.spec]
In an explicit specialization declaration for a member of a class
template or a member template that appears in namespace scope,
remain unspecialized, except that the declaration shall not
explicitly specialize a class member template if its enclosing
class templates are not explicitly specialized as well. */
- if (current_template_parms)
+ if (current_template_parms)
error ("enclosing class templates are not explicitly specialized");
}
/* Called at then end of processing a declaration preceded by
template<>. */
-void
+void
end_specialization (void)
{
finish_scope ();
/* We've just seen a template header. If SPECIALIZATION is nonzero,
it was of the form template <>. */
-static void
+static void
note_template_header (int specialization)
{
processing_specialization = specialization;
declared. Check that the namespace in which the specialization is
occurring is permissible. Returns false iff it is invalid to
specialize TMPL in the current namespace. */
-
+
static bool
check_specialization_namespace (tree tmpl)
{
tree tpl_ns = decl_namespace_context (tmpl);
/* [tmpl.expl.spec]
-
+
An explicit specialization shall be declared in the namespace of
which the template is a member, or, for member templates, in the
namespace of which the enclosing class or enclosing class
/* The TYPE is being declared. If it is a template type, that means it
is a partial specialization. Do appropriate error-checking. */
-void
+void
maybe_process_partial_specialization (tree type)
{
/* TYPE maybe an ERROR_MARK_NODE. */
for TMPL, a TEMPLATE_DECL. In particular, for such a template, we
do not use DECL_TEMPLATE_SPECIALIZATIONS at all. */
-static inline bool
+static inline bool
optimize_specialization_lookup_p (tree tmpl)
{
return (DECL_FUNCTION_TEMPLATE_P (tmpl)
&& !DECL_CONV_FN_P (tmpl)
/* It is possible to have a template that is not a member
template and is not a member of a template class:
-
- template <typename T>
+
+ template <typename T>
struct S { friend A::f(); };
-
+
Here, the friend function is a template, but the context does
not have template information. The optimized lookup relies
on having ARGS be the template arguments for both the class
specialization) of TMPL for the given template ARGS. If there is
no such specialization, return NULL_TREE. The ARGS are a vector of
arguments, or a vector of vectors of arguments, in the case of
- templates with more than one level of parameters.
+ templates with more than one level of parameters.
If TMPL is a type template and CLASS_SPECIALIZATIONS_P is true,
then we search for a partial specialization matching ARGS. This
parameter is ignored if TMPL is not a class template. */
-
+
static tree
-retrieve_specialization (tree tmpl, tree args,
+retrieve_specialization (tree tmpl, tree args,
bool class_specializations_p)
{
gcc_assert (TREE_CODE (tmpl) == TEMPLATE_DECL);
/* There should be as many levels of arguments as there are
levels of parameters. */
- gcc_assert (TMPL_ARGS_DEPTH (args)
+ gcc_assert (TMPL_ARGS_DEPTH (args)
== TMPL_PARMS_DEPTH (DECL_TEMPLATE_PARMS (tmpl)));
-
+
if (optimize_specialization_lookup_p (tmpl))
{
tree class_template;
class. Find the class specialization with those
arguments. */
class_template = CLASSTYPE_TI_TEMPLATE (DECL_CONTEXT (tmpl));
- class_specialization
+ class_specialization
= retrieve_specialization (class_template, args,
/*class_specializations_p=*/false);
if (!class_specialization)
while (*sp != NULL_TREE)
{
tree spec = *sp;
-
+
if (comp_template_args (TREE_PURPOSE (spec), args))
{
/* Use the move-to-front heuristic to speed up future
- searches. */
+ searches. */
if (spec != *head)
{
*sp = TREE_CHAIN (*sp);
if (TREE_CODE (decl) == FUNCTION_DECL)
{
- for (t = decl;
+ for (t = decl;
t != NULL_TREE;
t = DECL_TEMPLATE_INFO (t) ? DECL_TI_TEMPLATE (t) : NULL_TREE)
if (t == tmpl)
return 1;
}
- else
+ else
{
gcc_assert (TREE_CODE (decl) == TYPE_DECL);
? TREE_TYPE (CLASSTYPE_TI_TEMPLATE (t)) : NULL_TREE)
if (same_type_ignoring_top_level_qualifiers_p (t, TREE_TYPE (tmpl)))
return 1;
- }
+ }
return 0;
}
non-template class. In this case, the corresponding member of
every specialization of the class template is a friend of the
class granting friendship.
-
+
For example, given a template friend declaration
template <class T> friend void A<T>::f();
template_depth = template_class_depth (DECL_CONTEXT (friend));
if (template_depth
&& DECL_CLASS_SCOPE_P (decl)
- && is_specialization_of (TYPE_NAME (DECL_CONTEXT (decl)),
+ && is_specialization_of (TYPE_NAME (DECL_CONTEXT (decl)),
CLASSTYPE_TI_TEMPLATE (DECL_CONTEXT (friend))))
{
/* Next, we check the members themselves. In order to handle
gcc_assert (TREE_CODE (tmpl) == TEMPLATE_DECL);
- if (TREE_CODE (spec) == FUNCTION_DECL
+ if (TREE_CODE (spec) == FUNCTION_DECL
&& uses_template_parms (DECL_TI_ARGS (spec)))
/* This is the FUNCTION_DECL for a partial instantiation. Don't
register it; we want the corresponding TEMPLATE_DECL instead.
/* There should be as many levels of arguments as there are
levels of parameters. */
- gcc_assert (TMPL_ARGS_DEPTH (args)
+ gcc_assert (TMPL_ARGS_DEPTH (args)
== TMPL_PARMS_DEPTH (DECL_TEMPLATE_PARMS (tmpl)));
- fn = retrieve_specialization (tmpl, args,
+ fn = retrieve_specialization (tmpl, args,
/*class_specializations_p=*/false);
/* We can sometimes try to re-register a specialization that we've
already got. In particular, regenerate_decl_from_template calls
{
if (DECL_TEMPLATE_INSTANTIATION (fn))
{
- if (TREE_USED (fn)
+ if (TREE_USED (fn)
|| DECL_EXPLICIT_INSTANTIATION (fn))
{
error ("specialization of %qD after instantiation",
situation can occur if we have implicitly
instantiated a member function and then specialized
it later.
-
+
We can also wind up here if a friend declaration that
looked like an instantiation turns out to be a
specialization:
-
+
template <class T> void foo(T);
class S { friend void foo<>(int) };
- template <> void foo(int);
-
+ template <> void foo(int);
+
We transform the existing DECL in place so that any
pointers to it become pointers to the updated
declaration.
there were no definition, and vice versa. */
DECL_INITIAL (fn) = NULL_TREE;
duplicate_decls (spec, fn);
-
+
return fn;
}
}
line number so any errors match this new
definition. */
DECL_SOURCE_LOCATION (fn) = DECL_SOURCE_LOCATION (spec);
-
+
return fn;
}
}
{
void **slot;
- slot = htab_find_slot_with_hash (local_specializations, tmpl,
+ slot = htab_find_slot_with_hash (local_specializations, tmpl,
htab_hash_pointer (tmpl), INSERT);
*slot = build_tree_list (spec, tmpl);
}
issued. The error_mark_node is returned to indicate failure. */
static tree
-determine_specialization (tree template_id,
- tree decl,
- tree* targs_out,
+determine_specialization (tree template_id,
+ tree decl,
+ tree* targs_out,
int need_member_template,
int template_count)
{
/* Count the number of template headers specified for this
specialization. */
header_count = 0;
- for (b = current_binding_level;
+ for (b = current_binding_level;
b->kind == sk_template_parms;
b = b->level_chain)
++header_count;
/* Adjust the type of DECL in case FN is a static member. */
decl_arg_types = TYPE_ARG_TYPES (TREE_TYPE (decl));
- if (DECL_STATIC_FUNCTION_P (fn)
+ if (DECL_STATIC_FUNCTION_P (fn)
&& DECL_NONSTATIC_MEMBER_FUNCTION_P (decl))
decl_arg_types = TREE_CHAIN (decl_arg_types);
the const qualification is the same. This can be done by
checking the 'this' in the argument list. */
if (DECL_NONSTATIC_MEMBER_FUNCTION_P (fn)
- && !same_type_p (TREE_VALUE (fn_arg_types),
+ && !same_type_p (TREE_VALUE (fn_arg_types),
TREE_VALUE (decl_arg_types)))
continue;
is a template member function. So both lines are syntactically
correct, and check_explicit_specialization does not reject
them.
-
+
Here, we can do better, as we are matching the specialization
against the declarations. We count the number of template
headers, and we check if they match TEMPLATE_COUNT + 1
(TEMPLATE_COUNT is the number of qualifying template classes,
plus there must be another header for the member template
itself).
-
+
Notice that if header_count is zero, this is not a
specialization but rather a template instantiation, so there
is no check we can perform here. */
&& (TREE_VEC_LENGTH (DECL_INNERMOST_TEMPLATE_PARMS (fn))
!= TREE_VEC_LENGTH (TREE_VALUE (current_template_parms))))
continue;
-
+
/* See whether this function might be a specialization of this
template. */
targs = get_bindings (fn, decl, explicit_targs, /*check_ret=*/true);
/* This is an ordinary member function. However, since
we're here, we can assume it's enclosing class is a
template class. For example,
-
+
template <typename T> struct S { void f(); };
template <> void S<int>::f() {}
/* Adjust the type of DECL in case FN is a static member. */
decl_arg_types = TYPE_ARG_TYPES (TREE_TYPE (decl));
- if (DECL_STATIC_FUNCTION_P (fn)
+ if (DECL_STATIC_FUNCTION_P (fn)
&& DECL_NONSTATIC_MEMBER_FUNCTION_P (decl))
decl_arg_types = TREE_CHAIN (decl_arg_types);
- if (compparms (TYPE_ARG_TYPES (TREE_TYPE (fn)),
+ if (compparms (TYPE_ARG_TYPES (TREE_TYPE (fn)),
decl_arg_types))
/* They match! */
candidates = tree_cons (NULL_TREE, fn, candidates);
if (templates && TREE_CHAIN (templates))
{
/* We have:
-
+
[temp.expl.spec]
It is possible for a specialization with a given function
Partial ordering of overloaded function template
declarations is used in the following contexts to select
the function template to which a function template
- specialization refers:
+ specialization refers:
-- when an explicit specialization refers to a function
- template.
+ template.
So, we do use the partial ordering rules, at least for now.
This extension can only serve to make invalid programs valid,
if (TMPL_ARGS_HAVE_MULTIPLE_LEVELS (targs))
{
*targs_out = copy_node (targs);
- SET_TMPL_ARGS_LEVEL (*targs_out,
+ SET_TMPL_ARGS_LEVEL (*targs_out,
TMPL_ARGS_DEPTH (*targs_out),
TREE_PURPOSE (templates));
}
/* Returns a chain of parameter types, exactly like the SPEC_TYPES,
but with the default argument values filled in from those in the
TMPL_TYPES. */
-
+
static tree
copy_default_args_to_explicit_spec_1 (tree spec_types,
tree tmpl_types)
new_spec_types =
copy_default_args_to_explicit_spec_1 (TREE_CHAIN (spec_types),
TREE_CHAIN (tmpl_types));
-
+
/* Add the default argument for this parameter. */
return hash_tree_cons (TREE_PURPOSE (tmpl_types),
TREE_VALUE (spec_types),
template <class T> void f(T = 3);
template <> void f(double);
- void g () { f (); }
+ void g () { f (); }
works, as required.) An alternative approach would be to look up
the correct default arguments at the call-site, but this approach
old_type = TREE_TYPE (decl);
spec_types = TYPE_ARG_TYPES (old_type);
-
+
if (DECL_NONSTATIC_MEMBER_FUNCTION_P (decl))
{
/* Remove the this pointer, but remember the object's type for
object_type = TREE_TYPE (TREE_VALUE (spec_types));
spec_types = TREE_CHAIN (spec_types);
tmpl_types = TREE_CHAIN (tmpl_types);
-
+
if (DECL_HAS_IN_CHARGE_PARM_P (decl))
{
/* DECL may contain more parameters than TMPL due to the extra
}
/* Compute the merged default arguments. */
- new_spec_types =
+ new_spec_types =
copy_default_args_to_explicit_spec_1 (spec_types, tmpl_types);
/* Compute the new FUNCTION_TYPE. */
instead if all goes well. Issues an error message if something is
amiss. Returns error_mark_node if the error is not easily
recoverable.
-
- FLAGS is a bitmask consisting of the following flags:
+
+ FLAGS is a bitmask consisting of the following flags:
2: The function has a definition.
4: The function is a friend.
template <class T> struct S { void f(); };
void S<int>::f();
-
+
the TEMPLATE_COUNT would be 1. However, explicitly specialized
classes are not counted in the TEMPLATE_COUNT, so that in
If the function is a specialization, it is marked as such via
DECL_TEMPLATE_SPECIALIZATION. Furthermore, its DECL_TEMPLATE_INFO
- is set up correctly, and it is added to the list of specializations
+ is set up correctly, and it is added to the list of specializations
for that template. */
tree
-check_explicit_specialization (tree declarator,
- tree decl,
- int template_count,
+check_explicit_specialization (tree declarator,
+ tree decl,
+ int template_count,
int flags)
{
int have_def = flags & 2;
switch (tsk)
{
case tsk_none:
- if (processing_specialization)
+ if (processing_specialization)
{
specialization = 1;
SET_DECL_TEMPLATE_SPECIALIZATION (decl);
case tsk_expl_inst:
if (have_def)
error ("definition provided for explicit instantiation");
-
+
explicit_instantiation = 1;
break;
specialization the containing class. Something like:
template <class T> struct S {
- template <class U> void f (U);
+ template <class U> void f (U);
};
template <> template <class U> void S<int>::f(U) {}
-
+
That's a specialization -- but of the entire template. */
specialization = 1;
break;
This case is caught by the parser. However, on
something like:
-
+
template class C { void f(); };
(which is invalid) we can get here. The error will be
return decl;
}
- else if (ctype != NULL_TREE
+ else if (ctype != NULL_TREE
&& (TREE_CODE (TREE_OPERAND (declarator, 0)) ==
IDENTIFIER_NODE))
{
if (constructor_name_p (name, ctype))
{
int is_constructor = DECL_CONSTRUCTOR_P (decl);
-
+
if (is_constructor ? !TYPE_HAS_CONSTRUCTOR (ctype)
: !CLASSTYPE_DESTRUCTORS (ctype))
{
/* From [temp.expl.spec]:
-
+
If such an explicit specialization for the member
of a class template names an implicitly-declared
special member function (clause _special_), the
- program is ill-formed.
+ program is ill-formed.
Similar language is found in [temp.explicit]. */
error ("specialization of implicitly-declared special member function");
fns = ovl_cons (OVL_CURRENT (ovl), fns);
}
}
-
- if (fns == NULL_TREE)
+
+ if (fns == NULL_TREE)
{
error ("no member function %qD declared in %qT", name, ctype);
return error_mark_node;
else
TREE_OPERAND (declarator, 0) = fns;
}
-
+
/* Figure out what exactly is being specialized at this point.
Note that for an explicit instantiation, even one for a
member function, we cannot tell apriori whether the
elided if they can be deduced from the rest of the
declaration. */
tmpl = determine_specialization (declarator, decl,
- &targs,
+ &targs,
member_specialization,
template_count);
-
+
if (!tmpl || tmpl == error_mark_node)
/* We couldn't figure out what this declaration was
specializing. */
if (explicit_instantiation)
{
/* We don't set DECL_EXPLICIT_INSTANTIATION here; that
- is done by do_decl_instantiation later. */
+ is done by do_decl_instantiation later. */
int arg_depth = TMPL_ARGS_DEPTH (targs);
int parm_depth = TMPL_PARMS_DEPTH (DECL_TEMPLATE_PARMS (tmpl));
= TREE_VEC_ELT (targs, i);
targs = new_targs;
}
-
+
return instantiate_template (tmpl, targs, tf_error);
}
decl = register_specialization (decl, gen_tmpl, targs);
}
}
-
+
return decl;
}
if (parms1 == parms2)
return 1;
- for (p1 = parms1, p2 = parms2;
+ for (p1 = parms1, p2 = parms2;
p1 != NULL_TREE && p2 != NULL_TREE;
p1 = TREE_CHAIN (p1), p2 = TREE_CHAIN (p2))
{
if (TREE_VEC_LENGTH (t1) != TREE_VEC_LENGTH (t2))
return 0;
- for (i = 0; i < TREE_VEC_LENGTH (t2); ++i)
+ for (i = 0; i < TREE_VEC_LENGTH (t2); ++i)
{
tree parm1 = TREE_VALUE (TREE_VEC_ELT (t1, i));
tree parm2 = TREE_VALUE (TREE_VEC_ELT (t2, i));
/* We check for decl != olddecl to avoid bogus errors for using a
name inside a class. We check TPFI to avoid duplicate errors for
inline member templates. */
- if (decl == olddecl
+ if (decl == olddecl
|| TEMPLATE_PARMS_FOR_INLINE (current_template_parms))
return;
ORIG_LEVEL, DECL, and TYPE. */
static tree
-build_template_parm_index (int index,
- int level,
- int orig_level,
- tree decl,
+build_template_parm_index (int index,
+ int level,
+ int orig_level,
+ tree decl,
tree type)
{
tree t = make_node (TEMPLATE_PARM_INDEX);
TEMPLATE_PARM_INDEX already exists, it is returned; otherwise, a
new one is created. */
-static tree
+static tree
reduce_template_parm_level (tree index, tree type, int levels)
{
if (TEMPLATE_PARM_DESCENDANTS (index) == NULL_TREE
{
tree orig_decl = TEMPLATE_PARM_DECL (index);
tree decl, t;
-
+
decl = build_decl (TREE_CODE (orig_decl), DECL_NAME (orig_decl), type);
TREE_CONSTANT (decl) = TREE_CONSTANT (orig_decl);
TREE_INVARIANT (decl) = TREE_INVARIANT (orig_decl);
TREE_READONLY (decl) = TREE_READONLY (orig_decl);
DECL_ARTIFICIAL (decl) = 1;
SET_DECL_TEMPLATE_PARM_P (decl);
-
+
t = build_template_parm_index (TEMPLATE_PARM_IDX (index),
TEMPLATE_PARM_LEVEL (index) - levels,
TEMPLATE_PARM_ORIG_LEVEL (index),
TREE_CONSTANT (decl) = 1;
TREE_INVARIANT (decl) = 1;
TREE_READONLY (decl) = 1;
- DECL_INITIAL (parm) = DECL_INITIAL (decl)
+ DECL_INITIAL (parm) = DECL_INITIAL (decl)
= build_template_parm_index (idx, processing_template_decl,
processing_template_decl,
decl, TREE_TYPE (parm));
{
tree t;
parm = TREE_VALUE (TREE_VALUE (parm));
-
+
if (parm && TREE_CODE (parm) == TEMPLATE_DECL)
{
t = make_aggr_type (TEMPLATE_TEMPLATE_PARM);
- /* This is for distinguishing between real templates and template
+ /* This is for distinguishing between real templates and template
template parameters */
TREE_TYPE (parm) = t;
TREE_TYPE (DECL_TEMPLATE_RESULT (parm)) = t;
/* parm is either IDENTIFIER_NODE or NULL_TREE. */
decl = build_decl (TYPE_DECL, parm, t);
}
-
+
TYPE_NAME (t) = decl;
TYPE_STUB_DECL (t) = decl;
parm = decl;
TEMPLATE_TYPE_PARM_INDEX (t)
- = build_template_parm_index (idx, processing_template_decl,
+ = build_template_parm_index (idx, processing_template_decl,
processing_template_decl,
decl, TREE_TYPE (parm));
}
/* T will be a list if we are called from within a
begin/end_template_parm_list pair, but a vector directly
if within a begin/end_member_template_processing pair. */
- if (TREE_CODE (t) == TREE_LIST)
+ if (TREE_CODE (t) == TREE_LIST)
{
t = TREE_VALUE (t);
-
- if (TREE_CODE (t) == TYPE_DECL
+
+ if (TREE_CODE (t) == TYPE_DECL
|| TREE_CODE (t) == TEMPLATE_DECL)
t = TREE_TYPE (t);
else
DECL_NONCONVERTING_P (tmpl) = DECL_NONCONVERTING_P (decl);
DECL_ASSIGNMENT_OPERATOR_P (tmpl) = DECL_ASSIGNMENT_OPERATOR_P (decl);
if (DECL_OVERLOADED_OPERATOR_P (decl))
- SET_OVERLOADED_OPERATOR_CODE (tmpl,
+ SET_OVERLOADED_OPERATOR_CODE (tmpl,
DECL_OVERLOADED_OPERATOR_P (decl));
}
};
The S2<T> declaration is actually invalid; it is a
- full-specialization. Of course,
+ full-specialization. Of course,
template <class U>
struct S2<T (*)(U)>;
The argument list of the specialization shall not be identical to
the implicit argument list of the primary template. */
- if (comp_template_args
- (inner_args,
+ if (comp_template_args
+ (inner_args,
INNERMOST_TEMPLATE_ARGS (CLASSTYPE_TI_ARGS (TREE_TYPE
(maintmpl)))))
error ("partial specialization %qT does not specialize any template arguments", type);
{
if (tpd.arg_uses_template_parms[i])
error ("template argument %qE involves template parameter(s)", arg);
- else
+ else
{
/* Look at the corresponding template parameter,
marking which template parameters its type depends
upon. */
- tree type =
- TREE_TYPE (TREE_VALUE (TREE_VEC_ELT (main_inner_parms,
+ tree type =
+ TREE_TYPE (TREE_VALUE (TREE_VEC_ELT (main_inner_parms,
i)));
if (!tpd2.parms)
{
/* We haven't yet initialized TPD2. Do so now. */
- tpd2.arg_uses_template_parms
+ tpd2.arg_uses_template_parms
= alloca (sizeof (int) * nargs);
/* The number of parameters here is the number in the
main template, which, as checked in the assertion
above, is NARGS. */
tpd2.parms = alloca (sizeof (int) * nargs);
- tpd2.level =
+ tpd2.level =
TMPL_PARMS_DEPTH (DECL_TEMPLATE_PARMS (maintmpl));
}
&mark_template_parm,
&tpd2,
NULL);
-
+
if (tpd2.arg_uses_template_parms [i])
{
/* The type depended on some template parameters.
&& tpd.arg_uses_template_parms [j])
{
error ("type %qT of template argument %qE depends "
- "on template parameter(s)",
+ "on template parameter(s)",
type,
arg);
break;
}
}
- if (retrieve_specialization (maintmpl, specargs,
+ if (retrieve_specialization (maintmpl, specargs,
/*class_specializations_p=*/true))
/* We've already got this specialization. */
return decl;
int last_level_to_check;
tree parm_level;
- /* [temp.param]
+ /* [temp.param]
A default template-argument shall not be specified in a
function template declaration or a function template definition, nor
return;
/* [temp.param]
-
+
If a template-parameter has a default template-argument, all
subsequent template-parameters shall have a default
template-argument supplied. */
{
tree inner_parms = TREE_VALUE (parm_level);
int ntparms = TREE_VEC_LENGTH (inner_parms);
- int seen_def_arg_p = 0;
+ int seen_def_arg_p = 0;
int i;
- for (i = 0; i < ntparms; ++i)
+ for (i = 0; i < ntparms; ++i)
{
tree parm = TREE_VEC_ELT (inner_parms, i);
if (TREE_PURPOSE (parm))
struct S {};
but, in a partial specialization, they're not allowed even
there, as we have in [temp.class.spec]:
-
+
The template parameter list of a specialization shall not
- contain default template argument values.
+ contain default template argument values.
So, for a partial specialization, or for a function template,
we look at all of them. */
/* Check everything. */
last_level_to_check = 0;
- for (parm_level = parms;
- parm_level && TMPL_PARMS_DEPTH (parm_level) >= last_level_to_check;
+ for (parm_level = parms;
+ parm_level && TMPL_PARMS_DEPTH (parm_level) >= last_level_to_check;
parm_level = TREE_CHAIN (parm_level))
{
tree inner_parms = TREE_VALUE (parm_level);
int ntparms;
ntparms = TREE_VEC_LENGTH (inner_parms);
- for (i = 0; i < ntparms; ++i)
+ for (i = 0; i < ntparms; ++i)
if (TREE_PURPOSE (TREE_VEC_ELT (inner_parms, i)))
{
if (msg)
/* At this point, if we're still interested in issuing messages,
they must apply to classes surrounding the object declared. */
if (msg)
- msg = "default argument for template parameter for class enclosing %qD";
+ msg = "default argument for template parameter for class enclosing %qD";
}
}
/* Creates a TEMPLATE_DECL for the indicated DECL using the template
parameters given by current_template_args, or reuses a
previously existing one, if appropriate. Returns the DECL, or an
- equivalent one, if it is replaced via a call to duplicate_decls.
+ equivalent one, if it is replaced via a call to duplicate_decls.
If IS_FRIEND is nonzero, DECL is a friend declaration. */
member_template_p = true;
if (current_lang_name == lang_name_c)
error ("template with C linkage");
- else if (TREE_CODE (decl) == TYPE_DECL
- && ANON_AGGRNAME_P (DECL_NAME (decl)))
+ else if (TREE_CODE (decl) == TYPE_DECL
+ && ANON_AGGRNAME_P (DECL_NAME (decl)))
error ("template class without a name");
else if (TREE_CODE (decl) == FUNCTION_DECL)
{
if (DECL_DESTRUCTOR_P (decl))
{
/* [temp.mem]
-
+
A destructor shall not be a member template. */
error ("destructor %qD declared as member template", decl);
return error_mark_node;
|| (TREE_CHAIN (TYPE_ARG_TYPES ((TREE_TYPE (decl))))
== void_list_node)))
{
- /* [basic.stc.dynamic.allocation]
+ /* [basic.stc.dynamic.allocation]
An allocation function can be a function
template. ... Template allocation functions shall
/* Check to see that the rules regarding the use of default
arguments are not being violated. */
- check_default_tmpl_args (decl, current_template_parms,
+ check_default_tmpl_args (decl, current_template_parms,
primary, is_partial);
if (is_partial)
args = current_template_args ();
- if (!ctx
+ if (!ctx
|| TREE_CODE (ctx) == FUNCTION_DECL
|| (CLASS_TYPE_P (ctx) && TYPE_BEING_DEFINED (ctx))
|| (is_friend && !DECL_TEMPLATE_INFO (decl)))
/* If DECL is a TYPE_DECL for a class-template, then there won't
be DECL_LANG_SPECIFIC. The information equivalent to
DECL_TEMPLATE_INFO is found in TYPE_TEMPLATE_INFO instead. */
- else if (DECL_IMPLICIT_TYPEDEF_P (decl)
+ else if (DECL_IMPLICIT_TYPEDEF_P (decl)
&& TYPE_TEMPLATE_INFO (TREE_TYPE (decl))
&& TYPE_TI_TEMPLATE (TREE_TYPE (decl)))
{
}
else
tmpl = DECL_TI_TEMPLATE (decl);
-
+
if (DECL_FUNCTION_TEMPLATE_P (tmpl)
- && DECL_TEMPLATE_INFO (decl) && DECL_TI_ARGS (decl)
+ && DECL_TEMPLATE_INFO (decl) && DECL_TI_ARGS (decl)
&& DECL_TEMPLATE_SPECIALIZATION (decl)
&& DECL_MEMBER_TEMPLATE_P (tmpl))
{
earlier call to check_explicit_specialization. */
args = DECL_TI_ARGS (decl);
- new_tmpl
+ new_tmpl
= build_template_decl (decl, current_template_parms,
member_template_p);
DECL_TEMPLATE_RESULT (new_tmpl) = decl;
TREE_TYPE (new_tmpl) = TREE_TYPE (decl);
DECL_TI_TEMPLATE (decl) = new_tmpl;
SET_DECL_TEMPLATE_SPECIALIZATION (new_tmpl);
- DECL_TEMPLATE_INFO (new_tmpl)
+ DECL_TEMPLATE_INFO (new_tmpl)
= tree_cons (tmpl, args, NULL_TREE);
- register_specialization (new_tmpl,
- most_general_template (tmpl),
+ register_specialization (new_tmpl,
+ most_general_template (tmpl),
args);
return decl;
}
that we do not try to push a global template friend declared in a
template class; such a thing may well depend on the template
parameters of the class. */
- if (new_template_p && !ctx
+ if (new_template_p && !ctx
&& !(is_friend && template_class_depth (current_class_type) > 0))
{
tmpl = pushdecl_namespace_level (tmpl);
/* It is a conversion operator. See if the type converted to
depends on innermost template operands. */
-
+
if (uses_template_parms_level (TREE_TYPE (TREE_TYPE (tmpl)),
depth))
DECL_TEMPLATE_CONV_FN_P (tmpl) = 1;
template <class T> struct S;
template <class T> struct S {}; */
-void
+void
redeclare_class_template (tree type, tree parms)
{
tree tmpl;
{
cp_error_at ("previous declaration %qD", tmpl);
error ("used %d template parameter(s) instead of %d",
- TREE_VEC_LENGTH (tmpl_parms),
+ TREE_VEC_LENGTH (tmpl_parms),
TREE_VEC_LENGTH (parms));
return;
}
{
/* If we're in a template, but EXPR isn't value dependent, simplify
it. We're supposed to treat:
-
+
template <typename T> void f(T[1 + 1]);
template <typename T> void f(T[2]);
-
+
as two declarations of the same function, for example. */
if (processing_template_decl
&& !type_dependent_expression_p (expr)
/* EXPR is an expression which is used in a constant-expression context.
For instance, it could be a VAR_DECL with a constant initializer.
Extract the innest constant expression.
-
+
This is basically a more powerful version of
integral_constant_value, which can be used also in templates where
initializers can maintain a syntactic rather than semantic form
expressed as "& id-expression" where the & is optional if the name
refers to a function or array, or if the corresponding
template-parameter is a reference.
-
+
Here, we do not care about functions, as they are invalid anyway
for a parameter of type pointer-to-object. */
bool constant_address_p =
"because of conflicts in cv-qualification", expr, type);
return NULL_TREE;
}
-
+
if (!real_lvalue_p (expr))
{
error ("%qE is not a valid template argument for type %qT "
}
-/* Return 1 if PARM_PARMS and ARG_PARMS matches using rule for
- template template parameters. Both PARM_PARMS and ARG_PARMS are
- vectors of TREE_LIST nodes containing TYPE_DECL, TEMPLATE_DECL
+/* Return 1 if PARM_PARMS and ARG_PARMS matches using rule for
+ template template parameters. Both PARM_PARMS and ARG_PARMS are
+ vectors of TREE_LIST nodes containing TYPE_DECL, TEMPLATE_DECL
or PARM_DECL.
-
- ARG_PARMS may contain more parameters than PARM_PARMS. If this is
+
+ ARG_PARMS may contain more parameters than PARM_PARMS. If this is
the case, then extra parameters must have default arguments.
Consider the example:
template <class T, class Allocator = allocator> class vector;
template<template <class U> class TT> class C;
- C<vector> is a valid instantiation. PARM_PARMS for the above code
- contains a TYPE_DECL (for U), ARG_PARMS contains two TYPE_DECLs (for
- T and Allocator) and OUTER_ARGS contains the argument that is used to
+ C<vector> is a valid instantiation. PARM_PARMS for the above code
+ contains a TYPE_DECL (for U), ARG_PARMS contains two TYPE_DECLs (for
+ T and Allocator) and OUTER_ARGS contains the argument that is used to
substitute the TT parameter. */
static int
-coerce_template_template_parms (tree parm_parms,
- tree arg_parms,
- tsubst_flags_t complain,
+coerce_template_template_parms (tree parm_parms,
+ tree arg_parms,
+ tsubst_flags_t complain,
tree in_decl,
tree outer_args)
{
TREE_TYPE (arg)))
return 0;
break;
-
+
default:
gcc_unreachable ();
}
the full set of template arguments deduced so far. */
static tree
-convert_template_argument (tree parm,
- tree arg,
- tree args,
- tsubst_flags_t complain,
- int i,
+convert_template_argument (tree parm,
+ tree arg,
+ tree args,
+ tsubst_flags_t complain,
+ int i,
tree in_decl)
{
tree val;
tree inner_args;
int is_type, requires_type, is_tmpl_type, requires_tmpl_type;
-
+
inner_args = INNERMOST_TEMPLATE_ARGS (args);
- if (TREE_CODE (arg) == TREE_LIST
+ if (TREE_CODE (arg) == TREE_LIST
&& TREE_CODE (TREE_VALUE (arg)) == OFFSET_REF)
- {
+ {
/* The template argument was the name of some
member function. That's usually
invalid, but static members are OK. In any
&& TREE_CODE (DECL_TEMPLATE_RESULT (arg)) == TYPE_DECL)
|| TREE_CODE (arg) == TEMPLATE_TEMPLATE_PARM
|| TREE_CODE (arg) == UNBOUND_CLASS_TEMPLATE);
-
+
if (is_tmpl_type
&& (TREE_CODE (arg) == TEMPLATE_TEMPLATE_PARM
|| TREE_CODE (arg) == UNBOUND_CLASS_TEMPLATE))
{
pedwarn ("to refer to a type member of a template parameter, "
"use %<typename %E%>", arg);
-
+
arg = make_typename_type (TREE_OPERAND (arg, 0),
TREE_OPERAND (arg, 1),
typename_type,
}
return error_mark_node;
}
-
+
if (is_type)
{
if (requires_tmpl_type)
inner_args))
{
val = arg;
-
- /* TEMPLATE_TEMPLATE_PARM node is preferred over
+
+ /* TEMPLATE_TEMPLATE_PARM node is preferred over
TEMPLATE_DECL. */
- if (val != error_mark_node
+ if (val != error_mark_node
&& DECL_TEMPLATE_TEMPLATE_PARM_P (val))
val = TREE_TYPE (val);
}
error (" expected a template of type %qD, got %qD",
parm, arg);
}
-
+
val = error_mark_node;
}
}
if (invalid_nontype_parm_type_p (t, complain))
return error_mark_node;
-
+
if (!uses_template_parms (arg) && !uses_template_parms (t))
/* We used to call digest_init here. However, digest_init
will report errors, which we don't want when complain
provided in ARGLIST, or else trailing parameters must have default
values. If REQUIRE_ALL_ARGUMENTS is zero, we will attempt argument
deduction for any unspecified trailing arguments. */
-
+
static tree
-coerce_template_parms (tree parms,
- tree args,
+coerce_template_parms (tree parms,
+ tree args,
tree in_decl,
tsubst_flags_t complain,
int require_all_arguments)
&& require_all_arguments
&& TREE_PURPOSE (TREE_VEC_ELT (parms, nargs)) == NULL_TREE))
{
- if (complain & tf_error)
+ if (complain & tf_error)
{
error ("wrong number of template arguments (%d, should be %d)",
nargs, nparms);
-
+
if (in_decl)
cp_error_at ("provided for %qD", in_decl);
}
complain, in_decl);
else
break;
-
+
gcc_assert (arg);
if (arg == error_mark_node)
{
if (complain & tf_error)
error ("template argument %d is invalid", i + 1);
}
- else
- arg = convert_template_argument (TREE_VALUE (parm),
+ else
+ arg = convert_template_argument (TREE_VALUE (parm),
arg, new_args, complain, i,
- in_decl);
-
+ in_decl);
+
if (arg == error_mark_node)
lost++;
TREE_VEC_ELT (new_inner_args, i) = arg;
{
if (TREE_CODE (arg) == TEMPLATE_DECL)
{
- /* Already substituted with real template. Just output
+ /* Already substituted with real template. Just output
the template name here */
tree context = DECL_CONTEXT (arg);
if (context)
{
tree name = DECL_NAME (tmpl);
char *mangled_name = mangle_class_name_for_template
- (IDENTIFIER_POINTER (name),
+ (IDENTIFIER_POINTER (name),
DECL_INNERMOST_TEMPLATE_PARMS (tmpl),
CLASSTYPE_TI_ARGS (t));
tree id = get_identifier (mangled_name);
type = TREE_TYPE (fns);
if (TREE_CODE (fns) == OVERLOAD || !type)
type = unknown_type_node;
-
+
return build2 (TEMPLATE_ID_EXPR, type, fns, arglist);
}
maybe_get_template_decl_from_type_decl (tree decl)
{
return (decl != NULL_TREE
- && TREE_CODE (decl) == TYPE_DECL
+ && TREE_CODE (decl) == TYPE_DECL
&& DECL_ARTIFICIAL (decl)
&& CLASS_TYPE_P (TREE_TYPE (decl))
- && CLASSTYPE_TEMPLATE_INFO (TREE_TYPE (decl)))
+ && CLASSTYPE_TEMPLATE_INFO (TREE_TYPE (decl)))
? CLASSTYPE_TI_TEMPLATE (TREE_TYPE (decl)) : decl;
}
D1 is the PTYPENAME terminal, and ARGLIST is the list of arguments.
IN_DECL, if non-NULL, is the template declaration we are trying to
- instantiate.
+ instantiate.
If ENTERING_SCOPE is nonzero, we are about to enter the scope of
the class we are looking up.
-
+
Issue error and warning messages under control of COMPLAIN.
If the template class is really a local class in a template
function, then the FUNCTION_CONTEXT is the function in which it is
- being instantiated.
+ being instantiated.
??? Note that this function is currently called *twice* for each
template-id: the first time from the parser, while creating the
coercion (see convert_nontype_argument for more information on this). */
tree
-lookup_template_class (tree d1,
- tree arglist,
- tree in_decl,
- tree context,
- int entering_scope,
+lookup_template_class (tree d1,
+ tree arglist,
+ tree in_decl,
+ tree context,
+ int entering_scope,
tsubst_flags_t complain)
{
tree template = NULL_TREE, parmlist;
tree t;
-
+
timevar_push (TV_NAME_LOOKUP);
-
+
if (TREE_CODE (d1) == IDENTIFIER_NODE)
{
tree value = innermost_non_namespace_value (d1);
an implicit typename for the second A. Deal with it. */
if (TREE_CODE (type) == TYPENAME_TYPE && TREE_TYPE (type))
type = TREE_TYPE (type);
-
+
if (CLASSTYPE_TEMPLATE_INFO (type))
{
template = CLASSTYPE_TI_TEMPLATE (type);
d1 = DECL_NAME (template);
}
}
- else if (TREE_CODE (d1) == ENUMERAL_TYPE
+ else if (TREE_CODE (d1) == ENUMERAL_TYPE
|| (TYPE_P (d1) && IS_AGGR_TYPE (d1)))
{
template = TYPE_TI_TEMPLATE (d1);
}
complain &= ~tf_user;
-
+
if (DECL_TEMPLATE_TEMPLATE_PARM_P (template))
{
/* Create a new TEMPLATE_DECL and TEMPLATE_TEMPLATE_PARM node to store
template <class T, class U = std::allocator<T> > class TT
- The template parameter level of T and U are one level larger than
- of TT. To proper process the default argument of U, say when an
+ The template parameter level of T and U are one level larger than
+ of TT. To proper process the default argument of U, say when an
instantiation `TT<int>' is seen, we need to build the full
arguments containing {int} as the innermost level. Outer levels,
available when not appearing as default template argument, can be
parm = bind_template_template_parm (TREE_TYPE (template), arglist2);
POP_TIMEVAR_AND_RETURN (TV_NAME_LOOKUP, parm);
}
- else
+ else
{
tree template_type = TREE_TYPE (template);
tree gen_tmpl;
template <class U> struct S2 {};
template <class U> struct S2<U*> {};
};
-
+
we will be called with an ARGLIST of `U*', but the
TEMPLATE will be `template <class T> template
<class U> struct S1<T>::S2'. We must fill in the missing
arguments. */
- arglist
+ arglist
= add_outermost_template_args (TYPE_TI_ARGS (TREE_TYPE (template)),
arglist);
arg_depth = TMPL_ARGS_DEPTH (arglist);
/* Now we should have enough arguments. */
gcc_assert (parm_depth == arg_depth);
-
+
/* From here on, we're only interested in the most general
template. */
template = gen_tmpl;
int saved_depth = TMPL_ARGS_DEPTH (arglist);
tree bound_args = make_tree_vec (parm_depth);
-
+
for (i = saved_depth,
- t = DECL_TEMPLATE_PARMS (template);
+ t = DECL_TEMPLATE_PARMS (template);
i > 0 && t != NULL_TREE;
--i, t = TREE_CHAIN (t))
{
TREE_VEC_LENGTH (arglist) = saved_depth;
POP_TIMEVAR_AND_RETURN (TV_NAME_LOOKUP, error_mark_node);
}
-
+
SET_TMPL_ARGS_LEVEL (bound_args, i, a);
/* We temporarily reduce the length of the ARGLIST so
/* In the scope of a template class, explicit references to the
template class refer to the type of the template, not any
instantiation of it. For example, in:
-
+
template <class T> class C { void f(C<T>); }
the `C<T>' is just the same as `C'. Outside of the
arglist))
{
found = template_type;
-
+
if (!entering_scope && PRIMARY_TEMPLATE_P (template))
{
tree ctx;
-
- for (ctx = current_class_type;
+
+ for (ctx = current_class_type;
ctx && TREE_CODE (ctx) != NAMESPACE_DECL;
ctx = (TYPE_P (ctx)
? TYPE_CONTEXT (ctx)
: DECL_CONTEXT (ctx)))
if (TYPE_P (ctx) && same_type_p (ctx, template_type))
goto found_ctx;
-
+
/* We're not in the scope of the class, so the
TEMPLATE_TYPE is not the type we want after all. */
found = NULL_TREE;
INNERMOST_TEMPLATE_ARGS (arglist),
complain))
POP_TIMEVAR_AND_RETURN (TV_NAME_LOOKUP, error_mark_node);
-
- if (!is_partial_instantiation
+
+ if (!is_partial_instantiation
&& !PRIMARY_TEMPLATE_P (template)
&& TREE_CODE (CP_DECL_CONTEXT (template)) == NAMESPACE_DECL)
{
/*tag_scope=*/ts_global);
POP_TIMEVAR_AND_RETURN (TV_NAME_LOOKUP, found);
}
-
+
context = tsubst (DECL_CONTEXT (template), arglist,
complain, in_decl);
if (!context)
else
{
t = make_aggr_type (TREE_CODE (template_type));
- CLASSTYPE_DECLARED_CLASS (t)
+ CLASSTYPE_DECLARED_CLASS (t)
= CLASSTYPE_DECLARED_CLASS (template_type);
SET_CLASSTYPE_IMPLICIT_INSTANTIATION (t);
TYPE_FOR_JAVA (t) = TYPE_FOR_JAVA (template_type);
if (!TYPE_NAME (t))
{
TYPE_CONTEXT (t) = FROB_CONTEXT (context);
-
+
type_decl = create_implicit_typedef (DECL_NAME (template), t);
DECL_CONTEXT (type_decl) = TYPE_CONTEXT (t);
TYPE_STUB_DECL (t) = type_decl;
- DECL_SOURCE_LOCATION (type_decl)
+ DECL_SOURCE_LOCATION (type_decl)
= DECL_SOURCE_LOCATION (TYPE_STUB_DECL (template_type));
}
else
/* There was no partial instantiation. This happens
where C<T> is a member template of A<T> and it's used
in something like
-
+
template <typename T> struct B { A<T>::C<int> m; };
B<float>;
-
+
Create the partial instantiation.
*/
TREE_VEC_LENGTH (arglist)--;
}
}
- SET_TYPE_TEMPLATE_INFO (t, tree_cons (found, arglist, NULL_TREE));
- DECL_TEMPLATE_INSTANTIATIONS (template)
- = tree_cons (arglist, t,
+ SET_TYPE_TEMPLATE_INFO (t, tree_cons (found, arglist, NULL_TREE));
+ DECL_TEMPLATE_INSTANTIATIONS (template)
+ = tree_cons (arglist, t,
DECL_TEMPLATE_INSTANTIATIONS (template));
- if (TREE_CODE (t) == ENUMERAL_TYPE
+ if (TREE_CODE (t) == ENUMERAL_TYPE
&& !is_partial_instantiation)
/* Now that the type has been registered on the instantiations
list, we set up the enumerators. Because the enumeration
timevar_pop (TV_NAME_LOOKUP);
}
\f
-struct pair_fn_data
+struct pair_fn_data
{
tree_fn_t fn;
void *data;
break;
case TYPEOF_TYPE:
- if (for_each_template_parm (TYPE_FIELDS (t), fn, data,
+ if (for_each_template_parm (TYPE_FIELDS (t), fn, data,
pfd->visited))
return error_mark_node;
break;
&& for_each_template_parm (DECL_INITIAL (t), fn, data,
pfd->visited))
return error_mark_node;
- if (DECL_CONTEXT (t)
+ if (DECL_CONTEXT (t)
&& for_each_template_parm (DECL_CONTEXT (t), fn, data,
pfd->visited))
return error_mark_node;
break;
case TYPENAME_TYPE:
- if (!fn
+ if (!fn
|| for_each_template_parm (TYPENAME_TYPE_FULLNAME (t), fn,
data, pfd->visited))
return error_mark_node;
pfd->visited))
return error_mark_node;
break;
-
+
case INDIRECT_REF:
case COMPONENT_REF:
/* If there's no type, then this thing must be some expression
return NULL_TREE;
}
-/* For each TEMPLATE_TYPE_PARM, TEMPLATE_TEMPLATE_PARM,
- BOUND_TEMPLATE_TEMPLATE_PARM or TEMPLATE_PARM_INDEX in T,
+/* For each TEMPLATE_TYPE_PARM, TEMPLATE_TEMPLATE_PARM,
+ BOUND_TEMPLATE_TEMPLATE_PARM or TEMPLATE_PARM_INDEX in T,
call FN with the parameter and the DATA.
If FN returns nonzero, the iteration is terminated, and
for_each_template_parm returns 1. Otherwise, the iteration
pfd.visited = visited;
else
pfd.visited = pointer_set_create ();
- result = walk_tree (&t,
- for_each_template_parm_r,
+ result = walk_tree (&t,
+ for_each_template_parm_r,
&pfd,
pfd.visited) != NULL_TREE;
else if (TREE_CODE (t) == TREE_LIST)
dependent_p = (uses_template_parms (TREE_VALUE (t))
|| uses_template_parms (TREE_CHAIN (t)));
- else if (DECL_P (t)
- || EXPR_P (t)
+ else if (DECL_P (t)
+ || EXPR_P (t)
|| TREE_CODE (t) == TEMPLATE_PARM_INDEX
|| TREE_CODE (t) == OVERLOAD
|| TREE_CODE (t) == BASELINK
gcc_assert (t == error_mark_node);
dependent_p = false;
}
-
+
processing_template_decl = saved_processing_template_decl;
return dependent_p;
{
tree new_friend;
- if (TREE_CODE (decl) == FUNCTION_DECL
+ if (TREE_CODE (decl) == FUNCTION_DECL
&& DECL_TEMPLATE_INSTANTIATION (decl)
&& TREE_CODE (DECL_TI_TEMPLATE (decl)) != TEMPLATE_DECL)
/* This was a friend declared with an explicit template
argument list, e.g.:
-
+
friend void f<>(T);
-
+
to indicate that f was a template instantiation, not a new
function declaration. Now, we have to figure out what
instantiation of what template. */
tree new_args;
tree tmpl;
tree ns = decl_namespace_context (TYPE_MAIN_DECL (current_class_type));
-
+
/* Friend functions are looked up in the containing namespace scope.
We must enter that scope, to avoid finding member functions of the
current cless with same name. */
arglist = tsubst (DECL_TI_ARGS (decl), args,
tf_error | tf_warning, NULL_TREE);
template_id = lookup_template_function (fns, arglist);
-
+
new_friend = tsubst (decl, args, tf_error | tf_warning, NULL_TREE);
tmpl = determine_specialization (template_id, new_friend,
- &new_args,
+ &new_args,
/*need_member_template=*/0,
TREE_VEC_LENGTH (args));
return instantiate_template (tmpl, new_args, tf_error);
}
new_friend = tsubst (decl, args, tf_error | tf_warning, NULL_TREE);
-
+
/* The NEW_FRIEND will look like an instantiation, to the
compiler, but is not an instantiation from the point of view of
the language. For example, we might have had:
-
+
template <class T> struct S {
template <class U> friend void f(T, U);
};
-
+
Then, in S<int>, template <class U> void f(int, U) is not an
instantiation of anything. */
if (new_friend == error_mark_node)
return error_mark_node;
-
+
DECL_USE_TEMPLATE (new_friend) = 0;
if (TREE_CODE (decl) == TEMPLATE_DECL)
{
SET_DECL_RTL (new_friend, NULL_RTX);
SET_DECL_ASSEMBLER_NAME (new_friend, NULL_TREE);
}
-
+
if (DECL_NAMESPACE_SCOPE_P (new_friend))
{
tree old_decl;
possible. */
new_friend_template_info = DECL_TEMPLATE_INFO (new_friend);
new_friend_is_defn =
- (DECL_INITIAL (DECL_TEMPLATE_RESULT
+ (DECL_INITIAL (DECL_TEMPLATE_RESULT
(template_for_substitution (new_friend)))
!= NULL_TREE);
if (TREE_CODE (new_friend) == TEMPLATE_DECL)
{
/* This declaration is a `primary' template. */
DECL_PRIMARY_TEMPLATE (new_friend) = new_friend;
-
+
new_friend_result_template_info
= DECL_TEMPLATE_INFO (DECL_TEMPLATE_RESULT (new_friend));
}
declaration. For example, given:
template <class T> void f(T);
- template <class U> class C {
- template <class T> friend void f(T) {}
+ template <class U> class C {
+ template <class T> friend void f(T) {}
};
the friend declaration actually provides the definition
run through all specialization of `f', adding to their
DECL_TI_ARGS appropriately. In particular, they need a
new set of outer arguments, corresponding to the
- arguments for this class instantiation.
+ arguments for this class instantiation.
The same situation can arise with something like this:
friend void f(int);
- template <class T> class C {
+ template <class T> class C {
friend void f(T) {}
};
reregister_specialization (new_friend,
most_general_template (old_decl),
old_decl);
- else
+ else
{
tree t;
tree new_friend_args;
- DECL_TEMPLATE_INFO (DECL_TEMPLATE_RESULT (old_decl))
+ DECL_TEMPLATE_INFO (DECL_TEMPLATE_RESULT (old_decl))
= new_friend_result_template_info;
-
+
new_friend_args = TI_ARGS (new_friend_template_info);
- for (t = DECL_TEMPLATE_SPECIALIZATIONS (old_decl);
+ for (t = DECL_TEMPLATE_SPECIALIZATIONS (old_decl);
t != NULL_TREE;
t = TREE_CHAIN (t))
{
tree spec = TREE_VALUE (t);
-
- DECL_TI_ARGS (spec)
+
+ DECL_TI_ARGS (spec)
= add_outermost_template_args (new_friend_args,
DECL_TI_ARGS (spec));
}
if (TREE_CODE (context) == NAMESPACE_DECL)
push_nested_namespace (context);
else
- push_nested_class (tsubst (context, args, tf_none, NULL_TREE));
+ push_nested_class (tsubst (context, args, tf_none, NULL_TREE));
}
/* First, we look for a class template. */
- tmpl = lookup_name (DECL_NAME (friend_tmpl), /*prefer_type=*/0);
+ tmpl = lookup_name (DECL_NAME (friend_tmpl), /*prefer_type=*/0);
/* But, if we don't find one, it might be because we're in a
situation like this:
friend_type = TREE_TYPE (pushdecl_top_level (tmpl));
}
- if (context)
+ if (context)
{
if (TREE_CODE (context) == NAMESPACE_DECL)
pop_nested_namespace (context);
tree typedecl;
tree pbinfo;
tree base_list;
-
+
if (type == error_mark_node)
return error_mark_node;
- if (TYPE_BEING_DEFINED (type)
+ if (TYPE_BEING_DEFINED (type)
|| COMPLETE_TYPE_P (type)
|| dependent_type_p (type))
return type;
{
const char *str = "candidates are:";
error ("ambiguous class template instantiation for %q#T", type);
- for (t = DECL_TEMPLATE_SPECIALIZATIONS (template); t;
+ for (t = DECL_TEMPLATE_SPECIALIZATIONS (template); t;
t = TREE_CHAIN (t))
{
if (get_class_bindings (TREE_VALUE (t), TREE_PURPOSE (t), args))
template <class T> struct S {};
template <class T> struct S<T*> {};
-
+
and supposing that we are instantiating S<int*>, ARGS will
present be {int*} but we need {int}. */
- tree inner_args
+ tree inner_args
= get_class_bindings (TREE_VALUE (t), TREE_PURPOSE (t),
args);
the accessibility of types named in dependent bases are
looked up from. */
pushed_scope = push_scope (context ? context : global_namespace);
-
+
/* Substitute into each of the bases to determine the actual
basetypes. */
for (i = 0; BINFO_BASE_ITERATE (pbinfo, i, pbase_binfo); i++)
base = tsubst (BINFO_TYPE (pbase_binfo), args, tf_error, NULL_TREE);
if (base == error_mark_node)
continue;
-
+
base_list = tree_cons (access, base, base_list);
if (BINFO_VIRTUAL_P (pbase_binfo))
TREE_TYPE (base_list) = integer_type_node;
pushtag (name, newtag, /*tag_scope=*/ts_current);
}
}
- else if (TREE_CODE (t) == FUNCTION_DECL
+ else if (TREE_CODE (t) == FUNCTION_DECL
|| DECL_FUNCTION_TEMPLATE_P (t))
{
/* Build new TYPE_METHODS. */
tree r;
-
+
if (TREE_CODE (t) == TEMPLATE_DECL)
++processing_template_decl;
r = tsubst (t, args, tf_error, NULL_TREE);
/* The call to xref_tag_from_type does injection for friend
classes. */
push_nested_namespace (ns);
- friend_type =
- xref_tag_from_type (friend_type, NULL_TREE,
+ friend_type =
+ xref_tag_from_type (friend_type, NULL_TREE,
/*tag_scope=*/ts_current);
pop_nested_namespace (ns);
}
++processing_template_decl;
push_deferring_access_checks (dk_no_check);
}
-
+
r = tsubst_friend_function (t, args);
add_friend (type, r, /*complain=*/false);
if (TREE_CODE (t) == TEMPLATE_DECL)
default arguments may reference members of the class. */
if (!PRIMARY_TEMPLATE_P (template))
for (t = TYPE_METHODS (type); t; t = TREE_CHAIN (t))
- if (TREE_CODE (t) == FUNCTION_DECL
+ if (TREE_CODE (t) == FUNCTION_DECL
/* Implicitly generated member functions will not have template
information; they are not instantiations, but instead are
created "fresh" for each instantiation. */
tsubst_template_arg (tree t, tree args, tsubst_flags_t complain, tree in_decl)
{
tree r;
-
+
if (!t)
r = t;
else if (TYPE_P (t))
will always be set. */
if (!TREE_TYPE (r))
{
- int saved_processing_template_decl = processing_template_decl;
+ int saved_processing_template_decl = processing_template_decl;
processing_template_decl = 0;
r = tsubst_copy_and_build (r, /*args=*/NULL_TREE,
tf_error, /*in_decl=*/NULL_TREE,
/*function_p=*/false);
- processing_template_decl = saved_processing_template_decl;
+ processing_template_decl = saved_processing_template_decl;
}
r = fold (r);
}
int len = TREE_VEC_LENGTH (t);
int need_new = 0, i;
tree *elts = alloca (len * sizeof (tree));
-
+
for (i = 0; i < len; i++)
{
tree orig_arg = TREE_VEC_ELT (t, i);
new_arg = tsubst_template_args (orig_arg, args, complain, in_decl);
else
new_arg = tsubst_template_arg (orig_arg, args, complain, in_decl);
-
+
if (new_arg == error_mark_node)
return error_mark_node;
if (new_arg != orig_arg)
need_new = 1;
}
-
+
if (!need_new)
return t;
t = make_tree_vec (len);
for (i = 0; i < len; i++)
TREE_VEC_ELT (t, i) = elts[i];
-
+
return t;
}
new_parms = &(TREE_CHAIN (*new_parms)),
parms = TREE_CHAIN (parms))
{
- tree new_vec =
+ tree new_vec =
make_tree_vec (TREE_VEC_LENGTH (TREE_VALUE (parms)));
int i;
-
+
for (i = 0; i < TREE_VEC_LENGTH (new_vec); ++i)
{
tree tuple = TREE_VEC_ELT (TREE_VALUE (parms), i);
parm_decl = tsubst (parm_decl, args, complain, NULL_TREE);
default_value = tsubst_template_arg (default_value, args,
complain, NULL_TREE);
-
+
tuple = build_tree_list (default_value, parm_decl);
TREE_VEC_ELT (new_vec, i) = tuple;
}
-
- *new_parms =
- tree_cons (size_int (TMPL_PARMS_DEPTH (parms)
+
+ *new_parms =
+ tree_cons (size_int (TMPL_PARMS_DEPTH (parms)
- TMPL_ARGS_DEPTH (args)),
new_vec, NULL_TREE);
}
we are presently tsubst'ing. Return the substituted value. */
static tree
-tsubst_aggr_type (tree t,
- tree args,
- tsubst_flags_t complain,
- tree in_decl,
+tsubst_aggr_type (tree t,
+ tree args,
+ tsubst_flags_t complain,
+ tree in_decl,
int entering_scope)
{
if (t == NULL_TREE)
return cp_build_qualified_type_real (r, TYPE_QUALS (t), complain);
}
- else
+ else
/* This is not a template type, so there's nothing to do. */
return t;
/* This default argument came from a template. Instantiate the
default argument here, not in tsubst. In the case of
- something like:
-
+ something like:
+
template <class T>
struct S {
static T t();
void f(T = t());
};
-
+
we must be careful to do name lookup in the scope of S<T>,
rather than in the current class. */
push_access_scope (fn);
if (uses_template_parms (tmpl_args))
return;
- for (arg = TYPE_ARG_TYPES (TREE_TYPE (fn));
- arg;
+ for (arg = TYPE_ARG_TYPES (TREE_TYPE (fn));
+ arg;
arg = TREE_CHAIN (arg))
if (TREE_PURPOSE (arg))
- TREE_PURPOSE (arg) = tsubst_default_argument (fn,
+ TREE_PURPOSE (arg) = tsubst_default_argument (fn,
TREE_VALUE (arg),
TREE_PURPOSE (arg));
}
TREE_TYPE (r) = new_type;
DECL_TEMPLATE_RESULT (r)
= build_decl (TYPE_DECL, DECL_NAME (decl), new_type);
- DECL_TEMPLATE_PARMS (r)
+ DECL_TEMPLATE_PARMS (r)
= tsubst_template_parms (DECL_TEMPLATE_PARMS (t), args,
complain);
TYPE_NAME (new_type) = r;
The ARGS are for the surrounding class type, so the
full args contain the tsubst'd args for the context,
plus the innermost args from the template decl. */
- tmpl_args = DECL_CLASS_TEMPLATE_P (t)
+ tmpl_args = DECL_CLASS_TEMPLATE_P (t)
? CLASSTYPE_TI_ARGS (TREE_TYPE (t))
: DECL_TI_ARGS (DECL_TEMPLATE_RESULT (t));
full_args = tsubst_template_args (tmpl_args, args,
}
/* Make a new template decl. It will be similar to the
- original, but will record the current template arguments.
+ original, but will record the current template arguments.
We also create a new function declaration, which is just
like the old one, but points to this new template, rather
than the old one. */
gcc_assert (DECL_LANG_SPECIFIC (r) != 0);
TREE_CHAIN (r) = NULL_TREE;
- DECL_CONTEXT (r)
- = tsubst_aggr_type (DECL_CONTEXT (t), args,
- complain, in_decl,
- /*entering_scope=*/1);
+ DECL_CONTEXT (r)
+ = tsubst_aggr_type (DECL_CONTEXT (t), args,
+ complain, in_decl,
+ /*entering_scope=*/1);
DECL_TEMPLATE_INFO (r) = build_tree_list (t, args);
if (TREE_CODE (decl) == TYPE_DECL)
/* The template parameters for this new template are all the
template parameters for the old template, except the
outermost level of parameters. */
- DECL_TEMPLATE_PARMS (r)
+ DECL_TEMPLATE_PARMS (r)
= tsubst_template_parms (DECL_TEMPLATE_PARMS (t), args,
complain);
if (TREE_CODE (decl) != TYPE_DECL)
/* Record this non-type partial instantiation. */
- register_specialization (r, t,
+ register_specialization (r, t,
DECL_TI_ARGS (DECL_TEMPLATE_RESULT (r)));
}
break;
specialization, and the complete set of arguments used to
specialize R. */
gen_tmpl = most_general_template (DECL_TI_TEMPLATE (t));
- argvec = tsubst_template_args (DECL_TI_ARGS
+ argvec = tsubst_template_args (DECL_TI_ARGS
(DECL_TEMPLATE_RESULT (gen_tmpl)),
- args, complain, in_decl);
+ args, complain, in_decl);
/* Check to see if we already have this specialization. */
spec = retrieve_specialization (gen_tmpl, argvec,
this:
template <class T> struct S { template <class U> void f(); }
- template <> template <class U> void S<int>::f(U);
+ template <> template <class U> void S<int>::f(U);
Here, we'll be substituting into the specialization,
because that's where we can find the code we actually
want to generate, but we'll have enough arguments for
- the most general template.
+ the most general template.
We also deal with the peculiar case:
- template <class T> struct S {
+ template <class T> struct S {
template <class U> friend void f();
};
template <class U> void f() {}
which we can spot because the pattern will be a
specialization in this case. */
args_depth = TMPL_ARGS_DEPTH (args);
- parms_depth =
- TMPL_PARMS_DEPTH (DECL_TEMPLATE_PARMS (DECL_TI_TEMPLATE (t)));
+ parms_depth =
+ TMPL_PARMS_DEPTH (DECL_TEMPLATE_PARMS (DECL_TI_TEMPLATE (t)));
if (args_depth > parms_depth
&& !DECL_TEMPLATE_SPECIALIZATION (t))
args = get_innermost_template_args (args, parms_depth);
{
/* This special case arises when we have something like this:
- template <class T> struct S {
- friend void f<int>(int, double);
+ template <class T> struct S {
+ friend void f<int>(int, double);
};
Here, the DECL_TI_TEMPLATE for the friend declaration
member = 2;
else
member = 1;
- ctx = tsubst_aggr_type (DECL_CONTEXT (t), args,
+ ctx = tsubst_aggr_type (DECL_CONTEXT (t), args,
complain, t, /*entering_scope=*/1);
}
else
DECL_INITIAL (r) = NULL_TREE;
DECL_CONTEXT (r) = ctx;
- if (member && DECL_CONV_FN_P (r))
+ if (member && DECL_CONV_FN_P (r))
/* Type-conversion operator. Reconstruct the name, in
case it's the name of one of the template's parameters. */
DECL_NAME (r) = mangle_conv_op_name_for_type (TREE_TYPE (type));
GEN_TMPL is NULL. */
if (gen_tmpl)
{
- DECL_TEMPLATE_INFO (r)
+ DECL_TEMPLATE_INFO (r)
= tree_cons (gen_tmpl, argvec, NULL_TREE);
SET_DECL_IMPLICIT_INSTANTIATION (r);
register_specialization (r, gen_tmpl, argvec);
until they are called, for a template. But, for a
declaration like:
- template <class T> void f ()
+ template <class T> void f ()
{ extern void g(int i = T()); }
-
+
we should do the substitution when the template is
instantiated. We handle the member function case in
instantiate_class_template since the default arguments
/* Copy the list of befriending classes. */
for (friends = &DECL_BEFRIENDING_CLASSES (r);
*friends;
- friends = &TREE_CHAIN (*friends))
+ friends = &TREE_CHAIN (*friends))
{
*friends = copy_node (*friends);
TREE_VALUE (*friends) = tsubst (TREE_VALUE (*friends),
DECL_INITIAL (r) = tsubst_expr (DECL_INITIAL (t), args,
complain, in_decl);
TREE_CHAIN (r) = NULL_TREE;
- if (VOID_TYPE_P (type))
+ if (VOID_TYPE_P (type))
cp_error_at ("instantiation of %qD as type %qT", r, type);
}
break;
break;
}
}
-
+
/* Assume this is a non-local variable. */
local_p = 0;
if (TYPE_P (CP_DECL_CONTEXT (t)))
- ctx = tsubst_aggr_type (DECL_CONTEXT (t), args,
+ ctx = tsubst_aggr_type (DECL_CONTEXT (t), args,
complain,
in_decl, /*entering_scope=*/1);
else if (DECL_NAMESPACE_SCOPE_P (t))
default:
gcc_unreachable ();
- }
+ }
/* Restore the file and line information. */
input_location = saved_loc;
/* Substitute into the ARG_TYPES of a function type. */
static tree
-tsubst_arg_types (tree arg_types,
- tree args,
- tsubst_flags_t complain,
+tsubst_arg_types (tree arg_types,
+ tree args,
+ tsubst_flags_t complain,
tree in_decl)
{
tree remaining_arg_types;
if (!arg_types || arg_types == void_list_node)
return arg_types;
-
+
remaining_arg_types = tsubst_arg_types (TREE_CHAIN (arg_types),
args, complain, in_decl);
if (remaining_arg_types == error_mark_node)
mandates that they be instantiated only when needed, which is
done in build_over_call. */
default_arg = TREE_PURPOSE (arg_types);
-
+
if (default_arg && TREE_CODE (default_arg) == DEFAULT_ARG)
{
/* We've instantiated a template before its default arguments
}
else
result = hash_tree_cons (default_arg, type, remaining_arg_types);
-
+
return result;
}
results in an invalid type.] */
static tree
-tsubst_function_type (tree t,
- tree args,
- tsubst_flags_t complain,
+tsubst_function_type (tree t,
+ tree args,
+ tsubst_flags_t complain,
tree in_decl)
{
tree return_type;
/* The standard does not presently indicate that creation of a
function type with an invalid return type is a deduction failure.
However, that is clearly analogous to creating an array of "void"
- or a reference to a reference. This is core issue #486. */
+ or a reference to a reference. This is core issue #486. */
if (TREE_CODE (return_type) == ARRAY_TYPE
|| TREE_CODE (return_type) == FUNCTION_TYPE)
{
/* Substitute the argument types. */
arg_types = tsubst_arg_types (TYPE_ARG_TYPES (t), args,
- complain, in_decl);
+ complain, in_decl);
if (arg_types == error_mark_node)
return error_mark_node;
-
+
/* Construct a new type node and return it. */
if (TREE_CODE (t) == FUNCTION_TYPE)
fntype = build_function_type (return_type, arg_types);
if (! IS_AGGR_TYPE (r))
{
/* [temp.deduct]
-
+
Type deduction may fail for any of the following
reasons:
-
+
-- Attempting to create "pointer to member of T" when T
is not a class type. */
if (complain & tf_error)
r);
return error_mark_node;
}
-
- fntype = build_method_type_directly (r, return_type,
+
+ fntype = build_method_type_directly (r, return_type,
TREE_CHAIN (arg_types));
}
fntype = cp_build_qualified_type_real (fntype, TYPE_QUALS (t), complain);
fntype = cp_build_type_attribute_variant (fntype, TYPE_ATTRIBUTES (t));
-
- return fntype;
+
+ return fntype;
}
/* FNTYPE is a FUNCTION_TYPE or METHOD_TYPE. Substitute the template
specification. If there is no specification, return NULL_TREE. */
static tree
-tsubst_exception_specification (tree fntype,
- tree args,
+tsubst_exception_specification (tree fntype,
+ tree args,
tsubst_flags_t complain,
tree in_decl)
{
/* Substitute into the PARMS of a call-declarator. */
static tree
-tsubst_call_declarator_parms (tree parms,
- tree args,
- tsubst_flags_t complain,
+tsubst_call_declarator_parms (tree parms,
+ tree args,
+ tsubst_flags_t complain,
tree in_decl)
{
tree new_parms;
if (!parms || parms == void_list_node)
return parms;
-
+
new_parms = tsubst_call_declarator_parms (TREE_CHAIN (parms),
args, complain, in_decl);
/* Figure out the type of this parameter. */
type = tsubst (TREE_VALUE (parms), args, complain, in_decl);
-
+
/* Figure out the default argument as well. Note that we use
tsubst_expr since the default argument is really an expression. */
defarg = tsubst_expr (TREE_PURPOSE (parms), args, complain, in_decl);
if (pedantic)
pedwarn ("creating array with size zero");
}
- else if (integer_zerop (max)
- || (TREE_CODE (max) == INTEGER_CST
+ else if (integer_zerop (max)
+ || (TREE_CODE (max) == INTEGER_CST
&& INT_CST_LT (max, integer_zero_node)))
{
/* [temp.deduct]
Type deduction may fail for any of the following
- reasons:
+ reasons:
Attempting to create an array with a size that is
zero or negative. */
args, complain, in_decl);
if (argvec == error_mark_node)
return error_mark_node;
-
+
/* We can get a TEMPLATE_TEMPLATE_PARM here when we
are resolving nested-types in the signature of a
member function templates. Otherwise ARG is a
instantiated. */
if (TREE_CODE (arg) == TEMPLATE_TEMPLATE_PARM)
arg = TYPE_NAME (arg);
-
- r = lookup_template_class (arg,
- argvec, in_decl,
+
+ r = lookup_template_class (arg,
+ argvec, in_decl,
DECL_CONTEXT (arg),
/*entering_scope=*/0,
complain);
if (TREE_CODE (t) == BOUND_TEMPLATE_TEMPLATE_PARM)
{
tree argvec = tsubst (TYPE_TI_ARGS (t), args,
- complain, in_decl);
+ complain, in_decl);
if (argvec == error_mark_node)
return error_mark_node;
case TEMPLATE_PARM_INDEX:
r = reduce_template_parm_level (t, type, levels);
break;
-
+
default:
gcc_unreachable ();
}
return t;
return hash_tree_cons (purpose, value, chain);
}
-
+
case TREE_BINFO:
/* We should never be tsubsting a binfo. */
gcc_unreachable ();
/* [temp.deduct]
-
+
Type deduction may fail for any of the following
- reasons:
+ reasons:
-- Attempting to create a pointer to reference type.
-- Attempting to create a reference to a reference type or
if (r != error_mark_node)
/* Will this ever be needed for TYPE_..._TO values? */
layout_type (r);
-
+
return r;
}
case OFFSET_TYPE:
Type deduction may fail for any of the following
reasons:
-
+
-- Attempting to create "pointer to member of T" when T
is not a class type. */
if (complain & tf_error)
return error_mark_node;
/* Substitute the exception specification. */
- specs = tsubst_exception_specification (t, args, complain,
+ specs = tsubst_exception_specification (t, args, complain,
in_decl);
if (specs)
fntype = build_exception_variant (fntype, specs);
if (type == TREE_TYPE (t) && domain == TYPE_DOMAIN (t))
return t;
- /* These checks should match the ones in grokdeclarator.
+ /* These checks should match the ones in grokdeclarator.
- [temp.deduct]
-
- The deduction may fail for any of the following reasons:
+ [temp.deduct]
+
+ The deduction may fail for any of the following reasons:
-- Attempting to create an array with an element type that
- is void, a function type, or a reference type, or [DR337]
+ is void, a function type, or a reference type, or [DR337]
an abstract class type. */
- if (TREE_CODE (type) == VOID_TYPE
+ if (TREE_CODE (type) == VOID_TYPE
|| TREE_CODE (type) == FUNCTION_TYPE
|| TREE_CODE (type) == REFERENCE_TYPE)
{
if (CLASS_TYPE_P (type) && CLASSTYPE_PURE_VIRTUALS (type))
{
if (complain & tf_error)
- error ("creating array of %qT, which is an abstract class type",
+ error ("creating array of %qT, which is an abstract class type",
type);
- return error_mark_node;
+ return error_mark_node;
}
r = build_cplus_array_type (type, domain);
tree ctx = tsubst_aggr_type (TYPE_CONTEXT (t), args, complain,
in_decl, /*entering_scope=*/1);
tree f = tsubst_copy (TYPENAME_TYPE_FULLNAME (t), args,
- complain, in_decl);
+ complain, in_decl);
if (ctx == error_mark_node || f == error_mark_node)
return error_mark_node;
{
/* Normally, make_typename_type does not require that the CTX
have complete type in order to allow things like:
-
+
template <class T> struct S { typename S<T>::X Y; };
But, such constructs have already been resolved by this
complain |= tf_ignore_bad_quals;
f = TREE_TYPE (f);
}
-
+
if (TREE_CODE (f) != TYPENAME_TYPE)
{
if (TYPENAME_IS_ENUM_P (t) && TREE_CODE (f) != ENUMERAL_TYPE)
- error ("%qT resolves to %qT, which is not an enumeration type",
+ error ("%qT resolves to %qT, which is not an enumeration type",
t, f);
else if (TYPENAME_IS_CLASS_P (t) && !CLASS_TYPE_P (f))
- error ("%qT resolves to %qT, which is is not a class type",
+ error ("%qT resolves to %qT, which is is not a class type",
t, f);
}
return cp_build_qualified_type_real
(f, cp_type_quals (f) | cp_type_quals (t), complain);
}
-
+
case UNBOUND_CLASS_TEMPLATE:
{
tree ctx = tsubst_aggr_type (TYPE_CONTEXT (t), args, complain,
BASELINK_ACCESS_BINFO and BASELINK_BINFO are going to have
non-dependent types; otherwise, the lookup could not have
succeeded. However, they may indicate bases of the template
- class, rather than the instantiated class.
+ class, rather than the instantiated class.
In addition, lookups that were not ambiguous before may be
ambiguous now. Therefore, we perform the lookup again. */
}
name = DECL_NAME (get_first_fn (fns));
baselink = lookup_fnfields (qualifying_scope, name, /*protect=*/1);
-
+
/* If lookup found a single function, mark it as used at this
point. (If it lookup found multiple functions the one selected
later by overload resolution will be marked as used at that
/* Add back the template arguments, if present. */
if (BASELINK_P (baselink) && template_id_p)
- BASELINK_FUNCTIONS (baselink)
+ BASELINK_FUNCTIONS (baselink)
= build_nt (TEMPLATE_ID_EXPR,
BASELINK_FUNCTIONS (baselink),
template_args);
if (!object_type)
object_type = current_class_type;
- return adjust_result_of_qualified_name_lookup (baselink,
+ return adjust_result_of_qualified_name_lookup (baselink,
qualifying_scope,
object_type);
}
of "&". */
static tree
-tsubst_qualified_id (tree qualified_id, tree args,
+tsubst_qualified_id (tree qualified_id, tree args,
tsubst_flags_t complain, tree in_decl,
bool done, bool address_p)
{
if (dependent_type_p (scope))
return build_nt (SCOPE_REF, scope, expr);
-
+
if (!BASELINK_P (name) && !DECL_P (expr))
{
expr = lookup_qualified_name (scope, expr, /*is_type_p=*/0, false);
return error_mark_node;
}
}
-
+
if (DECL_P (expr))
{
check_accessibility_of_qualified_id (expr, /*object_type=*/NULL_TREE,
if (expr == error_mark_node || TREE_CODE (expr) == TREE_LIST)
{
if (complain & tf_error)
- qualified_name_lookup_error (scope,
+ qualified_name_lookup_error (scope,
TREE_OPERAND (qualified_id, 1),
expr);
return error_mark_node;
expr);
else if (TYPE_P (scope))
{
- expr = (adjust_result_of_qualified_name_lookup
+ expr = (adjust_result_of_qualified_name_lookup
(expr, scope, current_class_type));
expr = finish_qualified_id_expr (scope, expr, done, address_p);
}
-
+
expr = convert_from_reference (expr);
return expr;
/* Unfortunately, we cannot just call lookup_name here.
Consider:
-
+
template <int I> int f() {
enum E { a = I };
struct S { void g() { E e = a; } };
};
-
+
When we instantiate f<7>::S::g(), say, lookup_name is not
clever enough to find f<7>::a. */
- enum_type
- = tsubst_aggr_type (TREE_TYPE (t), args, complain, in_decl,
+ enum_type
+ = tsubst_aggr_type (TREE_TYPE (t), args, complain, in_decl,
/*entering_scope=*/0);
- for (v = TYPE_VALUES (enum_type);
- v != NULL_TREE;
+ for (v = TYPE_VALUES (enum_type);
+ v != NULL_TREE;
v = TREE_CHAIN (v))
if (TREE_PURPOSE (v) == DECL_NAME (t))
return TREE_VALUE (v);
return r;
}
}
-
+
return t;
case VAR_DECL:
case TEMPLATE_DECL:
if (DECL_TEMPLATE_TEMPLATE_PARM_P (t))
- return tsubst (TREE_TYPE (DECL_TEMPLATE_RESULT (t)),
+ return tsubst (TREE_TYPE (DECL_TEMPLATE_RESULT (t)),
args, complain, in_decl);
else if (DECL_FUNCTION_TEMPLATE_P (t) && DECL_MEMBER_TEMPLATE_P (t))
return tsubst (t, args, complain, in_decl);
object = tsubst_copy (TREE_OPERAND (t, 0), args, complain, in_decl);
name = TREE_OPERAND (t, 1);
- if (TREE_CODE (name) == BIT_NOT_EXPR)
+ if (TREE_CODE (name) == BIT_NOT_EXPR)
{
name = tsubst_copy (TREE_OPERAND (name, 0), args,
complain, in_decl);
name = build_nt (SCOPE_REF, base, name);
}
else if (TREE_CODE (name) == BASELINK)
- name = tsubst_baselink (name,
- non_reference (TREE_TYPE (object)),
- args, complain,
+ name = tsubst_baselink (name,
+ non_reference (TREE_TYPE (object)),
+ args, complain,
in_decl);
else
name = tsubst_copy (name, args, complain, in_decl);
NULL_TREE, NULL_TREE);
case CALL_EXPR:
- return build_nt (code,
+ return build_nt (code,
tsubst_copy (TREE_OPERAND (t, 0), args,
complain, in_decl),
tsubst_copy (TREE_OPERAND (t, 1), args, complain,
fn = tsubst_copy (fn, args, complain, in_decl);
if (targs)
targs = tsubst_template_args (targs, args, complain, in_decl);
-
+
return lookup_template_function (fn, targs);
}
case CONSTRUCTOR:
{
r = build_constructor
- (tsubst (TREE_TYPE (t), args, complain, in_decl),
+ (tsubst (TREE_TYPE (t), args, complain, in_decl),
tsubst_copy (CONSTRUCTOR_ELTS (t), args, complain, in_decl));
TREE_HAS_CONSTRUCTOR (r) = TREE_HAS_CONSTRUCTOR (t);
return r;
}
case CTOR_INITIALIZER:
- finish_mem_initializers (tsubst_initializer_list
+ finish_mem_initializers (tsubst_initializer_list
(TREE_OPERAND (t, 0), args));
break;
do_using_directive (tsubst_expr (USING_STMT_NAMESPACE (t),
args, complain, in_decl));
break;
-
+
case DECL_EXPR:
{
tree decl;
tree scope = USING_DECL_SCOPE (decl);
tree name = DECL_NAME (decl);
tree decl;
-
+
scope = tsubst_expr (scope, args, complain, in_decl);
decl = lookup_qualified_name (scope, name,
/*is_type_p=*/false,
&& ANON_AGGR_TYPE_P (TREE_TYPE (decl)))
/* Anonymous aggregates are a special case. */
finish_anon_union (decl);
- else
+ else
{
maybe_push_decl (decl);
if (TREE_CODE (decl) == VAR_DECL
(ASM_VOLATILE_P (t),
tsubst_expr (ASM_STRING (t), args, complain, in_decl),
tsubst_expr (ASM_OUTPUTS (t), args, complain, in_decl),
- tsubst_expr (ASM_INPUTS (t), args, complain, in_decl),
+ tsubst_expr (ASM_INPUTS (t), args, complain, in_decl),
tsubst_expr (ASM_CLOBBERS (t), args, complain, in_decl));
{
tree asm_expr = tmp;
finish_handler_sequence (stmt);
}
break;
-
+
case HANDLER:
{
tree decl;
default:
gcc_assert (!STATEMENT_CODE_P (TREE_CODE (t)));
-
+
return tsubst_copy_and_build (t, args, complain, in_decl,
/*function_p=*/false);
}
call. Return the substituted version of T. */
static tree
-tsubst_non_call_postfix_expression (tree t, tree args,
+tsubst_non_call_postfix_expression (tree t, tree args,
tsubst_flags_t complain,
tree in_decl)
{
analysis. FUNCTION_P is true if T is the "F" in "F (ARGS)". */
tree
-tsubst_copy_and_build (tree t,
- tree args,
- tsubst_flags_t complain,
+tsubst_copy_and_build (tree t,
+ tree args,
+ tsubst_flags_t complain,
tree in_decl,
bool function_p)
{
if (targs)
targs = tsubst_template_args (targs, args, complain, in_decl);
-
+
if (TREE_CODE (template) == COMPONENT_REF)
{
object = TREE_OPERAND (template, 0);
else
object = NULL_TREE;
template = lookup_template_function (template, targs);
-
+
if (object)
- return build3 (COMPONENT_REF, TREE_TYPE (template),
+ return build3 (COMPONENT_REF, TREE_TYPE (template),
object, template, NULL_TREE);
else
return template;
case ADDR_EXPR:
op1 = TREE_OPERAND (t, 0);
if (TREE_CODE (op1) == SCOPE_REF)
- op1 = tsubst_qualified_id (op1, args, complain, in_decl,
+ op1 = tsubst_qualified_id (op1, args, complain, in_decl,
/*done=*/true, /*address_p=*/true);
else
- op1 = tsubst_non_call_postfix_expression (op1, args, complain,
+ op1 = tsubst_non_call_postfix_expression (op1, args, complain,
in_decl);
if (TREE_CODE (op1) == LABEL_DECL)
return finish_label_address_expr (DECL_NAME (op1));
case MEMBER_REF:
case DOTSTAR_EXPR:
return build_x_binary_op
- (TREE_CODE (t),
+ (TREE_CODE (t),
RECUR (TREE_OPERAND (t, 0)),
RECUR (TREE_OPERAND (t, 1)),
/*overloaded_p=*/NULL);
args, complain, in_decl);
return build_x_binary_op (ARRAY_REF, op1, RECUR (TREE_OPERAND (t, 1)),
/*overloaded_p=*/NULL);
-
+
case SIZEOF_EXPR:
case ALIGNOF_EXPR:
op1 = TREE_OPERAND (t, 0);
{
qualified_p = true;
function = tsubst_qualified_id (function, args, complain, in_decl,
- /*done=*/false,
+ /*done=*/false,
/*address_p=*/false);
}
else
qualified_p = (TREE_CODE (function) == COMPONENT_REF
&& (TREE_CODE (TREE_OPERAND (function, 1))
== SCOPE_REF));
- function = tsubst_copy_and_build (function, args, complain,
+ function = tsubst_copy_and_build (function, args, complain,
in_decl,
!qualified_p);
if (BASELINK_P (function))
/*disallow_virtual=*/false,
/*koenig_p=*/false);
else
- return (build_new_method_call
+ return (build_new_method_call
(TREE_OPERAND (function, 0),
TREE_OPERAND (function, 1),
- call_args, NULL_TREE,
+ call_args, NULL_TREE,
qualified_p ? LOOKUP_NONVIRTUAL : LOOKUP_NORMAL));
}
- return finish_call_expr (function, call_args,
+ return finish_call_expr (function, call_args,
/*disallow_virtual=*/qualified_p,
koenig_p);
}
RECUR (TREE_OPERAND (t, 2)));
case PSEUDO_DTOR_EXPR:
- return finish_pseudo_destructor_expr
+ return finish_pseudo_destructor_expr
(RECUR (TREE_OPERAND (t, 0)),
RECUR (TREE_OPERAND (t, 1)),
RECUR (TREE_OPERAND (t, 2)));
member = TREE_OPERAND (t, 1);
if (BASELINK_P (member))
- member = tsubst_baselink (member,
+ member = tsubst_baselink (member,
non_reference (TREE_TYPE (object)),
args, complain, in_decl);
else
else if (!CLASS_TYPE_P (TREE_TYPE (object)))
{
if (TREE_CODE (member) == BIT_NOT_EXPR)
- return finish_pseudo_destructor_expr (object,
+ return finish_pseudo_destructor_expr (object,
NULL_TREE,
TREE_TYPE (object));
else if (TREE_CODE (member) == SCOPE_REF
&& (TREE_CODE (TREE_OPERAND (member, 1)) == BIT_NOT_EXPR))
- return finish_pseudo_destructor_expr (object,
+ return finish_pseudo_destructor_expr (object,
object,
TREE_TYPE (object));
}
{
tree tmpl;
tree args;
-
+
/* Lookup the template functions now that we know what the
scope is. */
tmpl = TREE_OPERAND (TREE_OPERAND (member, 1), 0);
args = TREE_OPERAND (TREE_OPERAND (member, 1), 1);
- member = lookup_qualified_name (TREE_OPERAND (member, 0), tmpl,
+ member = lookup_qualified_name (TREE_OPERAND (member, 0), tmpl,
/*is_type_p=*/false,
/*complain=*/false);
if (BASELINK_P (member))
{
- BASELINK_FUNCTIONS (member)
+ BASELINK_FUNCTIONS (member)
= build_nt (TEMPLATE_ID_EXPR, BASELINK_FUNCTIONS (member),
args);
- member = (adjust_result_of_qualified_name_lookup
- (member, BINFO_TYPE (BASELINK_BINFO (member)),
+ member = (adjust_result_of_qualified_name_lookup
+ (member, BINFO_TYPE (BASELINK_BINFO (member)),
TREE_TYPE (object)));
}
else
if (complain & tf_error)
{
if (TYPE_P (TREE_OPERAND (member, 0)))
- error ("%qT is not a class or namespace",
+ error ("%qT is not a class or namespace",
TREE_OPERAND (member, 0));
else
- error ("%qD is not a class or namespace",
+ error ("%qD is not a class or namespace",
TREE_OPERAND (member, 0));
}
return error_mark_node;
{
tree purpose = TREE_PURPOSE (elts);
tree value = TREE_VALUE (elts);
-
+
if (purpose && purpose_p)
purpose = RECUR (purpose);
value = RECUR (value);
r = tree_cons (purpose, value, r);
}
-
+
r = build_constructor (NULL_TREE, nreverse (r));
TREE_HAS_CONSTRUCTOR (r) = TREE_HAS_CONSTRUCTOR (t);
if (!args)
return t;
/* Fall through */
-
+
case PARM_DECL:
{
tree r = tsubst_copy (t, args, complain, in_decl);
-
+
if (TREE_CODE (TREE_TYPE (t)) != REFERENCE_TYPE)
/* If the original type was a reference, we'll be wrapped in
the appropriate INDIRECT_REF. */
case VA_ARG_EXPR:
return build_x_va_arg (RECUR (TREE_OPERAND (t, 0)),
- tsubst_copy (TREE_TYPE (t), args, complain,
+ tsubst_copy (TREE_TYPE (t), args, complain,
in_decl));
case OFFSETOF_EXPR:
for (ix = 0; ix != len; ix++)
{
tree t = TREE_VEC_ELT (args, ix);
-
+
if (TYPE_P (t))
{
/* [basic.link]: A name with no linkage (notably, the name
{
tree spec;
tree clone;
-
+
spec = instantiate_template (DECL_CLONED_FUNCTION (tmpl), targ_ptr,
complain);
if (spec == error_mark_node)
gcc_unreachable ();
return NULL_TREE;
}
-
+
/* Check to see if we already have this specialization. */
- spec = retrieve_specialization (tmpl, targ_ptr,
+ spec = retrieve_specialization (tmpl, targ_ptr,
/*class_specializations_p=*/false);
if (spec != NULL_TREE)
return spec;
if (check_instantiated_args (gen_tmpl, INNERMOST_TEMPLATE_ARGS (targ_ptr),
complain))
return error_mark_node;
-
+
/* We are building a FUNCTION_DECL, during which the access of its
parameters and return types have to be checked. However this
FUNCTION_DECL which is the desired context for access checking
/* The FN is a TEMPLATE_DECL for a function. The ARGS are the
arguments that are being used when calling it. TARGS is a vector
- into which the deduced template arguments are placed.
+ into which the deduced template arguments are placed.
Return zero for success, 2 for an incomplete match that doesn't resolve
all the types, and 1 for complete failure. An error message will be
The parameter STRICT is one of:
- DEDUCE_CALL:
+ DEDUCE_CALL:
We are deducing arguments for a function call, as in
[temp.deduct.call].
DEDUCE_CONV:
- We are deducing arguments for a conversion function, as in
+ We are deducing arguments for a conversion function, as in
[temp.deduct.conv].
DEDUCE_EXACT:
template, as in [temp.deduct.funcaddr]. */
int
-fn_type_unification (tree fn,
- tree explicit_targs,
- tree targs,
- tree args,
+fn_type_unification (tree fn,
+ tree explicit_targs,
+ tree targs,
+ tree args,
tree return_type,
unification_kind_t strict)
{
if (explicit_targs)
{
/* [temp.deduct]
-
+
The specified template arguments must match the template
parameters in kind (i.e., type, nontype, template), and there
must not be more arguments than there are parameters;
return 1;
converted_args
- = (coerce_template_parms (DECL_INNERMOST_TEMPLATE_PARMS (fn),
- explicit_targs, NULL_TREE, tf_none,
+ = (coerce_template_parms (DECL_INNERMOST_TEMPLATE_PARMS (fn),
+ explicit_targs, NULL_TREE, tf_none,
/*require_all_arguments=*/0));
if (converted_args == error_mark_node)
return 1;
processing_template_decl += incomplete;
fntype = tsubst (fntype, converted_args, tf_none, NULL_TREE);
processing_template_decl -= incomplete;
-
+
if (fntype == error_mark_node)
return 1;
for (i = NUM_TMPL_ARGS (converted_args); i--;)
TREE_VEC_ELT (targs, i) = TREE_VEC_ELT (converted_args, i);
}
-
+
parms = TYPE_ARG_TYPES (fntype);
/* Never do unification on the 'this' parameter. */
if (DECL_NONSTATIC_MEMBER_FUNCTION_P (fn))
parms = TREE_CHAIN (parms);
-
+
if (return_type)
{
/* We've been given a return type to match, prepend it. */
because the standard doesn't seem to explicitly prohibit it. Our
callers must be ready to deal with unification failures in any
event. */
- result = type_unification_real (DECL_INNERMOST_TEMPLATE_PARMS (fn),
+ result = type_unification_real (DECL_INNERMOST_TEMPLATE_PARMS (fn),
targs, parms, args, /*subr=*/0,
strict, /*allow_incomplete*/1);
- if (result == 0)
+ if (result == 0)
/* All is well so far. Now, check:
-
- [temp.deduct]
-
+
+ [temp.deduct]
+
When all template arguments have been deduced, all uses of
template parameters in nondeduced contexts are replaced with
the corresponding deduced argument values. If the
initialized with the result of the conversion function. */
static int
-maybe_adjust_types_for_deduction (unification_kind_t strict,
- tree* parm,
+maybe_adjust_types_for_deduction (unification_kind_t strict,
+ tree* parm,
tree* arg)
{
int result = 0;
-
+
switch (strict)
{
case DEDUCE_CALL:
if (TREE_CODE (*parm) != REFERENCE_TYPE)
{
/* [temp.deduct.call]
-
+
If P is not a reference type:
-
+
--If A is an array type, the pointer type produced by the
array-to-pointer standard conversion (_conv.array_) is
used in place of A for type deduction; otherwise,
-
+
--If A is a function type, the pointer type produced by
the function-to-pointer standard conversion
(_conv.func_) is used in place of A for type deduction;
otherwise,
-
+
--If A is a cv-qualified type, the top level
cv-qualifiers of A's type are ignored for type
deduction. */
else
*arg = TYPE_MAIN_VARIANT (*arg);
}
-
+
/* [temp.deduct.call]
-
+
If P is a cv-qualified type, the top level cv-qualifiers
of P's type are ignored for type deduction. If P is a
reference type, the type referred to by P is used for
too (which has been swapped into ARG). */
if (strict == DEDUCE_CONV && TREE_CODE (*arg) == REFERENCE_TYPE)
*arg = TREE_TYPE (*arg);
-
+
return result;
}
template). */
static int
-type_unification_real (tree tparms,
- tree targs,
- tree xparms,
- tree xargs,
+type_unification_real (tree tparms,
+ tree targs,
+ tree xparms,
+ tree xargs,
int subr,
- unification_kind_t strict,
+ unification_kind_t strict,
int allow_incomplete)
{
tree parm, arg;
sub_strict = (UNIFY_ALLOW_OUTER_LEVEL | UNIFY_ALLOW_MORE_CV_QUAL
| UNIFY_ALLOW_DERIVED);
break;
-
+
case DEDUCE_CONV:
sub_strict = UNIFY_ALLOW_LESS_CV_QUAL;
break;
case DEDUCE_EXACT:
sub_strict = UNIFY_ALLOW_NONE;
break;
-
+
default:
gcc_unreachable ();
}
return 1;
}
-
+
if (!TYPE_P (arg))
{
gcc_assert (TREE_TYPE (arg) != NULL_TREE);
if (arg == error_mark_node)
return 1;
}
-
+
{
int arg_strict = sub_strict;
-
+
if (!subr)
arg_strict |= maybe_adjust_types_for_deduction (strict, &parm, &arg);
return 1;
}
}
-
+
/* Fail if we've reached the end of the parm list, and more args
are present, and the parm list isn't variadic. */
if (args && args != void_list_node && parms == void_list_node)
error ("incomplete type unification");
return 2;
}
-
+
return 0;
}
succeeds, we go with that. Modifies TARGS and returns 0 on success. */
static int
-resolve_overloaded_unification (tree tparms,
+resolve_overloaded_unification (tree tparms,
tree targs,
tree parm,
- tree arg,
+ tree arg,
unification_kind_t strict,
int sub_strict)
{
if (subargs)
{
elem = tsubst (TREE_TYPE (fn), subargs, tf_none, NULL_TREE);
- good += try_one_overload (tparms, targs, tempargs, parm,
+ good += try_one_overload (tparms, targs, tempargs, parm,
elem, strict, sub_strict, addr_p);
}
}
{
gcc_assert (TREE_CODE (arg) == OVERLOAD
|| TREE_CODE (arg) == FUNCTION_DECL);
-
+
for (; arg; arg = OVL_NEXT (arg))
good += try_one_overload (tparms, targs, tempargs, parm,
TREE_TYPE (OVL_CURRENT (arg)),
static int
try_one_overload (tree tparms,
tree orig_targs,
- tree targs,
- tree parm,
- tree arg,
+ tree targs,
+ tree parm,
+ tree arg,
unification_kind_t strict,
int sub_strict,
bool addr_p)
tree copy_of_targs;
if (!CLASSTYPE_TEMPLATE_INFO (arg)
- || (most_general_template (CLASSTYPE_TI_TEMPLATE (arg))
+ || (most_general_template (CLASSTYPE_TI_TEMPLATE (arg))
!= most_general_template (CLASSTYPE_TI_TEMPLATE (parm))))
return NULL_TREE;
template <int I, int J, int K>
struct S {};
-
+
template <int I, int J>
struct S<I, J, 2> : public S<I, I, I>, S<J, J, J> {};
-
+
template <int I, int J, int K>
void f(S<I, J, K>, S<I, I, I>);
-
+
void g() {
S<0, 0, 0> s0;
S<0, 1, 2> s2;
-
+
f(s0, s2);
}
with S<I, I, I>. If we kept the already deduced knowledge, we
would reject the possibility I=1. */
copy_of_targs = make_tree_vec (TREE_VEC_LENGTH (targs));
-
+
/* If unification failed, we're done. */
if (unify (tparms, copy_of_targs, CLASSTYPE_TI_ARGS (parm),
CLASSTYPE_TI_ARGS (arg), UNIFY_ALLOW_NONE))
tree binfo;
gcc_assert (IS_AGGR_TYPE_CODE (TREE_CODE (arg)));
-
+
binfo = TYPE_BINFO (complete_type (arg));
if (!binfo)
/* The type could not be completed. */
applies. */
if (rval && !same_type_p (r, rval))
return NULL_TREE;
-
+
rval = r;
}
}
ARG.
UNIFY_ALLOW_INTEGER:
Allow any integral type to be deduced. See the TEMPLATE_PARM_INDEX
- case for more information.
+ case for more information.
UNIFY_ALLOW_OUTER_LEVEL:
This is the outermost level of a deduction. Used to determine validity
of qualification conversions. A valid qualification conversion must
strict &= ~UNIFY_ALLOW_DERIVED;
strict &= ~UNIFY_ALLOW_OUTER_MORE_CV_QUAL;
strict &= ~UNIFY_ALLOW_OUTER_LESS_CV_QUAL;
-
+
switch (TREE_CODE (parm))
{
case TYPENAME_TYPE:
/* Check for mixed types and values. */
if ((TREE_CODE (parm) == TEMPLATE_TYPE_PARM
&& TREE_CODE (tparm) != TYPE_DECL)
- || (TREE_CODE (parm) == TEMPLATE_TEMPLATE_PARM
+ || (TREE_CODE (parm) == TEMPLATE_TEMPLATE_PARM
&& TREE_CODE (tparm) != TEMPLATE_DECL))
return 1;
= DECL_INNERMOST_TEMPLATE_PARMS (TYPE_TI_TEMPLATE (arg));
int i;
- /* The parameter and argument roles have to be switched here
- in order to handle default arguments properly. For example,
- template<template <class> class TT> void f(TT<int>)
- should be able to accept vector<int> which comes from
- template <class T, class Allocator = allocator>
+ /* The parameter and argument roles have to be switched here
+ in order to handle default arguments properly. For example,
+ template<template <class> class TT> void f(TT<int>)
+ should be able to accept vector<int> which comes from
+ template <class T, class Allocator = allocator>
class vector. */
if (coerce_template_parms (argtmplvec, parmvec, parmtmpl, 0, 1)
== error_mark_node)
return 1;
-
- /* Deduce arguments T, i from TT<T> or TT<i>.
+
+ /* Deduce arguments T, i from TT<T> or TT<i>.
We check each element of PARMVEC and ARGVEC individually
rather than the whole TREE_VEC since they can have
different number of elements. */
for (i = 0; i < TREE_VEC_LENGTH (parmvec); ++i)
{
- if (unify (tparms, targs,
- TREE_VEC_ELT (parmvec, i),
- TREE_VEC_ELT (argvec, i),
+ if (unify (tparms, targs,
+ TREE_VEC_ELT (parmvec, i),
+ TREE_VEC_ELT (argvec, i),
UNIFY_ALLOW_NONE))
return 1;
}
a match unless we are allowing additional qualification.
If ARG is `const int' and PARM is just `T' that's OK;
that binds `const int' to `T'. */
- if (!check_cv_quals_for_unify (strict_in | UNIFY_ALLOW_LESS_CV_QUAL,
+ if (!check_cv_quals_for_unify (strict_in | UNIFY_ALLOW_LESS_CV_QUAL,
arg, parm))
return 1;
case TEMPLATE_PARM_INDEX:
tparm = TREE_VALUE (TREE_VEC_ELT (tparms, 0));
- if (TEMPLATE_PARM_LEVEL (parm)
+ if (TEMPLATE_PARM_LEVEL (parm)
!= template_decl_level (tparm))
/* The PARM is not one we're trying to unify. Just check
to see if it matches ARG. */
parameter-list and, if the corresponding template-argument is
deduced, the template-argument type shall match the type of the
template-parameter exactly, except that a template-argument
- deduced from an array bound may be of any integral type.
+ deduced from an array bound may be of any integral type.
The non-type parameter might use already deduced type parameters. */
tparm = tsubst (TREE_TYPE (parm), targs, 0, NULL_TREE);
if (!TREE_TYPE (arg))
{
if (TREE_CODE (arg) != POINTER_TYPE)
return 1;
-
+
/* [temp.deduct.call]
A can be another pointer or pointer to member type that can
We pass down STRICT here rather than UNIFY_ALLOW_NONE.
This will allow for additional cv-qualification of the
pointed-to types if appropriate. */
-
+
if (TREE_CODE (TREE_TYPE (arg)) == RECORD_TYPE)
/* The derived-to-base conversion only persists through one
level of pointers. */
strict |= (strict_in & UNIFY_ALLOW_DERIVED);
- return unify (tparms, targs, TREE_TYPE (parm),
+ return unify (tparms, targs, TREE_TYPE (parm),
TREE_TYPE (arg), strict);
}
not an integer constant. */
if (TREE_CODE (parm_max) == MINUS_EXPR)
{
- arg_max = fold_build2 (PLUS_EXPR,
+ arg_max = fold_build2 (PLUS_EXPR,
integer_type_node,
arg_max,
TREE_OPERAND (parm_max, 1));
case VOID_TYPE:
if (TREE_CODE (arg) != TREE_CODE (parm))
return 1;
-
+
/* We have already checked cv-qualification at the top of the
function. */
if (!same_type_ignoring_top_level_qualifiers_p (arg, parm))
case UNION_TYPE:
if (TREE_CODE (arg) != TREE_CODE (parm))
return 1;
-
+
if (TYPE_PTRMEMFUNC_P (parm))
{
if (!TYPE_PTRMEMFUNC_P (arg))
return 1;
- return unify (tparms, targs,
+ return unify (tparms, targs,
TYPE_PTRMEMFUNC_FN_TYPE (parm),
TYPE_PTRMEMFUNC_FN_TYPE (arg),
strict);
{
/* Fallback to the special case allowed in
[temp.deduct.call]:
-
+
If P is a class, and P has the form
template-id, then A can be a derived class of
the deduced A. Likewise, if P is a pointer to
return 1;
}
}
- else if (CLASSTYPE_TEMPLATE_INFO (arg)
- && (CLASSTYPE_TI_TEMPLATE (parm)
+ else if (CLASSTYPE_TEMPLATE_INFO (arg)
+ && (CLASSTYPE_TI_TEMPLATE (parm)
== CLASSTYPE_TI_TEMPLATE (arg)))
/* Perhaps PARM is something like S<U> and ARG is S<int>.
Then, we should unify `int' and `U'. */
TREE_TYPE (arg), UNIFY_ALLOW_NONE))
return 1;
return type_unification_real (tparms, targs, TYPE_ARG_TYPES (parm),
- TYPE_ARG_TYPES (arg), 1,
+ TYPE_ARG_TYPES (arg), 1,
DEDUCE_EXACT, 0);
case OFFSET_TYPE:
/* Determine the type of the function we are unifying against. */
method_type = TREE_TYPE (TYPE_PTRMEMFUNC_FN_TYPE (arg));
- fntype =
+ fntype =
build_function_type (TREE_TYPE (method_type),
TREE_CHAIN (TYPE_ARG_TYPES (method_type)));
/* Extract the cv-qualifiers of the member function from the
implicit object parameter and place them on the function
type to be restored later. */
- cv_quals =
+ cv_quals =
cp_type_quals(TREE_TYPE (TREE_VALUE (TYPE_ARG_TYPES (method_type))));
fntype = build_qualified_type (fntype, cv_quals);
return unify (tparms, targs, TREE_TYPE (parm), fntype, strict);
case CONST_DECL:
if (DECL_TEMPLATE_PARM_P (parm))
return unify (tparms, targs, DECL_INITIAL (parm), arg, strict);
- if (arg != integral_constant_value (parm))
+ if (arg != integral_constant_value (parm))
return 1;
return 0;
default:
gcc_assert (EXPR_P (parm));
-
+
/* We must be looking at an expression. This can happen with
- something like:
-
+ something like:
+
template <int I>
void foo(S<I>, S<I + 2>);
This is a "nondeduced context":
[deduct.type]
-
+
The nondeduced contexts are:
--A type that is a template-id in which one or more of
the template-arguments is an expression that references
- a template-parameter.
+ a template-parameter.
In these cases, we assume deduction succeeded, but don't
actually infer any unifications. */
else if (TREE_PUBLIC (result))
maybe_make_one_only (result);
}
-
+
/* If EXTERN_P, then this function will not be emitted -- unless
followed by an explicit instantiation, at which point its linkage
will be adjusted. If !EXTERN_P, then this function will be
emitted here. In neither circumstance do we want
import_export_decl to adjust the linkage. */
- DECL_INTERFACE_KNOWN (result) = 1;
+ DECL_INTERFACE_KNOWN (result) = 1;
}
/* Given two function templates PAT1 and PAT2, return:
we do *not* verify the deduced template argument values can be
substituted into non-deduced contexts, nor do we have to verify
that all template arguments have been deduced. */
-
+
int
more_specialized_fn (tree pat1, tree pat2, int len)
{
/* If only one is a member function, they are unordered. */
if (DECL_FUNCTION_MEMBER_P (decl1) != DECL_FUNCTION_MEMBER_P (decl2))
return 0;
-
+
/* Don't consider 'this' parameter. */
if (DECL_NONSTATIC_MEMBER_FUNCTION_P (decl1))
args1 = TREE_CHAIN (args1);
/* If only one is a conversion operator, they are unordered. */
if (DECL_CONV_FN_P (decl1) != DECL_CONV_FN_P (decl2))
return 0;
-
+
/* Consider the return type for a conversion function */
if (DECL_CONV_FN_P (decl1))
{
args2 = tree_cons (NULL_TREE, TREE_TYPE (TREE_TYPE (decl2)), args2);
len++;
}
-
+
processing_template_decl++;
-
+
while (len--)
{
tree arg1 = TREE_VALUE (args1);
arg1 = TREE_TYPE (arg1);
quals1 = cp_type_quals (arg1);
}
-
+
if (TREE_CODE (arg2) == REFERENCE_TYPE)
{
arg2 = TREE_TYPE (arg2);
case FUNCTION_TYPE:
arg1 = build_pointer_type (arg1);
break;
-
+
default:
break;
}
case FUNCTION_TYPE:
arg2 = build_pointer_type (arg2);
break;
-
+
default:
break;
}
}
}
-
+
arg1 = TYPE_MAIN_VARIANT (arg1);
arg2 = TYPE_MAIN_VARIANT (arg2);
-
+
deduce1 = !unify (tparms1, targs1, arg1, arg2, UNIFY_ALLOW_NONE);
deduce2 = !unify (tparms2, targs2, arg2, arg1, UNIFY_ALLOW_NONE);
/* We've failed to deduce something in either direction.
These must be unordered. */
break;
-
+
if (deduce1 && deduce2 && quals1 >= 0 && quals2 >= 0)
{
/* Deduces in both directions, see if quals can
better2 = 1;
if (deduce2 && !deduce1 && !better1)
better1 = 1;
-
+
args1 = TREE_CHAIN (args1);
args2 = TREE_CHAIN (args2);
}
FULL_ARGS is the full set of template arguments that triggers this
partial ordering. */
-
+
int
more_specialized_class (tree pat1, tree pat2, tree full_args)
{
tree targs;
int winner = 0;
- /* Just like what happens for functions, if we are ordering between
+ /* Just like what happens for functions, if we are ordering between
different class template specializations, we may encounter dependent
types in the arguments, and we need our dependency check functions
to behave correctly. */
arguments EXPLICIT_ARGS. If CHECK_RETTYPE is true, the return type must
also match. Return NULL_TREE if no satisfactory arguments could be
found. */
-
+
static tree
get_bindings (tree fn, tree decl, tree explicit_args, bool check_rettype)
{
tf_none, /*require_all_arguments=*/0));
if (converted_args == error_mark_node)
return NULL_TREE;
-
- decl_type = tsubst (decl_type, converted_args, tf_none, NULL_TREE);
+
+ decl_type = tsubst (decl_type, converted_args, tf_none, NULL_TREE);
if (decl_type == error_mark_node)
return NULL_TREE;
}
if (DECL_NONSTATIC_MEMBER_FUNCTION_P (decl))
decl_arg_types = TREE_CHAIN (decl_arg_types);
- if (fn_type_unification (fn, explicit_args, targs,
+ if (fn_type_unification (fn, explicit_args, targs,
decl_arg_types,
(check_rettype || DECL_CONV_FN_P (fn)
? TREE_TYPE (decl_type) : NULL_TREE),
/* Return the innermost template arguments that, when applied to a
template specialization whose innermost template parameters are
TPARMS, and whose specialization arguments are PARMS, yield the
- ARGS.
+ ARGS.
For example, suppose we have:
if (!instantiations)
return NULL_TREE;
-
+
++processing_template_decl;
-
+
champ = instantiations;
for (fn = TREE_CHAIN (instantiations); fn; fn = TREE_CHAIN (fn))
{
int fate = 0;
-
+
if (get_bindings (TREE_VALUE (champ),
DECL_TEMPLATE_RESULT (TREE_VALUE (fn)),
NULL_TREE, /*check_ret=*/false))
DECL_TEMPLATE_RESULT (TREE_VALUE (champ)),
NULL_TREE, /*check_ret=*/false))
fate++;
-
+
if (fate != 1)
{
if (!fate)
champ = fn;
}
}
-
+
if (champ)
/* Now verify that champ is better than everything earlier in the
instantiation list. */
champ = NULL_TREE;
break;
}
-
+
processing_template_decl--;
-
+
if (!champ)
return error_mark_node;
tmpl = most_general_template (tmpl);
for (t = DECL_TEMPLATE_SPECIALIZATIONS (tmpl); t; t = TREE_CHAIN (t))
{
- tree spec_args
+ tree spec_args
= get_class_bindings (TREE_VALUE (t), TREE_PURPOSE (t), args);
if (spec_args)
{
/* [temp.spec]
No program shall explicitly instantiate any template more
- than once.
+ than once.
We check DECL_NOT_REALLY_EXTERN so as not to complain when
the first instantiation was `extern' and the second is not,
CLASSTYPE_DEBUG_REQUESTED (t) = 1;
rest_of_type_compilation (t, 1);
}
-}
+}
/* Called from do_type_instantiation through binding_table_foreach to
do recursive instantiation for the type bound in ENTRY. */
non-null, is the RID for extern, inline or static. COMPLAIN is
nonzero if this is called from the parser, zero if called recursively,
since the standard is unclear (as detailed below). */
-
+
void
do_type_instantiation (tree t, tree storage, tsubst_flags_t complain)
{
if (storage != NULL_TREE)
{
if (pedantic && !in_system_header)
- pedwarn("ISO C++ forbids the use of %qE on explicit instantiations",
+ pedwarn("ISO C++ forbids the use of %qE on explicit instantiations",
storage);
if (storage == ridpointers[(int) RID_INLINE])
/* [temp.spec]
No program shall explicitly instantiate any template more
- than once.
+ than once.
If PREVIOUS_INSTANTIATION_EXTERN_P, then the first explicit
instantiation was `extern'. If EXTERN_P then the second is.
if (!previous_instantiation_extern_p && !extern_p
&& (complain & tf_error))
pedwarn ("duplicate explicit instantiation of %q#T", t);
-
+
/* If we've already instantiated the template, just return now. */
if (!CLASSTYPE_INTERFACE_ONLY (t))
return;
The explicit instantiation of a class template specialization
implies the instantiation of all of its members not
previously explicitly specialized in the translation unit
- containing the explicit instantiation.
+ containing the explicit instantiation.
Of course, we can't instantiate member template classes, since
we don't have any arguments for them. Note that the standard
tree specs;
int args_depth;
int parms_depth;
-
+
args_depth = TMPL_ARGS_DEPTH (args);
- parms_depth = TMPL_PARMS_DEPTH (DECL_TEMPLATE_PARMS (tmpl));
+ parms_depth = TMPL_PARMS_DEPTH (DECL_TEMPLATE_PARMS (tmpl));
if (args_depth > parms_depth)
args = get_innermost_template_args (args, parms_depth);
specs);
/* Merge parameter declarations. */
- decl_parm = skip_artificial_parms_for (decl,
+ decl_parm = skip_artificial_parms_for (decl,
DECL_ARGUMENTS (decl));
- pattern_parm
+ pattern_parm
= skip_artificial_parms_for (code_pattern,
DECL_ARGUMENTS (code_pattern));
while (decl_parm)
{
if (!DECL_INITIALIZED_IN_CLASS_P (decl)
&& DECL_INITIAL (code_pattern))
- DECL_INITIAL (decl) =
- tsubst_expr (DECL_INITIAL (code_pattern), args,
+ DECL_INITIAL (decl) =
+ tsubst_expr (DECL_INITIAL (code_pattern), args,
tf_error, DECL_TI_TEMPLATE (decl));
}
else
DECL_TEMPLATE_INSTANTIATION (tmpl)
/* We must also deal with friend templates. Given:
- template <class T> struct S {
+ template <class T> struct S {
template <class U> friend void f() {};
};
where we get the pattern for the instantiation from. On
other hand, if the definition comes outside the class, say:
- template <class T> struct S {
+ template <class T> struct S {
template <class U> friend void f();
};
template <class U> friend void f() {}
a specialization was declared, but not defined. */
gcc_assert (TREE_CODE (decl) != VAR_DECL
|| DECL_IN_AGGR_P (DECL_TEMPLATE_RESULT (tmpl)));
-
+
/* Fetch the more general template. */
tmpl = DECL_TI_TEMPLATE (tmpl);
}
int pattern_defined;
int need_push;
location_t saved_loc = input_location;
-
+
/* This function should only be used to instantiate templates for
functions and static member variables. */
gcc_assert (TREE_CODE (d) == FUNCTION_DECL
/* Unless an explicit instantiation directive has already determined
the linkage of D, remember that a definition is available for
this entity. */
- if (pattern_defined
+ if (pattern_defined
&& !DECL_INTERFACE_KNOWN (d)
&& !DECL_NOT_REALLY_EXTERN (d))
mark_definable (d);
pop_access_scope (d);
}
-
+
/* We should have set up DECL_INITIAL in instantiate_class_template
for in-class definitions of static data members. */
- gcc_assert (!(TREE_CODE (d) == VAR_DECL
+ gcc_assert (!(TREE_CODE (d) == VAR_DECL
&& DECL_INITIALIZED_IN_CLASS_P (d)
&& DECL_INITIAL (d) == NULL_TREE));
elsewhere. */
if (DECL_INTERFACE_KNOWN (d)
&& DECL_REALLY_EXTERN (d)
- && ! (TREE_CODE (d) == FUNCTION_DECL
+ && ! (TREE_CODE (d) == FUNCTION_DECL
&& DECL_INLINE (d)))
goto out;
/* Defer all other templates, unless we have been explicitly
{
input_location = saved_loc;
- if (at_eof && !pattern_defined
+ if (at_eof && !pattern_defined
&& DECL_EXPLICIT_INSTANTIATION (d))
/* [temp.explicit]
job, even though we'll not be emitting a copy of this
function. */
if (!(TREE_CODE (d) == FUNCTION_DECL
- && flag_inline_trees
+ && flag_inline_trees
&& DECL_DECLARED_INLINE_P (d)))
goto out;
}
/* Enter the scope of D so that access-checking works correctly. */
push_nested_class (DECL_CONTEXT (d));
- cp_finish_decl (d,
- (!DECL_INITIALIZED_IN_CLASS_P (d)
+ cp_finish_decl (d,
+ (!DECL_INITIALIZED_IN_CLASS_P (d)
? DECL_INITIAL (d) : NULL_TREE),
NULL_TREE, 0);
pop_nested_class ();
saved_local_specializations = local_specializations;
/* Set up the list of local specializations. */
- local_specializations = htab_create (37,
+ local_specializations = htab_create (37,
hash_local_specialization,
eq_local_specializations,
NULL);
return;
}
- do
+ do
{
reconsider = 0;
{
instantiate_class_template (instantiation);
if (CLASSTYPE_TEMPLATE_INSTANTIATION (instantiation))
- for (fn = TYPE_METHODS (instantiation);
+ for (fn = TYPE_METHODS (instantiation);
fn;
fn = TREE_CHAIN (fn))
if (! DECL_ARTIFICIAL (fn))
current_tinst_level = NULL_TREE;
}
last_pending_template = last;
- }
+ }
while (reconsider);
input_location = saved_loc;
decl = expand_member_init (decl);
if (decl && !DECL_P (decl))
in_base_initializer = 1;
-
+
init = tsubst_expr (TREE_VALUE (t), argvec, tf_error | tf_warning,
NULL_TREE);
in_base_initializer = 0;
decl = TREE_VALUE (e);
/* Note that in a template enum, the TREE_VALUE is the
CONST_DECL, not the corresponding INTEGER_CST. */
- value = tsubst_expr (DECL_INITIAL (decl),
+ value = tsubst_expr (DECL_INITIAL (decl),
args, tf_error | tf_warning,
NULL_TREE);
set_current_access_from_decl (decl);
/* Actually build the enumerator itself. */
- build_enumerator (DECL_NAME (decl), value, newtag);
+ build_enumerator (DECL_NAME (decl), value, newtag);
}
finish_enum (newtag);
arguments. So, innermost set of template parameters will appear in
the type. */
-tree
+tree
get_mostly_instantiated_function_type (tree decl)
{
tree fn_type;
return 0;
else if (TREE_CODE (type) == TYPENAME_TYPE)
return 0;
-
+
if (complain & tf_error)
error ("%q#T is not a valid type for a template constant parameter", type);
return 1;
-- a template parameter. Template template parameters are types
for us (since TYPE_P holds true for them) so we handle
them here. */
- if (TREE_CODE (type) == TEMPLATE_TYPE_PARM
+ if (TREE_CODE (type) == TEMPLATE_TYPE_PARM
|| TREE_CODE (type) == TEMPLATE_TEMPLATE_PARM)
return true;
/* -- a qualified-id with a nested-name-specifier which contains a
/* -- a compound type constructed from any dependent type. */
if (TYPE_PTR_TO_MEMBER_P (type))
return (dependent_type_p (TYPE_PTRMEM_CLASS_TYPE (type))
- || dependent_type_p (TYPE_PTRMEM_POINTED_TO_TYPE
+ || dependent_type_p (TYPE_PTRMEM_POINTED_TO_TYPE
(type)));
else if (TREE_CODE (type) == POINTER_TYPE
|| TREE_CODE (type) == REFERENCE_TYPE)
if (dependent_type_p (TREE_TYPE (type)))
return true;
- for (arg_type = TYPE_ARG_TYPES (type);
- arg_type;
+ for (arg_type = TYPE_ARG_TYPES (type);
+ arg_type;
arg_type = TREE_CHAIN (arg_type))
if (dependent_type_p (TREE_VALUE (arg_type)))
return true;
if (TREE_CODE (type) == ARRAY_TYPE)
{
if (TYPE_DOMAIN (type)
- && ((value_dependent_expression_p
+ && ((value_dependent_expression_p
(TYPE_MAX_VALUE (TYPE_DOMAIN (type))))
|| (type_dependent_expression_p
(TYPE_MAX_VALUE (TYPE_DOMAIN (type))))))
return true;
return dependent_type_p (TREE_TYPE (type));
}
-
+
/* -- a template-id in which either the template name is a template
parameter ... */
if (TREE_CODE (type) == BOUND_TEMPLATE_TEMPLATE_PARM)
/* ... or any of the template arguments is a dependent type or
an expression that is type-dependent or value-dependent. */
else if (CLASS_TYPE_P (type) && CLASSTYPE_TEMPLATE_INFO (type)
- && (any_dependent_template_arguments_p
+ && (any_dependent_template_arguments_p
(INNERMOST_TEMPLATE_ARGS (CLASSTYPE_TI_ARGS (type)))))
return true;
-
+
/* All TYPEOF_TYPEs are dependent; if the argument of the `typeof'
expression is not type-dependent, then it should already been
have resolved. */
if (TREE_CODE (type) == TYPEOF_TYPE)
return true;
-
+
/* The standard does not specifically mention types that are local
to template functions or local classes, but they should be
considered dependent too. For example:
- template <int I> void f() {
- enum E { a = I };
+ template <int I> void f() {
+ enum E { a = I };
S<sizeof (E)> s;
}
/* The suggested resolution to Core Issue 2 implies that if the
qualifying type is the current class, then we must peek
inside it. */
- if (DECL_P (name)
+ if (DECL_P (name)
&& currently_open_class (scope)
&& !criterion (name))
return false;
/* A name declared with a dependent type. */
if (DECL_P (expression) && type_dependent_expression_p (expression))
return true;
-
+
switch (TREE_CODE (expression))
{
case IDENTIFIER_NODE:
return false;
case VAR_DECL:
- /* A constant with integral or enumeration type and is initialized
+ /* A constant with integral or enumeration type and is initialized
with an expression that is value-dependent. */
if (DECL_INITIAL (expression)
&& INTEGRAL_OR_ENUMERATION_TYPE_P (TREE_TYPE (expression))
is value-dependent. */
{
tree type = TREE_TYPE (expression);
-
+
if (dependent_type_p (type))
return true;
-
+
/* A functional cast has a list of operands. */
expression = TREE_OPERAND (expression, 0);
if (!expression)
as "int()". This should not happen for aggregate types
because it would form non-constant expressions. */
gcc_assert (INTEGRAL_OR_ENUMERATION_TYPE_P (type));
-
+
return false;
}
-
+
if (TREE_CODE (expression) == TREE_LIST)
{
for (; expression; expression = TREE_CHAIN (expression))
return true;
return false;
}
-
+
return value_dependent_expression_p (expression);
}
-
+
case SIZEOF_EXPR:
case ALIGNOF_EXPR:
/* A `sizeof' expression is value-dependent if the operand is
{
tree function = TREE_OPERAND (expression, 0);
tree args = TREE_OPERAND (expression, 1);
-
+
if (value_dependent_expression_p (function))
return true;
-
+
if (! args)
return false;
-
+
if (TREE_CODE (args) == TREE_LIST)
{
for (; args; args = TREE_CHAIN (args))
return true;
return false;
}
-
+
return value_dependent_expression_p (args);
}
{
case tcc_reference:
case tcc_unary:
- return (value_dependent_expression_p
+ return (value_dependent_expression_p
(TREE_OPERAND (expression, 0)));
-
+
case tcc_comparison:
case tcc_binary:
- return ((value_dependent_expression_p
+ return ((value_dependent_expression_p
(TREE_OPERAND (expression, 0)))
- || (value_dependent_expression_p
+ || (value_dependent_expression_p
(TREE_OPERAND (expression, 1))));
-
+
case tcc_expression:
{
int i;
return true;
return false;
}
-
+
default:
break;
}
}
-
+
/* The expression is not value-dependent. */
return false;
}
/* An unresolved name is always dependent. */
if (TREE_CODE (expression) == IDENTIFIER_NODE)
return true;
-
+
/* Some expression forms are never type-dependent. */
if (TREE_CODE (expression) == PSEUDO_DTOR_EXPR
|| TREE_CODE (expression) == SIZEOF_EXPR
/* SCOPE_REF with non-null TREE_TYPE is always non-dependent. */
if (TREE_CODE (expression) == SCOPE_REF)
return false;
-
+
if (TREE_CODE (expression) == BASELINK)
expression = BASELINK_FUNCTIONS (expression);
-
+
if (TREE_CODE (expression) == TEMPLATE_ID_EXPR)
{
if (any_dependent_template_arguments_p
expression = TREE_OPERAND (expression, 0);
}
gcc_assert (TREE_CODE (expression) == OVERLOAD);
-
+
while (expression)
{
if (type_dependent_expression_p (OVL_CURRENT (expression)))
}
return false;
}
-
+
return (dependent_type_p (TREE_TYPE (expression)));
}
{
tree inner_expr;
- /* Preserve null pointer constants so that the type of things like
+ /* Preserve null pointer constants so that the type of things like
"p == 0" where "p" is a pointer can be determined. */
if (null_ptr_cst_p (expr))
return expr;
/* Preserve OVERLOADs; the functions must be available to resolve
types. */
- inner_expr = (TREE_CODE (expr) == ADDR_EXPR ?
+ inner_expr = (TREE_CODE (expr) == ADDR_EXPR ?
TREE_OPERAND (expr, 0) : expr);
if (is_overloaded_fn (inner_expr)
|| TREE_CODE (inner_expr) == OFFSET_REF)
return build3 (COND_EXPR,
TREE_TYPE (expr),
TREE_OPERAND (expr, 0),
- (TREE_OPERAND (expr, 1)
+ (TREE_OPERAND (expr, 1)
? build_non_dependent_expr (TREE_OPERAND (expr, 1))
: build_non_dependent_expr (TREE_OPERAND (expr, 0))),
build_non_dependent_expr (TREE_OPERAND (expr, 2)));
TREE_TYPE (expr),
TREE_OPERAND (expr, 0),
build_non_dependent_expr (TREE_OPERAND (expr, 1)));
-
- /* Otherwise, build a NON_DEPENDENT_EXPR.
+
+ /* Otherwise, build a NON_DEPENDENT_EXPR.
REFERENCE_TYPEs are not stripped for expressions in templates
because doing so would play havoc with mangling. Consider, for
example:
- template <typename T> void f<T& g>() { g(); }
+ template <typename T> void f<T& g>() { g(); }
In the body of "f", the expression for "g" will have
REFERENCE_TYPE, even though the standard says that it should
new_args = NULL_TREE;
for (a = args; a; a = TREE_CHAIN (a))
- new_args = tree_cons (NULL_TREE,
+ new_args = tree_cons (NULL_TREE,
build_non_dependent_expr (TREE_VALUE (a)),
new_args);
return nreverse (new_args);
BINFO_N_BASE_BINFOS (TYPE_BINFO (node)));
else
fprintf (file, " no-binfo");
-
+
fprintf (file, " use_template=%d", CLASSTYPE_USE_TEMPLATE (node));
if (CLASSTYPE_INTERFACE_ONLY (node))
fprintf (file, " interface-only");
}
return lbasename (filename);
-}
+}
static void
open_repo_file (const char *filename)
return false;
/* If the virtual table has been assigned to this translation unit,
export the class. */
- return (IDENTIFIER_REPO_CHOSEN
+ return (IDENTIFIER_REPO_CHOSEN
(DECL_ASSEMBLER_NAME (CLASSTYPE_VTABLES (class_type))));
}
init_rtti_processing (void)
{
tree type_info_type;
-
+
push_namespace (std_identifier);
type_info_type = xref_tag (class_type, get_identifier ("type_info"),
/*tag_scope=*/ts_current, false);
type_info_ptr_type = build_pointer_type (const_type_info_type_node);
unemitted_tinfo_decls = VEC_alloc (tree, gc, 124);
-
+
create_tinfo_types ();
}
offset = build_vtbl_ref (build_indirect_ref (exp, NULL), index);
- type = build_qualified_type (ptr_type_node,
+ type = build_qualified_type (ptr_type_node,
cp_type_quals (TREE_TYPE (exp)));
- return build2 (PLUS_EXPR, type, exp,
+ return build2 (PLUS_EXPR, type, exp,
convert_to_integer (ptrdiff_type_node, offset));
}
if (!get_global_value_if_present (fn, &fn))
fn = push_throw_library_fn (fn, build_function_type (ptr_type_node,
void_list_node));
-
+
return build_cxx_call (fn, NULL_TREE);
}
{
tree type;
tree t;
-
+
if (exp == error_mark_node)
return error_mark_node;
/* Peel off cv qualifiers. */
type = TYPE_MAIN_VARIANT (type);
-
+
if (!VOID_TYPE_P (type))
type = complete_type_or_else (type, exp);
-
+
if (!type)
return error_mark_node;
error ("cannot use typeid with -fno-rtti");
return false;
}
-
+
if (!COMPLETE_TYPE_P (const_type_info_type_node))
{
error ("must #include <typeinfo> before using typeid");
return false;
}
-
+
return true;
}
/* Return a VAR_DECL for the internal ABI defined type_info object for
TYPE. You must arrange that the decl is mark_used, if actually use
- it --- decls in vtables are only used if the vtable is output. */
+ it --- decls in vtables are only used if the vtable is output. */
tree
get_tinfo_decl (tree type)
tree name;
tree d;
- if (COMPLETE_TYPE_P (type)
+ if (COMPLETE_TYPE_P (type)
&& TREE_CODE (TYPE_SIZE (type)) != INTEGER_CST)
{
error ("cannot create type information for type %qT because "
- "its size is variable",
+ "its size is variable",
type);
return error_mark_node;
}
if (d)
return d;
}
-
+
name = mangle_typeinfo_for_type (type);
d = IDENTIFIER_GLOBAL_VALUE (name);
tree decl = get_tinfo_decl (type);
mark_used (decl);
- return build_nop (type_info_ptr_type,
+ return build_nop (type_info_ptr_type,
build_address (decl));
}
{
if (type == error_mark_node || !typeid_ok_p ())
return error_mark_node;
-
+
if (processing_template_decl)
return build_min (TYPEID_EXPR, const_type_info_type_node, type);
if (!VOID_TYPE_P (type))
type = complete_type_or_else (type, NULL_TREE);
-
+
if (!type)
return error_mark_node;
ifnonnull (tree test, tree result)
{
return build3 (COND_EXPR, TREE_TYPE (result),
- build2 (EQ_EXPR, boolean_type_node, test,
+ build2 (EQ_EXPR, boolean_type_node, test,
cp_convert (TREE_TYPE (test), integer_zero_node)),
cp_convert (TREE_TYPE (result), integer_zero_node),
result);
errstr = "source is of incomplete class type";
goto fail;
}
-
+
}
/* The dynamic_cast operator shall not cast away constness. */
{
warning (0, "dynamic_cast of %q#D to %q#T can never succeed",
op, type);
- retval = build_int_cst (type, 0);
+ retval = build_int_cst (type, 0);
return retval;
}
}
/* Determine how T and V are related. */
boff = dcast_base_hint (static_type, target_type);
-
+
/* Since expr is used twice below, save it. */
expr = save_expr (expr);
tree tinfo_ptr;
tree ns = abi_node;
const char *name;
-
+
push_nested_namespace (ns);
tinfo_ptr = xref_tag (class_type,
get_identifier ("__class_type_info"),
/*tag_scope=*/ts_current, false);
-
+
tinfo_ptr = build_pointer_type
(build_qualified_type
(tinfo_ptr, TYPE_QUAL_CONST));
if (tc == REFERENCE_TYPE)
{
tree bad = throw_bad_cast ();
-
+
result = save_expr (result);
return build3 (COND_EXPR, type, result, result, bad);
}
{
if (type == error_mark_node || expr == error_mark_node)
return error_mark_node;
-
+
if (processing_template_decl)
{
expr = build_min (DYNAMIC_CAST_EXPR, type, expr);
TREE_SIDE_EFFECTS (expr) = 1;
-
+
return expr;
}
{
int flags = 0;
int quals = cp_type_quals (type);
-
+
if (quals & TYPE_QUAL_CONST)
flags |= 1;
if (quals & TYPE_QUAL_VOLATILE)
case OFFSET_TYPE:
ptrmem:
- return
+ return
(target_incomplete_p (TYPE_PTRMEM_POINTED_TO_TYPE (type))
|| !COMPLETE_TYPE_P (TYPE_PTRMEM_CLASS_TYPE (type)));
tree init = NULL_TREE;
tree name_decl;
tree vtable_ptr;
-
+
{
tree name_name;
-
+
/* Generate the NTBS array variable. */
tree name_type = build_cplus_array_type
(build_qualified_type (char_type_node, TYPE_QUAL_CONST),
if (!vtable_ptr)
{
tree real_type;
-
+
push_nested_namespace (abi_node);
real_type = xref_tag (class_type, TINFO_REAL_NAME (desc),
/*tag_scope=*/ts_current, false);
pop_nested_namespace (abi_node);
-
+
if (!COMPLETE_TYPE_P (real_type))
{
/* We never saw a definition of this type, so we need to
}
init = tree_cons (NULL_TREE, vtable_ptr, init);
-
+
init = tree_cons (NULL_TREE, decay_conversion (name_decl), init);
-
+
init = build_constructor (NULL_TREE, nreverse (init));
TREE_CONSTANT (init) = 1;
TREE_INVARIANT (init) = 1;
TREE_STATIC (init) = 1;
init = tree_cons (NULL_TREE, init, NULL_TREE);
-
+
return init;
}
generic_initializer (tree desc, tree target)
{
tree init = tinfo_base_init (desc, target);
-
+
init = build_constructor (NULL_TREE, init);
TREE_CONSTANT (init) = 1;
TREE_INVARIANT (init) = 1;
tree to = TREE_TYPE (target);
int flags = qualifier_flags (to);
bool incomplete = target_incomplete_p (to);
-
+
if (incomplete)
flags |= 8;
init = tree_cons (NULL_TREE, build_int_cst (NULL_TREE, flags), init);
init = tree_cons (NULL_TREE,
get_tinfo_ptr (TYPE_MAIN_VARIANT (to)),
init);
-
+
init = build_constructor (NULL_TREE, nreverse (init));
TREE_CONSTANT (init) = 1;
TREE_INVARIANT (init) = 1;
tree klass = TYPE_PTRMEM_CLASS_TYPE (target);
int flags = qualifier_flags (to);
bool incomplete = target_incomplete_p (to);
-
+
if (incomplete)
flags |= 0x8;
if (!COMPLETE_TYPE_P (klass))
init);
init = tree_cons (NULL_TREE,
get_tinfo_ptr (klass),
- init);
-
+ init);
+
init = build_constructor (NULL_TREE, nreverse (init));
TREE_CONSTANT (init) = 1;
TREE_INVARIANT (init) = 1;
TREE_STATIC (init) = 1;
- return init;
+ return init;
}
/* Return the CONSTRUCTOR expr for a type_info of class TYPE.
class_initializer (tree desc, tree target, tree trail)
{
tree init = tinfo_base_init (desc, target);
-
+
TREE_CHAIN (init) = trail;
init = build_constructor (NULL_TREE, init);
TREE_CONSTANT (init) = 1;
TREE_INVARIANT (init) = 1;
TREE_STATIC (init) = 1;
- return init;
+ return init;
}
/* Returns true if the typeinfo for type should be placed in
case REAL_TYPE:
case VOID_TYPE:
return true;
-
+
default:
return false;
}
tree base_binfo = BINFO_BASE_BINFO (TYPE_BINFO (type), 0);
tree tinfo = get_tinfo_ptr (BINFO_TYPE (base_binfo));
tree base_inits = tree_cons (NULL_TREE, tinfo, NULL_TREE);
-
+
return class_initializer (var_desc, type, base_inits);
}
else
VEC(tree,gc) *base_accesses = BINFO_BASE_ACCESSES (binfo);
tree base_inits = NULL_TREE;
int ix;
-
+
/* Generate the base information initializer. */
for (ix = nbases; ix--;)
{
int flags = 0;
tree tinfo;
tree offset;
-
+
if (VEC_index (tree, base_accesses, ix) == access_public_node)
flags |= 2;
tinfo = get_tinfo_ptr (BINFO_TYPE (base_binfo));
}
else
offset = BINFO_OFFSET (base_binfo);
-
+
/* Combine offset and flags into one field. */
offset = cp_build_binary_op (LSHIFT_EXPR, offset,
build_int_cst (NULL_TREE, 8));
vtable. We have to delay generating the VAR_DECL of the vtable
until the end of the translation, when we'll have seen the library
definition, if there was one.
-
+
REAL_NAME is the runtime's name of the type. Trailing arguments are
additional FIELD_DECL's for the structure. The final argument must be
NULL. */
strcat (pseudo_name, "_pseudo");
if (ident)
sprintf (pseudo_name + strlen (pseudo_name), "%d", ident);
-
+
/* First field is the pseudo type_info base class. */
fields = build_decl (FIELD_DECL, NULL_TREE, ti_desc_type_node);
-
+
/* Now add the derived fields. */
while ((field_decl = va_arg (ap, tree)))
{
TREE_CHAIN (field_decl) = fields;
fields = field_decl;
}
-
+
/* Create the pseudo type. */
pseudo_type = make_aggr_type (RECORD_TYPE);
finish_builtin_struct (pseudo_type, pseudo_name, fields, NULL_TREE);
TINFO_REAL_NAME (result) = get_identifier (real_name);
TINFO_PSEUDO_TYPE (result) =
cp_build_qualified_type (pseudo_type, TYPE_QUAL_CONST);
-
+
va_end (ap);
return result;
}
VEC(tree,gc) *base_accesses = BINFO_BASE_ACCESSES (binfo);
tree base_binfo = BINFO_BASE_BINFO (binfo, 0);
int num_bases = BINFO_N_BASE_BINFOS (binfo);
-
+
if (num_bases == 1
&& VEC_index (tree, base_accesses, 0) == access_public_node
&& !BINFO_VIRTUAL_P (base_binfo)
{
tree var_desc;
tree array_domain, base_array;
-
+
if (TREE_VEC_LENGTH (vmi_class_desc_type_node) <= num_bases)
{
int ix;
tree extend = make_tree_vec (num_bases + 5);
-
+
for (ix = TREE_VEC_LENGTH (vmi_class_desc_type_node); ix--;)
TREE_VEC_ELT (extend, ix)
= TREE_VEC_ELT (vmi_class_desc_type_node, ix);
var_desc = TREE_VEC_ELT (vmi_class_desc_type_node, num_bases);
if (var_desc)
return var_desc;
-
+
/* Create the array of __base_class_type_info entries.
G++ 3.2 allocated an array that had one too many
entries, and then filled that extra entries with
gcc_assert (!ti_desc_type_node);
push_nested_namespace (abi_node);
-
+
/* Create the internal type_info structure. This is used as a base for
the other structures. */
{
ti_desc_type_node = make_aggr_type (RECORD_TYPE);
field = build_decl (FIELD_DECL, NULL_TREE, const_ptr_type_node);
fields = field;
-
+
field = build_decl (FIELD_DECL, NULL_TREE, const_string_type_node);
TREE_CHAIN (field) = fields;
fields = field;
-
+
finish_builtin_struct (ti_desc_type_node, "__type_info_pseudo",
fields, NULL_TREE);
TYPE_HAS_CONSTRUCTOR (ti_desc_type_node) = 1;
}
-
+
/* Fundamental type_info */
bltn_desc_type_node = create_pseudo_type_info
("__fundamental_type_info", 0,
enum_desc_type_node = create_pseudo_type_info
("__enum_type_info", 0,
NULL);
-
+
/* Class type_info. Add a flags field. */
class_desc_type_node = create_pseudo_type_info
("__class_type_info", 0,
NULL);
-
- /* Single public non-virtual base class. Add pointer to base class.
+
+ /* Single public non-virtual base class. Add pointer to base class.
This is really a descendant of __class_type_info. */
si_class_desc_type_node = create_pseudo_type_info
("__si_class_type_info", 0,
build_decl (FIELD_DECL, NULL_TREE, type_info_ptr_type),
NULL);
-
+
/* Base class internal helper. Pointer to base type, offset to base,
flags. */
{
tree field, fields;
-
+
field = build_decl (FIELD_DECL, NULL_TREE, type_info_ptr_type);
fields = field;
-
+
field = build_decl (FIELD_DECL, NULL_TREE, integer_types[itk_long]);
TREE_CHAIN (field) = fields;
fields = field;
-
+
base_desc_type_node = make_aggr_type (RECORD_TYPE);
finish_builtin_struct (base_desc_type_node, "__base_class_type_info_pseudo",
fields, NULL_TREE);
TYPE_HAS_CONSTRUCTOR (base_desc_type_node) = 1;
}
-
+
/* General hierarchy is created as necessary in this vector. */
vmi_class_desc_type_node = make_tree_vec (10);
-
+
/* Pointer type_info. Adds two fields, qualification mask
and pointer to the pointed to type. This is really a descendant of
__pbase_type_info. */
};
int ix;
tree bltn_type, dtor;
-
+
push_nested_namespace (abi_node);
bltn_type = xref_tag (class_type,
- get_identifier ("__fundamental_type_info"),
+ get_identifier ("__fundamental_type_info"),
/*tag_scope=*/ts_current, false);
pop_nested_namespace (abi_node);
if (!COMPLETE_TYPE_P (bltn_type))
types[0] = bltn;
types[1] = build_pointer_type (bltn);
- types[2] = build_pointer_type (build_qualified_type (bltn,
+ types[2] = build_pointer_type (build_qualified_type (bltn,
TYPE_QUAL_CONST));
-
+
for (i = 0; i < 3; ++i)
{
tree tinfo;
TREE_USED (tinfo) = 1;
mark_needed (tinfo);
/* The C++ ABI requires that these objects be COMDAT. But,
- On systems without weak symbols, initialized COMDAT
+ On systems without weak symbols, initialized COMDAT
objects are emitted with internal linkage. (See
comdat_linkage for details.) Since we want these objects
to have external linkage so that copies do not have to be
int in_library = typeinfo_in_lib_p (type);
tree var_desc, var_init;
- gcc_assert (DECL_TINFO_P (decl));
-
+ gcc_assert (DECL_TINFO_P (decl));
+
if (in_library)
{
if (doing_runtime)
data->binfo = binfo;
data->via_virtual
= binfo_via_virtual (data->binfo, data->t) != NULL_TREE;
-
+
if (!data->repeated_base)
/* If there are no repeated bases, we can stop now. */
return binfo;
-
+
if (data->want_any && !data->via_virtual)
/* If this is a non-virtual base, then we can't do
better. */
return binfo;
-
+
return dfs_skip_bases;
}
else
{
gcc_assert (binfo != data->binfo);
-
+
/* We've found more than one matching binfo. */
if (!data->want_any)
{
return dfs_skip_bases;
}
}
-
+
return NULL_TREE;
}
/* [class.access.base]
A base class is said to be accessible if an invented public
- member of the base class is accessible.
+ member of the base class is accessible.
If BASE is a non-proper base, this condition is trivially
true. */
tree binfo;
tree t_binfo;
base_kind bk;
-
+
if (t == error_mark_node || base == error_mark_node)
{
if (kind_ptr)
return error_mark_node;
}
gcc_assert (TYPE_P (base));
-
+
if (!TYPE_P (t))
{
t_binfo = t;
t = complete_type (TYPE_MAIN_VARIANT (t));
t_binfo = TYPE_BINFO (t);
}
-
+
base = complete_type (TYPE_MAIN_VARIANT (base));
if (t_binfo)
dfs_walk_once (t_binfo, dfs_lookup_base, NULL, &data);
binfo = data.binfo;
-
+
if (!binfo)
bk = data.ambiguous ? bk_ambig : bk_not_base;
else if (binfo == t_binfo)
if (kind_ptr)
*kind_ptr = bk;
-
+
return binfo;
}
if (BINFO_VIRTUAL_P (binfo))
data->virt_depth++;
-
+
if (SAME_BINFO_TYPE_P (BINFO_TYPE (binfo), data->subtype))
{
if (data->virt_depth)
data.virt_depth = 0;
data.offset = NULL_TREE;
data.repeated_base = CLASSTYPE_REPEATED_BASE_P (target);
-
+
dfs_walk_once_accessible (TYPE_BINFO (target), /*friends=*/false,
dfs_dcast_hint_pre, dfs_dcast_hint_post, &data);
return data.offset ? data.offset : ssize_int (-2);
if (TREE_CODE (type) == TEMPLATE_TYPE_PARM
|| TREE_CODE (type) == BOUND_TEMPLATE_TEMPLATE_PARM
|| TREE_CODE (type) == TYPENAME_TYPE)
- /* The TYPE_FIELDS of a TEMPLATE_TYPE_PARM and
+ /* The TYPE_FIELDS of a TEMPLATE_TYPE_PARM and
BOUND_TEMPLATE_TEMPLATE_PARM are not fields at all;
instead TYPE_FIELDS is the TEMPLATE_PARM_INDEX. (Miraculously,
the code often worked even when we treated the index as a list
}
if (DECL_NAME (field) == name
- && (!want_type
+ && (!want_type
|| TREE_CODE (field) == TYPE_DECL
|| DECL_CLASS_TEMPLATE_P (field)))
return field;
}
/* Return the FUNCTION_DECL, RECORD_TYPE, UNION_TYPE, or
- NAMESPACE_DECL corresponding to the innermost non-block scope. */
+ NAMESPACE_DECL corresponding to the innermost non-block scope. */
tree
current_scope (void)
context_for_name_lookup (tree decl)
{
/* [class.union]
-
+
For the purposes of name lookup, after the anonymous union
definition, the members of the anonymous union are considered to
have been defined in the scope in which the anonymous union is
- declared. */
+ declared. */
tree context = DECL_CONTEXT (decl);
while (context && TYPE_P (context) && ANON_AGGR_TYPE_P (context))
else
access = ak_public;
}
- else
+ else
{
/* First, check for an access-declaration that gives us more
access to the DECL. The CONST_DECL for an enumeration
if (DECL_LANG_SPECIFIC (decl) && !DECL_DISCRIMINATOR_P (decl))
{
tree decl_access = purpose_member (type, DECL_ACCESS (decl));
-
+
if (decl_access)
{
decl_access = TREE_VALUE (decl_access);
-
+
if (decl_access == access_public_node)
access = ak_public;
else if (decl_access == access_protected_node)
int i;
tree base_binfo;
VEC(tree,gc) *accesses;
-
+
/* Otherwise, scan our baseclasses, and pick the most favorable
access. */
accesses = BINFO_BASE_ACCESSES (binfo);
If a name can be reached by several paths through a multiple
inheritance graph, the access is that of the path that gives
- most access.
+ most access.
The algorithm we use is to make a post-order depth-first traversal
of the base-class hierarchy. As we come up the tree, we annotate
m as a member of N is protected, and the reference occurs in a
member or friend of class N, or in a member or friend of a
class P derived from N, where m as a member of P is private or
- protected.
+ protected.
Here DERIVED is a possible P and DECL is m. accessible_p will
iterate over various values of N, but the access to m in DERIVED
/* If m is inaccessible in DERIVED, then it's not a P. */
if (access == ak_none)
return 0;
-
+
/* [class.protected]
When a friend or a member function of a derived class references
tree t = binfo;
while (BINFO_INHERITANCE_CHAIN (t))
t = BINFO_INHERITANCE_CHAIN (t);
-
+
if (!DERIVED_FROM_P (derived, BINFO_TYPE (t)))
return 0;
}
if (TREE_CODE (scope) == FUNCTION_DECL
|| DECL_FUNCTION_TEMPLATE_P (scope))
{
- /* Perhaps this SCOPE is a member of a class which is a
- friend. */
+ /* Perhaps this SCOPE is a member of a class which is a
+ friend. */
if (DECL_CLASS_SCOPE_P (scope)
&& friend_accessible_p (DECL_CONTEXT (scope), decl, binfo))
return 1;
&& is_friend (BINFO_TYPE (binfo), scope))
return binfo;
}
-
+
return NULL_TREE;
}
CONSIDER_LOCAL is true, do consider special access the current
scope or friendship thereof we might have. */
-int
+int
accessible_p (tree type, tree decl, bool consider_local_p)
{
tree binfo;
protected, or
--there exists a base class B of N that is accessible at the point
- of reference, and m is accessible when named in class B.
+ of reference, and m is accessible when named in class B.
We walk the base class hierarchy, checking these conditions. */
if (access == ak_public
|| (access == ak_protected && protected_ok))
return 1;
-
+
if (!consider_local_p)
return 0;
-
+
/* Walk the hierarchy again, looking for a base class that allows
access. */
return dfs_walk_once_accessible (binfo, /*friends=*/true,
/* Within the scope of a template class, you can refer to the to the
current specialization with the name of the template itself. For
example:
-
+
template <typename T> struct S { S* sp; }
Returns nonzero if DECL is such a declaration in a class TYPE. */
is_subobject_of_p (tree parent, tree binfo)
{
tree probe;
-
+
for (probe = parent; probe; probe = BINFO_INHERITANCE_CHAIN (probe))
{
if (probe == binfo)
/* If this is a dependent base, don't look in it. */
if (BINFO_DEPENDENT_BASE_P (binfo))
return NULL_TREE;
-
+
/* If this base class is hidden by the best-known value so far, we
don't need to look. */
if (lfi->rval_binfo && BINFO_INHERITANCE_CHAIN (binfo) == lfi->rval_binfo
lfi->name);
if (e != NULL)
nval = TYPE_MAIN_DECL (e->type);
- else
+ else
goto done;
}
}
/* You must name a template base class with a template-id. */
- if (!same_type_p (type, lfi->type)
+ if (!same_type_p (type, lfi->type)
&& template_self_reference_p (type, nval))
goto done;
hide the old one, we might have an ambiguity. */
if (lfi->rval_binfo
&& !is_subobject_of_p (lfi->rval_binfo, binfo))
-
+
{
if (nval == lfi->rval && shared_member_p (nval))
/* The two things are really the same. */
just return NULL_TREE. */
if (!protect && lfi.ambiguous)
return NULL_TREE;
-
- if (protect == 2)
+
+ if (protect == 2)
{
if (lfi.ambiguous)
return lfi.ambiguous;
rval = error_mark_node;
}
- if (rval && is_overloaded_fn (rval))
+ if (rval && is_overloaded_fn (rval))
rval = build_baselink (rval_binfo, basetype_path, rval,
(IDENTIFIER_TYPENAME_P (name)
? TREE_TYPE (name): NULL_TREE));
lookup_field (tree xbasetype, tree name, int protect, bool want_type)
{
tree rval = lookup_member (xbasetype, name, protect, want_type);
-
+
/* Ignore functions, but propagate the ambiguity list. */
if (!error_operand_p (rval)
&& (rval && BASELINK_P (rval)))
int i;
tree fn;
VEC(tree,gc) *methods = CLASSTYPE_METHOD_VEC (class_type);
-
+
for (i = CLASSTYPE_FIRST_CONVERSION_SLOT;
VEC_iterate (tree, methods, i, fn); ++i)
{
fn = OVL_CURRENT (fn);
if (!DECL_CONV_FN_P (fn))
break;
-
+
if (TREE_CODE (fn) == TEMPLATE_DECL)
/* All the templated conversion functions are on the same
slot, so remember it. */
tree fn;
tree tmp;
size_t i;
-
+
if (!CLASS_TYPE_P (type))
return -1;
`B', not `D'. This function makes that adjustment. */
tree
-adjust_result_of_qualified_name_lookup (tree decl,
+adjust_result_of_qualified_name_lookup (tree decl,
tree qualifying_scope,
tree context_class)
{
- if (context_class && CLASS_TYPE_P (qualifying_scope)
+ if (context_class && CLASS_TYPE_P (qualifying_scope)
&& DERIVED_FROM_P (qualifying_scope, context_class)
&& BASELINK_P (decl))
{
if (base)
{
BASELINK_ACCESS_BINFO (decl) = base;
- BASELINK_BINFO (decl)
+ BASELINK_BINFO (decl)
= lookup_base (base, BINFO_TYPE (BASELINK_BINFO (decl)),
ba_unique | ba_quiet,
NULL);
tree rval;
unsigned ix;
tree base_binfo;
-
+
/* Call the pre-order walking function. */
if (pre_fn)
{
gcc_assert (rval != dfs_skip_bases);
return rval;
}
-
+
return NULL_TREE;
}
tree rval;
unsigned ix;
tree base_binfo;
-
+
/* Call the pre-order walking function. */
if (pre_fn)
{
{
if (rval == dfs_skip_bases)
goto skip_bases;
-
+
return rval;
}
}
continue;
BINFO_MARKED (base_binfo) = 1;
}
-
+
rval = dfs_walk_once_r (base_binfo, pre_fn, post_fn, data);
if (rval)
return rval;
}
-
+
skip_bases:
/* Call the post-order walking function. */
if (post_fn)
gcc_assert (rval != dfs_skip_bases);
return rval;
}
-
+
return NULL_TREE;
}
/* Worker for dfs_walk_once. Recursively unmark the virtual base binfos of
BINFO. */
-
+
static void
dfs_unmark_r (tree binfo)
{
unsigned ix;
tree base_binfo;
-
+
/* Process the basetypes. */
for (ix = 0; BINFO_BASE_ITERATE (binfo, ix, base_binfo); ix++)
{
gcc_assert (pre_fn || post_fn);
gcc_assert (!active);
active++;
-
+
if (!CLASSTYPE_DIAMOND_SHAPED_P (BINFO_TYPE (binfo)))
/* We are not diamond shaped, and therefore cannot encounter the
same binfo twice. */
VEC(tree,gc) *vbases;
unsigned ix;
tree base_binfo;
-
+
for (vbases = CLASSTYPE_VBASECLASSES (BINFO_TYPE (binfo)), ix = 0;
VEC_iterate (tree, vbases, ix, base_binfo); ix++)
BINFO_MARKED (base_binfo) = 0;
}
active--;
-
+
return rval;
}
{
if (rval == dfs_skip_bases)
goto skip_bases;
-
+
return rval;
}
}
if (mark && BINFO_MARKED (base_binfo))
continue;
-
+
/* If the base is inherited via private or protected
inheritance, then we can't see it, unless we are a friend of
the current binfo. */
if (!friends_p)
continue;
scope = current_scope ();
- if (!scope
+ if (!scope
|| TREE_CODE (scope) == NAMESPACE_DECL
|| !is_friend (BINFO_TYPE (binfo), scope))
continue;
if (rval)
return rval;
}
-
+
skip_bases:
/* Call the post-order walking function. */
if (post_fn)
gcc_assert (rval != dfs_skip_bases);
return rval;
}
-
+
return NULL_TREE;
}
bool diamond_shaped = CLASSTYPE_DIAMOND_SHAPED_P (BINFO_TYPE (binfo));
tree rval = dfs_walk_once_accessible_r (binfo, friends_p, diamond_shaped,
pre_fn, post_fn, data);
-
+
if (diamond_shaped)
{
if (!BINFO_INHERITANCE_CHAIN (binfo))
VEC(tree,gc) *vbases;
unsigned ix;
tree base_binfo;
-
+
for (vbases = CLASSTYPE_VBASECLASSES (BINFO_TYPE (binfo)), ix = 0;
VEC_iterate (tree, vbases, ix, base_binfo); ix++)
BINFO_MARKED (base_binfo) = 0;
{
/* Potentially covariant. */
unsigned base_quals, over_quals;
-
+
fail = !POINTER_TYPE_P (base_return);
if (!fail)
{
fail = cp_type_quals (base_return) != cp_type_quals (over_return);
-
+
base_return = TREE_TYPE (base_return);
over_return = TREE_TYPE (over_return);
}
if ((base_quals & over_quals) != over_quals)
fail = 1;
-
+
if (CLASS_TYPE_P (base_return) && CLASS_TYPE_P (over_return))
{
tree binfo = lookup_base (over_return, base_return,
DECL_INVALID_OVERRIDER_P (overrider) = 1;
return 0;
}
-
+
/* Check throw specifier is at least as strict. */
if (!comp_except_specs (base_throw, over_throw, 0))
{
DECL_INVALID_OVERRIDER_P (overrider) = 1;
return 0;
}
-
+
return 1;
}
/* Given a class TYPE, and a function decl FNDECL, look for
virtual functions in TYPE's hierarchy which FNDECL overrides.
We do not look in TYPE itself, only its bases.
-
+
Returns nonzero, if we find any. Set FNDECL's DECL_VIRTUAL_P, if we
find that it overrides anything.
-
+
We check that every function which is overridden, is correctly
overridden. */
for (ix = 0; BINFO_BASE_ITERATE (binfo, ix, base_binfo); ix++)
{
tree basetype = BINFO_TYPE (base_binfo);
-
+
if (TYPE_POLYMORPHIC_P (basetype))
found += look_for_overrides_r (basetype, fndecl);
}
if (ix >= 0)
{
tree fns = VEC_index (tree, CLASSTYPE_METHOD_VEC (type), ix);
-
+
for (; fns; fns = OVL_NEXT (fns))
{
tree fn = OVL_CURRENT (fns);
if (!BINFO_PRIMARY_P (binfo))
{
tree virtuals;
-
+
for (virtuals = BINFO_VIRTUALS (binfo);
virtuals;
virtuals = TREE_CHAIN (virtuals))
int we_hide_them;
int they_hide_us;
tree *prev, other;
-
+
if (!(virtual_depth || TREE_STATIC (level)))
/* Neither is morally virtual, so cannot hide each other. */
continue;
-
+
if (!TREE_VALUE (level))
/* They evaporated away already. */
continue;
if (!(we_hide_them || they_hide_us))
/* Neither is within the other, so no hiding can occur. */
continue;
-
+
for (prev = &TREE_VALUE (level), other = *prev; other;)
{
if (same_type_p (to_type, TREE_TYPE (other)))
{
tree t;
tree prev;
-
+
/* Remove the original other_convs portion from child_convs. */
for (prev = NULL, t = child_convs;
t != other_convs; prev = t, t = TREE_CHAIN (t))
continue;
-
+
if (prev)
TREE_CHAIN (prev) = NULL_TREE;
else
}
else
my_convs = child_convs;
-
+
return my_convs;
}
if (!TYPE_HAS_CONVERSION (BINFO_TYPE (binfo)))
{
*convs = *tpl_convs = NULL_TREE;
-
+
return 0;
}
-
+
if (BINFO_VIRTUAL_P (binfo))
virtual_depth++;
-
+
/* First, locate the unhidden ones at this level. */
- for (i = CLASSTYPE_FIRST_CONVERSION_SLOT;
+ for (i = CLASSTYPE_FIRST_CONVERSION_SLOT;
VEC_iterate (tree, method_vec, i, conv);
++i)
{
{
tree tpl = OVL_CURRENT (tpls);
tree type = DECL_CONV_FN_TYPE (tpl);
-
+
if (check_hidden_convs (binfo, virtual_depth, virtualness,
type, parent_tpl_convs, other_tpl_convs))
{
if (!IDENTIFIER_MARKED (name))
{
tree type = DECL_CONV_FN_TYPE (cur);
-
+
if (check_hidden_convs (binfo, virtual_depth, virtualness,
type, parent_convs, other_convs))
{
if (virtual_depth)
TREE_STATIC (parent_convs) = 1;
}
-
+
if (my_tpl_convs)
{
parent_tpl_convs = tree_cons (binfo, my_tpl_convs, parent_tpl_convs);
child_convs = other_convs;
child_tpl_convs = other_tpl_convs;
-
+
/* Now iterate over each base, looking for more conversions. */
for (i = 0; BINFO_BASE_ITERATE (binfo, i, base_binfo); i++)
{
child_convs, other_convs);
*tpl_convs = split_conversions (my_tpl_convs, parent_tpl_convs,
child_tpl_convs, other_tpl_convs);
-
+
return my_virtualness;
}
{
tree convs, tpl_convs;
tree list = NULL_TREE;
-
+
complete_type (type);
if (!TYPE_BINFO (type))
return NULL_TREE;
-
+
lookup_conversions_r (TYPE_BINFO (type), 0, 0,
NULL_TREE, NULL_TREE, NULL_TREE, NULL_TREE,
&convs, &tpl_convs);
-
+
/* Flatten the list-of-lists */
for (; convs; convs = TREE_CHAIN (convs))
{
list = probe;
}
}
-
+
for (; tpl_convs; tpl_convs = TREE_CHAIN (tpl_convs))
{
tree probe, next;
list = probe;
}
}
-
+
return list;
}
if (limit && !CLASSTYPE_VBASECLASSES (limit))
/* LIMIT has no virtual bases, so BINFO cannot be via one. */
return NULL_TREE;
-
+
for (; binfo && !SAME_BINFO_TYPE_P (BINFO_TYPE (binfo), limit);
binfo = BINFO_INHERITANCE_CHAIN (binfo))
{
copied_binfo (tree binfo, tree here)
{
tree result = NULL_TREE;
-
+
if (BINFO_VIRTUAL_P (binfo))
{
tree t;
tree cbinfo;
tree base_binfo;
int ix;
-
+
cbinfo = copied_binfo (BINFO_INHERITANCE_CHAIN (binfo), here);
for (ix = 0; BINFO_BASE_ITERATE (cbinfo, ix, base_binfo); ix++)
if (SAME_BINFO_TYPE_P (BINFO_TYPE (base_binfo), BINFO_TYPE (binfo)))
unsigned ix;
tree binfo;
VEC(tree,gc) *vbases;
-
+
for (vbases = CLASSTYPE_VBASECLASSES (t), ix = 0;
VEC_iterate (tree, vbases, ix, binfo); ix++)
if (SAME_BINFO_TYPE_P (BINFO_TYPE (binfo), base))
original_binfo (tree binfo, tree here)
{
tree result = NULL;
-
+
if (SAME_BINFO_TYPE_P (BINFO_TYPE (binfo), BINFO_TYPE (here)))
result = here;
else if (BINFO_VIRTUAL_P (binfo))
else if (BINFO_INHERITANCE_CHAIN (binfo))
{
tree base_binfos;
-
+
base_binfos = original_binfo (BINFO_INHERITANCE_CHAIN (binfo), here);
if (base_binfos)
{
int ix;
tree base_binfo;
-
+
for (ix = 0; (base_binfo = BINFO_BASE_BINFO (base_binfos, ix)); ix++)
if (SAME_BINFO_TYPE_P (BINFO_TYPE (base_binfo),
BINFO_TYPE (binfo)))
}
}
}
-
+
return result;
}
/* Perform the semantic phase of parsing, i.e., the process of
building tree structure, checking semantic consistency, and
building RTL. These routines are used both during actual parsing
- and during the instantiation of template functions.
+ and during the instantiation of template functions.
Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005
Free Software Foundation, Inc.
Written by Mark Mitchell (mmitchell@usa.net) based on code found
- formerly in parse.y and pt.c.
+ formerly in parse.y and pt.c.
This file is part of GCC.
under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2, or (at your option)
any later version.
-
+
GCC is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
-
+
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING. If not, write to the Free
Software Foundation, 59 Temple Place - Suite 330, Boston, MA
instantiations.
Typical use of access checking functions is described here:
-
+
1. When we enter a context that requires certain access checking
mode, the function `push_deferring_access_checks' is called with
DEFERRING argument specifying the desired mode. Access checking
names used in a decl-specifier-seq until we know what is being
declared because code like:
- class A {
+ class A {
class B {};
B* f();
}
A::B* A::f() { return 0; }
- is valid, even though `A::B' is not generally accessible.
+ is valid, even though `A::B' is not generally accessible.
The TREE_PURPOSE of each node is the scope used to qualify the
name being looked up; the TREE_VALUE is the DECL to which the
name was resolved. */
tree deferred_access_checks;
-
+
/* The current mode of access checks. */
enum deferring_kind deferring_access_checks_kind;
-
+
} deferred_access;
DEF_VEC_O (deferred_access);
DEF_VEC_ALLOC_O (deferred_access,gc);
VEC_pop (deferred_access, deferred_access_stack);
}
-/* Returns a TREE_LIST representing the deferred checks.
- The TREE_PURPOSE of each node is the type through which the
+/* Returns a TREE_LIST representing the deferred checks.
+ The TREE_PURPOSE of each node is the type through which the
access occurred; the TREE_VALUE is the declaration named.
*/
if (ptr->deferring_access_checks_kind == dk_no_deferred)
{
/* Check access. */
- for (; checks; checks = TREE_CHAIN (checks))
- enforce_access (TREE_PURPOSE (checks),
+ for (; checks; checks = TREE_CHAIN (checks))
+ enforce_access (TREE_PURPOSE (checks),
TREE_VALUE (checks));
}
else
/* Merge with parent. */
tree next;
tree original = ptr->deferred_access_checks;
-
+
for (; checks; checks = next)
{
tree probe;
-
+
next = TREE_CHAIN (checks);
for (probe = original; probe; probe = TREE_CHAIN (probe))
deferred_check;
deferred_check = TREE_CHAIN (deferred_check))
/* Check access. */
- enforce_access (TREE_PURPOSE (deferred_check),
+ enforce_access (TREE_PURPOSE (deferred_check),
TREE_VALUE (deferred_check));
}
*/
if (deferred_access_no_check)
return;
-
+
gcc_assert (TREE_CODE (binfo) == TREE_BINFO);
ptr = VEC_last (deferred_access, deferred_access_stack);
-
+
/* If we are not supposed to defer access checks, just check now. */
if (ptr->deferring_access_checks_kind == dk_no_deferred)
{
enforce_access (binfo, decl);
return;
}
-
+
/* See if we are already going to perform this check. */
for (check = ptr->deferred_access_checks;
check;
stmt_tree
current_stmt_tree (void)
{
- return (cfun
- ? &cfun->language->base.x_stmt_tree
+ return (cfun
+ ? &cfun->language->base.x_stmt_tree
: &scope_chain->x_stmt_tree);
}
block = poplevel (kept_level_p (), 1, 0);
stmt_list = pop_stmt_list (stmt_list);
-
+
if (!processing_template_decl)
{
stmt_list = c_build_bind_expr (block, stmt_list);
return stmt_list;
}
-/* Begin a new scope. */
+/* Begin a new scope. */
static tree
do_pushlevel (scope_kind sk)
for (;;) { A x = 42; if (!x) break; }
The statement list for BODY will be empty if the conditional did
not declare anything. */
-
+
static void
simplify_loop_decl_cond (tree *cond_p, tree body)
{
cond = *cond_p;
*cond_p = boolean_true_node;
-
+
if_stmt = begin_if_stmt ();
cond = build_unary_op (TRUTH_NOT_EXPR, cond, 0);
finish_if_stmt_cond (cond, if_stmt);
addresses, or some such. */
DECL_UNINLINABLE (current_function_decl) = 1;
}
-
+
check_goto (destination);
return add_stmt (build_stmt (GOTO_EXPR, destination));
/* Process the COND of an if-statement, which may be given by
IF_STMT. */
-void
+void
finish_if_stmt_cond (tree cond, tree if_stmt)
{
finish_cond (&IF_COND (if_stmt), maybe_convert_cond (cond));
/* Finish an if-statement. */
-void
+void
finish_if_stmt (tree if_stmt)
{
tree scope = TREE_CHAIN (if_stmt);
/* Process the COND of a while-statement, which may be given by
WHILE_STMT. */
-void
+void
finish_while_stmt_cond (tree cond, tree while_stmt)
{
finish_cond (&WHILE_COND (while_stmt), maybe_convert_cond (cond));
/* Finish a while-statement, which may be given by WHILE_STMT. */
-void
+void
finish_while_stmt (tree while_stmt)
{
WHILE_BODY (while_stmt) = do_poplevel (WHILE_BODY (while_stmt));
if (!processing_template_decl)
{
if (DECL_DESTRUCTOR_P (current_function_decl)
- || (DECL_CONSTRUCTOR_P (current_function_decl)
+ || (DECL_CONSTRUCTOR_P (current_function_decl)
&& targetm.cxx.cdtor_returns_this ()))
{
/* Similarly, all destructors must run destructors for
{
tree r;
- r = build_stmt (FOR_STMT, NULL_TREE, NULL_TREE,
+ r = build_stmt (FOR_STMT, NULL_TREE, NULL_TREE,
NULL_TREE, NULL_TREE);
if (flag_new_for_scope > 0)
add_stmt (do_poplevel (scope));
}
- finish_stmt ();
+ finish_stmt ();
}
/* Finish a break-statement. */
SWITCH_STMT_BODY (switch_stmt) =
pop_stmt_list (SWITCH_STMT_BODY (switch_stmt));
- pop_switch ();
+ pop_switch ();
finish_stmt ();
scope = TREE_CHAIN (switch_stmt);
/* Begin a compound statement. FLAGS contains some bits that control the
behavior and context. If BCS_NO_SCOPE is set, the compound statement
does not define a scope. If BCS_FN_BODY is set, this is the outermost
- block of a function. If BCS_TRY_BLOCK is set, this is the block
+ block of a function. If BCS_TRY_BLOCK is set, this is the block
created on behalf of a TRY statement. Returns a token to be passed to
finish_compound_stmt. */
/* Normally, we try hard to keep the BLOCK for a statement-expression.
But, if it's a statement-expression with a scopeless block, there's
nothing to keep, and we don't want to accidentally keep a block
- *inside* the scopeless block. */
+ *inside* the scopeless block. */
keep_next_level (false);
}
else
for (i = 0, t = input_operands; t; ++i, t = TREE_CHAIN (t))
{
constraint = TREE_STRING_POINTER (TREE_VALUE (TREE_PURPOSE (t)));
- operand = decay_conversion (TREE_VALUE (t));
+ operand = decay_conversion (TREE_VALUE (t));
/* If the type of the operand hasn't been determined (e.g.,
because it involves an overloaded function), then issue
resolve the overloading. */
if (TREE_TYPE (operand) == unknown_type_node)
{
- error ("type of asm operand %qE could not be determined",
+ error ("type of asm operand %qE could not be determined",
TREE_VALUE (t));
operand = error_mark_node;
}
/* When DECL goes out of scope, make sure that CLEANUP is executed. */
-void
+void
finish_decl_cleanup (tree decl, tree cleanup)
{
push_cleanup (decl, cleanup, false);
/* [expr.unary.op]/3 The qualified id of a pointer-to-member must not be
enclosed in parentheses. */
PTRMEM_OK_P (expr) = 0;
-
+
if (TREE_CODE (expr) == STRING_CST)
PAREN_STRING_LITERAL_P (expr) = 1;
-
+
return expr;
}
if (!object)
{
- if (current_function_decl
+ if (current_function_decl
&& DECL_STATIC_FUNCTION_P (current_function_decl))
cp_error_at ("invalid use of member %qD in static member function",
decl);
{
/* Set the cv qualifiers. */
int quals = cp_type_quals (TREE_TYPE (current_class_ref));
-
+
if (DECL_MUTABLE_P (decl))
quals &= ~TYPE_QUAL_CONST;
quals |= cp_type_quals (TREE_TYPE (decl));
type = cp_build_qualified_type (type, quals);
}
-
+
return build_min (COMPONENT_REF, type, object, decl, NULL_TREE);
}
else
{
tree access_type = TREE_TYPE (object);
tree lookup_context = context_for_name_lookup (decl);
-
+
while (!DERIVED_FROM_P (lookup_context, access_type))
{
access_type = TYPE_CONTEXT (access_type);
`A::B' then NESTED_NAME_SPECIFIER is `A'. */
void
-check_accessibility_of_qualified_id (tree decl,
- tree object_type,
+check_accessibility_of_qualified_id (tree decl,
+ tree object_type,
tree nested_name_specifier)
{
tree scope;
/* If we're not checking, return immediately. */
if (deferred_access_no_check)
return;
-
+
/* Determine the SCOPE of DECL. */
scope = context_for_name_lookup (decl);
/* If the SCOPE is not a type, then DECL is not a member. */
if (!TYPE_P (scope))
return;
/* Compute the scope through which DECL is being accessed. */
- if (object_type
+ if (object_type
/* OBJECT_TYPE might not be a class type; consider:
class A { typedef int I; };
{
if (TREE_CODE (expr) == SCOPE_REF)
expr = TREE_OPERAND (expr, 1);
- expr = build_offset_ref (qualifying_class, expr,
+ expr = build_offset_ref (qualifying_class, expr,
/*address_p=*/true);
return expr;
}
/* If so, the expression may be relative to the current
class. */
if (!shared_member_p (fns)
- && current_class_type
+ && current_class_type
&& DERIVED_FROM_P (qualifying_class, current_class_type))
- expr = (build_class_member_access_expr
+ expr = (build_class_member_access_expr
(maybe_dummy_object (qualifying_class, NULL),
expr,
BASELINK_ACCESS_BINFO (expr),
/* Begin a statement-expression. The value returned must be passed to
finish_stmt_expr. */
-tree
+tree
begin_stmt_expr (void)
{
return push_stmt_list ();
if (error_operand_p (expr))
return error_mark_node;
-
+
if (expr)
{
if (!processing_template_decl && !VOID_TYPE_P (TREE_TYPE (expr)))
add_stmt (result);
}
}
-
+
finish_stmt ();
/* Remember the last expression so that finish_stmt_expr
can pull it apart. */
TREE_TYPE (stmt_expr) = result;
-
+
return result;
}
by the previous begin_stmt_expr. Returns an expression
representing the statement-expression. */
-tree
+tree
finish_stmt_expr (tree stmt_expr, bool has_no_scope)
{
tree result, result_stmt, type;
Returns code for the call. */
-tree
+tree
finish_call_expr (tree fn, tree args, bool disallow_virtual, bool koenig_p)
{
tree result;
function call is transformed into a qualified function call
using (*this) as the postfix-expression to the left of the
. operator.... [Otherwise] a contrived object of type T
- becomes the implied object argument.
+ becomes the implied object argument.
This paragraph is unclear about this situation:
struct C : public A { void g() { B::f(); }};
In particular, for `B::f', this paragraph does not make clear
- whether "the class of that member function" refers to `A' or
+ whether "the class of that member function" refers to `A' or
to `B'. We believe it refers to `B'. */
- if (current_class_type
+ if (current_class_type
&& DERIVED_FROM_P (BINFO_TYPE (BASELINK_ACCESS_BINFO (fn)),
current_class_type)
&& current_class_ref)
}
result = build_new_method_call (object, fn, args, NULL_TREE,
- (disallow_virtual
+ (disallow_virtual
? LOOKUP_NONVIRTUAL : 0));
}
else if (is_overloaded_fn (fn))
is indicated by CODE, which should be POSTINCREMENT_EXPR or
POSTDECREMENT_EXPR.) */
-tree
+tree
finish_increment_expr (tree expr, enum tree_code code)
{
- return build_x_unary_op (code, expr);
+ return build_x_unary_op (code, expr);
}
/* Finish a use of `this'. Returns an expression for `this'. */
-tree
+tree
finish_this_expr (void)
{
tree result;
the TYPE for the type given. If SCOPE is non-NULL, the expression
was of the form `OBJECT.SCOPE::~DESTRUCTOR'. */
-tree
+tree
finish_pseudo_destructor_expr (tree object, tree scope, tree destructor)
{
if (destructor == error_mark_node)
error ("invalid qualifying scope in pseudo-destructor name");
return error_mark_node;
}
-
+
/* [expr.pseudo] says both:
The type designated by the pseudo-destructor-name shall be
We implement the more generous second sentence, since that is
what most other compilers do. */
- if (!same_type_ignoring_top_level_qualifiers_p (TREE_TYPE (object),
+ if (!same_type_ignoring_top_level_qualifiers_p (TREE_TYPE (object),
destructor))
{
error ("%qE is not of type %qT", object, destructor);
finish_fname (tree id)
{
tree decl;
-
+
decl = fname_decl (C_RID_CODE (id), id);
if (processing_template_decl)
decl = DECL_NAME (decl);
/* Finish a translation unit. */
-void
+void
finish_translation_unit (void)
{
/* In case there were missing closebraces,
/* Finish a template type parameter, specified as AGGR IDENTIFIER.
Returns the parameter. */
-tree
+tree
finish_template_type_parm (tree aggr, tree identifier)
{
if (aggr != class_type_node)
/* Finish a template template parameter, specified as AGGR IDENTIFIER.
Returns the parameter. */
-tree
+tree
finish_template_template_parm (tree aggr, tree identifier)
{
tree decl = build_decl (TYPE_DECL, identifier, NULL_TREE);
/* Try to emit a slightly smarter error message if we detect
that the user is using a template instantiation. */
- if (CLASSTYPE_TEMPLATE_INFO (t)
+ if (CLASSTYPE_TEMPLATE_INFO (t)
&& CLASSTYPE_TEMPLATE_INSTANTIATION (t))
error ("invalid use of type %qT as a default value for a "
"template template-parameter", t);
/* Update the location of the decl. */
DECL_SOURCE_LOCATION (TYPE_NAME (t)) = input_location;
-
+
if (TYPE_BEING_DEFINED (t))
{
t = make_aggr_type (TREE_CODE (t));
(t, finfo->interface_unknown);
}
reset_specialization();
-
+
/* Make a declaration for this class in its own scope. */
build_self_reference ();
gcc_assert (TREE_CHAIN (decl) == NULL_TREE);
/* Set up access control for DECL. */
- TREE_PRIVATE (decl)
+ TREE_PRIVATE (decl)
= (current_access_specifier == access_private_node);
- TREE_PROTECTED (decl)
+ TREE_PROTECTED (decl)
= (current_access_specifier == access_protected_node);
if (TREE_CODE (decl) == TEMPLATE_DECL)
{
/* Put functions on the TYPE_METHODS list and everything else on the
TYPE_FIELDS list. Note that these are built up in reverse order.
We reverse them (to obtain declaration order) in finish_struct. */
- if (TREE_CODE (decl) == FUNCTION_DECL
+ if (TREE_CODE (decl) == FUNCTION_DECL
|| DECL_FUNCTION_TEMPLATE_P (decl))
{
/* We also need to add this function to the
TREE_CHAIN (decl) = TYPE_METHODS (current_class_type);
TYPE_METHODS (current_class_type) = decl;
- maybe_add_class_template_decl_list (current_class_type, decl,
+ maybe_add_class_template_decl_list (current_class_type, decl,
/*friend_p=*/0);
}
/* Enter the DECL into the scope of the class. */
list.) */
if (TREE_CODE (decl) == TYPE_DECL)
- TYPE_FIELDS (current_class_type)
+ TYPE_FIELDS (current_class_type)
= chainon (TYPE_FIELDS (current_class_type), decl);
else
{
TYPE_FIELDS (current_class_type) = decl;
}
- maybe_add_class_template_decl_list (current_class_type, decl,
+ maybe_add_class_template_decl_list (current_class_type, decl,
/*friend_p=*/0);
}
comdat_linkage (decl);
DECL_INTERFACE_KNOWN (decl) = 1;
}
-
+
/* There's a good chance that we'll have to mangle names at some
point, even if only for emission in debugging information. */
if (TREE_CODE (decl) == VAR_DECL
access_{default,public,protected_private}_node. For a virtual base
we set TREE_TYPE. */
-tree
+tree
finish_base_specifier (tree base, tree access, bool virtual_p)
{
tree result;
else
error ("%<::%D%> has not been declared", name);
}
-
+
/* ID_EXPRESSION is a representation of parsed, but unprocessed,
id-expression. (See cp_parser_id_expression for details.) SCOPE,
if non-NULL, is the type or namespace used to explicitly qualify
ID_EXPRESSION. DECL is the entity to which that name has been
- resolved.
+ resolved.
*CONSTANT_EXPRESSION_P is true if we are presently parsing a
constant-expression. In that case, *NON_CONSTANT_EXPRESSION_P will
Return an expression for the entity, after issuing appropriate
diagnostics. This function is also responsible for transforming a
reference to a non-static member into a COMPONENT_REF that makes
- the use of "this" explicit.
+ the use of "this" explicit.
Upon return, *IDK will be filled in appropriately. */
tree
-finish_id_expression (tree id_expression,
+finish_id_expression (tree id_expression,
tree decl,
tree scope,
cp_id_kind *idk,
|| TREE_CODE (decl) == TYPE_DECL)
;
/* Look up the name. */
- else
+ else
{
if (decl == error_mark_node)
{
/* Name lookup failed. */
- if (scope
- && (!TYPE_P (scope)
+ if (scope
+ && (!TYPE_P (scope)
|| (!dependent_type_p (scope)
&& !(TREE_CODE (id_expression) == IDENTIFIER_NODE
&& IDENTIFIER_TYPENAME_P (id_expression)
|| TREE_CODE (decl) == TEMPLATE_PARM_INDEX)
{
tree r;
-
+
*idk = CP_ID_KIND_NONE;
if (TREE_CODE (decl) == TEMPLATE_PARM_INDEX)
decl = TEMPLATE_PARM_DECL (decl);
r = convert_from_reference (DECL_INITIAL (decl));
-
- if (integral_constant_expression_p
+
+ if (integral_constant_expression_p
&& !dependent_type_p (TREE_TYPE (decl))
&& !(INTEGRAL_OR_ENUMERATION_TYPE_P (TREE_TYPE (r))))
{
}
return r;
}
- /* Similarly, we resolve enumeration constants to their
+ /* Similarly, we resolve enumeration constants to their
underlying values. */
else if (TREE_CODE (decl) == CONST_DECL)
{
/* If the declaration was explicitly qualified indicate
that. The semantics of `A::f(3)' are different than
`f(3)' if `f' is virtual. */
- *idk = (scope
+ *idk = (scope
? CP_ID_KIND_QUALIFIED
: (TREE_CODE (decl) == TEMPLATE_ID_EXPR
? CP_ID_KIND_TEMPLATE_ID
/* A template-id where the name of the template was not resolved
is definitely dependent. */
else if (TREE_CODE (decl) == TEMPLATE_ID_EXPR
- && (TREE_CODE (TREE_OPERAND (decl, 0))
+ && (TREE_CODE (TREE_OPERAND (decl, 0))
== IDENTIFIER_NODE))
dependent_p = true;
/* For anything except an overloaded function, just check its
type. */
else if (!is_overloaded_fn (decl))
- dependent_p
+ dependent_p
= dependent_type_p (TREE_TYPE (decl));
/* For a set of overloaded functions, check each of the
functions. */
}
*non_integral_constant_expression_p = true;
}
-
+
if (TREE_CODE (decl) == NAMESPACE_DECL)
{
error ("use of namespace %qD as expression", decl);
if (scope)
{
- decl = (adjust_result_of_qualified_name_lookup
+ decl = (adjust_result_of_qualified_name_lookup
(decl, scope, current_class_type));
if (TREE_CODE (decl) == FUNCTION_DECL)
else
{
tree r = convert_from_reference (decl);
-
+
if (processing_template_decl
&& TYPE_P (scope))
r = build2 (SCOPE_REF, TREE_TYPE (r), scope, decl);
|| TREE_CODE (decl) == RESULT_DECL)
{
tree context = decl_function_context (decl);
-
+
if (context != NULL_TREE && context != current_function_decl
&& ! TREE_STATIC (decl))
{
return error_mark_node;
}
}
-
+
if (DECL_P (decl) && DECL_NONLOCAL (decl)
&& DECL_CLASS_SCOPE_P (decl)
&& DECL_CONTEXT (decl) != current_class_type)
{
tree path;
-
+
path = currently_open_derived_class (DECL_CONTEXT (decl));
perform_or_defer_access_check (TYPE_BINFO (path), decl);
}
-
+
decl = convert_from_reference (decl);
}
-
+
/* Resolve references to variables of anonymous unions
into COMPONENT_REFs. */
if (TREE_CODE (decl) == ALIAS_DECL)
with equivalent CALL_EXPRs. */
static tree
-simplify_aggr_init_exprs_r (tree* tp,
+simplify_aggr_init_exprs_r (tree* tp,
int* walk_subtrees,
void* data ATTRIBUTE_UNUSED)
{
{
/* The return type might have different cv-quals from the slot. */
tree fntype = TREE_TYPE (TREE_TYPE (fn));
-
+
gcc_assert (TREE_CODE (fntype) == FUNCTION_TYPE
|| TREE_CODE (fntype) == METHOD_TYPE);
addr = convert (build_pointer_type (TREE_TYPE (fntype)), addr);
args = tree_cons (NULL_TREE, addr, args);
}
- call_expr = build3 (CALL_EXPR,
+ call_expr = build3 (CALL_EXPR,
TREE_TYPE (TREE_TYPE (TREE_TYPE (fn))),
fn, args, NULL_TREE);
if (DECL_VIRTUAL_P (fn))
{
tree thunk;
-
+
for (thunk = DECL_THUNKS (fn); thunk; thunk = TREE_CHAIN (thunk))
{
if (!THUNK_ALIAS (thunk))
if (DECL_RESULT_THUNK_P (thunk))
{
tree probe;
-
+
for (probe = DECL_THUNKS (thunk);
probe; probe = TREE_CHAIN (probe))
use_thunk (probe, /*emit_p=*/1);
/* If this is a clone, go through the other clones now and mark
their parameters used. We have to do that here, as we don't
know whether any particular clone will be expanded, and
- therefore cannot pick one arbitrarily. */
+ therefore cannot pick one arbitrarily. */
tree probe;
for (probe = TREE_CHAIN (DECL_CLONED_FUNCTION (fn));
tree attributes;
/* FIXME: Attributes. */
- gcc_assert (ARITHMETIC_TYPE_P (t1)
+ gcc_assert (ARITHMETIC_TYPE_P (t1)
|| TREE_CODE (t1) == COMPLEX_TYPE
|| TREE_CODE (t1) == VECTOR_TYPE
|| TREE_CODE (t1) == ENUMERAL_TYPE);
- gcc_assert (ARITHMETIC_TYPE_P (t2)
+ gcc_assert (ARITHMETIC_TYPE_P (t2)
|| TREE_CODE (t2) == COMPLEX_TYPE
|| TREE_CODE (t1) == VECTOR_TYPE
|| TREE_CODE (t2) == ENUMERAL_TYPE);
convert to a long long. Otherwise, convert to an unsigned long
long. Otherwise, if either operand is long long, convert the
other to long long.
-
+
Since we're here, we know the TYPE_PRECISION is the same;
therefore converting to long long cannot represent all the values
of an unsigned long, so we choose unsigned long long in that
|| same_type_p (TYPE_MAIN_VARIANT (t2), long_long_integer_type_node))
{
tree t = ((TYPE_UNSIGNED (t1) || TYPE_UNSIGNED (t2))
- ? long_long_unsigned_type_node
+ ? long_long_unsigned_type_node
: long_long_integer_type_node);
return build_type_attribute_variant (t, attributes);
}
-
+
/* Go through the same procedure, but for longs. */
if (same_type_p (TYPE_MAIN_VARIANT (t1), long_unsigned_type_node)
|| same_type_p (TYPE_MAIN_VARIANT (t2), long_unsigned_type_node))
|| same_type_p (TYPE_MAIN_VARIANT (t2), float_type_node))
return build_type_attribute_variant (float_type_node,
attributes);
-
+
/* Two floating-point types whose TYPE_MAIN_VARIANTs are none of
the standard C++ floating-point types. Logic earlier in this
function has already eliminated the possibility that
/* Return the composite pointer type (see [expr.rel]) for T1 and T2.
ARG1 and ARG2 are the values with those types. The LOCATION is a
- string describing the current location, in case an error occurs.
+ string describing the current location, in case an error occurs.
This routine also implements the computation of a common type for
pointers-to-members as per [expr.eq]. */
-tree
+tree
composite_pointer_type (tree t1, tree t2, tree arg1, tree arg2,
const char* location)
{
return t2;
if (null_ptr_cst_p (arg2))
return t1;
-
+
/* We have:
[expr.rel]
if (pedantic && TYPE_PTRFN_P (t2))
pedwarn ("ISO C++ forbids %s between pointer of type %<void *%> "
"and pointer-to-function", location);
- result_type
+ result_type
= cp_build_qualified_type (void_type_node,
(cp_type_quals (TREE_TYPE (t1))
| cp_type_quals (TREE_TYPE (t2))));
class2 = TREE_TYPE (t2);
if (DERIVED_FROM_P (class1, class2))
- t2 = (build_pointer_type
+ t2 = (build_pointer_type
(cp_build_qualified_type (class1, TYPE_QUALS (class2))));
else if (DERIVED_FROM_P (class2, class1))
- t1 = (build_pointer_type
+ t1 = (build_pointer_type
(cp_build_qualified_type (class2, TYPE_QUALS (class1))));
else
{
/* Compare two exception specifier types for exactness or subsetness, if
allowed. Returns false for mismatch, true for match (same, or
derived and !exact).
-
+
[except.spec] "If a class X ... objects of class X or any class publicly
and unambiguously derived from X. Similarly, if a pointer type Y * ...
exceptions of type Y * or that are pointers to any type publicly and
[except.throw] and catch [except.catch] will do. They will ignore the
top level cv qualifiers, and allow qualifiers in the pointer to class
example.
-
+
We implement the letter of the standard. */
static bool
{
if (cp_type_quals (a) || cp_type_quals (b))
return false;
-
+
if (TREE_CODE (a) == POINTER_TYPE
&& TREE_CODE (b) == POINTER_TYPE)
{
if (cp_type_quals (a) || cp_type_quals (b))
return false;
}
-
+
if (TREE_CODE (a) != RECORD_TYPE
|| TREE_CODE (b) != RECORD_TYPE)
return false;
-
+
if (PUBLICLY_UNIQUELY_DERIVED_P (a, b))
return true;
}
if (t1 == t2)
return true;
-
+
if (t1 == NULL_TREE) /* T1 is ... */
return t2 == NULL_TREE || !exact;
if (!TREE_VALUE (t1)) /* t1 is EMPTY */
return false;
if (TREE_VALUE (t1) && !TREE_VALUE (t2)) /* T2 is EMPTY, T1 is not */
return !exact;
-
+
/* Neither set is ... or EMPTY, make sure each part of T2 is in T1.
Count how many we find, to determine exactness. For exact matching and
ordered T1, T2, this is an O(n) operation, otherwise its worst case is
{
tree a = TREE_VALUE (probe);
tree b = TREE_VALUE (t2);
-
+
if (comp_except_types (a, b, exact))
{
if (probe == base && exact)
extern int a[];
int a[3];
- by [basic.link]:
+ by [basic.link]:
declarations for an array object can specify
array types that differ by the presence or absence of a major
/* Suppress errors caused by previously reported errors. */
if (t1 == error_mark_node || t2 == error_mark_node)
return false;
-
+
gcc_assert (TYPE_P (t1) && TYPE_P (t2));
-
+
/* TYPENAME_TYPEs should be resolved if the qualifying scope is the
current instantiation. */
if (TREE_CODE (t1) == TYPENAME_TYPE)
if (resolved != error_mark_node)
t1 = resolved;
}
-
+
if (TREE_CODE (t2) == TYPENAME_TYPE)
{
tree resolved = resolve_typename_type (t2, /*only_current_p=*/true);
|| TREE_CODE (t1) == BOUND_TEMPLATE_TEMPLATE_PARM)
&& comp_template_args (TYPE_TI_ARGS (t1), TYPE_TI_ARGS (t2)))
break;
-
+
if ((strict & COMPARE_BASE) && DERIVED_FROM_P (t1, t2))
break;
else if ((strict & COMPARE_DERIVED) && DERIVED_FROM_P (t2, t1))
break;
-
+
return false;
case OFFSET_TYPE:
{
int q1 = cp_type_quals (type1);
int q2 = cp_type_quals (type2);
-
+
/* All qualifiers for TYPE2 must also appear in TYPE1. */
return (q1 & q2) == q2;
}
{
tree basetype = BINFO_TYPE (BINFO_BASE_BINFO (TYPE_BINFO (tt1), i));
tree trial = common_base_type (basetype, tt2);
-
+
if (trial)
{
if (trial == error_mark_node)
{
tree basetype = BINFO_TYPE (BINFO_BASE_BINFO (TYPE_BINFO (tt2), i));
tree trial = common_base_type (tt1, basetype);
-
+
if (trial)
{
if (trial == error_mark_node)
gcc_assert (op == SIZEOF_EXPR || op == ALIGNOF_EXPR);
if (type == error_mark_node)
return error_mark_node;
-
+
if (dependent_type_p (type))
{
value = build_min (op, size_type_node, type);
TREE_READONLY (value) = 1;
return value;
}
-
+
op_name = operator_name_info[(int) op].name;
type = non_reference (type);
cxx_sizeof_or_alignof_expr (tree e, enum tree_code op)
{
const char *op_name = operator_name_info[(int) op].name;
-
+
if (e == error_mark_node)
return error_mark_node;
-
+
if (processing_template_decl)
{
e = build_min (op, size_type_node, e);
TREE_SIDE_EFFECTS (e) = 0;
TREE_READONLY (e) = 1;
-
+
return e;
}
-
+
if (TREE_CODE (e) == COMPONENT_REF
&& TREE_CODE (TREE_OPERAND (e, 1)) == FIELD_DECL
&& DECL_C_BIT_FIELD (TREE_OPERAND (e, 1)))
}
else
e = TREE_TYPE (e);
-
+
return cxx_sizeof_or_alignof_type (e, op, true);
}
-
+
\f
/* EXPR is being used in a context that is not a function call.
Enforce:
- [expr.ref]
+ [expr.ref]
The expression can be used only as the left-hand operand of a
- member function call.
+ member function call.
[expr.mptr.operator]
If the result of .* or ->* is a function, then that result can be
- used only as the operand for the function call operator ().
+ used only as the operand for the function call operator ().
by issuing an error message if appropriate. Returns true iff EXPR
violates these rules. */
}
exp = integral_constant_value (exp);
-
+
/* build_c_cast puts on a NOP_EXPR to make the result not an lvalue.
Leave such NOP_EXPRs, since RHS is being used in non-lvalue context. */
tree ptrtype;
if (TREE_CODE (exp) == INDIRECT_REF)
- return build_nop (build_pointer_type (TREE_TYPE (type)),
+ return build_nop (build_pointer_type (TREE_TYPE (type)),
TREE_OPERAND (exp, 0));
if (TREE_CODE (exp) == COMPOUND_EXPR)
non-NULL, it indicates the path to the base used to name MEMBER.
If PRESERVE_REFERENCE is true, the expression returned will have
REFERENCE_TYPE if the MEMBER does. Otherwise, the expression
- returned will have the type referred to by the reference.
+ returned will have the type referred to by the reference.
This function does not perform access control; that is either done
earlier by the parser when the name of MEMBER is resolved to MEMBER
functions indicated by MEMBER. */
tree
-build_class_member_access_expr (tree object, tree member,
+build_class_member_access_expr (tree object, tree member,
tree access_path, bool preserve_reference)
{
tree object_type;
The type of the first expression shall be "class object" (of a
complete type). */
object_type = TREE_TYPE (object);
- if (!currently_open_class (object_type)
+ if (!currently_open_class (object_type)
&& !complete_type_or_else (object_type, object))
return error_mark_node;
if (!CLASS_TYPE_P (object_type))
{
- error ("request for member %qD in %qE, which is of non-class type %qT",
+ error ("request for member %qD in %qE, which is of non-class type %qT",
member, object, object_type);
return error_mark_node;
}
}
/* Convert to the base. */
- object = build_base_path (PLUS_EXPR, object, binfo,
+ object = build_base_path (PLUS_EXPR, object, binfo,
/*nonnull=*/1);
/* If we found the base successfully then we should be able
to convert to it successfully. */
&& !DECL_FIELD_IS_BASE (member)
&& !skip_evaluation)
{
- warning (0, "invalid access to non-static data member %qD of NULL object",
+ warning (0, "invalid access to non-static data member %qD of NULL object",
member);
warning (0, "(perhaps the %<offsetof%> macro was used incorrectly)");
}
constructed, and was then disassembled before calling
build_field_call. After the function-call code is
cleaned up, this waste can be eliminated. */
- && (!same_type_ignoring_top_level_qualifiers_p
+ && (!same_type_ignoring_top_level_qualifiers_p
(TREE_TYPE (object), DECL_CONTEXT (member))))
{
tree anonymous_union;
member_type = TREE_TYPE (member);
if (TREE_CODE (member_type) != REFERENCE_TYPE)
{
- type_quals = (cp_type_quals (member_type)
+ type_quals = (cp_type_quals (member_type)
| cp_type_quals (object_type));
-
+
/* A field is const (volatile) if the enclosing object, or the
field itself, is const (volatile). But, a mutable field is
not const, even within a const object. */
if (!preserve_reference)
/* [expr.ref]
-
+
If E2 is declared to have type "reference to T", then ... the
type of E1.E2 is T. */
result = convert_from_reference (result);
return build_min_nt (COMPONENT_REF, object, name, NULL_TREE);
object = build_non_dependent_expr (object);
}
-
+
/* [expr.ref]
The type of the first expression shall be "class object" (of a
complete type). */
- if (!currently_open_class (object_type)
+ if (!currently_open_class (object_type)
&& !complete_type_or_else (object_type, object))
return error_mark_node;
if (!CLASS_TYPE_P (object_type))
{
- error ("request for member %qD in %qE, which is of non-class type %qT",
+ error ("request for member %qD in %qE, which is of non-class type %qT",
name, object, object_type);
return error_mark_node;
}
name a member of OBJECT_TYPE. */
if (TREE_CODE (scope) == NAMESPACE_DECL)
{
- error ("%<%D::%D%> is not a member of %qT",
+ error ("%<%D::%D%> is not a member of %qT",
scope, name, object_type);
return error_mark_node;
}
else
{
/* Look up the member. */
- member = lookup_member (access_path, name, /*protect=*/1,
+ member = lookup_member (access_path, name, /*protect=*/1,
/*want_type=*/false);
if (member == NULL_TREE)
{
if (member == error_mark_node)
return error_mark_node;
}
-
+
if (is_template_id)
{
tree template = member;
-
+
if (BASELINK_P (template))
template = lookup_template_function (template, template_args);
else
if (POINTER_TYPE_P (type))
{
/* [expr.unary.op]
-
+
If the type of the expression is "pointer to T," the type
- of the result is "T."
+ of the result is "T."
We must use the canonical variant because certain parts of
the back end, like fold, do pointer comparisons between
be incomplete. In that case, the function will of course be
a member of C, and no conversion is required. In fact,
lookup_base will fail in that case, because incomplete
- classes do not have BINFOs. */
+ classes do not have BINFOs. */
basetype = TYPE_METHOD_BASETYPE (TREE_TYPE (fntype));
- if (!same_type_ignoring_top_level_qualifiers_p
+ if (!same_type_ignoring_top_level_qualifiers_p
(basetype, TREE_TYPE (TREE_TYPE (instance_ptr))))
{
basetype = lookup_base (TREE_TYPE (TREE_TYPE (instance_ptr)),
basetype, ba_check, NULL);
- instance_ptr = build_base_path (PLUS_EXPR, instance_ptr, basetype,
+ instance_ptr = build_base_path (PLUS_EXPR, instance_ptr, basetype,
1);
if (instance_ptr == error_mark_node)
return error_mark_node;
TREE_TYPE (e2) = TREE_TYPE (e3);
e1 = build_conditional_expr (e1, e2, e3);
-
+
/* Make sure this doesn't get evaluated first inside one of the
branches of the COND_EXPR. */
if (instance_save_expr)
/* Differs from default_conversion by not setting TREE_ADDRESSABLE
(because calling an inline function does not mean the function
needs to be separately compiled). */
-
+
if (DECL_INLINE (function))
function = inline_conversion (function);
else
NAME is an IDENTIFIER_NODE or 0. It is used only for error messages.
This is also where warnings about wrong number of args are generated.
-
+
Return a list of expressions for the parameters as converted.
Both VALUES and the returned value are chains of TREE_LIST nodes
if (typetail != 0 && typetail != void_list_node)
{
/* See if there are default arguments that can be used. */
- if (TREE_PURPOSE (typetail)
+ if (TREE_PURPOSE (typetail)
&& TREE_CODE (TREE_PURPOSE (typetail)) != DEFAULT_ARG)
{
for (; typetail != void_list_node; ++i)
{
- tree parmval
- = convert_default_arg (TREE_VALUE (typetail),
- TREE_PURPOSE (typetail),
+ tree parmval
+ = convert_default_arg (TREE_VALUE (typetail),
+ TREE_PURPOSE (typetail),
fndecl, i);
if (parmval == error_mark_node)
conversions on the operands. CODE is the kind of expression to build. */
tree
-build_x_binary_op (enum tree_code code, tree arg1, tree arg2,
+build_x_binary_op (enum tree_code code, tree arg1, tree arg2,
bool *overloaded_p)
{
tree orig_arg1;
if (code == DOTSTAR_EXPR)
expr = build_m_component_ref (arg1, arg2);
else
- expr = build_new_op (code, LOOKUP_NORMAL, arg1, arg2, NULL_TREE,
+ expr = build_new_op (code, LOOKUP_NORMAL, arg1, arg2, NULL_TREE,
overloaded_p);
if (processing_template_decl && expr != error_mark_node)
return build_min_non_dep (code, expr, orig_arg1, orig_arg2);
-
+
return expr;
}
/* Apply default conversions. */
op0 = orig_op0;
op1 = orig_op1;
-
+
if (code == TRUTH_AND_EXPR || code == TRUTH_ANDIF_EXPR
|| code == TRUTH_OR_EXPR || code == TRUTH_ORIF_EXPR
|| code == TRUTH_XOR_EXPR)
warning (0, "division by zero in %<%E / 0%>", op0);
else if (TREE_CODE (op1) == REAL_CST && real_zerop (op1))
warning (0, "division by zero in %<%E / 0.%>", op0);
-
+
if (code0 == COMPLEX_TYPE || code0 == VECTOR_TYPE)
code0 = TREE_CODE (TREE_TYPE (TREE_TYPE (op0)));
if (code1 == COMPLEX_TYPE || code1 == VECTOR_TYPE)
warning (0, "division by zero in %<%E %% 0%>", op0);
else if (code1 == REAL_TYPE && real_zerop (op1))
warning (0, "division by zero in %<%E %% 0.%>", op0);
-
+
if (code0 == INTEGER_TYPE && code1 == INTEGER_TYPE)
{
/* Although it would be tempting to shorten always here, that loses
if (warn_float_equal && (code0 == REAL_TYPE || code1 == REAL_TYPE))
warning (0, "comparing floating point with == or != is unsafe");
- build_type = boolean_type_node;
+ build_type = boolean_type_node;
if ((code0 == INTEGER_TYPE || code0 == REAL_TYPE
|| code0 == COMPLEX_TYPE)
&& (code1 == INTEGER_TYPE || code1 == REAL_TYPE
/* We generate:
- (op0.pfn == op1.pfn
+ (op0.pfn == op1.pfn
&& (!op0.pfn || op0.delta == op1.delta))
-
+
The reason for the `!op0.pfn' bit is that a NULL
pointer-to-member is any member with a zero PFN; the
DELTA field is unspecified. */
delta1 = build_ptrmemfunc_access_expr (op1,
delta_identifier);
e1 = cp_build_binary_op (EQ_EXPR, delta0, delta1);
- e2 = cp_build_binary_op (EQ_EXPR,
+ e2 = cp_build_binary_op (EQ_EXPR,
pfn0,
cp_convert (TREE_TYPE (pfn0),
integer_zero_node));
|| !same_type_p (TYPE_PTRMEMFUNC_FN_TYPE (type1),
type0));
}
-
+
break;
case MAX_EXPR:
}
if (((code0 == INTEGER_TYPE || code0 == REAL_TYPE || code0 == COMPLEX_TYPE)
- && (code1 == INTEGER_TYPE || code1 == REAL_TYPE
+ && (code1 == INTEGER_TYPE || code1 == REAL_TYPE
|| code1 == COMPLEX_TYPE)))
arithmetic_types_p = 1;
else
}
/* Determine the RESULT_TYPE, if it is not already known. */
if (!result_type
- && arithmetic_types_p
+ && arithmetic_types_p
&& (shorten || common || short_compare))
result_type = common_type (type0, type1);
/* If we're in a template, the only thing we need to know is the
RESULT_TYPE. */
if (processing_template_decl)
- return build2 (resultcode,
- build_type ? build_type : result_type,
+ return build2 (resultcode,
+ build_type ? build_type : result_type,
op0, op1);
if (arithmetic_types_p)
pass the copies by reference, then copy them back afterward. */
tree xop0 = op0, xop1 = op1, xresult_type = result_type;
enum tree_code xresultcode = resultcode;
- tree val
+ tree val
= shorten_compare (&xop0, &xop1, &xresult_type, &xresultcode);
if (val != 0)
return cp_convert (boolean_type_node, val);
tree primop1 = get_narrower (op1, &unsignedp1);
/* Check for comparison of different enum types. */
- if (TREE_CODE (TREE_TYPE (orig_op0)) == ENUMERAL_TYPE
- && TREE_CODE (TREE_TYPE (orig_op1)) == ENUMERAL_TYPE
+ if (TREE_CODE (TREE_TYPE (orig_op0)) == ENUMERAL_TYPE
+ && TREE_CODE (TREE_TYPE (orig_op1)) == ENUMERAL_TYPE
&& TYPE_MAIN_VARIANT (TREE_TYPE (orig_op0))
!= TYPE_MAIN_VARIANT (TREE_TYPE (orig_op1)))
{
- warning (0, "comparison between types %q#T and %q#T",
+ warning (0, "comparison between types %q#T and %q#T",
TREE_TYPE (orig_op0), TREE_TYPE (orig_op1));
}
primop0 = get_narrower (TREE_OPERAND (op0, 0), &unsignedp0);
if (TREE_CODE (primop1) == BIT_NOT_EXPR)
primop1 = get_narrower (TREE_OPERAND (op1, 0), &unsignedp1);
-
+
if (host_integerp (primop0, 0) || host_integerp (primop1, 0))
{
tree primop;
|| (orig_op1 == null_node
&& TREE_CODE (TREE_TYPE (op0)) != POINTER_TYPE)
/* Or, both are NULL and the operation was not a comparison. */
- || (orig_op0 == null_node && orig_op1 == null_node
+ || (orig_op0 == null_node && orig_op1 == null_node
&& code != EQ_EXPR && code != NE_EXPR)))
/* Some sort of arithmetic operation involving NULL was
performed. Note that pointer-difference and pointer-addition
if (! converted)
{
if (TREE_TYPE (op0) != result_type)
- op0 = cp_convert (result_type, op0);
+ op0 = cp_convert (result_type, op0);
if (TREE_TYPE (op1) != result_type)
- op1 = cp_convert (result_type, op1);
+ op1 = cp_convert (result_type, op1);
if (op0 == error_mark_node || op1 == error_mark_node)
return error_mark_node;
/* First do the subtraction as integers;
then drop through to build the divide operator. */
- op0 = cp_build_binary_op (MINUS_EXPR,
+ op0 = cp_build_binary_op (MINUS_EXPR,
cp_convert (restype, op0),
cp_convert (restype, op1));
if (!COMPLETE_TYPE_P (TREE_TYPE (TREE_TYPE (op1))))
error ("invalid use of a pointer to an incomplete type in pointer arithmetic");
- op1 = (TYPE_PTROB_P (ptrtype)
+ op1 = (TYPE_PTROB_P (ptrtype)
? size_in_bytes (target_type)
: integer_one_node);
tree orig_expr = xarg;
tree exp;
int ptrmem = 0;
-
+
if (processing_template_decl)
{
if (type_dependent_expression_p (xarg))
PTRMEM_OK_P (xarg) = 1;
}
}
-
+
if (TREE_CODE (xarg) == OFFSET_REF)
{
ptrmem = PTRMEM_OK_P (xarg);
-
+
if (!ptrmem && !flag_ms_extensions
&& TREE_CODE (TREE_TYPE (TREE_OPERAND (xarg, 1))) == METHOD_TYPE)
{
TREE_OPERAND (xarg, 0),
ovl_cons (TREE_OPERAND (xarg, 1), NULL_TREE));
PTRMEM_OK_P (xarg) = ptrmem;
- }
+ }
}
else if (TREE_CODE (xarg) == TARGET_EXPR)
warning (0, "taking address of temporary");
}
/* Just like cp_truthvalue_conversion, but we want a CLEANUP_POINT_EXPR. */
-
+
tree
condition_conversion (tree expr)
{
t = fold_build_cleanup_point_expr (boolean_type_node, t);
return t;
}
-
+
/* Return an ADDR_EXPR giving the address of T. This function
attempts no optimizations or simplifications; it is a low-level
primitive. */
case NOP_EXPR:
break;
-
+
case REALPART_EXPR:
if (TREE_CODE (arg) == COMPLEX_CST)
return TREE_REALPART (arg);
}
else
return cp_convert (TREE_TYPE (arg), integer_zero_node);
-
+
case PREINCREMENT_EXPR:
case POSTINCREMENT_EXPR:
case PREDECREMENT_EXPR:
pedwarn ("ISO C++ forbids %sing an enum",
(code == PREINCREMENT_EXPR || code == POSTINCREMENT_EXPR)
? "increment" : "decrement");
-
+
/* Compute the increment. */
if (TREE_CODE (argtype) == POINTER_TYPE)
{
tree type = complete_type (TREE_TYPE (argtype));
-
+
if (!COMPLETE_OR_VOID_TYPE_P (type))
error ("cannot %s a pointer to incomplete type %qT",
((code == PREINCREMENT_EXPR
arg = build_offset_ref (base, name, /*address_p=*/true);
}
- offset_ref:
+ offset_ref:
if (type_unknown_p (arg))
return build1 (ADDR_EXPR, unknown_type_node, arg);
-
+
/* Handle complex lvalues (when permitted)
by reduction to simpler cases. */
val = unary_complex_lvalue (code, arg);
if (!PTRMEM_OK_P (arg))
return build_unary_op (code, arg, 0);
-
+
t = TREE_OPERAND (arg, 1);
if (TREE_CODE (TREE_TYPE (t)) == REFERENCE_TYPE)
{
error ("cannot create pointer to reference member %qD", t);
return error_mark_node;
}
-
- type = build_ptrmem_type (context_for_name_lookup (t),
+
+ type = build_ptrmem_type (context_for_name_lookup (t),
TREE_TYPE (t));
t = make_ptrmem_cst (type, TREE_OPERAND (arg, 1));
return t;
If ARG is not a kind of expression we can handle, return
NULL_TREE. */
-
+
tree
unary_complex_lvalue (enum tree_code code, tree arg)
{
|| TREE_CODE (TREE_TYPE (arg)) == METHOD_TYPE
|| TREE_CODE (arg) == OFFSET_REF)
return NULL_TREE;
-
+
/* We permit compiler to make function calls returning
objects of aggregate type look like lvalues. */
{
expr = build_conditional_expr (ifexp, op1, op2);
if (processing_template_decl && expr != error_mark_node)
- return build_min_non_dep (COND_EXPR, expr,
+ return build_min_non_dep (COND_EXPR, expr,
orig_ifexp, orig_op1, orig_op2);
return expr;
}
tree build_x_compound_expr_from_list (tree list, const char *msg)
{
tree expr = TREE_VALUE (list);
-
+
if (TREE_CHAIN (list))
{
if (msg)
for (list = TREE_CHAIN (list); list; list = TREE_CHAIN (list))
expr = build_x_compound_expr (expr, TREE_VALUE (list));
}
-
+
return expr;
}
if (processing_template_decl && result != error_mark_node)
return build_min_non_dep (COMPOUND_EXPR, result, orig_op1, orig_op2);
-
+
return result;
}
build_compound_expr (tree lhs, tree rhs)
{
lhs = convert_to_void (lhs, "left-hand operand of comma");
-
+
if (lhs == error_mark_node || rhs == error_mark_node)
return error_mark_node;
-
+
if (TREE_CODE (rhs) == TARGET_EXPR)
{
/* If the rhs is a TARGET_EXPR, then build the compound
expression inside the target_expr's initializer. This
helps the compiler to eliminate unnecessary temporaries. */
tree init = TREE_OPERAND (rhs, 1);
-
+
init = build2 (COMPOUND_EXPR, TREE_TYPE (init), lhs, init);
TREE_OPERAND (rhs, 1) = init;
-
+
return rhs;
}
-
+
return build2 (COMPOUND_EXPR, TREE_TYPE (rhs), lhs, rhs);
}
only the other direction is permitted. If C_CAST_P is true, this
conversion is taking place as part of a C-style cast. */
-tree
+tree
convert_ptrmem (tree type, tree expr, bool allow_inverse_p,
bool c_cast_p)
{
if (TREE_CODE (expr) == PTRMEM_CST)
expr = cplus_expand_constant (expr);
delta = get_delta_difference (TYPE_PTRMEM_CLASS_TYPE (TREE_TYPE (expr)),
- TYPE_PTRMEM_CLASS_TYPE (type),
+ TYPE_PTRMEM_CLASS_TYPE (type),
allow_inverse_p,
c_cast_p);
if (!integer_zerop (delta))
- expr = cp_build_binary_op (PLUS_EXPR,
+ expr = cp_build_binary_op (PLUS_EXPR,
build_nop (ptrdiff_type_node, expr),
delta);
return build_nop (type, expr);
}
else
- return build_ptrmemfunc (TYPE_PTRMEMFUNC_FN_TYPE (type), expr,
+ return build_ptrmemfunc (TYPE_PTRMEMFUNC_FN_TYPE (type), expr,
allow_inverse_p, c_cast_p);
}
if (c_cast_p)
{
/* C-style casts are allowed to cast away constness. With
- WARN_CAST_QUAL, we still want to issue a warning. */
+ WARN_CAST_QUAL, we still want to issue a warning. */
diag_fn = warn_cast_qual ? warning0 : NULL;
desc = "cast";
}
diag_fn = error;
desc = "static_cast";
}
-
+
/* [expr.static.cast]
An lvalue of type "cv1 B", where B is a class type, can be cast
&& real_lvalue_p (expr)
&& DERIVED_FROM_P (intype, TREE_TYPE (type))
&& can_convert (build_pointer_type (TYPE_MAIN_VARIANT (intype)),
- build_pointer_type (TYPE_MAIN_VARIANT
+ build_pointer_type (TYPE_MAIN_VARIANT
(TREE_TYPE (type))))
&& (c_cast_p
|| at_least_as_qualified_p (TREE_TYPE (type), intype)))
ambiguity. However, if this is a static_cast being performed
because the user wrote a C-style cast, then accessibility is
not considered. */
- base = lookup_base (TREE_TYPE (type), intype,
- c_cast_p ? ba_unique : ba_check,
+ base = lookup_base (TREE_TYPE (type), intype,
+ c_cast_p ? ba_unique : ba_check,
NULL);
/* Convert from "B*" to "D*". This function will check that "B"
is not a virtual base of "D". */
- expr = build_base_path (MINUS_EXPR, build_address (expr),
+ expr = build_base_path (MINUS_EXPR, build_address (expr),
base, /*nonnull=*/false);
/* Convert the pointer to a reference -- but then remember that
there are no expressions with reference type in C++. */
result = build1 (NON_LVALUE_EXPR, TREE_TYPE (result), result);
return result;
}
-
+
/* [expr.static.cast]
Any expression can be explicitly converted to type cv void. */
floating point conversions, floating-integral conversions,
pointer conversions, and pointer to member conversions. */
/* DR 128
-
+
A value of integral _or enumeration_ type can be explicitly
converted to an enumeration type. */
/* The effect of all that is that any conversion between any two
if (TYPE_PTR_P (type) && TYPE_PTR_P (intype)
&& CLASS_TYPE_P (TREE_TYPE (type))
&& CLASS_TYPE_P (TREE_TYPE (intype))
- && can_convert (build_pointer_type (TYPE_MAIN_VARIANT
- (TREE_TYPE (intype))),
- build_pointer_type (TYPE_MAIN_VARIANT
+ && can_convert (build_pointer_type (TYPE_MAIN_VARIANT
+ (TREE_TYPE (intype))),
+ build_pointer_type (TYPE_MAIN_VARIANT
(TREE_TYPE (type)))))
{
tree base;
if (!c_cast_p)
check_for_casting_away_constness (intype, type, diag_fn, desc);
- base = lookup_base (TREE_TYPE (type), TREE_TYPE (intype),
- c_cast_p ? ba_unique : ba_check,
+ base = lookup_base (TREE_TYPE (type), TREE_TYPE (intype),
+ c_cast_p ? ba_unique : ba_check,
NULL);
return build_base_path (MINUS_EXPR, expr, base, /*nonnull=*/false);
}
-
+
if ((TYPE_PTRMEM_P (type) && TYPE_PTRMEM_P (intype))
|| (TYPE_PTRMEMFUNC_P (type) && TYPE_PTRMEMFUNC_P (intype)))
{
if (TYPE_PTRMEM_P (type))
{
- t1 = (build_ptrmem_type
+ t1 = (build_ptrmem_type
(c1,
TYPE_MAIN_VARIANT (TYPE_PTRMEM_POINTED_TO_TYPE (intype))));
- t2 = (build_ptrmem_type
+ t2 = (build_ptrmem_type
(c2,
TYPE_MAIN_VARIANT (TYPE_PTRMEM_POINTED_TO_TYPE (type))));
}
if (can_convert (t1, t2))
{
if (!c_cast_p)
- check_for_casting_away_constness (intype, type, diag_fn,
+ check_for_casting_away_constness (intype, type, diag_fn,
desc);
return convert_ptrmem (type, expr, /*allow_inverse_p=*/1,
c_cast_p);
}
}
-
+
/* [expr.static.cast]
An rvalue of type "pointer to cv void" can be explicitly
converted to a pointer to object type. A value of type pointer
to object converted to "pointer to cv void" and back to the
original pointer type will have its original value. */
- if (TREE_CODE (intype) == POINTER_TYPE
+ if (TREE_CODE (intype) == POINTER_TYPE
&& VOID_TYPE_P (TREE_TYPE (intype))
&& TYPE_PTROB_P (type))
{
if (valid_p)
return result;
- error ("invalid static_cast from type %qT to type %qT",
+ error ("invalid static_cast from type %qT to type %qT",
TREE_TYPE (expr), type);
return error_mark_node;
}
if (pedantic || warn_pmf2ptr)
pedwarn ("converting from %qT to %qT", intype, type);
-
+
if (TREE_CODE (intype) == METHOD_TYPE)
expr = build_addr_func (expr);
else if (TREE_CODE (expr) == PTRMEM_CST)
if (! real_lvalue_p (expr))
{
error ("invalid cast of an rvalue expression of type "
- "%qT to type %qT",
+ "%qT to type %qT",
intype, type);
return error_mark_node;
}
pointer-to-function and pointer-to-void types. If
-Wno-pmf-conversions has not been specified,
convert_member_func_to_ptr will issue an error message. */
- if ((TYPE_PTRMEMFUNC_P (intype)
+ if ((TYPE_PTRMEMFUNC_P (intype)
|| TREE_CODE (intype) == METHOD_TYPE)
&& TYPE_PTR_P (type)
&& (TREE_CODE (TREE_TYPE (type)) == FUNCTION_TYPE
array-to-pointer, and function-to-pointer conversions are
performed. */
expr = decay_conversion (expr);
-
+
/* build_c_cast puts on a NOP_EXPR to make the result not an lvalue.
Strip such NOP_EXPRs if VALUE is being used in non-lvalue context. */
if (TREE_CODE (expr) == NOP_EXPR
|| (TYPE_PTROBV_P (type) && TYPE_PTROBV_P (intype)))
{
if (!c_cast_p)
- check_for_casting_away_constness (intype, type, error,
+ check_for_casting_away_constness (intype, type, error,
"reinterpret_cast");
/* Warn about possible alignment problems. */
if (STRICT_ALIGNMENT && warn_cast_align
warning (0, "cast from %qT to %qT increases required alignment of "
"target type",
intype, type);
-
+
return fold_if_not_in_template (build_nop (type, expr));
}
else if ((TYPE_PTRFN_P (type) && TYPE_PTROBV_P (intype))
error ("invalid cast from type %qT to type %qT", intype, type);
return error_mark_node;
}
-
+
return cp_convert (type, expr);
}
if (processing_template_decl)
{
tree t = build_min (REINTERPRET_CAST_EXPR, type, expr);
-
+
if (!TREE_SIDE_EFFECTS (t)
&& type_dependent_expression_p (expr))
/* There might turn out to be side effects inside expr. */
}
if (complain)
- error ("invalid const_cast from type %qT to type %qT",
+ error ("invalid const_cast from type %qT to type %qT",
src_type, dst_type);
return error_mark_node;
}
if (processing_template_decl)
{
tree t = build_min (CONST_CAST_EXPR, type, expr);
-
+
if (!TREE_SIDE_EFFECTS (t)
&& type_dependent_expression_p (expr))
/* There might turn out to be side effects inside expr. */
&valid_p);
/* The static_cast or reinterpret_cast may be followed by a
const_cast. */
- if (valid_p
+ if (valid_p
/* A valid cast may result in errors if, for example, a
conversion to am ambiguous base class is required. */
&& !error_operand_p (result))
tree preeval = NULL_TREE;
rhs = stabilize_expr (rhs, &preeval);
-
+
/* Check this here to avoid odd errors when trying to convert
a throw to the type of the COND_EXPR. */
if (!lvalue_or_else (lhs, lv_assign))
cond = build2 (COMPOUND_EXPR, TREE_TYPE (lhs), preeval, cond);
return cond;
}
-
+
default:
break;
}
TREE_TYPE (lhs), TREE_TYPE (rhs));
return error_mark_node;
}
-
+
/* Now it looks like a plain assignment. */
modifycode = NOP_EXPR;
}
if (TREE_CODE (lhstype) == ARRAY_TYPE)
{
int from_array;
-
+
if (!same_or_base_type_p (TYPE_MAIN_VARIANT (lhstype),
TYPE_MAIN_VARIANT (TREE_TYPE (rhs))))
{
a pointer to member of FROM to a pointer to member of TO. */
static tree
-get_delta_difference (tree from, tree to,
+get_delta_difference (tree from, tree to,
bool allow_inverse_p,
bool c_cast_p)
{
else
{
tree virt_binfo = binfo_from_vbase (binfo);
-
+
/* This is a reinterpret cast, we choose to do nothing. */
if (allow_inverse_p)
warning (0, "pointer to member cast via virtual base %qT",
{
/* This is a reinterpret cast, we choose to do nothing. */
tree virt_binfo = binfo_from_vbase (binfo);
-
+
warning (0, "pointer to member cast via virtual base %qT",
BINFO_TYPE (virt_binfo));
}
}
}
- return fold_if_not_in_template (convert_to_integer (ptrdiff_type_node,
+ return fold_if_not_in_template (convert_to_integer (ptrdiff_type_node,
result));
}
TREE_STATIC (u) = (TREE_CONSTANT (u)
&& (initializer_constant_valid_p (pfn, TREE_TYPE (pfn))
!= NULL_TREE)
- && (initializer_constant_valid_p (delta, TREE_TYPE (delta))
+ && (initializer_constant_valid_p (delta, TREE_TYPE (delta))
!= NULL_TREE));
return u;
}
tree npfn = NULL_TREE;
tree n;
- if (!force
+ if (!force
&& !can_convert_arg (to_type, TREE_TYPE (pfn), pfn))
- error ("invalid conversion to type %qT from type %qT",
+ error ("invalid conversion to type %qT from type %qT",
to_type, pfn_type);
n = get_delta_difference (TYPE_PTRMEMFUNC_OBJECT_TYPE (pfn_type),
{
pfn = build_c_cast (type, integer_zero_node);
return build_ptrmemfunc1 (to_type,
- integer_zero_node,
+ integer_zero_node,
pfn);
}
{
tree delta;
tree pfn;
-
+
expand_ptrmemfunc_cst (t, &delta, &pfn);
if (pfn)
return pfn;
/* When -Wno-pmf-conversions is use, we just silently allow
conversions from pointers-to-members to plain pointers. If
the conversion doesn't work, cp_convert will complain. */
- if (!warn_pmf2ptr
- && TYPE_PTR_P (type)
+ if (!warn_pmf2ptr
+ && TYPE_PTR_P (type)
&& TYPE_PTRMEMFUNC_P (rhstype))
rhs = cp_convert (strip_top_quals (type), rhs);
else
/* We accept references to incomplete types, so we can
return here before checking if RHS is of complete type. */
-
+
if (codel == REFERENCE_TYPE)
{
/* This should eventually happen in convert_arguments. */
cp_error_at ("in passing argument %P of %q+D", parmnum, fndecl);
}
return rhs;
- }
+ }
if (exp != 0)
exp = require_complete_type (exp);
if (TREE_CODE (whats_returned) != ADDR_EXPR)
return;
- whats_returned = TREE_OPERAND (whats_returned, 0);
+ whats_returned = TREE_OPERAND (whats_returned, 0);
if (TREE_CODE (valtype) == REFERENCE_TYPE)
{
warning (0, "returning reference to temporary");
return;
}
- if (TREE_CODE (whats_returned) == VAR_DECL
+ if (TREE_CODE (whats_returned) == VAR_DECL
&& DECL_NAME (whats_returned)
&& TEMP_NAME_P (DECL_NAME (whats_returned)))
{
|| TREE_PUBLIC (whats_returned)))
{
if (TREE_CODE (valtype) == REFERENCE_TYPE)
- cp_warning_at ("reference to local variable %qD returned",
+ cp_warning_at ("reference to local variable %qD returned",
whats_returned);
else
- cp_warning_at ("address of local variable %qD returned",
+ cp_warning_at ("address of local variable %qD returned",
whats_returned);
return;
}
current_function_returns_value = 1;
return retval;
}
-
+
/* When no explicit return-value is given in a function with a named
return value, the named return value is used. */
result = DECL_RESULT (current_function_decl);
/* Check for a return statement with a value in a function that
isn't supposed to return a value. */
else if (retval && !fn_returns_value_p)
- {
+ {
if (VOID_TYPE_P (TREE_TYPE (retval)))
/* You can return a `void' value from a function of `void'
type. In that case, we have to evaluate the expression for
else
maybe_warn_about_returning_address_of_local (retval);
}
-
+
/* Actually copy the value returned into the appropriate location. */
if (retval && retval != result)
retval = build2 (INIT_EXPR, TREE_TYPE (result), result, retval);
if (TREE_CODE (from) == OFFSET_TYPE
&& comptypes (TYPE_OFFSET_BASETYPE (to),
- TYPE_OFFSET_BASETYPE (from),
+ TYPE_OFFSET_BASETYPE (from),
COMPARE_BASE | COMPARE_DERIVED))
continue;
if (TREE_CODE (to) != POINTER_TYPE)
return comptypes
- (TYPE_MAIN_VARIANT (to), TYPE_MAIN_VARIANT (from),
+ (TYPE_MAIN_VARIANT (to), TYPE_MAIN_VARIANT (from),
COMPARE_BASE | COMPARE_DERIVED);
}
}
if (type == error_mark_node)
return;
- if (TREE_CODE (type) == FUNCTION_TYPE
+ if (TREE_CODE (type) == FUNCTION_TYPE
&& type_quals != TYPE_UNQUALIFIED)
{
/* This was an error in C++98 (cv-qualifiers cannot be added to
TYPE_NEEDS_CONSTRUCTING (type)
/* If the type isn't complete, we don't know yet if it will need
constructing. */
- || !COMPLETE_TYPE_P (type)
+ || !COMPLETE_TYPE_P (type)
/* If the type has a mutable component, that component might be
modified. */
|| TYPE_HAS_MUTABLE_P (type))
_conv_) from:
Tcv1,(N-K+1) * cv1,(N-K+2) * ... cv1,N *
-
+
to
Tcv2,(M-K+1) * cv2,(M-K+2) * ... cv2,M *. */
cp_type_quals (*t2));
return;
}
-
+
quals1 = cp_type_quals (*t1);
quals2 = cp_type_quals (*t2);
if (TREE_CODE (t2) == REFERENCE_TYPE)
{
/* [expr.const.cast]
-
+
Casting from an lvalue of type T1 to an lvalue of type T2
using a reference cast casts away constness if a cast from an
rvalue of type "pointer to T1" to the type "pointer to T2"
if (TYPE_PTRMEM_P (t1) && TYPE_PTRMEM_P (t2))
/* [expr.const.cast]
-
+
Casting from an rvalue of type "pointer to data member of X
of type T1" to the type "pointer to data member of Y of type
T2" casts away constness if a cast from an rvalue of type
/* Casting away constness is only something that makes sense for
pointer or reference types. */
- if (TREE_CODE (t1) != POINTER_TYPE
+ if (TREE_CODE (t1) != POINTER_TYPE
|| TREE_CODE (t2) != POINTER_TYPE)
return false;
abstract_virtuals_error (tree decl, tree type)
{
VEC(tree,gc) *pure;
-
+
/* This function applies only to classes. Any other entity can never
be abstract. */
if (!CLASS_TYPE_P (type))
void **slot;
struct pending_abstract_type *pat;
- gcc_assert (!decl || DECL_P (decl)
+ gcc_assert (!decl || DECL_P (decl)
|| TREE_CODE (decl) == IDENTIFIER_NODE);
if (!abstract_pending_vars)
- abstract_pending_vars = htab_create_ggc (31, &pat_calc_hash,
+ abstract_pending_vars = htab_create_ggc (31, &pat_calc_hash,
&pat_compare, NULL);
slot = htab_find_slot_with_hash (abstract_pending_vars, type,
cp_error_at ("invalid abstract return type for member function %q+#D",
decl);
else if (TREE_CODE (decl) == FUNCTION_DECL)
- cp_error_at ("invalid abstract return type for function %q+#D",
+ cp_error_at ("invalid abstract return type for function %q+#D",
decl);
else if (TREE_CODE (decl) == IDENTIFIER_NODE)
/* Here we do not have location information, so use error instead
{
unsigned ix;
tree fn;
-
+
inform ("%J because the following virtual functions are pure "
"within %qT:", TYPE_MAIN_DECL (type), type);
VEC_truncate (tree, pure, 0);
}
else
- inform ("%J since type %qT has pure virtual functions",
+ inform ("%J since type %qT has pure virtual functions",
TYPE_MAIN_DECL (type), type);
return 1;
p_msg = error;
p_msg_at = cp_error_at;
}
-
+
/* Avoid duplicate error message. */
if (TREE_CODE (type) == ERROR_MARK)
return;
else
(*p_msg) ("insufficient contextual information to determine type");
break;
-
+
default:
gcc_unreachable ();
}
}
}
-/* A subroutine of store_init_value. Splits non-constant static
+/* A subroutine of store_init_value. Splits non-constant static
initializer INIT into a constant part and generates code to
perform the non-constant part of the initialization to DEST.
Returns the code for the runtime init. */
if (!complete_type_or_else (TREE_CODE (type) == ARRAY_TYPE
? TREE_TYPE (type) : type, NULL_TREE))
return error_mark_node;
-
+
/* Strip NON_LVALUE_EXPRs since we aren't using as an lvalue. */
if (TREE_CODE (init) == NON_LVALUE_EXPR)
init = TREE_OPERAND (init, 0);
types_memoized);
}
last_rval = expr;
- }
+ }
if (last_rval == NULL_TREE)
{
if (!TYPE_PTR_TO_MEMBER_P (ptrmem_type))
{
error ("%qE cannot be used as a member pointer, since it is of "
- "type %qT",
+ "type %qT",
component, ptrmem_type);
return error_mark_node;
}
-
- objtype = TYPE_MAIN_VARIANT (TREE_TYPE (datum));
+
+ objtype = TYPE_MAIN_VARIANT (TREE_TYPE (datum));
if (! IS_AGGR_TYPE (objtype))
{
error ("cannot apply member pointer %qE to %qE, which is of "
else
{
binfo = lookup_base (objtype, ctype, ba_check, NULL);
-
+
if (!binfo)
{
mismatch:
things are not as complex as they are for references to
non-static data members. */
type = cp_build_qualified_type (type,
- (cp_type_quals (type)
+ (cp_type_quals (type)
| cp_type_quals (TREE_TYPE (datum))));
datum = build_address (datum);
-
+
/* Convert object to the correct base. */
if (binfo)
datum = build_base_path (PLUS_EXPR, datum, binfo, 1);
-
+
/* Build an expression for "object + offset" where offset is the
value stored in the pointer-to-data-member. */
datum = build2 (PLUS_EXPR, build_pointer_type (type),
/* Prepare to evaluate as a call to a constructor. If this expression
is actually used, for example,
-
+
return X (arg1, arg2, ...);
-
+
then the slot being initialized will be filled in. */
if (!complete_type_or_else (type, NULL_TREE))
tree core = spec;
bool is_ptr;
int diag_type = -1; /* none */
-
+
if (spec == error_mark_node)
return list;
-
+
gcc_assert (spec && (!list || TREE_VALUE (list)));
-
+
/* [except.spec] 1, type in an exception specifier shall not be
incomplete, or pointer or ref to incomplete other than pointer
to cv void. */
if (ok)
{
tree probe;
-
+
for (probe = list; probe; probe = TREE_CHAIN (probe))
if (same_type_p (TREE_VALUE (probe), spec))
break;
}
else
diag_type = 0; /* error */
-
+
if (diag_type >= 0 && complain)
cxx_incomplete_type_diagnostic (NULL_TREE, core, diag_type);
else
{
tree orig_list = list;
-
+
for (; add; add = TREE_CHAIN (add))
{
tree spec = TREE_VALUE (add);
tree probe;
-
+
for (probe = orig_list; probe; probe = TREE_CHAIN (probe))
if (same_type_p (TREE_VALUE (probe), spec))
break;