1// -*- C++ -*-
2//===------------------------- fstream ------------------------------------===//
3//
4// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
5// See https://llvm.org/LICENSE.txt for license information.
6// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7//
8//===----------------------------------------------------------------------===//
9
10#ifndef _LIBCPP_FSTREAM
11#define _LIBCPP_FSTREAM
12
13/*
14 fstream synopsis
15
16template <class charT, class traits = char_traits<charT> >
17class basic_filebuf
18 : public basic_streambuf<charT, traits>
19{
20public:
21 typedef charT char_type;
22 typedef traits traits_type;
23 typedef typename traits_type::int_type int_type;
24 typedef typename traits_type::pos_type pos_type;
25 typedef typename traits_type::off_type off_type;
26
27 // 27.9.1.2 Constructors/destructor:
28 basic_filebuf();
29 basic_filebuf(basic_filebuf&& rhs);
30 virtual ~basic_filebuf();
31
32 // 27.9.1.3 Assign/swap:
33 basic_filebuf& operator=(basic_filebuf&& rhs);
34 void swap(basic_filebuf& rhs);
35
36 // 27.9.1.4 Members:
37 bool is_open() const;
38 basic_filebuf* open(const char* s, ios_base::openmode mode);
39 basic_filebuf* open(const string& s, ios_base::openmode mode);
40 basic_filebuf* open(const filesystem::path& p, ios_base::openmode mode); // C++17
41 basic_filebuf* close();
42
43protected:
44 // 27.9.1.5 Overridden virtual functions:
45 virtual streamsize showmanyc();
46 virtual int_type underflow();
47 virtual int_type uflow();
48 virtual int_type pbackfail(int_type c = traits_type::eof());
49 virtual int_type overflow (int_type c = traits_type::eof());
50 virtual basic_streambuf<char_type, traits_type>* setbuf(char_type* s, streamsize n);
51 virtual pos_type seekoff(off_type off, ios_base::seekdir way,
52 ios_base::openmode which = ios_base::in | ios_base::out);
53 virtual pos_type seekpos(pos_type sp,
54 ios_base::openmode which = ios_base::in | ios_base::out);
55 virtual int sync();
56 virtual void imbue(const locale& loc);
57};
58
59template <class charT, class traits>
60 void
61 swap(basic_filebuf<charT, traits>& x, basic_filebuf<charT, traits>& y);
62
63typedef basic_filebuf<char> filebuf;
64typedef basic_filebuf<wchar_t> wfilebuf;
65
66template <class charT, class traits = char_traits<charT> >
67class basic_ifstream
68 : public basic_istream<charT,traits>
69{
70public:
71 typedef charT char_type;
72 typedef traits traits_type;
73 typedef typename traits_type::int_type int_type;
74 typedef typename traits_type::pos_type pos_type;
75 typedef typename traits_type::off_type off_type;
76
77 basic_ifstream();
78 explicit basic_ifstream(const char* s, ios_base::openmode mode = ios_base::in);
79 explicit basic_ifstream(const string& s, ios_base::openmode mode = ios_base::in);
80 explicit basic_ifstream(const filesystem::path& p,
81 ios_base::openmode mode = ios_base::in); // C++17
82 basic_ifstream(basic_ifstream&& rhs);
83
84 basic_ifstream& operator=(basic_ifstream&& rhs);
85 void swap(basic_ifstream& rhs);
86
87 basic_filebuf<char_type, traits_type>* rdbuf() const;
88 bool is_open() const;
89 void open(const char* s, ios_base::openmode mode = ios_base::in);
90 void open(const string& s, ios_base::openmode mode = ios_base::in);
91 void open(const filesystem::path& s, ios_base::openmode mode = ios_base::in); // C++17
92
93 void close();
94};
95
96template <class charT, class traits>
97 void
98 swap(basic_ifstream<charT, traits>& x, basic_ifstream<charT, traits>& y);
99
100typedef basic_ifstream<char> ifstream;
101typedef basic_ifstream<wchar_t> wifstream;
102
103template <class charT, class traits = char_traits<charT> >
104class basic_ofstream
105 : public basic_ostream<charT,traits>
106{
107public:
108 typedef charT char_type;
109 typedef traits traits_type;
110 typedef typename traits_type::int_type int_type;
111 typedef typename traits_type::pos_type pos_type;
112 typedef typename traits_type::off_type off_type;
113
114 basic_ofstream();
115 explicit basic_ofstream(const char* s, ios_base::openmode mode = ios_base::out);
116 explicit basic_ofstream(const string& s, ios_base::openmode mode = ios_base::out);
117 explicit basic_ofstream(const filesystem::path& p,
118 ios_base::openmode mode = ios_base::out); // C++17
119 basic_ofstream(basic_ofstream&& rhs);
120
121 basic_ofstream& operator=(basic_ofstream&& rhs);
122 void swap(basic_ofstream& rhs);
123
124 basic_filebuf<char_type, traits_type>* rdbuf() const;
125 bool is_open() const;
126 void open(const char* s, ios_base::openmode mode = ios_base::out);
127 void open(const string& s, ios_base::openmode mode = ios_base::out);
128 void open(const filesystem::path& p,
129 ios_base::openmode mode = ios_base::out); // C++17
130
131 void close();
132};
133
134template <class charT, class traits>
135 void
136 swap(basic_ofstream<charT, traits>& x, basic_ofstream<charT, traits>& y);
137
138typedef basic_ofstream<char> ofstream;
139typedef basic_ofstream<wchar_t> wofstream;
140
141template <class charT, class traits=char_traits<charT> >
142class basic_fstream
143 : public basic_iostream<charT,traits>
144{
145public:
146 typedef charT char_type;
147 typedef traits traits_type;
148 typedef typename traits_type::int_type int_type;
149 typedef typename traits_type::pos_type pos_type;
150 typedef typename traits_type::off_type off_type;
151
152 basic_fstream();
153 explicit basic_fstream(const char* s, ios_base::openmode mode = ios_base::in|ios_base::out);
154 explicit basic_fstream(const string& s, ios_base::openmode mode = ios_base::in|ios_base::out);
155 explicit basic_fstream(const filesystem::path& p,
156 ios_base::openmode mode = ios_base::in|ios_base::out); C++17
157 basic_fstream(basic_fstream&& rhs);
158
159 basic_fstream& operator=(basic_fstream&& rhs);
160 void swap(basic_fstream& rhs);
161
162 basic_filebuf<char_type, traits_type>* rdbuf() const;
163 bool is_open() const;
164 void open(const char* s, ios_base::openmode mode = ios_base::in|ios_base::out);
165 void open(const string& s, ios_base::openmode mode = ios_base::in|ios_base::out);
166 void open(const filesystem::path& s,
167 ios_base::openmode mode = ios_base::in|ios_base::out); // C++17
168
169 void close();
170};
171
172template <class charT, class traits>
173 void swap(basic_fstream<charT, traits>& x, basic_fstream<charT, traits>& y);
174
175typedef basic_fstream<char> fstream;
176typedef basic_fstream<wchar_t> wfstream;
177
178} // std
179
180*/
181
182#include <__config>
183#include <ostream>
184#include <istream>
185#include <__locale>
186#include <cstdio>
187#include <cstdlib>
188#include <filesystem>
189
190#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
191#pragma GCC system_header
192#endif
193
194_LIBCPP_PUSH_MACROS
195#include <__undef_macros>
196
197
198_LIBCPP_BEGIN_NAMESPACE_STD
199
200template <class _CharT, class _Traits>
201class _LIBCPP_TEMPLATE_VIS basic_filebuf
202 : public basic_streambuf<_CharT, _Traits>
203{
204public:
205 typedef _CharT char_type;
206 typedef _Traits traits_type;
207 typedef typename traits_type::int_type int_type;
208 typedef typename traits_type::pos_type pos_type;
209 typedef typename traits_type::off_type off_type;
210 typedef typename traits_type::state_type state_type;
211
212 // 27.9.1.2 Constructors/destructor:
213 basic_filebuf();
214#ifndef _LIBCPP_CXX03_LANG
215 basic_filebuf(basic_filebuf&& __rhs);
216#endif
217 virtual ~basic_filebuf();
218
219 // 27.9.1.3 Assign/swap:
220#ifndef _LIBCPP_CXX03_LANG
221 _LIBCPP_INLINE_VISIBILITY
222 basic_filebuf& operator=(basic_filebuf&& __rhs);
223#endif
224 void swap(basic_filebuf& __rhs);
225
226 // 27.9.1.4 Members:
227 _LIBCPP_INLINE_VISIBILITY
228 bool is_open() const;
229#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
230 basic_filebuf* open(const char* __s, ios_base::openmode __mode);
231#ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
232 basic_filebuf* open(const wchar_t* __s, ios_base::openmode __mode);
233#endif
234 _LIBCPP_INLINE_VISIBILITY
235 basic_filebuf* open(const string& __s, ios_base::openmode __mode);
236
237#if _LIBCPP_STD_VER >= 17
238 _LIBCPP_AVAILABILITY_FILESYSTEM _LIBCPP_INLINE_VISIBILITY
239 basic_filebuf* open(const _VSTD_FS::path& __p, ios_base::openmode __mode) {
240 return open(__p.c_str(), __mode);
241 }
242#endif
243 _LIBCPP_INLINE_VISIBILITY
244 basic_filebuf* __open(int __fd, ios_base::openmode __mode);
245#endif
246 basic_filebuf* close();
247
248 _LIBCPP_INLINE_VISIBILITY
249 inline static const char*
250 __make_mdstring(ios_base::openmode __mode) _NOEXCEPT;
251
252 protected:
253 // 27.9.1.5 Overridden virtual functions:
254 virtual int_type underflow();
255 virtual int_type pbackfail(int_type __c = traits_type::eof());
256 virtual int_type overflow (int_type __c = traits_type::eof());
257 virtual basic_streambuf<char_type, traits_type>* setbuf(char_type* __s, streamsize __n);
258 virtual pos_type seekoff(off_type __off, ios_base::seekdir __way,
259 ios_base::openmode __wch = ios_base::in | ios_base::out);
260 virtual pos_type seekpos(pos_type __sp,
261 ios_base::openmode __wch = ios_base::in | ios_base::out);
262 virtual int sync();
263 virtual void imbue(const locale& __loc);
264
265private:
266 char* __extbuf_;
267 const char* __extbufnext_;
268 const char* __extbufend_;
269 char __extbuf_min_[8];
270 size_t __ebs_;
271 char_type* __intbuf_;
272 size_t __ibs_;
273 FILE* __file_;
274 const codecvt<char_type, char, state_type>* __cv_;
275 state_type __st_;
276 state_type __st_last_;
277 ios_base::openmode __om_;
278 ios_base::openmode __cm_;
279 bool __owns_eb_;
280 bool __owns_ib_;
281 bool __always_noconv_;
282
283 bool __read_mode();
284 void __write_mode();
285};
286
287template <class _CharT, class _Traits>
288basic_filebuf<_CharT, _Traits>::basic_filebuf()
289 : __extbuf_(0),
290 __extbufnext_(0),
291 __extbufend_(0),
292 __ebs_(0),
293 __intbuf_(0),
294 __ibs_(0),
295 __file_(0),
296 __cv_(nullptr),
297 __st_(),
298 __st_last_(),
299 __om_(0),
300 __cm_(0),
301 __owns_eb_(false),
302 __owns_ib_(false),
303 __always_noconv_(false)
304{
305 if (has_facet<codecvt<char_type, char, state_type> >(this->getloc()))
306 {
307 __cv_ = &use_facet<codecvt<char_type, char, state_type> >(this->getloc());
308 __always_noconv_ = __cv_->always_noconv();
309 }
310 setbuf(0, 4096);
311}
312
313#ifndef _LIBCPP_CXX03_LANG
314
315template <class _CharT, class _Traits>
316basic_filebuf<_CharT, _Traits>::basic_filebuf(basic_filebuf&& __rhs)
317 : basic_streambuf<_CharT, _Traits>(__rhs)
318{
319 if (__rhs.__extbuf_ == __rhs.__extbuf_min_)
320 {
321 __extbuf_ = __extbuf_min_;
322 __extbufnext_ = __extbuf_ + (__rhs.__extbufnext_ - __rhs.__extbuf_);
323 __extbufend_ = __extbuf_ + (__rhs.__extbufend_ - __rhs.__extbuf_);
324 }
325 else
326 {
327 __extbuf_ = __rhs.__extbuf_;
328 __extbufnext_ = __rhs.__extbufnext_;
329 __extbufend_ = __rhs.__extbufend_;
330 }
331 __ebs_ = __rhs.__ebs_;
332 __intbuf_ = __rhs.__intbuf_;
333 __ibs_ = __rhs.__ibs_;
334 __file_ = __rhs.__file_;
335 __cv_ = __rhs.__cv_;
336 __st_ = __rhs.__st_;
337 __st_last_ = __rhs.__st_last_;
338 __om_ = __rhs.__om_;
339 __cm_ = __rhs.__cm_;
340 __owns_eb_ = __rhs.__owns_eb_;
341 __owns_ib_ = __rhs.__owns_ib_;
342 __always_noconv_ = __rhs.__always_noconv_;
343 if (__rhs.pbase())
344 {
345 if (__rhs.pbase() == __rhs.__intbuf_)
346 this->setp(__intbuf_, __intbuf_ + (__rhs. epptr() - __rhs.pbase()));
347 else
348 this->setp((char_type*)__extbuf_,
349 (char_type*)__extbuf_ + (__rhs. epptr() - __rhs.pbase()));
350 this->__pbump(__rhs. pptr() - __rhs.pbase());
351 }
352 else if (__rhs.eback())
353 {
354 if (__rhs.eback() == __rhs.__intbuf_)
355 this->setg(__intbuf_, __intbuf_ + (__rhs.gptr() - __rhs.eback()),
356 __intbuf_ + (__rhs.egptr() - __rhs.eback()));
357 else
358 this->setg((char_type*)__extbuf_,
359 (char_type*)__extbuf_ + (__rhs.gptr() - __rhs.eback()),
360 (char_type*)__extbuf_ + (__rhs.egptr() - __rhs.eback()));
361 }
362 __rhs.__extbuf_ = 0;
363 __rhs.__extbufnext_ = 0;
364 __rhs.__extbufend_ = 0;
365 __rhs.__ebs_ = 0;
366 __rhs.__intbuf_ = 0;
367 __rhs.__ibs_ = 0;
368 __rhs.__file_ = 0;
369 __rhs.__st_ = state_type();
370 __rhs.__st_last_ = state_type();
371 __rhs.__om_ = 0;
372 __rhs.__cm_ = 0;
373 __rhs.__owns_eb_ = false;
374 __rhs.__owns_ib_ = false;
375 __rhs.setg(0, 0, 0);
376 __rhs.setp(0, 0);
377}
378
379template <class _CharT, class _Traits>
380inline
381basic_filebuf<_CharT, _Traits>&
382basic_filebuf<_CharT, _Traits>::operator=(basic_filebuf&& __rhs)
383{
384 close();
385 swap(__rhs);
386 return *this;
387}
388
389#endif // _LIBCPP_CXX03_LANG
390
391template <class _CharT, class _Traits>
392basic_filebuf<_CharT, _Traits>::~basic_filebuf()
393{
394#ifndef _LIBCPP_NO_EXCEPTIONS
395 try
396 {
397#endif // _LIBCPP_NO_EXCEPTIONS
398 close();
399#ifndef _LIBCPP_NO_EXCEPTIONS
400 }
401 catch (...)
402 {
403 }
404#endif // _LIBCPP_NO_EXCEPTIONS
405 if (__owns_eb_)
406 delete [] __extbuf_;
407 if (__owns_ib_)
408 delete [] __intbuf_;
409}
410
411template <class _CharT, class _Traits>
412void
413basic_filebuf<_CharT, _Traits>::swap(basic_filebuf& __rhs)
414{
415 basic_streambuf<char_type, traits_type>::swap(__rhs);
416 if (__extbuf_ != __extbuf_min_ && __rhs.__extbuf_ != __rhs.__extbuf_min_)
417 {
418 _VSTD::swap(__extbuf_, __rhs.__extbuf_);
419 _VSTD::swap(__extbufnext_, __rhs.__extbufnext_);
420 _VSTD::swap(__extbufend_, __rhs.__extbufend_);
421 }
422 else
423 {
424 ptrdiff_t __ln = __extbufnext_ - __extbuf_;
425 ptrdiff_t __le = __extbufend_ - __extbuf_;
426 ptrdiff_t __rn = __rhs.__extbufnext_ - __rhs.__extbuf_;
427 ptrdiff_t __re = __rhs.__extbufend_ - __rhs.__extbuf_;
428 if (__extbuf_ == __extbuf_min_ && __rhs.__extbuf_ != __rhs.__extbuf_min_)
429 {
430 __extbuf_ = __rhs.__extbuf_;
431 __rhs.__extbuf_ = __rhs.__extbuf_min_;
432 }
433 else if (__extbuf_ != __extbuf_min_ && __rhs.__extbuf_ == __rhs.__extbuf_min_)
434 {
435 __rhs.__extbuf_ = __extbuf_;
436 __extbuf_ = __extbuf_min_;
437 }
438 __extbufnext_ = __extbuf_ + __rn;
439 __extbufend_ = __extbuf_ + __re;
440 __rhs.__extbufnext_ = __rhs.__extbuf_ + __ln;
441 __rhs.__extbufend_ = __rhs.__extbuf_ + __le;
442 }
443 _VSTD::swap(__ebs_, __rhs.__ebs_);
444 _VSTD::swap(__intbuf_, __rhs.__intbuf_);
445 _VSTD::swap(__ibs_, __rhs.__ibs_);
446 _VSTD::swap(__file_, __rhs.__file_);
447 _VSTD::swap(__cv_, __rhs.__cv_);
448 _VSTD::swap(__st_, __rhs.__st_);
449 _VSTD::swap(__st_last_, __rhs.__st_last_);
450 _VSTD::swap(__om_, __rhs.__om_);
451 _VSTD::swap(__cm_, __rhs.__cm_);
452 _VSTD::swap(__owns_eb_, __rhs.__owns_eb_);
453 _VSTD::swap(__owns_ib_, __rhs.__owns_ib_);
454 _VSTD::swap(__always_noconv_, __rhs.__always_noconv_);
455 if (this->eback() == (char_type*)__rhs.__extbuf_min_)
456 {
457 ptrdiff_t __n = this->gptr() - this->eback();
458 ptrdiff_t __e = this->egptr() - this->eback();
459 this->setg((char_type*)__extbuf_min_,
460 (char_type*)__extbuf_min_ + __n,
461 (char_type*)__extbuf_min_ + __e);
462 }
463 else if (this->pbase() == (char_type*)__rhs.__extbuf_min_)
464 {
465 ptrdiff_t __n = this->pptr() - this->pbase();
466 ptrdiff_t __e = this->epptr() - this->pbase();
467 this->setp((char_type*)__extbuf_min_,
468 (char_type*)__extbuf_min_ + __e);
469 this->__pbump(__n);
470 }
471 if (__rhs.eback() == (char_type*)__extbuf_min_)
472 {
473 ptrdiff_t __n = __rhs.gptr() - __rhs.eback();
474 ptrdiff_t __e = __rhs.egptr() - __rhs.eback();
475 __rhs.setg((char_type*)__rhs.__extbuf_min_,
476 (char_type*)__rhs.__extbuf_min_ + __n,
477 (char_type*)__rhs.__extbuf_min_ + __e);
478 }
479 else if (__rhs.pbase() == (char_type*)__extbuf_min_)
480 {
481 ptrdiff_t __n = __rhs.pptr() - __rhs.pbase();
482 ptrdiff_t __e = __rhs.epptr() - __rhs.pbase();
483 __rhs.setp((char_type*)__rhs.__extbuf_min_,
484 (char_type*)__rhs.__extbuf_min_ + __e);
485 __rhs.__pbump(__n);
486 }
487}
488
489template <class _CharT, class _Traits>
490inline _LIBCPP_INLINE_VISIBILITY
491void
492swap(basic_filebuf<_CharT, _Traits>& __x, basic_filebuf<_CharT, _Traits>& __y)
493{
494 __x.swap(__y);
495}
496
497template <class _CharT, class _Traits>
498inline
499bool
500basic_filebuf<_CharT, _Traits>::is_open() const
501{
502 return __file_ != 0;
503}
504
505template <class _CharT, class _Traits>
506const char* basic_filebuf<_CharT, _Traits>::__make_mdstring(
507 ios_base::openmode __mode) _NOEXCEPT {
508 switch (__mode & ~ios_base::ate) {
509 case ios_base::out:
510 case ios_base::out | ios_base::trunc:
511 return "w";
512 case ios_base::out | ios_base::app:
513 case ios_base::app:
514 return "a";
515 case ios_base::in:
516 return "r";
517 case ios_base::in | ios_base::out:
518 return "r+";
519 case ios_base::in | ios_base::out | ios_base::trunc:
520 return "w+";
521 case ios_base::in | ios_base::out | ios_base::app:
522 case ios_base::in | ios_base::app:
523 return "a+";
524 case ios_base::out | ios_base::binary:
525 case ios_base::out | ios_base::trunc | ios_base::binary:
526 return "wb";
527 case ios_base::out | ios_base::app | ios_base::binary:
528 case ios_base::app | ios_base::binary:
529 return "ab";
530 case ios_base::in | ios_base::binary:
531 return "rb";
532 case ios_base::in | ios_base::out | ios_base::binary:
533 return "r+b";
534 case ios_base::in | ios_base::out | ios_base::trunc | ios_base::binary:
535 return "w+b";
536 case ios_base::in | ios_base::out | ios_base::app | ios_base::binary:
537 case ios_base::in | ios_base::app | ios_base::binary:
538 return "a+b";
539 default:
540 return nullptr;
541 }
542 _LIBCPP_UNREACHABLE();
543}
544
545#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
546template <class _CharT, class _Traits>
547basic_filebuf<_CharT, _Traits>*
548basic_filebuf<_CharT, _Traits>::open(const char* __s, ios_base::openmode __mode)
549{
550 basic_filebuf<_CharT, _Traits>* __rt = 0;
551 if (__file_ == 0)
552 {
553 if (const char* __mdstr = __make_mdstring(__mode)) {
554 __rt = this;
555 __file_ = fopen(__s, __mdstr);
556 if (__file_) {
557 __om_ = __mode;
558 if (__mode & ios_base::ate) {
559 if (fseek(__file_, 0, SEEK_END)) {
560 fclose(__file_);
561 __file_ = 0;
562 __rt = 0;
563 }
564 }
565 } else
566 __rt = 0;
567 }
568 }
569 return __rt;
570}
571
572template <class _CharT, class _Traits>
573_LIBCPP_INLINE_VISIBILITY basic_filebuf<_CharT, _Traits>*
574basic_filebuf<_CharT, _Traits>::__open(int __fd, ios_base::openmode __mode) {
575 basic_filebuf<_CharT, _Traits>* __rt = 0;
576 if (__file_ == 0) {
577 if (const char* __mdstr = __make_mdstring(__mode)) {
578 __rt = this;
579 __file_ = fdopen(__fd, __mdstr);
580 if (__file_) {
581 __om_ = __mode;
582 if (__mode & ios_base::ate) {
583 if (fseek(__file_, 0, SEEK_END)) {
584 fclose(__file_);
585 __file_ = 0;
586 __rt = 0;
587 }
588 }
589 } else
590 __rt = 0;
591 }
592 }
593 return __rt;
594}
595
596#ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
597// This is basically the same as the char* overload except that it uses _wfopen
598// and long mode strings.
599template <class _CharT, class _Traits>
600basic_filebuf<_CharT, _Traits>*
601basic_filebuf<_CharT, _Traits>::open(const wchar_t* __s, ios_base::openmode __mode)
602{
603 basic_filebuf<_CharT, _Traits>* __rt = 0;
604 if (__file_ == 0)
605 {
606 __rt = this;
607 const wchar_t* __mdstr;
608 switch (__mode & ~ios_base::ate)
609 {
610 case ios_base::out:
611 case ios_base::out | ios_base::trunc:
612 __mdstr = L"w";
613 break;
614 case ios_base::out | ios_base::app:
615 case ios_base::app:
616 __mdstr = L"a";
617 break;
618 case ios_base::in:
619 __mdstr = L"r";
620 break;
621 case ios_base::in | ios_base::out:
622 __mdstr = L"r+";
623 break;
624 case ios_base::in | ios_base::out | ios_base::trunc:
625 __mdstr = L"w+";
626 break;
627 case ios_base::in | ios_base::out | ios_base::app:
628 case ios_base::in | ios_base::app:
629 __mdstr = L"a+";
630 break;
631 case ios_base::out | ios_base::binary:
632 case ios_base::out | ios_base::trunc | ios_base::binary:
633 __mdstr = L"wb";
634 break;
635 case ios_base::out | ios_base::app | ios_base::binary:
636 case ios_base::app | ios_base::binary:
637 __mdstr = L"ab";
638 break;
639 case ios_base::in | ios_base::binary:
640 __mdstr = L"rb";
641 break;
642 case ios_base::in | ios_base::out | ios_base::binary:
643 __mdstr = L"r+b";
644 break;
645 case ios_base::in | ios_base::out | ios_base::trunc | ios_base::binary:
646 __mdstr = L"w+b";
647 break;
648 case ios_base::in | ios_base::out | ios_base::app | ios_base::binary:
649 case ios_base::in | ios_base::app | ios_base::binary:
650 __mdstr = L"a+b";
651 break;
652 default:
653 __rt = 0;
654 break;
655 }
656 if (__rt)
657 {
658 __file_ = _wfopen(__s, __mdstr);
659 if (__file_)
660 {
661 __om_ = __mode;
662 if (__mode & ios_base::ate)
663 {
664 if (fseek(__file_, 0, SEEK_END))
665 {
666 fclose(__file_);
667 __file_ = 0;
668 __rt = 0;
669 }
670 }
671 }
672 else
673 __rt = 0;
674 }
675 }
676 return __rt;
677}
678#endif
679
680template <class _CharT, class _Traits>
681inline
682basic_filebuf<_CharT, _Traits>*
683basic_filebuf<_CharT, _Traits>::open(const string& __s, ios_base::openmode __mode)
684{
685 return open(__s.c_str(), __mode);
686}
687#endif
688
689template <class _CharT, class _Traits>
690basic_filebuf<_CharT, _Traits>*
691basic_filebuf<_CharT, _Traits>::close()
692{
693 basic_filebuf<_CharT, _Traits>* __rt = 0;
694 if (__file_)
695 {
696 __rt = this;
697 unique_ptr<FILE, int(*)(FILE*)> __h(__file_, fclose);
698 if (sync())
699 __rt = 0;
700 if (fclose(__h.release()) == 0)
701 __file_ = 0;
702 else
703 __rt = 0;
704 setbuf(0, 0);
705 }
706 return __rt;
707}
708
709template <class _CharT, class _Traits>
710typename basic_filebuf<_CharT, _Traits>::int_type
711basic_filebuf<_CharT, _Traits>::underflow()
712{
713 if (__file_ == 0)
714 return traits_type::eof();
715 bool __initial = __read_mode();
716 char_type __1buf;
717 if (this->gptr() == 0)
718 this->setg(&__1buf, &__1buf+1, &__1buf+1);
719 const size_t __unget_sz = __initial ? 0 : min<size_t>((this->egptr() - this->eback()) / 2, 4);
720 int_type __c = traits_type::eof();
721 if (this->gptr() == this->egptr())
722 {
723 memmove(this->eback(), this->egptr() - __unget_sz, __unget_sz * sizeof(char_type));
724 if (__always_noconv_)
725 {
726 size_t __nmemb = static_cast<size_t>(this->egptr() - this->eback() - __unget_sz);
727 __nmemb = fread(this->eback() + __unget_sz, 1, __nmemb, __file_);
728 if (__nmemb != 0)
729 {
730 this->setg(this->eback(),
731 this->eback() + __unget_sz,
732 this->eback() + __unget_sz + __nmemb);
733 __c = traits_type::to_int_type(*this->gptr());
734 }
735 }
736 else
737 {
738 _LIBCPP_ASSERT ( !(__extbufnext_ == NULL && (__extbufend_ != __extbufnext_)), "underflow moving from NULL" );
739 if (__extbufend_ != __extbufnext_)
740 memmove(__extbuf_, __extbufnext_, __extbufend_ - __extbufnext_);
741 __extbufnext_ = __extbuf_ + (__extbufend_ - __extbufnext_);
742 __extbufend_ = __extbuf_ + (__extbuf_ == __extbuf_min_ ? sizeof(__extbuf_min_) : __ebs_);
743 size_t __nmemb = _VSTD::min(static_cast<size_t>(__ibs_ - __unget_sz),
744 static_cast<size_t>(__extbufend_ - __extbufnext_));
745 codecvt_base::result __r;
746 __st_last_ = __st_;
747 size_t __nr = fread((void*) const_cast<char *>(__extbufnext_), 1, __nmemb, __file_);
748 if (__nr != 0)
749 {
750 if (!__cv_)
751 __throw_bad_cast();
752
753 __extbufend_ = __extbufnext_ + __nr;
754 char_type* __inext;
755 __r = __cv_->in(__st_, __extbuf_, __extbufend_, __extbufnext_,
756 this->eback() + __unget_sz,
757 this->eback() + __ibs_, __inext);
758 if (__r == codecvt_base::noconv)
759 {
760 this->setg((char_type*)__extbuf_, (char_type*)__extbuf_,
761 (char_type*)const_cast<char *>(__extbufend_));
762 __c = traits_type::to_int_type(*this->gptr());
763 }
764 else if (__inext != this->eback() + __unget_sz)
765 {
766 this->setg(this->eback(), this->eback() + __unget_sz, __inext);
767 __c = traits_type::to_int_type(*this->gptr());
768 }
769 }
770 }
771 }
772 else
773 __c = traits_type::to_int_type(*this->gptr());
774 if (this->eback() == &__1buf)
775 this->setg(0, 0, 0);
776 return __c;
777}
778
779template <class _CharT, class _Traits>
780typename basic_filebuf<_CharT, _Traits>::int_type
781basic_filebuf<_CharT, _Traits>::pbackfail(int_type __c)
782{
783 if (__file_ && this->eback() < this->gptr())
784 {
785 if (traits_type::eq_int_type(__c, traits_type::eof()))
786 {
787 this->gbump(-1);
788 return traits_type::not_eof(__c);
789 }
790 if ((__om_ & ios_base::out) ||
791 traits_type::eq(traits_type::to_char_type(__c), this->gptr()[-1]))
792 {
793 this->gbump(-1);
794 *this->gptr() = traits_type::to_char_type(__c);
795 return __c;
796 }
797 }
798 return traits_type::eof();
799}
800
801template <class _CharT, class _Traits>
802typename basic_filebuf<_CharT, _Traits>::int_type
803basic_filebuf<_CharT, _Traits>::overflow(int_type __c)
804{
805 if (__file_ == 0)
806 return traits_type::eof();
807 __write_mode();
808 char_type __1buf;
809 char_type* __pb_save = this->pbase();
810 char_type* __epb_save = this->epptr();
811 if (!traits_type::eq_int_type(__c, traits_type::eof()))
812 {
813 if (this->pptr() == 0)
814 this->setp(&__1buf, &__1buf+1);
815 *this->pptr() = traits_type::to_char_type(__c);
816 this->pbump(1);
817 }
818 if (this->pptr() != this->pbase())
819 {
820 if (__always_noconv_)
821 {
822 size_t __nmemb = static_cast<size_t>(this->pptr() - this->pbase());
823 if (fwrite(this->pbase(), sizeof(char_type), __nmemb, __file_) != __nmemb)
824 return traits_type::eof();
825 }
826 else
827 {
828 char* __extbe = __extbuf_;
829 codecvt_base::result __r;
830 do
831 {
832 if (!__cv_)
833 __throw_bad_cast();
834
835 const char_type* __e;
836 __r = __cv_->out(__st_, this->pbase(), this->pptr(), __e,
837 __extbuf_, __extbuf_ + __ebs_, __extbe);
838 if (__e == this->pbase())
839 return traits_type::eof();
840 if (__r == codecvt_base::noconv)
841 {
842 size_t __nmemb = static_cast<size_t>(this->pptr() - this->pbase());
843 if (fwrite(this->pbase(), 1, __nmemb, __file_) != __nmemb)
844 return traits_type::eof();
845 }
846 else if (__r == codecvt_base::ok || __r == codecvt_base::partial)
847 {
848 size_t __nmemb = static_cast<size_t>(__extbe - __extbuf_);
849 if (fwrite(__extbuf_, 1, __nmemb, __file_) != __nmemb)
850 return traits_type::eof();
851 if (__r == codecvt_base::partial)
852 {
853 this->setp(const_cast<char_type*>(__e), this->pptr());
854 this->__pbump(this->epptr() - this->pbase());
855 }
856 }
857 else
858 return traits_type::eof();
859 } while (__r == codecvt_base::partial);
860 }
861 this->setp(__pb_save, __epb_save);
862 }
863 return traits_type::not_eof(__c);
864}
865
866template <class _CharT, class _Traits>
867basic_streambuf<_CharT, _Traits>*
868basic_filebuf<_CharT, _Traits>::setbuf(char_type* __s, streamsize __n)
869{
870 this->setg(0, 0, 0);
871 this->setp(0, 0);
872 if (__owns_eb_)
873 delete [] __extbuf_;
874 if (__owns_ib_)
875 delete [] __intbuf_;
876 __ebs_ = __n;
877 if (__ebs_ > sizeof(__extbuf_min_))
878 {
879 if (__always_noconv_ && __s)
880 {
881 __extbuf_ = (char*)__s;
882 __owns_eb_ = false;
883 }
884 else
885 {
886 __extbuf_ = new char[__ebs_];
887 __owns_eb_ = true;
888 }
889 }
890 else
891 {
892 __extbuf_ = __extbuf_min_;
893 __ebs_ = sizeof(__extbuf_min_);
894 __owns_eb_ = false;
895 }
896 if (!__always_noconv_)
897 {
898 __ibs_ = max<streamsize>(__n, sizeof(__extbuf_min_));
899 if (__s && __ibs_ >= sizeof(__extbuf_min_))
900 {
901 __intbuf_ = __s;
902 __owns_ib_ = false;
903 }
904 else
905 {
906 __intbuf_ = new char_type[__ibs_];
907 __owns_ib_ = true;
908 }
909 }
910 else
911 {
912 __ibs_ = 0;
913 __intbuf_ = 0;
914 __owns_ib_ = false;
915 }
916 return this;
917}
918
919template <class _CharT, class _Traits>
920typename basic_filebuf<_CharT, _Traits>::pos_type
921basic_filebuf<_CharT, _Traits>::seekoff(off_type __off, ios_base::seekdir __way,
922 ios_base::openmode)
923{
924 if (!__cv_)
925 __throw_bad_cast();
926
927 int __width = __cv_->encoding();
928 if (__file_ == 0 || (__width <= 0 && __off != 0) || sync())
929 return pos_type(off_type(-1));
930 // __width > 0 || __off == 0
931 int __whence;
932 switch (__way)
933 {
934 case ios_base::beg:
935 __whence = SEEK_SET;
936 break;
937 case ios_base::cur:
938 __whence = SEEK_CUR;
939 break;
940 case ios_base::end:
941 __whence = SEEK_END;
942 break;
943 default:
944 return pos_type(off_type(-1));
945 }
946#if defined(_LIBCPP_HAS_NO_OFF_T_FUNCTIONS)
947 if (fseek(__file_, __width > 0 ? __width * __off : 0, __whence))
948 return pos_type(off_type(-1));
949 pos_type __r = ftell(__file_);
950#else
951 if (fseeko(__file_, __width > 0 ? __width * __off : 0, __whence))
952 return pos_type(off_type(-1));
953 pos_type __r = ftello(__file_);
954#endif
955 __r.state(__st_);
956 return __r;
957}
958
959template <class _CharT, class _Traits>
960typename basic_filebuf<_CharT, _Traits>::pos_type
961basic_filebuf<_CharT, _Traits>::seekpos(pos_type __sp, ios_base::openmode)
962{
963 if (__file_ == 0 || sync())
964 return pos_type(off_type(-1));
965#if defined(_LIBCPP_HAS_NO_OFF_T_FUNCTIONS)
966 if (fseek(__file_, __sp, SEEK_SET))
967 return pos_type(off_type(-1));
968#else
969 if (fseeko(__file_, __sp, SEEK_SET))
970 return pos_type(off_type(-1));
971#endif
972 __st_ = __sp.state();
973 return __sp;
974}
975
976template <class _CharT, class _Traits>
977int
978basic_filebuf<_CharT, _Traits>::sync()
979{
980 if (__file_ == 0)
981 return 0;
982 if (!__cv_)
983 __throw_bad_cast();
984
985 if (__cm_ & ios_base::out)
986 {
987 if (this->pptr() != this->pbase())
988 if (overflow() == traits_type::eof())
989 return -1;
990 codecvt_base::result __r;
991 do
992 {
993 char* __extbe;
994 __r = __cv_->unshift(__st_, __extbuf_, __extbuf_ + __ebs_, __extbe);
995 size_t __nmemb = static_cast<size_t>(__extbe - __extbuf_);
996 if (fwrite(__extbuf_, 1, __nmemb, __file_) != __nmemb)
997 return -1;
998 } while (__r == codecvt_base::partial);
999 if (__r == codecvt_base::error)
1000 return -1;
1001 if (fflush(__file_))
1002 return -1;
1003 }
1004 else if (__cm_ & ios_base::in)
1005 {
1006 off_type __c;
1007 state_type __state = __st_last_;
1008 bool __update_st = false;
1009 if (__always_noconv_)
1010 __c = this->egptr() - this->gptr();
1011 else
1012 {
1013 int __width = __cv_->encoding();
1014 __c = __extbufend_ - __extbufnext_;
1015 if (__width > 0)
1016 __c += __width * (this->egptr() - this->gptr());
1017 else
1018 {
1019 if (this->gptr() != this->egptr())
1020 {
1021 const int __off = __cv_->length(__state, __extbuf_,
1022 __extbufnext_,
1023 this->gptr() - this->eback());
1024 __c += __extbufnext_ - __extbuf_ - __off;
1025 __update_st = true;
1026 }
1027 }
1028 }
1029#if defined(_LIBCPP_HAS_NO_OFF_T_FUNCTIONS)
1030 if (fseek(__file_, -__c, SEEK_CUR))
1031 return -1;
1032#else
1033 if (fseeko(__file_, -__c, SEEK_CUR))
1034 return -1;
1035#endif
1036 if (__update_st)
1037 __st_ = __state;
1038 __extbufnext_ = __extbufend_ = __extbuf_;
1039 this->setg(0, 0, 0);
1040 __cm_ = 0;
1041 }
1042 return 0;
1043}
1044
1045template <class _CharT, class _Traits>
1046void
1047basic_filebuf<_CharT, _Traits>::imbue(const locale& __loc)
1048{
1049 sync();
1050 __cv_ = &use_facet<codecvt<char_type, char, state_type> >(__loc);
1051 bool __old_anc = __always_noconv_;
1052 __always_noconv_ = __cv_->always_noconv();
1053 if (__old_anc != __always_noconv_)
1054 {
1055 this->setg(0, 0, 0);
1056 this->setp(0, 0);
1057 // invariant, char_type is char, else we couldn't get here
1058 if (__always_noconv_) // need to dump __intbuf_
1059 {
1060 if (__owns_eb_)
1061 delete [] __extbuf_;
1062 __owns_eb_ = __owns_ib_;
1063 __ebs_ = __ibs_;
1064 __extbuf_ = (char*)__intbuf_;
1065 __ibs_ = 0;
1066 __intbuf_ = 0;
1067 __owns_ib_ = false;
1068 }
1069 else // need to obtain an __intbuf_.
1070 { // If __extbuf_ is user-supplied, use it, else new __intbuf_
1071 if (!__owns_eb_ && __extbuf_ != __extbuf_min_)
1072 {
1073 __ibs_ = __ebs_;
1074 __intbuf_ = (char_type*)__extbuf_;
1075 __owns_ib_ = false;
1076 __extbuf_ = new char[__ebs_];
1077 __owns_eb_ = true;
1078 }
1079 else
1080 {
1081 __ibs_ = __ebs_;
1082 __intbuf_ = new char_type[__ibs_];
1083 __owns_ib_ = true;
1084 }
1085 }
1086 }
1087}
1088
1089template <class _CharT, class _Traits>
1090bool
1091basic_filebuf<_CharT, _Traits>::__read_mode()
1092{
1093 if (!(__cm_ & ios_base::in))
1094 {
1095 this->setp(0, 0);
1096 if (__always_noconv_)
1097 this->setg((char_type*)__extbuf_,
1098 (char_type*)__extbuf_ + __ebs_,
1099 (char_type*)__extbuf_ + __ebs_);
1100 else
1101 this->setg(__intbuf_, __intbuf_ + __ibs_, __intbuf_ + __ibs_);
1102 __cm_ = ios_base::in;
1103 return true;
1104 }
1105 return false;
1106}
1107
1108template <class _CharT, class _Traits>
1109void
1110basic_filebuf<_CharT, _Traits>::__write_mode()
1111{
1112 if (!(__cm_ & ios_base::out))
1113 {
1114 this->setg(0, 0, 0);
1115 if (__ebs_ > sizeof(__extbuf_min_))
1116 {
1117 if (__always_noconv_)
1118 this->setp((char_type*)__extbuf_,
1119 (char_type*)__extbuf_ + (__ebs_ - 1));
1120 else
1121 this->setp(__intbuf_, __intbuf_ + (__ibs_ - 1));
1122 }
1123 else
1124 this->setp(0, 0);
1125 __cm_ = ios_base::out;
1126 }
1127}
1128
1129// basic_ifstream
1130
1131template <class _CharT, class _Traits>
1132class _LIBCPP_TEMPLATE_VIS basic_ifstream
1133 : public basic_istream<_CharT, _Traits>
1134{
1135public:
1136 typedef _CharT char_type;
1137 typedef _Traits traits_type;
1138 typedef typename traits_type::int_type int_type;
1139 typedef typename traits_type::pos_type pos_type;
1140 typedef typename traits_type::off_type off_type;
1141
1142 _LIBCPP_INLINE_VISIBILITY
1143 basic_ifstream();
1144#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
1145 _LIBCPP_INLINE_VISIBILITY
1146 explicit basic_ifstream(const char* __s, ios_base::openmode __mode = ios_base::in);
1147#ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
1148 _LIBCPP_INLINE_VISIBILITY
1149 explicit basic_ifstream(const wchar_t* __s, ios_base::openmode __mode = ios_base::in);
1150#endif
1151 _LIBCPP_INLINE_VISIBILITY
1152 explicit basic_ifstream(const string& __s, ios_base::openmode __mode = ios_base::in);
1153#if _LIBCPP_STD_VER >= 17
1154 _LIBCPP_AVAILABILITY_FILESYSTEM _LIBCPP_INLINE_VISIBILITY
1155 explicit basic_ifstream(const filesystem::path& __p, ios_base::openmode __mode = ios_base::in)
1156 : basic_ifstream(__p.c_str(), __mode) {}
1157#endif // _LIBCPP_STD_VER >= 17
1158#endif
1159#ifndef _LIBCPP_CXX03_LANG
1160 _LIBCPP_INLINE_VISIBILITY
1161 basic_ifstream(basic_ifstream&& __rhs);
1162
1163 _LIBCPP_INLINE_VISIBILITY
1164 basic_ifstream& operator=(basic_ifstream&& __rhs);
1165#endif
1166 _LIBCPP_INLINE_VISIBILITY
1167 void swap(basic_ifstream& __rhs);
1168
1169 _LIBCPP_INLINE_VISIBILITY
1170 basic_filebuf<char_type, traits_type>* rdbuf() const;
1171 _LIBCPP_INLINE_VISIBILITY
1172 bool is_open() const;
1173#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
1174 void open(const char* __s, ios_base::openmode __mode = ios_base::in);
1175#ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
1176 void open(const wchar_t* __s, ios_base::openmode __mode = ios_base::in);
1177#endif
1178 void open(const string& __s, ios_base::openmode __mode = ios_base::in);
1179#if _LIBCPP_STD_VER >= 17
1180 _LIBCPP_AVAILABILITY_FILESYSTEM _LIBCPP_INLINE_VISIBILITY
1181 void open(const filesystem::path& __p,
1182 ios_base::openmode __mode = ios_base::in) {
1183 return open(__p.c_str(), __mode);
1184 }
1185#endif // _LIBCPP_STD_VER >= 17
1186
1187 _LIBCPP_INLINE_VISIBILITY
1188 void __open(int __fd, ios_base::openmode __mode);
1189#endif
1190 _LIBCPP_INLINE_VISIBILITY
1191 void close();
1192
1193private:
1194 basic_filebuf<char_type, traits_type> __sb_;
1195};
1196
1197template <class _CharT, class _Traits>
1198inline
1199basic_ifstream<_CharT, _Traits>::basic_ifstream()
1200 : basic_istream<char_type, traits_type>(&__sb_)
1201{
1202}
1203
1204#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
1205template <class _CharT, class _Traits>
1206inline
1207basic_ifstream<_CharT, _Traits>::basic_ifstream(const char* __s, ios_base::openmode __mode)
1208 : basic_istream<char_type, traits_type>(&__sb_)
1209{
1210 if (__sb_.open(__s, __mode | ios_base::in) == 0)
1211 this->setstate(ios_base::failbit);
1212}
1213
1214#ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
1215template <class _CharT, class _Traits>
1216inline
1217basic_ifstream<_CharT, _Traits>::basic_ifstream(const wchar_t* __s, ios_base::openmode __mode)
1218 : basic_istream<char_type, traits_type>(&__sb_)
1219{
1220 if (__sb_.open(__s, __mode | ios_base::in) == 0)
1221 this->setstate(ios_base::failbit);
1222}
1223#endif
1224
1225template <class _CharT, class _Traits>
1226inline
1227basic_ifstream<_CharT, _Traits>::basic_ifstream(const string& __s, ios_base::openmode __mode)
1228 : basic_istream<char_type, traits_type>(&__sb_)
1229{
1230 if (__sb_.open(__s, __mode | ios_base::in) == 0)
1231 this->setstate(ios_base::failbit);
1232}
1233#endif
1234
1235#ifndef _LIBCPP_CXX03_LANG
1236
1237template <class _CharT, class _Traits>
1238inline
1239basic_ifstream<_CharT, _Traits>::basic_ifstream(basic_ifstream&& __rhs)
1240 : basic_istream<char_type, traits_type>(_VSTD::move(__rhs)),
1241 __sb_(_VSTD::move(__rhs.__sb_))
1242{
1243 this->set_rdbuf(&__sb_);
1244}
1245
1246template <class _CharT, class _Traits>
1247inline
1248basic_ifstream<_CharT, _Traits>&
1249basic_ifstream<_CharT, _Traits>::operator=(basic_ifstream&& __rhs)
1250{
1251 basic_istream<char_type, traits_type>::operator=(_VSTD::move(__rhs));
1252 __sb_ = _VSTD::move(__rhs.__sb_);
1253 return *this;
1254}
1255
1256#endif // _LIBCPP_CXX03_LANG
1257
1258template <class _CharT, class _Traits>
1259inline
1260void
1261basic_ifstream<_CharT, _Traits>::swap(basic_ifstream& __rhs)
1262{
1263 basic_istream<char_type, traits_type>::swap(__rhs);
1264 __sb_.swap(__rhs.__sb_);
1265}
1266
1267template <class _CharT, class _Traits>
1268inline _LIBCPP_INLINE_VISIBILITY
1269void
1270swap(basic_ifstream<_CharT, _Traits>& __x, basic_ifstream<_CharT, _Traits>& __y)
1271{
1272 __x.swap(__y);
1273}
1274
1275template <class _CharT, class _Traits>
1276inline
1277basic_filebuf<_CharT, _Traits>*
1278basic_ifstream<_CharT, _Traits>::rdbuf() const
1279{
1280 return const_cast<basic_filebuf<char_type, traits_type>*>(&__sb_);
1281}
1282
1283template <class _CharT, class _Traits>
1284inline
1285bool
1286basic_ifstream<_CharT, _Traits>::is_open() const
1287{
1288 return __sb_.is_open();
1289}
1290
1291#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
1292template <class _CharT, class _Traits>
1293void
1294basic_ifstream<_CharT, _Traits>::open(const char* __s, ios_base::openmode __mode)
1295{
1296 if (__sb_.open(__s, __mode | ios_base::in))
1297 this->clear();
1298 else
1299 this->setstate(ios_base::failbit);
1300}
1301
1302#ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
1303template <class _CharT, class _Traits>
1304void
1305basic_ifstream<_CharT, _Traits>::open(const wchar_t* __s, ios_base::openmode __mode)
1306{
1307 if (__sb_.open(__s, __mode | ios_base::in))
1308 this->clear();
1309 else
1310 this->setstate(ios_base::failbit);
1311}
1312#endif
1313
1314template <class _CharT, class _Traits>
1315void
1316basic_ifstream<_CharT, _Traits>::open(const string& __s, ios_base::openmode __mode)
1317{
1318 if (__sb_.open(__s, __mode | ios_base::in))
1319 this->clear();
1320 else
1321 this->setstate(ios_base::failbit);
1322}
1323
1324template <class _CharT, class _Traits>
1325void basic_ifstream<_CharT, _Traits>::__open(int __fd,
1326 ios_base::openmode __mode) {
1327 if (__sb_.__open(__fd, __mode | ios_base::in))
1328 this->clear();
1329 else
1330 this->setstate(ios_base::failbit);
1331}
1332#endif
1333
1334template <class _CharT, class _Traits>
1335inline
1336void
1337basic_ifstream<_CharT, _Traits>::close()
1338{
1339 if (__sb_.close() == 0)
1340 this->setstate(ios_base::failbit);
1341}
1342
1343// basic_ofstream
1344
1345template <class _CharT, class _Traits>
1346class _LIBCPP_TEMPLATE_VIS basic_ofstream
1347 : public basic_ostream<_CharT, _Traits>
1348{
1349public:
1350 typedef _CharT char_type;
1351 typedef _Traits traits_type;
1352 typedef typename traits_type::int_type int_type;
1353 typedef typename traits_type::pos_type pos_type;
1354 typedef typename traits_type::off_type off_type;
1355
1356 _LIBCPP_INLINE_VISIBILITY
1357 basic_ofstream();
1358 _LIBCPP_INLINE_VISIBILITY
1359 explicit basic_ofstream(const char* __s, ios_base::openmode __mode = ios_base::out);
1360#ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
1361 _LIBCPP_INLINE_VISIBILITY
1362 explicit basic_ofstream(const wchar_t* __s, ios_base::openmode __mode = ios_base::out);
1363#endif
1364 _LIBCPP_INLINE_VISIBILITY
1365 explicit basic_ofstream(const string& __s, ios_base::openmode __mode = ios_base::out);
1366
1367#if _LIBCPP_STD_VER >= 17
1368 _LIBCPP_AVAILABILITY_FILESYSTEM _LIBCPP_INLINE_VISIBILITY
1369 explicit basic_ofstream(const filesystem::path& __p, ios_base::openmode __mode = ios_base::out)
1370 : basic_ofstream(__p.c_str(), __mode) {}
1371#endif // _LIBCPP_STD_VER >= 17
1372
1373#ifndef _LIBCPP_CXX03_LANG
1374 _LIBCPP_INLINE_VISIBILITY
1375 basic_ofstream(basic_ofstream&& __rhs);
1376
1377 _LIBCPP_INLINE_VISIBILITY
1378 basic_ofstream& operator=(basic_ofstream&& __rhs);
1379#endif
1380 _LIBCPP_INLINE_VISIBILITY
1381 void swap(basic_ofstream& __rhs);
1382
1383 _LIBCPP_INLINE_VISIBILITY
1384 basic_filebuf<char_type, traits_type>* rdbuf() const;
1385 _LIBCPP_INLINE_VISIBILITY
1386 bool is_open() const;
1387#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
1388 void open(const char* __s, ios_base::openmode __mode = ios_base::out);
1389#ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
1390 void open(const wchar_t* __s, ios_base::openmode __mode = ios_base::out);
1391#endif
1392 void open(const string& __s, ios_base::openmode __mode = ios_base::out);
1393
1394#if _LIBCPP_STD_VER >= 17
1395 _LIBCPP_AVAILABILITY_FILESYSTEM _LIBCPP_INLINE_VISIBILITY
1396 void open(const filesystem::path& __p, ios_base::openmode __mode = ios_base::out)
1397 { return open(__p.c_str(), __mode); }
1398#endif // _LIBCPP_STD_VER >= 17
1399
1400 _LIBCPP_INLINE_VISIBILITY
1401 void __open(int __fd, ios_base::openmode __mode);
1402#endif
1403 _LIBCPP_INLINE_VISIBILITY
1404 void close();
1405
1406private:
1407 basic_filebuf<char_type, traits_type> __sb_;
1408};
1409
1410template <class _CharT, class _Traits>
1411inline
1412basic_ofstream<_CharT, _Traits>::basic_ofstream()
1413 : basic_ostream<char_type, traits_type>(&__sb_)
1414{
1415}
1416
1417#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
1418template <class _CharT, class _Traits>
1419inline
1420basic_ofstream<_CharT, _Traits>::basic_ofstream(const char* __s, ios_base::openmode __mode)
1421 : basic_ostream<char_type, traits_type>(&__sb_)
1422{
1423 if (__sb_.open(__s, __mode | ios_base::out) == 0)
1424 this->setstate(ios_base::failbit);
1425}
1426
1427#ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
1428template <class _CharT, class _Traits>
1429inline
1430basic_ofstream<_CharT, _Traits>::basic_ofstream(const wchar_t* __s, ios_base::openmode __mode)
1431 : basic_ostream<char_type, traits_type>(&__sb_)
1432{
1433 if (__sb_.open(__s, __mode | ios_base::out) == 0)
1434 this->setstate(ios_base::failbit);
1435}
1436#endif
1437
1438template <class _CharT, class _Traits>
1439inline
1440basic_ofstream<_CharT, _Traits>::basic_ofstream(const string& __s, ios_base::openmode __mode)
1441 : basic_ostream<char_type, traits_type>(&__sb_)
1442{
1443 if (__sb_.open(__s, __mode | ios_base::out) == 0)
1444 this->setstate(ios_base::failbit);
1445}
1446#endif
1447
1448#ifndef _LIBCPP_CXX03_LANG
1449
1450template <class _CharT, class _Traits>
1451inline
1452basic_ofstream<_CharT, _Traits>::basic_ofstream(basic_ofstream&& __rhs)
1453 : basic_ostream<char_type, traits_type>(_VSTD::move(__rhs)),
1454 __sb_(_VSTD::move(__rhs.__sb_))
1455{
1456 this->set_rdbuf(&__sb_);
1457}
1458
1459template <class _CharT, class _Traits>
1460inline
1461basic_ofstream<_CharT, _Traits>&
1462basic_ofstream<_CharT, _Traits>::operator=(basic_ofstream&& __rhs)
1463{
1464 basic_ostream<char_type, traits_type>::operator=(_VSTD::move(__rhs));
1465 __sb_ = _VSTD::move(__rhs.__sb_);
1466 return *this;
1467}
1468
1469#endif // _LIBCPP_CXX03_LANG
1470
1471template <class _CharT, class _Traits>
1472inline
1473void
1474basic_ofstream<_CharT, _Traits>::swap(basic_ofstream& __rhs)
1475{
1476 basic_ostream<char_type, traits_type>::swap(__rhs);
1477 __sb_.swap(__rhs.__sb_);
1478}
1479
1480template <class _CharT, class _Traits>
1481inline _LIBCPP_INLINE_VISIBILITY
1482void
1483swap(basic_ofstream<_CharT, _Traits>& __x, basic_ofstream<_CharT, _Traits>& __y)
1484{
1485 __x.swap(__y);
1486}
1487
1488template <class _CharT, class _Traits>
1489inline
1490basic_filebuf<_CharT, _Traits>*
1491basic_ofstream<_CharT, _Traits>::rdbuf() const
1492{
1493 return const_cast<basic_filebuf<char_type, traits_type>*>(&__sb_);
1494}
1495
1496template <class _CharT, class _Traits>
1497inline
1498bool
1499basic_ofstream<_CharT, _Traits>::is_open() const
1500{
1501 return __sb_.is_open();
1502}
1503
1504#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
1505template <class _CharT, class _Traits>
1506void
1507basic_ofstream<_CharT, _Traits>::open(const char* __s, ios_base::openmode __mode)
1508{
1509 if (__sb_.open(__s, __mode | ios_base::out))
1510 this->clear();
1511 else
1512 this->setstate(ios_base::failbit);
1513}
1514
1515#ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
1516template <class _CharT, class _Traits>
1517void
1518basic_ofstream<_CharT, _Traits>::open(const wchar_t* __s, ios_base::openmode __mode)
1519{
1520 if (__sb_.open(__s, __mode | ios_base::out))
1521 this->clear();
1522 else
1523 this->setstate(ios_base::failbit);
1524}
1525#endif
1526
1527template <class _CharT, class _Traits>
1528void
1529basic_ofstream<_CharT, _Traits>::open(const string& __s, ios_base::openmode __mode)
1530{
1531 if (__sb_.open(__s, __mode | ios_base::out))
1532 this->clear();
1533 else
1534 this->setstate(ios_base::failbit);
1535}
1536
1537template <class _CharT, class _Traits>
1538void basic_ofstream<_CharT, _Traits>::__open(int __fd,
1539 ios_base::openmode __mode) {
1540 if (__sb_.__open(__fd, __mode | ios_base::out))
1541 this->clear();
1542 else
1543 this->setstate(ios_base::failbit);
1544}
1545#endif
1546
1547template <class _CharT, class _Traits>
1548inline
1549void
1550basic_ofstream<_CharT, _Traits>::close()
1551{
1552 if (__sb_.close() == 0)
1553 this->setstate(ios_base::failbit);
1554}
1555
1556// basic_fstream
1557
1558template <class _CharT, class _Traits>
1559class _LIBCPP_TEMPLATE_VIS basic_fstream
1560 : public basic_iostream<_CharT, _Traits>
1561{
1562public:
1563 typedef _CharT char_type;
1564 typedef _Traits traits_type;
1565 typedef typename traits_type::int_type int_type;
1566 typedef typename traits_type::pos_type pos_type;
1567 typedef typename traits_type::off_type off_type;
1568
1569 _LIBCPP_INLINE_VISIBILITY
1570 basic_fstream();
1571#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
1572 _LIBCPP_INLINE_VISIBILITY
1573 explicit basic_fstream(const char* __s, ios_base::openmode __mode = ios_base::in | ios_base::out);
1574#ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
1575 _LIBCPP_INLINE_VISIBILITY
1576 explicit basic_fstream(const wchar_t* __s, ios_base::openmode __mode = ios_base::in | ios_base::out);
1577#endif
1578 _LIBCPP_INLINE_VISIBILITY
1579 explicit basic_fstream(const string& __s, ios_base::openmode __mode = ios_base::in | ios_base::out);
1580
1581#if _LIBCPP_STD_VER >= 17
1582 _LIBCPP_AVAILABILITY_FILESYSTEM _LIBCPP_INLINE_VISIBILITY
1583 explicit basic_fstream(const filesystem::path& __p, ios_base::openmode __mode = ios_base::in | ios_base::out)
1584 : basic_fstream(__p.c_str(), __mode) {}
1585#endif // _LIBCPP_STD_VER >= 17
1586
1587#endif
1588#ifndef _LIBCPP_CXX03_LANG
1589 _LIBCPP_INLINE_VISIBILITY
1590 basic_fstream(basic_fstream&& __rhs);
1591
1592 _LIBCPP_INLINE_VISIBILITY
1593 basic_fstream& operator=(basic_fstream&& __rhs);
1594#endif
1595 _LIBCPP_INLINE_VISIBILITY
1596 void swap(basic_fstream& __rhs);
1597
1598 _LIBCPP_INLINE_VISIBILITY
1599 basic_filebuf<char_type, traits_type>* rdbuf() const;
1600 _LIBCPP_INLINE_VISIBILITY
1601 bool is_open() const;
1602#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
1603 void open(const char* __s, ios_base::openmode __mode = ios_base::in | ios_base::out);
1604#ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
1605 void open(const wchar_t* __s, ios_base::openmode __mode = ios_base::in | ios_base::out);
1606#endif
1607 void open(const string& __s, ios_base::openmode __mode = ios_base::in | ios_base::out);
1608
1609#if _LIBCPP_STD_VER >= 17
1610 _LIBCPP_AVAILABILITY_FILESYSTEM _LIBCPP_INLINE_VISIBILITY
1611 void open(const filesystem::path& __p, ios_base::openmode __mode = ios_base::in|ios_base::out)
1612 { return open(__p.c_str(), __mode); }
1613#endif // _LIBCPP_STD_VER >= 17
1614
1615#endif
1616 _LIBCPP_INLINE_VISIBILITY
1617 void close();
1618
1619private:
1620 basic_filebuf<char_type, traits_type> __sb_;
1621};
1622
1623template <class _CharT, class _Traits>
1624inline
1625basic_fstream<_CharT, _Traits>::basic_fstream()
1626 : basic_iostream<char_type, traits_type>(&__sb_)
1627{
1628}
1629
1630#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
1631template <class _CharT, class _Traits>
1632inline
1633basic_fstream<_CharT, _Traits>::basic_fstream(const char* __s, ios_base::openmode __mode)
1634 : basic_iostream<char_type, traits_type>(&__sb_)
1635{
1636 if (__sb_.open(__s, __mode) == 0)
1637 this->setstate(ios_base::failbit);
1638}
1639
1640#ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
1641template <class _CharT, class _Traits>
1642inline
1643basic_fstream<_CharT, _Traits>::basic_fstream(const wchar_t* __s, ios_base::openmode __mode)
1644 : basic_iostream<char_type, traits_type>(&__sb_)
1645{
1646 if (__sb_.open(__s, __mode) == 0)
1647 this->setstate(ios_base::failbit);
1648}
1649#endif
1650
1651template <class _CharT, class _Traits>
1652inline
1653basic_fstream<_CharT, _Traits>::basic_fstream(const string& __s, ios_base::openmode __mode)
1654 : basic_iostream<char_type, traits_type>(&__sb_)
1655{
1656 if (__sb_.open(__s, __mode) == 0)
1657 this->setstate(ios_base::failbit);
1658}
1659#endif
1660
1661#ifndef _LIBCPP_CXX03_LANG
1662
1663template <class _CharT, class _Traits>
1664inline
1665basic_fstream<_CharT, _Traits>::basic_fstream(basic_fstream&& __rhs)
1666 : basic_iostream<char_type, traits_type>(_VSTD::move(__rhs)),
1667 __sb_(_VSTD::move(__rhs.__sb_))
1668{
1669 this->set_rdbuf(&__sb_);
1670}
1671
1672template <class _CharT, class _Traits>
1673inline
1674basic_fstream<_CharT, _Traits>&
1675basic_fstream<_CharT, _Traits>::operator=(basic_fstream&& __rhs)
1676{
1677 basic_iostream<char_type, traits_type>::operator=(_VSTD::move(__rhs));
1678 __sb_ = _VSTD::move(__rhs.__sb_);
1679 return *this;
1680}
1681
1682#endif // _LIBCPP_CXX03_LANG
1683
1684template <class _CharT, class _Traits>
1685inline
1686void
1687basic_fstream<_CharT, _Traits>::swap(basic_fstream& __rhs)
1688{
1689 basic_iostream<char_type, traits_type>::swap(__rhs);
1690 __sb_.swap(__rhs.__sb_);
1691}
1692
1693template <class _CharT, class _Traits>
1694inline _LIBCPP_INLINE_VISIBILITY
1695void
1696swap(basic_fstream<_CharT, _Traits>& __x, basic_fstream<_CharT, _Traits>& __y)
1697{
1698 __x.swap(__y);
1699}
1700
1701template <class _CharT, class _Traits>
1702inline
1703basic_filebuf<_CharT, _Traits>*
1704basic_fstream<_CharT, _Traits>::rdbuf() const
1705{
1706 return const_cast<basic_filebuf<char_type, traits_type>*>(&__sb_);
1707}
1708
1709template <class _CharT, class _Traits>
1710inline
1711bool
1712basic_fstream<_CharT, _Traits>::is_open() const
1713{
1714 return __sb_.is_open();
1715}
1716
1717#ifndef _LIBCPP_HAS_NO_GLOBAL_FILESYSTEM_NAMESPACE
1718template <class _CharT, class _Traits>
1719void
1720basic_fstream<_CharT, _Traits>::open(const char* __s, ios_base::openmode __mode)
1721{
1722 if (__sb_.open(__s, __mode))
1723 this->clear();
1724 else
1725 this->setstate(ios_base::failbit);
1726}
1727
1728#ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
1729template <class _CharT, class _Traits>
1730void
1731basic_fstream<_CharT, _Traits>::open(const wchar_t* __s, ios_base::openmode __mode)
1732{
1733 if (__sb_.open(__s, __mode))
1734 this->clear();
1735 else
1736 this->setstate(ios_base::failbit);
1737}
1738#endif
1739
1740template <class _CharT, class _Traits>
1741void
1742basic_fstream<_CharT, _Traits>::open(const string& __s, ios_base::openmode __mode)
1743{
1744 if (__sb_.open(__s, __mode))
1745 this->clear();
1746 else
1747 this->setstate(ios_base::failbit);
1748}
1749#endif
1750
1751template <class _CharT, class _Traits>
1752inline
1753void
1754basic_fstream<_CharT, _Traits>::close()
1755{
1756 if (__sb_.close() == 0)
1757 this->setstate(ios_base::failbit);
1758}
1759
1760_LIBCPP_END_NAMESPACE_STD
1761
1762_LIBCPP_POP_MACROS
1763
1764#endif // _LIBCPP_FSTREAM
1765