home *** CD-ROM | disk | FTP | other *** search
/ H4CK3R 14 / hacker14.iso / programacao / cwin / c.exe / $INSTDIR / include / c++ / streambuf < prev    next >
Encoding:
Text File  |  2003-12-15  |  13.9 KB  |  502 lines

  1. // Stream buffer classes -*- C++ -*-
  2.  
  3. // Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002
  4. // Free Software Foundation, Inc.
  5. //
  6. // This file is part of the GNU ISO C++ Library.  This library is free
  7. // software; you can redistribute it and/or modify it under the
  8. // terms of the GNU General Public License as published by the
  9. // Free Software Foundation; either version 2, or (at your option)
  10. // any later version.
  11.  
  12. // This library is distributed in the hope that it will be useful,
  13. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  14. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  15. // GNU General Public License for more details.
  16.  
  17. // You should have received a copy of the GNU General Public License along
  18. // with this library; see the file COPYING.  If not, write to the Free
  19. // Software Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307,
  20. // USA.
  21.  
  22. // As a special exception, you may use this file as part of a free software
  23. // library without restriction.  Specifically, if other files instantiate
  24. // templates or use macros or inline functions from this file, or you compile
  25. // this file and link it with other files to produce an executable, this
  26. // file does not by itself cause the resulting executable to be covered by
  27. // the GNU General Public License.  This exception does not however
  28. // invalidate any other reasons why the executable file might be covered by
  29. // the GNU General Public License.
  30.  
  31. //
  32. // ISO C++ 14882: 27.5  Stream buffers
  33. //
  34.  
  35. /** @file streambuf
  36.  *  This is a Standard C++ Library header.  You should @c #include this header
  37.  *  in your programs, rather than any of the "st[dl]_*.h" implementation files.
  38.  */
  39.  
  40. #ifndef _CPP_STREAMBUF
  41. #define _CPP_STREAMBUF    1
  42.  
  43. #pragma GCC system_header
  44.  
  45. #include <bits/c++config.h>
  46. #include <iosfwd>
  47. #include <cstdio>     // For SEEK_SET, SEEK_CUR, SEEK_END
  48. #include <bits/localefwd.h>
  49. #include <bits/ios_base.h>
  50.  
  51. namespace std
  52. {
  53.   template<typename _CharT, typename _Traits>
  54.     streamsize
  55.     __copy_streambufs(basic_ios<_CharT, _Traits>& _ios,
  56.               basic_streambuf<_CharT, _Traits>* __sbin,
  57.               basic_streambuf<_CharT, _Traits>* __sbout);
  58.   
  59.   // 27.5.2 Template class basic_streambuf<_CharT, _Traits>
  60.   template<typename _CharT, typename _Traits>
  61.     class basic_streambuf 
  62.     {
  63.     public:
  64.       // Types:
  65.       typedef _CharT                     char_type;
  66.       typedef _Traits                     traits_type;
  67.       typedef typename traits_type::int_type         int_type;
  68.       typedef typename traits_type::pos_type         pos_type;
  69.       typedef typename traits_type::off_type         off_type;
  70.  
  71.       // Non-standard Types:
  72.       typedef ctype<char_type>                   __ctype_type;
  73.       typedef basic_streambuf<char_type, traits_type>      __streambuf_type;
  74.       typedef typename traits_type::state_type         __state_type;
  75.       
  76.       friend class basic_ios<char_type, traits_type>;
  77.       friend class basic_istream<char_type, traits_type>;
  78.       friend class basic_ostream<char_type, traits_type>;
  79.       friend class istreambuf_iterator<char_type, traits_type>;
  80.       friend class ostreambuf_iterator<char_type, traits_type>;
  81.  
  82.       friend streamsize
  83.       __copy_streambufs<>(basic_ios<char_type, traits_type>& __ios,
  84.               __streambuf_type* __sbin,__streambuf_type* __sbout);
  85.       
  86.     protected:
  87.       // Pointer to the beginning of internally-allocated
  88.       // space. Filebuf manually allocates/deallocates this, whereas
  89.       // stringstreams attempt to use the built-in intelligence of the
  90.       // string class. If you are managing memory, set this. If not,
  91.       // leave it NULL.
  92.       char_type*        _M_buf;     
  93.  
  94.       // Actual size of allocated internal buffer, in bytes.
  95.       size_t            _M_buf_size;
  96.  
  97.       // Optimal or preferred size of internal buffer, in bytes.
  98.       size_t            _M_buf_size_opt;
  99.  
  100.       // True iff _M_in_* and _M_out_* buffers should always point to
  101.       // the same place.  True for fstreams, false for sstreams.
  102.       bool             _M_buf_unified;    
  103.  
  104.       // This is based on _IO_FILE, just reordered to be more
  105.       // consistent, and is intended to be the most minimal abstraction
  106.       // for an internal buffer.
  107.       // get == input == read
  108.       // put == output == write
  109.       char_type*         _M_in_beg;      // Start of get area. 
  110.       char_type*         _M_in_cur;    // Current read area. 
  111.       char_type*         _M_in_end;    // End of get area. 
  112.       char_type*         _M_out_beg;     // Start of put area. 
  113.       char_type*         _M_out_cur;      // Current put area. 
  114.       char_type*         _M_out_end;      // End of put area. 
  115.  
  116.       // Place to stash in || out || in | out settings for current streambuf.
  117.       ios_base::openmode     _M_mode;    
  118.  
  119.       // Current locale setting.
  120.       locale             _M_buf_locale;    
  121.  
  122.       // True iff locale is initialized.
  123.       bool             _M_buf_locale_init;
  124.  
  125.       // Necessary bits for putback buffer management. Only used in
  126.       // the basic_filebuf class, as necessary for the standard
  127.       // requirements. The only basic_streambuf member function that
  128.       // needs access to these data members is in_avail...
  129.       // NB: pbacks of over one character are not currently supported.
  130.       static const size_t       _S_pback_size = 1; 
  131.       char_type            _M_pback[_S_pback_size]; 
  132.       char_type*        _M_pback_cur_save;
  133.       char_type*        _M_pback_end_save;
  134.       bool            _M_pback_init; 
  135.  
  136.       // Yet unused.
  137.       fpos<__state_type>    _M_pos;
  138.  
  139.       // Initializes pback buffers, and moves normal buffers to safety.
  140.       // Assumptions:
  141.       // _M_in_cur has already been moved back
  142.       void
  143.       _M_pback_create()
  144.       {
  145.     if (!_M_pback_init)
  146.       {
  147.         size_t __dist = _M_in_end - _M_in_cur;
  148.         size_t __len = min(_S_pback_size, __dist);
  149.         traits_type::copy(_M_pback, _M_in_cur, __len);
  150.         _M_pback_cur_save = _M_in_cur;
  151.         _M_pback_end_save = _M_in_end;
  152.         this->setg(_M_pback, _M_pback, _M_pback + __len);
  153.         _M_pback_init = true;
  154.       }
  155.       }
  156.  
  157.       // Deactivates pback buffer contents, and restores normal buffer.
  158.       // Assumptions:
  159.       // The pback buffer has only moved forward.
  160.       void
  161.       _M_pback_destroy()
  162.       {
  163.     if (_M_pback_init)
  164.       {
  165.         // Length _M_in_cur moved in the pback buffer.
  166.         size_t __off_cur = _M_in_cur - _M_pback;
  167.         
  168.         // For in | out buffers, the end can be pushed back...
  169.         size_t __off_end = 0;
  170.         size_t __pback_len = _M_in_end - _M_pback;
  171.         size_t __save_len = _M_pback_end_save - _M_buf;
  172.         if (__pback_len > __save_len)
  173.           __off_end = __pback_len - __save_len;
  174.  
  175.         this->setg(_M_buf, _M_pback_cur_save + __off_cur, 
  176.                _M_pback_end_save + __off_end);
  177.         _M_pback_cur_save = NULL;
  178.         _M_pback_end_save = NULL;
  179.         _M_pback_init = false;
  180.       }
  181.       }
  182.  
  183.       // Correctly sets the _M_in_cur pointer, and bumps the
  184.       // _M_out_cur pointer as well if necessary.
  185.       void 
  186.       _M_in_cur_move(off_type __n) // argument needs to be +-
  187.       {
  188.     bool __testout = _M_out_cur;
  189.     _M_in_cur += __n;
  190.     if (__testout && _M_buf_unified)
  191.       _M_out_cur += __n;
  192.       }
  193.  
  194.       // Correctly sets the _M_out_cur pointer, and bumps the
  195.       // appropriate _M_*_end pointers as well. Necessary for the
  196.       // un-tied stringbufs, in in|out mode.
  197.       // Invariant:
  198.       // __n + _M_out_[cur, end] <= _M_buf + _M_buf_size
  199.       // Assuming all _M_*_[beg, cur, end] pointers are operating on
  200.       // the same range:
  201.       // _M_buf <= _M_*_ <= _M_buf + _M_buf_size
  202.       void 
  203.       _M_out_cur_move(off_type __n) // argument needs to be +-
  204.       {
  205.     bool __testin = _M_in_cur;
  206.  
  207.     _M_out_cur += __n;
  208.     if (__testin && _M_buf_unified)
  209.       _M_in_cur += __n;
  210.     if (_M_out_cur > _M_out_end)
  211.       {
  212.         _M_out_end = _M_out_cur;
  213.         // NB: in | out buffers drag the _M_in_end pointer along...
  214.         if (__testin)
  215.           _M_in_end += __n;
  216.       }
  217.       }
  218.  
  219.       // Return the size of the output buffer.  This depends on the
  220.       // buffer in use: allocated buffers have a stored size in
  221.       // _M_buf_size and setbuf() buffers don't.
  222.       off_type
  223.       _M_out_buf_size()
  224.       {
  225.     off_type __ret = 0;
  226.     if (_M_out_cur)
  227.       {
  228.         // Using allocated buffer.
  229.         if (_M_out_beg == _M_buf)
  230.           __ret = _M_out_beg + _M_buf_size - _M_out_cur;
  231.         // Using non-allocated buffer.
  232.         else
  233.           __ret = _M_out_end - _M_out_cur;
  234.       }
  235.     return __ret;
  236.       }
  237.  
  238.   public:
  239.       virtual 
  240.       ~basic_streambuf() 
  241.       {
  242.     _M_buf_unified = false;
  243.     _M_buf_size = 0;
  244.     _M_buf_size_opt = 0;
  245.     _M_mode = ios_base::openmode(0);
  246.     _M_buf_locale_init = false;
  247.       }
  248.  
  249.       // Locales:
  250.       locale 
  251.       pubimbue(const locale &__loc)
  252.       {
  253.     locale __tmp(this->getloc());
  254.     this->imbue(__loc);
  255.     return __tmp;
  256.       }
  257.  
  258.       locale   
  259.       getloc() const
  260.       {
  261.     if (_M_buf_locale_init)
  262.       return _M_buf_locale; 
  263.     else 
  264.       return locale();
  265.       } 
  266.  
  267.       // Buffer and positioning:
  268.       __streambuf_type* 
  269.       pubsetbuf(char_type* __s, streamsize __n) 
  270.       { return this->setbuf(__s, __n); }
  271.  
  272.       pos_type 
  273.       pubseekoff(off_type __off, ios_base::seekdir __way, 
  274.          ios_base::openmode __mode = ios_base::in | ios_base::out)
  275.       { return this->seekoff(__off, __way, __mode); }
  276.  
  277.       pos_type 
  278.       pubseekpos(pos_type __sp,
  279.          ios_base::openmode __mode = ios_base::in | ios_base::out)
  280.       { return this->seekpos(__sp, __mode); }
  281.  
  282.       int 
  283.       pubsync() { return this->sync(); }
  284.  
  285.       // Get and put areas:
  286.       // Get area:
  287.       streamsize 
  288.       in_avail() 
  289.       { 
  290.     streamsize __ret;
  291.     if (_M_in_cur && _M_in_cur < _M_in_end)
  292.       {
  293.         if (_M_pback_init)
  294.           {
  295.         size_t __save_len =  _M_pback_end_save - _M_pback_cur_save;
  296.         size_t __pback_len = _M_in_cur - _M_pback;
  297.         __ret = __save_len - __pback_len;
  298.           }
  299.         else
  300.           __ret = this->egptr() - this->gptr();
  301.       }
  302.     else
  303.       __ret = this->showmanyc();
  304.     return __ret;
  305.       }
  306.  
  307.       int_type 
  308.       snextc()
  309.       {
  310.     int_type __eof = traits_type::eof();
  311.     return (traits_type::eq_int_type(this->sbumpc(), __eof) 
  312.         ? __eof : this->sgetc());
  313.       }
  314.  
  315.       int_type 
  316.       sbumpc();
  317.  
  318.       int_type 
  319.       sgetc()
  320.       {
  321.     int_type __ret;
  322.     if (_M_in_cur && _M_in_cur < _M_in_end)
  323.       __ret = traits_type::to_int_type(*(this->gptr()));
  324.     else 
  325.       __ret = this->underflow();
  326.     return __ret;
  327.       }
  328.  
  329.       streamsize 
  330.       sgetn(char_type* __s, streamsize __n)
  331.       { return this->xsgetn(__s, __n); }
  332.  
  333.       // Putback:
  334.       int_type 
  335.       sputbackc(char_type __c);
  336.  
  337.       int_type 
  338.       sungetc();
  339.  
  340.       // Put area:
  341.       int_type 
  342.       sputc(char_type __c);
  343.  
  344.       streamsize 
  345.       sputn(const char_type* __s, streamsize __n)
  346.       { return this->xsputn(__s, __n); }
  347.  
  348.     protected:
  349.       basic_streambuf()
  350.       : _M_buf(NULL), _M_buf_size(0), _M_buf_size_opt(BUFSIZ), 
  351.       _M_buf_unified(false), _M_in_beg(0), _M_in_cur(0), _M_in_end(0), 
  352.       _M_out_beg(0), _M_out_cur(0), _M_out_end(0), 
  353.       _M_mode(ios_base::openmode(0)), _M_buf_locale(locale()), 
  354.       _M_buf_locale_init(false), _M_pback_cur_save(0), _M_pback_end_save(0), 
  355.       _M_pback_init(false)
  356.       { }
  357.  
  358.       // Get area:
  359.       char_type* 
  360.       eback() const { return _M_in_beg; }
  361.  
  362.       char_type* 
  363.       gptr()  const { return _M_in_cur;  }
  364.  
  365.       char_type* 
  366.       egptr() const { return _M_in_end; }
  367.  
  368.       void 
  369.       gbump(int __n) { _M_in_cur += __n; }
  370.  
  371.       void 
  372.       setg(char_type* __gbeg, char_type* __gnext, char_type* __gend)
  373.       {
  374.     _M_in_beg = __gbeg;
  375.     _M_in_cur = __gnext;
  376.     _M_in_end = __gend;
  377.     if (!(_M_mode & ios_base::in) && __gbeg && __gnext && __gend)
  378.       _M_mode = _M_mode | ios_base::in;
  379.       }
  380.  
  381.       // Put area:
  382.       char_type* 
  383.       pbase() const { return _M_out_beg; }
  384.  
  385.       char_type* 
  386.       pptr() const { return _M_out_cur; }
  387.  
  388.       char_type* 
  389.       epptr() const { return _M_out_end; }
  390.  
  391.       void 
  392.       pbump(int __n) { _M_out_cur += __n; }
  393.  
  394.       void 
  395.       setp(char_type* __pbeg, char_type* __pend)
  396.       { 
  397.     _M_out_beg = _M_out_cur = __pbeg; 
  398.     _M_out_end = __pend; 
  399.     if (!(_M_mode & ios_base::out) && __pbeg && __pend)
  400.       _M_mode = _M_mode | ios_base::out;
  401.       }
  402.  
  403.       // Virtual functions:
  404.       // Locales:
  405.       virtual void 
  406.       imbue(const locale& __loc) 
  407.       { 
  408.     _M_buf_locale_init = true;
  409.     if (_M_buf_locale != __loc)
  410.       _M_buf_locale = __loc;
  411.       }
  412.  
  413.       // Buffer management and positioning:
  414.       virtual basic_streambuf<char_type,_Traits>* 
  415.       setbuf(char_type*, streamsize)
  416.       {    return this; }
  417.       
  418.       virtual pos_type 
  419.       seekoff(off_type, ios_base::seekdir,
  420.           ios_base::openmode /*__mode*/ = ios_base::in | ios_base::out)
  421.       { return pos_type(off_type(-1)); } 
  422.  
  423.       virtual pos_type 
  424.       seekpos(pos_type, 
  425.           ios_base::openmode /*__mode*/ = ios_base::in | ios_base::out)
  426.       { return pos_type(off_type(-1)); } 
  427.  
  428.       virtual int 
  429.       sync() { return 0; }
  430.  
  431.       // Get area:
  432.       virtual streamsize 
  433.       showmanyc() { return 0; }
  434.  
  435.       virtual streamsize 
  436.       xsgetn(char_type* __s, streamsize __n);
  437.  
  438.       virtual int_type 
  439.       underflow()
  440.       { return traits_type::eof(); }
  441.  
  442.       virtual int_type 
  443.       uflow() 
  444.       {
  445.     int_type __ret = traits_type::eof();
  446.     bool __testeof = traits_type::eq_int_type(this->underflow(), __ret);
  447.     bool __testpending = _M_in_cur && _M_in_cur < _M_in_end;
  448.     if (!__testeof && __testpending)
  449.       {
  450.         __ret = traits_type::to_int_type(*_M_in_cur);
  451.         ++_M_in_cur;
  452.         if (_M_buf_unified && _M_mode & ios_base::out)
  453.           ++_M_out_cur;
  454.       }
  455.     return __ret;    
  456.       }
  457.  
  458.       // Putback:
  459.       virtual int_type 
  460.       pbackfail(int_type /* __c */  = traits_type::eof())
  461.       { return traits_type::eof(); }
  462.  
  463.       // Put area:
  464.       virtual streamsize 
  465.       xsputn(const char_type* __s, streamsize __n);
  466.  
  467.       virtual int_type 
  468.       overflow(int_type /* __c */ = traits_type::eof())
  469.       { return traits_type::eof(); }
  470.  
  471. #ifdef _GLIBCPP_DEPRECATED
  472.     public:
  473.       void 
  474.       stossc() 
  475.       {
  476.     if (_M_in_cur < _M_in_end) 
  477.       ++_M_in_cur;
  478.     else 
  479.       this->uflow();
  480.       }
  481. #endif
  482.  
  483. #ifdef _GLIBCPP_RESOLVE_LIB_DEFECTS
  484.     // Side effect of DR 50. 
  485.     private:
  486.       basic_streambuf(const __streambuf_type&) { }; 
  487.  
  488.       __streambuf_type& 
  489.       operator=(const __streambuf_type&) { return *this; };
  490. #endif
  491.     };
  492. } // namespace std
  493.  
  494. #ifdef _GLIBCPP_NO_TEMPLATE_EXPORT
  495. # define export
  496. #endif
  497. #ifdef  _GLIBCPP_FULLY_COMPLIANT_HEADERS
  498. #include <bits/streambuf.tcc>
  499. #endif
  500.  
  501. #endif    
  502.