[libcxx-commits] [libcxx] [libc++][ranges][abi-break] Fix `movable_box` overwriting memory of data that lives in the tail padding (PR #71314)

Louis Dionne via libcxx-commits libcxx-commits at lists.llvm.org
Fri Dec 15 09:54:15 PST 2023


================
@@ -144,23 +151,47 @@ concept __doesnt_need_empty_state_for_move = movable<_Tp> || is_nothrow_move_con
 
 template <class _Tp>
 concept __doesnt_need_empty_state = __doesnt_need_empty_state_for_copy<_Tp> && __doesnt_need_empty_state_for_move<_Tp>;
+
+template <class _Tp>
+concept __can_use_no_unique_address = copyable<_Tp>;
 #  endif
 
+template <class _Tp>
+struct __movable_box_base {
+  _Tp __val_;
+
+  template <class... _Args>
+    requires is_constructible_v<_Tp, _Args&&...>
+  _LIBCPP_HIDE_FROM_ABI constexpr explicit __movable_box_base(_Args&&... __args)
+      : __val_(std::forward<_Args>(__args)...) {}
+};
+
+template <class _Tp>
+  requires __can_use_no_unique_address<_Tp>
+struct __movable_box_base<_Tp> {
+  _LIBCPP_NO_UNIQUE_ADDRESS _Tp __val_;
+
+  template <class... _Args>
+    requires is_constructible_v<_Tp, _Args&&...>
+  _LIBCPP_HIDE_FROM_ABI constexpr explicit __movable_box_base(_Args&&... __args)
+      : __val_(std::forward<_Args>(__args)...) {}
+};
+
 template <__movable_box_object _Tp>
   requires __doesnt_need_empty_state<_Tp>
-class __movable_box<_Tp> {
-  _LIBCPP_NO_UNIQUE_ADDRESS _Tp __val_;
+class __movable_box<_Tp> : private __movable_box_base<_Tp> {
----------------
ldionne wrote:

Can you make this a member with `[[no_unique_address]]` instead of a base class? This would remove the possibility of constructor inheritance messing stuff up. In that case maybe rename to `__movable_box_holder` or something.

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


More information about the libcxx-commits mailing list