-
Notifications
You must be signed in to change notification settings - Fork 14.7k
Description
ISSUE
LLVM 21.1.0-rc1's libc++ introduces template metaprogramming changes that break compatibility with large C++ codebases and C++ binding generators, specifically around std::invoke_result_t
and std::basic_string_view
template instantiations.
EXPECTED BEHAVIOR
LLVM 21's libc++ should maintain backward compatibility with existing C++ code patterns used in major projects, or provide clear migration paths.
STEPS TO REPRODUCE
Environment:
- LLVM 21.1.0-rc1 on macOS aarch64
- Large C++ codebase (Firefox, ~10M+ lines)
- C++ binding generator (rust-bindgen)
Template Usage Patterns That Break:
// 1. Complex invoke_result_t instantiations
template<typename ResolveFunction, typename ResolveValueT>
struct Promise {
using resolve_result = std::invoke_result_t<ResolveFunction, ResolveValueT>;
};
// 2. basic_string_view in template contexts
template<typename CharT, typename Traits = std::char_traits<CharT>>
class StringProcessor {
std::basic_string_view<CharT, Traits> view_;
};
Compilation Context:
clang++ -std=c++17 -I/opt/llvm-21.1.0-rc1/include/c++/v1 test.cpp
ATTEMPTS TO RESOLVE
Analysis of Template Changes
Compared LLVM 21 vs LLVM 19 template definitions:
LLVM 19 (Working):
template<class _Fn, class... _Args>
struct invoke_result : public __invoke_result<_Fn, _Args...> {};
template<class _Fn, class... _Args>
using invoke_result_t = typename invoke_result<_Fn, _Args...>::type;
LLVM 21 (Problematic):
// More complex SFINAE and template parameter handling
template<class _Fn, class... _Args>
struct invoke_result : public __invoke_result<_Fn, _Args...> {
// Additional template metaprogramming complexity
};
Impact on Binding Generators
Binding generators (bindgen, SWIG, etc.) fail because:
- Template Parameter Extraction: Cannot resolve
_CharT
,_Traits
,_Args
in complex instantiations - SFINAE Patterns: More sophisticated SFINAE in LLVM 21 breaks simple template parsing
- Nested Template Resolution: Deeply nested template hierarchies are not properly resolved
OUTCOME AND FINDINGS
Compatibility Regression
LLVM 21 introduces template metaprogramming changes that are:
- Semantically Equivalent: Same runtime behavior as LLVM 19
- Syntactically Different: Different template instantiation patterns
- Tool-Breaking: Incompatible with existing C++ tooling ecosystem
Affected Template Types
- std::invoke_result_t - Core issue in complex template instantiations
- std::basic_string_view - Template parameter resolution problems
- std::enable_if_t patterns - SFINAE changes break some use cases
Ecosystem Impact
This affects:
- Firefox (confirmed failing at 58% build completion)
- Other large C++ projects using binding generators
- C++ tooling ecosystem (bindgen, SWIG, etc.)
REQUESTED ACTION
Immediate (LLVM 21.1.0 stable)
- Template Compatibility Audit: Review template metaprogramming changes for backward compatibility
- Binding Generator Testing: Test LLVM 21 against major binding generators (bindgen, SWIG, pybind11)
- Documentation: Document template changes that affect tooling
Long Term
- Template Stability Policy: Consider impact on C++ tooling ecosystem when making template changes
- Binding Generator Liaison: Coordinate with binding generator maintainers on template changes
- Compatibility Testing: Add major C++ projects to LLVM CI for compatibility testing
Specific Technical Review
Files needing review:
libcxx/include/type_traits
(invoke_result_t implementation)libcxx/include/string_view
(basic_string_view template patterns)- Template SFINAE patterns that changed between LLVM 19 and 21
Questions for LLVM team:
- Were the template metaprogramming changes intentional compatibility breaks?
- Is there a migration path for binding generators?
- Can template instantiation patterns be made more tooling-friendly?
Priority: This will block adoption of LLVM 21 by major C++ projects that rely on binding generators.
Note: This is not a request to revert changes, but to ensure ecosystem compatibility is considered in template metaprogramming decisions.