os.h
Go to the documentation of this file.
1 //
2 // Copyright(c) 2015 Gabi Melman.
3 // Distributed under the MIT License (http://opensource.org/licenses/MIT)
4 //
5 #pragma once
6 
7 #include "opc/spdlog/common.h"
8 
9 #include <cstdio>
10 #include <ctime>
11 #include <functional>
12 #include <string>
13 #include <chrono>
14 #include <thread>
15 #include <algorithm>
16 #include <cstring>
17 #include <cstdlib>
18 #include <sys/stat.h>
19 #include <sys/types.h>
20 
21 #ifdef _WIN32
22 
23 #ifndef NOMINMAX
24 #define NOMINMAX //prevent windows redefining min/max
25 #endif
26 
27 #ifndef WIN32_LEAN_AND_MEAN
28 #define WIN32_LEAN_AND_MEAN
29 #endif
30 #include <windows.h>
31 #include <process.h> // _get_pid support
32 #include <io.h> // _get_osfhandle and _isatty support
33 
34 #ifdef __MINGW32__
35 #include <share.h>
36 #endif
37 
38 #else // unix
39 
40 #include <unistd.h>
41 #include <fcntl.h>
42 
43 #ifdef __linux__
44 #include <sys/syscall.h> //Use gettid() syscall under linux to get thread id
45 
46 #elif __FreeBSD__
47 #include <sys/thr.h> //Use thr_self() syscall under FreeBSD to get thread id
48 #endif
49 
50 #endif //unix
51 
52 #ifndef __has_feature // Clang - feature checking macros.
53 #define __has_feature(x) 0 // Compatibility with non-clang compilers.
54 #endif
55 
56 
57 namespace spdlog
58 {
59 namespace details
60 {
61 namespace os
62 {
63 
64 inline spdlog::log_clock::time_point now()
65 {
66 
67 #if defined __linux__ && defined SPDLOG_CLOCK_COARSE
68  timespec ts;
69  ::clock_gettime(CLOCK_REALTIME_COARSE, &ts);
70  return std::chrono::time_point<log_clock, typename log_clock::duration>(
71  std::chrono::duration_cast<typename log_clock::duration>(
72  std::chrono::seconds(ts.tv_sec) + std::chrono::nanoseconds(ts.tv_nsec)));
73 
74 
75 #else
76  return log_clock::now();
77 #endif
78 
79 }
80 inline std::tm localtime(const std::time_t &time_tt)
81 {
82 
83 #ifdef _WIN32
84  std::tm tm;
85  localtime_s(&tm, &time_tt);
86 #else
87  std::tm tm;
88  localtime_r(&time_tt, &tm);
89 #endif
90  return tm;
91 }
92 
93 inline std::tm localtime()
94 {
95  std::time_t now_t = time(nullptr);
96  return localtime(now_t);
97 }
98 
99 
100 inline std::tm gmtime(const std::time_t &time_tt)
101 {
102 
103 #ifdef _WIN32
104  std::tm tm;
105  gmtime_s(&tm, &time_tt);
106 #else
107  std::tm tm;
108  gmtime_r(&time_tt, &tm);
109 #endif
110  return tm;
111 }
112 
113 inline std::tm gmtime()
114 {
115  std::time_t now_t = time(nullptr);
116  return gmtime(now_t);
117 }
118 inline bool operator==(const std::tm& tm1, const std::tm& tm2)
119 {
120  return (tm1.tm_sec == tm2.tm_sec &&
121  tm1.tm_min == tm2.tm_min &&
122  tm1.tm_hour == tm2.tm_hour &&
123  tm1.tm_mday == tm2.tm_mday &&
124  tm1.tm_mon == tm2.tm_mon &&
125  tm1.tm_year == tm2.tm_year &&
126  tm1.tm_isdst == tm2.tm_isdst);
127 }
128 
129 inline bool operator!=(const std::tm& tm1, const std::tm& tm2)
130 {
131  return !(tm1 == tm2);
132 }
133 
134 // eol definition
135 #if !defined (SPDLOG_EOL)
136 #ifdef _WIN32
137 #define SPDLOG_EOL "\r\n"
138 #else
139 #define SPDLOG_EOL "\n"
140 #endif
141 #endif
142 
143 SPDLOG_CONSTEXPR static const char* eol = SPDLOG_EOL;
144 SPDLOG_CONSTEXPR static int eol_size = sizeof(SPDLOG_EOL) - 1;
145 
146 inline void prevent_child_fd(FILE *f)
147 {
148 #ifdef _WIN32
149  auto file_handle = (HANDLE)_get_osfhandle(_fileno(f));
150  if (!::SetHandleInformation(file_handle, HANDLE_FLAG_INHERIT, 0))
151  throw spdlog_ex("SetHandleInformation failed", errno);
152 #else
153  auto fd = fileno(f);
154  if (fcntl(fd, F_SETFD, FD_CLOEXEC) == -1)
155  throw spdlog_ex("fcntl with FD_CLOEXEC failed", errno);
156 #endif
157 }
158 
159 
160 //fopen_s on non windows for writing
161 inline int fopen_s(FILE** fp, const filename_t& filename, const filename_t& mode)
162 {
163 #ifdef _WIN32
164 #ifdef SPDLOG_WCHAR_FILENAMES
165  *fp = _wfsopen((filename.c_str()), mode.c_str(), _SH_DENYWR);
166 #else
167  *fp = _fsopen((filename.c_str()), mode.c_str(), _SH_DENYWR);
168 #endif
169 #else //unix
170  *fp = fopen((filename.c_str()), mode.c_str());
171 #endif
172 
173 #ifdef SPDLOG_PREVENT_CHILD_FD
174  if (*fp != nullptr)
175  prevent_child_fd(*fp);
176 #endif
177  return *fp == nullptr;
178 }
179 
180 
181 inline int remove(const filename_t &filename)
182 {
183 #if defined(_WIN32) && defined(SPDLOG_WCHAR_FILENAMES)
184  return _wremove(filename.c_str());
185 #else
186  return std::remove(filename.c_str());
187 #endif
188 }
189 
190 inline int rename(const filename_t& filename1, const filename_t& filename2)
191 {
192 #if defined(_WIN32) && defined(SPDLOG_WCHAR_FILENAMES)
193  return _wrename(filename1.c_str(), filename2.c_str());
194 #else
195  return std::rename(filename1.c_str(), filename2.c_str());
196 #endif
197 }
198 
199 
200 //Return if file exists
201 inline bool file_exists(const filename_t& filename)
202 {
203 #ifdef _WIN32
204 #ifdef SPDLOG_WCHAR_FILENAMES
205  auto attribs = GetFileAttributesW(filename.c_str());
206 #else
207  auto attribs = GetFileAttributesA(filename.c_str());
208 #endif
209  return (attribs != INVALID_FILE_ATTRIBUTES && !(attribs & FILE_ATTRIBUTE_DIRECTORY));
210 #else //common linux/unix all have the stat system call
211  struct stat buffer;
212  return (stat(filename.c_str(), &buffer) == 0);
213 #endif
214 }
215 
216 
217 
218 
219 //Return file size according to open FILE* object
220 inline size_t filesize(FILE *f)
221 {
222  if (f == nullptr)
223  throw spdlog_ex("Failed getting file size. fd is null");
224 #ifdef _WIN32
225  int fd = _fileno(f);
226 #if _WIN64 //64 bits
227  struct _stat64 st;
228  if (_fstat64(fd, &st) == 0)
229  return st.st_size;
230 
231 #else //windows 32 bits
232  long ret = _filelength(fd);
233  if (ret >= 0)
234  return static_cast<size_t>(ret);
235 #endif
236 
237 #else // unix
238  int fd = fileno(f);
239  //64 bits(but not in osx, where fstat64 is deprecated)
240 #if !defined(__FreeBSD__) && !defined(__APPLE__) && (defined(__x86_64__) || defined(__ppc64__))
241  struct stat64 st;
242  if (fstat64(fd, &st) == 0)
243  return static_cast<size_t>(st.st_size);
244 #else // unix 32 bits or osx
245  struct stat st;
246  if (fstat(fd, &st) == 0)
247  return static_cast<size_t>(st.st_size);
248 #endif
249 #endif
250  throw spdlog_ex("Failed getting file size from fd", errno);
251 }
252 
253 
254 
255 
256 //Return utc offset in minutes or throw spdlog_ex on failure
257 inline int utc_minutes_offset(const std::tm& tm = details::os::localtime())
258 {
259 
260 #ifdef _WIN32
261 #if _WIN32_WINNT < _WIN32_WINNT_WS08
262  TIME_ZONE_INFORMATION tzinfo;
263  auto rv = GetTimeZoneInformation(&tzinfo);
264 #else
265  DYNAMIC_TIME_ZONE_INFORMATION tzinfo;
266  auto rv = GetDynamicTimeZoneInformation(&tzinfo);
267 #endif
268  if (rv == TIME_ZONE_ID_INVALID)
269  throw spdlog::spdlog_ex("Failed getting timezone info. ", errno);
270 
271  int offset = -tzinfo.Bias;
272  if (tm.tm_isdst)
273  offset -= tzinfo.DaylightBias;
274  else
275  offset -= tzinfo.StandardBias;
276  return offset;
277 #else
278 
279 #if defined(sun) || defined(__sun)
280  // 'tm_gmtoff' field is BSD extension and it's missing on SunOS/Solaris
281  struct helper
282  {
283  static long int calculate_gmt_offset(const std::tm & localtm = details::os::localtime(), const std::tm & gmtm = details::os::gmtime())
284  {
285  int local_year = localtm.tm_year + (1900 - 1);
286  int gmt_year = gmtm.tm_year + (1900 - 1);
287 
288  long int days = (
289  // difference in day of year
290  localtm.tm_yday - gmtm.tm_yday
291 
292  // + intervening leap days
293  + ((local_year >> 2) - (gmt_year >> 2))
294  - (local_year / 100 - gmt_year / 100)
295  + ((local_year / 100 >> 2) - (gmt_year / 100 >> 2))
296 
297  // + difference in years * 365 */
298  + (long int)(local_year - gmt_year) * 365
299  );
300 
301  long int hours = (24 * days) + (localtm.tm_hour - gmtm.tm_hour);
302  long int mins = (60 * hours) + (localtm.tm_min - gmtm.tm_min);
303  long int secs = (60 * mins) + (localtm.tm_sec - gmtm.tm_sec);
304 
305  return secs;
306  }
307  };
308 
309  long int offset_seconds = helper::calculate_gmt_offset(tm);
310 #else
311  long int offset_seconds = tm.tm_gmtoff;
312 #endif
313 
314  return static_cast<int>(offset_seconds / 60);
315 #endif
316 }
317 
318 //Return current thread id as size_t
319 //It exists because the std::this_thread::get_id() is much slower(espcially under VS 2013)
320 inline size_t _thread_id()
321 {
322 #ifdef _WIN32
323  return static_cast<size_t>(::GetCurrentThreadId());
324 #elif __linux__
325 # if defined(__ANDROID__) && defined(__ANDROID_API__) && (__ANDROID_API__ < 21)
326 # define SYS_gettid __NR_gettid
327 # endif
328  return static_cast<size_t>(syscall(SYS_gettid));
329 #elif __FreeBSD__
330  long tid;
331  thr_self(&tid);
332  return static_cast<size_t>(tid);
333 #elif __APPLE__
334  uint64_t tid;
335  pthread_threadid_np(nullptr, &tid);
336  return static_cast<size_t>(tid);
337 #else //Default to standard C++11 (other Unix)
338  return static_cast<size_t>(std::hash<std::thread::id>()(std::this_thread::get_id()));
339 #endif
340 }
341 
342 //Return current thread id as size_t (from thread local storage)
343 inline size_t thread_id()
344 {
345 #if defined(_MSC_VER) && (_MSC_VER < 1900) || defined(__clang__) && !__has_feature(cxx_thread_local)
346  return _thread_id();
347 #else
348  static thread_local const size_t tid = _thread_id();
349  return tid;
350 #endif
351 }
352 
353 
354 
355 
356 // wchar support for windows file names (SPDLOG_WCHAR_FILENAMES must be defined)
357 #if defined(_WIN32) && defined(SPDLOG_WCHAR_FILENAMES)
358 #define SPDLOG_FILENAME_T(s) L ## s
359 inline std::string filename_to_str(const filename_t& filename)
360 {
361  std::wstring_convert<std::codecvt_utf8<wchar_t>, wchar_t> c;
362  return c.to_bytes(filename);
363 }
364 #else
365 #define SPDLOG_FILENAME_T(s) s
366 inline std::string filename_to_str(const filename_t& filename)
367 {
368  return filename;
369 }
370 #endif
371 
372 inline std::string errno_to_string(char[256], char* res)
373 {
374  return std::string(res);
375 }
376 
377 inline std::string errno_to_string(char buf[256], int res)
378 {
379  if (res == 0)
380  {
381  return std::string(buf);
382  }
383  else
384  {
385  return "Unknown error";
386  }
387 }
388 
389 // Return errno string (thread safe)
390 inline std::string errno_str(int err_num)
391 {
392  char buf[256];
393  SPDLOG_CONSTEXPR auto buf_size = sizeof(buf);
394 
395 #ifdef _WIN32
396  if (strerror_s(buf, buf_size, err_num) == 0)
397  return std::string(buf);
398  else
399  return "Unknown error";
400 
401 #elif defined(__FreeBSD__) || defined(__APPLE__) || defined(ANDROID) || defined(__SUNPRO_CC) || \
402  ((_POSIX_C_SOURCE >= 200112L) && ! defined(_GNU_SOURCE)) // posix version
403 
404  if (strerror_r(err_num, buf, buf_size) == 0)
405  return std::string(buf);
406  else
407  return "Unknown error";
408 
409 #else // gnu version (might not use the given buf, so its retval pointer must be used)
410  auto err = strerror_r(err_num, buf, buf_size); // let compiler choose type
411  return errno_to_string(buf, err); // use overloading to select correct stringify function
412 #endif
413 }
414 
415 inline int pid()
416 {
417 
418 #ifdef _WIN32
419  return ::_getpid();
420 #else
421  return static_cast<int>(::getpid());
422 #endif
423 
424 }
425 
426 
427 // Detrmine if the terminal supports colors
428 // Source: https://github.com/agauniyal/rang/
429 inline bool is_color_terminal()
430 {
431 #ifdef _WIN32
432  return true;
433 #else
434  static constexpr const char* Terms[] =
435  {
436  "ansi", "color", "console", "cygwin", "gnome", "konsole", "kterm",
437  "linux", "msys", "putty", "rxvt", "screen", "vt100", "xterm"
438  };
439 
440  const char *env_p = std::getenv("TERM");
441  if (env_p == nullptr)
442  {
443  return false;
444  }
445 
446  static const bool result = std::any_of(
447  std::begin(Terms), std::end(Terms), [&](const char* term)
448  {
449  return std::strstr(env_p, term) != nullptr;
450  });
451  return result;
452 #endif
453 }
454 
455 
456 // Detrmine if the terminal attached
457 // Source: https://github.com/agauniyal/rang/
458 inline bool in_terminal(FILE* file)
459 {
460 
461 #ifdef _WIN32
462  return _isatty(_fileno(file)) ? true : false;
463 #else
464  return isatty(fileno(file)) ? true : false;
465 #endif
466 }
467 } //os
468 } //details
469 } //spdlog
time
Definition: server.py:52
int rename(const filename_t &filename1, const filename_t &filename2)
Definition: os.h:190
static fmt::internal::Null strerror_s(char *, std::size_t,...)
Definition: format.cc:77
bool file_exists(const filename_t &filename)
Definition: os.h:201
static SPDLOG_CONSTEXPR int eol_size
Definition: os.h:144
int remove(const filename_t &filename)
Definition: os.h:181
size_t filesize(FILE *f)
Definition: os.h:220
static fmt::internal::Null strerror_r(int, char *,...)
Definition: format.cc:74
#define SPDLOG_CONSTEXPR
#define SPDLOG_EOL
Definition: os.h:139
spdlog::log_clock::time_point now()
Definition: os.h:64
bool in_terminal(FILE *file)
Definition: os.h:458
size_t thread_id()
Definition: os.h:343
int utc_minutes_offset(const std::tm &tm=details::os::localtime())
Definition: os.h:257
void prevent_child_fd(FILE *f)
Definition: os.h:146
std::string errno_str(int err_num)
Definition: os.h:390
std::tm localtime(const std::time_t &time_tt)
Definition: os.h:80
std::string filename_t
std::tm gmtime(const std::time_t &time_tt)
Definition: os.h:100
static SPDLOG_CONSTEXPR const char * eol
Definition: os.h:143
int fopen_s(FILE **fp, const filename_t &filename, const filename_t &mode)
Definition: os.h:161
static const days_array & days()
bool operator!=(const std::tm &tm1, const std::tm &tm2)
Definition: os.h:129
std::string errno_to_string(char[256], char *res)
Definition: os.h:372
bool is_color_terminal()
Definition: os.h:429
size_t _thread_id()
Definition: os.h:320
std::string filename_to_str(const filename_t &filename)
Definition: os.h:366
bool operator==(const std::tm &tm1, const std::tm &tm2)
Definition: os.h:118


ros_opcua_impl_freeopcua
Author(s): Denis Štogl
autogenerated on Tue Jan 19 2021 03:12:07