Scarab  v3.4.2
Project 8 C++ Utility Library
logger.hh
Go to the documentation of this file.
1 /*
2  * logger.hh
3  * Based on KLogger.h, from KATRIN's Kasper
4  *
5  * Created on: Jan 21, 2014
6  * Author: nsoblath
7  */
8 
9 #ifndef SCARAB_LOGGER_HH_
10 #define SCARAB_LOGGER_HH_
11 
12 #include "macros.hh"
13 #include "scarab_api.hh"
14 
23 // UTILITY MACROS
24 
25 #ifndef LOGGER_UTILITY_MACROS_
26 #define LOGGER_UTILITY_MACROS_
27 
28 #define msvc_bug_fix(m, args) m args
29 #define expand(x) x
30 
31 //#define va_num_args(...) va_num_args_(__VA_ARGS__, 5,4,3,2,1)
32 //#define va_num_args_(...) msvc_bug_fix(va_num_args_impl, (__VA_ARGS__))
33 #define va_num_args(...) expand( va_num_args_impl(__VA_ARGS__, 5,4,3,2,1))
34 #define va_num_args_impl(_1,_2,_3,_4,_5,N,...) N
35 
36 
37 #define macro_dispatcher(func, ...) macro_dispatcher_(func, va_num_args(__VA_ARGS__))
38 #define macro_dispatcher_(func, nargs) macro_dispatcher__(func, nargs)
39 #define macro_dispatcher__(func, nargs) func ## nargs
40 
41 #endif /* LOGGER_UTILITY_MACROS_ */
42 
43 // COLOR DEFINITIONS
44 #define COLOR_NORMAL "0"
45 #define COLOR_BRIGHT "1"
46 #define COLOR_FOREGROUND_RED "31"
47 #define COLOR_FOREGROUND_GREEN "32"
48 #define COLOR_FOREGROUND_YELLOW "33"
49 #define COLOR_FOREGROUND_BLUE "34"
50 #define COLOR_FOREGROUND_CYAN "36"
51 #define COLOR_FOREGROUND_WHITE "37"
52 #define COLOR_PREFIX "\033["
53 #define COLOR_SUFFIX "m"
54 #define COLOR_SEPARATOR ";"
55 
56 // INCLUDES
57 
58 #include <cstring>
59 #include <iostream>
60 #include <sstream>
61 
62 // CLASS DEFINITIONS
63 
67 namespace scarab
68 {
69 
113  {
114  public:
120  enum class ELevel : unsigned
121  {
122  eTrace = 0,
123  eDebug = 10,
124  eInfo = 20,
125  eProg = 25,
126  eWarn = 30,
127  eError = 40,
128  eFatal = 50
129  };
130 
131  public:
136  struct Location {
137  Location(const char* const fileName = "", const char* const functionName = "", int lineNumber = -1) :
138  fLineNumber(lineNumber), fFileName(fileName), fFunctionName(functionName)
139  { }
141  std::string fFileName;
142  std::string fFunctionName;
143  };
144 
145  public:
146  static logger& GetRootLogger() {
147  static logger rootLogger;
148  return rootLogger;
149  }
150 
151  public:
156  logger(const char* name = 0);
158  logger(const std::string& name);
159 
160  virtual ~logger();
161 
167  bool IsLevelEnabled(ELevel level) const;
168 
173  ELevel GetLevel() const;
174 
179  void SetLevel(ELevel level) const;
180 
184  void UseGlobalLevel() const;
185 
189  static logger::ELevel GetGlobalLevel();
190 
195  static void SetGlobalLevel(ELevel level);
196 
201  static void SetColored(bool flag);
202 
207  static void SetOutStream(std::ostream* stream);
208 
213  static void SetErrStream(std::ostream* stream);
214 
222  void Log(ELevel level, const std::string& message, const Location& loc = Location());
223 
230  void LogTrace(const std::string& message, const Location& loc = Location())
231  {
232  Log(ELevel::eTrace, message, loc);
233  }
240  void LogDebug(const std::string& message, const Location& loc = Location())
241  {
242  Log(ELevel::eDebug, message, loc);
243  }
250  void LogInfo(const std::string& message, const Location& loc = Location())
251  {
252  Log(ELevel::eInfo, message, loc);
253  }
260  void LogProg(const std::string& message, const Location& loc = Location())
261  {
262  Log(ELevel::eProg, message, loc);
263  }
270  void LogWarn(const std::string& message, const Location& loc = Location())
271  {
272  Log(ELevel::eWarn, message, loc);
273  }
280  void LogError(const std::string& message, const Location& loc = Location())
281  {
282  Log(ELevel::eError, message, loc);
283  }
290  void LogFatal(const std::string& message, const Location& loc = Location())
291  {
292  Log(ELevel::eFatal, message, loc);
293  }
294 
295  private:
296  struct Private;
297  std::shared_ptr<Private> fPrivate;
298  };
299 
300 }
301 
302 // PRIVATE MACROS
303 
304 #define __DEFAULT_LOGGER scarab::logger::GetRootLogger()
305 
306 #define __LOG_LOCATION scarab::logger::Location(__FILE__, __FUNC__, __LINE__)
307 #define __LOG_LOG_4(I,L,M,O) \
308  { \
309  if (I.IsLevelEnabled(scarab::logger::ELevel::e##L)) { \
310  static bool _sLoggerMarker = false; \
311  if (!O || !_sLoggerMarker) { \
312  _sLoggerMarker = true; \
313  std::ostringstream stream; stream << M; \
314  I.Log(scarab::logger::ELevel::e##L, stream.str(), __LOG_LOCATION); \
315  } \
316  } \
317  }
318 
319 
320 #define __LOG_LOG_3(I,L,M) __LOG_LOG_4(I,L,M,false)
321 #define __LOG_LOG_2(L,M) __LOG_LOG_4(__DEFAULT_LOGGER,L,M,false)
322 #define __LOG_LOG_1(M) __LOG_LOG_4(__DEFAULT_LOGGER,Debug,M,false)
323 
324 #define __LOG_TRACE_2(I,M) __LOG_LOG_4(I,Trace,M,false)
325 #define __LOG_TRACE_1(M) __LOG_LOG_4(__DEFAULT_LOGGER,Trace,M,false)
326 
327 #define __LOG_DEBUG_2(I,M) __LOG_LOG_4(I,Debug,M,false)
328 #define __LOG_DEBUG_1(M) __LOG_LOG_4(__DEFAULT_LOGGER,Debug,M,false)
329 
330 #define __LOG_INFO_2(I,M) __LOG_LOG_4(I,Info,M,false)
331 #define __LOG_INFO_1(M) __LOG_LOG_4(__DEFAULT_LOGGER,Info,M,false)
332 
333 #define __LOG_PROG_2(I,M) __LOG_LOG_4(I,Prog,M,false)
334 #define __LOG_PROG_1(M) __LOG_LOG_4(__DEFAULT_LOGGER,Prog,M,false)
335 
336 #define __LOG_WARN_2(I,M) __LOG_LOG_4(I,Warn,M,false)
337 #define __LOG_WARN_1(M) __LOG_LOG_4(__DEFAULT_LOGGER,Warn,M,false)
338 
339 #define __LOG_ERROR_2(I,M) __LOG_LOG_4(I,Error,M,false)
340 #define __LOG_ERROR_1(M) __LOG_LOG_4(__DEFAULT_LOGGER,Error,M,false)
341 
342 #define __LOG_FATAL_2(I,M) __LOG_LOG_4(I,Fatal,M,false)
343 #define __LOG_FATAL_1(M) __LOG_LOG_4(__DEFAULT_LOGGER,Fatal,M,false)
344 
345 #define __LOG_ASSERT_3(I,C,M) if (!(C)) { __LOG_ERROR_2(I,M) }
346 #define __LOG_ASSERT_2(C,M) __LOG_ASSERT_3(__DEFAULT_LOGGER,C,M)
347 
348 
349 #define __LOG_LOG_ONCE_3(I,L,M) __LOG_LOG_4(I,L,M,true)
350 #define __LOG_LOG_ONCE_2(L,M) __LOG_LOG_4(__DEFAULT_LOGGER,L,M,true)
351 #define __LOG_LOG_ONCE_1(M) __LOG_LOG_4(__DEFAULT_LOGGER,Debug,M,true)
352 
353 #define __LOG_TRACE_ONCE_2(I,M) __LOG_LOG_4(I,Trace,M,true)
354 #define __LOG_TRACE_ONCE_1(M) __LOG_LOG_4(__DEFAULT_LOGGER,Trace,M,true)
355 
356 #define __LOG_DEBUG_ONCE_2(I,M) __LOG_LOG_4(I,Debug,M,true)
357 #define __LOG_DEBUG_ONCE_1(M) __LOG_LOG_4(__DEFAULT_LOGGER,Debug,M,true)
358 
359 #define __LOG_INFO_ONCE_2(I,M) __LOG_LOG_4(I,Info,M,true)
360 #define __LOG_INFO_ONCE_1(M) __LOG_LOG_4(__DEFAULT_LOGGER,Info,M,true)
361 
362 #define __LOG_PROG_ONCE_2(I,M) __LOG_LOG_4(I,Prog,M,true)
363 #define __LOG_PROG_ONCE_1(M) __LOG_LOG_4(__DEFAULT_LOGGER,Prog,M,true)
364 
365 #define __LOG_WARN_ONCE_2(I,M) __LOG_LOG_4(I,Warn,M,true)
366 #define __LOG_WARN_ONCE_1(M) __LOG_LOG_4(__DEFAULT_LOGGER,Warn,M,true)
367 
368 #define __LOG_ERROR_ONCE_2(I,M) __LOG_LOG_4(I,Error,M,true)
369 #define __LOG_ERROR_ONCE_1(M) __LOG_LOG_4(__DEFAULT_LOGGER,Error,M,true)
370 
371 #define __LOG_FATAL_ONCE_2(I,M) __LOG_LOG_4(I,Fatal,M,true)
372 #define __LOG_FATAL_ONCE_1(M) __LOG_LOG_4(__DEFAULT_LOGGER,Fatal,M,true)
373 
374 
375 // PUBLIC MACROS
376 
377 #define LOGGER(I,K) static scarab::logger I(K);
378 
379 #ifndef _WIN32
380 
381 #define LOG(...) macro_dispatcher(__LOG_LOG_, __VA_ARGS__)(__VA_ARGS__)
382 #ifdef NDEBUG
383 #define LTRACE(...)
384 #define LDEBUG(...)
385 #else
386 #define LTRACE(...) macro_dispatcher(__LOG_TRACE_, __VA_ARGS__)(__VA_ARGS__)
387 #define LDEBUG(...) macro_dispatcher(__LOG_DEBUG_, __VA_ARGS__)(__VA_ARGS__)
388 #endif
389 #define LINFO(...) macro_dispatcher(__LOG_INFO_, __VA_ARGS__)(__VA_ARGS__)
390 #define LPROG(...) macro_dispatcher(__LOG_PROG_, __VA_ARGS__)(__VA_ARGS__)
391 #define LWARN(...) macro_dispatcher(__LOG_WARN_, __VA_ARGS__)(__VA_ARGS__)
392 #define LERROR(...) macro_dispatcher(__LOG_ERROR_, __VA_ARGS__)(__VA_ARGS__)
393 #define LFATAL(...) macro_dispatcher(__LOG_FATAL_, __VA_ARGS__)(__VA_ARGS__)
394 #define LASSERT(...) macro_dispatcher(__LOG_ASSERT_, __VA_ARGS__)(__VA_ARGS__)
395 
396 #define LOG_ONCE(...) macro_dispatcher(__LOG_LOG_ONCE_, __VA_ARGS__)(__VA_ARGS__)
397 #ifdef NDEBUG
398 #define LTRACE_ONCE(...)
399 #define LDEBUG_ONCE(...)
400 #else
401 #define LTRACE_ONCE(...) macro_dispatcher(__LOG_TRACE_ONCE_, __VA_ARGS__)(__VA_ARGS__)
402 #define LDEBUG_ONCE(...) macro_dispatcher(__LOG_DEBUG_ONCE_, __VA_ARGS__)(__VA_ARGS__)
403 #endif
404 #define LINFO_ONCE(...) macro_dispatcher(__LOG_INFO_ONCE_, __VA_ARGS__)(__VA_ARGS__)
405 #define LPROG_ONCE(...) macro_dispatcher(__LOG_PROG_ONCE_, __VA_ARGS__)(__VA_ARGS__)
406 #define LWARN_ONCE(...) macro_dispatcher(__LOG_WARN_ONCE_, __VA_ARGS__)(__VA_ARGS__)
407 #define LERROR_ONCE(...) macro_dispatcher(__LOG_ERROR_ONCE_, __VA_ARGS__)(__VA_ARGS__)
408 #define LFATAL_ONCE(...) macro_dispatcher(__LOG_FATAL_ONCE_, __VA_ARGS__)(__VA_ARGS__)
409 
410 #else /*_WIN32*/
411 
412 #define LOG(I, ...) __LOG_LOG_2(I, __VA_ARGS__)
413 #ifdef NDEBUG
414 #define LTRACE(I, ...)
415 #define LDEBUG(I, ...)
416 #else
417 #define LTRACE(I, ...) __LOG_TRACE_2(I, __VA_ARGS__)
418 #define LDEBUG(I, ...) __LOG_DEBUG_2(I, __VA_ARGS__)
419 #endif
420 #define LINFO(I, ...) __LOG_INFO_2(I, __VA_ARGS__)
421 #define LPROG(I, ...) __LOG_PROG_2(I, __VA_ARGS__)
422 #define LWARN(I, ...) __LOG_WARN_2(I, __VA_ARGS__)
423 #define LERROR(I, ...) __LOG_ERROR_2(I, __VA_ARGS__)
424 #define LFATAL(I, ...) __LOG_FATAL_2(I, __VA_ARGS__)
425 #define LASSERT(I, ...) __LOG_ASSERT_2(I, __VA_ARGS__)
426 
427 #define LOG_ONCE(I, ...) __LOG_LOG_ONCE_2(I, __VA_ARGS__)
428 #ifdef NDEBUG
429 #define LTRACE_ONCE(I, ...)
430 #define LDEBUG_ONCE(I, ...)
431 #else
432 #define LTRACE_ONCE(I, ...) __LOG_TRACE_ONCE_2(I, __VA_ARGS__)
433 #define LDEBUG_ONCE(I, ...) __LOG_DEBUG_ONCE_2(I, __VA_ARGS__)
434 #endif
435 #define LINFO_ONCE(I, ...) __LOG_INFO_ONCE_2(I, __VA_ARGS__)
436 #define LPROG_ONCE(I, ...) __LOG_PROG_ONCE_2(I, __VA_ARGS__)
437 #define LWARN_ONCE(I, ...) __LOG_WARN_ONCE_2(I, __VA_ARGS__)
438 #define LERROR_ONCE(I, ...) __LOG_ERROR_ONCE_2(I, __VA_ARGS__)
439 #define LFATAL_ONCE(I, ...) __LOG_FATAL_ONCE_2(I, __VA_ARGS__)
440 
441 #endif /*_WIN32*/
442 
443 #endif /* SCARAB_LOGGER_HH_ */
std::string fFileName
Definition: logger.hh:141
std::string fFunctionName
Definition: logger.hh:142
static logger & GetRootLogger()
Definition: logger.hh:146
void LogWarn(const std::string &message, const Location &loc=Location())
Definition: logger.hh:270
void LogInfo(const std::string &message, const Location &loc=Location())
Definition: logger.hh:250
#define SCARAB_API
Definition: scarab_api.hh:24
void LogProg(const std::string &message, const Location &loc=Location())
Definition: logger.hh:260
void LogDebug(const std::string &message, const Location &loc=Location())
Definition: logger.hh:240
void LogTrace(const std::string &message, const Location &loc=Location())
Definition: logger.hh:230
Location(const char *const fileName="", const char *const functionName="", int lineNumber=-1)
Definition: logger.hh:137
std::shared_ptr< Private > fPrivate
Definition: logger.hh:296
void LogFatal(const std::string &message, const Location &loc=Location())
Definition: logger.hh:290
void LogError(const std::string &message, const Location &loc=Location())
Definition: logger.hh:280