epoc32/include/stdapis/stlport/stl/_deque.h
author William Roberts <williamr@symbian.org>
Wed, 31 Mar 2010 12:27:01 +0100
branchSymbian2
changeset 3 e1b950c65cb4
parent 0 061f57f2323e
permissions -rw-r--r--
Attempt to represent the S^2->S^3 header reorganisation as a series of "hg rename" operations
     1 /*
     2  * © Portions copyright (c) 2006-2007 Nokia Corporation.  All rights reserved.
     3  *
     4  * Copyright (c) 1994
     5  * Hewlett-Packard Company
     6  *
     7  * Copyright (c) 1996,1997
     8  * Silicon Graphics Computer Systems, Inc.
     9  *
    10  * Copyright (c) 1997
    11  * Moscow Center for SPARC Technology
    12  *
    13  * Copyright (c) 1999 
    14  * Boris Fomitchev
    15  *
    16  * This material is provided "as is", with absolutely no warranty expressed
    17  * or implied. Any use is at your own risk.
    18  *
    19  * Permission to use or copy this software for any purpose is hereby granted 
    20  * without fee, provided the above notices are retained on all copies.
    21  * Permission to modify the code and to distribute modified code is granted,
    22  * provided the above notices are retained, and a notice that the code was
    23  * modified is included with the above copyright notice.
    24  *
    25  */
    26 
    27 /* NOTE: This is an internal header file, included by other STL headers.
    28  *   You should not attempt to use it directly.
    29  */
    30 
    31 #ifndef _STLP_INTERNAL_DEQUE_H
    32 #define _STLP_INTERNAL_DEQUE_H
    33 
    34 # ifndef _STLP_INTERNAL_ALGOBASE_H
    35 #  include <stl/_algobase.h>
    36 # endif
    37 
    38 # ifndef _STLP_INTERNAL_ALLOC_H
    39 #  include <stl/_alloc.h>
    40 # endif
    41 
    42 # ifndef _STLP_INTERNAL_ITERATOR_H
    43 #  include <stl/_iterator.h>
    44 # endif
    45 
    46 # ifndef _STLP_INTERNAL_UNINITIALIZED_H
    47 #  include <stl/_uninitialized.h>
    48 # endif
    49 
    50 # ifndef _STLP_RANGE_ERRORS_H
    51 #  include <stl/_range_errors.h>
    52 # endif
    53 
    54 /* Class invariants:
    55  *  For any nonsingular iterator i:
    56  *    i.node is the address of an element in the map array.  The
    57  *      contents of i.node is a pointer to the beginning of a node.
    58  *    i.first == *(i.node) 
    59  *    i.last  == i.first + node_size
    60  *    i.cur is a pointer in the range [i.first, i.last).  NOTE:
    61  *      the implication of this is that i.cur is always a dereferenceable
    62  *      pointer, even if i is a past-the-end iterator.
    63  *  Start and Finish are always nonsingular iterators.  NOTE: this means
    64  *    that an empty deque must have one node, and that a deque
    65  *    with N elements, where N is the buffer size, must have two nodes.
    66  *  For every node other than start.node and finish.node, every element
    67  *    in the node is an initialized object.  If start.node == finish.node,
    68  *    then [start.cur, finish.cur) are initialized objects, and
    69  *    the elements outside that range are uninitialized storage.  Otherwise,
    70  *    [start.cur, start.last) and [finish.first, finish.cur) are initialized
    71  *    objects, and [start.first, start.cur) and [finish.cur, finish.last)
    72  *    are uninitialized storage.
    73  *  [map, map + map_size) is a valid, non-empty range.  
    74  *  [start.node, finish.node] is a valid range contained within 
    75  *    [map, map + map_size).  
    76  *  A pointer in the range [map, map + map_size) points to an allocated node
    77  *    if and only if the pointer is in the range [start.node, finish.node].
    78  */
    79 
    80 # undef deque
    81 # define deque __WORKAROUND_DBG_RENAME(deque)
    82 
    83 _STLP_BEGIN_NAMESPACE
    84 
    85 template <class _Tp>
    86 struct _Deque_iterator_base {
    87 
    88   enum _Constants { 
    89     _blocksize = _MAX_BYTES, 
    90     __buffer_size = (sizeof(_Tp) < (size_t)_blocksize ?
    91    		    ( (size_t)_blocksize / sizeof(_Tp)) : size_t(1))
    92   };
    93 
    94   typedef random_access_iterator_tag iterator_category;
    95 
    96   typedef _Tp value_type;
    97   typedef size_t size_type;
    98   typedef ptrdiff_t difference_type;
    99 
   100   typedef value_type** _Map_pointer;
   101 
   102   typedef _Deque_iterator_base< _Tp > _Self;
   103 
   104   value_type* _M_cur;
   105   value_type* _M_first;
   106   value_type* _M_last;
   107   _Map_pointer _M_node;
   108 
   109   _Deque_iterator_base(value_type* __x, _Map_pointer __y) 
   110     : _M_cur(__x), _M_first(*__y),
   111       _M_last(*__y + __buffer_size), _M_node(__y) {}
   112   _Deque_iterator_base() : _M_cur(0), _M_first(0), _M_last(0), _M_node(0) {}
   113 
   114   difference_type _M_subtract(const _Self& __x) const {
   115     return difference_type(__buffer_size) * (_M_node - __x._M_node - 1) +
   116       (_M_cur - _M_first) + (__x._M_last - __x._M_cur);
   117   }
   118 
   119   void _M_increment() {
   120     if (++_M_cur == _M_last) {
   121       _M_set_node(_M_node + 1);
   122       _M_cur = _M_first;
   123     }
   124   }
   125 
   126   void _M_decrement() {
   127     if (_M_cur == _M_first) {
   128       _M_set_node(_M_node - 1);
   129       _M_cur = _M_last;
   130     }
   131     --_M_cur;
   132   }
   133 
   134   void _M_advance(difference_type __n)
   135   {
   136     difference_type __offset = __n + (_M_cur - _M_first);
   137     if (__offset >= 0 && __offset < difference_type(__buffer_size))
   138       _M_cur += __n;
   139     else {
   140       difference_type __node_offset =
   141         __offset > 0 ? __offset / __buffer_size
   142                    : -difference_type((-__offset - 1) / __buffer_size) - 1;
   143       _M_set_node(_M_node + __node_offset);
   144       _M_cur = _M_first + 
   145         (__offset - __node_offset * difference_type(__buffer_size));
   146     }
   147   }
   148 
   149   void _M_set_node(_Map_pointer __new_node) {
   150     _M_last = (_M_first = *(_M_node = __new_node)) + difference_type(__buffer_size);
   151   }
   152 };
   153 
   154 
   155 
   156 template <class _Tp, class _Traits>
   157 struct _Deque_iterator : public _Deque_iterator_base< _Tp> {
   158 
   159   typedef random_access_iterator_tag iterator_category;
   160   typedef _Tp value_type;
   161   typedef typename _Traits::reference  reference;
   162   typedef typename _Traits::pointer    pointer;
   163   typedef size_t size_type;
   164   typedef ptrdiff_t difference_type;
   165   typedef value_type** _Map_pointer;
   166 
   167   typedef _Deque_iterator_base< _Tp > _Base;
   168   typedef _Deque_iterator<_Tp, _Traits> _Self;
   169   typedef _Deque_iterator<_Tp, _Nonconst_traits<_Tp> > _Nonconst_self;
   170   typedef _Deque_iterator<_Tp, _Const_traits<_Tp> > _Const_self;
   171 
   172   _Deque_iterator(value_type* __x, _Map_pointer __y) :
   173     _Deque_iterator_base<value_type>(__x,__y) {}
   174 
   175   _Deque_iterator() {}
   176   _Deque_iterator(const _Nonconst_self& __x) : 
   177     _Deque_iterator_base<value_type>(__x) {}
   178 
   179   reference operator*() const { 
   180       return *this->_M_cur; 
   181   }
   182 
   183   _STLP_DEFINE_ARROW_OPERATOR
   184 
   185   difference_type operator-(const _Self& __x) const { return this->_M_subtract(__x); }
   186 
   187   _Self& operator++() { this->_M_increment(); return *this; }
   188   _Self operator++(int)  {
   189     _Self __tmp = *this;
   190     ++*this;
   191     return __tmp;
   192   }
   193 
   194   _Self& operator--() { this->_M_decrement(); return *this; }
   195   _Self operator--(int) {
   196     _Self __tmp = *this;
   197     --*this;
   198     return __tmp;
   199   }
   200 
   201   _Self& operator+=(difference_type __n) { this->_M_advance(__n); return *this; }
   202   _Self operator+(difference_type __n) const
   203   {
   204     _Self __tmp = *this;
   205     return __tmp += __n;
   206   }
   207 
   208   _Self& operator-=(difference_type __n) { return *this += -__n; }
   209   _Self operator-(difference_type __n) const {
   210     _Self __tmp = *this;
   211     return __tmp -= __n;
   212   }
   213 
   214   reference operator[](difference_type __n) const { return *(*this + __n); }
   215 };
   216 
   217 template <class _Tp, class _Traits>
   218 inline _Deque_iterator<_Tp, _Traits> _STLP_CALL
   219 operator+(ptrdiff_t __n, const _Deque_iterator<_Tp, _Traits>& __x)
   220 {
   221    return __x + __n;
   222 }
   223 
   224 
   225 #ifdef _STLP_USE_SEPARATE_RELOPS_NAMESPACE
   226 
   227 template <class _Tp>
   228 inline bool _STLP_CALL 
   229 operator==(const _Deque_iterator_base<_Tp >& __x,
   230 	   const _Deque_iterator_base<_Tp >& __y) { 
   231     return __x._M_cur == __y._M_cur; 
   232 }
   233 
   234 template <class _Tp>
   235 inline bool _STLP_CALL 
   236 operator < (const _Deque_iterator_base<_Tp >& __x,
   237 	    const _Deque_iterator_base<_Tp >& __y) { 
   238   return (__x._M_node == __y._M_node) ? 
   239     (__x._M_cur < __y._M_cur) : (__x._M_node < __y._M_node);
   240 }
   241 
   242 template <class _Tp>
   243 inline bool _STLP_CALL 
   244 operator!=(const _Deque_iterator_base<_Tp >& __x,
   245 	   const _Deque_iterator_base<_Tp >& __y) { 
   246     return __x._M_cur != __y._M_cur; 
   247 }
   248 template <class _Tp>
   249 inline bool _STLP_CALL 
   250 operator>(const _Deque_iterator_base<_Tp >& __x,
   251 	  const _Deque_iterator_base<_Tp >& __y) { 
   252     return __y < __x;
   253 }
   254 template <class _Tp>
   255 inline bool  _STLP_CALL operator>=(const _Deque_iterator_base<_Tp >& __x,
   256                                    const _Deque_iterator_base<_Tp >& __y) { 
   257     return !(__x < __y);
   258 }
   259 template <class _Tp>
   260 inline bool  _STLP_CALL operator<=(const _Deque_iterator_base<_Tp >& __x,
   261                                    const _Deque_iterator_base<_Tp >& __y) { 
   262     return !(__y < __x);
   263 }
   264 
   265 # else
   266 
   267 template <class _Tp, class _Traits1, class _Traits2>
   268 inline bool  _STLP_CALL
   269 operator==(const _Deque_iterator<_Tp, _Traits1 >& __x,
   270 	   const _Deque_iterator<_Tp, _Traits2 >& __y) { 
   271     return __x._M_cur == __y._M_cur; 
   272 }
   273 
   274 template <class _Tp, class _Traits1, class _Traits2>
   275 inline bool _STLP_CALL 
   276 operator < (const _Deque_iterator<_Tp, _Traits1 >& __x,
   277 	    const _Deque_iterator<_Tp, _Traits2 >& __y) { 
   278   return (__x._M_node == __y._M_node) ? 
   279     (__x._M_cur < __y._M_cur) : (__x._M_node < __y._M_node);
   280 }
   281 
   282 template <class _Tp>
   283 inline bool _STLP_CALL 
   284 operator!=(const _Deque_iterator<_Tp, _Nonconst_traits<_Tp> >& __x,
   285 	   const _Deque_iterator<_Tp, _Const_traits<_Tp> >& __y) { 
   286     return __x._M_cur != __y._M_cur; 
   287 }
   288 template <class _Tp>
   289 inline bool _STLP_CALL 
   290 operator>(const _Deque_iterator<_Tp, _Nonconst_traits<_Tp> >& __x,
   291 	  const _Deque_iterator<_Tp, _Const_traits<_Tp> >& __y) { 
   292     return __y < __x;
   293 }
   294 template <class _Tp>
   295 inline bool  _STLP_CALL
   296 operator>=(const _Deque_iterator<_Tp, _Nonconst_traits<_Tp> >& __x,
   297            const _Deque_iterator<_Tp, _Const_traits<_Tp> >& __y) { 
   298     return !(__x < __y);
   299 }
   300 template <class _Tp>
   301 inline bool _STLP_CALL
   302 operator<=(const _Deque_iterator<_Tp, _Nonconst_traits<_Tp> >& __x,
   303            const _Deque_iterator<_Tp, _Const_traits<_Tp> >& __y) { 
   304     return !(__y < __x);
   305 }
   306 # endif
   307 
   308 # ifdef _STLP_USE_OLD_HP_ITERATOR_QUERIES
   309 template <class _Tp, class _Traits> inline _Tp*  _STLP_CALL value_type(const _Deque_iterator<_Tp, _Traits  >&) { return (_Tp*)0; }
   310 template <class _Tp, class _Traits> inline random_access_iterator_tag _STLP_CALL 
   311 iterator_category(const _Deque_iterator<_Tp, _Traits  >&) { return random_access_iterator_tag(); }
   312 template <class _Tp, class _Traits> inline ptrdiff_t* _STLP_CALL 
   313 distance_type(const _Deque_iterator<_Tp, _Traits  >&) { return 0; }
   314 #endif
   315 
   316 // Deque base class.  It has two purposes.  First, its constructor
   317 //  and destructor allocate (but don't initialize) storage.  This makes
   318 //  exception safety easier.  Second, the base class encapsulates all of
   319 //  the differences between SGI-style allocators and standard-conforming
   320 //  allocators.
   321 
   322 template <class _Tp, class _Alloc>
   323 class _Deque_base 
   324 {
   325 public:
   326   typedef _Tp value_type;
   327   _STLP_FORCE_ALLOCATORS(_Tp, _Alloc)
   328   typedef typename _Alloc_traits<_Tp,_Alloc>::allocator_type  allocator_type;
   329   typedef typename _Alloc_traits<_Tp*, _Alloc>::allocator_type _Map_alloc_type;
   330 
   331   typedef _Deque_iterator<_Tp, _Nonconst_traits<_Tp> > iterator;
   332   typedef _Deque_iterator<_Tp, _Const_traits<_Tp> >   const_iterator;
   333 
   334   typedef _Deque_base<_Tp, _Alloc> _Base;
   335 
   336   static size_t  _STLP_CALL buffer_size() { return (size_t)_Deque_iterator_base<_Tp>::__buffer_size; } 
   337 
   338   _Deque_base(const allocator_type& __a, size_t __num_elements)
   339     : _M_start(), _M_finish(), _M_map(_STLP_CONVERT_ALLOCATOR(__a, _Tp*), 0),
   340       _M_map_size(__a, (size_t)0) {
   341     _STLP_PUSH_CLEANUP_ITEM(_Base, this) 
   342     _M_initialize_map(__num_elements);
   343   }
   344   _Deque_base(const allocator_type& __a)
   345     : _M_start(), _M_finish(), _M_map(_STLP_CONVERT_ALLOCATOR(__a, _Tp*), 0), 
   346       _M_map_size(__a, (size_t)0) {
   347      _STLP_PUSH_CLEANUP_ITEM(_Base, this)
   348   }
   349   ~_Deque_base();
   350 
   351 protected:
   352   void _M_initialize_map(size_t);
   353   void _M_create_nodes(_Tp** __nstart, _Tp** __nfinish);
   354   void _M_destroy_nodes(_Tp** __nstart, _Tp** __nfinish);
   355   enum { _S_initial_map_size = 8 };
   356 
   357 protected:
   358   iterator _M_start;
   359   iterator _M_finish;
   360   _STLP_alloc_proxy<value_type**, value_type*, _Map_alloc_type>  _M_map;
   361   _STLP_alloc_proxy<size_t, value_type,  allocator_type>   _M_map_size;  
   362 };
   363 
   364 
   365 template <class _Tp, _STLP_DEFAULT_ALLOCATOR_SELECT(_Tp) >
   366 class deque : public _Deque_base<_Tp, _Alloc> {
   367   typedef _Deque_base<_Tp, _Alloc> _Base;
   368   typedef deque<_Tp, _Alloc> _Self;
   369 public:                         // Basic types
   370   typedef _Tp value_type;
   371   typedef value_type* pointer;
   372   typedef const value_type* const_pointer;
   373   typedef value_type& reference;
   374   typedef const value_type& const_reference;
   375   typedef size_t size_type;
   376   typedef ptrdiff_t difference_type;
   377   typedef random_access_iterator_tag _Iterator_category;
   378   _STLP_FORCE_ALLOCATORS(_Tp, _Alloc)
   379   typedef typename _Base::allocator_type allocator_type;
   380 
   381 public:                         // Iterators
   382   typedef typename _Base::iterator       iterator;
   383   typedef typename _Base::const_iterator const_iterator;
   384 
   385   _STLP_DECLARE_RANDOM_ACCESS_REVERSE_ITERATORS;
   386 
   387 protected:                      // Internal typedefs
   388   typedef pointer* _Map_pointer;
   389   typedef typename  __type_traits<_Tp>::has_trivial_assignment_operator _TrivialAss;
   390   typedef typename  __type_traits<_Tp>::has_trivial_assignment_operator _IsPODType;
   391 
   392 public:                         // Basic accessors
   393   iterator begin() { return this->_M_start; }
   394   iterator end() { return this->_M_finish; }
   395   const_iterator begin() const { return const_iterator(this->_M_start); }
   396   const_iterator end() const { return const_iterator(this->_M_finish); }
   397 
   398   reverse_iterator rbegin() { return reverse_iterator(this->_M_finish); }
   399   reverse_iterator rend() { return reverse_iterator(this->_M_start); }
   400   const_reverse_iterator rbegin() const 
   401     { return const_reverse_iterator(this->_M_finish); }
   402   const_reverse_iterator rend() const 
   403     { return const_reverse_iterator(this->_M_start); }
   404 
   405   reference operator[](size_type __n)
   406     { return this->_M_start[difference_type(__n)]; }
   407   const_reference operator[](size_type __n) const 
   408     { return this->_M_start[difference_type(__n)]; }
   409 
   410   void _M_range_check(size_type __n) const {
   411     if (__n >= this->size())
   412       __stl_throw_out_of_range("deque");
   413   }
   414   reference at(size_type __n)
   415     { _M_range_check(__n); return (*this)[__n]; }
   416   const_reference at(size_type __n) const
   417     { _M_range_check(__n); return (*this)[__n]; }
   418 
   419   reference front() { return *this->_M_start; }
   420   reference back() {
   421     iterator __tmp = this->_M_finish;
   422     --__tmp;
   423     return *__tmp;
   424   }
   425   const_reference front() const { return *this->_M_start; }
   426   const_reference back() const {
   427     const_iterator __tmp = this->_M_finish;
   428     --__tmp;
   429     return *__tmp;
   430   }
   431 
   432   size_type size() const { return this->_M_finish - this->_M_start; }
   433   size_type max_size() const { return size_type(-1); }
   434   bool empty() const { return this->_M_finish == this->_M_start; }
   435   allocator_type get_allocator() const { return this->_M_map_size; }
   436 
   437 public:                         // Constructor, destructor.
   438   explicit deque(const allocator_type& __a = allocator_type()) 
   439     : _Deque_base<_Tp, _Alloc>(__a, 0) {
   440     _STLP_POP_CLEANUP_ITEM
   441   }
   442 
   443   deque(const _Self& __x) : 
   444     _Deque_base<_Tp, _Alloc>(__x.get_allocator(), __x.size()) {  
   445     uninitialized_copy(__x.begin(), __x.end(), this->_M_start); 
   446     _STLP_POP_CLEANUP_ITEM
   447   }
   448 
   449   deque(size_type __n, const value_type& __val,
   450         const allocator_type& __a = allocator_type()) : 
   451     _Deque_base<_Tp, _Alloc>(__a, __n)
   452     {
   453       _M_fill_initialize(__val); 
   454       _STLP_POP_CLEANUP_ITEM
   455     }
   456   // int,long variants may be needed 
   457   explicit deque(size_type __n) : _Deque_base<_Tp, _Alloc>(allocator_type(), __n)
   458   { 
   459 #ifdef __SYMBIAN32__
   460 // Though the below code is for Symbian
   461 // we are not using cleanup stack with this version.
   462     _M_fill_initialize(value_type()); 
   463 #else    
   464     value_type __p;
   465     _STLP_PUSH_CLEANUP_ITEM(_Tp, &__p) 	    
   466     _M_fill_initialize(__p); 
   467     // unconditional for __p
   468 //    CleanupStack::Pop();
   469     _STLP_POP_CLEANUP_ITEM
   470 #endif // __SYMBIAN32__    
   471   }
   472 
   473 #ifdef _STLP_MEMBER_TEMPLATES
   474 
   475   template <class _Integer>
   476   void _M_initialize_dispatch(_Integer __n, _Integer __x, const __true_type&) {
   477     this->_M_initialize_map(__n);
   478     _M_fill_initialize(__x);
   479   }
   480 
   481   template <class _InputIter>
   482   void _M_initialize_dispatch(_InputIter __first, _InputIter __last,
   483                               const __false_type&) {
   484     _M_range_initialize(__first, __last, _STLP_ITERATOR_CATEGORY(__first, _InputIter));
   485   }
   486 
   487 # ifdef _STLP_NEEDS_EXTRA_TEMPLATE_CONSTRUCTORS
   488   // VC++ needs this
   489   template <class _InputIterator>
   490   deque(_InputIterator __first, _InputIterator __last) : 
   491     _Deque_base<_Tp, _Alloc>(allocator_type()) {
   492     typedef typename _Is_integer<_InputIterator>::_Integral _Integral;
   493     _M_initialize_dispatch(__first, __last, _Integral());
   494     _STLP_POP_CLEANUP_ITEM
   495   }
   496 # endif
   497 
   498   // Check whether it's an integral type.  If so, it's not an iterator.
   499   template <class _InputIterator>
   500   deque(_InputIterator __first, _InputIterator __last,
   501         const allocator_type& __a _STLP_ALLOCATOR_TYPE_DFL) : 
   502     _Deque_base<_Tp, _Alloc>(__a) {
   503     typedef typename _Is_integer<_InputIterator>::_Integral _Integral;
   504     _M_initialize_dispatch(__first, __last, _Integral());
   505     _STLP_POP_CLEANUP_ITEM
   506   }
   507 
   508 # else
   509   deque(const value_type* __first, const value_type* __last,
   510         const allocator_type& __a = allocator_type() ) 
   511     : _Deque_base<_Tp, _Alloc>(__a, __last - __first) {  
   512     __uninitialized_copy(__first, __last, this->_M_start, _IsPODType()); 
   513     _STLP_POP_CLEANUP_ITEM
   514   }
   515 
   516   deque(const_iterator __first, const_iterator __last,
   517         const allocator_type& __a = allocator_type() ) 
   518     : _Deque_base<_Tp, _Alloc>(__a, __last - __first) { 
   519     __uninitialized_copy(__first, __last, this->_M_start, _IsPODType()); 
   520     _STLP_POP_CLEANUP_ITEM
   521   }
   522 #endif /* _STLP_MEMBER_TEMPLATES */
   523 
   524   ~deque() { 
   525     _STLP_STD::_Destroy(this->_M_start, this->_M_finish); 
   526   }
   527 
   528   _Self& operator= (const _Self& __x);
   529 
   530   void swap(_Self& __x) {
   531     _STLP_STD::swap(this->_M_start, __x._M_start);
   532     _STLP_STD::swap(this->_M_finish, __x._M_finish);
   533     _STLP_STD::swap(this->_M_map, __x._M_map);
   534     _STLP_STD::swap(this->_M_map_size, __x._M_map_size);
   535   }
   536 
   537 #ifdef _STLP_USE_TRAP_LEAVE
   538 public:
   539   static void* operator new (size_t __n, TLeave) { return _STLP_StackHelper<bool>::_NewLC(__n); }
   540   static void* operator new (size_t __n) { return _STLP_StackHelper<bool>::_NewLC(__n); }
   541 #endif
   542 
   543 public: 
   544   // assign(), a generalized assignment member function.  Two
   545   // versions: one that takes a count, and one that takes a range.
   546   // The range version is a member template, so we dispatch on whether
   547   // or not the type is an integer.
   548 
   549   void _M_fill_assign(size_type __n, const _Tp& __val) {
   550     if (__n > size()) {
   551       _STLP_STD::fill(begin(), end(), __val);
   552       insert(end(), __n - size(), __val);
   553     }
   554     else {
   555       erase(begin() + __n, end());
   556       _STLP_STD::fill(begin(), end(), __val);
   557     }
   558   }
   559 
   560   void assign(size_type __n, const _Tp& __val) {
   561     _M_fill_assign(__n, __val);
   562   }
   563 
   564 #ifdef _STLP_MEMBER_TEMPLATES
   565 
   566   template <class _InputIterator>
   567   void assign(_InputIterator __first, _InputIterator __last) {
   568     typedef typename _Is_integer<_InputIterator>::_Integral _Integral;
   569     _M_assign_dispatch(__first, __last, _Integral());
   570   }
   571 
   572 private:                        // helper functions for assign() 
   573 
   574   template <class _Integer>
   575   void _M_assign_dispatch(_Integer __n, _Integer __val, const __true_type&)
   576     { _M_fill_assign((size_type) __n, (_Tp) __val); }
   577 
   578   template <class _InputIterator>
   579   void _M_assign_dispatch(_InputIterator __first, _InputIterator __last,
   580                           const __false_type&) {
   581     _M_assign_aux(__first, __last, _STLP_ITERATOR_CATEGORY(__first, _InputIterator));
   582   }
   583 
   584   template <class _InputIter>
   585   void _M_assign_aux(_InputIter __first, _InputIter __last, const input_iterator_tag &) {
   586     iterator __cur = begin();
   587     for ( ; __first != __last && __cur != end(); ++__cur, ++__first)
   588       *__cur = *__first;
   589     if (__first == __last)
   590       erase(__cur, end());
   591     else
   592       insert(end(), __first, __last);
   593   }
   594 
   595   template <class _ForwardIterator>
   596   void _M_assign_aux(_ForwardIterator __first, _ForwardIterator __last,
   597                      const forward_iterator_tag &) {
   598     size_type __len = distance(__first, __last);
   599     if (__len > size()) {
   600       _ForwardIterator __mid = __first;
   601       advance(__mid, size());
   602       copy(__first, __mid, begin());
   603       insert(end(), __mid, __last);
   604     }
   605     else
   606       erase(copy(__first, __last, begin()), end());
   607   }
   608 
   609 #endif /* _STLP_MEMBER_TEMPLATES */
   610 
   611 public:                         // push_* and pop_*
   612   
   613   void push_back(const value_type& __t) {
   614     if (this->_M_finish._M_cur != this->_M_finish._M_last - 1) {
   615       _Construct(this->_M_finish._M_cur, __t);
   616       ++this->_M_finish._M_cur;
   617     }
   618     else
   619       _M_push_back_aux_v(__t);
   620   }
   621   void push_front(const value_type& __t) {
   622     if (this->_M_start._M_cur != this->_M_start._M_first) {
   623       _Construct(this->_M_start._M_cur - 1, __t);
   624       --this->_M_start._M_cur;
   625     }
   626     else
   627       _M_push_front_aux_v(__t);
   628   }
   629 
   630 # ifndef _STLP_NO_ANACHRONISMS
   631   void push_back() {
   632     if (this->_M_finish._M_cur != this->_M_finish._M_last - 1) {
   633       _Construct(this->_M_finish._M_cur);
   634       ++this->_M_finish._M_cur;
   635     }
   636     else
   637       _M_push_back_aux();
   638   }
   639   void push_front() {
   640     if (this->_M_start._M_cur != this->_M_start._M_first) {
   641       _Construct(this->_M_start._M_cur - 1);
   642       --this->_M_start._M_cur;
   643     }
   644     else
   645       _M_push_front_aux();
   646   }
   647 # endif
   648 
   649   void pop_back() {
   650     if (this->_M_finish._M_cur != this->_M_finish._M_first) {
   651       --this->_M_finish._M_cur;
   652       _STLP_STD::_Destroy(this->_M_finish._M_cur);
   653     }
   654     else
   655       _M_pop_back_aux();
   656   }
   657 
   658   void pop_front() {
   659     if (this->_M_start._M_cur != this->_M_start._M_last - 1) {
   660       _STLP_STD::_Destroy(this->_M_start._M_cur);
   661       ++this->_M_start._M_cur;
   662     }
   663     else 
   664       _M_pop_front_aux();
   665   }
   666 
   667 public:                         // Insert
   668 
   669   iterator insert(iterator __position, const value_type& __x) {
   670     if (__position._M_cur == this->_M_start._M_cur) {
   671       push_front(__x);
   672       return this->_M_start;
   673     }
   674     else if (__position._M_cur == this->_M_finish._M_cur) {
   675       push_back(__x);
   676       iterator __tmp = this->_M_finish;
   677       --__tmp;
   678       return __tmp;
   679     }
   680     else {
   681       return _M_insert_aux(__position, __x);
   682     }
   683   }
   684 
   685   iterator insert(iterator __position)
   686     { return insert(__position, value_type()); }
   687 
   688   void insert(iterator __pos, size_type __n, const value_type& __x) {
   689     _M_fill_insert(__pos, __n, __x);
   690   }
   691 
   692   void _M_fill_insert(iterator __pos, size_type __n, const value_type& __x);
   693 
   694 #ifdef _STLP_MEMBER_TEMPLATES  
   695 
   696   // Check whether it's an integral type.  If so, it's not an iterator.
   697   template <class _InputIterator>
   698   void insert(iterator __pos, _InputIterator __first, _InputIterator __last) {
   699     typedef typename _Is_integer<_InputIterator>::_Integral _Integral;
   700     _M_insert_dispatch(__pos, __first, __last, _Integral());
   701   }
   702 
   703   template <class _Integer>
   704   void _M_insert_dispatch(iterator __pos, _Integer __n, _Integer __x,
   705                           const __true_type&) {
   706     _M_fill_insert(__pos, (size_type) __n, (value_type) __x);
   707   }
   708 
   709   template <class _InputIterator>
   710   void _M_insert_dispatch(iterator __pos,
   711                           _InputIterator __first, _InputIterator __last,
   712                           const __false_type&) {
   713     insert(__pos, __first, __last, _STLP_ITERATOR_CATEGORY(__first, _InputIterator));
   714   }
   715 
   716 #else /* _STLP_MEMBER_TEMPLATES */
   717 
   718   void insert(iterator __pos,
   719               const value_type* __first, const value_type* __last);
   720   void insert(iterator __pos,
   721               const_iterator __first, const_iterator __last);
   722 
   723 #endif /* _STLP_MEMBER_TEMPLATES */
   724 
   725   void resize(size_type __new_size, value_type __x) {
   726     const size_type __len = size();
   727     if (__new_size < __len) 
   728       erase(this->_M_start + __new_size, this->_M_finish);
   729     else
   730       insert(this->_M_finish, __new_size - __len, __x);
   731   }
   732 
   733   void resize(size_type new_size) { resize(new_size, value_type()); }
   734 
   735 public:                         // Erase
   736   iterator erase(iterator __pos) {
   737     iterator __next = __pos;
   738     ++__next;
   739     difference_type __index = __pos - this->_M_start;
   740     if (size_type(__index) < this->size() >> 1) {
   741       copy_backward(this->_M_start, __pos, __next);
   742       pop_front();
   743     }
   744     else {
   745       copy(__next, this->_M_finish, __pos);
   746       pop_back();
   747     }
   748     return this->_M_start + __index;
   749   }
   750 
   751   iterator erase(iterator __first, iterator __last);
   752   void clear(); 
   753 
   754 protected:                        // Internal construction/destruction
   755 
   756   void _M_fill_initialize(const value_type& __val);
   757 
   758 #ifdef _STLP_MEMBER_TEMPLATES 
   759 
   760   template <class _InputIterator>
   761   void _M_range_initialize(_InputIterator __first,
   762 			   _InputIterator __last,
   763 			   const input_iterator_tag &) {
   764     this->_M_initialize_map(0);
   765     _STLP_TRY {
   766       for ( ; __first != __last; ++__first)
   767         push_back(*__first);
   768     }
   769     _STLP_UNWIND(clear());
   770   }
   771  template <class _ForwardIterator>
   772  void  _M_range_initialize(_ForwardIterator __first,
   773                            _ForwardIterator __last,
   774                            const forward_iterator_tag &)  {
   775    size_type __n = distance(__first, __last);
   776    this->_M_initialize_map(__n);
   777    _STLP_LEAVE_VOLATILE _Map_pointer __cur_node = 0 ;
   778    _STLP_TRY {
   779     for (__cur_node = this->_M_start._M_node; 
   780          __cur_node < this->_M_finish._M_node; 
   781 	 ++__cur_node) {
   782       _ForwardIterator __mid = __first;
   783       advance(__mid, this->buffer_size());
   784       uninitialized_copy(__first, __mid, *__cur_node);
   785       __first = __mid;
   786     }
   787     uninitialized_copy(__first, __last, this->_M_finish._M_first);
   788    }
   789   _STLP_UNWIND(_STLP_STD::_Destroy(this->_M_start, iterator(*__cur_node, __cur_node)));
   790  }
   791 #endif /* _STLP_MEMBER_TEMPLATES */
   792 
   793 protected:                        // Internal push_* and pop_*
   794 
   795   void _M_push_back_aux_v(const value_type&);
   796   void _M_push_front_aux_v(const value_type&);
   797 # ifndef _STLP_NO_ANACHRONISMS
   798   void _M_push_back_aux();
   799   void _M_push_front_aux();
   800 # endif
   801   void _M_pop_back_aux();
   802   void _M_pop_front_aux();
   803 
   804 protected:                        // Internal insert functions
   805 
   806 #ifdef _STLP_MEMBER_TEMPLATES
   807 
   808 template <class _InputIterator>
   809 void 
   810 insert(iterator __pos,
   811        _InputIterator __first,
   812        _InputIterator __last,
   813        const input_iterator_tag &)
   814 {
   815   copy(__first, __last, inserter(*this, __pos));
   816 }
   817 
   818 template <class _ForwardIterator>
   819 void  insert(iterator __pos,
   820 	     _ForwardIterator __first,
   821 	     _ForwardIterator __last,
   822 	     const forward_iterator_tag &)
   823  {
   824   size_type __n = distance(__first, __last);
   825   if (__pos._M_cur == this->_M_start._M_cur) {
   826     iterator __new_start = _M_reserve_elements_at_front(__n);
   827     _STLP_TRY {
   828       uninitialized_copy(__first, __last, __new_start);
   829       this->_M_start = __new_start;
   830     }
   831     _STLP_UNWIND(this->_M_destroy_nodes(__new_start._M_node, this->_M_start._M_node));
   832   }
   833   else if (__pos._M_cur == this->_M_finish._M_cur) {
   834     iterator __new_finish = _M_reserve_elements_at_back(__n);
   835     _STLP_TRY {
   836       uninitialized_copy(__first, __last, this->_M_finish);
   837       this->_M_finish = __new_finish;
   838     }
   839     _STLP_UNWIND(this->_M_destroy_nodes(this->_M_finish._M_node + 1, __new_finish._M_node + 1));
   840   }
   841   else
   842     _M_insert_aux(__pos, __first, __last, __n);
   843 }
   844 #endif /* _STLP_MEMBER_TEMPLATES */
   845 
   846   iterator _M_insert_aux(iterator __pos, const value_type& __x);
   847   iterator _M_insert_aux(iterator __pos);
   848   iterator _M_insert_aux_prepare(iterator __pos);
   849 
   850   void _M_insert_aux(iterator __pos, size_type __n, const value_type& __x);
   851 
   852 #ifdef _STLP_MEMBER_TEMPLATES  
   853   template <class _ForwardIterator>
   854   void _M_insert_aux(iterator __pos,
   855                      _ForwardIterator __first,
   856                      _ForwardIterator __last,
   857                      size_type __n) {
   858     
   859     const difference_type __elemsbefore = __pos - this->_M_start;
   860     size_type __length = size();
   861     if (__elemsbefore < difference_type(__length / 2)) {
   862       iterator __new_start = _M_reserve_elements_at_front(__n);
   863       iterator __old_start = this->_M_start;
   864       __pos = this->_M_start + __elemsbefore;
   865       _STLP_TRY {
   866 	if (__elemsbefore >= difference_type(__n)) {
   867 	  iterator __start_n = this->_M_start + difference_type(__n); 
   868 	  uninitialized_copy(this->_M_start, __start_n, __new_start);
   869 	  this->_M_start = __new_start;
   870 	  copy(__start_n, __pos, __old_start);
   871 	  copy(__first, __last, __pos - difference_type(__n));
   872 	}
   873 	else {
   874 	  _ForwardIterator __mid = __first;
   875 	  advance(__mid, difference_type(__n) - __elemsbefore);
   876 	  __uninitialized_copy_copy(this->_M_start, __pos, __first, __mid,
   877 				    __new_start, _IsPODType());
   878 	  this->_M_start = __new_start;
   879 	  copy(__mid, __last, __old_start);
   880 	}
   881       }
   882       _STLP_UNWIND(this->_M_destroy_nodes(__new_start._M_node, this->_M_start._M_node));
   883     }
   884     else {
   885       iterator __new_finish = _M_reserve_elements_at_back(__n);
   886       iterator __old_finish = this->_M_finish;
   887       const difference_type __elemsafter = 
   888 	difference_type(__length) - __elemsbefore;
   889       __pos = this->_M_finish - __elemsafter;
   890       _STLP_TRY {
   891       if (__elemsafter > difference_type(__n)) {
   892         iterator __finish_n = this->_M_finish - difference_type(__n);
   893         uninitialized_copy(__finish_n, this->_M_finish, this->_M_finish);
   894         this->_M_finish = __new_finish;
   895         copy_backward(__pos, __finish_n, __old_finish);
   896         copy(__first, __last, __pos);
   897       }
   898       else {
   899         _ForwardIterator __mid = __first;
   900         advance(__mid, __elemsafter);
   901         __uninitialized_copy_copy(__mid, __last, __pos, this->_M_finish, this->_M_finish, _IsPODType());
   902         this->_M_finish = __new_finish;
   903         copy(__first, __mid, __pos);
   904       }
   905       }
   906       _STLP_UNWIND(this->_M_destroy_nodes(this->_M_finish._M_node + 1, __new_finish._M_node + 1));
   907     }
   908   }
   909 #else /* _STLP_MEMBER_TEMPLATES */
   910   
   911   void _M_insert_aux(iterator __pos,
   912                      const value_type* __first, const value_type* __last,
   913                      size_type __n);
   914 
   915   void _M_insert_aux(iterator __pos, 
   916                      const_iterator __first, const_iterator __last,
   917                      size_type __n);
   918  
   919 #endif /* _STLP_MEMBER_TEMPLATES */
   920 
   921   iterator _M_reserve_elements_at_front(size_type __n) {
   922     size_type __vacancies = this->_M_start._M_cur - this->_M_start._M_first;
   923     if (__n > __vacancies) 
   924       _M_new_elements_at_front(__n - __vacancies);
   925     return this->_M_start - difference_type(__n);
   926   }
   927 
   928   iterator _M_reserve_elements_at_back(size_type __n) {
   929     size_type __vacancies = (this->_M_finish._M_last - this->_M_finish._M_cur) - 1;
   930     if (__n > __vacancies)
   931       _M_new_elements_at_back(__n - __vacancies);
   932     return this->_M_finish + difference_type(__n);
   933   }
   934 
   935   void _M_new_elements_at_front(size_type __new_elements);
   936   void _M_new_elements_at_back(size_type __new_elements);
   937 
   938 protected:                      // Allocation of _M_map and nodes
   939 
   940   // Makes sure the _M_map has space for new nodes.  Does not actually
   941   //  add the nodes.  Can invalidate _M_map pointers.  (And consequently, 
   942   //  deque iterators.)
   943 
   944   void _M_reserve_map_at_back (size_type __nodes_to_add = 1) {
   945     if (__nodes_to_add + 1 > this->_M_map_size._M_data - (this->_M_finish._M_node - this->_M_map._M_data))
   946       _M_reallocate_map(__nodes_to_add, false);
   947   }
   948 
   949   void _M_reserve_map_at_front (size_type __nodes_to_add = 1) {
   950     if (__nodes_to_add > size_type(this->_M_start._M_node - this->_M_map._M_data))
   951       _M_reallocate_map(__nodes_to_add, true);
   952   }
   953 
   954   void _M_reallocate_map(size_type __nodes_to_add, bool __add_at_front);
   955  
   956 };
   957 
   958 # define _STLP_TEMPLATE_CONTAINER deque<_Tp, _Alloc>
   959 # define _STLP_TEMPLATE_HEADER    template <class _Tp, class _Alloc>
   960 # include <stl/_relops_cont.h>
   961 # undef _STLP_TEMPLATE_CONTAINER
   962 # undef _STLP_TEMPLATE_HEADER
   963 
   964 _STLP_END_NAMESPACE 
   965 
   966 // do a cleanup
   967 # undef deque
   968 # undef __deque__
   969 # define __deque__ __WORKAROUND_DBG_RENAME(deque)
   970 
   971 # if !defined (_STLP_LINK_TIME_INSTANTIATION)
   972 #  include <stl/_deque.c>
   973 # endif
   974 
   975 #if defined (_STLP_DEBUG)
   976 # include <stl/debug/_deque.h>
   977 #endif
   978 
   979 # if defined (_STLP_USE_WRAPPER_FOR_ALLOC_PARAM)
   980 #  include <stl/wrappers/_deque.h>
   981 # endif
   982   
   983 #endif /* _STLP_INTERNAL_DEQUE_H */
   984 
   985 // Local Variables:
   986 // mode:C++
   987 // End:
   988