diff --git a/libcxx/docs/ReleaseNotes.rst b/libcxx/docs/ReleaseNotes.rst --- a/libcxx/docs/ReleaseNotes.rst +++ b/libcxx/docs/ReleaseNotes.rst @@ -86,6 +86,9 @@ supported anymore. Please migrate to using the new support for :ref:`assertions ` instead. +- ``vector::const_reference``, ``vector::const_iterator::reference`` + and ``bitset::const_reference`` are now aliases for `bool` in the unstable ABI. + ABI Changes ----------- diff --git a/libcxx/include/__bit_reference b/libcxx/include/__bit_reference --- a/libcxx/include/__bit_reference +++ b/libcxx/include/__bit_reference @@ -1109,7 +1109,11 @@ typedef typename _Cp::difference_type difference_type; typedef bool value_type; typedef __bit_iterator pointer; +#ifndef _LIBCPP_ABI_BITSET_VECTOR_BOOL_CONST_SUBSCRIPT_RETURN_BOOL typedef typename conditional<_IsConst, __bit_const_reference<_Cp>, __bit_reference<_Cp> >::type reference; +#else + using reference = typename conditional<_IsConst, bool, __bit_reference<_Cp>>::type; +#endif typedef random_access_iterator_tag iterator_category; private: @@ -1149,8 +1153,10 @@ return *this; } - _LIBCPP_INLINE_VISIBILITY reference operator*() const _NOEXCEPT - {return reference(__seg_, __storage_type(1) << __ctz_);} + _LIBCPP_INLINE_VISIBILITY reference operator*() const _NOEXCEPT { + return typename conditional<_IsConst, __bit_const_reference<_Cp>, __bit_reference<_Cp> > + ::type(__seg_, __storage_type(1) << __ctz_); + } _LIBCPP_INLINE_VISIBILITY __bit_iterator& operator++() { diff --git a/libcxx/test/std/containers/sequences/vector.bool/iterators.pass.cpp b/libcxx/test/std/containers/sequences/vector.bool/iterators.pass.cpp --- a/libcxx/test/std/containers/sequences/vector.bool/iterators.pass.cpp +++ b/libcxx/test/std/containers/sequences/vector.bool/iterators.pass.cpp @@ -24,6 +24,15 @@ int main(int, char**) { + using IterRefT = std::iterator_traits::iterator>::reference; + ASSERT_SAME_TYPE(IterRefT, std::vector::reference); + + using ConstIterRefT = std::iterator_traits::const_iterator>::reference; +#if !defined(_LIBCPP_VERSION) || defined(_LIBCPP_ABI_BITSET_VECTOR_BOOL_CONST_SUBSCRIPT_RETURN_BOOL) + ASSERT_SAME_TYPE(ConstIterRefT, bool); +#else + ASSERT_SAME_TYPE(ConstIterRefT, std::__bit_const_reference >); +#endif { typedef bool T; typedef std::vector C; diff --git a/libcxx/test/std/containers/sequences/vector.bool/types.pass.cpp b/libcxx/test/std/containers/sequences/vector.bool/types.pass.cpp --- a/libcxx/test/std/containers/sequences/vector.bool/types.pass.cpp +++ b/libcxx/test/std/containers/sequences/vector.bool/types.pass.cpp @@ -24,6 +24,7 @@ // typedef typename allocator_type::const_pointer const_pointer; // typedef std::reverse_iterator reverse_iterator; // typedef std::reverse_iterator const_reverse_iterator; +// typedef bool const_reference; // }; #include @@ -66,6 +67,9 @@ static_assert((std::is_same< typename C::const_reverse_iterator, std::reverse_iterator >::value), ""); +#if !defined(_LIBCPP_VERSION) || defined(_LIBCPP_ABI_BITSET_VECTOR_BOOL_CONST_SUBSCRIPT_RETURN_BOOL) + static_assert(std::is_same::value, ""); +#endif } int main(int, char**)