1 // 2 // io_context.hpp 3 // ~~~~~~~~~~~~~~ 4 // 5 // Copyright (c) 2003-2017 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 #ifndef ASIO_IO_CONTEXT_HPP 12 #define ASIO_IO_CONTEXT_HPP 13 14 #if defined(_MSC_VER) && (_MSC_VER >= 1200) 15 # pragma once 16 #endif // defined(_MSC_VER) && (_MSC_VER >= 1200) 17 18 #include "asio/detail/config.hpp" 19 #include <cstddef> 20 #include <stdexcept> 21 #include <typeinfo> 22 #include "asio/async_result.hpp" 23 #include "asio/detail/noncopyable.hpp" 24 #include "asio/detail/wrapped_handler.hpp" 25 #include "asio/error_code.hpp" 26 #include "asio/execution_context.hpp" 27 28 #if defined(ASIO_HAS_CHRONO) 29 # include "asio/detail/chrono.hpp" 30 #endif // defined(ASIO_HAS_CHRONO) 31 32 #if defined(ASIO_WINDOWS) || defined(__CYGWIN__) 33 # include "asio/detail/winsock_init.hpp" 34 #elif defined(__sun) || defined(__QNX__) || defined(__hpux) || defined(_AIX) \ 35 || defined(__osf__) 36 # include "asio/detail/signal_init.hpp" 37 #endif 38 39 #include "asio/detail/push_options.hpp" 40 41 namespace asio { 42 43 namespace detail { 44 #if defined(ASIO_HAS_IOCP) 45 typedef class win_iocp_io_context io_context_impl; 46 class win_iocp_overlapped_ptr; 47 #else 48 typedef class scheduler io_context_impl; 49 #endif 50 } // namespace detail 51 52 /// Provides core I/O functionality. 53 /** 54 * The io_context class provides the core I/O functionality for users of the 55 * asynchronous I/O objects, including: 56 * 57 * @li asio::ip::tcp::socket 58 * @li asio::ip::tcp::acceptor 59 * @li asio::ip::udp::socket 60 * @li asio::deadline_timer. 61 * 62 * The io_context class also includes facilities intended for developers of 63 * custom asynchronous services. 64 * 65 * @par Thread Safety 66 * @e Distinct @e objects: Safe.@n 67 * @e Shared @e objects: Safe, with the specific exceptions of the restart() 68 * and notify_fork() functions. Calling restart() while there are unfinished 69 * run(), run_one(), run_for(), run_until(), poll() or poll_one() calls results 70 * in undefined behaviour. The notify_fork() function should not be called 71 * while any io_context function, or any function on an I/O object that is 72 * associated with the io_context, is being called in another thread. 73 * 74 * @par Concepts: 75 * Dispatcher. 76 * 77 * @par Synchronous and asynchronous operations 78 * 79 * Synchronous operations on I/O objects implicitly run the io_context object 80 * for an individual operation. The io_context functions run(), run_one(), 81 * run_for(), run_until(), poll() or poll_one() must be called for the 82 * io_context to perform asynchronous operations on behalf of a C++ program. 83 * Notification that an asynchronous operation has completed is delivered by 84 * invocation of the associated handler. Handlers are invoked only by a thread 85 * that is currently calling any overload of run(), run_one(), run_for(), 86 * run_until(), poll() or poll_one() for the io_context. 87 * 88 * @par Effect of exceptions thrown from handlers 89 * 90 * If an exception is thrown from a handler, the exception is allowed to 91 * propagate through the throwing thread's invocation of run(), run_one(), 92 * run_for(), run_until(), poll() or poll_one(). No other threads that are 93 * calling any of these functions are affected. It is then the responsibility 94 * of the application to catch the exception. 95 * 96 * After the exception has been caught, the run(), run_one(), run_for(), 97 * run_until(), poll() or poll_one() call may be restarted @em without the need 98 * for an intervening call to restart(). This allows the thread to rejoin the 99 * io_context object's thread pool without impacting any other threads in the 100 * pool. 101 * 102 * For example: 103 * 104 * @code 105 * asio::io_context io_context; 106 * ... 107 * for (;;) 108 * { 109 * try 110 * { 111 * io_context.run(); 112 * break; // run() exited normally 113 * } 114 * catch (my_exception& e) 115 * { 116 * // Deal with exception as appropriate. 117 * } 118 * } 119 * @endcode 120 * 121 * @par Stopping the io_context from running out of work 122 * 123 * Some applications may need to prevent an io_context object's run() call from 124 * returning when there is no more work to do. For example, the io_context may 125 * be being run in a background thread that is launched prior to the 126 * application's asynchronous operations. The run() call may be kept running by 127 * creating an object of type 128 * asio::executor_work_guard<io_context::executor_type>: 129 * 130 * @code asio::io_context io_context; 131 * asio::executor_work_guard<asio::io_context::executor_type> 132 * = asio::make_work_guard(io_context); 133 * ... @endcode 134 * 135 * To effect a shutdown, the application will then need to call the io_context 136 * object's stop() member function. This will cause the io_context run() call 137 * to return as soon as possible, abandoning unfinished operations and without 138 * permitting ready handlers to be dispatched. 139 * 140 * Alternatively, if the application requires that all operations and handlers 141 * be allowed to finish normally, the work object may be explicitly reset. 142 * 143 * @code asio::io_context io_context; 144 * asio::executor_work_guard<asio::io_context::executor_type> 145 * = asio::make_work_guard(io_context); 146 * ... 147 * work.reset(); // Allow run() to exit. @endcode 148 */ 149 class io_context 150 : public execution_context 151 { 152 private: 153 typedef detail::io_context_impl impl_type; 154 #if defined(ASIO_HAS_IOCP) 155 friend class detail::win_iocp_overlapped_ptr; 156 #endif 157 158 public: 159 class executor_type; 160 friend class executor_type; 161 162 #if !defined(ASIO_NO_DEPRECATED) 163 class work; 164 friend class work; 165 #endif // !defined(ASIO_NO_DEPRECATED) 166 167 class service; 168 169 #if !defined(ASIO_NO_EXTENSIONS) 170 class strand; 171 #endif // !defined(ASIO_NO_EXTENSIONS) 172 173 /// The type used to count the number of handlers executed by the context. 174 typedef std::size_t count_type; 175 176 /// Constructor. 177 ASIO_DECL io_context(); 178 179 /// Constructor. 180 /** 181 * Construct with a hint about the required level of concurrency. 182 * 183 * @param concurrency_hint A suggestion to the implementation on how many 184 * threads it should allow to run simultaneously. 185 */ 186 ASIO_DECL explicit io_context(int concurrency_hint); 187 188 /// Destructor. 189 /** 190 * On destruction, the io_context performs the following sequence of 191 * operations: 192 * 193 * @li For each service object @c svc in the io_context set, in reverse order 194 * of the beginning of service object lifetime, performs 195 * @c svc->shutdown(). 196 * 197 * @li Uninvoked handler objects that were scheduled for deferred invocation 198 * on the io_context, or any associated strand, are destroyed. 199 * 200 * @li For each service object @c svc in the io_context set, in reverse order 201 * of the beginning of service object lifetime, performs 202 * <tt>delete static_cast<io_context::service*>(svc)</tt>. 203 * 204 * @note The destruction sequence described above permits programs to 205 * simplify their resource management by using @c shared_ptr<>. Where an 206 * object's lifetime is tied to the lifetime of a connection (or some other 207 * sequence of asynchronous operations), a @c shared_ptr to the object would 208 * be bound into the handlers for all asynchronous operations associated with 209 * it. This works as follows: 210 * 211 * @li When a single connection ends, all associated asynchronous operations 212 * complete. The corresponding handler objects are destroyed, and all 213 * @c shared_ptr references to the objects are destroyed. 214 * 215 * @li To shut down the whole program, the io_context function stop() is 216 * called to terminate any run() calls as soon as possible. The io_context 217 * destructor defined above destroys all handlers, causing all @c shared_ptr 218 * references to all connection objects to be destroyed. 219 */ 220 ASIO_DECL ~io_context(); 221 222 /// Obtains the executor associated with the io_context. 223 executor_type get_executor() ASIO_NOEXCEPT; 224 225 /// Run the io_context object's event processing loop. 226 /** 227 * The run() function blocks until all work has finished and there are no 228 * more handlers to be dispatched, or until the io_context has been stopped. 229 * 230 * Multiple threads may call the run() function to set up a pool of threads 231 * from which the io_context may execute handlers. All threads that are 232 * waiting in the pool are equivalent and the io_context may choose any one 233 * of them to invoke a handler. 234 * 235 * A normal exit from the run() function implies that the io_context object 236 * is stopped (the stopped() function returns @c true). Subsequent calls to 237 * run(), run_one(), poll() or poll_one() will return immediately unless there 238 * is a prior call to restart(). 239 * 240 * @return The number of handlers that were executed. 241 * 242 * @note Calling the run() function from a thread that is currently calling 243 * one of run(), run_one(), run_for(), run_until(), poll() or poll_one() on 244 * the same io_context object may introduce the potential for deadlock. It is 245 * the caller's reponsibility to avoid this. 246 * 247 * The poll() function may also be used to dispatch ready handlers, but 248 * without blocking. 249 */ 250 ASIO_DECL count_type run(); 251 252 #if !defined(ASIO_NO_DEPRECATED) 253 /// (Deprecated: Use non-error_code overload.) Run the io_context object's 254 /// event processing loop. 255 /** 256 * The run() function blocks until all work has finished and there are no 257 * more handlers to be dispatched, or until the io_context has been stopped. 258 * 259 * Multiple threads may call the run() function to set up a pool of threads 260 * from which the io_context may execute handlers. All threads that are 261 * waiting in the pool are equivalent and the io_context may choose any one 262 * of them to invoke a handler. 263 * 264 * A normal exit from the run() function implies that the io_context object 265 * is stopped (the stopped() function returns @c true). Subsequent calls to 266 * run(), run_one(), poll() or poll_one() will return immediately unless there 267 * is a prior call to restart(). 268 * 269 * @param ec Set to indicate what error occurred, if any. 270 * 271 * @return The number of handlers that were executed. 272 * 273 * @note Calling the run() function from a thread that is currently calling 274 * one of run(), run_one(), run_for(), run_until(), poll() or poll_one() on 275 * the same io_context object may introduce the potential for deadlock. It is 276 * the caller's reponsibility to avoid this. 277 * 278 * The poll() function may also be used to dispatch ready handlers, but 279 * without blocking. 280 */ 281 ASIO_DECL count_type run(asio::error_code& ec); 282 #endif // !defined(ASIO_NO_DEPRECATED) 283 284 #if defined(ASIO_HAS_CHRONO) || defined(GENERATING_DOCUMENTATION) 285 /// Run the io_context object's event processing loop for a specified 286 /// duration. 287 /** 288 * The run_for() function blocks until all work has finished and there are no 289 * more handlers to be dispatched, until the io_context has been stopped, or 290 * until the specified duration has elapsed. 291 * 292 * @param rel_time The duration for which the call may block. 293 * 294 * @return The number of handlers that were executed. 295 */ 296 template <typename Rep, typename Period> 297 std::size_t run_for(const chrono::duration<Rep, Period>& rel_time); 298 299 /// Run the io_context object's event processing loop until a specified time. 300 /** 301 * The run_until() function blocks until all work has finished and there are 302 * no more handlers to be dispatched, until the io_context has been stopped, 303 * or until the specified time has been reached. 304 * 305 * @param abs_time The time point until which the call may block. 306 * 307 * @return The number of handlers that were executed. 308 */ 309 template <typename Clock, typename Duration> 310 std::size_t run_until(const chrono::time_point<Clock, Duration>& abs_time); 311 #endif // defined(ASIO_HAS_CHRONO) || defined(GENERATING_DOCUMENTATION) 312 313 /// Run the io_context object's event processing loop to execute at most one 314 /// handler. 315 /** 316 * The run_one() function blocks until one handler has been dispatched, or 317 * until the io_context has been stopped. 318 * 319 * @return The number of handlers that were executed. A zero return value 320 * implies that the io_context object is stopped (the stopped() function 321 * returns @c true). Subsequent calls to run(), run_one(), poll() or 322 * poll_one() will return immediately unless there is a prior call to 323 * restart(). 324 * 325 * @note Calling the run_one() function from a thread that is currently 326 * calling one of run(), run_one(), run_for(), run_until(), poll() or 327 * poll_one() on the same io_context object may introduce the potential for 328 * deadlock. It is the caller's reponsibility to avoid this. 329 */ 330 ASIO_DECL count_type run_one(); 331 332 #if !defined(ASIO_NO_DEPRECATED) 333 /// (Deprecated: Use non-error_code overlaod.) Run the io_context object's 334 /// event processing loop to execute at most one handler. 335 /** 336 * The run_one() function blocks until one handler has been dispatched, or 337 * until the io_context has been stopped. 338 * 339 * @return The number of handlers that were executed. A zero return value 340 * implies that the io_context object is stopped (the stopped() function 341 * returns @c true). Subsequent calls to run(), run_one(), poll() or 342 * poll_one() will return immediately unless there is a prior call to 343 * restart(). 344 * 345 * @return The number of handlers that were executed. 346 * 347 * @note Calling the run_one() function from a thread that is currently 348 * calling one of run(), run_one(), run_for(), run_until(), poll() or 349 * poll_one() on the same io_context object may introduce the potential for 350 * deadlock. It is the caller's reponsibility to avoid this. 351 */ 352 ASIO_DECL count_type run_one(asio::error_code& ec); 353 #endif // !defined(ASIO_NO_DEPRECATED) 354 355 #if defined(ASIO_HAS_CHRONO) || defined(GENERATING_DOCUMENTATION) 356 /// Run the io_context object's event processing loop for a specified duration 357 /// to execute at most one handler. 358 /** 359 * The run_one_for() function blocks until one handler has been dispatched, 360 * until the io_context has been stopped, or until the specified duration has 361 * elapsed. 362 * 363 * @param rel_time The duration for which the call may block. 364 * 365 * @return The number of handlers that were executed. 366 */ 367 template <typename Rep, typename Period> 368 std::size_t run_one_for(const chrono::duration<Rep, Period>& rel_time); 369 370 /// Run the io_context object's event processing loop until a specified time 371 /// to execute at most one handler. 372 /** 373 * The run_one_until() function blocks until one handler has been dispatched, 374 * until the io_context has been stopped, or until the specified time has 375 * been reached. 376 * 377 * @param abs_time The time point until which the call may block. 378 * 379 * @return The number of handlers that were executed. 380 */ 381 template <typename Clock, typename Duration> 382 std::size_t run_one_until( 383 const chrono::time_point<Clock, Duration>& abs_time); 384 #endif // defined(ASIO_HAS_CHRONO) || defined(GENERATING_DOCUMENTATION) 385 386 /// Run the io_context object's event processing loop to execute ready 387 /// handlers. 388 /** 389 * The poll() function runs handlers that are ready to run, without blocking, 390 * until the io_context has been stopped or there are no more ready handlers. 391 * 392 * @return The number of handlers that were executed. 393 */ 394 ASIO_DECL count_type poll(); 395 396 #if !defined(ASIO_NO_DEPRECATED) 397 /// (Deprecated: Use non-error_code overload.) Run the io_context object's 398 /// event processing loop to execute ready handlers. 399 /** 400 * The poll() function runs handlers that are ready to run, without blocking, 401 * until the io_context has been stopped or there are no more ready handlers. 402 * 403 * @param ec Set to indicate what error occurred, if any. 404 * 405 * @return The number of handlers that were executed. 406 */ 407 ASIO_DECL count_type poll(asio::error_code& ec); 408 #endif // !defined(ASIO_NO_DEPRECATED) 409 410 /// Run the io_context object's event processing loop to execute one ready 411 /// handler. 412 /** 413 * The poll_one() function runs at most one handler that is ready to run, 414 * without blocking. 415 * 416 * @return The number of handlers that were executed. 417 */ 418 ASIO_DECL count_type poll_one(); 419 420 #if !defined(ASIO_NO_DEPRECATED) 421 /// (Deprecated: Use non-error_code overload.) Run the io_context object's 422 /// event processing loop to execute one ready handler. 423 /** 424 * The poll_one() function runs at most one handler that is ready to run, 425 * without blocking. 426 * 427 * @param ec Set to indicate what error occurred, if any. 428 * 429 * @return The number of handlers that were executed. 430 */ 431 ASIO_DECL count_type poll_one(asio::error_code& ec); 432 #endif // !defined(ASIO_NO_DEPRECATED) 433 434 /// Stop the io_context object's event processing loop. 435 /** 436 * This function does not block, but instead simply signals the io_context to 437 * stop. All invocations of its run() or run_one() member functions should 438 * return as soon as possible. Subsequent calls to run(), run_one(), poll() 439 * or poll_one() will return immediately until restart() is called. 440 */ 441 ASIO_DECL void stop(); 442 443 /// Determine whether the io_context object has been stopped. 444 /** 445 * This function is used to determine whether an io_context object has been 446 * stopped, either through an explicit call to stop(), or due to running out 447 * of work. When an io_context object is stopped, calls to run(), run_one(), 448 * poll() or poll_one() will return immediately without invoking any 449 * handlers. 450 * 451 * @return @c true if the io_context object is stopped, otherwise @c false. 452 */ 453 ASIO_DECL bool stopped() const; 454 455 /// Restart the io_context in preparation for a subsequent run() invocation. 456 /** 457 * This function must be called prior to any second or later set of 458 * invocations of the run(), run_one(), poll() or poll_one() functions when a 459 * previous invocation of these functions returned due to the io_context 460 * being stopped or running out of work. After a call to restart(), the 461 * io_context object's stopped() function will return @c false. 462 * 463 * This function must not be called while there are any unfinished calls to 464 * the run(), run_one(), poll() or poll_one() functions. 465 */ 466 ASIO_DECL void restart(); 467 468 #if !defined(ASIO_NO_DEPRECATED) 469 /// (Deprecated: Use restart().) Reset the io_context in preparation for a 470 /// subsequent run() invocation. 471 /** 472 * This function must be called prior to any second or later set of 473 * invocations of the run(), run_one(), poll() or poll_one() functions when a 474 * previous invocation of these functions returned due to the io_context 475 * being stopped or running out of work. After a call to restart(), the 476 * io_context object's stopped() function will return @c false. 477 * 478 * This function must not be called while there are any unfinished calls to 479 * the run(), run_one(), poll() or poll_one() functions. 480 */ 481 void reset(); 482 483 /// (Deprecated: Use asio::dispatch().) Request the io_context to 484 /// invoke the given handler. 485 /** 486 * This function is used to ask the io_context to execute the given handler. 487 * 488 * The io_context guarantees that the handler will only be called in a thread 489 * in which the run(), run_one(), poll() or poll_one() member functions is 490 * currently being invoked. The handler may be executed inside this function 491 * if the guarantee can be met. 492 * 493 * @param handler The handler to be called. The io_context will make 494 * a copy of the handler object as required. The function signature of the 495 * handler must be: @code void handler(); @endcode 496 * 497 * @note This function throws an exception only if: 498 * 499 * @li the handler's @c asio_handler_allocate function; or 500 * 501 * @li the handler's copy constructor 502 * 503 * throws an exception. 504 */ 505 template <typename CompletionHandler> 506 ASIO_INITFN_RESULT_TYPE(CompletionHandler, void ()) 507 dispatch(ASIO_MOVE_ARG(CompletionHandler) handler); 508 509 /// (Deprecated: Use asio::post().) Request the io_context to invoke 510 /// the given handler and return immediately. 511 /** 512 * This function is used to ask the io_context to execute the given handler, 513 * but without allowing the io_context to call the handler from inside this 514 * function. 515 * 516 * The io_context guarantees that the handler will only be called in a thread 517 * in which the run(), run_one(), poll() or poll_one() member functions is 518 * currently being invoked. 519 * 520 * @param handler The handler to be called. The io_context will make 521 * a copy of the handler object as required. The function signature of the 522 * handler must be: @code void handler(); @endcode 523 * 524 * @note This function throws an exception only if: 525 * 526 * @li the handler's @c asio_handler_allocate function; or 527 * 528 * @li the handler's copy constructor 529 * 530 * throws an exception. 531 */ 532 template <typename CompletionHandler> 533 ASIO_INITFN_RESULT_TYPE(CompletionHandler, void ()) 534 post(ASIO_MOVE_ARG(CompletionHandler) handler); 535 536 /// (Deprecated: Use asio::bind_executor().) Create a new handler that 537 /// automatically dispatches the wrapped handler on the io_context. 538 /** 539 * This function is used to create a new handler function object that, when 540 * invoked, will automatically pass the wrapped handler to the io_context 541 * object's dispatch function. 542 * 543 * @param handler The handler to be wrapped. The io_context will make a copy 544 * of the handler object as required. The function signature of the handler 545 * must be: @code void handler(A1 a1, ... An an); @endcode 546 * 547 * @return A function object that, when invoked, passes the wrapped handler to 548 * the io_context object's dispatch function. Given a function object with the 549 * signature: 550 * @code R f(A1 a1, ... An an); @endcode 551 * If this function object is passed to the wrap function like so: 552 * @code io_context.wrap(f); @endcode 553 * then the return value is a function object with the signature 554 * @code void g(A1 a1, ... An an); @endcode 555 * that, when invoked, executes code equivalent to: 556 * @code io_context.dispatch(boost::bind(f, a1, ... an)); @endcode 557 */ 558 template <typename Handler> 559 #if defined(GENERATING_DOCUMENTATION) 560 unspecified 561 #else 562 detail::wrapped_handler<io_context&, Handler> 563 #endif 564 wrap(Handler handler); 565 #endif // !defined(ASIO_NO_DEPRECATED) 566 567 private: 568 // Helper function to add the implementation. 569 ASIO_DECL impl_type& add_impl(impl_type* impl); 570 571 // Backwards compatible overload for use with services derived from 572 // io_context::service. 573 template <typename Service> 574 friend Service& use_service(io_context& ioc); 575 576 #if defined(ASIO_WINDOWS) || defined(__CYGWIN__) 577 detail::winsock_init<> init_; 578 #elif defined(__sun) || defined(__QNX__) || defined(__hpux) || defined(_AIX) \ 579 || defined(__osf__) 580 detail::signal_init<> init_; 581 #endif 582 583 // The implementation. 584 impl_type& impl_; 585 }; 586 587 /// Executor used to submit functions to an io_context. 588 class io_context::executor_type 589 { 590 public: 591 /// Obtain the underlying execution context. 592 io_context& context() const ASIO_NOEXCEPT; 593 594 /// Inform the io_context that it has some outstanding work to do. 595 /** 596 * This function is used to inform the io_context that some work has begun. 597 * This ensures that the io_context's run() and run_one() functions do not 598 * exit while the work is underway. 599 */ 600 void on_work_started() const ASIO_NOEXCEPT; 601 602 /// Inform the io_context that some work is no longer outstanding. 603 /** 604 * This function is used to inform the io_context that some work has 605 * finished. Once the count of unfinished work reaches zero, the io_context 606 * is stopped and the run() and run_one() functions may exit. 607 */ 608 void on_work_finished() const ASIO_NOEXCEPT; 609 610 /// Request the io_context to invoke the given function object. 611 /** 612 * This function is used to ask the io_context to execute the given function 613 * object. If the current thread is running the io_context, @c dispatch() 614 * executes the function before returning. Otherwise, the function will be 615 * scheduled to run on the io_context. 616 * 617 * @param f The function object to be called. The executor will make a copy 618 * of the handler object as required. The function signature of the function 619 * object must be: @code void function(); @endcode 620 * 621 * @param a An allocator that may be used by the executor to allocate the 622 * internal storage needed for function invocation. 623 */ 624 template <typename Function, typename Allocator> 625 void dispatch(ASIO_MOVE_ARG(Function) f, const Allocator& a) const; 626 627 /// Request the io_context to invoke the given function object. 628 /** 629 * This function is used to ask the io_context to execute the given function 630 * object. The function object will never be executed inside @c post(). 631 * Instead, it will be scheduled to run on the io_context. 632 * 633 * @param f The function object to be called. The executor will make a copy 634 * of the handler object as required. The function signature of the function 635 * object must be: @code void function(); @endcode 636 * 637 * @param a An allocator that may be used by the executor to allocate the 638 * internal storage needed for function invocation. 639 */ 640 template <typename Function, typename Allocator> 641 void post(ASIO_MOVE_ARG(Function) f, const Allocator& a) const; 642 643 /// Request the io_context to invoke the given function object. 644 /** 645 * This function is used to ask the io_context to execute the given function 646 * object. The function object will never be executed inside @c defer(). 647 * Instead, it will be scheduled to run on the io_context. 648 * 649 * If the current thread belongs to the io_context, @c defer() will delay 650 * scheduling the function object until the current thread returns control to 651 * the pool. 652 * 653 * @param f The function object to be called. The executor will make a copy 654 * of the handler object as required. The function signature of the function 655 * object must be: @code void function(); @endcode 656 * 657 * @param a An allocator that may be used by the executor to allocate the 658 * internal storage needed for function invocation. 659 */ 660 template <typename Function, typename Allocator> 661 void defer(ASIO_MOVE_ARG(Function) f, const Allocator& a) const; 662 663 /// Determine whether the io_context is running in the current thread. 664 /** 665 * @return @c true if the current thread is running the io_context. Otherwise 666 * returns @c false. 667 */ 668 bool running_in_this_thread() const ASIO_NOEXCEPT; 669 670 /// Compare two executors for equality. 671 /** 672 * Two executors are equal if they refer to the same underlying io_context. 673 */ operator ==(const executor_type & a,const executor_type & b)674 friend bool operator==(const executor_type& a, 675 const executor_type& b) ASIO_NOEXCEPT 676 { 677 return &a.io_context_ == &b.io_context_; 678 } 679 680 /// Compare two executors for inequality. 681 /** 682 * Two executors are equal if they refer to the same underlying io_context. 683 */ operator !=(const executor_type & a,const executor_type & b)684 friend bool operator!=(const executor_type& a, 685 const executor_type& b) ASIO_NOEXCEPT 686 { 687 return &a.io_context_ != &b.io_context_; 688 } 689 690 private: 691 friend class io_context; 692 693 // Constructor. executor_type(io_context & i)694 explicit executor_type(io_context& i) : io_context_(i) {} 695 696 // The underlying io_context. 697 io_context& io_context_; 698 }; 699 700 #if !defined(ASIO_NO_DEPRECATED) 701 /// (Deprecated: Use executor_work_guard.) Class to inform the io_context when 702 /// it has work to do. 703 /** 704 * The work class is used to inform the io_context when work starts and 705 * finishes. This ensures that the io_context object's run() function will not 706 * exit while work is underway, and that it does exit when there is no 707 * unfinished work remaining. 708 * 709 * The work class is copy-constructible so that it may be used as a data member 710 * in a handler class. It is not assignable. 711 */ 712 class io_context::work 713 { 714 public: 715 /// Constructor notifies the io_context that work is starting. 716 /** 717 * The constructor is used to inform the io_context that some work has begun. 718 * This ensures that the io_context object's run() function will not exit 719 * while the work is underway. 720 */ 721 explicit work(asio::io_context& io_context); 722 723 /// Copy constructor notifies the io_context that work is starting. 724 /** 725 * The constructor is used to inform the io_context that some work has begun. 726 * This ensures that the io_context object's run() function will not exit 727 * while the work is underway. 728 */ 729 work(const work& other); 730 731 /// Destructor notifies the io_context that the work is complete. 732 /** 733 * The destructor is used to inform the io_context that some work has 734 * finished. Once the count of unfinished work reaches zero, the io_context 735 * object's run() function is permitted to exit. 736 */ 737 ~work(); 738 739 /// Get the io_context associated with the work. 740 asio::io_context& get_io_context(); 741 742 /// (Deprecated: Use get_io_context().) Get the io_context associated with the 743 /// work. 744 asio::io_context& get_io_service(); 745 746 private: 747 // Prevent assignment. 748 void operator=(const work& other); 749 750 // The io_context implementation. 751 detail::io_context_impl& io_context_impl_; 752 }; 753 #endif // !defined(ASIO_NO_DEPRECATED) 754 755 /// Base class for all io_context services. 756 class io_context::service 757 : public execution_context::service 758 { 759 public: 760 /// Get the io_context object that owns the service. 761 asio::io_context& get_io_context(); 762 763 #if !defined(ASIO_NO_DEPRECATED) 764 /// Get the io_context object that owns the service. 765 asio::io_context& get_io_service(); 766 #endif // !defined(ASIO_NO_DEPRECATED) 767 768 private: 769 /// Destroy all user-defined handler objects owned by the service. 770 ASIO_DECL virtual void shutdown(); 771 772 #if !defined(ASIO_NO_DEPRECATED) 773 /// (Deprecated: Use shutdown().) Destroy all user-defined handler objects 774 /// owned by the service. 775 ASIO_DECL virtual void shutdown_service(); 776 #endif // !defined(ASIO_NO_DEPRECATED) 777 778 /// Handle notification of a fork-related event to perform any necessary 779 /// housekeeping. 780 /** 781 * This function is not a pure virtual so that services only have to 782 * implement it if necessary. The default implementation does nothing. 783 */ 784 ASIO_DECL virtual void notify_fork( 785 execution_context::fork_event event); 786 787 #if !defined(ASIO_NO_DEPRECATED) 788 /// (Deprecated: Use notify_fork().) Handle notification of a fork-related 789 /// event to perform any necessary housekeeping. 790 /** 791 * This function is not a pure virtual so that services only have to 792 * implement it if necessary. The default implementation does nothing. 793 */ 794 ASIO_DECL virtual void fork_service( 795 execution_context::fork_event event); 796 #endif // !defined(ASIO_NO_DEPRECATED) 797 798 protected: 799 /// Constructor. 800 /** 801 * @param owner The io_context object that owns the service. 802 */ 803 ASIO_DECL service(asio::io_context& owner); 804 805 /// Destructor. 806 ASIO_DECL virtual ~service(); 807 }; 808 809 namespace detail { 810 811 // Special service base class to keep classes header-file only. 812 template <typename Type> 813 class service_base 814 : public asio::io_context::service 815 { 816 public: 817 static asio::detail::service_id<Type> id; 818 819 // Constructor. service_base(asio::io_context & io_context)820 service_base(asio::io_context& io_context) 821 : asio::io_context::service(io_context) 822 { 823 } 824 }; 825 826 template <typename Type> 827 asio::detail::service_id<Type> service_base<Type>::id; 828 829 } // namespace detail 830 } // namespace asio 831 832 #include "asio/detail/pop_options.hpp" 833 834 #include "asio/impl/io_context.hpp" 835 #if defined(ASIO_HEADER_ONLY) 836 # include "asio/impl/io_context.ipp" 837 #endif // defined(ASIO_HEADER_ONLY) 838 839 // If both io_context.hpp and strand.hpp have been included, automatically 840 // include the header file needed for the io_context::strand class. 841 #if !defined(ASIO_NO_EXTENSIONS) 842 # if defined(ASIO_STRAND_HPP) 843 # include "asio/io_context_strand.hpp" 844 # endif // defined(ASIO_STRAND_HPP) 845 #endif // !defined(ASIO_NO_EXTENSIONS) 846 847 #endif // ASIO_IO_CONTEXT_HPP 848