00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039 #ifndef _OSGLOG_H_
00040 #define _OSGLOG_H_
00041 #ifdef __sgi
00042 #pragma once
00043 #endif
00044
00045 #include <OSGBaseTypes.h>
00046 #include <OSGTime.h>
00047
00048 #include <fstream>
00049 #include <list>
00050
00055 OSG_BEGIN_NAMESPACE
00056
00060 enum LogType
00061 {
00062 LOG_NONE = 0,
00063 LOG_STDOUT = 1,
00064 LOG_STDERR = 2,
00065 LOG_FILE = 3,
00066 LOG_BUFFER = 4
00067 };
00068
00072 enum LogLevel
00073 {
00074 LOG_LOG = 0,
00075 LOG_FATAL = 1,
00076 LOG_WARNING = 2,
00077 LOG_NOTICE = 3,
00078 LOG_INFO = 4,
00079 LOG_DEBUG = 5
00080 };
00081
00085 enum LogHeaderElem
00086 {
00087 LOG_NONE_HEADER = 0,
00088 LOG_BEGIN_NEWLINE_HEADER = 1,
00089 LOG_TYPE_HEADER = 2,
00090 LOG_TIMESTAMP_HEADER = 4,
00091 LOG_MODULE_HEADER = 8,
00092 LOG_FILE_HEADER = 16,
00093 LOG_LINE_HEADER = 32,
00094 LOG_END_NEWLINE_HEADER = 64,
00095
00096 LOG_COLOR_HEADER = 8192,
00097 LOG_TAB_HEADER = 16384,
00098 LOG_ALL_HEADER = 32767
00099 };
00100
00105 enum LogModuleHandling
00106 {
00107 LOG_MODULE_NONE = 0,
00108 LOG_MODULE_KNOWN = 1,
00109 LOG_MODULE_UNKNOWN = 2,
00110 LOG_MODULE_UNDEFINED = 4,
00111 LOG_MODULE_ALL = 7
00112 };
00113
00120 struct OSG_BASE_DLLMAPPING LogOStream : public std::ostream
00121 {
00122 public:
00123
00124 LogOStream(std::streambuf *buf);
00125
00126 virtual ~LogOStream(void);
00127
00128 void setrdbuf(std::streambuf *buf);
00129 };
00130
00137 class OSG_BASE_DLLMAPPING LogBuf : public std::streambuf
00138 {
00139
00140
00141 public:
00142
00143
00144
00145 typedef void (*Callback)(const Char8 *data,
00146 Int32 size,
00147 void *clientData);
00148
00150 struct Chunk
00151 {
00152 Char8 *data;
00153 Int32 size;
00154
00155 Chunk(void);
00156 ~Chunk(void);
00157 };
00158
00159
00163 LogBuf( UInt32 bufferSize = 1024);
00164 LogBuf(const LogBuf & );
00165
00167
00171 virtual ~LogBuf();
00172
00174
00178 bool getEnabled (void );
00179 void setEnabled (bool value = true);
00180
00181 void clearChunkBag(void );
00182
00184
00187 void setCallback (Callback cb,
00188 void *clientData = 0,
00189 bool flushData = false);
00190 void removeCallback(void );
00191
00192
00194
00195
00196 private:
00197
00198 bool _enabled;
00199
00200 std::list<Chunk*> _chunkBag;
00201
00202 Callback _callback;
00203 void *_clientData;
00204
00205 const LogBuf &operator=(const LogBuf &);
00206 void write (const Char8 *buffer,
00207 std::streamsize size );
00208
00209
00213 virtual Int32 overflow( Int32 c );
00214 virtual Int32 sync ( void );
00215 virtual std::streamsize xsputn (const Char8 *buffer,
00216 std::streamsize size);
00217
00218 };
00219
00224 class OSG_BASE_DLLMAPPING Log : public std::ostream
00225 {
00226
00227
00228 public:
00229
00230
00234 Log( LogType logType = LOG_STDERR,
00235 LogLevel logLevel = LOG_NOTICE);
00236
00237 Log(const Char8 *fileName,
00238 LogLevel logLevel = LOG_NOTICE);
00239
00241
00245 virtual ~Log(void);
00246
00248
00252 void lock (void) {;}
00253 void unlock(void) {;}
00254
00256
00260 virtual void setHeaderElem ( UInt32 elemMask,
00261 bool force = false);
00262 virtual void addHeaderElem ( LogHeaderElem elem,
00263 bool force = false);
00264 virtual void delHeaderElem ( LogHeaderElem elem,
00265 bool force = false);
00266 virtual bool hasHeaderElem ( LogHeaderElem elem);
00267
00268 virtual void addModuleHandling( LogModuleHandling handling,
00269 bool force = false);
00270 virtual void delModuleHandling( LogModuleHandling handling,
00271 bool force = false);
00272
00273 virtual void addModuleName (const Char8 *module,
00274 bool isStatic = false);
00275 virtual void delModuleName (const Char8 *module );
00276
00277 bool hasModule (const Char8 *module );
00278 bool checkModule (const Char8 *module );
00279
00281
00285 LogType getLogType ( void );
00286 void setLogType ( LogType logType, bool force = false);
00287
00288 LogLevel getLogLevel ( void);
00289 void setLogLevel ( LogLevel logLevel, bool force = false);
00290 bool checkLevel ( LogLevel logLevel );
00291
00292 void setLogFile (const Char8 *fileName, bool force = false);
00293
00294 Time getRefTime ( void );
00295 void setRefTime ( Time refTime );
00296 void resetRefTime( void );
00297
00299
00303 LogBuf &getLogBuf(void );
00304
00305 std::ostream &stream (LogLevel level);
00306 std::ostream &nilstream(void );
00307
00309
00313 std::ostream &doHeader( LogLevel level,
00314 const Char8 *module,
00315 const Char8 *file,
00316 UInt32 line );
00317
00318 void doLog (const Char8 *format, ...);
00319
00321
00322
00323 protected:
00324
00325
00329 void connect(void );
00330
00331 bool colorHeader(LogLevel level, const char *sep);
00332
00334
00335
00336 private:
00337
00338 typedef std::ostream Inherited;
00339
00340 friend OSG_BASE_DLLMAPPING void doInitLog(void);
00341
00342
00347 struct OSG_BASE_DLLMAPPING nilbuf : public std::streambuf
00348 {
00349 };
00350
00352 struct Module
00353 {
00354 const Char8 *name;
00355 bool isStatic;
00356
00357 Module(void);
00358 };
00359
00361
00365 static nilbuf *_nilbufP;
00366 static std::ostream *_nilstreamP;
00367
00368 static const Char8 *_levelName[];
00369 static const Char8 *_levelColor[];
00370
00372
00376 LogType _logType;
00377 LogLevel _logLevel;
00378
00379 std::fstream _fileStream;
00380
00381 LogBuf _logBuf;
00382 LogOStream *_streamVec[6];
00383
00384 UInt32 _headerElem;
00385 UInt32 _moduleHandling;
00386
00387
00388 std::list<Module> _moduleList;
00389
00390 Time _refTime;
00391
00393
00397 Log(const Log &source);
00398
00400
00404 void operator =(const Log &source);
00405
00407 };
00408
00409 typedef Log *LogP;
00410
00411 #ifndef OSG_LOG_MODULE
00412 #define OSG_LOG_MODULE "OpenSG"
00413 #endif
00414
00415 extern OSG_BASE_DLLMAPPING LogP osgLogP;
00416
00417
00418 OSG_BASE_DLLMAPPING void doInitLog ( void );
00419 inline void initLog ( void );
00420 inline Log &osgLog ( void );
00421 inline std::ostream &osgStartLog( bool logHeader,
00422 LogLevel level,
00423 const Char8 *module,
00424 const Char8 *file,
00425 UInt32 line );
00426
00427 inline std::ostream &endLog ( std::ostream &strm );
00428
00429 inline void indentLog ( UInt32 indent,
00430 std::ostream &stream );
00431
00432
00437 #define SLOG \
00438 OSG::osgStartLog(true, OSG::LOG_LOG, OSG_LOG_MODULE, __FILE__, __LINE__)
00439
00444 #define SFATAL \
00445 OSG::osgStartLog(true, OSG::LOG_FATAL, OSG_LOG_MODULE, __FILE__, __LINE__)
00446
00451 #define SWARNING \
00452 OSG::osgStartLog(true, OSG::LOG_WARNING, OSG_LOG_MODULE, __FILE__, __LINE__)
00453
00458 #define SNOTICE \
00459 OSG::osgStartLog(true, OSG::LOG_NOTICE, OSG_LOG_MODULE, __FILE__, __LINE__)
00460
00465 #define SINFO \
00466 OSG::osgStartLog(true, OSG::LOG_INFO, OSG_LOG_MODULE, __FILE__, __LINE__)
00467
00468
00473 #define PLOG \
00474 OSG::osgStartLog(false, OSG::LOG_LOG, OSG_LOG_MODULE, __FILE__, __LINE__)
00475
00480 #define PFATAL \
00481 OSG::osgStartLog(false, OSG::LOG_FATAL, OSG_LOG_MODULE, __FILE__, __LINE__)
00482
00487 #define PWARNING \
00488 OSG::osgStartLog(false, OSG::LOG_WARNING, OSG_LOG_MODULE, __FILE__, __LINE__)
00489
00494 #define PNOTICE \
00495 OSG::osgStartLog(false, OSG::LOG_NOTICE, OSG_LOG_MODULE, __FILE__, __LINE__)
00496
00501 #define PINFO \
00502 OSG::osgStartLog(false, OSG::LOG_INFO, OSG_LOG_MODULE, __FILE__, __LINE__)
00503
00504
00505
00506
00507
00508
00513 #define FLOG(par) \
00514 { \
00515 OSG::initLog(); \
00516 OSG::osgStartLog(true, \
00517 OSG::LOG_LOG, \
00518 OSG_LOG_MODULE, \
00519 __FILE__, \
00520 __LINE__); \
00521 OSG::osgLogP->doLog par; \
00522 OSG::osgLogP->unlock(); \
00523 }
00524
00529 #define FFATAL(par) \
00530 { \
00531 OSG::initLog(); \
00532 if(OSG::osgLogP->checkLevel(OSG::LOG_FATAL)) \
00533 { \
00534 OSG::osgStartLog(true, \
00535 OSG::LOG_FATAL, \
00536 OSG_LOG_MODULE, \
00537 __FILE__, \
00538 __LINE__); \
00539 OSG::osgLogP->doLog par; \
00540 OSG::osgLogP->unlock(); \
00541 } \
00542 }
00543
00548 #define FWARNING(par) \
00549 { \
00550 OSG::initLog(); \
00551 if(OSG::osgLogP->checkLevel(OSG::LOG_WARNING)) \
00552 { \
00553 OSG::osgStartLog(true, \
00554 OSG::LOG_WARNING, \
00555 OSG_LOG_MODULE, \
00556 __FILE__, \
00557 __LINE__); \
00558 OSG::osgLogP->doLog par; \
00559 OSG::osgLogP->unlock(); \
00560 } \
00561 }
00562
00567 #define FNOTICE(par) \
00568 { \
00569 OSG::initLog(); \
00570 if(OSG::osgLogP->checkLevel(OSG::LOG_NOTICE)) \
00571 { \
00572 OSG::osgStartLog(true, \
00573 OSG::LOG_NOTICE, \
00574 OSG_LOG_MODULE, \
00575 __FILE__, \
00576 __LINE__); \
00577 OSG::osgLogP->doLog par; \
00578 OSG::osgLogP->unlock(); \
00579 } \
00580 }
00581
00586 #define FINFO(par) \
00587 { \
00588 OSG::initLog(); \
00589 if(OSG::osgLogP->checkLevel(OSG::LOG_INFO)) \
00590 { \
00591 OSG::osgStartLog(true, \
00592 OSG::LOG_INFO, \
00593 OSG_LOG_MODULE, \
00594 __FILE__, \
00595 __LINE__); \
00596 OSG::osgLogP->doLog par; \
00597 OSG::osgLogP->unlock(); \
00598 } \
00599 }
00600
00605 #ifdef OSG_DEBUG
00606 #define FDEBUG(par) \
00607 { \
00608 OSG::initLog(); \
00609 if(OSG::osgLogP->checkLevel(OSG::LOG_DEBUG)) \
00610 { \
00611 OSG::osgStartLog(true, \
00612 OSG::LOG_DEBUG,OSG_LOG_MODULE, \
00613 __FILE__, \
00614 __LINE__); \
00615 OSG::osgLogP->doLog par; \
00616 OSG::osgLogP->unlock(); \
00617 } \
00618 }
00619 #else
00620 #define FDEBUG(par)
00621 #endif
00622
00627 #define FASSERT(condition, doExit) \
00628 { \
00629 if (!condition) \
00630 { \
00631 OSG::osgLog().lock(); \
00632 OSG::osgLog().stream(OSG::LOG_FATAL) \
00633 << OSG_LOG_MODULE \
00634 << ':' \
00635 << __FILE__ \
00636 << ':' \
00637 << __LINE__ \
00638 << " FATAL ASSERT: " \
00639 << (doExit ? "exit system" : "try to keep running") \
00640 << std::flush << std::endl; \
00641 OSG::osgLog().unlock(); \
00642 if(doExit) \
00643 exit(-1); \
00644 } \
00645 }
00646
00651 #define FFASSERT(condition, doExit, par) \
00652 { \
00653 if(!condition) \
00654 { \
00655 OSG::osgLog().lock(); \
00656 OSG::osgLog().stream(OSG::LOG_FATAL) \
00657 << OSG_LOG_MODULE \
00658 << ':' \
00659 << __FILE__ \
00660 << ':' \
00661 << __LINE__ \
00662 << " FATAL ASSERT: " \
00663 << (doExit ? "exit system" : "try to keep running") \
00664 << std::flush << std::endl; \
00665 OSG::osgLogP->doLog par \
00666 OSG::osgLog().unlock(); \
00667 if(doExit) \
00668 exit(-1); \
00669 } \
00670 }
00671
00672
00673
00678 #define FPLOG(par) \
00679 { \
00680 OSG::initLog(); \
00681 OSG::osgStartLog(false, \
00682 OSG::LOG_LOG, \
00683 OSG_LOG_MODULE, \
00684 __FILE__, \
00685 __LINE__); \
00686 OSG::osgLogP->doLog par; \
00687 OSG::osgLogP->unlock(); \
00688 }
00689
00694 #define FPFPATAL(par) \
00695 { \
00696 OSG::initLog(); \
00697 if(OSG::osgLogP->checkLevel(OSG::LOG_FPATAL)) \
00698 { \
00699 OSG::osgStartLog(false, \
00700 OSG::LOG_FPATAL, \
00701 OSG_LOG_MODULE, \
00702 __FILE__, \
00703 __LINE__); \
00704 OSG::osgLogP->doLog par; \
00705 OSG::osgLogP->unlock(); \
00706 } \
00707 }
00708
00713 #define FPWARNING(par) \
00714 { \
00715 OSG::initLog(); \
00716 if(OSG::osgLogP->checkLevel(OSG::LOG_WARNING)) \
00717 { \
00718 OSG::osgStartLog(false, \
00719 OSG::LOG_WARNING, \
00720 OSG_LOG_MODULE, \
00721 __FILE__, \
00722 __LINE__); \
00723 OSG::osgLogP->doLog par; \
00724 OSG::osgLogP->unlock(); \
00725 } \
00726 }
00727
00732 #define FPNOTICE(par) \
00733 { \
00734 OSG::initLog(); \
00735 if(OSG::osgLogP->checkLevel(OSG::LOG_NOTICE)) \
00736 { \
00737 OSG::osgStartLog(false, \
00738 OSG::LOG_NOTICE, \
00739 OSG_LOG_MODULE, \
00740 __FILE__, \
00741 __LINE__); \
00742 OSG::osgLogP->doLog par; \
00743 OSG::osgLogP->unlock(); \
00744 } \
00745 }
00746
00751 #define FPINFPO(par) \
00752 { \
00753 OSG::initLog(); \
00754 if(OSG::osgLogP->checkLevel(OSG::LOG_INFPO)) \
00755 { \
00756 OSG::osgStartLog(false, \
00757 OSG::LOG_INFPO, \
00758 OSG_LOG_MODULE, \
00759 __FILE__, \
00760 __LINE__); \
00761 OSG::osgLogP->doLog par; \
00762 OSG::osgLogP->unlock(); \
00763 } \
00764 }
00765
00770 #ifdef OSG_DEBUG
00771 #define FPDEBUG(par) \
00772 { \
00773 OSG::initLog(); \
00774 if(OSG::osgLogP->checkLevel(OSG::LOG_DEBUG)) \
00775 { \
00776 OSG::osgStartLog(false, \
00777 OSG::LOG_DEBUG,OSG_LOG_MODULE, \
00778 __FILE__, \
00779 __LINE__); \
00780 OSG::osgLogP->doLog par; \
00781 OSG::osgLogP->unlock(); \
00782 } \
00783 }
00784 #else
00785 #define FPDEBUG(par)
00786 #endif
00787
00788 OSG_END_NAMESPACE
00789
00790 #include <OSGLog.inl>
00791
00792 #endif