100db7afdSDavid E. O'Brien // Stream buffer classes -*- C++ -*-
200db7afdSDavid E. O'Brien 
3*f8a1b7d9SAlexander Kabaev // Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006
400db7afdSDavid E. O'Brien // Free Software Foundation, Inc.
500db7afdSDavid E. O'Brien //
600db7afdSDavid E. O'Brien // This file is part of the GNU ISO C++ Library.  This library is free
700db7afdSDavid E. O'Brien // software; you can redistribute it and/or modify it under the
800db7afdSDavid E. O'Brien // terms of the GNU General Public License as published by the
900db7afdSDavid E. O'Brien // Free Software Foundation; either version 2, or (at your option)
1000db7afdSDavid E. O'Brien // any later version.
1100db7afdSDavid E. O'Brien 
1200db7afdSDavid E. O'Brien // This library is distributed in the hope that it will be useful,
1300db7afdSDavid E. O'Brien // but WITHOUT ANY WARRANTY; without even the implied warranty of
1400db7afdSDavid E. O'Brien // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
1500db7afdSDavid E. O'Brien // GNU General Public License for more details.
1600db7afdSDavid E. O'Brien 
1700db7afdSDavid E. O'Brien // You should have received a copy of the GNU General Public License along
1800db7afdSDavid E. O'Brien // with this library; see the file COPYING.  If not, write to the Free
19*f8a1b7d9SAlexander Kabaev // Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
2000db7afdSDavid E. O'Brien // USA.
2100db7afdSDavid E. O'Brien 
2200db7afdSDavid E. O'Brien // As a special exception, you may use this file as part of a free software
2300db7afdSDavid E. O'Brien // library without restriction.  Specifically, if other files instantiate
2400db7afdSDavid E. O'Brien // templates or use macros or inline functions from this file, or you compile
2500db7afdSDavid E. O'Brien // this file and link it with other files to produce an executable, this
2600db7afdSDavid E. O'Brien // file does not by itself cause the resulting executable to be covered by
2700db7afdSDavid E. O'Brien // the GNU General Public License.  This exception does not however
2800db7afdSDavid E. O'Brien // invalidate any other reasons why the executable file might be covered by
2900db7afdSDavid E. O'Brien // the GNU General Public License.
3000db7afdSDavid E. O'Brien 
31*f8a1b7d9SAlexander Kabaev /** @file streambuf.tcc
32*f8a1b7d9SAlexander Kabaev  *  This is an internal header file, included by other library headers.
33*f8a1b7d9SAlexander Kabaev  *  You should not attempt to use it directly.
34*f8a1b7d9SAlexander Kabaev  */
35*f8a1b7d9SAlexander Kabaev 
3600db7afdSDavid E. O'Brien //
3700db7afdSDavid E. O'Brien // ISO C++ 14882: 27.5  Stream buffers
3800db7afdSDavid E. O'Brien //
3900db7afdSDavid E. O'Brien 
40ffeaf689SAlexander Kabaev #ifndef _STREAMBUF_TCC
41ffeaf689SAlexander Kabaev #define _STREAMBUF_TCC 1
4200db7afdSDavid E. O'Brien 
4300db7afdSDavid E. O'Brien #pragma GCC system_header
4400db7afdSDavid E. O'Brien 
_GLIBCXX_BEGIN_NAMESPACE(std)45*f8a1b7d9SAlexander Kabaev _GLIBCXX_BEGIN_NAMESPACE(std)
46*f8a1b7d9SAlexander Kabaev 
4700db7afdSDavid E. O'Brien   template<typename _CharT, typename _Traits>
4800db7afdSDavid E. O'Brien     streamsize
4900db7afdSDavid E. O'Brien     basic_streambuf<_CharT, _Traits>::
5000db7afdSDavid E. O'Brien     xsgetn(char_type* __s, streamsize __n)
5100db7afdSDavid E. O'Brien     {
5200db7afdSDavid E. O'Brien       streamsize __ret = 0;
5300db7afdSDavid E. O'Brien       while (__ret < __n)
5400db7afdSDavid E. O'Brien 	{
55*f8a1b7d9SAlexander Kabaev 	  const streamsize __buf_len = this->egptr() - this->gptr();
56ffeaf689SAlexander Kabaev 	  if (__buf_len)
5700db7afdSDavid E. O'Brien 	    {
58*f8a1b7d9SAlexander Kabaev 	      const streamsize __remaining = __n - __ret;
59*f8a1b7d9SAlexander Kabaev 	      const streamsize __len = std::min(__buf_len, __remaining);
60ffeaf689SAlexander Kabaev 	      traits_type::copy(__s, this->gptr(), __len);
6100db7afdSDavid E. O'Brien 	      __ret += __len;
6200db7afdSDavid E. O'Brien 	      __s += __len;
63ffeaf689SAlexander Kabaev 	      this->gbump(__len);
6400db7afdSDavid E. O'Brien 	    }
6500db7afdSDavid E. O'Brien 
6600db7afdSDavid E. O'Brien 	  if (__ret < __n)
6700db7afdSDavid E. O'Brien 	    {
68ffeaf689SAlexander Kabaev 	      const int_type __c = this->uflow();
69ca6500fcSAlexander Kabaev 	      if (!traits_type::eq_int_type(__c, traits_type::eof()))
7000db7afdSDavid E. O'Brien 		{
7100db7afdSDavid E. O'Brien 		  traits_type::assign(*__s++, traits_type::to_char_type(__c));
7200db7afdSDavid E. O'Brien 		  ++__ret;
7300db7afdSDavid E. O'Brien 		}
7400db7afdSDavid E. O'Brien 	      else
7500db7afdSDavid E. O'Brien 		break;
7600db7afdSDavid E. O'Brien 	    }
7700db7afdSDavid E. O'Brien 	}
7800db7afdSDavid E. O'Brien       return __ret;
7900db7afdSDavid E. O'Brien     }
8000db7afdSDavid E. O'Brien 
8100db7afdSDavid E. O'Brien   template<typename _CharT, typename _Traits>
8200db7afdSDavid E. O'Brien     streamsize
8300db7afdSDavid E. O'Brien     basic_streambuf<_CharT, _Traits>::
xsputn(const char_type * __s,streamsize __n)8400db7afdSDavid E. O'Brien     xsputn(const char_type* __s, streamsize __n)
8500db7afdSDavid E. O'Brien     {
8600db7afdSDavid E. O'Brien       streamsize __ret = 0;
8700db7afdSDavid E. O'Brien       while (__ret < __n)
8800db7afdSDavid E. O'Brien 	{
89*f8a1b7d9SAlexander Kabaev 	  const streamsize __buf_len = this->epptr() - this->pptr();
90ffeaf689SAlexander Kabaev 	  if (__buf_len)
9100db7afdSDavid E. O'Brien 	    {
92*f8a1b7d9SAlexander Kabaev 	      const streamsize __remaining = __n - __ret;
93*f8a1b7d9SAlexander Kabaev 	      const streamsize __len = std::min(__buf_len, __remaining);
94ffeaf689SAlexander Kabaev 	      traits_type::copy(this->pptr(), __s, __len);
9500db7afdSDavid E. O'Brien 	      __ret += __len;
9600db7afdSDavid E. O'Brien 	      __s += __len;
97ffeaf689SAlexander Kabaev 	      this->pbump(__len);
9800db7afdSDavid E. O'Brien 	    }
9900db7afdSDavid E. O'Brien 
10000db7afdSDavid E. O'Brien 	  if (__ret < __n)
10100db7afdSDavid E. O'Brien 	    {
10200db7afdSDavid E. O'Brien 	      int_type __c = this->overflow(traits_type::to_int_type(*__s));
103ca6500fcSAlexander Kabaev 	      if (!traits_type::eq_int_type(__c, traits_type::eof()))
10400db7afdSDavid E. O'Brien 		{
10500db7afdSDavid E. O'Brien 		  ++__ret;
10600db7afdSDavid E. O'Brien 		  ++__s;
10700db7afdSDavid E. O'Brien 		}
10800db7afdSDavid E. O'Brien 	      else
10900db7afdSDavid E. O'Brien 		break;
11000db7afdSDavid E. O'Brien 	    }
11100db7afdSDavid E. O'Brien 	}
11200db7afdSDavid E. O'Brien       return __ret;
11300db7afdSDavid E. O'Brien     }
11400db7afdSDavid E. O'Brien 
11500db7afdSDavid E. O'Brien   // Conceivably, this could be used to implement buffer-to-buffer
11600db7afdSDavid E. O'Brien   // copies, if this was ever desired in an un-ambiguous way by the
117*f8a1b7d9SAlexander Kabaev   // standard.
11800db7afdSDavid E. O'Brien   template<typename _CharT, typename _Traits>
11900db7afdSDavid E. O'Brien     streamsize
__copy_streambufs_eof(basic_streambuf<_CharT,_Traits> * __sbin,basic_streambuf<_CharT,_Traits> * __sbout,bool & __ineof)120*f8a1b7d9SAlexander Kabaev     __copy_streambufs_eof(basic_streambuf<_CharT, _Traits>* __sbin,
121*f8a1b7d9SAlexander Kabaev 			  basic_streambuf<_CharT, _Traits>* __sbout,
122*f8a1b7d9SAlexander Kabaev 			  bool& __ineof)
12300db7afdSDavid E. O'Brien     {
12400db7afdSDavid E. O'Brien       streamsize __ret = 0;
125*f8a1b7d9SAlexander Kabaev       __ineof = true;
1261b86b14eSAlexander Kabaev       typename _Traits::int_type __c = __sbin->sgetc();
1271b86b14eSAlexander Kabaev       while (!_Traits::eq_int_type(__c, _Traits::eof()))
12800db7afdSDavid E. O'Brien 	{
1291b86b14eSAlexander Kabaev 	  __c = __sbout->sputc(_Traits::to_char_type(__c));
1301b86b14eSAlexander Kabaev 	  if (_Traits::eq_int_type(__c, _Traits::eof()))
131*f8a1b7d9SAlexander Kabaev 	    {
132*f8a1b7d9SAlexander Kabaev 	      __ineof = false;
1338f1134fbSDavid E. O'Brien 	      break;
134*f8a1b7d9SAlexander Kabaev 	    }
1351b86b14eSAlexander Kabaev 	  ++__ret;
1361b86b14eSAlexander Kabaev 	  __c = __sbin->snextc();
1378f1134fbSDavid E. O'Brien 	}
13800db7afdSDavid E. O'Brien       return __ret;
13900db7afdSDavid E. O'Brien     }
14000db7afdSDavid E. O'Brien 
141*f8a1b7d9SAlexander Kabaev   template<typename _CharT, typename _Traits>
142*f8a1b7d9SAlexander Kabaev     inline streamsize
__copy_streambufs(basic_streambuf<_CharT,_Traits> * __sbin,basic_streambuf<_CharT,_Traits> * __sbout)143*f8a1b7d9SAlexander Kabaev     __copy_streambufs(basic_streambuf<_CharT, _Traits>* __sbin,
144*f8a1b7d9SAlexander Kabaev 		      basic_streambuf<_CharT, _Traits>* __sbout)
145*f8a1b7d9SAlexander Kabaev     {
146*f8a1b7d9SAlexander Kabaev       bool __ineof;
147*f8a1b7d9SAlexander Kabaev       return __copy_streambufs_eof(__sbin, __sbout, __ineof);
148*f8a1b7d9SAlexander Kabaev     }
149*f8a1b7d9SAlexander Kabaev 
15000db7afdSDavid E. O'Brien   // Inhibit implicit instantiations for required instantiations,
15100db7afdSDavid E. O'Brien   // which are defined via explicit instantiations elsewhere.
15200db7afdSDavid E. O'Brien   // NB:  This syntax is a GNU extension.
153ffeaf689SAlexander Kabaev #if _GLIBCXX_EXTERN_TEMPLATE
15400db7afdSDavid E. O'Brien   extern template class basic_streambuf<char>;
15500db7afdSDavid E. O'Brien   extern template
15600db7afdSDavid E. O'Brien     streamsize
157*f8a1b7d9SAlexander Kabaev     __copy_streambufs(basic_streambuf<char>*,
158*f8a1b7d9SAlexander Kabaev 		      basic_streambuf<char>*);
159*f8a1b7d9SAlexander Kabaev   extern template
160*f8a1b7d9SAlexander Kabaev     streamsize
161*f8a1b7d9SAlexander Kabaev     __copy_streambufs_eof(basic_streambuf<char>*,
162*f8a1b7d9SAlexander Kabaev 			  basic_streambuf<char>*, bool&);
16300db7afdSDavid E. O'Brien 
164ffeaf689SAlexander Kabaev #ifdef _GLIBCXX_USE_WCHAR_T
16500db7afdSDavid E. O'Brien   extern template class basic_streambuf<wchar_t>;
16600db7afdSDavid E. O'Brien   extern template
16700db7afdSDavid E. O'Brien     streamsize
168*f8a1b7d9SAlexander Kabaev     __copy_streambufs(basic_streambuf<wchar_t>*,
169*f8a1b7d9SAlexander Kabaev 		      basic_streambuf<wchar_t>*);
170*f8a1b7d9SAlexander Kabaev   extern template
171*f8a1b7d9SAlexander Kabaev     streamsize
172*f8a1b7d9SAlexander Kabaev     __copy_streambufs_eof(basic_streambuf<wchar_t>*,
173*f8a1b7d9SAlexander Kabaev 			  basic_streambuf<wchar_t>*, bool&);
1748f1134fbSDavid E. O'Brien #endif
1751b86b14eSAlexander Kabaev #endif
176*f8a1b7d9SAlexander Kabaev 
177*f8a1b7d9SAlexander Kabaev _GLIBCXX_END_NAMESPACE
17800db7afdSDavid E. O'Brien 
17900db7afdSDavid E. O'Brien #endif
180