]> git.proxmox.com Git - ceph.git/blame - ceph/src/boost/libs/beast/test/beast/core/file_test.hpp
bump version to 19.2.0-pve1
[ceph.git] / ceph / src / boost / libs / beast / test / beast / core / file_test.hpp
CommitLineData
b32b8144 1//
92f5a8d4 2// Copyright (c) 2016-2019 Vinnie Falco (vinnie dot falco at gmail dot com)
b32b8144
FG
3//
4// Distributed under the Boost Software License, Version 1.0. (See accompanying
5// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
6//
7// Official repository: https://github.com/boostorg/beast
8//
9
92f5a8d4
TL
10#ifndef BOOST_BEAST_FILE_TEST_HPP
11#define BOOST_BEAST_FILE_TEST_HPP
b32b8144 12
92f5a8d4
TL
13#include <boost/beast/_experimental/unit_test/suite.hpp>
14#include <boost/beast/core/string.hpp>
15#include <boost/beast/core/file_base.hpp>
16#include <boost/filesystem/path.hpp>
17#include <boost/filesystem/operations.hpp>
f67539c2 18#include <boost/filesystem/fstream.hpp>
92f5a8d4 19#include <cstdio>
1e59de90 20#include <fstream>
b32b8144 21#include <string>
1e59de90 22#include <iterator>
92f5a8d4 23#include <type_traits>
b32b8144
FG
24
25namespace boost {
26namespace beast {
27
f67539c2 28template<class File, bool append_unicode_suffix = false>
b32b8144 29void
92f5a8d4 30test_file()
b32b8144 31{
92f5a8d4
TL
32 BOOST_STATIC_ASSERT(
33 is_file<File>::value);
34 BOOST_STATIC_ASSERT(
35 ! std::is_copy_constructible<File>::value);
36 BOOST_STATIC_ASSERT(
37 ! std::is_copy_assignable<File>::value);
b32b8144 38
92f5a8d4 39 namespace fs = boost::filesystem;
b32b8144 40
f67539c2
TL
41 static constexpr
42#ifdef _WIN32
43 boost::winapi::WCHAR_ unicode_suffix[] = { 0xd83e, 0xdd84, 0x0000 }; // UTF-16-LE unicorn
44#else
45 char unicode_suffix[] = { '\xf0', '\x9f', '\xa6', '\x84', '\x00' }; // UTF-8 unicorn
46#endif
47
92f5a8d4
TL
48 class temp_path
49 {
50 fs::path path_;
f67539c2 51 std::vector<char> utf8_str_;
92f5a8d4
TL
52
53 public:
54 temp_path()
55 : path_(fs::unique_path())
92f5a8d4 56 {
f67539c2
TL
57 if (append_unicode_suffix)
58 path_ += unicode_suffix;
59#ifdef _WIN32
60 constexpr auto cp = boost::winapi::CP_UTF8_;
61 constexpr auto flags = boost::winapi::WC_ERR_INVALID_CHARS_;
62 auto sz = boost::winapi::WideCharToMultiByte(
63 cp, flags, path_.c_str(), -1, nullptr, 0,
64 nullptr, nullptr);
65 BEAST_EXPECT(sz != 0);
66 utf8_str_.resize(sz);
67 auto ret = boost::winapi::WideCharToMultiByte(
68 cp, flags, path_.c_str(), -1,
69 utf8_str_.data(), sz,
70 nullptr, nullptr);
71 BEAST_EXPECT(ret == sz);
72#endif
92f5a8d4
TL
73 }
74
75 operator fs::path const&()
76 {
77 return path_;
78 }
79
80 operator char const*()
81 {
f67539c2
TL
82#ifdef _WIN32
83 return utf8_str_.data();
84#else
85 return path_.c_str();
86#endif
92f5a8d4
TL
87 }
88 };
89
90 auto const create =
1e59de90 91 [](fs::path const& path, std::string const& data = "")
92f5a8d4 92 {
92f5a8d4 93 BEAST_EXPECT(! fs::exists(path));
f67539c2
TL
94 fs::ofstream out(path);
95 BEAST_EXPECT(out.is_open());
1e59de90
TL
96 if (data.size())
97 out.write(data.c_str(), data.size());
92f5a8d4
TL
98 };
99
100 auto const remove =
101 [](fs::path const& path)
102 {
103 fs::remove(path);
f67539c2 104 BEAST_EXPECT(! fs::exists(path));
92f5a8d4
TL
105 };
106
1e59de90
TL
107 auto const consume_file =
108 [](fs::path const& path)
109 {
110 // no exceptions - failure will result in an empty string
111 std::ifstream in;
112 in.open(path.native());
113 noskipws(in);
114 auto s = std::string(
115 std::istream_iterator<char>(in),
116 std::istream_iterator<char>());
117 in.close();
118 return s;
119 };
120
92f5a8d4
TL
121 temp_path path;
122
123 // bad file descriptor
124 {
125 File f;
126 char buf[1];
127 BEAST_EXPECT(! f.is_open());
128 BEAST_EXPECT(! fs::exists(path));
129 {
130 error_code ec;
131 f.size(ec);
132 BEAST_EXPECT(ec == errc::bad_file_descriptor);
133 }
134 {
135 error_code ec;
136 f.pos(ec);
137 BEAST_EXPECT(ec == errc::bad_file_descriptor);
138 }
139 {
140 error_code ec;
141 f.seek(0, ec);
142 BEAST_EXPECT(ec == errc::bad_file_descriptor);
143 }
144 {
145 error_code ec;
146 f.read(buf, 0, ec);
147 BEAST_EXPECT(ec == errc::bad_file_descriptor);
148 }
149 {
150 error_code ec;
151 f.write(buf, 0, ec);
152 BEAST_EXPECT(ec == errc::bad_file_descriptor);
153 }
154 }
155
156 // file_mode::read
157 {
158 {
159 File f;
160 error_code ec;
161 create(path);
162 f.open(path, file_mode::read, ec);
163 BEAST_EXPECT(! ec);
164 }
165 remove(path);
166 }
167
168 // file_mode::scan
169 {
170 {
171 File f;
172 error_code ec;
173 create(path);
174 f.open(path, file_mode::scan, ec);
175 BEAST_EXPECT(! ec);
176 }
177 remove(path);
178 }
179
180 // file_mode::write
181 {
182 {
183 File f;
184 error_code ec;
185 BEAST_EXPECT(! fs::exists(path));
186 f.open(path, file_mode::write, ec);
187 BEAST_EXPECT(! ec);
188 BEAST_EXPECT(fs::exists(path));
189 }
190 {
191 File f;
192 error_code ec;
193 BEAST_EXPECT(fs::exists(path));
194 f.open(path, file_mode::write, ec);
195 BEAST_EXPECT(! ec);
196 BEAST_EXPECT(fs::exists(path));
197 }
198 remove(path);
199 }
200
201 // file_mode::write_new
202 {
203 {
204 File f;
205 error_code ec;
206 BEAST_EXPECT(! fs::exists(path));
207 f.open(path, file_mode::write_new, ec);
208 BEAST_EXPECTS(! ec, ec.message());
209 BEAST_EXPECT(fs::exists(path));
210 }
211 {
212 File f;
213 error_code ec;
214 BEAST_EXPECT(fs::exists(path));
215 f.open(path, file_mode::write_new, ec);
216 BEAST_EXPECT(ec);
217 }
218 remove(path);
219 }
220
221 // file_mode::write_existing
222 {
223 {
224 File f;
225 error_code ec;
226 BEAST_EXPECT(! fs::exists(path));
227 f.open(path, file_mode::write_existing, ec);
228 BEAST_EXPECT(ec);
229 BEAST_EXPECT(! fs::exists(path));
230 }
231 {
232 File f;
233 error_code ec;
234 create(path);
235 BEAST_EXPECT(fs::exists(path));
236 f.open(path, file_mode::write_existing, ec);
237 BEAST_EXPECT(! ec);
238 }
239 remove(path);
240 }
241
242 // file_mode::append
243 {
244 {
245 File f;
246 error_code ec;
247 BEAST_EXPECT(! fs::exists(path));
248 f.open(path, file_mode::append, ec);
249 BEAST_EXPECT(! ec);
250 BEAST_EXPECT(fs::exists(path));
1e59de90
TL
251 static const std::string extra = "the";
252 f.write(extra.c_str(), extra.size(), ec);
253 BEAST_EXPECT(!ec);
254 f.close(ec);
255 auto s = consume_file(path);
256 BEAST_EXPECT(s == "the");
92f5a8d4 257 }
1e59de90 258
92f5a8d4
TL
259 {
260 File f;
261 error_code ec;
262 BEAST_EXPECT(fs::exists(path));
263 f.open(path, file_mode::append, ec);
264 BEAST_EXPECT(! ec);
265 BEAST_EXPECT(fs::exists(path));
1e59de90
TL
266 static const std::string extra = " cat";
267 f.write(extra.c_str(), extra.size(), ec);
268 BEAST_EXPECT(!ec);
269 f.close(ec);
270 auto s = consume_file(path);
271 BEAST_EXPECTS(s == "the cat", s);
92f5a8d4
TL
272 }
273 remove(path);
274 }
275
276 // file_mode::append_existing
277 {
278 {
279 File f;
280 error_code ec;
281 BEAST_EXPECT(! fs::exists(path));
282 f.open(path, file_mode::append_existing, ec);
283 BEAST_EXPECT(ec);
284 BEAST_EXPECT(! fs::exists(path));
285 }
286 remove(path);
287 {
288 File f;
289 error_code ec;
1e59de90 290 create(path, "the cat");
92f5a8d4
TL
291 f.open(path, file_mode::append_existing, ec);
292 BEAST_EXPECT(! ec);
1e59de90
TL
293 static std::string const extra = " sat";
294 f.write(extra.c_str(), extra.size(), ec);
295 BEAST_EXPECT(!ec);
296 f.close(ec);
297 BEAST_EXPECT(!ec);
298 auto s = consume_file(path);
299 BEAST_EXPECTS(s == "the cat sat", s);
92f5a8d4
TL
300 }
301 remove(path);
302 }
303
304 // special members
b32b8144
FG
305 {
306 {
307 File f1;
92f5a8d4
TL
308 error_code ec;
309 f1.open(path, file_mode::write, ec);
310 BEAST_EXPECT(! ec);
311 BEAST_EXPECT(f1.is_open());
312
313 // move constructor
314 File f2(std::move(f1));
315 BEAST_EXPECT(! f1.is_open());
316 BEAST_EXPECT(f2.is_open());
317
318 // move assignment
b32b8144
FG
319 File f3;
320 f3 = std::move(f2);
92f5a8d4
TL
321 BEAST_EXPECT(! f2.is_open());
322 BEAST_EXPECT(f3.is_open());
323 }
324 remove(path);
b32b8144
FG
325 }
326
92f5a8d4
TL
327 // re-open
328 {
329 {
330 File f;
331 error_code ec;
332 f.open(path, file_mode::write, ec);
333 BEAST_EXPECT(! ec);
334 f.open(path, file_mode::write, ec);
335 BEAST_EXPECT(! ec);
336 }
337 remove(path);
338 }
b32b8144 339
92f5a8d4
TL
340 // re-assign
341 {
342 temp_path path2;
343 {
344 error_code ec;
b32b8144 345
92f5a8d4
TL
346 File f1;
347 f1.open(path, file_mode::write, ec);
348 BEAST_EXPECT(! ec);
b32b8144 349
92f5a8d4
TL
350 File f2;
351 f2.open(path2, file_mode::write, ec);
352 BEAST_EXPECT(! ec);
b32b8144 353
92f5a8d4
TL
354 f2 = std::move(f1);
355 BEAST_EXPECT(! f1.is_open());
356 BEAST_EXPECT(f2.is_open());
357 }
358 remove(path);
359 remove(path2);
360 }
b32b8144 361
92f5a8d4
TL
362 // self-move
363 {
364 {
365 File f;
366 error_code ec;
367 f.open(path, file_mode::write, ec);
368 BEAST_EXPECT(! ec);
369 f = std::move(f);
370 BEAST_EXPECT(f.is_open());
371 }
372 remove(path);
373 }
b32b8144 374
92f5a8d4
TL
375 // native_handle
376 {
377 {
378 File f;
379 auto none = f.native_handle();
380 error_code ec;
381 f.open(path, file_mode::write, ec);
382 BEAST_EXPECT(! ec);
383 auto fd = f.native_handle();
384 BEAST_EXPECT(fd != none);
385 f.native_handle(none);
386 BEAST_EXPECT(! f.is_open());
387 }
388 remove(path);
389 }
b32b8144 390
92f5a8d4
TL
391 // read and write
392 {
393 string_view const s = "Hello, world!";
b32b8144 394
92f5a8d4
TL
395 // write
396 {
397 File f;
398 error_code ec;
399 f.open(path, file_mode::write, ec);
400 BEAST_EXPECT(! ec);
b32b8144 401
92f5a8d4
TL
402 f.write(s.data(), s.size(), ec);
403 BEAST_EXPECT(! ec);
b32b8144 404
92f5a8d4
TL
405 auto size = f.size(ec);
406 BEAST_EXPECT(! ec);
407 BEAST_EXPECT(size == s.size());
b32b8144 408
92f5a8d4
TL
409 auto pos = f.pos(ec);
410 BEAST_EXPECT(! ec);
411 BEAST_EXPECT(pos == size);
b32b8144 412
92f5a8d4
TL
413 f.close(ec);
414 BEAST_EXPECT(! ec);
415 }
416
417 // read
418 {
419 File f;
420 error_code ec;
421 f.open(path, file_mode::read, ec);
422 BEAST_EXPECT(! ec);
b32b8144 423
92f5a8d4
TL
424 std::string buf;
425 buf.resize(s.size());
426 f.read(&buf[0], buf.size(), ec);
427 BEAST_EXPECT(! ec);
428 BEAST_EXPECT(buf == s);
b32b8144 429
92f5a8d4
TL
430 f.seek(1, ec);
431 BEAST_EXPECT(! ec);
432 buf.resize(3);
433 f.read(&buf[0], buf.size(), ec);
434 BEAST_EXPECT(! ec);
435 BEAST_EXPECT(buf == "ell");
b32b8144 436
92f5a8d4
TL
437 auto pos = f.pos(ec);
438 BEAST_EXPECT(! ec);
439 BEAST_EXPECT(pos == 4);
440 }
441 remove(path);
442 }
b32b8144 443
92f5a8d4 444 BEAST_EXPECT(! fs::exists(path));
b32b8144
FG
445}
446
447} // beast
448} // boost
449
450#endif