openthread-br  0.3.0-72c0388
code_utils.hpp
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2017, The OpenThread Authors.
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions are met:
7  * 1. Redistributions of source code must retain the above copyright
8  * notice, this list of conditions and the following disclaimer.
9  * 2. Redistributions in binary form must reproduce the above copyright
10  * notice, this list of conditions and the following disclaimer in the
11  * documentation and/or other materials provided with the distribution.
12  * 3. Neither the name of the copyright holder nor the
13  * names of its contributors may be used to endorse or promote products
14  * derived from this software without specific prior written permission.
15  *
16  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
20  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
23  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
24  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
25  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26  * POSSIBILITY OF SUCH DAMAGE.
27  */
28 
33 #ifndef OTBR_COMMON_CODE_UTILS_HPP_
34 #define OTBR_COMMON_CODE_UTILS_HPP_
35 
36 #ifndef OTBR_LOG_TAG
37 #define OTBR_LOG_TAG "UTILS"
38 #endif
39 
40 #include <assert.h>
41 #include <memory>
42 #include <stdlib.h>
43 
44 #include "common/logging.hpp"
45 
55 #define OTBR_ALIGNED(aMem, aAlignType) \
56  reinterpret_cast<aAlignType>( \
57  ((reinterpret_cast<unsigned long>(aMem) + sizeof(aAlignType) - 1) / sizeof(aAlignType)) * sizeof(aAlignType))
58 
59 #ifndef CONTAINING_RECORD
60 #define BASE 0x1
61 #define myoffsetof(s, m) (((size_t) & (((s *)BASE)->m)) - BASE)
62 #define CONTAINING_RECORD(address, type, field) ((type *)((uint8_t *)(address)-myoffsetof(type, field)))
63 #endif /* CONTAINING_RECORD */
64 
73 #define SuccessOrExit(aStatus) \
74  do \
75  { \
76  if ((aStatus) != 0) \
77  { \
78  goto exit; \
79  } \
80  } while (false)
81 
90 #define SuccessOrDie(aStatus, aMessage) \
91  do \
92  { \
93  if ((aStatus) != 0) \
94  { \
95  otbrLogEmerg("FAILED %s:%d - %s", __FILE__, __LINE__, aMessage); \
96  exit(-1); \
97  } \
98  } while (false)
99 
110 #define VerifyOrExit(aCondition, ...) \
111  do \
112  { \
113  if (!(aCondition)) \
114  { \
115  __VA_ARGS__; \
116  goto exit; \
117  } \
118  } while (false)
119 
128 #define VerifyOrDie(aCondition, aMessage) \
129  do \
130  { \
131  if (!(aCondition)) \
132  { \
133  otbrLogEmerg("FAILED %s:%d - %s", __FILE__, __LINE__, aMessage); \
134  exit(-1); \
135  } \
136  } while (false)
137 
150 #define ExitNow(...) \
151  do \
152  { \
153  __VA_ARGS__; \
154  goto exit; \
155  } while (false)
156 
157 #define OTBR_NOOP
158 #define OTBR_UNUSED_VARIABLE(variable) ((void)(variable))
159 
160 template <typename T, typename... Args> std::unique_ptr<T> MakeUnique(Args &&... args)
161 {
162  return std::unique_ptr<T>(new T(std::forward<Args>(args)...));
163 }
164 
170 {
171 public:
172  NonCopyable(const NonCopyable &) = delete;
173  NonCopyable &operator=(const NonCopyable &) = delete;
174 
175 protected:
176  NonCopyable(void) = default;
177 };
178 
179 template <typename T> class Optional
180 {
181 public:
182  constexpr Optional(void) = default;
183 
184  Optional(T aValue) { SetValue(aValue); }
185 
186  ~Optional(void) { ClearValue(); }
187 
188  Optional(const Optional &aOther) { AssignFrom(aOther); }
189 
190  Optional &operator=(const Optional &aOther) { AssignFrom(aOther); }
191 
192  constexpr const T *operator->(void)const { return &GetValue(); }
193 
194  constexpr const T &operator*(void)const { return GetValue(); }
195 
196  constexpr bool HasValue(void) const { return mHasValue; }
197 
198 private:
199  T &GetValue(void) const
200  {
201  assert(mHasValue);
202  return *const_cast<T *>(reinterpret_cast<const T *>(&mStorage));
203  }
204 
205  void ClearValue(void)
206  {
207  if (mHasValue)
208  {
209  GetValue().~T();
210  mHasValue = false;
211  }
212  }
213 
214  void SetValue(const T &aValue)
215  {
216  ClearValue();
217  new (&mStorage) T(aValue);
218  mHasValue = true;
219  }
220 
221  void AssignFrom(const Optional &aOther)
222  {
223  ClearValue();
224  if (aOther.mHasValue)
225  {
226  SetValue(aOther.GetValue());
227  }
228  }
229 
230  alignas(T) unsigned char mStorage[sizeof(T)];
231  bool mHasValue = false;
232 };
233 
234 #endif // OTBR_COMMON_CODE_UTILS_HPP_
logging.hpp
NonCopyable
Definition: code_utils.hpp:169
Optional
Definition: code_utils.hpp:179