diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index e6b4f45db671f2f35013c6893a94c258196b39ad..7fc9a0707535bffe555bca0a86801981ef57b302 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,3 +1,7 @@ +2007-05-22 Ollie Wild <aaw@google.com> + + * decl.c (duplicate_decls): Verify namespace names are unique. + 2007-05-21 Mark Mitchell <mark@codesourcery.com> * decl.c (cxx_maybe_build_cleanup): Handle diff --git a/gcc/cp/decl.c b/gcc/cp/decl.c index c76568a16f34379c4a83457d431a48328c32d006..02b38225a9e843743e0660b8958d14c06b027eff 100644 --- a/gcc/cp/decl.c +++ b/gcc/cp/decl.c @@ -1297,30 +1297,36 @@ duplicate_decls (tree newdecl, tree olddecl, bool newdecl_is_friend) } else if (TREE_CODE (olddecl) != TREE_CODE (newdecl)) { - if ((TREE_CODE (olddecl) == TYPE_DECL && DECL_ARTIFICIAL (olddecl) - && TREE_CODE (newdecl) != TYPE_DECL - && ! (TREE_CODE (newdecl) == TEMPLATE_DECL - && TREE_CODE (DECL_TEMPLATE_RESULT (newdecl)) == TYPE_DECL)) - || (TREE_CODE (newdecl) == TYPE_DECL && DECL_ARTIFICIAL (newdecl) - && TREE_CODE (olddecl) != TYPE_DECL - && ! (TREE_CODE (olddecl) == TEMPLATE_DECL - && (TREE_CODE (DECL_TEMPLATE_RESULT (olddecl)) - == TYPE_DECL)))) - { - /* We do nothing special here, because C++ does such nasty - things with TYPE_DECLs. Instead, just let the TYPE_DECL - get shadowed, and know that if we need to find a TYPE_DECL - for a given name, we can look in the IDENTIFIER_TYPE_VALUE - slot of the identifier. */ - return NULL_TREE; + /* C++ Standard, 3.3, clause 4: + "[Note: a namespace name or a class template name must be unique + in its declarative region (7.3.2, clause 14). ]" */ + if (TREE_CODE (olddecl) != NAMESPACE_DECL + && TREE_CODE (newdecl) != NAMESPACE_DECL + && (TREE_CODE (olddecl) != TEMPLATE_DECL + || TREE_CODE (DECL_TEMPLATE_RESULT (olddecl)) != TYPE_DECL) + && (TREE_CODE (newdecl) != TEMPLATE_DECL + || TREE_CODE (DECL_TEMPLATE_RESULT (newdecl)) != TYPE_DECL)) + { + if ((TREE_CODE (olddecl) == TYPE_DECL && DECL_ARTIFICIAL (olddecl) + && TREE_CODE (newdecl) != TYPE_DECL) + || (TREE_CODE (newdecl) == TYPE_DECL && DECL_ARTIFICIAL (newdecl) + && TREE_CODE (olddecl) != TYPE_DECL)) + { + /* We do nothing special here, because C++ does such nasty + things with TYPE_DECLs. Instead, just let the TYPE_DECL + get shadowed, and know that if we need to find a TYPE_DECL + for a given name, we can look in the IDENTIFIER_TYPE_VALUE + slot of the identifier. */ + return NULL_TREE; + } + + if ((TREE_CODE (newdecl) == FUNCTION_DECL + && DECL_FUNCTION_TEMPLATE_P (olddecl)) + || (TREE_CODE (olddecl) == FUNCTION_DECL + && DECL_FUNCTION_TEMPLATE_P (newdecl))) + return NULL_TREE; } - if ((TREE_CODE (newdecl) == FUNCTION_DECL - && DECL_FUNCTION_TEMPLATE_P (olddecl)) - || (TREE_CODE (olddecl) == FUNCTION_DECL - && DECL_FUNCTION_TEMPLATE_P (newdecl))) - return NULL_TREE; - error ("%q#D redeclared as different kind of symbol", newdecl); if (TREE_CODE (olddecl) == TREE_LIST) olddecl = TREE_VALUE (olddecl); diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 601700c8debfca17551ca137720ac5ab59463e3a..77b6a7fa3260b64b4108ef5039ea37d229753bbe 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2007-05-22 Ollie Wild <aaw@google.com> + + * g++.dg/lookup/name-clash5.C: New test. + * g++.dg/lookup/name-clash6.C: New test. + 2007-05-22 H.J. Lu <hongjiu.lu@intel.com> * g++.dg/other/i386-2.C: Update comments on header files tested. diff --git a/gcc/testsuite/g++.dg/lookup/name-clash5.C b/gcc/testsuite/g++.dg/lookup/name-clash5.C new file mode 100644 index 0000000000000000000000000000000000000000..7f220d8877f7c88925c6922a0acdba74ff292f07 --- /dev/null +++ b/gcc/testsuite/g++.dg/lookup/name-clash5.C @@ -0,0 +1,13 @@ +// Copyright (C) 2007 Free Software Foundation +// Contributed by Ollie Wild <aaw@google.com> +// { dg-do compile } + +// C++ Standard, 3.3, clause 4: +// "[Note: a namespace name or a class template name must be unique in its +// declarative region (7.3.2, clause 14). ]" + +namespace N +{ // { dg-error "previous declaration" } +} + +class N; // { dg-error "redeclared" } diff --git a/gcc/testsuite/g++.dg/lookup/name-clash6.C b/gcc/testsuite/g++.dg/lookup/name-clash6.C new file mode 100644 index 0000000000000000000000000000000000000000..63a0b15bf5eea55d687dc370e0fa8afe7fe99fc3 --- /dev/null +++ b/gcc/testsuite/g++.dg/lookup/name-clash6.C @@ -0,0 +1,13 @@ +// Copyright (C) 2007 Free Software Foundation +// Contributed by Ollie Wild <aaw@google.com> +// { dg-do compile } + +// C++ Standard, 3.3, clause 4: +// "[Note: a namespace name or a class template name must be unique in its +// declarative region (7.3.2, clause 14). ]" + +class N; // { dg-error "previous declaration" } + +namespace N +{ // { dg-error "redeclared" } +}