1//
2// detail/handler_tracking.hpp
3// ~~~~~~~~~~~~~~~~~~~~~~~~~~~
4//
5// Copyright (c) 2003-2015 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_DETAIL_HANDLER_TRACKING_HPP
12#define ASIO_DETAIL_HANDLER_TRACKING_HPP
13
14
15#include "asio/detail/config.hpp"
16
17#if defined(ASIO_ENABLE_HANDLER_TRACKING)
18# include "asio/error_code.hpp"
19# include "asio/detail/cstdint.hpp"
20# include "asio/detail/static_mutex.hpp"
21# include "asio/detail/tss_ptr.hpp"
22#endif // defined(ASIO_ENABLE_HANDLER_TRACKING)
23
24#include "asio/detail/push_options.hpp"
25
26namespace asio {
27namespace detail {
28
29#if defined(ASIO_ENABLE_HANDLER_TRACKING)
30
31class handler_tracking
32{
33public:
34  class completion;
35
36  // Base class for objects containing tracked handlers.
37  class tracked_handler
38  {
39  private:
40    // Only the handler_tracking class will have access to the id.
41    friend class handler_tracking;
42    friend class completion;
43    uint64_t id_;
44
45  protected:
46    // Constructor initialises with no id.
47    tracked_handler() : id_(0) {}
48
49    // Prevent deletion through this type.
50    ~tracked_handler() {}
51  };
52
53  // Initialise the tracking system.
54  ASIO_DECL static void init();
55
56  // Record the creation of a tracked handler.
57  ASIO_DECL static void creation(tracked_handler* h,
58      const char* object_type, void* object, const char* op_name);
59
60  class completion
61  {
62  public:
63    // Constructor records that handler is to be invoked with no arguments.
64    ASIO_DECL explicit completion(tracked_handler* h);
65
66    // Destructor records only when an exception is thrown from the handler, or
67    // if the memory is being freed without the handler having been invoked.
68    ASIO_DECL ~completion();
69
70    // Records that handler is to be invoked with no arguments.
71    ASIO_DECL void invocation_begin();
72
73    // Records that handler is to be invoked with one arguments.
74    ASIO_DECL void invocation_begin(const asio::error_code& ec);
75
76    // Constructor records that handler is to be invoked with two arguments.
77    ASIO_DECL void invocation_begin(
78        const asio::error_code& ec, std::size_t bytes_transferred);
79
80    // Constructor records that handler is to be invoked with two arguments.
81    ASIO_DECL void invocation_begin(
82        const asio::error_code& ec, int signal_number);
83
84    // Constructor records that handler is to be invoked with two arguments.
85    ASIO_DECL void invocation_begin(
86        const asio::error_code& ec, const char* arg);
87
88    // Record that handler invocation has ended.
89    ASIO_DECL void invocation_end();
90
91  private:
92    friend class handler_tracking;
93    uint64_t id_;
94    bool invoked_;
95    completion* next_;
96  };
97
98  // Record an operation that affects pending handlers.
99  ASIO_DECL static void operation(const char* object_type,
100      void* object, const char* op_name);
101
102  // Write a line of output.
103  ASIO_DECL static void write_line(const char* format, ...);
104
105private:
106  struct tracking_state;
107  ASIO_DECL static tracking_state* get_state();
108};
109
110# define ASIO_INHERIT_TRACKED_HANDLER    : public asio::detail::handler_tracking::tracked_handler
111
112# define ASIO_ALSO_INHERIT_TRACKED_HANDLER    , public asio::detail::handler_tracking::tracked_handler
113
114# define ASIO_HANDLER_TRACKING_INIT    asio::detail::handler_tracking::init()
115
116# define ASIO_HANDLER_CREATION(args)    asio::detail::handler_tracking::creation args
117
118# define ASIO_HANDLER_COMPLETION(args)    asio::detail::handler_tracking::completion tracked_completion args
119
120# define ASIO_HANDLER_INVOCATION_BEGIN(args)    tracked_completion.invocation_begin args
121
122# define ASIO_HANDLER_INVOCATION_END    tracked_completion.invocation_end()
123
124# define ASIO_HANDLER_OPERATION(args)    asio::detail::handler_tracking::operation args
125
126#else // defined(ASIO_ENABLE_HANDLER_TRACKING)
127
128# define ASIO_INHERIT_TRACKED_HANDLER
129# define ASIO_ALSO_INHERIT_TRACKED_HANDLER
130# define ASIO_HANDLER_TRACKING_INIT (void)0
131# define ASIO_HANDLER_CREATION(args) (void)0
132# define ASIO_HANDLER_COMPLETION(args) (void)0
133# define ASIO_HANDLER_INVOCATION_BEGIN(args) (void)0
134# define ASIO_HANDLER_INVOCATION_END (void)0
135# define ASIO_HANDLER_OPERATION(args) (void)0
136
137#endif // defined(ASIO_ENABLE_HANDLER_TRACKING)
138
139} // namespace detail
140} // namespace asio
141
142#include "asio/detail/pop_options.hpp"
143
144# include "asio/detail/impl/handler_tracking.ipp"
145
146#endif // ASIO_DETAIL_HANDLER_TRACKING_HPP
147