std_fstream.h revision 171828
1193326Sed// File based streams -*- C++ -*-
2193326Sed
3193326Sed// Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005,
4193326Sed// 2006, 2007
5193326Sed// Free Software Foundation, Inc.
6193326Sed//
7193326Sed// This file is part of the GNU ISO C++ Library.  This library is free
8193326Sed// software; you can redistribute it and/or modify it under the
9193326Sed// terms of the GNU General Public License as published by the
10193326Sed// Free Software Foundation; either version 2, or (at your option)
11193326Sed// any later version.
12193326Sed
13193326Sed// This library is distributed in the hope that it will be useful,
14193326Sed// but WITHOUT ANY WARRANTY; without even the implied warranty of
15193326Sed// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16193326Sed// GNU General Public License for more details.
17193326Sed
18193326Sed// You should have received a copy of the GNU General Public License along
19193326Sed// with this library; see the file COPYING.  If not, write to the Free
20203955Srdivacky// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
21193326Sed// USA.
22193326Sed
23193326Sed// As a special exception, you may use this file as part of a free software
24193326Sed// library without restriction.  Specifically, if other files instantiate
25193326Sed// templates or use macros or inline functions from this file, or you compile
26199990Srdivacky// this file and link it with other files to produce an executable, this
27193326Sed// file does not by itself cause the resulting executable to be covered by
28193326Sed// the GNU General Public License.  This exception does not however
29193326Sed// invalidate any other reasons why the executable file might be covered by
30193326Sed// the GNU General Public License.
31193326Sed
32199990Srdivacky/** @file fstream
33199990Srdivacky *  This is a Standard C++ Library header.
34193326Sed */
35193326Sed
36198092Srdivacky//
37198092Srdivacky// ISO C++ 14882: 27.8  File-based streams
38193326Sed//
39198092Srdivacky
40193326Sed#ifndef _GLIBCXX_FSTREAM
41193326Sed#define _GLIBCXX_FSTREAM 1
42193326Sed
43193326Sed#pragma GCC system_header
44193326Sed
45193326Sed#include <istream>
46193326Sed#include <ostream>
47193326Sed#include <locale>	// For codecvt
48221345Sdim#include <cstdio>       // For SEEK_SET, SEEK_CUR, SEEK_END, BUFSIZ
49193326Sed#include <bits/basic_file.h>
50193326Sed#include <bits/gthr.h>
51193326Sed
52193326Sed_GLIBCXX_BEGIN_NAMESPACE(std)
53193326Sed
54193326Sed  // [27.8.1.1] template class basic_filebuf
55218893Sdim  /**
56193326Sed   *  @brief  The actual work of input and output (for files).
57193326Sed   *
58221345Sdim   *  This class associates both its input and output sequence with an
59193326Sed   *  external disk file, and maintains a joint file position for both
60193326Sed   *  sequences.  Many of its sematics are described in terms of similar
61193326Sed   *  behavior in the Standard C Library's @c FILE streams.
62193326Sed  */
63193326Sed  // Requirements on traits_type, specific to this class:
64221345Sdim  // traits_type::pos_type must be fpos<traits_type::state_type>
65193326Sed  // traits_type::off_type must be streamoff
66193326Sed  // traits_type::state_type must be Assignable and DefaultConstructable,
67193326Sed  // and traits_type::state_type() must be the initial state for codecvt.
68193326Sed  template<typename _CharT, typename _Traits>
69193326Sed    class basic_filebuf : public basic_streambuf<_CharT, _Traits>
70193326Sed    {
71193326Sed    public:
72193326Sed      // Types:
73193326Sed      typedef _CharT                     	        char_type;
74193326Sed      typedef _Traits                    	        traits_type;
75193326Sed      typedef typename traits_type::int_type 		int_type;
76199482Srdivacky      typedef typename traits_type::pos_type 		pos_type;
77199482Srdivacky      typedef typename traits_type::off_type 		off_type;
78198092Srdivacky
79199482Srdivacky      typedef basic_streambuf<char_type, traits_type>  	__streambuf_type;
80193326Sed      typedef basic_filebuf<char_type, traits_type>     __filebuf_type;
81193326Sed      typedef __basic_file<char>		        __file_type;
82193326Sed      typedef typename traits_type::state_type          __state_type;
83198092Srdivacky      typedef codecvt<char_type, char, __state_type>    __codecvt_type;
84195341Sed
85193326Sed      friend class ios_base; // For sync_with_stdio.
86193326Sed
87195341Sed    protected:
88198092Srdivacky      // Data Members:
89195341Sed      // MT lock inherited from libio or other low-level io library.
90198092Srdivacky      __c_lock          	_M_lock;
91193326Sed
92193326Sed      // External buffer.
93193326Sed      __file_type 		_M_file;
94193326Sed
95193326Sed      /**
96193326Sed       *  @if maint
97193326Sed       *  Place to stash in || out || in | out settings for current filebuf.
98193326Sed       *  @endif
99198092Srdivacky      */
100193326Sed      ios_base::openmode 	_M_mode;
101193326Sed
102193326Sed      // Beginning state type for codecvt.
103198092Srdivacky      __state_type 		_M_state_beg;
104193326Sed
105198092Srdivacky      // During output, the state that corresponds to pptr(),
106195341Sed      // during input, the state that corresponds to egptr() and
107193326Sed      // _M_ext_next.
108193326Sed      __state_type		_M_state_cur;
109193326Sed
110193326Sed      // Not used for output. During input, the state that corresponds
111193326Sed      // to eback() and _M_ext_buf.
112193326Sed      __state_type		_M_state_last;
113193326Sed
114221345Sdim      /**
115193326Sed       *  @if maint
116193326Sed       *  Pointer to the beginning of internal buffer.
117193326Sed       *  @endif
118193326Sed      */
119193326Sed      char_type*		_M_buf;
120193326Sed
121193326Sed      /**
122195341Sed       *  @if maint
123193326Sed       *  Actual size of internal buffer. This number is equal to the size
124193326Sed       *  of the put area + 1 position, reserved for the overflow char of
125195341Sed       *  a full area.
126193326Sed       *  @endif
127193326Sed      */
128193326Sed      size_t			_M_buf_size;
129193326Sed
130193326Sed      // Set iff _M_buf is allocated memory from _M_allocate_internal_buffer.
131193326Sed      bool			_M_buf_allocated;
132193326Sed
133193326Sed      /**
134193326Sed       *  @if maint
135193326Sed       *  _M_reading == false && _M_writing == false for 'uncommitted' mode;
136195341Sed       *  _M_reading == true for 'read' mode;
137193326Sed       *  _M_writing == true for 'write' mode;
138193326Sed       *
139193326Sed       *  NB: _M_reading == true && _M_writing == true is unused.
140193326Sed       *  @endif
141193326Sed      */
142193326Sed      bool                      _M_reading;
143193326Sed      bool                      _M_writing;
144193326Sed
145193326Sed      //@{
146193326Sed      /**
147193326Sed       *  @if maint
148193326Sed       *  Necessary bits for putback buffer management.
149193326Sed       *
150193326Sed       *  @note pbacks of over one character are not currently supported.
151195341Sed       *  @endif
152193326Sed      */
153193326Sed      char_type			_M_pback;
154193326Sed      char_type*		_M_pback_cur_save;
155200583Srdivacky      char_type*		_M_pback_end_save;
156200583Srdivacky      bool			_M_pback_init;
157200583Srdivacky      //@}
158200583Srdivacky
159200583Srdivacky      // Cached codecvt facet.
160200583Srdivacky      const __codecvt_type* 	_M_codecvt;
161200583Srdivacky
162200583Srdivacky      /**
163200583Srdivacky       *  @if maint
164200583Srdivacky       *  Buffer for external characters. Used for input when
165200583Srdivacky       *  codecvt::always_noconv() == false. When valid, this corresponds
166198092Srdivacky       *  to eback().
167195341Sed       *  @endif
168193326Sed      */
169193326Sed      char*			_M_ext_buf;
170199990Srdivacky
171199990Srdivacky      /**
172193326Sed       *  @if maint
173193326Sed       *  Size of buffer held by _M_ext_buf.
174193326Sed       *  @endif
175193326Sed      */
176193326Sed      streamsize		_M_ext_buf_size;
177193326Sed
178195341Sed      /**
179193326Sed       *  @if maint
180193326Sed       *  Pointers into the buffer held by _M_ext_buf that delimit a
181193326Sed       *  subsequence of bytes that have been read but not yet converted.
182193326Sed       *  When valid, _M_ext_next corresponds to egptr().
183193326Sed       *  @endif
184198092Srdivacky      */
185198092Srdivacky      const char*		_M_ext_next;
186198092Srdivacky      char*			_M_ext_end;
187198092Srdivacky
188198092Srdivacky      /**
189210299Sed       *  @if maint
190198092Srdivacky       *  Initializes pback buffers, and moves normal buffers to safety.
191198092Srdivacky       *  Assumptions:
192198092Srdivacky       *  _M_in_cur has already been moved back
193193326Sed       *  @endif
194193326Sed      */
195193326Sed      void
196193326Sed      _M_create_pback()
197193326Sed      {
198193326Sed	if (!_M_pback_init)
199193326Sed	  {
200193326Sed	    _M_pback_cur_save = this->gptr();
201193326Sed	    _M_pback_end_save = this->egptr();
202195341Sed	    this->setg(&_M_pback, &_M_pback, &_M_pback + 1);
203193326Sed	    _M_pback_init = true;
204212904Sdim	  }
205212904Sdim      }
206212904Sdim
207212904Sdim      /**
208212904Sdim       *  @if maint
209212904Sdim       *  Deactivates pback buffer contents, and restores normal buffer.
210193326Sed       *  Assumptions:
211193326Sed       *  The pback buffer has only moved forward.
212193326Sed       *  @endif
213193326Sed      */
214210299Sed      void
215210299Sed      _M_destroy_pback() throw()
216210299Sed      {
217210299Sed	if (_M_pback_init)
218210299Sed	  {
219210299Sed	    // Length _M_in_cur moved in the pback buffer.
220210299Sed	    _M_pback_cur_save += this->gptr() != this->eback();
221210299Sed	    this->setg(_M_buf, _M_pback_cur_save, _M_pback_end_save);
222198092Srdivacky	    _M_pback_init = false;
223198092Srdivacky	  }
224198092Srdivacky      }
225193326Sed
226193326Sed    public:
227193326Sed      // Constructors/destructor:
228193326Sed      /**
229193326Sed       *  @brief  Does not open any files.
230193326Sed       *
231193326Sed       *  The default constructor initializes the parent class using its
232193326Sed       *  own default ctor.
233193326Sed      */
234193326Sed      basic_filebuf();
235193326Sed
236193326Sed      /**
237193326Sed       *  @brief  The destructor closes the file first.
238193326Sed      */
239193326Sed      virtual
240193326Sed      ~basic_filebuf()
241193326Sed      { this->close(); }
242193326Sed
243193326Sed      // Members:
244193326Sed      /**
245193326Sed       *  @brief  Returns true if the external file is open.
246193326Sed      */
247193326Sed      bool
248193326Sed      is_open() const throw()
249193326Sed      { return _M_file.is_open(); }
250193326Sed
251193326Sed      /**
252193326Sed       *  @brief  Opens an external file.
253210299Sed       *  @param  s  The name of the file.
254210299Sed       *  @param  mode  The open mode flags.
255210299Sed       *  @return  @c this on success, NULL on failure
256210299Sed       *
257210299Sed       *  If a file is already open, this function immediately fails.
258210299Sed       *  Otherwise it tries to open the file named @a s using the flags
259210299Sed       *  given in @a mode.
260210299Sed       *
261210299Sed       *  Table 92, adapted here, gives the relation between openmode
262210299Sed       *  combinations and the equivalent fopen() flags.
263193326Sed       *  (NB: lines in|out|app and binary|in|out|app per DR 596)
264193326Sed       *  +---------------------------------------------------------+
265198092Srdivacky       *  | ios_base Flag combination            stdio equivalent   |
266198092Srdivacky       *  |binary  in  out  trunc  app                              |
267193326Sed       *  +---------------------------------------------------------+
268198092Srdivacky       *  |             +                        "w"                |
269193326Sed       *  |             +           +            "a"                |
270193326Sed       *  |             +     +                  "w"                |
271193326Sed       *  |         +                            "r"                |
272193326Sed       *  |         +   +                        "r+"               |
273193326Sed       *  |         +   +     +                  "w+"               |
274198092Srdivacky       *  |         +   +           +            "a+"               |
275193326Sed       *  +---------------------------------------------------------+
276193326Sed       *  |   +         +                        "wb"               |
277193326Sed       *  |   +         +           +            "ab"               |
278193326Sed       *  |   +         +     +                  "wb"               |
279193326Sed       *  |   +     +                            "rb"               |
280193326Sed       *  |   +     +   +                        "r+b"              |
281193326Sed       *  |   +     +   +     +                  "w+b"              |
282193326Sed       *  |   +     +   +           +            "a+b"              |
283193326Sed       *  +---------------------------------------------------------+
284193326Sed       */
285193326Sed      __filebuf_type*
286193326Sed      open(const char* __s, ios_base::openmode __mode);
287193326Sed
288193326Sed      /**
289193326Sed       *  @brief  Closes the currently associated file.
290193326Sed       *  @return  @c this on success, NULL on failure
291193326Sed       *
292193326Sed       *  If no file is currently open, this function immediately fails.
293193326Sed       *
294193326Sed       *  If a "put buffer area" exists, @c overflow(eof) is called to flush
295193326Sed       *  all the characters.  The file is then closed.
296193326Sed       *
297193326Sed       *  If any operations fail, this function also fails.
298193326Sed      */
299193326Sed      __filebuf_type*
300193326Sed      close() throw();
301193326Sed
302193326Sed    protected:
303193326Sed      void
304193326Sed      _M_allocate_internal_buffer();
305193326Sed
306193326Sed      void
307193326Sed      _M_destroy_internal_buffer() throw();
308193326Sed
309193326Sed      // [27.8.1.4] overridden virtual functions
310193326Sed      virtual streamsize
311193326Sed      showmanyc();
312221345Sdim
313221345Sdim      // Stroustrup, 1998, p. 628
314221345Sdim      // underflow() and uflow() functions are called to get the next
315221345Sdim      // charater from the real input source when the buffer is empty.
316221345Sdim      // Buffered input uses underflow()
317193326Sed
318218893Sdim      virtual int_type
319218893Sdim      underflow();
320218893Sdim
321218893Sdim      virtual int_type
322218893Sdim      pbackfail(int_type __c = _Traits::eof());
323218893Sdim
324218893Sdim      // Stroustrup, 1998, p 648
325218893Sdim      // The overflow() function is called to transfer characters to the
326218893Sdim      // real output destination when the buffer is full. A call to
327218893Sdim      // overflow(c) outputs the contents of the buffer plus the
328218893Sdim      // character c.
329218893Sdim      // 27.5.2.4.5
330218893Sdim      // Consume some sequence of the characters in the pending sequence.
331218893Sdim      virtual int_type
332218893Sdim      overflow(int_type __c = _Traits::eof());
333218893Sdim
334218893Sdim      // Convert internal byte sequence to external, char-based
335218893Sdim      // sequence via codecvt.
336218893Sdim      bool
337218893Sdim      _M_convert_to_external(char_type*, streamsize);
338193326Sed
339193326Sed      /**
340193326Sed       *  @brief  Manipulates the buffer.
341193326Sed       *  @param  s  Pointer to a buffer area.
342207619Srdivacky       *  @param  n  Size of @a s.
343207619Srdivacky       *  @return  @c this
344198092Srdivacky       *
345193326Sed       *  If no file has been opened, and both @a s and @a n are zero, then
346193326Sed       *  the stream becomes unbuffered.  Otherwise, @c s is used as a
347193326Sed       *  buffer; see
348193326Sed       *  http://gcc.gnu.org/onlinedocs/libstdc++/27_io/howto.html#2
349193326Sed       *  for more.
350193326Sed      */
351193326Sed      virtual __streambuf_type*
352193326Sed      setbuf(char_type* __s, streamsize __n);
353207619Srdivacky
354193326Sed      virtual pos_type
355193326Sed      seekoff(off_type __off, ios_base::seekdir __way,
356193326Sed	      ios_base::openmode __mode = ios_base::in | ios_base::out);
357193326Sed
358193326Sed      virtual pos_type
359193326Sed      seekpos(pos_type __pos,
360198092Srdivacky	      ios_base::openmode __mode = ios_base::in | ios_base::out);
361193326Sed
362193326Sed      // Common code for seekoff and seekpos
363212904Sdim      pos_type
364212904Sdim      _M_seek(off_type __off, ios_base::seekdir __way, __state_type __state);
365212904Sdim
366212904Sdim      virtual int
367212904Sdim      sync();
368193326Sed
369193326Sed      virtual void
370198893Srdivacky      imbue(const locale& __loc);
371193326Sed
372193326Sed      virtual streamsize
373193326Sed      xsgetn(char_type* __s, streamsize __n);
374193326Sed
375193326Sed      virtual streamsize
376212904Sdim      xsputn(const char_type* __s, streamsize __n);
377193326Sed
378218893Sdim      // Flushes output buffer, then writes unshift sequence.
379218893Sdim      bool
380218893Sdim      _M_terminate_output();
381218893Sdim
382218893Sdim      /**
383218893Sdim       *  @if maint
384218893Sdim       *  This function sets the pointers of the internal buffer, both get
385218893Sdim       *  and put areas. Typically:
386193326Sed       *
387193326Sed       *   __off == egptr() - eback() upon underflow/uflow ('read' mode);
388193326Sed       *   __off == 0 upon overflow ('write' mode);
389193326Sed       *   __off == -1 upon open, setbuf, seekoff/pos ('uncommitted' mode).
390193326Sed       *
391193326Sed       *  NB: epptr() - pbase() == _M_buf_size - 1, since _M_buf_size
392193326Sed       *  reflects the actual allocated memory and the last cell is reserved
393193326Sed       *  for the overflow char of a full put area.
394193326Sed       *  @endif
395193326Sed      */
396193326Sed      void
397193326Sed      _M_set_buffer(streamsize __off)
398198092Srdivacky      {
399193326Sed 	const bool __testin = _M_mode & ios_base::in;
400193326Sed 	const bool __testout = _M_mode & ios_base::out;
401193326Sed
402193326Sed	if (__testin && __off > 0)
403223017Sdim	  this->setg(_M_buf, _M_buf, _M_buf + __off);
404193326Sed	else
405193326Sed	  this->setg(_M_buf, _M_buf, _M_buf);
406193326Sed
407193326Sed	if (__testout && __off == 0 && _M_buf_size > 1 )
408193326Sed	  this->setp(_M_buf, _M_buf + _M_buf_size - 1);
409193326Sed	else
410193326Sed	  this->setp(NULL, NULL);
411193326Sed      }
412200583Srdivacky    };
413218893Sdim
414218893Sdim  // [27.8.1.5] Template class basic_ifstream
415218893Sdim  /**
416218893Sdim   *  @brief  Controlling input for files.
417218893Sdim   *
418218893Sdim   *  This class supports reading from named files, using the inherited
419218893Sdim   *  functions from std::basic_istream.  To control the associated
420218893Sdim   *  sequence, an instance of std::basic_filebuf is used, which this page
421218893Sdim   *  refers to as @c sb.
422221345Sdim  */
423221345Sdim  template<typename _CharT, typename _Traits>
424200583Srdivacky    class basic_ifstream : public basic_istream<_CharT, _Traits>
425221345Sdim    {
426200583Srdivacky    public:
427200583Srdivacky      // Types:
428200583Srdivacky      typedef _CharT 					char_type;
429200583Srdivacky      typedef _Traits 					traits_type;
430200583Srdivacky      typedef typename traits_type::int_type 		int_type;
431221345Sdim      typedef typename traits_type::pos_type 		pos_type;
432200583Srdivacky      typedef typename traits_type::off_type 		off_type;
433200583Srdivacky
434200583Srdivacky      // Non-standard types:
435200583Srdivacky      typedef basic_filebuf<char_type, traits_type> 	__filebuf_type;
436200583Srdivacky      typedef basic_istream<char_type, traits_type>	__istream_type;
437221345Sdim
438221345Sdim    private:
439221345Sdim      __filebuf_type	_M_filebuf;
440221345Sdim
441221345Sdim    public:
442221345Sdim      // Constructors/Destructors:
443221345Sdim      /**
444221345Sdim       *  @brief  Default constructor.
445221345Sdim       *
446221345Sdim       *  Initializes @c sb using its default constructor, and passes
447221345Sdim       *  @c &sb to the base class initializer.  Does not open any files
448200583Srdivacky       *  (you haven't given it a filename to open).
449200583Srdivacky      */
450198092Srdivacky      basic_ifstream() : __istream_type(), _M_filebuf()
451198092Srdivacky      { this->init(&_M_filebuf); }
452198092Srdivacky
453223017Sdim      /**
454223017Sdim       *  @brief  Create an input file stream.
455223017Sdim       *  @param  s  Null terminated string specifying the filename.
456223017Sdim       *  @param  mode  Open file in specified mode (see std::ios_base).
457223017Sdim       *
458223017Sdim       *  @c ios_base::in is automatically included in @a mode.
459223017Sdim       *
460223017Sdim       *  Tip:  When using std::string to hold the filename, you must use
461223017Sdim       *  .c_str() before passing it to this constructor.
462223017Sdim      */
463223017Sdim      explicit
464223017Sdim      basic_ifstream(const char* __s, ios_base::openmode __mode = ios_base::in)
465223017Sdim      : __istream_type(), _M_filebuf()
466223017Sdim      {
467223017Sdim	this->init(&_M_filebuf);
468223017Sdim	this->open(__s, __mode);
469223017Sdim      }
470223017Sdim
471223017Sdim      /**
472223017Sdim       *  @brief  The destructor does nothing.
473223017Sdim       *
474223017Sdim       *  The file is closed by the filebuf object, not the formatting
475223017Sdim       *  stream.
476223017Sdim      */
477223017Sdim      ~basic_ifstream()
478223017Sdim      { }
479223017Sdim
480223017Sdim      // Members:
481223017Sdim      /**
482223017Sdim       *  @brief  Accessing the underlying buffer.
483223017Sdim       *  @return  The current basic_filebuf buffer.
484203955Srdivacky       *
485223017Sdim       *  This hides both signatures of std::basic_ios::rdbuf().
486223017Sdim      */
487223017Sdim      __filebuf_type*
488223017Sdim      rdbuf() const
489223017Sdim      { return const_cast<__filebuf_type*>(&_M_filebuf); }
490223017Sdim
491223017Sdim      /**
492223017Sdim       *  @brief  Wrapper to test for an open file.
493223017Sdim       *  @return  @c rdbuf()->is_open()
494223017Sdim      */
495223017Sdim      bool
496223017Sdim      is_open()
497223017Sdim      { return _M_filebuf.is_open(); }
498223017Sdim
499223017Sdim      // _GLIBCXX_RESOLVE_LIB_DEFECTS
500223017Sdim      // 365. Lack of const-qualification in clause 27
501223017Sdim      bool
502223017Sdim      is_open() const
503223017Sdim      { return _M_filebuf.is_open(); }
504223017Sdim
505223017Sdim      /**
506223017Sdim       *  @brief  Opens an external file.
507223017Sdim       *  @param  s  The name of the file.
508223017Sdim       *  @param  mode  The open mode flags.
509223017Sdim       *
510203955Srdivacky       *  Calls @c std::basic_filebuf::open(s,mode|in).  If that function
511198092Srdivacky       *  fails, @c failbit is set in the stream's error state.
512198092Srdivacky       *
513223017Sdim       *  Tip:  When using std::string to hold the filename, you must use
514198092Srdivacky       *  .c_str() before passing it to this constructor.
515198092Srdivacky      */
516198092Srdivacky      void
517198092Srdivacky      open(const char* __s, ios_base::openmode __mode = ios_base::in)
518193326Sed      {
519218893Sdim	if (!_M_filebuf.open(__s, __mode | ios_base::in))
520193326Sed	  this->setstate(ios_base::failbit);
521193326Sed	else
522193326Sed	  // _GLIBCXX_RESOLVE_LIB_DEFECTS
523193326Sed	  // 409. Closing an fstream should clear error state
524193326Sed	  this->clear();
525193326Sed      }
526223017Sdim
527193326Sed      /**
528223017Sdim       *  @brief  Close the file.
529193326Sed       *
530193326Sed       *  Calls @c std::basic_filebuf::close().  If that function
531193326Sed       *  fails, @c failbit is set in the stream's error state.
532193326Sed      */
533193326Sed      void
534193326Sed      close()
535193326Sed      {
536193326Sed	if (!_M_filebuf.close())
537193326Sed	  this->setstate(ios_base::failbit);
538193326Sed      }
539193326Sed    };
540193326Sed
541193326Sed
542193326Sed  // [27.8.1.8] Template class basic_ofstream
543193326Sed  /**
544195341Sed   *  @brief  Controlling output for files.
545193326Sed   *
546193326Sed   *  This class supports reading from named files, using the inherited
547193326Sed   *  functions from std::basic_ostream.  To control the associated
548193326Sed   *  sequence, an instance of std::basic_filebuf is used, which this page
549193326Sed   *  refers to as @c sb.
550193326Sed  */
551193326Sed  template<typename _CharT, typename _Traits>
552193326Sed    class basic_ofstream : public basic_ostream<_CharT,_Traits>
553193326Sed    {
554193326Sed    public:
555193326Sed      // Types:
556193326Sed      typedef _CharT 					char_type;
557193326Sed      typedef _Traits 					traits_type;
558193326Sed      typedef typename traits_type::int_type 		int_type;
559193326Sed      typedef typename traits_type::pos_type 		pos_type;
560193326Sed      typedef typename traits_type::off_type 		off_type;
561223017Sdim
562223017Sdim      // Non-standard types:
563223017Sdim      typedef basic_filebuf<char_type, traits_type> 	__filebuf_type;
564223017Sdim      typedef basic_ostream<char_type, traits_type>	__ostream_type;
565223017Sdim
566223017Sdim    private:
567193326Sed      __filebuf_type	_M_filebuf;
568193326Sed
569218893Sdim    public:
570218893Sdim      // Constructors:
571218893Sdim      /**
572218893Sdim       *  @brief  Default constructor.
573218893Sdim       *
574193326Sed       *  Initializes @c sb using its default constructor, and passes
575212904Sdim       *  @c &sb to the base class initializer.  Does not open any files
576193326Sed       *  (you haven't given it a filename to open).
577193326Sed      */
578193326Sed      basic_ofstream(): __ostream_type(), _M_filebuf()
579193326Sed      { this->init(&_M_filebuf); }
580193326Sed
581193326Sed      /**
582193326Sed       *  @brief  Create an output file stream.
583198893Srdivacky       *  @param  s  Null terminated string specifying the filename.
584193326Sed       *  @param  mode  Open file in specified mode (see std::ios_base).
585193326Sed       *
586193326Sed       *  @c ios_base::out|ios_base::trunc is automatically included in
587221345Sdim       *  @a mode.
588221345Sdim       *
589193326Sed       *  Tip:  When using std::string to hold the filename, you must use
590193326Sed       *  .c_str() before passing it to this constructor.
591218893Sdim      */
592218893Sdim      explicit
593218893Sdim      basic_ofstream(const char* __s,
594218893Sdim		     ios_base::openmode __mode = ios_base::out|ios_base::trunc)
595218893Sdim      : __ostream_type(), _M_filebuf()
596218893Sdim      {
597193326Sed	this->init(&_M_filebuf);
598193326Sed	this->open(__s, __mode);
599193326Sed      }
600193326Sed
601193326Sed      /**
602193326Sed       *  @brief  The destructor does nothing.
603193326Sed       *
604193326Sed       *  The file is closed by the filebuf object, not the formatting
605193326Sed       *  stream.
606193326Sed      */
607193326Sed      ~basic_ofstream()
608193326Sed      { }
609193326Sed
610193326Sed      // Members:
611193326Sed      /**
612221345Sdim       *  @brief  Accessing the underlying buffer.
613221345Sdim       *  @return  The current basic_filebuf buffer.
614221345Sdim       *
615221345Sdim       *  This hides both signatures of std::basic_ios::rdbuf().
616221345Sdim      */
617221345Sdim      __filebuf_type*
618221345Sdim      rdbuf() const
619221345Sdim      { return const_cast<__filebuf_type*>(&_M_filebuf); }
620193326Sed
621193326Sed      /**
622193326Sed       *  @brief  Wrapper to test for an open file.
623193326Sed       *  @return  @c rdbuf()->is_open()
624207619Srdivacky      */
625193326Sed      bool
626193326Sed      is_open()
627193326Sed      { return _M_filebuf.is_open(); }
628193326Sed
629193326Sed      // _GLIBCXX_RESOLVE_LIB_DEFECTS
630193326Sed      // 365. Lack of const-qualification in clause 27
631193326Sed      bool
632193326Sed      is_open() const
633207619Srdivacky      { return _M_filebuf.is_open(); }
634193326Sed
635193326Sed      /**
636193326Sed       *  @brief  Opens an external file.
637207619Srdivacky       *  @param  s  The name of the file.
638193326Sed       *  @param  mode  The open mode flags.
639193326Sed       *
640207619Srdivacky       *  Calls @c std::basic_filebuf::open(s,mode|out|trunc).  If that
641193326Sed       *  function fails, @c failbit is set in the stream's error state.
642193326Sed       *
643193326Sed       *  Tip:  When using std::string to hold the filename, you must use
644193326Sed       *  .c_str() before passing it to this constructor.
645207619Srdivacky      */
646207619Srdivacky      void
647198092Srdivacky      open(const char* __s,
648193326Sed	   ios_base::openmode __mode = ios_base::out | ios_base::trunc)
649193326Sed      {
650193326Sed	if (!_M_filebuf.open(__s, __mode | ios_base::out))
651193326Sed	  this->setstate(ios_base::failbit);
652198092Srdivacky	else
653198092Srdivacky	  // _GLIBCXX_RESOLVE_LIB_DEFECTS
654193326Sed	  // 409. Closing an fstream should clear error state
655193326Sed	  this->clear();
656193326Sed      }
657193326Sed
658193326Sed      /**
659193326Sed       *  @brief  Close the file.
660198092Srdivacky       *
661198092Srdivacky       *  Calls @c std::basic_filebuf::close().  If that function
662198092Srdivacky       *  fails, @c failbit is set in the stream's error state.
663198092Srdivacky      */
664221345Sdim      void
665221345Sdim      close()
666221345Sdim      {
667193326Sed	if (!_M_filebuf.close())
668193326Sed	  this->setstate(ios_base::failbit);
669193326Sed      }
670193326Sed    };
671193326Sed
672193326Sed
673193326Sed  // [27.8.1.11] Template class basic_fstream
674193326Sed  /**
675198092Srdivacky   *  @brief  Controlling intput and output for files.
676193326Sed   *
677193326Sed   *  This class supports reading from and writing to named files, using
678193326Sed   *  the inherited functions from std::basic_iostream.  To control the
679193326Sed   *  associated sequence, an instance of std::basic_filebuf is used, which
680193326Sed   *  this page refers to as @c sb.
681193326Sed  */
682193326Sed  template<typename _CharT, typename _Traits>
683193326Sed    class basic_fstream : public basic_iostream<_CharT, _Traits>
684193326Sed    {
685193326Sed    public:
686193326Sed      // Types:
687193326Sed      typedef _CharT 					char_type;
688193326Sed      typedef _Traits 					traits_type;
689193326Sed      typedef typename traits_type::int_type 		int_type;
690193326Sed      typedef typename traits_type::pos_type 		pos_type;
691193326Sed      typedef typename traits_type::off_type 		off_type;
692193326Sed
693193326Sed      // Non-standard types:
694195341Sed      typedef basic_filebuf<char_type, traits_type> 	__filebuf_type;
695193326Sed      typedef basic_ios<char_type, traits_type>		__ios_type;
696193326Sed      typedef basic_iostream<char_type, traits_type>	__iostream_type;
697221345Sdim
698193576Sed    private:
699198092Srdivacky      __filebuf_type	_M_filebuf;
700193576Sed
701193576Sed    public:
702193576Sed      // Constructors/destructor:
703193576Sed      /**
704198092Srdivacky       *  @brief  Default constructor.
705193576Sed       *
706198092Srdivacky       *  Initializes @c sb using its default constructor, and passes
707193576Sed       *  @c &sb to the base class initializer.  Does not open any files
708198092Srdivacky       *  (you haven't given it a filename to open).
709193576Sed      */
710193576Sed      basic_fstream()
711193576Sed      : __iostream_type(), _M_filebuf()
712193576Sed      { this->init(&_M_filebuf); }
713193576Sed
714194179Sed      /**
715194179Sed       *  @brief  Create an input/output file stream.
716198092Srdivacky       *  @param  s  Null terminated string specifying the filename.
717221345Sdim       *  @param  mode  Open file in specified mode (see std::ios_base).
718193576Sed       *
719193576Sed       *  Tip:  When using std::string to hold the filename, you must use
720193576Sed       *  .c_str() before passing it to this constructor.
721193576Sed      */
722193576Sed      explicit
723198092Srdivacky      basic_fstream(const char* __s,
724193576Sed		    ios_base::openmode __mode = ios_base::in | ios_base::out)
725193576Sed      : __iostream_type(NULL), _M_filebuf()
726193576Sed      {
727218893Sdim	this->init(&_M_filebuf);
728218893Sdim	this->open(__s, __mode);
729218893Sdim      }
730193576Sed
731193576Sed      /**
732193576Sed       *  @brief  The destructor does nothing.
733193576Sed       *
734198092Srdivacky       *  The file is closed by the filebuf object, not the formatting
735193576Sed       *  stream.
736193576Sed      */
737198092Srdivacky      ~basic_fstream()
738193576Sed      { }
739193576Sed
740221345Sdim      // Members:
741221345Sdim      /**
742221345Sdim       *  @brief  Accessing the underlying buffer.
743221345Sdim       *  @return  The current basic_filebuf buffer.
744193576Sed       *
745193576Sed       *  This hides both signatures of std::basic_ios::rdbuf().
746198092Srdivacky      */
747193576Sed      __filebuf_type*
748193576Sed      rdbuf() const
749221345Sdim      { return const_cast<__filebuf_type*>(&_M_filebuf); }
750221345Sdim
751218893Sdim      /**
752218893Sdim       *  @brief  Wrapper to test for an open file.
753218893Sdim       *  @return  @c rdbuf()->is_open()
754218893Sdim      */
755210299Sed      bool
756210299Sed      is_open()
757210299Sed      { return _M_filebuf.is_open(); }
758193326Sed
759193326Sed      // _GLIBCXX_RESOLVE_LIB_DEFECTS
760193326Sed      // 365. Lack of const-qualification in clause 27
761193326Sed      bool
762193326Sed      is_open() const
763193326Sed      { return _M_filebuf.is_open(); }
764193326Sed
765193326Sed      /**
766193326Sed       *  @brief  Opens an external file.
767193326Sed       *  @param  s  The name of the file.
768193326Sed       *  @param  mode  The open mode flags.
769207619Srdivacky       *
770193326Sed       *  Calls @c std::basic_filebuf::open(s,mode).  If that
771193326Sed       *  function fails, @c failbit is set in the stream's error state.
772193326Sed       *
773193326Sed       *  Tip:  When using std::string to hold the filename, you must use
774193326Sed       *  .c_str() before passing it to this constructor.
775193326Sed      */
776198092Srdivacky      void
777193326Sed      open(const char* __s,
778193326Sed	   ios_base::openmode __mode = ios_base::in | ios_base::out)
779193326Sed      {
780198092Srdivacky	if (!_M_filebuf.open(__s, __mode))
781193326Sed	  this->setstate(ios_base::failbit);
782193326Sed	else
783193326Sed	  // _GLIBCXX_RESOLVE_LIB_DEFECTS
784193326Sed	  // 409. Closing an fstream should clear error state
785198092Srdivacky	  this->clear();
786193326Sed      }
787193326Sed
788207619Srdivacky      /**
789193326Sed       *  @brief  Close the file.
790193326Sed       *
791198092Srdivacky       *  Calls @c std::basic_filebuf::close().  If that function
792193326Sed       *  fails, @c failbit is set in the stream's error state.
793193326Sed      */
794198092Srdivacky      void
795193326Sed      close()
796193326Sed      {
797198092Srdivacky	if (!_M_filebuf.close())
798193326Sed	  this->setstate(ios_base::failbit);
799193326Sed      }
800193326Sed    };
801193326Sed
802193326Sed_GLIBCXX_END_NAMESPACE
803193326Sed
804193326Sed#ifndef _GLIBCXX_EXPORT_TEMPLATE
805193326Sed# include <bits/fstream.tcc>
806193326Sed#endif
807193326Sed
808193326Sed#endif /* _GLIBCXX_FSTREAM */
809193326Sed