Skip to content

[libc++] Resolve LWG4439 and LWG4300#174257

Merged
frederick-vs-ja merged 4 commits into
llvm:mainfrom
smallp-o-p:LWG4439
Jan 3, 2026
Merged

[libc++] Resolve LWG4439 and LWG4300#174257
frederick-vs-ja merged 4 commits into
llvm:mainfrom
smallp-o-p:LWG4439

Conversation

@smallp-o-p

@smallp-o-p smallp-o-p commented Jan 3, 2026

Copy link
Copy Markdown
Contributor

Resolves #171340 implemented in #155202

Resolves #171402 implemented in #155202

  • Add swap test for optional<T&> to ensure an ADL-found swap isn't selected.
  • Drive-by: Update documentation for LWG4300 since it's already completed

@smallp-o-p smallp-o-p requested a review from a team as a code owner January 3, 2026 01:01
@llvmbot llvmbot added the libc++ libc++ C++ Standard Library. Not GNU libstdc++. Not libc++abi. label Jan 3, 2026
@llvmbot

llvmbot commented Jan 3, 2026

Copy link
Copy Markdown
Member

@llvm/pr-subscribers-libcxx

Author: William Tran-Viet (smallp-o-p)

Changes

Resolves #171340, #171402

  • Add swap test for optional&lt;T&amp;&gt; to ensure an ADL-found swap isn't selected.
  • Drive-by: Update documentation for LWG4300 since it's already completed

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

2 Files Affected:

  • (modified) libcxx/docs/Status/Cxx2cIssues.csv (+2-2)
  • (modified) libcxx/test/std/utilities/optional/optional.specalg/swap.pass.cpp (+21)
diff --git a/libcxx/docs/Status/Cxx2cIssues.csv b/libcxx/docs/Status/Cxx2cIssues.csv
index 8d312cd688daa..651b8c891ec00 100644
--- a/libcxx/docs/Status/Cxx2cIssues.csv
+++ b/libcxx/docs/Status/Cxx2cIssues.csv
@@ -179,7 +179,7 @@
 "`LWG4294 <https://wg21.link/LWG4294>`__","``bitset(const CharT*)`` constructor needs to be constrained","2025-11 (Kona)","","","`#171336 <https://github.com/llvm/llvm-project/issues/171336>`__",""
 "`LWG4297 <https://wg21.link/LWG4297>`__","Missing ``permutable`` constraint for iterator overloads in Parallel Range Algorithms","2025-11 (Kona)","","","`#171338 <https://github.com/llvm/llvm-project/issues/171338>`__",""
 "`LWG4299 <https://wg21.link/LWG4299>`__","Missing *Mandates:* part in ``optional<T&>::transform``","2025-11 (Kona)","","","`#171339 <https://github.com/llvm/llvm-project/issues/171339>`__",""
-"`LWG4300 <https://wg21.link/LWG4300>`__","Missing *Returns:* element in ``optional<T&>::emplace``","2025-11 (Kona)","","","`#171340 <https://github.com/llvm/llvm-project/issues/171340>`__",""
+"`LWG4300 <https://wg21.link/LWG4300>`__","Missing *Returns:* element in ``optional<T&>::emplace``","2025-11 (Kona)","|Complete|","22","`#171340 <https://github.com/llvm/llvm-project/issues/171340>`__",""
 "`LWG4301 <https://wg21.link/LWG4301>`__","``condition_variable{_any}::wait_{for, until}`` should take timeout by value","2025-11 (Kona)","","","`#171341 <https://github.com/llvm/llvm-project/issues/171341>`__",""
 "`LWG4302 <https://wg21.link/LWG4302>`__","Problematic ``vector_sum_of_squares`` wording","2025-11 (Kona)","","","`#171342 <https://github.com/llvm/llvm-project/issues/171342>`__",""
 "`LWG4304 <https://wg21.link/LWG4304>`__","``std::optional<NonReturnable&>`` is ill-formed due to ``value_or``","2025-11 (Kona)","","","`#171343 <https://github.com/llvm/llvm-project/issues/171343>`__",""
@@ -237,7 +237,7 @@
 "`LWG4434 <https://wg21.link/LWG4434>`__","``meta::is_accessible`` does not need to consider incomplete *D*","2025-11 (Kona)","","","`#171399 <https://github.com/llvm/llvm-project/issues/171399>`__",""
 "`LWG4435 <https://wg21.link/LWG4435>`__","``meta::has_identifier`` doesn't handle all types","2025-11 (Kona)","","","`#171400 <https://github.com/llvm/llvm-project/issues/171400>`__",""
 "`LWG4438 <https://wg21.link/LWG4438>`__","Bad expression in [exec.when.all]","2025-11 (Kona)","","","`#171401 <https://github.com/llvm/llvm-project/issues/171401>`__",""
-"`LWG4439 <https://wg21.link/LWG4439>`__","``std::optional<T&>::swap`` possibly selects ADL-found ``swap``","2025-11 (Kona)","","","`#171402 <https://github.com/llvm/llvm-project/issues/171402>`__",""
+"`LWG4439 <https://wg21.link/LWG4439>`__","``std::optional<T&>::swap`` possibly selects ADL-found ``swap``","2025-11 (Kona)","|Complete|","22","`#171402 <https://github.com/llvm/llvm-project/issues/171402>`__",""
 "`LWG4440 <https://wg21.link/LWG4440>`__","Forward declarations of entities need also in entries","2025-11 (Kona)","","","`#171403 <https://github.com/llvm/llvm-project/issues/171403>`__",""
 "`LWG4441 <https://wg21.link/LWG4441>`__","``ranges::rotate`` do not handle sized-but-not-sized-sentinel ranges correctly","2025-11 (Kona)","","","`#171404 <https://github.com/llvm/llvm-project/issues/171404>`__",""
 "`LWG4442 <https://wg21.link/LWG4442>`__","Clarify ``expr`` and ``fn`` for ``meta::reflect_object`` and ``meta::reflect_function``","2025-11 (Kona)","","","`#171405 <https://github.com/llvm/llvm-project/issues/171405>`__",""
diff --git a/libcxx/test/std/utilities/optional/optional.specalg/swap.pass.cpp b/libcxx/test/std/utilities/optional/optional.specalg/swap.pass.cpp
index c757120a1c146..0d84c6026f12e 100644
--- a/libcxx/test/std/utilities/optional/optional.specalg/swap.pass.cpp
+++ b/libcxx/test/std/utilities/optional/optional.specalg/swap.pass.cpp
@@ -175,6 +175,26 @@ constexpr bool test_swap_ref() {
   }
   return true;
 }
+
+struct ADLSwap {
+  static inline bool called_adl_swap{false};
+
+  friend void swap(ADLSwap&, ADLSwap&) noexcept { called_adl_swap = true; }
+};
+
+// LWG4439: Verify that an ADL-found swap is not selected when calling optional<T&>::swap()
+void test_ref_swap_adl() {
+  ADLSwap t1{};
+  ADLSwap t2{};
+
+  std::optional<ADLSwap&> o{t1};
+  std::optional<ADLSwap&> o2{t2};
+
+  o.swap(o2);
+
+  assert(!ADLSwap::called_adl_swap);
+}
+
 #endif
 
 int main(int, char**)
@@ -185,6 +205,7 @@ int main(int, char**)
     static_assert(test_swap_ref<double>());
     test_swap_ref<int>();
     test_swap_ref<double>();
+    test_ref_swap_adl();
 #endif
     {
         optional<int> opt1;

@Zingam

Zingam commented Jan 3, 2026

Copy link
Copy Markdown
Contributor

Can you do "Resolves # implemented in " for each issue?

Comment thread libcxx/test/std/utilities/optional/optional.specalg/swap.pass.cpp

@frederick-vs-ja frederick-vs-ja left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM!

@frederick-vs-ja frederick-vs-ja merged commit 7bc05a8 into llvm:main Jan 3, 2026
81 checks passed
mahesh-attarde pushed a commit to mahesh-attarde/llvm-project that referenced this pull request Jan 6, 2026
Resolves llvm#171340 implemented in llvm#155202

Resolves llvm#171402 implemented in llvm#155202

- Add `swap` test for `optional<T&>` to ensure an ADL-found swap isn't
selected.
- Drive-by: Update documentation for LWG4300 since it's already
completed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

libc++ libc++ C++ Standard Library. Not GNU libstdc++. Not libc++abi.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

LWG4439: std::optional<T&>::swap possibly selects ADL-found swap LWG4300: Missing Returns: element in optional<T&>::emplace

4 participants