/tmp/bitcoin/src/util/expected.h
Line | Count | Source |
1 | | // Copyright (c) The Bitcoin Core developers |
2 | | // Distributed under the MIT software license, see the accompanying |
3 | | // file COPYING or https://opensource.org/license/mit. |
4 | | |
5 | | #ifndef BITCOIN_UTIL_EXPECTED_H |
6 | | #define BITCOIN_UTIL_EXPECTED_H |
7 | | |
8 | | #include <attributes.h> |
9 | | #include <util/check.h> |
10 | | |
11 | | #include <exception> |
12 | | #include <utility> |
13 | | #include <variant> |
14 | | |
15 | | namespace util { |
16 | | |
17 | | /// The util::Unexpected class represents an unexpected value stored in |
18 | | /// util::Expected. |
19 | | template <class E> |
20 | | class Unexpected |
21 | | { |
22 | | public: |
23 | 152 | constexpr explicit Unexpected(E e) : m_error(std::move(e)) {}util::Unexpected<std::unique_ptr<int, std::default_delete<int>>>::Unexpected(std::unique_ptr<int, std::default_delete<int>>) Line | Count | Source | 23 | 4 | constexpr explicit Unexpected(E e) : m_error(std::move(e)) {} |
Unexecuted instantiation: util::Unexpected<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::Unexpected(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>) util::Unexpected<ThreadPool::SubmitError>::Unexpected(ThreadPool::SubmitError) Line | Count | Source | 23 | 7 | constexpr explicit Unexpected(E e) : m_error(std::move(e)) {} |
util::Unexpected<int>::Unexpected(int) Line | Count | Source | 23 | 1 | constexpr explicit Unexpected(E e) : m_error(std::move(e)) {} |
util::Unexpected<char const*>::Unexpected(char const*) Line | Count | Source | 23 | 6 | constexpr explicit Unexpected(E e) : m_error(std::move(e)) {} |
util::Unexpected<node::ReadRawError>::Unexpected(node::ReadRawError) Line | Count | Source | 23 | 134 | constexpr explicit Unexpected(E e) : m_error(std::move(e)) {} |
|
24 | | |
25 | 1 | constexpr const E& error() const& noexcept LIFETIMEBOUND { return m_error; } |
26 | 2 | constexpr E& error() & noexcept LIFETIMEBOUND { return m_error; } |
27 | 152 | constexpr E&& error() && noexcept LIFETIMEBOUND { return std::move(m_error); }util::Unexpected<ThreadPool::SubmitError>::error() && Line | Count | Source | 27 | 7 | constexpr E&& error() && noexcept LIFETIMEBOUND { return std::move(m_error); } |
util::Unexpected<int>::error() && Line | Count | Source | 27 | 1 | constexpr E&& error() && noexcept LIFETIMEBOUND { return std::move(m_error); } |
util::Unexpected<char const*>::error() && Line | Count | Source | 27 | 6 | constexpr E&& error() && noexcept LIFETIMEBOUND { return std::move(m_error); } |
util::Unexpected<std::unique_ptr<int, std::default_delete<int>>>::error() && Line | Count | Source | 27 | 4 | constexpr E&& error() && noexcept LIFETIMEBOUND { return std::move(m_error); } |
Unexecuted instantiation: util::Unexpected<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::error() && util::Unexpected<node::ReadRawError>::error() && Line | Count | Source | 27 | 134 | constexpr E&& error() && noexcept LIFETIMEBOUND { return std::move(m_error); } |
|
28 | | |
29 | | private: |
30 | | E m_error; |
31 | | }; |
32 | | |
33 | | struct BadExpectedAccess : std::exception { |
34 | 0 | const char* what() const noexcept override { return "Bad util::Expected access"; } |
35 | | }; |
36 | | |
37 | | /// The util::Expected class provides a standard way for low-level functions to |
38 | | /// return either error values or result values. |
39 | | /// |
40 | | /// It provides a smaller version of std::expected from C++23. Missing features |
41 | | /// can be added, if needed. |
42 | | template <class T, class E> |
43 | | class Expected |
44 | | { |
45 | | private: |
46 | | std::variant<T, E> m_data; |
47 | | |
48 | | public: |
49 | 1 | constexpr Expected() : m_data{std::in_place_index<0>, T{}} {} |
50 | 328k | constexpr Expected(T v) : m_data{std::in_place_index<0>, std::move(v)} {}util::Expected<std::future<void>, ThreadPool::SubmitError>::Expected(std::future<void>) Line | Count | Source | 50 | 171k | constexpr Expected(T v) : m_data{std::in_place_index<0>, std::move(v)} {} |
util::Expected<std::future<bool>, ThreadPool::SubmitError>::Expected(std::future<bool>) Line | Count | Source | 50 | 2 | constexpr Expected(T v) : m_data{std::in_place_index<0>, std::move(v)} {} |
util::Expected<std::future<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>, ThreadPool::SubmitError>::Expected(std::future<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>) Line | Count | Source | 50 | 1 | constexpr Expected(T v) : m_data{std::in_place_index<0>, std::move(v)} {} |
Unexecuted instantiation: util::Expected<std::vector<std::future<void>, std::allocator<std::future<void>>>, ThreadPool::SubmitError>::Expected(std::vector<std::future<void>, std::allocator<std::future<void>>>) util::Expected<std::vector<std::future<int>, std::allocator<std::future<int>>>, ThreadPool::SubmitError>::Expected(std::vector<std::future<int>, std::allocator<std::future<int>>>) Line | Count | Source | 50 | 2 | constexpr Expected(T v) : m_data{std::in_place_index<0>, std::move(v)} {} |
util_expected_tests.cpp:util::Expected<util_expected_tests::expected_value::test_method()::Obj, int>::Expected(util_expected_tests::expected_value::test_method()::Obj) Line | Count | Source | 50 | 1 | constexpr Expected(T v) : m_data{std::in_place_index<0>, std::move(v)} {} |
util::Expected<std::unique_ptr<int, std::default_delete<int>>, int>::Expected(std::unique_ptr<int, std::default_delete<int>>) Line | Count | Source | 50 | 3 | constexpr Expected(T v) : m_data{std::in_place_index<0>, std::move(v)} {} |
util::Expected<char const*, std::unique_ptr<int, std::default_delete<int>>>::Expected(char const*) Line | Count | Source | 50 | 1 | constexpr Expected(T v) : m_data{std::in_place_index<0>, std::move(v)} {} |
util::Expected<TxoSpender, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::Expected(TxoSpender) Line | Count | Source | 50 | 20 | constexpr Expected(T v) : m_data{std::in_place_index<0>, std::move(v)} {} |
util::Expected<std::optional<TxoSpender>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::Expected(std::optional<TxoSpender>) Line | Count | Source | 50 | 35 | constexpr Expected(T v) : m_data{std::in_place_index<0>, std::move(v)} {} |
util::Expected<std::vector<std::byte, std::allocator<std::byte>>, node::ReadRawError>::Expected(std::vector<std::byte, std::allocator<std::byte>>) Line | Count | Source | 50 | 156k | constexpr Expected(T v) : m_data{std::in_place_index<0>, std::move(v)} {} |
|
51 | | template <class Err> |
52 | 145 | constexpr Expected(Unexpected<Err> u) : m_data{std::in_place_index<1>, std::move(u).error()} |
53 | 145 | { |
54 | 145 | } util::Expected<std::future<void>, ThreadPool::SubmitError>::Expected<ThreadPool::SubmitError>(util::Unexpected<ThreadPool::SubmitError>) Line | Count | Source | 52 | 5 | constexpr Expected(Unexpected<Err> u) : m_data{std::in_place_index<1>, std::move(u).error()} | 53 | 5 | { | 54 | 5 | } |
Unexecuted instantiation: util::Expected<std::future<bool>, ThreadPool::SubmitError>::Expected<ThreadPool::SubmitError>(util::Unexpected<ThreadPool::SubmitError>) Unexecuted instantiation: util::Expected<std::future<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>, ThreadPool::SubmitError>::Expected<ThreadPool::SubmitError>(util::Unexpected<ThreadPool::SubmitError>) util::Expected<std::vector<std::future<void>, std::allocator<std::future<void>>>, ThreadPool::SubmitError>::Expected<ThreadPool::SubmitError>(util::Unexpected<ThreadPool::SubmitError>) Line | Count | Source | 52 | 2 | constexpr Expected(Unexpected<Err> u) : m_data{std::in_place_index<1>, std::move(u).error()} | 53 | 2 | { | 54 | 2 | } |
Unexecuted instantiation: util::Expected<std::vector<std::future<int>, std::allocator<std::future<int>>>, ThreadPool::SubmitError>::Expected<ThreadPool::SubmitError>(util::Unexpected<ThreadPool::SubmitError>) util::Expected<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, int>::Expected<int>(util::Unexpected<int>) Line | Count | Source | 52 | 1 | constexpr Expected(Unexpected<Err> u) : m_data{std::in_place_index<1>, std::move(u).error()} | 53 | 1 | { | 54 | 1 | } |
util::Expected<int, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::Expected<char const*>(util::Unexpected<char const*>) Line | Count | Source | 52 | 1 | constexpr Expected(Unexpected<Err> u) : m_data{std::in_place_index<1>, std::move(u).error()} | 53 | 1 | { | 54 | 1 | } |
util::Expected<int, std::unique_ptr<int, std::default_delete<int>>>::Expected<std::unique_ptr<int, std::default_delete<int>>>(util::Unexpected<std::unique_ptr<int, std::default_delete<int>>>) Line | Count | Source | 52 | 1 | constexpr Expected(Unexpected<Err> u) : m_data{std::in_place_index<1>, std::move(u).error()} | 53 | 1 | { | 54 | 1 | } |
util::Expected<char const*, std::unique_ptr<int, std::default_delete<int>>>::Expected<std::unique_ptr<int, std::default_delete<int>>>(util::Unexpected<std::unique_ptr<int, std::default_delete<int>>>) Line | Count | Source | 52 | 1 | constexpr Expected(Unexpected<Err> u) : m_data{std::in_place_index<1>, std::move(u).error()} | 53 | 1 | { | 54 | 1 | } |
Unexecuted instantiation: util::Expected<TxoSpender, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::Expected<char const*>(util::Unexpected<char const*>) Unexecuted instantiation: util::Expected<std::optional<TxoSpender>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::Expected<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>(util::Unexpected<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>) util::Expected<std::vector<std::byte, std::allocator<std::byte>>, node::ReadRawError>::Expected<node::ReadRawError>(util::Unexpected<node::ReadRawError>) Line | Count | Source | 52 | 134 | constexpr Expected(Unexpected<Err> u) : m_data{std::in_place_index<1>, std::move(u).error()} | 53 | 134 | { | 54 | 134 | } |
|
55 | | |
56 | 485k | constexpr bool has_value() const noexcept { return m_data.index() == 0; }util::Expected<std::vector<std::byte, std::allocator<std::byte>>, node::ReadRawError>::has_value() const Line | Count | Source | 56 | 313k | constexpr bool has_value() const noexcept { return m_data.index() == 0; } |
util::Expected<std::future<void>, ThreadPool::SubmitError>::has_value() const Line | Count | Source | 56 | 171k | constexpr bool has_value() const noexcept { return m_data.index() == 0; } |
util::Expected<std::vector<std::future<void>, std::allocator<std::future<void>>>, ThreadPool::SubmitError>::has_value() const Line | Count | Source | 56 | 2 | constexpr bool has_value() const noexcept { return m_data.index() == 0; } |
util::Expected<std::future<bool>, ThreadPool::SubmitError>::has_value() const Line | Count | Source | 56 | 4 | constexpr bool has_value() const noexcept { return m_data.index() == 0; } |
util::Expected<std::future<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>, ThreadPool::SubmitError>::has_value() const Line | Count | Source | 56 | 2 | constexpr bool has_value() const noexcept { return m_data.index() == 0; } |
util::Expected<std::vector<std::future<int>, std::allocator<std::future<int>>>, ThreadPool::SubmitError>::has_value() const Line | Count | Source | 56 | 4 | constexpr bool has_value() const noexcept { return m_data.index() == 0; } |
util::Expected<std::optional<TxoSpender>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::has_value() const Line | Count | Source | 56 | 80 | constexpr bool has_value() const noexcept { return m_data.index() == 0; } |
util_expected_tests.cpp:util::Expected<util_expected_tests::expected_value::test_method()::Obj, int>::has_value() const Line | Count | Source | 56 | 12 | constexpr bool has_value() const noexcept { return m_data.index() == 0; } |
util::Expected<std::unique_ptr<int, std::default_delete<int>>, int>::has_value() const Line | Count | Source | 56 | 4 | constexpr bool has_value() const noexcept { return m_data.index() == 0; } |
util::Expected<int, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::has_value() const Line | Count | Source | 56 | 1 | constexpr bool has_value() const noexcept { return m_data.index() == 0; } |
util::Expected<char const*, std::unique_ptr<int, std::default_delete<int>>>::has_value() const Line | Count | Source | 56 | 1 | constexpr bool has_value() const noexcept { return m_data.index() == 0; } |
util::Expected<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, int>::has_value() const Line | Count | Source | 56 | 1 | constexpr bool has_value() const noexcept { return m_data.index() == 0; } |
util::Expected<TxoSpender, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::has_value() const Line | Count | Source | 56 | 60 | constexpr bool has_value() const noexcept { return m_data.index() == 0; } |
|
57 | 157k | constexpr explicit operator bool() const noexcept { return has_value(); }util::Expected<std::vector<std::byte, std::allocator<std::byte>>, node::ReadRawError>::operator bool() const Line | Count | Source | 57 | 156k | constexpr explicit operator bool() const noexcept { return has_value(); } |
util::Expected<std::future<void>, ThreadPool::SubmitError>::operator bool() const Line | Count | Source | 57 | 366 | constexpr explicit operator bool() const noexcept { return has_value(); } |
util::Expected<std::vector<std::future<void>, std::allocator<std::future<void>>>, ThreadPool::SubmitError>::operator bool() const Line | Count | Source | 57 | 2 | constexpr explicit operator bool() const noexcept { return has_value(); } |
util::Expected<std::future<bool>, ThreadPool::SubmitError>::operator bool() const Line | Count | Source | 57 | 2 | constexpr explicit operator bool() const noexcept { return has_value(); } |
util::Expected<std::future<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>, ThreadPool::SubmitError>::operator bool() const Line | Count | Source | 57 | 1 | constexpr explicit operator bool() const noexcept { return has_value(); } |
util::Expected<std::vector<std::future<int>, std::allocator<std::future<int>>>, ThreadPool::SubmitError>::operator bool() const Line | Count | Source | 57 | 2 | constexpr explicit operator bool() const noexcept { return has_value(); } |
util_expected_tests.cpp:util::Expected<util_expected_tests::expected_value::test_method()::Obj, int>::operator bool() const Line | Count | Source | 57 | 1 | constexpr explicit operator bool() const noexcept { return has_value(); } |
util::Expected<TxoSpender, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::operator bool() const Line | Count | Source | 57 | 20 | constexpr explicit operator bool() const noexcept { return has_value(); } |
util::Expected<std::optional<TxoSpender>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::operator bool() const Line | Count | Source | 57 | 15 | constexpr explicit operator bool() const noexcept { return has_value(); } |
|
58 | | |
59 | | constexpr const T& value() const& LIFETIMEBOUND |
60 | 153k | { |
61 | 153k | if (!has_value()) { |
62 | 1 | throw BadExpectedAccess{}; |
63 | 1 | } |
64 | 153k | return std::get<0>(m_data); |
65 | 153k | } util::Expected<std::optional<TxoSpender>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::value() const & Line | Count | Source | 60 | 45 | { | 61 | 45 | if (!has_value()) { | 62 | 0 | throw BadExpectedAccess{}; | 63 | 0 | } | 64 | 45 | return std::get<0>(m_data); | 65 | 45 | } |
util_expected_tests.cpp:util::Expected<util_expected_tests::expected_value::test_method()::Obj, int>::value() const & Line | Count | Source | 60 | 3 | { | 61 | 3 | if (!has_value()) { | 62 | 0 | throw BadExpectedAccess{}; | 63 | 0 | } | 64 | 3 | return std::get<0>(m_data); | 65 | 3 | } |
util::Expected<int, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::value() const & Line | Count | Source | 60 | 1 | { | 61 | 1 | if (!has_value()) { | 62 | 1 | throw BadExpectedAccess{}; | 63 | 1 | } | 64 | 0 | return std::get<0>(m_data); | 65 | 1 | } |
Unexecuted instantiation: util::Expected<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>, int>::value() const & util::Expected<TxoSpender, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::value() const & Line | Count | Source | 60 | 40 | { | 61 | 40 | if (!has_value()) { | 62 | 0 | throw BadExpectedAccess{}; | 63 | 0 | } | 64 | 40 | return std::get<0>(m_data); | 65 | 40 | } |
util::Expected<std::vector<std::byte, std::allocator<std::byte>>, node::ReadRawError>::value() const & Line | Count | Source | 60 | 153k | { | 61 | 153k | if (!has_value()) { | 62 | 0 | throw BadExpectedAccess{}; | 63 | 0 | } | 64 | 153k | return std::get<0>(m_data); | 65 | 153k | } |
|
66 | | constexpr T& value() & LIFETIMEBOUND |
67 | 3.36k | { |
68 | 3.36k | if (!has_value()) { |
69 | 0 | throw BadExpectedAccess{}; |
70 | 0 | } |
71 | 3.36k | return std::get<0>(m_data); |
72 | 3.36k | } util::Expected<std::vector<std::byte, std::allocator<std::byte>>, node::ReadRawError>::value() & Line | Count | Source | 67 | 2.97k | { | 68 | 2.97k | if (!has_value()) { | 69 | 0 | throw BadExpectedAccess{}; | 70 | 0 | } | 71 | 2.97k | return std::get<0>(m_data); | 72 | 2.97k | } |
util::Expected<std::future<void>, ThreadPool::SubmitError>::value() & Line | Count | Source | 67 | 361 | { | 68 | 361 | if (!has_value()) { | 69 | 0 | throw BadExpectedAccess{}; | 70 | 0 | } | 71 | 361 | return std::get<0>(m_data); | 72 | 361 | } |
util::Expected<std::future<bool>, ThreadPool::SubmitError>::value() & Line | Count | Source | 67 | 2 | { | 68 | 2 | if (!has_value()) { | 69 | 0 | throw BadExpectedAccess{}; | 70 | 0 | } | 71 | 2 | return std::get<0>(m_data); | 72 | 2 | } |
util::Expected<std::future<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>, ThreadPool::SubmitError>::value() & Line | Count | Source | 67 | 1 | { | 68 | 1 | if (!has_value()) { | 69 | 0 | throw BadExpectedAccess{}; | 70 | 0 | } | 71 | 1 | return std::get<0>(m_data); | 72 | 1 | } |
util::Expected<std::vector<std::future<int>, std::allocator<std::future<int>>>, ThreadPool::SubmitError>::value() & Line | Count | Source | 67 | 2 | { | 68 | 2 | if (!has_value()) { | 69 | 0 | throw BadExpectedAccess{}; | 70 | 0 | } | 71 | 2 | return std::get<0>(m_data); | 72 | 2 | } |
util::Expected<std::optional<TxoSpender>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::value() & Line | Count | Source | 67 | 10 | { | 68 | 10 | if (!has_value()) { | 69 | 0 | throw BadExpectedAccess{}; | 70 | 0 | } | 71 | 10 | return std::get<0>(m_data); | 72 | 10 | } |
util_expected_tests.cpp:util::Expected<util_expected_tests::expected_value::test_method()::Obj, int>::value() & Line | Count | Source | 67 | 7 | { | 68 | 7 | if (!has_value()) { | 69 | 0 | throw BadExpectedAccess{}; | 70 | 0 | } | 71 | 7 | return std::get<0>(m_data); | 72 | 7 | } |
util::Expected<std::unique_ptr<int, std::default_delete<int>>, int>::value() & Line | Count | Source | 67 | 3 | { | 68 | 3 | if (!has_value()) { | 69 | 0 | throw BadExpectedAccess{}; | 70 | 0 | } | 71 | 3 | return std::get<0>(m_data); | 72 | 3 | } |
util::Expected<char const*, std::unique_ptr<int, std::default_delete<int>>>::value() & Line | Count | Source | 67 | 1 | { | 68 | 1 | if (!has_value()) { | 69 | 0 | throw BadExpectedAccess{}; | 70 | 0 | } | 71 | 1 | return std::get<0>(m_data); | 72 | 1 | } |
|
73 | 11 | constexpr T&& value() && LIFETIMEBOUND { return std::move(value()); }util::Expected<std::optional<TxoSpender>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::value() && Line | Count | Source | 73 | 10 | constexpr T&& value() && LIFETIMEBOUND { return std::move(value()); } |
util::Expected<std::unique_ptr<int, std::default_delete<int>>, int>::value() && Line | Count | Source | 73 | 1 | constexpr T&& value() && LIFETIMEBOUND { return std::move(value()); } |
|
74 | | |
75 | | template <class U> |
76 | | T value_or(U&& default_value) const& |
77 | 1 | { |
78 | 1 | return has_value() ? value() : std::forward<U>(default_value); |
79 | 1 | } |
80 | | template <class U> |
81 | | T value_or(U&& default_value) && |
82 | 1 | { |
83 | 1 | return has_value() ? std::move(value()) : std::forward<U>(default_value); |
84 | 1 | } |
85 | | |
86 | 14 | constexpr const E& error() const& noexcept LIFETIMEBOUND { return *Assert(std::get_if<1>(&m_data)); }util::Expected<std::vector<std::future<void>, std::allocator<std::future<void>>>, ThreadPool::SubmitError>::error() const & Line | Count | Source | 86 | 2 | constexpr const E& error() const& noexcept LIFETIMEBOUND { return *Assert(std::get_if<1>(&m_data)); } |
Unexecuted instantiation: util::Expected<TxoSpender, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::error() const & util::Expected<std::vector<std::byte, std::allocator<std::byte>>, node::ReadRawError>::error() const & Line | Count | Source | 86 | 12 | constexpr const E& error() const& noexcept LIFETIMEBOUND { return *Assert(std::get_if<1>(&m_data)); } |
Unexecuted instantiation: util::Expected<std::optional<TxoSpender>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::error() const & |
87 | 21 | constexpr E& error() & noexcept LIFETIMEBOUND { return *Assert(std::get_if<1>(&m_data)); }util::Expected<std::vector<std::byte, std::allocator<std::byte>>, node::ReadRawError>::error() & Line | Count | Source | 87 | 14 | constexpr E& error() & noexcept LIFETIMEBOUND { return *Assert(std::get_if<1>(&m_data)); } |
util::Expected<std::future<void>, ThreadPool::SubmitError>::error() & Line | Count | Source | 87 | 5 | constexpr E& error() & noexcept LIFETIMEBOUND { return *Assert(std::get_if<1>(&m_data)); } |
util::Expected<int, std::unique_ptr<int, std::default_delete<int>>>::error() & Line | Count | Source | 87 | 1 | constexpr E& error() & noexcept LIFETIMEBOUND { return *Assert(std::get_if<1>(&m_data)); } |
util::Expected<char const*, std::unique_ptr<int, std::default_delete<int>>>::error() & Line | Count | Source | 87 | 1 | constexpr E& error() & noexcept LIFETIMEBOUND { return *Assert(std::get_if<1>(&m_data)); } |
|
88 | 1 | constexpr E&& error() && noexcept LIFETIMEBOUND { return std::move(error()); } |
89 | | |
90 | 1 | constexpr void swap(Expected& other) noexcept { m_data.swap(other.m_data); } |
91 | | |
92 | 2.93k | constexpr T& operator*() & noexcept LIFETIMEBOUND { return value(); }util_expected_tests.cpp:util::Expected<util_expected_tests::expected_value::test_method()::Obj, int>::operator*() & Line | Count | Source | 92 | 2 | constexpr T& operator*() & noexcept LIFETIMEBOUND { return value(); } |
util::Expected<std::vector<std::byte, std::allocator<std::byte>>, node::ReadRawError>::operator*() & Line | Count | Source | 92 | 2.93k | constexpr T& operator*() & noexcept LIFETIMEBOUND { return value(); } |
|
93 | 153k | constexpr const T& operator*() const& noexcept LIFETIMEBOUND { return value(); }util::Expected<std::optional<TxoSpender>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::operator*() const & Line | Count | Source | 93 | 20 | constexpr const T& operator*() const& noexcept LIFETIMEBOUND { return value(); } |
util_expected_tests.cpp:util::Expected<util_expected_tests::expected_value::test_method()::Obj, int>::operator*() const & Line | Count | Source | 93 | 1 | constexpr const T& operator*() const& noexcept LIFETIMEBOUND { return value(); } |
util::Expected<TxoSpender, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::operator*() const & Line | Count | Source | 93 | 20 | constexpr const T& operator*() const& noexcept LIFETIMEBOUND { return value(); } |
util::Expected<std::vector<std::byte, std::allocator<std::byte>>, node::ReadRawError>::operator*() const & Line | Count | Source | 93 | 153k | constexpr const T& operator*() const& noexcept LIFETIMEBOUND { return value(); } |
|
94 | 367 | constexpr T&& operator*() && noexcept LIFETIMEBOUND { return std::move(value()); }util::Expected<std::future<void>, ThreadPool::SubmitError>::operator*() && Line | Count | Source | 94 | 361 | constexpr T&& operator*() && noexcept LIFETIMEBOUND { return std::move(value()); } |
util::Expected<std::future<bool>, ThreadPool::SubmitError>::operator*() && Line | Count | Source | 94 | 2 | constexpr T&& operator*() && noexcept LIFETIMEBOUND { return std::move(value()); } |
util::Expected<std::future<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>, ThreadPool::SubmitError>::operator*() && Line | Count | Source | 94 | 1 | constexpr T&& operator*() && noexcept LIFETIMEBOUND { return std::move(value()); } |
util::Expected<std::vector<std::future<int>, std::allocator<std::future<int>>>, ThreadPool::SubmitError>::operator*() && Line | Count | Source | 94 | 2 | constexpr T&& operator*() && noexcept LIFETIMEBOUND { return std::move(value()); } |
util::Expected<std::unique_ptr<int, std::default_delete<int>>, int>::operator*() && Line | Count | Source | 94 | 1 | constexpr T&& operator*() && noexcept LIFETIMEBOUND { return std::move(value()); } |
|
95 | | |
96 | 33 | constexpr T* operator->() noexcept LIFETIMEBOUND { return &value(); }util::Expected<std::vector<std::byte, std::allocator<std::byte>>, node::ReadRawError>::operator->() Line | Count | Source | 96 | 31 | constexpr T* operator->() noexcept LIFETIMEBOUND { return &value(); } |
util_expected_tests.cpp:util::Expected<util_expected_tests::expected_value::test_method()::Obj, int>::operator->() Line | Count | Source | 96 | 2 | constexpr T* operator->() noexcept LIFETIMEBOUND { return &value(); } |
|
97 | 31 | constexpr const T* operator->() const noexcept LIFETIMEBOUND { return &value(); }util::Expected<std::optional<TxoSpender>, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::operator->() const Line | Count | Source | 97 | 10 | constexpr const T* operator->() const noexcept LIFETIMEBOUND { return &value(); } |
util_expected_tests.cpp:util::Expected<util_expected_tests::expected_value::test_method()::Obj, int>::operator->() const Line | Count | Source | 97 | 1 | constexpr const T* operator->() const noexcept LIFETIMEBOUND { return &value(); } |
util::Expected<TxoSpender, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::operator->() const Line | Count | Source | 97 | 20 | constexpr const T* operator->() const noexcept LIFETIMEBOUND { return &value(); } |
|
98 | | }; |
99 | | |
100 | | template <class E> |
101 | | class Expected<void, E> |
102 | | { |
103 | | private: |
104 | | std::variant<std::monostate, E> m_data; |
105 | | |
106 | | public: |
107 | 3 | constexpr Expected() : m_data{std::in_place_index<0>, std::monostate{}} {} |
108 | | template <class Err> |
109 | 6 | constexpr Expected(Unexpected<Err> u) : m_data{std::in_place_index<1>, std::move(u).error()} |
110 | 6 | { |
111 | 6 | } util::Expected<void, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::Expected<char const*>(util::Unexpected<char const*>) Line | Count | Source | 109 | 5 | constexpr Expected(Unexpected<Err> u) : m_data{std::in_place_index<1>, std::move(u).error()} | 110 | 5 | { | 111 | 5 | } |
util::Expected<void, std::unique_ptr<int, std::default_delete<int>>>::Expected<std::unique_ptr<int, std::default_delete<int>>>(util::Unexpected<std::unique_ptr<int, std::default_delete<int>>>) Line | Count | Source | 109 | 1 | constexpr Expected(Unexpected<Err> u) : m_data{std::in_place_index<1>, std::move(u).error()} | 110 | 1 | { | 111 | 1 | } |
|
112 | | |
113 | 11 | constexpr bool has_value() const noexcept { return m_data.index() == 0; } |
114 | 6 | constexpr explicit operator bool() const noexcept { return has_value(); } |
115 | | |
116 | 1 | constexpr void operator*() const noexcept { return value(); } |
117 | | constexpr void value() const |
118 | 3 | { |
119 | 3 | if (!has_value()) { |
120 | 1 | throw BadExpectedAccess{}; |
121 | 1 | } |
122 | 3 | } |
123 | | |
124 | 4 | constexpr const E& error() const& noexcept LIFETIMEBOUND { return *Assert(std::get_if<1>(&m_data)); } |
125 | 3 | constexpr E& error() & noexcept LIFETIMEBOUND { return *Assert(std::get_if<1>(&m_data)); }util::Expected<void, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>>::error() & Line | Count | Source | 125 | 2 | constexpr E& error() & noexcept LIFETIMEBOUND { return *Assert(std::get_if<1>(&m_data)); } |
util::Expected<void, std::unique_ptr<int, std::default_delete<int>>>::error() & Line | Count | Source | 125 | 1 | constexpr E& error() & noexcept LIFETIMEBOUND { return *Assert(std::get_if<1>(&m_data)); } |
|
126 | 1 | constexpr E&& error() && noexcept LIFETIMEBOUND { return std::move(error()); } |
127 | | }; |
128 | | |
129 | | } // namespace util |
130 | | |
131 | | #endif // BITCOIN_UTIL_EXPECTED_H |