// -*- C++ -*-
//===----------------------------------------------------------------------===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//

#ifndef _LIBCPP_FSTREAM
#define _LIBCPP_FSTREAM

/*
    fstream synopsis

template <class charT, class traits = char_traits<charT> >
class basic_filebuf
    : public basic_streambuf<charT, traits>
{
public:
    typedef charT                          char_type;
    typedef traits                         traits_type;
    typedef typename traits_type::int_type int_type;
    typedef typename traits_type::pos_type pos_type;
    typedef typename traits_type::off_type off_type;

    // 27.9.1.2 Constructors/destructor:
    basic_filebuf();
    basic_filebuf(basic_filebuf&& rhs);
    virtual ~basic_filebuf();

    // 27.9.1.3 Assign/swap:
    basic_filebuf& operator=(basic_filebuf&& rhs);
    void swap(basic_filebuf& rhs);

    // 27.9.1.4 Members:
    bool is_open() const;
    basic_filebuf* open(const char* s, ios_base::openmode mode);
    basic_filebuf* open(const string& s, ios_base::openmode mode);
    basic_filebuf* open(const filesystem::path& p, ios_base::openmode mode); // C++17
    basic_filebuf* close();

protected:
    // 27.9.1.5 Overridden virtual functions:
    virtual streamsize showmanyc();
    virtual int_type underflow();
    virtual int_type uflow();
    virtual int_type pbackfail(int_type c = traits_type::eof());
    virtual int_type overflow (int_type c = traits_type::eof());
    virtual basic_streambuf<char_type, traits_type>* setbuf(char_type* s, streamsize n);
    virtual pos_type seekoff(off_type off, ios_base::seekdir way,
                             ios_base::openmode which = ios_base::in | ios_base::out);
    virtual pos_type seekpos(pos_type sp,
                             ios_base::openmode which = ios_base::in | ios_base::out);
    virtual int sync();
    virtual void imbue(const locale& loc);
};

template <class charT, class traits>
  void
  swap(basic_filebuf<charT, traits>& x, basic_filebuf<charT, traits>& y);

typedef basic_filebuf<char>    filebuf;
typedef basic_filebuf<wchar_t> wfilebuf;

template <class charT, class traits = char_traits<charT> >
class basic_ifstream
    : public basic_istream<charT,traits>
{
public:
    typedef charT                          char_type;
    typedef traits                         traits_type;
    typedef typename traits_type::int_type int_type;
    typedef typename traits_type::pos_type pos_type;
    typedef typename traits_type::off_type off_type;
    using native_handle_type = typename basic_filebuf<charT, traits>::native_handle_type; // Since C++26

    basic_ifstream();
    explicit basic_ifstream(const char* s, ios_base::openmode mode = ios_base::in);
    explicit basic_ifstream(const string& s, ios_base::openmode mode = ios_base::in);
    explicit basic_ifstream(const filesystem::path& p,
                            ios_base::openmode mode = ios_base::in); // C++17
    basic_ifstream(basic_ifstream&& rhs);

    basic_ifstream& operator=(basic_ifstream&& rhs);
    void swap(basic_ifstream& rhs);

    basic_filebuf<char_type, traits_type>* rdbuf() const;
    native_handle_type native_handle() const noexcept; // Since C++26
    bool is_open() const;
    void open(const char* s, ios_base::openmode mode = ios_base::in);
    void open(const string& s, ios_base::openmode mode = ios_base::in);
    void open(const filesystem::path& s, ios_base::openmode mode = ios_base::in); // C++17

    void close();
};

template <class charT, class traits>
  void
  swap(basic_ifstream<charT, traits>& x, basic_ifstream<charT, traits>& y);

typedef basic_ifstream<char>    ifstream;
typedef basic_ifstream<wchar_t> wifstream;

template <class charT, class traits = char_traits<charT> >
class basic_ofstream
    : public basic_ostream<charT,traits>
{
public:
    typedef charT                          char_type;
    typedef traits                         traits_type;
    typedef typename traits_type::int_type int_type;
    typedef typename traits_type::pos_type pos_type;
    typedef typename traits_type::off_type off_type;
    using native_handle_type = typename basic_filebuf<charT, traits>::native_handle_type; // Since C++26

    basic_ofstream();
    explicit basic_ofstream(const char* s, ios_base::openmode mode = ios_base::out);
    explicit basic_ofstream(const string& s, ios_base::openmode mode = ios_base::out);
    explicit basic_ofstream(const filesystem::path& p,
                            ios_base::openmode mode = ios_base::out); // C++17
    basic_ofstream(basic_ofstream&& rhs);

    basic_ofstream& operator=(basic_ofstream&& rhs);
    void swap(basic_ofstream& rhs);

    basic_filebuf<char_type, traits_type>* rdbuf() const;
    native_handle_type native_handle() const noexcept; // Since C++26

    bool is_open() const;
    void open(const char* s, ios_base::openmode mode = ios_base::out);
    void open(const string& s, ios_base::openmode mode = ios_base::out);
    void open(const filesystem::path& p,
              ios_base::openmode mode = ios_base::out); // C++17

    void close();
};

template <class charT, class traits>
  void
  swap(basic_ofstream<charT, traits>& x, basic_ofstream<charT, traits>& y);

typedef basic_ofstream<char>    ofstream;
typedef basic_ofstream<wchar_t> wofstream;

template <class charT, class traits=char_traits<charT> >
class basic_fstream
    : public basic_iostream<charT,traits>
{
public:
    typedef charT                          char_type;
    typedef traits                         traits_type;
    typedef typename traits_type::int_type int_type;
    typedef typename traits_type::pos_type pos_type;
    typedef typename traits_type::off_type off_type;
    using native_handle_type = typename basic_filebuf<charT, traits>::native_handle_type; // Since C++26

    basic_fstream();
    explicit basic_fstream(const char* s, ios_base::openmode mode = ios_base::in|ios_base::out);
    explicit basic_fstream(const string& s, ios_base::openmode mode = ios_base::in|ios_base::out);
    explicit basic_fstream(const filesystem::path& p,
                           ios_base::openmode mode = ios_base::in|ios_base::out); C++17
    basic_fstream(basic_fstream&& rhs);

    basic_fstream& operator=(basic_fstream&& rhs);
    void swap(basic_fstream& rhs);

    basic_filebuf<char_type, traits_type>* rdbuf() const;
    native_handle_type native_handle() const noexcept; // Since C++26
    bool is_open() const;
    void open(const char* s, ios_base::openmode mode = ios_base::in|ios_base::out);
    void open(const string& s, ios_base::openmode mode = ios_base::in|ios_base::out);
    void open(const filesystem::path& s,
              ios_base::openmode mode = ios_base::in|ios_base::out); // C++17

    void close();
};

template <class charT, class traits>
  void swap(basic_fstream<charT, traits>& x, basic_fstream<charT, traits>& y);

typedef basic_fstream<char>    fstream;
typedef basic_fstream<wchar_t> wfstream;

}  // std

*/

#include <__algorithm/max.h>
#include <__assert> // all public C++ headers provide the assertion handler
#include <__availability>
#include <__config>
#include <__fwd/fstream.h>
#include <__locale>
#include <__utility/move.h>
#include <__utility/swap.h>
#include <__utility/unreachable.h>
#include <cstdio>
#include <filesystem>
#include <istream>
#include <ostream>
#include <typeinfo>
#include <version>

#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
#  pragma GCC system_header
#endif

_LIBCPP_PUSH_MACROS
#include <__undef_macros>

#if defined(_LIBCPP_MSVCRT) || defined(_NEWLIB_VERSION)
#  define _LIBCPP_HAS_NO_OFF_T_FUNCTIONS
#endif

#if !defined(_LIBCPP_HAS_NO_FILESYSTEM)

_LIBCPP_BEGIN_NAMESPACE_STD

#  if _LIBCPP_STD_VER >= 26 && defined(_LIBCPP_WIN32API)
_LIBCPP_EXPORTED_FROM_ABI void* __filebuf_windows_native_handle(FILE* __file) noexcept;
#  endif

template <class _CharT, class _Traits>
class _LIBCPP_TEMPLATE_VIS basic_filebuf : public basic_streambuf<_CharT, _Traits> {
public:
  typedef _CharT char_type;
  typedef _Traits traits_type;
  typedef typename traits_type::int_type int_type;
  typedef typename traits_type::pos_type pos_type;
  typedef typename traits_type::off_type off_type;
  typedef typename traits_type::state_type state_type;
#  if _LIBCPP_STD_VER >= 26
#    if defined(_LIBCPP_WIN32API)
  using native_handle_type = void*; // HANDLE
#    elif __has_include(<unistd.h>)
  using native_handle_type = int; // POSIX file descriptor
#    else
#      error "Provide a native file handle!"
#    endif
#  endif

  // 27.9.1.2 Constructors/destructor:
  basic_filebuf();
  basic_filebuf(basic_filebuf&& __rhs);
  ~basic_filebuf() override;

  // 27.9.1.3 Assign/swap:
  _LIBCPP_HIDE_FROM_ABI basic_filebuf& operator=(basic_filebuf&& __rhs);
  void swap(basic_filebuf& __rhs);

  // 27.9.1.4 Members:
  _LIBCPP_HIDE_FROM_ABI bool is_open() const;
  basic_filebuf* open(const char* __s, ios_base::openmode __mode);
#  ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
  basic_filebuf* open(const wchar_t* __s, ios_base::openmode __mode);
#  endif
  _LIBCPP_HIDE_FROM_ABI basic_filebuf* open(const string& __s, ios_base::openmode __mode);

#  if _LIBCPP_STD_VER >= 17
  _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY _LIBCPP_HIDE_FROM_ABI basic_filebuf*
  open(const filesystem::path& __p, ios_base::openmode __mode) {
    return open(__p.c_str(), __mode);
  }
#  endif
  _LIBCPP_HIDE_FROM_ABI basic_filebuf* __open(int __fd, ios_base::openmode __mode);
  basic_filebuf* close();
#  if _LIBCPP_STD_VER >= 26
  _LIBCPP_HIDE_FROM_ABI native_handle_type native_handle() const noexcept {
    _LIBCPP_ASSERT_UNCATEGORIZED(this->is_open(), "File must be opened");
#    if defined(_LIBCPP_WIN32API)
    return std::__filebuf_windows_native_handle(__file_);
#    elif __has_include(<unistd.h>)
    return fileno(__file_);
#    else
#      error "Provide a way to determine the file native handle!"
#    endif
  }
#  endif //  _LIBCPP_STD_VER >= 26

  _LIBCPP_HIDE_FROM_ABI inline static const char* __make_mdstring(ios_base::openmode __mode) _NOEXCEPT;

protected:
  // 27.9.1.5 Overridden virtual functions:
  int_type underflow() override;
  int_type pbackfail(int_type __c = traits_type::eof()) override;
  int_type overflow(int_type __c = traits_type::eof()) override;
  basic_streambuf<char_type, traits_type>* setbuf(char_type* __s, streamsize __n) override;
  pos_type
  seekoff(off_type __off, ios_base::seekdir __way, ios_base::openmode __wch = ios_base::in | ios_base::out) override;
  pos_type seekpos(pos_type __sp, ios_base::openmode __wch = ios_base::in | ios_base::out) override;
  int sync() override;
  void imbue(const locale& __loc) override;

private:
  char* __extbuf_;
  const char* __extbufnext_;
  const char* __extbufend_;
  char __extbuf_min_[8];
  size_t __ebs_;
  char_type* __intbuf_;
  size_t __ibs_;
  FILE* __file_;
  const codecvt<char_type, char, state_type>* __cv_;
  state_type __st_;
  state_type __st_last_;
  ios_base::openmode __om_;
  ios_base::openmode __cm_;
  bool __owns_eb_;
  bool __owns_ib_;
  bool __always_noconv_;

  bool __read_mode();
  void __write_mode();

  _LIBCPP_EXPORTED_FROM_ABI friend FILE* __get_ostream_file(ostream&);
};

template <class _CharT, class _Traits>
basic_filebuf<_CharT, _Traits>::basic_filebuf()
    : __extbuf_(nullptr),
      __extbufnext_(nullptr),
      __extbufend_(nullptr),
      __ebs_(0),
      __intbuf_(nullptr),
      __ibs_(0),
      __file_(nullptr),
      __cv_(nullptr),
      __st_(),
      __st_last_(),
      __om_(0),
      __cm_(0),
      __owns_eb_(false),
      __owns_ib_(false),
      __always_noconv_(false) {
  if (std::has_facet<codecvt<char_type, char, state_type> >(this->getloc())) {
    __cv_            = &std::use_facet<codecvt<char_type, char, state_type> >(this->getloc());
    __always_noconv_ = __cv_->always_noconv();
  }
  setbuf(nullptr, 4096);
}

template <class _CharT, class _Traits>
basic_filebuf<_CharT, _Traits>::basic_filebuf(basic_filebuf&& __rhs) : basic_streambuf<_CharT, _Traits>(__rhs) {
  if (__rhs.__extbuf_ == __rhs.__extbuf_min_) {
    __extbuf_     = __extbuf_min_;
    __extbufnext_ = __extbuf_ + (__rhs.__extbufnext_ - __rhs.__extbuf_);
    __extbufend_  = __extbuf_ + (__rhs.__extbufend_ - __rhs.__extbuf_);
  } else {
    __extbuf_     = __rhs.__extbuf_;
    __extbufnext_ = __rhs.__extbufnext_;
    __extbufend_  = __rhs.__extbufend_;
  }
  __ebs_           = __rhs.__ebs_;
  __intbuf_        = __rhs.__intbuf_;
  __ibs_           = __rhs.__ibs_;
  __file_          = __rhs.__file_;
  __cv_            = __rhs.__cv_;
  __st_            = __rhs.__st_;
  __st_last_       = __rhs.__st_last_;
  __om_            = __rhs.__om_;
  __cm_            = __rhs.__cm_;
  __owns_eb_       = __rhs.__owns_eb_;
  __owns_ib_       = __rhs.__owns_ib_;
  __always_noconv_ = __rhs.__always_noconv_;
  if (__rhs.pbase()) {
    if (__rhs.pbase() == __rhs.__intbuf_)
      this->setp(__intbuf_, __intbuf_ + (__rhs.epptr() - __rhs.pbase()));
    else
      this->setp((char_type*)__extbuf_, (char_type*)__extbuf_ + (__rhs.epptr() - __rhs.pbase()));
    this->__pbump(__rhs.pptr() - __rhs.pbase());
  } else if (__rhs.eback()) {
    if (__rhs.eback() == __rhs.__intbuf_)
      this->setg(__intbuf_, __intbuf_ + (__rhs.gptr() - __rhs.eback()), __intbuf_ + (__rhs.egptr() - __rhs.eback()));
    else
      this->setg((char_type*)__extbuf_,
                 (char_type*)__extbuf_ + (__rhs.gptr() - __rhs.eback()),
                 (char_type*)__extbuf_ + (__rhs.egptr() - __rhs.eback()));
  }
  __rhs.__extbuf_     = nullptr;
  __rhs.__extbufnext_ = nullptr;
  __rhs.__extbufend_  = nullptr;
  __rhs.__ebs_        = 0;
  __rhs.__intbuf_     = 0;
  __rhs.__ibs_        = 0;
  __rhs.__file_       = nullptr;
  __rhs.__st_         = state_type();
  __rhs.__st_last_    = state_type();
  __rhs.__om_         = 0;
  __rhs.__cm_         = 0;
  __rhs.__owns_eb_    = false;
  __rhs.__owns_ib_    = false;
  __rhs.setg(0, 0, 0);
  __rhs.setp(0, 0);
}

template <class _CharT, class _Traits>
inline basic_filebuf<_CharT, _Traits>& basic_filebuf<_CharT, _Traits>::operator=(basic_filebuf&& __rhs) {
  close();
  swap(__rhs);
  return *this;
}

template <class _CharT, class _Traits>
basic_filebuf<_CharT, _Traits>::~basic_filebuf() {
#  ifndef _LIBCPP_HAS_NO_EXCEPTIONS
  try {
#  endif // _LIBCPP_HAS_NO_EXCEPTIONS
    close();
#  ifndef _LIBCPP_HAS_NO_EXCEPTIONS
  } catch (...) {
  }
#  endif // _LIBCPP_HAS_NO_EXCEPTIONS
  if (__owns_eb_)
    delete[] __extbuf_;
  if (__owns_ib_)
    delete[] __intbuf_;
}

template <class _CharT, class _Traits>
void basic_filebuf<_CharT, _Traits>::swap(basic_filebuf& __rhs) {
  basic_streambuf<char_type, traits_type>::swap(__rhs);
  if (__extbuf_ != __extbuf_min_ && __rhs.__extbuf_ != __rhs.__extbuf_min_) {
    // Neither *this nor __rhs uses the small buffer, so we can simply swap the pointers.
    std::swap(__extbuf_, __rhs.__extbuf_);
    std::swap(__extbufnext_, __rhs.__extbufnext_);
    std::swap(__extbufend_, __rhs.__extbufend_);
  } else {
    ptrdiff_t __ln = __extbufnext_ ? __extbufnext_ - __extbuf_ : 0;
    ptrdiff_t __le = __extbufend_ ? __extbufend_ - __extbuf_ : 0;
    ptrdiff_t __rn = __rhs.__extbufnext_ ? __rhs.__extbufnext_ - __rhs.__extbuf_ : 0;
    ptrdiff_t __re = __rhs.__extbufend_ ? __rhs.__extbufend_ - __rhs.__extbuf_ : 0;
    if (__extbuf_ == __extbuf_min_ && __rhs.__extbuf_ != __rhs.__extbuf_min_) {
      // *this uses the small buffer, but __rhs doesn't.
      __extbuf_       = __rhs.__extbuf_;
      __rhs.__extbuf_ = __rhs.__extbuf_min_;
      std::memmove(__rhs.__extbuf_min_, __extbuf_min_, sizeof(__extbuf_min_));
    } else if (__extbuf_ != __extbuf_min_ && __rhs.__extbuf_ == __rhs.__extbuf_min_) {
      // *this doesn't use the small buffer, but __rhs does.
      __rhs.__extbuf_ = __extbuf_;
      __extbuf_       = __extbuf_min_;
      std::memmove(__extbuf_min_, __rhs.__extbuf_min_, sizeof(__extbuf_min_));
    } else {
      // Both *this and __rhs use the small buffer.
      char __tmp[sizeof(__extbuf_min_)];
      std::memmove(__tmp, __extbuf_min_, sizeof(__extbuf_min_));
      std::memmove(__extbuf_min_, __rhs.__extbuf_min_, sizeof(__extbuf_min_));
      std::memmove(__rhs.__extbuf_min_, __tmp, sizeof(__extbuf_min_));
    }
    __extbufnext_       = __extbuf_ + __rn;
    __extbufend_        = __extbuf_ + __re;
    __rhs.__extbufnext_ = __rhs.__extbuf_ + __ln;
    __rhs.__extbufend_  = __rhs.__extbuf_ + __le;
  }
  std::swap(__ebs_, __rhs.__ebs_);
  std::swap(__intbuf_, __rhs.__intbuf_);
  std::swap(__ibs_, __rhs.__ibs_);
  std::swap(__file_, __rhs.__file_);
  std::swap(__cv_, __rhs.__cv_);
  std::swap(__st_, __rhs.__st_);
  std::swap(__st_last_, __rhs.__st_last_);
  std::swap(__om_, __rhs.__om_);
  std::swap(__cm_, __rhs.__cm_);
  std::swap(__owns_eb_, __rhs.__owns_eb_);
  std::swap(__owns_ib_, __rhs.__owns_ib_);
  std::swap(__always_noconv_, __rhs.__always_noconv_);
  if (this->eback() == (char_type*)__rhs.__extbuf_min_) {
    ptrdiff_t __n = this->gptr() - this->eback();
    ptrdiff_t __e = this->egptr() - this->eback();
    this->setg((char_type*)__extbuf_min_, (char_type*)__extbuf_min_ + __n, (char_type*)__extbuf_min_ + __e);
  } else if (this->pbase() == (char_type*)__rhs.__extbuf_min_) {
    ptrdiff_t __n = this->pptr() - this->pbase();
    ptrdiff_t __e = this->epptr() - this->pbase();
    this->setp((char_type*)__extbuf_min_, (char_type*)__extbuf_min_ + __e);
    this->__pbump(__n);
  }
  if (__rhs.eback() == (char_type*)__extbuf_min_) {
    ptrdiff_t __n = __rhs.gptr() - __rhs.eback();
    ptrdiff_t __e = __rhs.egptr() - __rhs.eback();
    __rhs.setg(
        (char_type*)__rhs.__extbuf_min_, (char_type*)__rhs.__extbuf_min_ + __n, (char_type*)__rhs.__extbuf_min_ + __e);
  } else if (__rhs.pbase() == (char_type*)__extbuf_min_) {
    ptrdiff_t __n = __rhs.pptr() - __rhs.pbase();
    ptrdiff_t __e = __rhs.epptr() - __rhs.pbase();
    __rhs.setp((char_type*)__rhs.__extbuf_min_, (char_type*)__rhs.__extbuf_min_ + __e);
    __rhs.__pbump(__n);
  }
}

template <class _CharT, class _Traits>
inline _LIBCPP_HIDE_FROM_ABI void swap(basic_filebuf<_CharT, _Traits>& __x, basic_filebuf<_CharT, _Traits>& __y) {
  __x.swap(__y);
}

template <class _CharT, class _Traits>
inline bool basic_filebuf<_CharT, _Traits>::is_open() const {
  return __file_ != nullptr;
}

template <class _CharT, class _Traits>
const char* basic_filebuf<_CharT, _Traits>::__make_mdstring(ios_base::openmode __mode) _NOEXCEPT {
  switch (__mode & ~ios_base::ate) {
  case ios_base::out:
  case ios_base::out | ios_base::trunc:
    return "w" _LIBCPP_FOPEN_CLOEXEC_MODE;
  case ios_base::out | ios_base::app:
  case ios_base::app:
    return "a" _LIBCPP_FOPEN_CLOEXEC_MODE;
  case ios_base::in:
    return "r" _LIBCPP_FOPEN_CLOEXEC_MODE;
  case ios_base::in | ios_base::out:
    return "r+" _LIBCPP_FOPEN_CLOEXEC_MODE;
  case ios_base::in | ios_base::out | ios_base::trunc:
    return "w+" _LIBCPP_FOPEN_CLOEXEC_MODE;
  case ios_base::in | ios_base::out | ios_base::app:
  case ios_base::in | ios_base::app:
    return "a+" _LIBCPP_FOPEN_CLOEXEC_MODE;
  case ios_base::out | ios_base::binary:
  case ios_base::out | ios_base::trunc | ios_base::binary:
    return "wb" _LIBCPP_FOPEN_CLOEXEC_MODE;
  case ios_base::out | ios_base::app | ios_base::binary:
  case ios_base::app | ios_base::binary:
    return "ab" _LIBCPP_FOPEN_CLOEXEC_MODE;
  case ios_base::in | ios_base::binary:
    return "rb" _LIBCPP_FOPEN_CLOEXEC_MODE;
  case ios_base::in | ios_base::out | ios_base::binary:
    return "r+b" _LIBCPP_FOPEN_CLOEXEC_MODE;
  case ios_base::in | ios_base::out | ios_base::trunc | ios_base::binary:
    return "w+b" _LIBCPP_FOPEN_CLOEXEC_MODE;
  case ios_base::in | ios_base::out | ios_base::app | ios_base::binary:
  case ios_base::in | ios_base::app | ios_base::binary:
    return "a+b" _LIBCPP_FOPEN_CLOEXEC_MODE;
#  if _LIBCPP_STD_VER >= 23
  case ios_base::out | ios_base::noreplace:
  case ios_base::out | ios_base::trunc | ios_base::noreplace:
    return "wx" _LIBCPP_FOPEN_CLOEXEC_MODE;
  case ios_base::in | ios_base::out | ios_base::trunc | ios_base::noreplace:
    return "w+x" _LIBCPP_FOPEN_CLOEXEC_MODE;
  case ios_base::out | ios_base::binary | ios_base::noreplace:
  case ios_base::out | ios_base::trunc | ios_base::binary | ios_base::noreplace:
    return "wbx" _LIBCPP_FOPEN_CLOEXEC_MODE;
  case ios_base::in | ios_base::out | ios_base::trunc | ios_base::binary | ios_base::noreplace:
    return "w+bx" _LIBCPP_FOPEN_CLOEXEC_MODE;
#  endif // _LIBCPP_STD_VER >= 23
  default:
    return nullptr;
  }
  __libcpp_unreachable();
}

template <class _CharT, class _Traits>
basic_filebuf<_CharT, _Traits>* basic_filebuf<_CharT, _Traits>::open(const char* __s, ios_base::openmode __mode) {
  basic_filebuf<_CharT, _Traits>* __rt = nullptr;
  if (__file_ == nullptr) {
    if (const char* __mdstr = __make_mdstring(__mode)) {
      __rt    = this;
      __file_ = fopen(__s, __mdstr);
      if (__file_) {
        __om_ = __mode;
        if (__mode & ios_base::ate) {
          if (fseek(__file_, 0, SEEK_END)) {
            fclose(__file_);
            __file_ = nullptr;
            __rt    = nullptr;
          }
        }
      } else
        __rt = nullptr;
    }
  }
  return __rt;
}

template <class _CharT, class _Traits>
inline basic_filebuf<_CharT, _Traits>* basic_filebuf<_CharT, _Traits>::__open(int __fd, ios_base::openmode __mode) {
  basic_filebuf<_CharT, _Traits>* __rt = nullptr;
  if (__file_ == nullptr) {
    if (const char* __mdstr = __make_mdstring(__mode)) {
      __rt    = this;
      __file_ = fdopen(__fd, __mdstr);
      if (__file_) {
        __om_ = __mode;
        if (__mode & ios_base::ate) {
          if (fseek(__file_, 0, SEEK_END)) {
            fclose(__file_);
            __file_ = nullptr;
            __rt    = nullptr;
          }
        }
      } else
        __rt = nullptr;
    }
  }
  return __rt;
}

#  ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
// This is basically the same as the char* overload except that it uses _wfopen
// and long mode strings.
template <class _CharT, class _Traits>
basic_filebuf<_CharT, _Traits>* basic_filebuf<_CharT, _Traits>::open(const wchar_t* __s, ios_base::openmode __mode) {
  basic_filebuf<_CharT, _Traits>* __rt = nullptr;
  if (__file_ == nullptr) {
    __rt = this;
    const wchar_t* __mdstr;
    switch (__mode & ~ios_base::ate) {
    case ios_base::out:
    case ios_base::out | ios_base::trunc:
      __mdstr = L"w";
      break;
    case ios_base::out | ios_base::app:
    case ios_base::app:
      __mdstr = L"a";
      break;
    case ios_base::in:
      __mdstr = L"r";
      break;
    case ios_base::in | ios_base::out:
      __mdstr = L"r+";
      break;
    case ios_base::in | ios_base::out | ios_base::trunc:
      __mdstr = L"w+";
      break;
    case ios_base::in | ios_base::out | ios_base::app:
    case ios_base::in | ios_base::app:
      __mdstr = L"a+";
      break;
    case ios_base::out | ios_base::binary:
    case ios_base::out | ios_base::trunc | ios_base::binary:
      __mdstr = L"wb";
      break;
    case ios_base::out | ios_base::app | ios_base::binary:
    case ios_base::app | ios_base::binary:
      __mdstr = L"ab";
      break;
    case ios_base::in | ios_base::binary:
      __mdstr = L"rb";
      break;
    case ios_base::in | ios_base::out | ios_base::binary:
      __mdstr = L"r+b";
      break;
    case ios_base::in | ios_base::out | ios_base::trunc | ios_base::binary:
      __mdstr = L"w+b";
      break;
    case ios_base::in | ios_base::out | ios_base::app | ios_base::binary:
    case ios_base::in | ios_base::app | ios_base::binary:
      __mdstr = L"a+b";
      break;
#    if _LIBCPP_STD_VER >= 23
    case ios_base::out | ios_base::noreplace:
    case ios_base::out | ios_base::trunc | ios_base::noreplace:
      __mdstr = L"wx";
      break;
    case ios_base::in | ios_base::out | ios_base::trunc | ios_base::noreplace:
      __mdstr = L"w+x";
      break;
    case ios_base::out | ios_base::binary | ios_base::noreplace:
    case ios_base::out | ios_base::trunc | ios_base::binary | ios_base::noreplace:
      __mdstr = L"wbx";
      break;
    case ios_base::in | ios_base::out | ios_base::trunc | ios_base::binary | ios_base::noreplace:
      __mdstr = L"w+bx";
      break;
#    endif // _LIBCPP_STD_VER >= 23
    default:
      __rt = nullptr;
      break;
    }
    if (__rt) {
      __file_ = _wfopen(__s, __mdstr);
      if (__file_) {
        __om_ = __mode;
        if (__mode & ios_base::ate) {
          if (fseek(__file_, 0, SEEK_END)) {
            fclose(__file_);
            __file_ = nullptr;
            __rt    = nullptr;
          }
        }
      } else
        __rt = nullptr;
    }
  }
  return __rt;
}
#  endif

template <class _CharT, class _Traits>
inline basic_filebuf<_CharT, _Traits>*
basic_filebuf<_CharT, _Traits>::open(const string& __s, ios_base::openmode __mode) {
  return open(__s.c_str(), __mode);
}

template <class _CharT, class _Traits>
basic_filebuf<_CharT, _Traits>* basic_filebuf<_CharT, _Traits>::close() {
  basic_filebuf<_CharT, _Traits>* __rt = nullptr;
  if (__file_) {
    __rt = this;
    unique_ptr<FILE, int (*)(FILE*)> __h(__file_, fclose);
    if (sync())
      __rt = nullptr;
    if (fclose(__h.release()))
      __rt = nullptr;
    __file_ = nullptr;
    setbuf(0, 0);
  }
  return __rt;
}

template <class _CharT, class _Traits>
typename basic_filebuf<_CharT, _Traits>::int_type basic_filebuf<_CharT, _Traits>::underflow() {
  if (__file_ == nullptr)
    return traits_type::eof();
  bool __initial = __read_mode();
  char_type __1buf;
  if (this->gptr() == nullptr)
    this->setg(&__1buf, &__1buf + 1, &__1buf + 1);
  const size_t __unget_sz = __initial ? 0 : std::min<size_t>((this->egptr() - this->eback()) / 2, 4);
  int_type __c            = traits_type::eof();
  if (this->gptr() == this->egptr()) {
    std::memmove(this->eback(), this->egptr() - __unget_sz, __unget_sz * sizeof(char_type));
    if (__always_noconv_) {
      size_t __nmemb = static_cast<size_t>(this->egptr() - this->eback() - __unget_sz);
      __nmemb        = ::fread(this->eback() + __unget_sz, 1, __nmemb, __file_);
      if (__nmemb != 0) {
        this->setg(this->eback(), this->eback() + __unget_sz, this->eback() + __unget_sz + __nmemb);
        __c = traits_type::to_int_type(*this->gptr());
      }
    } else {
      if (__extbufend_ != __extbufnext_) {
        _LIBCPP_ASSERT_NON_NULL(__extbufnext_ != nullptr, "underflow moving from nullptr");
        _LIBCPP_ASSERT_NON_NULL(__extbuf_ != nullptr, "underflow moving into nullptr");
        std::memmove(__extbuf_, __extbufnext_, __extbufend_ - __extbufnext_);
      }
      __extbufnext_ = __extbuf_ + (__extbufend_ - __extbufnext_);
      __extbufend_  = __extbuf_ + (__extbuf_ == __extbuf_min_ ? sizeof(__extbuf_min_) : __ebs_);
      size_t __nmemb =
          std::min(static_cast<size_t>(__ibs_ - __unget_sz), static_cast<size_t>(__extbufend_ - __extbufnext_));
      codecvt_base::result __r;
      __st_last_  = __st_;
      size_t __nr = fread((void*)const_cast<char*>(__extbufnext_), 1, __nmemb, __file_);
      if (__nr != 0) {
        if (!__cv_)
          __throw_bad_cast();

        __extbufend_ = __extbufnext_ + __nr;
        char_type* __inext;
        __r = __cv_->in(
            __st_, __extbuf_, __extbufend_, __extbufnext_, this->eback() + __unget_sz, this->eback() + __ibs_, __inext);
        if (__r == codecvt_base::noconv) {
          this->setg((char_type*)__extbuf_, (char_type*)__extbuf_, (char_type*)const_cast<char*>(__extbufend_));
          __c = traits_type::to_int_type(*this->gptr());
        } else if (__inext != this->eback() + __unget_sz) {
          this->setg(this->eback(), this->eback() + __unget_sz, __inext);
          __c = traits_type::to_int_type(*this->gptr());
        }
      }
    }
  } else
    __c = traits_type::to_int_type(*this->gptr());
  if (this->eback() == &__1buf)
    this->setg(nullptr, nullptr, nullptr);
  return __c;
}

template <class _CharT, class _Traits>
typename basic_filebuf<_CharT, _Traits>::int_type basic_filebuf<_CharT, _Traits>::pbackfail(int_type __c) {
  if (__file_ && this->eback() < this->gptr()) {
    if (traits_type::eq_int_type(__c, traits_type::eof())) {
      this->gbump(-1);
      return traits_type::not_eof(__c);
    }
    if ((__om_ & ios_base::out) || traits_type::eq(traits_type::to_char_type(__c), this->gptr()[-1])) {
      this->gbump(-1);
      *this->gptr() = traits_type::to_char_type(__c);
      return __c;
    }
  }
  return traits_type::eof();
}

template <class _CharT, class _Traits>
typename basic_filebuf<_CharT, _Traits>::int_type basic_filebuf<_CharT, _Traits>::overflow(int_type __c) {
  if (__file_ == nullptr)
    return traits_type::eof();
  __write_mode();
  char_type __1buf;
  char_type* __pb_save  = this->pbase();
  char_type* __epb_save = this->epptr();
  if (!traits_type::eq_int_type(__c, traits_type::eof())) {
    if (this->pptr() == nullptr)
      this->setp(&__1buf, &__1buf + 1);
    *this->pptr() = traits_type::to_char_type(__c);
    this->pbump(1);
  }
  if (this->pptr() != this->pbase()) {
    if (__always_noconv_) {
      size_t __nmemb = static_cast<size_t>(this->pptr() - this->pbase());
      if (std::fwrite(this->pbase(), sizeof(char_type), __nmemb, __file_) != __nmemb)
        return traits_type::eof();
    } else {
      char* __extbe = __extbuf_;
      codecvt_base::result __r;
      do {
        if (!__cv_)
          __throw_bad_cast();

        const char_type* __e;
        __r = __cv_->out(__st_, this->pbase(), this->pptr(), __e, __extbuf_, __extbuf_ + __ebs_, __extbe);
        if (__e == this->pbase())
          return traits_type::eof();
        if (__r == codecvt_base::noconv) {
          size_t __nmemb = static_cast<size_t>(this->pptr() - this->pbase());
          if (std::fwrite(this->pbase(), 1, __nmemb, __file_) != __nmemb)
            return traits_type::eof();
        } else if (__r == codecvt_base::ok || __r == codecvt_base::partial) {
          size_t __nmemb = static_cast<size_t>(__extbe - __extbuf_);
          if (fwrite(__extbuf_, 1, __nmemb, __file_) != __nmemb)
            return traits_type::eof();
          if (__r == codecvt_base::partial) {
            this->setp(const_cast<char_type*>(__e), this->pptr());
            this->__pbump(this->epptr() - this->pbase());
          }
        } else
          return traits_type::eof();
      } while (__r == codecvt_base::partial);
    }
    this->setp(__pb_save, __epb_save);
  }
  return traits_type::not_eof(__c);
}

template <class _CharT, class _Traits>
basic_streambuf<_CharT, _Traits>* basic_filebuf<_CharT, _Traits>::setbuf(char_type* __s, streamsize __n) {
  this->setg(nullptr, nullptr, nullptr);
  this->setp(nullptr, nullptr);
  if (__owns_eb_)
    delete[] __extbuf_;
  if (__owns_ib_)
    delete[] __intbuf_;
  __ebs_ = __n;
  if (__ebs_ > sizeof(__extbuf_min_)) {
    if (__always_noconv_ && __s) {
      __extbuf_  = (char*)__s;
      __owns_eb_ = false;
    } else {
      __extbuf_  = new char[__ebs_];
      __owns_eb_ = true;
    }
  } else {
    __extbuf_  = __extbuf_min_;
    __ebs_     = sizeof(__extbuf_min_);
    __owns_eb_ = false;
  }
  if (!__always_noconv_) {
    __ibs_ = max<streamsize>(__n, sizeof(__extbuf_min_));
    if (__s && __ibs_ > sizeof(__extbuf_min_)) {
      __intbuf_  = __s;
      __owns_ib_ = false;
    } else {
      __intbuf_  = new char_type[__ibs_];
      __owns_ib_ = true;
    }
  } else {
    __ibs_     = 0;
    __intbuf_  = nullptr;
    __owns_ib_ = false;
  }
  return this;
}

template <class _CharT, class _Traits>
typename basic_filebuf<_CharT, _Traits>::pos_type
basic_filebuf<_CharT, _Traits>::seekoff(off_type __off, ios_base::seekdir __way, ios_base::openmode) {
  if (!__cv_)
    __throw_bad_cast();

  int __width = __cv_->encoding();
  if (__file_ == nullptr || (__width <= 0 && __off != 0) || sync())
    return pos_type(off_type(-1));
  // __width > 0 || __off == 0
  int __whence;
  switch (__way) {
  case ios_base::beg:
    __whence = SEEK_SET;
    break;
  case ios_base::cur:
    __whence = SEEK_CUR;
    break;
  case ios_base::end:
    __whence = SEEK_END;
    break;
  default:
    return pos_type(off_type(-1));
  }
#  if defined(_LIBCPP_HAS_NO_OFF_T_FUNCTIONS)
  if (fseek(__file_, __width > 0 ? __width * __off : 0, __whence))
    return pos_type(off_type(-1));
  pos_type __r = ftell(__file_);
#  else
  if (::fseeko(__file_, __width > 0 ? __width * __off : 0, __whence))
    return pos_type(off_type(-1));
  pos_type __r = ftello(__file_);
#  endif
  __r.state(__st_);
  return __r;
}

template <class _CharT, class _Traits>
typename basic_filebuf<_CharT, _Traits>::pos_type
basic_filebuf<_CharT, _Traits>::seekpos(pos_type __sp, ios_base::openmode) {
  if (__file_ == nullptr || sync())
    return pos_type(off_type(-1));
#  if defined(_LIBCPP_HAS_NO_OFF_T_FUNCTIONS)
  if (fseek(__file_, __sp, SEEK_SET))
    return pos_type(off_type(-1));
#  else
  if (::fseeko(__file_, __sp, SEEK_SET))
    return pos_type(off_type(-1));
#  endif
  __st_ = __sp.state();
  return __sp;
}

template <class _CharT, class _Traits>
int basic_filebuf<_CharT, _Traits>::sync() {
  if (__file_ == nullptr)
    return 0;
  if (!__cv_)
    __throw_bad_cast();

  if (__cm_ & ios_base::out) {
    if (this->pptr() != this->pbase())
      if (overflow() == traits_type::eof())
        return -1;
    codecvt_base::result __r;
    do {
      char* __extbe;
      __r            = __cv_->unshift(__st_, __extbuf_, __extbuf_ + __ebs_, __extbe);
      size_t __nmemb = static_cast<size_t>(__extbe - __extbuf_);
      if (fwrite(__extbuf_, 1, __nmemb, __file_) != __nmemb)
        return -1;
    } while (__r == codecvt_base::partial);
    if (__r == codecvt_base::error)
      return -1;
    if (fflush(__file_))
      return -1;
  } else if (__cm_ & ios_base::in) {
    off_type __c;
    state_type __state = __st_last_;
    bool __update_st   = false;
    if (__always_noconv_)
      __c = this->egptr() - this->gptr();
    else {
      int __width = __cv_->encoding();
      __c         = __extbufend_ - __extbufnext_;
      if (__width > 0)
        __c += __width * (this->egptr() - this->gptr());
      else {
        if (this->gptr() != this->egptr()) {
          const int __off = __cv_->length(__state, __extbuf_, __extbufnext_, this->gptr() - this->eback());
          __c += __extbufnext_ - __extbuf_ - __off;
          __update_st = true;
        }
      }
    }
#  if defined(_LIBCPP_HAS_NO_OFF_T_FUNCTIONS)
    if (fseek(__file_, -__c, SEEK_CUR))
      return -1;
#  else
    if (::fseeko(__file_, -__c, SEEK_CUR))
      return -1;
#  endif
    if (__update_st)
      __st_ = __state;
    __extbufnext_ = __extbufend_ = __extbuf_;
    this->setg(nullptr, nullptr, nullptr);
    __cm_ = 0;
  }
  return 0;
}

template <class _CharT, class _Traits>
void basic_filebuf<_CharT, _Traits>::imbue(const locale& __loc) {
  sync();
  __cv_            = &std::use_facet<codecvt<char_type, char, state_type> >(__loc);
  bool __old_anc   = __always_noconv_;
  __always_noconv_ = __cv_->always_noconv();
  if (__old_anc != __always_noconv_) {
    this->setg(nullptr, nullptr, nullptr);
    this->setp(nullptr, nullptr);
    // invariant, char_type is char, else we couldn't get here
    if (__always_noconv_) // need to dump __intbuf_
    {
      if (__owns_eb_)
        delete[] __extbuf_;
      __owns_eb_ = __owns_ib_;
      __ebs_     = __ibs_;
      __extbuf_  = (char*)__intbuf_;
      __ibs_     = 0;
      __intbuf_  = nullptr;
      __owns_ib_ = false;
    } else // need to obtain an __intbuf_.
    {      // If __extbuf_ is user-supplied, use it, else new __intbuf_
      if (!__owns_eb_ && __extbuf_ != __extbuf_min_) {
        __ibs_     = __ebs_;
        __intbuf_  = (char_type*)__extbuf_;
        __owns_ib_ = false;
        __extbuf_  = new char[__ebs_];
        __owns_eb_ = true;
      } else {
        __ibs_     = __ebs_;
        __intbuf_  = new char_type[__ibs_];
        __owns_ib_ = true;
      }
    }
  }
}

template <class _CharT, class _Traits>
bool basic_filebuf<_CharT, _Traits>::__read_mode() {
  if (!(__cm_ & ios_base::in)) {
    this->setp(nullptr, nullptr);
    if (__always_noconv_)
      this->setg((char_type*)__extbuf_, (char_type*)__extbuf_ + __ebs_, (char_type*)__extbuf_ + __ebs_);
    else
      this->setg(__intbuf_, __intbuf_ + __ibs_, __intbuf_ + __ibs_);
    __cm_ = ios_base::in;
    return true;
  }
  return false;
}

template <class _CharT, class _Traits>
void basic_filebuf<_CharT, _Traits>::__write_mode() {
  if (!(__cm_ & ios_base::out)) {
    this->setg(nullptr, nullptr, nullptr);
    if (__ebs_ > sizeof(__extbuf_min_)) {
      if (__always_noconv_)
        this->setp((char_type*)__extbuf_, (char_type*)__extbuf_ + (__ebs_ - 1));
      else
        this->setp(__intbuf_, __intbuf_ + (__ibs_ - 1));
    } else
      this->setp(nullptr, nullptr);
    __cm_ = ios_base::out;
  }
}

// basic_ifstream

template <class _CharT, class _Traits>
class _LIBCPP_TEMPLATE_VIS basic_ifstream : public basic_istream<_CharT, _Traits> {
public:
  typedef _CharT char_type;
  typedef _Traits traits_type;
  typedef typename traits_type::int_type int_type;
  typedef typename traits_type::pos_type pos_type;
  typedef typename traits_type::off_type off_type;
#  if _LIBCPP_STD_VER >= 26
  using native_handle_type = typename basic_filebuf<_CharT, _Traits>::native_handle_type;
#  endif

  _LIBCPP_HIDE_FROM_ABI basic_ifstream();
  _LIBCPP_HIDE_FROM_ABI explicit basic_ifstream(const char* __s, ios_base::openmode __mode = ios_base::in);
#  ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
  _LIBCPP_HIDE_FROM_ABI explicit basic_ifstream(const wchar_t* __s, ios_base::openmode __mode = ios_base::in);
#  endif
  _LIBCPP_HIDE_FROM_ABI explicit basic_ifstream(const string& __s, ios_base::openmode __mode = ios_base::in);
#  if _LIBCPP_STD_VER >= 17
  _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY _LIBCPP_HIDE_FROM_ABI explicit basic_ifstream(
      const filesystem::path& __p, ios_base::openmode __mode = ios_base::in)
      : basic_ifstream(__p.c_str(), __mode) {}
#  endif // _LIBCPP_STD_VER >= 17
  _LIBCPP_HIDE_FROM_ABI basic_ifstream(basic_ifstream&& __rhs);
  _LIBCPP_HIDE_FROM_ABI basic_ifstream& operator=(basic_ifstream&& __rhs);
  _LIBCPP_HIDE_FROM_ABI void swap(basic_ifstream& __rhs);

  _LIBCPP_HIDE_FROM_ABI basic_filebuf<char_type, traits_type>* rdbuf() const;
#  if _LIBCPP_STD_VER >= 26
  _LIBCPP_HIDE_FROM_ABI native_handle_type native_handle() const noexcept { return rdbuf()->native_handle(); }
#  endif
  _LIBCPP_HIDE_FROM_ABI bool is_open() const;
  void open(const char* __s, ios_base::openmode __mode = ios_base::in);
#  ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
  void open(const wchar_t* __s, ios_base::openmode __mode = ios_base::in);
#  endif
  void open(const string& __s, ios_base::openmode __mode = ios_base::in);
#  if _LIBCPP_STD_VER >= 17
  _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY _LIBCPP_HIDE_FROM_ABI void
  open(const filesystem::path& __p, ios_base::openmode __mode = ios_base::in) {
    return open(__p.c_str(), __mode);
  }
#  endif // _LIBCPP_STD_VER >= 17

  _LIBCPP_HIDE_FROM_ABI void __open(int __fd, ios_base::openmode __mode);
  _LIBCPP_HIDE_FROM_ABI void close();

private:
  basic_filebuf<char_type, traits_type> __sb_;
};

template <class _CharT, class _Traits>
inline basic_ifstream<_CharT, _Traits>::basic_ifstream() : basic_istream<char_type, traits_type>(&__sb_) {}

template <class _CharT, class _Traits>
inline basic_ifstream<_CharT, _Traits>::basic_ifstream(const char* __s, ios_base::openmode __mode)
    : basic_istream<char_type, traits_type>(&__sb_) {
  if (__sb_.open(__s, __mode | ios_base::in) == nullptr)
    this->setstate(ios_base::failbit);
}

#  ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
template <class _CharT, class _Traits>
inline basic_ifstream<_CharT, _Traits>::basic_ifstream(const wchar_t* __s, ios_base::openmode __mode)
    : basic_istream<char_type, traits_type>(&__sb_) {
  if (__sb_.open(__s, __mode | ios_base::in) == nullptr)
    this->setstate(ios_base::failbit);
}
#  endif

template <class _CharT, class _Traits>
inline basic_ifstream<_CharT, _Traits>::basic_ifstream(const string& __s, ios_base::openmode __mode)
    : basic_istream<char_type, traits_type>(&__sb_) {
  if (__sb_.open(__s, __mode | ios_base::in) == nullptr)
    this->setstate(ios_base::failbit);
}

template <class _CharT, class _Traits>
inline basic_ifstream<_CharT, _Traits>::basic_ifstream(basic_ifstream&& __rhs)
    : basic_istream<char_type, traits_type>(std::move(__rhs)), __sb_(std::move(__rhs.__sb_)) {
  this->set_rdbuf(&__sb_);
}

template <class _CharT, class _Traits>
inline basic_ifstream<_CharT, _Traits>& basic_ifstream<_CharT, _Traits>::operator=(basic_ifstream&& __rhs) {
  basic_istream<char_type, traits_type>::operator=(std::move(__rhs));
  __sb_ = std::move(__rhs.__sb_);
  return *this;
}

template <class _CharT, class _Traits>
inline void basic_ifstream<_CharT, _Traits>::swap(basic_ifstream& __rhs) {
  basic_istream<char_type, traits_type>::swap(__rhs);
  __sb_.swap(__rhs.__sb_);
}

template <class _CharT, class _Traits>
inline _LIBCPP_HIDE_FROM_ABI void swap(basic_ifstream<_CharT, _Traits>& __x, basic_ifstream<_CharT, _Traits>& __y) {
  __x.swap(__y);
}

template <class _CharT, class _Traits>
inline basic_filebuf<_CharT, _Traits>* basic_ifstream<_CharT, _Traits>::rdbuf() const {
  return const_cast<basic_filebuf<char_type, traits_type>*>(&__sb_);
}

template <class _CharT, class _Traits>
inline bool basic_ifstream<_CharT, _Traits>::is_open() const {
  return __sb_.is_open();
}

template <class _CharT, class _Traits>
void basic_ifstream<_CharT, _Traits>::open(const char* __s, ios_base::openmode __mode) {
  if (__sb_.open(__s, __mode | ios_base::in))
    this->clear();
  else
    this->setstate(ios_base::failbit);
}

#  ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
template <class _CharT, class _Traits>
void basic_ifstream<_CharT, _Traits>::open(const wchar_t* __s, ios_base::openmode __mode) {
  if (__sb_.open(__s, __mode | ios_base::in))
    this->clear();
  else
    this->setstate(ios_base::failbit);
}
#  endif

template <class _CharT, class _Traits>
void basic_ifstream<_CharT, _Traits>::open(const string& __s, ios_base::openmode __mode) {
  if (__sb_.open(__s, __mode | ios_base::in))
    this->clear();
  else
    this->setstate(ios_base::failbit);
}

template <class _CharT, class _Traits>
inline void basic_ifstream<_CharT, _Traits>::__open(int __fd, ios_base::openmode __mode) {
  if (__sb_.__open(__fd, __mode | ios_base::in))
    this->clear();
  else
    this->setstate(ios_base::failbit);
}

template <class _CharT, class _Traits>
inline void basic_ifstream<_CharT, _Traits>::close() {
  if (__sb_.close() == 0)
    this->setstate(ios_base::failbit);
}

// basic_ofstream

template <class _CharT, class _Traits>
class _LIBCPP_TEMPLATE_VIS basic_ofstream : public basic_ostream<_CharT, _Traits> {
public:
  typedef _CharT char_type;
  typedef _Traits traits_type;
  typedef typename traits_type::int_type int_type;
  typedef typename traits_type::pos_type pos_type;
  typedef typename traits_type::off_type off_type;
#  if _LIBCPP_STD_VER >= 26
  using native_handle_type = typename basic_filebuf<_CharT, _Traits>::native_handle_type;
#  endif

  _LIBCPP_HIDE_FROM_ABI basic_ofstream();
  _LIBCPP_HIDE_FROM_ABI explicit basic_ofstream(const char* __s, ios_base::openmode __mode = ios_base::out);
#  ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
  _LIBCPP_HIDE_FROM_ABI explicit basic_ofstream(const wchar_t* __s, ios_base::openmode __mode = ios_base::out);
#  endif
  _LIBCPP_HIDE_FROM_ABI explicit basic_ofstream(const string& __s, ios_base::openmode __mode = ios_base::out);

#  if _LIBCPP_STD_VER >= 17
  _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY _LIBCPP_HIDE_FROM_ABI explicit basic_ofstream(
      const filesystem::path& __p, ios_base::openmode __mode = ios_base::out)
      : basic_ofstream(__p.c_str(), __mode) {}
#  endif // _LIBCPP_STD_VER >= 17

  _LIBCPP_HIDE_FROM_ABI basic_ofstream(basic_ofstream&& __rhs);
  _LIBCPP_HIDE_FROM_ABI basic_ofstream& operator=(basic_ofstream&& __rhs);
  _LIBCPP_HIDE_FROM_ABI void swap(basic_ofstream& __rhs);

  _LIBCPP_HIDE_FROM_ABI basic_filebuf<char_type, traits_type>* rdbuf() const;
#  if _LIBCPP_STD_VER >= 26
  _LIBCPP_HIDE_FROM_ABI native_handle_type native_handle() const noexcept { return rdbuf()->native_handle(); }
#  endif
  _LIBCPP_HIDE_FROM_ABI bool is_open() const;
  void open(const char* __s, ios_base::openmode __mode = ios_base::out);
#  ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
  void open(const wchar_t* __s, ios_base::openmode __mode = ios_base::out);
#  endif
  void open(const string& __s, ios_base::openmode __mode = ios_base::out);

#  if _LIBCPP_STD_VER >= 17
  _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY _LIBCPP_HIDE_FROM_ABI void
  open(const filesystem::path& __p, ios_base::openmode __mode = ios_base::out) {
    return open(__p.c_str(), __mode);
  }
#  endif // _LIBCPP_STD_VER >= 17

  _LIBCPP_HIDE_FROM_ABI void __open(int __fd, ios_base::openmode __mode);
  _LIBCPP_HIDE_FROM_ABI void close();

private:
  basic_filebuf<char_type, traits_type> __sb_;
};

template <class _CharT, class _Traits>
inline basic_ofstream<_CharT, _Traits>::basic_ofstream() : basic_ostream<char_type, traits_type>(&__sb_) {}

template <class _CharT, class _Traits>
inline basic_ofstream<_CharT, _Traits>::basic_ofstream(const char* __s, ios_base::openmode __mode)
    : basic_ostream<char_type, traits_type>(&__sb_) {
  if (__sb_.open(__s, __mode | ios_base::out) == nullptr)
    this->setstate(ios_base::failbit);
}

#  ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
template <class _CharT, class _Traits>
inline basic_ofstream<_CharT, _Traits>::basic_ofstream(const wchar_t* __s, ios_base::openmode __mode)
    : basic_ostream<char_type, traits_type>(&__sb_) {
  if (__sb_.open(__s, __mode | ios_base::out) == nullptr)
    this->setstate(ios_base::failbit);
}
#  endif

template <class _CharT, class _Traits>
inline basic_ofstream<_CharT, _Traits>::basic_ofstream(const string& __s, ios_base::openmode __mode)
    : basic_ostream<char_type, traits_type>(&__sb_) {
  if (__sb_.open(__s, __mode | ios_base::out) == nullptr)
    this->setstate(ios_base::failbit);
}

template <class _CharT, class _Traits>
inline basic_ofstream<_CharT, _Traits>::basic_ofstream(basic_ofstream&& __rhs)
    : basic_ostream<char_type, traits_type>(std::move(__rhs)), __sb_(std::move(__rhs.__sb_)) {
  this->set_rdbuf(&__sb_);
}

template <class _CharT, class _Traits>
inline basic_ofstream<_CharT, _Traits>& basic_ofstream<_CharT, _Traits>::operator=(basic_ofstream&& __rhs) {
  basic_ostream<char_type, traits_type>::operator=(std::move(__rhs));
  __sb_ = std::move(__rhs.__sb_);
  return *this;
}

template <class _CharT, class _Traits>
inline void basic_ofstream<_CharT, _Traits>::swap(basic_ofstream& __rhs) {
  basic_ostream<char_type, traits_type>::swap(__rhs);
  __sb_.swap(__rhs.__sb_);
}

template <class _CharT, class _Traits>
inline _LIBCPP_HIDE_FROM_ABI void swap(basic_ofstream<_CharT, _Traits>& __x, basic_ofstream<_CharT, _Traits>& __y) {
  __x.swap(__y);
}

template <class _CharT, class _Traits>
inline basic_filebuf<_CharT, _Traits>* basic_ofstream<_CharT, _Traits>::rdbuf() const {
  return const_cast<basic_filebuf<char_type, traits_type>*>(&__sb_);
}

template <class _CharT, class _Traits>
inline bool basic_ofstream<_CharT, _Traits>::is_open() const {
  return __sb_.is_open();
}

template <class _CharT, class _Traits>
void basic_ofstream<_CharT, _Traits>::open(const char* __s, ios_base::openmode __mode) {
  if (__sb_.open(__s, __mode | ios_base::out))
    this->clear();
  else
    this->setstate(ios_base::failbit);
}

#  ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
template <class _CharT, class _Traits>
void basic_ofstream<_CharT, _Traits>::open(const wchar_t* __s, ios_base::openmode __mode) {
  if (__sb_.open(__s, __mode | ios_base::out))
    this->clear();
  else
    this->setstate(ios_base::failbit);
}
#  endif

template <class _CharT, class _Traits>
void basic_ofstream<_CharT, _Traits>::open(const string& __s, ios_base::openmode __mode) {
  if (__sb_.open(__s, __mode | ios_base::out))
    this->clear();
  else
    this->setstate(ios_base::failbit);
}

template <class _CharT, class _Traits>
inline void basic_ofstream<_CharT, _Traits>::__open(int __fd, ios_base::openmode __mode) {
  if (__sb_.__open(__fd, __mode | ios_base::out))
    this->clear();
  else
    this->setstate(ios_base::failbit);
}

template <class _CharT, class _Traits>
inline void basic_ofstream<_CharT, _Traits>::close() {
  if (__sb_.close() == nullptr)
    this->setstate(ios_base::failbit);
}

// basic_fstream

template <class _CharT, class _Traits>
class _LIBCPP_TEMPLATE_VIS basic_fstream : public basic_iostream<_CharT, _Traits> {
public:
  typedef _CharT char_type;
  typedef _Traits traits_type;
  typedef typename traits_type::int_type int_type;
  typedef typename traits_type::pos_type pos_type;
  typedef typename traits_type::off_type off_type;
#  if _LIBCPP_STD_VER >= 26
  using native_handle_type = typename basic_filebuf<_CharT, _Traits>::native_handle_type;
#  endif

  _LIBCPP_HIDE_FROM_ABI basic_fstream();
  _LIBCPP_HIDE_FROM_ABI explicit basic_fstream(const char* __s,
                                               ios_base::openmode __mode = ios_base::in | ios_base::out);
#  ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
  _LIBCPP_HIDE_FROM_ABI explicit basic_fstream(const wchar_t* __s,
                                               ios_base::openmode __mode = ios_base::in | ios_base::out);
#  endif
  _LIBCPP_HIDE_FROM_ABI explicit basic_fstream(const string& __s,
                                               ios_base::openmode __mode = ios_base::in | ios_base::out);

#  if _LIBCPP_STD_VER >= 17
  _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY _LIBCPP_HIDE_FROM_ABI explicit basic_fstream(
      const filesystem::path& __p, ios_base::openmode __mode = ios_base::in | ios_base::out)
      : basic_fstream(__p.c_str(), __mode) {}
#  endif // _LIBCPP_STD_VER >= 17

  _LIBCPP_HIDE_FROM_ABI basic_fstream(basic_fstream&& __rhs);

  _LIBCPP_HIDE_FROM_ABI basic_fstream& operator=(basic_fstream&& __rhs);

  _LIBCPP_HIDE_FROM_ABI void swap(basic_fstream& __rhs);

  _LIBCPP_HIDE_FROM_ABI basic_filebuf<char_type, traits_type>* rdbuf() const;
#  if _LIBCPP_STD_VER >= 26
  _LIBCPP_HIDE_FROM_ABI native_handle_type native_handle() const noexcept { return rdbuf()->native_handle(); }
#  endif
  _LIBCPP_HIDE_FROM_ABI bool is_open() const;
  _LIBCPP_HIDE_FROM_ABI void open(const char* __s, ios_base::openmode __mode = ios_base::in | ios_base::out);
#  ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
  void open(const wchar_t* __s, ios_base::openmode __mode = ios_base::in | ios_base::out);
#  endif
  _LIBCPP_HIDE_FROM_ABI void open(const string& __s, ios_base::openmode __mode = ios_base::in | ios_base::out);

#  if _LIBCPP_STD_VER >= 17
  _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY _LIBCPP_HIDE_FROM_ABI void
  open(const filesystem::path& __p, ios_base::openmode __mode = ios_base::in | ios_base::out) {
    return open(__p.c_str(), __mode);
  }
#  endif // _LIBCPP_STD_VER >= 17

  _LIBCPP_HIDE_FROM_ABI void close();

private:
  basic_filebuf<char_type, traits_type> __sb_;
};

template <class _CharT, class _Traits>
inline basic_fstream<_CharT, _Traits>::basic_fstream() : basic_iostream<char_type, traits_type>(&__sb_) {}

template <class _CharT, class _Traits>
inline basic_fstream<_CharT, _Traits>::basic_fstream(const char* __s, ios_base::openmode __mode)
    : basic_iostream<char_type, traits_type>(&__sb_) {
  if (__sb_.open(__s, __mode) == nullptr)
    this->setstate(ios_base::failbit);
}

#  ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
template <class _CharT, class _Traits>
inline basic_fstream<_CharT, _Traits>::basic_fstream(const wchar_t* __s, ios_base::openmode __mode)
    : basic_iostream<char_type, traits_type>(&__sb_) {
  if (__sb_.open(__s, __mode) == nullptr)
    this->setstate(ios_base::failbit);
}
#  endif

template <class _CharT, class _Traits>
inline basic_fstream<_CharT, _Traits>::basic_fstream(const string& __s, ios_base::openmode __mode)
    : basic_iostream<char_type, traits_type>(&__sb_) {
  if (__sb_.open(__s, __mode) == nullptr)
    this->setstate(ios_base::failbit);
}

template <class _CharT, class _Traits>
inline basic_fstream<_CharT, _Traits>::basic_fstream(basic_fstream&& __rhs)
    : basic_iostream<char_type, traits_type>(std::move(__rhs)), __sb_(std::move(__rhs.__sb_)) {
  this->set_rdbuf(&__sb_);
}

template <class _CharT, class _Traits>
inline basic_fstream<_CharT, _Traits>& basic_fstream<_CharT, _Traits>::operator=(basic_fstream&& __rhs) {
  basic_iostream<char_type, traits_type>::operator=(std::move(__rhs));
  __sb_ = std::move(__rhs.__sb_);
  return *this;
}

template <class _CharT, class _Traits>
inline void basic_fstream<_CharT, _Traits>::swap(basic_fstream& __rhs) {
  basic_iostream<char_type, traits_type>::swap(__rhs);
  __sb_.swap(__rhs.__sb_);
}

template <class _CharT, class _Traits>
inline _LIBCPP_HIDE_FROM_ABI void swap(basic_fstream<_CharT, _Traits>& __x, basic_fstream<_CharT, _Traits>& __y) {
  __x.swap(__y);
}

template <class _CharT, class _Traits>
inline basic_filebuf<_CharT, _Traits>* basic_fstream<_CharT, _Traits>::rdbuf() const {
  return const_cast<basic_filebuf<char_type, traits_type>*>(&__sb_);
}

template <class _CharT, class _Traits>
inline bool basic_fstream<_CharT, _Traits>::is_open() const {
  return __sb_.is_open();
}

template <class _CharT, class _Traits>
void basic_fstream<_CharT, _Traits>::open(const char* __s, ios_base::openmode __mode) {
  if (__sb_.open(__s, __mode))
    this->clear();
  else
    this->setstate(ios_base::failbit);
}

#  ifdef _LIBCPP_HAS_OPEN_WITH_WCHAR
template <class _CharT, class _Traits>
void basic_fstream<_CharT, _Traits>::open(const wchar_t* __s, ios_base::openmode __mode) {
  if (__sb_.open(__s, __mode))
    this->clear();
  else
    this->setstate(ios_base::failbit);
}
#  endif

template <class _CharT, class _Traits>
void basic_fstream<_CharT, _Traits>::open(const string& __s, ios_base::openmode __mode) {
  if (__sb_.open(__s, __mode))
    this->clear();
  else
    this->setstate(ios_base::failbit);
}

template <class _CharT, class _Traits>
inline void basic_fstream<_CharT, _Traits>::close() {
  if (__sb_.close() == nullptr)
    this->setstate(ios_base::failbit);
}

#  if _LIBCPP_AVAILABILITY_HAS_ADDITIONAL_IOSTREAM_EXPLICIT_INSTANTIATIONS_1
extern template class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS basic_ifstream<char>;
extern template class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS basic_ofstream<char>;
extern template class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS basic_filebuf<char>;
#  endif

_LIBCPP_END_NAMESPACE_STD

#endif // _LIBCPP_HAS_NO_FILESYSTEM

_LIBCPP_POP_MACROS

#if !defined(_LIBCPP_REMOVE_TRANSITIVE_INCLUDES) && _LIBCPP_STD_VER <= 20
#  include <atomic>
#  include <concepts>
#  include <cstdlib>
#  include <iosfwd>
#  include <limits>
#  include <mutex>
#  include <new>
#  include <stdexcept>
#  include <type_traits>
#endif

#endif // _LIBCPP_FSTREAM
