------- Additional Comments From aoliva at gcc dot gnu dot org  2005-04-19 
21:45 -------
Subject: [PR c++/21087] don't keep builtin anticipated decl, override it with 
actual declaration

When push_overloaded_decl() was passed a new declaration that matches
a builtin decl, it would verify that the declarations matched and, if
so, leave the existing (built-in) declaration alone.

The intended behavior is to merge the built-in declaration with the
new declaration, into the location of the built-in declaration.

The problem is that duplicate_decl() doesn't perform such merging when
the new declaration is a template decl, and then we end up with an
overload involving the template decl and the anticipated built-in
decl.  However, overloads involving anticipated decls are something we
try to avoid, and actually check for elsewhere.

This patch fixes the code such that, if the existing decl is
anticipated and the two decls weren't merged, we discard the built-in
and use the new decl by itself.

Bootstrapped and regtested on amd64-linux-gnu.  Ok to install?

Index: gcc/cp/ChangeLog
from  Alexandre Oliva  <[EMAIL PROTECTED]>

        PR c++/21087
        * name-lookup.c (push_overloaded_decl): Do not overload with
        non-duplicate anticipated built-in.

Index: gcc/cp/name-lookup.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/name-lookup.c,v
retrieving revision 1.113
diff -u -p -r1.113 name-lookup.c
--- gcc/cp/name-lookup.c 14 Mar 2005 14:51:14 -0000 1.113
+++ gcc/cp/name-lookup.c 19 Apr 2005 19:20:11 -0000
@@ -1883,6 +1883,13 @@ push_overloaded_decl (tree decl, int fla
              if (duplicate_decls (decl, fn) == fn)
                POP_TIMEVAR_AND_RETURN (TV_NAME_LOOKUP, fn);
            }
+
+         /* We don't overload implicit built-ins.  duplicate_decls()
+            may fail to merge the decls if the new decl is e.g. a
+            template function.  */
+         if (TREE_CODE (old) == FUNCTION_DECL
+             && DECL_ANTICIPATED (old))
+           old = NULL;
        }
       else if (old == error_mark_node)
        /* Ignore the undefined symbol marker.  */
Index: gcc/testsuite/ChangeLog
from  Alexandre Oliva  <[EMAIL PROTECTED]>

        PR c++/21087
        * g++.dg/lookup/builtin2.C: New test.

Index: gcc/testsuite/g++.dg/lookup/builtin2.C
===================================================================
RCS file: gcc/testsuite/g++.dg/lookup/builtin2.C
diff -N gcc/testsuite/g++.dg/lookup/builtin2.C
--- /dev/null   1 Jan 1970 00:00:00 -0000
+++ gcc/testsuite/g++.dg/lookup/builtin2.C 19 Apr 2005 19:20:27 -0000
@@ -0,0 +1,19 @@
+/* { dg-do compile } */
+
+/* PR c++/21087 */
+
+/* We used to overload the template function with the built-in
+   declaration, instead of replacing it as we should, and then barf at
+   the using decl because of a test that none of the overload set
+   members were anticipated built-ins.  */
+
+extern "C" signed int toupper(signed int __c) throw();
+namespace std
+{
+  template< typename a > a toupper(a,int){}
+  using ::toupper;
+}
+
+int f () {
+  std::toupper((signed int)'a');
+}

-- 
Alexandre Oliva             http://www.ic.unicamp.br/~oliva/
Red Hat Compiler Engineer   [EMAIL PROTECTED], gcc.gnu.org}
Free Software Evangelist  [EMAIL PROTECTED], gnu.org}


-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=21087

Reply via email to