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 thread_specific.hpp
9 * \author Andrey Semashev
10 * \date 01.03.2008
11 *
12 * \brief This header is the Boost.Log library implementation, see the library documentation
13 * at http://www.boost.org/doc/libs/release/libs/log/doc/html/index.html.
14 */
15
16#ifndef BOOST_LOG_DETAIL_THREAD_SPECIFIC_HPP_INCLUDED_
17#define BOOST_LOG_DETAIL_THREAD_SPECIFIC_HPP_INCLUDED_
18
19#include <boost/type_traits/is_pod.hpp>
20#include <boost/log/detail/config.hpp>
21
22#ifdef BOOST_HAS_PRAGMA_ONCE
23#pragma once
24#endif
25
26#if !defined(BOOST_LOG_NO_THREADS)
27
28#include <boost/log/detail/header.hpp>
29
30namespace boost {
31
32BOOST_LOG_OPEN_NAMESPACE
33
34namespace aux {
35
36//! Base class for TLS to hide platform-specific storage management
37class thread_specific_base
38{
39private:
40#if defined(BOOST_THREAD_PLATFORM_WIN32)
41 typedef unsigned long key_storage;
42#else
43 typedef void* key_storage;
44#endif
45
46 key_storage m_Key;
47
48protected:
49 BOOST_LOG_API thread_specific_base();
50 BOOST_LOG_API ~thread_specific_base();
51 BOOST_LOG_API void* get_content() const;
52 BOOST_LOG_API void set_content(void* value) const;
53
54 // Copying prohibited
55 BOOST_DELETED_FUNCTION(thread_specific_base(thread_specific_base const&))
56 BOOST_DELETED_FUNCTION(thread_specific_base& operator= (thread_specific_base const&))
57};
58
59//! A TLS wrapper for small POD types with least possible overhead
60template< typename T >
61class thread_specific :
62 public thread_specific_base
63{
64 static_assert(sizeof(T) <= sizeof(void*) && is_pod< T >::value, "Boost.Log: Thread-specific values must be PODs and must not exceed the size of a pointer");
65
66 //! Union to perform type casting
67 union value_storage
68 {
69 void* as_pointer;
70 T as_value;
71 };
72
73public:
74 //! Default constructor
75 BOOST_DEFAULTED_FUNCTION(thread_specific(), {})
76 //! Initializing constructor
77 thread_specific(T const& value)
78 {
79 set(value);
80 }
81 //! Assignment
82 thread_specific& operator= (T const& value)
83 {
84 set(value);
85 return *this;
86 }
87
88 //! Accessor
89 T get() const
90 {
91 value_storage cast = {};
92 cast.as_pointer = thread_specific_base::get_content();
93 return cast.as_value;
94 }
95
96 //! Setter
97 void set(T const& value)
98 {
99 value_storage cast = {};
100 cast.as_value = value;
101 thread_specific_base::set_content(cast.as_pointer);
102 }
103};
104
105} // namespace aux
106
107BOOST_LOG_CLOSE_NAMESPACE // namespace log
108
109} // namespace boost
110
111#include <boost/log/detail/footer.hpp>
112
113#endif // !defined(BOOST_LOG_NO_THREADS)
114
115#endif // BOOST_LOG_DETAIL_THREAD_SPECIFIC_HPP_INCLUDED_
116

source code of boost/libs/log/include/boost/log/detail/thread_specific.hpp