Coverage Report

Created: 2026-11-12 07:18

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/boost/boost/system/result.hpp
Line
Count
Source
1
#ifndef BOOST_SYSTEM_RESULT_HPP_INCLUDED
2
#define BOOST_SYSTEM_RESULT_HPP_INCLUDED
3
4
// Copyright 2017, 2021-2025 Peter Dimov.
5
// Distributed under the Boost Software License, Version 1.0.
6
// https://www.boost.org/LICENSE_1_0.txt
7
8
#include <boost/system/errc.hpp>
9
#include <boost/system/system_error.hpp>
10
#include <boost/system/detail/error_code.hpp>
11
#include <boost/system/detail/error_category_impl.hpp>
12
#include <boost/variant2/variant.hpp>
13
#include <boost/compat/invoke.hpp>
14
#include <boost/throw_exception.hpp>
15
#include <boost/assert/source_location.hpp>
16
#include <boost/assert.hpp>
17
#include <boost/config.hpp>
18
#include <type_traits>
19
#include <utility>
20
#include <iosfwd>
21
#include <system_error>
22
#include <exception>
23
24
//
25
26
namespace boost
27
{
28
namespace system
29
{
30
31
// throw_exception_from_error
32
33
#if defined(__GNUC__) && __GNUC__ >= 7 && __GNUC__ <= 8
34
# pragma GCC diagnostic push
35
# pragma GCC diagnostic ignored "-Wattributes"
36
#endif
37
38
BOOST_NORETURN BOOST_NOINLINE inline void throw_exception_from_error( error_code const & e, boost::source_location const& loc )
39
0
{
40
0
    boost::throw_with_location( system_error( e ), loc );
41
0
}
42
43
BOOST_NORETURN BOOST_NOINLINE inline void throw_exception_from_error( errc::errc_t const & e, boost::source_location const& loc )
44
0
{
45
0
    boost::throw_with_location( system_error( make_error_code( e ) ), loc );
46
0
}
47
48
BOOST_NORETURN BOOST_NOINLINE inline void throw_exception_from_error( std::error_code const & e, boost::source_location const& loc )
49
0
{
50
0
    boost::throw_with_location( std::system_error( e ), loc );
51
0
}
52
53
BOOST_NORETURN BOOST_NOINLINE inline void throw_exception_from_error( std::errc const & e, boost::source_location const& loc )
54
0
{
55
0
    boost::throw_with_location( std::system_error( make_error_code( e ) ), loc );
56
0
}
57
58
BOOST_NORETURN BOOST_NOINLINE inline void throw_exception_from_error( std::exception_ptr const & p, boost::source_location const& loc )
59
0
{
60
0
    if( p )
61
0
    {
62
0
        std::rethrow_exception( p );
63
0
    }
64
0
    else
65
0
    {
66
0
        boost::throw_with_location( std::bad_exception(), loc );
67
0
    }
68
0
}
69
70
#if defined(__GNUC__) && __GNUC__ >= 7 && __GNUC__ <= 8
71
# pragma GCC diagnostic pop
72
#endif
73
74
// in_place_*
75
76
using in_place_value_t = variant2::in_place_index_t<0>;
77
BOOST_INLINE_CONSTEXPR in_place_value_t in_place_value{};
78
79
using in_place_error_t = variant2::in_place_index_t<1>;
80
BOOST_INLINE_CONSTEXPR in_place_error_t in_place_error{};
81
82
namespace detail
83
{
84
85
template<class T> using remove_cvref = typename std::remove_cv< typename std::remove_reference<T>::type >::type;
86
87
template<class... T> using is_errc_t = std::is_same<mp11::mp_list<remove_cvref<T>...>, mp11::mp_list<errc::errc_t>>;
88
89
template<class T, class... A> struct is_constructible: std::is_constructible<T, A...> {};
90
template<class A> struct is_constructible<bool, A>: std::is_convertible<A, bool> {};
91
template<class A> struct is_constructible<bool const, A>: std::is_convertible<A, bool> {};
92
93
} // namespace detail
94
95
// result
96
97
template<class T, class E = error_code> class result
98
{
99
private:
100
101
    variant2::variant<T, E> v_;
102
103
public:
104
105
    using value_type = T;
106
    using error_type = E;
107
108
    static constexpr in_place_value_t in_place_value{};
109
    static constexpr in_place_error_t in_place_error{};
110
111
public:
112
113
    // constructors
114
115
    // default
116
    template<class En2 = void, class En = typename std::enable_if<
117
        std::is_void<En2>::value &&
118
        std::is_default_constructible<T>::value
119
        >::type>
120
    constexpr result()
121
        noexcept( std::is_nothrow_default_constructible<T>::value )
122
        : v_( in_place_value )
123
    {
124
    }
125
126
    // implicit, value
127
    template<class A = T, typename std::enable_if<
128
        std::is_convertible<A, T>::value &&
129
        !(detail::is_errc_t<A>::value && std::is_arithmetic<T>::value) &&
130
        !std::is_convertible<A, E>::value, int>::type = 0>
131
    constexpr result( A&& a )
132
        noexcept( std::is_nothrow_constructible<T, A>::value )
133
0
        : v_( in_place_value, std::forward<A>(a) )
134
0
    {
135
0
    }
Unexecuted instantiation: _ZN5boost6system6resultIlNS0_10error_codeEEC2IRKlTnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_lEE5valuentaasr6detail9is_errc_tIS9_EE5valueL_ZNS7_17integral_constantIbLb1EE5valueEEntsr3std14is_convertibleIS9_S2_EE5valueEiE4typeELi0EEEOS9_
Unexecuted instantiation: _ZN5boost6system6resultImNS0_10error_codeEEC2IRKmTnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_mEE5valuentaasr6detail9is_errc_tIS9_EE5valueL_ZNS7_17integral_constantIbLb1EE5valueEEntsr3std14is_convertibleIS9_S2_EE5valueEiE4typeELi0EEEOS9_
Unexecuted instantiation: _ZN5boost6system6resultIdNS0_10error_codeEEC2IRKdTnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_dEE5valuentaasr6detail9is_errc_tIS9_EE5valueL_ZNS7_17integral_constantIbLb1EE5valueEEntsr3std14is_convertibleIS9_S2_EE5valueEiE4typeELi0EEEOS9_
Unexecuted instantiation: _ZN5boost6system6resultIbNS0_10error_codeEEC2IRKbTnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_bEE5valuentaasr6detail9is_errc_tIS9_EE5valueL_ZNS7_17integral_constantIbLb1EE5valueEEntsr3std14is_convertibleIS9_S2_EE5valueEiE4typeELi0EEEOS9_
Unexecuted instantiation: _ZN5boost6system6resultIDnNS0_10error_codeEEC2IDnTnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_DnEE5valuentaasr6detail9is_errc_tIS7_EE5valueL_ZNS5_17integral_constantIbLb0EE5valueEEntsr3std14is_convertibleIS7_S2_EE5valueEiE4typeELi0EEEOS7_
136
137
    // implicit, error
138
    template<class A = E, class = void, typename std::enable_if<
139
        std::is_convertible<A, E>::value &&
140
        !std::is_convertible<A, T>::value, int>::type = 0>
141
    constexpr result( A&& a )
142
        noexcept( std::is_nothrow_constructible<E, A>::value )
143
0
        : v_( in_place_error, std::forward<A>(a) )
144
0
    {
145
0
    }
Unexecuted instantiation: _ZN5boost6system6resultIlNS0_10error_codeEEC2IS2_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S2_EE5valuentsr3std14is_convertibleIS7_lEE5valueEiE4typeELi0EEEOS7_
Unexecuted instantiation: _ZN5boost6system6resultImNS0_10error_codeEEC2IS2_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S2_EE5valuentsr3std14is_convertibleIS7_mEE5valueEiE4typeELi0EEEOS7_
Unexecuted instantiation: _ZN5boost6system6resultIdNS0_10error_codeEEC2IS2_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S2_EE5valuentsr3std14is_convertibleIS7_dEE5valueEiE4typeELi0EEEOS7_
Unexecuted instantiation: _ZN5boost6system6resultIbNS0_10error_codeEEC2IS2_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S2_EE5valuentsr3std14is_convertibleIS7_bEE5valueEiE4typeELi0EEEOS7_
Unexecuted instantiation: _ZN5boost6system6resultIDnNS0_10error_codeEEC2IS2_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S2_EE5valuentsr3std14is_convertibleIS7_DnEE5valueEiE4typeELi0EEEOS7_
146
147
    // explicit, value
148
    template<class... A, class En = typename std::enable_if<
149
        detail::is_constructible<T, A...>::value &&
150
        !(detail::is_errc_t<A...>::value && std::is_arithmetic<T>::value) &&
151
        !detail::is_constructible<E, A...>::value &&
152
        sizeof...(A) >= 1
153
        >::type>
154
    explicit constexpr result( A&&... a )
155
        noexcept( std::is_nothrow_constructible<T, A...>::value )
156
        : v_( in_place_value, std::forward<A>(a)... )
157
    {
158
    }
159
160
    // explicit, error
161
    template<class... A, class En2 = void, class En = typename std::enable_if<
162
        !detail::is_constructible<T, A...>::value &&
163
        detail::is_constructible<E, A...>::value &&
164
        sizeof...(A) >= 1
165
        >::type>
166
    explicit constexpr result( A&&... a )
167
        noexcept( std::is_nothrow_constructible<E, A...>::value )
168
        : v_( in_place_error, std::forward<A>(a)... )
169
    {
170
    }
171
172
    // tagged, value
173
    template<class... A, class En = typename std::enable_if<
174
        std::is_constructible<T, A...>::value
175
        >::type>
176
    constexpr result( in_place_value_t, A&&... a )
177
        noexcept( std::is_nothrow_constructible<T, A...>::value )
178
        : v_( in_place_value, std::forward<A>(a)... )
179
    {
180
    }
181
182
    // tagged, error
183
    template<class... A, class En = typename std::enable_if<
184
        std::is_constructible<E, A...>::value
185
        >::type>
186
    constexpr result( in_place_error_t, A&&... a )
187
        noexcept( std::is_nothrow_constructible<E, A...>::value )
188
        : v_( in_place_error, std::forward<A>(a)... )
189
    {
190
    }
191
192
    // converting
193
    template<class T2, class E2, class En = typename std::enable_if<
194
        std::is_convertible<T2, T>::value &&
195
        std::is_convertible<E2, E>::value &&
196
        !std::is_convertible<result<T2, E2> const&, T>::value
197
        >::type>
198
    BOOST_CXX14_CONSTEXPR result( result<T2, E2> const& r2 )
199
        noexcept(
200
            std::is_nothrow_constructible<T, T2 const&>::value &&
201
            std::is_nothrow_constructible<E, E2>::value &&
202
            std::is_nothrow_default_constructible<E2>::value &&
203
            std::is_nothrow_copy_constructible<E2>::value )
204
        : v_( in_place_error, r2.error() )
205
    {
206
        if( r2 )
207
        {
208
            v_.template emplace<0>( r2.unsafe_value() );
209
        }
210
    }
211
212
    template<class T2, class E2, class En = typename std::enable_if<
213
        std::is_convertible<T2, T>::value &&
214
        std::is_convertible<E2, E>::value &&
215
        !std::is_convertible<result<T2, E2>&&, T>::value
216
        >::type>
217
    BOOST_CXX14_CONSTEXPR result( result<T2, E2>&& r2 )
218
        noexcept(
219
            std::is_nothrow_constructible<T, T2&&>::value &&
220
            std::is_nothrow_constructible<E, E2>::value &&
221
            std::is_nothrow_default_constructible<E2>::value &&
222
            std::is_nothrow_copy_constructible<E2>::value )
223
        : v_( in_place_error, r2.error() )
224
    {
225
        if( r2 )
226
        {
227
            v_.template emplace<0>( std::move( r2 ).unsafe_value() );
228
        }
229
    }
230
231
    // queries
232
233
    constexpr bool has_value() const noexcept
234
0
    {
235
0
        return v_.index() == 0;
236
0
    }
Unexecuted instantiation: boost::system::result<long, boost::system::error_code>::has_value() const
Unexecuted instantiation: boost::system::result<unsigned long, boost::system::error_code>::has_value() const
Unexecuted instantiation: boost::system::result<double, boost::system::error_code>::has_value() const
Unexecuted instantiation: boost::system::result<bool, boost::system::error_code>::has_value() const
237
238
    constexpr bool has_error() const noexcept
239
    {
240
        return v_.index() == 1;
241
    }
242
243
    constexpr explicit operator bool() const noexcept
244
    {
245
        return v_.index() == 0;
246
    }
247
248
    // checked value access
249
#if defined( BOOST_NO_CXX11_REF_QUALIFIERS )
250
251
    BOOST_CXX14_CONSTEXPR T value( boost::source_location const& loc = BOOST_CURRENT_LOCATION ) const
252
    {
253
        if( has_value() )
254
        {
255
            return variant2::unsafe_get<0>( v_ );
256
        }
257
        else
258
        {
259
            throw_exception_from_error( variant2::unsafe_get<1>( v_ ), loc );
260
        }
261
    }
262
263
#else
264
265
    BOOST_CXX14_CONSTEXPR T& value( boost::source_location const& loc = BOOST_CURRENT_LOCATION ) &
266
0
    {
267
0
        if( has_value() )
268
0
        {
269
0
            return variant2::unsafe_get<0>( v_ );
270
0
        }
271
0
        else
272
0
        {
273
0
            throw_exception_from_error( variant2::unsafe_get<1>( v_ ), loc );
274
0
        }
275
0
    }
Unexecuted instantiation: boost::system::result<long, boost::system::error_code>::value(boost::source_location const&) &
Unexecuted instantiation: boost::system::result<unsigned long, boost::system::error_code>::value(boost::source_location const&) &
Unexecuted instantiation: boost::system::result<double, boost::system::error_code>::value(boost::source_location const&) &
Unexecuted instantiation: boost::system::result<bool, boost::system::error_code>::value(boost::source_location const&) &
276
277
    BOOST_CXX14_CONSTEXPR T const& value( boost::source_location const& loc = BOOST_CURRENT_LOCATION ) const&
278
    {
279
        if( has_value() )
280
        {
281
            return variant2::unsafe_get<0>( v_ );
282
        }
283
        else
284
        {
285
            throw_exception_from_error( variant2::unsafe_get<1>( v_ ), loc );
286
        }
287
    }
288
289
    template<class U = T>
290
        BOOST_CXX14_CONSTEXPR
291
        typename std::enable_if<std::is_move_constructible<U>::value, T>::type
292
        value( boost::source_location const& loc = BOOST_CURRENT_LOCATION ) &&
293
0
    {
294
0
        return std::move( value( loc ) );
295
0
    }
Unexecuted instantiation: _ZNO5boost6system6resultIlNS0_10error_codeEE5valueIlEENSt3__19enable_ifIXsr3std21is_move_constructibleIT_EE5valueElE4typeERKNS_15source_locationE
Unexecuted instantiation: _ZNO5boost6system6resultImNS0_10error_codeEE5valueImEENSt3__19enable_ifIXsr3std21is_move_constructibleIT_EE5valueEmE4typeERKNS_15source_locationE
Unexecuted instantiation: _ZNO5boost6system6resultIdNS0_10error_codeEE5valueIdEENSt3__19enable_ifIXsr3std21is_move_constructibleIT_EE5valueEdE4typeERKNS_15source_locationE
Unexecuted instantiation: _ZNO5boost6system6resultIbNS0_10error_codeEE5valueIbEENSt3__19enable_ifIXsr3std21is_move_constructibleIT_EE5valueEbE4typeERKNS_15source_locationE
296
297
    template<class U = T>
298
        BOOST_CXX14_CONSTEXPR
299
        typename std::enable_if<!std::is_move_constructible<U>::value, T&&>::type
300
        value( boost::source_location const& loc = BOOST_CURRENT_LOCATION ) &&
301
    {
302
        return std::move( value( loc ) );
303
    }
304
305
    template<class U = T>
306
        BOOST_CXX14_CONSTEXPR
307
        typename std::enable_if<std::is_move_constructible<U>::value, T>::type
308
        value() const && = delete;
309
310
    template<class U = T>
311
        BOOST_CXX14_CONSTEXPR
312
        typename std::enable_if<!std::is_move_constructible<U>::value, T const&&>::type
313
        value( boost::source_location const& loc = BOOST_CURRENT_LOCATION ) const &&
314
    {
315
        return std::move( value( loc ) );
316
    }
317
318
#endif
319
320
    // checked value access
321
322
    BOOST_CXX14_CONSTEXPR T* operator->()
323
    {
324
        return &value();
325
    }
326
327
    BOOST_CXX14_CONSTEXPR T const* operator->() const
328
    {
329
        return &value();
330
    }
331
332
#if defined( BOOST_NO_CXX11_REF_QUALIFIERS )
333
334
    BOOST_CXX14_CONSTEXPR T& operator*()
335
    {
336
        return value();
337
    }
338
339
    BOOST_CXX14_CONSTEXPR T const& operator*() const
340
    {
341
        return value();
342
    }
343
344
#else
345
346
    BOOST_CXX14_CONSTEXPR T& operator*() &
347
    {
348
        return value();
349
    }
350
351
    BOOST_CXX14_CONSTEXPR T const& operator*() const &
352
    {
353
        return value();
354
    }
355
356
    template<class U = T>
357
        BOOST_CXX14_CONSTEXPR
358
        typename std::enable_if<std::is_move_constructible<U>::value, T>::type
359
        operator*() &&
360
    {
361
        return std::move( value() );
362
    }
363
364
    template<class U = T>
365
        BOOST_CXX14_CONSTEXPR
366
        typename std::enable_if<!std::is_move_constructible<U>::value, T&&>::type
367
        operator*() &&
368
    {
369
        return std::move( value() );
370
    }
371
372
    template<class U = T>
373
        BOOST_CXX14_CONSTEXPR
374
        typename std::enable_if<std::is_move_constructible<U>::value, T>::type
375
        operator*() const && = delete;
376
377
    template<class U = T>
378
        BOOST_CXX14_CONSTEXPR
379
        typename std::enable_if<!std::is_move_constructible<U>::value, T const&&>::type
380
        operator*() const &&
381
    {
382
        return std::move( value() );
383
    }
384
385
#endif
386
387
    // unchecked value access
388
389
#if defined( BOOST_NO_CXX11_REF_QUALIFIERS )
390
391
    BOOST_CXX14_CONSTEXPR T& unsafe_value()
392
    {
393
        BOOST_ASSERT( has_value() );
394
        return *variant2::get_if<0>( &v_ );
395
    }
396
397
    BOOST_CXX14_CONSTEXPR T const& unsafe_value() const
398
    {
399
        BOOST_ASSERT( has_value() );
400
        return *variant2::get_if<0>( &v_ );
401
    }
402
403
#else
404
405
    BOOST_CXX14_CONSTEXPR T& unsafe_value() &
406
    {
407
        BOOST_ASSERT( has_value() );
408
        return *variant2::get_if<0>( &v_ );
409
    }
410
411
    BOOST_CXX14_CONSTEXPR T const& unsafe_value() const &
412
    {
413
        BOOST_ASSERT( has_value() );
414
        return *variant2::get_if<0>( &v_ );
415
    }
416
417
    template<class U = T>
418
        BOOST_CXX14_CONSTEXPR
419
        typename std::enable_if<std::is_move_constructible<U>::value, T>::type
420
        unsafe_value() &&
421
    {
422
        BOOST_ASSERT( has_value() );
423
        return std::move( *variant2::get_if<0>( &v_ ) );
424
    }
425
426
    template<class U = T>
427
        BOOST_CXX14_CONSTEXPR
428
        typename std::enable_if<!std::is_move_constructible<U>::value, T&&>::type
429
        unsafe_value() &&
430
    {
431
        BOOST_ASSERT( has_value() );
432
        return std::move( *variant2::get_if<0>( &v_ ) );
433
    }
434
435
    template<class U = T>
436
        BOOST_CXX14_CONSTEXPR
437
        typename std::enable_if<std::is_move_constructible<U>::value, T>::type
438
        unsafe_value() const && = delete;
439
440
    template<class U = T>
441
        BOOST_CXX14_CONSTEXPR
442
        typename std::enable_if<!std::is_move_constructible<U>::value, T const&&>::type
443
        unsafe_value() const &&
444
    {
445
        BOOST_ASSERT( has_value() );
446
        return std::move( *variant2::get_if<0>( &v_ ) );
447
    }
448
449
#endif
450
451
    // error access
452
453
    constexpr E error() const &
454
        noexcept( std::is_nothrow_default_constructible<E>::value && std::is_nothrow_copy_constructible<E>::value )
455
    {
456
        return has_error()? variant2::unsafe_get<1>( v_ ): E();
457
    }
458
459
    BOOST_CXX14_CONSTEXPR E error() &&
460
        noexcept( std::is_nothrow_default_constructible<E>::value && std::is_nothrow_move_constructible<E>::value )
461
    {
462
        return has_error()? std::move( variant2::unsafe_get<1>( v_ ) ): E();
463
    }
464
465
    // emplace
466
467
    template<class... A>
468
    BOOST_CXX14_CONSTEXPR T& emplace( A&&... a )
469
    {
470
        return v_.template emplace<0>( std::forward<A>(a)... );
471
    }
472
473
    // swap
474
475
    BOOST_CXX14_CONSTEXPR void swap( result& r )
476
        noexcept( noexcept( v_.swap( r.v_ ) ) )
477
    {
478
        v_.swap( r.v_ );
479
    }
480
481
    friend BOOST_CXX14_CONSTEXPR void swap( result & r1, result & r2 )
482
        noexcept( noexcept( r1.swap( r2 ) ) )
483
    {
484
        r1.swap( r2 );
485
    }
486
487
    // equality
488
489
    friend constexpr bool operator==( result const & r1, result const & r2 )
490
        noexcept( noexcept( r1.v_ == r2.v_ ) )
491
    {
492
        return r1.v_ == r2.v_;
493
    }
494
495
    friend constexpr bool operator!=( result const & r1, result const & r2 )
496
        noexcept( noexcept( !( r1 == r2 ) ) )
497
    {
498
        return !( r1 == r2 );
499
    }
500
};
501
502
#if defined(BOOST_NO_CXX17_INLINE_VARIABLES)
503
504
template<class T, class E> constexpr in_place_value_t result<T, E>::in_place_value;
505
template<class T, class E> constexpr in_place_error_t result<T, E>::in_place_error;
506
507
#endif
508
509
template<class Ch, class Tr, class T, class E> std::basic_ostream<Ch, Tr>& operator<<( std::basic_ostream<Ch, Tr>& os, result<T, E> const & r )
510
{
511
    if( r.has_value() )
512
    {
513
        os << "value:" << r.unsafe_value();
514
    }
515
    else
516
    {
517
        os << "error:" << r.error();
518
    }
519
520
    return os;
521
}
522
523
// result<void>
524
525
template<class E> class result<void, E>
526
{
527
private:
528
529
    variant2::variant<variant2::monostate, E> v_;
530
531
public:
532
533
    using value_type = void;
534
    using error_type = E;
535
536
    static constexpr in_place_value_t in_place_value{};
537
    static constexpr in_place_error_t in_place_error{};
538
539
public:
540
541
    // constructors
542
543
    // default
544
    constexpr result() noexcept
545
        : v_( in_place_value )
546
    {
547
    }
548
549
    // explicit, error
550
    template<class A, class En = typename std::enable_if<
551
        std::is_constructible<E, A>::value &&
552
        !std::is_convertible<A, E>::value
553
        >::type>
554
    explicit constexpr result( A&& a )
555
        noexcept( std::is_nothrow_constructible<E, A>::value )
556
        : v_( in_place_error, std::forward<A>(a) )
557
    {
558
    }
559
560
    // implicit, error
561
    template<class A, class En2 = void, class En = typename std::enable_if<
562
        std::is_convertible<A, E>::value
563
        >::type>
564
    constexpr result( A&& a )
565
        noexcept( std::is_nothrow_constructible<E, A>::value )
566
        : v_( in_place_error, std::forward<A>(a) )
567
    {
568
    }
569
570
    // more than one arg, error
571
    template<class... A, class En2 = void, class En3 = void, class En = typename std::enable_if<
572
        std::is_constructible<E, A...>::value &&
573
        sizeof...(A) >= 2
574
        >::type>
575
    constexpr result( A&&... a )
576
        noexcept( std::is_nothrow_constructible<E, A...>::value )
577
        : v_( in_place_error, std::forward<A>(a)... )
578
    {
579
    }
580
581
    // tagged, value
582
    constexpr result( in_place_value_t ) noexcept
583
        : v_( in_place_value )
584
    {
585
    }
586
587
    // tagged, error
588
    template<class... A, class En = typename std::enable_if<
589
        std::is_constructible<E, A...>::value
590
        >::type>
591
    constexpr result( in_place_error_t, A&&... a )
592
        noexcept( std::is_nothrow_constructible<E, A...>::value )
593
        : v_( in_place_error, std::forward<A>(a)... )
594
    {
595
    }
596
597
    // converting
598
    template<class E2, class En = typename std::enable_if<
599
        std::is_convertible<E2, E>::value
600
        >::type>
601
    BOOST_CXX14_CONSTEXPR result( result<void, E2> const& r2 )
602
        noexcept(
603
            std::is_nothrow_constructible<E, E2>::value &&
604
            std::is_nothrow_default_constructible<E2>::value &&
605
            std::is_nothrow_copy_constructible<E2>::value )
606
        : v_( in_place_error, r2.error() )
607
    {
608
        if( r2 )
609
        {
610
            this->emplace();
611
        }
612
    }
613
614
    // queries
615
616
    constexpr bool has_value() const noexcept
617
    {
618
        return v_.index() == 0;
619
    }
620
621
    constexpr bool has_error() const noexcept
622
    {
623
        return v_.index() == 1;
624
    }
625
626
    constexpr explicit operator bool() const noexcept
627
    {
628
        return v_.index() == 0;
629
    }
630
631
    // checked value access
632
633
    BOOST_CXX14_CONSTEXPR void value( boost::source_location const& loc = BOOST_CURRENT_LOCATION ) const
634
    {
635
        if( has_value() )
636
        {
637
        }
638
        else
639
        {
640
            throw_exception_from_error( variant2::unsafe_get<1>( v_ ), loc );
641
        }
642
    }
643
644
    // checked value access
645
646
    BOOST_CXX14_CONSTEXPR void* operator->()
647
    {
648
        value();
649
        return &variant2::unsafe_get<0>( v_ );
650
    }
651
652
    BOOST_CXX14_CONSTEXPR void const* operator->() const
653
    {
654
        value();
655
        return &variant2::unsafe_get<0>( v_ );
656
    }
657
658
    BOOST_CXX14_CONSTEXPR void operator*() const
659
    {
660
        return value();
661
    }
662
663
    // unchecked value access
664
665
    BOOST_CXX14_CONSTEXPR void unsafe_value() const
666
    {
667
        BOOST_ASSERT( has_value() );
668
    }
669
670
    // error access
671
672
    constexpr E error() const &
673
        noexcept( std::is_nothrow_default_constructible<E>::value && std::is_nothrow_copy_constructible<E>::value )
674
    {
675
        return has_error()? variant2::unsafe_get<1>( v_ ): E();
676
    }
677
678
    BOOST_CXX14_CONSTEXPR E error() &&
679
        noexcept( std::is_nothrow_default_constructible<E>::value && std::is_nothrow_move_constructible<E>::value )
680
    {
681
        return has_error()? std::move( variant2::unsafe_get<1>( v_ ) ): E();
682
    }
683
684
    // emplace
685
686
    BOOST_CXX14_CONSTEXPR void emplace()
687
    {
688
        v_.template emplace<0>();
689
    }
690
691
    // swap
692
693
    BOOST_CXX14_CONSTEXPR void swap( result& r )
694
        noexcept( noexcept( v_.swap( r.v_ ) ) )
695
    {
696
        v_.swap( r.v_ );
697
    }
698
699
    friend BOOST_CXX14_CONSTEXPR void swap( result & r1, result & r2 )
700
        noexcept( noexcept( r1.swap( r2 ) ) )
701
    {
702
        r1.swap( r2 );
703
    }
704
705
    // equality
706
707
    friend constexpr bool operator==( result const & r1, result const & r2 )
708
        noexcept( noexcept( r1.v_ == r2.v_ ) )
709
    {
710
        return r1.v_ == r2.v_;
711
    }
712
713
    friend constexpr bool operator!=( result const & r1, result const & r2 )
714
        noexcept( noexcept( !( r1 == r2 ) ) )
715
    {
716
        return !( r1 == r2 );
717
    }
718
};
719
720
#if defined(BOOST_NO_CXX17_INLINE_VARIABLES)
721
722
template<class E> constexpr in_place_value_t result<void, E>::in_place_value;
723
template<class E> constexpr in_place_error_t result<void, E>::in_place_error;
724
725
#endif
726
727
template<class Ch, class Tr, class E> std::basic_ostream<Ch, Tr>& operator<<( std::basic_ostream<Ch, Tr>& os, result<void, E> const & r )
728
{
729
    if( r.has_value() )
730
    {
731
        os << "value:void";
732
    }
733
    else
734
    {
735
        os << "error:" << r.error();
736
    }
737
738
    return os;
739
}
740
741
// result<T&, E>
742
743
namespace detail
744
{
745
746
template<class U, class A> struct reference_to_temporary: std::integral_constant<bool,
747
    !std::is_reference<A>::value ||
748
    !std::is_convertible<typename std::remove_reference<A>::type*, U*>::value
749
> {};
750
751
} // namespace detail
752
753
template<class U, class E> class result<U&, E>
754
{
755
private:
756
757
    variant2::variant<U*, E> v_;
758
759
public:
760
761
    using value_type = U&;
762
    using error_type = E;
763
764
    static constexpr in_place_value_t in_place_value{};
765
    static constexpr in_place_error_t in_place_error{};
766
767
public:
768
769
    // constructors
770
771
    // implicit, value
772
    template<class A, typename std::enable_if<
773
        std::is_convertible<A, U&>::value &&
774
        !detail::reference_to_temporary<U, A>::value &&
775
        !std::is_convertible<A, E>::value, int>::type = 0>
776
    constexpr result( A&& a )
777
        noexcept( std::is_nothrow_constructible<U&, A>::value )
778
0
        : v_( in_place_value, &static_cast<U&>( std::forward<A>(a) ) )
779
0
    {
780
0
    }
Unexecuted instantiation: _ZN5boost6system6resultIRNS_4json5valueENS0_10error_codeEEC2IS4_TnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_S4_EE5valuentsr6detail22reference_to_temporaryIS3_SA_EE5valuentsr3std14is_convertibleISA_S5_EE5valueEiE4typeELi0EEEOSA_
Unexecuted instantiation: _ZN5boost6system6resultIRKNS_4json5valueENS0_10error_codeEEC2IRS3_TnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_S5_EE5valuentsr6detail22reference_to_temporaryIS4_SC_EE5valuentsr3std14is_convertibleISC_S6_EE5valueEiE4typeELi0EEEOSC_
Unexecuted instantiation: _ZN5boost6system6resultIRKNS_4json5valueENS0_10error_codeEEC2IS5_TnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_S5_EE5valuentsr6detail22reference_to_temporaryIS4_SB_EE5valuentsr3std14is_convertibleISB_S6_EE5valueEiE4typeELi0EEEOSB_
Unexecuted instantiation: _ZN5boost6system6resultIRcNS0_10error_codeEEC2IS2_TnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_S2_EE5valuentsr6detail22reference_to_temporaryIcS8_EE5valuentsr3std14is_convertibleIS8_S3_EE5valueEiE4typeELi0EEEOS8_
Unexecuted instantiation: _ZN5boost6system6resultIRKcNS0_10error_codeEEC2IS3_TnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_S3_EE5valuentsr6detail22reference_to_temporaryIS2_S9_EE5valuentsr3std14is_convertibleIS9_S4_EE5valueEiE4typeELi0EEEOS9_
Unexecuted instantiation: _ZN5boost6system6resultIRNS_4json5arrayENS0_10error_codeEEC2IS4_TnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_S4_EE5valuentsr6detail22reference_to_temporaryIS3_SA_EE5valuentsr3std14is_convertibleISA_S5_EE5valueEiE4typeELi0EEEOSA_
Unexecuted instantiation: _ZN5boost6system6resultIRKNS_4json5arrayENS0_10error_codeEEC2IS5_TnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_S5_EE5valuentsr6detail22reference_to_temporaryIS4_SB_EE5valuentsr3std14is_convertibleISB_S6_EE5valueEiE4typeELi0EEEOSB_
Unexecuted instantiation: _ZN5boost6system6resultIRNS_4json6objectENS0_10error_codeEEC2IS4_TnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_S4_EE5valuentsr6detail22reference_to_temporaryIS3_SA_EE5valuentsr3std14is_convertibleISA_S5_EE5valueEiE4typeELi0EEEOSA_
Unexecuted instantiation: _ZN5boost6system6resultIRKNS_4json6objectENS0_10error_codeEEC2IS5_TnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_S5_EE5valuentsr6detail22reference_to_temporaryIS4_SB_EE5valuentsr3std14is_convertibleISB_S6_EE5valueEiE4typeELi0EEEOSB_
Unexecuted instantiation: _ZN5boost6system6resultIRNS_4json6stringENS0_10error_codeEEC2IS4_TnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_S4_EE5valuentsr6detail22reference_to_temporaryIS3_SA_EE5valuentsr3std14is_convertibleISA_S5_EE5valueEiE4typeELi0EEEOSA_
Unexecuted instantiation: _ZN5boost6system6resultIRKNS_4json6stringENS0_10error_codeEEC2IS5_TnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_S5_EE5valuentsr6detail22reference_to_temporaryIS4_SB_EE5valuentsr3std14is_convertibleISB_S6_EE5valueEiE4typeELi0EEEOSB_
Unexecuted instantiation: _ZN5boost6system6resultIRlNS0_10error_codeEEC2IS2_TnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_S2_EE5valuentsr6detail22reference_to_temporaryIlS8_EE5valuentsr3std14is_convertibleIS8_S3_EE5valueEiE4typeELi0EEEOS8_
Unexecuted instantiation: _ZN5boost6system6resultIRmNS0_10error_codeEEC2IS2_TnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_S2_EE5valuentsr6detail22reference_to_temporaryImS8_EE5valuentsr3std14is_convertibleIS8_S3_EE5valueEiE4typeELi0EEEOS8_
Unexecuted instantiation: _ZN5boost6system6resultIRdNS0_10error_codeEEC2IS2_TnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_S2_EE5valuentsr6detail22reference_to_temporaryIdS8_EE5valuentsr3std14is_convertibleIS8_S3_EE5valueEiE4typeELi0EEEOS8_
Unexecuted instantiation: _ZN5boost6system6resultIRbNS0_10error_codeEEC2IS2_TnNSt3__19enable_ifIXaaaasr3std14is_convertibleIT_S2_EE5valuentsr6detail22reference_to_temporaryIbS8_EE5valuentsr3std14is_convertibleIS8_S3_EE5valueEiE4typeELi0EEEOS8_
781
782
    // implicit, error
783
    template<class A = E, class = void, typename std::enable_if<
784
        std::is_convertible<A, E>::value &&
785
        !std::is_convertible<A, U&>::value, int>::type = 0>
786
    constexpr result( A&& a )
787
        noexcept( std::is_nothrow_constructible<E, A>::value )
788
0
        : v_( in_place_error, std::forward<A>(a) )
789
0
    {
790
0
    }
Unexecuted instantiation: _ZN5boost6system6resultIRNS_4json5valueENS0_10error_codeEEC2IS5_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S5_EE5valuentsr3std14is_convertibleISA_S4_EE5valueEiE4typeELi0EEEOSA_
Unexecuted instantiation: _ZN5boost6system6resultIRKNS_4json5valueENS0_10error_codeEEC2IS6_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S6_EE5valuentsr3std14is_convertibleISB_S5_EE5valueEiE4typeELi0EEEOSB_
Unexecuted instantiation: _ZN5boost6system6resultIRcNS0_10error_codeEEC2IS3_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S3_EE5valuentsr3std14is_convertibleIS8_S2_EE5valueEiE4typeELi0EEEOS8_
Unexecuted instantiation: _ZN5boost6system6resultIRKcNS0_10error_codeEEC2IS4_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S4_EE5valuentsr3std14is_convertibleIS9_S3_EE5valueEiE4typeELi0EEEOS9_
Unexecuted instantiation: _ZN5boost6system6resultIRNS_4json5arrayENS0_10error_codeEEC2IS5_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S5_EE5valuentsr3std14is_convertibleISA_S4_EE5valueEiE4typeELi0EEEOSA_
Unexecuted instantiation: _ZN5boost6system6resultIRKNS_4json5arrayENS0_10error_codeEEC2IS6_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S6_EE5valuentsr3std14is_convertibleISB_S5_EE5valueEiE4typeELi0EEEOSB_
Unexecuted instantiation: _ZN5boost6system6resultIRNS_4json6objectENS0_10error_codeEEC2IS5_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S5_EE5valuentsr3std14is_convertibleISA_S4_EE5valueEiE4typeELi0EEEOSA_
Unexecuted instantiation: _ZN5boost6system6resultIRKNS_4json6objectENS0_10error_codeEEC2IS6_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S6_EE5valuentsr3std14is_convertibleISB_S5_EE5valueEiE4typeELi0EEEOSB_
Unexecuted instantiation: _ZN5boost6system6resultIRNS_4json6stringENS0_10error_codeEEC2IS5_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S5_EE5valuentsr3std14is_convertibleISA_S4_EE5valueEiE4typeELi0EEEOSA_
Unexecuted instantiation: _ZN5boost6system6resultIRKNS_4json6stringENS0_10error_codeEEC2IS6_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S6_EE5valuentsr3std14is_convertibleISB_S5_EE5valueEiE4typeELi0EEEOSB_
Unexecuted instantiation: _ZN5boost6system6resultIRlNS0_10error_codeEEC2IS3_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S3_EE5valuentsr3std14is_convertibleIS8_S2_EE5valueEiE4typeELi0EEEOS8_
Unexecuted instantiation: _ZN5boost6system6resultIRmNS0_10error_codeEEC2IS3_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S3_EE5valuentsr3std14is_convertibleIS8_S2_EE5valueEiE4typeELi0EEEOS8_
Unexecuted instantiation: _ZN5boost6system6resultIRdNS0_10error_codeEEC2IS3_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S3_EE5valuentsr3std14is_convertibleIS8_S2_EE5valueEiE4typeELi0EEEOS8_
Unexecuted instantiation: _ZN5boost6system6resultIRbNS0_10error_codeEEC2IS3_vTnNSt3__19enable_ifIXaasr3std14is_convertibleIT_S3_EE5valuentsr3std14is_convertibleIS8_S2_EE5valueEiE4typeELi0EEEOS8_
791
792
    // explicit, value
793
    template<class A, class En = typename std::enable_if<
794
        detail::is_constructible<U&, A>::value &&
795
        !std::is_convertible<A, U&>::value &&
796
        !detail::reference_to_temporary<U, A>::value &&
797
        !detail::is_constructible<E, A>::value
798
        >::type>
799
    explicit constexpr result( A&& a )
800
        noexcept( std::is_nothrow_constructible<U&, A>::value )
801
        : v_( in_place_value, &static_cast<U&>( std::forward<A>(a) ) )
802
    {
803
    }
804
805
    // explicit, error
806
    template<class... A, class En2 = void, class En = typename std::enable_if<
807
        !detail::is_constructible<U&, A...>::value &&
808
        detail::is_constructible<E, A...>::value &&
809
        sizeof...(A) >= 1
810
        >::type>
811
    explicit constexpr result( A&&... a )
812
        noexcept( std::is_nothrow_constructible<E, A...>::value )
813
        : v_( in_place_error, std::forward<A>(a)... )
814
    {
815
    }
816
817
    // tagged, value
818
    template<class A, class En = typename std::enable_if<
819
        std::is_constructible<U&, A>::value &&
820
        !detail::reference_to_temporary<U, A>::value
821
        >::type>
822
    constexpr result( in_place_value_t, A&& a )
823
        noexcept( std::is_nothrow_constructible<U&, A>::value )
824
        : v_( in_place_value, &static_cast<U&>( std::forward<A>(a) ) )
825
    {
826
    }
827
828
    // tagged, error
829
    template<class... A, class En = typename std::enable_if<
830
        std::is_constructible<E, A...>::value
831
        >::type>
832
    constexpr result( in_place_error_t, A&&... a )
833
        noexcept( std::is_nothrow_constructible<E, A...>::value )
834
        : v_( in_place_error, std::forward<A>(a)... )
835
    {
836
    }
837
838
    // converting
839
    template<class U2, class E2, class En = typename std::enable_if<
840
        std::is_convertible<U2&, U&>::value &&
841
        !detail::reference_to_temporary<U, U2&>::value &&
842
        std::is_convertible<E2, E>::value &&
843
        !std::is_convertible<result<U2&, E2> const&, U&>::value
844
        >::type>
845
    BOOST_CXX14_CONSTEXPR result( result<U2&, E2> const& r2 )
846
        noexcept(
847
            std::is_nothrow_constructible<U&, U2&>::value &&
848
            std::is_nothrow_constructible<E, E2>::value &&
849
            std::is_nothrow_default_constructible<E2>::value &&
850
            std::is_nothrow_copy_constructible<E2>::value )
851
        : v_( in_place_error, r2.error() )
852
    {
853
        if( r2 )
854
        {
855
            this->emplace( r2.unsafe_value() );
856
        }
857
    }
858
859
    // queries
860
861
    constexpr bool has_value() const noexcept
862
0
    {
863
0
        return v_.index() == 0;
864
0
    }
Unexecuted instantiation: boost::system::result<boost::json::value const&, boost::system::error_code>::has_value() const
Unexecuted instantiation: boost::system::result<boost::json::value&, boost::system::error_code>::has_value() const
Unexecuted instantiation: boost::system::result<char const&, boost::system::error_code>::has_value() const
Unexecuted instantiation: boost::system::result<boost::json::object&, boost::system::error_code>::has_value() const
Unexecuted instantiation: boost::system::result<boost::json::object const&, boost::system::error_code>::has_value() const
Unexecuted instantiation: boost::system::result<boost::json::array&, boost::system::error_code>::has_value() const
Unexecuted instantiation: boost::system::result<boost::json::array const&, boost::system::error_code>::has_value() const
Unexecuted instantiation: boost::system::result<boost::json::string const&, boost::system::error_code>::has_value() const
Unexecuted instantiation: boost::system::result<long&, boost::system::error_code>::has_value() const
Unexecuted instantiation: boost::system::result<unsigned long&, boost::system::error_code>::has_value() const
Unexecuted instantiation: boost::system::result<double&, boost::system::error_code>::has_value() const
Unexecuted instantiation: boost::system::result<bool&, boost::system::error_code>::has_value() const
865
866
    constexpr bool has_error() const noexcept
867
0
    {
868
0
        return v_.index() == 1;
869
0
    }
Unexecuted instantiation: boost::system::result<boost::json::object&, boost::system::error_code>::has_error() const
Unexecuted instantiation: boost::system::result<boost::json::object const&, boost::system::error_code>::has_error() const
Unexecuted instantiation: boost::system::result<boost::json::array&, boost::system::error_code>::has_error() const
Unexecuted instantiation: boost::system::result<boost::json::array const&, boost::system::error_code>::has_error() const
870
871
    constexpr explicit operator bool() const noexcept
872
0
    {
873
0
        return v_.index() == 0;
874
0
    }
Unexecuted instantiation: boost::system::result<boost::json::object&, boost::system::error_code>::operator bool() const
Unexecuted instantiation: boost::system::result<boost::json::object const&, boost::system::error_code>::operator bool() const
Unexecuted instantiation: boost::system::result<boost::json::array&, boost::system::error_code>::operator bool() const
Unexecuted instantiation: boost::system::result<boost::json::array const&, boost::system::error_code>::operator bool() const
875
876
    // checked value access
877
878
    BOOST_CXX14_CONSTEXPR U& value( boost::source_location const& loc = BOOST_CURRENT_LOCATION ) const
879
0
    {
880
0
        if( has_value() )
881
0
        {
882
0
            return *variant2::unsafe_get<0>( v_ );
883
0
        }
884
0
        else
885
0
        {
886
0
            throw_exception_from_error( variant2::unsafe_get<1>( v_ ), loc );
887
0
        }
888
0
    }
Unexecuted instantiation: boost::system::result<boost::json::value const&, boost::system::error_code>::value(boost::source_location const&) const
Unexecuted instantiation: boost::system::result<boost::json::value&, boost::system::error_code>::value(boost::source_location const&) const
Unexecuted instantiation: boost::system::result<char const&, boost::system::error_code>::value(boost::source_location const&) const
Unexecuted instantiation: boost::system::result<boost::json::object const&, boost::system::error_code>::value(boost::source_location const&) const
Unexecuted instantiation: boost::system::result<boost::json::array const&, boost::system::error_code>::value(boost::source_location const&) const
Unexecuted instantiation: boost::system::result<boost::json::string const&, boost::system::error_code>::value(boost::source_location const&) const
Unexecuted instantiation: boost::system::result<long&, boost::system::error_code>::value(boost::source_location const&) const
Unexecuted instantiation: boost::system::result<unsigned long&, boost::system::error_code>::value(boost::source_location const&) const
Unexecuted instantiation: boost::system::result<double&, boost::system::error_code>::value(boost::source_location const&) const
Unexecuted instantiation: boost::system::result<bool&, boost::system::error_code>::value(boost::source_location const&) const
889
890
    // checked value access
891
892
    BOOST_CXX14_CONSTEXPR U* operator->() const
893
    {
894
        return &value();
895
    }
896
897
    BOOST_CXX14_CONSTEXPR U& operator*() const
898
    {
899
        return value();
900
    }
901
902
    // unchecked value access
903
904
    BOOST_CXX14_CONSTEXPR U& unsafe_value() const
905
0
    {
906
0
        BOOST_ASSERT( has_value() );
907
0
        return *( has_value()? variant2::unsafe_get<0>( v_ ): 0 );
908
0
    }
Unexecuted instantiation: boost::system::result<boost::json::object&, boost::system::error_code>::unsafe_value() const
Unexecuted instantiation: boost::system::result<boost::json::object const&, boost::system::error_code>::unsafe_value() const
Unexecuted instantiation: boost::system::result<boost::json::array&, boost::system::error_code>::unsafe_value() const
Unexecuted instantiation: boost::system::result<boost::json::array const&, boost::system::error_code>::unsafe_value() const
909
910
    // error access
911
912
    constexpr E error() const &
913
        noexcept( std::is_nothrow_default_constructible<E>::value && std::is_nothrow_copy_constructible<E>::value )
914
0
    {
915
0
        return has_error()? variant2::unsafe_get<1>( v_ ): E();
916
0
    }
Unexecuted instantiation: boost::system::result<boost::json::object&, boost::system::error_code>::error() const &
Unexecuted instantiation: boost::system::result<boost::json::object const&, boost::system::error_code>::error() const &
Unexecuted instantiation: boost::system::result<boost::json::array&, boost::system::error_code>::error() const &
Unexecuted instantiation: boost::system::result<boost::json::array const&, boost::system::error_code>::error() const &
917
918
    BOOST_CXX14_CONSTEXPR E error() &&
919
        noexcept( std::is_nothrow_default_constructible<E>::value && std::is_nothrow_move_constructible<E>::value )
920
    {
921
        return has_error()? std::move( variant2::unsafe_get<1>( v_ ) ): E();
922
    }
923
924
    // emplace
925
926
    template<class A, class En = typename std::enable_if<
927
        detail::is_constructible<U&, A>::value &&
928
        !detail::reference_to_temporary<U, A>::value
929
        >::type>
930
    BOOST_CXX14_CONSTEXPR U& emplace( A&& a )
931
    {
932
        return *v_.template emplace<0>( &static_cast<U&>( a ) );
933
    }
934
935
    // swap
936
937
    BOOST_CXX14_CONSTEXPR void swap( result& r )
938
        noexcept( noexcept( v_.swap( r.v_ ) ) )
939
    {
940
        v_.swap( r.v_ );
941
    }
942
943
    friend BOOST_CXX14_CONSTEXPR void swap( result & r1, result & r2 )
944
        noexcept( noexcept( r1.swap( r2 ) ) )
945
    {
946
        r1.swap( r2 );
947
    }
948
949
    // equality
950
951
    friend constexpr bool operator==( result const & r1, result const & r2 )
952
        noexcept( noexcept( r1 && r2? r1.unsafe_value() == r2.unsafe_value(): r1.v_ == r2.v_ ) )
953
    {
954
        return r1 && r2? r1.unsafe_value() == r2.unsafe_value(): r1.v_ == r2.v_;
955
    }
956
957
    friend constexpr bool operator!=( result const & r1, result const & r2 )
958
        noexcept( noexcept( !( r1 == r2 ) ) )
959
    {
960
        return !( r1 == r2 );
961
    }
962
};
963
964
#if defined(BOOST_NO_CXX17_INLINE_VARIABLES)
965
966
template<class U, class E> constexpr in_place_value_t result<U&, E>::in_place_value;
967
template<class U, class E> constexpr in_place_error_t result<U&, E>::in_place_error;
968
969
#endif
970
971
// operator|
972
973
namespace detail
974
{
975
976
// is_value_convertible_to
977
978
template<class T, class U> struct is_value_convertible_to: std::is_convertible<T, U>
979
{
980
};
981
982
template<class T, class U> struct is_value_convertible_to<T, U&>:
983
    std::integral_constant<bool,
984
        std::is_lvalue_reference<T>::value &&
985
        std::is_convertible<typename std::remove_reference<T>::type*, U*>::value>
986
{
987
};
988
989
// is_result
990
991
template<class T> struct is_result: std::false_type {};
992
template<class T, class E> struct is_result< result<T, E> >: std::true_type {};
993
994
} // namespace detail
995
996
// result | value
997
998
template<class T, class E, class U,
999
    class En = typename std::enable_if<std::is_convertible<U, typename std::decay<T>::type>::value>::type
1000
>
1001
typename std::decay<T>::type
1002
operator|( result<T, E> const& r, U&& u )
1003
{
1004
    if( r )
1005
    {
1006
        return r.unsafe_value();
1007
    }
1008
    else
1009
    {
1010
        return std::forward<U>( u );
1011
    }
1012
}
1013
1014
template<class T, class E, class U,
1015
    class En = typename std::enable_if<std::is_convertible<U, typename std::decay<T>::type>::value>::type
1016
>
1017
typename std::decay<T>::type
1018
operator|( result<T, E>&& r, U&& u )
1019
{
1020
    if( r )
1021
    {
1022
        return std::move( r ).unsafe_value();
1023
    }
1024
    else
1025
    {
1026
        return std::forward<U>( u );
1027
    }
1028
}
1029
1030
// result | nullary-returning-value
1031
1032
template<class T, class E, class F,
1033
    class U = decltype( std::declval<F>()() ),
1034
    class En = typename std::enable_if<detail::is_value_convertible_to<U, T>::value>::type
1035
>
1036
T operator|( result<T, E> const& r, F&& f )
1037
{
1038
    if( r )
1039
    {
1040
        return r.unsafe_value();
1041
    }
1042
    else
1043
    {
1044
        return std::forward<F>( f )();
1045
    }
1046
}
1047
1048
template<class T, class E, class F,
1049
    class U = decltype( std::declval<F>()() ),
1050
    class En = typename std::enable_if<detail::is_value_convertible_to<U, T>::value>::type
1051
>
1052
T operator|( result<T, E>&& r, F&& f )
1053
{
1054
    if( r )
1055
    {
1056
        return std::move( r ).unsafe_value();
1057
    }
1058
    else
1059
    {
1060
        return std::forward<F>( f )();
1061
    }
1062
}
1063
1064
template<class T, class E, class F,
1065
    class U = decltype( std::declval<F>()() ),
1066
    class En = typename std::enable_if<
1067
        std::is_convertible<U, typename std::decay<T>::type>::value &&
1068
        !detail::is_value_convertible_to<U, T&>::value
1069
    >::type
1070
>
1071
typename std::decay<T>::type
1072
operator|( result<T&, E> const& r, F&& f )
1073
{
1074
    if( r )
1075
    {
1076
        return r.unsafe_value();
1077
    }
1078
    else
1079
    {
1080
        return std::forward<F>( f )();
1081
    }
1082
}
1083
1084
// result | nullary-returning-result
1085
1086
template<class T, class E, class F,
1087
    class U = decltype( std::declval<F>()() ),
1088
    class En1 = typename std::enable_if<detail::is_result<U>::value>::type,
1089
    class En2 = typename std::enable_if<detail::is_value_convertible_to<T, typename U::value_type>::value>::type
1090
>
1091
U operator|( result<T, E> const& r, F&& f )
1092
{
1093
    if( r )
1094
    {
1095
        return r.unsafe_value();
1096
    }
1097
    else
1098
    {
1099
        return std::forward<F>( f )();
1100
    }
1101
}
1102
1103
template<class T, class E, class F,
1104
    class U = decltype( std::declval<F>()() ),
1105
    class En1 = typename std::enable_if<detail::is_result<U>::value>::type,
1106
    class En2 = typename std::enable_if<detail::is_value_convertible_to<T, typename U::value_type>::value>::type
1107
>
1108
U operator|( result<T, E>&& r, F&& f )
1109
{
1110
    if( r )
1111
    {
1112
        return std::move( r ).unsafe_value();
1113
    }
1114
    else
1115
    {
1116
        return std::forward<F>( f )();
1117
    }
1118
}
1119
1120
template<class E, class F,
1121
    class U = decltype( std::declval<F>()() ),
1122
    class En1 = typename std::enable_if<detail::is_result<U>::value>::type,
1123
    class En2 = typename std::enable_if<std::is_void<typename U::value_type>::value>::type
1124
>
1125
U operator|( result<void, E> const& r, F&& f )
1126
{
1127
    if( r )
1128
    {
1129
        return {};
1130
    }
1131
    else
1132
    {
1133
        return std::forward<F>( f )();
1134
    }
1135
}
1136
1137
template<class E, class F,
1138
    class U = decltype( std::declval<F>()() ),
1139
    class En1 = typename std::enable_if<detail::is_result<U>::value>::type,
1140
    class En2 = typename std::enable_if<std::is_void<typename U::value_type>::value>::type
1141
>
1142
U operator|( result<void, E>&& r, F&& f )
1143
{
1144
    if( r )
1145
    {
1146
        return {};
1147
    }
1148
    else
1149
    {
1150
        return std::forward<F>( f )();
1151
    }
1152
}
1153
1154
// operator|=
1155
1156
// result |= value
1157
1158
template<class T, class E, class U,
1159
    class En = typename std::enable_if<detail::is_value_convertible_to<U, T>::value>::type
1160
>
1161
result<T, E>& operator|=( result<T, E>& r, U&& u )
1162
{
1163
    if( !r )
1164
    {
1165
        r = std::forward<U>( u );
1166
    }
1167
1168
    return r;
1169
}
1170
1171
// result |= nullary-returning-value
1172
1173
template<class T, class E, class F,
1174
    class U = decltype( std::declval<F>()() ),
1175
    class En = typename std::enable_if<detail::is_value_convertible_to<U, T>::value>::type
1176
>
1177
result<T, E>& operator|=( result<T, E>& r, F&& f )
1178
{
1179
    if( !r )
1180
    {
1181
        r = std::forward<F>( f )();
1182
    }
1183
1184
    return r;
1185
}
1186
1187
// result |= nullary-returning-result
1188
1189
template<class T, class E, class F,
1190
    class U = decltype( std::declval<F>()() ),
1191
    class En1 = typename std::enable_if<detail::is_result<U>::value>::type,
1192
    class En2 = typename std::enable_if<detail::is_value_convertible_to<typename U::value_type, T>::value>::type,
1193
    class En3 = typename std::enable_if<std::is_convertible<typename U::error_type, E>::value>::type
1194
>
1195
result<T, E>& operator|=( result<T, E>& r, F&& f )
1196
{
1197
    if( !r )
1198
    {
1199
        r = std::forward<F>( f )();
1200
    }
1201
1202
    return r;
1203
}
1204
1205
// operator&
1206
1207
// result & unary-returning-value
1208
1209
template<class T, class E, class F,
1210
    class U = compat::invoke_result_t<F, T&>,
1211
    class En1 = typename std::enable_if<!detail::is_result<U>::value>::type,
1212
    class En2 = typename std::enable_if<!std::is_void<U>::value>::type
1213
>
1214
result<U, E> operator&( result<T, E>& r, F&& f )
1215
{
1216
    if( r.has_error() )
1217
    {
1218
        return r.error();
1219
    }
1220
    else
1221
    {
1222
        return compat::invoke( std::forward<F>( f ), r.unsafe_value() );
1223
    }
1224
}
1225
1226
template<class T, class E, class F,
1227
    class U = compat::invoke_result_t<F, T const&>,
1228
    class En1 = typename std::enable_if<!detail::is_result<U>::value>::type,
1229
    class En2 = typename std::enable_if<!std::is_void<U>::value>::type
1230
>
1231
result<U, E> operator&( result<T, E> const& r, F&& f )
1232
{
1233
    if( r.has_error() )
1234
    {
1235
        return r.error();
1236
    }
1237
    else
1238
    {
1239
        return compat::invoke( std::forward<F>( f ), r.unsafe_value() );
1240
    }
1241
}
1242
1243
template<class T, class E, class F,
1244
    class U = typename std::decay< compat::invoke_result_t<F, T> >::type,
1245
    class En1 = typename std::enable_if<!detail::is_result<U>::value>::type,
1246
    class En2 = typename std::enable_if<!std::is_void<U>::value>::type
1247
>
1248
result<U, E> operator&( result<T, E>&& r, F&& f )
1249
{
1250
    if( r.has_error() )
1251
    {
1252
        return r.error();
1253
    }
1254
    else
1255
    {
1256
        return compat::invoke( std::forward<F>( f ), std::move( r ).unsafe_value() );
1257
    }
1258
}
1259
1260
template<class T, class E, class F,
1261
    class U = compat::invoke_result_t<F, T&>,
1262
    class En1 = typename std::enable_if<!detail::is_result<U>::value>::type,
1263
    class En2 = typename std::enable_if<!std::is_void<U>::value>::type
1264
>
1265
result<U, E> operator&( result<T&, E>&& r, F&& f )
1266
{
1267
    if( r.has_error() )
1268
    {
1269
        return r.error();
1270
    }
1271
    else
1272
    {
1273
        return compat::invoke( std::forward<F>( f ), std::move( r ).unsafe_value() );
1274
    }
1275
}
1276
1277
template<class T, class E, class F,
1278
    class U = compat::invoke_result_t<F, T const&>,
1279
    class En = typename std::enable_if<std::is_void<U>::value>::type
1280
>
1281
result<U, E> operator&( result<T, E> const& r, F&& f )
1282
{
1283
    if( r.has_error() )
1284
    {
1285
        return r.error();
1286
    }
1287
    else
1288
    {
1289
        compat::invoke( std::forward<F>( f ), r.unsafe_value() );
1290
        return {};
1291
    }
1292
}
1293
1294
template<class T, class E, class F,
1295
    class U = compat::invoke_result_t<F, T>,
1296
    class En = typename std::enable_if<std::is_void<U>::value>::type
1297
>
1298
result<U, E> operator&( result<T, E>&& r, F&& f )
1299
{
1300
    if( r.has_error() )
1301
    {
1302
        return r.error();
1303
    }
1304
    else
1305
    {
1306
        compat::invoke( std::forward<F>( f ), std::move( r ).unsafe_value() );
1307
        return {};
1308
    }
1309
}
1310
1311
template<class E, class F,
1312
    class U = decltype( std::declval<F>()() ),
1313
    class En1 = typename std::enable_if<!detail::is_result<U>::value>::type,
1314
    class En2 = typename std::enable_if<!std::is_void<U>::value>::type
1315
>
1316
result<U, E> operator&( result<void, E> const& r, F&& f )
1317
{
1318
    if( r.has_error() )
1319
    {
1320
        return r.error();
1321
    }
1322
    else
1323
    {
1324
        return std::forward<F>( f )();
1325
    }
1326
}
1327
1328
template<class E, class F,
1329
    class U = decltype( std::declval<F>()() ),
1330
    class En = typename std::enable_if<std::is_void<U>::value>::type
1331
>
1332
result<U, E> operator&( result<void, E> const& r, F&& f )
1333
{
1334
    if( r.has_error() )
1335
    {
1336
        return r.error();
1337
    }
1338
    else
1339
    {
1340
        std::forward<F>( f )();
1341
        return {};
1342
    }
1343
}
1344
1345
// result & unary-returning-result
1346
1347
template<class T, class E, class F,
1348
    class U = typename std::decay< compat::invoke_result_t<F, T&> >::type,
1349
    class En1 = typename std::enable_if<detail::is_result<U>::value>::type,
1350
    class En2 = typename std::enable_if<std::is_convertible<E, typename U::error_type>::value>::type
1351
>
1352
U operator&( result<T, E>& r, F&& f )
1353
{
1354
    if( r.has_error() )
1355
    {
1356
        return r.error();
1357
    }
1358
    else
1359
    {
1360
        return compat::invoke( std::forward<F>( f ), r.unsafe_value() );
1361
    }
1362
}
1363
1364
template<class T, class E, class F,
1365
    class U = typename std::decay< compat::invoke_result_t<F, T const&> >::type,
1366
    class En1 = typename std::enable_if<detail::is_result<U>::value>::type,
1367
    class En2 = typename std::enable_if<std::is_convertible<E, typename U::error_type>::value>::type
1368
>
1369
U operator&( result<T, E> const& r, F&& f )
1370
{
1371
    if( r.has_error() )
1372
    {
1373
        return r.error();
1374
    }
1375
    else
1376
    {
1377
        return compat::invoke( std::forward<F>( f ), r.unsafe_value() );
1378
    }
1379
}
1380
1381
template<class T, class E, class F,
1382
    class U = typename std::decay< compat::invoke_result_t<F, T> >::type,
1383
    class En1 = typename std::enable_if<detail::is_result<U>::value>::type,
1384
    class En2 = typename std::enable_if<std::is_convertible<E, typename U::error_type>::value>::type
1385
>
1386
U operator&( result<T, E>&& r, F&& f )
1387
{
1388
    if( r.has_error() )
1389
    {
1390
        return r.error();
1391
    }
1392
    else
1393
    {
1394
        return compat::invoke( std::forward<F>( f ), std::move( r ).unsafe_value() );
1395
    }
1396
}
1397
1398
template<class E, class F,
1399
    class U = decltype( std::declval<F>()() ),
1400
    class En1 = typename std::enable_if<detail::is_result<U>::value>::type,
1401
    class En2 = typename std::enable_if<std::is_convertible<E, typename U::error_type>::value>::type
1402
>
1403
U operator&( result<void, E> const& r, F&& f )
1404
{
1405
    if( r.has_error() )
1406
    {
1407
        return r.error();
1408
    }
1409
    else
1410
    {
1411
        return std::forward<F>( f )();
1412
    }
1413
}
1414
1415
// operator&=
1416
1417
// result &= unary-returning-value
1418
1419
template<class T, class E, class F,
1420
    class U = decltype( std::declval<F>()( std::declval<T>() ) ),
1421
    class En1 = typename std::enable_if<!detail::is_result<U>::value>::type,
1422
    class En2 = typename std::enable_if<detail::is_value_convertible_to<U, T>::value>::type
1423
>
1424
result<T, E>& operator&=( result<T, E>& r, F&& f )
1425
{
1426
    if( r )
1427
    {
1428
        r = std::forward<F>( f )( std::move( r ).unsafe_value() );
1429
    }
1430
1431
    return r;
1432
}
1433
1434
template<class E, class F,
1435
    class U = decltype( std::declval<F>()() ),
1436
    class En = typename std::enable_if<!detail::is_result<U>::value>::type
1437
>
1438
result<void, E>& operator&=( result<void, E>& r, F&& f )
1439
{
1440
    if( r )
1441
    {
1442
        std::forward<F>( f )();
1443
    }
1444
1445
    return r;
1446
}
1447
1448
// result &= unary-returning-result
1449
1450
template<class T, class E, class F,
1451
    class U = decltype( std::declval<F>()( std::declval<T>() ) ),
1452
    class En1 = typename std::enable_if<detail::is_result<U>::value>::type,
1453
    class En2 = typename std::enable_if<detail::is_value_convertible_to<typename U::value_type, T>::value>::type,
1454
    class En3 = typename std::enable_if<std::is_convertible<typename U::error_type, E>::value>::type
1455
>
1456
result<T, E>& operator&=( result<T, E>& r, F&& f )
1457
{
1458
    if( r )
1459
    {
1460
        r = std::forward<F>( f )( std::move( r ).unsafe_value() );
1461
    }
1462
1463
    return r;
1464
}
1465
1466
template<class E, class F,
1467
    class U = decltype( std::declval<F>()() ),
1468
    class En1 = typename std::enable_if<detail::is_result<U>::value>::type,
1469
    class En2 = typename std::enable_if<std::is_void<typename U::value_type>::value>::type,
1470
    class En3 = typename std::enable_if<std::is_convertible<typename U::error_type, E>::value>::type
1471
>
1472
result<void, E>& operator&=( result<void, E>& r, F&& f )
1473
{
1474
    if( r )
1475
    {
1476
        r = std::forward<F>( f )();
1477
    }
1478
1479
    return r;
1480
}
1481
1482
} // namespace system
1483
} // namespace boost
1484
1485
#endif // #ifndef BOOST_SYSTEM_RESULT_HPP_INCLUDED