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