Subversion Repositories Kolibri OS

Rev

Go to most recent revision | Blame | Last modification | View Log | RSS feed

  1. // Debugging vector implementation -*- C++ -*-
  2.  
  3. // Copyright (C) 2003-2015 Free Software Foundation, Inc.
  4. //
  5. // This file is part of the GNU ISO C++ Library.  This library is free
  6. // software; you can redistribute it and/or modify it under the
  7. // terms of the GNU General Public License as published by the
  8. // Free Software Foundation; either version 3, or (at your option)
  9. // any later version.
  10.  
  11. // This library is distributed in the hope that it will be useful,
  12. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14. // GNU General Public License for more details.
  15.  
  16. // Under Section 7 of GPL version 3, you are granted additional
  17. // permissions described in the GCC Runtime Library Exception, version
  18. // 3.1, as published by the Free Software Foundation.
  19.  
  20. // You should have received a copy of the GNU General Public License and
  21. // a copy of the GCC Runtime Library Exception along with this program;
  22. // see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
  23. // <http://www.gnu.org/licenses/>.
  24.  
  25. /** @file debug/vector
  26.  *  This file is a GNU debug extension to the Standard C++ Library.
  27.  */
  28.  
  29. #ifndef _GLIBCXX_DEBUG_VECTOR
  30. #define _GLIBCXX_DEBUG_VECTOR 1
  31.  
  32. #include <vector>
  33. #include <utility>
  34. #include <debug/safe_sequence.h>
  35. #include <debug/safe_container.h>
  36. #include <debug/safe_iterator.h>
  37.  
  38. namespace __gnu_debug
  39. {
  40.   /** @brief Base class for Debug Mode vector.
  41.    *
  42.    * Adds information about the guaranteed capacity, which is useful for
  43.    * detecting code which relies on non-portable implementation details of
  44.    * the libstdc++ reallocation policy.
  45.    */
  46.   template<typename _SafeSequence,
  47.            typename _BaseSequence>
  48.     class _Safe_vector
  49.     {
  50.       typedef typename _BaseSequence::size_type size_type;
  51.  
  52.       const _SafeSequence&
  53.       _M_seq() const { return *static_cast<const _SafeSequence*>(this); }
  54.  
  55.     protected:
  56.       _Safe_vector() _GLIBCXX_NOEXCEPT
  57.         : _M_guaranteed_capacity(0)
  58.       { _M_update_guaranteed_capacity(); }
  59.  
  60.       _Safe_vector(const _Safe_vector&) _GLIBCXX_NOEXCEPT
  61.         : _M_guaranteed_capacity(0)
  62.       { _M_update_guaranteed_capacity(); }
  63.  
  64.       _Safe_vector(size_type __n) _GLIBCXX_NOEXCEPT
  65.         : _M_guaranteed_capacity(__n)
  66.       { }
  67.  
  68. #if __cplusplus >= 201103L
  69.       _Safe_vector(_Safe_vector&& __x) noexcept
  70.         : _Safe_vector()
  71.       { __x._M_guaranteed_capacity = 0; }
  72.  
  73.       _Safe_vector&
  74.       operator=(const _Safe_vector&) noexcept
  75.       {
  76.         _M_update_guaranteed_capacity();
  77.         return *this;
  78.       }
  79.  
  80.       _Safe_vector&
  81.       operator=(_Safe_vector&& __x) noexcept
  82.       {
  83.         _M_update_guaranteed_capacity();
  84.         __x._M_guaranteed_capacity = 0;
  85.         return *this;
  86.       }
  87. #endif
  88.  
  89.       size_type _M_guaranteed_capacity;
  90.  
  91.       bool
  92.       _M_requires_reallocation(size_type __elements) const _GLIBCXX_NOEXCEPT
  93.       { return __elements > _M_seq().capacity(); }
  94.  
  95.       void
  96.       _M_update_guaranteed_capacity() _GLIBCXX_NOEXCEPT
  97.       {
  98.         if (_M_seq().size() > _M_guaranteed_capacity)
  99.           _M_guaranteed_capacity = _M_seq().size();
  100.       }
  101.     };
  102. }
  103.  
  104. namespace std _GLIBCXX_VISIBILITY(default)
  105. {
  106. namespace __debug
  107. {
  108.   /// Class std::vector with safety/checking/debug instrumentation.
  109.   template<typename _Tp,
  110.            typename _Allocator = std::allocator<_Tp> >
  111.     class vector
  112.     : public __gnu_debug::_Safe_container<
  113.         vector<_Tp, _Allocator>, _Allocator, __gnu_debug::_Safe_sequence>,
  114.       public _GLIBCXX_STD_C::vector<_Tp, _Allocator>,
  115.       public __gnu_debug::_Safe_vector<
  116.         vector<_Tp, _Allocator>,
  117.         _GLIBCXX_STD_C::vector<_Tp, _Allocator> >
  118.     {
  119.       typedef _GLIBCXX_STD_C::vector<_Tp, _Allocator>           _Base;
  120.       typedef __gnu_debug::_Safe_container<
  121.         vector, _Allocator, __gnu_debug::_Safe_sequence>        _Safe;
  122.       typedef __gnu_debug::_Safe_vector<vector, _Base>          _Safe_vector;
  123.  
  124.       typedef typename _Base::iterator          _Base_iterator;
  125.       typedef typename _Base::const_iterator    _Base_const_iterator;
  126.       typedef __gnu_debug::_Equal_to<_Base_const_iterator> _Equal;
  127.  
  128.     public:
  129.       typedef typename _Base::reference                 reference;
  130.       typedef typename _Base::const_reference           const_reference;
  131.  
  132.       typedef __gnu_debug::_Safe_iterator<
  133.         _Base_iterator, vector>                         iterator;
  134.       typedef __gnu_debug::_Safe_iterator<
  135.         _Base_const_iterator, vector>                   const_iterator;
  136.  
  137.       typedef typename _Base::size_type                 size_type;
  138.       typedef typename _Base::difference_type           difference_type;
  139.  
  140.       typedef _Tp                                       value_type;
  141.       typedef _Allocator                                allocator_type;
  142.       typedef typename _Base::pointer                   pointer;
  143.       typedef typename _Base::const_pointer             const_pointer;
  144.       typedef std::reverse_iterator<iterator>           reverse_iterator;
  145.       typedef std::reverse_iterator<const_iterator>     const_reverse_iterator;
  146.  
  147.       // 23.2.4.1 construct/copy/destroy:
  148.  
  149. #if __cplusplus < 201103L
  150.       vector() _GLIBCXX_NOEXCEPT
  151.       : _Base() { }
  152. #else
  153.       vector() = default;
  154. #endif
  155.  
  156.       explicit
  157.       vector(const _Allocator& __a) _GLIBCXX_NOEXCEPT
  158.       : _Base(__a) { }
  159.  
  160. #if __cplusplus >= 201103L
  161.       explicit
  162.       vector(size_type __n, const _Allocator& __a = _Allocator())
  163.       : _Base(__n, __a), _Safe_vector(__n) { }
  164.  
  165.       vector(size_type __n, const _Tp& __value,
  166.              const _Allocator& __a = _Allocator())
  167.       : _Base(__n, __value, __a) { }
  168. #else
  169.       explicit
  170.       vector(size_type __n, const _Tp& __value = _Tp(),
  171.              const _Allocator& __a = _Allocator())
  172.       : _Base(__n, __value, __a) { }
  173. #endif
  174.  
  175. #if __cplusplus >= 201103L
  176.       template<class _InputIterator,
  177.                typename = std::_RequireInputIter<_InputIterator>>
  178. #else
  179.       template<class _InputIterator>
  180. #endif
  181.         vector(_InputIterator __first, _InputIterator __last,
  182.                const _Allocator& __a = _Allocator())
  183.         : _Base(__gnu_debug::__base(__gnu_debug::__check_valid_range(__first,
  184.                                                                      __last)),
  185.                 __gnu_debug::__base(__last), __a) { }
  186.  
  187. #if __cplusplus < 201103L
  188.       vector(const vector& __x)
  189.       : _Base(__x) { }
  190.  
  191.       ~vector() _GLIBCXX_NOEXCEPT { }
  192. #else
  193.       vector(const vector&) = default;
  194.       vector(vector&&) = default;
  195.  
  196.       vector(const vector& __x, const allocator_type& __a)
  197.       : _Base(__x, __a) { }
  198.  
  199.       vector(vector&& __x, const allocator_type& __a)
  200.       : _Safe(std::move(__x._M_safe()), __a),
  201.         _Base(std::move(__x._M_base()), __a),
  202.         _Safe_vector(std::move(__x)) { }
  203.  
  204.       vector(initializer_list<value_type> __l,
  205.              const allocator_type& __a = allocator_type())
  206.       : _Base(__l, __a) { }
  207.  
  208.       ~vector() = default;
  209. #endif
  210.  
  211.       /// Construction from a normal-mode vector
  212.       vector(const _Base& __x)
  213.       : _Base(__x) { }
  214.  
  215. #if __cplusplus < 201103L
  216.       vector&
  217.       operator=(const vector& __x)
  218.       {
  219.         this->_M_safe() = __x;
  220.         _M_base() = __x;
  221.         this->_M_update_guaranteed_capacity();
  222.         return *this;
  223.       }
  224. #else
  225.       vector&
  226.       operator=(const vector&) = default;
  227.  
  228.       vector&
  229.       operator=(vector&&) = default;
  230.  
  231.       vector&
  232.       operator=(initializer_list<value_type> __l)
  233.       {
  234.         _M_base() = __l;
  235.         this->_M_invalidate_all();
  236.         this->_M_update_guaranteed_capacity();
  237.         return *this;
  238.       }
  239. #endif
  240.  
  241. #if __cplusplus >= 201103L
  242.       template<typename _InputIterator,
  243.                typename = std::_RequireInputIter<_InputIterator>>
  244. #else
  245.       template<typename _InputIterator>
  246. #endif
  247.         void
  248.         assign(_InputIterator __first, _InputIterator __last)
  249.         {
  250.           __glibcxx_check_valid_range(__first, __last);
  251.           _Base::assign(__gnu_debug::__base(__first),
  252.                         __gnu_debug::__base(__last));
  253.           this->_M_invalidate_all();
  254.           this->_M_update_guaranteed_capacity();
  255.         }
  256.  
  257.       void
  258.       assign(size_type __n, const _Tp& __u)
  259.       {
  260.         _Base::assign(__n, __u);
  261.         this->_M_invalidate_all();
  262.         this->_M_update_guaranteed_capacity();
  263.       }
  264.  
  265. #if __cplusplus >= 201103L
  266.       void
  267.       assign(initializer_list<value_type> __l)
  268.       {
  269.         _Base::assign(__l);
  270.         this->_M_invalidate_all();
  271.         this->_M_update_guaranteed_capacity();
  272.       }
  273. #endif
  274.  
  275.       using _Base::get_allocator;
  276.  
  277.       // iterators:
  278.       iterator
  279.       begin() _GLIBCXX_NOEXCEPT
  280.       { return iterator(_Base::begin(), this); }
  281.  
  282.       const_iterator
  283.       begin() const _GLIBCXX_NOEXCEPT
  284.       { return const_iterator(_Base::begin(), this); }
  285.  
  286.       iterator
  287.       end() _GLIBCXX_NOEXCEPT
  288.       { return iterator(_Base::end(), this); }
  289.  
  290.       const_iterator
  291.       end() const _GLIBCXX_NOEXCEPT
  292.       { return const_iterator(_Base::end(), this); }
  293.  
  294.       reverse_iterator
  295.       rbegin() _GLIBCXX_NOEXCEPT
  296.       { return reverse_iterator(end()); }
  297.  
  298.       const_reverse_iterator
  299.       rbegin() const _GLIBCXX_NOEXCEPT
  300.       { return const_reverse_iterator(end()); }
  301.  
  302.       reverse_iterator
  303.       rend() _GLIBCXX_NOEXCEPT
  304.       { return reverse_iterator(begin()); }
  305.  
  306.       const_reverse_iterator
  307.       rend() const _GLIBCXX_NOEXCEPT
  308.       { return const_reverse_iterator(begin()); }
  309.  
  310. #if __cplusplus >= 201103L
  311.       const_iterator
  312.       cbegin() const noexcept
  313.       { return const_iterator(_Base::begin(), this); }
  314.  
  315.       const_iterator
  316.       cend() const noexcept
  317.       { return const_iterator(_Base::end(), this); }
  318.  
  319.       const_reverse_iterator
  320.       crbegin() const noexcept
  321.       { return const_reverse_iterator(end()); }
  322.  
  323.       const_reverse_iterator
  324.       crend() const noexcept
  325.       { return const_reverse_iterator(begin()); }
  326. #endif
  327.  
  328.       // 23.2.4.2 capacity:
  329.       using _Base::size;
  330.       using _Base::max_size;
  331.  
  332. #if __cplusplus >= 201103L
  333.       void
  334.       resize(size_type __sz)
  335.       {
  336.         bool __realloc = this->_M_requires_reallocation(__sz);
  337.         if (__sz < this->size())
  338.           this->_M_invalidate_after_nth(__sz);
  339.         _Base::resize(__sz);
  340.         if (__realloc)
  341.           this->_M_invalidate_all();
  342.         this->_M_update_guaranteed_capacity();
  343.       }
  344.  
  345.       void
  346.       resize(size_type __sz, const _Tp& __c)
  347.       {
  348.         bool __realloc = this->_M_requires_reallocation(__sz);
  349.         if (__sz < this->size())
  350.           this->_M_invalidate_after_nth(__sz);
  351.         _Base::resize(__sz, __c);
  352.         if (__realloc)
  353.           this->_M_invalidate_all();
  354.         this->_M_update_guaranteed_capacity();
  355.       }
  356. #else
  357.       void
  358.       resize(size_type __sz, _Tp __c = _Tp())
  359.       {
  360.         bool __realloc = this->_M_requires_reallocation(__sz);
  361.         if (__sz < this->size())
  362.           this->_M_invalidate_after_nth(__sz);
  363.         _Base::resize(__sz, __c);
  364.         if (__realloc)
  365.           this->_M_invalidate_all();
  366.         this->_M_update_guaranteed_capacity();
  367.       }
  368. #endif
  369.  
  370. #if __cplusplus >= 201103L
  371.       void
  372.       shrink_to_fit()
  373.       {
  374.         if (_Base::_M_shrink_to_fit())
  375.           {
  376.             this->_M_guaranteed_capacity = _Base::capacity();
  377.             this->_M_invalidate_all();
  378.           }
  379.       }
  380. #endif
  381.  
  382.       size_type
  383.       capacity() const _GLIBCXX_NOEXCEPT
  384.       {
  385. #ifdef _GLIBCXX_DEBUG_PEDANTIC
  386.         return this->_M_guaranteed_capacity;
  387. #else
  388.         return _Base::capacity();
  389. #endif
  390.       }
  391.  
  392.       using _Base::empty;
  393.  
  394.       void
  395.       reserve(size_type __n)
  396.       {
  397.         bool __realloc = this->_M_requires_reallocation(__n);
  398.         _Base::reserve(__n);
  399.         if (__n > this->_M_guaranteed_capacity)
  400.           this->_M_guaranteed_capacity = __n;
  401.         if (__realloc)
  402.           this->_M_invalidate_all();
  403.       }
  404.  
  405.       // element access:
  406.       reference
  407.       operator[](size_type __n) _GLIBCXX_NOEXCEPT
  408.       {
  409.         __glibcxx_check_subscript(__n);
  410.         return _M_base()[__n];
  411.       }
  412.  
  413.       const_reference
  414.       operator[](size_type __n) const _GLIBCXX_NOEXCEPT
  415.       {
  416.         __glibcxx_check_subscript(__n);
  417.         return _M_base()[__n];
  418.       }
  419.  
  420.       using _Base::at;
  421.  
  422.       reference
  423.       front() _GLIBCXX_NOEXCEPT
  424.       {
  425.         __glibcxx_check_nonempty();
  426.         return _Base::front();
  427.       }
  428.  
  429.       const_reference
  430.       front() const _GLIBCXX_NOEXCEPT
  431.       {
  432.         __glibcxx_check_nonempty();
  433.         return _Base::front();
  434.       }
  435.  
  436.       reference
  437.       back() _GLIBCXX_NOEXCEPT
  438.       {
  439.         __glibcxx_check_nonempty();
  440.         return _Base::back();
  441.       }
  442.  
  443.       const_reference
  444.       back() const _GLIBCXX_NOEXCEPT
  445.       {
  446.         __glibcxx_check_nonempty();
  447.         return _Base::back();
  448.       }
  449.  
  450.       // _GLIBCXX_RESOLVE_LIB_DEFECTS
  451.       // DR 464. Suggestion for new member functions in standard containers.
  452.       using _Base::data;
  453.  
  454.       // 23.2.4.3 modifiers:
  455.       void
  456.       push_back(const _Tp& __x)
  457.       {
  458.         bool __realloc = this->_M_requires_reallocation(this->size() + 1);
  459.         _Base::push_back(__x);
  460.         if (__realloc)
  461.           this->_M_invalidate_all();
  462.         this->_M_update_guaranteed_capacity();
  463.       }
  464.  
  465. #if __cplusplus >= 201103L
  466.       template<typename _Up = _Tp>
  467.         typename __gnu_cxx::__enable_if<!std::__are_same<_Up, bool>::__value,
  468.                                         void>::__type
  469.         push_back(_Tp&& __x)
  470.         { emplace_back(std::move(__x)); }
  471.  
  472.       template<typename... _Args>
  473.         void
  474.         emplace_back(_Args&&... __args)
  475.         {
  476.           bool __realloc = this->_M_requires_reallocation(this->size() + 1);
  477.           _Base::emplace_back(std::forward<_Args>(__args)...);
  478.           if (__realloc)
  479.             this->_M_invalidate_all();
  480.           this->_M_update_guaranteed_capacity();
  481.         }
  482. #endif
  483.  
  484.       void
  485.       pop_back() _GLIBCXX_NOEXCEPT
  486.       {
  487.         __glibcxx_check_nonempty();
  488.         this->_M_invalidate_if(_Equal(--_Base::end()));
  489.         _Base::pop_back();
  490.       }
  491.  
  492. #if __cplusplus >= 201103L
  493.       template<typename... _Args>
  494.         iterator
  495.         emplace(const_iterator __position, _Args&&... __args)
  496.         {
  497.           __glibcxx_check_insert(__position);
  498.           bool __realloc = this->_M_requires_reallocation(this->size() + 1);
  499.           difference_type __offset = __position.base() - _Base::begin();
  500.           _Base_iterator __res = _Base::emplace(__position.base(),
  501.                                                 std::forward<_Args>(__args)...);
  502.           if (__realloc)
  503.             this->_M_invalidate_all();
  504.           else
  505.             this->_M_invalidate_after_nth(__offset);
  506.           this->_M_update_guaranteed_capacity();
  507.           return iterator(__res, this);
  508.         }
  509. #endif
  510.  
  511.       iterator
  512. #if __cplusplus >= 201103L
  513.       insert(const_iterator __position, const _Tp& __x)
  514. #else
  515.       insert(iterator __position, const _Tp& __x)
  516. #endif
  517.       {
  518.         __glibcxx_check_insert(__position);
  519.         bool __realloc = this->_M_requires_reallocation(this->size() + 1);
  520.         difference_type __offset = __position.base() - _Base::begin();
  521.         _Base_iterator __res = _Base::insert(__position.base(), __x);
  522.         if (__realloc)
  523.           this->_M_invalidate_all();
  524.         else
  525.           this->_M_invalidate_after_nth(__offset);
  526.         this->_M_update_guaranteed_capacity();
  527.         return iterator(__res, this);
  528.       }
  529.  
  530. #if __cplusplus >= 201103L
  531.       template<typename _Up = _Tp>
  532.         typename __gnu_cxx::__enable_if<!std::__are_same<_Up, bool>::__value,
  533.                                         iterator>::__type
  534.         insert(const_iterator __position, _Tp&& __x)
  535.         { return emplace(__position, std::move(__x)); }
  536.  
  537.       iterator
  538.       insert(const_iterator __position, initializer_list<value_type> __l)
  539.       { return this->insert(__position, __l.begin(), __l.end()); }
  540. #endif
  541.  
  542. #if __cplusplus >= 201103L
  543.       iterator
  544.       insert(const_iterator __position, size_type __n, const _Tp& __x)
  545.       {
  546.         __glibcxx_check_insert(__position);
  547.         bool __realloc = this->_M_requires_reallocation(this->size() + __n);
  548.         difference_type __offset = __position.base() - _Base::cbegin();
  549.         _Base_iterator __res = _Base::insert(__position.base(), __n, __x);
  550.         if (__realloc)
  551.           this->_M_invalidate_all();
  552.         else
  553.           this->_M_invalidate_after_nth(__offset);
  554.         this->_M_update_guaranteed_capacity();
  555.         return iterator(__res, this);
  556.       }
  557. #else
  558.       void
  559.       insert(iterator __position, size_type __n, const _Tp& __x)
  560.       {
  561.         __glibcxx_check_insert(__position);
  562.         bool __realloc = this->_M_requires_reallocation(this->size() + __n);
  563.         difference_type __offset = __position.base() - _Base::begin();
  564.         _Base::insert(__position.base(), __n, __x);
  565.         if (__realloc)
  566.           this->_M_invalidate_all();
  567.         else
  568.           this->_M_invalidate_after_nth(__offset);
  569.         this->_M_update_guaranteed_capacity();
  570.       }
  571. #endif
  572.  
  573. #if __cplusplus >= 201103L
  574.       template<class _InputIterator,
  575.                typename = std::_RequireInputIter<_InputIterator>>
  576.         iterator
  577.         insert(const_iterator __position,
  578.                _InputIterator __first, _InputIterator __last)
  579.         {
  580.           __glibcxx_check_insert_range(__position, __first, __last);
  581.  
  582.           /* Hard to guess if invalidation will occur, because __last
  583.              - __first can't be calculated in all cases, so we just
  584.              punt here by checking if it did occur. */
  585.           _Base_iterator __old_begin = _M_base().begin();
  586.           difference_type __offset = __position.base() - _Base::cbegin();
  587.           _Base_iterator __res = _Base::insert(__position.base(),
  588.                                                __gnu_debug::__base(__first),
  589.                                                __gnu_debug::__base(__last));
  590.  
  591.           if (_M_base().begin() != __old_begin)
  592.             this->_M_invalidate_all();
  593.           else
  594.             this->_M_invalidate_after_nth(__offset);
  595.           this->_M_update_guaranteed_capacity();
  596.           return iterator(__res, this);
  597.         }
  598. #else
  599.       template<class _InputIterator>
  600.         void
  601.         insert(iterator __position,
  602.                _InputIterator __first, _InputIterator __last)
  603.         {
  604.           __glibcxx_check_insert_range(__position, __first, __last);
  605.  
  606.           /* Hard to guess if invalidation will occur, because __last
  607.              - __first can't be calculated in all cases, so we just
  608.              punt here by checking if it did occur. */
  609.           _Base_iterator __old_begin = _M_base().begin();
  610.           difference_type __offset = __position.base() - _Base::begin();
  611.           _Base::insert(__position.base(), __gnu_debug::__base(__first),
  612.                                            __gnu_debug::__base(__last));
  613.  
  614.           if (_M_base().begin() != __old_begin)
  615.             this->_M_invalidate_all();
  616.           else
  617.             this->_M_invalidate_after_nth(__offset);
  618.           this->_M_update_guaranteed_capacity();
  619.         }
  620. #endif
  621.  
  622.       iterator
  623. #if __cplusplus >= 201103L
  624.       erase(const_iterator __position)
  625. #else
  626.       erase(iterator __position)
  627. #endif
  628.       {
  629.         __glibcxx_check_erase(__position);
  630.         difference_type __offset = __position.base() - _Base::begin();
  631.         _Base_iterator __res = _Base::erase(__position.base());
  632.         this->_M_invalidate_after_nth(__offset);
  633.         return iterator(__res, this);
  634.       }
  635.  
  636.       iterator
  637. #if __cplusplus >= 201103L
  638.       erase(const_iterator __first, const_iterator __last)
  639. #else
  640.       erase(iterator __first, iterator __last)
  641. #endif
  642.       {
  643.         // _GLIBCXX_RESOLVE_LIB_DEFECTS
  644.         // 151. can't currently clear() empty container
  645.         __glibcxx_check_erase_range(__first, __last);
  646.  
  647.         if (__first.base() != __last.base())
  648.           {
  649.             difference_type __offset = __first.base() - _Base::begin();
  650.             _Base_iterator __res = _Base::erase(__first.base(),
  651.                                                 __last.base());
  652.             this->_M_invalidate_after_nth(__offset);
  653.             return iterator(__res, this);
  654.           }
  655.         else
  656. #if __cplusplus >= 201103L
  657.           return begin() + (__first.base() - cbegin().base());
  658. #else
  659.           return __first;
  660. #endif
  661.       }
  662.  
  663.       void
  664.       swap(vector& __x)
  665. #if __cplusplus >= 201103L
  666.         noexcept( noexcept(declval<_Base>().swap(__x)) )
  667. #endif
  668.       {
  669.         _Safe::_M_swap(__x);
  670.         _Base::swap(__x);
  671.         std::swap(this->_M_guaranteed_capacity, __x._M_guaranteed_capacity);
  672.       }
  673.  
  674.       void
  675.       clear() _GLIBCXX_NOEXCEPT
  676.       {
  677.         _Base::clear();
  678.         this->_M_invalidate_all();
  679.       }
  680.  
  681.       _Base&
  682.       _M_base() _GLIBCXX_NOEXCEPT { return *this; }
  683.  
  684.       const _Base&
  685.       _M_base() const _GLIBCXX_NOEXCEPT { return *this; }
  686.  
  687.     private:
  688.       void
  689.       _M_invalidate_after_nth(difference_type __n) _GLIBCXX_NOEXCEPT
  690.       {
  691.         typedef __gnu_debug::_After_nth_from<_Base_const_iterator> _After_nth;
  692.         this->_M_invalidate_if(_After_nth(__n, _Base::begin()));
  693.       }
  694.     };
  695.  
  696.   template<typename _Tp, typename _Alloc>
  697.     inline bool
  698.     operator==(const vector<_Tp, _Alloc>& __lhs,
  699.                const vector<_Tp, _Alloc>& __rhs)
  700.     { return __lhs._M_base() == __rhs._M_base(); }
  701.  
  702.   template<typename _Tp, typename _Alloc>
  703.     inline bool
  704.     operator!=(const vector<_Tp, _Alloc>& __lhs,
  705.                const vector<_Tp, _Alloc>& __rhs)
  706.     { return __lhs._M_base() != __rhs._M_base(); }
  707.  
  708.   template<typename _Tp, typename _Alloc>
  709.     inline bool
  710.     operator<(const vector<_Tp, _Alloc>& __lhs,
  711.               const vector<_Tp, _Alloc>& __rhs)
  712.     { return __lhs._M_base() < __rhs._M_base(); }
  713.  
  714.   template<typename _Tp, typename _Alloc>
  715.     inline bool
  716.     operator<=(const vector<_Tp, _Alloc>& __lhs,
  717.                const vector<_Tp, _Alloc>& __rhs)
  718.     { return __lhs._M_base() <= __rhs._M_base(); }
  719.  
  720.   template<typename _Tp, typename _Alloc>
  721.     inline bool
  722.     operator>=(const vector<_Tp, _Alloc>& __lhs,
  723.                const vector<_Tp, _Alloc>& __rhs)
  724.     { return __lhs._M_base() >= __rhs._M_base(); }
  725.  
  726.   template<typename _Tp, typename _Alloc>
  727.     inline bool
  728.     operator>(const vector<_Tp, _Alloc>& __lhs,
  729.               const vector<_Tp, _Alloc>& __rhs)
  730.     { return __lhs._M_base() > __rhs._M_base(); }
  731.  
  732.   template<typename _Tp, typename _Alloc>
  733.     inline void
  734.     swap(vector<_Tp, _Alloc>& __lhs, vector<_Tp, _Alloc>& __rhs)
  735.     { __lhs.swap(__rhs); }
  736.  
  737. } // namespace __debug
  738.  
  739. #if __cplusplus >= 201103L
  740.   // DR 1182.
  741.   /// std::hash specialization for vector<bool>.
  742.   template<typename _Alloc>
  743.     struct hash<__debug::vector<bool, _Alloc>>
  744.     : public __hash_base<size_t, __debug::vector<bool, _Alloc>>
  745.     {
  746.       size_t
  747.       operator()(const __debug::vector<bool, _Alloc>& __b) const noexcept
  748.       { return std::hash<_GLIBCXX_STD_C::vector<bool, _Alloc>>()
  749.           (__b._M_base()); }
  750.     };
  751. #endif
  752.  
  753. } // namespace std
  754.  
  755. namespace __gnu_debug
  756. {
  757.   template<typename _Tp, typename _Alloc>
  758.     struct _Is_contiguous_sequence<std::__debug::vector<_Tp, _Alloc> >
  759.     : std::__true_type
  760.     { };
  761.  
  762.   template<typename _Alloc>
  763.     struct _Is_contiguous_sequence<std::__debug::vector<bool, _Alloc> >
  764.     : std::__false_type
  765.     { };
  766. }
  767.  
  768. #endif
  769.