Subversion Repositories Kolibri OS

Rev

Blame | Last modification | View Log | RSS feed

  1. // Versatile string -*- C++ -*-
  2.  
  3. // Copyright (C) 2005-2013 Free Software Foundation, Inc.
  4. //
  5. // This file is part of the GNU ISO C++ Library.  This library is free
  6. // software; you can redistribute it and/or modify it under the
  7. // terms of the GNU General Public License as published by the
  8. // Free Software Foundation; either version 3, or (at your option)
  9. // any later version.
  10.  
  11. // This library is distributed in the hope that it will be useful,
  12. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14. // GNU General Public License for more details.
  15.  
  16. // Under Section 7 of GPL version 3, you are granted additional
  17. // permissions described in the GCC Runtime Library Exception, version
  18. // 3.1, as published by the Free Software Foundation.
  19.  
  20. // You should have received a copy of the GNU General Public License and
  21. // a copy of the GCC Runtime Library Exception along with this program;
  22. // see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
  23. // <http://www.gnu.org/licenses/>.
  24.  
  25. /** @file ext/vstring.tcc
  26.  *  This is an internal header file, included by other library headers.
  27.  *  Do not attempt to use it directly. @headername{ext/vstring.h}
  28.  */
  29.  
  30. #ifndef _VSTRING_TCC
  31. #define _VSTRING_TCC 1
  32.  
  33. #pragma GCC system_header
  34.  
  35. #include <bits/cxxabi_forced.h>
  36.  
  37. namespace __gnu_cxx _GLIBCXX_VISIBILITY(default)
  38. {
  39. _GLIBCXX_BEGIN_NAMESPACE_VERSION
  40.  
  41.   template<typename _CharT, typename _Traits, typename _Alloc,
  42.            template <typename, typename, typename> class _Base>
  43.     const typename __versa_string<_CharT, _Traits, _Alloc, _Base>::size_type
  44.     __versa_string<_CharT, _Traits, _Alloc, _Base>::npos;
  45.  
  46.   template<typename _CharT, typename _Traits, typename _Alloc,
  47.            template <typename, typename, typename> class _Base>
  48.     void
  49.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  50.     resize(size_type __n, _CharT __c)
  51.     {
  52.       const size_type __size = this->size();
  53.       if (__size < __n)
  54.         this->append(__n - __size, __c);
  55.       else if (__n < __size)
  56.         this->_M_erase(__n, __size - __n);
  57.     }
  58.  
  59.   template<typename _CharT, typename _Traits, typename _Alloc,
  60.            template <typename, typename, typename> class _Base>
  61.     __versa_string<_CharT, _Traits, _Alloc, _Base>&
  62.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  63.     _M_append(const _CharT* __s, size_type __n)
  64.     {
  65.       const size_type __len = __n + this->size();
  66.  
  67.       if (__len <= this->capacity() && !this->_M_is_shared())
  68.         {
  69.           if (__n)
  70.             this->_S_copy(this->_M_data() + this->size(), __s, __n);
  71.         }
  72.       else
  73.         this->_M_mutate(this->size(), size_type(0), __s, __n);
  74.  
  75.       this->_M_set_length(__len);
  76.       return *this;
  77.     }
  78.  
  79.   template<typename _CharT, typename _Traits, typename _Alloc,
  80.            template <typename, typename, typename> class _Base>
  81.     template<typename _InputIterator>
  82.       __versa_string<_CharT, _Traits, _Alloc, _Base>&
  83.       __versa_string<_CharT, _Traits, _Alloc, _Base>::
  84.       _M_replace_dispatch(iterator __i1, iterator __i2, _InputIterator __k1,
  85.                           _InputIterator __k2, std::__false_type)
  86.       {
  87.         const __versa_string __s(__k1, __k2);
  88.         const size_type __n1 = __i2 - __i1;
  89.         return _M_replace(__i1 - _M_ibegin(), __n1, __s._M_data(),
  90.                           __s.size());
  91.       }
  92.  
  93.   template<typename _CharT, typename _Traits, typename _Alloc,
  94.            template <typename, typename, typename> class _Base>
  95.     __versa_string<_CharT, _Traits, _Alloc, _Base>&
  96.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  97.     _M_replace_aux(size_type __pos1, size_type __n1, size_type __n2,
  98.                    _CharT __c)
  99.     {
  100.       _M_check_length(__n1, __n2, "__versa_string::_M_replace_aux");
  101.  
  102.       const size_type __old_size = this->size();
  103.       const size_type __new_size = __old_size + __n2 - __n1;
  104.  
  105.       if (__new_size <= this->capacity() && !this->_M_is_shared())
  106.         {
  107.           _CharT* __p = this->_M_data() + __pos1;
  108.  
  109.           const size_type __how_much = __old_size - __pos1 - __n1;
  110.           if (__how_much && __n1 != __n2)
  111.             this->_S_move(__p + __n2, __p + __n1, __how_much);
  112.         }
  113.       else
  114.         this->_M_mutate(__pos1, __n1, 0, __n2);
  115.  
  116.       if (__n2)
  117.         this->_S_assign(this->_M_data() + __pos1, __n2, __c);
  118.  
  119.       this->_M_set_length(__new_size);
  120.       return *this;
  121.     }
  122.  
  123.   template<typename _CharT, typename _Traits, typename _Alloc,
  124.            template <typename, typename, typename> class _Base>
  125.     __versa_string<_CharT, _Traits, _Alloc, _Base>&
  126.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  127.     _M_replace(size_type __pos, size_type __len1, const _CharT* __s,
  128.                const size_type __len2)
  129.     {
  130.       _M_check_length(__len1, __len2, "__versa_string::_M_replace");
  131.  
  132.       const size_type __old_size = this->size();
  133.       const size_type __new_size = __old_size + __len2 - __len1;
  134.      
  135.       if (__new_size <= this->capacity() && !this->_M_is_shared())
  136.         {
  137.           _CharT* __p = this->_M_data() + __pos;
  138.  
  139.           const size_type __how_much = __old_size - __pos - __len1;
  140.           if (_M_disjunct(__s))
  141.             {
  142.               if (__how_much && __len1 != __len2)
  143.                 this->_S_move(__p + __len2, __p + __len1, __how_much);
  144.               if (__len2)
  145.                 this->_S_copy(__p, __s, __len2);
  146.             }
  147.           else
  148.             {
  149.               // Work in-place.
  150.               if (__len2 && __len2 <= __len1)
  151.                 this->_S_move(__p, __s, __len2);
  152.               if (__how_much && __len1 != __len2)
  153.                 this->_S_move(__p + __len2, __p + __len1, __how_much);
  154.               if (__len2 > __len1)
  155.                 {
  156.                   if (__s + __len2 <= __p + __len1)
  157.                     this->_S_move(__p, __s, __len2);
  158.                   else if (__s >= __p + __len1)
  159.                     this->_S_copy(__p, __s + __len2 - __len1, __len2);
  160.                   else
  161.                     {
  162.                       const size_type __nleft = (__p + __len1) - __s;
  163.                       this->_S_move(__p, __s, __nleft);
  164.                       this->_S_copy(__p + __nleft, __p + __len2,
  165.                                     __len2 - __nleft);
  166.                     }
  167.                 }
  168.             }
  169.         }
  170.       else
  171.         this->_M_mutate(__pos, __len1, __s, __len2);
  172.  
  173.       this->_M_set_length(__new_size);
  174.       return *this;
  175.     }
  176.  
  177.   template<typename _CharT, typename _Traits, typename _Alloc,
  178.            template <typename, typename, typename> class _Base>
  179.     __versa_string<_CharT, _Traits, _Alloc, _Base>
  180.     operator+(const __versa_string<_CharT, _Traits, _Alloc, _Base>& __lhs,
  181.               const __versa_string<_CharT, _Traits, _Alloc, _Base>& __rhs)
  182.     {
  183.       __versa_string<_CharT, _Traits, _Alloc, _Base> __str;
  184.       __str.reserve(__lhs.size() + __rhs.size());
  185.       __str.append(__lhs);
  186.       __str.append(__rhs);
  187.       return __str;
  188.     }
  189.  
  190.   template<typename _CharT, typename _Traits, typename _Alloc,
  191.            template <typename, typename, typename> class _Base>
  192.     __versa_string<_CharT, _Traits, _Alloc, _Base>
  193.     operator+(const _CharT* __lhs,
  194.               const __versa_string<_CharT, _Traits, _Alloc, _Base>& __rhs)
  195.     {
  196.       __glibcxx_requires_string(__lhs);
  197.       typedef __versa_string<_CharT, _Traits, _Alloc, _Base> __string_type;
  198.       typedef typename __string_type::size_type   __size_type;
  199.       const __size_type __len = _Traits::length(__lhs);
  200.       __string_type __str;
  201.       __str.reserve(__len + __rhs.size());
  202.       __str.append(__lhs, __len);
  203.       __str.append(__rhs);
  204.       return __str;
  205.     }
  206.  
  207.   template<typename _CharT, typename _Traits, typename _Alloc,
  208.            template <typename, typename, typename> class _Base>
  209.     __versa_string<_CharT, _Traits, _Alloc, _Base>
  210.     operator+(_CharT __lhs,
  211.               const __versa_string<_CharT, _Traits, _Alloc, _Base>& __rhs)
  212.     {
  213.       __versa_string<_CharT, _Traits, _Alloc, _Base> __str;
  214.       __str.reserve(__rhs.size() + 1);
  215.       __str.push_back(__lhs);
  216.       __str.append(__rhs);
  217.       return __str;
  218.     }
  219.  
  220.   template<typename _CharT, typename _Traits, typename _Alloc,
  221.            template <typename, typename, typename> class _Base>
  222.     __versa_string<_CharT, _Traits, _Alloc, _Base>
  223.     operator+(const __versa_string<_CharT, _Traits, _Alloc, _Base>& __lhs,
  224.               const _CharT* __rhs)
  225.     {
  226.       __glibcxx_requires_string(__rhs);
  227.       typedef __versa_string<_CharT, _Traits, _Alloc, _Base> __string_type;
  228.       typedef typename __string_type::size_type   __size_type;
  229.       const __size_type __len = _Traits::length(__rhs);
  230.       __string_type __str;
  231.       __str.reserve(__lhs.size() + __len);
  232.       __str.append(__lhs);
  233.       __str.append(__rhs, __len);
  234.       return __str;
  235.     }
  236.  
  237.   template<typename _CharT, typename _Traits, typename _Alloc,
  238.            template <typename, typename, typename> class _Base>
  239.     __versa_string<_CharT, _Traits, _Alloc, _Base>
  240.     operator+(const __versa_string<_CharT, _Traits, _Alloc, _Base>& __lhs,
  241.               _CharT __rhs)
  242.     {
  243.       __versa_string<_CharT, _Traits, _Alloc, _Base> __str;
  244.       __str.reserve(__lhs.size() + 1);
  245.       __str.append(__lhs);
  246.       __str.push_back(__rhs);
  247.       return __str;
  248.     }
  249.  
  250.   template<typename _CharT, typename _Traits, typename _Alloc,
  251.            template <typename, typename, typename> class _Base>
  252.     typename __versa_string<_CharT, _Traits, _Alloc, _Base>::size_type
  253.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  254.     copy(_CharT* __s, size_type __n, size_type __pos) const
  255.     {
  256.       _M_check(__pos, "__versa_string::copy");
  257.       __n = _M_limit(__pos, __n);
  258.       __glibcxx_requires_string_len(__s, __n);
  259.       if (__n)
  260.         this->_S_copy(__s, this->_M_data() + __pos, __n);
  261.       // 21.3.5.7 par 3: do not append null.  (good.)
  262.       return __n;
  263.     }
  264.  
  265.   template<typename _CharT, typename _Traits, typename _Alloc,
  266.            template <typename, typename, typename> class _Base>
  267.     typename __versa_string<_CharT, _Traits, _Alloc, _Base>::size_type
  268.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  269.     find(const _CharT* __s, size_type __pos, size_type __n) const
  270.     {
  271.       __glibcxx_requires_string_len(__s, __n);
  272.       const size_type __size = this->size();
  273.       const _CharT* __data = this->_M_data();
  274.  
  275.       if (__n == 0)
  276.         return __pos <= __size ? __pos : npos;
  277.  
  278.       if (__n <= __size)
  279.         {
  280.           for (; __pos <= __size - __n; ++__pos)
  281.             if (traits_type::eq(__data[__pos], __s[0])
  282.                 && traits_type::compare(__data + __pos + 1,
  283.                                         __s + 1, __n - 1) == 0)
  284.               return __pos;
  285.         }
  286.       return npos;
  287.     }
  288.  
  289.   template<typename _CharT, typename _Traits, typename _Alloc,
  290.            template <typename, typename, typename> class _Base>
  291.     typename __versa_string<_CharT, _Traits, _Alloc, _Base>::size_type
  292.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  293.     find(_CharT __c, size_type __pos) const _GLIBCXX_NOEXCEPT
  294.     {
  295.       size_type __ret = npos;
  296.       const size_type __size = this->size();
  297.       if (__pos < __size)
  298.         {
  299.           const _CharT* __data = this->_M_data();
  300.           const size_type __n = __size - __pos;
  301.           const _CharT* __p = traits_type::find(__data + __pos, __n, __c);
  302.           if (__p)
  303.             __ret = __p - __data;
  304.         }
  305.       return __ret;
  306.     }
  307.  
  308.   template<typename _CharT, typename _Traits, typename _Alloc,
  309.            template <typename, typename, typename> class _Base>
  310.     typename __versa_string<_CharT, _Traits, _Alloc, _Base>::size_type
  311.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  312.     rfind(const _CharT* __s, size_type __pos, size_type __n) const
  313.     {
  314.       __glibcxx_requires_string_len(__s, __n);
  315.       const size_type __size = this->size();
  316.       if (__n <= __size)
  317.         {
  318.           __pos = std::min(size_type(__size - __n), __pos);
  319.           const _CharT* __data = this->_M_data();
  320.           do
  321.             {
  322.               if (traits_type::compare(__data + __pos, __s, __n) == 0)
  323.                 return __pos;
  324.             }
  325.           while (__pos-- > 0);
  326.         }
  327.       return npos;
  328.     }
  329.  
  330.   template<typename _CharT, typename _Traits, typename _Alloc,
  331.            template <typename, typename, typename> class _Base>
  332.     typename __versa_string<_CharT, _Traits, _Alloc, _Base>::size_type
  333.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  334.     rfind(_CharT __c, size_type __pos) const _GLIBCXX_NOEXCEPT
  335.     {
  336.       size_type __size = this->size();
  337.       if (__size)
  338.         {
  339.           if (--__size > __pos)
  340.             __size = __pos;
  341.           for (++__size; __size-- > 0; )
  342.             if (traits_type::eq(this->_M_data()[__size], __c))
  343.               return __size;
  344.         }
  345.       return npos;
  346.     }
  347.  
  348.   template<typename _CharT, typename _Traits, typename _Alloc,
  349.            template <typename, typename, typename> class _Base>
  350.     typename __versa_string<_CharT, _Traits, _Alloc, _Base>::size_type
  351.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  352.     find_first_of(const _CharT* __s, size_type __pos, size_type __n) const
  353.     {
  354.       __glibcxx_requires_string_len(__s, __n);
  355.       for (; __n && __pos < this->size(); ++__pos)
  356.         {
  357.           const _CharT* __p = traits_type::find(__s, __n,
  358.                                                 this->_M_data()[__pos]);
  359.           if (__p)
  360.             return __pos;
  361.         }
  362.       return npos;
  363.     }
  364.  
  365.   template<typename _CharT, typename _Traits, typename _Alloc,
  366.            template <typename, typename, typename> class _Base>
  367.     typename __versa_string<_CharT, _Traits, _Alloc, _Base>::size_type
  368.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  369.     find_last_of(const _CharT* __s, size_type __pos, size_type __n) const
  370.     {
  371.       __glibcxx_requires_string_len(__s, __n);
  372.       size_type __size = this->size();
  373.       if (__size && __n)
  374.         {
  375.           if (--__size > __pos)
  376.             __size = __pos;
  377.           do
  378.             {
  379.               if (traits_type::find(__s, __n, this->_M_data()[__size]))
  380.                 return __size;
  381.             }
  382.           while (__size-- != 0);
  383.         }
  384.       return npos;
  385.     }
  386.  
  387.   template<typename _CharT, typename _Traits, typename _Alloc,
  388.            template <typename, typename, typename> class _Base>
  389.     typename __versa_string<_CharT, _Traits, _Alloc, _Base>::size_type
  390.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  391.     find_first_not_of(const _CharT* __s, size_type __pos, size_type __n) const
  392.     {
  393.       __glibcxx_requires_string_len(__s, __n);
  394.       for (; __pos < this->size(); ++__pos)
  395.         if (!traits_type::find(__s, __n, this->_M_data()[__pos]))
  396.           return __pos;
  397.       return npos;
  398.     }
  399.  
  400.   template<typename _CharT, typename _Traits, typename _Alloc,
  401.            template <typename, typename, typename> class _Base>
  402.     typename __versa_string<_CharT, _Traits, _Alloc, _Base>::size_type
  403.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  404.     find_first_not_of(_CharT __c, size_type __pos) const _GLIBCXX_NOEXCEPT
  405.     {
  406.       for (; __pos < this->size(); ++__pos)
  407.         if (!traits_type::eq(this->_M_data()[__pos], __c))
  408.           return __pos;
  409.       return npos;
  410.     }
  411.  
  412.   template<typename _CharT, typename _Traits, typename _Alloc,
  413.            template <typename, typename, typename> class _Base>
  414.     typename __versa_string<_CharT, _Traits, _Alloc, _Base>::size_type
  415.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  416.     find_last_not_of(const _CharT* __s, size_type __pos, size_type __n) const
  417.     {
  418.       __glibcxx_requires_string_len(__s, __n);
  419.       size_type __size = this->size();
  420.       if (__size)
  421.         {
  422.           if (--__size > __pos)
  423.             __size = __pos;
  424.           do
  425.             {
  426.               if (!traits_type::find(__s, __n, this->_M_data()[__size]))
  427.                 return __size;
  428.             }
  429.           while (__size--);
  430.         }
  431.       return npos;
  432.     }
  433.  
  434.   template<typename _CharT, typename _Traits, typename _Alloc,
  435.            template <typename, typename, typename> class _Base>
  436.     typename __versa_string<_CharT, _Traits, _Alloc, _Base>::size_type
  437.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  438.     find_last_not_of(_CharT __c, size_type __pos) const _GLIBCXX_NOEXCEPT
  439.     {
  440.       size_type __size = this->size();
  441.       if (__size)
  442.         {
  443.           if (--__size > __pos)
  444.             __size = __pos;
  445.           do
  446.             {
  447.               if (!traits_type::eq(this->_M_data()[__size], __c))
  448.                 return __size;
  449.             }
  450.           while (__size--);
  451.         }
  452.       return npos;
  453.     }
  454.  
  455.   template<typename _CharT, typename _Traits, typename _Alloc,
  456.            template <typename, typename, typename> class _Base>
  457.     int
  458.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  459.     compare(size_type __pos, size_type __n, const __versa_string& __str) const
  460.     {
  461.       _M_check(__pos, "__versa_string::compare");
  462.       __n = _M_limit(__pos, __n);
  463.       const size_type __osize = __str.size();
  464.       const size_type __len = std::min(__n, __osize);
  465.       int __r = traits_type::compare(this->_M_data() + __pos,
  466.                                      __str.data(), __len);
  467.       if (!__r)
  468.         __r = this->_S_compare(__n, __osize);
  469.       return __r;
  470.     }
  471.  
  472.   template<typename _CharT, typename _Traits, typename _Alloc,
  473.            template <typename, typename, typename> class _Base>
  474.     int
  475.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  476.     compare(size_type __pos1, size_type __n1, const __versa_string& __str,
  477.             size_type __pos2, size_type __n2) const
  478.     {
  479.       _M_check(__pos1, "__versa_string::compare");
  480.       __str._M_check(__pos2, "__versa_string::compare");
  481.       __n1 = _M_limit(__pos1, __n1);
  482.       __n2 = __str._M_limit(__pos2, __n2);
  483.       const size_type __len = std::min(__n1, __n2);
  484.       int __r = traits_type::compare(this->_M_data() + __pos1,
  485.                                      __str.data() + __pos2, __len);
  486.       if (!__r)
  487.         __r = this->_S_compare(__n1, __n2);
  488.       return __r;
  489.     }
  490.  
  491.   template<typename _CharT, typename _Traits, typename _Alloc,
  492.            template <typename, typename, typename> class _Base>
  493.     int
  494.     __versa_string<_CharT, _Traits, _Alloc, _Base>::
  495.     compare(const _CharT* __s) const
  496.     {
  497.       __glibcxx_requires_string(__s);
  498.       const size_type __size = this->size();
  499.       const size_type __osize = traits_type::length(__s);
  500.       const size_type __len = std::min(__size, __osize);
  501.       int __r = traits_type::compare(this->_M_data(), __s, __len);
  502.       if (!__r)
  503.         __r = this->_S_compare(__size, __osize);
  504.       return __r;
  505.     }
  506.  
  507.   template<typename _CharT, typename _Traits, typename _Alloc,
  508.            template <typename, typename, typename> class _Base>
  509.     int
  510.     __versa_string <_CharT, _Traits, _Alloc, _Base>::
  511.     compare(size_type __pos, size_type __n1, const _CharT* __s) const
  512.     {
  513.       __glibcxx_requires_string(__s);
  514.       _M_check(__pos, "__versa_string::compare");
  515.       __n1 = _M_limit(__pos, __n1);
  516.       const size_type __osize = traits_type::length(__s);
  517.       const size_type __len = std::min(__n1, __osize);
  518.       int __r = traits_type::compare(this->_M_data() + __pos, __s, __len);
  519.       if (!__r)
  520.         __r = this->_S_compare(__n1, __osize);
  521.       return __r;
  522.     }
  523.  
  524.   template<typename _CharT, typename _Traits, typename _Alloc,
  525.            template <typename, typename, typename> class _Base>
  526.     int
  527.     __versa_string <_CharT, _Traits, _Alloc, _Base>::
  528.     compare(size_type __pos, size_type __n1, const _CharT* __s,
  529.             size_type __n2) const
  530.     {
  531.       __glibcxx_requires_string_len(__s, __n2);
  532.       _M_check(__pos, "__versa_string::compare");
  533.       __n1 = _M_limit(__pos, __n1);
  534.       const size_type __len = std::min(__n1, __n2);
  535.       int __r = traits_type::compare(this->_M_data() + __pos, __s, __len);
  536.       if (!__r)
  537.         __r = this->_S_compare(__n1, __n2);
  538.       return __r;
  539.     }
  540.  
  541. _GLIBCXX_END_NAMESPACE_VERSION
  542. } // namespace
  543.  
  544. namespace std _GLIBCXX_VISIBILITY(default)
  545. {
  546. _GLIBCXX_BEGIN_NAMESPACE_VERSION
  547.  
  548.   template<typename _CharT, typename _Traits, typename _Alloc,
  549.            template <typename, typename, typename> class _Base>
  550.     basic_istream<_CharT, _Traits>&
  551.     operator>>(basic_istream<_CharT, _Traits>& __in,
  552.                __gnu_cxx::__versa_string<_CharT, _Traits,
  553.                                          _Alloc, _Base>& __str)
  554.     {
  555.       typedef basic_istream<_CharT, _Traits>            __istream_type;
  556.       typedef typename __istream_type::ios_base         __ios_base;
  557.       typedef __gnu_cxx::__versa_string<_CharT, _Traits, _Alloc, _Base>
  558.                                                         __string_type;
  559.       typedef typename __istream_type::int_type         __int_type;
  560.       typedef typename __string_type::size_type         __size_type;
  561.       typedef ctype<_CharT>                             __ctype_type;
  562.       typedef typename __ctype_type::ctype_base         __ctype_base;
  563.  
  564.       __size_type __extracted = 0;
  565.       typename __ios_base::iostate __err = __ios_base::goodbit;
  566.       typename __istream_type::sentry __cerb(__in, false);
  567.       if (__cerb)
  568.         {
  569.           __try
  570.             {
  571.               // Avoid reallocation for common case.
  572.               __str.erase();
  573.               _CharT __buf[128];
  574.               __size_type __len = 0;
  575.               const streamsize __w = __in.width();
  576.               const __size_type __n = __w > 0 ? static_cast<__size_type>(__w)
  577.                                               : __str.max_size();
  578.               const __ctype_type& __ct = use_facet<__ctype_type>(__in.getloc());
  579.               const __int_type __eof = _Traits::eof();
  580.               __int_type __c = __in.rdbuf()->sgetc();
  581.  
  582.               while (__extracted < __n
  583.                      && !_Traits::eq_int_type(__c, __eof)
  584.                      && !__ct.is(__ctype_base::space,
  585.                                  _Traits::to_char_type(__c)))
  586.                 {
  587.                   if (__len == sizeof(__buf) / sizeof(_CharT))
  588.                     {
  589.                       __str.append(__buf, sizeof(__buf) / sizeof(_CharT));
  590.                       __len = 0;
  591.                     }
  592.                   __buf[__len++] = _Traits::to_char_type(__c);
  593.                   ++__extracted;
  594.                   __c = __in.rdbuf()->snextc();
  595.                 }
  596.               __str.append(__buf, __len);
  597.  
  598.               if (_Traits::eq_int_type(__c, __eof))
  599.                 __err |= __ios_base::eofbit;
  600.               __in.width(0);
  601.             }
  602.           __catch(__cxxabiv1::__forced_unwind&)
  603.             {
  604.               __in._M_setstate(__ios_base::badbit);
  605.               __throw_exception_again;
  606.             }
  607.           __catch(...)
  608.             {
  609.               // _GLIBCXX_RESOLVE_LIB_DEFECTS
  610.               // 91. Description of operator>> and getline() for string<>
  611.               // might cause endless loop
  612.               __in._M_setstate(__ios_base::badbit);
  613.             }
  614.         }
  615.       // 211.  operator>>(istream&, string&) doesn't set failbit
  616.       if (!__extracted)
  617.         __err |= __ios_base::failbit;
  618.       if (__err)
  619.         __in.setstate(__err);
  620.       return __in;
  621.     }      
  622.  
  623.   template<typename _CharT, typename _Traits, typename _Alloc,
  624.            template <typename, typename, typename> class _Base>
  625.     basic_istream<_CharT, _Traits>&
  626.     getline(basic_istream<_CharT, _Traits>& __in,
  627.             __gnu_cxx::__versa_string<_CharT, _Traits, _Alloc, _Base>& __str,
  628.             _CharT __delim)
  629.     {
  630.       typedef basic_istream<_CharT, _Traits>            __istream_type;
  631.       typedef typename __istream_type::ios_base         __ios_base;
  632.       typedef __gnu_cxx::__versa_string<_CharT, _Traits, _Alloc, _Base>
  633.                                                         __string_type;
  634.       typedef typename __istream_type::int_type         __int_type;
  635.       typedef typename __string_type::size_type         __size_type;
  636.  
  637.       __size_type __extracted = 0;
  638.       const __size_type __n = __str.max_size();
  639.       typename __ios_base::iostate __err = __ios_base::goodbit;
  640.       typename __istream_type::sentry __cerb(__in, true);
  641.       if (__cerb)
  642.         {
  643.           __try
  644.             {
  645.               // Avoid reallocation for common case.
  646.               __str.erase();
  647.               _CharT __buf[128];
  648.               __size_type __len = 0;
  649.               const __int_type __idelim = _Traits::to_int_type(__delim);
  650.               const __int_type __eof = _Traits::eof();
  651.               __int_type __c = __in.rdbuf()->sgetc();
  652.  
  653.               while (__extracted < __n
  654.                      && !_Traits::eq_int_type(__c, __eof)
  655.                      && !_Traits::eq_int_type(__c, __idelim))
  656.                 {
  657.                   if (__len == sizeof(__buf) / sizeof(_CharT))
  658.                     {
  659.                       __str.append(__buf, sizeof(__buf) / sizeof(_CharT));
  660.                       __len = 0;
  661.                     }
  662.                   __buf[__len++] = _Traits::to_char_type(__c);
  663.                   ++__extracted;
  664.                   __c = __in.rdbuf()->snextc();
  665.                 }
  666.               __str.append(__buf, __len);
  667.  
  668.               if (_Traits::eq_int_type(__c, __eof))
  669.                 __err |= __ios_base::eofbit;
  670.               else if (_Traits::eq_int_type(__c, __idelim))
  671.                 {
  672.                   ++__extracted;                 
  673.                   __in.rdbuf()->sbumpc();
  674.                 }
  675.               else
  676.                 __err |= __ios_base::failbit;
  677.             }
  678.           __catch(__cxxabiv1::__forced_unwind&)
  679.             {
  680.               __in._M_setstate(__ios_base::badbit);
  681.               __throw_exception_again;
  682.             }
  683.           __catch(...)
  684.             {
  685.               // _GLIBCXX_RESOLVE_LIB_DEFECTS
  686.               // 91. Description of operator>> and getline() for string<>
  687.               // might cause endless loop
  688.               __in._M_setstate(__ios_base::badbit);
  689.             }
  690.         }
  691.       if (!__extracted)
  692.         __err |= __ios_base::failbit;
  693.       if (__err)
  694.         __in.setstate(__err);
  695.       return __in;
  696.     }      
  697.  
  698. _GLIBCXX_END_NAMESPACE_VERSION
  699. } // namespace
  700.  
  701. #endif // _VSTRING_TCC
  702.