1*46035553Spatrick// -*- C++ -*- 2*46035553Spatrick//===--------------------------- filesystem -------------------------------===// 3*46035553Spatrick// 4*46035553Spatrick// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 5*46035553Spatrick// See https://llvm.org/LICENSE.txt for license information. 6*46035553Spatrick// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 7*46035553Spatrick// 8*46035553Spatrick//===----------------------------------------------------------------------===// 9*46035553Spatrick#ifndef _LIBCPP_FILESYSTEM 10*46035553Spatrick#define _LIBCPP_FILESYSTEM 11*46035553Spatrick/* 12*46035553Spatrick filesystem synopsis 13*46035553Spatrick 14*46035553Spatrick namespace std { namespace filesystem { 15*46035553Spatrick 16*46035553Spatrick class path; 17*46035553Spatrick 18*46035553Spatrick void swap(path& lhs, path& rhs) noexcept; 19*46035553Spatrick size_t hash_value(const path& p) noexcept; 20*46035553Spatrick 21*46035553Spatrick bool operator==(const path& lhs, const path& rhs) noexcept; 22*46035553Spatrick bool operator!=(const path& lhs, const path& rhs) noexcept; 23*46035553Spatrick bool operator< (const path& lhs, const path& rhs) noexcept; 24*46035553Spatrick bool operator<=(const path& lhs, const path& rhs) noexcept; 25*46035553Spatrick bool operator> (const path& lhs, const path& rhs) noexcept; 26*46035553Spatrick bool operator>=(const path& lhs, const path& rhs) noexcept; 27*46035553Spatrick 28*46035553Spatrick path operator/ (const path& lhs, const path& rhs); 29*46035553Spatrick 30*46035553Spatrick // fs.path.io operators are friends of path. 31*46035553Spatrick template <class charT, class traits> 32*46035553Spatrick friend basic_ostream<charT, traits>& 33*46035553Spatrick operator<<(basic_ostream<charT, traits>& os, const path& p); 34*46035553Spatrick 35*46035553Spatrick template <class charT, class traits> 36*46035553Spatrick friend basic_istream<charT, traits>& 37*46035553Spatrick operator>>(basic_istream<charT, traits>& is, path& p); 38*46035553Spatrick 39*46035553Spatrick template <class Source> 40*46035553Spatrick path u8path(const Source& source); 41*46035553Spatrick template <class InputIterator> 42*46035553Spatrick path u8path(InputIterator first, InputIterator last); 43*46035553Spatrick 44*46035553Spatrick class filesystem_error; 45*46035553Spatrick class directory_entry; 46*46035553Spatrick 47*46035553Spatrick class directory_iterator; 48*46035553Spatrick 49*46035553Spatrick // enable directory_iterator range-based for statements 50*46035553Spatrick directory_iterator begin(directory_iterator iter) noexcept; 51*46035553Spatrick directory_iterator end(const directory_iterator&) noexcept; 52*46035553Spatrick 53*46035553Spatrick class recursive_directory_iterator; 54*46035553Spatrick 55*46035553Spatrick // enable recursive_directory_iterator range-based for statements 56*46035553Spatrick recursive_directory_iterator begin(recursive_directory_iterator iter) noexcept; 57*46035553Spatrick recursive_directory_iterator end(const recursive_directory_iterator&) noexcept; 58*46035553Spatrick 59*46035553Spatrick class file_status; 60*46035553Spatrick 61*46035553Spatrick struct space_info 62*46035553Spatrick { 63*46035553Spatrick uintmax_t capacity; 64*46035553Spatrick uintmax_t free; 65*46035553Spatrick uintmax_t available; 66*46035553Spatrick }; 67*46035553Spatrick 68*46035553Spatrick enum class file_type; 69*46035553Spatrick enum class perms; 70*46035553Spatrick enum class perm_options; 71*46035553Spatrick enum class copy_options; 72*46035553Spatrick enum class directory_options; 73*46035553Spatrick 74*46035553Spatrick typedef chrono::time_point<trivial-clock> file_time_type; 75*46035553Spatrick 76*46035553Spatrick // operational functions 77*46035553Spatrick 78*46035553Spatrick path absolute(const path& p); 79*46035553Spatrick path absolute(const path& p, error_code &ec); 80*46035553Spatrick 81*46035553Spatrick path canonical(const path& p); 82*46035553Spatrick path canonical(const path& p, error_code& ec); 83*46035553Spatrick 84*46035553Spatrick void copy(const path& from, const path& to); 85*46035553Spatrick void copy(const path& from, const path& to, error_code& ec); 86*46035553Spatrick void copy(const path& from, const path& to, copy_options options); 87*46035553Spatrick void copy(const path& from, const path& to, copy_options options, 88*46035553Spatrick error_code& ec); 89*46035553Spatrick 90*46035553Spatrick bool copy_file(const path& from, const path& to); 91*46035553Spatrick bool copy_file(const path& from, const path& to, error_code& ec); 92*46035553Spatrick bool copy_file(const path& from, const path& to, copy_options option); 93*46035553Spatrick bool copy_file(const path& from, const path& to, copy_options option, 94*46035553Spatrick error_code& ec); 95*46035553Spatrick 96*46035553Spatrick void copy_symlink(const path& existing_symlink, const path& new_symlink); 97*46035553Spatrick void copy_symlink(const path& existing_symlink, const path& new_symlink, 98*46035553Spatrick error_code& ec) noexcept; 99*46035553Spatrick 100*46035553Spatrick bool create_directories(const path& p); 101*46035553Spatrick bool create_directories(const path& p, error_code& ec); 102*46035553Spatrick 103*46035553Spatrick bool create_directory(const path& p); 104*46035553Spatrick bool create_directory(const path& p, error_code& ec) noexcept; 105*46035553Spatrick 106*46035553Spatrick bool create_directory(const path& p, const path& attributes); 107*46035553Spatrick bool create_directory(const path& p, const path& attributes, 108*46035553Spatrick error_code& ec) noexcept; 109*46035553Spatrick 110*46035553Spatrick void create_directory_symlink(const path& to, const path& new_symlink); 111*46035553Spatrick void create_directory_symlink(const path& to, const path& new_symlink, 112*46035553Spatrick error_code& ec) noexcept; 113*46035553Spatrick 114*46035553Spatrick void create_hard_link(const path& to, const path& new_hard_link); 115*46035553Spatrick void create_hard_link(const path& to, const path& new_hard_link, 116*46035553Spatrick error_code& ec) noexcept; 117*46035553Spatrick 118*46035553Spatrick void create_symlink(const path& to, const path& new_symlink); 119*46035553Spatrick void create_symlink(const path& to, const path& new_symlink, 120*46035553Spatrick error_code& ec) noexcept; 121*46035553Spatrick 122*46035553Spatrick path current_path(); 123*46035553Spatrick path current_path(error_code& ec); 124*46035553Spatrick void current_path(const path& p); 125*46035553Spatrick void current_path(const path& p, error_code& ec) noexcept; 126*46035553Spatrick 127*46035553Spatrick bool exists(file_status s) noexcept; 128*46035553Spatrick bool exists(const path& p); 129*46035553Spatrick bool exists(const path& p, error_code& ec) noexcept; 130*46035553Spatrick 131*46035553Spatrick bool equivalent(const path& p1, const path& p2); 132*46035553Spatrick bool equivalent(const path& p1, const path& p2, error_code& ec) noexcept; 133*46035553Spatrick 134*46035553Spatrick uintmax_t file_size(const path& p); 135*46035553Spatrick uintmax_t file_size(const path& p, error_code& ec) noexcept; 136*46035553Spatrick 137*46035553Spatrick uintmax_t hard_link_count(const path& p); 138*46035553Spatrick uintmax_t hard_link_count(const path& p, error_code& ec) noexcept; 139*46035553Spatrick 140*46035553Spatrick bool is_block_file(file_status s) noexcept; 141*46035553Spatrick bool is_block_file(const path& p); 142*46035553Spatrick bool is_block_file(const path& p, error_code& ec) noexcept; 143*46035553Spatrick 144*46035553Spatrick bool is_character_file(file_status s) noexcept; 145*46035553Spatrick bool is_character_file(const path& p); 146*46035553Spatrick bool is_character_file(const path& p, error_code& ec) noexcept; 147*46035553Spatrick 148*46035553Spatrick bool is_directory(file_status s) noexcept; 149*46035553Spatrick bool is_directory(const path& p); 150*46035553Spatrick bool is_directory(const path& p, error_code& ec) noexcept; 151*46035553Spatrick 152*46035553Spatrick bool is_empty(const path& p); 153*46035553Spatrick bool is_empty(const path& p, error_code& ec) noexcept; 154*46035553Spatrick 155*46035553Spatrick bool is_fifo(file_status s) noexcept; 156*46035553Spatrick bool is_fifo(const path& p); 157*46035553Spatrick bool is_fifo(const path& p, error_code& ec) noexcept; 158*46035553Spatrick 159*46035553Spatrick bool is_other(file_status s) noexcept; 160*46035553Spatrick bool is_other(const path& p); 161*46035553Spatrick bool is_other(const path& p, error_code& ec) noexcept; 162*46035553Spatrick 163*46035553Spatrick bool is_regular_file(file_status s) noexcept; 164*46035553Spatrick bool is_regular_file(const path& p); 165*46035553Spatrick bool is_regular_file(const path& p, error_code& ec) noexcept; 166*46035553Spatrick 167*46035553Spatrick bool is_socket(file_status s) noexcept; 168*46035553Spatrick bool is_socket(const path& p); 169*46035553Spatrick bool is_socket(const path& p, error_code& ec) noexcept; 170*46035553Spatrick 171*46035553Spatrick bool is_symlink(file_status s) noexcept; 172*46035553Spatrick bool is_symlink(const path& p); 173*46035553Spatrick bool is_symlink(const path& p, error_code& ec) noexcept; 174*46035553Spatrick 175*46035553Spatrick file_time_type last_write_time(const path& p); 176*46035553Spatrick file_time_type last_write_time(const path& p, error_code& ec) noexcept; 177*46035553Spatrick void last_write_time(const path& p, file_time_type new_time); 178*46035553Spatrick void last_write_time(const path& p, file_time_type new_time, 179*46035553Spatrick error_code& ec) noexcept; 180*46035553Spatrick 181*46035553Spatrick void permissions(const path& p, perms prms, 182*46035553Spatrick perm_options opts=perm_options::replace); 183*46035553Spatrick void permissions(const path& p, perms prms, error_code& ec) noexcept; 184*46035553Spatrick void permissions(const path& p, perms prms, perm_options opts, 185*46035553Spatrick error_code& ec); 186*46035553Spatrick 187*46035553Spatrick path proximate(const path& p, error_code& ec); 188*46035553Spatrick path proximate(const path& p, const path& base = current_path()); 189*46035553Spatrick path proximate(const path& p, const path& base, error_code &ec); 190*46035553Spatrick 191*46035553Spatrick path read_symlink(const path& p); 192*46035553Spatrick path read_symlink(const path& p, error_code& ec); 193*46035553Spatrick 194*46035553Spatrick path relative(const path& p, error_code& ec); 195*46035553Spatrick path relative(const path& p, const path& base=current_path()); 196*46035553Spatrick path relative(const path& p, const path& base, error_code& ec); 197*46035553Spatrick 198*46035553Spatrick bool remove(const path& p); 199*46035553Spatrick bool remove(const path& p, error_code& ec) noexcept; 200*46035553Spatrick 201*46035553Spatrick uintmax_t remove_all(const path& p); 202*46035553Spatrick uintmax_t remove_all(const path& p, error_code& ec); 203*46035553Spatrick 204*46035553Spatrick void rename(const path& from, const path& to); 205*46035553Spatrick void rename(const path& from, const path& to, error_code& ec) noexcept; 206*46035553Spatrick 207*46035553Spatrick void resize_file(const path& p, uintmax_t size); 208*46035553Spatrick void resize_file(const path& p, uintmax_t size, error_code& ec) noexcept; 209*46035553Spatrick 210*46035553Spatrick space_info space(const path& p); 211*46035553Spatrick space_info space(const path& p, error_code& ec) noexcept; 212*46035553Spatrick 213*46035553Spatrick file_status status(const path& p); 214*46035553Spatrick file_status status(const path& p, error_code& ec) noexcept; 215*46035553Spatrick 216*46035553Spatrick bool status_known(file_status s) noexcept; 217*46035553Spatrick 218*46035553Spatrick file_status symlink_status(const path& p); 219*46035553Spatrick file_status symlink_status(const path& p, error_code& ec) noexcept; 220*46035553Spatrick 221*46035553Spatrick path temp_directory_path(); 222*46035553Spatrick path temp_directory_path(error_code& ec); 223*46035553Spatrick 224*46035553Spatrick path weakly_canonical(path const& p); 225*46035553Spatrick path weakly_canonical(path const& p, error_code& ec); 226*46035553Spatrick 227*46035553Spatrick 228*46035553Spatrick} } // namespaces std::filesystem 229*46035553Spatrick 230*46035553Spatrick*/ 231*46035553Spatrick 232*46035553Spatrick#include <__config> 233*46035553Spatrick#include <cstddef> 234*46035553Spatrick#include <cstdlib> 235*46035553Spatrick#include <chrono> 236*46035553Spatrick#include <iterator> 237*46035553Spatrick#include <iosfwd> 238*46035553Spatrick#include <locale> 239*46035553Spatrick#include <memory> 240*46035553Spatrick#include <stack> 241*46035553Spatrick#include <string> 242*46035553Spatrick#include <system_error> 243*46035553Spatrick#include <utility> 244*46035553Spatrick#include <iomanip> // for quoted 245*46035553Spatrick#include <string_view> 246*46035553Spatrick#include <version> 247*46035553Spatrick 248*46035553Spatrick#include <__debug> 249*46035553Spatrick 250*46035553Spatrick#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER) 251*46035553Spatrick#pragma GCC system_header 252*46035553Spatrick#endif 253*46035553Spatrick 254*46035553Spatrick_LIBCPP_PUSH_MACROS 255*46035553Spatrick#include <__undef_macros> 256*46035553Spatrick 257*46035553Spatrick#ifndef _LIBCPP_CXX03_LANG 258*46035553Spatrick 259*46035553Spatrick_LIBCPP_BEGIN_NAMESPACE_FILESYSTEM 260*46035553Spatrick 261*46035553Spatrick_LIBCPP_AVAILABILITY_FILESYSTEM_PUSH 262*46035553Spatrick 263*46035553Spatricktypedef chrono::time_point<_FilesystemClock> file_time_type; 264*46035553Spatrick 265*46035553Spatrickstruct _LIBCPP_TYPE_VIS space_info { 266*46035553Spatrick uintmax_t capacity; 267*46035553Spatrick uintmax_t free; 268*46035553Spatrick uintmax_t available; 269*46035553Spatrick}; 270*46035553Spatrick 271*46035553Spatrickenum class _LIBCPP_ENUM_VIS file_type : signed char { 272*46035553Spatrick none = 0, 273*46035553Spatrick not_found = -1, 274*46035553Spatrick regular = 1, 275*46035553Spatrick directory = 2, 276*46035553Spatrick symlink = 3, 277*46035553Spatrick block = 4, 278*46035553Spatrick character = 5, 279*46035553Spatrick fifo = 6, 280*46035553Spatrick socket = 7, 281*46035553Spatrick unknown = 8 282*46035553Spatrick}; 283*46035553Spatrick 284*46035553Spatrickenum class _LIBCPP_ENUM_VIS perms : unsigned { 285*46035553Spatrick none = 0, 286*46035553Spatrick 287*46035553Spatrick owner_read = 0400, 288*46035553Spatrick owner_write = 0200, 289*46035553Spatrick owner_exec = 0100, 290*46035553Spatrick owner_all = 0700, 291*46035553Spatrick 292*46035553Spatrick group_read = 040, 293*46035553Spatrick group_write = 020, 294*46035553Spatrick group_exec = 010, 295*46035553Spatrick group_all = 070, 296*46035553Spatrick 297*46035553Spatrick others_read = 04, 298*46035553Spatrick others_write = 02, 299*46035553Spatrick others_exec = 01, 300*46035553Spatrick others_all = 07, 301*46035553Spatrick 302*46035553Spatrick all = 0777, 303*46035553Spatrick 304*46035553Spatrick set_uid = 04000, 305*46035553Spatrick set_gid = 02000, 306*46035553Spatrick sticky_bit = 01000, 307*46035553Spatrick mask = 07777, 308*46035553Spatrick unknown = 0xFFFF, 309*46035553Spatrick}; 310*46035553Spatrick 311*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 312*46035553Spatrickinline constexpr perms operator&(perms _LHS, perms _RHS) { 313*46035553Spatrick return static_cast<perms>(static_cast<unsigned>(_LHS) & 314*46035553Spatrick static_cast<unsigned>(_RHS)); 315*46035553Spatrick} 316*46035553Spatrick 317*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 318*46035553Spatrickinline constexpr perms operator|(perms _LHS, perms _RHS) { 319*46035553Spatrick return static_cast<perms>(static_cast<unsigned>(_LHS) | 320*46035553Spatrick static_cast<unsigned>(_RHS)); 321*46035553Spatrick} 322*46035553Spatrick 323*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 324*46035553Spatrickinline constexpr perms operator^(perms _LHS, perms _RHS) { 325*46035553Spatrick return static_cast<perms>(static_cast<unsigned>(_LHS) ^ 326*46035553Spatrick static_cast<unsigned>(_RHS)); 327*46035553Spatrick} 328*46035553Spatrick 329*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 330*46035553Spatrickinline constexpr perms operator~(perms _LHS) { 331*46035553Spatrick return static_cast<perms>(~static_cast<unsigned>(_LHS)); 332*46035553Spatrick} 333*46035553Spatrick 334*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 335*46035553Spatrickinline perms& operator&=(perms& _LHS, perms _RHS) { return _LHS = _LHS & _RHS; } 336*46035553Spatrick 337*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 338*46035553Spatrickinline perms& operator|=(perms& _LHS, perms _RHS) { return _LHS = _LHS | _RHS; } 339*46035553Spatrick 340*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 341*46035553Spatrickinline perms& operator^=(perms& _LHS, perms _RHS) { return _LHS = _LHS ^ _RHS; } 342*46035553Spatrick 343*46035553Spatrickenum class _LIBCPP_ENUM_VIS perm_options : unsigned char { 344*46035553Spatrick replace = 1, 345*46035553Spatrick add = 2, 346*46035553Spatrick remove = 4, 347*46035553Spatrick nofollow = 8 348*46035553Spatrick}; 349*46035553Spatrick 350*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 351*46035553Spatrickinline constexpr perm_options operator&(perm_options _LHS, perm_options _RHS) { 352*46035553Spatrick return static_cast<perm_options>(static_cast<unsigned>(_LHS) & 353*46035553Spatrick static_cast<unsigned>(_RHS)); 354*46035553Spatrick} 355*46035553Spatrick 356*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 357*46035553Spatrickinline constexpr perm_options operator|(perm_options _LHS, perm_options _RHS) { 358*46035553Spatrick return static_cast<perm_options>(static_cast<unsigned>(_LHS) | 359*46035553Spatrick static_cast<unsigned>(_RHS)); 360*46035553Spatrick} 361*46035553Spatrick 362*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 363*46035553Spatrickinline constexpr perm_options operator^(perm_options _LHS, perm_options _RHS) { 364*46035553Spatrick return static_cast<perm_options>(static_cast<unsigned>(_LHS) ^ 365*46035553Spatrick static_cast<unsigned>(_RHS)); 366*46035553Spatrick} 367*46035553Spatrick 368*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 369*46035553Spatrickinline constexpr perm_options operator~(perm_options _LHS) { 370*46035553Spatrick return static_cast<perm_options>(~static_cast<unsigned>(_LHS)); 371*46035553Spatrick} 372*46035553Spatrick 373*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 374*46035553Spatrickinline perm_options& operator&=(perm_options& _LHS, perm_options _RHS) { 375*46035553Spatrick return _LHS = _LHS & _RHS; 376*46035553Spatrick} 377*46035553Spatrick 378*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 379*46035553Spatrickinline perm_options& operator|=(perm_options& _LHS, perm_options _RHS) { 380*46035553Spatrick return _LHS = _LHS | _RHS; 381*46035553Spatrick} 382*46035553Spatrick 383*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 384*46035553Spatrickinline perm_options& operator^=(perm_options& _LHS, perm_options _RHS) { 385*46035553Spatrick return _LHS = _LHS ^ _RHS; 386*46035553Spatrick} 387*46035553Spatrick 388*46035553Spatrickenum class _LIBCPP_ENUM_VIS copy_options : unsigned short { 389*46035553Spatrick none = 0, 390*46035553Spatrick skip_existing = 1, 391*46035553Spatrick overwrite_existing = 2, 392*46035553Spatrick update_existing = 4, 393*46035553Spatrick recursive = 8, 394*46035553Spatrick copy_symlinks = 16, 395*46035553Spatrick skip_symlinks = 32, 396*46035553Spatrick directories_only = 64, 397*46035553Spatrick create_symlinks = 128, 398*46035553Spatrick create_hard_links = 256, 399*46035553Spatrick __in_recursive_copy = 512, 400*46035553Spatrick}; 401*46035553Spatrick 402*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 403*46035553Spatrickinline constexpr copy_options operator&(copy_options _LHS, copy_options _RHS) { 404*46035553Spatrick return static_cast<copy_options>(static_cast<unsigned short>(_LHS) & 405*46035553Spatrick static_cast<unsigned short>(_RHS)); 406*46035553Spatrick} 407*46035553Spatrick 408*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 409*46035553Spatrickinline constexpr copy_options operator|(copy_options _LHS, copy_options _RHS) { 410*46035553Spatrick return static_cast<copy_options>(static_cast<unsigned short>(_LHS) | 411*46035553Spatrick static_cast<unsigned short>(_RHS)); 412*46035553Spatrick} 413*46035553Spatrick 414*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 415*46035553Spatrickinline constexpr copy_options operator^(copy_options _LHS, copy_options _RHS) { 416*46035553Spatrick return static_cast<copy_options>(static_cast<unsigned short>(_LHS) ^ 417*46035553Spatrick static_cast<unsigned short>(_RHS)); 418*46035553Spatrick} 419*46035553Spatrick 420*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 421*46035553Spatrickinline constexpr copy_options operator~(copy_options _LHS) { 422*46035553Spatrick return static_cast<copy_options>(~static_cast<unsigned short>(_LHS)); 423*46035553Spatrick} 424*46035553Spatrick 425*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 426*46035553Spatrickinline copy_options& operator&=(copy_options& _LHS, copy_options _RHS) { 427*46035553Spatrick return _LHS = _LHS & _RHS; 428*46035553Spatrick} 429*46035553Spatrick 430*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 431*46035553Spatrickinline copy_options& operator|=(copy_options& _LHS, copy_options _RHS) { 432*46035553Spatrick return _LHS = _LHS | _RHS; 433*46035553Spatrick} 434*46035553Spatrick 435*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 436*46035553Spatrickinline copy_options& operator^=(copy_options& _LHS, copy_options _RHS) { 437*46035553Spatrick return _LHS = _LHS ^ _RHS; 438*46035553Spatrick} 439*46035553Spatrick 440*46035553Spatrickenum class _LIBCPP_ENUM_VIS directory_options : unsigned char { 441*46035553Spatrick none = 0, 442*46035553Spatrick follow_directory_symlink = 1, 443*46035553Spatrick skip_permission_denied = 2 444*46035553Spatrick}; 445*46035553Spatrick 446*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 447*46035553Spatrickinline constexpr directory_options operator&(directory_options _LHS, 448*46035553Spatrick directory_options _RHS) { 449*46035553Spatrick return static_cast<directory_options>(static_cast<unsigned char>(_LHS) & 450*46035553Spatrick static_cast<unsigned char>(_RHS)); 451*46035553Spatrick} 452*46035553Spatrick 453*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 454*46035553Spatrickinline constexpr directory_options operator|(directory_options _LHS, 455*46035553Spatrick directory_options _RHS) { 456*46035553Spatrick return static_cast<directory_options>(static_cast<unsigned char>(_LHS) | 457*46035553Spatrick static_cast<unsigned char>(_RHS)); 458*46035553Spatrick} 459*46035553Spatrick 460*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 461*46035553Spatrickinline constexpr directory_options operator^(directory_options _LHS, 462*46035553Spatrick directory_options _RHS) { 463*46035553Spatrick return static_cast<directory_options>(static_cast<unsigned char>(_LHS) ^ 464*46035553Spatrick static_cast<unsigned char>(_RHS)); 465*46035553Spatrick} 466*46035553Spatrick 467*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 468*46035553Spatrickinline constexpr directory_options operator~(directory_options _LHS) { 469*46035553Spatrick return static_cast<directory_options>(~static_cast<unsigned char>(_LHS)); 470*46035553Spatrick} 471*46035553Spatrick 472*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 473*46035553Spatrickinline directory_options& operator&=(directory_options& _LHS, 474*46035553Spatrick directory_options _RHS) { 475*46035553Spatrick return _LHS = _LHS & _RHS; 476*46035553Spatrick} 477*46035553Spatrick 478*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 479*46035553Spatrickinline directory_options& operator|=(directory_options& _LHS, 480*46035553Spatrick directory_options _RHS) { 481*46035553Spatrick return _LHS = _LHS | _RHS; 482*46035553Spatrick} 483*46035553Spatrick 484*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 485*46035553Spatrickinline directory_options& operator^=(directory_options& _LHS, 486*46035553Spatrick directory_options _RHS) { 487*46035553Spatrick return _LHS = _LHS ^ _RHS; 488*46035553Spatrick} 489*46035553Spatrick 490*46035553Spatrickclass _LIBCPP_TYPE_VIS file_status { 491*46035553Spatrickpublic: 492*46035553Spatrick // constructors 493*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 494*46035553Spatrick file_status() noexcept : file_status(file_type::none) {} 495*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 496*46035553Spatrick explicit file_status(file_type __ft, perms __prms = perms::unknown) noexcept 497*46035553Spatrick : __ft_(__ft), 498*46035553Spatrick __prms_(__prms) {} 499*46035553Spatrick 500*46035553Spatrick file_status(const file_status&) noexcept = default; 501*46035553Spatrick file_status(file_status&&) noexcept = default; 502*46035553Spatrick 503*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 504*46035553Spatrick ~file_status() {} 505*46035553Spatrick 506*46035553Spatrick file_status& operator=(const file_status&) noexcept = default; 507*46035553Spatrick file_status& operator=(file_status&&) noexcept = default; 508*46035553Spatrick 509*46035553Spatrick // observers 510*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 511*46035553Spatrick file_type type() const noexcept { return __ft_; } 512*46035553Spatrick 513*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 514*46035553Spatrick perms permissions() const noexcept { return __prms_; } 515*46035553Spatrick 516*46035553Spatrick // modifiers 517*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 518*46035553Spatrick void type(file_type __ft) noexcept { __ft_ = __ft; } 519*46035553Spatrick 520*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 521*46035553Spatrick void permissions(perms __p) noexcept { __prms_ = __p; } 522*46035553Spatrick 523*46035553Spatrickprivate: 524*46035553Spatrick file_type __ft_; 525*46035553Spatrick perms __prms_; 526*46035553Spatrick}; 527*46035553Spatrick 528*46035553Spatrickclass _LIBCPP_TYPE_VIS directory_entry; 529*46035553Spatrick 530*46035553Spatricktemplate <class _Tp> 531*46035553Spatrickstruct __can_convert_char { 532*46035553Spatrick static const bool value = false; 533*46035553Spatrick}; 534*46035553Spatricktemplate <class _Tp> 535*46035553Spatrickstruct __can_convert_char<const _Tp> : public __can_convert_char<_Tp> {}; 536*46035553Spatricktemplate <> 537*46035553Spatrickstruct __can_convert_char<char> { 538*46035553Spatrick static const bool value = true; 539*46035553Spatrick using __char_type = char; 540*46035553Spatrick}; 541*46035553Spatricktemplate <> 542*46035553Spatrickstruct __can_convert_char<wchar_t> { 543*46035553Spatrick static const bool value = true; 544*46035553Spatrick using __char_type = wchar_t; 545*46035553Spatrick}; 546*46035553Spatricktemplate <> 547*46035553Spatrickstruct __can_convert_char<char16_t> { 548*46035553Spatrick static const bool value = true; 549*46035553Spatrick using __char_type = char16_t; 550*46035553Spatrick}; 551*46035553Spatricktemplate <> 552*46035553Spatrickstruct __can_convert_char<char32_t> { 553*46035553Spatrick static const bool value = true; 554*46035553Spatrick using __char_type = char32_t; 555*46035553Spatrick}; 556*46035553Spatrick 557*46035553Spatricktemplate <class _ECharT> 558*46035553Spatricktypename enable_if<__can_convert_char<_ECharT>::value, bool>::type 559*46035553Spatrick__is_separator(_ECharT __e) { 560*46035553Spatrick return __e == _ECharT('/'); 561*46035553Spatrick} 562*46035553Spatrick 563*46035553Spatrickstruct _NullSentinal {}; 564*46035553Spatrick 565*46035553Spatricktemplate <class _Tp> 566*46035553Spatrickusing _Void = void; 567*46035553Spatrick 568*46035553Spatricktemplate <class _Tp, class = void> 569*46035553Spatrickstruct __is_pathable_string : public false_type {}; 570*46035553Spatrick 571*46035553Spatricktemplate <class _ECharT, class _Traits, class _Alloc> 572*46035553Spatrickstruct __is_pathable_string< 573*46035553Spatrick basic_string<_ECharT, _Traits, _Alloc>, 574*46035553Spatrick _Void<typename __can_convert_char<_ECharT>::__char_type> > 575*46035553Spatrick : public __can_convert_char<_ECharT> { 576*46035553Spatrick using _Str = basic_string<_ECharT, _Traits, _Alloc>; 577*46035553Spatrick using _Base = __can_convert_char<_ECharT>; 578*46035553Spatrick static _ECharT const* __range_begin(_Str const& __s) { return __s.data(); } 579*46035553Spatrick static _ECharT const* __range_end(_Str const& __s) { 580*46035553Spatrick return __s.data() + __s.length(); 581*46035553Spatrick } 582*46035553Spatrick static _ECharT __first_or_null(_Str const& __s) { 583*46035553Spatrick return __s.empty() ? _ECharT{} : __s[0]; 584*46035553Spatrick } 585*46035553Spatrick}; 586*46035553Spatrick 587*46035553Spatricktemplate <class _ECharT, class _Traits> 588*46035553Spatrickstruct __is_pathable_string< 589*46035553Spatrick basic_string_view<_ECharT, _Traits>, 590*46035553Spatrick _Void<typename __can_convert_char<_ECharT>::__char_type> > 591*46035553Spatrick : public __can_convert_char<_ECharT> { 592*46035553Spatrick using _Str = basic_string_view<_ECharT, _Traits>; 593*46035553Spatrick using _Base = __can_convert_char<_ECharT>; 594*46035553Spatrick static _ECharT const* __range_begin(_Str const& __s) { return __s.data(); } 595*46035553Spatrick static _ECharT const* __range_end(_Str const& __s) { 596*46035553Spatrick return __s.data() + __s.length(); 597*46035553Spatrick } 598*46035553Spatrick static _ECharT __first_or_null(_Str const& __s) { 599*46035553Spatrick return __s.empty() ? _ECharT{} : __s[0]; 600*46035553Spatrick } 601*46035553Spatrick}; 602*46035553Spatrick 603*46035553Spatricktemplate <class _Source, class _DS = typename decay<_Source>::type, 604*46035553Spatrick class _UnqualPtrType = 605*46035553Spatrick typename remove_const<typename remove_pointer<_DS>::type>::type, 606*46035553Spatrick bool _IsCharPtr = is_pointer<_DS>::value&& 607*46035553Spatrick __can_convert_char<_UnqualPtrType>::value> 608*46035553Spatrickstruct __is_pathable_char_array : false_type {}; 609*46035553Spatrick 610*46035553Spatricktemplate <class _Source, class _ECharT, class _UPtr> 611*46035553Spatrickstruct __is_pathable_char_array<_Source, _ECharT*, _UPtr, true> 612*46035553Spatrick : __can_convert_char<typename remove_const<_ECharT>::type> { 613*46035553Spatrick using _Base = __can_convert_char<typename remove_const<_ECharT>::type>; 614*46035553Spatrick 615*46035553Spatrick static _ECharT const* __range_begin(const _ECharT* __b) { return __b; } 616*46035553Spatrick static _ECharT const* __range_end(const _ECharT* __b) { 617*46035553Spatrick using _Iter = const _ECharT*; 618*46035553Spatrick const _ECharT __sentinal = _ECharT{}; 619*46035553Spatrick _Iter __e = __b; 620*46035553Spatrick for (; *__e != __sentinal; ++__e) 621*46035553Spatrick ; 622*46035553Spatrick return __e; 623*46035553Spatrick } 624*46035553Spatrick 625*46035553Spatrick static _ECharT __first_or_null(const _ECharT* __b) { return *__b; } 626*46035553Spatrick}; 627*46035553Spatrick 628*46035553Spatricktemplate <class _Iter, bool _IsIt = __is_cpp17_input_iterator<_Iter>::value, 629*46035553Spatrick class = void> 630*46035553Spatrickstruct __is_pathable_iter : false_type {}; 631*46035553Spatrick 632*46035553Spatricktemplate <class _Iter> 633*46035553Spatrickstruct __is_pathable_iter< 634*46035553Spatrick _Iter, true, 635*46035553Spatrick _Void<typename __can_convert_char< 636*46035553Spatrick typename iterator_traits<_Iter>::value_type>::__char_type> > 637*46035553Spatrick : __can_convert_char<typename iterator_traits<_Iter>::value_type> { 638*46035553Spatrick using _ECharT = typename iterator_traits<_Iter>::value_type; 639*46035553Spatrick using _Base = __can_convert_char<_ECharT>; 640*46035553Spatrick 641*46035553Spatrick static _Iter __range_begin(_Iter __b) { return __b; } 642*46035553Spatrick static _NullSentinal __range_end(_Iter) { return _NullSentinal{}; } 643*46035553Spatrick 644*46035553Spatrick static _ECharT __first_or_null(_Iter __b) { return *__b; } 645*46035553Spatrick}; 646*46035553Spatrick 647*46035553Spatricktemplate <class _Tp, bool _IsStringT = __is_pathable_string<_Tp>::value, 648*46035553Spatrick bool _IsCharIterT = __is_pathable_char_array<_Tp>::value, 649*46035553Spatrick bool _IsIterT = !_IsCharIterT && __is_pathable_iter<_Tp>::value> 650*46035553Spatrickstruct __is_pathable : false_type { 651*46035553Spatrick static_assert(!_IsStringT && !_IsCharIterT && !_IsIterT, "Must all be false"); 652*46035553Spatrick}; 653*46035553Spatrick 654*46035553Spatricktemplate <class _Tp> 655*46035553Spatrickstruct __is_pathable<_Tp, true, false, false> : __is_pathable_string<_Tp> {}; 656*46035553Spatrick 657*46035553Spatricktemplate <class _Tp> 658*46035553Spatrickstruct __is_pathable<_Tp, false, true, false> : __is_pathable_char_array<_Tp> { 659*46035553Spatrick}; 660*46035553Spatrick 661*46035553Spatricktemplate <class _Tp> 662*46035553Spatrickstruct __is_pathable<_Tp, false, false, true> : __is_pathable_iter<_Tp> {}; 663*46035553Spatrick 664*46035553Spatricktemplate <class _ECharT> 665*46035553Spatrickstruct _PathCVT { 666*46035553Spatrick static_assert(__can_convert_char<_ECharT>::value, 667*46035553Spatrick "Char type not convertible"); 668*46035553Spatrick 669*46035553Spatrick typedef __narrow_to_utf8<sizeof(_ECharT) * __CHAR_BIT__> _Narrower; 670*46035553Spatrick 671*46035553Spatrick static void __append_range(string& __dest, _ECharT const* __b, 672*46035553Spatrick _ECharT const* __e) { 673*46035553Spatrick _Narrower()(back_inserter(__dest), __b, __e); 674*46035553Spatrick } 675*46035553Spatrick 676*46035553Spatrick template <class _Iter> 677*46035553Spatrick static void __append_range(string& __dest, _Iter __b, _Iter __e) { 678*46035553Spatrick static_assert(!is_same<_Iter, _ECharT*>::value, "Call const overload"); 679*46035553Spatrick if (__b == __e) 680*46035553Spatrick return; 681*46035553Spatrick basic_string<_ECharT> __tmp(__b, __e); 682*46035553Spatrick _Narrower()(back_inserter(__dest), __tmp.data(), 683*46035553Spatrick __tmp.data() + __tmp.length()); 684*46035553Spatrick } 685*46035553Spatrick 686*46035553Spatrick template <class _Iter> 687*46035553Spatrick static void __append_range(string& __dest, _Iter __b, _NullSentinal) { 688*46035553Spatrick static_assert(!is_same<_Iter, _ECharT*>::value, "Call const overload"); 689*46035553Spatrick const _ECharT __sentinal = _ECharT{}; 690*46035553Spatrick if (*__b == __sentinal) 691*46035553Spatrick return; 692*46035553Spatrick basic_string<_ECharT> __tmp; 693*46035553Spatrick for (; *__b != __sentinal; ++__b) 694*46035553Spatrick __tmp.push_back(*__b); 695*46035553Spatrick _Narrower()(back_inserter(__dest), __tmp.data(), 696*46035553Spatrick __tmp.data() + __tmp.length()); 697*46035553Spatrick } 698*46035553Spatrick 699*46035553Spatrick template <class _Source> 700*46035553Spatrick static void __append_source(string& __dest, _Source const& __s) { 701*46035553Spatrick using _Traits = __is_pathable<_Source>; 702*46035553Spatrick __append_range(__dest, _Traits::__range_begin(__s), 703*46035553Spatrick _Traits::__range_end(__s)); 704*46035553Spatrick } 705*46035553Spatrick}; 706*46035553Spatrick 707*46035553Spatricktemplate <> 708*46035553Spatrickstruct _PathCVT<char> { 709*46035553Spatrick 710*46035553Spatrick template <class _Iter> 711*46035553Spatrick static typename enable_if<__is_exactly_cpp17_input_iterator<_Iter>::value>::type 712*46035553Spatrick __append_range(string& __dest, _Iter __b, _Iter __e) { 713*46035553Spatrick for (; __b != __e; ++__b) 714*46035553Spatrick __dest.push_back(*__b); 715*46035553Spatrick } 716*46035553Spatrick 717*46035553Spatrick template <class _Iter> 718*46035553Spatrick static typename enable_if<__is_cpp17_forward_iterator<_Iter>::value>::type 719*46035553Spatrick __append_range(string& __dest, _Iter __b, _Iter __e) { 720*46035553Spatrick __dest.__append_forward_unsafe(__b, __e); 721*46035553Spatrick } 722*46035553Spatrick 723*46035553Spatrick template <class _Iter> 724*46035553Spatrick static void __append_range(string& __dest, _Iter __b, _NullSentinal) { 725*46035553Spatrick const char __sentinal = char{}; 726*46035553Spatrick for (; *__b != __sentinal; ++__b) 727*46035553Spatrick __dest.push_back(*__b); 728*46035553Spatrick } 729*46035553Spatrick 730*46035553Spatrick template <class _Source> 731*46035553Spatrick static void __append_source(string& __dest, _Source const& __s) { 732*46035553Spatrick using _Traits = __is_pathable<_Source>; 733*46035553Spatrick __append_range(__dest, _Traits::__range_begin(__s), 734*46035553Spatrick _Traits::__range_end(__s)); 735*46035553Spatrick } 736*46035553Spatrick}; 737*46035553Spatrick 738*46035553Spatrickclass _LIBCPP_TYPE_VIS path { 739*46035553Spatrick template <class _SourceOrIter, class _Tp = path&> 740*46035553Spatrick using _EnableIfPathable = 741*46035553Spatrick typename enable_if<__is_pathable<_SourceOrIter>::value, _Tp>::type; 742*46035553Spatrick 743*46035553Spatrick template <class _Tp> 744*46035553Spatrick using _SourceChar = typename __is_pathable<_Tp>::__char_type; 745*46035553Spatrick 746*46035553Spatrick template <class _Tp> 747*46035553Spatrick using _SourceCVT = _PathCVT<_SourceChar<_Tp> >; 748*46035553Spatrick 749*46035553Spatrickpublic: 750*46035553Spatrick typedef char value_type; 751*46035553Spatrick typedef basic_string<value_type> string_type; 752*46035553Spatrick typedef _VSTD::string_view __string_view; 753*46035553Spatrick static constexpr value_type preferred_separator = '/'; 754*46035553Spatrick 755*46035553Spatrick enum class _LIBCPP_ENUM_VIS format : unsigned char { 756*46035553Spatrick auto_format, 757*46035553Spatrick native_format, 758*46035553Spatrick generic_format 759*46035553Spatrick }; 760*46035553Spatrick 761*46035553Spatrick // constructors and destructor 762*46035553Spatrick _LIBCPP_INLINE_VISIBILITY path() noexcept {} 763*46035553Spatrick _LIBCPP_INLINE_VISIBILITY path(const path& __p) : __pn_(__p.__pn_) {} 764*46035553Spatrick _LIBCPP_INLINE_VISIBILITY path(path&& __p) noexcept 765*46035553Spatrick : __pn_(_VSTD::move(__p.__pn_)) {} 766*46035553Spatrick 767*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 768*46035553Spatrick path(string_type&& __s, format = format::auto_format) noexcept 769*46035553Spatrick : __pn_(_VSTD::move(__s)) {} 770*46035553Spatrick 771*46035553Spatrick template <class _Source, class = _EnableIfPathable<_Source, void> > 772*46035553Spatrick path(const _Source& __src, format = format::auto_format) { 773*46035553Spatrick _SourceCVT<_Source>::__append_source(__pn_, __src); 774*46035553Spatrick } 775*46035553Spatrick 776*46035553Spatrick template <class _InputIt> 777*46035553Spatrick path(_InputIt __first, _InputIt __last, format = format::auto_format) { 778*46035553Spatrick typedef typename iterator_traits<_InputIt>::value_type _ItVal; 779*46035553Spatrick _PathCVT<_ItVal>::__append_range(__pn_, __first, __last); 780*46035553Spatrick } 781*46035553Spatrick 782*46035553Spatrick // TODO Implement locale conversions. 783*46035553Spatrick template <class _Source, class = _EnableIfPathable<_Source, void> > 784*46035553Spatrick path(const _Source& __src, const locale& __loc, format = format::auto_format); 785*46035553Spatrick template <class _InputIt> 786*46035553Spatrick path(_InputIt __first, _InputIt _last, const locale& __loc, 787*46035553Spatrick format = format::auto_format); 788*46035553Spatrick 789*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 790*46035553Spatrick ~path() = default; 791*46035553Spatrick 792*46035553Spatrick // assignments 793*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 794*46035553Spatrick path& operator=(const path& __p) { 795*46035553Spatrick __pn_ = __p.__pn_; 796*46035553Spatrick return *this; 797*46035553Spatrick } 798*46035553Spatrick 799*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 800*46035553Spatrick path& operator=(path&& __p) noexcept { 801*46035553Spatrick __pn_ = _VSTD::move(__p.__pn_); 802*46035553Spatrick return *this; 803*46035553Spatrick } 804*46035553Spatrick 805*46035553Spatrick template <class = void> 806*46035553Spatrick _LIBCPP_INLINE_VISIBILITY path& operator=(string_type&& __s) noexcept { 807*46035553Spatrick __pn_ = _VSTD::move(__s); 808*46035553Spatrick return *this; 809*46035553Spatrick } 810*46035553Spatrick 811*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 812*46035553Spatrick path& assign(string_type&& __s) noexcept { 813*46035553Spatrick __pn_ = _VSTD::move(__s); 814*46035553Spatrick return *this; 815*46035553Spatrick } 816*46035553Spatrick 817*46035553Spatrick template <class _Source> 818*46035553Spatrick _LIBCPP_INLINE_VISIBILITY _EnableIfPathable<_Source> 819*46035553Spatrick operator=(const _Source& __src) { 820*46035553Spatrick return this->assign(__src); 821*46035553Spatrick } 822*46035553Spatrick 823*46035553Spatrick template <class _Source> 824*46035553Spatrick _EnableIfPathable<_Source> assign(const _Source& __src) { 825*46035553Spatrick __pn_.clear(); 826*46035553Spatrick _SourceCVT<_Source>::__append_source(__pn_, __src); 827*46035553Spatrick return *this; 828*46035553Spatrick } 829*46035553Spatrick 830*46035553Spatrick template <class _InputIt> 831*46035553Spatrick path& assign(_InputIt __first, _InputIt __last) { 832*46035553Spatrick typedef typename iterator_traits<_InputIt>::value_type _ItVal; 833*46035553Spatrick __pn_.clear(); 834*46035553Spatrick _PathCVT<_ItVal>::__append_range(__pn_, __first, __last); 835*46035553Spatrick return *this; 836*46035553Spatrick } 837*46035553Spatrick 838*46035553Spatrickprivate: 839*46035553Spatrick template <class _ECharT> 840*46035553Spatrick static bool __source_is_absolute(_ECharT __first_or_null) { 841*46035553Spatrick return __is_separator(__first_or_null); 842*46035553Spatrick } 843*46035553Spatrick 844*46035553Spatrickpublic: 845*46035553Spatrick // appends 846*46035553Spatrick path& operator/=(const path& __p) { 847*46035553Spatrick if (__p.is_absolute()) { 848*46035553Spatrick __pn_ = __p.__pn_; 849*46035553Spatrick return *this; 850*46035553Spatrick } 851*46035553Spatrick if (has_filename()) 852*46035553Spatrick __pn_ += preferred_separator; 853*46035553Spatrick __pn_ += __p.native(); 854*46035553Spatrick return *this; 855*46035553Spatrick } 856*46035553Spatrick 857*46035553Spatrick // FIXME: Use _LIBCPP_DIAGNOSE_WARNING to produce a diagnostic when __src 858*46035553Spatrick // is known at compile time to be "/' since the user almost certainly intended 859*46035553Spatrick // to append a separator instead of overwriting the path with "/" 860*46035553Spatrick template <class _Source> 861*46035553Spatrick _LIBCPP_INLINE_VISIBILITY _EnableIfPathable<_Source> 862*46035553Spatrick operator/=(const _Source& __src) { 863*46035553Spatrick return this->append(__src); 864*46035553Spatrick } 865*46035553Spatrick 866*46035553Spatrick template <class _Source> 867*46035553Spatrick _EnableIfPathable<_Source> append(const _Source& __src) { 868*46035553Spatrick using _Traits = __is_pathable<_Source>; 869*46035553Spatrick using _CVT = _PathCVT<_SourceChar<_Source> >; 870*46035553Spatrick if (__source_is_absolute(_Traits::__first_or_null(__src))) 871*46035553Spatrick __pn_.clear(); 872*46035553Spatrick else if (has_filename()) 873*46035553Spatrick __pn_ += preferred_separator; 874*46035553Spatrick _CVT::__append_source(__pn_, __src); 875*46035553Spatrick return *this; 876*46035553Spatrick } 877*46035553Spatrick 878*46035553Spatrick template <class _InputIt> 879*46035553Spatrick path& append(_InputIt __first, _InputIt __last) { 880*46035553Spatrick typedef typename iterator_traits<_InputIt>::value_type _ItVal; 881*46035553Spatrick static_assert(__can_convert_char<_ItVal>::value, "Must convertible"); 882*46035553Spatrick using _CVT = _PathCVT<_ItVal>; 883*46035553Spatrick if (__first != __last && __source_is_absolute(*__first)) 884*46035553Spatrick __pn_.clear(); 885*46035553Spatrick else if (has_filename()) 886*46035553Spatrick __pn_ += preferred_separator; 887*46035553Spatrick _CVT::__append_range(__pn_, __first, __last); 888*46035553Spatrick return *this; 889*46035553Spatrick } 890*46035553Spatrick 891*46035553Spatrick // concatenation 892*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 893*46035553Spatrick path& operator+=(const path& __x) { 894*46035553Spatrick __pn_ += __x.__pn_; 895*46035553Spatrick return *this; 896*46035553Spatrick } 897*46035553Spatrick 898*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 899*46035553Spatrick path& operator+=(const string_type& __x) { 900*46035553Spatrick __pn_ += __x; 901*46035553Spatrick return *this; 902*46035553Spatrick } 903*46035553Spatrick 904*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 905*46035553Spatrick path& operator+=(__string_view __x) { 906*46035553Spatrick __pn_ += __x; 907*46035553Spatrick return *this; 908*46035553Spatrick } 909*46035553Spatrick 910*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 911*46035553Spatrick path& operator+=(const value_type* __x) { 912*46035553Spatrick __pn_ += __x; 913*46035553Spatrick return *this; 914*46035553Spatrick } 915*46035553Spatrick 916*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 917*46035553Spatrick path& operator+=(value_type __x) { 918*46035553Spatrick __pn_ += __x; 919*46035553Spatrick return *this; 920*46035553Spatrick } 921*46035553Spatrick 922*46035553Spatrick template <class _ECharT> 923*46035553Spatrick typename enable_if<__can_convert_char<_ECharT>::value, path&>::type 924*46035553Spatrick operator+=(_ECharT __x) { 925*46035553Spatrick basic_string<_ECharT> __tmp; 926*46035553Spatrick __tmp += __x; 927*46035553Spatrick _PathCVT<_ECharT>::__append_source(__pn_, __tmp); 928*46035553Spatrick return *this; 929*46035553Spatrick } 930*46035553Spatrick 931*46035553Spatrick template <class _Source> 932*46035553Spatrick _EnableIfPathable<_Source> operator+=(const _Source& __x) { 933*46035553Spatrick return this->concat(__x); 934*46035553Spatrick } 935*46035553Spatrick 936*46035553Spatrick template <class _Source> 937*46035553Spatrick _EnableIfPathable<_Source> concat(const _Source& __x) { 938*46035553Spatrick _SourceCVT<_Source>::__append_source(__pn_, __x); 939*46035553Spatrick return *this; 940*46035553Spatrick } 941*46035553Spatrick 942*46035553Spatrick template <class _InputIt> 943*46035553Spatrick path& concat(_InputIt __first, _InputIt __last) { 944*46035553Spatrick typedef typename iterator_traits<_InputIt>::value_type _ItVal; 945*46035553Spatrick _PathCVT<_ItVal>::__append_range(__pn_, __first, __last); 946*46035553Spatrick return *this; 947*46035553Spatrick } 948*46035553Spatrick 949*46035553Spatrick // modifiers 950*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 951*46035553Spatrick void clear() noexcept { __pn_.clear(); } 952*46035553Spatrick 953*46035553Spatrick path& make_preferred() { return *this; } 954*46035553Spatrick 955*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 956*46035553Spatrick path& remove_filename() { 957*46035553Spatrick auto __fname = __filename(); 958*46035553Spatrick if (!__fname.empty()) 959*46035553Spatrick __pn_.erase(__fname.data() - __pn_.data()); 960*46035553Spatrick return *this; 961*46035553Spatrick } 962*46035553Spatrick 963*46035553Spatrick path& replace_filename(const path& __replacement) { 964*46035553Spatrick remove_filename(); 965*46035553Spatrick return (*this /= __replacement); 966*46035553Spatrick } 967*46035553Spatrick 968*46035553Spatrick path& replace_extension(const path& __replacement = path()); 969*46035553Spatrick 970*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 971*46035553Spatrick void swap(path& __rhs) noexcept { __pn_.swap(__rhs.__pn_); } 972*46035553Spatrick 973*46035553Spatrick // private helper to allow reserving memory in the path 974*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 975*46035553Spatrick void __reserve(size_t __s) { __pn_.reserve(__s); } 976*46035553Spatrick 977*46035553Spatrick // native format observers 978*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 979*46035553Spatrick const string_type& native() const noexcept { return __pn_; } 980*46035553Spatrick 981*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 982*46035553Spatrick const value_type* c_str() const noexcept { return __pn_.c_str(); } 983*46035553Spatrick 984*46035553Spatrick _LIBCPP_INLINE_VISIBILITY operator string_type() const { return __pn_; } 985*46035553Spatrick 986*46035553Spatrick template <class _ECharT, class _Traits = char_traits<_ECharT>, 987*46035553Spatrick class _Allocator = allocator<_ECharT> > 988*46035553Spatrick basic_string<_ECharT, _Traits, _Allocator> 989*46035553Spatrick string(const _Allocator& __a = _Allocator()) const { 990*46035553Spatrick using _CVT = __widen_from_utf8<sizeof(_ECharT) * __CHAR_BIT__>; 991*46035553Spatrick using _Str = basic_string<_ECharT, _Traits, _Allocator>; 992*46035553Spatrick _Str __s(__a); 993*46035553Spatrick __s.reserve(__pn_.size()); 994*46035553Spatrick _CVT()(back_inserter(__s), __pn_.data(), __pn_.data() + __pn_.size()); 995*46035553Spatrick return __s; 996*46035553Spatrick } 997*46035553Spatrick 998*46035553Spatrick _LIBCPP_INLINE_VISIBILITY std::string string() const { return __pn_; } 999*46035553Spatrick _LIBCPP_INLINE_VISIBILITY std::wstring wstring() const { 1000*46035553Spatrick return string<wchar_t>(); 1001*46035553Spatrick } 1002*46035553Spatrick _LIBCPP_INLINE_VISIBILITY std::string u8string() const { return __pn_; } 1003*46035553Spatrick _LIBCPP_INLINE_VISIBILITY std::u16string u16string() const { 1004*46035553Spatrick return string<char16_t>(); 1005*46035553Spatrick } 1006*46035553Spatrick _LIBCPP_INLINE_VISIBILITY std::u32string u32string() const { 1007*46035553Spatrick return string<char32_t>(); 1008*46035553Spatrick } 1009*46035553Spatrick 1010*46035553Spatrick // generic format observers 1011*46035553Spatrick template <class _ECharT, class _Traits = char_traits<_ECharT>, 1012*46035553Spatrick class _Allocator = allocator<_ECharT> > 1013*46035553Spatrick basic_string<_ECharT, _Traits, _Allocator> 1014*46035553Spatrick generic_string(const _Allocator& __a = _Allocator()) const { 1015*46035553Spatrick return string<_ECharT, _Traits, _Allocator>(__a); 1016*46035553Spatrick } 1017*46035553Spatrick 1018*46035553Spatrick std::string generic_string() const { return __pn_; } 1019*46035553Spatrick std::wstring generic_wstring() const { return string<wchar_t>(); } 1020*46035553Spatrick std::string generic_u8string() const { return __pn_; } 1021*46035553Spatrick std::u16string generic_u16string() const { return string<char16_t>(); } 1022*46035553Spatrick std::u32string generic_u32string() const { return string<char32_t>(); } 1023*46035553Spatrick 1024*46035553Spatrickprivate: 1025*46035553Spatrick int __compare(__string_view) const; 1026*46035553Spatrick __string_view __root_name() const; 1027*46035553Spatrick __string_view __root_directory() const; 1028*46035553Spatrick __string_view __root_path_raw() const; 1029*46035553Spatrick __string_view __relative_path() const; 1030*46035553Spatrick __string_view __parent_path() const; 1031*46035553Spatrick __string_view __filename() const; 1032*46035553Spatrick __string_view __stem() const; 1033*46035553Spatrick __string_view __extension() const; 1034*46035553Spatrick 1035*46035553Spatrickpublic: 1036*46035553Spatrick // compare 1037*46035553Spatrick _LIBCPP_INLINE_VISIBILITY int compare(const path& __p) const noexcept { 1038*46035553Spatrick return __compare(__p.__pn_); 1039*46035553Spatrick } 1040*46035553Spatrick _LIBCPP_INLINE_VISIBILITY int compare(const string_type& __s) const { 1041*46035553Spatrick return __compare(__s); 1042*46035553Spatrick } 1043*46035553Spatrick _LIBCPP_INLINE_VISIBILITY int compare(__string_view __s) const { 1044*46035553Spatrick return __compare(__s); 1045*46035553Spatrick } 1046*46035553Spatrick _LIBCPP_INLINE_VISIBILITY int compare(const value_type* __s) const { 1047*46035553Spatrick return __compare(__s); 1048*46035553Spatrick } 1049*46035553Spatrick 1050*46035553Spatrick // decomposition 1051*46035553Spatrick _LIBCPP_INLINE_VISIBILITY path root_name() const { 1052*46035553Spatrick return string_type(__root_name()); 1053*46035553Spatrick } 1054*46035553Spatrick _LIBCPP_INLINE_VISIBILITY path root_directory() const { 1055*46035553Spatrick return string_type(__root_directory()); 1056*46035553Spatrick } 1057*46035553Spatrick _LIBCPP_INLINE_VISIBILITY path root_path() const { 1058*46035553Spatrick return root_name().append(string_type(__root_directory())); 1059*46035553Spatrick } 1060*46035553Spatrick _LIBCPP_INLINE_VISIBILITY path relative_path() const { 1061*46035553Spatrick return string_type(__relative_path()); 1062*46035553Spatrick } 1063*46035553Spatrick _LIBCPP_INLINE_VISIBILITY path parent_path() const { 1064*46035553Spatrick return string_type(__parent_path()); 1065*46035553Spatrick } 1066*46035553Spatrick _LIBCPP_INLINE_VISIBILITY path filename() const { 1067*46035553Spatrick return string_type(__filename()); 1068*46035553Spatrick } 1069*46035553Spatrick _LIBCPP_INLINE_VISIBILITY path stem() const { return string_type(__stem()); } 1070*46035553Spatrick _LIBCPP_INLINE_VISIBILITY path extension() const { 1071*46035553Spatrick return string_type(__extension()); 1072*46035553Spatrick } 1073*46035553Spatrick 1074*46035553Spatrick // query 1075*46035553Spatrick _LIBCPP_NODISCARD_AFTER_CXX17 _LIBCPP_INLINE_VISIBILITY bool 1076*46035553Spatrick empty() const noexcept { 1077*46035553Spatrick return __pn_.empty(); 1078*46035553Spatrick } 1079*46035553Spatrick 1080*46035553Spatrick _LIBCPP_INLINE_VISIBILITY bool has_root_name() const { 1081*46035553Spatrick return !__root_name().empty(); 1082*46035553Spatrick } 1083*46035553Spatrick _LIBCPP_INLINE_VISIBILITY bool has_root_directory() const { 1084*46035553Spatrick return !__root_directory().empty(); 1085*46035553Spatrick } 1086*46035553Spatrick _LIBCPP_INLINE_VISIBILITY bool has_root_path() const { 1087*46035553Spatrick return !__root_path_raw().empty(); 1088*46035553Spatrick } 1089*46035553Spatrick _LIBCPP_INLINE_VISIBILITY bool has_relative_path() const { 1090*46035553Spatrick return !__relative_path().empty(); 1091*46035553Spatrick } 1092*46035553Spatrick _LIBCPP_INLINE_VISIBILITY bool has_parent_path() const { 1093*46035553Spatrick return !__parent_path().empty(); 1094*46035553Spatrick } 1095*46035553Spatrick _LIBCPP_INLINE_VISIBILITY bool has_filename() const { 1096*46035553Spatrick return !__filename().empty(); 1097*46035553Spatrick } 1098*46035553Spatrick _LIBCPP_INLINE_VISIBILITY bool has_stem() const { return !__stem().empty(); } 1099*46035553Spatrick _LIBCPP_INLINE_VISIBILITY bool has_extension() const { 1100*46035553Spatrick return !__extension().empty(); 1101*46035553Spatrick } 1102*46035553Spatrick 1103*46035553Spatrick _LIBCPP_INLINE_VISIBILITY bool is_absolute() const { 1104*46035553Spatrick return has_root_directory(); 1105*46035553Spatrick } 1106*46035553Spatrick _LIBCPP_INLINE_VISIBILITY bool is_relative() const { return !is_absolute(); } 1107*46035553Spatrick 1108*46035553Spatrick // relative paths 1109*46035553Spatrick path lexically_normal() const; 1110*46035553Spatrick path lexically_relative(const path& __base) const; 1111*46035553Spatrick 1112*46035553Spatrick _LIBCPP_INLINE_VISIBILITY path lexically_proximate(const path& __base) const { 1113*46035553Spatrick path __result = this->lexically_relative(__base); 1114*46035553Spatrick if (__result.native().empty()) 1115*46035553Spatrick return *this; 1116*46035553Spatrick return __result; 1117*46035553Spatrick } 1118*46035553Spatrick 1119*46035553Spatrick // iterators 1120*46035553Spatrick class _LIBCPP_TYPE_VIS iterator; 1121*46035553Spatrick typedef iterator const_iterator; 1122*46035553Spatrick 1123*46035553Spatrick iterator begin() const; 1124*46035553Spatrick iterator end() const; 1125*46035553Spatrick 1126*46035553Spatrick template <class _CharT, class _Traits> 1127*46035553Spatrick _LIBCPP_INLINE_VISIBILITY friend 1128*46035553Spatrick typename enable_if<is_same<_CharT, char>::value && 1129*46035553Spatrick is_same<_Traits, char_traits<char> >::value, 1130*46035553Spatrick basic_ostream<_CharT, _Traits>&>::type 1131*46035553Spatrick operator<<(basic_ostream<_CharT, _Traits>& __os, const path& __p) { 1132*46035553Spatrick __os << std::__quoted(__p.native()); 1133*46035553Spatrick return __os; 1134*46035553Spatrick } 1135*46035553Spatrick 1136*46035553Spatrick template <class _CharT, class _Traits> 1137*46035553Spatrick _LIBCPP_INLINE_VISIBILITY friend 1138*46035553Spatrick typename enable_if<!is_same<_CharT, char>::value || 1139*46035553Spatrick !is_same<_Traits, char_traits<char> >::value, 1140*46035553Spatrick basic_ostream<_CharT, _Traits>&>::type 1141*46035553Spatrick operator<<(basic_ostream<_CharT, _Traits>& __os, const path& __p) { 1142*46035553Spatrick __os << std::__quoted(__p.string<_CharT, _Traits>()); 1143*46035553Spatrick return __os; 1144*46035553Spatrick } 1145*46035553Spatrick 1146*46035553Spatrick template <class _CharT, class _Traits> 1147*46035553Spatrick _LIBCPP_INLINE_VISIBILITY friend basic_istream<_CharT, _Traits>& 1148*46035553Spatrick operator>>(basic_istream<_CharT, _Traits>& __is, path& __p) { 1149*46035553Spatrick basic_string<_CharT, _Traits> __tmp; 1150*46035553Spatrick __is >> __quoted(__tmp); 1151*46035553Spatrick __p = __tmp; 1152*46035553Spatrick return __is; 1153*46035553Spatrick } 1154*46035553Spatrick 1155*46035553Spatrick friend _LIBCPP_INLINE_VISIBILITY bool operator==(const path& __lhs, const path& __rhs) noexcept { 1156*46035553Spatrick return __lhs.compare(__rhs) == 0; 1157*46035553Spatrick } 1158*46035553Spatrick friend _LIBCPP_INLINE_VISIBILITY bool operator!=(const path& __lhs, const path& __rhs) noexcept { 1159*46035553Spatrick return __lhs.compare(__rhs) != 0; 1160*46035553Spatrick } 1161*46035553Spatrick friend _LIBCPP_INLINE_VISIBILITY bool operator<(const path& __lhs, const path& __rhs) noexcept { 1162*46035553Spatrick return __lhs.compare(__rhs) < 0; 1163*46035553Spatrick } 1164*46035553Spatrick friend _LIBCPP_INLINE_VISIBILITY bool operator<=(const path& __lhs, const path& __rhs) noexcept { 1165*46035553Spatrick return __lhs.compare(__rhs) <= 0; 1166*46035553Spatrick } 1167*46035553Spatrick friend _LIBCPP_INLINE_VISIBILITY bool operator>(const path& __lhs, const path& __rhs) noexcept { 1168*46035553Spatrick return __lhs.compare(__rhs) > 0; 1169*46035553Spatrick } 1170*46035553Spatrick friend _LIBCPP_INLINE_VISIBILITY bool operator>=(const path& __lhs, const path& __rhs) noexcept { 1171*46035553Spatrick return __lhs.compare(__rhs) >= 0; 1172*46035553Spatrick } 1173*46035553Spatrick 1174*46035553Spatrick friend _LIBCPP_INLINE_VISIBILITY path operator/(const path& __lhs, 1175*46035553Spatrick const path& __rhs) { 1176*46035553Spatrick path __result(__lhs); 1177*46035553Spatrick __result /= __rhs; 1178*46035553Spatrick return __result; 1179*46035553Spatrick } 1180*46035553Spatrickprivate: 1181*46035553Spatrick inline _LIBCPP_INLINE_VISIBILITY path& 1182*46035553Spatrick __assign_view(__string_view const& __s) noexcept { 1183*46035553Spatrick __pn_ = string_type(__s); 1184*46035553Spatrick return *this; 1185*46035553Spatrick } 1186*46035553Spatrick string_type __pn_; 1187*46035553Spatrick}; 1188*46035553Spatrick 1189*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void swap(path& __lhs, path& __rhs) noexcept { 1190*46035553Spatrick __lhs.swap(__rhs); 1191*46035553Spatrick} 1192*46035553Spatrick 1193*46035553Spatrick_LIBCPP_FUNC_VIS 1194*46035553Spatricksize_t hash_value(const path& __p) noexcept; 1195*46035553Spatrick 1196*46035553Spatricktemplate <class _Source> 1197*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 1198*46035553Spatrick typename enable_if<__is_pathable<_Source>::value, path>::type 1199*46035553Spatrick u8path(const _Source& __s) { 1200*46035553Spatrick static_assert( 1201*46035553Spatrick is_same<typename __is_pathable<_Source>::__char_type, char>::value, 1202*46035553Spatrick "u8path(Source const&) requires Source have a character type of type " 1203*46035553Spatrick "'char'"); 1204*46035553Spatrick return path(__s); 1205*46035553Spatrick} 1206*46035553Spatrick 1207*46035553Spatricktemplate <class _InputIt> 1208*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 1209*46035553Spatrick typename enable_if<__is_pathable<_InputIt>::value, path>::type 1210*46035553Spatrick u8path(_InputIt __f, _InputIt __l) { 1211*46035553Spatrick static_assert( 1212*46035553Spatrick is_same<typename __is_pathable<_InputIt>::__char_type, char>::value, 1213*46035553Spatrick "u8path(Iter, Iter) requires Iter have a value_type of type 'char'"); 1214*46035553Spatrick return path(__f, __l); 1215*46035553Spatrick} 1216*46035553Spatrick 1217*46035553Spatrickclass _LIBCPP_TYPE_VIS path::iterator { 1218*46035553Spatrickpublic: 1219*46035553Spatrick enum _ParserState : unsigned char { 1220*46035553Spatrick _Singular, 1221*46035553Spatrick _BeforeBegin, 1222*46035553Spatrick _InRootName, 1223*46035553Spatrick _InRootDir, 1224*46035553Spatrick _InFilenames, 1225*46035553Spatrick _InTrailingSep, 1226*46035553Spatrick _AtEnd 1227*46035553Spatrick }; 1228*46035553Spatrick 1229*46035553Spatrickpublic: 1230*46035553Spatrick typedef bidirectional_iterator_tag iterator_category; 1231*46035553Spatrick 1232*46035553Spatrick typedef path value_type; 1233*46035553Spatrick typedef std::ptrdiff_t difference_type; 1234*46035553Spatrick typedef const path* pointer; 1235*46035553Spatrick typedef const path& reference; 1236*46035553Spatrick 1237*46035553Spatrick typedef void 1238*46035553Spatrick __stashing_iterator_tag; // See reverse_iterator and __is_stashing_iterator 1239*46035553Spatrick 1240*46035553Spatrickpublic: 1241*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1242*46035553Spatrick iterator() 1243*46035553Spatrick : __stashed_elem_(), __path_ptr_(nullptr), __entry_(), 1244*46035553Spatrick __state_(_Singular) {} 1245*46035553Spatrick 1246*46035553Spatrick iterator(const iterator&) = default; 1247*46035553Spatrick ~iterator() = default; 1248*46035553Spatrick 1249*46035553Spatrick iterator& operator=(const iterator&) = default; 1250*46035553Spatrick 1251*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1252*46035553Spatrick reference operator*() const { return __stashed_elem_; } 1253*46035553Spatrick 1254*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1255*46035553Spatrick pointer operator->() const { return &__stashed_elem_; } 1256*46035553Spatrick 1257*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1258*46035553Spatrick iterator& operator++() { 1259*46035553Spatrick _LIBCPP_ASSERT(__state_ != _Singular, 1260*46035553Spatrick "attempting to increment a singular iterator"); 1261*46035553Spatrick _LIBCPP_ASSERT(__state_ != _AtEnd, 1262*46035553Spatrick "attempting to increment the end iterator"); 1263*46035553Spatrick return __increment(); 1264*46035553Spatrick } 1265*46035553Spatrick 1266*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1267*46035553Spatrick iterator operator++(int) { 1268*46035553Spatrick iterator __it(*this); 1269*46035553Spatrick this->operator++(); 1270*46035553Spatrick return __it; 1271*46035553Spatrick } 1272*46035553Spatrick 1273*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1274*46035553Spatrick iterator& operator--() { 1275*46035553Spatrick _LIBCPP_ASSERT(__state_ != _Singular, 1276*46035553Spatrick "attempting to decrement a singular iterator"); 1277*46035553Spatrick _LIBCPP_ASSERT(__entry_.data() != __path_ptr_->native().data(), 1278*46035553Spatrick "attempting to decrement the begin iterator"); 1279*46035553Spatrick return __decrement(); 1280*46035553Spatrick } 1281*46035553Spatrick 1282*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1283*46035553Spatrick iterator operator--(int) { 1284*46035553Spatrick iterator __it(*this); 1285*46035553Spatrick this->operator--(); 1286*46035553Spatrick return __it; 1287*46035553Spatrick } 1288*46035553Spatrick 1289*46035553Spatrickprivate: 1290*46035553Spatrick friend class path; 1291*46035553Spatrick 1292*46035553Spatrick inline _LIBCPP_INLINE_VISIBILITY friend bool operator==(const iterator&, 1293*46035553Spatrick const iterator&); 1294*46035553Spatrick 1295*46035553Spatrick iterator& __increment(); 1296*46035553Spatrick iterator& __decrement(); 1297*46035553Spatrick 1298*46035553Spatrick path __stashed_elem_; 1299*46035553Spatrick const path* __path_ptr_; 1300*46035553Spatrick path::__string_view __entry_; 1301*46035553Spatrick _ParserState __state_; 1302*46035553Spatrick}; 1303*46035553Spatrick 1304*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool operator==(const path::iterator& __lhs, 1305*46035553Spatrick const path::iterator& __rhs) { 1306*46035553Spatrick return __lhs.__path_ptr_ == __rhs.__path_ptr_ && 1307*46035553Spatrick __lhs.__entry_.data() == __rhs.__entry_.data(); 1308*46035553Spatrick} 1309*46035553Spatrick 1310*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool operator!=(const path::iterator& __lhs, 1311*46035553Spatrick const path::iterator& __rhs) { 1312*46035553Spatrick return !(__lhs == __rhs); 1313*46035553Spatrick} 1314*46035553Spatrick 1315*46035553Spatrick// TODO(ldionne): We need to pop the pragma and push it again after 1316*46035553Spatrick// filesystem_error to work around PR41078. 1317*46035553Spatrick_LIBCPP_AVAILABILITY_FILESYSTEM_POP 1318*46035553Spatrick 1319*46035553Spatrickclass _LIBCPP_AVAILABILITY_FILESYSTEM _LIBCPP_EXCEPTION_ABI filesystem_error : public system_error { 1320*46035553Spatrickpublic: 1321*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1322*46035553Spatrick filesystem_error(const string& __what, error_code __ec) 1323*46035553Spatrick : system_error(__ec, __what), 1324*46035553Spatrick __storage_(make_shared<_Storage>(path(), path())) { 1325*46035553Spatrick __create_what(0); 1326*46035553Spatrick } 1327*46035553Spatrick 1328*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1329*46035553Spatrick filesystem_error(const string& __what, const path& __p1, error_code __ec) 1330*46035553Spatrick : system_error(__ec, __what), 1331*46035553Spatrick __storage_(make_shared<_Storage>(__p1, path())) { 1332*46035553Spatrick __create_what(1); 1333*46035553Spatrick } 1334*46035553Spatrick 1335*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1336*46035553Spatrick filesystem_error(const string& __what, const path& __p1, const path& __p2, 1337*46035553Spatrick error_code __ec) 1338*46035553Spatrick : system_error(__ec, __what), 1339*46035553Spatrick __storage_(make_shared<_Storage>(__p1, __p2)) { 1340*46035553Spatrick __create_what(2); 1341*46035553Spatrick } 1342*46035553Spatrick 1343*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1344*46035553Spatrick const path& path1() const noexcept { return __storage_->__p1_; } 1345*46035553Spatrick 1346*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1347*46035553Spatrick const path& path2() const noexcept { return __storage_->__p2_; } 1348*46035553Spatrick 1349*46035553Spatrick ~filesystem_error() override; // key function 1350*46035553Spatrick 1351*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1352*46035553Spatrick const char* what() const noexcept override { 1353*46035553Spatrick return __storage_->__what_.c_str(); 1354*46035553Spatrick } 1355*46035553Spatrick 1356*46035553Spatrick void __create_what(int __num_paths); 1357*46035553Spatrick 1358*46035553Spatrickprivate: 1359*46035553Spatrick struct _LIBCPP_HIDDEN _Storage { 1360*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1361*46035553Spatrick _Storage(const path& __p1, const path& __p2) : __p1_(__p1), __p2_(__p2) {} 1362*46035553Spatrick 1363*46035553Spatrick path __p1_; 1364*46035553Spatrick path __p2_; 1365*46035553Spatrick string __what_; 1366*46035553Spatrick }; 1367*46035553Spatrick shared_ptr<_Storage> __storage_; 1368*46035553Spatrick}; 1369*46035553Spatrick 1370*46035553Spatrick_LIBCPP_AVAILABILITY_FILESYSTEM_PUSH 1371*46035553Spatrick 1372*46035553Spatricktemplate <class... _Args> 1373*46035553Spatrick_LIBCPP_NORETURN inline _LIBCPP_INLINE_VISIBILITY 1374*46035553Spatrick#ifndef _LIBCPP_NO_EXCEPTIONS 1375*46035553Spatrickvoid __throw_filesystem_error(_Args&&... __args) { 1376*46035553Spatrick throw filesystem_error(std::forward<_Args>(__args)...); 1377*46035553Spatrick} 1378*46035553Spatrick#else 1379*46035553Spatrickvoid __throw_filesystem_error(_Args&&...) { 1380*46035553Spatrick _VSTD::abort(); 1381*46035553Spatrick} 1382*46035553Spatrick#endif 1383*46035553Spatrick 1384*46035553Spatrick// operational functions 1385*46035553Spatrick 1386*46035553Spatrick_LIBCPP_FUNC_VIS 1387*46035553Spatrickpath __absolute(const path&, error_code* __ec = nullptr); 1388*46035553Spatrick_LIBCPP_FUNC_VIS 1389*46035553Spatrickpath __canonical(const path&, error_code* __ec = nullptr); 1390*46035553Spatrick_LIBCPP_FUNC_VIS 1391*46035553Spatrickvoid __copy(const path& __from, const path& __to, copy_options __opt, 1392*46035553Spatrick error_code* __ec = nullptr); 1393*46035553Spatrick_LIBCPP_FUNC_VIS 1394*46035553Spatrickbool __copy_file(const path& __from, const path& __to, copy_options __opt, 1395*46035553Spatrick error_code* __ec = nullptr); 1396*46035553Spatrick_LIBCPP_FUNC_VIS 1397*46035553Spatrickvoid __copy_symlink(const path& __existing_symlink, const path& __new_symlink, 1398*46035553Spatrick error_code* __ec = nullptr); 1399*46035553Spatrick_LIBCPP_FUNC_VIS 1400*46035553Spatrickbool __create_directories(const path& p, error_code* ec = nullptr); 1401*46035553Spatrick_LIBCPP_FUNC_VIS 1402*46035553Spatrickbool __create_directory(const path& p, error_code* ec = nullptr); 1403*46035553Spatrick_LIBCPP_FUNC_VIS 1404*46035553Spatrickbool __create_directory(const path& p, const path& attributes, 1405*46035553Spatrick error_code* ec = nullptr); 1406*46035553Spatrick_LIBCPP_FUNC_VIS 1407*46035553Spatrickvoid __create_directory_symlink(const path& __to, const path& __new_symlink, 1408*46035553Spatrick error_code* __ec = nullptr); 1409*46035553Spatrick_LIBCPP_FUNC_VIS 1410*46035553Spatrickvoid __create_hard_link(const path& __to, const path& __new_hard_link, 1411*46035553Spatrick error_code* __ec = nullptr); 1412*46035553Spatrick_LIBCPP_FUNC_VIS 1413*46035553Spatrickvoid __create_symlink(const path& __to, const path& __new_symlink, 1414*46035553Spatrick error_code* __ec = nullptr); 1415*46035553Spatrick_LIBCPP_FUNC_VIS 1416*46035553Spatrickpath __current_path(error_code* __ec = nullptr); 1417*46035553Spatrick_LIBCPP_FUNC_VIS 1418*46035553Spatrickvoid __current_path(const path&, error_code* __ec = nullptr); 1419*46035553Spatrick_LIBCPP_FUNC_VIS 1420*46035553Spatrickbool __equivalent(const path&, const path&, error_code* __ec = nullptr); 1421*46035553Spatrick_LIBCPP_FUNC_VIS 1422*46035553Spatrickuintmax_t __file_size(const path&, error_code* __ec = nullptr); 1423*46035553Spatrick_LIBCPP_FUNC_VIS 1424*46035553Spatrickuintmax_t __hard_link_count(const path&, error_code* __ec = nullptr); 1425*46035553Spatrick_LIBCPP_FUNC_VIS 1426*46035553Spatrickbool __fs_is_empty(const path& p, error_code* ec = nullptr); 1427*46035553Spatrick_LIBCPP_FUNC_VIS 1428*46035553Spatrickfile_time_type __last_write_time(const path& p, error_code* ec = nullptr); 1429*46035553Spatrick_LIBCPP_FUNC_VIS 1430*46035553Spatrickvoid __last_write_time(const path& p, file_time_type new_time, 1431*46035553Spatrick error_code* ec = nullptr); 1432*46035553Spatrick_LIBCPP_FUNC_VIS 1433*46035553Spatrickvoid __permissions(const path&, perms, perm_options, error_code* = nullptr); 1434*46035553Spatrick_LIBCPP_FUNC_VIS 1435*46035553Spatrickpath __read_symlink(const path& p, error_code* ec = nullptr); 1436*46035553Spatrick_LIBCPP_FUNC_VIS 1437*46035553Spatrickbool __remove(const path& p, error_code* ec = nullptr); 1438*46035553Spatrick_LIBCPP_FUNC_VIS 1439*46035553Spatrickuintmax_t __remove_all(const path& p, error_code* ec = nullptr); 1440*46035553Spatrick_LIBCPP_FUNC_VIS 1441*46035553Spatrickvoid __rename(const path& from, const path& to, error_code* ec = nullptr); 1442*46035553Spatrick_LIBCPP_FUNC_VIS 1443*46035553Spatrickvoid __resize_file(const path& p, uintmax_t size, error_code* ec = nullptr); 1444*46035553Spatrick_LIBCPP_FUNC_VIS 1445*46035553Spatrickspace_info __space(const path&, error_code* __ec = nullptr); 1446*46035553Spatrick_LIBCPP_FUNC_VIS 1447*46035553Spatrickfile_status __status(const path&, error_code* __ec = nullptr); 1448*46035553Spatrick_LIBCPP_FUNC_VIS 1449*46035553Spatrickfile_status __symlink_status(const path&, error_code* __ec = nullptr); 1450*46035553Spatrick_LIBCPP_FUNC_VIS 1451*46035553Spatrickpath __system_complete(const path&, error_code* __ec = nullptr); 1452*46035553Spatrick_LIBCPP_FUNC_VIS 1453*46035553Spatrickpath __temp_directory_path(error_code* __ec = nullptr); 1454*46035553Spatrick_LIBCPP_FUNC_VIS 1455*46035553Spatrickpath __weakly_canonical(path const& __p, error_code* __ec = nullptr); 1456*46035553Spatrick 1457*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path current_path() { 1458*46035553Spatrick return __current_path(); 1459*46035553Spatrick} 1460*46035553Spatrick 1461*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path current_path(error_code& __ec) { 1462*46035553Spatrick return __current_path(&__ec); 1463*46035553Spatrick} 1464*46035553Spatrick 1465*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void current_path(const path& __p) { 1466*46035553Spatrick __current_path(__p); 1467*46035553Spatrick} 1468*46035553Spatrick 1469*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void current_path(const path& __p, 1470*46035553Spatrick error_code& __ec) noexcept { 1471*46035553Spatrick __current_path(__p, &__ec); 1472*46035553Spatrick} 1473*46035553Spatrick 1474*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path absolute(const path& __p) { 1475*46035553Spatrick return __absolute(__p); 1476*46035553Spatrick} 1477*46035553Spatrick 1478*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path absolute(const path& __p, 1479*46035553Spatrick error_code& __ec) { 1480*46035553Spatrick return __absolute(__p, &__ec); 1481*46035553Spatrick} 1482*46035553Spatrick 1483*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path canonical(const path& __p) { 1484*46035553Spatrick return __canonical(__p); 1485*46035553Spatrick} 1486*46035553Spatrick 1487*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path canonical(const path& __p, 1488*46035553Spatrick error_code& __ec) { 1489*46035553Spatrick return __canonical(__p, &__ec); 1490*46035553Spatrick} 1491*46035553Spatrick 1492*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void copy(const path& __from, 1493*46035553Spatrick const path& __to) { 1494*46035553Spatrick __copy(__from, __to, copy_options::none); 1495*46035553Spatrick} 1496*46035553Spatrick 1497*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void copy(const path& __from, const path& __to, 1498*46035553Spatrick error_code& __ec) { 1499*46035553Spatrick __copy(__from, __to, copy_options::none, &__ec); 1500*46035553Spatrick} 1501*46035553Spatrick 1502*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void copy(const path& __from, const path& __to, 1503*46035553Spatrick copy_options __opt) { 1504*46035553Spatrick __copy(__from, __to, __opt); 1505*46035553Spatrick} 1506*46035553Spatrick 1507*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void copy(const path& __from, const path& __to, 1508*46035553Spatrick copy_options __opt, 1509*46035553Spatrick error_code& __ec) { 1510*46035553Spatrick __copy(__from, __to, __opt, &__ec); 1511*46035553Spatrick} 1512*46035553Spatrick 1513*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool copy_file(const path& __from, 1514*46035553Spatrick const path& __to) { 1515*46035553Spatrick return __copy_file(__from, __to, copy_options::none); 1516*46035553Spatrick} 1517*46035553Spatrick 1518*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool 1519*46035553Spatrickcopy_file(const path& __from, const path& __to, error_code& __ec) { 1520*46035553Spatrick return __copy_file(__from, __to, copy_options::none, &__ec); 1521*46035553Spatrick} 1522*46035553Spatrick 1523*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool 1524*46035553Spatrickcopy_file(const path& __from, const path& __to, copy_options __opt) { 1525*46035553Spatrick return __copy_file(__from, __to, __opt); 1526*46035553Spatrick} 1527*46035553Spatrick 1528*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool copy_file(const path& __from, 1529*46035553Spatrick const path& __to, 1530*46035553Spatrick copy_options __opt, 1531*46035553Spatrick error_code& __ec) { 1532*46035553Spatrick return __copy_file(__from, __to, __opt, &__ec); 1533*46035553Spatrick} 1534*46035553Spatrick 1535*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void copy_symlink(const path& __existing, 1536*46035553Spatrick const path& __new) { 1537*46035553Spatrick __copy_symlink(__existing, __new); 1538*46035553Spatrick} 1539*46035553Spatrick 1540*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void 1541*46035553Spatrickcopy_symlink(const path& __ext, const path& __new, error_code& __ec) noexcept { 1542*46035553Spatrick __copy_symlink(__ext, __new, &__ec); 1543*46035553Spatrick} 1544*46035553Spatrick 1545*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool create_directories(const path& __p) { 1546*46035553Spatrick return __create_directories(__p); 1547*46035553Spatrick} 1548*46035553Spatrick 1549*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool create_directories(const path& __p, 1550*46035553Spatrick error_code& __ec) { 1551*46035553Spatrick return __create_directories(__p, &__ec); 1552*46035553Spatrick} 1553*46035553Spatrick 1554*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool create_directory(const path& __p) { 1555*46035553Spatrick return __create_directory(__p); 1556*46035553Spatrick} 1557*46035553Spatrick 1558*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool 1559*46035553Spatrickcreate_directory(const path& __p, error_code& __ec) noexcept { 1560*46035553Spatrick return __create_directory(__p, &__ec); 1561*46035553Spatrick} 1562*46035553Spatrick 1563*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool create_directory(const path& __p, 1564*46035553Spatrick const path& __attrs) { 1565*46035553Spatrick return __create_directory(__p, __attrs); 1566*46035553Spatrick} 1567*46035553Spatrick 1568*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool 1569*46035553Spatrickcreate_directory(const path& __p, const path& __attrs, 1570*46035553Spatrick error_code& __ec) noexcept { 1571*46035553Spatrick return __create_directory(__p, __attrs, &__ec); 1572*46035553Spatrick} 1573*46035553Spatrick 1574*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void 1575*46035553Spatrickcreate_directory_symlink(const path& __to, const path& __new) { 1576*46035553Spatrick __create_directory_symlink(__to, __new); 1577*46035553Spatrick} 1578*46035553Spatrick 1579*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void 1580*46035553Spatrickcreate_directory_symlink(const path& __to, const path& __new, 1581*46035553Spatrick error_code& __ec) noexcept { 1582*46035553Spatrick __create_directory_symlink(__to, __new, &__ec); 1583*46035553Spatrick} 1584*46035553Spatrick 1585*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void create_hard_link(const path& __to, 1586*46035553Spatrick const path& __new) { 1587*46035553Spatrick __create_hard_link(__to, __new); 1588*46035553Spatrick} 1589*46035553Spatrick 1590*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void 1591*46035553Spatrickcreate_hard_link(const path& __to, const path& __new, 1592*46035553Spatrick error_code& __ec) noexcept { 1593*46035553Spatrick __create_hard_link(__to, __new, &__ec); 1594*46035553Spatrick} 1595*46035553Spatrick 1596*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void create_symlink(const path& __to, 1597*46035553Spatrick const path& __new) { 1598*46035553Spatrick __create_symlink(__to, __new); 1599*46035553Spatrick} 1600*46035553Spatrick 1601*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void 1602*46035553Spatrickcreate_symlink(const path& __to, const path& __new, error_code& __ec) noexcept { 1603*46035553Spatrick return __create_symlink(__to, __new, &__ec); 1604*46035553Spatrick} 1605*46035553Spatrick 1606*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool status_known(file_status __s) noexcept { 1607*46035553Spatrick return __s.type() != file_type::none; 1608*46035553Spatrick} 1609*46035553Spatrick 1610*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool exists(file_status __s) noexcept { 1611*46035553Spatrick return status_known(__s) && __s.type() != file_type::not_found; 1612*46035553Spatrick} 1613*46035553Spatrick 1614*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool exists(const path& __p) { 1615*46035553Spatrick return exists(__status(__p)); 1616*46035553Spatrick} 1617*46035553Spatrick 1618*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool exists(const path& __p, 1619*46035553Spatrick error_code& __ec) noexcept { 1620*46035553Spatrick auto __s = __status(__p, &__ec); 1621*46035553Spatrick if (status_known(__s)) 1622*46035553Spatrick __ec.clear(); 1623*46035553Spatrick return exists(__s); 1624*46035553Spatrick} 1625*46035553Spatrick 1626*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool equivalent(const path& __p1, 1627*46035553Spatrick const path& __p2) { 1628*46035553Spatrick return __equivalent(__p1, __p2); 1629*46035553Spatrick} 1630*46035553Spatrick 1631*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool 1632*46035553Spatrickequivalent(const path& __p1, const path& __p2, error_code& __ec) noexcept { 1633*46035553Spatrick return __equivalent(__p1, __p2, &__ec); 1634*46035553Spatrick} 1635*46035553Spatrick 1636*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY uintmax_t file_size(const path& __p) { 1637*46035553Spatrick return __file_size(__p); 1638*46035553Spatrick} 1639*46035553Spatrick 1640*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY uintmax_t 1641*46035553Spatrickfile_size(const path& __p, error_code& __ec) noexcept { 1642*46035553Spatrick return __file_size(__p, &__ec); 1643*46035553Spatrick} 1644*46035553Spatrick 1645*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY uintmax_t hard_link_count(const path& __p) { 1646*46035553Spatrick return __hard_link_count(__p); 1647*46035553Spatrick} 1648*46035553Spatrick 1649*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY uintmax_t 1650*46035553Spatrickhard_link_count(const path& __p, error_code& __ec) noexcept { 1651*46035553Spatrick return __hard_link_count(__p, &__ec); 1652*46035553Spatrick} 1653*46035553Spatrick 1654*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_block_file(file_status __s) noexcept { 1655*46035553Spatrick return __s.type() == file_type::block; 1656*46035553Spatrick} 1657*46035553Spatrick 1658*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_block_file(const path& __p) { 1659*46035553Spatrick return is_block_file(__status(__p)); 1660*46035553Spatrick} 1661*46035553Spatrick 1662*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_block_file(const path& __p, 1663*46035553Spatrick error_code& __ec) noexcept { 1664*46035553Spatrick return is_block_file(__status(__p, &__ec)); 1665*46035553Spatrick} 1666*46035553Spatrick 1667*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool 1668*46035553Spatrickis_character_file(file_status __s) noexcept { 1669*46035553Spatrick return __s.type() == file_type::character; 1670*46035553Spatrick} 1671*46035553Spatrick 1672*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_character_file(const path& __p) { 1673*46035553Spatrick return is_character_file(__status(__p)); 1674*46035553Spatrick} 1675*46035553Spatrick 1676*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool 1677*46035553Spatrickis_character_file(const path& __p, error_code& __ec) noexcept { 1678*46035553Spatrick return is_character_file(__status(__p, &__ec)); 1679*46035553Spatrick} 1680*46035553Spatrick 1681*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_directory(file_status __s) noexcept { 1682*46035553Spatrick return __s.type() == file_type::directory; 1683*46035553Spatrick} 1684*46035553Spatrick 1685*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_directory(const path& __p) { 1686*46035553Spatrick return is_directory(__status(__p)); 1687*46035553Spatrick} 1688*46035553Spatrick 1689*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_directory(const path& __p, 1690*46035553Spatrick error_code& __ec) noexcept { 1691*46035553Spatrick return is_directory(__status(__p, &__ec)); 1692*46035553Spatrick} 1693*46035553Spatrick 1694*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_empty(const path& __p) { 1695*46035553Spatrick return __fs_is_empty(__p); 1696*46035553Spatrick} 1697*46035553Spatrick 1698*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_empty(const path& __p, 1699*46035553Spatrick error_code& __ec) { 1700*46035553Spatrick return __fs_is_empty(__p, &__ec); 1701*46035553Spatrick} 1702*46035553Spatrick 1703*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_fifo(file_status __s) noexcept { 1704*46035553Spatrick return __s.type() == file_type::fifo; 1705*46035553Spatrick} 1706*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_fifo(const path& __p) { 1707*46035553Spatrick return is_fifo(__status(__p)); 1708*46035553Spatrick} 1709*46035553Spatrick 1710*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_fifo(const path& __p, 1711*46035553Spatrick error_code& __ec) noexcept { 1712*46035553Spatrick return is_fifo(__status(__p, &__ec)); 1713*46035553Spatrick} 1714*46035553Spatrick 1715*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool 1716*46035553Spatrickis_regular_file(file_status __s) noexcept { 1717*46035553Spatrick return __s.type() == file_type::regular; 1718*46035553Spatrick} 1719*46035553Spatrick 1720*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_regular_file(const path& __p) { 1721*46035553Spatrick return is_regular_file(__status(__p)); 1722*46035553Spatrick} 1723*46035553Spatrick 1724*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool 1725*46035553Spatrickis_regular_file(const path& __p, error_code& __ec) noexcept { 1726*46035553Spatrick return is_regular_file(__status(__p, &__ec)); 1727*46035553Spatrick} 1728*46035553Spatrick 1729*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_socket(file_status __s) noexcept { 1730*46035553Spatrick return __s.type() == file_type::socket; 1731*46035553Spatrick} 1732*46035553Spatrick 1733*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_socket(const path& __p) { 1734*46035553Spatrick return is_socket(__status(__p)); 1735*46035553Spatrick} 1736*46035553Spatrick 1737*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_socket(const path& __p, 1738*46035553Spatrick error_code& __ec) noexcept { 1739*46035553Spatrick return is_socket(__status(__p, &__ec)); 1740*46035553Spatrick} 1741*46035553Spatrick 1742*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_symlink(file_status __s) noexcept { 1743*46035553Spatrick return __s.type() == file_type::symlink; 1744*46035553Spatrick} 1745*46035553Spatrick 1746*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_symlink(const path& __p) { 1747*46035553Spatrick return is_symlink(__symlink_status(__p)); 1748*46035553Spatrick} 1749*46035553Spatrick 1750*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_symlink(const path& __p, 1751*46035553Spatrick error_code& __ec) noexcept { 1752*46035553Spatrick return is_symlink(__symlink_status(__p, &__ec)); 1753*46035553Spatrick} 1754*46035553Spatrick 1755*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_other(file_status __s) noexcept { 1756*46035553Spatrick return exists(__s) && !is_regular_file(__s) && !is_directory(__s) && 1757*46035553Spatrick !is_symlink(__s); 1758*46035553Spatrick} 1759*46035553Spatrick 1760*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_other(const path& __p) { 1761*46035553Spatrick return is_other(__status(__p)); 1762*46035553Spatrick} 1763*46035553Spatrick 1764*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool is_other(const path& __p, 1765*46035553Spatrick error_code& __ec) noexcept { 1766*46035553Spatrick return is_other(__status(__p, &__ec)); 1767*46035553Spatrick} 1768*46035553Spatrick 1769*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY file_time_type 1770*46035553Spatricklast_write_time(const path& __p) { 1771*46035553Spatrick return __last_write_time(__p); 1772*46035553Spatrick} 1773*46035553Spatrick 1774*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY file_time_type 1775*46035553Spatricklast_write_time(const path& __p, error_code& __ec) noexcept { 1776*46035553Spatrick return __last_write_time(__p, &__ec); 1777*46035553Spatrick} 1778*46035553Spatrick 1779*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void last_write_time(const path& __p, 1780*46035553Spatrick file_time_type __t) { 1781*46035553Spatrick __last_write_time(__p, __t); 1782*46035553Spatrick} 1783*46035553Spatrick 1784*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void 1785*46035553Spatricklast_write_time(const path& __p, file_time_type __t, 1786*46035553Spatrick error_code& __ec) noexcept { 1787*46035553Spatrick __last_write_time(__p, __t, &__ec); 1788*46035553Spatrick} 1789*46035553Spatrick 1790*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void 1791*46035553Spatrickpermissions(const path& __p, perms __prms, 1792*46035553Spatrick perm_options __opts = perm_options::replace) { 1793*46035553Spatrick __permissions(__p, __prms, __opts); 1794*46035553Spatrick} 1795*46035553Spatrick 1796*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void permissions(const path& __p, perms __prms, 1797*46035553Spatrick error_code& __ec) noexcept { 1798*46035553Spatrick __permissions(__p, __prms, perm_options::replace, &__ec); 1799*46035553Spatrick} 1800*46035553Spatrick 1801*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void permissions(const path& __p, perms __prms, 1802*46035553Spatrick perm_options __opts, 1803*46035553Spatrick error_code& __ec) { 1804*46035553Spatrick __permissions(__p, __prms, __opts, &__ec); 1805*46035553Spatrick} 1806*46035553Spatrick 1807*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path proximate(const path& __p, 1808*46035553Spatrick const path& __base, 1809*46035553Spatrick error_code& __ec) { 1810*46035553Spatrick path __tmp = __weakly_canonical(__p, &__ec); 1811*46035553Spatrick if (__ec) 1812*46035553Spatrick return {}; 1813*46035553Spatrick path __tmp_base = __weakly_canonical(__base, &__ec); 1814*46035553Spatrick if (__ec) 1815*46035553Spatrick return {}; 1816*46035553Spatrick return __tmp.lexically_proximate(__tmp_base); 1817*46035553Spatrick} 1818*46035553Spatrick 1819*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path proximate(const path& __p, 1820*46035553Spatrick error_code& __ec) { 1821*46035553Spatrick return proximate(__p, current_path(), __ec); 1822*46035553Spatrick} 1823*46035553Spatrick 1824*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path 1825*46035553Spatrickproximate(const path& __p, const path& __base = current_path()) { 1826*46035553Spatrick return __weakly_canonical(__p).lexically_proximate( 1827*46035553Spatrick __weakly_canonical(__base)); 1828*46035553Spatrick} 1829*46035553Spatrick 1830*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path read_symlink(const path& __p) { 1831*46035553Spatrick return __read_symlink(__p); 1832*46035553Spatrick} 1833*46035553Spatrick 1834*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path read_symlink(const path& __p, 1835*46035553Spatrick error_code& __ec) { 1836*46035553Spatrick return __read_symlink(__p, &__ec); 1837*46035553Spatrick} 1838*46035553Spatrick 1839*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path relative(const path& __p, 1840*46035553Spatrick const path& __base, 1841*46035553Spatrick error_code& __ec) { 1842*46035553Spatrick path __tmp = __weakly_canonical(__p, &__ec); 1843*46035553Spatrick if (__ec) 1844*46035553Spatrick return path(); 1845*46035553Spatrick path __tmpbase = __weakly_canonical(__base, &__ec); 1846*46035553Spatrick if (__ec) 1847*46035553Spatrick return path(); 1848*46035553Spatrick return __tmp.lexically_relative(__tmpbase); 1849*46035553Spatrick} 1850*46035553Spatrick 1851*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path relative(const path& __p, 1852*46035553Spatrick error_code& __ec) { 1853*46035553Spatrick return relative(__p, current_path(), __ec); 1854*46035553Spatrick} 1855*46035553Spatrick 1856*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path 1857*46035553Spatrickrelative(const path& __p, const path& __base = current_path()) { 1858*46035553Spatrick return __weakly_canonical(__p).lexically_relative(__weakly_canonical(__base)); 1859*46035553Spatrick} 1860*46035553Spatrick 1861*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool remove(const path& __p) { 1862*46035553Spatrick return __remove(__p); 1863*46035553Spatrick} 1864*46035553Spatrick 1865*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool remove(const path& __p, 1866*46035553Spatrick error_code& __ec) noexcept { 1867*46035553Spatrick return __remove(__p, &__ec); 1868*46035553Spatrick} 1869*46035553Spatrick 1870*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY uintmax_t remove_all(const path& __p) { 1871*46035553Spatrick return __remove_all(__p); 1872*46035553Spatrick} 1873*46035553Spatrick 1874*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY uintmax_t remove_all(const path& __p, 1875*46035553Spatrick error_code& __ec) { 1876*46035553Spatrick return __remove_all(__p, &__ec); 1877*46035553Spatrick} 1878*46035553Spatrick 1879*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void rename(const path& __from, 1880*46035553Spatrick const path& __to) { 1881*46035553Spatrick return __rename(__from, __to); 1882*46035553Spatrick} 1883*46035553Spatrick 1884*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void 1885*46035553Spatrickrename(const path& __from, const path& __to, error_code& __ec) noexcept { 1886*46035553Spatrick return __rename(__from, __to, &__ec); 1887*46035553Spatrick} 1888*46035553Spatrick 1889*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void resize_file(const path& __p, 1890*46035553Spatrick uintmax_t __ns) { 1891*46035553Spatrick return __resize_file(__p, __ns); 1892*46035553Spatrick} 1893*46035553Spatrick 1894*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY void 1895*46035553Spatrickresize_file(const path& __p, uintmax_t __ns, error_code& __ec) noexcept { 1896*46035553Spatrick return __resize_file(__p, __ns, &__ec); 1897*46035553Spatrick} 1898*46035553Spatrick 1899*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY space_info space(const path& __p) { 1900*46035553Spatrick return __space(__p); 1901*46035553Spatrick} 1902*46035553Spatrick 1903*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY space_info space(const path& __p, 1904*46035553Spatrick error_code& __ec) noexcept { 1905*46035553Spatrick return __space(__p, &__ec); 1906*46035553Spatrick} 1907*46035553Spatrick 1908*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY file_status status(const path& __p) { 1909*46035553Spatrick return __status(__p); 1910*46035553Spatrick} 1911*46035553Spatrick 1912*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY file_status status(const path& __p, 1913*46035553Spatrick error_code& __ec) noexcept { 1914*46035553Spatrick return __status(__p, &__ec); 1915*46035553Spatrick} 1916*46035553Spatrick 1917*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY file_status symlink_status(const path& __p) { 1918*46035553Spatrick return __symlink_status(__p); 1919*46035553Spatrick} 1920*46035553Spatrick 1921*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY file_status 1922*46035553Spatricksymlink_status(const path& __p, error_code& __ec) noexcept { 1923*46035553Spatrick return __symlink_status(__p, &__ec); 1924*46035553Spatrick} 1925*46035553Spatrick 1926*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path temp_directory_path() { 1927*46035553Spatrick return __temp_directory_path(); 1928*46035553Spatrick} 1929*46035553Spatrick 1930*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path temp_directory_path(error_code& __ec) { 1931*46035553Spatrick return __temp_directory_path(&__ec); 1932*46035553Spatrick} 1933*46035553Spatrick 1934*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path weakly_canonical(path const& __p) { 1935*46035553Spatrick return __weakly_canonical(__p); 1936*46035553Spatrick} 1937*46035553Spatrick 1938*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY path weakly_canonical(path const& __p, 1939*46035553Spatrick error_code& __ec) { 1940*46035553Spatrick return __weakly_canonical(__p, &__ec); 1941*46035553Spatrick} 1942*46035553Spatrick 1943*46035553Spatrickclass directory_iterator; 1944*46035553Spatrickclass recursive_directory_iterator; 1945*46035553Spatrickclass _LIBCPP_HIDDEN __dir_stream; 1946*46035553Spatrick 1947*46035553Spatrickclass directory_entry { 1948*46035553Spatrick typedef _VSTD_FS::path _Path; 1949*46035553Spatrick 1950*46035553Spatrickpublic: 1951*46035553Spatrick // constructors and destructors 1952*46035553Spatrick directory_entry() noexcept = default; 1953*46035553Spatrick directory_entry(directory_entry const&) = default; 1954*46035553Spatrick directory_entry(directory_entry&&) noexcept = default; 1955*46035553Spatrick 1956*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1957*46035553Spatrick explicit directory_entry(_Path const& __p) : __p_(__p) { 1958*46035553Spatrick error_code __ec; 1959*46035553Spatrick __refresh(&__ec); 1960*46035553Spatrick } 1961*46035553Spatrick 1962*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1963*46035553Spatrick directory_entry(_Path const& __p, error_code& __ec) : __p_(__p) { 1964*46035553Spatrick __refresh(&__ec); 1965*46035553Spatrick } 1966*46035553Spatrick 1967*46035553Spatrick ~directory_entry() {} 1968*46035553Spatrick 1969*46035553Spatrick directory_entry& operator=(directory_entry const&) = default; 1970*46035553Spatrick directory_entry& operator=(directory_entry&&) noexcept = default; 1971*46035553Spatrick 1972*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1973*46035553Spatrick void assign(_Path const& __p) { 1974*46035553Spatrick __p_ = __p; 1975*46035553Spatrick error_code __ec; 1976*46035553Spatrick __refresh(&__ec); 1977*46035553Spatrick } 1978*46035553Spatrick 1979*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1980*46035553Spatrick void assign(_Path const& __p, error_code& __ec) { 1981*46035553Spatrick __p_ = __p; 1982*46035553Spatrick __refresh(&__ec); 1983*46035553Spatrick } 1984*46035553Spatrick 1985*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1986*46035553Spatrick void replace_filename(_Path const& __p) { 1987*46035553Spatrick __p_.replace_filename(__p); 1988*46035553Spatrick error_code __ec; 1989*46035553Spatrick __refresh(&__ec); 1990*46035553Spatrick } 1991*46035553Spatrick 1992*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1993*46035553Spatrick void replace_filename(_Path const& __p, error_code& __ec) { 1994*46035553Spatrick __p_ = __p_.parent_path() / __p; 1995*46035553Spatrick __refresh(&__ec); 1996*46035553Spatrick } 1997*46035553Spatrick 1998*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 1999*46035553Spatrick void refresh() { __refresh(); } 2000*46035553Spatrick 2001*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2002*46035553Spatrick void refresh(error_code& __ec) noexcept { __refresh(&__ec); } 2003*46035553Spatrick 2004*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2005*46035553Spatrick _Path const& path() const noexcept { return __p_; } 2006*46035553Spatrick 2007*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2008*46035553Spatrick operator const _Path&() const noexcept { return __p_; } 2009*46035553Spatrick 2010*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2011*46035553Spatrick bool exists() const { return _VSTD_FS::exists(file_status{__get_ft()}); } 2012*46035553Spatrick 2013*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2014*46035553Spatrick bool exists(error_code& __ec) const noexcept { 2015*46035553Spatrick return _VSTD_FS::exists(file_status{__get_ft(&__ec)}); 2016*46035553Spatrick } 2017*46035553Spatrick 2018*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2019*46035553Spatrick bool is_block_file() const { return __get_ft() == file_type::block; } 2020*46035553Spatrick 2021*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2022*46035553Spatrick bool is_block_file(error_code& __ec) const noexcept { 2023*46035553Spatrick return __get_ft(&__ec) == file_type::block; 2024*46035553Spatrick } 2025*46035553Spatrick 2026*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2027*46035553Spatrick bool is_character_file() const { return __get_ft() == file_type::character; } 2028*46035553Spatrick 2029*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2030*46035553Spatrick bool is_character_file(error_code& __ec) const noexcept { 2031*46035553Spatrick return __get_ft(&__ec) == file_type::character; 2032*46035553Spatrick } 2033*46035553Spatrick 2034*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2035*46035553Spatrick bool is_directory() const { return __get_ft() == file_type::directory; } 2036*46035553Spatrick 2037*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2038*46035553Spatrick bool is_directory(error_code& __ec) const noexcept { 2039*46035553Spatrick return __get_ft(&__ec) == file_type::directory; 2040*46035553Spatrick } 2041*46035553Spatrick 2042*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2043*46035553Spatrick bool is_fifo() const { return __get_ft() == file_type::fifo; } 2044*46035553Spatrick 2045*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2046*46035553Spatrick bool is_fifo(error_code& __ec) const noexcept { 2047*46035553Spatrick return __get_ft(&__ec) == file_type::fifo; 2048*46035553Spatrick } 2049*46035553Spatrick 2050*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2051*46035553Spatrick bool is_other() const { return _VSTD_FS::is_other(file_status{__get_ft()}); } 2052*46035553Spatrick 2053*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2054*46035553Spatrick bool is_other(error_code& __ec) const noexcept { 2055*46035553Spatrick return _VSTD_FS::is_other(file_status{__get_ft(&__ec)}); 2056*46035553Spatrick } 2057*46035553Spatrick 2058*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2059*46035553Spatrick bool is_regular_file() const { return __get_ft() == file_type::regular; } 2060*46035553Spatrick 2061*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2062*46035553Spatrick bool is_regular_file(error_code& __ec) const noexcept { 2063*46035553Spatrick return __get_ft(&__ec) == file_type::regular; 2064*46035553Spatrick } 2065*46035553Spatrick 2066*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2067*46035553Spatrick bool is_socket() const { return __get_ft() == file_type::socket; } 2068*46035553Spatrick 2069*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2070*46035553Spatrick bool is_socket(error_code& __ec) const noexcept { 2071*46035553Spatrick return __get_ft(&__ec) == file_type::socket; 2072*46035553Spatrick } 2073*46035553Spatrick 2074*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2075*46035553Spatrick bool is_symlink() const { return __get_sym_ft() == file_type::symlink; } 2076*46035553Spatrick 2077*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2078*46035553Spatrick bool is_symlink(error_code& __ec) const noexcept { 2079*46035553Spatrick return __get_sym_ft(&__ec) == file_type::symlink; 2080*46035553Spatrick } 2081*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2082*46035553Spatrick uintmax_t file_size() const { return __get_size(); } 2083*46035553Spatrick 2084*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2085*46035553Spatrick uintmax_t file_size(error_code& __ec) const noexcept { 2086*46035553Spatrick return __get_size(&__ec); 2087*46035553Spatrick } 2088*46035553Spatrick 2089*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2090*46035553Spatrick uintmax_t hard_link_count() const { return __get_nlink(); } 2091*46035553Spatrick 2092*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2093*46035553Spatrick uintmax_t hard_link_count(error_code& __ec) const noexcept { 2094*46035553Spatrick return __get_nlink(&__ec); 2095*46035553Spatrick } 2096*46035553Spatrick 2097*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2098*46035553Spatrick file_time_type last_write_time() const { return __get_write_time(); } 2099*46035553Spatrick 2100*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2101*46035553Spatrick file_time_type last_write_time(error_code& __ec) const noexcept { 2102*46035553Spatrick return __get_write_time(&__ec); 2103*46035553Spatrick } 2104*46035553Spatrick 2105*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2106*46035553Spatrick file_status status() const { return __get_status(); } 2107*46035553Spatrick 2108*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2109*46035553Spatrick file_status status(error_code& __ec) const noexcept { 2110*46035553Spatrick return __get_status(&__ec); 2111*46035553Spatrick } 2112*46035553Spatrick 2113*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2114*46035553Spatrick file_status symlink_status() const { return __get_symlink_status(); } 2115*46035553Spatrick 2116*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2117*46035553Spatrick file_status symlink_status(error_code& __ec) const noexcept { 2118*46035553Spatrick return __get_symlink_status(&__ec); 2119*46035553Spatrick } 2120*46035553Spatrick 2121*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2122*46035553Spatrick bool operator<(directory_entry const& __rhs) const noexcept { 2123*46035553Spatrick return __p_ < __rhs.__p_; 2124*46035553Spatrick } 2125*46035553Spatrick 2126*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2127*46035553Spatrick bool operator==(directory_entry const& __rhs) const noexcept { 2128*46035553Spatrick return __p_ == __rhs.__p_; 2129*46035553Spatrick } 2130*46035553Spatrick 2131*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2132*46035553Spatrick bool operator!=(directory_entry const& __rhs) const noexcept { 2133*46035553Spatrick return __p_ != __rhs.__p_; 2134*46035553Spatrick } 2135*46035553Spatrick 2136*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2137*46035553Spatrick bool operator<=(directory_entry const& __rhs) const noexcept { 2138*46035553Spatrick return __p_ <= __rhs.__p_; 2139*46035553Spatrick } 2140*46035553Spatrick 2141*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2142*46035553Spatrick bool operator>(directory_entry const& __rhs) const noexcept { 2143*46035553Spatrick return __p_ > __rhs.__p_; 2144*46035553Spatrick } 2145*46035553Spatrick 2146*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2147*46035553Spatrick bool operator>=(directory_entry const& __rhs) const noexcept { 2148*46035553Spatrick return __p_ >= __rhs.__p_; 2149*46035553Spatrick } 2150*46035553Spatrick 2151*46035553Spatrickprivate: 2152*46035553Spatrick friend class directory_iterator; 2153*46035553Spatrick friend class recursive_directory_iterator; 2154*46035553Spatrick friend class __dir_stream; 2155*46035553Spatrick 2156*46035553Spatrick enum _CacheType : unsigned char { 2157*46035553Spatrick _Empty, 2158*46035553Spatrick _IterSymlink, 2159*46035553Spatrick _IterNonSymlink, 2160*46035553Spatrick _RefreshSymlink, 2161*46035553Spatrick _RefreshSymlinkUnresolved, 2162*46035553Spatrick _RefreshNonSymlink 2163*46035553Spatrick }; 2164*46035553Spatrick 2165*46035553Spatrick struct __cached_data { 2166*46035553Spatrick uintmax_t __size_; 2167*46035553Spatrick uintmax_t __nlink_; 2168*46035553Spatrick file_time_type __write_time_; 2169*46035553Spatrick perms __sym_perms_; 2170*46035553Spatrick perms __non_sym_perms_; 2171*46035553Spatrick file_type __type_; 2172*46035553Spatrick _CacheType __cache_type_; 2173*46035553Spatrick 2174*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2175*46035553Spatrick __cached_data() noexcept { __reset(); } 2176*46035553Spatrick 2177*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2178*46035553Spatrick void __reset() { 2179*46035553Spatrick __cache_type_ = _Empty; 2180*46035553Spatrick __type_ = file_type::none; 2181*46035553Spatrick __sym_perms_ = __non_sym_perms_ = perms::unknown; 2182*46035553Spatrick __size_ = __nlink_ = uintmax_t(-1); 2183*46035553Spatrick __write_time_ = file_time_type::min(); 2184*46035553Spatrick } 2185*46035553Spatrick }; 2186*46035553Spatrick 2187*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2188*46035553Spatrick static __cached_data __create_iter_result(file_type __ft) { 2189*46035553Spatrick __cached_data __data; 2190*46035553Spatrick __data.__type_ = __ft; 2191*46035553Spatrick __data.__cache_type_ = [&]() { 2192*46035553Spatrick switch (__ft) { 2193*46035553Spatrick case file_type::none: 2194*46035553Spatrick return _Empty; 2195*46035553Spatrick case file_type::symlink: 2196*46035553Spatrick return _IterSymlink; 2197*46035553Spatrick default: 2198*46035553Spatrick return _IterNonSymlink; 2199*46035553Spatrick } 2200*46035553Spatrick }(); 2201*46035553Spatrick return __data; 2202*46035553Spatrick } 2203*46035553Spatrick 2204*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2205*46035553Spatrick void __assign_iter_entry(_Path&& __p, __cached_data __dt) { 2206*46035553Spatrick __p_ = std::move(__p); 2207*46035553Spatrick __data_ = __dt; 2208*46035553Spatrick } 2209*46035553Spatrick 2210*46035553Spatrick _LIBCPP_FUNC_VIS 2211*46035553Spatrick error_code __do_refresh() noexcept; 2212*46035553Spatrick 2213*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2214*46035553Spatrick static bool __is_dne_error(error_code const& __ec) { 2215*46035553Spatrick if (!__ec) 2216*46035553Spatrick return true; 2217*46035553Spatrick switch (static_cast<errc>(__ec.value())) { 2218*46035553Spatrick case errc::no_such_file_or_directory: 2219*46035553Spatrick case errc::not_a_directory: 2220*46035553Spatrick return true; 2221*46035553Spatrick default: 2222*46035553Spatrick return false; 2223*46035553Spatrick } 2224*46035553Spatrick } 2225*46035553Spatrick 2226*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2227*46035553Spatrick void __handle_error(const char* __msg, error_code* __dest_ec, 2228*46035553Spatrick error_code const& __ec, bool __allow_dne = false) const { 2229*46035553Spatrick if (__dest_ec) { 2230*46035553Spatrick *__dest_ec = __ec; 2231*46035553Spatrick return; 2232*46035553Spatrick } 2233*46035553Spatrick if (__ec && (!__allow_dne || !__is_dne_error(__ec))) 2234*46035553Spatrick __throw_filesystem_error(__msg, __p_, __ec); 2235*46035553Spatrick } 2236*46035553Spatrick 2237*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2238*46035553Spatrick void __refresh(error_code* __ec = nullptr) { 2239*46035553Spatrick __handle_error("in directory_entry::refresh", __ec, __do_refresh(), 2240*46035553Spatrick /*allow_dne*/ true); 2241*46035553Spatrick } 2242*46035553Spatrick 2243*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2244*46035553Spatrick file_type __get_sym_ft(error_code* __ec = nullptr) const { 2245*46035553Spatrick switch (__data_.__cache_type_) { 2246*46035553Spatrick case _Empty: 2247*46035553Spatrick return __symlink_status(__p_, __ec).type(); 2248*46035553Spatrick case _IterSymlink: 2249*46035553Spatrick case _RefreshSymlink: 2250*46035553Spatrick case _RefreshSymlinkUnresolved: 2251*46035553Spatrick if (__ec) 2252*46035553Spatrick __ec->clear(); 2253*46035553Spatrick return file_type::symlink; 2254*46035553Spatrick case _IterNonSymlink: 2255*46035553Spatrick case _RefreshNonSymlink: 2256*46035553Spatrick file_status __st(__data_.__type_); 2257*46035553Spatrick if (__ec && !_VSTD_FS::exists(__st)) 2258*46035553Spatrick *__ec = make_error_code(errc::no_such_file_or_directory); 2259*46035553Spatrick else if (__ec) 2260*46035553Spatrick __ec->clear(); 2261*46035553Spatrick return __data_.__type_; 2262*46035553Spatrick } 2263*46035553Spatrick _LIBCPP_UNREACHABLE(); 2264*46035553Spatrick } 2265*46035553Spatrick 2266*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2267*46035553Spatrick file_type __get_ft(error_code* __ec = nullptr) const { 2268*46035553Spatrick switch (__data_.__cache_type_) { 2269*46035553Spatrick case _Empty: 2270*46035553Spatrick case _IterSymlink: 2271*46035553Spatrick case _RefreshSymlinkUnresolved: 2272*46035553Spatrick return __status(__p_, __ec).type(); 2273*46035553Spatrick case _IterNonSymlink: 2274*46035553Spatrick case _RefreshNonSymlink: 2275*46035553Spatrick case _RefreshSymlink: { 2276*46035553Spatrick file_status __st(__data_.__type_); 2277*46035553Spatrick if (__ec && !_VSTD_FS::exists(__st)) 2278*46035553Spatrick *__ec = make_error_code(errc::no_such_file_or_directory); 2279*46035553Spatrick else if (__ec) 2280*46035553Spatrick __ec->clear(); 2281*46035553Spatrick return __data_.__type_; 2282*46035553Spatrick } 2283*46035553Spatrick } 2284*46035553Spatrick _LIBCPP_UNREACHABLE(); 2285*46035553Spatrick } 2286*46035553Spatrick 2287*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2288*46035553Spatrick file_status __get_status(error_code* __ec = nullptr) const { 2289*46035553Spatrick switch (__data_.__cache_type_) { 2290*46035553Spatrick case _Empty: 2291*46035553Spatrick case _IterNonSymlink: 2292*46035553Spatrick case _IterSymlink: 2293*46035553Spatrick case _RefreshSymlinkUnresolved: 2294*46035553Spatrick return __status(__p_, __ec); 2295*46035553Spatrick case _RefreshNonSymlink: 2296*46035553Spatrick case _RefreshSymlink: 2297*46035553Spatrick return file_status(__get_ft(__ec), __data_.__non_sym_perms_); 2298*46035553Spatrick } 2299*46035553Spatrick _LIBCPP_UNREACHABLE(); 2300*46035553Spatrick } 2301*46035553Spatrick 2302*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2303*46035553Spatrick file_status __get_symlink_status(error_code* __ec = nullptr) const { 2304*46035553Spatrick switch (__data_.__cache_type_) { 2305*46035553Spatrick case _Empty: 2306*46035553Spatrick case _IterNonSymlink: 2307*46035553Spatrick case _IterSymlink: 2308*46035553Spatrick return __symlink_status(__p_, __ec); 2309*46035553Spatrick case _RefreshNonSymlink: 2310*46035553Spatrick return file_status(__get_sym_ft(__ec), __data_.__non_sym_perms_); 2311*46035553Spatrick case _RefreshSymlink: 2312*46035553Spatrick case _RefreshSymlinkUnresolved: 2313*46035553Spatrick return file_status(__get_sym_ft(__ec), __data_.__sym_perms_); 2314*46035553Spatrick } 2315*46035553Spatrick _LIBCPP_UNREACHABLE(); 2316*46035553Spatrick } 2317*46035553Spatrick 2318*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2319*46035553Spatrick uintmax_t __get_size(error_code* __ec = nullptr) const { 2320*46035553Spatrick switch (__data_.__cache_type_) { 2321*46035553Spatrick case _Empty: 2322*46035553Spatrick case _IterNonSymlink: 2323*46035553Spatrick case _IterSymlink: 2324*46035553Spatrick case _RefreshSymlinkUnresolved: 2325*46035553Spatrick return _VSTD_FS::__file_size(__p_, __ec); 2326*46035553Spatrick case _RefreshSymlink: 2327*46035553Spatrick case _RefreshNonSymlink: { 2328*46035553Spatrick error_code __m_ec; 2329*46035553Spatrick file_status __st(__get_ft(&__m_ec)); 2330*46035553Spatrick __handle_error("in directory_entry::file_size", __ec, __m_ec); 2331*46035553Spatrick if (_VSTD_FS::exists(__st) && !_VSTD_FS::is_regular_file(__st)) { 2332*46035553Spatrick errc __err_kind = _VSTD_FS::is_directory(__st) ? errc::is_a_directory 2333*46035553Spatrick : errc::not_supported; 2334*46035553Spatrick __handle_error("in directory_entry::file_size", __ec, 2335*46035553Spatrick make_error_code(__err_kind)); 2336*46035553Spatrick } 2337*46035553Spatrick return __data_.__size_; 2338*46035553Spatrick } 2339*46035553Spatrick } 2340*46035553Spatrick _LIBCPP_UNREACHABLE(); 2341*46035553Spatrick } 2342*46035553Spatrick 2343*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2344*46035553Spatrick uintmax_t __get_nlink(error_code* __ec = nullptr) const { 2345*46035553Spatrick switch (__data_.__cache_type_) { 2346*46035553Spatrick case _Empty: 2347*46035553Spatrick case _IterNonSymlink: 2348*46035553Spatrick case _IterSymlink: 2349*46035553Spatrick case _RefreshSymlinkUnresolved: 2350*46035553Spatrick return _VSTD_FS::__hard_link_count(__p_, __ec); 2351*46035553Spatrick case _RefreshSymlink: 2352*46035553Spatrick case _RefreshNonSymlink: { 2353*46035553Spatrick error_code __m_ec; 2354*46035553Spatrick (void)__get_ft(&__m_ec); 2355*46035553Spatrick __handle_error("in directory_entry::hard_link_count", __ec, __m_ec); 2356*46035553Spatrick return __data_.__nlink_; 2357*46035553Spatrick } 2358*46035553Spatrick } 2359*46035553Spatrick _LIBCPP_UNREACHABLE(); 2360*46035553Spatrick } 2361*46035553Spatrick 2362*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2363*46035553Spatrick file_time_type __get_write_time(error_code* __ec = nullptr) const { 2364*46035553Spatrick switch (__data_.__cache_type_) { 2365*46035553Spatrick case _Empty: 2366*46035553Spatrick case _IterNonSymlink: 2367*46035553Spatrick case _IterSymlink: 2368*46035553Spatrick case _RefreshSymlinkUnresolved: 2369*46035553Spatrick return _VSTD_FS::__last_write_time(__p_, __ec); 2370*46035553Spatrick case _RefreshSymlink: 2371*46035553Spatrick case _RefreshNonSymlink: { 2372*46035553Spatrick error_code __m_ec; 2373*46035553Spatrick file_status __st(__get_ft(&__m_ec)); 2374*46035553Spatrick __handle_error("in directory_entry::last_write_time", __ec, __m_ec); 2375*46035553Spatrick if (_VSTD_FS::exists(__st) && 2376*46035553Spatrick __data_.__write_time_ == file_time_type::min()) 2377*46035553Spatrick __handle_error("in directory_entry::last_write_time", __ec, 2378*46035553Spatrick make_error_code(errc::value_too_large)); 2379*46035553Spatrick return __data_.__write_time_; 2380*46035553Spatrick } 2381*46035553Spatrick } 2382*46035553Spatrick _LIBCPP_UNREACHABLE(); 2383*46035553Spatrick } 2384*46035553Spatrick 2385*46035553Spatrickprivate: 2386*46035553Spatrick _Path __p_; 2387*46035553Spatrick __cached_data __data_; 2388*46035553Spatrick}; 2389*46035553Spatrick 2390*46035553Spatrickclass __dir_element_proxy { 2391*46035553Spatrickpublic: 2392*46035553Spatrick inline _LIBCPP_INLINE_VISIBILITY directory_entry operator*() { 2393*46035553Spatrick return _VSTD::move(__elem_); 2394*46035553Spatrick } 2395*46035553Spatrick 2396*46035553Spatrickprivate: 2397*46035553Spatrick friend class directory_iterator; 2398*46035553Spatrick friend class recursive_directory_iterator; 2399*46035553Spatrick explicit __dir_element_proxy(directory_entry const& __e) : __elem_(__e) {} 2400*46035553Spatrick __dir_element_proxy(__dir_element_proxy&& __o) 2401*46035553Spatrick : __elem_(_VSTD::move(__o.__elem_)) {} 2402*46035553Spatrick directory_entry __elem_; 2403*46035553Spatrick}; 2404*46035553Spatrick 2405*46035553Spatrickclass directory_iterator { 2406*46035553Spatrickpublic: 2407*46035553Spatrick typedef directory_entry value_type; 2408*46035553Spatrick typedef ptrdiff_t difference_type; 2409*46035553Spatrick typedef value_type const* pointer; 2410*46035553Spatrick typedef value_type const& reference; 2411*46035553Spatrick typedef input_iterator_tag iterator_category; 2412*46035553Spatrick 2413*46035553Spatrickpublic: 2414*46035553Spatrick //ctor & dtor 2415*46035553Spatrick directory_iterator() noexcept {} 2416*46035553Spatrick 2417*46035553Spatrick explicit directory_iterator(const path& __p) 2418*46035553Spatrick : directory_iterator(__p, nullptr) {} 2419*46035553Spatrick 2420*46035553Spatrick directory_iterator(const path& __p, directory_options __opts) 2421*46035553Spatrick : directory_iterator(__p, nullptr, __opts) {} 2422*46035553Spatrick 2423*46035553Spatrick directory_iterator(const path& __p, error_code& __ec) 2424*46035553Spatrick : directory_iterator(__p, &__ec) {} 2425*46035553Spatrick 2426*46035553Spatrick directory_iterator(const path& __p, directory_options __opts, 2427*46035553Spatrick error_code& __ec) 2428*46035553Spatrick : directory_iterator(__p, &__ec, __opts) {} 2429*46035553Spatrick 2430*46035553Spatrick directory_iterator(const directory_iterator&) = default; 2431*46035553Spatrick directory_iterator(directory_iterator&&) = default; 2432*46035553Spatrick directory_iterator& operator=(const directory_iterator&) = default; 2433*46035553Spatrick 2434*46035553Spatrick directory_iterator& operator=(directory_iterator&& __o) noexcept { 2435*46035553Spatrick // non-default implementation provided to support self-move assign. 2436*46035553Spatrick if (this != &__o) { 2437*46035553Spatrick __imp_ = _VSTD::move(__o.__imp_); 2438*46035553Spatrick } 2439*46035553Spatrick return *this; 2440*46035553Spatrick } 2441*46035553Spatrick 2442*46035553Spatrick ~directory_iterator() = default; 2443*46035553Spatrick 2444*46035553Spatrick const directory_entry& operator*() const { 2445*46035553Spatrick _LIBCPP_ASSERT(__imp_, "The end iterator cannot be dereferenced"); 2446*46035553Spatrick return __dereference(); 2447*46035553Spatrick } 2448*46035553Spatrick 2449*46035553Spatrick const directory_entry* operator->() const { return &**this; } 2450*46035553Spatrick 2451*46035553Spatrick directory_iterator& operator++() { return __increment(); } 2452*46035553Spatrick 2453*46035553Spatrick __dir_element_proxy operator++(int) { 2454*46035553Spatrick __dir_element_proxy __p(**this); 2455*46035553Spatrick __increment(); 2456*46035553Spatrick return __p; 2457*46035553Spatrick } 2458*46035553Spatrick 2459*46035553Spatrick directory_iterator& increment(error_code& __ec) { return __increment(&__ec); } 2460*46035553Spatrick 2461*46035553Spatrickprivate: 2462*46035553Spatrick inline _LIBCPP_INLINE_VISIBILITY friend bool 2463*46035553Spatrick operator==(const directory_iterator& __lhs, 2464*46035553Spatrick const directory_iterator& __rhs) noexcept; 2465*46035553Spatrick 2466*46035553Spatrick // construct the dir_stream 2467*46035553Spatrick _LIBCPP_FUNC_VIS 2468*46035553Spatrick directory_iterator(const path&, error_code*, 2469*46035553Spatrick directory_options = directory_options::none); 2470*46035553Spatrick 2471*46035553Spatrick _LIBCPP_FUNC_VIS 2472*46035553Spatrick directory_iterator& __increment(error_code* __ec = nullptr); 2473*46035553Spatrick 2474*46035553Spatrick _LIBCPP_FUNC_VIS 2475*46035553Spatrick const directory_entry& __dereference() const; 2476*46035553Spatrick 2477*46035553Spatrickprivate: 2478*46035553Spatrick shared_ptr<__dir_stream> __imp_; 2479*46035553Spatrick}; 2480*46035553Spatrick 2481*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool 2482*46035553Spatrickoperator==(const directory_iterator& __lhs, 2483*46035553Spatrick const directory_iterator& __rhs) noexcept { 2484*46035553Spatrick return __lhs.__imp_ == __rhs.__imp_; 2485*46035553Spatrick} 2486*46035553Spatrick 2487*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool 2488*46035553Spatrickoperator!=(const directory_iterator& __lhs, 2489*46035553Spatrick const directory_iterator& __rhs) noexcept { 2490*46035553Spatrick return !(__lhs == __rhs); 2491*46035553Spatrick} 2492*46035553Spatrick 2493*46035553Spatrick// enable directory_iterator range-based for statements 2494*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY directory_iterator 2495*46035553Spatrickbegin(directory_iterator __iter) noexcept { 2496*46035553Spatrick return __iter; 2497*46035553Spatrick} 2498*46035553Spatrick 2499*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY directory_iterator 2500*46035553Spatrickend(const directory_iterator&) noexcept { 2501*46035553Spatrick return directory_iterator(); 2502*46035553Spatrick} 2503*46035553Spatrick 2504*46035553Spatrickclass recursive_directory_iterator { 2505*46035553Spatrickpublic: 2506*46035553Spatrick using value_type = directory_entry; 2507*46035553Spatrick using difference_type = std::ptrdiff_t; 2508*46035553Spatrick using pointer = directory_entry const*; 2509*46035553Spatrick using reference = directory_entry const&; 2510*46035553Spatrick using iterator_category = std::input_iterator_tag; 2511*46035553Spatrick 2512*46035553Spatrickpublic: 2513*46035553Spatrick // constructors and destructor 2514*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2515*46035553Spatrick recursive_directory_iterator() noexcept : __rec_(false) {} 2516*46035553Spatrick 2517*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2518*46035553Spatrick explicit recursive_directory_iterator( 2519*46035553Spatrick const path& __p, directory_options __xoptions = directory_options::none) 2520*46035553Spatrick : recursive_directory_iterator(__p, __xoptions, nullptr) {} 2521*46035553Spatrick 2522*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2523*46035553Spatrick recursive_directory_iterator(const path& __p, directory_options __xoptions, 2524*46035553Spatrick error_code& __ec) 2525*46035553Spatrick : recursive_directory_iterator(__p, __xoptions, &__ec) {} 2526*46035553Spatrick 2527*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2528*46035553Spatrick recursive_directory_iterator(const path& __p, error_code& __ec) 2529*46035553Spatrick : recursive_directory_iterator(__p, directory_options::none, &__ec) {} 2530*46035553Spatrick 2531*46035553Spatrick recursive_directory_iterator(const recursive_directory_iterator&) = default; 2532*46035553Spatrick recursive_directory_iterator(recursive_directory_iterator&&) = default; 2533*46035553Spatrick 2534*46035553Spatrick recursive_directory_iterator& 2535*46035553Spatrick operator=(const recursive_directory_iterator&) = default; 2536*46035553Spatrick 2537*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2538*46035553Spatrick recursive_directory_iterator& 2539*46035553Spatrick operator=(recursive_directory_iterator&& __o) noexcept { 2540*46035553Spatrick // non-default implementation provided to support self-move assign. 2541*46035553Spatrick if (this != &__o) { 2542*46035553Spatrick __imp_ = _VSTD::move(__o.__imp_); 2543*46035553Spatrick __rec_ = __o.__rec_; 2544*46035553Spatrick } 2545*46035553Spatrick return *this; 2546*46035553Spatrick } 2547*46035553Spatrick 2548*46035553Spatrick ~recursive_directory_iterator() = default; 2549*46035553Spatrick 2550*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2551*46035553Spatrick const directory_entry& operator*() const { return __dereference(); } 2552*46035553Spatrick 2553*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2554*46035553Spatrick const directory_entry* operator->() const { return &__dereference(); } 2555*46035553Spatrick 2556*46035553Spatrick recursive_directory_iterator& operator++() { return __increment(); } 2557*46035553Spatrick 2558*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2559*46035553Spatrick __dir_element_proxy operator++(int) { 2560*46035553Spatrick __dir_element_proxy __p(**this); 2561*46035553Spatrick __increment(); 2562*46035553Spatrick return __p; 2563*46035553Spatrick } 2564*46035553Spatrick 2565*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2566*46035553Spatrick recursive_directory_iterator& increment(error_code& __ec) { 2567*46035553Spatrick return __increment(&__ec); 2568*46035553Spatrick } 2569*46035553Spatrick 2570*46035553Spatrick _LIBCPP_FUNC_VIS directory_options options() const; 2571*46035553Spatrick _LIBCPP_FUNC_VIS int depth() const; 2572*46035553Spatrick 2573*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2574*46035553Spatrick void pop() { __pop(); } 2575*46035553Spatrick 2576*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2577*46035553Spatrick void pop(error_code& __ec) { __pop(&__ec); } 2578*46035553Spatrick 2579*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2580*46035553Spatrick bool recursion_pending() const { return __rec_; } 2581*46035553Spatrick 2582*46035553Spatrick _LIBCPP_INLINE_VISIBILITY 2583*46035553Spatrick void disable_recursion_pending() { __rec_ = false; } 2584*46035553Spatrick 2585*46035553Spatrickprivate: 2586*46035553Spatrick _LIBCPP_FUNC_VIS 2587*46035553Spatrick recursive_directory_iterator(const path& __p, directory_options __opt, 2588*46035553Spatrick error_code* __ec); 2589*46035553Spatrick 2590*46035553Spatrick _LIBCPP_FUNC_VIS 2591*46035553Spatrick const directory_entry& __dereference() const; 2592*46035553Spatrick 2593*46035553Spatrick _LIBCPP_FUNC_VIS 2594*46035553Spatrick bool __try_recursion(error_code* __ec); 2595*46035553Spatrick 2596*46035553Spatrick _LIBCPP_FUNC_VIS 2597*46035553Spatrick void __advance(error_code* __ec = nullptr); 2598*46035553Spatrick 2599*46035553Spatrick _LIBCPP_FUNC_VIS 2600*46035553Spatrick recursive_directory_iterator& __increment(error_code* __ec = nullptr); 2601*46035553Spatrick 2602*46035553Spatrick _LIBCPP_FUNC_VIS 2603*46035553Spatrick void __pop(error_code* __ec = nullptr); 2604*46035553Spatrick 2605*46035553Spatrick inline _LIBCPP_INLINE_VISIBILITY friend bool 2606*46035553Spatrick operator==(const recursive_directory_iterator&, 2607*46035553Spatrick const recursive_directory_iterator&) noexcept; 2608*46035553Spatrick 2609*46035553Spatrick struct _LIBCPP_HIDDEN __shared_imp; 2610*46035553Spatrick shared_ptr<__shared_imp> __imp_; 2611*46035553Spatrick bool __rec_; 2612*46035553Spatrick}; // class recursive_directory_iterator 2613*46035553Spatrick 2614*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY bool 2615*46035553Spatrickoperator==(const recursive_directory_iterator& __lhs, 2616*46035553Spatrick const recursive_directory_iterator& __rhs) noexcept { 2617*46035553Spatrick return __lhs.__imp_ == __rhs.__imp_; 2618*46035553Spatrick} 2619*46035553Spatrick 2620*46035553Spatrick_LIBCPP_INLINE_VISIBILITY 2621*46035553Spatrickinline bool operator!=(const recursive_directory_iterator& __lhs, 2622*46035553Spatrick const recursive_directory_iterator& __rhs) noexcept { 2623*46035553Spatrick return !(__lhs == __rhs); 2624*46035553Spatrick} 2625*46035553Spatrick// enable recursive_directory_iterator range-based for statements 2626*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY recursive_directory_iterator 2627*46035553Spatrickbegin(recursive_directory_iterator __iter) noexcept { 2628*46035553Spatrick return __iter; 2629*46035553Spatrick} 2630*46035553Spatrick 2631*46035553Spatrickinline _LIBCPP_INLINE_VISIBILITY recursive_directory_iterator 2632*46035553Spatrickend(const recursive_directory_iterator&) noexcept { 2633*46035553Spatrick return recursive_directory_iterator(); 2634*46035553Spatrick} 2635*46035553Spatrick 2636*46035553Spatrick_LIBCPP_AVAILABILITY_FILESYSTEM_POP 2637*46035553Spatrick 2638*46035553Spatrick_LIBCPP_END_NAMESPACE_FILESYSTEM 2639*46035553Spatrick 2640*46035553Spatrick#endif // !_LIBCPP_CXX03_LANG 2641*46035553Spatrick 2642*46035553Spatrick_LIBCPP_POP_MACROS 2643*46035553Spatrick 2644*46035553Spatrick#endif // _LIBCPP_FILESYSTEM 2645