See https://bugs.llvm.org/show_bug.cgi?id=20855
Libc++ goes out of it's way to diagnose std::tuple constructions which are UB due to lifetime bugs caused by reference creation. For example:
// The 'const std::string&' is created *inside* the tuple constructor, and its lifetime is over before the end of the constructor call. std::tuple<int, const std::string&> t(std::make_tuple(42, "abc"));
However, we are over-aggressive and we incorrectly diagnose cases such as:
void foo(std::tuple<int const&, int const&> const&); foo(std::make_tuple(42, 42));
This patch fixes the incorrectly diagnosed cases, as well as converting the diagnostic to use the newly added Clang trait __reference_binds_to_temporary. The new trait allows us to diagnose cases we previously couldn't such as:
std::tuple<int, const std::string&> t(42, "abc");
It would be reasonable to consider is_base_of here too.