[Bug c++/90679] New: Template specialization with const: “ambiguous template instantiation” error
nikolaus+gcc@nikolaus-demmel.de
gcc-bugzilla@gcc.gnu.org
Thu May 30 12:21:00 GMT 2019
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=90679
Bug ID: 90679
Summary: Template specialization with const: “ambiguous
template instantiation” error
Product: gcc
Version: 9.1.0
Status: UNCONFIRMED
Severity: normal
Priority: P3
Component: c++
Assignee: unassigned at gcc dot gnu.org
Reporter: nikolaus+gcc@nikolaus-demmel.de
Target Milestone: ---
The below repro-example should compile (IMHO), but it fails with "ambiguous
template instantiation". Same on gcc 7,8,9,trunk according to
https://godbolt.org/z/69Bomq, so probably not a regression.
clang compiles this just fine. See also
https://stackoverflow.com/q/56333067/1813258
Specializing traits<Map<C>> and traits<Map<const C>> works fine, as does
traits<first_type<C>> and traits<first_type<const C>>, so it seems to be this
combination.
In my real code `first_type<C>` has some additional template parameters for
SFINAE.
$ g++-9 -Wall -Wextra foobar.cpp
foobar.cpp: In function 'int main()':
foobar.cpp:36:38: error: ambiguous template instantiation for 'struct
traits<Map<const Foo> >'
36 | std::cout << traits<Map<const Foo>>::N << std::endl;
| ^~
foobar.cpp:24:8: note: candidates are: 'template<class C> struct
traits<Map<first_type<C> > > [with C = const Foo]'
24 | struct traits<Map<first_type<C>>> {
| ^~~~~~~~~~~~~~~~~~~~~~~~~~
foobar.cpp:30:8: note: 'template<class C> struct
traits<Map<first_type<const C> > > [with C = Foo]'
30 | struct traits<Map<first_type<const C>>> {
| ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
foobar.cpp:36:40: error: incomplete type 'traits<Map<const Foo> >' used in
nested name specifier
36 | std::cout << traits<Map<const Foo>>::N << std::endl;
| ^
$ g++-9 -v
Using built-in specs.
COLLECT_GCC=g++-9
COLLECT_LTO_WRAPPER=/usr/local/Cellar/gcc/9.1.0/libexec/gcc/x86_64-apple-darwin16/9.1.0/lto-wrapper
Target: x86_64-apple-darwin16
Configured with: ../configure --build=x86_64-apple-darwin16
--prefix=/usr/local/Cellar/gcc/9.1.0
--libdir=/usr/local/Cellar/gcc/9.1.0/lib/gcc/9 --disable-nls
--enable-checking=release --enable-languages=c,c++,objc,obj-c++,fortran
--program-suffix=-9 --with-gmp=/usr/local/opt/gmp
--with-mpfr=/usr/local/opt/mpfr --with-mpc=/usr/local/opt/libmpc
--with-isl=/usr/local/opt/isl --with-system-zlib --with-pkgversion='Homebrew
GCC 9.1.0' --with-bugurl=https://github.com/Homebrew/homebrew-core/issues
Thread model: posix
gcc version 9.1.0 (Homebrew GCC 9.1.0)
$ cat foobar.cpp
#include <iostream>
#include <type_traits>
class Foo {};
template <class T, class...>
using first_type = T;
template <class C>
class Map {};
template <class C>
struct traits {};
//#define FIX_GCC
#ifdef FIX_GCC
template <typename C>
struct traits<Map<first_type<C, std::enable_if_t<!std::is_const_v<C>>>>> {
static constexpr int N = 2;
};
#else
template <typename C>
struct traits<Map<first_type<C>>> {
static constexpr int N = 2;
};
#endif
template <typename C>
struct traits<Map<first_type<const C>>> {
static constexpr int N = 3;
};
int main() {
std::cout << traits<Map<Foo>>::N << std::endl;
std::cout << traits<Map<const Foo>>::N << std::endl;
return 0;
}
More information about the Gcc-bugs
mailing list