https://gcc.gnu.org/bugzilla/show_bug.cgi?id=89231

            Bug ID: 89231
           Summary: Ambiguous template instantiation for variadic nested
                    class
           Product: gcc
           Version: 8.2.1
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: c++
          Assignee: unassigned at gcc dot gnu.org
          Reporter: andreas.stoeckel at googlemail dot com
  Target Milestone: ---

The following program causes an "ambiguous template instantiation" error in G++
g++ (GCC) 8.2.1 20181215, although one of the class specialisations should be
preferred.

----

template<typename... Ps>
struct A {
        template <int... Ns>
        struct Collect {};

        template <int C, int I = 0, typename S = Collect<>>
        struct Seq;

        template <int C, int I, int... N>
        struct Seq<C, I, Collect<N...>> : Seq<C - 1, I + 1, Collect<N..., I>>
{};

        template <int I, int... N>
        struct Seq<0, I, Collect<N...>> : Collect<N...> {};
};

int main() {
        A<>::Seq<4> test;
}

---

Error:

test.cpp: In instantiation of ‘struct A<>::Seq<1, 3, A<>::Collect<0, 1, 2> >’:
test.cpp:10:9:   recursively required from ‘struct A<>::Seq<3, 1,
A<>::Collect<0> >’
test.cpp:10:9:   required from ‘struct A<>::Seq<4>’
test.cpp:17:14:   required from here
test.cpp:10:9: error: ambiguous template instantiation for ‘struct A<>::Seq<0,
4, A<>::Collect<0, 1, 2, 3> >’
  struct Seq<C, I, Collect<N...>> : Seq<C - 1, I + 1, Collect<N..., I>> {};
         ^~~~~~~~~~~~~~~~~~~~~~~~
test.cpp:10:9: note: candidates are: ‘template<class ... Ps> template<int C,
int I, int ...N> struct A<Ps>::Seq<C, I, A<Ps>::Collect<N ...> > [with int C =
0; int I = 4; int ...N = {0, 1, 2, 3}; Ps = {}]’
test.cpp:13:9: note:                 ‘template<class ... Ps> template<int I,
int ...N> struct A<Ps>::Seq<0, I, A<Ps>::Collect<N ...> > [with int I = 4; int
...N = {0, 1, 2, 3}; Ps = {}]’
  struct Seq<0, I, Collect<N...>> : Collect<N...> {};
         ^~~~~~~~~~~~~~~~~~~~~~~~
test.cpp:10:9: error: invalid use of incomplete type ‘struct A<>::Seq<0, 4,
A<>::Collect<0, 1, 2, 3> >’
  struct Seq<C, I, Collect<N...>> : Seq<C - 1, I + 1, Collect<N..., I>> {};
         ^~~~~~~~~~~~~~~~~~~~~~~~
test.cpp:7:9: note: declaration of ‘struct A<>::Seq<0, 4, A<>::Collect<0, 1, 2,
3> >’
  struct Seq;

---

Note: this code compiles fine with clang++. It also compiles fine as long as
"struct A" is not a template.

Reply via email to