[libcxx-commits] [libcxx] [libc++][format] LWG4061: Should `std::basic_format_context` be default-constructible/copyable/movable? (PR #97251)

via libcxx-commits libcxx-commits at lists.llvm.org
Sun Jun 30 19:46:05 PDT 2024


llvmbot wrote:


<!--LLVM PR SUMMARY COMMENT-->

@llvm/pr-subscribers-libcxx

Author: A. Jiang (frederick-vs-ja)

<details>
<summary>Changes</summary>

See [LWG4061](https://cplusplus.github.io/LWG/issue4061) and [P3341R0](https://wg21.link/p3341r0). Effectively reverts commit 36ce0c3b1e581ca310ae7d0cbc6af002cc5d0251.

`libcxx/test/std/utilities/format/format.functions/bug_81590.compile.pass.cpp` has a `format` function that unexpectedly passes the `basic_format_context` by value, which is made ill-formed by LWG4061. This PR changes the function to pass the context by reference.

---
Full diff: https://github.com/llvm/llvm-project/pull/97251.diff


3 Files Affected:

- (modified) libcxx/include/__format/format_context.h (+3) 
- (modified) libcxx/test/std/utilities/format/format.formatter/format.context/format.context/ctor.pass.cpp (+14-6) 
- (modified) libcxx/test/std/utilities/format/format.functions/bug_81590.compile.pass.cpp (+1-1) 


``````````diff
diff --git a/libcxx/include/__format/format_context.h b/libcxx/include/__format/format_context.h
index 087d4bf289b87..20c07559eae44 100644
--- a/libcxx/include/__format/format_context.h
+++ b/libcxx/include/__format/format_context.h
@@ -131,6 +131,9 @@ class
   _LIBCPP_HIDE_FROM_ABI explicit basic_format_context(_OutIt __out_it, basic_format_args<basic_format_context> __args)
       : __out_it_(std::move(__out_it)), __args_(__args) {}
 #  endif
+
+  basic_format_context(const basic_format_context&)            = delete;
+  basic_format_context& operator=(const basic_format_context&) = delete;
 };
 
 // A specialization for __retarget_buffer
diff --git a/libcxx/test/std/utilities/format/format.formatter/format.context/format.context/ctor.pass.cpp b/libcxx/test/std/utilities/format/format.formatter/format.context/format.context/ctor.pass.cpp
index 40720105060f0..83ece7da73ad3 100644
--- a/libcxx/test/std/utilities/format/format.formatter/format.context/format.context/ctor.pass.cpp
+++ b/libcxx/test/std/utilities/format/format.formatter/format.context/format.context/ctor.pass.cpp
@@ -112,19 +112,27 @@ void test() {
 #endif
 }
 
+// The default constructor is suppressed by the deleted copy operations.
+// The move operations are implicitly deleted due to the deleted copy operations.
+
 // std::back_insert_iterator<std::string>, copyable
-static_assert(std::is_copy_constructible_v<std::basic_format_context<std::back_insert_iterator<std::string>, char>>);
-static_assert(std::is_copy_assignable_v<std::basic_format_context<std::back_insert_iterator<std::string>, char>>);
+static_assert(
+    !std::is_default_constructible_v<std::basic_format_context<std::back_insert_iterator<std::string>, char>>);
+
+static_assert(!std::is_copy_constructible_v<std::basic_format_context<std::back_insert_iterator<std::string>, char>>);
+static_assert(!std::is_copy_assignable_v<std::basic_format_context<std::back_insert_iterator<std::string>, char>>);
 
-static_assert(std::is_move_constructible_v<std::basic_format_context<std::back_insert_iterator<std::string>, char>>);
-static_assert(std::is_move_assignable_v<std::basic_format_context<std::back_insert_iterator<std::string>, char>>);
+static_assert(!std::is_move_constructible_v<std::basic_format_context<std::back_insert_iterator<std::string>, char>>);
+static_assert(!std::is_move_assignable_v<std::basic_format_context<std::back_insert_iterator<std::string>, char>>);
 
 // cpp20_output_iterator, move only
+static_assert(!std::is_default_constructible_v<std::basic_format_context<cpp20_output_iterator<int*>, char>>);
+
 static_assert(!std::is_copy_constructible_v<std::basic_format_context<cpp20_output_iterator<int*>, char>>);
 static_assert(!std::is_copy_assignable_v<std::basic_format_context<cpp20_output_iterator<int*>, char>>);
 
-static_assert(std::is_move_constructible_v<std::basic_format_context<cpp20_output_iterator<int*>, char>>);
-static_assert(std::is_move_assignable_v<std::basic_format_context<cpp20_output_iterator<int*>, char>>);
+static_assert(!std::is_move_constructible_v<std::basic_format_context<cpp20_output_iterator<int*>, char>>);
+static_assert(!std::is_move_assignable_v<std::basic_format_context<cpp20_output_iterator<int*>, char>>);
 
 int main(int, char**) {
   test<std::back_insert_iterator<std::basic_string<char>>, char>();
diff --git a/libcxx/test/std/utilities/format/format.functions/bug_81590.compile.pass.cpp b/libcxx/test/std/utilities/format/format.functions/bug_81590.compile.pass.cpp
index 127f6546ccbe7..5f248f88582d0 100644
--- a/libcxx/test/std/utilities/format/format.functions/bug_81590.compile.pass.cpp
+++ b/libcxx/test/std/utilities/format/format.functions/bug_81590.compile.pass.cpp
@@ -25,7 +25,7 @@ struct X : std::variant<X*> {
 
 template <>
 struct std::formatter<X, char> : std::formatter<std::string, char> {
-  static constexpr auto format(const X& x, auto ctx) {
+  static constexpr auto format(const X& x, auto& ctx) {
     if (!x.p)
       return ctx.out();
     auto m = [&](const X* t) { return std::format_to(ctx.out(), "{}", *t); };

``````````

</details>


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


More information about the libcxx-commits mailing list