This page is a snapshot from the LWG issues list, see the Library Active Issues List for more information and the meaning of New status.

3911. unique_ptr's operator* is missing a mandate

Section: 20.3.1.3.5 [unique.ptr.single.observers], 20.3.1.4.4 [unique.ptr.runtime.observers] Status: New Submitter: Brian Bi Opened: 2023-03-27 Last modified: 2023-06-01

Priority: 3

View all other issues in [unique.ptr.single.observers].

View all issues with New status.

Discussion:

The return type of std::unique_ptr<T>::operator* is std::add_lvalue_reference_t<T>, but there is no mandate stating that *get() is convertible to that type. There also does not appear to be a mandate that *get() is a valid expression; dereferenceability is not part of the Cpp17NullablePointer requirements. A similar issue appears to exist for std::unique_ptr<T[]>::operator[].

[2023-03-28; Reflector poll]

Set priority to 3 after reflector poll.

"It would be nice to Mandate !reference_converts_from_temporary_v<add_lvalue_reference_t<T>, decltype(*get())>." "noexcept-specifier isn't quite right, conversion from *get() to T& can throw."

Previous resolution [SUPERSEDED]:

This wording is relative to N4944.

  1. Add the following bullet before 20.3.1.3.5 [unique.ptr.single.observers] paragraph 1:

    
    constexpr add_lvalue_reference_t<T> operator*() const noexcept(noexcept(*declval<pointer>()));
    

    -?- Mandates: *get() is a valid expression that is convertible to add_lvalue_reference_t<T>.

    -1- Preconditions: get() != nullptr.

    -2- Returns: *get().

  2. Add the following bullet before 20.3.1.4.4 [unique.ptr.runtime.observers] paragraph 1:

    
    constexpr T& operator[](size_t i) const;
    

    -?- Mandates: get()[i] is a valid expression that is convertible to T&.

    -1- Preconditions: i < the number of elements in the array to which the stored pointer points.

    -2- Returns: get()[i].

[2023-04-03; Jonathan provides new wording as requested by LWG]

Proposed resolution:

This wording is relative to N4944.

  1. Add the following bullet before 20.3.1.3.5 [unique.ptr.single.observers] paragraph 1:

    
    constexpr add_lvalue_reference_t<T> operator*() const noexcept(noexcept(*declval<pointer>()));
    

    -1- Preconditions: get() != nullptr.

    -2- Returns Effects: Equivalent to: return *get();.

  2. Add the following bullet before 20.3.1.4.4 [unique.ptr.runtime.observers] paragraph 1:

    
    constexpr T& operator[](size_t i) const;
    

    -1- Preconditions: get() != nullptr i < the number of elements in the array to which the stored pointer points.

    -2- Returns Effects: Equivalent to: return get()[i];.