summaryrefslogtreecommitdiff
path: root/absl
diff options
context:
space:
mode:
authorGravatar Evan Brown <ezb@google.com>2022-09-20 13:12:25 -0700
committerGravatar Copybara-Service <copybara-worker@google.com>2022-09-20 13:13:13 -0700
commitd859fafe1ab9edc9c04ca262d9993be82c757881 (patch)
tree6794fb010d0f423ea6a8fb65176efb9231ad095d /absl
parent800c04f64afa48271c6eaee67da489a7ebf92757 (diff)
Change the macro ABSL_IS_TRIVIALLY_RELOCATABLE into a type trait - absl::is_trivially_relocatable - and move it from optimization.h to type_traits.h.
Example of how to change to the new type trait: ``` #include "absl/base/attributes.h" if (ABSL_IS_TRIVIALLY_RELOCATABLE(T)) { DoSomething(); } ``` to ``` #include "absl/meta/type_traits.h" if (absl::is_trivially_relocatable<T>::value) { DoSomething(); } ``` Note that optimization.h is also built in C mode so we can't put a type trait there. PiperOrigin-RevId: 475633715 Change-Id: I2bc85f3f6711d1280049fd01eb97c497d2d0d929
Diffstat (limited to 'absl')
-rw-r--r--absl/base/optimization.h24
-rw-r--r--absl/base/optimization_test.cc19
-rw-r--r--absl/meta/BUILD.bazel1
-rw-r--r--absl/meta/CMakeLists.txt1
-rw-r--r--absl/meta/type_traits.h28
-rw-r--r--absl/meta/type_traits_test.cc19
6 files changed, 49 insertions, 43 deletions
diff --git a/absl/base/optimization.h b/absl/base/optimization.h
index 57999a18..db5cc097 100644
--- a/absl/base/optimization.h
+++ b/absl/base/optimization.h
@@ -249,28 +249,4 @@
#define ABSL_INTERNAL_UNIQUE_SMALL_NAME()
#endif
-// ABSL_IS_TRIVIALLY_RELOCATABLE(type)
-// Detects whether a type is "trivially relocatable" -- meaning it can be
-// relocated without invoking the constructor/destructor, using a form of move
-// elision.
-//
-// Example:
-//
-// if constexpr (ABSL_IS_TRIVIALLY_RELOCATABLE(T)) {
-// memcpy(new_location, old_location, sizeof(T));
-// } else {
-// new(new_location) T(std::move(*old_location));
-// old_location->~T();
-// }
-//
-// Upstream documentation:
-//
-// https://clang.llvm.org/docs/LanguageExtensions.html#:~:text=__is_trivially_relocatable
-//
-#if ABSL_HAVE_BUILTIN(__is_trivially_relocatable)
-#define ABSL_IS_TRIVIALLY_RELOCATABLE(type) __is_trivially_relocatable(type)
-#else
-#define ABSL_IS_TRIVIALLY_RELOCATABLE(type) false
-#endif
-
#endif // ABSL_BASE_OPTIMIZATION_H_
diff --git a/absl/base/optimization_test.cc b/absl/base/optimization_test.cc
index 5f7a8f4c..e83369f3 100644
--- a/absl/base/optimization_test.cc
+++ b/absl/base/optimization_test.cc
@@ -15,7 +15,6 @@
#include "absl/base/optimization.h"
#include "gtest/gtest.h"
-#include "absl/base/attributes.h"
#include "absl/types/optional.h"
namespace {
@@ -127,22 +126,4 @@ TEST(PredictTest, ExplicitBoolConversion) {
if (ABSL_PREDICT_FALSE(is_false)) ADD_FAILURE();
}
-TEST(TrivallyRelocatable, Sanity) {
-#if !defined(ABSL_HAVE_ATTRIBUTE_TRIVIAL_ABI) || \
- !ABSL_HAVE_BUILTIN(__is_trivially_relocatable)
- GTEST_SKIP() << "No trivial ABI support.";
-#endif
-
- struct Trivial {};
- struct NonTrivial {
- NonTrivial(const NonTrivial&) {}
- };
- struct ABSL_ATTRIBUTE_TRIVIAL_ABI TrivialAbi {
- TrivialAbi(const TrivialAbi&) {}
- };
- EXPECT_TRUE(ABSL_IS_TRIVIALLY_RELOCATABLE(Trivial));
- EXPECT_FALSE(ABSL_IS_TRIVIALLY_RELOCATABLE(NonTrivial));
- EXPECT_TRUE(ABSL_IS_TRIVIALLY_RELOCATABLE(TrivialAbi));
-}
-
} // namespace
diff --git a/absl/meta/BUILD.bazel b/absl/meta/BUILD.bazel
index fb379251..4478ccf7 100644
--- a/absl/meta/BUILD.bazel
+++ b/absl/meta/BUILD.bazel
@@ -42,6 +42,7 @@ cc_test(
linkopts = ABSL_DEFAULT_LINKOPTS,
deps = [
":type_traits",
+ "//absl/base:core_headers",
"@com_google_googletest//:gtest_main",
],
)
diff --git a/absl/meta/CMakeLists.txt b/absl/meta/CMakeLists.txt
index 9de4bd37..f16f17bd 100644
--- a/absl/meta/CMakeLists.txt
+++ b/absl/meta/CMakeLists.txt
@@ -34,6 +34,7 @@ absl_cc_test(
COPTS
${ABSL_TEST_COPTS}
DEPS
+ absl::core_headers
absl::type_traits
GTest::gmock_main
)
diff --git a/absl/meta/type_traits.h b/absl/meta/type_traits.h
index 46b76906..6e6001fe 100644
--- a/absl/meta/type_traits.h
+++ b/absl/meta/type_traits.h
@@ -813,6 +813,34 @@ using swap_internal::Swap;
using swap_internal::StdSwapIsUnconstrained;
} // namespace type_traits_internal
+
+// absl::is_trivially_relocatable<T>
+// Detects whether a type is "trivially relocatable" -- meaning it can be
+// relocated without invoking the constructor/destructor, using a form of move
+// elision.
+//
+// Example:
+//
+// if constexpr (absl::is_trivially_relocatable<T>::value) {
+// memcpy(new_location, old_location, sizeof(T));
+// } else {
+// new(new_location) T(std::move(*old_location));
+// old_location->~T();
+// }
+//
+// Upstream documentation:
+//
+// https://clang.llvm.org/docs/LanguageExtensions.html#:~:text=__is_trivially_relocatable
+//
+#if ABSL_HAVE_BUILTIN(__is_trivially_relocatable)
+template <class T>
+struct is_trivially_relocatable
+ : std::integral_constant<bool, __is_trivially_relocatable(T)> {};
+#else
+template <class T>
+struct is_trivially_relocatable : std::integral_constant<bool, false> {};
+#endif
+
ABSL_NAMESPACE_END
} // namespace absl
diff --git a/absl/meta/type_traits_test.cc b/absl/meta/type_traits_test.cc
index fe96554d..d08d9ad9 100644
--- a/absl/meta/type_traits_test.cc
+++ b/absl/meta/type_traits_test.cc
@@ -21,6 +21,7 @@
#include <vector>
#include "gtest/gtest.h"
+#include "absl/base/attributes.h"
namespace {
@@ -1394,4 +1395,22 @@ TEST(TypeTraitsTest, IsNothrowSwappable) {
EXPECT_TRUE(IsNothrowSwappable<adl_namespace::SpecialNoexceptSwap>::value);
}
+TEST(TrivallyRelocatable, Sanity) {
+#if !defined(ABSL_HAVE_ATTRIBUTE_TRIVIAL_ABI) || \
+ !ABSL_HAVE_BUILTIN(__is_trivially_relocatable)
+ GTEST_SKIP() << "No trivial ABI support.";
+#endif
+
+ struct Trivial {};
+ struct NonTrivial {
+ NonTrivial(const NonTrivial&) {} // NOLINT
+ };
+ struct ABSL_ATTRIBUTE_TRIVIAL_ABI TrivialAbi {
+ TrivialAbi(const TrivialAbi&) {} // NOLINT
+ };
+ EXPECT_TRUE(absl::is_trivially_relocatable<Trivial>::value);
+ EXPECT_FALSE(absl::is_trivially_relocatable<NonTrivial>::value);
+ EXPECT_TRUE(absl::is_trivially_relocatable<TrivialAbi>::value);
+}
+
} // namespace