Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Conversation

@H-G-Hristov
Copy link
Contributor

[[nodiscard]] should be applied to functions where discarding the return value is most likely a correctness issue.

Towards #172124

@H-G-Hristov H-G-Hristov requested a review from a team as a code owner December 27, 2025 08:17
@llvmbot llvmbot added the libc++ libc++ C++ Standard Library. Not GNU libstdc++. Not libc++abi. label Dec 27, 2025
@llvmbot
Copy link
Member

llvmbot commented Dec 27, 2025

@llvm/pr-subscribers-libcxx

Author: Hristo Hristov (H-G-Hristov)

Changes

[[nodiscard]] should be applied to functions where discarding the return value is most likely a correctness issue.

Towards #172124


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

2 Files Affected:

  • (modified) libcxx/include/__ranges/repeat_view.h (+17-10)
  • (added) libcxx/test/libcxx/ranges/range.factories/range.repeat.view/nodiscard.verify.cpp (+58)
diff --git a/libcxx/include/__ranges/repeat_view.h b/libcxx/include/__ranges/repeat_view.h
index 56b09701c8090..9192183f48013 100644
--- a/libcxx/include/__ranges/repeat_view.h
+++ b/libcxx/include/__ranges/repeat_view.h
@@ -108,17 +108,21 @@ class _LIBCPP_ABI_LLVM18_NO_UNIQUE_ADDRESS repeat_view : public view_interface<r
           __bound_ >= 0, "The behavior is undefined if Bound is not unreachable_sentinel_t and bound is negative");
   }
 
-  _LIBCPP_HIDE_FROM_ABI constexpr __iterator begin() const { return __iterator(std::addressof(*__value_)); }
+  [[nodiscard]] _LIBCPP_HIDE_FROM_ABI constexpr __iterator begin() const {
+    return __iterator(std::addressof(*__value_));
+  }
 
-  _LIBCPP_HIDE_FROM_ABI constexpr __iterator end() const
+  [[nodiscard]] _LIBCPP_HIDE_FROM_ABI constexpr __iterator end() const
     requires(!same_as<_Bound, unreachable_sentinel_t>)
   {
     return __iterator(std::addressof(*__value_), __bound_);
   }
 
-  _LIBCPP_HIDE_FROM_ABI constexpr unreachable_sentinel_t end() const noexcept { return unreachable_sentinel; }
+  [[nodiscard]] _LIBCPP_HIDE_FROM_ABI constexpr unreachable_sentinel_t end() const noexcept {
+    return unreachable_sentinel;
+  }
 
-  _LIBCPP_HIDE_FROM_ABI constexpr auto size() const
+  [[nodiscard]] _LIBCPP_HIDE_FROM_ABI constexpr auto size() const
     requires(!same_as<_Bound, unreachable_sentinel_t>)
   {
     return std::__to_unsigned_like(__bound_);
@@ -152,7 +156,7 @@ class repeat_view<_Tp, _Bound>::__iterator {
 
   _LIBCPP_HIDE_FROM_ABI __iterator() = default;
 
-  _LIBCPP_HIDE_FROM_ABI constexpr const _Tp& operator*() const noexcept { return *__value_; }
+  [[nodiscard]] _LIBCPP_HIDE_FROM_ABI constexpr const _Tp& operator*() const noexcept { return *__value_; }
 
   _LIBCPP_HIDE_FROM_ABI constexpr __iterator& operator++() {
     ++__current_;
@@ -192,7 +196,9 @@ class repeat_view<_Tp, _Bound>::__iterator {
     return *this;
   }
 
-  _LIBCPP_HIDE_FROM_ABI constexpr const _Tp& operator[](difference_type __n) const noexcept { return *(*this + __n); }
+  [[nodiscard]] _LIBCPP_HIDE_FROM_ABI constexpr const _Tp& operator[](difference_type __n) const noexcept {
+    return *(*this + __n);
+  }
 
   _LIBCPP_HIDE_FROM_ABI friend constexpr bool operator==(const __iterator& __x, const __iterator& __y) {
     return __x.__current_ == __y.__current_;
@@ -202,22 +208,23 @@ class repeat_view<_Tp, _Bound>::__iterator {
     return __x.__current_ <=> __y.__current_;
   }
 
-  _LIBCPP_HIDE_FROM_ABI friend constexpr __iterator operator+(__iterator __i, difference_type __n) {
+  [[nodiscard]] _LIBCPP_HIDE_FROM_ABI friend constexpr __iterator operator+(__iterator __i, difference_type __n) {
     __i += __n;
     return __i;
   }
 
-  _LIBCPP_HIDE_FROM_ABI friend constexpr __iterator operator+(difference_type __n, __iterator __i) {
+  [[nodiscard]] _LIBCPP_HIDE_FROM_ABI friend constexpr __iterator operator+(difference_type __n, __iterator __i) {
     __i += __n;
     return __i;
   }
 
-  _LIBCPP_HIDE_FROM_ABI friend constexpr __iterator operator-(__iterator __i, difference_type __n) {
+  [[nodiscard]] _LIBCPP_HIDE_FROM_ABI friend constexpr __iterator operator-(__iterator __i, difference_type __n) {
     __i -= __n;
     return __i;
   }
 
-  _LIBCPP_HIDE_FROM_ABI friend constexpr difference_type operator-(const __iterator& __x, const __iterator& __y) {
+  [[nodiscard]] _LIBCPP_HIDE_FROM_ABI friend constexpr difference_type
+  operator-(const __iterator& __x, const __iterator& __y) {
     return static_cast<difference_type>(__x.__current_) - static_cast<difference_type>(__y.__current_);
   }
 
diff --git a/libcxx/test/libcxx/ranges/range.factories/range.repeat.view/nodiscard.verify.cpp b/libcxx/test/libcxx/ranges/range.factories/range.repeat.view/nodiscard.verify.cpp
new file mode 100644
index 0000000000000..3008df94002e3
--- /dev/null
+++ b/libcxx/test/libcxx/ranges/range.factories/range.repeat.view/nodiscard.verify.cpp
@@ -0,0 +1,58 @@
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+// REQUIRES: std-at-least-c++23
+
+// Check that functions are marked [[nodiscard]]
+
+#include <ranges>
+
+void test() {
+  auto uv = std::views::repeat(49);
+  auto v = std::views::repeat(94, 82);
+
+  // [range.repeat.view]
+
+  // expected-warning@+1 {{ignoring return value of function declared with 'nodiscard' attribute}}
+  v.begin();
+
+  // expected-warning@+1 {{ignoring return value of function declared with 'nodiscard' attribute}}
+  v.end();
+  // expected-warning@+1 {{ignoring return value of function declared with 'nodiscard' attribute}}
+  uv.end();
+
+  // expected-warning@+1 {{ignoring return value of function declared with 'nodiscard' attribute}}
+  v.size();
+
+  // [range.repeat.iterator]
+
+  auto it = v.begin();
+
+  // expected-warning@+1 {{ignoring return value of function declared with 'nodiscard' attribute}}
+  it[0];
+
+  // expected-warning@+1 {{ignoring return value of function declared with 'nodiscard' attribute}}
+  it + 1;
+
+  // expected-warning@+1 {{ignoring return value of function declared with 'nodiscard' attribute}}
+  1 + it;
+
+  // expected-warning@+1 {{ignoring return value of function declared with 'nodiscard' attribute}}
+  it - 1;
+
+  // expected-warning@+1 {{ignoring return value of function declared with 'nodiscard' attribute}}
+  it - it;
+
+  // [range.repeat.overview]
+
+  // expected-warning@+1 {{ignoring return value of function declared with 'nodiscard' attribute}}
+  std::views::repeat(47);
+
+  // expected-warning@+1 {{ignoring return value of function declared with 'nodiscard' attribute}}
+  std::views::repeat(94, 82);
+}

@github-actions
Copy link

github-actions bot commented Dec 27, 2025

✅ With the latest revision this PR passed the C/C++ code formatter.

`[[nodiscard]]` should be applied to functions where discarding the return value is most likely a correctness issue.

- https://libcxx.llvm.org/CodingGuidelines.html
- https://wg21.link/range.repeat

Towards llvm#172124
@H-G-Hristov H-G-Hristov force-pushed the hgh/libcxx/nodiscard-to-repeat_view branch from 69bb01c to 75a3b56 Compare December 27, 2025 08:21
@Zingam Zingam added the ranges Issues related to `<ranges>` label Dec 27, 2025
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. ranges Issues related to `<ranges>`

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants