Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Recursive template instantiation exceeded error in dtor, but not in ctor. Why?

Tags:

c++

templates

Try clang++ and g++, same result for both.
fatal error: recursive template instantiation exceeded maximum depth

template<class T>
struct Bar {
  ~Bar() {
    if (ptr) { delete ptr; }
  }
  Bar<Bar<T>> * ptr{nullptr};
};

int main() { Bar<void> obj; }

But ctor version compiles without error:

template<class T>
struct Bar {
  Bar() {
    if (ptr) { delete ptr; }
  }
  Bar<Bar<T>> * ptr{nullptr};
};

int main() { Bar<void> obj; }

What's the problem with dtor version?

like image 787
amordo Avatar asked Aug 07 '21 12:08

amordo


1 Answers

What's the problem with dtor version?

Think about what a declaration like Bar<void> obj; means.

That object needs have its destructor called when main returns. So the destructor ~Bar<void> will be instantiated.

What does the instantiated destructor contain? A delete expression. You may reason that it's under a nullity check, and so will never be executed, but that doesn't matter. C++ code is resolved statically, and must be correct even when a compiler can eliminate dead code.

That delete expression will need to invoke the destructor of Bar<Bar<void>>, and it must therefore be instantiated... Rinse and repeat.

On the other hand, in the constructor version, you have a trivial destructor. It does nothing, and certainly doesn't needs to instantiate any other type. So it compiles just fine when the constructor has to instantiate it.

like image 58
StoryTeller - Unslander Monica Avatar answered Oct 19 '22 10:10

StoryTeller - Unslander Monica