]> git.uio.no Git - u/mrichter/AliRoot.git/blob - HLT/BASE/AliHLTLogging.h
updated logging concept
[u/mrichter/AliRoot.git] / HLT / BASE / AliHLTLogging.h
1 // @(#) $Id$
2
3 #ifndef ALIHLTLOGGING_H
4 #define ALIHLTLOGGING_H
5 /* This file is property of and copyright by the ALICE HLT Project        * 
6  * ALICE Experiment at CERN, All rights reserved.                         *
7  * See cxx source for full Copyright notice                               */
8
9 /** @file   AliHLTLogging.h
10     @author Matthias Richter, Timm Steinbeck
11     @date   
12     @brief  HLT module logging primitives.
13 */
14
15 #include "AliHLTDataTypes.h"
16 #include "AliHLTStdIncludes.h"
17 #include "TString.h"
18 #include "TObject.h"
19 #include "TArrayC.h"
20
21 class AliHLTComponentHandler;
22 //#define LOG_PREFIX ""       // logging prefix, for later extensions
23
24 #define ALILOG_WRAPPER_LIBRARY "libHLTrec.so"
25
26 /* the logging macros can be used inside methods of classes which inherit from 
27  * AliHLTLogging
28  */
29 // HLTMessage is not filtered
30 #define HLTMessage( ... )   LoggingVarargs(kHLTLogNone,      NULL , NULL , __FILE__ , __LINE__ , __VA_ARGS__ )
31
32 // function name
33 #if defined(__GNUC__) || defined(__ICC) || defined(__ECC) || defined(__APPLE__)
34 #define FUNCTIONNAME() __FUNCTION__
35 #else
36 #define FUNCTIONNAME() "???"
37 #endif
38
39 // the following macros are filtered by the Global and Local Log Filter
40 #define HLTBenchmark( ... ) LoggingVarargs(kHLTLogBenchmark, Class_Name() , FUNCTIONNAME() , __FILE__ , __LINE__ , __VA_ARGS__ )
41 #ifdef __DEBUG
42 #define HLTDebug( ... )     if (CheckFilter(kHLTLogDebug) && CheckGroup(Class_Name())) LoggingVarargs(kHLTLogDebug,     Class_Name() , FUNCTIONNAME() , __FILE__ , __LINE__ , __VA_ARGS__ )
43 #else
44 #define HLTDebug( ... )
45 #endif
46 #define HLTInfo( ... )      if (CheckFilter(kHLTLogInfo))    LoggingVarargs(kHLTLogInfo,      Class_Name() , FUNCTIONNAME() , __FILE__ , __LINE__ , __VA_ARGS__ )
47 #define HLTWarning( ... )   if (CheckFilter(kHLTLogWarning)) LoggingVarargs(kHLTLogWarning,   Class_Name() , FUNCTIONNAME() , __FILE__ , __LINE__ , __VA_ARGS__ )
48 #define HLTError( ... )     if (CheckFilter(kHLTLogError))   LoggingVarargs(kHLTLogError,     Class_Name() , FUNCTIONNAME() , __FILE__ , __LINE__ , __VA_ARGS__ )
49 #define HLTFatal( ... )     if (CheckFilter(kHLTLogFatal))   LoggingVarargs(kHLTLogFatal,     Class_Name() , FUNCTIONNAME() , __FILE__ , __LINE__ , __VA_ARGS__ )
50 #define HLTImportant( ... ) if (CheckFilter(kHLTLogImportant))LoggingVarargs(kHLTLogImportant,Class_Name() , FUNCTIONNAME() , __FILE__ , __LINE__ , __VA_ARGS__ )
51
52 // helper macro to set the keyword
53 #define HLTLogKeyword(a)    AliHLTKeyword hltlogTmpkey(this, a)
54
55 #define HLT_DEFAULT_LOG_KEYWORD "no key"
56
57 /**
58  * @class AliHLTLogging
59  * Basic logging class. All classes inherit the besic HLT logging functionality.
60  * Logging levels are controlled by a global logging filter and a local logging
61  * filter.
62  * 
63  * @section alihlt_logging_levels Logging Levels
64  * Logging levels are switched by a bit pattern,  AliHLTComponentLogSeverity {
65  * - ::kHLTLogNone no logging (0)
66  * - ::kHLTLogBenchmark benchmark messages (0x1)
67  * - ::kHLTLogDebug debug messages (0x2)
68  * - ::kHLTLogInfo info messages (0x4)
69  * - ::kHLTLogWarning warning messages (0x8)
70  * - ::kHLTLogError error messages (0x10)
71  * - ::kHLTLogFatal fatal error messages (0x20)
72  * - ::kHLTLogImportant few important messages not to be filtered out (0x40)
73  * - ::kHLTLogAll special value to enable all messages (0x7f)
74  * - ::kHLTLogDefault the default logging level: Warning, Error, Fatal, Important (0x79)
75  *
76  * @section alihlt_logging_filter Logging Filters
77  * The class provides a global and a local logging filter, the AND beween both
78  * defines whether a message is printed or not.
79  *
80  * The global filter is by default set to ::kHLTLogAll. Please note that AliHLTSystem
81  * changes the global logging level to ::kHLTLogDefault. The global filter can be
82  * adjusted by means of SetGlobalLoggingLevel().
83  *
84  * The local filter is set to ::kHLTLogAll and can be adjusted by
85  * SetLocalLoggingLevel(). The default can be changed for all objects by
86  * SetLocalLoggingDefault(). Please note that a change of the default level only
87  * applies to objects generated after the change of the default.
88  *
89  * @section alihlt_logging_external Redirection
90  * - external logging function
91  * - keyword
92  *
93  * @section alihlt_logging_aliroot AliRoot Redirection
94  * - switching of redirection
95  * - logging options in AliSimulation/AliReconstruction
96  *
97  * @ingroup alihlt_component
98  */
99 class AliHLTLogging {
100 public:
101   AliHLTLogging();
102   AliHLTLogging(const AliHLTLogging&);
103   AliHLTLogging& operator=(const AliHLTLogging&);
104   virtual ~AliHLTLogging();
105
106   /** set the default key word
107    * the keyword is intended to simplify the use of logging macros
108    */ 
109   void SetDefaultKeyword(const char* keyword) { fpDefaultKeyword=keyword; }
110
111   /**
112    * Set a temporary keyword
113    * returns the old key value
114    */
115   const char* SetKeyword(const char* keyword) 
116     { 
117       const char* currentKeyword=fpCurrentKeyword;
118       fpCurrentKeyword=keyword;
119       return currentKeyword; 
120     }
121
122   /**
123    * Get the current keyword
124    */
125   const char* GetKeyword() const
126     {
127       if (fpCurrentKeyword) return fpCurrentKeyword;
128       else if (fpDefaultKeyword) return fpDefaultKeyword;
129       return HLT_DEFAULT_LOG_KEYWORD;
130     }
131   
132   /**
133    * Init the AliLogging class for use from external package.
134    * This initializes the logging callback. <br>
135    * Only deployed by external users of the C wrapper interface, not used
136    * when running in AliRoot
137    */
138   static int Init(AliHLTfctLogging pFun);
139
140   /**
141    * Init the message trap in AliLog.
142    * This initializes the AliLog trap, the AliLog class is the logging
143    * mechanism of AliRoot. The trap can fetch log messages written to
144    * AliLog, components and detector algorithms can use the AliLog
145    * mechanism to be as close as possible to Offline habits. <br>
146    * Only used with external users of the C wrapper interface, not used
147    * when running in AliRoot
148    */
149   static int InitAliLogTrap(AliHLTComponentHandler* pHandler);
150
151   /**
152    * Init the AliRoot logging function.
153    * All log messages are redirected to AliLog when running in AliRoot.
154    * Note: when running in PubSub, AliLog messages are redirected to PubSub,
155    * see AliHLTLogging::InitAliLogTrap
156    */
157   static int InitAliLogFunc(AliHLTComponentHandler* pHandler);
158
159   /**
160    * Genaral logging function
161    */
162   int Logging( AliHLTComponentLogSeverity severity, const char* origin, const char* keyword, const char* message, ... );
163
164   /**
165    * Logging function with two origin parameters, used by the log macros
166    */
167   virtual int LoggingVarargs(AliHLTComponentLogSeverity severity, 
168                              const char* originClass, const char* originFunc,
169                              const char* file, int line, ... ) const;
170
171   /**
172    * Send formatted string to the different channels
173    */
174   int SendMessage(AliHLTComponentLogSeverity severity, 
175                   const char* originClass, const char* originFunc,
176                   const char* file, int line,
177                   const char* message) const;
178
179   /**
180    * Evaluate the group of the debug message from the class name.
181    * @return 1 if message should be printed
182    */
183   int CheckGroup(const char* originClass) const;
184
185   /**
186    * Set the black list of classes.
187    * If the white list is set, debug messages are skipped for
188    * all classes matching one of the regular expressions in the string.
189    */
190   static int SetBlackList(const char* classnames);
191
192   /**
193    * Set the white list of classes.
194    * If the white list is set, debug messages are only printed for
195    * classes matching one of the regular expressions in the string.
196    */
197   static int SetWhiteList(const char* classnames);
198
199   /**
200    * Apply filter
201    * @return 1 if message should pass
202    */
203   int CheckFilter(AliHLTComponentLogSeverity severity) const;
204
205   /**
206    * Set global logging level
207    * logging filter for all objects
208    */
209   static void SetGlobalLoggingLevel(AliHLTComponentLogSeverity level);
210
211   /**
212    * Get global logging level
213    * logging filter for all objects
214    */
215   static AliHLTComponentLogSeverity GetGlobalLoggingLevel();
216
217   /**
218    * Set local logging level
219    * logging filter for individual object
220    */
221   virtual void SetLocalLoggingLevel(AliHLTComponentLogSeverity level);
222
223   /**
224    * Set local logging default
225    * Default logging filter for individual objects.
226    */
227   static void SetLocalLoggingDefault(AliHLTComponentLogSeverity level);
228
229   /**
230    * Get local logging level
231    * logging filter for individual object
232    */
233   AliHLTComponentLogSeverity GetLocalLoggingLevel();
234
235   /**
236    * Print message to stdout
237    */
238   static int Message(void * param, AliHLTComponentLogSeverity severity, const char* origin, const char* keyword, const char* message);
239
240   /**
241    * Build the log string from format specifier and variadac arguments
242    * @param format     format string of printf style
243    * @param ap         opened and initialized argument list
244    * @param bAppend    append to current content
245    * @return const char string with the formatted message 
246    */
247   static const char* BuildLogString(const char *format, va_list ap, bool bAppend=false);
248
249   /**
250    * Set the log string from format specifier and from variable arguments.
251    * @param format     format string of printf style
252    * @return const char string with the formatted message 
253    */
254   static const char* SetLogString(const char *format, ... );
255
256   /**
257    * Get parameter given by the external caller.
258    * This functionality is not yet implemented. It is intended
259    * to pass the parameter pointer given to the component at
260    * initialization back to the caller.
261    */
262   virtual void* GetParameter() const {return NULL;}
263
264   /**
265    * Switch logging through AliLog on or off
266    * @param sw          1 = logging through AliLog
267    */
268   void SwitchAliLog(int sw) {fgUseAliLog=(sw!=0);}
269
270   /** target stream for AliRoot logging methods */
271   static ostringstream fgLogstr;                                   //! transient
272
273   /** 
274    * The message function for dynamic use.
275    * In order to avoid dependencies on AliRoot libraries, libHLTbase loads
276    * the library dynamically and looks for the symbol.
277    */
278   typedef int (*AliHLTDynamicMessage)(AliHLTComponentLogSeverity severity, 
279                                       const char* originClass, 
280                                       const char* originFunc,
281                                       const char* file, int line, 
282                                       const char* message); 
283
284   /**
285    * The init function of the message callback for dynamic use.
286    * In order to avoid dependencies on AliRoot libraries, libHLTbase loads
287    * the library dynamically and looks for the symbol.
288    */
289   typedef int (*InitAliDynamicMessageCallback)();
290   
291 protected:
292   /** the AliRoot logging function */
293   static AliHLTDynamicMessage fgAliLoggingFunc;                    //! transient
294
295 private:
296   /** the global logging filter */
297   static  AliHLTComponentLogSeverity fgGlobalLogFilter;            // see above
298   /** the local logging filter for one class */
299   AliHLTComponentLogSeverity fLocalLogFilter;                      // see above
300   /** the global logging filter */
301   static  AliHLTComponentLogSeverity fgLocalLogDefault;            // see above
302   /** logging callback from the framework */
303   static AliHLTfctLogging fgLoggingFunc;                           // see above
304   /** default keyword */
305   const char* fpDefaultKeyword;                                    //! transient
306   /** current keyword */
307   const char* fpCurrentKeyword;                                    //! transient
308   /** switch for logging through AliLog, default on */
309   static int fgUseAliLog;                                          // see above
310   /**
311    * The global logging buffer.
312    * The buffer is created with an initial size and grown dynamically on
313    * demand.
314    */
315   static TArrayC fgAliHLTLoggingTarget;                            //! transient
316   
317   /** the maximum size of the buffer */
318   static const int fgkALIHLTLOGGINGMAXBUFFERSIZE;                  //! transient
319
320   /** groups of classes not to print debug messages */
321   static TString fgBlackList;                                      //! transient
322   
323   /** groups of classes not to print debug messages */
324   static TString fgWhiteList;                                      //! transient
325   
326   ClassDef(AliHLTLogging, 3)
327 };
328
329 /* the class AliHLTKeyword is a simple helper class used by the HLTLogKeyword macro
330  * HLTLogKeyword("a keyword") creates an object of AliHLTKeyword which sets the keyword for the logging class
331  * the object is destroyed automatically when the current scope is left and so the keyword is set
332  * to the original value
333  */
334 class AliHLTKeyword {
335  public:
336   AliHLTKeyword()
337     :
338     fpParent(NULL),
339     fpOriginal(NULL)
340     {
341     }
342
343   AliHLTKeyword(AliHLTLogging* parent, const char* keyword)
344     :
345     fpParent(parent),
346     fpOriginal(NULL)
347     {
348       if (parent) {
349         fpOriginal=fpParent->SetKeyword(keyword);
350       }
351     }
352
353   AliHLTKeyword(const AliHLTKeyword& kw)
354     :
355     fpParent(kw.fpParent),
356     fpOriginal(kw.fpOriginal)
357     {
358     }
359
360   AliHLTKeyword& operator=(const AliHLTKeyword& kw)
361     { 
362       fpParent=kw.fpParent;
363       fpOriginal=kw.fpOriginal;
364       return *this;
365     }
366
367   ~AliHLTKeyword()
368     {
369       if (fpParent) {
370         fpParent->SetKeyword(fpOriginal);
371       }
372     }
373
374  private:
375   AliHLTLogging* fpParent;                                         //! transient
376   const char* fpOriginal;                                          //! transient
377 };
378 #endif
379