1#ifndef BOOST_SYSTEM_DETAIL_ERROR_CATEGORY_HPP_INCLUDED
2#define BOOST_SYSTEM_DETAIL_ERROR_CATEGORY_HPP_INCLUDED
3
4// Copyright Beman Dawes 2006, 2007
5// Copyright Christoper Kohlhoff 2007
6// Copyright Peter Dimov 2017, 2018
7//
8// Distributed under the Boost Software License, Version 1.0. (See accompanying
9// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
10//
11// See library home page at http://www.boost.org/libs/system
12
13#include <boost/system/detail/config.hpp>
14#include <boost/cstdint.hpp>
15#include <boost/config.hpp>
16#include <boost/config/workaround.hpp>
17#include <string>
18#include <functional>
19#include <cstddef>
20#include <system_error>
21#include <atomic>
22
23namespace boost
24{
25
26namespace system
27{
28
29class error_category;
30class error_code;
31class error_condition;
32
33std::size_t hash_value( error_code const & ec );
34
35namespace detail
36{
37
38BOOST_SYSTEM_CONSTEXPR bool failed_impl( int ev, error_category const & cat );
39
40class std_category;
41
42} // namespace detail
43
44#if ( defined( BOOST_GCC ) && BOOST_GCC >= 40600 ) || defined( BOOST_CLANG )
45#pragma GCC diagnostic push
46#pragma GCC diagnostic ignored "-Wnon-virtual-dtor"
47#endif
48
49#if defined(BOOST_MSVC) && BOOST_MSVC < 1900
50#pragma warning(push)
51#pragma warning(disable: 4351) // new behavior: elements of array will be default initialized
52#endif
53
54class BOOST_SYMBOL_VISIBLE error_category
55{
56private:
57
58 friend std::size_t hash_value( error_code const & ec );
59 friend BOOST_SYSTEM_CONSTEXPR bool detail::failed_impl( int ev, error_category const & cat );
60
61 friend class error_code;
62 friend class error_condition;
63
64public:
65
66 error_category( error_category const & ) = delete;
67 error_category& operator=( error_category const & ) = delete;
68
69private:
70
71 boost::ulong_long_type id_;
72
73 static std::size_t const stdcat_size_ = 4 * sizeof( void const* );
74
75 union
76 {
77 mutable unsigned char stdcat_[ stdcat_size_ ];
78 void const* stdcat_align_;
79 };
80
81 mutable std::atomic< unsigned > sc_init_;
82
83protected:
84
85 ~error_category() = default;
86
87 constexpr error_category() noexcept: id_( 0 ), stdcat_(), sc_init_()
88 {
89 }
90
91 explicit constexpr error_category( boost::ulong_long_type id ) noexcept: id_( id ), stdcat_(), sc_init_()
92 {
93 }
94
95public:
96
97 virtual const char * name() const noexcept = 0;
98
99 virtual error_condition default_error_condition( int ev ) const noexcept;
100 virtual bool equivalent( int code, const error_condition & condition ) const noexcept;
101 virtual bool equivalent( const error_code & code, int condition ) const noexcept;
102
103 virtual std::string message( int ev ) const = 0;
104 virtual char const * message( int ev, char * buffer, std::size_t len ) const noexcept;
105
106 virtual bool failed( int ev ) const noexcept
107 {
108 return ev != 0;
109 }
110
111 friend BOOST_SYSTEM_CONSTEXPR bool operator==( error_category const & lhs, error_category const & rhs ) noexcept
112 {
113 return rhs.id_ == 0? &lhs == &rhs: lhs.id_ == rhs.id_;
114 }
115
116 friend BOOST_SYSTEM_CONSTEXPR bool operator!=( error_category const & lhs, error_category const & rhs ) noexcept
117 {
118 return !( lhs == rhs );
119 }
120
121 friend BOOST_SYSTEM_CONSTEXPR bool operator<( error_category const & lhs, error_category const & rhs ) noexcept
122 {
123 if( lhs.id_ < rhs.id_ )
124 {
125 return true;
126 }
127
128 if( lhs.id_ > rhs.id_ )
129 {
130 return false;
131 }
132
133 if( rhs.id_ != 0 )
134 {
135 return false; // equal
136 }
137
138 return std::less<error_category const *>()( &lhs, &rhs );
139 }
140
141 void init_stdcat() const;
142
143# if defined(__SUNPRO_CC) // trailing __global is not supported
144 operator std::error_category const & () const;
145# else
146 operator std::error_category const & () const BOOST_SYMBOL_VISIBLE;
147# endif
148};
149
150#if defined(BOOST_MSVC) && BOOST_MSVC < 1900
151#pragma warning(pop)
152#endif
153
154#if ( defined( BOOST_GCC ) && BOOST_GCC >= 40600 ) || defined( BOOST_CLANG )
155#pragma GCC diagnostic pop
156#endif
157
158namespace detail
159{
160
161static const boost::ulong_long_type generic_category_id = ( boost::ulong_long_type( 0xB2AB117A ) << 32 ) + 0x257EDFD0;
162static const boost::ulong_long_type system_category_id = generic_category_id + 1;
163static const boost::ulong_long_type interop_category_id = generic_category_id + 2;
164
165BOOST_SYSTEM_CONSTEXPR inline bool failed_impl( int ev, error_category const & cat )
166{
167 if( cat.id_ == system_category_id || cat.id_ == generic_category_id )
168 {
169 return ev != 0;
170 }
171 else
172 {
173 return cat.failed( ev );
174 }
175}
176
177} // namespace detail
178
179} // namespace system
180
181} // namespace boost
182
183#endif // #ifndef BOOST_SYSTEM_DETAIL_ERROR_CATEGORY_HPP_INCLUDED
184

source code of boost/libs/system/include/boost/system/detail/error_category.hpp