aboutsummaryrefslogtreecommitdiff
path: root/gcc/c-decl.c
diff options
context:
space:
mode:
authorJoseph Myers <joseph@codesourcery.com>2010-05-23 21:47:16 +0100
committerJoseph Myers <jsm28@gcc.gnu.org>2010-05-23 21:47:16 +0100
commitdc5027f47440baef6b984b029fb5c3e5ee59e5ba (patch)
tree83fb32a9434ffd3ff6d6985dd79f64b42099c036 /gcc/c-decl.c
parent8f9e812dacef3cc9eedb9fa17111affa93454287 (diff)
downloadgcc-dc5027f47440baef6b984b029fb5c3e5ee59e5ba.zip
gcc-dc5027f47440baef6b984b029fb5c3e5ee59e5ba.tar.gz
gcc-dc5027f47440baef6b984b029fb5c3e5ee59e5ba.tar.bz2
c-decl.c (diagnose_mismatched_decls): Give error for duplicate typedefs with different but compatible types.
* c-decl.c (diagnose_mismatched_decls): Give error for duplicate typedefs with different but compatible types. Allow duplicate typedefs with the same type except for pedantic non-C1X, but give warning for variably modified types. * c-typeck.c (tagged_types_tu_compatible_p, function_types_compatible_p, type_lists_compatible_p, comptypes_internal): Add parameter different_types_p; set *different_types_p for different but compatible types. All callers changed. (comptypes_check_different_types): New. * c-tree.h (comptypes_check_different_types): Declare. testsuite: * gcc.dg/c1x-typedef-1.c, gcc.dg/c1x-typedef-2.c, gcc.dg/c90-typedef-1.c, gcc.dg/c99-typedef-1.c: New tests. * gcc.dg/decl-8.c: Use -std=gnu89 -pedantic-errors. From-SVN: r159767
Diffstat (limited to 'gcc/c-decl.c')
-rw-r--r--gcc/c-decl.c38
1 files changed, 34 insertions, 4 deletions
diff --git a/gcc/c-decl.c b/gcc/c-decl.c
index af038e1..68b0f8c 100644
--- a/gcc/c-decl.c
+++ b/gcc/c-decl.c
@@ -1786,18 +1786,48 @@ diagnose_mismatched_decls (tree newdecl, tree olddecl,
/* Redeclaration of a type is a constraint violation (6.7.2.3p1),
but silently ignore the redeclaration if either is in a system
- header. (Conflicting redeclarations were handled above.) */
+ header. (Conflicting redeclarations were handled above.) This
+ is allowed for C1X if the types are the same, not just
+ compatible. */
if (TREE_CODE (newdecl) == TYPE_DECL)
{
+ bool types_different = false;
+ int comptypes_result;
+
+ comptypes_result
+ = comptypes_check_different_types (oldtype, newtype, &types_different);
+
+ if (comptypes_result != 1 || types_different)
+ {
+ error ("redefinition of typedef %q+D with different type", newdecl);
+ locate_old_decl (olddecl);
+ return false;
+ }
+
if (DECL_IN_SYSTEM_HEADER (newdecl)
|| DECL_IN_SYSTEM_HEADER (olddecl)
|| TREE_NO_WARNING (newdecl)
|| TREE_NO_WARNING (olddecl))
return true; /* Allow OLDDECL to continue in use. */
- error ("redefinition of typedef %q+D", newdecl);
- locate_old_decl (olddecl);
- return false;
+ if (pedantic && !flag_isoc1x)
+ {
+ pedwarn (input_location, OPT_pedantic,
+ "redefinition of typedef %q+D", newdecl);
+ locate_old_decl (olddecl);
+ }
+ else if (variably_modified_type_p (newtype, NULL))
+ {
+ /* Whether there is a constraint violation for the types not
+ being the same cannot be determined at compile time; a
+ warning that there may be one at runtime is considered
+ appropriate (WG14 reflector message 11743, 8 May 2009). */
+ warning (0, "redefinition of typedef %q+D may be a constraint "
+ "violation at runtime", newdecl);
+ locate_old_decl (olddecl);
+ }
+
+ return true;
}
/* Function declarations can either be 'static' or 'extern' (no