<table border="1" cellspacing="0" cellpadding="8">
<tr>
<th>Issue</th>
<td>
<a href=https://github.com/llvm/llvm-project/issues/106428>106428</a>
</td>
</tr>
<tr>
<th>Summary</th>
<td>
[libc++] std::invoke() substitution failure when using function object with default argument
</td>
</tr>
<tr>
<th>Labels</th>
<td>
</td>
</tr>
<tr>
<th>Assignees</th>
<td>
</td>
</tr>
<tr>
<th>Reporter</th>
<td>
tcbrindle
</td>
</tr>
</table>
<pre>
The following test program compiles with libc++17 and libstdc++, but fails with libc++18:
```cpp
#include <concepts>
#include <functional>
#include <ranges>
#include <source_location>
#define FWD(x) static_cast<decltype(x)&&>(x)
struct add_fn {
template <std::integral T>
constexpr auto operator()(T lhs, T rhs,
std::source_location loc = std::source_location::current())
const -> T
{
return lhs + rhs;
}
};
inline constexpr auto add = add_fn{};
struct fold_op {
template <typename Rng, typename Func, typename Init>
constexpr auto operator()(Rng&& rng, Func func, Init init) const
{
auto init_ = std::ranges::range_value_t<Rng>(std::move(init));
for (auto&& elem : rng) {
init_ = std::invoke(func, std::move(init_), FWD(elem));
}
return init_;
}
};
inline constexpr auto fold = fold_op{};
auto sum(std::span<int const> arr) -> int
{
return fold(arr, add, 0);
}
```
https://godbolt.org/z/h47dnM3eP
The error is:
```
<source>:27:21: error: no matching function for call to 'invoke'
27 | init_ = std::invoke(func, std::move(init_), FWD(elem));
| ^~~~~~~~~~~
<source>:38:16: note: in instantiation of function template specialization 'fold_op::operator()<std::span<const int> &, add_fn, int>' requested here
38 | return fold(arr, add, 0);
| ^
/opt/compiler-explorer/clang-18.1.0/bin/../include/c++/v1/__functional/invoke.h:27:1: note: candidate template ignored: substitution failure [with _Fn = add_fn &, _Args = <__libcpp_remove_reference_t<int &>, const int &>]
27 | invoke(_Fn&& __f, _Args&&... __args) noexcept(is_nothrow_invocable_v<_Fn, _Args...>) {
| ^
1 error generated.
Compiler returned: 1
```
Removing the `source_location` default argument from `add_fn::operator()` allows the code to compile as expected.
</pre>
<img width="1px" height="1px" alt="" src="http://email.email.llvm.org/o/eJy8Vk9v6zYM_zTKhahhy0mcHHJo0xrYYcDwUGBHQ5bpRJsieZKc9r3DPvtAW3bSNB32LgsC_6Ep8kfyJ4rCe3UwiDu2emKr54Xow9G6XZC1U6bRuKht8333ekRordb2TZkDBPQBOmcPTpxA2lOnNHp4U-EIWtWS8SfGn7IChGlI4EMTZYzvoe4DtELpzws2LH9k6TNLp-s6Hf-y66KE58pI3TcILN9LayR2wbP85d7ntjcyKGuE_kLBCXPAr1Z72zuJlbZSkJGL1qTbYKsMQvn7M-Obd8a34IMISlZS-MDyfYNSh-8dxq-Mr-mfv0zvV9Z8cL0MIJqmag2w4mkUAwAEPHVahBFSaChD-aMyAQ9OaHidYZGutMYHfO8ciD5YsB06EaxjfDP437yCPnoqwSu44SEune3exAzaSmD585cKo1D2zqEJk5vtBdAMCh5Y_gKvly-XGB2G3hlCBow_DcDyp2vF55ip4nn-MF6V0VSAm6hF0wyYx2SSn08LY7pbq5vKdl_nm6pnxAnhmzlQ2ub3sjfyg-AXo8JPlWKwSIQAN9omk9BGu2QOFNnk29HUvczF3-CAlKuPtZrYPT9XZ6F7rIib5H5g4qx9smdianRK__zGT2sdML4hdxE6ajwByx_HGLafodHvDjJlzvZP8jbFew9FNcDYx_1Frr7ANTNkEkRGjUZm7Z8mEtFjwB15cpdK43XQ9_3pOqG-E4ble2VCrGD-AsI5ytOwGZQJE56rgCJ2ckm5Jv09UZlu6XX0l3CmJnkN6BhCN5Sel4yXB9vUVofEugPj5Q_Gy-OyaMyvOf52vYh6PDpnHSj_VSeOr1N7JBLlj7ygS0ZMGNbTg7FwEkEe6biYGvFAISm0hmCB8WLiQTHHzwtgxR7-R_7cuptZtXr5e_7djTqn4ypbj8EGpLsi1vkgTFBjA7XtJfi5s_gOpRJa_Rh1GC8mhg0x3PSKq7YfKTV2VOJP_gLDVtxP3Y7vo5zxAhz-1aMP2MARHcag880c8n_m2iVTbDWflaXtAuNlPP3dA7532jp0JNPCHB6yTZIlKeNlrQzjZZIwXsbzlXSmgaA8Z4yXVXV1WpMeVTg5TuTKrrMshWlUQ5mcU6oOxjqkNIHvax9U6EfCCaV7h8BWT8OwUZXm6nCYklc9uoMf5CzfVxVNJF1XOSQ2VQ5bdGjk2DhpO0_H-B7mSkyy1fMtlWeuVqWJbbOq2tnrKEqSBKpKDO9bMBbfaa4hIvvK2HB09q0iQ1LUGqszoSzNbCNJkgHPpwb8oWJZ3NsHNMQvbJJRvo8FjHQYk5j9S2_5RnkZpsAjAluntzPBOoUGW9HrAMId-hOaAK2zJ9KNNL3H83UKguZLP9iVtkHqEpFeIDzge4fygvv6umh2ebPNt2KBu6zgy816U2Tp4rhr1_W2bjMhUS4buW7kmstiu0qxaMWqKfKF2vGUL9MN32SbLFtuE1mv8lSu1htcpVu-TtkyxZNQOtH6fKIOulDe97jL0vWSbxZa1Kj9NDu7HWk91P3Bs2WqlQ_-si6ooIcp-zLxstW9rjaMkvdY_HZEA73_0FJt_QfKMI7St2lf9E7vbo4CFY59nUh7YrwkaPH20DlLhmjvUXye8TKGeN7xfwIAAP__HM6SVw">