https://gcc.gnu.org/bugzilla/show_bug.cgi?id=107600
--- Comment #6 from Jonathan Wakely <redi at gcc dot gnu.org> --- This regressed the following testcase: struct X; template<class T> struct default_delete { void operator()(T*) { static_assert(sizeof(T), "type is not incomplete"); } }; template<class T, class D = default_delete<T>> struct unique_ptr { ~unique_ptr() { del(ptr); } T* ptr; D del; }; constexpr bool b = __has_trivial_destructor(unique_ptr<X>); Previously this compiled without error, the compiler could tell immediately that ~unique_ptr() is not trivial. Now it seems to instantiate it, which then requires X to be complete. up.cc: In instantiation of 'void default_delete<T>::operator()(T*) [with T = X]': up.cc:12:22: required from 'unique_ptr<T, D>::~unique_ptr() [with T = X; D = default_delete<X>]' 12 | ~unique_ptr() { del(ptr); } | ~~~^~~~~ up.cc:19:58: required from here 19 | constexpr bool b = __has_trivial_destructor(unique_ptr<X>); | ^ up.cc:6:39: error: invalid application of 'sizeof' to incomplete type 'X' 6 | void operator()(T*) { static_assert(sizeof(T), "type is not incomplete"); } | ^~~~~~~~~