epoc32/include/tools/stlport/stl/_string.h
author William Roberts <williamr@symbian.org>
Wed, 31 Mar 2010 12:33:34 +0100
branchSymbian3
changeset 4 837f303aceeb
permissions -rw-r--r--
Current Symbian^3 public API header files (from PDK 3.0.h)
This is the epoc32/include tree with the "platform" subtrees removed, and
all but a selected few mbg and rsg files removed.
williamr@4
     1
/*
williamr@4
     2
 * Copyright (c) 1997-1999
williamr@4
     3
 * Silicon Graphics Computer Systems, Inc.
williamr@4
     4
 *
williamr@4
     5
 * Copyright (c) 1999
williamr@4
     6
 * Boris Fomitchev
williamr@4
     7
 *
williamr@4
     8
 * This material is provided "as is", with absolutely no warranty expressed
williamr@4
     9
 * or implied. Any use is at your own risk.
williamr@4
    10
 *
williamr@4
    11
 * Permission to use or copy this software for any purpose is hereby granted
williamr@4
    12
 * without fee, provided the above notices are retained on all copies.
williamr@4
    13
 * Permission to modify the code and to distribute modified code is granted,
williamr@4
    14
 * provided the above notices are retained, and a notice that the code was
williamr@4
    15
 * modified is included with the above copyright notice.
williamr@4
    16
 *
williamr@4
    17
 */
williamr@4
    18
williamr@4
    19
#ifndef _STLP_INTERNAL_STRING_H
williamr@4
    20
#define _STLP_INTERNAL_STRING_H
williamr@4
    21
williamr@4
    22
#ifndef _STLP_INTERNAL_ALLOC_H
williamr@4
    23
#  include <stl/_alloc.h>
williamr@4
    24
#endif
williamr@4
    25
williamr@4
    26
#ifndef _STLP_STRING_FWD_H
williamr@4
    27
#  include <stl/_string_fwd.h>
williamr@4
    28
#endif
williamr@4
    29
williamr@4
    30
#ifndef _STLP_INTERNAL_FUNCTION_BASE_H
williamr@4
    31
#  include <stl/_function_base.h>
williamr@4
    32
#endif
williamr@4
    33
williamr@4
    34
#ifndef _STLP_INTERNAL_ALGOBASE_H
williamr@4
    35
#  include <stl/_algobase.h>
williamr@4
    36
#endif
williamr@4
    37
williamr@4
    38
#ifndef _STLP_INTERNAL_ITERATOR_H
williamr@4
    39
#  include <stl/_iterator.h>
williamr@4
    40
#endif
williamr@4
    41
williamr@4
    42
#ifndef _STLP_INTERNAL_UNINITIALIZED_H
williamr@4
    43
#  include <stl/_uninitialized.h>
williamr@4
    44
#endif
williamr@4
    45
williamr@4
    46
#if defined (_STLP_USE_TEMPLATE_EXPRESSION)
williamr@4
    47
#  include <stl/_string_sum.h>
williamr@4
    48
#endif /* _STLP_USE_TEMPLATE_EXPRESSION */
williamr@4
    49
williamr@4
    50
#if defined (__MWERKS__) && ! defined (_STLP_USE_OWN_NAMESPACE)
williamr@4
    51
williamr@4
    52
// MSL implementation classes expect to see the definition of streampos
williamr@4
    53
// when this header is included. We expect this to be fixed in later MSL
williamr@4
    54
// implementations
williamr@4
    55
#  if !defined( __MSL_CPP__ ) || __MSL_CPP__ < 0x4105
williamr@4
    56
#    include <stl/msl_string.h>
williamr@4
    57
#  endif
williamr@4
    58
#endif // __MWERKS__
williamr@4
    59
williamr@4
    60
/*
williamr@4
    61
 * Standard C++ string class.  This class has performance
williamr@4
    62
 * characteristics very much like vector<>, meaning, for example, that
williamr@4
    63
 * it does not perform reference-count or copy-on-write, and that
williamr@4
    64
 * concatenation of two strings is an O(N) operation.
williamr@4
    65
williamr@4
    66
 * There are three reasons why basic_string is not identical to
williamr@4
    67
 * vector.
williamr@4
    68
 * First, basic_string can always stores a null character
williamr@4
    69
 * at the end (macro dependent); this makes it possible for c_str to
williamr@4
    70
 * be a fast operation.
williamr@4
    71
 * Second, the C++ standard requires basic_string to copy elements
williamr@4
    72
 * using char_traits<>::assign, char_traits<>::copy, and
williamr@4
    73
 * char_traits<>::move.  This means that all of vector<>'s low-level
williamr@4
    74
 * operations must be rewritten.  Third, basic_string<> has a lot of
williamr@4
    75
 * extra functions in its interface that are convenient but, strictly
williamr@4
    76
 * speaking, redundant.
williamr@4
    77
williamr@4
    78
 * Additionally, the C++ standard imposes a major restriction: according
williamr@4
    79
 * to the standard, the character type _CharT must be a POD type.  This
williamr@4
    80
 * implementation weakens that restriction, and allows _CharT to be a
williamr@4
    81
 * a user-defined non-POD type.  However, _CharT must still have a
williamr@4
    82
 * default constructor.
williamr@4
    83
 */
williamr@4
    84
williamr@4
    85
#include <stl/_string_base.h>
williamr@4
    86
williamr@4
    87
_STLP_BEGIN_NAMESPACE
williamr@4
    88
williamr@4
    89
// ------------------------------------------------------------
williamr@4
    90
// Class basic_string.
williamr@4
    91
williamr@4
    92
// Class invariants:
williamr@4
    93
// (1) [start, finish) is a valid range.
williamr@4
    94
// (2) Each iterator in [start, finish) points to a valid object
williamr@4
    95
//     of type value_type.
williamr@4
    96
// (3) *finish is a valid object of type value_type; when
williamr@4
    97
//     value_type is not a POD it is value_type().
williamr@4
    98
// (4) [finish + 1, end_of_storage) is a valid range.
williamr@4
    99
// (5) Each iterator in [finish + 1, end_of_storage) points to
williamr@4
   100
//     unininitialized memory.
williamr@4
   101
williamr@4
   102
// Note one important consequence: a string of length n must manage
williamr@4
   103
// a block of memory whose size is at least n + 1.
williamr@4
   104
williamr@4
   105
struct _String_reserve_t {};
williamr@4
   106
williamr@4
   107
#if defined (_STLP_USE_MSVC6_MEM_T_BUG_WORKAROUND)
williamr@4
   108
#  define basic_string _STLP_NO_MEM_T_NAME(str)
williamr@4
   109
#elif defined (_STLP_DEBUG)
williamr@4
   110
#  define basic_string _STLP_NON_DBG_NAME(str)
williamr@4
   111
#endif
williamr@4
   112
williamr@4
   113
#if defined (basic_string)
williamr@4
   114
_STLP_MOVE_TO_PRIV_NAMESPACE
williamr@4
   115
#endif
williamr@4
   116
williamr@4
   117
template <class _CharT, class _Traits, class _Alloc>
williamr@4
   118
class basic_string : protected _STLP_PRIV _String_base<_CharT,_Alloc>
williamr@4
   119
#if defined (_STLP_USE_PARTIAL_SPEC_WORKAROUND) && !defined (basic_string)
williamr@4
   120
                   , public __stlport_class<basic_string<_CharT, _Traits, _Alloc> >
williamr@4
   121
#endif
williamr@4
   122
{
williamr@4
   123
protected:                        // Protected members inherited from base.
williamr@4
   124
  typedef _STLP_PRIV _String_base<_CharT,_Alloc> _Base;
williamr@4
   125
  typedef basic_string<_CharT, _Traits, _Alloc> _Self;
williamr@4
   126
  // fbp : used to optimize char/wchar_t cases, and to simplify
williamr@4
   127
  // _STLP_DEF_CONST_PLCT_NEW_BUG problem workaround
williamr@4
   128
  typedef typename _IsIntegral<_CharT>::_Ret _Char_Is_Integral;
williamr@4
   129
  typedef typename _IsPOD<_CharT>::_Type _Char_Is_POD;
williamr@4
   130
  typedef random_access_iterator_tag r_a_i_t;
williamr@4
   131
williamr@4
   132
public:
williamr@4
   133
  typedef _CharT value_type;
williamr@4
   134
  typedef _Traits traits_type;
williamr@4
   135
williamr@4
   136
  typedef value_type* pointer;
williamr@4
   137
  typedef const value_type* const_pointer;
williamr@4
   138
  typedef value_type& reference;
williamr@4
   139
  typedef const value_type& const_reference;
williamr@4
   140
  typedef typename _Base::size_type size_type;
williamr@4
   141
  typedef ptrdiff_t difference_type;
williamr@4
   142
  typedef random_access_iterator_tag _Iterator_category;
williamr@4
   143
williamr@4
   144
  typedef const value_type* const_iterator;
williamr@4
   145
  typedef value_type*       iterator;
williamr@4
   146
williamr@4
   147
  _STLP_DECLARE_RANDOM_ACCESS_REVERSE_ITERATORS;
williamr@4
   148
williamr@4
   149
#include <stl/_string_npos.h>
williamr@4
   150
williamr@4
   151
  typedef _String_reserve_t _Reserve_t;
williamr@4
   152
williamr@4
   153
public:                         // Constructor, destructor, assignment.
williamr@4
   154
  typedef typename _Base::allocator_type allocator_type;
williamr@4
   155
williamr@4
   156
  allocator_type get_allocator() const
williamr@4
   157
  { return _STLP_CONVERT_ALLOCATOR((const allocator_type&)this->_M_end_of_storage, _CharT); }
williamr@4
   158
williamr@4
   159
#if !defined (_STLP_DONT_SUP_DFLT_PARAM)
williamr@4
   160
  explicit basic_string(const allocator_type& __a = allocator_type())
williamr@4
   161
#else
williamr@4
   162
  basic_string()
williamr@4
   163
      : _STLP_PRIV _String_base<_CharT,_Alloc>(allocator_type(), _Base::_DEFAULT_SIZE)
williamr@4
   164
  { _M_terminate_string(); }
williamr@4
   165
  explicit basic_string(const allocator_type& __a)
williamr@4
   166
#endif
williamr@4
   167
      : _STLP_PRIV _String_base<_CharT,_Alloc>(__a, _Base::_DEFAULT_SIZE)
williamr@4
   168
  { _M_terminate_string(); }
williamr@4
   169
williamr@4
   170
#if !defined (_STLP_DONT_SUP_DFLT_PARAM)
williamr@4
   171
  basic_string(_Reserve_t, size_t __n,
williamr@4
   172
               const allocator_type& __a = allocator_type())
williamr@4
   173
#else
williamr@4
   174
  basic_string(_Reserve_t, size_t __n)
williamr@4
   175
    : _STLP_PRIV _String_base<_CharT,_Alloc>(allocator_type(), __n + 1)
williamr@4
   176
  { _M_terminate_string(); }
williamr@4
   177
  basic_string(_Reserve_t, size_t __n, const allocator_type& __a)
williamr@4
   178
#endif
williamr@4
   179
    : _STLP_PRIV _String_base<_CharT,_Alloc>(__a, __n + 1)
williamr@4
   180
  { _M_terminate_string(); }
williamr@4
   181
williamr@4
   182
  basic_string(const _Self&);
williamr@4
   183
williamr@4
   184
#if !defined (_STLP_DONT_SUP_DFLT_PARAM)
williamr@4
   185
  basic_string(const _Self& __s, size_type __pos, size_type __n = npos,
williamr@4
   186
               const allocator_type& __a = allocator_type())
williamr@4
   187
#else
williamr@4
   188
  basic_string(const _Self& __s, size_type __pos)
williamr@4
   189
    : _STLP_PRIV _String_base<_CharT,_Alloc>(allocator_type()) {
williamr@4
   190
    if (__pos > __s.size())
williamr@4
   191
      this->_M_throw_out_of_range();
williamr@4
   192
    else
williamr@4
   193
      _M_range_initialize(__s._M_Start() + __pos, __s._M_Finish());
williamr@4
   194
  }
williamr@4
   195
  basic_string(const _Self& __s, size_type __pos, size_type __n)
williamr@4
   196
    : _STLP_PRIV _String_base<_CharT,_Alloc>(allocator_type()) {
williamr@4
   197
    if (__pos > __s.size())
williamr@4
   198
      this->_M_throw_out_of_range();
williamr@4
   199
    else
williamr@4
   200
      _M_range_initialize(__s._M_Start() + __pos,
williamr@4
   201
                          __s._M_Start() + __pos + (min) (__n, __s.size() - __pos));
williamr@4
   202
  }
williamr@4
   203
  basic_string(const _Self& __s, size_type __pos, size_type __n,
williamr@4
   204
               const allocator_type& __a)
williamr@4
   205
#endif
williamr@4
   206
    : _STLP_PRIV _String_base<_CharT,_Alloc>(__a) {
williamr@4
   207
    if (__pos > __s.size())
williamr@4
   208
      this->_M_throw_out_of_range();
williamr@4
   209
    else
williamr@4
   210
      _M_range_initialize(__s._M_Start() + __pos,
williamr@4
   211
                          __s._M_Start() + __pos + (min) (__n, __s.size() - __pos));
williamr@4
   212
  }
williamr@4
   213
williamr@4
   214
#if !defined (_STLP_DONT_SUP_DFLT_PARAM)
williamr@4
   215
  basic_string(const _CharT* __s, size_type __n,
williamr@4
   216
               const allocator_type& __a = allocator_type())
williamr@4
   217
#else
williamr@4
   218
  basic_string(const _CharT* __s, size_type __n)
williamr@4
   219
    : _STLP_PRIV _String_base<_CharT,_Alloc>(allocator_type()) {
williamr@4
   220
      _STLP_FIX_LITERAL_BUG(__s)
williamr@4
   221
      _M_range_initialize(__s, __s + __n);
williamr@4
   222
    }
williamr@4
   223
  basic_string(const _CharT* __s, size_type __n, const allocator_type& __a)
williamr@4
   224
#endif
williamr@4
   225
    : _STLP_PRIV _String_base<_CharT,_Alloc>(__a) {
williamr@4
   226
      _STLP_FIX_LITERAL_BUG(__s)
williamr@4
   227
      _M_range_initialize(__s, __s + __n);
williamr@4
   228
    }
williamr@4
   229
williamr@4
   230
#if !defined (_STLP_DONT_SUP_DFLT_PARAM)
williamr@4
   231
  basic_string(const _CharT* __s,
williamr@4
   232
               const allocator_type& __a = allocator_type());
williamr@4
   233
#else
williamr@4
   234
  basic_string(const _CharT* __s);
williamr@4
   235
  basic_string(const _CharT* __s, const allocator_type& __a);
williamr@4
   236
#endif
williamr@4
   237
williamr@4
   238
#if !defined (_STLP_DONT_SUP_DFLT_PARAM)
williamr@4
   239
  basic_string(size_type __n, _CharT __c,
williamr@4
   240
               const allocator_type& __a = allocator_type())
williamr@4
   241
#else
williamr@4
   242
  basic_string(size_type __n, _CharT __c)
williamr@4
   243
    : _STLP_PRIV _String_base<_CharT,_Alloc>(allocator_type(), __n + 1) {
williamr@4
   244
#  if defined (_STLP_USE_SHORT_STRING_OPTIM)
williamr@4
   245
    if (this->_M_using_static_buf()) {
williamr@4
   246
      _Traits::assign(this->_M_Start(), __n, __c);
williamr@4
   247
      this->_M_finish = this->_M_Start() + __n;
williamr@4
   248
    }
williamr@4
   249
    else
williamr@4
   250
#  endif
williamr@4
   251
    this->_M_finish = _STLP_PRIV __uninitialized_fill_n(this->_M_Start(), __n, __c);
williamr@4
   252
    _M_terminate_string();
williamr@4
   253
  }
williamr@4
   254
  basic_string(size_type __n, _CharT __c, const allocator_type& __a)
williamr@4
   255
#endif
williamr@4
   256
    : _STLP_PRIV _String_base<_CharT,_Alloc>(__a, __n + 1) {
williamr@4
   257
#if defined (_STLP_USE_SHORT_STRING_OPTIM)
williamr@4
   258
    if (this->_M_using_static_buf()) {
williamr@4
   259
      _Traits::assign(this->_M_Start(), __n, __c);
williamr@4
   260
      this->_M_finish = this->_M_Start() + __n;
williamr@4
   261
    }
williamr@4
   262
    else
williamr@4
   263
#endif
williamr@4
   264
    this->_M_finish = _STLP_PRIV __uninitialized_fill_n(this->_M_Start(), __n, __c);
williamr@4
   265
    _M_terminate_string();
williamr@4
   266
  }
williamr@4
   267
williamr@4
   268
  basic_string(__move_source<_Self> src)
williamr@4
   269
    : _STLP_PRIV _String_base<_CharT,_Alloc>(__move_source<_Base>(src.get())) {}
williamr@4
   270
williamr@4
   271
  // Check to see if _InputIterator is an integer type.  If so, then
williamr@4
   272
  // it can't be an iterator.
williamr@4
   273
#if defined (_STLP_MEMBER_TEMPLATES) && !(defined (__MRC__) || (defined(__SC__) && !defined(__DMC__))) //*ty 04/30/2001 - mpw compilers choke on this ctor
williamr@4
   274
#  if !defined (_STLP_USE_MSVC6_MEM_T_BUG_WORKAROUND)
williamr@4
   275
  template <class _InputIterator>
williamr@4
   276
  basic_string(_InputIterator __f, _InputIterator __l,
williamr@4
   277
               const allocator_type & __a _STLP_ALLOCATOR_TYPE_DFL)
williamr@4
   278
    : _STLP_PRIV _String_base<_CharT,_Alloc>(__a) {
williamr@4
   279
    typedef typename _IsIntegral<_InputIterator>::_Ret _Integral;
williamr@4
   280
    _M_initialize_dispatch(__f, __l, _Integral());
williamr@4
   281
  }
williamr@4
   282
#    if defined (_STLP_NEEDS_EXTRA_TEMPLATE_CONSTRUCTORS)
williamr@4
   283
  template <class _InputIterator>
williamr@4
   284
  basic_string(_InputIterator __f, _InputIterator __l)
williamr@4
   285
    : _STLP_PRIV _String_base<_CharT,_Alloc>(allocator_type()) {
williamr@4
   286
    typedef typename _IsIntegral<_InputIterator>::_Ret _Integral;
williamr@4
   287
    _M_initialize_dispatch(__f, __l, _Integral());
williamr@4
   288
  }
williamr@4
   289
#    endif
williamr@4
   290
#  else
williamr@4
   291
  /* We need an additionnal constructor to build an empty string without
williamr@4
   292
   * any allocation or termination char*/
williamr@4
   293
protected:
williamr@4
   294
  struct _CalledFromWorkaround_t {};
williamr@4
   295
  basic_string(_CalledFromWorkaround_t, const allocator_type &__a)
williamr@4
   296
    : _String_base<_CharT,_Alloc>(__a) {}
williamr@4
   297
public:
williamr@4
   298
#  endif /* _STLP_USE_MSVC6_MEM_T_BUG_WORKAROUND */
williamr@4
   299
#endif /* !__MRC__ || (__SC__ && !__DMC__) */
williamr@4
   300
williamr@4
   301
#if !(defined (_STLP_MEMBER_TEMPLATES) && !(defined (__MRC__) || (defined (__SC__) && !defined (__DMC__)))) || \
williamr@4
   302
    !defined (_STLP_NO_METHOD_SPECIALIZATION) && !defined (_STLP_NO_EXTENSIONS) || \
williamr@4
   303
     defined (_STLP_USE_MSVC6_MEM_T_BUG_WORKAROUND)
williamr@4
   304
  basic_string(const _CharT* __f, const _CharT* __l,
williamr@4
   305
               const allocator_type& __a _STLP_ALLOCATOR_TYPE_DFL)
williamr@4
   306
    : _STLP_PRIV _String_base<_CharT,_Alloc>(__a) {
williamr@4
   307
    _STLP_FIX_LITERAL_BUG(__f)  _STLP_FIX_LITERAL_BUG(__l)
williamr@4
   308
    _M_range_initialize(__f, __l);
williamr@4
   309
  }
williamr@4
   310
#  if defined (_STLP_NEEDS_EXTRA_TEMPLATE_CONSTRUCTORS)
williamr@4
   311
  basic_string(const _CharT* __f, const _CharT* __l)
williamr@4
   312
    : _STLP_PRIV _String_base<_CharT,_Alloc>(allocator_type()) {
williamr@4
   313
    _STLP_FIX_LITERAL_BUG(__f)  _STLP_FIX_LITERAL_BUG(__l)
williamr@4
   314
    _M_range_initialize(__f, __l);
williamr@4
   315
  }
williamr@4
   316
#  endif
williamr@4
   317
#endif /* _STLP_MEMBER_TEMPLATES */
williamr@4
   318
williamr@4
   319
private:
williamr@4
   320
  template <class _InputIter>
williamr@4
   321
  void _M_range_initialize(_InputIter __f, _InputIter __l,
williamr@4
   322
                           const input_iterator_tag &__tag) {
williamr@4
   323
    this->_M_allocate_block();
williamr@4
   324
    _M_construct_null(this->_M_Finish());
williamr@4
   325
    _STLP_TRY {
williamr@4
   326
      _M_appendT(__f, __l, __tag);
williamr@4
   327
    }
williamr@4
   328
    _STLP_UNWIND(this->_M_destroy_range())
williamr@4
   329
  }
williamr@4
   330
williamr@4
   331
  template <class _ForwardIter>
williamr@4
   332
  void _M_range_initialize(_ForwardIter __f, _ForwardIter __l,
williamr@4
   333
                           const forward_iterator_tag &) {
williamr@4
   334
    difference_type __n = distance(__f, __l);
williamr@4
   335
    this->_M_allocate_block(__n + 1);
williamr@4
   336
#if defined (_STLP_USE_SHORT_STRING_OPTIM)
williamr@4
   337
    if (this->_M_using_static_buf()) {
williamr@4
   338
      _M_copyT(__f, __l, this->_M_Start());
williamr@4
   339
      this->_M_finish = this->_M_Start() + __n;
williamr@4
   340
    }
williamr@4
   341
    else
williamr@4
   342
#endif /* _STLP_USE_SHORT_STRING_OPTIM */
williamr@4
   343
    this->_M_finish = uninitialized_copy(__f, __l, this->_M_Start());
williamr@4
   344
    this->_M_terminate_string();
williamr@4
   345
  }
williamr@4
   346
williamr@4
   347
  template <class _InputIter>
williamr@4
   348
  void _M_range_initializeT(_InputIter __f, _InputIter __l) {
williamr@4
   349
    _M_range_initialize(__f, __l, _STLP_ITERATOR_CATEGORY(__f, _InputIter));
williamr@4
   350
  }
williamr@4
   351
williamr@4
   352
  template <class _Integer>
williamr@4
   353
  void _M_initialize_dispatch(_Integer __n, _Integer __x, const __true_type& /*_Integral*/) {
williamr@4
   354
    this->_M_allocate_block(__n + 1);
williamr@4
   355
#if defined (_STLP_USE_SHORT_STRING_OPTIM)
williamr@4
   356
    if (this->_M_using_static_buf()) {
williamr@4
   357
      _Traits::assign(this->_M_Start(), __n, __x);
williamr@4
   358
      this->_M_finish = this->_M_Start() + __n;
williamr@4
   359
    }
williamr@4
   360
    else
williamr@4
   361
#endif /* _STLP_USE_SHORT_STRING_OPTIM */
williamr@4
   362
    this->_M_finish = _STLP_PRIV __uninitialized_fill_n(this->_M_Start(), __n, __x);
williamr@4
   363
    this->_M_terminate_string();
williamr@4
   364
  }
williamr@4
   365
williamr@4
   366
  template <class _InputIter>
williamr@4
   367
  void _M_initialize_dispatch(_InputIter __f, _InputIter __l, const __false_type& /*_Integral*/) {
williamr@4
   368
    _M_range_initializeT(__f, __l);
williamr@4
   369
  }
williamr@4
   370
williamr@4
   371
public:
williamr@4
   372
  ~basic_string()
williamr@4
   373
  { this->_M_destroy_range(); }
williamr@4
   374
williamr@4
   375
  _Self& operator=(const _Self& __s) {
williamr@4
   376
    if (&__s != this)
williamr@4
   377
      _M_assign(__s._M_Start(), __s._M_Finish());
williamr@4
   378
    return *this;
williamr@4
   379
  }
williamr@4
   380
williamr@4
   381
  _Self& operator=(const _CharT* __s) {
williamr@4
   382
    _STLP_FIX_LITERAL_BUG(__s)
williamr@4
   383
    return _M_assign(__s, __s + traits_type::length(__s));
williamr@4
   384
  }
williamr@4
   385
williamr@4
   386
  _Self& operator=(_CharT __c)
williamr@4
   387
  { return assign(__STATIC_CAST(size_type,1), __c); }
williamr@4
   388
williamr@4
   389
protected:
williamr@4
   390
williamr@4
   391
  static _CharT _STLP_CALL _M_null()
williamr@4
   392
  { return _STLP_DEFAULT_CONSTRUCTED(_CharT); }
williamr@4
   393
williamr@4
   394
protected:                     // Helper functions used by constructors
williamr@4
   395
                               // and elsewhere.
williamr@4
   396
  // fbp : simplify integer types (char, wchar)
williamr@4
   397
  void _M_construct_null_aux(_CharT* __p, const __false_type& /*_Is_Integral*/) const {
williamr@4
   398
#if defined (_STLP_USE_SHORT_STRING_OPTIM)
williamr@4
   399
    if (this->_M_using_static_buf())
williamr@4
   400
      _Traits::assign(*__p, _M_null());
williamr@4
   401
    else
williamr@4
   402
#endif /*_STLP_USE_SHORT_STRING_OPTIM*/
williamr@4
   403
    _STLP_STD::_Construct(__p);
williamr@4
   404
  }
williamr@4
   405
  void _M_construct_null_aux(_CharT* __p, const __true_type& /*_Is_Integral*/) const
williamr@4
   406
  { *__p = 0; }
williamr@4
   407
williamr@4
   408
  void _M_force_construct_null(_CharT*, const __true_type& /* _Is_POD */) const
williamr@4
   409
  { /*Nothing to do*/ }
williamr@4
   410
  void _M_force_construct_null(_CharT* __p, const __false_type& /* _Is_POD */) const
williamr@4
   411
  { _M_construct_null_aux(__p, _Char_Is_Integral()); }
williamr@4
   412
williamr@4
   413
  void _M_construct_null(_CharT* __p) const {
williamr@4
   414
    typedef __false_type _Answer;
williamr@4
   415
williamr@4
   416
    _M_force_construct_null(__p, _Answer());
williamr@4
   417
  }
williamr@4
   418
williamr@4
   419
protected:
williamr@4
   420
  // Helper functions used by constructors.  It is a severe error for
williamr@4
   421
  // any of them to be called anywhere except from within constructors.
williamr@4
   422
  void _M_terminate_string_aux(const __false_type& __is_integral) {
williamr@4
   423
    _STLP_TRY {
williamr@4
   424
      _M_construct_null_aux(this->_M_Finish(), __is_integral);
williamr@4
   425
    }
williamr@4
   426
    _STLP_UNWIND(this->_M_destroy_range(0,0))
williamr@4
   427
  }
williamr@4
   428
williamr@4
   429
  void _M_terminate_string_aux(const __true_type& __is_integral)
williamr@4
   430
  { _M_construct_null_aux(this->_M_Finish(), __is_integral); }
williamr@4
   431
williamr@4
   432
  void _M_force_terminate_string(const __true_type& /* _Is_POD */)
williamr@4
   433
  { /*Nothing to do*/ }
williamr@4
   434
  void _M_force_terminate_string(const __false_type& /* _Is_POD */)
williamr@4
   435
  { _M_terminate_string_aux(_Char_Is_Integral()); }
williamr@4
   436
williamr@4
   437
  void _M_terminate_string() {
williamr@4
   438
    typedef __false_type _Answer;
williamr@4
   439
williamr@4
   440
    _M_force_terminate_string(_Answer());
williamr@4
   441
  }
williamr@4
   442
williamr@4
   443
  bool _M_inside(const _CharT* __s) const {
williamr@4
   444
    _STLP_FIX_LITERAL_BUG(__s)
williamr@4
   445
    return (__s >= this->_M_Start()) && (__s < this->_M_Finish());
williamr@4
   446
  }
williamr@4
   447
williamr@4
   448
  void _M_range_initialize(const _CharT* __f, const _CharT* __l) {
williamr@4
   449
    _STLP_FIX_LITERAL_BUG(__f) _STLP_FIX_LITERAL_BUG(__l)
williamr@4
   450
    ptrdiff_t __n = __l - __f;
williamr@4
   451
    this->_M_allocate_block(__n + 1);
williamr@4
   452
#if defined (_STLP_USE_SHORT_STRING_OPTIM)
williamr@4
   453
    if (this->_M_using_static_buf()) {
williamr@4
   454
      _M_copy(__f, __l, this->_M_Start());
williamr@4
   455
      this->_M_finish = this->_M_Start() + __n;
williamr@4
   456
    }
williamr@4
   457
    else
williamr@4
   458
#endif /* _STLP_USE_SHORT_STRING_OPTIM */
williamr@4
   459
    this->_M_finish = uninitialized_copy(__f, __l, this->_M_Start());
williamr@4
   460
    _M_terminate_string();
williamr@4
   461
  }
williamr@4
   462
williamr@4
   463
public:                         // Iterators.
williamr@4
   464
  iterator begin()             { return this->_M_Start(); }
williamr@4
   465
  iterator end()               { return this->_M_Finish(); }
williamr@4
   466
  const_iterator begin() const { return this->_M_Start(); }
williamr@4
   467
  const_iterator end()   const { return this->_M_Finish(); }
williamr@4
   468
williamr@4
   469
  reverse_iterator rbegin()
williamr@4
   470
    { return reverse_iterator(this->_M_Finish()); }
williamr@4
   471
  reverse_iterator rend()
williamr@4
   472
    { return reverse_iterator(this->_M_Start()); }
williamr@4
   473
  const_reverse_iterator rbegin() const
williamr@4
   474
    { return const_reverse_iterator(this->_M_Finish()); }
williamr@4
   475
  const_reverse_iterator rend()   const
williamr@4
   476
    { return const_reverse_iterator(this->_M_Start()); }
williamr@4
   477
williamr@4
   478
public:                         // Size, capacity, etc.
williamr@4
   479
  size_type size() const { return this->_M_Finish() - this->_M_Start(); }
williamr@4
   480
  size_type length() const { return size(); }
williamr@4
   481
  size_t max_size() const { return _Base::max_size(); }
williamr@4
   482
williamr@4
   483
  void resize(size_type __n, _CharT __c) {
williamr@4
   484
    if (__n <= size())
williamr@4
   485
      erase(begin() + __n, end());
williamr@4
   486
    else
williamr@4
   487
      append(__n - size(), __c);
williamr@4
   488
  }
williamr@4
   489
williamr@4
   490
  void resize(size_type __n) { resize(__n, _M_null()); }
williamr@4
   491
williamr@4
   492
  void reserve(size_type = 0);
williamr@4
   493
williamr@4
   494
  size_type capacity() const
williamr@4
   495
  { return (this->_M_end_of_storage._M_data - this->_M_Start()) - 1; }
williamr@4
   496
williamr@4
   497
  void clear() {
williamr@4
   498
    if (!empty()) {
williamr@4
   499
      _Traits::assign(*(this->_M_Start()), _M_null());
williamr@4
   500
      this->_M_destroy_range(1);
williamr@4
   501
      this->_M_finish = this->_M_Start();
williamr@4
   502
    }
williamr@4
   503
  }
williamr@4
   504
williamr@4
   505
  bool empty() const { return this->_M_Start() == this->_M_Finish(); }
williamr@4
   506
williamr@4
   507
public:                         // Element access.
williamr@4
   508
williamr@4
   509
  const_reference operator[](size_type __n) const
williamr@4
   510
  { return *(this->_M_Start() + __n); }
williamr@4
   511
  reference operator[](size_type __n)
williamr@4
   512
  { return *(this->_M_Start() + __n); }
williamr@4
   513
williamr@4
   514
  const_reference at(size_type __n) const {
williamr@4
   515
    if (__n >= size())
williamr@4
   516
      this->_M_throw_out_of_range();
williamr@4
   517
    return *(this->_M_Start() + __n);
williamr@4
   518
  }
williamr@4
   519
williamr@4
   520
  reference at(size_type __n) {
williamr@4
   521
    if (__n >= size())
williamr@4
   522
      this->_M_throw_out_of_range();
williamr@4
   523
    return *(this->_M_Start() + __n);
williamr@4
   524
  }
williamr@4
   525
williamr@4
   526
public:                         // Append, operator+=, push_back.
williamr@4
   527
williamr@4
   528
  _Self& operator+=(const _Self& __s) { return append(__s); }
williamr@4
   529
  _Self& operator+=(const _CharT* __s) { _STLP_FIX_LITERAL_BUG(__s) return append(__s); }
williamr@4
   530
  _Self& operator+=(_CharT __c) { push_back(__c); return *this; }
williamr@4
   531
williamr@4
   532
#if defined (_STLP_MEMBER_TEMPLATES)
williamr@4
   533
#  if !defined (_STLP_USE_MSVC6_MEM_T_BUG_WORKAROUND)
williamr@4
   534
private: // Helper functions for append.
williamr@4
   535
  template <class _InputIter>
williamr@4
   536
  _Self& _M_appendT(_InputIter __first, _InputIter __last,
williamr@4
   537
                    const input_iterator_tag &) {
williamr@4
   538
    for ( ; __first != __last ; ++__first)
williamr@4
   539
      push_back(*__first);
williamr@4
   540
    return *this;
williamr@4
   541
  }
williamr@4
   542
williamr@4
   543
  template <class _ForwardIter>
williamr@4
   544
  _Self& _M_appendT(_ForwardIter __first, _ForwardIter __last,
williamr@4
   545
                    const forward_iterator_tag &) {
williamr@4
   546
    if (__first != __last) {
williamr@4
   547
      const size_type __old_size = this->size();
williamr@4
   548
      difference_type __n = distance(__first, __last);
williamr@4
   549
      if (__STATIC_CAST(size_type,__n) > this->max_size() || __old_size > this->max_size() - __STATIC_CAST(size_type,__n))
williamr@4
   550
        this->_M_throw_length_error();
williamr@4
   551
      if (__old_size + __n > this->capacity()) {
williamr@4
   552
        size_type __len = __old_size + (max)(__old_size, __STATIC_CAST(size_type,__n)) + 1;
williamr@4
   553
        pointer __new_start = this->_M_end_of_storage.allocate(__len, __len);
williamr@4
   554
        pointer __new_finish = __new_start;
williamr@4
   555
        _STLP_TRY {
williamr@4
   556
          __new_finish = uninitialized_copy(this->_M_Start(), this->_M_Finish(), __new_start);
williamr@4
   557
          __new_finish = uninitialized_copy(__first, __last, __new_finish);
williamr@4
   558
          _M_construct_null(__new_finish);
williamr@4
   559
        }
williamr@4
   560
        _STLP_UNWIND((_STLP_STD::_Destroy_Range(__new_start,__new_finish),
williamr@4
   561
          this->_M_end_of_storage.deallocate(__new_start, __len)))
williamr@4
   562
          this->_M_destroy_range();
williamr@4
   563
        this->_M_deallocate_block();
williamr@4
   564
        this->_M_reset(__new_start, __new_finish, __new_start + __len);
williamr@4
   565
      }
williamr@4
   566
      else {
williamr@4
   567
        _ForwardIter __f1 = __first;
williamr@4
   568
        ++__f1;
williamr@4
   569
#if defined (_STLP_USE_SHORT_STRING_OPTIM)
williamr@4
   570
        if (this->_M_using_static_buf())
williamr@4
   571
          _M_copyT(__f1, __last, this->_M_Finish() + 1);
williamr@4
   572
        else
williamr@4
   573
#endif /* _STLP_USE_SHORT_STRING_OPTIM */
williamr@4
   574
          uninitialized_copy(__f1, __last, this->_M_Finish() + 1);
williamr@4
   575
        _STLP_TRY {
williamr@4
   576
          _M_construct_null(this->_M_Finish() + __n);
williamr@4
   577
        }
williamr@4
   578
        _STLP_UNWIND(this->_M_destroy_ptr_range(this->_M_Finish() + 1, this->_M_Finish() + __n))
williamr@4
   579
        _Traits::assign(*this->_M_finish, *__first);
williamr@4
   580
        this->_M_finish += __n;
williamr@4
   581
      }
williamr@4
   582
    }
williamr@4
   583
    return *this;
williamr@4
   584
  }
williamr@4
   585
williamr@4
   586
  template <class _Integer>
williamr@4
   587
  _Self& _M_append_dispatch(_Integer __n, _Integer __x, const __true_type& /*Integral*/)
williamr@4
   588
  { return append((size_type) __n, (_CharT) __x); }
williamr@4
   589
williamr@4
   590
  template <class _InputIter>
williamr@4
   591
  _Self& _M_append_dispatch(_InputIter __f, _InputIter __l, const __false_type& /*Integral*/)
williamr@4
   592
  { return _M_appendT(__f, __l, _STLP_ITERATOR_CATEGORY(__f, _InputIter)); }
williamr@4
   593
williamr@4
   594
public:
williamr@4
   595
  // Check to see if _InputIterator is an integer type.  If so, then
williamr@4
   596
  // it can't be an iterator.
williamr@4
   597
  template <class _InputIter>
williamr@4
   598
  _Self& append(_InputIter __first, _InputIter __last) {
williamr@4
   599
    typedef typename _IsIntegral<_InputIter>::_Ret _Integral;
williamr@4
   600
    return _M_append_dispatch(__first, __last, _Integral());
williamr@4
   601
  }
williamr@4
   602
#  endif
williamr@4
   603
#endif
williamr@4
   604
williamr@4
   605
protected:
williamr@4
   606
  _Self& _M_append(const _CharT* __first, const _CharT* __last);
williamr@4
   607
williamr@4
   608
public:
williamr@4
   609
#if !defined (_STLP_MEMBER_TEMPLATES) || \
williamr@4
   610
    !defined (_STLP_NO_METHOD_SPECIALIZATION) && !defined (_STLP_NO_EXTENSIONS)
williamr@4
   611
#  if !defined (_STLP_USE_MSVC6_MEM_T_BUG_WORKAROUND)
williamr@4
   612
  _Self& append(const _CharT* __first, const _CharT* __last) {
williamr@4
   613
    _STLP_FIX_LITERAL_BUG(__first)_STLP_FIX_LITERAL_BUG(__last)
williamr@4
   614
    return _M_append(__first, __last);
williamr@4
   615
  }
williamr@4
   616
#  endif
williamr@4
   617
#endif
williamr@4
   618
williamr@4
   619
  _Self& append(const _Self& __s)
williamr@4
   620
  { return _M_append(__s._M_Start(), __s._M_Finish()); }
williamr@4
   621
williamr@4
   622
  _Self& append(const _Self& __s,
williamr@4
   623
                size_type __pos, size_type __n) {
williamr@4
   624
    if (__pos > __s.size())
williamr@4
   625
      this->_M_throw_out_of_range();
williamr@4
   626
    return _M_append(__s._M_Start() + __pos,
williamr@4
   627
                     __s._M_Start() + __pos + (min) (__n, __s.size() - __pos));
williamr@4
   628
  }
williamr@4
   629
williamr@4
   630
  _Self& append(const _CharT* __s, size_type __n)
williamr@4
   631
  { _STLP_FIX_LITERAL_BUG(__s) return _M_append(__s, __s+__n); }
williamr@4
   632
  _Self& append(const _CharT* __s)
williamr@4
   633
  { _STLP_FIX_LITERAL_BUG(__s) return _M_append(__s, __s + traits_type::length(__s)); }
williamr@4
   634
  _Self& append(size_type __n, _CharT __c);
williamr@4
   635
williamr@4
   636
public:
williamr@4
   637
  void push_back(_CharT __c) {
williamr@4
   638
    if (this->_M_Finish() + 1 == this->_M_end_of_storage._M_data)
williamr@4
   639
      reserve(size() + (max)(size(), __STATIC_CAST(size_type,1)));
williamr@4
   640
    _M_construct_null(this->_M_Finish() + 1);
williamr@4
   641
    _Traits::assign(*(this->_M_Finish()), __c);
williamr@4
   642
    ++this->_M_finish;
williamr@4
   643
  }
williamr@4
   644
williamr@4
   645
  void pop_back() {
williamr@4
   646
    _Traits::assign(*(this->_M_Finish() - 1), _M_null());
williamr@4
   647
    this->_M_destroy_back();
williamr@4
   648
    --this->_M_finish;
williamr@4
   649
  }
williamr@4
   650
williamr@4
   651
public:                         // Assign
williamr@4
   652
  _Self& assign(const _Self& __s)
williamr@4
   653
  { return _M_assign(__s._M_Start(), __s._M_Finish()); }
williamr@4
   654
williamr@4
   655
  _Self& assign(const _Self& __s,
williamr@4
   656
                size_type __pos, size_type __n) {
williamr@4
   657
    if (__pos > __s.size())
williamr@4
   658
      this->_M_throw_out_of_range();
williamr@4
   659
    return _M_assign(__s._M_Start() + __pos,
williamr@4
   660
                     __s._M_Start() + __pos + (min) (__n, __s.size() - __pos));
williamr@4
   661
  }
williamr@4
   662
williamr@4
   663
  _Self& assign(const _CharT* __s, size_type __n)
williamr@4
   664
  { _STLP_FIX_LITERAL_BUG(__s) return _M_assign(__s, __s + __n); }
williamr@4
   665
williamr@4
   666
  _Self& assign(const _CharT* __s)
williamr@4
   667
  { _STLP_FIX_LITERAL_BUG(__s) return _M_assign(__s, __s + _Traits::length(__s)); }
williamr@4
   668
williamr@4
   669
  _Self& assign(size_type __n, _CharT __c);
williamr@4
   670
williamr@4
   671
#if defined (_STLP_MEMBER_TEMPLATES)
williamr@4
   672
#  if !defined (_STLP_USE_MSVC6_MEM_T_BUG_WORKAROUND)
williamr@4
   673
private:                        // Helper functions for assign.
williamr@4
   674
  template <class _Integer>
williamr@4
   675
  _Self& _M_assign_dispatch(_Integer __n, _Integer __x, const __true_type& /*_Integral*/)
williamr@4
   676
  { return assign((size_type) __n, (_CharT) __x); }
williamr@4
   677
williamr@4
   678
  template <class _InputIter>
williamr@4
   679
  _Self& _M_assign_dispatch(_InputIter __f, _InputIter __l, const __false_type& /*_Integral*/) {
williamr@4
   680
    pointer __cur = this->_M_Start();
williamr@4
   681
    while (__f != __l && __cur != this->_M_Finish()) {
williamr@4
   682
      _Traits::assign(*__cur, *__f);
williamr@4
   683
      ++__f;
williamr@4
   684
      ++__cur;
williamr@4
   685
    }
williamr@4
   686
    if (__f == __l)
williamr@4
   687
      erase(__cur, this->end());
williamr@4
   688
    else
williamr@4
   689
      _M_appendT(__f, __l, _STLP_ITERATOR_CATEGORY(__f, _InputIter));
williamr@4
   690
    return *this;
williamr@4
   691
  }
williamr@4
   692
williamr@4
   693
public:
williamr@4
   694
  // Check to see if _InputIterator is an integer type.  If so, then
williamr@4
   695
  // it can't be an iterator.
williamr@4
   696
  template <class _InputIter>
williamr@4
   697
  _Self& assign(_InputIter __first, _InputIter __last) {
williamr@4
   698
    typedef typename _IsIntegral<_InputIter>::_Ret _Integral;
williamr@4
   699
    return _M_assign_dispatch(__first, __last, _Integral());
williamr@4
   700
  }
williamr@4
   701
#  endif
williamr@4
   702
#endif
williamr@4
   703
williamr@4
   704
protected:
williamr@4
   705
  _Self& _M_assign(const _CharT* __f, const _CharT* __l);
williamr@4
   706
williamr@4
   707
public:
williamr@4
   708
williamr@4
   709
#if !defined (_STLP_MEMBER_TEMPLATES) || \
williamr@4
   710
    !defined (_STLP_NO_METHOD_SPECIALIZATION) && !defined (_STLP_NO_EXTENSIONS)
williamr@4
   711
#  if !defined (_STLP_USE_MSVC6_MEM_T_BUG_WORKAROUND)
williamr@4
   712
  _Self& assign(const _CharT* __f, const _CharT* __l) {
williamr@4
   713
    _STLP_FIX_LITERAL_BUG(__f) _STLP_FIX_LITERAL_BUG(__l)
williamr@4
   714
    return _M_assign(__f, __l);
williamr@4
   715
  }
williamr@4
   716
#  endif
williamr@4
   717
#endif
williamr@4
   718
williamr@4
   719
public:                         // Insert
williamr@4
   720
williamr@4
   721
  _Self& insert(size_type __pos, const _Self& __s) {
williamr@4
   722
    if (__pos > size())
williamr@4
   723
      this->_M_throw_out_of_range();
williamr@4
   724
    if (size() > max_size() - __s.size())
williamr@4
   725
      this->_M_throw_length_error();
williamr@4
   726
    _M_insert(begin() + __pos, __s._M_Start(), __s._M_Finish(), &__s == this);
williamr@4
   727
    return *this;
williamr@4
   728
  }
williamr@4
   729
williamr@4
   730
  _Self& insert(size_type __pos, const _Self& __s,
williamr@4
   731
                size_type __beg, size_type __n) {
williamr@4
   732
    if (__pos > size() || __beg > __s.size())
williamr@4
   733
      this->_M_throw_out_of_range();
williamr@4
   734
    size_type __len = (min) (__n, __s.size() - __beg);
williamr@4
   735
    if (size() > max_size() - __len)
williamr@4
   736
      this->_M_throw_length_error();
williamr@4
   737
    _M_insert(begin() + __pos,
williamr@4
   738
              __s._M_Start() + __beg, __s._M_Start() + __beg + __len, &__s == this);
williamr@4
   739
    return *this;
williamr@4
   740
  }
williamr@4
   741
  _Self& insert(size_type __pos, const _CharT* __s, size_type __n) {
williamr@4
   742
    _STLP_FIX_LITERAL_BUG(__s)
williamr@4
   743
    if (__pos > size())
williamr@4
   744
      this->_M_throw_out_of_range();
williamr@4
   745
    if (size() > max_size() - __n)
williamr@4
   746
      this->_M_throw_length_error();
williamr@4
   747
    _M_insert(begin() + __pos, __s, __s + __n, _M_inside(__s));
williamr@4
   748
    return *this;
williamr@4
   749
  }
williamr@4
   750
williamr@4
   751
  _Self& insert(size_type __pos, const _CharT* __s) {
williamr@4
   752
    _STLP_FIX_LITERAL_BUG(__s)
williamr@4
   753
    if (__pos > size())
williamr@4
   754
      this->_M_throw_out_of_range();
williamr@4
   755
    size_type __len = _Traits::length(__s);
williamr@4
   756
    if (size() > max_size() - __len)
williamr@4
   757
      this->_M_throw_length_error();
williamr@4
   758
    _M_insert(this->_M_Start() + __pos, __s, __s + __len, _M_inside(__s));
williamr@4
   759
    return *this;
williamr@4
   760
  }
williamr@4
   761
williamr@4
   762
  _Self& insert(size_type __pos, size_type __n, _CharT __c) {
williamr@4
   763
    if (__pos > size())
williamr@4
   764
      this->_M_throw_out_of_range();
williamr@4
   765
    if (size() > max_size() - __n)
williamr@4
   766
      this->_M_throw_length_error();
williamr@4
   767
    insert(begin() + __pos, __n, __c);
williamr@4
   768
    return *this;
williamr@4
   769
  }
williamr@4
   770
williamr@4
   771
  iterator insert(iterator __p, _CharT __c) {
williamr@4
   772
    _STLP_FIX_LITERAL_BUG(__p)
williamr@4
   773
    if (__p == end()) {
williamr@4
   774
      push_back(__c);
williamr@4
   775
      return this->_M_Finish() - 1;
williamr@4
   776
    }
williamr@4
   777
    else
williamr@4
   778
      return _M_insert_aux(__p, __c);
williamr@4
   779
  }
williamr@4
   780
williamr@4
   781
  void insert(iterator __p, size_t __n, _CharT __c);
williamr@4
   782
williamr@4
   783
protected:  // Helper functions for insert.
williamr@4
   784
williamr@4
   785
  void _M_insert(iterator __p, const _CharT* __first, const _CharT* __last, bool __self_ref);
williamr@4
   786
williamr@4
   787
  pointer _M_insert_aux(pointer, _CharT);
williamr@4
   788
williamr@4
   789
  void _M_copy(const _CharT* __f, const _CharT* __l, _CharT* __res) {
williamr@4
   790
    _STLP_FIX_LITERAL_BUG(__f) _STLP_FIX_LITERAL_BUG(__l)
williamr@4
   791
    _STLP_FIX_LITERAL_BUG(__res)
williamr@4
   792
    _Traits::copy(__res, __f, __l - __f);
williamr@4
   793
  }
williamr@4
   794
williamr@4
   795
  void _M_move(const _CharT* __f, const _CharT* __l, _CharT* __res) {
williamr@4
   796
    _STLP_FIX_LITERAL_BUG(__f) _STLP_FIX_LITERAL_BUG(__l)
williamr@4
   797
    _Traits::move(__res, __f, __l - __f);
williamr@4
   798
  }
williamr@4
   799
williamr@4
   800
#if defined (_STLP_MEMBER_TEMPLATES)
williamr@4
   801
#  if !defined (_STLP_USE_MSVC6_MEM_T_BUG_WORKAROUND)
williamr@4
   802
  template <class _ForwardIter>
williamr@4
   803
  void _M_insert_overflow(iterator __pos, _ForwardIter __first, _ForwardIter __last,
williamr@4
   804
                          difference_type __n) {
williamr@4
   805
    const size_type __old_size = this->size();
williamr@4
   806
    size_type __len = __old_size + (max)(__old_size, __STATIC_CAST(size_type,__n)) + 1;
williamr@4
   807
    pointer __new_start = this->_M_end_of_storage.allocate(__len, __len);
williamr@4
   808
    pointer __new_finish = __new_start;
williamr@4
   809
    _STLP_TRY {
williamr@4
   810
      __new_finish = uninitialized_copy(this->_M_Start(), __pos, __new_start);
williamr@4
   811
      __new_finish = uninitialized_copy(__first, __last, __new_finish);
williamr@4
   812
      __new_finish = uninitialized_copy(__pos, this->_M_Finish(), __new_finish);
williamr@4
   813
      _M_construct_null(__new_finish);
williamr@4
   814
    }
williamr@4
   815
    _STLP_UNWIND((_STLP_STD::_Destroy_Range(__new_start,__new_finish),
williamr@4
   816
                  this->_M_end_of_storage.deallocate(__new_start, __len)))
williamr@4
   817
    this->_M_destroy_range();
williamr@4
   818
    this->_M_deallocate_block();
williamr@4
   819
    this->_M_reset(__new_start, __new_finish, __new_start + __len);
williamr@4
   820
  }
williamr@4
   821
williamr@4
   822
  template <class _InputIter>
williamr@4
   823
  void _M_insertT(iterator __p, _InputIter __first, _InputIter __last,
williamr@4
   824
                  const input_iterator_tag &) {
williamr@4
   825
    for ( ; __first != __last; ++__first) {
williamr@4
   826
      __p = insert(__p, *__first);
williamr@4
   827
      ++__p;
williamr@4
   828
    }
williamr@4
   829
  }
williamr@4
   830
williamr@4
   831
  template <class _ForwardIter>
williamr@4
   832
  void _M_insertT(iterator __pos, _ForwardIter __first, _ForwardIter __last,
williamr@4
   833
                  const forward_iterator_tag &) {
williamr@4
   834
    if (__first != __last) {
williamr@4
   835
      difference_type __n = distance(__first, __last);
williamr@4
   836
      if (this->_M_end_of_storage._M_data - this->_M_finish >= __n + 1) {
williamr@4
   837
        const difference_type __elems_after = this->_M_finish - __pos;
williamr@4
   838
        if (__elems_after >= __n) {
williamr@4
   839
#    if defined (_STLP_USE_SHORT_STRING_OPTIM)
williamr@4
   840
          if (this->_M_using_static_buf())
williamr@4
   841
            _M_copy((this->_M_Finish() - __n) + 1, this->_M_Finish() + 1, this->_M_Finish() + 1);
williamr@4
   842
          else
williamr@4
   843
#    endif /* _STLP_USE_SHORT_STRING_OPTIM */
williamr@4
   844
          uninitialized_copy((this->_M_Finish() - __n) + 1, this->_M_Finish() + 1, this->_M_Finish() + 1);
williamr@4
   845
          this->_M_finish += __n;
williamr@4
   846
          _Traits::move(__pos + __n, __pos, (__elems_after - __n) + 1);
williamr@4
   847
          _M_copyT(__first, __last, __pos);
williamr@4
   848
        }
williamr@4
   849
        else {
williamr@4
   850
          pointer __old_finish = this->_M_Finish();
williamr@4
   851
          _ForwardIter __mid = __first;
williamr@4
   852
          advance(__mid, __elems_after + 1);
williamr@4
   853
#    if defined (_STLP_USE_SHORT_STRING_OPTIM)
williamr@4
   854
          if (this->_M_using_static_buf())
williamr@4
   855
            _M_copyT(__mid, __last, this->_M_Finish() + 1);
williamr@4
   856
          else
williamr@4
   857
#    endif /* _STLP_USE_SHORT_STRING_OPTIM */
williamr@4
   858
          uninitialized_copy(__mid, __last, this->_M_Finish() + 1);
williamr@4
   859
          this->_M_finish += __n - __elems_after;
williamr@4
   860
          _STLP_TRY {
williamr@4
   861
#    if defined (_STLP_USE_SHORT_STRING_OPTIM)
williamr@4
   862
            if (this->_M_using_static_buf())
williamr@4
   863
              _M_copy(__pos, __old_finish + 1, this->_M_Finish());
williamr@4
   864
            else
williamr@4
   865
#    endif /* _STLP_USE_SHORT_STRING_OPTIM */
williamr@4
   866
            uninitialized_copy(__pos, __old_finish + 1, this->_M_Finish());
williamr@4
   867
            this->_M_finish += __elems_after;
williamr@4
   868
          }
williamr@4
   869
          _STLP_UNWIND((this->_M_destroy_ptr_range(__old_finish + 1, this->_M_Finish()),
williamr@4
   870
                        this->_M_finish = __old_finish))
williamr@4
   871
          _M_copyT(__first, __mid, __pos);
williamr@4
   872
        }
williamr@4
   873
      }
williamr@4
   874
      else {
williamr@4
   875
        _M_insert_overflow(__pos, __first, __last, __n);
williamr@4
   876
      }
williamr@4
   877
    }
williamr@4
   878
  }
williamr@4
   879
williamr@4
   880
  template <class _Integer>
williamr@4
   881
  void _M_insert_dispatch(iterator __p, _Integer __n, _Integer __x,
williamr@4
   882
                          const __true_type& /*Integral*/) {
williamr@4
   883
    insert(__p, (size_type) __n, (_CharT) __x);
williamr@4
   884
  }
williamr@4
   885
williamr@4
   886
  template <class _InputIter>
williamr@4
   887
  void _M_insert_dispatch(iterator __p, _InputIter __first, _InputIter __last,
williamr@4
   888
                          const __false_type& /*Integral*/) {
williamr@4
   889
    _STLP_FIX_LITERAL_BUG(__p)
williamr@4
   890
    /*
williamr@4
   891
     * Within the basic_string implementation we are only going to check for
williamr@4
   892
     * self referencing if iterators are string iterators or _CharT pointers.
williamr@4
   893
     * A user could encapsulate those iterator within their own iterator interface
williamr@4
   894
     * and in this case lead to a bad behavior, this is a known limitation.
williamr@4
   895
     */
williamr@4
   896
    typedef typename _AreSameUnCVTypes<_InputIter, iterator>::_Ret _IsIterator;
williamr@4
   897
    typedef typename _AreSameUnCVTypes<_InputIter, const_iterator>::_Ret _IsConstIterator;
williamr@4
   898
    typedef typename _Lor2<_IsIterator, _IsConstIterator>::_Ret _CheckInside;
williamr@4
   899
    _M_insert_aux(__p, __first, __last, _CheckInside());
williamr@4
   900
  }
williamr@4
   901
williamr@4
   902
  template <class _RandomIter>
williamr@4
   903
  void _M_insert_aux (iterator __p, _RandomIter __first, _RandomIter __last,
williamr@4
   904
                      const __true_type& /*_CheckInside*/) {
williamr@4
   905
    _STLP_FIX_LITERAL_BUG(__p)
williamr@4
   906
    _M_insert(__p, &(*__first), &(*__last), _M_inside(&(*__first)));
williamr@4
   907
  }
williamr@4
   908
williamr@4
   909
  template<class _InputIter>
williamr@4
   910
  void _M_insert_aux (iterator __p, _InputIter __first, _InputIter __last,
williamr@4
   911
                      const __false_type& /*_CheckInside*/) {
williamr@4
   912
    _STLP_FIX_LITERAL_BUG(__p)
williamr@4
   913
    _M_insertT(__p, __first, __last, _STLP_ITERATOR_CATEGORY(__first, _InputIter));
williamr@4
   914
  }
williamr@4
   915
williamr@4
   916
  template <class _InputIterator>
williamr@4
   917
  void _M_copyT(_InputIterator __first, _InputIterator __last, pointer __result) {
williamr@4
   918
    _STLP_FIX_LITERAL_BUG(__result)
williamr@4
   919
    for ( ; __first != __last; ++__first, ++__result)
williamr@4
   920
      _Traits::assign(*__result, *__first);
williamr@4
   921
  }
williamr@4
   922
williamr@4
   923
#    if !defined (_STLP_NO_METHOD_SPECIALIZATION)
williamr@4
   924
  void _M_copyT(const _CharT* __f, const _CharT* __l, _CharT* __res) {
williamr@4
   925
    _STLP_FIX_LITERAL_BUG(__f) _STLP_FIX_LITERAL_BUG(__l)
williamr@4
   926
    _STLP_FIX_LITERAL_BUG(__res)
williamr@4
   927
    _Traits::copy(__res, __f, __l - __f);
williamr@4
   928
  }
williamr@4
   929
#    endif
williamr@4
   930
williamr@4
   931
public:
williamr@4
   932
  // Check to see if _InputIterator is an integer type.  If so, then
williamr@4
   933
  // it can't be an iterator.
williamr@4
   934
  template <class _InputIter>
williamr@4
   935
  void insert(iterator __p, _InputIter __first, _InputIter __last) {
williamr@4
   936
    typedef typename _IsIntegral<_InputIter>::_Ret _Integral;
williamr@4
   937
    _M_insert_dispatch(__p, __first, __last, _Integral());
williamr@4
   938
  }
williamr@4
   939
#  endif
williamr@4
   940
#endif
williamr@4
   941
williamr@4
   942
public:
williamr@4
   943
williamr@4
   944
#if !defined (_STLP_MEMBER_TEMPLATES) || \
williamr@4
   945
    !defined (_STLP_NO_METHOD_SPECIALIZATION) && !defined (_STLP_NO_EXTENSIONS)
williamr@4
   946
  void insert(iterator __p, const _CharT* __f, const _CharT* __l) {
williamr@4
   947
    _STLP_FIX_LITERAL_BUG(__f) _STLP_FIX_LITERAL_BUG(__l)
williamr@4
   948
    _M_insert(__p, __f, __l, _M_inside(__f));
williamr@4
   949
  }
williamr@4
   950
#endif
williamr@4
   951
williamr@4
   952
public:                         // Erase.
williamr@4
   953
williamr@4
   954
  _Self& erase(size_type __pos = 0, size_type __n = npos) {
williamr@4
   955
    if (__pos > size())
williamr@4
   956
      this->_M_throw_out_of_range();
williamr@4
   957
    erase(begin() + __pos, begin() + __pos + (min) (__n, size() - __pos));
williamr@4
   958
    return *this;
williamr@4
   959
  }
williamr@4
   960
williamr@4
   961
  iterator erase(iterator __pos) {
williamr@4
   962
    // The move includes the terminating _CharT().
williamr@4
   963
    _Traits::move(__pos, __pos + 1, this->_M_Finish() - __pos);
williamr@4
   964
    this->_M_destroy_back();
williamr@4
   965
    --this->_M_finish;
williamr@4
   966
    return __pos;
williamr@4
   967
  }
williamr@4
   968
williamr@4
   969
  iterator erase(iterator __first, iterator __last) {
williamr@4
   970
    if (__first != __last) {
williamr@4
   971
      // The move includes the terminating _CharT().
williamr@4
   972
      traits_type::move(__first, __last, (this->_M_Finish() - __last) + 1);
williamr@4
   973
      pointer __new_finish = this->_M_Finish() - (__last - __first);
williamr@4
   974
      this->_M_destroy_ptr_range(__new_finish + 1, this->_M_Finish() + 1);
williamr@4
   975
      this->_M_finish = __new_finish;
williamr@4
   976
    }
williamr@4
   977
    return __first;
williamr@4
   978
  }
williamr@4
   979
williamr@4
   980
public:                         // Replace.  (Conceptually equivalent
williamr@4
   981
                                // to erase followed by insert.)
williamr@4
   982
  _Self& replace(size_type __pos, size_type __n, const _Self& __s) {
williamr@4
   983
    if (__pos > size())
williamr@4
   984
      this->_M_throw_out_of_range();
williamr@4
   985
    const size_type __len = (min) (__n, size() - __pos);
williamr@4
   986
    if (size() - __len >= max_size() - __s.size())
williamr@4
   987
      this->_M_throw_length_error();
williamr@4
   988
    return _M_replace(begin() + __pos, begin() + __pos + __len,
williamr@4
   989
                      __s._M_Start(), __s._M_Finish(), &__s == this);
williamr@4
   990
  }
williamr@4
   991
williamr@4
   992
  _Self& replace(size_type __pos1, size_type __n1, const _Self& __s,
williamr@4
   993
                 size_type __pos2, size_type __n2) {
williamr@4
   994
    if (__pos1 > size() || __pos2 > __s.size())
williamr@4
   995
      this->_M_throw_out_of_range();
williamr@4
   996
    const size_type __len1 = (min) (__n1, size() - __pos1);
williamr@4
   997
    const size_type __len2 = (min) (__n2, __s.size() - __pos2);
williamr@4
   998
    if (size() - __len1 >= max_size() - __len2)
williamr@4
   999
      this->_M_throw_length_error();
williamr@4
  1000
    return _M_replace(begin() + __pos1, begin() + __pos1 + __len1,
williamr@4
  1001
                      __s._M_Start() + __pos2, __s._M_Start() + __pos2 + __len2, &__s == this);
williamr@4
  1002
  }
williamr@4
  1003
williamr@4
  1004
  _Self& replace(size_type __pos, size_type __n1,
williamr@4
  1005
                 const _CharT* __s, size_type __n2) {
williamr@4
  1006
    _STLP_FIX_LITERAL_BUG(__s)
williamr@4
  1007
    if (__pos > size())
williamr@4
  1008
      this->_M_throw_out_of_range();
williamr@4
  1009
    const size_type __len = (min) (__n1, size() - __pos);
williamr@4
  1010
    if (__n2 > max_size() || size() - __len >= max_size() - __n2)
williamr@4
  1011
      this->_M_throw_length_error();
williamr@4
  1012
    return _M_replace(begin() + __pos, begin() + __pos + __len,
williamr@4
  1013
                      __s, __s + __n2, _M_inside(__s));
williamr@4
  1014
  }
williamr@4
  1015
williamr@4
  1016
  _Self& replace(size_type __pos, size_type __n1, const _CharT* __s) {
williamr@4
  1017
    _STLP_FIX_LITERAL_BUG(__s)
williamr@4
  1018
    if (__pos > size())
williamr@4
  1019
      this->_M_throw_out_of_range();
williamr@4
  1020
    const size_type __len = (min) (__n1, size() - __pos);
williamr@4
  1021
    const size_type __n2 = _Traits::length(__s);
williamr@4
  1022
    if (__n2 > max_size() || size() - __len >= max_size() - __n2)
williamr@4
  1023
      this->_M_throw_length_error();
williamr@4
  1024
    return _M_replace(begin() + __pos, begin() + __pos + __len,
williamr@4
  1025
                      __s, __s + _Traits::length(__s), _M_inside(__s));
williamr@4
  1026
  }
williamr@4
  1027
williamr@4
  1028
  _Self& replace(size_type __pos, size_type __n1,
williamr@4
  1029
                 size_type __n2, _CharT __c) {
williamr@4
  1030
    if (__pos > size())
williamr@4
  1031
      this->_M_throw_out_of_range();
williamr@4
  1032
    const size_type __len = (min) (__n1, size() - __pos);
williamr@4
  1033
    if (__n2 > max_size() || size() - __len >= max_size() - __n2)
williamr@4
  1034
      this->_M_throw_length_error();
williamr@4
  1035
    return replace(begin() + __pos, begin() + __pos + __len, __n2, __c);
williamr@4
  1036
  }
williamr@4
  1037
williamr@4
  1038
  _Self& replace(iterator __first, iterator __last, const _Self& __s) {
williamr@4
  1039
    _STLP_FIX_LITERAL_BUG(__first)_STLP_FIX_LITERAL_BUG(__last)
williamr@4
  1040
    return _M_replace(__first, __last, __s._M_Start(), __s._M_Finish(), &__s == this);
williamr@4
  1041
  }
williamr@4
  1042
williamr@4
  1043
  _Self& replace(iterator __first, iterator __last,
williamr@4
  1044
                 const _CharT* __s, size_type __n) {
williamr@4
  1045
    _STLP_FIX_LITERAL_BUG(__first)_STLP_FIX_LITERAL_BUG(__last)
williamr@4
  1046
    _STLP_FIX_LITERAL_BUG(__s)
williamr@4
  1047
    return _M_replace(__first, __last, __s, __s + __n, _M_inside(__s));
williamr@4
  1048
  }
williamr@4
  1049
williamr@4
  1050
  _Self& replace(iterator __first, iterator __last,
williamr@4
  1051
                 const _CharT* __s) {
williamr@4
  1052
    _STLP_FIX_LITERAL_BUG(__first)_STLP_FIX_LITERAL_BUG(__last)
williamr@4
  1053
    _STLP_FIX_LITERAL_BUG(__s)
williamr@4
  1054
    return _M_replace(__first, __last, __s, __s + _Traits::length(__s), _M_inside(__s));
williamr@4
  1055
  }
williamr@4
  1056
williamr@4
  1057
  _Self& replace(iterator __first, iterator __last, size_type __n, _CharT __c);
williamr@4
  1058
williamr@4
  1059
protected:                        // Helper functions for replace.
williamr@4
  1060
  _Self& _M_replace(iterator __first, iterator __last,
williamr@4
  1061
                    const _CharT* __f, const _CharT* __l, bool __self_ref);
williamr@4
  1062
williamr@4
  1063
public:
williamr@4
  1064
#if defined (_STLP_MEMBER_TEMPLATES)
williamr@4
  1065
#  if !defined (_STLP_USE_MSVC6_MEM_T_BUG_WORKAROUND)
williamr@4
  1066
  template <class _Integer>
williamr@4
  1067
  _Self& _M_replace_dispatch(iterator __first, iterator __last,
williamr@4
  1068
                             _Integer __n, _Integer __x, const __true_type& /*IsIntegral*/) {
williamr@4
  1069
    _STLP_FIX_LITERAL_BUG(__first) _STLP_FIX_LITERAL_BUG(__last)
williamr@4
  1070
    return replace(__first, __last, (size_type) __n, (_CharT) __x);
williamr@4
  1071
  }
williamr@4
  1072
williamr@4
  1073
  template <class _InputIter>
williamr@4
  1074
  _Self& _M_replace_dispatch(iterator __first, iterator __last,
williamr@4
  1075
                             _InputIter __f, _InputIter __l, const __false_type& /*IsIntegral*/) {
williamr@4
  1076
    _STLP_FIX_LITERAL_BUG(__first) _STLP_FIX_LITERAL_BUG(__last)
williamr@4
  1077
    typedef typename _AreSameUnCVTypes<_InputIter, iterator>::_Ret _IsIterator;
williamr@4
  1078
    typedef typename _AreSameUnCVTypes<_InputIter, const_iterator>::_Ret _IsConstIterator;
williamr@4
  1079
    typedef typename _Lor2<_IsIterator, _IsConstIterator>::_Ret _CheckInside;
williamr@4
  1080
    return _M_replace_aux(__first, __last, __f, __l, _CheckInside());
williamr@4
  1081
  }
williamr@4
  1082
williamr@4
  1083
  template <class _RandomIter>
williamr@4
  1084
  _Self& _M_replace_aux(iterator __first, iterator __last,
williamr@4
  1085
                        _RandomIter __f, _RandomIter __l, __true_type const& /*_CheckInside*/) {
williamr@4
  1086
    _STLP_FIX_LITERAL_BUG(__first) _STLP_FIX_LITERAL_BUG(__last)
williamr@4
  1087
    return _M_replace(__first, __last, &(*__f), &(*__l), _M_inside(&(*__f)));
williamr@4
  1088
  }
williamr@4
  1089
williamr@4
  1090
  template <class _InputIter>
williamr@4
  1091
  _Self& _M_replace_aux(iterator __first, iterator __last,
williamr@4
  1092
                     _InputIter __f, _InputIter __l, __false_type const& /*_CheckInside*/) {
williamr@4
  1093
    _STLP_FIX_LITERAL_BUG(__first) _STLP_FIX_LITERAL_BUG(__last)
williamr@4
  1094
    return _M_replaceT(__first, __last, __f, __l, _STLP_ITERATOR_CATEGORY(__f, _InputIter));
williamr@4
  1095
  }
williamr@4
  1096
williamr@4
  1097
  template <class _InputIter>
williamr@4
  1098
  _Self& _M_replaceT(iterator __first, iterator __last,
williamr@4
  1099
                     _InputIter __f, _InputIter __l, const input_iterator_tag&__ite_tag) {
williamr@4
  1100
    _STLP_FIX_LITERAL_BUG(__first) _STLP_FIX_LITERAL_BUG(__last)
williamr@4
  1101
    for ( ; __first != __last && __f != __l; ++__first, ++__f)
williamr@4
  1102
      _Traits::assign(*__first, *__f);
williamr@4
  1103
    if (__f == __l)
williamr@4
  1104
      erase(__first, __last);
williamr@4
  1105
    else
williamr@4
  1106
      _M_insertT(__last, __f, __l, __ite_tag);
williamr@4
  1107
    return *this;
williamr@4
  1108
  }
williamr@4
  1109
williamr@4
  1110
  template <class _ForwardIter>
williamr@4
  1111
  _Self& _M_replaceT(iterator __first, iterator __last,
williamr@4
  1112
                     _ForwardIter __f, _ForwardIter __l, const forward_iterator_tag &__ite_tag) {
williamr@4
  1113
    _STLP_FIX_LITERAL_BUG(__first) _STLP_FIX_LITERAL_BUG(__last)
williamr@4
  1114
    difference_type __n = distance(__f, __l);
williamr@4
  1115
    const difference_type __len = __last - __first;
williamr@4
  1116
    if (__len >= __n) {
williamr@4
  1117
      _M_copyT(__f, __l, __first);
williamr@4
  1118
      erase(__first + __n, __last);
williamr@4
  1119
    }
williamr@4
  1120
    else {
williamr@4
  1121
      _ForwardIter __m = __f;
williamr@4
  1122
      advance(__m, __len);
williamr@4
  1123
      _M_copyT(__f, __m, __first);
williamr@4
  1124
      _M_insertT(__last, __m, __l, __ite_tag);
williamr@4
  1125
    }
williamr@4
  1126
    return *this;
williamr@4
  1127
  }
williamr@4
  1128
williamr@4
  1129
public:
williamr@4
  1130
  // Check to see if _InputIter is an integer type.  If so, then
williamr@4
  1131
  // it can't be an iterator.
williamr@4
  1132
  template <class _InputIter>
williamr@4
  1133
  _Self& replace(iterator __first, iterator __last,
williamr@4
  1134
                 _InputIter __f, _InputIter __l) {
williamr@4
  1135
    _STLP_FIX_LITERAL_BUG(__first)_STLP_FIX_LITERAL_BUG(__last)
williamr@4
  1136
    typedef typename _IsIntegral<_InputIter>::_Ret _Integral;
williamr@4
  1137
    return _M_replace_dispatch(__first, __last, __f, __l,  _Integral());
williamr@4
  1138
  }
williamr@4
  1139
williamr@4
  1140
#  endif
williamr@4
  1141
#endif
williamr@4
  1142
williamr@4
  1143
#if !defined (_STLP_MEMBER_TEMPLATES) || \
williamr@4
  1144
    !defined (_STLP_NO_METHOD_SPECIALIZATION) && !defined (_STLP_NO_EXTENSIONS)
williamr@4
  1145
#  if !defined (_STLP_USE_MSVC6_MEM_T_BUG_WORKAROUND)
williamr@4
  1146
  _Self& replace(iterator __first, iterator __last,
williamr@4
  1147
                 const _CharT* __f, const _CharT* __l) {
williamr@4
  1148
    _STLP_FIX_LITERAL_BUG(__first)_STLP_FIX_LITERAL_BUG(__last)
williamr@4
  1149
    _STLP_FIX_LITERAL_BUG(__f) _STLP_FIX_LITERAL_BUG(__l)
williamr@4
  1150
    return _M_replace(__first, __last, __f, __l, _M_inside(__f));
williamr@4
  1151
  }
williamr@4
  1152
#  endif
williamr@4
  1153
#endif
williamr@4
  1154
williamr@4
  1155
public:                         // Other modifier member functions.
williamr@4
  1156
williamr@4
  1157
  size_type copy(_CharT* __s, size_type __n, size_type __pos = 0) const {
williamr@4
  1158
    _STLP_FIX_LITERAL_BUG(__s)
williamr@4
  1159
    if (__pos > size())
williamr@4
  1160
      this->_M_throw_out_of_range();
williamr@4
  1161
    const size_type __len = (min) (__n, size() - __pos);
williamr@4
  1162
    _Traits::copy(__s, this->_M_Start() + __pos, __len);
williamr@4
  1163
    return __len;
williamr@4
  1164
  }
williamr@4
  1165
williamr@4
  1166
  void swap(_Self& __s) {
williamr@4
  1167
    this->_M_Swap(__s);
williamr@4
  1168
  }
williamr@4
  1169
williamr@4
  1170
public:                         // Conversion to C string.
williamr@4
  1171
williamr@4
  1172
  const _CharT* c_str() const { return this->_M_Start(); }
williamr@4
  1173
  const _CharT* data()  const { return this->_M_Start(); }
williamr@4
  1174
williamr@4
  1175
public:                         // find.
williamr@4
  1176
williamr@4
  1177
  size_type find(const _Self& __s, size_type __pos = 0) const
williamr@4
  1178
    { return find(__s._M_Start(), __pos, __s.size()); }
williamr@4
  1179
williamr@4
  1180
  size_type find(const _CharT* __s, size_type __pos = 0) const
williamr@4
  1181
    { _STLP_FIX_LITERAL_BUG(__s) return find(__s, __pos, _Traits::length(__s)); }
williamr@4
  1182
williamr@4
  1183
  size_type find(const _CharT* __s, size_type __pos, size_type __n) const;
williamr@4
  1184
williamr@4
  1185
  // WIE: Versant schema compiler 5.2.2 ICE workaround
williamr@4
  1186
  size_type find(_CharT __c) const { return find(__c, 0); }
williamr@4
  1187
  size_type find(_CharT __c, size_type __pos /* = 0 */) const;
williamr@4
  1188
williamr@4
  1189
public:                         // rfind.
williamr@4
  1190
williamr@4
  1191
  size_type rfind(const _Self& __s, size_type __pos = npos) const
williamr@4
  1192
    { return rfind(__s._M_Start(), __pos, __s.size()); }
williamr@4
  1193
williamr@4
  1194
  size_type rfind(const _CharT* __s, size_type __pos = npos) const
williamr@4
  1195
    { _STLP_FIX_LITERAL_BUG(__s) return rfind(__s, __pos, _Traits::length(__s)); }
williamr@4
  1196
williamr@4
  1197
  size_type rfind(const _CharT* __s, size_type __pos, size_type __n) const;
williamr@4
  1198
  size_type rfind(_CharT __c, size_type __pos = npos) const;
williamr@4
  1199
williamr@4
  1200
public:                         // find_first_of
williamr@4
  1201
williamr@4
  1202
  size_type find_first_of(const _Self& __s, size_type __pos = 0) const
williamr@4
  1203
    { return find_first_of(__s._M_Start(), __pos, __s.size()); }
williamr@4
  1204
williamr@4
  1205
  size_type find_first_of(const _CharT* __s, size_type __pos = 0) const
williamr@4
  1206
    { _STLP_FIX_LITERAL_BUG(__s) return find_first_of(__s, __pos, _Traits::length(__s)); }
williamr@4
  1207
williamr@4
  1208
  size_type find_first_of(const _CharT* __s, size_type __pos,
williamr@4
  1209
                          size_type __n) const;
williamr@4
  1210
williamr@4
  1211
  size_type find_first_of(_CharT __c, size_type __pos = 0) const
williamr@4
  1212
    { return find(__c, __pos); }
williamr@4
  1213
williamr@4
  1214
public:                         // find_last_of
williamr@4
  1215
williamr@4
  1216
  size_type find_last_of(const _Self& __s,
williamr@4
  1217
                         size_type __pos = npos) const
williamr@4
  1218
    { return find_last_of(__s._M_Start(), __pos, __s.size()); }
williamr@4
  1219
williamr@4
  1220
  size_type find_last_of(const _CharT* __s, size_type __pos = npos) const
williamr@4
  1221
    { _STLP_FIX_LITERAL_BUG(__s) return find_last_of(__s, __pos, _Traits::length(__s)); }
williamr@4
  1222
williamr@4
  1223
  size_type find_last_of(const _CharT* __s, size_type __pos,
williamr@4
  1224
                         size_type __n) const;
williamr@4
  1225
williamr@4
  1226
  size_type find_last_of(_CharT __c, size_type __pos = npos) const {
williamr@4
  1227
    return rfind(__c, __pos);
williamr@4
  1228
  }
williamr@4
  1229
williamr@4
  1230
public:                         // find_first_not_of
williamr@4
  1231
williamr@4
  1232
  size_type find_first_not_of(const _Self& __s,
williamr@4
  1233
                              size_type __pos = 0) const
williamr@4
  1234
    { return find_first_not_of(__s._M_Start(), __pos, __s.size()); }
williamr@4
  1235
williamr@4
  1236
  size_type find_first_not_of(const _CharT* __s, size_type __pos = 0) const
williamr@4
  1237
  { _STLP_FIX_LITERAL_BUG(__s) return find_first_not_of(__s, __pos, _Traits::length(__s)); }
williamr@4
  1238
williamr@4
  1239
  size_type find_first_not_of(const _CharT* __s, size_type __pos,
williamr@4
  1240
                              size_type __n) const;
williamr@4
  1241
williamr@4
  1242
  size_type find_first_not_of(_CharT __c, size_type __pos = 0) const;
williamr@4
  1243
williamr@4
  1244
public:                         // find_last_not_of
williamr@4
  1245
williamr@4
  1246
  size_type find_last_not_of(const _Self& __s,
williamr@4
  1247
                             size_type __pos = npos) const
williamr@4
  1248
  { return find_last_not_of(__s._M_Start(), __pos, __s.size()); }
williamr@4
  1249
williamr@4
  1250
  size_type find_last_not_of(const _CharT* __s, size_type __pos = npos) const
williamr@4
  1251
    { _STLP_FIX_LITERAL_BUG(__s) return find_last_not_of(__s, __pos, _Traits::length(__s)); }
williamr@4
  1252
williamr@4
  1253
  size_type find_last_not_of(const _CharT* __s, size_type __pos,
williamr@4
  1254
                             size_type __n) const;
williamr@4
  1255
williamr@4
  1256
  size_type find_last_not_of(_CharT __c, size_type __pos = npos) const;
williamr@4
  1257
williamr@4
  1258
public:                         // Substring.
williamr@4
  1259
  _Self substr(size_type __pos = 0, size_type __n = npos) const
williamr@4
  1260
  { return _Self(*this, __pos, __n, get_allocator()); }
williamr@4
  1261
williamr@4
  1262
public:                         // Compare
williamr@4
  1263
  int compare(const _Self& __s) const
williamr@4
  1264
  { return _M_compare(this->_M_Start(), this->_M_Finish(), __s._M_Start(), __s._M_Finish()); }
williamr@4
  1265
williamr@4
  1266
  int compare(size_type __pos1, size_type __n1,
williamr@4
  1267
              const _Self& __s) const {
williamr@4
  1268
    if (__pos1 > size())
williamr@4
  1269
      this->_M_throw_out_of_range();
williamr@4
  1270
    return _M_compare(this->_M_Start() + __pos1,
williamr@4
  1271
                      this->_M_Start() + __pos1 + (min) (__n1, size() - __pos1),
williamr@4
  1272
                      __s._M_Start(), __s._M_Finish());
williamr@4
  1273
  }
williamr@4
  1274
williamr@4
  1275
  int compare(size_type __pos1, size_type __n1,
williamr@4
  1276
              const _Self& __s,
williamr@4
  1277
              size_type __pos2, size_type __n2) const {
williamr@4
  1278
    if (__pos1 > size() || __pos2 > __s.size())
williamr@4
  1279
      this->_M_throw_out_of_range();
williamr@4
  1280
    return _M_compare(this->_M_Start() + __pos1,
williamr@4
  1281
                      this->_M_Start() + __pos1 + (min) (__n1, size() - __pos1),
williamr@4
  1282
                      __s._M_Start() + __pos2,
williamr@4
  1283
                      __s._M_Start() + __pos2 + (min) (__n2, __s.size() - __pos2));
williamr@4
  1284
  }
williamr@4
  1285
williamr@4
  1286
  int compare(const _CharT* __s) const {
williamr@4
  1287
    _STLP_FIX_LITERAL_BUG(__s)
williamr@4
  1288
    return _M_compare(this->_M_Start(), this->_M_Finish(), __s, __s + _Traits::length(__s));
williamr@4
  1289
  }
williamr@4
  1290
williamr@4
  1291
  int compare(size_type __pos1, size_type __n1, const _CharT* __s) const {
williamr@4
  1292
    _STLP_FIX_LITERAL_BUG(__s)
williamr@4
  1293
    if (__pos1 > size())
williamr@4
  1294
      this->_M_throw_out_of_range();
williamr@4
  1295
    return _M_compare(this->_M_Start() + __pos1,
williamr@4
  1296
                      this->_M_Start() + __pos1 + (min) (__n1, size() - __pos1),
williamr@4
  1297
                      __s, __s + _Traits::length(__s));
williamr@4
  1298
  }
williamr@4
  1299
williamr@4
  1300
  int compare(size_type __pos1, size_type __n1, const _CharT* __s,
williamr@4
  1301
              size_type __n2) const {
williamr@4
  1302
    _STLP_FIX_LITERAL_BUG(__s)
williamr@4
  1303
    if (__pos1 > size())
williamr@4
  1304
      this->_M_throw_out_of_range();
williamr@4
  1305
    return _M_compare(this->_M_Start() + __pos1,
williamr@4
  1306
                      this->_M_Start() + __pos1 + (min) (__n1, size() - __pos1),
williamr@4
  1307
                      __s, __s + __n2);
williamr@4
  1308
  }
williamr@4
  1309
williamr@4
  1310
public:                        // Helper functions for compare.
williamr@4
  1311
williamr@4
  1312
  static int _STLP_CALL _M_compare(const _CharT* __f1, const _CharT* __l1,
williamr@4
  1313
                                   const _CharT* __f2, const _CharT* __l2) {
williamr@4
  1314
    const ptrdiff_t __n1 = __l1 - __f1;
williamr@4
  1315
    const ptrdiff_t __n2 = __l2 - __f2;
williamr@4
  1316
    const int cmp = _Traits::compare(__f1, __f2, (min) (__n1, __n2));
williamr@4
  1317
    return cmp != 0 ? cmp : (__n1 < __n2 ? -1 : (__n1 > __n2 ? 1 : 0));
williamr@4
  1318
  }
williamr@4
  1319
#if defined (_STLP_USE_TEMPLATE_EXPRESSION) && !defined (_STLP_DEBUG) && !defined (_STLP_USE_MSVC6_MEM_T_BUG_WORKAROUND)
williamr@4
  1320
#  define _STLP_STRING_SUM_BASE(__reserve, __size, __alloc) _STLP_PRIV _String_base<_CharT,_Alloc>(__alloc, __size + 1)
williamr@4
  1321
#  include <stl/_string_sum_methods.h>
williamr@4
  1322
#  undef _STLP_STRING_SUM_BASE
williamr@4
  1323
#endif /* _STLP_USE_TEMPLATE_EXPRESSION */
williamr@4
  1324
};
williamr@4
  1325
williamr@4
  1326
#if !defined (_STLP_STATIC_CONST_INIT_BUG)
williamr@4
  1327
#  if defined (__GNUC__) && (__GNUC__ == 2) && (__GNUC_MINOR__ == 96)
williamr@4
  1328
template <class _CharT, class _Traits, class _Alloc>
williamr@4
  1329
const size_t basic_string<_CharT, _Traits, _Alloc>::npos = ~(size_t) 0;
williamr@4
  1330
#  endif
williamr@4
  1331
#endif
williamr@4
  1332
williamr@4
  1333
#if defined (_STLP_USE_TEMPLATE_EXPORT)
williamr@4
  1334
_STLP_EXPORT_TEMPLATE_CLASS basic_string<char, char_traits<char>, allocator<char> >;
williamr@4
  1335
#  if defined (_STLP_HAS_WCHAR_T)
williamr@4
  1336
_STLP_EXPORT_TEMPLATE_CLASS basic_string<wchar_t, char_traits<wchar_t>, allocator<wchar_t> >;
williamr@4
  1337
#  endif
williamr@4
  1338
#endif /* _STLP_USE_TEMPLATE_EXPORT */
williamr@4
  1339
williamr@4
  1340
#if defined (basic_string)
williamr@4
  1341
_STLP_MOVE_TO_STD_NAMESPACE
williamr@4
  1342
#  undef basic_string
williamr@4
  1343
#endif
williamr@4
  1344
williamr@4
  1345
_STLP_END_NAMESPACE
williamr@4
  1346
williamr@4
  1347
#if defined (_STLP_USE_MSVC6_MEM_T_BUG_WORKAROUND)
williamr@4
  1348
#  include <stl/_string_workaround.h>
williamr@4
  1349
#endif
williamr@4
  1350
williamr@4
  1351
#if defined (_STLP_DEBUG)
williamr@4
  1352
#  include <stl/debug/_string.h>
williamr@4
  1353
#endif
williamr@4
  1354
williamr@4
  1355
_STLP_BEGIN_NAMESPACE
williamr@4
  1356
williamr@4
  1357
// ------------------------------------------------------------
williamr@4
  1358
// Non-member functions.
williamr@4
  1359
// Swap.
williamr@4
  1360
#if defined (_STLP_FUNCTION_TMPL_PARTIAL_ORDER)
williamr@4
  1361
template <class _CharT, class _Traits, class _Alloc>
williamr@4
  1362
inline void _STLP_CALL
williamr@4
  1363
swap(basic_string<_CharT,_Traits,_Alloc>& __x,
williamr@4
  1364
     basic_string<_CharT,_Traits,_Alloc>& __y)
williamr@4
  1365
{ __x.swap(__y); }
williamr@4
  1366
#endif /* _STLP_FUNCTION_TMPL_PARTIAL_ORDER */
williamr@4
  1367
williamr@4
  1368
#if defined (_STLP_CLASS_PARTIAL_SPECIALIZATION)
williamr@4
  1369
template <class _CharT, class _Traits, class _Alloc>
williamr@4
  1370
struct __move_traits<basic_string<_CharT, _Traits, _Alloc> > {
williamr@4
  1371
  typedef __stlp_movable implemented;
williamr@4
  1372
  //Completness depends on the allocator:
williamr@4
  1373
  typedef typename __move_traits<_Alloc>::complete complete;
williamr@4
  1374
};
williamr@4
  1375
/*#else
williamr@4
  1376
 * There is no need to specialize for string and wstring in this case
williamr@4
  1377
 * as the default __move_traits will already tell that string is movable
williamr@4
  1378
 * but not complete. We cannot define it as complete as nothing guaranty
williamr@4
  1379
 * that the STLport user hasn't specialized std::allocator for char or
williamr@4
  1380
 * wchar_t.
williamr@4
  1381
 */
williamr@4
  1382
#endif
williamr@4
  1383
williamr@4
  1384
_STLP_MOVE_TO_PRIV_NAMESPACE
williamr@4
  1385
williamr@4
  1386
template <class _CharT, class _Traits, class _Alloc>
williamr@4
  1387
void _STLP_CALL _S_string_copy(const basic_string<_CharT,_Traits,_Alloc>& __s,
williamr@4
  1388
                               _CharT* __buf, size_t __n);
williamr@4
  1389
williamr@4
  1390
#if defined(_STLP_USE_WIDE_INTERFACE)
williamr@4
  1391
// A couple of functions to transfer between ASCII/Unicode
williamr@4
  1392
wstring __ASCIIToWide(const char *ascii);
williamr@4
  1393
string __WideToASCII(const wchar_t *wide);
williamr@4
  1394
#endif
williamr@4
  1395
williamr@4
  1396
inline const char* _STLP_CALL
williamr@4
  1397
__get_c_string(const string& __str) { return __str.c_str(); }
williamr@4
  1398
williamr@4
  1399
_STLP_MOVE_TO_STD_NAMESPACE
williamr@4
  1400
williamr@4
  1401
_STLP_END_NAMESPACE
williamr@4
  1402
williamr@4
  1403
#include <stl/_string_operators.h>
williamr@4
  1404
williamr@4
  1405
#if defined(_STLP_USE_NO_IOSTREAMS) || \
williamr@4
  1406
    (defined (_STLP_EXPOSE_STREAM_IMPLEMENTATION) && !defined (_STLP_LINK_TIME_INSTANTIATION))
williamr@4
  1407
#  include <stl/_string.c>
williamr@4
  1408
#endif
williamr@4
  1409
williamr@4
  1410
#endif /* _STLP_INTERNAL_STRING_H */
williamr@4
  1411
williamr@4
  1412
/*
williamr@4
  1413
 * Local Variables:
williamr@4
  1414
 * mode:C++
williamr@4
  1415
 * End:
williamr@4
  1416
 */