nx_camera_sdk  1.0
Camera SDK
plugin_tools.h
Go to the documentation of this file.
1 // Copyright 2018-present Network Optix, Inc. Licensed under MPL 2.0: www.mozilla.org/MPL/2.0/
2 
3 #pragma once
4 
9 // TODO: Remove this file when Storage and Camera SDKs are merged into Analytics SDK.
10 
11 #if defined(_WIN32)
12  #include <Windows.h>
13  #undef min
14  #undef max
15 #endif
16 
17 #include <cstdlib>
18 #include <cstring>
19 #include <cerrno>
20 #include <sstream>
21 #include <iomanip>
22 #include <limits>
23 #include <type_traits>
24 
25 #include "plugin_api.h"
26 
27 namespace nxpt {
28 
29 namespace atomic {
30 
31 #ifdef _WIN32
32  typedef volatile LONG AtomicLong;
33 #elif __GNUC__
34  typedef volatile long AtomicLong;
35 #else
36  #error "Unsupported compiler is used."
37 #endif
38 
40 static AtomicLong inc(AtomicLong* val)
41 {
42  #ifdef _WIN32
43  return InterlockedIncrement(val);
44  #elif __GNUC__
45  return __sync_add_and_fetch(val, 1);
46  #endif
47 }
48 
50 static AtomicLong dec(AtomicLong* val)
51 {
52  #ifdef _WIN32
53  return InterlockedDecrement(val);
54  #elif __GNUC__
55  return __sync_sub_and_fetch(val, 1);
56  #endif
57 }
58 
59 } // namespace atomic
60 
69 {
70 public:
71  CommonRefManager(const CommonRefManager&) = delete;
72  CommonRefManager& operator=(const CommonRefManager&) = delete;
73 
79  m_refCount(1),
80  m_objToWatch(objToWatch),
81  m_refCountingDelegate(0)
82  {
83  }
84 
89  CommonRefManager(CommonRefManager* refCountingDelegate):
90  m_refCountingDelegate(refCountingDelegate)
91  {
92  }
93 
95  int addRef() const
96  {
97  return m_refCountingDelegate
98  ? m_refCountingDelegate->addRef()
99  : atomic::inc(&m_refCount);
100  }
101 
106  int releaseRef() const
107  {
108  if (m_refCountingDelegate)
109  return m_refCountingDelegate->releaseRef();
110 
111  const int newRefCounter = atomic::dec(&m_refCount);
112  if (newRefCounter == 0)
113  delete m_objToWatch;
114  return newRefCounter;
115  }
116 
117  int refCount() const
118  {
119  if (m_refCountingDelegate)
120  return m_refCountingDelegate->refCount();
121  return m_refCount;
122  }
123 
124 private:
125  mutable atomic::AtomicLong m_refCount;
126  nxpl::PluginInterface* m_objToWatch;
127  CommonRefManager* m_refCountingDelegate;
128 };
129 
130 template <typename T>
131 class CommonRefCounter: public T
132 {
133 public:
134  CommonRefCounter(const CommonRefCounter&) = delete;
135  CommonRefCounter& operator=(const CommonRefCounter&) = delete;
137  CommonRefCounter& operator=(CommonRefCounter&&) = delete;
138  virtual ~CommonRefCounter() = default;
139 
140  virtual int addRef() const override { return m_refManager.addRef(); }
141  virtual int releaseRef() const override { return m_refManager.releaseRef(); }
142 
143  int refCount() const { return m_refManager.refCount(); }
144 
145 protected:
146  CommonRefManager m_refManager;
147 
148  CommonRefCounter(): m_refManager(static_cast<T*>(this)) {}
149  CommonRefCounter(CommonRefManager* refManager): m_refManager(refManager) {}
150 };
151 
156 template<typename RefCountableInterface>
157 int refCount(const nxpl::PluginInterface* object)
158 {
159  if (object == nullptr)
160  return 0;
161 
162  if (const auto commonRefCounter = dynamic_cast<CommonRefCounter<RefCountableInterface>*>(object))
163  return commonRefCounter->refCount();
164 
165  (void) object->addRef();
166  return object->releaseRef();
167 }
168 
169 enum NxGuidFormatOption
170 {
171  uppercase = 0x1,
172  hyphens = 0x2,
173  braces = 0x4,
174  applyAll = uppercase | hyphens | braces
175 };
176 
178 {
179 public:
180  static nxpl::NX_GUID nullGuid()
181  {
182  return {{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}};
183  }
184 
185  static nxpl::NX_GUID fromRawData(const char* data)
186  {
187  nxpl::NX_GUID result;
188  memcpy(result.bytes, data, sizeof(result.bytes));
189  return result;
190  }
191 
192  static nxpl::NX_GUID fromStdString(const std::string& guidStr)
193  {
194  static const auto kMinGuidStrSize = 32;
195  static const auto kGuidBytesNumber = 16;
196 
197  if (guidStr.size() < kMinGuidStrSize)
198  return NxGuidHelper::nullGuid();
199 
200  nxpl::NX_GUID guid;
201  int currentByteIndex = 0;
202  std::string currentByteString;
203  for (std::string::size_type i = 0; i < guidStr.size(); ++i)
204  {
205  if (guidStr[i] == '{' || guidStr[i] == '}' || guidStr[i] == '-'
206  || guidStr[i] == '\t' || guidStr[i] == '\n' || guidStr[i] == 'r'
207  || guidStr[i] == ' ')
208  {
209  continue;
210  }
211 
212  if (currentByteIndex >= kGuidBytesNumber)
213  return NxGuidHelper::nullGuid();
214 
215  currentByteString += guidStr[i];
216  if (currentByteString.size() == 2)
217  {
218  char* pEnd = nullptr;
219  errno = 0; //< Required before strtol().
220  const long v = std::strtol(currentByteString.c_str(), &pEnd, /*base*/ 16);
221  const bool hasError = v > std::numeric_limits<unsigned char>::max()
222  || v < std::numeric_limits<unsigned char>::min()
223  || errno != 0
224  || *pEnd != '\0';
225 
226  if (hasError)
227  return NxGuidHelper::nullGuid();
228 
229  guid.bytes[currentByteIndex] = (unsigned char) v;
230  ++currentByteIndex;
231  currentByteString.clear();
232  }
233  }
234 
235  if (currentByteIndex != kGuidBytesNumber)
236  return NxGuidHelper::nullGuid();
237 
238  return guid;
239  }
240 };
241 
242 static std::string toStdString(
243  const nxpl::NX_GUID& guid,
244  unsigned int format = NxGuidFormatOption::applyAll)
245 {
246  std::stringstream ss;
247  ss << std::hex << std::setfill('0');
248 
249  if (format & NxGuidFormatOption::braces)
250  ss << '{';
251 
252  if (format & NxGuidFormatOption::uppercase)
253  ss << std::uppercase;
254 
255  for (int i = 0; i < 4; ++i)
256  {
257  ss << std::setw(2);
258  ss << static_cast<unsigned int>(guid.bytes[i]);
259  }
260 
261  if (format & NxGuidFormatOption::hyphens)
262  ss << '-';
263 
264  for (int i = 0; i < 2; ++i)
265  {
266  ss << std::setw(2);
267  ss << static_cast<unsigned int>(guid.bytes[4 + i]);
268  }
269 
270  if (format & NxGuidFormatOption::hyphens)
271  ss << "-";
272 
273  for (int i = 0; i < 2; ++i)
274  {
275  ss << std::setw(2);
276  ss << static_cast<unsigned int>(guid.bytes[6 + i]);
277  }
278 
279  if (format & NxGuidFormatOption::hyphens)
280  ss << "-";
281 
282  for (int i = 0; i < 2; ++i)
283  {
284  ss << std::setw(2);
285  ss << static_cast<unsigned int>(guid.bytes[8 + i]);
286  }
287 
288  if (format & NxGuidFormatOption::hyphens)
289  ss << "-";
290 
291  for (int i = 0; i < 6; ++i)
292  {
293  ss << std::setw(2);
294  ss << static_cast<unsigned int>(guid.bytes[10 + i]);
295  }
296 
297  if (format & NxGuidFormatOption::braces)
298  ss << '}';
299 
300  return ss.str();
301 }
302 
303 } // namespace nxpt
304 
305 namespace nxpl {
306 
307 inline bool operator==(const nxpl::NX_GUID& id1, const nxpl::NX_GUID& id2)
308 {
309  return memcmp(id1.bytes, id2.bytes, sizeof(id1.bytes)) == 0;
310 }
311 
312 inline std::ostream& operator<<(std::ostream& os, const nxpl::NX_GUID& id)
313 {
314  return os << nxpt::toStdString(id);
315 }
316 
317 } // namespace nxpl
318 
319 namespace std {
320 
321 template<>
322 struct hash<nxpl::NX_GUID>
323 {
324  std::size_t operator()(const nxpl::NX_GUID& guid) const
325  {
326  std::size_t h;
327 
328  for (size_t i = 0; i < sizeof(guid.bytes); ++i)
329  h = (h + (324723947 + guid.bytes[i])) ^ 93485734985;
330 
331  return h;
332  }
333 };
334 
335 } // namespace std
virtual int addRef() const =0
Increment reference counter.
static AtomicLong inc(AtomicLong *val)
Definition: plugin_tools.h:40
unsigned char bytes[16]
GUID bytes.
Definition: plugin_api.h:29
Definition: plugin_tools.h:319
Base class for every interface, provided by plugin.
Definition: plugin_api.h:44
static AtomicLong dec(AtomicLong *val)
Definition: plugin_tools.h:50
CommonRefManager(nxpl::PluginInterface *objToWatch)
Definition: plugin_tools.h:78
GUID of plugin interface.
Definition: plugin_api.h:26
VMS dynamic plugin API (c++)
Definition: plugin_api.h:23
Definition: plugin_tools.h:177
Definition: plugin_tools.h:131
CommonRefManager(CommonRefManager *refCountingDelegate)
Definition: plugin_tools.h:89
Definition: plugin_tools.h:68
int addRef() const
Definition: plugin_tools.h:95
Definition: plugin_tools.h:27
int releaseRef() const
Definition: plugin_tools.h:106