Patch PR c++/45200
authordodji <dodji@138bc75d-0d04-0410-961f-82ee72b054a4>
Mon, 6 Sep 2010 18:44:23 +0000 (18:44 +0000)
committerdodji <dodji@138bc75d-0d04-0410-961f-82ee72b054a4>
Mon, 6 Sep 2010 18:44:23 +0000 (18:44 +0000)
    Fix PR c++/45200, c++/45293, c++/45558

gcc/cp/Changelog:
PR c++/45200
PR c++/45293
PR c++/45558
* tree.c (strip_typedefs): Strip typedefs from the context of
TYPENAME_TYPEs.

gcc/testsuite/ChangeLog:
PR c++/45200
PR c++/45293
PR c++/45558
* g++.dg/template/typedef34.C: New test.
* g++.dg/template/typedef35.C: New test.

git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@163929 138bc75d-0d04-0410-961f-82ee72b054a4

gcc/cp/ChangeLog
gcc/cp/tree.c
gcc/cp/typeck.c
gcc/testsuite/ChangeLog
gcc/testsuite/g++.dg/template/typedef34.C [new file with mode: 0644]
gcc/testsuite/g++.dg/template/typedef35.C [new file with mode: 0644]

index 99c720c..f777ae9 100644 (file)
@@ -1,3 +1,11 @@
+2010-09-06  Dodji Seketeli  <dodji@redhat.com>
+
+       PR c++/45200
+       PR c++/45293
+       PR c++/45558
+       * tree.c (strip_typedefs): Strip typedefs from the context of
+       TYPENAME_TYPEs.
+
 2010-09-06  Mark Mitchell  <mark@codesourcery.com>
 
        * typeck.c (cp_build_binary_op): Call do_warn_double_promotion.
index af5a82f..ea01d1f 100644 (file)
@@ -1047,6 +1047,11 @@ strip_typedefs (tree t)
                                            TYPE_RAISES_EXCEPTIONS (t));
       }
       break;
+    case TYPENAME_TYPE:
+      result = make_typename_type (strip_typedefs (TYPE_CONTEXT (t)),
+                                  TYPENAME_TYPE_FULLNAME (t),
+                                  typename_type, tf_none);
+      break;
     default:
       break;
     }
index e96272f..0ac95d0 100644 (file)
@@ -1220,7 +1220,7 @@ incompatible_dependent_types_p (tree t1, tree t2)
 
   if (!t1_typedef_variant_p || !t2_typedef_variant_p)
     /* Either T1 or T2 is not a typedef so we cannot compare the
-       the template parms of the typedefs of T1 and T2.
+       template parms of the typedefs of T1 and T2.
        At this point, if the main variant type of T1 and T2 are equal
        it means the two types can't be incompatible, from the perspective
        of this function.  */
index f989ce7..4805390 100644 (file)
@@ -1,3 +1,11 @@
+2010-09-06  Dodji Seketeli  <dodji@redhat.com>
+
+       PR c++/45200
+       PR c++/45293
+       PR c++/45558
+       * g++.dg/template/typedef34.C: New test.
+       * g++.dg/template/typedef35.C: New test.
+
 2010-09-06  Uros Bizjak  <ubizjak@gmail.com>
 
        PR target/22152
diff --git a/gcc/testsuite/g++.dg/template/typedef34.C b/gcc/testsuite/g++.dg/template/typedef34.C
new file mode 100644 (file)
index 0000000..a82e155
--- /dev/null
@@ -0,0 +1,37 @@
+// Origin PR c++/45200
+// { dg-do compile }
+
+template<typename T>
+struct remove_reference
+{
+  typedef T type;
+};
+
+template<typename TestType>
+struct forward_as_lref
+{
+};
+
+template<typename Seq, typename N>
+struct apply1
+{
+  typedef typename remove_reference<Seq>::type seq;
+  typedef forward_as_lref<typename seq::seq_type> type; //#0
+};
+
+template<typename Seq>
+struct apply
+{
+  typedef forward_as_lref<typename remove_reference<Seq>::type::seq_type> type; //#1
+};
+
+struct reverse_view
+{
+  typedef int seq_type;
+};
+
+int
+main()
+{
+  apply<reverse_view >::type a2;
+}
diff --git a/gcc/testsuite/g++.dg/template/typedef35.C b/gcc/testsuite/g++.dg/template/typedef35.C
new file mode 100644 (file)
index 0000000..2dddf09
--- /dev/null
@@ -0,0 +1,41 @@
+// Origin c++/45558
+// { dg-do compile }
+
+template <typename S, typename T>
+struct C
+{
+  template <typename U>
+  struct B
+  {
+    template <typename W>
+    struct E
+    {
+      explicit E(const W &x) : w(x) {}
+      const W &w;
+    };
+  };
+};
+
+struct F;
+template <typename X>
+struct D
+{
+  D() {}
+};
+
+const D<F> g;
+template <typename S, typename T>
+struct A
+{
+  template <typename U>
+  struct B : C<S, T>::template B<U>
+  {
+    typedef typename C<S, T>::template B<U> V;
+    static const D<typename V::template E<D<F> > > a;
+  };
+};
+
+template <typename S, typename T>
+template <typename U>
+const D<typename C<S, T>::template B<U>::template E<D<F> > >
+A<S, T>::B<U>::a = typename C<S, T>::template B<U>::template E<D<F> >(g);