alexfh wrote: The reduced test case: https://gcc.godbolt.org/z/KhebWaGsc
``` #include <variant> #include <vector> namespace testing { template <typename T> struct Matcher { Matcher(int); Matcher(T); }; template <typename T, typename M> Matcher<T> SafeMatcherCast(M polymorphic_matcher_or_value) { return polymorphic_matcher_or_value; } namespace internal { template <typename MatcherTuple> struct ElementsAreMatcher { template <typename Container> operator Matcher<Container>() { typedef typename std::remove_const< typename std::remove_reference<Container>::type>::type ::value_type Element; typedef std::vector<Matcher<Element>> MatcherVec; MatcherVec matchers; matchers.reserve(std::tuple_size<MatcherTuple>::value); return 0; } }; } // namespace internal } // namespace testing template <typename> struct Nullable { template <typename V> Nullable(V); }; void f(testing::internal::ElementsAreMatcher<std::tuple<>> m) { testing::SafeMatcherCast<std::vector<std::variant<Nullable<int>>>>(m); } ``` ``` In file included from <source>:1: /opt/compiler-explorer/clang-trunk-20250723/bin/../include/c++/v1/variant:1186:37: fatal error: recursive template instantiation exceeded maximum depth of 1024 1186 | enable_if_t<!is_same_v<__remove_cvref_t<_Arg>, variant>, int> = 0, | ^ /opt/compiler-explorer/clang-trunk-20250723/bin/../include/c++/v1/variant:1192:35: note: while substituting prior template arguments into non-type template parameter [with _Arg = testing::Matcher<std::variant<Nullable<int>>>] 1192 | _LIBCPP_HIDE_FROM_ABI constexpr variant(_Arg&& __arg) noexcept(is_nothrow_constructible_v<_Tp, _Arg>) | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 1193 | : __impl_(in_place_index<_Ip>, std::forward<_Arg>(__arg)) {} | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ /opt/compiler-explorer/clang-trunk-20250723/bin/../include/c++/v1/__type_traits/invoke.h:71:69: note: while substituting deduced template arguments into function template 'variant' [with _Arg = testing::Matcher<std::variant<Nullable<int>>>, $1 = (no value), $2 = (no value), $3 = (no value), _Tp = (no value), _Ip = (no value), $6 = (no value)] 71 | using __invoke_result_t _LIBCPP_NODEBUG = decltype(__builtin_invoke(std::declval<_Args>()...)); | ^ /opt/compiler-explorer/clang-trunk-20250723/bin/../include/c++/v1/__type_traits/invoke.h:387:1: note: in instantiation of template type alias '__invoke_result_t' requested here 387 | using invoke_result_t = __invoke_result_t<_Fn, _Args...>; | ^ /opt/compiler-explorer/clang-trunk-20250723/bin/../include/c++/v1/variant:1140:1: note: in instantiation of template type alias 'invoke_result_t' requested here 1140 | using __best_match_t _LIBCPP_NODEBUG = typename invoke_result_t<_MakeOverloads<_Types...>, _Tp, _Tp>::type; | ^ /opt/compiler-explorer/clang-trunk-20250723/bin/../include/c++/v1/variant:1189:45: note: in instantiation of template type alias '__best_match_t' requested here 1189 | class _Tp = __variant_detail::__best_match_t<_Arg, _Types...>, | ^ /opt/compiler-explorer/clang-trunk-20250723/bin/../include/c++/v1/variant:1192:35: note: (skipping 2539 contexts in backtrace; use -ftemplate-backtrace-limit=0 to see all) 1192 | _LIBCPP_HIDE_FROM_ABI constexpr variant(_Arg&& __arg) noexcept(is_nothrow_constructible_v<_Tp, _Arg>) | ^ /opt/compiler-explorer/clang-trunk-20250723/bin/../include/c++/v1/__vector/vector.h:845:8: note: in instantiation of function template specialization 'std::__uninitialized_allocator_relocate<std::allocator<testing::Matcher<std::variant<Nullable<int>>>>, testing::Matcher<std::variant<Nullable<int>>> *>' requested here 845 | std::__uninitialized_allocator_relocate( | ^ /opt/compiler-explorer/clang-trunk-20250723/bin/../include/c++/v1/__vector/vector.h:1101:5: note: in instantiation of member function 'std::vector<testing::Matcher<std::variant<Nullable<int>>>>::__swap_out_circular_buffer' requested here 1101 | __swap_out_circular_buffer(__v); | ^ <source>:20:14: note: in instantiation of member function 'std::vector<testing::Matcher<std::variant<Nullable<int>>>>::reserve' requested here 20 | matchers.reserve(std::tuple_size<MatcherTuple>::value); | ^ <source>:10:10: note: in instantiation of function template specialization 'testing::internal::ElementsAreMatcher<std::tuple<>>::operator Matcher<std::vector<std::variant<Nullable<int>>>>' requested here 10 | return polymorphic_matcher_or_value; | ^ <source>:30:12: note: in instantiation of function template specialization 'testing::SafeMatcherCast<std::vector<std::variant<Nullable<int>>>, testing::internal::ElementsAreMatcher<std::tuple<>>>' requested here 30 | testing::SafeMatcherCast<std::vector<std::variant<Nullable<int>>>>(m); | ^ ``` @philnik777 PTAL https://github.com/llvm/llvm-project/pull/116709 _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits