30 #ifndef _GLIBCXX_EXPERIMENTAL_FS_PATH_H
31 #define _GLIBCXX_EXPERIMENTAL_FS_PATH_H 1
33 #if __cplusplus < 201103L
47 #if __cplusplus == 201402L
51 #if defined(_WIN32) && !defined(__CYGWIN__)
52 # define _GLIBCXX_FILESYSTEM_IS_WINDOWS 1
56 namespace std _GLIBCXX_VISIBILITY(default)
58 _GLIBCXX_BEGIN_NAMESPACE_VERSION
60 namespace experimental
66 _GLIBCXX_BEGIN_NAMESPACE_CXX11
68 #if __cplusplus == 201402L
70 #elif __cplusplus > 201402L
81 template<
typename _CharT,
82 typename _Ch =
typename remove_const<_CharT>::type>
83 using __is_encoded_char
84 = __or_<is_same<_Ch, char>,
85 is_same<_Ch, wchar_t>,
86 #ifdef _GLIBCXX_USE_CHAR8_T
87 is_same<_Ch, char8_t>,
89 is_same<_Ch, char16_t>,
90 is_same<_Ch, char32_t>>;
92 template<
typename _Iter,
94 using __is_path_iter_src
95 = __and_<__is_encoded_char<typename _Iter_traits::value_type>,
97 typename _Iter_traits::iterator_category>>;
99 template<
typename _Iter>
100 static __is_path_iter_src<_Iter>
101 __is_path_src(_Iter,
int);
103 template<
typename _CharT,
typename _Traits,
typename _Alloc>
104 static __is_encoded_char<_CharT>
105 __is_path_src(
const basic_string<_CharT, _Traits, _Alloc>&,
int);
107 #if __cplusplus >= 201402L
108 template<
typename _CharT,
typename _Traits>
109 static __is_encoded_char<_CharT>
110 __is_path_src(
const basic_string_view<_CharT, _Traits>&,
int);
113 template<
typename _Unknown>
115 __is_path_src(
const _Unknown&, ...);
117 template<
typename _Tp1,
typename _Tp2>
118 struct __constructible_from;
120 template<
typename _Iter>
121 struct __constructible_from<_Iter, _Iter>
122 : __is_path_iter_src<_Iter>
125 template<
typename _Source>
126 struct __constructible_from<_Source, void>
127 : decltype(__is_path_src(std::declval<const _Source&>(), 0))
130 template<
typename _Tp1,
typename _Tp2 = void,
131 typename _Tp1_nocv =
typename remove_cv<_Tp1>::type,
132 typename _Tp1_noptr =
typename remove_pointer<_Tp1>::type>
133 using _Path =
typename
135 __not_<is_void<_Tp1_noptr>>,
136 __constructible_from<_Tp1, _Tp2>>::value,
139 template<
typename _Source>
141 _S_range_begin(_Source __begin) {
return __begin; }
143 struct __nul_terminated { };
145 template<
typename _Source>
146 inline __nul_terminated
147 _S_range_end(_Source) {
return {}; }
149 template<
typename _CharT,
typename _Traits,
typename _Alloc>
151 _S_range_begin(
const basic_string<_CharT, _Traits, _Alloc>& __str)
152 {
return __str.data(); }
154 template<
typename _CharT,
typename _Traits,
typename _Alloc>
156 _S_range_end(
const basic_string<_CharT, _Traits, _Alloc>& __str)
157 {
return __str.data() + __str.size(); }
159 #if __cplusplus >= 201402L
160 template<
typename _CharT,
typename _Traits>
162 _S_range_begin(
const basic_string_view<_CharT, _Traits>& __str)
163 {
return __str.data(); }
165 template<
typename _CharT,
typename _Traits>
167 _S_range_end(
const basic_string_view<_CharT, _Traits>& __str)
168 {
return __str.data() + __str.size(); }
171 template<
typename _Tp,
172 typename _Iter = decltype(_S_range_begin(std::declval<_Tp>())),
174 typename _UnqualVal =
typename std::remove_const<_Val>::type>
179 template<
typename _Tp,
180 typename _Iter = decltype(_S_range_begin(std::declval<_Tp>())),
182 typename _UnqualVal =
typename std::remove_const<_Val>::type>
186 #ifdef _GLIBCXX_USE_CHAR8_T
189 >::value, _UnqualVal>::type;
204 #ifdef _GLIBCXX_FILESYSTEM_IS_WINDOWS
205 typedef wchar_t value_type;
206 static constexpr value_type preferred_separator = L
'\\';
208 typedef char value_type;
209 static constexpr value_type preferred_separator =
'/';
219 path(string_type&& __source);
221 template<
typename _Source,
222 typename _Require = __detail::_Path<_Source>>
223 path(_Source
const& __source)
224 : _M_pathname(_S_convert(__detail::_S_range_begin(__source),
225 __detail::_S_range_end(__source)))
226 { _M_split_cmpts(); }
228 template<
typename _InputIterator,
229 typename _Require = __detail::_Path<_InputIterator, _InputIterator>>
230 path(_InputIterator __first, _InputIterator __last)
231 : _M_pathname(_S_convert(__first, __last))
232 { _M_split_cmpts(); }
234 template<
typename _Source,
235 typename _Require = __detail::_Path<_Source>,
236 typename _Require2 = __detail::__value_type_is_char<_Source>>
237 path(_Source
const& __source,
const locale& __loc)
238 : _M_pathname(_S_convert_loc(__detail::_S_range_begin(__source),
239 __detail::_S_range_end(__source), __loc))
240 { _M_split_cmpts(); }
242 template<
typename _InputIterator,
243 typename _Require = __detail::_Path<_InputIterator, _InputIterator>,
244 typename _Require2 = __detail::__value_type_is_char<_InputIterator>>
245 path(_InputIterator __first, _InputIterator __last,
const locale& __loc)
246 : _M_pathname(_S_convert_loc(__first, __last, __loc))
247 { _M_split_cmpts(); }
254 path& operator=(
path&& __p) noexcept;
255 path& operator=(string_type&& __source);
256 path& assign(string_type&& __source);
258 template<
typename _Source>
259 __detail::_Path<_Source>&
260 operator=(_Source
const& __source)
261 {
return *
this =
path(__source); }
263 template<
typename _Source>
264 __detail::_Path<_Source>&
265 assign(_Source
const& __source)
266 {
return *
this =
path(__source); }
268 template<
typename _InputIterator>
269 __detail::_Path<_InputIterator, _InputIterator>&
270 assign(_InputIterator __first, _InputIterator __last)
271 {
return *
this =
path(__first, __last); }
275 path& operator/=(
const path& __p) {
return _M_append(__p._M_pathname); }
277 template<
typename _Source>
278 __detail::_Path<_Source>&
279 operator/=(_Source
const& __source)
280 {
return append(__source); }
282 template<
typename _Source>
283 __detail::_Path<_Source>&
284 append(_Source
const& __source)
286 return _M_append(_S_convert(__detail::_S_range_begin(__source),
287 __detail::_S_range_end(__source)));
290 template<
typename _InputIterator>
291 __detail::_Path<_InputIterator, _InputIterator>&
292 append(_InputIterator __first, _InputIterator __last)
293 {
return _M_append(_S_convert(__first, __last)); }
298 path& operator+=(
const string_type& __x);
299 path& operator+=(
const value_type* __x);
300 path& operator+=(value_type __x);
301 #if __cplusplus >= 201402L
305 template<
typename _Source>
306 __detail::_Path<_Source>&
307 operator+=(_Source
const& __x) {
return concat(__x); }
309 template<
typename _CharT>
310 __detail::_Path<_CharT*, _CharT*>&
311 operator+=(_CharT __x);
313 template<
typename _Source>
314 __detail::_Path<_Source>&
315 concat(_Source
const& __x)
317 return *
this += _S_convert(__detail::_S_range_begin(__x),
318 __detail::_S_range_end(__x));
321 template<
typename _InputIterator>
322 __detail::_Path<_InputIterator, _InputIterator>&
323 concat(_InputIterator __first, _InputIterator __last)
324 {
return *
this += _S_convert(__first, __last); }
328 void clear() noexcept { _M_pathname.
clear(); _M_split_cmpts(); }
330 path& make_preferred();
331 path& remove_filename();
332 path& replace_filename(
const path& __replacement);
333 path& replace_extension(
const path& __replacement =
path());
335 void swap(
path& __rhs) noexcept;
339 const string_type& native()
const noexcept {
return _M_pathname; }
340 const value_type* c_str()
const noexcept {
return _M_pathname.
c_str(); }
341 operator string_type()
const {
return _M_pathname; }
343 template<
typename _CharT,
typename _Traits = std::
char_traits<_CharT>,
344 typename _Allocator = std::allocator<_CharT>>
346 string(
const _Allocator& __a = _Allocator())
const;
349 #if _GLIBCXX_USE_WCHAR_T
352 #ifdef _GLIBCXX_USE_CHAR8_T
353 __attribute__((__abi_tag__(
"__u8")))
354 std::u8string u8string()
const;
362 template<
typename _CharT,
typename _Traits = std::
char_traits<_CharT>,
363 typename _Allocator = std::allocator<_CharT>>
365 generic_string(
const _Allocator& __a = _Allocator())
const;
368 #if _GLIBCXX_USE_WCHAR_T
371 #ifdef _GLIBCXX_USE_CHAR8_T
372 __attribute__((__abi_tag__(
"__u8")))
373 std::u8string generic_u8string()
const;
382 int compare(
const path& __p)
const noexcept;
383 int compare(
const string_type& __s)
const;
384 int compare(
const value_type* __s)
const;
385 #if __cplusplus >= 201402L
391 path root_name()
const;
392 path root_directory()
const;
393 path root_path()
const;
394 path relative_path()
const;
395 path parent_path()
const;
396 path filename()
const;
398 path extension()
const;
402 _GLIBCXX_NODISCARD
bool empty()
const noexcept {
return _M_pathname.
empty(); }
403 bool has_root_name()
const;
404 bool has_root_directory()
const;
405 bool has_root_path()
const;
406 bool has_relative_path()
const;
407 bool has_parent_path()
const;
408 bool has_filename()
const;
409 bool has_stem()
const;
410 bool has_extension()
const;
411 bool is_absolute()
const;
412 bool is_relative()
const {
return !is_absolute(); }
423 template<
typename _InputIterator,
426 =
typename std::remove_cv<typename _Traits::value_type>::type>
428 _S_string_from_iter(_InputIterator __source)
431 for (_CharT __ch = *__source; __ch != _CharT(); __ch = *++__source)
438 enum class _Type : unsigned char {
439 _Multi, _Root_name, _Root_dir, _Filename
442 path(string_type __str, _Type __type);
444 enum class _Split { _Stem, _Extension };
446 path& _M_append(
const string_type& __str)
448 if (!_M_pathname.
empty() && !_S_is_dir_sep(_M_pathname.
back())
449 && !__str.empty() && !_S_is_dir_sep(__str.front()))
450 _M_pathname += preferred_separator;
451 _M_pathname += __str;
458 template<
typename _CharT>
462 _S_convert(value_type* __src, __detail::__nul_terminated)
463 {
return string_type(__src); }
466 _S_convert(
const value_type* __src, __detail::__nul_terminated)
467 {
return string_type(__src); }
469 template<
typename _Iter>
471 _S_convert(_Iter __first, _Iter __last)
474 return _Cvt<typename remove_cv<__value_type>::type>::
475 _S_convert(__first, __last);
478 template<
typename _InputIterator>
480 _S_convert(_InputIterator __src, __detail::__nul_terminated)
482 auto __s = _S_string_from_iter(__src);
483 return _S_convert(__s.c_str(), __s.c_str() + __s.size());
487 _S_convert_loc(
const char* __first,
const char* __last,
491 _S_convert_loc(
char* __first,
char* __last,
const std::locale& __loc)
493 return _S_convert_loc(
const_cast<const char*
>(__first),
494 const_cast<const char*
>(__last), __loc);
497 template<
typename _Iter>
499 _S_convert_loc(_Iter __first, _Iter __last,
const std::locale& __loc)
502 return _S_convert_loc(__str.
data(), __str.
data()+__str.
size(), __loc);
505 template<
typename _InputIterator>
507 _S_convert_loc(_InputIterator __src, __detail::__nul_terminated,
510 const std::string __s = _S_string_from_iter(__src);
511 return _S_convert_loc(__s.
data(), __s.
data() + __s.
size(), __loc);
514 static bool _S_is_dir_sep(value_type __ch)
516 #ifdef _GLIBCXX_FILESYSTEM_IS_WINDOWS
517 return __ch == L
'/' || __ch == preferred_separator;
523 void _M_split_cmpts();
525 void _M_add_root_name(
size_t __n);
526 void _M_add_root_dir(
size_t __pos);
527 void _M_add_filename(
size_t __pos,
size_t __n);
529 string_type _M_pathname;
532 using _List = _GLIBCXX_STD_C::vector<_Cmpt>;
534 _Type _M_type = _Type::_Multi;
540 inline void swap(
path& __lhs,
path& __rhs) noexcept { __lhs.swap(__rhs); }
543 size_t hash_value(
const path& __p) noexcept;
546 inline bool operator<(
const path& __lhs,
const path& __rhs) noexcept;
549 inline bool operator<=(
const path& __lhs,
const path& __rhs) noexcept
550 {
return !(__rhs < __lhs); }
553 inline bool operator>(
const path& __lhs,
const path& __rhs) noexcept
554 {
return __rhs < __lhs; }
557 inline bool operator>=(
const path& __lhs,
const path& __rhs) noexcept
558 {
return !(__lhs < __rhs); }
561 inline bool operator==(
const path& __lhs,
const path& __rhs) noexcept;
564 inline bool operator!=(
const path& __lhs,
const path& __rhs) noexcept
565 {
return !(__lhs == __rhs); }
568 inline path
operator/(
const path& __lhs,
const path& __rhs)
570 path __result(__lhs);
576 template<
typename _CharT,
typename _Traits>
577 basic_ostream<_CharT, _Traits>&
578 operator<<(basic_ostream<_CharT, _Traits>& __os,
const path& __p)
580 auto __tmp = __p.string<_CharT, _Traits>();
581 using __quoted_string
583 __os << __quoted_string{__tmp, _CharT(
'"'), _CharT(
'\\')};
588 template<
typename _CharT,
typename _Traits>
589 basic_istream<_CharT, _Traits>&
590 operator>>(basic_istream<_CharT, _Traits>& __is, path& __p)
592 basic_string<_CharT, _Traits> __tmp;
593 using __quoted_string
595 if (__is >> __quoted_string{ __tmp, _CharT(
'"'), _CharT(
'\\') })
601 #ifdef _GLIBCXX_FILESYSTEM_IS_WINDOWS
602 template<
typename _InputIterator>
604 __u8path(_InputIterator __first, _InputIterator __last,
char)
607 std::codecvt_utf8_utf16<path::value_type> __cvt;
608 path::string_type __tmp;
610 const char*
const __ptr = __u8str.
data();
611 if (__str_codecvt_in_all(__ptr, __ptr + __u8str.size(), __tmp, __cvt))
612 return path{ __tmp };
613 _GLIBCXX_THROW_OR_ABORT(filesystem_error(
614 "Cannot convert character sequence",
618 #ifdef _GLIBCXX_USE_CHAR8_T
619 template<
typename _InputIterator>
621 __u8path(_InputIterator __first, _InputIterator __last, char8_t)
623 return path{ __first, __last };
628 template<
typename _InputIterator,
629 typename _Require = __detail::_Path<_InputIterator, _InputIterator>,
631 __detail::__value_type_is_char_or_char8_t<_InputIterator>>
633 u8path(_InputIterator __first, _InputIterator __last)
635 #ifdef _GLIBCXX_FILESYSTEM_IS_WINDOWS
636 return __u8path(__first, __last, _CharT{});
638 return path{ __first, __last };
643 #ifdef _GLIBCXX_FILESYSTEM_IS_WINDOWS
645 __u8path(
const string& __s,
char)
647 return filesystem::u8path(__s.data(), __s.data() + __s.size());
650 template<
typename _Source>
651 inline __enable_if_t<is_convertible<const _Source&, string>::value, path>
652 __u8path(
const _Source& __source,
char)
655 return filesystem::u8path(__s.
data(), __s.
data() + __s.
size());
658 template<
typename _Source>
659 inline __enable_if_t<!is_convertible<const _Source&, string>::value, path>
660 __u8path(
const _Source& __source,
char)
662 std::string __s = path::_S_string_from_iter(__source);
663 return filesystem::u8path(__s.
data(), __s.
data() + __s.
size());
666 #ifdef _GLIBCXX_USE_CHAR8_T
667 template<
typename _Source>
669 __u8path(
const _Source& __source, char8_t)
671 return path{ __source };
676 template<
typename _Source,
677 typename _Require = __detail::_Path<_Source>,
679 __detail::__value_type_is_char_or_char8_t<_Source>>
681 u8path(
const _Source& __source)
683 #ifdef _GLIBCXX_FILESYSTEM_IS_WINDOWS
684 return __u8path(__source, _CharT{});
686 return path{ __source };
705 :
system_error(__ec, __what_arg), _M_path1(__p1), _M_path2(__p2)
710 const path& path1()
const noexcept {
return _M_path1; }
711 const path& path2()
const noexcept {
return _M_path2; }
712 const char*
what() const noexcept {
return _M_what.
c_str(); }
723 struct path::_Cmpt :
path
725 _Cmpt(string_type __s, _Type __t,
size_t __pos)
728 _Cmpt() : _M_pos(-1) { }
735 struct path::_Cvt<path::value_type>
740 using __codecvt_utf8_to_wide = _Cvt;
742 template<
typename _WStr>
744 __str_codecvt_in_all(
const char*,
const char*,
745 _WStr&, __codecvt_utf8_to_wide&) noexcept
748 template<
typename _Iter>
750 _S_convert(_Iter __first, _Iter __last)
751 {
return string_type{__first, __last}; }
755 template<
typename _CharT>
761 using __codecvt_utf8_to_wchar
762 = __conditional_t<
sizeof(wchar_t) ==
sizeof(char32_t),
763 std::codecvt_utf8<wchar_t>,
764 std::codecvt_utf8_utf16<wchar_t>>;
768 struct __codecvt_utf8_to_utfNN :
std::codecvt<_CharT, char, mbstate_t>
773 using __codecvt_utf8_to_wide
774 = __conditional_t<is_same<_CharT, wchar_t>::value,
775 __codecvt_utf8_to_wchar,
776 __codecvt_utf8_to_utfNN>;
779 #pragma GCC diagnostic push
780 #pragma GCC diagnostic ignored "-Wc++17-extensions"
782 _S_convert(
const _CharT* __f,
const _CharT* __l)
784 #ifdef _GLIBCXX_FILESYSTEM_IS_WINDOWS
785 if constexpr (is_same<_CharT, char>::value)
787 std::codecvt_utf8_utf16<wchar_t> __cvt;
790 if (__str_codecvt_in_all(__f, __l, __wstr, __cvt))
793 #ifdef _GLIBCXX_USE_CHAR8_T
794 else if constexpr (is_same<_CharT, char8_t>::value)
795 return _S_convert((
const char*)__f, (
const char*)__l);
800 __codecvt_utf8_to_utfNN __cvt;
802 if (__str_codecvt_out_all(__f, __l, __str, __cvt))
806 _GLIBCXX_THROW_OR_ABORT(filesystem_error(
807 "Cannot convert character sequence",
810 #ifdef _GLIBCXX_USE_CHAR8_T
811 if constexpr (is_same<_CharT, char8_t>::value)
812 return string_type(__f, __l);
816 __codecvt_utf8_to_wide __cvt;
818 if (__str_codecvt_out_all(__f, __l, __str, __cvt))
820 _GLIBCXX_THROW_OR_ABORT(filesystem_error(
821 "Cannot convert character sequence",
826 #pragma GCC diagnostic pop
829 _S_convert(_CharT* __f, _CharT* __l)
831 return _S_convert(
const_cast<const _CharT*
>(__f),
832 const_cast<const _CharT*
>(__l));
835 template<
typename _Iter>
837 _S_convert(_Iter __first, _Iter __last)
840 return _S_convert(__str.
data(), __str.
data() + __str.
size());
843 template<
typename _Iter,
typename _Cont>
845 _S_convert(__gnu_cxx::__normal_iterator<_Iter, _Cont> __first,
846 __gnu_cxx::__normal_iterator<_Iter, _Cont> __last)
847 {
return _S_convert(__first.base(), __last.base()); }
855 using difference_type = std::ptrdiff_t;
861 iterator() noexcept : _M_path(
nullptr), _M_cur(), _M_at_end() { }
872 {
auto __tmp = *
this; ++*
this;
return __tmp; }
877 {
auto __tmp = *
this; --*
this;
return __tmp; }
881 {
return __lhs._M_equals(__rhs); }
885 {
return !__lhs._M_equals(__rhs); }
890 iterator(
const path* __path, path::_List::const_iterator __iter) noexcept
891 : _M_path(__path), _M_cur(__iter), _M_at_end()
895 : _M_path(__path), _M_cur(), _M_at_end(__at_end)
898 bool _M_equals(
iterator)
const noexcept;
901 path::_List::const_iterator _M_cur;
906 path::path() noexcept = default;
913 : _M_pathname(
std::
move(__p._M_pathname)),
914 _M_cmpts(__p._M_cmpts),
919 path::path(string_type&& __source)
920 : _M_pathname(
std::
move(__source))
921 { _M_split_cmpts(); }
924 path::path(string_type __str, _Type __type)
925 : _M_pathname(__str), _M_type(__type)
927 __glibcxx_assert(!empty());
928 __glibcxx_assert(_M_type != _Type::_Multi);
932 path::~path() =
default;
935 path::operator=(
const path& __p) =
default;
938 path::operator=(path&& __p) noexcept
940 _M_pathname =
std::move(__p._M_pathname);
942 _M_type = __p._M_type;
948 path::operator=(string_type&& __source)
949 {
return *
this = path(
std::move(__source)); }
952 path::assign(string_type&& __source)
953 {
return *
this = path(
std::move(__source)); }
956 path::operator+=(
const path& __p)
958 return operator+=(__p.native());
962 path::operator+=(
const string_type& __x)
970 path::operator+=(
const value_type* __x)
978 path::operator+=(value_type __x)
985 #if __cplusplus >= 201402L
987 path::operator+=(basic_string_view<value_type> __x)
989 _M_pathname.append(__x.data(), __x.size());
995 template<
typename _CharT>
996 inline __detail::_Path<_CharT*, _CharT*>&
997 path::operator+=(_CharT __x)
1000 return concat(__addr, __addr + 1);
1004 path::make_preferred()
1006 #ifdef _GLIBCXX_FILESYSTEM_IS_WINDOWS
1007 std::replace(_M_pathname.begin(), _M_pathname.end(), L
'/',
1008 preferred_separator);
1013 inline void path::swap(path& __rhs) noexcept
1015 _M_pathname.swap(__rhs._M_pathname);
1016 _M_cmpts.swap(__rhs._M_cmpts);
1017 std::swap(_M_type, __rhs._M_type);
1020 #pragma GCC diagnostic push
1021 #pragma GCC diagnostic ignored "-Wc++17-extensions"
1022 template<
typename _CharT,
typename _Traits,
typename _Allocator>
1026 using _WString = basic_string<_CharT, _Traits, _Allocator>;
1028 const value_type* __first = _M_pathname.data();
1029 const value_type* __last = __first + _M_pathname.size();
1031 if constexpr (is_same<_CharT, value_type>::value)
1032 return _WString(__first, __last, __a);
1033 #ifdef _GLIBCXX_FILESYSTEM_IS_WINDOWS
1036 using _CharAlloc = __alloc_rebind<_Allocator, char>;
1037 using _String = basic_string<char, char_traits<char>, _CharAlloc>;
1041 codecvt_utf8_utf16<value_type> __cvt;
1042 _String __u8str{_CharAlloc{__a}};
1043 if (__str_codecvt_out_all(__first, __last, __u8str, __cvt))
1045 if constexpr (is_same<_CharT, char>::value)
1047 #ifdef _GLIBCXX_USE_CHAR8_T
1048 else if constexpr (is_same<_CharT, char8_t>::value)
1049 return _WString(__u8str.begin(), __u8str.end(), __a);
1053 _WString __wstr(__a);
1055 typename path::_Cvt<_CharT>::__codecvt_utf8_to_wide __cvt;
1056 const char* __f = __u8str.data();
1057 const char* __l = __f + __u8str.size();
1058 if (__str_codecvt_in_all(__f, __l, __wstr, __cvt))
1064 #ifdef _GLIBCXX_USE_CHAR8_T
1065 else if constexpr (is_same<_CharT, char8_t>::value)
1066 return _WString(__first, __last, __a);
1070 typename path::_Cvt<_CharT>::__codecvt_utf8_to_wide __cvt;
1071 _WString __wstr(__a);
1072 if (__str_codecvt_in_all(__first, __last, __wstr, __cvt))
1076 _GLIBCXX_THROW_OR_ABORT(filesystem_error(
1077 "Cannot convert character sequence",
1080 #pragma GCC diagnostic pop
1085 #if _GLIBCXX_USE_WCHAR_T
1090 #ifdef _GLIBCXX_USE_CHAR8_T
1091 inline std::u8string
1092 path::u8string()
const {
return string<char8_t>(); }
1095 path::u8string()
const
1097 #ifdef _GLIBCXX_FILESYSTEM_IS_WINDOWS
1100 std::codecvt_utf8_utf16<value_type> __cvt;
1101 const value_type* __first = _M_pathname.data();
1102 const value_type* __last = __first + _M_pathname.size();
1103 if (__str_codecvt_out_all(__first, __last, __str, __cvt))
1105 _GLIBCXX_THROW_OR_ABORT(filesystem_error(
1106 "Cannot convert character sequence",
1120 template<
typename _CharT,
typename _Traits,
typename _Allocator>
1122 path::generic_string(
const _Allocator& __a)
const
1124 #ifdef _GLIBCXX_FILESYSTEM_IS_WINDOWS
1125 const _CharT __slash = is_same<_CharT, wchar_t>::value
1129 const _CharT __slash = _CharT(
'/');
1131 basic_string<_CharT, _Traits, _Allocator> __str(__a);
1132 __str.
reserve(_M_pathname.size());
1133 bool __add_slash =
false;
1134 for (
auto& __elem : *
this)
1136 if (__elem._M_type == _Type::_Root_dir)
1143 __str += __elem.string<_CharT, _Traits, _Allocator>(__a);
1144 __add_slash = __elem._M_type == _Type::_Filename;
1150 path::generic_string()
const {
return generic_string<char>(); }
1152 #if _GLIBCXX_USE_WCHAR_T
1154 path::generic_wstring()
const {
return generic_string<wchar_t>(); }
1157 #ifdef _GLIBCXX_USE_CHAR8_T
1158 inline std::u8string
1159 path::generic_u8string()
const {
return generic_string<char8_t>(); }
1162 path::generic_u8string()
const {
return generic_string<char>(); }
1166 path::generic_u16string()
const {
return generic_string<char16_t>(); }
1169 path::generic_u32string()
const {
return generic_string<char32_t>(); }
1172 path::compare(
const string_type& __s)
const {
return compare(path(__s)); }
1175 path::compare(
const value_type* __s)
const {
return compare(path(__s)); }
1177 #if __cplusplus >= 201402L
1179 path::compare(basic_string_view<value_type> __s)
const
1180 {
return compare(path(__s)); }
1184 path::filename()
const {
return empty() ? path() : *--end(); }
1189 auto ext = _M_find_extension();
1190 if (ext.first && ext.second != 0)
1191 return path{ext.first->substr(0, ext.second)};
1196 path::extension()
const
1198 auto ext = _M_find_extension();
1200 return path{ext.first->substr(ext.second)};
1205 path::has_stem()
const
1207 auto ext = _M_find_extension();
1208 return ext.first && ext.second != 0;
1212 path::has_extension()
const
1214 auto ext = _M_find_extension();
1219 path::is_absolute()
const
1221 #ifdef _GLIBCXX_FILESYSTEM_IS_WINDOWS
1222 return has_root_name() && has_root_directory();
1224 return has_root_directory();
1228 inline path::iterator
1229 path::begin() const noexcept
1231 if (_M_type == _Type::_Multi)
1232 return iterator(
this, _M_cmpts.begin());
1233 return iterator(
this,
false);
1236 inline path::iterator
1237 path::end() const noexcept
1239 if (_M_type == _Type::_Multi)
1240 return iterator(
this, _M_cmpts.end());
1241 return iterator(
this,
true);
1244 inline path::iterator&
1245 path::iterator::operator++() noexcept
1247 __glibcxx_assert(_M_path !=
nullptr);
1248 if (_M_path->_M_type == _Type::_Multi)
1250 __glibcxx_assert(_M_cur != _M_path->_M_cmpts.end());
1255 __glibcxx_assert(!_M_at_end);
1261 inline path::iterator&
1262 path::iterator::operator--() noexcept
1264 __glibcxx_assert(_M_path !=
nullptr);
1265 if (_M_path->_M_type == _Type::_Multi)
1267 __glibcxx_assert(_M_cur != _M_path->_M_cmpts.begin());
1272 __glibcxx_assert(_M_at_end);
1278 inline path::iterator::reference
1281 __glibcxx_assert(_M_path !=
nullptr);
1282 if (_M_path->_M_type == _Type::_Multi)
1284 __glibcxx_assert(_M_cur != _M_path->_M_cmpts.end());
1291 path::iterator::_M_equals(iterator __rhs)
const noexcept
1293 if (_M_path != __rhs._M_path)
1295 if (_M_path ==
nullptr)
1297 if (_M_path->_M_type == path::_Type::_Multi)
1298 return _M_cur == __rhs._M_cur;
1299 return _M_at_end == __rhs._M_at_end;
1306 inline bool operator<(
const path& __lhs,
const path& __rhs) noexcept
1307 {
return __lhs.compare(__rhs) < 0; }
1309 inline bool operator==(
const path& __lhs,
const path& __rhs) noexcept
1310 {
return __lhs.compare(__rhs) == 0; }
1313 _GLIBCXX_END_NAMESPACE_CXX11
1318 _GLIBCXX_END_NAMESPACE_VERSION
constexpr bool operator<=(const duration< _Rep1, _Period1 > &__lhs, const duration< _Rep2, _Period2 > &__rhs)
constexpr bool operator>=(const duration< _Rep1, _Period1 > &__lhs, const duration< _Rep2, _Period2 > &__rhs)
constexpr bool operator<(const duration< _Rep1, _Period1 > &__lhs, const duration< _Rep2, _Period2 > &__rhs)
constexpr bool operator>(const duration< _Rep1, _Period1 > &__lhs, const duration< _Rep2, _Period2 > &__rhs)
constexpr complex< _Tp > operator*(const complex< _Tp > &__x, const complex< _Tp > &__y)
Return new complex value x times y.
constexpr complex< _Tp > operator/(const complex< _Tp > &__x, const complex< _Tp > &__y)
Return new complex value x divided by y.
error_code make_error_code(future_errc __errc) noexcept
Overload of make_error_code for future_errc.
__bool_constant< false > false_type
The type used as a compile-time boolean with false value.
constexpr _Tp * __addressof(_Tp &__r) noexcept
Same as C++11 std::addressof.
constexpr std::remove_reference< _Tp >::type && move(_Tp &&__t) noexcept
Convert a value to an rvalue.
basic_string< char > string
A string of char.
basic_string< char32_t > u32string
A string of char32_t.
basic_string< char16_t > u16string
A string of char16_t.
basic_string< wchar_t > wstring
A string of wchar_t.
ISO C++ entities toplevel namespace is std.
std::basic_istream< _CharT, _Traits > & operator>>(std::basic_istream< _CharT, _Traits > &__is, bitset< _Nb > &__x)
Global I/O operators for bitsets.
std::basic_ostream< _CharT, _Traits > & operator<<(std::basic_ostream< _CharT, _Traits > &__os, const bitset< _Nb > &__x)
Global I/O operators for bitsets.
A non-owning reference to a string.
An exception type that includes an error_code value.
Define a member typedef type only if a boolean constant is true.
Primary class template codecvt.
void push_back(_CharT __c)
Append a single character.
const _CharT * c_str() const noexcept
Return const pointer to null-terminated contents.
void reserve(size_type __res_arg)
Attempt to preallocate enough memory for specified number of characters.
size_type size() const noexcept
Returns the number of characters in the string, not including any null-termination.
const _CharT * data() const noexcept
Return const pointer to contents.
bool empty() const noexcept
static const size_type npos
Value returned by various member functions when they fail.
Traits class for iterators.
Container class for localization functionality.
Struct for delimited strings.
Struct holding two objects of arbitrary type.
Bidirectional iterators support a superset of forward iterator operations.
Exception type thrown by the Filesystem TS library.
const char * what() const noexcept
An iterator for the components of a path.
A non-owning reference to a string.