[ADT] Allow structured bindings on PointerIntPair
authorBenjamin Kramer <benny.kra@googlemail.com>
Sun, 4 Dec 2022 15:10:00 +0000 (16:10 +0100)
committerBenjamin Kramer <benny.kra@googlemail.com>
Sun, 4 Dec 2022 15:16:04 +0000 (16:16 +0100)
Apart from simplifying code, this has the advantage of making the
interface between std::pair and PointerIntPair more uniform.

llvm/include/llvm/ADT/PointerIntPair.h
llvm/unittests/ADT/PointerIntPairTest.cpp

index 1192850..9278ccd 100644 (file)
@@ -227,6 +227,32 @@ struct PointerLikeTypeTraits<
       PtrTraits::NumLowBitsAvailable - IntBits;
 };
 
+// Allow structured bindings on PointerIntPair.
+template <std::size_t I, typename PointerTy, unsigned IntBits, typename IntType,
+          typename PtrTraits, typename Info>
+decltype(auto)
+get(const PointerIntPair<PointerTy, IntBits, IntType, PtrTraits, Info> &Pair) {
+  static_assert(I < 2);
+  if constexpr (I == 0)
+    return Pair.getPointer();
+  else
+    return Pair.getInt();
+}
+
 } // end namespace llvm
 
+namespace std {
+template <typename PointerTy, unsigned IntBits, typename IntType,
+          typename PtrTraits, typename Info>
+struct tuple_size<
+    llvm::PointerIntPair<PointerTy, IntBits, IntType, PtrTraits, Info>>
+    : std::integral_constant<std::size_t, 2> {};
+
+template <std::size_t I, typename PointerTy, unsigned IntBits, typename IntType,
+          typename PtrTraits, typename Info>
+struct tuple_element<
+    I, llvm::PointerIntPair<PointerTy, IntBits, IntType, PtrTraits, Info>>
+    : std::conditional<I == 0, PointerTy, IntType> {};
+} // namespace std
+
 #endif // LLVM_ADT_POINTERINTPAIR_H
index 9e5e0ee..b279005 100644 (file)
@@ -62,6 +62,10 @@ TEST(PointerIntPairTest, GetSet) {
   EXPECT_EQ(&s, Pair2.getPointer());
   EXPECT_EQ(E::Case3, Pair2.getInt());
 
+  auto [Pointer2, Int2] = Pair2;
+  EXPECT_EQ(Pair2.getPointer(), Pointer2);
+  EXPECT_EQ(Pair2.getInt(), Int2);
+
   static_assert(std::is_trivially_copyable_v<PointerIntPair<S *, 2, E>>,
                 "trivially copyable");
 }