comparison Core/Logging.cpp @ 3359:815b81142ff7 emscripten-logging

Enable custom logging functions to redirect to emscripten specific logging calls in the ORTHANC_ENABLE_LOGGING_STDIO mode.
author Benjamin Golinvaux <bgo@osimis.io>
date Tue, 07 May 2019 11:23:11 +0200
parents 54cdad5a7228
children ea07b29c6d0e
comparison
equal deleted inserted replaced
3355:eb18269de57f 3359:815b81142ff7
61 } 61 }
62 62
63 void EnableTraceLevel(bool enabled) 63 void EnableTraceLevel(bool enabled)
64 { 64 {
65 } 65 }
66 66
67 bool IsTraceLevelEnabled()
68 {
69 return false;
70 }
71
72 bool IsInfoLevelEnabled()
73 {
74 return false;
75 }
76
67 void SetTargetFile(const std::string& path) 77 void SetTargetFile(const std::string& path)
68 { 78 {
69 } 79 }
70 80
71 void SetTargetFolder(const std::string& path) 81 void SetTargetFolder(const std::string& path)
138 148
139 149
140 #elif ORTHANC_ENABLE_LOGGING_STDIO == 1 150 #elif ORTHANC_ENABLE_LOGGING_STDIO == 1
141 151
142 /********************************************************* 152 /*********************************************************
143 * Logger compatible with <stdio.h> 153 * Logger compatible with <stdio.h> OR logger that sends its
154 * output to the emscripten html5 api (depending on the
155 * definition of __EMSCRIPTEN__)
144 *********************************************************/ 156 *********************************************************/
145 157
146 #include <stdio.h> 158 #include <stdio.h>
147 #include <boost/lexical_cast.hpp> 159 #include <boost/lexical_cast.hpp>
160
161 #ifdef __EMSCRIPTEN__
162 #include "emscripten/html5.h"
163 #endif
148 164
149 namespace Orthanc 165 namespace Orthanc
150 { 166 {
151 namespace Logging 167 namespace Logging
152 { 168 {
153 static bool globalVerbose_ = false; 169 static bool globalVerbose_ = false;
154 static bool globalTrace_ = false; 170 static bool globalTrace_ = false;
155 171
172 #ifdef __EMSCRIPTEN__
173 void defaultErrorLogFunc(const char* msg)
174 {
175 emscripten_console_error(msg);
176 }
177
178 void defaultWarningLogFunc(const char* msg)
179 {
180 emscripten_console_warn(msg);
181 }
182
183 void defaultInfoLogFunc(const char* msg)
184 {
185 emscripten_console_log(msg);
186 }
187
188 void defaultTraceLogFunc(const char* msg)
189 {
190 emscripten_console_log(msg);
191 }
192 #else
193 // __EMSCRIPTEN__ not #defined
194 void defaultErrorLogFunc(const char* msg)
195 {
196 fprintf(stderr, "E: %s\n", msg);
197 }
198
199 void defaultWarningLogFunc(const char*)
200 {
201 fprintf(stdout, "W: %s\n", msg);
202 }
203
204 void defaultInfoLogFunc(const char*)
205 {
206 fprintf(stdout, "I: %s\n", msg);
207 }
208
209 void defaultTraceLogFunc(const char*)
210 {
211 fprintf(stdout, "T: %s\n", msg);
212 }
213 #endif
214 // __EMSCRIPTEN__
215
216 static LoggingFunction globalErrorLogFunc = defaultErrorLogFunc;
217 static LoggingFunction globalWarningLogFunc = defaultWarningLogFunc;
218 static LoggingFunction globalInfoLogFunc = defaultInfoLogFunc;
219 static LoggingFunction globalTraceLogFunc = defaultTraceLogFunc;
220
221 void SetErrorWarnInfoTraceLoggingFunctions(
222 LoggingFunction errorLogFunc,
223 LoggingFunction warningLogfunc,
224 LoggingFunction infoLogFunc,
225 LoggingFunction traceLogFunc)
226 {
227 globalErrorLogFunc = errorLogFunc;
228 globalWarningLogFunc = warningLogfunc;
229 globalInfoLogFunc = infoLogFunc;
230 globalTraceLogFunc = traceLogFunc;
231 }
232
156 InternalLogger::InternalLogger(InternalLevel level, 233 InternalLogger::InternalLogger(InternalLevel level,
157 const char* file /* ignored */, 234 const char* file /* ignored */,
158 int line /* ignored */) : 235 int line /* ignored */) :
159 level_(level) 236 level_(level)
160 { 237 {
163 InternalLogger::~InternalLogger() 240 InternalLogger::~InternalLogger()
164 { 241 {
165 switch (level_) 242 switch (level_)
166 { 243 {
167 case InternalLevel_ERROR: 244 case InternalLevel_ERROR:
168 fprintf(stderr, "E: %s\n", message_.c_str()); 245 globalErrorLogFunc(message_.c_str());
169 break; 246 break;
170 247
171 case InternalLevel_WARNING: 248 case InternalLevel_WARNING:
172 fprintf(stdout, "W: %s\n", message_.c_str()); 249 globalWarningLogFunc(message_.c_str());
173 break; 250 break;
174 251
175 case InternalLevel_INFO: 252 case InternalLevel_INFO:
176 if (globalVerbose_) 253 if (globalVerbose_)
177 { 254 {
178 fprintf(stdout, "I: %s\n", message_.c_str()); 255 globalInfoLogFunc(message_.c_str());
256 // TODO: stone_console_info(message_.c_str());
179 } 257 }
180 break; 258 break;
181 259
182 case InternalLevel_TRACE: 260 case InternalLevel_TRACE:
183 if (globalTrace_) 261 if (globalTrace_)
184 { 262 {
185 fprintf(stdout, "T: %s\n", message_.c_str()); 263 globalTraceLogFunc(message_.c_str());
186 } 264 }
187 break; 265 break;
188 266
189 default: 267 default:
190 fprintf(stderr, "Unknown log level (%d) for message: %s\n", level_, message_.c_str()); 268 {
269 std::stringstream ss;
270 ss << "Unknown log level (" << level_ << ") for message: " << message_;
271 auto s = ss.str();
272 globalErrorLogFunc(s.c_str());
273 }
191 } 274 }
192 } 275 }
193 276
194 void EnableInfoLevel(bool enabled) 277 void EnableInfoLevel(bool enabled)
195 { 278 {
196 globalVerbose_ = enabled; 279 globalVerbose_ = enabled;
197 } 280 }
198 281
282 bool IsInfoLevelEnabled()
283 {
284 return globalVerbose_;
285 }
286
199 void EnableTraceLevel(bool enabled) 287 void EnableTraceLevel(bool enabled)
200 { 288 {
201 globalTrace_ = enabled; 289 globalTrace_ = enabled;
202 } 290 }
291
292 bool IsTraceLevelEnabled()
293 {
294 return globalTrace_;
295 }
296
203 } 297 }
204 } 298 }
205 299
206 300
207 #else /* ORTHANC_ENABLE_LOGGING_PLUGIN == 0 && 301 #else /* ORTHANC_ENABLE_LOGGING_PLUGIN == 0 &&
386 480
387 LoggingMemento CreateLoggingMemento() 481 LoggingMemento CreateLoggingMemento()
388 { 482 {
389 LoggingMementoImpl* memento = new LoggingMementoImpl(); 483 LoggingMementoImpl* memento = new LoggingMementoImpl();
390 484
391 memento->valid_ = TRUE; 485 memento->valid_ = true;
392 { 486 {
393 boost::mutex::scoped_lock lock(loggingMutex_); 487 boost::mutex::scoped_lock lock(loggingMutex_);
394 memento->infoEnabled_ = loggingContext_->infoEnabled_; 488 memento->infoEnabled_ = loggingContext_->infoEnabled_;
395 memento->traceEnabled_ = loggingContext_->traceEnabled_; 489 memento->traceEnabled_ = loggingContext_->traceEnabled_;
396 memento->targetFile_ = loggingContext_->targetFile_; 490 memento->targetFile_ = loggingContext_->targetFile_;
407 { 501 {
408 LoggingMementoImpl* memento = 502 LoggingMementoImpl* memento =
409 reinterpret_cast<LoggingMementoImpl*>(mementoPtr); 503 reinterpret_cast<LoggingMementoImpl*>(mementoPtr);
410 if (!memento->valid_) 504 if (!memento->valid_)
411 throw std::runtime_error("Memento already used"); 505 throw std::runtime_error("Memento already used");
412 memento->valid_ = FALSE; 506 memento->valid_ = false;
413 { 507 {
414 boost::mutex::scoped_lock lock(loggingMutex_); 508 boost::mutex::scoped_lock lock(loggingMutex_);
415 loggingContext_.reset(new LoggingContext); 509 loggingContext_.reset(new LoggingContext);
416 loggingContext_->error_ = memento->error_; 510 loggingContext_->error_ = memento->error_;
417 loggingContext_->warning_ = memento->warning_; 511 loggingContext_->warning_ = memento->warning_;
448 // Also disable the "TRACE" level when info-level debugging is disabled 542 // Also disable the "TRACE" level when info-level debugging is disabled
449 loggingContext_->traceEnabled_ = false; 543 loggingContext_->traceEnabled_ = false;
450 } 544 }
451 } 545 }
452 546
547 bool IsInfoLevelEnable()
548 {
549 boost::mutex::scoped_lock lock(loggingMutex_);
550 assert(loggingContext_.get() != NULL);
551
552 return loggingContext_->infoEnabled_;
553 }
554
453 void EnableTraceLevel(bool enabled) 555 void EnableTraceLevel(bool enabled)
454 { 556 {
455 boost::mutex::scoped_lock lock(loggingMutex_); 557 boost::mutex::scoped_lock lock(loggingMutex_);
456 assert(loggingContext_.get() != NULL); 558 assert(loggingContext_.get() != NULL);
457 559
460 if (enabled) 562 if (enabled)
461 { 563 {
462 // Also enable the "INFO" level when trace-level debugging is enabled 564 // Also enable the "INFO" level when trace-level debugging is enabled
463 loggingContext_->infoEnabled_ = true; 565 loggingContext_->infoEnabled_ = true;
464 } 566 }
567 }
568
569 bool IsTraceLevelEnable()
570 {
571 boost::mutex::scoped_lock lock(loggingMutex_);
572 assert(loggingContext_.get() != NULL);
573
574 return loggingContext_->traceEnabled_;
465 } 575 }
466 576
467 577
468 static void CheckFile(std::auto_ptr<std::ofstream>& f) 578 static void CheckFile(std::auto_ptr<std::ofstream>& f)
469 { 579 {
662 { 772 {
663 loggingContext_->file_->flush(); 773 loggingContext_->file_->flush();
664 } 774 }
665 } 775 }
666 776
667
668
669
670 /*
671 struct FunctionCallingStream : std::ostream, std::streambuf
672 {
673 template<typename T>
674 FunctionCallingStream(T func) : std::ostream(this), func_(func) {}
675
676 int overflow(int c)
677 {
678 if (c != '\n')
679 {
680 currentLine_
681 }
682 else
683 {
684 func_(currentLine_.str().c_str());
685 currentLine_.str("");
686 currentLine_.clear("");
687 }
688 return 0;
689 }
690
691 private:
692 std::stringstream currentLine_;
693 };
694 */
695
696 void SetErrorWarnInfoLoggingStreams(std::ostream* errorStream, 777 void SetErrorWarnInfoLoggingStreams(std::ostream* errorStream,
697 std::ostream* warningStream, 778 std::ostream* warningStream,
698 std::ostream* infoStream) 779 std::ostream* infoStream)
699 { 780 {
700 boost::mutex::scoped_lock lock(loggingMutex_); 781 boost::mutex::scoped_lock lock(loggingMutex_);