[libcxx-commits] [libcxx] [libc++][C++26] P2562R1: `constexpr` Stable Sorting (PR #110320)

A. Jiang via libcxx-commits libcxx-commits at lists.llvm.org
Sat Oct 12 05:37:14 PDT 2024


================
@@ -34,6 +34,26 @@ _LIBCPP_PUSH_MACROS
 
 _LIBCPP_BEGIN_NAMESPACE_STD
 
+// Workaround for "constexpr placement new" bug in gcc (fixed in 14.2).
+// See https://github.com/llvm/llvm-project/pull/110320#discussion_r1788557715.
+#define __STABLE_SORT_NEW_IMPL(__placement_arg, __type, __new_initializer_func, __new_initializer_arg)                 \
+  do {                                                                                                                 \
+    ::new ((void*)__placement_arg) __type(__new_initializer_func(__new_initializer_arg));                              \
+  } while (0)
+#if !defined(__clang__) && defined(__GNUC__) && (__GNUC__ * 10000 + __GNUC_MINOR__ * 100 <= 140100)
+#  define __STABLE_SORT_NEW(__placement_arg, __type, __new_initializer_func, __new_initializer_arg)                    \
+    do {                                                                                                               \
+      [__placement_arg, &__new_initializer_arg] {                                                                      \
+        __STABLE_SORT_NEW_IMPL(__placement_arg, __type, __new_initializer_func, __new_initializer_arg);                \
+      }();                                                                                                             \
+    } while (0)
+#else
+#  define __STABLE_SORT_NEW(__placement_arg, __type, __new_initializer_func, __new_initializer_arg)                    \
+    do {                                                                                                               \
+      __STABLE_SORT_NEW_IMPL(__placement_arg, __type, __new_initializer_func, __new_initializer_arg);                  \
+    } while (0)
+#endif
----------------
frederick-vs-ja wrote:

It might be better to use the name `_LIBCPP_MOVING_PLACEMENT_NEW` as the workaround (if necessary) will be used by multiple headers.

Also it seems that removing the `do { } while (0)` wrapper works.

```suggestion
#if _LIBCPP_STD_VER >= 26 && !defined(__clang__) && defined(__GNUC__) &&                                               \
    (__GNUC__ * 10000 + __GNUC_MINOR__ * 100 <= 140100)
#  define _LIBCPP_MOVING_PLACEMENT_NEW(__ptr, __type, __move_func, __iter)                                             \
  [__ptr, &__iter] { ::new ((void*)__ptr) __type(__move_func(__iter)); }()
#else
#  define _LIBCPP_MOVING_PLACEMENT_NEW(__ptr, __type, __move_func, __iter)                                             \
  ::new ((void*)__ptr) __type(__move_func(__iter))
#endif
```

https://github.com/llvm/llvm-project/pull/110320


More information about the libcxx-commits mailing list