#include <Streambuf.h>
Inheritance diagram for ASSA::Streambuf:
Public Member Functions | |
virtual | ~Streambuf () |
Streambuf * | pubsetbuf (char *s_, int n_) |
Set buffer. | |
int | pubsync () |
int | in_avail () |
This function returns the number of characters immediately available in the get area. | |
int | snextc () |
This function moves the get pointer forward one position, then returns the character after the get pointer's new position. | |
int | sbumpc () |
This function should probably have been called ``sgetc''. | |
int | sgetc () |
This function returns the character after the get pointer, or EOF if the get pointer is at the end of the sequence. | |
int | sgetn (char *b_, int len_) |
This function gets the next len_ characters following the get pointer, copying them to the char array pointed to by b_; it advances the get pointer past the last character fetched. | |
int | sputc (char c_) |
This function stores c just after the put pointer, and advances the pointer one position, possibly extending the sequence. | |
int | sputn (char *b_, int len_) |
From the location pointed to by ptr, stores exactly len characters after the put pointer, advancing the put pointer just past the last character. | |
void | unbuffered (int i_) |
If i_ is non-zero, then all IO operations are buffered. | |
int | unbuffered () |
Protected Member Functions | |
Streambuf () | |
The default constructor is protected for class Streambuf to asssure that only objects for classes derived from this class may be constructed. | |
Streambuf (const Streambuf &) | |
Streambuf & | operator= (const Streambuf &) |
char * | base () const |
Returns the lowest possible value for gptr() - the beginning of the get area. | |
char * | gptr () const |
Returns a pointer to the beginning of the get area, and thus to the next character to be fetched (if there are any). | |
char * | egptr () const |
Returns a pointer just past the end of the get area, the maximum possible value for gptr(). | |
void | setg (char *gbeg_, char *gnext_, char *gend_) |
Set get area pointers. | |
char * | pbase () const |
Returns a pointer to the beginning fo the space available for the put area, the lowest possible value for pptr(). | |
char * | pptr () const |
Returns a pointer to the beginning of the put area, and thus to the location of the next character that is stored (if possible). | |
char * | epptr () const |
Returns a pointer just past the end of the put area, the maximum possible value for pptr(). | |
void | setp (char *pbeg_, char *pend_) |
Set put area pointers. | |
void | pbump (int n_) |
Advances the next pointer for the output sequence by n_. | |
void | setb (char *b_, char *eb_, int del_) |
Establish the reserve area (buffer). | |
void | init () |
virtual Streambuf * | setbuf (char *p_, int len_) |
Performs an operation that is defined separately for each class derived from Streambuf. | |
virtual int | sync () |
This function synchronizes the streambuf with its actual stream of characters. | |
virtual int | showmanyc () |
The morphemes of showmanyc are "es-how-many-see", not "show-man-ic". | |
virtual int | xsgetn (char *b_, int len_) |
Assigns up to len_ characters to successive elements of the array whose first element is designated by b_. | |
virtual int | underflow () |
This function is called to supply characters for input (from some source) when the get area is empty, although it may be called at other times. | |
virtual int | uflow () |
Reads the characters from the input sequence, if possible, and moves the stream position past it, as follows:. | |
virtual int | xsputn (const char *b_, int len_) |
Writes up to len_ characters to the output sequence as if by repeated calls to sputc (c). | |
virtual int | overflow (int c=EOF) |
This function is called to consume characters (flush them to output), typically when the put area is full and an attempt is made to store another character. | |
virtual int | doallocate () |
This function is called by allocate when unbuffered() is zero and base() is zero. |
Streambuf class is based on Standard C++ iostream streambuf class.
Extending std::streambuf is always pain due to the obscurity and complexity of its interface, and in general, lack of the source code needed to efficiently understand its implementation.
I wrote my own Streambuf that implements a subset of std::streambuf functions - a bare minimum to get by for Socket buffering.
The buffer of a Streambuf may be considered to have three parts: the get area, the put area, and the reserve area (which is the same as the buffer area).
The get area contains the characters immediately available for input.
The put area holds characters stored for output but not yet consumed by (flushed to) their ultimate destination. The get and put areas may be disjoint or may overlap (in my implementation they are two disjoined buffers). The reserve area is the entire buffer, overlapped by the get and put areas (in my implementation, reserve area covers get area only). The get and put areas may expand into the remainder of the reserve area. In the course of input and output operations, the sizes of the get and put areas expand and shrink, always bounded by the total buffer size.
Definition at line 90 of file Streambuf.h.
|
Definition at line 442 of file Streambuf.h. References ASSA::io_ptrs::m_buf_base, ASSA::io_ptrs::m_buf_end, ASSA::io_ptrs::m_flags, ASSA::STRMBUFTRACE, trace_with_mask, and ASSA::io_ptrs::USER_BUF. 00443 { 00444 trace_with_mask("Streambuf::~Streambuf",STRMBUFTRACE); 00445 00446 if (!(m_flags & USER_BUF)) { 00447 delete [] m_buf_base; 00448 m_buf_base = m_buf_end = 0; 00449 } 00450 }
|
|
The default constructor is protected for class Streambuf to asssure that only objects for classes derived from this class may be constructed.
Definition at line 419 of file Streambuf.h. References init(), ASSA::STRMBUFTRACE, and trace_with_mask. 00420 { 00421 trace_with_mask("Streambuf::Streambuf",STRMBUFTRACE); 00422 00423 init (); 00424 }
|
|
|
|
Returns the lowest possible value for gptr() - the beginning of the get area.
Definition at line 454 of file Streambuf.h. References ASSA::io_ptrs::m_read_base, ASSA::STRMBUFTRACE, and trace_with_mask. Referenced by ASSA::Socketbuf::underflow(). 00455 { 00456 trace_with_mask("Streambuf::base",STRMBUFTRACE); 00457 00458 return m_read_base; 00459 }
|
|
This function is called by allocate when unbuffered() is zero and base() is zero. It attempts to make a buffer of suitable size available. On success it must call setb to establish the reserve area, then return a value greater than zero. On failure it returns EOF. The default behavior is to allocate a buffer using new. Reimplemented in ASSA::Socketbuf. Definition at line 249 of file Streambuf.cpp. 00250 { 00251 trace_with_mask("Streambuf::doallocate",STRMBUFTRACE); 00252 00253 char* buf; 00254 buf = new char [1024]; 00255 if (buf == NULL) { 00256 return EOF; 00257 } 00258 setb (buf, buf+1024, 1); 00259 00260 return 1; 00261 }
|
|
Returns a pointer just past the end of the get area, the maximum possible value for gptr().
Definition at line 472 of file Streambuf.h. References ASSA::io_ptrs::m_read_end, ASSA::STRMBUFTRACE, and trace_with_mask. Referenced by ASSA::Socketbuf::underflow(). 00473 { 00474 trace_with_mask("Streambuf::egptr",STRMBUFTRACE); 00475 00476 return m_read_end; 00477 }
|
|
Returns a pointer just past the end of the put area, the maximum possible value for pptr(). The space from pptr() through epptr() is immediately available for storing characters without a flush operation. Definition at line 497 of file Streambuf.h. References ASSA::io_ptrs::m_write_end, ASSA::STRMBUFTRACE, and trace_with_mask. Referenced by ASSA::Socketbuf::flush_output(), and ASSA::Socketbuf::overflow(). 00498 { 00499 trace_with_mask("Streambuf::epptr",STRMBUFTRACE); 00500 return m_write_end; 00501 }
|
|
Returns a pointer to the beginning of the get area, and thus to the next character to be fetched (if there are any). The characters immediately available are from gptr() through egptr()-1. If egptr()<=gptr(), no char- acters are available. Definition at line 463 of file Streambuf.h. References ASSA::io_ptrs::m_read_ptr, ASSA::STRMBUFTRACE, and trace_with_mask. Referenced by ASSA::Socketbuf::underflow(). 00464 { 00465 trace_with_mask("Streambuf::gptr",STRMBUFTRACE); 00466 00467 return m_read_ptr; 00468 }
|
|
This function returns the number of characters immediately available in the get area. It is certain that i characters may be fetched without error, and without accessing any external device. Definition at line 389 of file Streambuf.h. References ASSA::io_ptrs::m_read_end, ASSA::io_ptrs::m_read_ptr, ASSA::STRMBUFTRACE, and trace_with_mask. Referenced by ASSA::IPv4Socket::clone(), ASSA::IPv4Socket::close(), ASSA::Socket::getBytesAvail(), and ASSA::IPv4Socket::in_avail(). 00390 { 00391 trace_with_mask("Streambuf::in_avail",STRMBUFTRACE); 00392 00393 return m_read_end - m_read_ptr; 00394 }
|
|
Definition at line 428 of file Streambuf.h. References ASSA::io_ptrs::m_buf_base, ASSA::io_ptrs::m_buf_end, ASSA::io_ptrs::m_flags, ASSA::io_ptrs::m_read_base, ASSA::io_ptrs::m_read_end, ASSA::io_ptrs::m_read_ptr, ASSA::io_ptrs::m_shortbuf, ASSA::io_ptrs::m_write_base, ASSA::io_ptrs::m_write_end, ASSA::io_ptrs::m_write_ptr, ASSA::STRMBUFTRACE, and trace_with_mask. Referenced by Streambuf(). 00429 { 00430 trace_with_mask("Streambuf::init", STRMBUFTRACE); 00431 00432 m_read_base = m_read_ptr = m_read_end = 0; 00433 m_write_base = m_write_ptr = m_write_end = 0; 00434 m_buf_base = m_buf_end = 0; 00435 m_flags = 0; 00436 00437 m_shortbuf[0] = 0; 00438 }
|
|
|
|
This function is called to consume characters (flush them to output), typically when the put area is full and an attempt is made to store another character. If c is not EOF, overflow must either store or consume the character, following those already in the put area. It returns EOF on error, any other value on success. The default behavior of the base class version is undefined, so each derived class must define its own overflow. The normal action for a derived class version is to consume the characters in the put area (those between pbase() and pptr()), call setp() to set up a new put area, then store c (using sputc()) if it is not EOF. Reimplemented in ASSA::Socketbuf. Definition at line 597 of file Streambuf.h. References ASSA::STRMBUFTRACE, and trace_with_mask. Referenced by sputc(). 00598 { 00599 trace_with_mask("Streambuf::overflow",STRMBUFTRACE); 00600 00601 return (EOF); 00602 }
|
|
Returns a pointer to the beginning fo the space available for the put area, the lowest possible value for pptr(). The area from pbase() through pptr()-1 represents characters which have been stored int the buffer but not yet consumed. Definition at line 481 of file Streambuf.h. References ASSA::io_ptrs::m_write_base, ASSA::STRMBUFTRACE, and trace_with_mask. Referenced by ASSA::Socketbuf::flush_output(), and ASSA::Socketbuf::overflow(). 00482 { 00483 trace_with_mask("Streambuf::pbase",STRMBUFTRACE); 00484 return m_write_base; 00485 }
|
|
Advances the next pointer for the output sequence by n_.
Definition at line 505 of file Streambuf.h. References ASSA::io_ptrs::m_write_ptr, ASSA::STRMBUFTRACE, and trace_with_mask. Referenced by ASSA::Socketbuf::flush_output(), and ASSA::Socketbuf::xput_char(). 00506 { 00507 trace_with_mask("Streambuf::pbump",STRMBUFTRACE); 00508 m_write_ptr += n_; 00509 }
|
|
Returns a pointer to the beginning of the put area, and thus to the location of the next character that is stored (if possible).
Definition at line 489 of file Streambuf.h. References ASSA::io_ptrs::m_write_ptr, ASSA::STRMBUFTRACE, and trace_with_mask. Referenced by ASSA::Socketbuf::flush_output(), ASSA::Socketbuf::overflow(), and ASSA::Socketbuf::xput_char(). 00490 { 00491 trace_with_mask("Streambuf::pptr",STRMBUFTRACE); 00492 return m_write_ptr; 00493 }
|
|
Set buffer.
Definition at line 371 of file Streambuf.h. References setbuf(), ASSA::STRMBUFTRACE, and trace_with_mask. 00372 { 00373 trace_with_mask("Streambuf::pubsetbuf",STRMBUFTRACE); 00374 00375 return setbuf (s_, n_); 00376 }
|
|
Definition at line 380 of file Streambuf.h. References ASSA::STRMBUFTRACE, sync(), and trace_with_mask. 00381 { 00382 trace_with_mask("Streambuf::pubsync",STRMBUFTRACE); 00383 00384 return sync (); 00385 }
|
|
This function should probably have been called ``sgetc''. It moves the get pointer forward one posi- tion and returns the character it moved past. If the get pointer is currently at the end of the sequence, this function returns EOF. Definition at line 529 of file Streambuf.h. References ASSA::io_ptrs::m_read_end, ASSA::io_ptrs::m_read_ptr, ASSA::STRMBUFTRACE, trace_with_mask, and uflow(). Referenced by ASSA::IPv4Socket::close(), and ASSA::IPv4Socket::read(). 00530 { 00531 trace_with_mask("Streambuf::sbumpc",STRMBUFTRACE); 00532 00533 return (m_read_ptr >= m_read_end ? uflow () 00534 : *(unsigned char *) m_read_ptr++); 00535 }
|
|
Establish the reserve area (buffer). Set base() to b_, ebuf() to eb_. If del_ is non-zero, the buffer will be deleted whenever base() is changed by another call to setb(), or when Streambuf destructor is invoked. If del_ is zero, the buffer will not be deleted automatically.
Definition at line 95 of file Streambuf.cpp. Referenced by ASSA::Socketbuf::doallocate(). 00096 { 00097 trace_with_mask("Streambuf::setb",STRMBUFTRACE); 00098 00099 if (m_buf_base && !(m_flags & USER_BUF)) 00100 delete m_buf_base; 00101 00102 m_buf_base = b_; 00103 m_buf_end = eb_; 00104 00105 if (del_) 00106 m_flags &= ~ USER_BUF; // clear bit 00107 else 00108 m_flags |= USER_BUF; // set bit 00109 00110 dump (); 00111 }
|
|
Performs an operation that is defined separately for each class derived from Streambuf. Default behavior is to set internal buffer to p_. If p_ is NULL or len_ is 0, then unbuffered I/O (one byte at a time) is assumed.
Definition at line 115 of file Streambuf.cpp. Referenced by pubsetbuf(). 00116 { 00117 trace_with_mask("Streambuf::setb",STRMBUFTRACE); 00118 00119 if (sync () == EOF) // Flush out all pending bytes before 00120 return NULL; // resetting buffer. Also, first time around, 00121 // calling sync() suppose to set put area 00122 // pointers. 00123 00124 if (p_ == NULL || len_ == 0) { 00125 DL((STRMBUF,"Unbuffered IO set.\n")); 00126 unbuffered (1); 00127 // We do it from doalloc instead - vlg 00128 // setb (m_shortbuf, m_shortbuf+1, 0); 00129 } 00130 else { 00131 DL((STRMBUF,"Buffered IO set.\n")); 00132 unbuffered (0); 00133 setb (p_, p_ + len_, 0); 00134 } 00135 setp (0, 0); 00136 setg (0, 0, 0); 00137 00138 return this; 00139 }
|
|
Set get area pointers.
Definition at line 84 of file Streambuf.cpp. Referenced by ASSA::Socketbuf::doallocate(), and ASSA::Socketbuf::underflow(). 00085 { 00086 trace_with_mask("Streambuf::setg",STRMBUFTRACE); 00087 00088 m_read_base = gbeg_; 00089 m_read_ptr = gnext_; 00090 m_read_end = gend_; 00091 }
|
|
Set put area pointers.
Definition at line 578 of file Streambuf.h. References ASSA::io_ptrs::m_write_base, ASSA::io_ptrs::m_write_end, ASSA::io_ptrs::m_write_ptr, ASSA::STRMBUFTRACE, and trace_with_mask. Referenced by ASSA::Socketbuf::doallocate(), and ASSA::Socketbuf::flush_output(). 00579 { 00580 trace_with_mask("Streambuf::setp",STRMBUFTRACE); 00581 00582 m_write_base = m_write_ptr = pbeg_; 00583 m_write_end = pend_; 00584 }
|
|
This function returns the character after the get pointer, or EOF if the get pointer is at the end of the sequence. Despite its name, this function does NOT move the get pointer. Definition at line 539 of file Streambuf.h. References ASSA::io_ptrs::m_read_end, ASSA::io_ptrs::m_read_ptr, ASSA::STRMBUFTRACE, trace_with_mask, and underflow(). 00540 { 00541 trace_with_mask("Streambuf::sgetc",STRMBUFTRACE); 00542 00543 return (m_read_ptr >= m_read_end && underflow () == EOF 00544 ? EOF : *(unsigned char*) m_read_ptr); 00545 }
|
|
This function gets the next len_ characters following the get pointer, copying them to the char array pointed to by b_; it advances the get pointer past the last character fetched. If fewer than len characters are left, it gets as many as are available.
Definition at line 549 of file Streambuf.h. References ASSA::STRMBUFTRACE, trace_with_mask, and xsgetn(). 00550 { 00551 trace_with_mask("Streambuf::sgetn",STRMBUFTRACE); 00552 00553 return xsgetn (data_, len_); 00554 }
|
|
The morphemes of showmanyc are "es-how-many-see", not "show-man-ic". Return an estimate of the number of characters available in the sequence, or -1. If it returns a positive value, then successive calls to underflow() will not return EOF until at least that number of characters have been supplied. If showmanyc() returns -1, then calls to underflow() or uflow() will fail. The intention is not only that these calls will not return EOF, but that they will return ``immediately.'' Reimplemented in ASSA::Socketbuf. Definition at line 521 of file Streambuf.h. References ASSA::STRMBUFTRACE, and trace_with_mask. 00522 { 00523 trace_with_mask("Streambuf::showmanyc",STRMBUFTRACE); 00524 return -1; 00525 }
|
|
This function moves the get pointer forward one position, then returns the character after the get pointer's new position. If the get pointer is at the end of the sequence before or after the call to this function (no character is available), this function returns EOF. Example: Suppose the input buffer looks like this: abc|def where `|' marks the position of the get pointer. This function will advance the get pointer and return `e'. Definition at line 72 of file Streambuf.cpp. 00073 { 00074 trace_with_mask("Streambuf::snextc",STRMBUFTRACE); 00075 00076 if (m_read_ptr >= m_read_end && underflow () == EOF) { 00077 return EOF; 00078 } 00079 return m_read_ptr++, sgetc (); 00080 }
|
|
This function stores c just after the put pointer, and advances the pointer one position, possibly extending the sequence. It returns c, or EOF on error. What constitutes an error depends on the actual derived buffer class. Definition at line 558 of file Streambuf.h. References ASSA::io_ptrs::m_write_end, ASSA::io_ptrs::m_write_ptr, overflow(), ASSA::STRMBUFTRACE, and trace_with_mask. Referenced by ASSA::IPv4Socket::write(). 00559 { 00560 trace_with_mask("Streambuf::sputc",STRMBUFTRACE); 00561 00562 return (m_write_ptr >= m_write_end 00563 ? overflow (c_) 00564 : (unsigned char) (*m_write_ptr++ = c_)); 00565 }
|
|
From the location pointed to by ptr, stores exactly len characters after the put pointer, advancing the put pointer just past the last character. It returns the number of characters stored, which ought to be len. Fewer than len characters stored indicates some sort of error. Definition at line 569 of file Streambuf.h. References ASSA::STRMBUFTRACE, trace_with_mask, and xsputn(). 00570 { 00571 trace_with_mask("Streambuf::sputn",STRMBUFTRACE); 00572 00573 return xsputn (b_, len_); 00574 }
|
|
This function synchronizes the streambuf with its actual stream of characters. The derived class version should flush any characters in the put area to their final destination, and if possible give back any characters in the input buffer to their source. It should return EOF on any error, zero on success. The default behavior of the base class version is to return zero if there are no pending input or output characters (in_avail() and out_waiting() are both zero), and return EOF otherwise. Reimplemented in ASSA::Socketbuf. Definition at line 513 of file Streambuf.h. References ASSA::STRMBUFTRACE, and trace_with_mask. Referenced by pubsync(). 00514 { 00515 trace_with_mask("Streambuf::sync",STRMBUFTRACE); 00516 return 0; 00517 }
|
|
Reads the characters from the input sequence, if possible, and moves the stream position past it, as follows:. 1) If the input sequence has a read position available the function signals success by returning (unsigned char)*gnext++. 2) Otherwise, if the function can read the character x directly from the associated input sequence, it signals succes by returning (unsigned char) x. If the function makes a read position available, it also assigns x to *gnext. The default behavior is to call underflow () and, if that function returns EOF or fails to make a read position available, return EOF. Otherwise, the function signals success by returning (unsigned char)*gnext++. Definition at line 187 of file Streambuf.cpp. Referenced by sbumpc(). 00188 { 00189 trace_with_mask("Streambuf::uflow",STRMBUFTRACE); 00190 00191 if (underflow () == EOF) 00192 return EOF; 00193 dump (); 00194 return *(unsigned char *) m_read_ptr++; 00195 }
|
|
Definition at line 398 of file Streambuf.h. References ASSA::io_ptrs::m_flags, ASSA::STRMBUFTRACE, trace_with_mask, and ASSA::io_ptrs::UNBUFFERED. Referenced by ASSA::Socketbuf::flush_output(), ASSA::Socketbuf::overflow(), ASSA::Socketbuf::Socketbuf(), and ASSA::Socketbuf::underflow(). 00399 { 00400 trace_with_mask("Streambuf::unbuffered",STRMBUFTRACE); 00401 00402 return m_flags & UNBUFFERED ? 1 : 0; 00403 }
|
|
If i_ is non-zero, then all IO operations are buffered. If i_ is zero, then unbuffered IO is performed (one character at a time. Definition at line 407 of file Streambuf.h. References ASSA::io_ptrs::m_flags, ASSA::STRMBUFTRACE, trace_with_mask, and ASSA::io_ptrs::UNBUFFERED. Referenced by ASSA::IPv4Socket::read(), and ASSA::IPv4Socket::write(). 00408 { 00409 trace_with_mask("Streambuf::unbuffered",STRMBUFTRACE); 00410 00411 if (i_) 00412 m_flags |= UNBUFFERED; // set 00413 else 00414 m_flags &= ~ UNBUFFERED; // unset 00415 }
|
|
This function is called to supply characters for input (from some source) when the get area is empty, although it may be called at other times. If the get area is not empty, it should just return the first character (without advancing the get pointer). If the get area is empty, it should establish a new get area, aquire new input, and return the first character, if any. If no input characters are available, it should leave an empty get area and return EOF. The default behavior of the base class version is undefined, so each derived class must define its own underflow. Reimplemented in ASSA::Socketbuf. Definition at line 588 of file Streambuf.h. References ASSA::STRMBUFTRACE, and trace_with_mask. Referenced by sgetc(). 00589 { 00590 trace_with_mask("Streambuf::underflow",STRMBUFTRACE); 00591 00592 return (EOF); 00593 }
|
|
Assigns up to len_ characters to successive elements of the array whose first element is designated by b_. The characters assigned are read from the input sequence as if by repeated calls to sbumpc(). Assigning stops when either len_ characters have been assigned or a call to sbumpc() would return EOF.
Definition at line 143 of file Streambuf.cpp. Referenced by sgetn(). 00144 { 00145 trace_with_mask("Streambuf::xsgetn",STRMBUFTRACE); 00146 00147 /* 00148 Get area is empty and nothing is on the socket. 00149 */ 00150 int count = m_read_end - m_read_ptr; // Bytes in Get area 00151 00152 if (count == 0 && underflow () == EOF) { 00153 DL((STRMBUFTRACE,"returning %d. count: %d\n", EOF)); 00154 return EOF; 00155 } 00156 count = m_read_end - m_read_ptr; // Adjusted bytes in Get area 00157 00158 DL((STRMBUFTRACE,"Adjusted bytes in Get Area: %d\n",count)); 00159 00160 if (count > len_) { 00161 count = len_; 00162 } 00163 00164 if (count <= 0) { 00165 count = 0; // Peer closed connection 00166 } 00167 else if (count > 20) { 00168 memcpy (data_, m_read_ptr, count); 00169 m_read_ptr += count; 00170 } 00171 else { 00172 char* s = data_; 00173 char* p = m_read_ptr; 00174 int i = count; 00175 while (i-- > 0) { 00176 *s++ = *p++; 00177 } 00178 m_read_ptr = p; 00179 } 00180 DL((STRMBUFTRACE,"Transferred %d bytes to user-space buffer\n", count)); 00181 00182 return (count); 00183 }
|
|
Writes up to len_ characters to the output sequence as if by repeated calls to sputc (c). The characters written are obtained from successive elements of the array whose first element is designated by b_. Writing stops when either len_ characters have been written or a call to sputc(c) would return EOF.
Definition at line 199 of file Streambuf.cpp. Referenced by sputn(). 00200 { 00201 trace_with_mask("Streambuf::xsputn",STRMBUFTRACE); 00202 00203 const char* s = data_; 00204 int more = len_; 00205 if (more <= 0) { 00206 return 0; 00207 } 00208 00209 for (;;) { 00210 int count = m_write_end - m_write_ptr; // Space available 00211 00212 if (count > 0) { 00213 00214 if (count > more) // Enough buffer space 00215 count = more; 00216 00217 if (count > 20) { 00218 memcpy (m_write_ptr, s, count); 00219 s += count; 00220 m_write_ptr += count; 00221 } 00222 else if (count <= 0) { 00223 count = 0; 00224 } 00225 else { 00226 char* p = m_write_ptr; 00227 int i; 00228 00229 for (i=count; --i >= 0;) { 00230 *p++ = *s++; 00231 } 00232 m_write_ptr = p; 00233 } 00234 more -= count; 00235 } // if (count>0) 00236 00237 if (more == 0 || overflow ((unsigned char) *s++) == EOF) { 00238 break; 00239 } 00240 more--; 00241 00242 } // for (;;) 00243 00244 return (len_ - more); 00245 }
|