http://gcc.gnu.org/bugzilla/show_bug.cgi?id=51817
Bug #: 51817 Summary: [C++11] argument deduction fails when A-type parameter-type-list has additional parameters Classification: Unclassified Product: gcc Version: 4.6.0 Status: UNCONFIRMED Severity: normal Priority: P3 Component: c++ AssignedTo: unassig...@gcc.gnu.org ReportedBy: hst...@ca.ibm.com Host: powerpc64-unknown-linux-gnu Target: powerpc64-unknown-linux-gnu The behaviour of the following test case was clarified in paper N2242 for variadic templates. In the 2011 FDIS subclause 14.8.2.5 [temp.deduct.type] paragraph 10, deduction from a function type considers P/A pairs from the parameter-type-list only where the "P" function type has a parameter. Deduction is not specified to fail if there are additional parameters in the corresponding "A" function type. I use the --std=c++0x option; however, I do not believe that the C++03 wording prohibits the C++2011 behaviour. The second call to foo in main should be the same as the first (working) call. If compiled and linked with -DVERBOSE, the resulting program should print: Converting from A<void (int, char)> to A<void (int)>. foo(A<void (int)> called. Converting from A<void (int, char)> to A<void (int)>. foo(A<void (int)> called. ### Self-contained source: $ cat parmlistlen.cpp template <typename U> struct A { template <typename V> operator A<V>(); }; template <typename T> void foo(A<void (T)>); void foo(); int main() { A<void (int, char)> a; foo<int>(a); foo(a); // seems to fail in argument deduction } #ifdef VERBOSE extern "C" int printf(const char *, ...); template <typename T> struct tyStr { static const char str[]; }; template <> const char tyStr<void (int, char)>::str[] = "void (int, char)"; template <> const char tyStr<void (int)>::str[] = "void (int)"; template <typename T> void foo(A<void (T)>) { printf("foo(A<%s> called.\n", tyStr<void (T)>::str); } template <typename U> template <typename V> A<U>::operator A<V>() { printf("Converting from A<%s> to A<%s>.\n", tyStr<U>::str, tyStr<V>::str); return A<V>(); } #endif ### Compiler Invocation: $ g++-4.6.0 --std='c++0x' parmlistlen.cpp parmlistlen.cpp: In function 'int main()': parmlistlen.cpp:12:9: error: no matching function for call to 'foo(A<void(int, char)>&)' parmlistlen.cpp:12:9: note: candidates are: parmlistlen.cpp:6:28: note: template<class T> void foo(A<void(T)>) parmlistlen.cpp:7:6: note: void foo() parmlistlen.cpp:7:6: note: candidate expects 0 arguments, 1 provided ### g++ -v output: $ g++-4.6.0 -v Using built-in specs. COLLECT_GCC=g++-4.6.0 COLLECT_LTO_WRAPPER=/data/gcc/libexec/gcc/powerpc64-unknown-linux-gnu/4.6.0/lto-wrapper Target: powerpc64-unknown-linux-gnu Configured with: ./configure --prefix=/data/gcc --program-suffix=-4.6.0 --disable-libssp --disable-libgcj --enable-version-specific-runtime-libs --with-cpu=default32 --enable-secureplt --with-long-double-128 --enable-shared --enable-__cxa_atexit --enable-threads=posix --enable-languages=c,c++,fortran --with-gmp=/usr/local Thread model: posix gcc version 4.6.0 (GCC)