]> git.proxmox.com Git - ceph.git/blob - ceph/src/boost/libs/asio/test/execution/schedule.cpp
import quincy beta 17.1.0
[ceph.git] / ceph / src / boost / libs / asio / test / execution / schedule.cpp
1 //
2 // schedule.cpp
3 // ~~~~~~~~~~~~
4 //
5 // Copyright (c) 2003-2020 Christopher M. Kohlhoff (chris at kohlhoff dot com)
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 // Disable autolinking for unit tests.
12 #if !defined(BOOST_ALL_NO_LIB)
13 #define BOOST_ALL_NO_LIB 1
14 #endif // !defined(BOOST_ALL_NO_LIB)
15
16 // Test that header file is self-contained.
17 #include <boost/asio/execution/schedule.hpp>
18
19 #include <boost/system/error_code.hpp>
20 #include <boost/asio/execution/sender.hpp>
21 #include <boost/asio/execution/submit.hpp>
22 #include <boost/asio/traits/connect_member.hpp>
23 #include <boost/asio/traits/start_member.hpp>
24 #include <boost/asio/traits/submit_member.hpp>
25 #include "../unit_test.hpp"
26
27 namespace exec = boost::asio::execution;
28
29 struct operation_state
30 {
31 void start() BOOST_ASIO_NOEXCEPT
32 {
33 }
34 };
35
36 namespace boost {
37 namespace asio {
38 namespace traits {
39
40 #if !defined(BOOST_ASIO_HAS_DEDUCED_START_MEMBER_TRAIT)
41
42 template <>
43 struct start_member<operation_state>
44 {
45 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_valid = true);
46 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_noexcept = true);
47 typedef void result_type;
48 };
49
50 #endif // !defined(BOOST_ASIO_HAS_DEDUCED_START_MEMBER_TRAIT)
51
52 } // namespace traits
53 } // namespace asio
54 } // namespace boost
55
56 struct sender : exec::sender_base
57 {
58 sender()
59 {
60 }
61
62 template <typename R>
63 operation_state connect(BOOST_ASIO_MOVE_ARG(R) r) const
64 {
65 (void)r;
66 return operation_state();
67 }
68
69 template <typename R>
70 void submit(BOOST_ASIO_MOVE_ARG(R) r) const
71 {
72 typename boost::asio::decay<R>::type tmp(BOOST_ASIO_MOVE_CAST(R)(r));
73 exec::set_value(tmp);
74 }
75 };
76
77 namespace boost {
78 namespace asio {
79 namespace traits {
80
81 #if !defined(BOOST_ASIO_HAS_DEDUCED_CONNECT_MEMBER_TRAIT)
82
83 template <typename R>
84 struct connect_member<const sender, R>
85 {
86 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_valid = true);
87 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_noexcept = false);
88 typedef operation_state result_type;
89 };
90
91 #endif // !defined(BOOST_ASIO_HAS_DEDUCED_CONNECT_MEMBER_TRAIT)
92
93 #if !defined(BOOST_ASIO_HAS_DEDUCED_SUBMIT_MEMBER_TRAIT)
94
95 template <typename R>
96 struct submit_member<const sender, R>
97 {
98 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_valid = true);
99 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_noexcept = false);
100 typedef void result_type;
101 };
102
103 #endif // !defined(BOOST_ASIO_HAS_DEDUCED_SUBMIT_MEMBER_TRAIT)
104
105 } // namespace traits
106 } // namespace asio
107 } // namespace boost
108
109 struct no_schedule
110 {
111 };
112
113 struct const_member_schedule
114 {
115 sender schedule() const BOOST_ASIO_NOEXCEPT
116 {
117 return sender();
118 }
119 };
120
121 #if !defined(BOOST_ASIO_HAS_DEDUCED_SCHEDULE_MEMBER_TRAIT)
122
123 namespace boost {
124 namespace asio {
125 namespace traits {
126
127 template <>
128 struct schedule_member<const const_member_schedule>
129 {
130 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_valid = true);
131 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_noexcept = true);
132 typedef sender result_type;
133 };
134
135 } // namespace traits
136 } // namespace asio
137 } // namespace boost
138
139 #endif // !defined(BOOST_ASIO_HAS_DEDUCED_SCHEDULE_MEMBER_TRAIT)
140
141 struct free_schedule_const_receiver
142 {
143 friend sender schedule(
144 const free_schedule_const_receiver&) BOOST_ASIO_NOEXCEPT
145 {
146 return sender();
147 }
148 };
149
150 #if !defined(BOOST_ASIO_HAS_DEDUCED_SCHEDULE_FREE_TRAIT)
151
152 namespace boost {
153 namespace asio {
154 namespace traits {
155
156 template <>
157 struct schedule_free<const free_schedule_const_receiver>
158 {
159 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_valid = true);
160 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_noexcept = true);
161 typedef sender result_type;
162 };
163
164 } // namespace traits
165 } // namespace asio
166 } // namespace boost
167
168 #endif // !defined(BOOST_ASIO_HAS_DEDUCED_SCHEDULE_FREE_TRAIT)
169
170 struct non_const_member_schedule
171 {
172 sender schedule() BOOST_ASIO_NOEXCEPT
173 {
174 return sender();
175 }
176 };
177
178 #if !defined(BOOST_ASIO_HAS_DEDUCED_SCHEDULE_MEMBER_TRAIT)
179
180 namespace boost {
181 namespace asio {
182 namespace traits {
183
184 template <>
185 struct schedule_member<non_const_member_schedule>
186 {
187 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_valid = true);
188 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_noexcept = true);
189 typedef sender result_type;
190 };
191
192 } // namespace traits
193 } // namespace asio
194 } // namespace boost
195
196 #endif // !defined(BOOST_ASIO_HAS_DEDUCED_SCHEDULE_MEMBER_TRAIT)
197
198 struct free_schedule_non_const_receiver
199 {
200 friend sender schedule(
201 free_schedule_non_const_receiver&) BOOST_ASIO_NOEXCEPT
202 {
203 return sender();
204 }
205 };
206
207 #if !defined(BOOST_ASIO_HAS_DEDUCED_SCHEDULE_FREE_TRAIT)
208
209 namespace boost {
210 namespace asio {
211 namespace traits {
212
213 template <>
214 struct schedule_free<free_schedule_non_const_receiver>
215 {
216 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_valid = true);
217 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_noexcept = true);
218 typedef sender result_type;
219 };
220
221 } // namespace traits
222 } // namespace asio
223 } // namespace boost
224
225 #endif // !defined(BOOST_ASIO_HAS_DEDUCED_SCHEDULE_FREE_TRAIT)
226
227 struct executor
228 {
229 executor()
230 {
231 }
232
233 executor(const executor&) BOOST_ASIO_NOEXCEPT
234 {
235 }
236
237 #if defined(BOOST_ASIO_HAS_MOVE)
238 executor(executor&&) BOOST_ASIO_NOEXCEPT
239 {
240 }
241 #endif // defined(BOOST_ASIO_HAS_MOVE)
242
243 template <typename F>
244 void execute(BOOST_ASIO_MOVE_ARG(F) f) const BOOST_ASIO_NOEXCEPT
245 {
246 typename boost::asio::decay<F>::type tmp(BOOST_ASIO_MOVE_CAST(F)(f));
247 tmp();
248 }
249
250 bool operator==(const executor&) const BOOST_ASIO_NOEXCEPT
251 {
252 return true;
253 }
254
255 bool operator!=(const executor&) const BOOST_ASIO_NOEXCEPT
256 {
257 return false;
258 }
259 };
260
261 namespace boost {
262 namespace asio {
263 namespace traits {
264
265 #if !defined(BOOST_ASIO_HAS_DEDUCED_EXECUTE_MEMBER_TRAIT)
266
267 template <typename F>
268 struct execute_member<executor, F>
269 {
270 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_valid = true);
271 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_noexcept = true);
272 typedef void result_type;
273 };
274
275 #endif // !defined(BOOST_ASIO_HAS_DEDUCED_SET_ERROR_MEMBER_TRAIT)
276 #if !defined(BOOST_ASIO_HAS_DEDUCED_EQUALITY_COMPARABLE_TRAIT)
277
278 template <>
279 struct equality_comparable<executor>
280 {
281 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_valid = true);
282 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_noexcept = true);
283 };
284
285 #endif // !defined(BOOST_ASIO_HAS_DEDUCED_EQUALITY_COMPARABLE_TRAIT)
286
287 } // namespace traits
288 } // namespace asio
289 } // namespace boost
290
291 void test_can_schedule()
292 {
293 BOOST_ASIO_CONSTEXPR bool b1 = exec::can_schedule<
294 no_schedule&>::value;
295 BOOST_ASIO_CHECK(b1 == false);
296
297 BOOST_ASIO_CONSTEXPR bool b2 = exec::can_schedule<
298 const no_schedule&>::value;
299 BOOST_ASIO_CHECK(b2 == false);
300
301 BOOST_ASIO_CONSTEXPR bool b3 = exec::can_schedule<
302 const_member_schedule&>::value;
303 BOOST_ASIO_CHECK(b3 == true);
304
305 BOOST_ASIO_CONSTEXPR bool b4 = exec::can_schedule<
306 const const_member_schedule&>::value;
307 BOOST_ASIO_CHECK(b4 == true);
308
309 BOOST_ASIO_CONSTEXPR bool b5 = exec::can_schedule<
310 free_schedule_const_receiver&>::value;
311 BOOST_ASIO_CHECK(b5 == true);
312
313 BOOST_ASIO_CONSTEXPR bool b6 = exec::can_schedule<
314 const free_schedule_const_receiver&>::value;
315 BOOST_ASIO_CHECK(b6 == true);
316
317 BOOST_ASIO_CONSTEXPR bool b7 = exec::can_schedule<
318 non_const_member_schedule&>::value;
319 BOOST_ASIO_CHECK(b7 == true);
320
321 BOOST_ASIO_CONSTEXPR bool b8 = exec::can_schedule<
322 const non_const_member_schedule&>::value;
323 BOOST_ASIO_CHECK(b8 == false);
324
325 BOOST_ASIO_CONSTEXPR bool b9 = exec::can_schedule<
326 free_schedule_non_const_receiver&>::value;
327 BOOST_ASIO_CHECK(b9 == true);
328
329 BOOST_ASIO_CONSTEXPR bool b10 = exec::can_schedule<
330 const free_schedule_non_const_receiver&>::value;
331 BOOST_ASIO_CHECK(b10 == false);
332
333 BOOST_ASIO_CONSTEXPR bool b11 = exec::can_schedule<
334 executor&>::value;
335 BOOST_ASIO_CHECK(b11 == true);
336
337 BOOST_ASIO_CONSTEXPR bool b12 = exec::can_schedule<
338 const executor&>::value;
339 BOOST_ASIO_CHECK(b12 == true);
340 }
341
342 struct receiver
343 {
344 int* count_;
345
346 receiver(int* count)
347 : count_(count)
348 {
349 }
350
351 receiver(const receiver& other) BOOST_ASIO_NOEXCEPT
352 : count_(other.count_)
353 {
354 }
355
356 #if defined(BOOST_ASIO_HAS_MOVE)
357 receiver(receiver&& other) BOOST_ASIO_NOEXCEPT
358 : count_(other.count_)
359 {
360 other.count_ = 0;
361 }
362 #endif // defined(BOOST_ASIO_HAS_MOVE)
363
364 void set_value() BOOST_ASIO_NOEXCEPT
365 {
366 ++(*count_);
367 }
368
369 template <typename E>
370 void set_error(BOOST_ASIO_MOVE_ARG(E) e) BOOST_ASIO_NOEXCEPT
371 {
372 (void)e;
373 }
374
375 void set_done() BOOST_ASIO_NOEXCEPT
376 {
377 }
378 };
379
380 namespace boost {
381 namespace asio {
382 namespace traits {
383
384 #if !defined(BOOST_ASIO_HAS_DEDUCED_SET_VALUE_MEMBER_TRAIT)
385
386 template <>
387 struct set_value_member<receiver, void()>
388 {
389 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_valid = true);
390 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_noexcept = true);
391 typedef void result_type;
392 };
393
394 #endif // !defined(BOOST_ASIO_HAS_DEDUCED_SET_VALUE_MEMBER_TRAIT)
395
396 #if !defined(BOOST_ASIO_HAS_DEDUCED_SET_ERROR_MEMBER_TRAIT)
397
398 template <typename E>
399 struct set_error_member<receiver, E>
400 {
401 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_valid = true);
402 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_noexcept = true);
403 typedef void result_type;
404 };
405
406 #endif // !defined(BOOST_ASIO_HAS_DEDUCED_SET_ERROR_MEMBER_TRAIT)
407
408 #if !defined(BOOST_ASIO_HAS_DEDUCED_SET_DONE_MEMBER_TRAIT)
409
410 template <>
411 struct set_done_member<receiver>
412 {
413 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_valid = true);
414 BOOST_ASIO_STATIC_CONSTEXPR(bool, is_noexcept = true);
415 typedef void result_type;
416 };
417
418 #endif // !defined(BOOST_ASIO_HAS_DEDUCED_SET_DONE_MEMBER_TRAIT)
419
420 } // namespace traits
421 } // namespace asio
422 } // namespace boost
423
424 void test_schedule()
425 {
426 int count = 0;
427 const_member_schedule ex1 = {};
428 exec::submit(
429 exec::schedule(ex1),
430 receiver(&count));
431 BOOST_ASIO_CHECK(count == 1);
432
433 count = 0;
434 const const_member_schedule ex2 = {};
435 exec::submit(
436 exec::schedule(ex2),
437 receiver(&count));
438 BOOST_ASIO_CHECK(count == 1);
439
440 count = 0;
441 exec::submit(
442 exec::schedule(const_member_schedule()),
443 receiver(&count));
444 BOOST_ASIO_CHECK(count == 1);
445
446 count = 0;
447 free_schedule_const_receiver ex3 = {};
448 exec::submit(
449 exec::schedule(ex3),
450 receiver(&count));
451 BOOST_ASIO_CHECK(count == 1);
452
453 count = 0;
454 const free_schedule_const_receiver ex4 = {};
455 exec::submit(
456 exec::schedule(ex4),
457 receiver(&count));
458 BOOST_ASIO_CHECK(count == 1);
459
460 count = 0;
461 exec::submit(
462 exec::schedule(free_schedule_const_receiver()),
463 receiver(&count));
464 BOOST_ASIO_CHECK(count == 1);
465
466 count = 0;
467 non_const_member_schedule ex5 = {};
468 exec::submit(
469 exec::schedule(ex5),
470 receiver(&count));
471 BOOST_ASIO_CHECK(count == 1);
472
473 count = 0;
474 free_schedule_non_const_receiver ex6 = {};
475 exec::submit(
476 exec::schedule(ex6),
477 receiver(&count));
478 BOOST_ASIO_CHECK(count == 1);
479
480 count = 0;
481 executor ex7;
482 exec::submit(
483 exec::schedule(ex7),
484 receiver(&count));
485 BOOST_ASIO_CHECK(count == 1);
486
487 count = 0;
488 const executor ex8;
489 exec::submit(
490 exec::schedule(ex8),
491 receiver(&count));
492 BOOST_ASIO_CHECK(count == 1);
493
494 count = 0;
495 exec::submit(
496 exec::schedule(executor()),
497 receiver(&count));
498 BOOST_ASIO_CHECK(count == 1);
499 }
500
501 BOOST_ASIO_TEST_SUITE
502 (
503 "schedule",
504 BOOST_ASIO_TEST_CASE(test_can_schedule)
505 BOOST_ASIO_TEST_CASE(test_schedule)
506 )