00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036 #ifndef _FSTREAM_TCC
00037 #define _FSTREAM_TCC 1
00038
00039 #pragma GCC system_header
00040
00041 #include <cxxabi-forced.h>
00042
00043 _GLIBCXX_BEGIN_NAMESPACE(std)
00044
00045 template<typename _CharT, typename _Traits>
00046 void
00047 basic_filebuf<_CharT, _Traits>::
00048 _M_allocate_internal_buffer()
00049 {
00050
00051
00052 if (!_M_buf_allocated && !_M_buf)
00053 {
00054 _M_buf = new char_type[_M_buf_size];
00055 _M_buf_allocated = true;
00056 }
00057 }
00058
00059 template<typename _CharT, typename _Traits>
00060 void
00061 basic_filebuf<_CharT, _Traits>::
00062 _M_destroy_internal_buffer() throw()
00063 {
00064 if (_M_buf_allocated)
00065 {
00066 delete [] _M_buf;
00067 _M_buf = NULL;
00068 _M_buf_allocated = false;
00069 }
00070 delete [] _M_ext_buf;
00071 _M_ext_buf = NULL;
00072 _M_ext_buf_size = 0;
00073 _M_ext_next = NULL;
00074 _M_ext_end = NULL;
00075 }
00076
00077 template<typename _CharT, typename _Traits>
00078 basic_filebuf<_CharT, _Traits>::
00079 basic_filebuf() : __streambuf_type(), _M_lock(), _M_file(&_M_lock),
00080 _M_mode(ios_base::openmode(0)), _M_state_beg(), _M_state_cur(),
00081 _M_state_last(), _M_buf(NULL), _M_buf_size(BUFSIZ),
00082 _M_buf_allocated(false), _M_reading(false), _M_writing(false), _M_pback(),
00083 _M_pback_cur_save(0), _M_pback_end_save(0), _M_pback_init(false),
00084 _M_codecvt(0), _M_ext_buf(0), _M_ext_buf_size(0), _M_ext_next(0),
00085 _M_ext_end(0)
00086 {
00087 if (has_facet<__codecvt_type>(this->_M_buf_locale))
00088 _M_codecvt = &use_facet<__codecvt_type>(this->_M_buf_locale);
00089 }
00090
00091 template<typename _CharT, typename _Traits>
00092 typename basic_filebuf<_CharT, _Traits>::__filebuf_type*
00093 basic_filebuf<_CharT, _Traits>::
00094 open(const char* __s, ios_base::openmode __mode)
00095 {
00096 __filebuf_type *__ret = NULL;
00097 if (!this->is_open())
00098 {
00099 _M_file.open(__s, __mode);
00100 if (this->is_open())
00101 {
00102 _M_allocate_internal_buffer();
00103 _M_mode = __mode;
00104
00105
00106 _M_reading = false;
00107 _M_writing = false;
00108 _M_set_buffer(-1);
00109
00110
00111 _M_state_last = _M_state_cur = _M_state_beg;
00112
00113
00114 if ((__mode & ios_base::ate)
00115 && this->seekoff(0, ios_base::end, __mode)
00116 == pos_type(off_type(-1)))
00117 this->close();
00118 else
00119 __ret = this;
00120 }
00121 }
00122 return __ret;
00123 }
00124
00125 template<typename _CharT, typename _Traits>
00126 typename basic_filebuf<_CharT, _Traits>::__filebuf_type*
00127 basic_filebuf<_CharT, _Traits>::
00128 close()
00129 {
00130 if (!this->is_open())
00131 return NULL;
00132
00133 bool __testfail = false;
00134 {
00135
00136 struct __close_sentry
00137 {
00138 basic_filebuf *__fb;
00139 __close_sentry (basic_filebuf *__fbi): __fb(__fbi) { }
00140 ~__close_sentry ()
00141 {
00142 __fb->_M_mode = ios_base::openmode(0);
00143 __fb->_M_pback_init = false;
00144 __fb->_M_destroy_internal_buffer();
00145 __fb->_M_reading = false;
00146 __fb->_M_writing = false;
00147 __fb->_M_set_buffer(-1);
00148 __fb->_M_state_last = __fb->_M_state_cur = __fb->_M_state_beg;
00149 }
00150 } __cs (this);
00151
00152 __try
00153 {
00154 if (!_M_terminate_output())
00155 __testfail = true;
00156 }
00157 __catch(__cxxabiv1::__forced_unwind&)
00158 {
00159 _M_file.close();
00160 __throw_exception_again;
00161 }
00162 __catch(...)
00163 { __testfail = true; }
00164 }
00165
00166 if (!_M_file.close())
00167 __testfail = true;
00168
00169 if (__testfail)
00170 return NULL;
00171 else
00172 return this;
00173 }
00174
00175 template<typename _CharT, typename _Traits>
00176 streamsize
00177 basic_filebuf<_CharT, _Traits>::
00178 showmanyc()
00179 {
00180 streamsize __ret = -1;
00181 const bool __testin = _M_mode & ios_base::in;
00182 if (__testin && this->is_open())
00183 {
00184
00185
00186 __ret = this->egptr() - this->gptr();
00187
00188 #if _GLIBCXX_HAVE_DOS_BASED_FILESYSTEM
00189
00190 const bool __testbinary = _M_mode & ios_base::binary;
00191 if (__check_facet(_M_codecvt).encoding() >= 0
00192 && __testbinary)
00193 #else
00194 if (__check_facet(_M_codecvt).encoding() >= 0)
00195 #endif
00196 __ret += _M_file.showmanyc() / _M_codecvt->max_length();
00197 }
00198 return __ret;
00199 }
00200
00201 template<typename _CharT, typename _Traits>
00202 typename basic_filebuf<_CharT, _Traits>::int_type
00203 basic_filebuf<_CharT, _Traits>::
00204 underflow()
00205 {
00206 int_type __ret = traits_type::eof();
00207 const bool __testin = _M_mode & ios_base::in;
00208 if (__testin && !_M_writing)
00209 {
00210
00211
00212
00213 _M_destroy_pback();
00214
00215 if (this->gptr() < this->egptr())
00216 return traits_type::to_int_type(*this->gptr());
00217
00218
00219 const size_t __buflen = _M_buf_size > 1 ? _M_buf_size - 1 : 1;
00220
00221
00222 bool __got_eof = false;
00223
00224 streamsize __ilen = 0;
00225 codecvt_base::result __r = codecvt_base::ok;
00226 if (__check_facet(_M_codecvt).always_noconv())
00227 {
00228 __ilen = _M_file.xsgetn(reinterpret_cast<char*>(this->eback()),
00229 __buflen);
00230 if (__ilen == 0)
00231 __got_eof = true;
00232 }
00233 else
00234 {
00235
00236
00237 const int __enc = _M_codecvt->encoding();
00238 streamsize __blen;
00239 streamsize __rlen;
00240 if (__enc > 0)
00241 __blen = __rlen = __buflen * __enc;
00242 else
00243 {
00244 __blen = __buflen + _M_codecvt->max_length() - 1;
00245 __rlen = __buflen;
00246 }
00247 const streamsize __remainder = _M_ext_end - _M_ext_next;
00248 __rlen = __rlen > __remainder ? __rlen - __remainder : 0;
00249
00250
00251
00252 if (_M_reading && this->egptr() == this->eback() && __remainder)
00253 __rlen = 0;
00254
00255
00256
00257 if (_M_ext_buf_size < __blen)
00258 {
00259 char* __buf = new char[__blen];
00260 if (__remainder)
00261 __builtin_memcpy(__buf, _M_ext_next, __remainder);
00262
00263 delete [] _M_ext_buf;
00264 _M_ext_buf = __buf;
00265 _M_ext_buf_size = __blen;
00266 }
00267 else if (__remainder)
00268 __builtin_memmove(_M_ext_buf, _M_ext_next, __remainder);
00269
00270 _M_ext_next = _M_ext_buf;
00271 _M_ext_end = _M_ext_buf + __remainder;
00272 _M_state_last = _M_state_cur;
00273
00274 do
00275 {
00276 if (__rlen > 0)
00277 {
00278
00279
00280
00281 if (_M_ext_end - _M_ext_buf + __rlen > _M_ext_buf_size)
00282 {
00283 __throw_ios_failure(__N("basic_filebuf::underflow "
00284 "codecvt::max_length() "
00285 "is not valid"));
00286 }
00287 streamsize __elen = _M_file.xsgetn(_M_ext_end, __rlen);
00288 if (__elen == 0)
00289 __got_eof = true;
00290 else if (__elen == -1)
00291 break;
00292 _M_ext_end += __elen;
00293 }
00294
00295 char_type* __iend = this->eback();
00296 if (_M_ext_next < _M_ext_end)
00297 __r = _M_codecvt->in(_M_state_cur, _M_ext_next,
00298 _M_ext_end, _M_ext_next,
00299 this->eback(),
00300 this->eback() + __buflen, __iend);
00301 if (__r == codecvt_base::noconv)
00302 {
00303 size_t __avail = _M_ext_end - _M_ext_buf;
00304 __ilen = std::min(__avail, __buflen);
00305 traits_type::copy(this->eback(),
00306 reinterpret_cast<char_type*>
00307 (_M_ext_buf), __ilen);
00308 _M_ext_next = _M_ext_buf + __ilen;
00309 }
00310 else
00311 __ilen = __iend - this->eback();
00312
00313
00314
00315
00316 if (__r == codecvt_base::error)
00317 break;
00318
00319 __rlen = 1;
00320 }
00321 while (__ilen == 0 && !__got_eof);
00322 }
00323
00324 if (__ilen > 0)
00325 {
00326 _M_set_buffer(__ilen);
00327 _M_reading = true;
00328 __ret = traits_type::to_int_type(*this->gptr());
00329 }
00330 else if (__got_eof)
00331 {
00332
00333
00334
00335 _M_set_buffer(-1);
00336 _M_reading = false;
00337
00338
00339 if (__r == codecvt_base::partial)
00340 __throw_ios_failure(__N("basic_filebuf::underflow "
00341 "incomplete character in file"));
00342 }
00343 else if (__r == codecvt_base::error)
00344 __throw_ios_failure(__N("basic_filebuf::underflow "
00345 "invalid byte sequence in file"));
00346 else
00347 __throw_ios_failure(__N("basic_filebuf::underflow "
00348 "error reading the file"));
00349 }
00350 return __ret;
00351 }
00352
00353 template<typename _CharT, typename _Traits>
00354 typename basic_filebuf<_CharT, _Traits>::int_type
00355 basic_filebuf<_CharT, _Traits>::
00356 pbackfail(int_type __i)
00357 {
00358 int_type __ret = traits_type::eof();
00359 const bool __testin = _M_mode & ios_base::in;
00360 if (__testin && !_M_writing)
00361 {
00362
00363
00364 const bool __testpb = _M_pback_init;
00365 const bool __testeof = traits_type::eq_int_type(__i, __ret);
00366 int_type __tmp;
00367 if (this->eback() < this->gptr())
00368 {
00369 this->gbump(-1);
00370 __tmp = traits_type::to_int_type(*this->gptr());
00371 }
00372 else if (this->seekoff(-1, ios_base::cur) != pos_type(off_type(-1)))
00373 {
00374 __tmp = this->underflow();
00375 if (traits_type::eq_int_type(__tmp, __ret))
00376 return __ret;
00377 }
00378 else
00379 {
00380
00381
00382
00383
00384
00385 return __ret;
00386 }
00387
00388
00389
00390 if (!__testeof && traits_type::eq_int_type(__i, __tmp))
00391 __ret = __i;
00392 else if (__testeof)
00393 __ret = traits_type::not_eof(__i);
00394 else if (!__testpb)
00395 {
00396 _M_create_pback();
00397 _M_reading = true;
00398 *this->gptr() = traits_type::to_char_type(__i);
00399 __ret = __i;
00400 }
00401 }
00402 return __ret;
00403 }
00404
00405 template<typename _CharT, typename _Traits>
00406 typename basic_filebuf<_CharT, _Traits>::int_type
00407 basic_filebuf<_CharT, _Traits>::
00408 overflow(int_type __c)
00409 {
00410 int_type __ret = traits_type::eof();
00411 const bool __testeof = traits_type::eq_int_type(__c, __ret);
00412 const bool __testout = _M_mode & ios_base::out;
00413 if (__testout && !_M_reading)
00414 {
00415 if (this->pbase() < this->pptr())
00416 {
00417
00418 if (!__testeof)
00419 {
00420 *this->pptr() = traits_type::to_char_type(__c);
00421 this->pbump(1);
00422 }
00423
00424
00425
00426 if (_M_convert_to_external(this->pbase(),
00427 this->pptr() - this->pbase()))
00428 {
00429 _M_set_buffer(0);
00430 __ret = traits_type::not_eof(__c);
00431 }
00432 }
00433 else if (_M_buf_size > 1)
00434 {
00435
00436
00437
00438 _M_set_buffer(0);
00439 _M_writing = true;
00440 if (!__testeof)
00441 {
00442 *this->pptr() = traits_type::to_char_type(__c);
00443 this->pbump(1);
00444 }
00445 __ret = traits_type::not_eof(__c);
00446 }
00447 else
00448 {
00449
00450 char_type __conv = traits_type::to_char_type(__c);
00451 if (__testeof || _M_convert_to_external(&__conv, 1))
00452 {
00453 _M_writing = true;
00454 __ret = traits_type::not_eof(__c);
00455 }
00456 }
00457 }
00458 return __ret;
00459 }
00460
00461 template<typename _CharT, typename _Traits>
00462 bool
00463 basic_filebuf<_CharT, _Traits>::
00464 _M_convert_to_external(_CharT* __ibuf, streamsize __ilen)
00465 {
00466
00467 streamsize __elen;
00468 streamsize __plen;
00469 if (__check_facet(_M_codecvt).always_noconv())
00470 {
00471 __elen = _M_file.xsputn(reinterpret_cast<char*>(__ibuf), __ilen);
00472 __plen = __ilen;
00473 }
00474 else
00475 {
00476
00477
00478 streamsize __blen = __ilen * _M_codecvt->max_length();
00479 char* __buf = static_cast<char*>(__builtin_alloca(__blen));
00480
00481 char* __bend;
00482 const char_type* __iend;
00483 codecvt_base::result __r;
00484 __r = _M_codecvt->out(_M_state_cur, __ibuf, __ibuf + __ilen,
00485 __iend, __buf, __buf + __blen, __bend);
00486
00487 if (__r == codecvt_base::ok || __r == codecvt_base::partial)
00488 __blen = __bend - __buf;
00489 else if (__r == codecvt_base::noconv)
00490 {
00491
00492 __buf = reinterpret_cast<char*>(__ibuf);
00493 __blen = __ilen;
00494 }
00495 else
00496 __throw_ios_failure(__N("basic_filebuf::_M_convert_to_external "
00497 "conversion error"));
00498
00499 __elen = _M_file.xsputn(__buf, __blen);
00500 __plen = __blen;
00501
00502
00503 if (__r == codecvt_base::partial && __elen == __plen)
00504 {
00505 const char_type* __iresume = __iend;
00506 streamsize __rlen = this->pptr() - __iend;
00507 __r = _M_codecvt->out(_M_state_cur, __iresume,
00508 __iresume + __rlen, __iend, __buf,
00509 __buf + __blen, __bend);
00510 if (__r != codecvt_base::error)
00511 {
00512 __rlen = __bend - __buf;
00513 __elen = _M_file.xsputn(__buf, __rlen);
00514 __plen = __rlen;
00515 }
00516 else
00517 __throw_ios_failure(__N("basic_filebuf::_M_convert_to_external "
00518 "conversion error"));
00519 }
00520 }
00521 return __elen == __plen;
00522 }
00523
00524 template<typename _CharT, typename _Traits>
00525 streamsize
00526 basic_filebuf<_CharT, _Traits>::
00527 xsgetn(_CharT* __s, streamsize __n)
00528 {
00529
00530 streamsize __ret = 0;
00531 if (_M_pback_init)
00532 {
00533 if (__n > 0 && this->gptr() == this->eback())
00534 {
00535 *__s++ = *this->gptr();
00536 this->gbump(1);
00537 __ret = 1;
00538 --__n;
00539 }
00540 _M_destroy_pback();
00541 }
00542
00543
00544
00545
00546 const bool __testin = _M_mode & ios_base::in;
00547 const streamsize __buflen = _M_buf_size > 1 ? _M_buf_size - 1 : 1;
00548
00549 if (__n > __buflen && __check_facet(_M_codecvt).always_noconv()
00550 && __testin && !_M_writing)
00551 {
00552
00553 const streamsize __avail = this->egptr() - this->gptr();
00554 if (__avail != 0)
00555 {
00556 if (__avail == 1)
00557 *__s = *this->gptr();
00558 else
00559 traits_type::copy(__s, this->gptr(), __avail);
00560 __s += __avail;
00561 this->gbump(__avail);
00562 __ret += __avail;
00563 __n -= __avail;
00564 }
00565
00566
00567
00568 streamsize __len;
00569 for (;;)
00570 {
00571 __len = _M_file.xsgetn(reinterpret_cast<char*>(__s),
00572 __n);
00573 if (__len == -1)
00574 __throw_ios_failure(__N("basic_filebuf::xsgetn "
00575 "error reading the file"));
00576 if (__len == 0)
00577 break;
00578
00579 __n -= __len;
00580 __ret += __len;
00581 if (__n == 0)
00582 break;
00583
00584 __s += __len;
00585 }
00586
00587 if (__n == 0)
00588 {
00589 _M_set_buffer(0);
00590 _M_reading = true;
00591 }
00592 else if (__len == 0)
00593 {
00594
00595
00596
00597 _M_set_buffer(-1);
00598 _M_reading = false;
00599 }
00600 }
00601 else
00602 __ret += __streambuf_type::xsgetn(__s, __n);
00603
00604 return __ret;
00605 }
00606
00607 template<typename _CharT, typename _Traits>
00608 streamsize
00609 basic_filebuf<_CharT, _Traits>::
00610 xsputn(const _CharT* __s, streamsize __n)
00611 {
00612
00613
00614
00615 streamsize __ret = 0;
00616 const bool __testout = _M_mode & ios_base::out;
00617 if (__check_facet(_M_codecvt).always_noconv()
00618 && __testout && !_M_reading)
00619 {
00620
00621 const streamsize __chunk = 1ul << 10;
00622 streamsize __bufavail = this->epptr() - this->pptr();
00623
00624
00625 if (!_M_writing && _M_buf_size > 1)
00626 __bufavail = _M_buf_size - 1;
00627
00628 const streamsize __limit = std::min(__chunk, __bufavail);
00629 if (__n >= __limit)
00630 {
00631 const streamsize __buffill = this->pptr() - this->pbase();
00632 const char* __buf = reinterpret_cast<const char*>(this->pbase());
00633 __ret = _M_file.xsputn_2(__buf, __buffill,
00634 reinterpret_cast<const char*>(__s),
00635 __n);
00636 if (__ret == __buffill + __n)
00637 {
00638 _M_set_buffer(0);
00639 _M_writing = true;
00640 }
00641 if (__ret > __buffill)
00642 __ret -= __buffill;
00643 else
00644 __ret = 0;
00645 }
00646 else
00647 __ret = __streambuf_type::xsputn(__s, __n);
00648 }
00649 else
00650 __ret = __streambuf_type::xsputn(__s, __n);
00651 return __ret;
00652 }
00653
00654 template<typename _CharT, typename _Traits>
00655 typename basic_filebuf<_CharT, _Traits>::__streambuf_type*
00656 basic_filebuf<_CharT, _Traits>::
00657 setbuf(char_type* __s, streamsize __n)
00658 {
00659 if (!this->is_open())
00660 {
00661 if (__s == 0 && __n == 0)
00662 _M_buf_size = 1;
00663 else if (__s && __n > 0)
00664 {
00665
00666
00667
00668
00669
00670
00671
00672
00673 _M_buf = __s;
00674 _M_buf_size = __n;
00675 }
00676 }
00677 return this;
00678 }
00679
00680
00681
00682
00683 template<typename _CharT, typename _Traits>
00684 typename basic_filebuf<_CharT, _Traits>::pos_type
00685 basic_filebuf<_CharT, _Traits>::
00686 seekoff(off_type __off, ios_base::seekdir __way, ios_base::openmode)
00687 {
00688 int __width = 0;
00689 if (_M_codecvt)
00690 __width = _M_codecvt->encoding();
00691 if (__width < 0)
00692 __width = 0;
00693
00694 pos_type __ret = pos_type(off_type(-1));
00695 const bool __testfail = __off != 0 && __width <= 0;
00696 if (this->is_open() && !__testfail)
00697 {
00698
00699 _M_destroy_pback();
00700
00701
00702
00703
00704
00705
00706 __state_type __state = _M_state_beg;
00707 off_type __computed_off = __off * __width;
00708 if (_M_reading && __way == ios_base::cur)
00709 {
00710 if (_M_codecvt->always_noconv())
00711 __computed_off += this->gptr() - this->egptr();
00712 else
00713 {
00714
00715
00716
00717 const int __gptr_off =
00718 _M_codecvt->length(_M_state_last, _M_ext_buf, _M_ext_next,
00719 this->gptr() - this->eback());
00720 __computed_off += _M_ext_buf + __gptr_off - _M_ext_end;
00721
00722
00723
00724 __state = _M_state_last;
00725 }
00726 }
00727 __ret = _M_seek(__computed_off, __way, __state);
00728 }
00729 return __ret;
00730 }
00731
00732
00733
00734
00735
00736 template<typename _CharT, typename _Traits>
00737 typename basic_filebuf<_CharT, _Traits>::pos_type
00738 basic_filebuf<_CharT, _Traits>::
00739 seekpos(pos_type __pos, ios_base::openmode)
00740 {
00741 pos_type __ret = pos_type(off_type(-1));
00742 if (this->is_open())
00743 {
00744
00745 _M_destroy_pback();
00746 __ret = _M_seek(off_type(__pos), ios_base::beg, __pos.state());
00747 }
00748 return __ret;
00749 }
00750
00751 template<typename _CharT, typename _Traits>
00752 typename basic_filebuf<_CharT, _Traits>::pos_type
00753 basic_filebuf<_CharT, _Traits>::
00754 _M_seek(off_type __off, ios_base::seekdir __way, __state_type __state)
00755 {
00756 pos_type __ret = pos_type(off_type(-1));
00757 if (_M_terminate_output())
00758 {
00759
00760 __ret = pos_type(_M_file.seekoff(__off, __way));
00761 if (__ret != pos_type(off_type(-1)))
00762 {
00763 _M_reading = false;
00764 _M_writing = false;
00765 _M_ext_next = _M_ext_end = _M_ext_buf;
00766 _M_set_buffer(-1);
00767 _M_state_cur = __state;
00768 __ret.state(_M_state_cur);
00769 }
00770 }
00771 return __ret;
00772 }
00773
00774 template<typename _CharT, typename _Traits>
00775 bool
00776 basic_filebuf<_CharT, _Traits>::
00777 _M_terminate_output()
00778 {
00779
00780 bool __testvalid = true;
00781 if (this->pbase() < this->pptr())
00782 {
00783 const int_type __tmp = this->overflow();
00784 if (traits_type::eq_int_type(__tmp, traits_type::eof()))
00785 __testvalid = false;
00786 }
00787
00788
00789 if (_M_writing && !__check_facet(_M_codecvt).always_noconv()
00790 && __testvalid)
00791 {
00792
00793
00794
00795 const size_t __blen = 128;
00796 char __buf[__blen];
00797 codecvt_base::result __r;
00798 streamsize __ilen = 0;
00799
00800 do
00801 {
00802 char* __next;
00803 __r = _M_codecvt->unshift(_M_state_cur, __buf,
00804 __buf + __blen, __next);
00805 if (__r == codecvt_base::error)
00806 __testvalid = false;
00807 else if (__r == codecvt_base::ok ||
00808 __r == codecvt_base::partial)
00809 {
00810 __ilen = __next - __buf;
00811 if (__ilen > 0)
00812 {
00813 const streamsize __elen = _M_file.xsputn(__buf, __ilen);
00814 if (__elen != __ilen)
00815 __testvalid = false;
00816 }
00817 }
00818 }
00819 while (__r == codecvt_base::partial && __ilen > 0 && __testvalid);
00820
00821 if (__testvalid)
00822 {
00823
00824
00825
00826
00827 const int_type __tmp = this->overflow();
00828 if (traits_type::eq_int_type(__tmp, traits_type::eof()))
00829 __testvalid = false;
00830 }
00831 }
00832 return __testvalid;
00833 }
00834
00835 template<typename _CharT, typename _Traits>
00836 int
00837 basic_filebuf<_CharT, _Traits>::
00838 sync()
00839 {
00840
00841
00842 int __ret = 0;
00843 if (this->pbase() < this->pptr())
00844 {
00845 const int_type __tmp = this->overflow();
00846 if (traits_type::eq_int_type(__tmp, traits_type::eof()))
00847 __ret = -1;
00848 }
00849 return __ret;
00850 }
00851
00852 template<typename _CharT, typename _Traits>
00853 void
00854 basic_filebuf<_CharT, _Traits>::
00855 imbue(const locale& __loc)
00856 {
00857 bool __testvalid = true;
00858
00859 const __codecvt_type* _M_codecvt_tmp = 0;
00860 if (__builtin_expect(has_facet<__codecvt_type>(__loc), true))
00861 _M_codecvt_tmp = &use_facet<__codecvt_type>(__loc);
00862
00863 if (this->is_open())
00864 {
00865
00866 if ((_M_reading || _M_writing)
00867 && __check_facet(_M_codecvt).encoding() == -1)
00868 __testvalid = false;
00869 else
00870 {
00871 if (_M_reading)
00872 {
00873 if (__check_facet(_M_codecvt).always_noconv())
00874 {
00875 if (_M_codecvt_tmp
00876 && !__check_facet(_M_codecvt_tmp).always_noconv())
00877 __testvalid = this->seekoff(0, ios_base::cur, _M_mode)
00878 != pos_type(off_type(-1));
00879 }
00880 else
00881 {
00882
00883 _M_ext_next = _M_ext_buf
00884 + _M_codecvt->length(_M_state_last, _M_ext_buf, _M_ext_next,
00885 this->gptr() - this->eback());
00886 const streamsize __remainder = _M_ext_end - _M_ext_next;
00887 if (__remainder)
00888 __builtin_memmove(_M_ext_buf, _M_ext_next, __remainder);
00889
00890 _M_ext_next = _M_ext_buf;
00891 _M_ext_end = _M_ext_buf + __remainder;
00892 _M_set_buffer(-1);
00893 _M_state_last = _M_state_cur = _M_state_beg;
00894 }
00895 }
00896 else if (_M_writing && (__testvalid = _M_terminate_output()))
00897 _M_set_buffer(-1);
00898 }
00899 }
00900
00901 if (__testvalid)
00902 _M_codecvt = _M_codecvt_tmp;
00903 else
00904 _M_codecvt = 0;
00905 }
00906
00907
00908
00909
00910 #if _GLIBCXX_EXTERN_TEMPLATE
00911 extern template class basic_filebuf<char>;
00912 extern template class basic_ifstream<char>;
00913 extern template class basic_ofstream<char>;
00914 extern template class basic_fstream<char>;
00915
00916 #ifdef _GLIBCXX_USE_WCHAR_T
00917 extern template class basic_filebuf<wchar_t>;
00918 extern template class basic_ifstream<wchar_t>;
00919 extern template class basic_ofstream<wchar_t>;
00920 extern template class basic_fstream<wchar_t>;
00921 #endif
00922 #endif
00923
00924 _GLIBCXX_END_NAMESPACE
00925
00926 #endif