CatapultServer  v0.5.0.1 (Elephant)
exceptions.h
Go to the documentation of this file.
1 
21 #pragma once
22 #include "utils/BaseValue.h"
23 #include "utils/HexFormatter.h"
24 #include "utils/Logging.h"
25 #include "utils/NonCopyable.h"
26 #include <boost/exception/exception.hpp>
27 #include <boost/exception/info.hpp>
28 #include <boost/throw_exception.hpp>
29 #include <atomic>
30 #include <exception>
31 
32 #if defined(WIN32) || defined(WIN64)
33 #define VISIBLE_EXCEPTION_ATTRIBUTE
34 #else
35 #define VISIBLE_EXCEPTION_ATTRIBUTE __attribute__ ((visibility ("default")))
36 #endif
37 
38 namespace catapult {
39 
41  template<typename TStlException>
42  class VISIBLE_EXCEPTION_ATTRIBUTE catapult_error : public TStlException, public boost::exception, public utils::NonCopyable {
43  public:
45  explicit catapult_error(const char* what) : TStlException(what)
46  {}
47 
50  : TStlException(rhs.what())
51  , boost::exception(rhs)
52  , utils::NonCopyable()
53  {}
54 
57  : TStlException(rhs.what())
58  , boost::exception(std::move(rhs))
59  , utils::NonCopyable()
60  {}
61  };
62 
63  template<typename TStlException>
64  class VISIBLE_EXCEPTION_ATTRIBUTE catapult_error<catapult_error<TStlException>> : public catapult_error<TStlException> {
65  public:
67  explicit catapult_error(const char* what) : catapult_error<TStlException>(what)
68  {}
69 
71  catapult_error(const catapult_error& rhs) : catapult_error<TStlException>(rhs)
72  {}
73 
75  catapult_error(catapult_error&& rhs) : catapult_error<TStlException>(std::move(rhs))
76  {}
77 
80  {}
81 
83  catapult_error(catapult_error<TStlException>&& rhs) : catapult_error<TStlException>(std::move(rhs))
84  {}
85  };
86 
91 
93  struct ErrorParam1 {};
94 
96  struct ErrorParam2 {};
97 
98  namespace exception_detail {
101  template<typename T, typename X = std::enable_if_t<!std::is_pointer_v<T>>>
102  constexpr T ConvertToValue(const T& value) {
103  return value;
104  }
105 
107  template<typename TValue, typename TTag>
108  constexpr TValue ConvertToValue(const utils::BaseValue<TValue, TTag>& value) {
109  return value.unwrap();
110  }
111 
113  template<typename T>
114  constexpr T ConvertToValue(const std::atomic<T>& value) {
115  return value;
116  }
117 
119  template<typename TInputIterator>
121  // ContainerHexFormatter only holds iterators to data, which may not be valid at catch site
122  // since an exception is being thrown, perf doesn't matter, so stringify proactively
123  std::ostringstream out;
124  out << value;
125  return out.str();
126  }
127 
129  template<typename TErrorParam>
130  class Make {
131  public:
133  template<typename T>
134  static auto From(const T& value) {
135  return boost::error_info<TErrorParam, decltype(ConvertToValue(value))>(ConvertToValue(value));
136  }
137  };
138  }
139 }
140 
142 #define CATAPULT_THROW_EXCEPTION(EXCEPTION) \
143  BOOST_THROW_EXCEPTION(EXCEPTION)
144 
146 #define CATAPULT_THROW_AND_LOG_0(TYPE, MESSAGE) { \
147  CATAPULT_LOG(error) << "Throwing exception: " << MESSAGE; \
148  CATAPULT_THROW_EXCEPTION(TYPE(MESSAGE)); \
149 }
150 
152 #define CATAPULT_THROW_AND_LOG_1(TYPE, MESSAGE, PARAM1) { \
153  auto detail1 = exception_detail::Make<ErrorParam1>::From(PARAM1); \
154  CATAPULT_LOG(error) << "Throwing exception: " << MESSAGE << " (" << detail1.value() << ")"; \
155  CATAPULT_THROW_EXCEPTION(TYPE(MESSAGE) << detail1); \
156 }
157 
159 #define CATAPULT_THROW_AND_LOG_2(TYPE, MESSAGE, PARAM1, PARAM2) { \
160  auto detail1 = exception_detail::Make<ErrorParam1>::From(PARAM1); \
161  auto detail2 = exception_detail::Make<ErrorParam2>::From(PARAM2); \
162  CATAPULT_LOG(error) << "Throwing exception: " << MESSAGE << " (" << detail1.value() << ", " << detail2.value() << ")"; \
163  CATAPULT_THROW_EXCEPTION(TYPE(MESSAGE) << detail1 << detail2); \
164 }
165 
167 #define CATAPULT_THROW_RUNTIME_ERROR(MESSAGE) \
168  CATAPULT_THROW_AND_LOG_0(catapult_runtime_error, MESSAGE)
169 
171 #define CATAPULT_THROW_RUNTIME_ERROR_1(MESSAGE, PARAM1) \
172  CATAPULT_THROW_AND_LOG_1(catapult_runtime_error, MESSAGE, PARAM1)
173 
175 #define CATAPULT_THROW_RUNTIME_ERROR_2(MESSAGE, PARAM1, PARAM2) \
176  CATAPULT_THROW_AND_LOG_2(catapult_runtime_error, MESSAGE, PARAM1, PARAM2)
177 
179 #define CATAPULT_THROW_INVALID_ARGUMENT(MESSAGE) \
180  CATAPULT_THROW_AND_LOG_0(catapult_invalid_argument, MESSAGE)
181 
183 #define CATAPULT_THROW_INVALID_ARGUMENT_1(MESSAGE, PARAM1) \
184  CATAPULT_THROW_AND_LOG_1(catapult_invalid_argument, MESSAGE, PARAM1)
185 
187 #define CATAPULT_THROW_INVALID_ARGUMENT_2(MESSAGE, PARAM1, PARAM2) \
188  CATAPULT_THROW_AND_LOG_2(catapult_invalid_argument, MESSAGE, PARAM1, PARAM2)
189 
191 #define CATAPULT_THROW_OUT_OF_RANGE(MESSAGE) \
192  CATAPULT_THROW_AND_LOG_0(catapult_out_of_range, MESSAGE)
193 
195 #define CATAPULT_THROW_FILE_IO_ERROR(MESSAGE) \
196  CATAPULT_THROW_AND_LOG_0(catapult_file_io_error, MESSAGE)
catapult::catapult_error::catapult_error
catapult_error(const catapult_error &rhs)
Copy constructs an exception from rhs.
Definition: exceptions.h:49
catapult::exception_detail::ConvertToValue
constexpr T ConvertToValue(const T &value)
Definition: exceptions.h:102
catapult::catapult_error< catapult_error< TStlException > >::catapult_error
catapult_error(catapult_error< TStlException > &&rhs)
Move constructs an exception from rhs.
Definition: exceptions.h:83
catapult::ErrorParam1
Tag for first custom exception parameter.
Definition: exceptions.h:93
catapult::exception_detail::Make
Helper class for creating boost::error_info.
Definition: exceptions.h:130
boost
Definition: IoThreadPool.h:25
catapult::utils::BasicBaseValue< TValue, TTag, BaseValue< TValue, TTag > >::unwrap
constexpr ValueType unwrap() const
Unwraps this value and returns the underlying raw value.
Definition: BaseValue.h:53
catapult::utils::BaseValue
Immutable wrapper for basic types, to provide some type-safety.
Definition: BaseValue.h:100
catapult::exception_detail::Make::From
static auto From(const T &value)
Creates a boost::error_info with the specified value.
Definition: exceptions.h:134
HexFormatter.h
catapult::catapult_error< catapult_error< TStlException > >::catapult_error
catapult_error(const char *what)
Creates an exception with a message (what).
Definition: exceptions.h:67
catapult::utils::ContainerHexFormatter
Formatter for printing a container of integral hex numbers to a stream.
Definition: HexFormatter.h:89
catapult::catapult_error< catapult_error< TStlException > >::catapult_error
catapult_error(catapult_error &&rhs)
Move constructs an exception from rhs.
Definition: exceptions.h:75
catapult::catapult_error< catapult_error< TStlException > >::catapult_error
catapult_error(const catapult_error &rhs)
Copy constructs an exception from rhs.
Definition: exceptions.h:71
VISIBLE_EXCEPTION_ATTRIBUTE
#define VISIBLE_EXCEPTION_ATTRIBUTE
Definition: exceptions.h:35
catapult
Definition: AddressExtractionExtension.cpp:28
catapult::catapult_error< catapult_error< TStlException > >::catapult_error
catapult_error(const catapult_error< TStlException > &rhs)
Copy constructs an exception from rhs.
Definition: exceptions.h:79
catapult::catapult_error
Base class for all catapult exceptions that derives from both std::exception and boost::exception.
Definition: exceptions.h:42
Logging.h
catapult::utils::NonCopyable
A class that can neither be copied nor moved.
Definition: NonCopyable.h:26
catapult::catapult_error::catapult_error
catapult_error(catapult_error &&rhs)
Move constructs an exception from rhs.
Definition: exceptions.h:56
catapult::catapult_error::catapult_error
catapult_error(const char *what)
Creates an exception with a message (what).
Definition: exceptions.h:45
BaseValue.h
catapult::ErrorParam2
Tag for second custom exception parameter.
Definition: exceptions.h:96
NonCopyable.h