Subversion Repositories Kolibri OS

Rev

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

  1. // Input streams operating on strings-*- C++ -*-
  2.  
  3. // Copyright (C) 2004-2015 Free Software Foundation, Inc.
  4. //
  5. // This file is part of the GNU ISO C++ Library.  This library is free
  6. // software; you can redistribute it and/or modify it under the
  7. // terms of the GNU General Public License as published by the
  8. // Free Software Foundation; either version 3, or (at your option)
  9. // any later version.
  10.  
  11. // This library is distributed in the hope that it will be useful,
  12. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14. // GNU General Public License for more details.
  15.  
  16. // Under Section 7 of GPL version 3, you are granted additional
  17. // permissions described in the GCC Runtime Library Exception, version
  18. // 3.1, as published by the Free Software Foundation.
  19.  
  20. // You should have received a copy of the GNU General Public License and
  21. // a copy of the GCC Runtime Library Exception along with this program;
  22. // see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
  23. // <http://www.gnu.org/licenses/>.
  24.  
  25. //
  26. // ISO C++ 14882: 27.6.1  Input streams
  27. //
  28.  
  29. #ifndef _GLIBCXX_USE_CXX11_ABI
  30. // Instantiations in this file use the new SSO std::string ABI unless included
  31. // by another file which defines _GLIBCXX_USE_CXX11_ABI=0.
  32. # define _GLIBCXX_USE_CXX11_ABI 1
  33. #endif
  34. #include <istream>
  35. #include <string>
  36.  
  37. namespace std _GLIBCXX_VISIBILITY(default)
  38. {
  39. _GLIBCXX_BEGIN_NAMESPACE_VERSION
  40.  
  41.   template<>
  42.     basic_istream<char>&
  43.     operator>>(basic_istream<char>& __in, basic_string<char>& __str)
  44.     {
  45.       typedef basic_istream<char>               __istream_type;
  46.       typedef __istream_type::int_type          __int_type;
  47.       typedef __istream_type::traits_type       __traits_type;
  48.       typedef __istream_type::__streambuf_type  __streambuf_type;
  49.       typedef __istream_type::__ctype_type      __ctype_type;
  50.       typedef basic_string<char>                __string_type;
  51.       typedef __string_type::size_type          __size_type;
  52.  
  53.       __size_type __extracted = 0;
  54.       ios_base::iostate __err = ios_base::goodbit;
  55.       __istream_type::sentry __cerb(__in, false);
  56.       if (__cerb)
  57.         {
  58.           __try
  59.             {
  60.               __str.erase();
  61.               const streamsize __w = __in.width();
  62.               const __size_type __n = __w > 0 ? static_cast<__size_type>(__w)
  63.                                               : __str.max_size();
  64.               const __ctype_type& __ct = use_facet<__ctype_type>(__in.getloc());
  65.               const __int_type __eof = __traits_type::eof();
  66.               __streambuf_type* __sb = __in.rdbuf();
  67.               __int_type __c = __sb->sgetc();
  68.  
  69.               while (__extracted < __n
  70.                      && !__traits_type::eq_int_type(__c, __eof)
  71.                      && !__ct.is(ctype_base::space,
  72.                                  __traits_type::to_char_type(__c)))
  73.                 {
  74.                   streamsize __size = std::min(streamsize(__sb->egptr()
  75.                                                           - __sb->gptr()),
  76.                                                streamsize(__n - __extracted));
  77.                   if (__size > 1)
  78.                     {
  79.                       __size = (__ct.scan_is(ctype_base::space,
  80.                                              __sb->gptr() + 1,
  81.                                              __sb->gptr() + __size)
  82.                                 - __sb->gptr());
  83.                       __str.append(__sb->gptr(), __size);
  84.                       __sb->__safe_gbump(__size);
  85.                       __extracted += __size;
  86.                       __c = __sb->sgetc();
  87.                     }
  88.                   else
  89.                     {
  90.                       __str += __traits_type::to_char_type(__c);
  91.                       ++__extracted;
  92.                       __c = __sb->snextc();
  93.                     }
  94.                 }
  95.  
  96.               if (__traits_type::eq_int_type(__c, __eof))
  97.                 __err |= ios_base::eofbit;
  98.               __in.width(0);
  99.             }
  100.           __catch(__cxxabiv1::__forced_unwind&)
  101.             {
  102.               __in._M_setstate(ios_base::badbit);
  103.               __throw_exception_again;
  104.             }
  105.           __catch(...)
  106.             {
  107.               // _GLIBCXX_RESOLVE_LIB_DEFECTS
  108.               // 91. Description of operator>> and getline() for string<>
  109.               // might cause endless loop
  110.               __in._M_setstate(ios_base::badbit);
  111.             }
  112.         }
  113.       if (!__extracted)
  114.         __err |= ios_base::failbit;
  115.       if (__err)
  116.         __in.setstate(__err);
  117.       return __in;
  118.     }
  119.  
  120.   template<>
  121.     basic_istream<char>&
  122.     getline(basic_istream<char>& __in, basic_string<char>& __str,
  123.             char __delim)
  124.     {
  125.       typedef basic_istream<char>               __istream_type;
  126.       typedef __istream_type::int_type          __int_type;
  127.       typedef __istream_type::char_type         __char_type;
  128.       typedef __istream_type::traits_type       __traits_type;
  129.       typedef __istream_type::__streambuf_type  __streambuf_type;
  130.       typedef basic_string<char>                __string_type;
  131.       typedef __string_type::size_type          __size_type;
  132.  
  133.       __size_type __extracted = 0;
  134.       const __size_type __n = __str.max_size();
  135.       ios_base::iostate __err = ios_base::goodbit;
  136.       __istream_type::sentry __cerb(__in, true);
  137.       if (__cerb)
  138.         {
  139.           __try
  140.             {
  141.               __str.erase();
  142.               const __int_type __idelim = __traits_type::to_int_type(__delim);
  143.               const __int_type __eof = __traits_type::eof();
  144.               __streambuf_type* __sb = __in.rdbuf();
  145.               __int_type __c = __sb->sgetc();
  146.  
  147.               while (__extracted < __n
  148.                      && !__traits_type::eq_int_type(__c, __eof)
  149.                      && !__traits_type::eq_int_type(__c, __idelim))
  150.                 {
  151.                   streamsize __size = std::min(streamsize(__sb->egptr()
  152.                                                           - __sb->gptr()),
  153.                                                streamsize(__n - __extracted));
  154.                   if (__size > 1)
  155.                     {
  156.                       const __char_type* __p = __traits_type::find(__sb->gptr(),
  157.                                                                    __size,
  158.                                                                    __delim);
  159.                       if (__p)
  160.                         __size = __p - __sb->gptr();
  161.                       __str.append(__sb->gptr(), __size);
  162.                       __sb->__safe_gbump(__size);
  163.                       __extracted += __size;
  164.                       __c = __sb->sgetc();
  165.                     }
  166.                   else
  167.                     {
  168.                       __str += __traits_type::to_char_type(__c);
  169.                       ++__extracted;
  170.                       __c = __sb->snextc();
  171.                     }
  172.                 }
  173.  
  174.               if (__traits_type::eq_int_type(__c, __eof))
  175.                 __err |= ios_base::eofbit;
  176.               else if (__traits_type::eq_int_type(__c, __idelim))
  177.                 {
  178.                   ++__extracted;
  179.                   __sb->sbumpc();
  180.                 }
  181.               else
  182.                 __err |= ios_base::failbit;
  183.             }
  184.           __catch(__cxxabiv1::__forced_unwind&)
  185.             {
  186.               __in._M_setstate(ios_base::badbit);
  187.               __throw_exception_again;
  188.             }
  189.           __catch(...)
  190.             {
  191.               // _GLIBCXX_RESOLVE_LIB_DEFECTS
  192.               // 91. Description of operator>> and getline() for string<>
  193.               // might cause endless loop
  194.               __in._M_setstate(ios_base::badbit);
  195.             }
  196.         }
  197.       if (!__extracted)
  198.         __err |= ios_base::failbit;
  199.       if (__err)
  200.         __in.setstate(__err);
  201.       return __in;
  202.     }
  203.  
  204. #ifdef _GLIBCXX_USE_WCHAR_T
  205.   template<>
  206.     basic_istream<wchar_t>&
  207.     getline(basic_istream<wchar_t>& __in, basic_string<wchar_t>& __str,
  208.             wchar_t __delim)
  209.     {
  210.       typedef basic_istream<wchar_t>            __istream_type;
  211.       typedef __istream_type::int_type          __int_type;
  212.       typedef __istream_type::char_type         __char_type;
  213.       typedef __istream_type::traits_type       __traits_type;
  214.       typedef __istream_type::__streambuf_type  __streambuf_type;
  215.       typedef basic_string<wchar_t>             __string_type;
  216.       typedef __string_type::size_type          __size_type;
  217.  
  218.       __size_type __extracted = 0;
  219.       const __size_type __n = __str.max_size();
  220.       ios_base::iostate __err = ios_base::goodbit;
  221.       __istream_type::sentry __cerb(__in, true);
  222.       if (__cerb)
  223.         {
  224.           __try
  225.             {
  226.               __str.erase();
  227.               const __int_type __idelim = __traits_type::to_int_type(__delim);
  228.               const __int_type __eof = __traits_type::eof();
  229.               __streambuf_type* __sb = __in.rdbuf();
  230.               __int_type __c = __sb->sgetc();
  231.  
  232.               while (__extracted < __n
  233.                      && !__traits_type::eq_int_type(__c, __eof)
  234.                      && !__traits_type::eq_int_type(__c, __idelim))
  235.                 {
  236.                   streamsize __size = std::min(streamsize(__sb->egptr()
  237.                                                           - __sb->gptr()),
  238.                                                streamsize(__n - __extracted));
  239.                   if (__size > 1)
  240.                     {
  241.                       const __char_type* __p = __traits_type::find(__sb->gptr(),
  242.                                                                    __size,
  243.                                                                    __delim);
  244.                       if (__p)
  245.                         __size = __p - __sb->gptr();
  246.                       __str.append(__sb->gptr(), __size);
  247.                       __sb->__safe_gbump(__size);
  248.                       __extracted += __size;
  249.                       __c = __sb->sgetc();
  250.                     }
  251.                   else
  252.                     {
  253.                       __str += __traits_type::to_char_type(__c);
  254.                       ++__extracted;
  255.                       __c = __sb->snextc();
  256.                     }
  257.                 }
  258.  
  259.               if (__traits_type::eq_int_type(__c, __eof))
  260.                 __err |= ios_base::eofbit;
  261.               else if (__traits_type::eq_int_type(__c, __idelim))
  262.                 {
  263.                   ++__extracted;
  264.                   __sb->sbumpc();
  265.                 }
  266.               else
  267.                 __err |= ios_base::failbit;
  268.             }
  269.           __catch(__cxxabiv1::__forced_unwind&)
  270.             {
  271.               __in._M_setstate(ios_base::badbit);
  272.               __throw_exception_again;
  273.             }
  274.           __catch(...)
  275.             {
  276.               // _GLIBCXX_RESOLVE_LIB_DEFECTS
  277.               // 91. Description of operator>> and getline() for string<>
  278.               // might cause endless loop
  279.               __in._M_setstate(ios_base::badbit);
  280.             }
  281.         }
  282.       if (!__extracted)
  283.         __err |= ios_base::failbit;
  284.       if (__err)
  285.         __in.setstate(__err);
  286.       return __in;
  287.     }
  288. #endif
  289.  
  290. _GLIBCXX_END_NAMESPACE_VERSION
  291. } // namespace
  292.