]> git.proxmox.com Git - ceph.git/blob - ceph/src/boost/libs/spirit/include/boost/spirit/home/classic/iterator/file_iterator.hpp
bump version to 12.2.2-pve1
[ceph.git] / ceph / src / boost / libs / spirit / include / boost / spirit / home / classic / iterator / file_iterator.hpp
1 /*=============================================================================
2 Copyright (c) 2003 Giovanni Bajo
3 Copyright (c) 2003 Thomas Witt
4 Copyright (c) 2003 Hartmut Kaiser
5 http://spirit.sourceforge.net/
6
7 Distributed under the Boost Software License, Version 1.0. (See accompanying
8 file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
9 =============================================================================*/
10
11 ///////////////////////////////////////////////////////////////////////////////
12 //
13 // File Iterator structure
14 //
15 // The new structure is designed on layers. The top class (used by the user)
16 // is file_iterator, which implements a full random access iterator through
17 // the file, and some specific member functions (constructor that opens
18 // the file, make_end() to generate the end iterator, operator bool to check
19 // if the file was opened correctly).
20 //
21 // file_iterator implements the random access iterator interface by the means
22 // of boost::iterator_adaptor, that is inhering an object created with it.
23 // iterator_adaptor gets a low-level file iterator implementation (with just
24 // a few member functions) and a policy (that basically describes to it how
25 // the low-level file iterator interface is). The advantage is that
26 // with boost::iterator_adaptor only 5 functions are needed to implement
27 // a fully conformant random access iterator, instead of dozens of functions
28 // and operators.
29 //
30 // There are two low-level file iterators implemented in this module. The
31 // first (std_file_iterator) uses cstdio stream functions (fopen/fread), which
32 // support full buffering, and is available everywhere (it's standard C++).
33 // The second (mmap_file_iterator) is currently available only on Windows
34 // platforms, and uses memory mapped files, which gives a decent speed boost.
35 //
36 ///////////////////////////////////////////////////////////////////////////////
37 //
38 // TODO LIST:
39 //
40 // - In the Win32 mmap iterator, we could check if keeping a handle to the
41 // opened file is really required. If it's not, we can just store the file
42 // length (for make_end()) and save performance. Notice that this should be
43 // tested under different Windows versions, the behaviour might change.
44 // - Add some error support (by the means of some exceptions) in case of
45 // low-level I/O failure.
46 //
47 ///////////////////////////////////////////////////////////////////////////////
48
49 #ifndef BOOST_SPIRIT_FILE_ITERATOR_HPP
50 #define BOOST_SPIRIT_FILE_ITERATOR_HPP
51
52 #include <string>
53 #include <boost/config.hpp>
54 #include <boost/iterator_adaptors.hpp>
55 #include <boost/spirit/home/classic/namespace.hpp>
56 #include <boost/spirit/home/classic/core/safe_bool.hpp>
57
58 #include <boost/spirit/home/classic/iterator/file_iterator_fwd.hpp>
59
60 #if !defined(BOOST_SPIRIT_FILEITERATOR_STD)
61 # if (defined(WIN32) || defined(_WIN32) || defined(__WIN32__)) \
62 && !defined(BOOST_DISABLE_WIN32)
63 # define BOOST_SPIRIT_FILEITERATOR_WINDOWS
64 # elif defined(BOOST_HAS_UNISTD_H)
65 extern "C"
66 {
67 # include <unistd.h>
68 }
69 # ifdef _POSIX_MAPPED_FILES
70 # define BOOST_SPIRIT_FILEITERATOR_POSIX
71 # endif // _POSIX_MAPPED_FILES
72 # endif // BOOST_HAS_UNISTD_H
73
74 # if !defined(BOOST_SPIRIT_FILEITERATOR_WINDOWS) && \
75 !defined(BOOST_SPIRIT_FILEITERATOR_POSIX)
76 # define BOOST_SPIRIT_FILEITERATOR_STD
77 # endif
78 #endif // BOOST_SPIRIT_FILEITERATOR_STD
79
80 ///////////////////////////////////////////////////////////////////////////////
81 namespace boost { namespace spirit {
82
83 BOOST_SPIRIT_CLASSIC_NAMESPACE_BEGIN
84
85 template <
86 typename CharT = char,
87 typename BaseIterator =
88 #ifdef BOOST_SPIRIT_FILEITERATOR_STD
89 fileiter_impl::std_file_iterator<CharT>
90 #else
91 fileiter_impl::mmap_file_iterator<CharT>
92 #endif
93 > class file_iterator;
94
95 ///////////////////////////////////////////////////////////////////////////////
96 namespace fileiter_impl {
97
98 /////////////////////////////////////////////////////////////////////////
99 //
100 // file_iter_generator
101 //
102 // Template meta-function to invoke boost::iterator_adaptor
103 // NOTE: This cannot be moved into the implementation file because of
104 // a bug of MSVC 7.0 and previous versions (base classes types are
105 // looked up at compilation time, not instantion types, and
106 // file_iterator would break).
107 //
108 /////////////////////////////////////////////////////////////////////////
109
110 #if !defined(BOOST_ITERATOR_ADAPTORS_VERSION) || \
111 BOOST_ITERATOR_ADAPTORS_VERSION < 0x0200
112 #error "Please use at least Boost V1.31.0 while compiling the file_iterator class!"
113 #else // BOOST_ITERATOR_ADAPTORS_VERSION < 0x0200
114
115 template <typename CharT, typename BaseIteratorT>
116 struct file_iter_generator
117 {
118 public:
119 typedef BaseIteratorT adapted_t;
120 typedef typename adapted_t::value_type value_type;
121
122 typedef boost::iterator_adaptor <
123 file_iterator<CharT, BaseIteratorT>,
124 adapted_t,
125 value_type const,
126 std::random_access_iterator_tag,
127 boost::use_default,
128 std::ptrdiff_t
129 > type;
130 };
131
132 #endif // BOOST_ITERATOR_ADAPTORS_VERSION < 0x0200
133
134 ///////////////////////////////////////////////////////////////////////////////
135 } /* namespace impl */
136
137
138 ///////////////////////////////////////////////////////////////////////////////
139 //
140 // file_iterator
141 //
142 // Iterates through an opened file.
143 //
144 // The main iterator interface is implemented by the iterator_adaptors
145 // library, which wraps a conforming iterator interface around the
146 // impl::BaseIterator class. This class merely derives the iterator_adaptors
147 // generated class to implement the custom constructors and make_end()
148 // member function.
149 //
150 ///////////////////////////////////////////////////////////////////////////////
151
152 template<typename CharT, typename BaseIteratorT>
153 class file_iterator
154 : public fileiter_impl::file_iter_generator<CharT, BaseIteratorT>::type,
155 public safe_bool<file_iterator<CharT, BaseIteratorT> >
156 {
157 private:
158 typedef typename
159 fileiter_impl::file_iter_generator<CharT, BaseIteratorT>::type
160 base_t;
161 typedef typename
162 fileiter_impl::file_iter_generator<CharT, BaseIteratorT>::adapted_t
163 adapted_t;
164
165 public:
166 file_iterator()
167 {}
168
169 file_iterator(std::string const& fileName)
170 : base_t(adapted_t(fileName))
171 {}
172
173 file_iterator(const base_t& iter)
174 : base_t(iter)
175 {}
176
177 inline file_iterator& operator=(const base_t& iter);
178 file_iterator make_end(void);
179
180 // operator bool. This borrows a trick from boost::shared_ptr to avoid
181 // to interfere with arithmetic operations.
182 bool operator_bool(void) const
183 { return this->base(); }
184
185 private:
186 friend class ::boost::iterator_core_access;
187
188 typename base_t::reference dereference() const
189 {
190 return this->base_reference().get_cur_char();
191 }
192
193 void increment()
194 {
195 this->base_reference().next_char();
196 }
197
198 void decrement()
199 {
200 this->base_reference().prev_char();
201 }
202
203 void advance(typename base_t::difference_type n)
204 {
205 this->base_reference().advance(n);
206 }
207
208 template <
209 typename OtherDerivedT, typename OtherIteratorT,
210 typename V, typename C, typename R, typename D
211 >
212 typename base_t::difference_type distance_to(
213 iterator_adaptor<OtherDerivedT, OtherIteratorT, V, C, R, D>
214 const &x) const
215 {
216 return x.base().distance(this->base_reference());
217 }
218 };
219
220 ///////////////////////////////////////////////////////////////////////////////
221 BOOST_SPIRIT_CLASSIC_NAMESPACE_END
222
223 }} /* namespace BOOST_SPIRIT_CLASSIC_NS */
224
225 ///////////////////////////////////////////////////////////////////////////////
226 #include <boost/spirit/home/classic/iterator/impl/file_iterator.ipp> /* implementation */
227
228 #endif /* BOOST_SPIRIT_FILE_ITERATOR_HPP */
229