29#ifndef _GLIBCXX_DEBUG_SAFE_ITERATOR_H
30#define _GLIBCXX_DEBUG_SAFE_ITERATOR_H 1
38#if __cplusplus > 201703L
42#define _GLIBCXX_DEBUG_VERIFY_OPERANDS(_Lhs, _Rhs, _BadMsgId, _DiffMsgId) \
43 _GLIBCXX_DEBUG_VERIFY((!_Lhs._M_singular() && !_Rhs._M_singular()) \
44 || (_Lhs._M_value_initialized() \
45 && _Rhs._M_value_initialized()), \
46 _M_message(_BadMsgId) \
47 ._M_iterator(_Lhs, #_Lhs) \
48 ._M_iterator(_Rhs, #_Rhs)); \
49 _GLIBCXX_DEBUG_VERIFY(_Lhs._M_can_compare(_Rhs), \
50 _M_message(_DiffMsgId) \
51 ._M_iterator(_Lhs, #_Lhs) \
52 ._M_iterator(_Rhs, #_Rhs))
54#define _GLIBCXX_DEBUG_VERIFY_EQ_OPERANDS(_Lhs, _Rhs) \
55 _GLIBCXX_DEBUG_VERIFY_OPERANDS(_Lhs, _Rhs, __msg_iter_compare_bad, \
56 __msg_compare_different)
58#define _GLIBCXX_DEBUG_VERIFY_REL_OPERANDS(_Lhs, _Rhs) \
59 _GLIBCXX_DEBUG_VERIFY_OPERANDS(_Lhs, _Rhs, __msg_iter_order_bad, \
60 __msg_order_different)
62#define _GLIBCXX_DEBUG_VERIFY_DIST_OPERANDS(_Lhs, _Rhs) \
63 _GLIBCXX_DEBUG_VERIFY_OPERANDS(_Lhs, _Rhs, __msg_distance_bad, \
64 __msg_distance_different)
71 template<
typename _Sequence>
74 template<
typename _Iterator,
typename _Category>
79 template<
typename _Iterator,
typename _Category>
82 {
return __it.
base() == __it._M_get_sequence()->_M_base().begin(); }
86 template<
typename _Sequence>
89 typedef _Distance_traits<typename _Sequence::iterator> _DistTraits;
91 static typename _DistTraits::__type
92 _S_size(
const _Sequence& __seq)
112 template<
typename _Iterator,
typename _Sequence,
typename _Category
118 typedef _Iterator _Iter_base;
124 typedef std::__are_same<
typename _Sequence::_Base::const_iterator,
125 _Iterator> _IsConstant;
127 typedef typename __gnu_cxx::__conditional_type<
128 _IsConstant::__value,
129 typename _Sequence::_Base::iterator,
130 typename _Sequence::_Base::const_iterator>::__type _OtherIterator;
132 struct _Unchecked { };
134 _Safe_iterator(
const _Safe_iterator& __x, _Unchecked) _GLIBCXX_NOEXCEPT
135 : _Iter_base(__x.
base()), _Safe_base()
139 typedef _Iterator iterator_type;
140 typedef typename _Traits::iterator_category iterator_category;
141 typedef typename _Traits::value_type value_type;
142 typedef typename _Traits::difference_type difference_type;
143 typedef typename _Traits::reference reference;
144 typedef typename _Traits::pointer pointer;
146#if __cplusplus > 201703L && __cpp_lib_concepts
147 using iterator_concept = std::__detail::__iter_concept<_Iterator>;
162 : _Iter_base(__i), _Safe_base(__seq,
_S_constant())
169 : _Iter_base(__x.
base()), _Safe_base()
175 _M_message(__msg_init_copy_singular)
176 ._M_iterator(*
this,
"this")
177 ._M_iterator(__x,
"other"));
181#if __cplusplus >= 201103L
191 _M_message(__msg_init_copy_singular)
192 ._M_iterator(*
this,
"this")
193 ._M_iterator(__x,
"other"));
205 template<
typename _MutableIterator>
207 const _Safe_iterator<_MutableIterator, _Sequence,
208 typename __gnu_cxx::__enable_if<_IsConstant::__value &&
209 std::__are_same<_MutableIterator, _OtherIterator>::__value,
210 _Category>::__type>& __x)
212 : _Iter_base(__x.
base())
218 _M_message(__msg_init_const_singular)
219 ._M_iterator(*
this,
"this")
220 ._M_iterator(__x,
"other"));
234 _M_message(__msg_copy_singular)
235 ._M_iterator(*
this,
"this")
236 ._M_iterator(__x,
"other"));
254#if __cplusplus >= 201103L
264 _M_message(__msg_copy_singular)
265 ._M_iterator(*
this,
"this")
266 ._M_iterator(__x,
"other"));
285 __x.
base() = _Iterator();
299 _M_message(__msg_bad_deref)
300 ._M_iterator(*
this,
"this"));
313 _M_message(__msg_bad_deref)
314 ._M_iterator(*
this,
"this"));
315 return base().operator->();
327 _M_message(__msg_bad_inc)
328 ._M_iterator(*
this,
"this"));
342 _M_message(__msg_bad_inc)
343 ._M_iterator(*
this,
"this"));
344 _Safe_iterator __ret(*
this, _Unchecked());
352 static _GLIBCXX_CONSTEXPR
bool
354 {
return _IsConstant::__value; }
360 base() _GLIBCXX_NOEXCEPT {
return *
this; }
363 base() const _GLIBCXX_NOEXCEPT {
return *
this; }
369 operator _Iterator() const _GLIBCXX_NOEXCEPT {
return *
this; }
393 return ++
__base != _M_get_sequence()->_M_base().end();
410 _M_can_advance(difference_type __n,
bool __strict =
false)
const;
413 template<
typename _Diff>
422 bool __check_dereferenceable =
true)
const;
425 typename __gnu_cxx::__conditional_type<
426 _IsConstant::__value,
const _Sequence*, _Sequence*>::__type
427 _M_get_sequence()
const
431 typename _Distance_traits<_Iterator>::__type
435 typename _Distance_traits<_Iterator>::__type
436 _M_get_distance_from_begin()
const;
439 typename _Distance_traits<_Iterator>::__type
440 _M_get_distance_to_end()
const;
445 {
return base() == _M_get_sequence()->_M_base().begin(); }
450 {
return base() == _M_get_sequence()->_M_base().end(); }
456 {
return _BeforeBeginHelper<_Sequence>::_S_Is(*
this); }
462 {
return _BeforeBeginHelper<_Sequence>::_S_Is_Beginnest(*
this); }
470 operator==(
const _Self& __lhs,
const _Self& __rhs) _GLIBCXX_NOEXCEPT
472 _GLIBCXX_DEBUG_VERIFY_EQ_OPERANDS(__lhs, __rhs);
473 return __lhs.base() == __rhs.base();
476 template<
typename _IteR>
479 operator==(
const _Self& __lhs,
483 _GLIBCXX_DEBUG_VERIFY_EQ_OPERANDS(__lhs, __rhs);
484 return __lhs.base() == __rhs.base();
487#if ! __cpp_lib_three_way_comparison
490 operator!=(
const _Self& __lhs,
const _Self& __rhs) _GLIBCXX_NOEXCEPT
492 _GLIBCXX_DEBUG_VERIFY_EQ_OPERANDS(__lhs, __rhs);
493 return __lhs.base() != __rhs.base();
496 template<
typename _IteR>
499 operator!=(
const _Self& __lhs,
500 const _Safe_iterator<_IteR, _Sequence, iterator_category>& __rhs)
503 _GLIBCXX_DEBUG_VERIFY_EQ_OPERANDS(__lhs, __rhs);
504 return __lhs.base() != __rhs.base();
509 template<
typename _Iterator,
typename _Sequence>
510 class _Safe_iterator<_Iterator, _Sequence, std::bidirectional_iterator_tag>
511 :
public _Safe_iterator<_Iterator, _Sequence, std::forward_iterator_tag>
513 typedef _Safe_iterator<_Iterator, _Sequence,
514 std::forward_iterator_tag> _Safe_base;
517 typedef typename _Safe_base::_OtherIterator _OtherIterator;
519 typedef typename _Safe_base::_Unchecked _Unchecked;
522 _Unchecked __unchecked) _GLIBCXX_NOEXCEPT
523 : _Safe_base(__x, __unchecked)
539 : _Safe_base(__i, __seq)
549#if __cplusplus >= 201103L
558 template<
typename _MutableIterator>
560 const _Safe_iterator<_MutableIterator, _Sequence,
561 typename __gnu_cxx::__enable_if<_Safe_base::_IsConstant::__value &&
562 std::__are_same<_MutableIterator, _OtherIterator>::__value,
563 std::bidirectional_iterator_tag>::__type>& __x)
568#if __cplusplus >= 201103L
571 operator=(
const _Safe_iterator&) =
default;
581 _Safe_base::operator=(__x);
594 _Safe_base::operator++();
606 _M_message(__msg_bad_inc)
607 ._M_iterator(*
this,
"this"));
608 _Safe_iterator __ret(*
this, _Unchecked());
619 operator--() _GLIBCXX_NOEXCEPT
621 _GLIBCXX_DEBUG_VERIFY(this->_M_decrementable(),
622 _M_message(__msg_bad_dec)
623 ._M_iterator(*
this,
"this"));
634 operator--(
int) _GLIBCXX_NOEXCEPT
636 _GLIBCXX_DEBUG_VERIFY(this->_M_decrementable(),
637 _M_message(__msg_bad_dec)
638 ._M_iterator(*
this,
"this"));
639 _Safe_iterator __ret(*
this, _Unchecked());
648 _M_decrementable()
const
652 template<
typename _Iterator,
typename _Sequence>
653 class _Safe_iterator<_Iterator, _Sequence, std::random_access_iterator_tag>
655 std::bidirectional_iterator_tag>
657 typedef _Safe_iterator<_Iterator, _Sequence,
658 std::bidirectional_iterator_tag> _Safe_base;
659 typedef typename _Safe_base::_OtherIterator _OtherIterator;
661 typedef typename _Safe_base::_Self _Self;
662 typedef _Safe_iterator<_OtherIterator, _Sequence,
663 std::random_access_iterator_tag> _OtherSelf;
665 typedef typename _Safe_base::_Unchecked _Unchecked;
667 _Unchecked __unchecked) _GLIBCXX_NOEXCEPT
668 : _Safe_base(__x, __unchecked)
672 typedef typename _Safe_base::difference_type difference_type;
673 typedef typename _Safe_base::reference reference;
687 : _Safe_base(__i, __seq)
697#if __cplusplus >= 201103L
706 template<
typename _MutableIterator>
708 const _Safe_iterator<_MutableIterator, _Sequence,
709 typename __gnu_cxx::__enable_if<_Safe_base::_IsConstant::__value &&
710 std::__are_same<_MutableIterator, _OtherIterator>::__value,
711 std::random_access_iterator_tag>::__type>& __x)
716#if __cplusplus >= 201103L
719 operator=(
const _Safe_iterator&) =
default;
729 _Safe_base::operator=(__x);
736 _M_valid_range(
const _Safe_iterator& __rhs,
748 _Safe_base::operator++();
760 _M_message(__msg_bad_inc)
761 ._M_iterator(*
this,
"this"));
762 _Safe_iterator __ret(*
this, _Unchecked());
773 operator--() _GLIBCXX_NOEXCEPT
775 _Safe_base::operator--();
784 operator--(
int) _GLIBCXX_NOEXCEPT
786 _GLIBCXX_DEBUG_VERIFY(this->_M_decrementable(),
787 _M_message(__msg_bad_dec)
788 ._M_iterator(*
this,
"this"));
789 _Safe_iterator __ret(*
this, _Unchecked());
797 operator[](difference_type __n)
const _GLIBCXX_NOEXCEPT
799 _GLIBCXX_DEBUG_VERIFY(this->_M_can_advance(__n)
800 && this->_M_can_advance(__n + 1),
801 _M_message(__msg_iter_subscript_oob)
802 ._M_iterator(*this)._M_integer(__n));
803 return this->
base()[__n];
807 operator+=(difference_type __n) _GLIBCXX_NOEXCEPT
809 _GLIBCXX_DEBUG_VERIFY(this->_M_can_advance(__n),
810 _M_message(__msg_advance_oob)
811 ._M_iterator(*this)._M_integer(__n));
818 operator-=(difference_type __n) _GLIBCXX_NOEXCEPT
820 _GLIBCXX_DEBUG_VERIFY(this->_M_can_advance(-__n),
821 _M_message(__msg_retreat_oob)
822 ._M_iterator(*this)._M_integer(__n));
828#if __cpp_lib_three_way_comparison
831 operator<=>(
const _Self& __lhs,
const _Self& __rhs)
noexcept
833 _GLIBCXX_DEBUG_VERIFY_REL_OPERANDS(__lhs, __rhs);
834 return __lhs.base() <=> __rhs.base();
839 operator<=>(
const _Self& __lhs,
const _OtherSelf& __rhs)
noexcept
841 _GLIBCXX_DEBUG_VERIFY_REL_OPERANDS(__lhs, __rhs);
842 return __lhs.base() <=> __rhs.base();
847 operator<(
const _Self& __lhs,
const _Self& __rhs) _GLIBCXX_NOEXCEPT
849 _GLIBCXX_DEBUG_VERIFY_REL_OPERANDS(__lhs, __rhs);
850 return __lhs.base() < __rhs.base();
855 operator<(
const _Self& __lhs,
const _OtherSelf& __rhs) _GLIBCXX_NOEXCEPT
857 _GLIBCXX_DEBUG_VERIFY_REL_OPERANDS(__lhs, __rhs);
858 return __lhs.base() < __rhs.base();
863 operator<=(
const _Self& __lhs,
const _Self& __rhs) _GLIBCXX_NOEXCEPT
865 _GLIBCXX_DEBUG_VERIFY_REL_OPERANDS(__lhs, __rhs);
866 return __lhs.base() <= __rhs.base();
871 operator<=(
const _Self& __lhs,
const _OtherSelf& __rhs) _GLIBCXX_NOEXCEPT
873 _GLIBCXX_DEBUG_VERIFY_REL_OPERANDS(__lhs, __rhs);
874 return __lhs.base() <= __rhs.base();
879 operator>(
const _Self& __lhs,
const _Self& __rhs) _GLIBCXX_NOEXCEPT
881 _GLIBCXX_DEBUG_VERIFY_REL_OPERANDS(__lhs, __rhs);
882 return __lhs.base() > __rhs.base();
887 operator>(
const _Self& __lhs,
const _OtherSelf& __rhs) _GLIBCXX_NOEXCEPT
889 _GLIBCXX_DEBUG_VERIFY_REL_OPERANDS(__lhs, __rhs);
890 return __lhs.base() > __rhs.base();
895 operator>=(
const _Self& __lhs,
const _Self& __rhs) _GLIBCXX_NOEXCEPT
897 _GLIBCXX_DEBUG_VERIFY_REL_OPERANDS(__lhs, __rhs);
898 return __lhs.base() >= __rhs.base();
903 operator>=(
const _Self& __lhs,
const _OtherSelf& __rhs) _GLIBCXX_NOEXCEPT
905 _GLIBCXX_DEBUG_VERIFY_REL_OPERANDS(__lhs, __rhs);
906 return __lhs.base() >= __rhs.base();
915 friend difference_type
916 operator-(
const _Self& __lhs,
const _OtherSelf& __rhs) _GLIBCXX_NOEXCEPT
918 _GLIBCXX_DEBUG_VERIFY_DIST_OPERANDS(__lhs, __rhs);
919 return __lhs.base() - __rhs.base();
923 friend difference_type
924 operator-(
const _Self& __lhs,
const _Self& __rhs) _GLIBCXX_NOEXCEPT
926 _GLIBCXX_DEBUG_VERIFY_DIST_OPERANDS(__lhs, __rhs);
927 return __lhs.base() - __rhs.base();
932 operator+(
const _Self& __x, difference_type __n) _GLIBCXX_NOEXCEPT
934 _GLIBCXX_DEBUG_VERIFY(__x._M_can_advance(__n),
935 _M_message(__msg_advance_oob)
936 ._M_iterator(__x)._M_integer(__n));
942 operator+(difference_type __n,
const _Self& __x) _GLIBCXX_NOEXCEPT
944 _GLIBCXX_DEBUG_VERIFY(__x._M_can_advance(__n),
945 _M_message(__msg_advance_oob)
946 ._M_iterator(__x)._M_integer(__n));
952 operator-(
const _Self& __x, difference_type __n) _GLIBCXX_NOEXCEPT
954 _GLIBCXX_DEBUG_VERIFY(__x._M_can_advance(-__n),
955 _M_message(__msg_retreat_oob)
956 ._M_iterator(__x)._M_integer(__n));
962 template<
typename _Iterator,
typename _Sequence,
typename _Category>
968 typename _Distance_traits<_Iterator>::__type& __dist)
969 {
return __first._M_valid_range(__last, __dist); }
971 template<
typename _Iterator,
typename _Sequence,
typename _Category>
975 const _Safe_iterator<_Iterator, _Sequence,
978 typename _Distance_traits<_Iterator>::__type __dist;
979 return __first._M_valid_range(__last, __dist);
982 template<
typename _Iterator,
typename _Sequence,
typename _Category,
987 {
return __it._M_can_advance(__n); }
989 template<
typename _Iterator,
typename _Sequence,
typename _Category,
995 {
return __it._M_can_advance(__dist, __way); }
997 template<
typename _Iterator,
typename _Sequence>
1000 std::random_access_iterator_tag>& __it)
1001 {
return __it.base(); }
1003#if __cplusplus < 201103L
1004 template<
typename _Iterator,
typename _Sequence>
1006 {
typedef _Iterator _Type; };
1009 template<
typename _Iterator,
typename _Sequence>
1012 {
return __it.base(); }
1016#if __cplusplus >= 201103L && __cplusplus <= 201703L
1017namespace std _GLIBCXX_VISIBILITY(default)
1019_GLIBCXX_BEGIN_NAMESPACE_VERSION
1021 template<
typename _Iterator,
typename _Container,
typename _Sequence>
1023 __to_address(
const __gnu_debug::_Safe_iterator<
1024 __gnu_cxx::__normal_iterator<_Iterator, _Container>,
1025 _Sequence>& __it)
noexcept
1026 ->
decltype(std::__to_address(__it.base().base()))
1027 {
return std::__to_address(__it.base().base()); }
1029_GLIBCXX_END_NAMESPACE_VERSION
1033#undef _GLIBCXX_DEBUG_VERIFY_DIST_OPERANDS
1034#undef _GLIBCXX_DEBUG_VERIFY_REL_OPERANDS
1035#undef _GLIBCXX_DEBUG_VERIFY_EQ_OPERANDS
1036#undef _GLIBCXX_DEBUG_VERIFY_OPERANDS
constexpr complex< _Tp > operator-(const complex< _Tp > &__x, const complex< _Tp > &__y)
Return new complex value x minus y.
constexpr complex< _Tp > operator+(const complex< _Tp > &__x, const complex< _Tp > &__y)
Return new complex value x plus y.
pair(_T1, _T2) -> pair< _T1, _T2 >
Two pairs of the same type are equal iff their members are equal.
constexpr pair< typename __decay_and_strip< _T1 >::__type, typename __decay_and_strip< _T2 >::__type > make_pair(_T1 &&__x, _T2 &&__y)
A convenience wrapper for creating a pair from two objects.
void swap(any &__x, any &__y) noexcept
Exchange the states of two any objects.
constexpr _Tp * __addressof(_Tp &__r) noexcept
Same as C++11 std::addressof.
ISO C++ entities toplevel namespace is std.
GNU debug classes for public use.
constexpr bool __valid_range(_InputIterator __first, _InputIterator __last, typename _Distance_traits< _InputIterator >::__type &__dist)
constexpr _Iterator __base(_Iterator __it)
bool _M_incrementable() const
Is the iterator incrementable?
reference operator*() const noexcept
Iterator dereference.
_Safe_iterator operator++(int) noexcept
Iterator postincrement.
_Safe_iterator(const _Safe_iterator &__x) noexcept
Copy construction.
_Safe_iterator(_Safe_iterator &&__x) noexcept
Move construction.
bool _M_dereferenceable() const
Is the iterator dereferenceable?
void _M_attach_single(_Safe_sequence_base *__seq)
bool _M_before_dereferenceable() const
Is the iterator before a dereferenceable one?
_Safe_iterator & operator=(const _Safe_iterator &__x) noexcept
Copy assignment.
_Safe_iterator(const _Safe_iterator< _MutableIterator, _Sequence, typename __gnu_cxx::__enable_if< _IsConstant::__value &&std::__are_same< _MutableIterator, _OtherIterator >::__value, _Category >::__type > &__x) noexcept
Converting constructor from a mutable iterator to a constant iterator.
bool _M_is_beginnest() const
Is this iterator equal to the sequence's before_begin() iterator if any or begin() otherwise?
_Safe_iterator & operator++() noexcept
Iterator preincrement.
_Safe_iterator & operator=(_Safe_iterator &&__x) noexcept
Move assignment.
bool _M_is_begin() const
Is this iterator equal to the sequence's begin() iterator?
bool _M_value_initialized() const
Is the iterator value-initialized?
_Iterator & base() noexcept
Return the underlying iterator.
_Safe_iterator() noexcept
_Safe_iterator(_Iterator __i, const _Safe_sequence_base *__seq) noexcept
Safe iterator construction from an unsafe iterator and its sequence.
bool _M_is_end() const
Is this iterator equal to the sequence's end() iterator?
void _M_attach(_Safe_sequence_base *__seq)
bool _M_is_before_begin() const
Is this iterator equal to the sequence's before_begin() iterator if any?
static constexpr bool _S_constant()
Determine if this is a constant iterator.
pointer operator->() const noexcept
Iterator dereference.
Traits class for iterators.
Struct holding two objects of arbitrary type.
_Safe_sequence_base * _M_sequence
__gnu_cxx::__mutex & _M_get_mutex()
void _M_attach_single(_Safe_sequence_base *__seq, bool __constant)
void _M_attach(_Safe_sequence_base *__seq, bool __constant)
unsigned int _M_version
The container version number. This number may never be 0.