1 | // -*- C++ -*- |
2 | //===----------------------------------------------------------------------===// |
3 | // |
4 | // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. |
5 | // See https://llvm.org/LICENSE.txt for license information. |
6 | // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception |
7 | // |
8 | //===----------------------------------------------------------------------===// |
9 | |
10 | #ifndef _LIBCPP___FILESYSTEM_PATH_ITERATOR_H |
11 | #define _LIBCPP___FILESYSTEM_PATH_ITERATOR_H |
12 | |
13 | #include <__assert> |
14 | #include <__config> |
15 | #include <__filesystem/path.h> |
16 | #include <__iterator/iterator_traits.h> |
17 | |
18 | #if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER) |
19 | # pragma GCC system_header |
20 | #endif |
21 | |
22 | #if _LIBCPP_STD_VER >= 17 |
23 | |
24 | _LIBCPP_BEGIN_NAMESPACE_FILESYSTEM |
25 | |
26 | class _LIBCPP_EXPORTED_FROM_ABI path::iterator { |
27 | public: |
28 | enum _ParserState : unsigned char { |
29 | _Singular, |
30 | _BeforeBegin, |
31 | _InRootName, |
32 | _InRootDir, |
33 | _InFilenames, |
34 | _InTrailingSep, |
35 | _AtEnd |
36 | }; |
37 | |
38 | public: |
39 | typedef input_iterator_tag iterator_category; |
40 | typedef bidirectional_iterator_tag iterator_concept; |
41 | |
42 | typedef path value_type; |
43 | typedef ptrdiff_t difference_type; |
44 | typedef const path* pointer; |
45 | typedef path reference; |
46 | |
47 | public: |
48 | _LIBCPP_HIDE_FROM_ABI iterator() : __stashed_elem_(), __path_ptr_(nullptr), __entry_(), __state_(_Singular) {} |
49 | |
50 | _LIBCPP_HIDE_FROM_ABI iterator(const iterator&) = default; |
51 | _LIBCPP_HIDE_FROM_ABI ~iterator() = default; |
52 | |
53 | _LIBCPP_HIDE_FROM_ABI iterator& operator=(const iterator&) = default; |
54 | |
55 | _LIBCPP_HIDE_FROM_ABI reference operator*() const { return __stashed_elem_; } |
56 | |
57 | _LIBCPP_HIDE_FROM_ABI pointer operator->() const { return &__stashed_elem_; } |
58 | |
59 | _LIBCPP_HIDE_FROM_ABI iterator& operator++() { |
60 | _LIBCPP_ASSERT_NON_NULL(__state_ != _Singular, "attempting to increment a singular iterator" ); |
61 | _LIBCPP_ASSERT_UNCATEGORIZED(__state_ != _AtEnd, "attempting to increment the end iterator" ); |
62 | return __increment(); |
63 | } |
64 | |
65 | _LIBCPP_HIDE_FROM_ABI iterator operator++(int) { |
66 | iterator __it(*this); |
67 | this->operator++(); |
68 | return __it; |
69 | } |
70 | |
71 | _LIBCPP_HIDE_FROM_ABI iterator& operator--() { |
72 | _LIBCPP_ASSERT_NON_NULL(__state_ != _Singular, "attempting to decrement a singular iterator" ); |
73 | _LIBCPP_ASSERT_UNCATEGORIZED( |
74 | __entry_.data() != __path_ptr_->native().data(), "attempting to decrement the begin iterator" ); |
75 | return __decrement(); |
76 | } |
77 | |
78 | _LIBCPP_HIDE_FROM_ABI iterator operator--(int) { |
79 | iterator __it(*this); |
80 | this->operator--(); |
81 | return __it; |
82 | } |
83 | |
84 | private: |
85 | friend class path; |
86 | |
87 | inline _LIBCPP_HIDE_FROM_ABI friend bool operator==(const iterator&, const iterator&); |
88 | |
89 | iterator& __increment(); |
90 | iterator& __decrement(); |
91 | |
92 | path __stashed_elem_; |
93 | const path* __path_ptr_; |
94 | path::__string_view __entry_; |
95 | _ParserState __state_; |
96 | }; |
97 | |
98 | _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY |
99 | inline _LIBCPP_HIDE_FROM_ABI bool operator==(const path::iterator& __lhs, const path::iterator& __rhs) { |
100 | return __lhs.__path_ptr_ == __rhs.__path_ptr_ && __lhs.__entry_.data() == __rhs.__entry_.data(); |
101 | } |
102 | |
103 | _LIBCPP_AVAILABILITY_FILESYSTEM_LIBRARY |
104 | inline _LIBCPP_HIDE_FROM_ABI bool operator!=(const path::iterator& __lhs, const path::iterator& __rhs) { |
105 | return !(__lhs == __rhs); |
106 | } |
107 | |
108 | _LIBCPP_END_NAMESPACE_FILESYSTEM |
109 | |
110 | #endif // _LIBCPP_STD_VER >= 17 |
111 | |
112 | #endif // _LIBCPP___FILESYSTEM_PATH_ITERATOR_H |
113 | |