From patchwork Wed Aug 11 18:25:36 2010 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Dodji Seketeli X-Patchwork-Id: 61497 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Received: from sourceware.org (server1.sourceware.org [209.132.180.131]) by ozlabs.org (Postfix) with SMTP id 5166AB70DF for ; Thu, 12 Aug 2010 04:25:49 +1000 (EST) Received: (qmail 11352 invoked by alias); 11 Aug 2010 18:25:47 -0000 Received: (qmail 11303 invoked by uid 22791); 11 Aug 2010 18:25:45 -0000 X-SWARE-Spam-Status: No, hits=-5.3 required=5.0 tests=AWL, BAYES_00, RCVD_IN_DNSWL_HI, SPF_HELO_PASS, T_MIME_NO_TEXT, T_RP_MATCHES_RCVD, T_TVD_MIME_NO_HEADERS X-Spam-Check-By: sourceware.org Received: from mx1.redhat.com (HELO mx1.redhat.com) (209.132.183.28) by sourceware.org (qpsmtpd/0.43rc1) with ESMTP; Wed, 11 Aug 2010 18:25:40 +0000 Received: from int-mx08.intmail.prod.int.phx2.redhat.com (int-mx08.intmail.prod.int.phx2.redhat.com [10.5.11.21]) by mx1.redhat.com (8.13.8/8.13.8) with ESMTP id o7BIPd4e003407 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK) for ; Wed, 11 Aug 2010 14:25:39 -0400 Received: from adjoa.redhat.com (ovpn01.gateway.prod.ext.phx2.redhat.com [10.5.9.1]) by int-mx08.intmail.prod.int.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id o7BIPaNa005673; Wed, 11 Aug 2010 14:25:37 -0400 From: Dodji Seketeli To: GCC Patches Cc: Jason Merrill Subject: [Dodji Seketeli] Patch PR c++/45200 X-URL: http://www.seketeli.org/dodji Date: Wed, 11 Aug 2010 20:25:36 +0200 Message-ID: User-Agent: Gnus/5.13 (Gnus v5.13) Emacs/23.1 (gnu/linux) MIME-Version: 1.0 X-IsSubscribed: yes Mailing-List: contact gcc-patches-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Id: List-Unsubscribe: List-Archive: List-Post: List-Help: Sender: gcc-patches-owner@gcc.gnu.org Delivered-To: mailing list gcc-patches@gcc.gnu.org Sorry, I previously forwarded this to the wrong mailing list. Hello, In the example accompanying the patch below we consider that the types forward_as_lref at line marked with //#0 and forward_as_lref::type::seq_type> at the line marked with //#1 should compare equal. And I believe that is correct[1]. It follows that during the instantiantion of apply, lookup_class_template looks up an instantiation for forward_as_lref::type::seq_type> and returns forward_as_lref. Then the tsubst'ing of forward_as_lref in the context of template struct apply fails because it tries to reuse the typedef seq that was defined in the incompatible context template struct apply1. This case seems to argue for stripping typedefs from the TYPE_CONTEXT of TYPENAME_TYPEs when they are passed as template arguments. I refrained from doing it before because I thought that incompatible_dependent_types_p would be enough to handle all comparisons involving dependent typedefs. [1]: This is based on the resolution of PR c++/43800 at http://gcc.gnu.org/ml/gcc-patches/2010-04/msg01241.html Tested on x86_64-unknown-linux-gnu against trunk and the 4.5 branch. OK to commit to both branches? commit d9a0f93c1fda1d97cda5747003de84edd3812bda Author: Dodji Seketeli Date: Mon Aug 9 23:12:39 2010 +0200 Fix PR c++/45200 gcc/cp/Changelog: PR c++/45200 * tree.c (strip_typedefs): Strip typedefs from the context of TYPENAME_TYPEs. gcc/testsuite/ChangeLog: PR c++/45200 * g++.dg/template/typedef34.C: New test. diff --git a/gcc/cp/tree.c b/gcc/cp/tree.c index 450b9e8..6b2aab0 100644 --- a/gcc/cp/tree.c +++ b/gcc/cp/tree.c @@ -1046,6 +1046,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; } diff --git a/gcc/cp/typeck.c b/gcc/cp/typeck.c index 484d299..a506053 100644 --- a/gcc/cp/typeck.c +++ b/gcc/cp/typeck.c @@ -1212,7 +1212,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. */ diff --git a/gcc/testsuite/g++.dg/template/typedef34.C b/gcc/testsuite/g++.dg/template/typedef34.C new file mode 100644 index 0000000..9bb4460 --- /dev/null +++ b/gcc/testsuite/g++.dg/template/typedef34.C @@ -0,0 +1,37 @@ +// Origin PR c++/45200 +// { dg-do compile } + +template +struct remove_reference +{ + typedef T type; +}; + +template +struct forward_as_lref +{ +}; + +template +struct apply1 +{ + typedef typename remove_reference::type seq; + typedef forward_as_lref type; //#0 +}; + +template +struct apply +{ + typedef forward_as_lref::type::seq_type> type; //#1 +}; + +struct reverse_view +{ + typedef int seq_type; +}; + +int +main() +{ + apply::type a2; +}