1ffeaf689SAlexander Kabaev// Debugging list implementation -*- C++ -*- 2ffeaf689SAlexander Kabaev 3*f8a1b7d9SAlexander Kabaev// Copyright (C) 2003, 2004, 2005, 2006 4ffeaf689SAlexander Kabaev// Free Software Foundation, Inc. 5ffeaf689SAlexander Kabaev// 6ffeaf689SAlexander Kabaev// This file is part of the GNU ISO C++ Library. This library is free 7ffeaf689SAlexander Kabaev// software; you can redistribute it and/or modify it under the 8ffeaf689SAlexander Kabaev// terms of the GNU General Public License as published by the 9ffeaf689SAlexander Kabaev// Free Software Foundation; either version 2, or (at your option) 10ffeaf689SAlexander Kabaev// any later version. 11ffeaf689SAlexander Kabaev 12ffeaf689SAlexander Kabaev// This library is distributed in the hope that it will be useful, 13ffeaf689SAlexander Kabaev// but WITHOUT ANY WARRANTY; without even the implied warranty of 14ffeaf689SAlexander Kabaev// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15ffeaf689SAlexander Kabaev// GNU General Public License for more details. 16ffeaf689SAlexander Kabaev 17ffeaf689SAlexander Kabaev// You should have received a copy of the GNU General Public License along 18ffeaf689SAlexander Kabaev// with this library; see the file COPYING. If not, write to the Free 19*f8a1b7d9SAlexander Kabaev// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, 20ffeaf689SAlexander Kabaev// USA. 21ffeaf689SAlexander Kabaev 22ffeaf689SAlexander Kabaev// As a special exception, you may use this file as part of a free software 23ffeaf689SAlexander Kabaev// library without restriction. Specifically, if other files instantiate 24ffeaf689SAlexander Kabaev// templates or use macros or inline functions from this file, or you compile 25ffeaf689SAlexander Kabaev// this file and link it with other files to produce an executable, this 26ffeaf689SAlexander Kabaev// file does not by itself cause the resulting executable to be covered by 27ffeaf689SAlexander Kabaev// the GNU General Public License. This exception does not however 28ffeaf689SAlexander Kabaev// invalidate any other reasons why the executable file might be covered by 29ffeaf689SAlexander Kabaev// the GNU General Public License. 30ffeaf689SAlexander Kabaev 31*f8a1b7d9SAlexander Kabaev// Free Software Foundation, Inc. 32*f8a1b7d9SAlexander Kabaev// 33*f8a1b7d9SAlexander Kabaev// This file is part of the GNU ISO C++ Library. This library is free 34*f8a1b7d9SAlexander Kabaev// software; you can redistribute it and/or modify it under the 35*f8a1b7d9SAlexander Kabaev// terms of the GNU General Public License as published by the 36*f8a1b7d9SAlexander Kabaev// Free Software Foundation; either version 2, or (at your option) 37*f8a1b7d9SAlexander Kabaev// any later version. 38*f8a1b7d9SAlexander Kabaev 39*f8a1b7d9SAlexander Kabaev// This library is distributed in the hope that it will be useful, 40*f8a1b7d9SAlexander Kabaev// but WITHOUT ANY WARRANTY; without even the implied warranty of 41*f8a1b7d9SAlexander Kabaev// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 42*f8a1b7d9SAlexander Kabaev// GNU General Public License for more details. 43*f8a1b7d9SAlexander Kabaev 44*f8a1b7d9SAlexander Kabaev// You should have received a copy of the GNU General Public License along 45*f8a1b7d9SAlexander Kabaev// with this library; see the file COPYING. If not, write to the Free 46*f8a1b7d9SAlexander Kabaev// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, 47*f8a1b7d9SAlexander Kabaev// USA. 48*f8a1b7d9SAlexander Kabaev 49*f8a1b7d9SAlexander Kabaev// As a special exception, you may use this file as part of a free software 50*f8a1b7d9SAlexander Kabaev// library without restriction. Specifically, if other files instantiate 51*f8a1b7d9SAlexander Kabaev// templates or use macros or inline functions from this file, or you compile 52*f8a1b7d9SAlexander Kabaev// this file and link it with other files to produce an executable, this 53*f8a1b7d9SAlexander Kabaev// file does not by itself cause the resulting executable to be covered by 54*f8a1b7d9SAlexander Kabaev// the GNU General Public License. This exception does not however 55*f8a1b7d9SAlexander Kabaev// invalidate any other reasons why the executable file might be covered by 56*f8a1b7d9SAlexander Kabaev// the GNU General Public License. 57*f8a1b7d9SAlexander Kabaev 58*f8a1b7d9SAlexander Kabaev/** @file debug/list 59*f8a1b7d9SAlexander Kabaev * This file is a GNU debug extension to the Standard C++ Library. 60*f8a1b7d9SAlexander Kabaev */ 61*f8a1b7d9SAlexander Kabaev 62ffeaf689SAlexander Kabaev#ifndef _GLIBCXX_DEBUG_LIST 63ffeaf689SAlexander Kabaev#define _GLIBCXX_DEBUG_LIST 1 64ffeaf689SAlexander Kabaev 65ffeaf689SAlexander Kabaev#include <list> 66ffeaf689SAlexander Kabaev#include <bits/stl_algo.h> 67ffeaf689SAlexander Kabaev#include <debug/safe_sequence.h> 68ffeaf689SAlexander Kabaev#include <debug/safe_iterator.h> 69ffeaf689SAlexander Kabaev 70*f8a1b7d9SAlexander Kabaevnamespace std 71*f8a1b7d9SAlexander Kabaev{ 72*f8a1b7d9SAlexander Kabaevnamespace __debug 73ffeaf689SAlexander Kabaev{ 74ffeaf689SAlexander Kabaev template<typename _Tp, typename _Allocator = std::allocator<_Tp> > 75ffeaf689SAlexander Kabaev class list 76ffeaf689SAlexander Kabaev : public _GLIBCXX_STD::list<_Tp, _Allocator>, 77ffeaf689SAlexander Kabaev public __gnu_debug::_Safe_sequence<list<_Tp, _Allocator> > 78ffeaf689SAlexander Kabaev { 79ffeaf689SAlexander Kabaev typedef _GLIBCXX_STD::list<_Tp, _Allocator> _Base; 80ffeaf689SAlexander Kabaev typedef __gnu_debug::_Safe_sequence<list> _Safe_base; 81ffeaf689SAlexander Kabaev 82ffeaf689SAlexander Kabaev public: 83*f8a1b7d9SAlexander Kabaev typedef typename _Base::reference reference; 84*f8a1b7d9SAlexander Kabaev typedef typename _Base::const_reference const_reference; 85ffeaf689SAlexander Kabaev 86ffeaf689SAlexander Kabaev typedef __gnu_debug::_Safe_iterator<typename _Base::iterator, list> 87ffeaf689SAlexander Kabaev iterator; 88ffeaf689SAlexander Kabaev typedef __gnu_debug::_Safe_iterator<typename _Base::const_iterator, list> 89ffeaf689SAlexander Kabaev const_iterator; 90ffeaf689SAlexander Kabaev 91ffeaf689SAlexander Kabaev typedef typename _Base::size_type size_type; 92ffeaf689SAlexander Kabaev typedef typename _Base::difference_type difference_type; 93ffeaf689SAlexander Kabaev 94ffeaf689SAlexander Kabaev typedef _Tp value_type; 95ffeaf689SAlexander Kabaev typedef _Allocator allocator_type; 96*f8a1b7d9SAlexander Kabaev typedef typename _Base::pointer pointer; 97*f8a1b7d9SAlexander Kabaev typedef typename _Base::const_pointer const_pointer; 98ffeaf689SAlexander Kabaev typedef std::reverse_iterator<iterator> reverse_iterator; 99ffeaf689SAlexander Kabaev typedef std::reverse_iterator<const_iterator> const_reverse_iterator; 100ffeaf689SAlexander Kabaev 101ffeaf689SAlexander Kabaev // 23.2.2.1 construct/copy/destroy: 102ffeaf689SAlexander Kabaev explicit list(const _Allocator& __a = _Allocator()) 103ffeaf689SAlexander Kabaev : _Base(__a) { } 104ffeaf689SAlexander Kabaev 105ffeaf689SAlexander Kabaev explicit list(size_type __n, const _Tp& __value = _Tp(), 106ffeaf689SAlexander Kabaev const _Allocator& __a = _Allocator()) 107ffeaf689SAlexander Kabaev : _Base(__n, __value, __a) { } 108ffeaf689SAlexander Kabaev 109ffeaf689SAlexander Kabaev template<class _InputIterator> 110ffeaf689SAlexander Kabaev list(_InputIterator __first, _InputIterator __last, 111ffeaf689SAlexander Kabaev const _Allocator& __a = _Allocator()) 112ffeaf689SAlexander Kabaev : _Base(__gnu_debug::__check_valid_range(__first, __last), __last, __a) 113ffeaf689SAlexander Kabaev { } 114ffeaf689SAlexander Kabaev 115ffeaf689SAlexander Kabaev 116ffeaf689SAlexander Kabaev list(const list& __x) : _Base(__x), _Safe_base() { } 117ffeaf689SAlexander Kabaev 118ffeaf689SAlexander Kabaev list(const _Base& __x) : _Base(__x), _Safe_base() { } 119ffeaf689SAlexander Kabaev 120ffeaf689SAlexander Kabaev ~list() { } 121ffeaf689SAlexander Kabaev 122ffeaf689SAlexander Kabaev list& 123ffeaf689SAlexander Kabaev operator=(const list& __x) 124ffeaf689SAlexander Kabaev { 125ffeaf689SAlexander Kabaev static_cast<_Base&>(*this) = __x; 126ffeaf689SAlexander Kabaev this->_M_invalidate_all(); 127ffeaf689SAlexander Kabaev return *this; 128ffeaf689SAlexander Kabaev } 129ffeaf689SAlexander Kabaev 130ffeaf689SAlexander Kabaev template<class _InputIterator> 131ffeaf689SAlexander Kabaev void 132ffeaf689SAlexander Kabaev assign(_InputIterator __first, _InputIterator __last) 133ffeaf689SAlexander Kabaev { 134ffeaf689SAlexander Kabaev __glibcxx_check_valid_range(__first, __last); 135ffeaf689SAlexander Kabaev _Base::assign(__first, __last); 136ffeaf689SAlexander Kabaev this->_M_invalidate_all(); 137ffeaf689SAlexander Kabaev } 138ffeaf689SAlexander Kabaev 139ffeaf689SAlexander Kabaev void 140ffeaf689SAlexander Kabaev assign(size_type __n, const _Tp& __t) 141ffeaf689SAlexander Kabaev { 142ffeaf689SAlexander Kabaev _Base::assign(__n, __t); 143ffeaf689SAlexander Kabaev this->_M_invalidate_all(); 144ffeaf689SAlexander Kabaev } 145ffeaf689SAlexander Kabaev 146ffeaf689SAlexander Kabaev using _Base::get_allocator; 147ffeaf689SAlexander Kabaev 148ffeaf689SAlexander Kabaev // iterators: 149ffeaf689SAlexander Kabaev iterator 150ffeaf689SAlexander Kabaev begin() 151ffeaf689SAlexander Kabaev { return iterator(_Base::begin(), this); } 152ffeaf689SAlexander Kabaev 153ffeaf689SAlexander Kabaev const_iterator 154ffeaf689SAlexander Kabaev begin() const 155ffeaf689SAlexander Kabaev { return const_iterator(_Base::begin(), this); } 156ffeaf689SAlexander Kabaev 157ffeaf689SAlexander Kabaev iterator 158ffeaf689SAlexander Kabaev end() 159ffeaf689SAlexander Kabaev { return iterator(_Base::end(), this); } 160ffeaf689SAlexander Kabaev 161ffeaf689SAlexander Kabaev const_iterator 162ffeaf689SAlexander Kabaev end() const 163ffeaf689SAlexander Kabaev { return const_iterator(_Base::end(), this); } 164ffeaf689SAlexander Kabaev 165ffeaf689SAlexander Kabaev reverse_iterator 166ffeaf689SAlexander Kabaev rbegin() 167ffeaf689SAlexander Kabaev { return reverse_iterator(end()); } 168ffeaf689SAlexander Kabaev 169ffeaf689SAlexander Kabaev const_reverse_iterator 170ffeaf689SAlexander Kabaev rbegin() const 171ffeaf689SAlexander Kabaev { return const_reverse_iterator(end()); } 172ffeaf689SAlexander Kabaev 173ffeaf689SAlexander Kabaev reverse_iterator 174ffeaf689SAlexander Kabaev rend() 175ffeaf689SAlexander Kabaev { return reverse_iterator(begin()); } 176ffeaf689SAlexander Kabaev 177ffeaf689SAlexander Kabaev const_reverse_iterator 178ffeaf689SAlexander Kabaev rend() const 179ffeaf689SAlexander Kabaev { return const_reverse_iterator(begin()); } 180ffeaf689SAlexander Kabaev 181ffeaf689SAlexander Kabaev // 23.2.2.2 capacity: 182ffeaf689SAlexander Kabaev using _Base::empty; 183ffeaf689SAlexander Kabaev using _Base::size; 184ffeaf689SAlexander Kabaev using _Base::max_size; 185ffeaf689SAlexander Kabaev 186ffeaf689SAlexander Kabaev void 187ffeaf689SAlexander Kabaev resize(size_type __sz, _Tp __c = _Tp()) 188ffeaf689SAlexander Kabaev { 189ffeaf689SAlexander Kabaev this->_M_detach_singular(); 190ffeaf689SAlexander Kabaev 191ffeaf689SAlexander Kabaev // if __sz < size(), invalidate all iterators in [begin+__sz, end()) 192ffeaf689SAlexander Kabaev iterator __victim = begin(); 193ffeaf689SAlexander Kabaev iterator __end = end(); 194ffeaf689SAlexander Kabaev for (size_type __i = __sz; __victim != __end && __i > 0; --__i) 195ffeaf689SAlexander Kabaev ++__victim; 196ffeaf689SAlexander Kabaev 197ffeaf689SAlexander Kabaev while (__victim != __end) 198ffeaf689SAlexander Kabaev { 199ffeaf689SAlexander Kabaev iterator __real_victim = __victim++; 200ffeaf689SAlexander Kabaev __real_victim._M_invalidate(); 201ffeaf689SAlexander Kabaev } 202ffeaf689SAlexander Kabaev 203ffeaf689SAlexander Kabaev try 204ffeaf689SAlexander Kabaev { 205ffeaf689SAlexander Kabaev _Base::resize(__sz, __c); 206ffeaf689SAlexander Kabaev } 207ffeaf689SAlexander Kabaev catch(...) 208ffeaf689SAlexander Kabaev { 209ffeaf689SAlexander Kabaev this->_M_revalidate_singular(); 210ffeaf689SAlexander Kabaev __throw_exception_again; 211ffeaf689SAlexander Kabaev } 212ffeaf689SAlexander Kabaev } 213ffeaf689SAlexander Kabaev 214ffeaf689SAlexander Kabaev // element access: 215ffeaf689SAlexander Kabaev reference 216ffeaf689SAlexander Kabaev front() 217ffeaf689SAlexander Kabaev { 218ffeaf689SAlexander Kabaev __glibcxx_check_nonempty(); 219ffeaf689SAlexander Kabaev return _Base::front(); 220ffeaf689SAlexander Kabaev } 221ffeaf689SAlexander Kabaev 222ffeaf689SAlexander Kabaev const_reference 223ffeaf689SAlexander Kabaev front() const 224ffeaf689SAlexander Kabaev { 225ffeaf689SAlexander Kabaev __glibcxx_check_nonempty(); 226ffeaf689SAlexander Kabaev return _Base::front(); 227ffeaf689SAlexander Kabaev } 228ffeaf689SAlexander Kabaev 229ffeaf689SAlexander Kabaev reference 230ffeaf689SAlexander Kabaev back() 231ffeaf689SAlexander Kabaev { 232ffeaf689SAlexander Kabaev __glibcxx_check_nonempty(); 233ffeaf689SAlexander Kabaev return _Base::back(); 234ffeaf689SAlexander Kabaev } 235ffeaf689SAlexander Kabaev 236ffeaf689SAlexander Kabaev const_reference 237ffeaf689SAlexander Kabaev back() const 238ffeaf689SAlexander Kabaev { 239ffeaf689SAlexander Kabaev __glibcxx_check_nonempty(); 240ffeaf689SAlexander Kabaev return _Base::back(); 241ffeaf689SAlexander Kabaev } 242ffeaf689SAlexander Kabaev 243ffeaf689SAlexander Kabaev // 23.2.2.3 modifiers: 244ffeaf689SAlexander Kabaev using _Base::push_front; 245ffeaf689SAlexander Kabaev 246ffeaf689SAlexander Kabaev void 247ffeaf689SAlexander Kabaev pop_front() 248ffeaf689SAlexander Kabaev { 249ffeaf689SAlexander Kabaev __glibcxx_check_nonempty(); 250ffeaf689SAlexander Kabaev iterator __victim = begin(); 251ffeaf689SAlexander Kabaev __victim._M_invalidate(); 252ffeaf689SAlexander Kabaev _Base::pop_front(); 253ffeaf689SAlexander Kabaev } 254ffeaf689SAlexander Kabaev 255ffeaf689SAlexander Kabaev using _Base::push_back; 256ffeaf689SAlexander Kabaev 257ffeaf689SAlexander Kabaev void 258ffeaf689SAlexander Kabaev pop_back() 259ffeaf689SAlexander Kabaev { 260ffeaf689SAlexander Kabaev __glibcxx_check_nonempty(); 261ffeaf689SAlexander Kabaev iterator __victim = end(); 262ffeaf689SAlexander Kabaev --__victim; 263ffeaf689SAlexander Kabaev __victim._M_invalidate(); 264ffeaf689SAlexander Kabaev _Base::pop_back(); 265ffeaf689SAlexander Kabaev } 266ffeaf689SAlexander Kabaev 267ffeaf689SAlexander Kabaev iterator 268ffeaf689SAlexander Kabaev insert(iterator __position, const _Tp& __x) 269ffeaf689SAlexander Kabaev { 270ffeaf689SAlexander Kabaev __glibcxx_check_insert(__position); 271ffeaf689SAlexander Kabaev return iterator(_Base::insert(__position.base(), __x), this); 272ffeaf689SAlexander Kabaev } 273ffeaf689SAlexander Kabaev 274ffeaf689SAlexander Kabaev void 275ffeaf689SAlexander Kabaev insert(iterator __position, size_type __n, const _Tp& __x) 276ffeaf689SAlexander Kabaev { 277ffeaf689SAlexander Kabaev __glibcxx_check_insert(__position); 278ffeaf689SAlexander Kabaev _Base::insert(__position.base(), __n, __x); 279ffeaf689SAlexander Kabaev } 280ffeaf689SAlexander Kabaev 281ffeaf689SAlexander Kabaev template<class _InputIterator> 282ffeaf689SAlexander Kabaev void 283ffeaf689SAlexander Kabaev insert(iterator __position, _InputIterator __first, 284ffeaf689SAlexander Kabaev _InputIterator __last) 285ffeaf689SAlexander Kabaev { 286ffeaf689SAlexander Kabaev __glibcxx_check_insert_range(__position, __first, __last); 287ffeaf689SAlexander Kabaev _Base::insert(__position.base(), __first, __last); 288ffeaf689SAlexander Kabaev } 289ffeaf689SAlexander Kabaev 290ffeaf689SAlexander Kabaev iterator 291ffeaf689SAlexander Kabaev erase(iterator __position) 292ffeaf689SAlexander Kabaev { 293ffeaf689SAlexander Kabaev __glibcxx_check_erase(__position); 294ffeaf689SAlexander Kabaev __position._M_invalidate(); 295ffeaf689SAlexander Kabaev return iterator(_Base::erase(__position.base()), this); 296ffeaf689SAlexander Kabaev } 297ffeaf689SAlexander Kabaev 298ffeaf689SAlexander Kabaev iterator 299ffeaf689SAlexander Kabaev erase(iterator __position, iterator __last) 300ffeaf689SAlexander Kabaev { 301ffeaf689SAlexander Kabaev // _GLIBCXX_RESOLVE_LIB_DEFECTS 302ffeaf689SAlexander Kabaev // 151. can't currently clear() empty container 303ffeaf689SAlexander Kabaev __glibcxx_check_erase_range(__position, __last); 304ffeaf689SAlexander Kabaev for (iterator __victim = __position; __victim != __last; ) 305ffeaf689SAlexander Kabaev { 306ffeaf689SAlexander Kabaev iterator __old = __victim; 307ffeaf689SAlexander Kabaev ++__victim; 308ffeaf689SAlexander Kabaev __old._M_invalidate(); 309ffeaf689SAlexander Kabaev } 310ffeaf689SAlexander Kabaev return iterator(_Base::erase(__position.base(), __last.base()), this); 311ffeaf689SAlexander Kabaev } 312ffeaf689SAlexander Kabaev 313ffeaf689SAlexander Kabaev void 314ffeaf689SAlexander Kabaev swap(list& __x) 315ffeaf689SAlexander Kabaev { 316ffeaf689SAlexander Kabaev _Base::swap(__x); 317ffeaf689SAlexander Kabaev this->_M_swap(__x); 318ffeaf689SAlexander Kabaev } 319ffeaf689SAlexander Kabaev 320ffeaf689SAlexander Kabaev void 321ffeaf689SAlexander Kabaev clear() 322ffeaf689SAlexander Kabaev { 323ffeaf689SAlexander Kabaev _Base::clear(); 324ffeaf689SAlexander Kabaev this->_M_invalidate_all(); 325ffeaf689SAlexander Kabaev } 326ffeaf689SAlexander Kabaev 327ffeaf689SAlexander Kabaev // 23.2.2.4 list operations: 328ffeaf689SAlexander Kabaev void 329ffeaf689SAlexander Kabaev splice(iterator __position, list& __x) 330ffeaf689SAlexander Kabaev { 331ffeaf689SAlexander Kabaev _GLIBCXX_DEBUG_VERIFY(&__x != this, 332*f8a1b7d9SAlexander Kabaev _M_message(__gnu_debug::__msg_self_splice) 333ffeaf689SAlexander Kabaev ._M_sequence(*this, "this")); 334ffeaf689SAlexander Kabaev this->splice(__position, __x, __x.begin(), __x.end()); 335ffeaf689SAlexander Kabaev } 336ffeaf689SAlexander Kabaev 337ffeaf689SAlexander Kabaev void 338ffeaf689SAlexander Kabaev splice(iterator __position, list& __x, iterator __i) 339ffeaf689SAlexander Kabaev { 340ffeaf689SAlexander Kabaev __glibcxx_check_insert(__position); 341*f8a1b7d9SAlexander Kabaev 342*f8a1b7d9SAlexander Kabaev // We used to perform the splice_alloc check: not anymore, redundant 343*f8a1b7d9SAlexander Kabaev // after implementing the relevant bits of N1599. 344*f8a1b7d9SAlexander Kabaev 345ffeaf689SAlexander Kabaev _GLIBCXX_DEBUG_VERIFY(__i._M_dereferenceable(), 346*f8a1b7d9SAlexander Kabaev _M_message(__gnu_debug::__msg_splice_bad) 347ffeaf689SAlexander Kabaev ._M_iterator(__i, "__i")); 348ffeaf689SAlexander Kabaev _GLIBCXX_DEBUG_VERIFY(__i._M_attached_to(&__x), 349*f8a1b7d9SAlexander Kabaev _M_message(__gnu_debug::__msg_splice_other) 350ffeaf689SAlexander Kabaev ._M_iterator(__i, "__i")._M_sequence(__x, "__x")); 351ffeaf689SAlexander Kabaev 352ffeaf689SAlexander Kabaev // _GLIBCXX_RESOLVE_LIB_DEFECTS 353ffeaf689SAlexander Kabaev // 250. splicing invalidates iterators 354ffeaf689SAlexander Kabaev this->_M_transfer_iter(__i); 355ffeaf689SAlexander Kabaev _Base::splice(__position.base(), __x._M_base(), __i.base()); 356ffeaf689SAlexander Kabaev } 357ffeaf689SAlexander Kabaev 358ffeaf689SAlexander Kabaev void 359ffeaf689SAlexander Kabaev splice(iterator __position, list& __x, iterator __first, iterator __last) 360ffeaf689SAlexander Kabaev { 361ffeaf689SAlexander Kabaev __glibcxx_check_insert(__position); 362ffeaf689SAlexander Kabaev __glibcxx_check_valid_range(__first, __last); 363ffeaf689SAlexander Kabaev _GLIBCXX_DEBUG_VERIFY(__first._M_attached_to(&__x), 364*f8a1b7d9SAlexander Kabaev _M_message(__gnu_debug::__msg_splice_other) 365ffeaf689SAlexander Kabaev ._M_sequence(__x, "x") 366ffeaf689SAlexander Kabaev ._M_iterator(__first, "first")); 367*f8a1b7d9SAlexander Kabaev 368*f8a1b7d9SAlexander Kabaev // We used to perform the splice_alloc check: not anymore, redundant 369*f8a1b7d9SAlexander Kabaev // after implementing the relevant bits of N1599. 370ffeaf689SAlexander Kabaev 371ffeaf689SAlexander Kabaev for (iterator __tmp = __first; __tmp != __last; ) 372ffeaf689SAlexander Kabaev { 373ffeaf689SAlexander Kabaev _GLIBCXX_DEBUG_VERIFY(&__x != this || __tmp != __position, 374*f8a1b7d9SAlexander Kabaev _M_message(__gnu_debug::__msg_splice_overlap) 375ffeaf689SAlexander Kabaev ._M_iterator(__tmp, "position") 376ffeaf689SAlexander Kabaev ._M_iterator(__first, "first") 377ffeaf689SAlexander Kabaev ._M_iterator(__last, "last")); 378ffeaf689SAlexander Kabaev iterator __victim = __tmp++; 379ffeaf689SAlexander Kabaev // _GLIBCXX_RESOLVE_LIB_DEFECTS 380ffeaf689SAlexander Kabaev // 250. splicing invalidates iterators 381ffeaf689SAlexander Kabaev this->_M_transfer_iter(__victim); 382ffeaf689SAlexander Kabaev } 383ffeaf689SAlexander Kabaev 384ffeaf689SAlexander Kabaev _Base::splice(__position.base(), __x._M_base(), __first.base(), 385ffeaf689SAlexander Kabaev __last.base()); 386ffeaf689SAlexander Kabaev } 387ffeaf689SAlexander Kabaev 388ffeaf689SAlexander Kabaev void 389ffeaf689SAlexander Kabaev remove(const _Tp& __value) 390ffeaf689SAlexander Kabaev { 391ffeaf689SAlexander Kabaev for (iterator __x = begin(); __x.base() != _Base::end(); ) 392ffeaf689SAlexander Kabaev { 393ffeaf689SAlexander Kabaev if (*__x == __value) 394ffeaf689SAlexander Kabaev __x = erase(__x); 395ffeaf689SAlexander Kabaev else 396ffeaf689SAlexander Kabaev ++__x; 397ffeaf689SAlexander Kabaev } 398ffeaf689SAlexander Kabaev } 399ffeaf689SAlexander Kabaev 400ffeaf689SAlexander Kabaev template<class _Predicate> 401ffeaf689SAlexander Kabaev void 402ffeaf689SAlexander Kabaev remove_if(_Predicate __pred) 403ffeaf689SAlexander Kabaev { 404ffeaf689SAlexander Kabaev for (iterator __x = begin(); __x.base() != _Base::end(); ) 405ffeaf689SAlexander Kabaev { 406ffeaf689SAlexander Kabaev if (__pred(*__x)) 407ffeaf689SAlexander Kabaev __x = erase(__x); 408ffeaf689SAlexander Kabaev else 409ffeaf689SAlexander Kabaev ++__x; 410ffeaf689SAlexander Kabaev } 411ffeaf689SAlexander Kabaev } 412ffeaf689SAlexander Kabaev 413ffeaf689SAlexander Kabaev void 414ffeaf689SAlexander Kabaev unique() 415ffeaf689SAlexander Kabaev { 416ffeaf689SAlexander Kabaev iterator __first = begin(); 417ffeaf689SAlexander Kabaev iterator __last = end(); 418ffeaf689SAlexander Kabaev if (__first == __last) 419ffeaf689SAlexander Kabaev return; 420ffeaf689SAlexander Kabaev iterator __next = __first; 421ffeaf689SAlexander Kabaev while (++__next != __last) 422ffeaf689SAlexander Kabaev { 423ffeaf689SAlexander Kabaev if (*__first == *__next) 424ffeaf689SAlexander Kabaev erase(__next); 425ffeaf689SAlexander Kabaev else 426ffeaf689SAlexander Kabaev __first = __next; 427ffeaf689SAlexander Kabaev __next = __first; 428ffeaf689SAlexander Kabaev } 429ffeaf689SAlexander Kabaev } 430ffeaf689SAlexander Kabaev 431ffeaf689SAlexander Kabaev template<class _BinaryPredicate> 432ffeaf689SAlexander Kabaev void 433ffeaf689SAlexander Kabaev unique(_BinaryPredicate __binary_pred) 434ffeaf689SAlexander Kabaev { 435ffeaf689SAlexander Kabaev iterator __first = begin(); 436ffeaf689SAlexander Kabaev iterator __last = end(); 437ffeaf689SAlexander Kabaev if (__first == __last) 438ffeaf689SAlexander Kabaev return; 439ffeaf689SAlexander Kabaev iterator __next = __first; 440ffeaf689SAlexander Kabaev while (++__next != __last) 441ffeaf689SAlexander Kabaev { 442ffeaf689SAlexander Kabaev if (__binary_pred(*__first, *__next)) 443ffeaf689SAlexander Kabaev erase(__next); 444ffeaf689SAlexander Kabaev else 445ffeaf689SAlexander Kabaev __first = __next; 446ffeaf689SAlexander Kabaev __next = __first; 447ffeaf689SAlexander Kabaev } 448ffeaf689SAlexander Kabaev } 449ffeaf689SAlexander Kabaev 450ffeaf689SAlexander Kabaev void 451ffeaf689SAlexander Kabaev merge(list& __x) 452ffeaf689SAlexander Kabaev { 453ffeaf689SAlexander Kabaev __glibcxx_check_sorted(_Base::begin(), _Base::end()); 454ffeaf689SAlexander Kabaev __glibcxx_check_sorted(__x.begin().base(), __x.end().base()); 455ffeaf689SAlexander Kabaev for (iterator __tmp = __x.begin(); __tmp != __x.end(); ) 456ffeaf689SAlexander Kabaev { 457ffeaf689SAlexander Kabaev iterator __victim = __tmp++; 458ffeaf689SAlexander Kabaev __victim._M_attach(&__x); 459ffeaf689SAlexander Kabaev } 460ffeaf689SAlexander Kabaev _Base::merge(__x._M_base()); 461ffeaf689SAlexander Kabaev } 462ffeaf689SAlexander Kabaev 463ffeaf689SAlexander Kabaev template<class _Compare> 464ffeaf689SAlexander Kabaev void 465ffeaf689SAlexander Kabaev merge(list& __x, _Compare __comp) 466ffeaf689SAlexander Kabaev { 467ffeaf689SAlexander Kabaev __glibcxx_check_sorted_pred(_Base::begin(), _Base::end(), __comp); 468ffeaf689SAlexander Kabaev __glibcxx_check_sorted_pred(__x.begin().base(), __x.end().base(), 469ffeaf689SAlexander Kabaev __comp); 470ffeaf689SAlexander Kabaev for (iterator __tmp = __x.begin(); __tmp != __x.end(); ) 471ffeaf689SAlexander Kabaev { 472ffeaf689SAlexander Kabaev iterator __victim = __tmp++; 473ffeaf689SAlexander Kabaev __victim._M_attach(&__x); 474ffeaf689SAlexander Kabaev } 475ffeaf689SAlexander Kabaev _Base::merge(__x._M_base(), __comp); 476ffeaf689SAlexander Kabaev } 477ffeaf689SAlexander Kabaev 478ffeaf689SAlexander Kabaev void 479ffeaf689SAlexander Kabaev sort() { _Base::sort(); } 480ffeaf689SAlexander Kabaev 481ffeaf689SAlexander Kabaev template<typename _StrictWeakOrdering> 482ffeaf689SAlexander Kabaev void 483ffeaf689SAlexander Kabaev sort(_StrictWeakOrdering __pred) { _Base::sort(__pred); } 484ffeaf689SAlexander Kabaev 485ffeaf689SAlexander Kabaev using _Base::reverse; 486ffeaf689SAlexander Kabaev 487ffeaf689SAlexander Kabaev _Base& 488ffeaf689SAlexander Kabaev _M_base() { return *this; } 489ffeaf689SAlexander Kabaev 490ffeaf689SAlexander Kabaev const _Base& 491ffeaf689SAlexander Kabaev _M_base() const { return *this; } 492ffeaf689SAlexander Kabaev 493ffeaf689SAlexander Kabaev private: 494ffeaf689SAlexander Kabaev void 495ffeaf689SAlexander Kabaev _M_invalidate_all() 496ffeaf689SAlexander Kabaev { 497ffeaf689SAlexander Kabaev typedef typename _Base::const_iterator _Base_const_iterator; 498ffeaf689SAlexander Kabaev typedef __gnu_debug::_Not_equal_to<_Base_const_iterator> _Not_equal; 499ffeaf689SAlexander Kabaev this->_M_invalidate_if(_Not_equal(_M_base().end())); 500ffeaf689SAlexander Kabaev } 501ffeaf689SAlexander Kabaev }; 502ffeaf689SAlexander Kabaev 503ffeaf689SAlexander Kabaev template<typename _Tp, typename _Alloc> 504ffeaf689SAlexander Kabaev inline bool 505ffeaf689SAlexander Kabaev operator==(const list<_Tp, _Alloc>& __lhs, const list<_Tp, _Alloc>& __rhs) 506ffeaf689SAlexander Kabaev { return __lhs._M_base() == __rhs._M_base(); } 507ffeaf689SAlexander Kabaev 508ffeaf689SAlexander Kabaev template<typename _Tp, typename _Alloc> 509ffeaf689SAlexander Kabaev inline bool 510ffeaf689SAlexander Kabaev operator!=(const list<_Tp, _Alloc>& __lhs, const list<_Tp, _Alloc>& __rhs) 511ffeaf689SAlexander Kabaev { return __lhs._M_base() != __rhs._M_base(); } 512ffeaf689SAlexander Kabaev 513ffeaf689SAlexander Kabaev template<typename _Tp, typename _Alloc> 514ffeaf689SAlexander Kabaev inline bool 515ffeaf689SAlexander Kabaev operator<(const list<_Tp, _Alloc>& __lhs, const list<_Tp, _Alloc>& __rhs) 516ffeaf689SAlexander Kabaev { return __lhs._M_base() < __rhs._M_base(); } 517ffeaf689SAlexander Kabaev 518ffeaf689SAlexander Kabaev template<typename _Tp, typename _Alloc> 519ffeaf689SAlexander Kabaev inline bool 520ffeaf689SAlexander Kabaev operator<=(const list<_Tp, _Alloc>& __lhs, const list<_Tp, _Alloc>& __rhs) 521ffeaf689SAlexander Kabaev { return __lhs._M_base() <= __rhs._M_base(); } 522ffeaf689SAlexander Kabaev 523ffeaf689SAlexander Kabaev template<typename _Tp, typename _Alloc> 524ffeaf689SAlexander Kabaev inline bool 525ffeaf689SAlexander Kabaev operator>=(const list<_Tp, _Alloc>& __lhs, const list<_Tp, _Alloc>& __rhs) 526ffeaf689SAlexander Kabaev { return __lhs._M_base() >= __rhs._M_base(); } 527ffeaf689SAlexander Kabaev 528ffeaf689SAlexander Kabaev template<typename _Tp, typename _Alloc> 529ffeaf689SAlexander Kabaev inline bool 530ffeaf689SAlexander Kabaev operator>(const list<_Tp, _Alloc>& __lhs, const list<_Tp, _Alloc>& __rhs) 531ffeaf689SAlexander Kabaev { return __lhs._M_base() > __rhs._M_base(); } 532ffeaf689SAlexander Kabaev 533ffeaf689SAlexander Kabaev template<typename _Tp, typename _Alloc> 534ffeaf689SAlexander Kabaev inline void 535ffeaf689SAlexander Kabaev swap(list<_Tp, _Alloc>& __lhs, list<_Tp, _Alloc>& __rhs) 536ffeaf689SAlexander Kabaev { __lhs.swap(__rhs); } 537*f8a1b7d9SAlexander Kabaev} // namespace __debug 538*f8a1b7d9SAlexander Kabaev} // namespace std 539ffeaf689SAlexander Kabaev 540ffeaf689SAlexander Kabaev#endif 541