Bug 26988 - [4.1 Regression] template constructor in template class derived from virtual base can not be specialized
Summary: [4.1 Regression] template constructor in template class derived from virtual ...
Status: RESOLVED FIXED
Alias: None
Product: gcc
Classification: Unclassified
Component: c++ (show other bugs)
Version: 4.0.2
: P2 normal
Target Milestone: 4.2.0
Assignee: Mark Mitchell
URL:
Keywords: monitored, rejects-valid
Depends on: 9050
Blocks:
  Show dependency treegraph
 
Reported: 2006-04-02 15:05 UTC by Ingo Nolden
Modified: 2008-07-04 15:26 UTC (History)
5 users (show)

See Also:
Host:
Target:
Build:
Known to work: 2.95 4.2.0 4.3.0
Known to fail: 3.3.5 3.4.4 4.0.1 4.0.4 4.1.0 4.1.3
Last reconfirmed: 2006-04-18 03:45:10


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Ingo Nolden 2006-04-02 15:05:46 UTC
Given the following code:


 #define VIRTUAL virtual
//#define VIRTUAL                    // use this to 'fix' the code

#include <iostream>
using namespace std;


struct VirtualBase{};
		
		
struct Bar : public VIRTUAL VirtualBase
{		
	template< typename castT >explicit
	Bar( castT const& cast );
};
template< >
Bar::Bar( int const & cast )
{
	cout << "Called Bar::Bar( int )!" << endl;
}
template< typename T >
struct Hello : public VIRTUAL VirtualBase
{
	Hello( int i );
};
template< >
Hello< char >::Hello( int i )
{
	cout << "Called Hello::Hello( int )!" << endl;
}

template< typename T >
struct Foo : public VIRTUAL VirtualBase
{		
	template< typename castT >
	Foo( castT const& cast );
	
	template< typename T1 >
	void func( T1 );
	
};
template< > template< >
Foo< char >::Foo( int const & cast )
{
	cout << "Called Foo::Foo( int )!" << endl;
}


int main()
{
	Foo< char > fooChar( 42 );
	
	Bar barChar( 42 );	
	Hello< char > helloChar( 42 );
	
	return 0;
}

compiled with:
g++ -v -save-temps main.cpp

gives the following output


Es werden eingebaute Spezifikationen verwendet.
Ziel: i386-redhat-linux
Konfiguriert mit: ../configure --prefix=/usr --mandir=/usr/share/man --infodir=/usr/share/info --enable-shared --enable-threads=posix --enable-checking=release --with-system-zlib --enable-__cxa_atexit --disable-libunwind-exceptions --enable-libgcj-multifile --enable-languages=c,c++,objc,java,f95,ada --enable-java-awt=gtk --with-java-home=/usr/lib/jvm/java-1.4.2-gcj-1.4.2.0/jre --host=i386-redhat-linux
Thread-Modell: posix
gcc-Version 4.0.2 20051125 (Red Hat 4.0.2-8)
 /usr/libexec/gcc/i386-redhat-linux/4.0.2/cc1plus -E -quiet -v -D_GNU_SOURCE main.cpp -fpch-preprocess -o main.ii
nicht vorhandenes Verzeichnis »/usr/lib/gcc/i386-redhat-linux/4.0.2/../../../../i386-redhat-linux/include« wird ignoriert
#include "..." - Suche beginnt hier:
#include <...> - Suche beginnt hier:
 /usr/lib/gcc/i386-redhat-linux/4.0.2/../../../../include/c++/4.0.2
 /usr/lib/gcc/i386-redhat-linux/4.0.2/../../../../include/c++/4.0.2/i386-redhat-linux
 /usr/lib/gcc/i386-redhat-linux/4.0.2/../../../../include/c++/4.0.2/backward
 /usr/local/include
 /usr/lib/gcc/i386-redhat-linux/4.0.2/include
 /usr/include
Ende der Suchliste.
 /usr/libexec/gcc/i386-redhat-linux/4.0.2/cc1plus -fpreprocessed main.ii -quiet -dumpbase main.cpp -auxbase main -version -o main.s
GNU C++ version 4.0.2 20051125 (Red Hat 4.0.2-8) (i386-redhat-linux)
	compiled by GNU C version 4.0.2 20051125 (Red Hat 4.0.2-8).
GGC-Heuristik: --param ggc-min-expand=99 --param ggc-min-heapsize=129465
main.cpp:18: Fehler: Template-ID »Bar<>« für »Bar::Bar(const int&)« passt zu keiner Templatedeklaration
main.cpp:18: Fehler: ungültige Funktionsdeklaration
main.cpp:55: Fehler: Template-ID »Foo<>« für »Foo<char>::Foo(const int&)« passt zu keiner Templatedeklaration
main.cpp:55: Fehler: ungültige Funktionsdeklaration

========================================

The problem can be fixed, by putting the comment to the other #define at the beginning.

I reproduced this on WinXP - gcc-3.4.2, Linux FC4 with gcc-4.0.0 and 4.0.2

However MSVC 7.1 + 8.0 and Comeau accept the code.
Comment 1 Andrew Pinski 2006-04-02 16:21:53 UTC
Related to PR 9050.
Comment 2 Wolfgang Bangerth 2006-04-18 03:45:10 UTC
Confirmed, though this doesn't seem to have anything to do with PR 9050.

Here's a shorter testcase:
--------------
struct B{};

struct Bar : virtual B {               
    template <typename T> Bar( T const& cast );
};

template <> Bar::Bar( int const & cast ) {}

template <typename T>
struct Foo : virtual B {               
    template <typename T1> Foo( T1 const& cast );
};

template< > template< >
Foo< char >::Foo( int const & cast ) {}
---------------------

g/x> /home/bangerth/bin/gcc-4.1-pre/bin/c++ -c x.cc
x.cc:7: error: template-id &#8216;Bar<>&#8217; for &#8216;Bar::Bar(const int&)&#8217; does not match any template declaration
x.cc:7: error: invalid function declaration
x.cc:15: error: template-id &#8216;Foo<>&#8217; for &#8216;Foo<char>::Foo(const int&)&#8217; does not match any template declaration
x.cc:15: error: invalid function declaration

The thing that makes me think that this has nothing to do with 9050 is that
if the inheritance is made non-virtual, then the bug goes away. That's 
certainly odd behavior -- this is a bug in semantic analysis, not in the 
parser!

This used to work in 2.95, so is a regression of rejects-valid kind.

W.
Comment 3 Mark Mitchell 2006-05-25 02:34:23 UTC
Will not be fixed in 4.1.1; adjust target milestone to 4.1.2.
Comment 4 Mark Mitchell 2007-01-11 04:05:34 UTC
The problem here is that we are not skipping artificial arguments (other than the "this" pointer) when trying to match the specialization.  The additional parameters for constructors for classes with virtual bases are therefore confusing the compiler.
Comment 5 Gabriel Dos Reis 2007-02-03 16:45:18 UTC
Won't fix in GCC-4.0.x  Adjusting milestone.
Comment 6 Mark Mitchell 2007-02-11 20:15:25 UTC
Subject: Bug 26988

Author: mmitchel
Date: Sun Feb 11 20:15:13 2007
New Revision: 121822

URL: http://gcc.gnu.org/viewcvs?root=gcc&view=rev&rev=121822
Log:
	PR c++/26988
	* pt.c (determine_specialization): Use skip_artificial_parms_for.
	(fn_type_unificiation): Likewise.
	(get_bindings): Likewise.
	PR c++/26988
	* g++.dg/template/spec34.C: New test

Added:
    trunk/gcc/testsuite/g++.dg/template/spec34.C
Modified:
    trunk/gcc/cp/ChangeLog
    trunk/gcc/cp/pt.c
    trunk/gcc/testsuite/ChangeLog

Comment 7 Mark Mitchell 2007-02-11 21:41:07 UTC
Subject: Bug 26988

Author: mmitchel
Date: Sun Feb 11 21:40:56 2007
New Revision: 121826

URL: http://gcc.gnu.org/viewcvs?root=gcc&view=rev&rev=121826
Log:
	PR c++/26988
	* pt.c (determine_specialization): Use skip_artificial_parms_for.
	(fn_type_unificiation): Likewise.
	(get_bindings): Likewise.
	PR c++/26988
	* g++.dg/template/spec34.C: New test

Added:
    branches/gcc-4_2-branch/gcc/testsuite/g++.dg/template/spec34.C
Modified:
    branches/gcc-4_2-branch/gcc/cp/ChangeLog
    branches/gcc-4_2-branch/gcc/cp/pt.c
    branches/gcc-4_2-branch/gcc/testsuite/ChangeLog

Comment 8 Mark Mitchell 2007-02-11 21:41:26 UTC
Fixed in 4.2.0, 4.3.0.
Comment 9 Joseph S. Myers 2008-07-04 15:26:27 UTC
Closing 4.1 branch.