std::declval<cv void>
should be (cv-unqualified) void
Section: 22.2.6 [declval] Status: New Submitter: Jiang An Opened: 2023-03-07 Last modified: 2023-03-22
Priority: 4
View other active issues in [declval].
View all other issues in [declval].
View all issues with New status.
Discussion:
Currently libc++ and libstdc++ determine the return type of std::declval
like this:
template<class _Tp> _Tp&& __declval_ret(int); // selected when _Tp is a referenceable type template<class _Tp> _Tp __declval_ret(long); // selected when _Tp is cv void template<class _Tp> decltype(__declval_ret<_Tp>(0)) declval() noexcept;
This strategy avoids instantiation of class templates. But it also drops cv-qualifiers of the return type
when the type is cv void
, which is different from the standard requirements. Such difference has
no impact in normal use of std::declval
, but is observable via decltype(std::declval<const void>)
and its friends.
[2023-03-22; Reflector poll]
Set priority to 4 after reflector poll.
"The testcase isn't even valid with the previous 'conforming' libstdc++ implementation."
"declval
isn't an addressable function, so would prefer if this
was ill-formed rather than complicating the definition for this case."
Proposed resolution:
This wording is relative to N4928.
Modify 22.2.1 [utility.syn], header <utility>
synopsis, and 22.2.6 [declval] as indicated:
template<class T> remove_cv_t<add_rvalue_reference_t<T>> declval() noexcept; // as unevaluated operand