summaryrefslogtreecommitdiffstats
path: root/contrib/gcc/cp
diff options
context:
space:
mode:
authorobrien <obrien@FreeBSD.org>2002-12-04 15:42:16 +0000
committerobrien <obrien@FreeBSD.org>2002-12-04 15:42:16 +0000
commit7a1080fa5c329ea8a9505e51ce151719955bcfa2 (patch)
tree78b77287e56e2a87be73638176124be85a8fc6c7 /contrib/gcc/cp
parentef3bb1318428b8cfb1c8287f61b9b1f23f9bf0b5 (diff)
downloadFreeBSD-src-7a1080fa5c329ea8a9505e51ce151719955bcfa2.zip
FreeBSD-src-7a1080fa5c329ea8a9505e51ce151719955bcfa2.tar.gz
Gcc 3.2.1 release virgin vendor import. (19-Nov-2002)
Diffstat (limited to 'contrib/gcc/cp')
-rw-r--r--contrib/gcc/cp/ChangeLog188
-rw-r--r--contrib/gcc/cp/cfns.h9
-rw-r--r--contrib/gcc/cp/class.c48
-rw-r--r--contrib/gcc/cp/cp-lang.c21
-rw-r--r--contrib/gcc/cp/cp-tree.h29
-rw-r--r--contrib/gcc/cp/cvt.c10
-rw-r--r--contrib/gcc/cp/decl.c64
-rw-r--r--contrib/gcc/cp/decl2.c14
-rw-r--r--contrib/gcc/cp/init.c2
-rw-r--r--contrib/gcc/cp/lex.c17
-rw-r--r--contrib/gcc/cp/mangle.c73
-rw-r--r--contrib/gcc/cp/method.c2
-rw-r--r--contrib/gcc/cp/parse.y30
-rw-r--r--contrib/gcc/cp/pt.c10
-rw-r--r--contrib/gcc/cp/rtti.c8
-rw-r--r--contrib/gcc/cp/semantics.c2
-rw-r--r--contrib/gcc/cp/spew.c93
-rw-r--r--contrib/gcc/cp/tree.c20
-rw-r--r--contrib/gcc/cp/typeck.c19
-rw-r--r--contrib/gcc/cp/typeck2.c5
20 files changed, 540 insertions, 124 deletions
diff --git a/contrib/gcc/cp/ChangeLog b/contrib/gcc/cp/ChangeLog
index cc84a03..5a611ae 100644
--- a/contrib/gcc/cp/ChangeLog
+++ b/contrib/gcc/cp/ChangeLog
@@ -1,3 +1,191 @@
+2002-11-19 Release Manager
+
+ * GCC 3.2.1 Released.
+
+2002-11-19 Release Manager
+
+ * GCC 3.2.1 Released.
+
+2002-11-18 Release Manager
+
+ * GCC 3.2.1 Released.
+
+2002-11-11 Nathan Sidwell <nathan@codesourcery.com>
+
+ PR c++/7788
+ * rtti.c (unemitted_tinfo_decl_p): Check it has a field.
+
+2002-11-02 Zack Weinberg <zack@codesourcery.com>
+
+ PR c/7353 redux
+ * decl2.c (grokfield): Reject TYPE_DECLs with initializers.
+
+2002-11-01 Gabriel Dos Reis <gdr@integrable-solutions.net>
+
+ PR C++/2521
+ * typeck.c (build_x_unary_op): Handle pointer-to-member.
+
+2002-10-30 Mark Mitchell <mark@codesourcery.com>
+
+ PR c++/8160
+ * typeck2.c (process_init_constructor): Call complete_array_type.
+
+ PR c++/8149
+ * decl.c (make_typename_type): Issue errors about invalid results.
+
+2002-10-29 Mark Mitchell <mark@codesourcery.com>
+
+ PR c++/8287
+ * decl.c (finish_destructor_body): Create the label to jump to
+ when returning from a destructor here.
+ (finish_function_body): Rather than here.
+
+ * semantics.c (finish_alignof): Call complete_type before calling
+ c_alignof.
+ * decl2.c (build_expr_from_tree): Use
+ finish_sizeof/finish_alignof.
+
+2002-10-10 Jim Wilson <wilson@redhat.com>
+
+ * decl.c (duplicate_decls): Don't call decl_attributes.
+
+2002-10-25 Zack Weinberg <zack@codesourcery.com>
+
+ PR middle-end/6994
+ * cp-lang.c (cp_var_mod_type_p): New: C++ hook for
+ variably_modified_type_p.
+ * cp-tree.h: Remove prototype of variably_modified_type_p.
+ * tree.c (variably_modified_type_p): Remove; now implemented
+ in language-independent code.
+
+ PR c++/7266
+ * decl.c (grokdeclarator): Check that TREE_OPERAND 0 of a
+ SCOPE_REF is not null before dereferencing it.
+
+2002-10-24 David Edelsohn <edelsohn@gnu.org>
+
+ PR c++/7228
+ * cp-tree.h (CLASSTYPE_READONLY_FIELDS_NEED_INIT): Check that
+ lang_type structure exists before accessing field.
+ (SET_CLASSTYPE_READONLY_FIELDS_NEED_INIT): New macro.
+ (CLASSTYPE_REF_FIELDS_NEED_INIT): Similar.
+ (SET_CLASSTYPE_REF_FIELDS_NEED_INIT): New macro.
+ * class.c (check_field_decls): Use new macros.
+ * typeck2.c (process_init_constructor): Remove redundant check for
+ existence of lang_type structure.
+
+2002-10-23 Mark Mitchell <mark@codesourcery.com>
+
+ PR c++/8067
+ * decl.c (maybe_inject_for_scope_var): Ignore __FUNCTION__ and
+ related variables.
+
+2002-10-23 Mark Mitchell <mark@codesourcery.com>
+
+ PR c++/7679
+ * spew.c (next_token): Do not return an endless stream of
+ END_OF_SAVED_INPUT tokens.
+ (snarf_method): Add three END_OF_SAVED_INPUT tokens to the end of
+ the cached token stream.
+ (snarf_defarg): Likewise.
+
+2002-10-22 Mark Mitchell <mark@codesourcery.com>
+
+ PR c++/6579
+ * spew.c (snarf_parenthesized_expression): New function.
+ (snarf_block): Use it.
+
+2002-10-21 Matthias Klose <doko@debian.org>
+
+ * Backport, without whitespace change:
+ 2002-06-19 Akim Demaille <akim@epita.fr>
+ * parse.y (TYPENAME): Rename as tTYPENAME to avoid the clash with
+ decl.h's TYPENAME.
+ * spew.c, lex.c: Adjust.
+ * parse.y (explicit_instantiation): Add empty action to override
+ the default $$ = $1 where it introduces a type clash.
+
+2002-10-21 Mark Mitchell <mark@codesourcery.com>
+
+ PR c++/8218
+ * cp-tree.h (lang_type_class): Add contains_empty_class_p.
+ (CLASSTYPE_CONTAINS_EMPTY_CLASS_P): New macro.
+ * class.c (check_bases): Update CLASSTYPE_CONTAINS_EMPTY_CLASS_P.
+ (check_field_decls): Likewise.
+ (layout_class_type): Likewise.
+ (finish_struct_1): Initialize it.
+ (walk_subobject_offsets): Use it to prune searches.
+
+2002-10-18 Zack Weinberg <zack@codesourcery.com>
+
+ * decl.c (start_decl): Point users of the old initialized-
+ typedef extension at __typeof__.
+
+2002-10-18 Nathan Sidwell <nathan@codesourcery.com>
+
+ PR c++/7676
+ * class.c (add_method): Compare template parms too.
+
+2002-10-17 Mark Mitchell <mark@codesourcery.com>
+
+ * mangle.c (globals): Add entity and need_abi_warning.
+ (write_prefix): Likewise.
+ (write_template_prefix): Likewise.
+ (start_mangling): Add entity parameter.
+ (finish_mangling): Warn about names whose mangling will change.
+ (mangle_decl_string): Adjust.
+ (mangle_type_string): Likewise.
+ (mangle_special_for_type): Likewise.
+ (mangle_ctor_vtbl_for_type): Likewise.
+ (mangle_thunk): Likewise.
+ (mangle_guard_variable): Likewise.
+ (mangle_ref_init_variable): Likewise.
+
+ PR c++/7584
+ * class.c (handle_using_decl): Allow the declaration used to be
+ from an ambiguous base.
+
+2002-10-16 Mark Mitchell <mark@codesourcery.com>
+
+ PR c++/7478
+ * cvt.c (convert_to_reference): Allow references as the incoming
+ type.
+
+ PR c++/8134
+ * tree.c (zero_init_p): Always return 1.
+
+ PR c++/7524
+ * method.c (do_build_assign_ref): Use cp_build_qualified_type, not
+ build_qualified_type.
+
+2002-10-14 Mark Mitchell <mark@codesourcery.com>
+
+ PR c++/7176
+ * lex.c (do_identifier): Add another option for the parsing
+ parameter.
+ * parse.y (do_id): Use it.
+
+2002-10-11 Mark Mitchell <mark@codesourcery.com>
+
+ PR c++/5661
+ * cp-tree.h (variably_modified_type_p): New function.
+ (grokdeclarator) Tighten check for variably modified types as
+ fields.
+ * pt.c (convert_template_argument): Do not allow variably modified
+ types as template arguments.
+ * tree.c (variably_modified_type_p): New function.
+
+2002-10-11 Jason Molenda <jmolenda@apple.com>
+
+ * init.c (build_field_list): Provide uses_unions_p with a default
+ value.
+
+2002-10-10 Gabriel Dos Reis <gdr@integrable-solutions.net>
+
+ PRs C++/6803, C++/7721 and C++/7803
+ * decl.c (grokdeclarator): Gracefully handle template-name as
+ decl-specifier.
+
2002-10-09 Zack Weinberg <zack@codesourcery.com>
PR c/7353
diff --git a/contrib/gcc/cp/cfns.h b/contrib/gcc/cp/cfns.h
index a139160..c7e6a9d 100644
--- a/contrib/gcc/cp/cfns.h
+++ b/contrib/gcc/cp/cfns.h
@@ -1,6 +1,5 @@
-/* C code produced by gperf version 2.7.2 */
-/* Command-line: gperf -o -C -E -k '1-6,$' -j1 -D -N libc_name_p /FBSD/src/gnu/usr.bin/cc/cc1plus/../../../../contrib/gcc/cp/cfns.gperf */
-/* $FreeBSD$ */
+/* C code produced by gperf version 2.7 */
+/* Command-line: gperf -o -C -E -k 1-6,$ -j1 -D -N libc_name_p ../../../egcs-CVS20000404/gcc/cp/cfns.gperf */
#ifdef __GNUC__
__inline
#endif
@@ -13,10 +12,6 @@ const char * libc_name_p PARAMS ((const char *, unsigned int));
#ifdef __GNUC__
__inline
-#else
-#ifdef __cplusplus
-inline
-#endif
#endif
static unsigned int
hash (str, len)
diff --git a/contrib/gcc/cp/class.c b/contrib/gcc/cp/class.c
index 2395d79..2ac4e30 100644
--- a/contrib/gcc/cp/class.c
+++ b/contrib/gcc/cp/class.c
@@ -945,6 +945,13 @@ add_method (type, method, error_p)
&& (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))
@@ -1150,9 +1157,12 @@ handle_using_decl (using_decl, t)
tree flist = NULL_TREE;
tree old_value;
- binfo = binfo_or_else (ctype, t);
+ binfo = lookup_base (t, ctype, ba_any, NULL);
if (! binfo)
- return;
+ {
+ error_not_base_type (t, ctype);
+ return;
+ }
if (name == constructor_name (ctype)
|| name == constructor_name_full (ctype))
@@ -1338,6 +1348,8 @@ check_bases (t, cant_have_default_ctor_p, cant_have_const_ctor_p,
TYPE_OVERLOADS_ARRAY_REF (t) |= TYPE_OVERLOADS_ARRAY_REF (basetype);
TYPE_OVERLOADS_ARROW (t) |= TYPE_OVERLOADS_ARROW (basetype);
TYPE_POLYMORPHIC_P (t) |= TYPE_POLYMORPHIC_P (basetype);
+ CLASSTYPE_CONTAINS_EMPTY_CLASS_P (t)
+ |= CLASSTYPE_CONTAINS_EMPTY_CLASS_P (basetype);
}
}
@@ -3237,10 +3249,18 @@ check_field_decls (t, access_decls, empty_p,
;
else
{
+ tree element_type;
+
/* The class is non-empty. */
*empty_p = 0;
/* The class is not even nearly empty. */
CLASSTYPE_NEARLY_EMPTY_P (t) = 0;
+ /* 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)
+ && CLASSTYPE_CONTAINS_EMPTY_CLASS_P (element_type))
+ CLASSTYPE_CONTAINS_EMPTY_CLASS_P (t) = 1;
}
}
@@ -3322,7 +3342,7 @@ check_field_decls (t, access_decls, empty_p,
{
CLASSTYPE_NON_POD_P (t) = 1;
if (DECL_INITIAL (x) == NULL_TREE)
- CLASSTYPE_REF_FIELDS_NEED_INIT (t) = 1;
+ SET_CLASSTYPE_REF_FIELDS_NEED_INIT (t, 1);
/* ARM $12.6.2: [A member initializer list] (or, for an
aggregate, initialization by a brace-enclosed list) is the
@@ -3356,7 +3376,7 @@ check_field_decls (t, access_decls, empty_p,
{
C_TYPE_FIELDS_READONLY (t) = 1;
if (DECL_INITIAL (x) == NULL_TREE)
- CLASSTYPE_READONLY_FIELDS_NEED_INIT (t) = 1;
+ SET_CLASSTYPE_READONLY_FIELDS_NEED_INIT (t, 1);
/* ARM $12.6.2: [A member initializer list] (or, for an
aggregate, initialization by a brace-enclosed list) is the
@@ -3372,8 +3392,9 @@ check_field_decls (t, access_decls, empty_p,
else if (IS_AGGR_TYPE (type))
{
C_TYPE_FIELDS_READONLY (t) |= C_TYPE_FIELDS_READONLY (type);
- CLASSTYPE_READONLY_FIELDS_NEED_INIT (t)
- |= CLASSTYPE_READONLY_FIELDS_NEED_INIT (type);
+ SET_CLASSTYPE_READONLY_FIELDS_NEED_INIT (t,
+ CLASSTYPE_READONLY_FIELDS_NEED_INIT (t)
+ | CLASSTYPE_READONLY_FIELDS_NEED_INIT (type));
}
/* Core issue 80: A nonstatic data member is required to have a
@@ -3507,6 +3528,10 @@ walk_subobject_offsets (type, f, offset, offsets, max_offset, vbases_p)
tree field;
int i;
+ /* Avoid recursing into objects that are not interesting. */
+ if (!CLASSTYPE_CONTAINS_EMPTY_CLASS_P (type))
+ return 0;
+
/* Record the location of TYPE. */
r = (*f) (type, offset, offsets);
if (r)
@@ -3552,9 +3577,15 @@ walk_subobject_offsets (type, f, offset, offsets, max_offset, vbases_p)
}
else if (TREE_CODE (type) == ARRAY_TYPE)
{
+ tree element_type = strip_array_types (type);
tree domain = TYPE_DOMAIN (type);
tree index;
+ /* Avoid recursing into objects that are not interesting. */
+ if (!CLASS_TYPE_P (element_type)
+ || !CLASSTYPE_CONTAINS_EMPTY_CLASS_P (element_type))
+ return 0;
+
/* Step through each of the elements in the array. */
for (index = size_zero_node;
INT_CST_LT (index, TYPE_MAX_VALUE (domain));
@@ -4267,6 +4298,7 @@ check_bases_and_members (t, empty_p)
/* Assume that the class is nearly empty; we'll clear this flag if
it turns out not to be nearly empty. */
CLASSTYPE_NEARLY_EMPTY_P (t) = 1;
+ CLASSTYPE_CONTAINS_EMPTY_CLASS_P (t) = 0;
/* Check all the base-classes. */
check_bases (t, &cant_have_default_ctor, &cant_have_const_ctor,
@@ -4974,6 +5006,10 @@ layout_class_type (t, empty_p, vfuns_p, virtuals_p)
CLASSTYPE_ALIGN (t) = TYPE_ALIGN (t);
CLASSTYPE_USER_ALIGN (t) = TYPE_USER_ALIGN (t);
+ /* Every empty class contains an empty class. */
+ if (*empty_p)
+ CLASSTYPE_CONTAINS_EMPTY_CLASS_P (t) = 1;
+
/* Set the TYPE_DECL for this type to contain the right
value for DECL_OFFSET, so that we can use it as part
of a COMPONENT_REF for multiple inheritance. */
diff --git a/contrib/gcc/cp/cp-lang.c b/contrib/gcc/cp/cp-lang.c
index b573cce..1464ef6 100644
--- a/contrib/gcc/cp/cp-lang.c
+++ b/contrib/gcc/cp/cp-lang.c
@@ -30,6 +30,7 @@ Boston, MA 02111-1307, USA. */
static HOST_WIDE_INT cxx_get_alias_set PARAMS ((tree));
static tree cp_expr_size PARAMS ((tree));
+static bool cp_var_mod_type_p PARAMS ((tree));
#undef LANG_HOOKS_NAME
#define LANG_HOOKS_NAME "GNU C++"
@@ -84,6 +85,8 @@ static tree cp_expr_size PARAMS ((tree));
cp_copy_res_decl_for_inlining
#undef LANG_HOOKS_TREE_INLINING_ANON_AGGR_TYPE_P
#define LANG_HOOKS_TREE_INLINING_ANON_AGGR_TYPE_P anon_aggr_type_p
+#undef LANG_HOOKS_TREE_INLINING_VAR_MOD_TYPE_P
+#define LANG_HOOKS_TREE_INLINING_VAR_MOD_TYPE_P cp_var_mod_type_p
#undef LANG_HOOKS_TREE_INLINING_START_INLINING
#define LANG_HOOKS_TREE_INLINING_START_INLINING cp_start_inlining
#undef LANG_HOOKS_TREE_INLINING_END_INLINING
@@ -130,3 +133,21 @@ cp_expr_size (exp)
/* Use the default code. */
return lhd_expr_size (exp);
}
+
+/* Returns true if T is a variably modified type, in the sense of C99.
+ This routine needs only check cases that cannot be handled by the
+ language-independent logic in tree-inline.c. */
+
+static bool
+cp_var_mod_type_p (tree type)
+{
+ /* If TYPE is a pointer-to-member, it is variably modified if either
+ the class or the member are variably modified. */
+ if (TYPE_PTRMEM_P (type) || TYPE_PTRMEMFUNC_P (type))
+ return (variably_modified_type_p (TYPE_PTRMEM_CLASS_TYPE (type))
+ || variably_modified_type_p (TYPE_PTRMEM_POINTED_TO_TYPE (type)));
+
+ /* All other types are not variably modified. */
+ return false;
+}
+
diff --git a/contrib/gcc/cp/cp-tree.h b/contrib/gcc/cp/cp-tree.h
index 4bd0879..9e8199f 100644
--- a/contrib/gcc/cp/cp-tree.h
+++ b/contrib/gcc/cp/cp-tree.h
@@ -1251,6 +1251,7 @@ struct lang_type
unsigned java_interface : 1;
unsigned non_zero_init : 1;
+ unsigned contains_empty_class_p : 1;
/* When adding a flag here, consider whether or not it ought to
apply to a template instance if it applies to the template. If
@@ -1259,7 +1260,7 @@ struct lang_type
/* There are some bits left to fill out a 32-bit word. Keep track
of this by updating the size of this bitfield whenever you add or
remove a flag. */
- unsigned dummy : 7;
+ unsigned dummy : 6;
int vsize;
@@ -1520,6 +1521,10 @@ struct lang_type
#define CLASSTYPE_NEARLY_EMPTY_P(NODE) \
(TYPE_LANG_SPECIFIC (NODE)->nearly_empty_p)
+/* Nonzero if this class contains an empty subobject. */
+#define CLASSTYPE_CONTAINS_EMPTY_CLASS_P(NODE) \
+ (TYPE_LANG_SPECIFIC (NODE)->contains_empty_class_p)
+
/* A list of class types of which this type is a friend. The
TREE_VALUE is normally a TYPE, but will be a TEMPLATE_DECL in the
case of a template friend. */
@@ -1534,13 +1539,21 @@ struct lang_type
#define CLASSTYPE_DECLARED_CLASS(NODE) \
(TYPE_LANG_SPECIFIC (NODE)->declared_class)
-/* Nonzero if this class has const members which have no specified initialization. */
-#define CLASSTYPE_READONLY_FIELDS_NEED_INIT(NODE) \
- (TYPE_LANG_SPECIFIC (NODE)->const_needs_init)
-
-/* Nonzero if this class has ref members which have no specified initialization. */
-#define CLASSTYPE_REF_FIELDS_NEED_INIT(NODE) \
- (TYPE_LANG_SPECIFIC (NODE)->ref_needs_init)
+/* Nonzero if this class has const members
+ which have no specified initialization. */
+#define CLASSTYPE_READONLY_FIELDS_NEED_INIT(NODE) \
+ (TYPE_LANG_SPECIFIC (NODE) \
+ ? TYPE_LANG_SPECIFIC (NODE)->const_needs_init : 0)
+#define SET_CLASSTYPE_READONLY_FIELDS_NEED_INIT(NODE, VALUE) \
+ (TYPE_LANG_SPECIFIC (NODE)->const_needs_init = (VALUE))
+
+/* Nonzero if this class has ref members
+ which have no specified initialization. */
+#define CLASSTYPE_REF_FIELDS_NEED_INIT(NODE) \
+ (TYPE_LANG_SPECIFIC (NODE) \
+ ? TYPE_LANG_SPECIFIC (NODE)->ref_needs_init : 0)
+#define SET_CLASSTYPE_REF_FIELDS_NEED_INIT(NODE, VALUE) \
+ (TYPE_LANG_SPECIFIC (NODE)->ref_needs_init = (VALUE))
/* Nonzero if this class is included from a header file which employs
`#pragma interface', and it is not included in its implementation file. */
diff --git a/contrib/gcc/cp/cvt.c b/contrib/gcc/cp/cvt.c
index 9b4f68f..5e6c92c 100644
--- a/contrib/gcc/cp/cvt.c
+++ b/contrib/gcc/cp/cvt.c
@@ -464,12 +464,13 @@ convert_to_reference (reftype, expr, convtype, flags, decl)
tree decl;
{
register tree type = TYPE_MAIN_VARIANT (TREE_TYPE (reftype));
- register tree intype = TREE_TYPE (expr);
+ register tree intype;
tree rval = NULL_TREE;
tree rval_as_conversion = NULL_TREE;
int i;
- if (TREE_CODE (type) == FUNCTION_TYPE && intype == unknown_type_node)
+ if (TREE_CODE (type) == FUNCTION_TYPE
+ && TREE_TYPE (expr) == unknown_type_node)
{
expr = instantiate_type (type, expr,
(flags & LOOKUP_COMPLAIN)
@@ -479,6 +480,11 @@ convert_to_reference (reftype, expr, convtype, flags, decl)
intype = TREE_TYPE (expr);
}
+ else
+ {
+ expr = convert_from_reference (expr);
+ intype = TREE_TYPE (expr);
+ }
my_friendly_assert (TREE_CODE (intype) != REFERENCE_TYPE, 364);
diff --git a/contrib/gcc/cp/decl.c b/contrib/gcc/cp/decl.c
index 26484d7..06b081c 100644
--- a/contrib/gcc/cp/decl.c
+++ b/contrib/gcc/cp/decl.c
@@ -3500,7 +3500,6 @@ duplicate_decls (newdecl, olddecl)
except for any that we copy here from the old type. */
DECL_ATTRIBUTES (newdecl)
= (*targetm.merge_decl_attributes) (olddecl, newdecl);
- decl_attributes (&newdecl, DECL_ATTRIBUTES (newdecl), 0);
if (TREE_CODE (newdecl) == TEMPLATE_DECL)
{
@@ -5760,6 +5759,12 @@ make_typename_type (context, name, complain)
t = lookup_field (context, name, 0, 1);
if (t)
{
+ if (TREE_CODE (t) != TYPE_DECL)
+ {
+ if (complain & tf_error)
+ error ("no type named `%#T' in `%#T'", name, context);
+ return error_mark_node;
+ }
if (DECL_ARTIFICIAL (t) || !(complain & tf_keep_type_decl))
t = TREE_TYPE (t);
if (IMPLICIT_TYPENAME_P (t))
@@ -7328,7 +7333,7 @@ start_decl (declarator, declspecs, initialized, attributes, prefix_attributes)
switch (TREE_CODE (decl))
{
case TYPE_DECL:
- error ("typedef `%D' is initialized", decl);
+ error ("typedef `%D' is initialized (use __typeof__ instead)", decl);
initialized = 0;
break;
@@ -8026,6 +8031,12 @@ maybe_inject_for_scope_var (decl)
{
if (!DECL_NAME (decl))
return;
+
+ /* Declarations of __FUNCTION__ and its ilk appear magically when
+ the variable is first used. If that happens to be inside a
+ for-loop, we don't want to do anything special. */
+ if (DECL_PRETTY_FUNCTION_P (decl))
+ return;
if (current_binding_level->is_for_scope)
{
@@ -10060,6 +10071,16 @@ grokdeclarator (declarator, declspecs, decl_context, initialized, attrlist)
next = 0;
break;
+ case TEMPLATE_DECL:
+ /* Sometimes, we see a template-name used as part of a
+ decl-specifier like in
+ std::allocator alloc;
+ Handle that gracefully. */
+ error ("invalid use of template-name '%E' in a declarator",
+ decl);
+ return error_mark_node;
+ break;
+
default:
internal_error ("`%D' as declarator", decl);
}
@@ -10700,19 +10721,6 @@ grokdeclarator (declarator, declspecs, decl_context, initialized, attrlist)
type = create_array_type_for_decl (dname, type, size);
- /* VLAs never work as fields. */
- if (decl_context == FIELD && !processing_template_decl
- && TREE_CODE (type) == ARRAY_TYPE
- && TYPE_DOMAIN (type) != NULL_TREE
- && !TREE_CONSTANT (TYPE_MAX_VALUE (TYPE_DOMAIN (type))))
- {
- error ("size of member `%D' is not constant", dname);
- /* Proceed with arbitrary constant size, so that offset
- computations don't get confused. */
- type = create_array_type_for_decl (dname, TREE_TYPE (type),
- integer_one_node);
- }
-
ctype = NULL_TREE;
}
break;
@@ -11019,8 +11027,9 @@ grokdeclarator (declarator, declspecs, decl_context, initialized, attrlist)
pop_decl_namespace ();
else if (friendp && (TREE_COMPLEXITY (declarator) < 2))
/* Don't fall out into global scope. Hides real bug? --eichin */ ;
- else if (! IS_AGGR_TYPE_CODE
- (TREE_CODE (TREE_OPERAND (declarator, 0))))
+ else if (!TREE_OPERAND (declarator, 0)
+ || !IS_AGGR_TYPE_CODE
+ (TREE_CODE (TREE_OPERAND (declarator, 0))))
;
else if (TREE_COMPLEXITY (declarator) == current_class_depth)
{
@@ -11200,6 +11209,14 @@ grokdeclarator (declarator, declspecs, decl_context, initialized, attrlist)
type = error_mark_node;
}
+ if (decl_context == FIELD
+ && !processing_template_decl
+ && variably_modified_type_p (type))
+ {
+ error ("data member may not have variably modified type `%T'", type);
+ type = error_mark_node;
+ }
+
if (explicitp == 1 || (explicitp && friendp))
{
/* [dcl.fct.spec] The explicit specifier shall only be used in
@@ -14101,6 +14118,10 @@ finish_destructor_body ()
{
tree exprstmt;
+ /* Any return from a destructor will end up here; that way all base
+ and member cleanups will be run when the function returns. */
+ add_stmt (build_stmt (LABEL_STMT, dtor_label));
+
/* And perform cleanups for our bases and members. */
perform_base_cleanups ();
@@ -14176,14 +14197,7 @@ void
finish_function_body (compstmt)
tree compstmt;
{
- if (processing_template_decl)
- /* Do nothing now. */;
- else if (DECL_DESTRUCTOR_P (current_function_decl))
- /* Any return from a destructor will end up here. Put it before the
- cleanups so that an explicit return doesn't duplicate them. */
- add_stmt (build_stmt (LABEL_STMT, dtor_label));
-
- /* Close the block; in a destructor, run the member cleanups. */
+ /* Close the block. */
finish_compound_stmt (0, compstmt);
if (processing_template_decl)
diff --git a/contrib/gcc/cp/decl2.c b/contrib/gcc/cp/decl2.c
index 4334963..730bbfb 100644
--- a/contrib/gcc/cp/decl2.c
+++ b/contrib/gcc/cp/decl2.c
@@ -1519,7 +1519,13 @@ grokfield (declarator, declspecs, init, asmspec_tree, attrlist)
/* friend or constructor went bad. */
return value;
if (TREE_TYPE (value) == error_mark_node)
- return error_mark_node;
+ return error_mark_node;
+
+ if (TREE_CODE (value) == TYPE_DECL && init)
+ {
+ error ("typedef `%D' is initialized (use __typeof__ instead)", value);
+ init = NULL_TREE;
+ }
/* Pass friendly classes back. */
if (TREE_CODE (value) == VOID_TYPE)
@@ -3795,10 +3801,8 @@ build_expr_from_tree (t)
case ALIGNOF_EXPR:
{
tree r = build_expr_from_tree (TREE_OPERAND (t, 0));
- if (!TYPE_P (r))
- return TREE_CODE (t) == SIZEOF_EXPR ? expr_sizeof (r) : c_alignof_expr (r);
- else
- return TREE_CODE (t) == SIZEOF_EXPR ? c_sizeof (r) : c_alignof (r);
+ return (TREE_CODE (t) == SIZEOF_EXPR
+ ? finish_sizeof (r) : finish_alignof (r));
}
case MODOP_EXPR:
diff --git a/contrib/gcc/cp/init.c b/contrib/gcc/cp/init.c
index a46d853..df63e67 100644
--- a/contrib/gcc/cp/init.c
+++ b/contrib/gcc/cp/init.c
@@ -348,6 +348,8 @@ build_field_list (t, list, uses_unions_p)
{
tree fields;
+ *uses_unions_p = 0;
+
/* Note whether or not T is a union. */
if (TREE_CODE (t) == UNION_TYPE)
*uses_unions_p = 1;
diff --git a/contrib/gcc/cp/lex.c b/contrib/gcc/cp/lex.c
index d68957a..c40469c 100644
--- a/contrib/gcc/cp/lex.c
+++ b/contrib/gcc/cp/lex.c
@@ -90,10 +90,11 @@ extern YYSTYPE yylval; /* the semantic value of the */
int warn_traditional = 0;
int flag_digraphs = 1;
-/* the declaration found for the last IDENTIFIER token read in.
- yylex must look this up to detect typedefs, which get token type TYPENAME,
- so it is left around in case the identifier is not a typedef but is
- used in a context which makes it a reference to a variable. */
+/* the declaration found for the last IDENTIFIER token read in. yylex
+ must look this up to detect typedefs, which get token type
+ tTYPENAME, so it is left around in case the identifier is not a
+ typedef but is used in a context which makes it a reference to a
+ variable. */
tree lastiddecl;
/* Array for holding counts of the numbers of tokens seen. */
@@ -739,7 +740,7 @@ yyprint (file, yychar, yylval)
switch (yychar)
{
case IDENTIFIER:
- case TYPENAME:
+ case tTYPENAME:
case TYPESPEC:
case PTYPENAME:
case PFUNCNAME:
@@ -977,7 +978,7 @@ check_for_missing_semicolon (type)
if ((yychar > 255
&& yychar != SCSPEC
&& yychar != IDENTIFIER
- && yychar != TYPENAME
+ && yychar != tTYPENAME
&& yychar != CV_QUALIFIER
&& yychar != SELFNAME)
|| yychar == 0 /* EOF */)
@@ -1194,7 +1195,7 @@ do_identifier (token, parsing, args)
tree args;
{
register tree id;
- int lexing = (parsing == 1);
+ int lexing = (parsing == 1 || parsing == 3);
if (! lexing)
id = lookup_name (token, 0);
@@ -1216,7 +1217,7 @@ do_identifier (token, parsing, args)
/* Remember that this name has been used in the class definition, as per
[class.scope0] */
- if (id && parsing)
+ if (id && parsing && parsing != 3)
maybe_note_name_used_in_class (token, id);
if (id == error_mark_node)
diff --git a/contrib/gcc/cp/mangle.c b/contrib/gcc/cp/mangle.c
index ba312b7..10f2b62 100644
--- a/contrib/gcc/cp/mangle.c
+++ b/contrib/gcc/cp/mangle.c
@@ -93,6 +93,13 @@ static struct globals
/* An array of the current substitution candidates, in the order
we've seen them. */
varray_type substitutions;
+
+ /* The entity that is being mangled. */
+ tree entity;
+
+ /* True if the mangling will be different in a future version of the
+ ABI. */
+ bool need_abi_warning;
} G;
/* Indices into subst_identifiers. These are identifiers used in
@@ -186,8 +193,8 @@ static const char *mangle_decl_string PARAMS ((tree));
/* Control functions. */
-static inline void start_mangling PARAMS ((void));
-static inline const char *finish_mangling PARAMS ((void));
+static inline void start_mangling PARAMS ((tree));
+static inline const char *finish_mangling PARAMS ((bool));
static tree mangle_special_for_type PARAMS ((tree, const char *));
/* Foreign language functions. */
@@ -884,6 +891,10 @@ write_prefix (node)
template_info = CLASSTYPE_TEMPLATE_INFO (node);
}
+ /* In G++ 3.2, the name of the template parameter was used. */
+ if (TREE_CODE (node) == TEMPLATE_TYPE_PARM)
+ G.need_abi_warning = true;
+
if (template_info != NULL)
/* Templated. */
{
@@ -955,6 +966,10 @@ write_template_prefix (node)
if (find_substitution (substitution))
return;
+ /* In G++ 3.2, the name of the template template parameter was used. */
+ if (TREE_CODE (TREE_TYPE (template)) == TEMPLATE_TEMPLATE_PARM)
+ G.need_abi_warning = true;
+
write_prefix (context);
write_unqualified_name (decl);
@@ -1823,6 +1838,10 @@ write_expression (expr)
write_template_arg_literal (expr);
else if (DECL_P (expr))
{
+ /* G++ 3.2 incorrectly mangled non-type template arguments of
+ enumeration type using their names. */
+ if (code == CONST_DECL)
+ G.need_abi_warning = 1;
write_char ('L');
write_mangled_name (expr);
write_char ('E');
@@ -1878,7 +1897,12 @@ write_expression (expr)
if (TREE_CODE (TREE_OPERAND (expr, 1)) == IDENTIFIER_NODE)
write_source_name (TREE_OPERAND (expr, 1));
else
- write_encoding (TREE_OPERAND (expr, 1));
+ {
+ /* G++ 3.2 incorrectly put out both the "sr" code and
+ the nested name of the qualified name. */
+ G.need_abi_warning = 1;
+ write_encoding (TREE_OPERAND (expr, 1));
+ }
break;
default:
@@ -1983,6 +2007,10 @@ write_template_arg (node)
write_template_template_arg (node);
else if (DECL_P (node))
{
+ /* G++ 3.2 incorrectly mangled non-type template arguments of
+ enumeration type using their names. */
+ if (code == CONST_DECL)
+ G.need_abi_warning = 1;
write_char ('L');
write_char ('Z');
write_encoding (node);
@@ -2152,16 +2180,23 @@ write_substitution (seq_id)
/* Start mangling a new name or type. */
static inline void
-start_mangling ()
+start_mangling (tree entity)
{
+ G.entity = entity;
+ G.need_abi_warning = false;
obstack_free (&G.name_obstack, obstack_base (&G.name_obstack));
}
/* Done with mangling. Return the generated mangled name. */
static inline const char *
-finish_mangling ()
+finish_mangling (bool warn)
{
+ if (warn_abi && warn && G.need_abi_warning)
+ warning ("the mangled name of `%D' will change in a future "
+ "version of GCC",
+ G.entity);
+
/* Clear all the substitutions. */
VARRAY_POP_ALL (G.substitutions);
@@ -2197,7 +2232,7 @@ mangle_decl_string (decl)
{
const char *result;
- start_mangling ();
+ start_mangling (decl);
if (TREE_CODE (decl) == TYPE_DECL)
write_type (TREE_TYPE (decl));
@@ -2224,7 +2259,7 @@ mangle_decl_string (decl)
write_string (" *INTERNAL* ");
}
- result = finish_mangling ();
+ result = finish_mangling (/*warn=*/true);
if (DEBUG_MANGLE)
fprintf (stderr, "mangle_decl_string = '%s'\n\n", result);
return result;
@@ -2249,9 +2284,9 @@ mangle_type_string (type)
{
const char *result;
- start_mangling ();
+ start_mangling (type);
write_type (type);
- result = finish_mangling ();
+ result = finish_mangling (/*warn=*/false);
if (DEBUG_MANGLE)
fprintf (stderr, "mangle_type_string = '%s'\n\n", result);
return result;
@@ -2279,7 +2314,7 @@ mangle_special_for_type (type, code)
/* We don't have an actual decl here for the special component, so
we can't just process the <encoded-name>. Instead, fake it. */
- start_mangling ();
+ start_mangling (type);
/* Start the mangling. */
write_string ("_Z");
@@ -2287,7 +2322,7 @@ mangle_special_for_type (type, code)
/* Add the type. */
write_type (type);
- result = finish_mangling ();
+ result = finish_mangling (/*warn=*/false);
if (DEBUG_MANGLE)
fprintf (stderr, "mangle_special_for_type = %s\n\n", result);
@@ -2354,7 +2389,7 @@ mangle_ctor_vtbl_for_type (type, binfo)
{
const char *result;
- start_mangling ();
+ start_mangling (type);
write_string ("_Z");
write_string ("TC");
@@ -2363,7 +2398,7 @@ mangle_ctor_vtbl_for_type (type, binfo)
write_char ('_');
write_type (BINFO_TYPE (binfo));
- result = finish_mangling ();
+ result = finish_mangling (/*warn=*/false);
if (DEBUG_MANGLE)
fprintf (stderr, "mangle_ctor_vtbl_for_type = %s\n\n", result);
return get_identifier (result);
@@ -2387,7 +2422,7 @@ mangle_thunk (fn_decl, offset, vcall_offset)
{
const char *result;
- start_mangling ();
+ start_mangling (fn_decl);
write_string ("_Z");
/* The <special-name> for virtual thunks is Tv, for non-virtual
@@ -2413,7 +2448,7 @@ mangle_thunk (fn_decl, offset, vcall_offset)
/* Scoped name. */
write_encoding (fn_decl);
- result = finish_mangling ();
+ result = finish_mangling (/*warn=*/false);
if (DEBUG_MANGLE)
fprintf (stderr, "mangle_thunk = %s\n\n", result);
return get_identifier (result);
@@ -2454,7 +2489,7 @@ tree
mangle_guard_variable (variable)
tree variable;
{
- start_mangling ();
+ start_mangling (variable);
write_string ("_ZGV");
if (strncmp (IDENTIFIER_POINTER (DECL_NAME (variable)), "_ZGR", 4) == 0)
/* The name of a guard variable for a reference temporary should refer
@@ -2462,7 +2497,7 @@ mangle_guard_variable (variable)
write_string (IDENTIFIER_POINTER (DECL_NAME (variable)) + 4);
else
write_name (variable, /*ignore_local_scope=*/0);
- return get_identifier (finish_mangling ());
+ return get_identifier (finish_mangling (/*warn=*/false));
}
/* Return an identifier for the name of a temporary variable used to
@@ -2473,10 +2508,10 @@ tree
mangle_ref_init_variable (variable)
tree variable;
{
- start_mangling ();
+ start_mangling (variable);
write_string ("_ZGR");
write_name (variable, /*ignore_local_scope=*/0);
- return get_identifier (finish_mangling ());
+ return get_identifier (finish_mangling (/*warn=*/false));
}
diff --git a/contrib/gcc/cp/method.c b/contrib/gcc/cp/method.c
index e4af0ab..5bb555d 100644
--- a/contrib/gcc/cp/method.c
+++ b/contrib/gcc/cp/method.c
@@ -688,7 +688,7 @@ do_build_assign_ref (fndecl)
comp = build (COMPONENT_REF, TREE_TYPE (field), comp, field);
init = build (COMPONENT_REF,
- build_qualified_type (TREE_TYPE (field), cvquals),
+ cp_build_qualified_type (TREE_TYPE (field), cvquals),
init, field);
if (DECL_NAME (field))
diff --git a/contrib/gcc/cp/parse.y b/contrib/gcc/cp/parse.y
index 6782621..5328ed3 100644
--- a/contrib/gcc/cp/parse.y
+++ b/contrib/gcc/cp/parse.y
@@ -253,7 +253,7 @@ cp_parse_init ()
/* All identifiers that are declared typedefs in the current block.
In some contexts, they are treated just like IDENTIFIER,
but they can also serve as typespecs in declarations. */
-%token TYPENAME
+%token tTYPENAME
%token SELFNAME
/* A template function. */
@@ -315,7 +315,7 @@ cp_parse_init ()
%nonassoc IF
%nonassoc ELSE
-%left IDENTIFIER PFUNCNAME TYPENAME SELFNAME PTYPENAME SCSPEC TYPESPEC CV_QUALIFIER ENUM AGGR ELLIPSIS TYPEOF SIGOF OPERATOR NSNAME TYPENAME_KEYWORD ATTRIBUTE
+%left IDENTIFIER PFUNCNAME tTYPENAME SELFNAME PTYPENAME SCSPEC TYPESPEC CV_QUALIFIER ENUM AGGR ELLIPSIS TYPEOF SIGOF OPERATOR NSNAME TYPENAME_KEYWORD ATTRIBUTE
%left '{' ',' ';'
@@ -345,7 +345,7 @@ cp_parse_init ()
%type <code> unop
-%type <ttype> identifier IDENTIFIER TYPENAME CONSTANT expr nonnull_exprlist
+%type <ttype> identifier IDENTIFIER tTYPENAME CONSTANT expr nonnull_exprlist
%type <ttype> PFUNCNAME maybe_identifier
%type <ttype> paren_expr_or_null nontrivial_exprlist SELFNAME
%type <ttype> expr_no_commas expr_no_comma_rangle
@@ -994,7 +994,7 @@ member_init:
identifier:
IDENTIFIER
- | TYPENAME
+ | tTYPENAME
| SELFNAME
| PTYPENAME
| NSNAME
@@ -1031,17 +1031,21 @@ explicit_instantiation:
{ do_type_instantiation ($4.t, $1, 1);
yyungetc (';', 1); }
end_explicit_instantiation
+ {}
| SCSPEC TEMPLATE begin_explicit_instantiation typed_declspecs
declarator
{ tree specs = strip_attrs ($4.t);
do_decl_instantiation (specs, $5, $1); }
end_explicit_instantiation
+ {}
| SCSPEC TEMPLATE begin_explicit_instantiation notype_declarator
{ do_decl_instantiation (NULL_TREE, $4, $1); }
end_explicit_instantiation
+ {}
| SCSPEC TEMPLATE begin_explicit_instantiation constructor_declarator
{ do_decl_instantiation (NULL_TREE, $4, $1); }
end_explicit_instantiation
+ {}
;
begin_explicit_instantiation:
@@ -1060,7 +1064,7 @@ template_type:
PTYPENAME '<' template_arg_list_opt template_close_bracket
.finish_template_type
{ $$ = $5; }
- | TYPENAME '<' template_arg_list_opt template_close_bracket
+ | tTYPENAME '<' template_arg_list_opt template_close_bracket
.finish_template_type
{ $$ = $5; }
| self_template_type
@@ -1507,7 +1511,7 @@ do_id:
don't do_identifier; we only do that for unqualified
identifiers. */
if (!lastiddecl || TREE_CODE (lastiddecl) != TREE_LIST)
- $$ = do_identifier ($<ttype>-1, 1, NULL_TREE);
+ $$ = do_identifier ($<ttype>-1, 3, NULL_TREE);
else
$$ = $<ttype>-1;
}
@@ -1532,7 +1536,7 @@ object_template_id:
unqualified_id:
notype_unqualified_id
- | TYPENAME
+ | tTYPENAME
| SELFNAME
;
@@ -2767,7 +2771,7 @@ after_type_component_declarator0:
after_type_declarator maybeasm maybe_attribute maybe_init
{ $$ = parse_field0 ($1, $<ftype>0.t, $<ftype>0.lookups,
$3, $2, $4); }
- | TYPENAME ':' expr_no_commas maybe_attribute
+ | tTYPENAME ':' expr_no_commas maybe_attribute
{ $$ = parse_bitfield0 ($1, $<ftype>0.t, $<ftype>0.lookups,
$4, $3); }
;
@@ -2790,7 +2794,7 @@ notype_component_declarator0:
after_type_component_declarator:
after_type_declarator maybeasm maybe_attribute maybe_init
{ $$ = parse_field ($1, $3, $2, $4); }
- | TYPENAME ':' expr_no_commas maybe_attribute
+ | tTYPENAME ':' expr_no_commas maybe_attribute
{ $$ = parse_bitfield ($1, $4, $3); }
;
@@ -3062,7 +3066,7 @@ functional_cast:
;
type_name:
- TYPENAME
+ tTYPENAME
| SELFNAME
| template_type %prec EMPTY
;
@@ -3086,7 +3090,7 @@ nested_name_specifier:
/* Why the @#$%^& do type_name and notype_identifier need to be expanded
inline here?!? (jason) */
nested_name_specifier_1:
- TYPENAME SCOPE
+ tTYPENAME SCOPE
{
if (TREE_CODE ($1) == IDENTIFIER_NODE)
{
@@ -3172,7 +3176,7 @@ typename_sub1:
/* This needs to return a TYPE_DECL for simple names so that we don't
forget what name was used. */
typename_sub2:
- TYPENAME SCOPE
+ tTYPENAME SCOPE
{
if (TREE_CODE ($1) != TYPE_DECL)
$$ = lastiddecl;
@@ -3610,7 +3614,7 @@ label_colon:
{ finish_label_stmt ($1); }
| PTYPENAME ':'
{ finish_label_stmt ($1); }
- | TYPENAME ':'
+ | tTYPENAME ':'
{ finish_label_stmt ($1); }
| SELFNAME ':'
{ finish_label_stmt ($1); }
diff --git a/contrib/gcc/cp/pt.c b/contrib/gcc/cp/pt.c
index 8fc9f74..b8e9545 100644
--- a/contrib/gcc/cp/pt.c
+++ b/contrib/gcc/cp/pt.c
@@ -3430,6 +3430,16 @@ convert_template_argument (parm, arg, args, complain, i, in_decl)
val, t);
return error_mark_node;
}
+
+ /* In order to avoid all sorts of complications, we do
+ not allow variably-modified types as template
+ arguments. */
+ if (variably_modified_type_p (val))
+ {
+ error ("template-argument `%T' is a variably modified type",
+ val);
+ return error_mark_node;
+ }
}
}
}
diff --git a/contrib/gcc/cp/rtti.c b/contrib/gcc/cp/rtti.c
index ae23234..39cb1c6 100644
--- a/contrib/gcc/cp/rtti.c
+++ b/contrib/gcc/cp/rtti.c
@@ -1413,11 +1413,13 @@ unemitted_tinfo_decl_p (t, data)
TREE_CODE (t) == VAR_DECL
/* whos name points back to itself */
&& IDENTIFIER_GLOBAL_VALUE (DECL_NAME (t)) == t
- /* whos name's type is non-null */
+ /* whose name's type is non-null */
&& TREE_TYPE (DECL_NAME (t))
- /* and whos type is a struct */
+ /* and whose type is a struct */
&& TREE_CODE (TREE_TYPE (t)) == RECORD_TYPE
- /* with a first field of our pseudo type info */
+ /* with a field */
+ && TYPE_FIELDS (TREE_TYPE (t))
+ /* which is our pseudo type info */
&& TREE_TYPE (TYPE_FIELDS (TREE_TYPE (t))) == ti_desc_type_node)
return 1;
return 0;
diff --git a/contrib/gcc/cp/semantics.c b/contrib/gcc/cp/semantics.c
index 43d3074..a484203 100644
--- a/contrib/gcc/cp/semantics.c
+++ b/contrib/gcc/cp/semantics.c
@@ -2117,7 +2117,7 @@ finish_alignof (t)
if (processing_template_decl)
return build_min_nt (ALIGNOF_EXPR, t);
- return TYPE_P (t) ? c_alignof (t) : c_alignof_expr (t);
+ return TYPE_P (t) ? c_alignof (complete_type (t)) : c_alignof_expr (t);
}
/* Generate RTL for the statement T, and its substatements, and any
diff --git a/contrib/gcc/cp/spew.c b/contrib/gcc/cp/spew.c
index 212dada..278a99a 100644
--- a/contrib/gcc/cp/spew.c
+++ b/contrib/gcc/cp/spew.c
@@ -115,6 +115,7 @@ static SPEW_INLINE int read_process_identifier PARAMS ((YYSTYPE *));
static SPEW_INLINE void feed_input PARAMS ((struct unparsed_text *));
static SPEW_INLINE void snarf_block PARAMS ((const char *, int));
static tree snarf_defarg PARAMS ((void));
+static void snarf_parenthesized_expression PARAMS ((const char *, int));
static int frob_id PARAMS ((int, int, tree *));
/* The list of inline functions being held off until we reach the end of
@@ -141,10 +142,11 @@ static enum cpp_ttype last_token;
static tree last_token_id;
/* From lex.c: */
-/* the declaration found for the last IDENTIFIER token read in.
- yylex must look this up to detect typedefs, which get token type TYPENAME,
- so it is left around in case the identifier is not a typedef but is
- used in a context which makes it a reference to a variable. */
+/* the declaration found for the last IDENTIFIER token read in. yylex
+ must look this up to detect typedefs, which get token type
+ tTYPENAME, so it is left around in case the identifier is not a
+ typedef but is used in a context which makes it a reference to a
+ variable. */
extern tree lastiddecl; /* let our brains leak out here too */
extern int yychar; /* the lookahead symbol */
extern YYSTYPE yylval; /* the semantic value of the */
@@ -483,9 +485,8 @@ add_token (t)
memcpy (t, feed->input->pos, sizeof (struct token));
return (feed->input->pos++)->yychar;
}
-
- memcpy (t, &Teosi, sizeof (struct token));
- return END_OF_SAVED_INPUT;
+
+ return 0;
}
/* Shift the next token onto the fifo. */
@@ -628,11 +629,11 @@ identifier_type (decl)
if (t && t == decl)
return SELFNAME;
- return TYPENAME;
+ return tTYPENAME;
}
/* token[0] == AGGR (struct/union/enum)
- Thus, token[1] is either a TYPENAME or a TYPENAME_DEFN.
+ Thus, token[1] is either a tTYPENAME or a TYPENAME_DEFN.
If token[2] == '{' or ':' then it's TYPENAME_DEFN.
It's also a definition if it's a forward declaration (as in 'struct Foo;')
which we can tell if token[2] == ';' *and* token[-1] != FRIEND or NEW. */
@@ -644,7 +645,7 @@ do_aggr ()
scan_tokens (2);
yc1 = nth_token (1)->yychar;
- if (yc1 != TYPENAME && yc1 != IDENTIFIER && yc1 != PTYPENAME)
+ if (yc1 != tTYPENAME && yc1 != IDENTIFIER && yc1 != PTYPENAME)
return;
yc2 = nth_token (2)->yychar;
if (yc2 == ';')
@@ -659,7 +660,7 @@ do_aggr ()
switch (yc1)
{
- case TYPENAME:
+ case tTYPENAME:
nth_token (1)->yychar = TYPENAME_DEFN;
break;
case PTYPENAME:
@@ -757,7 +758,7 @@ yylex ()
break;
}
case IDENTIFIER_DEFN:
- case TYPENAME:
+ case tTYPENAME:
case TYPENAME_DEFN:
case PTYPENAME:
case PTYPENAME_DEFN:
@@ -897,7 +898,7 @@ frob_id (yyc, peek, idp)
yyc = identifier_type (trrr);
switch(yyc)
{
- case TYPENAME:
+ case tTYPENAME:
case SELFNAME:
case NSNAME:
case PTYPENAME:
@@ -1031,6 +1032,38 @@ process_next_inline (i)
}
+/* Accumulate the tokens that make up a parenthesized expression in T,
+ having already read the opening parenthesis. */
+
+static void
+snarf_parenthesized_expression (starting_file, starting_line)
+ const char *starting_file;
+ int starting_line;
+{
+ int yyc;
+ int level = 1;
+
+ while (1)
+ {
+ size_t point;
+
+ point = obstack_object_size (&inline_text_obstack);
+ obstack_blank (&inline_text_obstack, sizeof (struct token));
+ yyc = add_token ((struct token *)
+ (obstack_base (&inline_text_obstack) + point));
+ if (yyc == '(')
+ ++level;
+ else if (yyc == ')' && --level == 0)
+ break;
+ else if (yyc == 0)
+ {
+ error_with_file_and_line (starting_file, starting_line,
+ "end of file read inside definition");
+ break;
+ }
+ }
+}
+
/* Subroutine of snarf_method, deals with actual absorption of the block. */
static SPEW_INLINE void
@@ -1113,6 +1146,8 @@ snarf_block (starting_file, starting_line)
else if (look_for_semicolon && blev == 0)
break;
}
+ else if (yyc == '(' && blev == 0)
+ snarf_parenthesized_expression (starting_file, starting_line);
else if (yyc == 0)
{
error_with_file_and_line (starting_file, starting_line,
@@ -1131,12 +1166,27 @@ snarf_method (decl)
int starting_lineno = lineno;
const char *starting_filename = input_filename;
size_t len;
+ int i;
struct unparsed_text *meth;
/* Leave room for the header, then absorb the block. */
obstack_blank (&inline_text_obstack, sizeof (struct unparsed_text));
snarf_block (starting_filename, starting_lineno);
+ /* Add three END_OF_SAVED_INPUT tokens. We used to provide an
+ infinite stream of END_OF_SAVED_INPUT tokens -- but that can
+ cause the compiler to get stuck in an infinite loop when
+ encountering invalid code. We need more than one because the
+ parser sometimes peeks ahead several tokens. */
+ for (i = 0; i < 3; ++i)
+ {
+ size_t point = obstack_object_size (&inline_text_obstack);
+ obstack_blank (&inline_text_obstack, sizeof (struct token));
+ memcpy ((struct token *)
+ (obstack_base (&inline_text_obstack) + point),
+ &Teosi,
+ sizeof (struct token));
+ }
len = obstack_object_size (&inline_text_obstack);
meth = (struct unparsed_text *) obstack_finish (&inline_text_obstack);
@@ -1187,6 +1237,7 @@ snarf_defarg ()
size_t point;
size_t len;
struct unparsed_text *buf;
+ int i;
tree arg;
obstack_blank (&inline_text_obstack, sizeof (struct unparsed_text));
@@ -1216,6 +1267,20 @@ snarf_defarg ()
push_token ((struct token *) (obstack_base (&inline_text_obstack) + point));
/* This is the documented way to shrink a growing obstack block. */
obstack_blank (&inline_text_obstack, - (int) sizeof (struct token));
+ /* Add three END_OF_SAVED_INPUT tokens. We used to provide an
+ infinite stream of END_OF_SAVED_INPUT tokens -- but that can
+ cause the compiler to get stuck in an infinite loop when
+ encountering invalid code. We need more than one because the
+ parser sometimes peeks ahead several tokens. */
+ for (i = 0; i < 3; ++i)
+ {
+ point = obstack_object_size (&inline_text_obstack);
+ obstack_blank (&inline_text_obstack, sizeof (struct token));
+ memcpy ((struct token *)
+ (obstack_base (&inline_text_obstack) + point),
+ &Teosi,
+ sizeof (struct token));
+ }
done:
len = obstack_object_size (&inline_text_obstack);
@@ -1448,7 +1513,7 @@ debug_yychar (yy)
{
if (yy<256)
fprintf (stderr, "->%d < %c >\n", lineno, yy);
- else if (yy == IDENTIFIER || yy == TYPENAME)
+ else if (yy == IDENTIFIER || yy == tTYPENAME)
{
const char *id;
if (TREE_CODE (yylval.ttype) == IDENTIFIER_NODE)
diff --git a/contrib/gcc/cp/tree.c b/contrib/gcc/cp/tree.c
index 748ab9a..65dca00 100644
--- a/contrib/gcc/cp/tree.c
+++ b/contrib/gcc/cp/tree.c
@@ -1903,19 +1903,19 @@ pod_type_p (t)
int
zero_init_p (t)
- tree t;
+ tree t ATTRIBUTE_UNUSED;
{
- t = strip_array_types (t);
-
- /* NULL pointers to data members are initialized with -1. */
- if (TYPE_PTRMEM_P (t))
- return 0;
+ /* This is not a correct implementation of this function. As a
+ result, pointers-to-members will not be correctly
+ zero-initialized.
- /* Classes that contain types that can't be zero-initialized, cannot
- be zero-initialized themselves. */
- if (CLASS_TYPE_P (t) && CLASSTYPE_NON_ZERO_INIT_P (t))
- return 0;
+ However, using a correct implementation of this function results
+ in many other failures. Correcting these other failures required
+ a major infrastructure improvement, which was undertaken in the
+ GCC 3.3 source base.
+ In order to reduce risk, these changes were not ported to the GCC
+ 3.2 source base. */
return 1;
}
diff --git a/contrib/gcc/cp/typeck.c b/contrib/gcc/cp/typeck.c
index d326969..b019d0a 100644
--- a/contrib/gcc/cp/typeck.c
+++ b/contrib/gcc/cp/typeck.c
@@ -4167,6 +4167,25 @@ build_x_unary_op (code, xarg)
}
if (code == ADDR_EXPR)
{
+ /* A pointer to member-function can be formed only by saying
+ &X::mf. */
+ if (!flag_ms_extensions && TREE_CODE (TREE_TYPE (xarg)) == METHOD_TYPE
+ && (TREE_CODE (xarg) != OFFSET_REF || !PTRMEM_OK_P (xarg)))
+ {
+ if (TREE_CODE (xarg) != OFFSET_REF)
+ {
+ error ("invalid use of '%E' to form a pointer-to-member-function. Use a qualified-id.",
+ xarg);
+ return error_mark_node;
+ }
+ else
+ {
+ error ("parenthesis around '%E' cannot be used to form a pointer-to-member-function",
+ xarg);
+ PTRMEM_OK_P (xarg) = 1;
+ }
+ }
+
if (TREE_CODE (xarg) == OFFSET_REF)
{
ptrmem = PTRMEM_OK_P (xarg);
diff --git a/contrib/gcc/cp/typeck2.c b/contrib/gcc/cp/typeck2.c
index d3febeb..f8e612b 100644
--- a/contrib/gcc/cp/typeck2.c
+++ b/contrib/gcc/cp/typeck2.c
@@ -863,8 +863,7 @@ process_init_constructor (type, init, elts)
{
if (TREE_READONLY (field))
error ("uninitialized const member `%D'", field);
- else if (TYPE_LANG_SPECIFIC (TREE_TYPE (field))
- && CLASSTYPE_READONLY_FIELDS_NEED_INIT (TREE_TYPE (field)))
+ else if (CLASSTYPE_READONLY_FIELDS_NEED_INIT (TREE_TYPE (field)))
error ("member `%D' with uninitialized const fields",
field);
else if (TREE_CODE (TREE_TYPE (field)) == REFERENCE_TYPE)
@@ -976,6 +975,8 @@ process_init_constructor (type, init, elts)
return error_mark_node;
result = build (CONSTRUCTOR, type, NULL_TREE, nreverse (members));
+ if (TREE_CODE (type) == ARRAY_TYPE && TYPE_DOMAIN (type) == NULL_TREE)
+ complete_array_type (type, result, /*do_default=*/0);
if (init)
TREE_HAS_CONSTRUCTOR (result) = TREE_HAS_CONSTRUCTOR (init);
if (allconstant) TREE_CONSTANT (result) = 1;
OpenPOWER on IntegriCloud