197403Sobrien// istream classes -*- C++ -*-
297403Sobrien
3169691Skan// Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005,
4169691Skan// 2006, 2007
597403Sobrien// Free Software Foundation, Inc.
697403Sobrien//
797403Sobrien// This file is part of the GNU ISO C++ Library.  This library is free
897403Sobrien// software; you can redistribute it and/or modify it under the
997403Sobrien// terms of the GNU General Public License as published by the
1097403Sobrien// Free Software Foundation; either version 2, or (at your option)
1197403Sobrien// any later version.
1297403Sobrien
1397403Sobrien// This library is distributed in the hope that it will be useful,
1497403Sobrien// but WITHOUT ANY WARRANTY; without even the implied warranty of
1597403Sobrien// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
1697403Sobrien// GNU General Public License for more details.
1797403Sobrien
1897403Sobrien// You should have received a copy of the GNU General Public License along
1997403Sobrien// with this library; see the file COPYING.  If not, write to the Free
20169691Skan// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
2197403Sobrien// USA.
2297403Sobrien
2397403Sobrien// As a special exception, you may use this file as part of a free software
2497403Sobrien// library without restriction.  Specifically, if other files instantiate
2597403Sobrien// templates or use macros or inline functions from this file, or you compile
2697403Sobrien// this file and link it with other files to produce an executable, this
2797403Sobrien// file does not by itself cause the resulting executable to be covered by
2897403Sobrien// the GNU General Public License.  This exception does not however
2997403Sobrien// invalidate any other reasons why the executable file might be covered by
3097403Sobrien// the GNU General Public License.
3197403Sobrien
32169691Skan/** @file istream.tcc
33169691Skan *  This is an internal header file, included by other library headers.
34169691Skan *  You should not attempt to use it directly.
35169691Skan */
36169691Skan
3797403Sobrien//
38132720Skan// ISO C++ 14882: 27.6.1  Input streams
3997403Sobrien//
4097403Sobrien
41132720Skan#ifndef _ISTREAM_TCC
42132720Skan#define _ISTREAM_TCC 1
43132720Skan
4497403Sobrien#pragma GCC system_header
4597403Sobrien
4697403Sobrien#include <locale>
4797403Sobrien#include <ostream> // For flush()
4897403Sobrien
49169691Skan_GLIBCXX_BEGIN_NAMESPACE(std)
50169691Skan
5197403Sobrien  template<typename _CharT, typename _Traits>
5297403Sobrien    basic_istream<_CharT, _Traits>::sentry::
53132720Skan    sentry(basic_istream<_CharT, _Traits>& __in, bool __noskip) : _M_ok(false)
5497403Sobrien    {
55132720Skan      ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
56132720Skan      if (__in.good())
5797403Sobrien	{
5897403Sobrien	  if (__in.tie())
5997403Sobrien	    __in.tie()->flush();
60132720Skan	  if (!__noskip && (__in.flags() & ios_base::skipws))
61132720Skan	    {
6297403Sobrien	      const __int_type __eof = traits_type::eof();
6397403Sobrien	      __streambuf_type* __sb = __in.rdbuf();
6497403Sobrien	      __int_type __c = __sb->sgetc();
6597403Sobrien
66132720Skan	      const __ctype_type& __ct = __check_facet(__in._M_ctype);
67132720Skan	      while (!traits_type::eq_int_type(__c, __eof)
68132720Skan		     && __ct.is(ctype_base::space, 
69132720Skan				traits_type::to_char_type(__c)))
70132720Skan		__c = __sb->snextc();
7197403Sobrien
72132720Skan	      // _GLIBCXX_RESOLVE_LIB_DEFECTS
73132720Skan	      // 195. Should basic_istream::sentry's constructor ever
74132720Skan	      // set eofbit?
75102782Skan	      if (traits_type::eq_int_type(__c, __eof))
76132720Skan		__err |= ios_base::eofbit;
7797403Sobrien	    }
7897403Sobrien	}
7997403Sobrien
80132720Skan      if (__in.good() && __err == ios_base::goodbit)
8197403Sobrien	_M_ok = true;
8297403Sobrien      else
8397403Sobrien	{
84132720Skan	  __err |= ios_base::failbit;
85132720Skan	  __in.setstate(__err);
8697403Sobrien	}
8797403Sobrien    }
8897403Sobrien
8997403Sobrien  template<typename _CharT, typename _Traits>
90169691Skan    template<typename _ValueT>
91169691Skan      basic_istream<_CharT, _Traits>&
92169691Skan      basic_istream<_CharT, _Traits>::
93169691Skan      _M_extract(_ValueT& __v)
94169691Skan      {
95169691Skan	sentry __cerb(*this, false);
96169691Skan	if (__cerb)
97169691Skan	  {
98169691Skan	    ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
99169691Skan	    try
100169691Skan	      {
101169691Skan		const __num_get_type& __ng = __check_facet(this->_M_num_get);
102169691Skan		__ng.get(*this, 0, *this, __err, __v);
103169691Skan	      }
104169691Skan	    catch(...)
105169691Skan	      { this->_M_setstate(ios_base::badbit); }
106169691Skan	    if (__err)
107169691Skan	      this->setstate(__err);
108169691Skan	  }
109169691Skan	return *this;
110169691Skan      }
11197403Sobrien
11297403Sobrien  template<typename _CharT, typename _Traits>
113132720Skan    basic_istream<_CharT, _Traits>&
11497403Sobrien    basic_istream<_CharT, _Traits>::
11597403Sobrien    operator>>(short& __n)
11697403Sobrien    {
117169691Skan      // _GLIBCXX_RESOLVE_LIB_DEFECTS
118169691Skan      // 118. basic_istream uses nonexistent num_get member functions.
119169691Skan      long __l;
120169691Skan      _M_extract(__l);
121169691Skan      if (!this->fail())
12297403Sobrien	{
123169691Skan	  if (numeric_limits<short>::min() <= __l
124169691Skan	      && __l <= numeric_limits<short>::max())
125169691Skan	    __n = __l;
126169691Skan	  else
127169691Skan	    this->setstate(ios_base::failbit);
12897403Sobrien	}
12997403Sobrien      return *this;
13097403Sobrien    }
131169691Skan    
13297403Sobrien  template<typename _CharT, typename _Traits>
133132720Skan    basic_istream<_CharT, _Traits>&
13497403Sobrien    basic_istream<_CharT, _Traits>::
13597403Sobrien    operator>>(int& __n)
13697403Sobrien    {
137169691Skan      // _GLIBCXX_RESOLVE_LIB_DEFECTS
138169691Skan      // 118. basic_istream uses nonexistent num_get member functions.
139169691Skan      long __l;
140169691Skan      _M_extract(__l);
141169691Skan      if (!this->fail())
14297403Sobrien	{
143169691Skan	  if (numeric_limits<int>::min() <= __l
144169691Skan	      && __l <= numeric_limits<int>::max())
145169691Skan	    __n = __l;
146169691Skan	  else
147169691Skan	    this->setstate(ios_base::failbit);
14897403Sobrien	}
14997403Sobrien      return *this;
15097403Sobrien    }
15197403Sobrien
15297403Sobrien  template<typename _CharT, typename _Traits>
153132720Skan    basic_istream<_CharT, _Traits>&
15497403Sobrien    basic_istream<_CharT, _Traits>::
15597403Sobrien    operator>>(__streambuf_type* __sbout)
15697403Sobrien    {
157132720Skan      ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
158132720Skan      sentry __cerb(*this, false);
159132720Skan      if (__cerb && __sbout)
160132720Skan	{
161132720Skan	  try
162132720Skan	    {
163169691Skan	      bool __ineof;
164169691Skan	      if (!__copy_streambufs_eof(this->rdbuf(), __sbout, __ineof))
165132720Skan		__err |= ios_base::failbit;
166169691Skan	      if (__ineof)
167169691Skan		__err |= ios_base::eofbit;
168132720Skan	    }
169132720Skan	  catch(...)
170132720Skan	    { this->_M_setstate(ios_base::failbit); }
171132720Skan	}
172132720Skan      else if (!__sbout)
173132720Skan	__err |= ios_base::failbit;
174132720Skan      if (__err)
175132720Skan	this->setstate(__err);
176132720Skan      return *this;
17797403Sobrien    }
17897403Sobrien
17997403Sobrien  template<typename _CharT, typename _Traits>
18097403Sobrien    typename basic_istream<_CharT, _Traits>::int_type
18197403Sobrien    basic_istream<_CharT, _Traits>::
18297403Sobrien    get(void)
18397403Sobrien    {
18497403Sobrien      const int_type __eof = traits_type::eof();
18597403Sobrien      int_type __c = __eof;
18697403Sobrien      _M_gcount = 0;
187132720Skan      ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
18897403Sobrien      sentry __cerb(*this, true);
189132720Skan      if (__cerb)
19097403Sobrien	{
191132720Skan	  try
19297403Sobrien	    {
19397403Sobrien	      __c = this->rdbuf()->sbumpc();
19497403Sobrien	      // 27.6.1.1 paragraph 3
195102782Skan	      if (!traits_type::eq_int_type(__c, __eof))
19697403Sobrien		_M_gcount = 1;
19797403Sobrien	      else
198132720Skan		__err |= ios_base::eofbit;
19997403Sobrien	    }
200117397Skan	  catch(...)
201132720Skan	    { this->_M_setstate(ios_base::badbit); }
20297403Sobrien	}
203132720Skan      if (!_M_gcount)
204132720Skan	__err |= ios_base::failbit;
205132720Skan      if (__err)
206132720Skan	this->setstate(__err);
20797403Sobrien      return __c;
20897403Sobrien    }
20997403Sobrien
21097403Sobrien  template<typename _CharT, typename _Traits>
21197403Sobrien    basic_istream<_CharT, _Traits>&
21297403Sobrien    basic_istream<_CharT, _Traits>::
21397403Sobrien    get(char_type& __c)
21497403Sobrien    {
21597403Sobrien      _M_gcount = 0;
216132720Skan      ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
21797403Sobrien      sentry __cerb(*this, true);
218132720Skan      if (__cerb)
21997403Sobrien	{
220132720Skan	  try
22197403Sobrien	    {
222132720Skan	      const int_type __cb = this->rdbuf()->sbumpc();
22397403Sobrien	      // 27.6.1.1 paragraph 3
224132720Skan	      if (!traits_type::eq_int_type(__cb, traits_type::eof()))
22597403Sobrien		{
22697403Sobrien		  _M_gcount = 1;
227132720Skan		  __c = traits_type::to_char_type(__cb);
22897403Sobrien		}
22997403Sobrien	      else
230132720Skan		__err |= ios_base::eofbit;
23197403Sobrien	    }
232117397Skan	  catch(...)
233132720Skan	    { this->_M_setstate(ios_base::badbit); }
23497403Sobrien	}
235132720Skan      if (!_M_gcount)
236132720Skan	__err |= ios_base::failbit;
237132720Skan      if (__err)
238132720Skan	this->setstate(__err);
23997403Sobrien      return *this;
24097403Sobrien    }
24197403Sobrien
24297403Sobrien  template<typename _CharT, typename _Traits>
24397403Sobrien    basic_istream<_CharT, _Traits>&
24497403Sobrien    basic_istream<_CharT, _Traits>::
24597403Sobrien    get(char_type* __s, streamsize __n, char_type __delim)
24697403Sobrien    {
24797403Sobrien      _M_gcount = 0;
248132720Skan      ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
24997403Sobrien      sentry __cerb(*this, true);
250132720Skan      if (__cerb)
25197403Sobrien	{
252132720Skan	  try
25397403Sobrien	    {
25497403Sobrien	      const int_type __idelim = traits_type::to_int_type(__delim);
25597403Sobrien	      const int_type __eof = traits_type::eof();
25697403Sobrien	      __streambuf_type* __sb = this->rdbuf();
257132720Skan	      int_type __c = __sb->sgetc();
258132720Skan
259132720Skan	      while (_M_gcount + 1 < __n
260102782Skan		     && !traits_type::eq_int_type(__c, __eof)
261102782Skan		     && !traits_type::eq_int_type(__c, __idelim))
26297403Sobrien		{
26397403Sobrien		  *__s++ = traits_type::to_char_type(__c);
264132720Skan		  ++_M_gcount;
26597403Sobrien		  __c = __sb->snextc();
26697403Sobrien		}
267102782Skan	      if (traits_type::eq_int_type(__c, __eof))
268132720Skan		__err |= ios_base::eofbit;
26997403Sobrien	    }
270117397Skan	  catch(...)
271132720Skan	    { this->_M_setstate(ios_base::badbit); }
27297403Sobrien	}
273169691Skan      // _GLIBCXX_RESOLVE_LIB_DEFECTS
274169691Skan      // 243. get and getline when sentry reports failure.
275169691Skan      if (__n > 0)
276169691Skan	*__s = char_type();
27797403Sobrien      if (!_M_gcount)
278132720Skan	__err |= ios_base::failbit;
279132720Skan      if (__err)
280132720Skan	this->setstate(__err);
28197403Sobrien      return *this;
28297403Sobrien    }
28397403Sobrien
28497403Sobrien  template<typename _CharT, typename _Traits>
28597403Sobrien    basic_istream<_CharT, _Traits>&
28697403Sobrien    basic_istream<_CharT, _Traits>::
28797403Sobrien    get(__streambuf_type& __sb, char_type __delim)
28897403Sobrien    {
28997403Sobrien      _M_gcount = 0;
290132720Skan      ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
29197403Sobrien      sentry __cerb(*this, true);
292132720Skan      if (__cerb)
29397403Sobrien	{
294132720Skan	  try
29597403Sobrien	    {
29697403Sobrien	      const int_type __idelim = traits_type::to_int_type(__delim);
297132720Skan	      const int_type __eof = traits_type::eof();
29897403Sobrien	      __streambuf_type* __this_sb = this->rdbuf();
29997403Sobrien	      int_type __c = __this_sb->sgetc();
300102782Skan	      char_type __c2 = traits_type::to_char_type(__c);
301132720Skan
302132720Skan	      while (!traits_type::eq_int_type(__c, __eof)
303132720Skan		     && !traits_type::eq_int_type(__c, __idelim)
304102782Skan		     && !traits_type::eq_int_type(__sb.sputc(__c2), __eof))
30597403Sobrien		{
30697403Sobrien		  ++_M_gcount;
30797403Sobrien		  __c = __this_sb->snextc();
308102782Skan		  __c2 = traits_type::to_char_type(__c);
30997403Sobrien		}
310102782Skan	      if (traits_type::eq_int_type(__c, __eof))
311132720Skan		__err |= ios_base::eofbit;
31297403Sobrien	    }
313117397Skan	  catch(...)
314132720Skan	    { this->_M_setstate(ios_base::badbit); }
31597403Sobrien	}
31697403Sobrien      if (!_M_gcount)
317132720Skan	__err |= ios_base::failbit;
318132720Skan      if (__err)
319132720Skan	this->setstate(__err);
32097403Sobrien      return *this;
32197403Sobrien    }
32297403Sobrien
32397403Sobrien  template<typename _CharT, typename _Traits>
32497403Sobrien    basic_istream<_CharT, _Traits>&
32597403Sobrien    basic_istream<_CharT, _Traits>::
32697403Sobrien    getline(char_type* __s, streamsize __n, char_type __delim)
32797403Sobrien    {
32897403Sobrien      _M_gcount = 0;
329132720Skan      ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
33097403Sobrien      sentry __cerb(*this, true);
331132720Skan      if (__cerb)
332169691Skan        {
333132720Skan          try
334169691Skan            {
335169691Skan              const int_type __idelim = traits_type::to_int_type(__delim);
336169691Skan              const int_type __eof = traits_type::eof();
337169691Skan              __streambuf_type* __sb = this->rdbuf();
338169691Skan              int_type __c = __sb->sgetc();
339132720Skan
340169691Skan              while (_M_gcount + 1 < __n
341169691Skan                     && !traits_type::eq_int_type(__c, __eof)
342169691Skan                     && !traits_type::eq_int_type(__c, __idelim))
343169691Skan                {
344169691Skan                  *__s++ = traits_type::to_char_type(__c);
345169691Skan                  __c = __sb->snextc();
346169691Skan                  ++_M_gcount;
347169691Skan                }
348169691Skan              if (traits_type::eq_int_type(__c, __eof))
349169691Skan                __err |= ios_base::eofbit;
350169691Skan              else
351169691Skan                {
352169691Skan                  if (traits_type::eq_int_type(__c, __idelim))
353169691Skan                    {
354169691Skan                      __sb->sbumpc();
355169691Skan                      ++_M_gcount;
356169691Skan                    }
357169691Skan                  else
358169691Skan                    __err |= ios_base::failbit;
359169691Skan                }
360169691Skan            }
361169691Skan          catch(...)
362169691Skan            { this->_M_setstate(ios_base::badbit); }
363169691Skan        }
364169691Skan      // _GLIBCXX_RESOLVE_LIB_DEFECTS
365169691Skan      // 243. get and getline when sentry reports failure.
366169691Skan      if (__n > 0)
367169691Skan	*__s = char_type();
36897403Sobrien      if (!_M_gcount)
369169691Skan        __err |= ios_base::failbit;
370132720Skan      if (__err)
371169691Skan        this->setstate(__err);
37297403Sobrien      return *this;
37397403Sobrien    }
374132720Skan
375169691Skan  // We provide three overloads, since the first two are much simpler
376169691Skan  // than the general case. Also, the latter two can thus adopt the
377169691Skan  // same "batchy" strategy used by getline above.
37897403Sobrien  template<typename _CharT, typename _Traits>
37997403Sobrien    basic_istream<_CharT, _Traits>&
38097403Sobrien    basic_istream<_CharT, _Traits>::
381169691Skan    ignore(void)
38297403Sobrien    {
38397403Sobrien      _M_gcount = 0;
38497403Sobrien      sentry __cerb(*this, true);
385169691Skan      if (__cerb)
38697403Sobrien	{
387132720Skan	  ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
388132720Skan	  try
38997403Sobrien	    {
39097403Sobrien	      const int_type __eof = traits_type::eof();
39197403Sobrien	      __streambuf_type* __sb = this->rdbuf();
392132720Skan
393169691Skan	      if (traits_type::eq_int_type(__sb->sbumpc(), __eof))
394132720Skan		__err |= ios_base::eofbit;
395169691Skan	      else
396169691Skan		_M_gcount = 1;
39797403Sobrien	    }
398117397Skan	  catch(...)
399132720Skan	    { this->_M_setstate(ios_base::badbit); }
400132720Skan	  if (__err)
401132720Skan	    this->setstate(__err);
40297403Sobrien	}
40397403Sobrien      return *this;
40497403Sobrien    }
405132720Skan
40697403Sobrien  template<typename _CharT, typename _Traits>
407169691Skan    basic_istream<_CharT, _Traits>&
408169691Skan    basic_istream<_CharT, _Traits>::
409169691Skan    ignore(streamsize __n)
410169691Skan    {
411169691Skan      _M_gcount = 0;
412169691Skan      sentry __cerb(*this, true);
413169691Skan      if (__cerb && __n > 0)
414169691Skan        {
415169691Skan          ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
416169691Skan          try
417169691Skan            {
418169691Skan              const int_type __eof = traits_type::eof();
419169691Skan              __streambuf_type* __sb = this->rdbuf();
420169691Skan              int_type __c = __sb->sgetc();
421169691Skan
422169691Skan	      // N.B. On LFS-enabled platforms streamsize is still 32 bits
423169691Skan	      // wide: if we want to implement the standard mandated behavior
424169691Skan	      // for n == max() (see 27.6.1.3/24) we are at risk of signed
425169691Skan	      // integer overflow: thus these contortions. Also note that,
426169691Skan	      // by definition, when more than 2G chars are actually ignored,
427169691Skan	      // _M_gcount (the return value of gcount, that is) cannot be
428169691Skan	      // really correct, being unavoidably too small.
429169691Skan	      bool __large_ignore = false;
430169691Skan	      while (true)
431169691Skan		{
432169691Skan		  while (_M_gcount < __n
433169691Skan			 && !traits_type::eq_int_type(__c, __eof))
434169691Skan		    {
435169691Skan		      ++_M_gcount;
436169691Skan		      __c = __sb->snextc();
437169691Skan		    }
438169691Skan		  if (__n == numeric_limits<streamsize>::max()
439169691Skan		      && !traits_type::eq_int_type(__c, __eof))
440169691Skan		    {
441169691Skan		      _M_gcount = numeric_limits<streamsize>::min();
442169691Skan		      __large_ignore = true;
443169691Skan		    }
444169691Skan		  else
445169691Skan		    break;
446169691Skan		}
447169691Skan
448169691Skan	      if (__large_ignore)
449169691Skan		_M_gcount = numeric_limits<streamsize>::max();
450169691Skan
451169691Skan	      if (traits_type::eq_int_type(__c, __eof))
452169691Skan                __err |= ios_base::eofbit;
453169691Skan            }
454169691Skan          catch(...)
455169691Skan            { this->_M_setstate(ios_base::badbit); }
456169691Skan          if (__err)
457169691Skan            this->setstate(__err);
458169691Skan        }
459169691Skan      return *this;
460169691Skan    }
461169691Skan
462169691Skan  template<typename _CharT, typename _Traits>
463169691Skan    basic_istream<_CharT, _Traits>&
464169691Skan    basic_istream<_CharT, _Traits>::
465169691Skan    ignore(streamsize __n, int_type __delim)
466169691Skan    {
467169691Skan      _M_gcount = 0;
468169691Skan      sentry __cerb(*this, true);
469169691Skan      if (__cerb && __n > 0)
470169691Skan        {
471169691Skan          ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
472169691Skan          try
473169691Skan            {
474169691Skan              const int_type __eof = traits_type::eof();
475169691Skan              __streambuf_type* __sb = this->rdbuf();
476169691Skan              int_type __c = __sb->sgetc();
477169691Skan
478169691Skan	      // See comment above.
479169691Skan	      bool __large_ignore = false;
480169691Skan	      while (true)
481169691Skan		{
482169691Skan		  while (_M_gcount < __n
483169691Skan			 && !traits_type::eq_int_type(__c, __eof)
484169691Skan			 && !traits_type::eq_int_type(__c, __delim))
485169691Skan		    {
486169691Skan		      ++_M_gcount;
487169691Skan		      __c = __sb->snextc();
488169691Skan		    }
489169691Skan		  if (__n == numeric_limits<streamsize>::max()
490169691Skan		      && !traits_type::eq_int_type(__c, __eof)
491169691Skan		      && !traits_type::eq_int_type(__c, __delim))
492169691Skan		    {
493169691Skan		      _M_gcount = numeric_limits<streamsize>::min();
494169691Skan		      __large_ignore = true;
495169691Skan		    }
496169691Skan		  else
497169691Skan		    break;
498169691Skan		}
499169691Skan
500169691Skan	      if (__large_ignore)
501169691Skan		_M_gcount = numeric_limits<streamsize>::max();
502169691Skan
503169691Skan              if (traits_type::eq_int_type(__c, __eof))
504169691Skan                __err |= ios_base::eofbit;
505169691Skan	      else if (traits_type::eq_int_type(__c, __delim))
506169691Skan		{
507169691Skan		  if (_M_gcount < numeric_limits<streamsize>::max())
508169691Skan		    ++_M_gcount;
509169691Skan		  __sb->sbumpc();
510169691Skan		}
511169691Skan            }
512169691Skan          catch(...)
513169691Skan            { this->_M_setstate(ios_base::badbit); }
514169691Skan          if (__err)
515169691Skan            this->setstate(__err);
516169691Skan        }
517169691Skan      return *this;
518169691Skan    }
519169691Skan
520169691Skan  template<typename _CharT, typename _Traits>
52197403Sobrien    typename basic_istream<_CharT, _Traits>::int_type
52297403Sobrien    basic_istream<_CharT, _Traits>::
52397403Sobrien    peek(void)
52497403Sobrien    {
52597403Sobrien      int_type __c = traits_type::eof();
52697403Sobrien      _M_gcount = 0;
52797403Sobrien      sentry __cerb(*this, true);
52897403Sobrien      if (__cerb)
52997403Sobrien	{
530132720Skan	  ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
531122182Skan	  try
532122182Skan	    {
533122182Skan	      __c = this->rdbuf()->sgetc();
534122182Skan	      if (traits_type::eq_int_type(__c, traits_type::eof()))
535132720Skan		__err |= ios_base::eofbit;
536122182Skan	    }
537117397Skan	  catch(...)
538132720Skan	    { this->_M_setstate(ios_base::badbit); }
539132720Skan	  if (__err)
540132720Skan	    this->setstate(__err);
541132720Skan	}
54297403Sobrien      return __c;
54397403Sobrien    }
54497403Sobrien
54597403Sobrien  template<typename _CharT, typename _Traits>
54697403Sobrien    basic_istream<_CharT, _Traits>&
54797403Sobrien    basic_istream<_CharT, _Traits>::
54897403Sobrien    read(char_type* __s, streamsize __n)
54997403Sobrien    {
55097403Sobrien      _M_gcount = 0;
55197403Sobrien      sentry __cerb(*this, true);
552132720Skan      if (__cerb)
55397403Sobrien	{
554132720Skan	  ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
555132720Skan	  try
55697403Sobrien	    {
55797403Sobrien	      _M_gcount = this->rdbuf()->sgetn(__s, __n);
55897403Sobrien	      if (_M_gcount != __n)
559132720Skan		__err |= (ios_base::eofbit | ios_base::failbit);
560132720Skan	    }
561117397Skan	  catch(...)
562132720Skan	    { this->_M_setstate(ios_base::badbit); }
563132720Skan	  if (__err)
564132720Skan	    this->setstate(__err);
56597403Sobrien	}
56697403Sobrien      return *this;
56797403Sobrien    }
568132720Skan
56997403Sobrien  template<typename _CharT, typename _Traits>
570132720Skan    streamsize
57197403Sobrien    basic_istream<_CharT, _Traits>::
57297403Sobrien    readsome(char_type* __s, streamsize __n)
57397403Sobrien    {
57497403Sobrien      _M_gcount = 0;
57597403Sobrien      sentry __cerb(*this, true);
576132720Skan      if (__cerb)
57797403Sobrien	{
578132720Skan	  ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
579132720Skan	  try
58097403Sobrien	    {
581107606Sobrien	      // Cannot compare int_type with streamsize generically.
582132720Skan	      const streamsize __num = this->rdbuf()->in_avail();
583132720Skan	      if (__num > 0)
584132720Skan		_M_gcount = this->rdbuf()->sgetn(__s, std::min(__num, __n));
585132720Skan	      else if (__num == -1)
586132720Skan		__err |= ios_base::eofbit;
58797403Sobrien	    }
588117397Skan	  catch(...)
589132720Skan	    { this->_M_setstate(ios_base::badbit); }
590132720Skan	  if (__err)
591132720Skan	    this->setstate(__err);
59297403Sobrien	}
59397403Sobrien      return _M_gcount;
59497403Sobrien    }
595132720Skan
59697403Sobrien  template<typename _CharT, typename _Traits>
59797403Sobrien    basic_istream<_CharT, _Traits>&
59897403Sobrien    basic_istream<_CharT, _Traits>::
59997403Sobrien    putback(char_type __c)
60097403Sobrien    {
601132720Skan      // _GLIBCXX_RESOLVE_LIB_DEFECTS
602132720Skan      // 60. What is a formatted input function?
603117397Skan      _M_gcount = 0;
60497403Sobrien      sentry __cerb(*this, true);
605132720Skan      if (__cerb)
60697403Sobrien	{
607132720Skan	  ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
608132720Skan	  try
60997403Sobrien	    {
61097403Sobrien	      const int_type __eof = traits_type::eof();
61197403Sobrien	      __streambuf_type* __sb = this->rdbuf();
612132720Skan	      if (!__sb
613102782Skan		  || traits_type::eq_int_type(__sb->sputbackc(__c), __eof))
614132720Skan		__err |= ios_base::badbit;
61597403Sobrien	    }
616117397Skan	  catch(...)
617132720Skan	    { this->_M_setstate(ios_base::badbit); }
618132720Skan	  if (__err)
619132720Skan	    this->setstate(__err);
62097403Sobrien	}
62197403Sobrien      return *this;
62297403Sobrien    }
623132720Skan
62497403Sobrien  template<typename _CharT, typename _Traits>
62597403Sobrien    basic_istream<_CharT, _Traits>&
62697403Sobrien    basic_istream<_CharT, _Traits>::
62797403Sobrien    unget(void)
62897403Sobrien    {
629132720Skan      // _GLIBCXX_RESOLVE_LIB_DEFECTS
630132720Skan      // 60. What is a formatted input function?
63197403Sobrien      _M_gcount = 0;
63297403Sobrien      sentry __cerb(*this, true);
633132720Skan      if (__cerb)
63497403Sobrien	{
635132720Skan	  ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
636132720Skan	  try
63797403Sobrien	    {
63897403Sobrien	      const int_type __eof = traits_type::eof();
63997403Sobrien	      __streambuf_type* __sb = this->rdbuf();
640132720Skan	      if (!__sb
641102782Skan		  || traits_type::eq_int_type(__sb->sungetc(), __eof))
642132720Skan		__err |= ios_base::badbit;
64397403Sobrien	    }
644117397Skan	  catch(...)
645132720Skan	    { this->_M_setstate(ios_base::badbit); }
646132720Skan	  if (__err)
647132720Skan	    this->setstate(__err);
64897403Sobrien	}
64997403Sobrien      return *this;
65097403Sobrien    }
651132720Skan
65297403Sobrien  template<typename _CharT, typename _Traits>
65397403Sobrien    int
65497403Sobrien    basic_istream<_CharT, _Traits>::
65597403Sobrien    sync(void)
65697403Sobrien    {
657132720Skan      // _GLIBCXX_RESOLVE_LIB_DEFECTS
658117397Skan      // DR60.  Do not change _M_gcount.
659102782Skan      int __ret = -1;
66097403Sobrien      sentry __cerb(*this, true);
661132720Skan      if (__cerb)
66297403Sobrien	{
663132720Skan	  ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
664132720Skan	  try
66597403Sobrien	    {
66697403Sobrien	      __streambuf_type* __sb = this->rdbuf();
667102782Skan	      if (__sb)
668102782Skan		{
669102782Skan		  if (__sb->pubsync() == -1)
670132720Skan		    __err |= ios_base::badbit;
671132720Skan		  else
672102782Skan		    __ret = 0;
673102782Skan		}
67497403Sobrien	    }
675117397Skan	  catch(...)
676132720Skan	    { this->_M_setstate(ios_base::badbit); }
677132720Skan	  if (__err)
678132720Skan	    this->setstate(__err);
67997403Sobrien	}
68097403Sobrien      return __ret;
68197403Sobrien    }
682132720Skan
68397403Sobrien  template<typename _CharT, typename _Traits>
68497403Sobrien    typename basic_istream<_CharT, _Traits>::pos_type
68597403Sobrien    basic_istream<_CharT, _Traits>::
68697403Sobrien    tellg(void)
68797403Sobrien    {
688132720Skan      // _GLIBCXX_RESOLVE_LIB_DEFECTS
689117397Skan      // DR60.  Do not change _M_gcount.
69097403Sobrien      pos_type __ret = pos_type(-1);
691132720Skan      try
692132720Skan	{
693132720Skan	  if (!this->fail())
694169691Skan	    __ret = this->rdbuf()->pubseekoff(0, ios_base::cur,
695169691Skan					      ios_base::in);
696132720Skan	}
697132720Skan      catch(...)
698132720Skan	{ this->_M_setstate(ios_base::badbit); }
69997403Sobrien      return __ret;
70097403Sobrien    }
70197403Sobrien
70297403Sobrien  template<typename _CharT, typename _Traits>
70397403Sobrien    basic_istream<_CharT, _Traits>&
70497403Sobrien    basic_istream<_CharT, _Traits>::
70597403Sobrien    seekg(pos_type __pos)
70697403Sobrien    {
707132720Skan      // _GLIBCXX_RESOLVE_LIB_DEFECTS
708117397Skan      // DR60.  Do not change _M_gcount.
709132720Skan      ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
710132720Skan      try
71197403Sobrien	{
712132720Skan	  if (!this->fail())
713132720Skan	    {
714132720Skan	      // 136.  seekp, seekg setting wrong streams?
715132720Skan	      const pos_type __p = this->rdbuf()->pubseekpos(__pos,
716132720Skan							     ios_base::in);
717169691Skan	      
718169691Skan	      // 129.  Need error indication from seekp() and seekg()
719132720Skan	      if (__p == pos_type(off_type(-1)))
720132720Skan		__err |= ios_base::failbit;
721132720Skan	    }
72297403Sobrien	}
723132720Skan      catch(...)
724132720Skan	{ this->_M_setstate(ios_base::badbit); }
725132720Skan      if (__err)
726132720Skan	this->setstate(__err);
72797403Sobrien      return *this;
72897403Sobrien    }
72997403Sobrien
73097403Sobrien  template<typename _CharT, typename _Traits>
73197403Sobrien    basic_istream<_CharT, _Traits>&
73297403Sobrien    basic_istream<_CharT, _Traits>::
73397403Sobrien    seekg(off_type __off, ios_base::seekdir __dir)
73497403Sobrien    {
735132720Skan      // _GLIBCXX_RESOLVE_LIB_DEFECTS
736117397Skan      // DR60.  Do not change _M_gcount.
737132720Skan      ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
738132720Skan      try
73997403Sobrien	{
740132720Skan	  if (!this->fail())
741132720Skan	    {
742132720Skan	      // 136.  seekp, seekg setting wrong streams?
743132720Skan	      const pos_type __p = this->rdbuf()->pubseekoff(__off, __dir,
744132720Skan							     ios_base::in);
745169691Skan	      
746169691Skan	      // 129.  Need error indication from seekp() and seekg()
747132720Skan	      if (__p == pos_type(off_type(-1)))
748132720Skan		__err |= ios_base::failbit;
749132720Skan	    }
75097403Sobrien	}
751132720Skan      catch(...)
752132720Skan	{ this->_M_setstate(ios_base::badbit); }
753132720Skan      if (__err)
754132720Skan	this->setstate(__err);
75597403Sobrien      return *this;
75697403Sobrien    }
75797403Sobrien
75897403Sobrien  // 27.6.1.2.3 Character extraction templates
75997403Sobrien  template<typename _CharT, typename _Traits>
76097403Sobrien    basic_istream<_CharT, _Traits>&
76197403Sobrien    operator>>(basic_istream<_CharT, _Traits>& __in, _CharT& __c)
76297403Sobrien    {
763132720Skan      typedef basic_istream<_CharT, _Traits>		__istream_type;
764132720Skan      typedef typename __istream_type::int_type         __int_type;
765132720Skan
76697403Sobrien      typename __istream_type::sentry __cerb(__in, false);
76797403Sobrien      if (__cerb)
76897403Sobrien	{
769132720Skan	  ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
770132720Skan	  try
77197403Sobrien	    {
772132720Skan	      const __int_type __cb = __in.rdbuf()->sbumpc();
773132720Skan	      if (!_Traits::eq_int_type(__cb, _Traits::eof()))
774132720Skan		__c = _Traits::to_char_type(__cb);
775132720Skan	      else
776132720Skan		__err |= (ios_base::eofbit | ios_base::failbit);
77797403Sobrien	    }
778132720Skan	  catch(...)
779132720Skan	    { __in._M_setstate(ios_base::badbit); }
780132720Skan	  if (__err)
781132720Skan	    __in.setstate(__err);
78297403Sobrien	}
78397403Sobrien      return __in;
78497403Sobrien    }
78597403Sobrien
78697403Sobrien  template<typename _CharT, typename _Traits>
78797403Sobrien    basic_istream<_CharT, _Traits>&
78897403Sobrien    operator>>(basic_istream<_CharT, _Traits>& __in, _CharT* __s)
78997403Sobrien    {
790132720Skan      typedef basic_istream<_CharT, _Traits>		__istream_type;
79197403Sobrien      typedef typename __istream_type::__streambuf_type __streambuf_type;
792132720Skan      typedef typename _Traits::int_type		int_type;
793132720Skan      typedef _CharT					char_type;
794132720Skan      typedef ctype<_CharT>				__ctype_type;
795132720Skan
79697403Sobrien      streamsize __extracted = 0;
797132720Skan      ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
79897403Sobrien      typename __istream_type::sentry __cerb(__in, false);
79997403Sobrien      if (__cerb)
80097403Sobrien	{
801132720Skan	  try
80297403Sobrien	    {
80397403Sobrien	      // Figure out how many characters to extract.
80497403Sobrien	      streamsize __num = __in.width();
805117397Skan	      if (__num <= 0)
80697403Sobrien		__num = numeric_limits<streamsize>::max();
807132720Skan
808132720Skan	      const __ctype_type& __ct = use_facet<__ctype_type>(__in.getloc());
809132720Skan
81097403Sobrien	      const int_type __eof = _Traits::eof();
81197403Sobrien	      __streambuf_type* __sb = __in.rdbuf();
81297403Sobrien	      int_type __c = __sb->sgetc();
813132720Skan
814132720Skan	      while (__extracted < __num - 1
815107606Sobrien		     && !_Traits::eq_int_type(__c, __eof)
816132720Skan		     && !__ct.is(ctype_base::space,
817132720Skan				 _Traits::to_char_type(__c)))
81897403Sobrien		{
819117397Skan		  *__s++ = _Traits::to_char_type(__c);
82097403Sobrien		  ++__extracted;
82197403Sobrien		  __c = __sb->snextc();
82297403Sobrien		}
823107606Sobrien	      if (_Traits::eq_int_type(__c, __eof))
824132720Skan		__err |= ios_base::eofbit;
82597403Sobrien
826132720Skan	      // _GLIBCXX_RESOLVE_LIB_DEFECTS
827132720Skan	      // 68.  Extractors for char* should store null at end
82897403Sobrien	      *__s = char_type();
82997403Sobrien	      __in.width(0);
83097403Sobrien	    }
831117397Skan	  catch(...)
832132720Skan	    { __in._M_setstate(ios_base::badbit); }
83397403Sobrien	}
83497403Sobrien      if (!__extracted)
835132720Skan	__err |= ios_base::failbit;
836132720Skan      if (__err)
837132720Skan	__in.setstate(__err);
83897403Sobrien      return __in;
83997403Sobrien    }
84097403Sobrien
84197403Sobrien  // 27.6.1.4 Standard basic_istream manipulators
84297403Sobrien  template<typename _CharT, typename _Traits>
843132720Skan    basic_istream<_CharT,_Traits>&
84497403Sobrien    ws(basic_istream<_CharT,_Traits>& __in)
84597403Sobrien    {
846132720Skan      typedef basic_istream<_CharT, _Traits>		__istream_type;
84797403Sobrien      typedef typename __istream_type::__streambuf_type __streambuf_type;
848132720Skan      typedef typename __istream_type::__ctype_type	__ctype_type;
849132720Skan      typedef typename __istream_type::int_type		__int_type;
85097403Sobrien
851132720Skan      const __ctype_type& __ct = use_facet<__ctype_type>(__in.getloc());
852132720Skan      const __int_type __eof = _Traits::eof();
85397403Sobrien      __streambuf_type* __sb = __in.rdbuf();
85497403Sobrien      __int_type __c = __sb->sgetc();
85597403Sobrien
856132720Skan      while (!_Traits::eq_int_type(__c, __eof)
857132720Skan	     && __ct.is(ctype_base::space, _Traits::to_char_type(__c)))
85897403Sobrien	__c = __sb->snextc();
859107606Sobrien
860107606Sobrien       if (_Traits::eq_int_type(__c, __eof))
861132720Skan	 __in.setstate(ios_base::eofbit);
86297403Sobrien      return __in;
86397403Sobrien    }
86497403Sobrien
86597403Sobrien  // 21.3.7.9 basic_string::getline and operators
86697403Sobrien  template<typename _CharT, typename _Traits, typename _Alloc>
86797403Sobrien    basic_istream<_CharT, _Traits>&
86897403Sobrien    operator>>(basic_istream<_CharT, _Traits>& __in,
86997403Sobrien	       basic_string<_CharT, _Traits, _Alloc>& __str)
87097403Sobrien    {
871132720Skan      typedef basic_istream<_CharT, _Traits>		__istream_type;
872132720Skan      typedef typename __istream_type::int_type		__int_type;
87397403Sobrien      typedef typename __istream_type::__streambuf_type __streambuf_type;
874132720Skan      typedef typename __istream_type::__ctype_type	__ctype_type;
875132720Skan      typedef basic_string<_CharT, _Traits, _Alloc>	__string_type;
87697403Sobrien      typedef typename __string_type::size_type		__size_type;
877132720Skan
87897403Sobrien      __size_type __extracted = 0;
879132720Skan      ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
88097403Sobrien      typename __istream_type::sentry __cerb(__in, false);
881132720Skan      if (__cerb)
88297403Sobrien	{
883132720Skan	  try
884132720Skan	    {
885132720Skan	      // Avoid reallocation for common case.
886132720Skan	      __str.erase();
887132720Skan	      _CharT __buf[128];
888132720Skan	      __size_type __len = 0;	      
889132720Skan	      const streamsize __w = __in.width();
890132720Skan	      const __size_type __n = __w > 0 ? static_cast<__size_type>(__w)
891132720Skan		                              : __str.max_size();
892132720Skan	      const __ctype_type& __ct = use_facet<__ctype_type>(__in.getloc());
893132720Skan	      const __int_type __eof = _Traits::eof();
894132720Skan	      __streambuf_type* __sb = __in.rdbuf();
895132720Skan	      __int_type __c = __sb->sgetc();
89697403Sobrien
897132720Skan	      while (__extracted < __n
898132720Skan		     && !_Traits::eq_int_type(__c, __eof)
899132720Skan		     && !__ct.is(ctype_base::space, _Traits::to_char_type(__c)))
900132720Skan		{
901132720Skan		  if (__len == sizeof(__buf) / sizeof(_CharT))
902132720Skan		    {
903132720Skan		      __str.append(__buf, sizeof(__buf) / sizeof(_CharT));
904132720Skan		      __len = 0;
905132720Skan		    }
906132720Skan		  __buf[__len++] = _Traits::to_char_type(__c);
907132720Skan		  ++__extracted;
908132720Skan		  __c = __sb->snextc();
909132720Skan		}
910132720Skan	      __str.append(__buf, __len);
911132720Skan
912132720Skan	      if (_Traits::eq_int_type(__c, __eof))
913132720Skan		__err |= ios_base::eofbit;
914132720Skan	      __in.width(0);
915132720Skan	    }
916132720Skan	  catch(...)
91797403Sobrien	    {
918132720Skan	      // _GLIBCXX_RESOLVE_LIB_DEFECTS
919132720Skan	      // 91. Description of operator>> and getline() for string<>
920132720Skan	      // might cause endless loop
921132720Skan	      __in._M_setstate(ios_base::badbit);
92297403Sobrien	    }
92397403Sobrien	}
924132720Skan      // 211.  operator>>(istream&, string&) doesn't set failbit
92597403Sobrien      if (!__extracted)
926132720Skan	__err |= ios_base::failbit;
927132720Skan      if (__err)
928132720Skan	__in.setstate(__err);
92997403Sobrien      return __in;
93097403Sobrien    }
93197403Sobrien
93297403Sobrien  template<typename _CharT, typename _Traits, typename _Alloc>
93397403Sobrien    basic_istream<_CharT, _Traits>&
93497403Sobrien    getline(basic_istream<_CharT, _Traits>& __in,
93597403Sobrien	    basic_string<_CharT, _Traits, _Alloc>& __str, _CharT __delim)
93697403Sobrien    {
937132720Skan      typedef basic_istream<_CharT, _Traits>		__istream_type;
938132720Skan      typedef typename __istream_type::int_type		__int_type;
93997403Sobrien      typedef typename __istream_type::__streambuf_type __streambuf_type;
940132720Skan      typedef typename __istream_type::__ctype_type	__ctype_type;
941132720Skan      typedef basic_string<_CharT, _Traits, _Alloc>	__string_type;
94297403Sobrien      typedef typename __string_type::size_type		__size_type;
94397403Sobrien
94497403Sobrien      __size_type __extracted = 0;
945132720Skan      const __size_type __n = __str.max_size();
946132720Skan      ios_base::iostate __err = ios_base::iostate(ios_base::goodbit);
94797403Sobrien      typename __istream_type::sentry __cerb(__in, true);
948132720Skan      if (__cerb)
94997403Sobrien	{
950132720Skan	  try
951132720Skan	    {
952132720Skan	      __str.erase();
953132720Skan	      const __int_type __idelim = _Traits::to_int_type(__delim);
954132720Skan	      const __int_type __eof = _Traits::eof();
955132720Skan	      __streambuf_type* __sb = __in.rdbuf();
956132720Skan	      __int_type __c = __sb->sgetc();
95797403Sobrien
958132720Skan	      while (__extracted < __n
959132720Skan		     && !_Traits::eq_int_type(__c, __eof)
960132720Skan		     && !_Traits::eq_int_type(__c, __idelim))
961132720Skan		{
962169691Skan		  __str += _Traits::to_char_type(__c);
963132720Skan		  ++__extracted;
964132720Skan		  __c = __sb->snextc();
965132720Skan		}
96697403Sobrien
967132720Skan	      if (_Traits::eq_int_type(__c, __eof))
968132720Skan		__err |= ios_base::eofbit;
969132720Skan	      else if (_Traits::eq_int_type(__c, __idelim))
970132720Skan		{
971132720Skan		  ++__extracted;		  
972132720Skan		  __sb->sbumpc();
973132720Skan		}
974132720Skan	      else
975132720Skan		__err |= ios_base::failbit;
976132720Skan	    }
977132720Skan	  catch(...)
97897403Sobrien	    {
979132720Skan	      // _GLIBCXX_RESOLVE_LIB_DEFECTS
980132720Skan	      // 91. Description of operator>> and getline() for string<>
981132720Skan	      // might cause endless loop
982132720Skan	      __in._M_setstate(ios_base::badbit);
98397403Sobrien	    }
98497403Sobrien	}
985132720Skan      if (!__extracted)
986132720Skan	__err |= ios_base::failbit;
987132720Skan      if (__err)
988132720Skan	__in.setstate(__err);
98997403Sobrien      return __in;
99097403Sobrien    }
99197403Sobrien
99297403Sobrien  // Inhibit implicit instantiations for required instantiations,
993132720Skan  // which are defined via explicit instantiations elsewhere.
99497403Sobrien  // NB:  This syntax is a GNU extension.
995132720Skan#if _GLIBCXX_EXTERN_TEMPLATE
99697403Sobrien  extern template class basic_istream<char>;
99797403Sobrien  extern template istream& ws(istream&);
99897403Sobrien  extern template istream& operator>>(istream&, char&);
99997403Sobrien  extern template istream& operator>>(istream&, char*);
100097403Sobrien  extern template istream& operator>>(istream&, unsigned char&);
100197403Sobrien  extern template istream& operator>>(istream&, signed char&);
100297403Sobrien  extern template istream& operator>>(istream&, unsigned char*);
100397403Sobrien  extern template istream& operator>>(istream&, signed char*);
100497403Sobrien
1005169691Skan  extern template istream& istream::_M_extract(unsigned short&);
1006169691Skan  extern template istream& istream::_M_extract(unsigned int&);  
1007169691Skan  extern template istream& istream::_M_extract(long&);
1008169691Skan  extern template istream& istream::_M_extract(unsigned long&);
1009169691Skan  extern template istream& istream::_M_extract(bool&);
1010169691Skan#ifdef _GLIBCXX_USE_LONG_LONG
1011169691Skan  extern template istream& istream::_M_extract(long long&);
1012169691Skan  extern template istream& istream::_M_extract(unsigned long long&);
1013169691Skan#endif
1014169691Skan  extern template istream& istream::_M_extract(float&);
1015169691Skan  extern template istream& istream::_M_extract(double&);
1016169691Skan  extern template istream& istream::_M_extract(long double&);
1017169691Skan  extern template istream& istream::_M_extract(void*&);
1018169691Skan
1019146897Skan  extern template class basic_iostream<char>;
1020146897Skan
1021132720Skan#ifdef _GLIBCXX_USE_WCHAR_T
102297403Sobrien  extern template class basic_istream<wchar_t>;
102397403Sobrien  extern template wistream& ws(wistream&);
102497403Sobrien  extern template wistream& operator>>(wistream&, wchar_t&);
102597403Sobrien  extern template wistream& operator>>(wistream&, wchar_t*);
1026146897Skan
1027169691Skan  extern template wistream& wistream::_M_extract(unsigned short&);
1028169691Skan  extern template wistream& wistream::_M_extract(unsigned int&);  
1029169691Skan  extern template wistream& wistream::_M_extract(long&);
1030169691Skan  extern template wistream& wistream::_M_extract(unsigned long&);
1031169691Skan  extern template wistream& wistream::_M_extract(bool&);
1032169691Skan#ifdef _GLIBCXX_USE_LONG_LONG
1033169691Skan  extern template wistream& wistream::_M_extract(long long&);
1034169691Skan  extern template wistream& wistream::_M_extract(unsigned long long&);
1035169691Skan#endif
1036169691Skan  extern template wistream& wistream::_M_extract(float&);
1037169691Skan  extern template wistream& wistream::_M_extract(double&);
1038169691Skan  extern template wistream& wistream::_M_extract(long double&);
1039169691Skan  extern template wistream& wistream::_M_extract(void*&);
1040169691Skan
1041146897Skan  extern template class basic_iostream<wchar_t>;
1042102782Skan#endif
1043117397Skan#endif
1044132720Skan
1045169691Skan_GLIBCXX_END_NAMESPACE
1046169691Skan
1047132720Skan#endif
1048