1 #ifndef BOOST_LEAF_TEST_EC_HPP_INCLUDED
2 #define BOOST_LEAF_TEST_EC_HPP_INCLUDED
3 
4 // Copyright (c) 2018-2020 Emil Dotchevski and Reverge Studios, Inc.
5 
6 // Distributed under the Boost Software License, Version 1.0. (See accompanying
7 // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
8 
9 #include <system_error>
10 
11 enum class errc_a { a0 = 10, a1, a2, a3 };
12 
13 namespace std { template <> struct is_error_code_enum<errc_a>: true_type { }; }
14 
cat_errc_a()15 inline std::error_category const & cat_errc_a()
16 {
17     class cat : public std::error_category
18     {
19         char const * name() const noexcept
20         {
21             return "errc_a";
22         }
23         std::string message(int code) const
24         {
25             switch( errc_a(code) )
26             {
27                 case errc_a::a0: return "a0";
28                 case errc_a::a1: return "a1";
29                 case errc_a::a2: return "a2";
30                 case errc_a::a3: return "a3";
31                 default: return "error";
32             }
33         }
34     };
35     static cat c;
36     return c;
37 }
38 
make_error_code(errc_a code)39 inline std::error_code make_error_code( errc_a code )
40 {
41     return std::error_code(int(code), cat_errc_a());
42 }
43 
44 template <int> struct e_errc_a { std::error_code value; };
45 
46 ///////////////////////////////////
47 
48 enum class errc_b { b0 = 20, b1, b2, b3 };
49 
50 namespace std { template <> struct is_error_code_enum<errc_b>: true_type { }; };
51 
cat_errc_b()52 inline std::error_category const & cat_errc_b()
53 {
54     class cat : public std::error_category
55     {
56         char const * name() const noexcept
57         {
58             return "errc_b";
59         }
60         std::string message(int code) const
61         {
62             switch( errc_b(code) )
63             {
64                 case errc_b::b0: return "b0";
65                 case errc_b::b1: return "b1";
66                 case errc_b::b2: return "b2";
67                 case errc_b::b3: return "b3";
68                 default: return "error";
69             }
70         }
71     };
72     static cat c;
73     return c;
74 }
75 
make_error_code(errc_b code)76 inline std::error_code make_error_code( errc_b code )
77 {
78     return std::error_code(int(code), cat_errc_b());
79 }
80 
81 template <int> struct e_errc_b { std::error_code value; };
82 
83 ///////////////////////////////////
84 
85 enum class cond_x { x00 = 30, x11, x22, x33 };
86 
87 namespace std { template <> struct is_error_condition_enum<cond_x>: true_type { }; };
88 
cat_cond_x()89 inline std::error_category const & cat_cond_x()
90 {
91     class cat : public std::error_category
92     {
93         char const * name() const noexcept
94         {
95             return "cond_x";
96         }
97         std::string message(int cond) const
98         {
99             switch( cond_x(cond) )
100             {
101                 case cond_x::x00:
102                     return "x00";
103                 case cond_x::x11:
104                     return "x11";
105                 case cond_x::x22:
106                     return "x22";
107                 case cond_x::x33:
108                     return "x33";
109                 default:
110                     return "error";
111             }
112         }
113         bool equivalent(std::error_code const & code, int cond) const noexcept
114         {
115             switch( cond_x(cond) )
116             {
117                 case cond_x::x00:
118                     return code==make_error_code(errc_a::a0) || code==make_error_code(errc_b::b0);
119                 case cond_x::x11:
120                     return code==make_error_code(errc_a::a1) || code==make_error_code(errc_b::b1);
121                 case cond_x::x22:
122                     return code==make_error_code(errc_a::a2) || code==make_error_code(errc_b::b2);
123                 case cond_x::x33:
124                     return code==make_error_code(errc_a::a3) || code==make_error_code(errc_b::b3);
125                 default:
126                     return false;
127             }
128         }
129     };
130     static cat c;
131     return c;
132 }
133 
make_error_condition(cond_x cond)134 inline std::error_condition make_error_condition( cond_x cond )
135 {
136     return std::error_condition(int(cond), cat_cond_x());
137 }
138 
139 template <int> struct e_cond_x { cond_x value; };
140 
141 ///////////////////////////////////
142 
143 enum class cond_y { y03 = 40, y12, y21, y30 };
144 
145 namespace std { template <> struct is_error_condition_enum<cond_y>: true_type { }; };
146 
cat_cond_y()147 inline std::error_category const & cat_cond_y()
148 {
149     class cat : public std::error_category
150     {
151         char const * name() const noexcept
152         {
153             return "cond_y";
154         }
155         std::string message( int cond ) const
156         {
157             switch( cond_y(cond) )
158             {
159                 case cond_y::y03:
160                     return "y03";
161                 case cond_y::y12:
162                     return "y12";
163                 case cond_y::y21:
164                     return "y21";
165                 case cond_y::y30:
166                     return "y30";
167                 default:
168                     return "error";
169             }
170         }
171         bool equivalent(std::error_code const & code, int cond) const noexcept
172         {
173             switch( cond_y(cond) )
174             {
175                 case cond_y::y03:
176                     return code==make_error_code(errc_a::a0) || code==make_error_code(errc_b::b0);
177                 case cond_y::y12:
178                     return code==make_error_code(errc_a::a1) || code==make_error_code(errc_b::b1);
179                 case cond_y::y21:
180                     return code==make_error_code(errc_a::a2) || code==make_error_code(errc_b::b2);
181                 case cond_y::y30:
182                     return code==make_error_code(errc_a::a3) || code==make_error_code(errc_b::b3);
183                 default:
184                     return false;
185             }
186         }
187     };
188     static cat c;
189     return c;
190 }
191 
make_error_condition(cond_y cond)192 inline std::error_condition make_error_condition( cond_y cond )
193 {
194     return std::error_condition(int(cond), cat_cond_y());
195 }
196 
197 template <int> struct e_cond_y { cond_y value; };
198 
199 #endif
200