1/*
2 * Copyright Andrey Semashev 2007 - 2015.
3 * Distributed under the Boost Software License, Version 1.0.
4 * (See accompanying file LICENSE_1_0.txt or copy at
5 * http://www.boost.org/LICENSE_1_0.txt)
6 */
7/*!
8 * \file unlocked_frontend.hpp
9 * \author Andrey Semashev
10 * \date 14.07.2009
11 *
12 * The header contains declaration of an unlocked sink frontend.
13 */
14
15#ifndef BOOST_LOG_SINKS_UNLOCKED_FRONTEND_HPP_INCLUDED_
16#define BOOST_LOG_SINKS_UNLOCKED_FRONTEND_HPP_INCLUDED_
17
18#include <boost/smart_ptr/shared_ptr.hpp>
19#include <boost/smart_ptr/make_shared_object.hpp>
20#include <boost/preprocessor/control/if.hpp>
21#include <boost/preprocessor/comparison/equal.hpp>
22#include <boost/log/detail/config.hpp>
23#include <boost/log/detail/parameter_tools.hpp>
24#include <boost/log/detail/fake_mutex.hpp>
25#include <boost/log/sinks/basic_sink_frontend.hpp>
26#include <boost/log/sinks/frontend_requirements.hpp>
27#include <boost/log/detail/header.hpp>
28
29#ifdef BOOST_HAS_PRAGMA_ONCE
30#pragma once
31#endif
32
33namespace boost {
34
35BOOST_LOG_OPEN_NAMESPACE
36
37namespace sinks {
38
39#ifndef BOOST_LOG_DOXYGEN_PASS
40
41#define BOOST_LOG_SINK_CTOR_FORWARD_INTERNAL_1(z, n, data)\
42 template< typename T0 >\
43 explicit unlocked_sink(T0 const& arg0, typename boost::log::aux::enable_if_named_parameters< T0, boost::log::aux::sfinae_dummy >::type = boost::log::aux::sfinae_dummy()) :\
44 base_type(false),\
45 m_pBackend(boost::make_shared< sink_backend_type >(arg0)) {}
46
47#define BOOST_LOG_SINK_CTOR_FORWARD_INTERNAL_N(z, n, data)\
48 template< BOOST_PP_ENUM_PARAMS_Z(z, n, typename T) >\
49 explicit unlocked_sink(BOOST_PP_ENUM_BINARY_PARAMS_Z(z, n, T, const& arg)) :\
50 base_type(false),\
51 m_pBackend(boost::make_shared< sink_backend_type >(BOOST_PP_ENUM_PARAMS_Z(z, n, arg))) {}
52
53#define BOOST_LOG_SINK_CTOR_FORWARD_INTERNAL(z, n, data)\
54 BOOST_PP_IF(BOOST_PP_EQUAL(n, 1), BOOST_LOG_SINK_CTOR_FORWARD_INTERNAL_1, BOOST_LOG_SINK_CTOR_FORWARD_INTERNAL_N)(z, n, data)
55
56#endif // BOOST_LOG_DOXYGEN_PASS
57
58/*!
59 * \brief Non-blocking logging sink frontend
60 *
61 * The sink frontend does not perform thread synchronization and
62 * simply passes logging records to the sink backend.
63 */
64template< typename SinkBackendT >
65class unlocked_sink :
66 public aux::make_sink_frontend_base< SinkBackendT >::type
67{
68 typedef typename aux::make_sink_frontend_base< SinkBackendT >::type base_type;
69
70public:
71 //! Sink implementation type
72 typedef SinkBackendT sink_backend_type;
73 //! \cond
74 static_assert(has_requirement< typename sink_backend_type::frontend_requirements, concurrent_feeding >::value, "Unlocked sink frontend is incompatible with the specified backend: thread synchronization requirements are not met");
75 //! \endcond
76
77 //! Type of pointer to the backend
78 typedef shared_ptr< sink_backend_type > locked_backend_ptr;
79
80private:
81 //! Pointer to the backend
82 const shared_ptr< sink_backend_type > m_pBackend;
83
84public:
85 /*!
86 * Default constructor. Constructs the sink backend instance.
87 * Requires the backend to be default-constructible.
88 */
89 unlocked_sink() :
90 base_type(false),
91 m_pBackend(boost::make_shared< sink_backend_type >())
92 {
93 }
94 /*!
95 * Constructor attaches user-constructed backend instance
96 *
97 * \param backend Pointer to the backend instance
98 *
99 * \pre \a backend is not \c NULL.
100 */
101 explicit unlocked_sink(shared_ptr< sink_backend_type > const& backend) :
102 base_type(false),
103 m_pBackend(backend)
104 {
105 }
106
107 /*!
108 * Constructor that passes arbitrary named parameters to the interprocess sink backend constructor.
109 * Refer to the backend documentation for the list of supported parameters.
110 */
111#ifndef BOOST_LOG_DOXYGEN_PASS
112 BOOST_LOG_PARAMETRIZED_CONSTRUCTORS_GEN(BOOST_LOG_SINK_CTOR_FORWARD_INTERNAL, ~)
113#else
114 template< typename... Args >
115 explicit unlocked_sink(Args&&... args);
116#endif
117
118 /*!
119 * Locking accessor to the attached backend.
120 *
121 * \note Does not do any actual locking, provided only for interface consistency
122 * with other frontends.
123 */
124 locked_backend_ptr locked_backend()
125 {
126 return m_pBackend;
127 }
128
129 /*!
130 * Passes the log record to the backend
131 */
132 void consume(record_view const& rec)
133 {
134 boost::log::aux::fake_mutex m;
135 base_type::feed_record(rec, m, *m_pBackend);
136 }
137
138 /*!
139 * The method performs flushing of any internal buffers that may hold log records. The method
140 * may take considerable time to complete and may block both the calling thread and threads
141 * attempting to put new records into the sink while this call is in progress.
142 */
143 void flush()
144 {
145 boost::log::aux::fake_mutex m;
146 base_type::flush_backend(m, *m_pBackend);
147 }
148};
149
150#undef BOOST_LOG_SINK_CTOR_FORWARD_INTERNAL_1
151#undef BOOST_LOG_SINK_CTOR_FORWARD_INTERNAL_N
152#undef BOOST_LOG_SINK_CTOR_FORWARD_INTERNAL
153
154} // namespace sinks
155
156BOOST_LOG_CLOSE_NAMESPACE // namespace log
157
158} // namespace boost
159
160#include <boost/log/detail/footer.hpp>
161
162#endif // BOOST_LOG_SINKS_UNLOCKED_FRONTEND_HPP_INCLUDED_
163

source code of boost/libs/log/include/boost/log/sinks/unlocked_frontend.hpp