comparison OrthancFramework/Sources/Logging.cpp @ 4269:c7bd2f21ccc3

new macro CLOG, and sharing more code between logging engines
author Sebastien Jodogne <s.jodogne@gmail.com>
date Mon, 02 Nov 2020 17:15:57 +0100
parents 0ae2ca210077
children 251a8b07fa37
comparison
equal deleted inserted replaced
4268:0ae2ca210077 4269:c7bd2f21ccc3
24 #include "Logging.h" 24 #include "Logging.h"
25 25
26 #include "OrthancException.h" 26 #include "OrthancException.h"
27 27
28 28
29 namespace Orthanc
30 {
31 namespace Logging
32 {
33 const char* EnumerationToString(LogLevel level)
34 {
35 switch (level)
36 {
37 case LogLevel_ERROR:
38 return "ERROR";
39
40 case LogLevel_WARNING:
41 return "WARNING";
42
43 case LogLevel_INFO:
44 return "INFO";
45
46 case LogLevel_TRACE:
47 return "TRACE";
48
49 default:
50 throw OrthancException(ErrorCode_ParameterOutOfRange);
51 }
52 }
53
54
55 LogLevel StringToLogLevel(const char *level)
56 {
57 if (strcmp(level, "ERROR") == 0)
58 {
59 return LogLevel_ERROR;
60 }
61 else if (strcmp(level, "WARNING") == 0)
62 {
63 return LogLevel_WARNING;
64 }
65 else if (strcmp(level, "INFO") == 0)
66 {
67 return LogLevel_INFO;
68 }
69 else if (strcmp(level, "TRACE") == 0)
70 {
71 return LogLevel_TRACE;
72 }
73 else
74 {
75 throw OrthancException(ErrorCode_InternalError);
76 }
77 }
78 }
79 }
80
81
82 #if ORTHANC_ENABLE_LOGGING != 1
83
84 namespace Orthanc
85 {
86 namespace Logging
87 {
88 void InitializePluginContext(void* pluginContext)
89 {
90 }
91
92 void Initialize()
93 {
94 }
95
96 void Finalize()
97 {
98 }
99
100 void Reset()
101 {
102 }
103
104 void Flush()
105 {
106 }
107
108 void EnableInfoLevel(bool enabled)
109 {
110 }
111
112 void EnableTraceLevel(bool enabled)
113 {
114 }
115
116 bool IsTraceLevelEnabled()
117 {
118 return false;
119 }
120
121 bool IsInfoLevelEnabled()
122 {
123 return false;
124 }
125
126 void SetTargetFile(const std::string& path)
127 {
128 }
129
130 void SetTargetFolder(const std::string& path)
131 {
132 }
133 }
134 }
135
136
137 #elif ORTHANC_ENABLE_LOGGING_STDIO == 1
138
139 /********************************************************* 29 /*********************************************************
140 * Logger compatible with <stdio.h> OR logger that sends its 30 * Common section
141 * output to the emscripten html5 api (depending on the
142 * definition of __EMSCRIPTEN__)
143 *********************************************************/ 31 *********************************************************/
144
145 #include <stdio.h>
146
147 #ifdef __EMSCRIPTEN__
148 # include <emscripten/html5.h>
149 #endif
150 32
151 namespace Orthanc 33 namespace Orthanc
152 { 34 {
153 namespace Logging 35 namespace Logging
154 { 36 {
155 static bool infoEnabled_ = false; 37 static bool infoEnabled_ = false;
156 static bool traceEnabled_ = false; 38 static bool traceEnabled_ = false;
157 39
40 const char* EnumerationToString(LogLevel level)
41 {
42 switch (level)
43 {
44 case LogLevel_ERROR:
45 return "ERROR";
46
47 case LogLevel_WARNING:
48 return "WARNING";
49
50 case LogLevel_INFO:
51 return "INFO";
52
53 case LogLevel_TRACE:
54 return "TRACE";
55
56 default:
57 throw OrthancException(ErrorCode_ParameterOutOfRange);
58 }
59 }
60
61
62 LogLevel StringToLogLevel(const char *level)
63 {
64 if (strcmp(level, "ERROR") == 0)
65 {
66 return LogLevel_ERROR;
67 }
68 else if (strcmp(level, "WARNING") == 0)
69 {
70 return LogLevel_WARNING;
71 }
72 else if (strcmp(level, "INFO") == 0)
73 {
74 return LogLevel_INFO;
75 }
76 else if (strcmp(level, "TRACE") == 0)
77 {
78 return LogLevel_TRACE;
79 }
80 else
81 {
82 throw OrthancException(ErrorCode_InternalError);
83 }
84 }
85
86 void EnableInfoLevel(bool enabled)
87 {
88 infoEnabled_ = enabled;
89
90 if (!enabled)
91 {
92 // Also disable the "TRACE" level when info-level debugging is disabled
93 traceEnabled_ = false;
94 }
95 }
96
97 bool IsInfoLevelEnabled()
98 {
99 return infoEnabled_;
100 }
101
102 void EnableTraceLevel(bool enabled)
103 {
104 traceEnabled_ = enabled;
105
106 if (enabled)
107 {
108 // Also enable the "INFO" level when trace-level debugging is enabled
109 infoEnabled_ = true;
110 }
111 }
112
113 bool IsTraceLevelEnabled()
114 {
115 return traceEnabled_;
116 }
117
118 static bool IsLoggingEnabled(LogLevel level,
119 LogCategory category)
120 {
121 if (level == LogLevel_ERROR ||
122 level == LogLevel_WARNING)
123 {
124 return true;
125 }
126 else if (level == LogLevel_INFO)
127 {
128 return infoEnabled_;
129 }
130 else if (level == LogLevel_TRACE)
131 {
132 return traceEnabled_;
133 }
134 else
135 {
136 return false;
137 }
138 }
139 }
140 }
141
142
143
144 #if ORTHANC_ENABLE_LOGGING != 1
145
146 /*********************************************************
147 * Section if logging is disabled
148 *********************************************************/
149
150 namespace Orthanc
151 {
152 namespace Logging
153 {
154 void InitializePluginContext(void* pluginContext)
155 {
156 }
157
158 void Initialize()
159 {
160 }
161
162 void Finalize()
163 {
164 }
165
166 void Reset()
167 {
168 }
169
170 void Flush()
171 {
172 }
173
174 void SetTargetFile(const std::string& path)
175 {
176 }
177
178 void SetTargetFolder(const std::string& path)
179 {
180 }
181 }
182 }
183
184
185 #elif ORTHANC_ENABLE_LOGGING_STDIO == 1
186
187 /*********************************************************
188 * Logger compatible with <stdio.h> OR logger that sends its
189 * output to the emscripten html5 api (depending on the
190 * definition of __EMSCRIPTEN__)
191 *********************************************************/
192
193 #include <stdio.h>
194
195 #ifdef __EMSCRIPTEN__
196 # include <emscripten/html5.h>
197 #endif
198
199 namespace Orthanc
200 {
201 namespace Logging
202 {
158 #ifdef __EMSCRIPTEN__ 203 #ifdef __EMSCRIPTEN__
159 static void ErrorLogFunc(const char* msg) 204 static void ErrorLogFunc(const char* msg)
160 { 205 {
161 emscripten_console_error(msg); 206 emscripten_console_error(msg);
162 } 207 }
200 245
201 InternalLogger::~InternalLogger() 246 InternalLogger::~InternalLogger()
202 { 247 {
203 std::string message = messageStream_.str(); 248 std::string message = messageStream_.str();
204 249
205 switch (level_) 250 if (IsLoggingEnabled(level_, category_))
206 { 251 {
207 case LogLevel_ERROR: 252 switch (level_)
208 ErrorLogFunc(message.c_str()); 253 {
209 break; 254 case LogLevel_ERROR:
210 255 ErrorLogFunc(message.c_str());
211 case LogLevel_WARNING: 256 break;
212 WarningLogFunc(message.c_str()); 257
213 break; 258 case LogLevel_WARNING:
214 259 WarningLogFunc(message.c_str());
215 case LogLevel_INFO: 260 break;
216 if (infoEnabled_) 261
217 { 262 case LogLevel_INFO:
218 InfoLogFunc(message.c_str()); 263 InfoLogFunc(message.c_str());
219 // TODO: stone_console_info(message_.c_str()); 264 // TODO: stone_console_info(message_.c_str());
265 break;
266
267 case LogLevel_TRACE:
268 TraceLogFunc(message.c_str());
269 break;
270
271 default:
272 {
273 std::stringstream ss;
274 ss << "Unknown log level (" << level_ << ") for message: " << message;
275 std::string s = ss.str();
276 ErrorLogFunc(s.c_str());
220 } 277 }
221 break;
222
223 case LogLevel_TRACE:
224 // TODO - Check trace category
225 if (traceEnabled_)
226 {
227 TraceLogFunc(message.c_str());
228 }
229 break;
230
231 default:
232 {
233 std::stringstream ss;
234 ss << "Unknown log level (" << level_ << ") for message: " << message;
235 std::string s = ss.str();
236 ErrorLogFunc(s.c_str());
237 } 278 }
238 } 279 }
239 } 280 }
240 281
241 void InitializePluginContext(void* pluginContext) 282 void InitializePluginContext(void* pluginContext)
254 { 295 {
255 } 296 }
256 297
257 void Flush() 298 void Flush()
258 { 299 {
259 }
260
261 void EnableInfoLevel(bool enabled)
262 {
263 infoEnabled_ = enabled;
264
265 if (!enabled)
266 {
267 // Also disable the "TRACE" level when info-level debugging is disabled
268 traceEnabled_ = false;
269 }
270 }
271
272 bool IsInfoLevelEnabled()
273 {
274 return infoEnabled_;
275 }
276
277 void EnableTraceLevel(bool enabled)
278 {
279 traceEnabled_ = enabled;
280 }
281
282 bool IsTraceLevelEnabled()
283 {
284 return traceEnabled_;
285 } 300 }
286 301
287 void SetTargetFile(const std::string& path) 302 void SetTargetFile(const std::string& path)
288 { 303 {
289 } 304 }
366 381
367 static std::unique_ptr<LoggingStreamsContext> loggingStreamsContext_; 382 static std::unique_ptr<LoggingStreamsContext> loggingStreamsContext_;
368 static boost::mutex loggingStreamsMutex_; 383 static boost::mutex loggingStreamsMutex_;
369 static Orthanc::Logging::NullStream nullStream_; 384 static Orthanc::Logging::NullStream nullStream_;
370 static OrthancPluginContext* pluginContext_ = NULL; 385 static OrthancPluginContext* pluginContext_ = NULL;
371 static bool infoEnabled_ = false;
372 static bool traceEnabled_ = false;
373 386
374 387
375 namespace Orthanc 388 namespace Orthanc
376 { 389 {
377 namespace Logging 390 namespace Logging
494 case LogLevel_TRACE: 507 case LogLevel_TRACE:
495 c = 'T'; 508 c = 'T';
496 break; 509 break;
497 510
498 default: 511 default:
499 throw OrthancException(ErrorCode_InternalError); 512 c = '?';
513 break;
500 } 514 }
501 515
502 char date[64]; 516 char date[64];
503 sprintf(date, "%c%02d%02d %02d:%02d:%02d.%06d ", 517 sprintf(date, "%c%02d%02d %02d:%02d:%02d.%06d ",
504 c, 518 c,
573 SetTargetFile(old->targetFile_); 587 SetTargetFile(old->targetFile_);
574 } 588 }
575 } 589 }
576 590
577 591
578 void EnableInfoLevel(bool enabled)
579 {
580 infoEnabled_ = enabled;
581
582 if (!enabled)
583 {
584 // Also disable the "TRACE" level when info-level debugging is disabled
585 traceEnabled_ = false;
586 }
587 }
588
589 bool IsInfoLevelEnabled()
590 {
591 return infoEnabled_;
592 }
593
594 void EnableTraceLevel(bool enabled)
595 {
596 traceEnabled_ = enabled;
597
598 if (enabled)
599 {
600 // Also enable the "INFO" level when trace-level debugging is enabled
601 infoEnabled_ = true;
602 }
603 }
604
605 bool IsTraceLevelEnabled()
606 {
607 return traceEnabled_;
608 }
609
610
611 void SetTargetFolder(const std::string& path) 592 void SetTargetFolder(const std::string& path)
612 { 593 {
613 boost::mutex::scoped_lock lock(loggingStreamsMutex_); 594 boost::mutex::scoped_lock lock(loggingStreamsMutex_);
614 if (loggingStreamsContext_.get() != NULL) 595 if (loggingStreamsContext_.get() != NULL)
615 { 596 {
642 } 623 }
643 } 624 }
644 625
645 626
646 InternalLogger::InternalLogger(LogLevel level, 627 InternalLogger::InternalLogger(LogLevel level,
647 TraceCategory category, 628 LogCategory category,
648 const char* file, 629 const char* file,
649 int line) : 630 int line) :
650 lock_(loggingStreamsMutex_, boost::defer_lock_t()), 631 lock_(loggingStreamsMutex_, boost::defer_lock_t()),
651 level_(level), 632 level_(level),
652 category_(category),
653 stream_(&nullStream_) // By default, logging to "/dev/null" is simulated 633 stream_(&nullStream_) // By default, logging to "/dev/null" is simulated
654 { 634 {
655 if (pluginContext_ != NULL) 635 if (pluginContext_ != NULL)
656 { 636 {
657 // We are logging using the Orthanc plugin SDK 637 // We are logging using the Orthanc plugin SDK
658 638
659 if (level == LogLevel_TRACE) 639 if (level == LogLevel_TRACE ||
640 !IsLoggingEnabled(level, category))
660 { 641 {
661 // No trace level in plugins, directly exit as the stream is 642 // No trace level in plugins, directly exit as the stream is
662 // set to "/dev/null" 643 // set to "/dev/null"
663 return; 644 return;
664 } 645 }
670 } 651 }
671 else 652 else
672 { 653 {
673 // We are logging in a standalone application, not inside an Orthanc plugin 654 // We are logging in a standalone application, not inside an Orthanc plugin
674 655
675 if ((level == LogLevel_INFO && !infoEnabled_) || 656 if (!IsLoggingEnabled(level, category))
676 (level == LogLevel_TRACE && !traceEnabled_)) // TODO - Check trace category
677 { 657 {
678 // This logging level is disabled, directly exit as the 658 // This logging level is disabled, directly exit as the
679 // stream is set to "/dev/null" 659 // stream is set to "/dev/null"
680 return; 660 return;
681 } 661 }
708 case LogLevel_INFO: 688 case LogLevel_INFO:
709 case LogLevel_TRACE: 689 case LogLevel_TRACE:
710 stream_ = loggingStreamsContext_->info_; 690 stream_ = loggingStreamsContext_->info_;
711 break; 691 break;
712 692
713 default: 693 default: // Should not occur
714 throw OrthancException(ErrorCode_InternalError); 694 stream_ = loggingStreamsContext_->error_;
695 break;
715 } 696 }
716 697
717 if (stream_ == &nullStream_) 698 if (stream_ == &nullStream_)
718 { 699 {
719 // The logging is disabled for this level, we can release 700 // The logging is disabled for this level, we can release