This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

C++ PATCH: Fix PR5189


This patch fixes C++ PR 5189, whereby we ended up in an infinite
loop in the compiler since we were trying to use a copy constructor
whose only argument was a value parameter of the destination type.

Boostrapped and tested on i686-pc-linux-gnu, applied on the mainline
and on the branch.

--
Mark Mitchell                   mark@codesourcery.com
CodeSourcery, LLC               http://www.codesourcery.com

2002-04-12  Mark Mitchell  <mark@codesourcery.com>

	PR c++/5189.
	* call.c (add_template_candidate_real): Do not treat member
	templates as copy constructors.

2002-04-12  Mark Mitchell  <mark@codesourcery.com>

	PR c++/5189.
	* g++.dg/template/copy1.C: New test.

Index: testsuite/g++.dg/template/copy1.C
===================================================================
RCS file: testsuite/g++.dg/template/copy1.C
diff -N testsuite/g++.dg/template/copy1.C
*** /dev/null	1 Jan 1970 00:00:00 -0000
--- testsuite/g++.dg/template/copy1.C	13 Apr 2002 01:28:12 -0000
***************
*** 0 ****
--- 1,14 ----
+ // { dg-do compile }
+
+ // Origin: hkluender@otg.com
+
+ // PR 5189
+
+ struct A
+ {
+   A(A&); // { dg-error "candidate" "" }
+   template <class T> A(T);
+ };
+
+ A a = 0; // { dg-error "no matching function|initializing" "" }
+
Index: cp/call.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/call.c,v
retrieving revision 1.307.2.5
diff -c -p -r1.307.2.5 call.c
*** cp/call.c	27 Mar 2002 19:13:59 -0000	1.307.2.5
--- cp/call.c	13 Apr 2002 01:28:13 -0000
*************** add_template_candidate_real (candidates,
*** 2238,2243 ****
--- 2238,2273 ----
    if (fn == error_mark_node)
      return candidates;

+   /* In [class.copy]:
+
+        A member function template is never instantiated to perform the
+        copy of a class object to an object of its class type.
+
+      It's a little unclear what this means; the standard explicitly
+      does allow a template to be used to copy a class.  For example,
+      in:
+
+        struct A {
+          A(A&);
+ 	 template <class T> A(const T&);
+        };
+        const A f ();
+        void g () { A a (f ()); }
+
+      the member template will be used to make the copy.  The section
+      quoted above appears in the paragraph that forbids constructors
+      whose only parameter is (a possibly cv-qualified variant of) the
+      class type, and a logical interpretation is that the intent was
+      to forbid the instantiation of member templates which would then
+      have that form.  */
+   if (DECL_CONSTRUCTOR_P (fn) && list_length (arglist) == 2)
+     {
+       tree arg_types = FUNCTION_FIRST_USER_PARMTYPE (fn);
+       if (arg_types && same_type_p (TYPE_MAIN_VARIANT (TREE_VALUE 
(arg_types)),
+ 				    ctype))
+ 	return candidates;
+     }
+
    if (obj != NULL_TREE)
      /* Aha, this is a conversion function.  */
      cand = add_conv_candidate (candidates, fn, obj, arglist);


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]