From 421844e7209277ce775c5b635a5cc76906df94e9 Mon Sep 17 00:00:00 2001 From: Mark Mitchell Date: Mon, 22 May 2000 22:52:32 +0000 Subject: [PATCH] cp-tree.h (IDENTIFIER_TYPENAME_P): Use a flag, not strncmp. * cp-tree.h (IDENTIFIER_TYPENAME_P): Use a flag, not strncmp. (DECL_CONV_FN_P): Simplify. (DECL_OPERATOR): Remove. (language_to_string): Declare. * decl.c (duplicate_decls): Fix typo in comment. (grokdeclarator): Adjust use of IDENTIFIER_TYPENAME_P. (grok_op_properties): Use DECL_CONV_FN_P instead of IDENTIFIER_TYPENAME_P. * dump.c (dequeue_and_dump): Dump the language linkage of declarations. * error.c (language_to_string): Give it external linkage. * method.c (build_typename_overload): Set IDENTIFIER_TYPENAME_P. (implicitly_declare_fn): Set DECL_LANGUAGE. * pt.c (check_explicit_specialization): Use DECL_CONV_FN_P, not IDENTIFIER_TYPENAME_P. (tsubst_decl): Likewise. (tsubst_copy): Adjust use of IDENTIFIER_TYPENAME_P. * semantics.c (finish_member_declaration): Don't mark members of classes declared in an extern "C" region as extern "C". From-SVN: r34095 --- gcc/cp/ChangeLog | 22 ++++++++++++++++++++++ gcc/cp/cp-tree.h | 17 ++++++----------- gcc/cp/decl.c | 12 +++++------- gcc/cp/dump.c | 2 ++ gcc/cp/error.c | 3 +-- gcc/cp/method.c | 4 ++++ gcc/cp/pt.c | 13 +++++-------- gcc/cp/semantics.c | 7 +++++++ 8 files changed, 52 insertions(+), 28 deletions(-) diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index 2a5c755159c..5fa56d00296 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,3 +1,25 @@ +2000-05-22 Mark Mitchell + + * cp-tree.h (IDENTIFIER_TYPENAME_P): Use a flag, not strncmp. + (DECL_CONV_FN_P): Simplify. + (DECL_OPERATOR): Remove. + (language_to_string): Declare. + * decl.c (duplicate_decls): Fix typo in comment. + (grokdeclarator): Adjust use of IDENTIFIER_TYPENAME_P. + (grok_op_properties): Use DECL_CONV_FN_P instead of + IDENTIFIER_TYPENAME_P. + * dump.c (dequeue_and_dump): Dump the language linkage of + declarations. + * error.c (language_to_string): Give it external linkage. + * method.c (build_typename_overload): Set IDENTIFIER_TYPENAME_P. + (implicitly_declare_fn): Set DECL_LANGUAGE. + * pt.c (check_explicit_specialization): Use DECL_CONV_FN_P, not + IDENTIFIER_TYPENAME_P. + (tsubst_decl): Likewise. + (tsubst_copy): Adjust use of IDENTIFIER_TYPENAME_P. + * semantics.c (finish_member_declaration): Don't mark members of + classes declared in an extern "C" region as extern "C". + 2000-05-22 Martin v. Löwis * decl2.c (qualified_lookup_using_namespace): Look through diff --git a/gcc/cp/cp-tree.h b/gcc/cp/cp-tree.h index d21a195af23..1cc9740a3f7 100644 --- a/gcc/cp/cp-tree.h +++ b/gcc/cp/cp-tree.h @@ -73,6 +73,7 @@ Boston, MA 02111-1307, USA. */ or FIELD_DECL). NEED_TEMPORARY_P (in REF_BIND, BASE_CONV) SCOPE_PARTIAL_P (in SCOPE_STMT) + IDENTIFIER_TYPENAME_P (in IDENTIFIER_NODE) 5: BINFO_PRIMARY_MARKED_P (in BINFO) 6: BINFO_VBASE_PRIMARY_P (in BINFO) @@ -484,10 +485,8 @@ struct tree_srcloc /* Nonzero if this identifier is the name of a type-conversion operator. */ -#define IDENTIFIER_TYPENAME_P(NODE) \ - (! strncmp (IDENTIFIER_POINTER (NODE), \ - OPERATOR_TYPENAME_FORMAT, \ - strlen (OPERATOR_TYPENAME_FORMAT))) +#define IDENTIFIER_TYPENAME_P(NODE) \ + (TREE_LANG_FLAG_4 (NODE)) /* Nonzero if this identifier is the name of a constructor or destructor. */ @@ -1972,8 +1971,8 @@ struct lang_decl (DECL_LANG_SPECIFIC (NODE)->cloned_function) /* Non-zero if NODE is a user-defined conversion operator. */ -#define DECL_CONV_FN_P(NODE) \ - (IDENTIFIER_TYPENAME_P (DECL_NAME (NODE)) && TREE_TYPE (DECL_NAME (NODE))) +#define DECL_CONV_FN_P(NODE) \ + (IDENTIFIER_TYPENAME_P (DECL_NAME (NODE))) /* Non-zero if NODE is an overloaded operator. */ #define DECL_OVERLOADED_OPERATOR_P(NODE) \ @@ -2684,11 +2683,6 @@ extern int flag_new_for_scope; #define DECL_THIS_STATIC(NODE) \ DECL_LANG_FLAG_6 (VAR_FUNCTION_OR_PARM_DECL_CHECK (NODE)) -/* Nonzero in FUNCTION_DECL means it is really an operator. - Just used to communicate formatting information to dbxout.c. */ -#define DECL_OPERATOR(NODE) \ - (DECL_LANG_SPECIFIC(FUNCTION_DECL_CHECK (NODE))->decl_flags.operator_attr) - /* Nonzero if TYPE is an anonymous union or struct type. We have to use a flag for this because "A union for which objects or pointers are declared is not an anonymous union" [class.union]. */ @@ -4084,6 +4078,7 @@ extern const char *context_as_string PARAMS ((tree, enum tree_string_ extern const char *lang_decl_name PARAMS ((tree, int)); extern const char *cp_file_of PARAMS ((tree)); extern int cp_line_of PARAMS ((tree)); +extern const char *language_to_string PARAMS ((enum languages, int)); /* in except.c */ extern void init_exception_processing PARAMS ((void)); diff --git a/gcc/cp/decl.c b/gcc/cp/decl.c index 6e80505b854..2fd0fe109e0 100644 --- a/gcc/cp/decl.c +++ b/gcc/cp/decl.c @@ -3126,9 +3126,9 @@ duplicate_decls (newdecl, olddecl) DECL_THIS_STATIC (olddecl) = 1; TREE_PUBLIC (olddecl) = 0; - /* Make the olddeclaration consistent with the new one so that - all remnants of the builtin-ness of this function will be - banished. */ + /* Make the old declaration consistent with the new one so + that all remnants of the builtin-ness of this function + will be banished. */ DECL_LANGUAGE (olddecl) = DECL_LANGUAGE (newdecl); DECL_RTL (olddecl) = DECL_RTL (newdecl); DECL_ASSEMBLER_NAME (olddecl) = DECL_ASSEMBLER_NAME (newdecl); @@ -9643,9 +9643,7 @@ grokdeclarator (declarator, declspecs, decl_context, initialized, attrlist) dname); name = IDENTIFIER_POINTER (dname); } - if (! IDENTIFIER_OPNAME_P (dname) - /* GNU/Linux headers use '__op'. Arrgh. */ - || (IDENTIFIER_TYPENAME_P (dname) && ! TREE_TYPE (dname))) + else if (!IDENTIFIER_OPNAME_P (dname)) name = IDENTIFIER_POINTER (dname); else { @@ -12183,7 +12181,7 @@ grok_op_properties (decl, virtualp, friendp) an enumeration, or a reference to an enumeration. 13.4.0.6 */ if (! methodp || DECL_STATIC_FUNCTION_P (decl)) { - if (IDENTIFIER_TYPENAME_P (name) + if (DECL_CONV_FN_P (decl) || name == ansi_opname[(int) CALL_EXPR] || name == ansi_opname[(int) MODIFY_EXPR] || name == ansi_opname[(int) COMPONENT_REF] diff --git a/gcc/cp/dump.c b/gcc/cp/dump.c index 96b0016e9fc..16cbba399b7 100644 --- a/gcc/cp/dump.c +++ b/gcc/cp/dump.c @@ -395,6 +395,8 @@ dequeue_and_dump (di) dump_string (di, "artificial"); if (TREE_CHAIN (t)) dump_child ("chan", TREE_CHAIN (t)); + if (DECL_LANG_SPECIFIC (t) && DECL_LANGUAGE (t) != lang_cplusplus) + dump_string (di, language_to_string (DECL_LANGUAGE (t), 0)); } else if (code_class == 't') { diff --git a/gcc/cp/error.c b/gcc/cp/error.c index 8f0fdf346e6..bfd921f5aad 100644 --- a/gcc/cp/error.c +++ b/gcc/cp/error.c @@ -64,7 +64,6 @@ static const char *cv_to_string PARAMS ((tree, int)); static const char *decl_to_string PARAMS ((tree, int)); static const char *expr_to_string PARAMS ((tree, int)); static const char *fndecl_to_string PARAMS ((tree, int)); -static const char *language_to_string PARAMS ((enum languages, int)); static const char *op_to_string PARAMS ((enum tree_code, int)); static const char *parm_to_string PARAMS ((int, int)); static const char *type_to_string PARAMS ((tree, int)); @@ -2267,7 +2266,7 @@ code_to_string (c, v) return tree_code_name [c]; } -static const char * +const char * language_to_string (c, v) enum languages c; int v ATTRIBUTE_UNUSED; diff --git a/gcc/cp/method.c b/gcc/cp/method.c index bbb580d622b..53b51536bb9 100644 --- a/gcc/cp/method.c +++ b/gcc/cp/method.c @@ -1766,6 +1766,7 @@ build_typename_overload (type) build_mangled_name (type, 0, 1); id = get_identifier (obstack_base (&scratch_obstack)); IDENTIFIER_OPNAME_P (id) = 1; + IDENTIFIER_TYPENAME_P (id) = 1; TREE_TYPE (id) = type; end_squangling (); return id; @@ -2580,6 +2581,9 @@ implicitly_declare_fn (kind, type, const_p) DECL_NOT_REALLY_EXTERN (fn) = 1; DECL_THIS_INLINE (fn) = 1; DECL_INLINE (fn) = 1; + /* Even within an `extern "C"' block, members get C++ linkage. See + [dcl.link] for details. */ + DECL_LANGUAGE (fn) = lang_cplusplus; defer_fn (fn); return fn; diff --git a/gcc/cp/pt.c b/gcc/cp/pt.c index 3b3f7862fb4..04cac4e04e7 100644 --- a/gcc/cp/pt.c +++ b/gcc/cp/pt.c @@ -1392,7 +1392,7 @@ check_explicit_specialization (declarator, decl, template_count, flags) name = is_constructor ? ctor_identifier : dtor_identifier; } - if (!IDENTIFIER_TYPENAME_P (name)) + if (!DECL_CONV_FN_P (decl)) { idx = lookup_fnfields_1 (ctype, name); if (idx >= 0) @@ -5687,7 +5687,7 @@ tsubst_decl (t, args, type, in_decl) /*complain=*/1, t, /*entering_scope=*/1); - if (member && IDENTIFIER_TYPENAME_P (DECL_NAME (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) = build_typename_overload (TREE_TYPE (type)); @@ -7055,12 +7055,9 @@ tsubst_copy (t, args, complain, in_decl) return tsubst (t, args, complain, in_decl); case IDENTIFIER_NODE: - if (IDENTIFIER_TYPENAME_P (t) - /* Make sure it's not just a variable named `__opr', for instance, - which can occur in some existing code. */ - && TREE_TYPE (t)) - return build_typename_overload - (tsubst (TREE_TYPE (t), args, complain, in_decl)); + if (IDENTIFIER_TYPENAME_P (t)) + return (build_typename_overload + (tsubst (TREE_TYPE (t), args, complain, in_decl))); else return t; diff --git a/gcc/cp/semantics.c b/gcc/cp/semantics.c index 8f9a28bdfce..b5cf6890c1f 100644 --- a/gcc/cp/semantics.c +++ b/gcc/cp/semantics.c @@ -2004,6 +2004,13 @@ finish_member_declaration (decl) /* Mark the DECL as a member of the current class. */ DECL_CONTEXT (decl) = current_class_type; + /* [dcl.link] + + A C language linkage is ignored for the names of class members + and the member function type of class member functions. */ + if (DECL_LANG_SPECIFIC (decl) && DECL_LANGUAGE (decl) == lang_c) + DECL_LANGUAGE (decl) = lang_cplusplus; + /* 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. */