| The Gaudi Framework v27r1

- Main Page
- Related Pages
- Modules
- Namespaces
- Classes
- Files

- File List
- File Members

Message.cpp
Go to the documentation of this file.
1 #include <string>
2 #include <iostream>
3 #include <iomanip>
4 #include <cstdlib>
5 #include <cstdio>
6 #include <cctype>
7 #include <algorithm>
8 #include "GaudiKernel/IMessageSvc.h"
9 #include "GaudiKernel/Message.h"
10 #include "GaudiKernel/Timing.h"
11 #include "GaudiKernel/Time.h"
12 #include "GaudiKernel/ThreadLocalContext.h"
13
14 using namespace MSG;
15
16 namespace {
17 // get the current time from the system and format it according to the format
18 inline std::string formattedTime (const std::string &fmt, bool universal = false )
19 {
20 return Gaudi::Time::current().format(!universal, fmt);
21 }
22 }
23
24 //#############################################################################
25 // ---------------------------------------------------------------------------
26 // Routine: Constructor.
27 // Purpose:
28 // ---------------------------------------------------------------------------
29 //
30 Message::Message()
31 {
32 m_ecSlot = Gaudi::Hive::currentContextId();
33 m_ecEvt = Gaudi::Hive::currentContextEvt();
34 m_ecThrd = pthread_self();
35 }
36
37 //#############################################################################
38 // ---------------------------------------------------------------------------
39 // Routine: Constructor.
40 // Purpose:
41 // ---------------------------------------------------------------------------
42 //
43 Message::Message ( const char* src, int type, const char* msg ) :
44 m_message( msg ), m_source( src ), m_type( type )
45 {
46 m_ecSlot = Gaudi::Hive::currentContextId();
47 m_ecEvt = Gaudi::Hive::currentContextEvt();
48 m_ecThrd = pthread_self();
49 }
50
51 //#############################################################################
52 // ---------------------------------------------------------------------------
53 // Routine: Constructor.
54 // Purpose:
55 // ---------------------------------------------------------------------------
56 //
57 Message::Message ( std::string src, int type, std::string msg ) :
58 m_message( std::move(msg) ), m_source( std::move(src) ), m_type( type )
59 {
60 m_ecSlot = Gaudi::Hive::currentContextId();
61 m_ecEvt = Gaudi::Hive::currentContextEvt();
62 m_ecThrd = pthread_self();
63 }
64
65 //#############################################################################
66 // ---------------------------------------------------------------------------
67 // Routine: getMessage
68 // Purpose: Get the message string.
69 // ---------------------------------------------------------------------------
70 //
71 const std::string& Message::getMessage() const
72 {
73 return m_message;
74 }
75
76 //#############################################################################
77 // ---------------------------------------------------------------------------
78 // Routine: setMessage
79 // Purpose: Set the message string.
80 // ---------------------------------------------------------------------------
81 //
82 void Message::setMessage( std::string msg )
83 {
84 m_message = std::move(msg);
85 }
86
87 //#############################################################################
88 // ---------------------------------------------------------------------------
89 // Routine: getType
90 // Purpose: Get the message type.
91 // ---------------------------------------------------------------------------
92 //
93 int Message::getType() const
94 {
95 return m_type;
96 }
97
98 //#############################################################################
99 // ---------------------------------------------------------------------------
100 // Routine: setType
101 // Purpose: Set the message type.
102 // ---------------------------------------------------------------------------
103 //
104 void Message::setType( int msg_type )
105 {
106 m_type = msg_type;
107 }
108
109 //#############################################################################
110 // ---------------------------------------------------------------------------
111 // Routine: getSource
112 // Purpose: Get the message source.
113 // ---------------------------------------------------------------------------
114 //
115 const std::string& Message::getSource() const
116 {
117 return m_source;
118 }
119
120 //#############################################################################
121 // ---------------------------------------------------------------------------
122 // Routine: setSource
123 // Purpose: Set the message source.
124 // ---------------------------------------------------------------------------
125 //
126 void Message::setSource( std::string src )
127 {
128 m_source = std::move(src);
129 }
130
131 //#############################################################################
132 // ---------------------------------------------------------------------------
133 // Routine: operator <<
134 // Purpose:Insert the message into a stream.
135 // ---------------------------------------------------------------------------
136 //
137 std::ostream& operator << ( std::ostream& stream, const Message& msg )
138 {
139 msg.makeFormattedMsg( msg.m_format );
140 stream << msg.m_formatted_msg;
141 return stream;
142 }
143
144 //#############################################################################
145 // ---------------------------------------------------------------------------
146 // Routine: operator <
147 // Purpose: comparison operator needed for maps
148 // ---------------------------------------------------------------------------
149 //
150 bool Message::operator < ( const Message& b )
151 {
152 return m_type < b.m_type ||
153 m_source < b.m_source ||
154 m_message < b.m_message;
155 }
156
157 //#############################################################################
158 // ---------------------------------------------------------------------------
159 // Routine: operator ==
160 // Purpose: comparison op.
161 // ---------------------------------------------------------------------------
162 //
163 bool operator == ( const Message& a, const Message& b )
164 {
165 return a.m_source == b.m_source &&
166 a.m_type == b.m_type &&
167 a.m_message == b.m_message;
168 }
169
170 //#############################################################################
171 // ---------------------------------------------------------------------------
172 // Routine:
173 // Purpose: Get the format string.
174 // ---------------------------------------------------------------------------
175 //
176 const std::string& Message::getFormat() const
177 {
178 return m_format;
179 }
180
181 //#############################################################################
182 // ---------------------------------------------------------------------------
183 // Routine:
184 // Purpose: Get the default format string.
185 // ---------------------------------------------------------------------------
186 //
187 const std::string Message::getDefaultFormat()
188 {
189 return DEFAULT_FORMAT;
190 }
191
192
193 //#############################################################################
194 // ---------------------------------------------------------------------------
195 // Routine:
196 // Purpose: Set the format string -
197 // use isFormatted() to check for valid format.
198 // ---------------------------------------------------------------------------
199 //
200 void Message::setFormat( std::string format ) const
201 {
202 if (LIKELY(!format.empty())) {
203 m_format = std::move(format);
204 } else {
205 m_format = DEFAULT_FORMAT;
206 }
207 }
208
209 //#############################################################################
210 // ---------------------------------------------------------------------------
211 // Routine:
212 // Purpose: Get the time format string.
213 // ---------------------------------------------------------------------------
214 //
215 const std::string& Message::getTimeFormat() const
216 {
217 return m_time_format;
218 }
219
220 //#############################################################################
221 // ---------------------------------------------------------------------------
222 // Routine:
223 // Purpose: Get the default time format string.
224 // ---------------------------------------------------------------------------
225 //
226 const std::string Message::getDefaultTimeFormat()
227 {
228 return DEFAULT_TIME_FORMAT ;
229 }
230
231
232 //#############################################################################
233 // ---------------------------------------------------------------------------
234 // Routine:
235 // Purpose: Set the time format string -
236 // use isFormatted() to check for valid format.
237 // ---------------------------------------------------------------------------
238 //
239 void Message::setTimeFormat( std::string timeFormat ) const
240 {
241 m_time_format = ( timeFormat.empty() ? DEFAULT_TIME_FORMAT
242 : std::move(timeFormat) );
243 }
244
245 //#############################################################################
246 // ---------------------------------------------------------------------------
247 // Routine: makeFormattedMsg
248 // Purpose: This formats the message according to the format string.
249 // ---------------------------------------------------------------------------
250 //
251 void Message::makeFormattedMsg( const std::string& format ) const
252 {
253 m_formatted_msg.clear();
254 auto i = format.begin();
255 while( i != format.end() ) {
256
257 // Output format string until format statement found.
258 while( i != format.end() && *i != FORMAT_PREFIX )
259 m_formatted_msg += *i++;
260
261 // Test for end of format string.
262 if ( i == format.end() ) break;
263 i++;
264
265 // Find type of formatting.
266 std::string this_format;
267 while( i != format.end() && *i != FORMAT_PREFIX &&
268 *i != MESSAGE && *i != TYPE && *i != SOURCE &&
269 *i != FILL && *i != WIDTH && *i != TIME && *i != UTIME &&
270 *i != SLOT && *i != EVTNUM && *i != THREAD &&
271 *i != JUSTIFY_LEFT && *i != JUSTIFY_RIGHT ) {
272 this_format += *i++;
273 }
274
275 // Reached end of string with improper format.
276 if ( i == format.end() ) {
277 invalidFormat();
278 break;
279 }
280
281 this_format += *i++;
282 decodeFormat( this_format );
283 }
284 }
285
286 //#############################################################################
287 // ---------------------------------------------------------------------------
288 // Routine: decodeFormat
289 // Purpose: This the work horse that checks for a valid format string.
290 // ---------------------------------------------------------------------------
291 //
292 void Message::decodeFormat( const std::string& format ) const
293 {
294 if ( ! format.empty() ) {
295 const char FORMAT_TYPE = format[ format.length() - 1 ];
296 const std::string FORMAT_PARAM = format.substr( 0, format.length() - 1 );
297
298 // Now test the format.
299 std::string level;
300 switch( FORMAT_TYPE ) {
301 case FILL:
302 if ( FORMAT_PARAM.length() == 1 ) {
303 m_fill = FORMAT_PARAM[0];
304 }
305 else
306 invalidFormat();
307 break;
308
309 case TIME:
310 {
311 sizeField( formattedTime ( m_time_format ) );
312 }
313 break;
314
315 case UTIME:
316 {
317 sizeField( formattedTime ( m_time_format, true ) );
318 }
319 break;
320
321 case THREAD:
322 {
323 std::ostringstream ost;
324 // ost << "0x" << std::hex << pthread_self();
325 ost << "0x" << std::hex << m_ecThrd;
326 const std::string& thrStr( ost.str() );
327 sizeField( thrStr );
328 }
329 break;
330
331 case SLOT:
332 {
333 if (m_ecEvt >= 0) {
334 std::ostringstream ost;
335 ost << m_ecSlot;
336 const std::string& slotStr (ost.str());
337 sizeField( slotStr );
338 } else {
339 const std::string& slotStr( "" );
340 sizeField( slotStr );
341 }
342 }
343 break;
344
345 case EVTNUM:
346 {
347 if (m_ecEvt >= 0 ) {
348 std::ostringstream ost;
349 ost << m_ecEvt;
350 const std::string& slotStr (ost.str());
351 sizeField( slotStr );
352 } else {
353 const std::string& slotStr( "" );
354 sizeField( slotStr );
355 }
356 }
357 break;
358
359 case MESSAGE:
360 sizeField( m_message );
361 break;
362
363 case SOURCE:
364 sizeField( m_source );
365 break;
366
367 case TYPE:
368 switch ( m_type ) {
369 #define SET(x) case x: level=#x; break
370 SET( NIL );
371 SET( VERBOSE );
372 SET( DEBUG );
373 SET( INFO );
374 SET( WARNING );
375 SET( ERROR );
376 SET( FATAL );
377 case ALWAYS: level="SUCCESS"; break;
378 default:
379 level = "UNKNOWN";
380 break;
381 #undef SET
382 }
383 sizeField( level );
384 break;
385
386 case FORMAT_PREFIX: m_formatted_msg += FORMAT_PREFIX; break;
387 case JUSTIFY_RIGHT: m_left = false; break;
388 case JUSTIFY_LEFT: m_left = true; break;
389 case WIDTH: setWidth( FORMAT_PARAM ); break;
390 default: invalidFormat(); break;
391 }
392 }
393 else
394 invalidFormat();
395 }
396
397 //#############################################################################
398 // ---------------------------------------------------------------------------
399 // Routine: invalidFormat.
400 // Purpose: called when invalid format found.
401 // ---------------------------------------------------------------------------
402 //
403
404 void Message::invalidFormat() const
405 {
406 makeFormattedMsg( DEFAULT_FORMAT );
407 }
408
409 //#############################################################################
410 // ---------------------------------------------------------------------------
411 // Routine: setWidth
412 // Purpose: Sets the minimum width of a stream field.
413 // ---------------------------------------------------------------------------
414 //
415 namespace {
416 // Check that a container only contains digits.
417 constexpr struct all_digit_t {
418 template <typename C>
419 bool operator()(const C& c) const {
420 return std::all_of( std::begin(c), std::end(c),
421 [](typename C::const_reference i) {
422 return isdigit(i);
423 } );
424 }
425 } all_digits {};
426 }
427
428
429 void Message::setWidth( const std::string& formatArg ) const
430 {
431 // Convert string to int, if string contains digits only...
432 if ( all_digits(formatArg) ) m_width = std::stoi(formatArg);
433 else invalidFormat();
434 }
435
436 //#############################################################################
437 // ---------------------------------------------------------------------------
438 // Routine: sizeField
439 // Purpose: Truncates or pads the text to m_width as necessary
440 // ---------------------------------------------------------------------------
441 //
442
443 void Message::sizeField( const std::string& text ) const
444 {
445 std::string newText;
446 if ( m_width == 0 || m_width == static_cast<int>( text.length() ) ) {
447 newText = text;
448 }
449 else {
450
451 // Truncate the text if it is too long.
452 if ( m_width < static_cast<int>( text.length() ) ) {
453 newText = text.substr( 0, m_width );
454 for ( int i = 0, j = newText.length()-1; i < 3 && j >= 0; ++i, --j )
455 newText[ j ] = '.';
456 }
457
458 // Pad the text.
459 else {
460 newText = std::string( m_width, m_fill );
461 if ( m_left )
462 newText.replace( newText.begin(), newText.begin() + text.length(),
463 text.begin(), text.end() );
464 else
465 newText.replace( newText.end() - text.length(), newText.end(),
466 text.begin(), text.end() );
467 }
468 }
469
470 m_formatted_msg += newText;
471 }
Message::m_ecSlot
size_t m_ecSlot
Definition: Message.h:166
Message::m_ecEvt
long int m_ecEvt
Definition: Message.h:167
Message::TYPE
static const char TYPE
The character used to indicate that the message type should be printed.
Definition: Message.h:131
Message::m_left
bool m_left
Justification.
Definition: Message.h:114
Message::MESSAGE
static const char MESSAGE
The character used to indicate that the message should be printed.
Definition: Message.h:128
Message::getFormat
const std::string & getFormat() const
Get the format string.
Definition: Message.cpp:176
Message::m_fill
char m_fill
The current fill character.
Definition: Message.h:108
Message::JUSTIFY_LEFT
static const char JUSTIFY_LEFT
The character used to indicate start of left text justification.
Definition: Message.h:122
Gaudi::Hive::currentContextId
GAUDI_API ContextIdType currentContextId()
Return the current context id.
Definition: ThreadLocalContext.cpp:8
std::string::empty
T empty(T...args)
format
GAUDI_API std::string format(const char *,...)
MsgStream format utility "a la sprintf(...)".
Definition: MsgStream.cpp:119
Message::m_formatted_msg
std::string m_formatted_msg
Formatted message.
Definition: Message.h:105
Message::THREAD
static const char THREAD
Definition: Message.h:164
Message::m_time_format
std::string m_time_format
Time format string.
Definition: Message.h:99
Message::decodeFormat
void decodeFormat(const std::string &format) const
Decode format.
Definition: Message.cpp:292
GaudiMP.FdsRegistry.msg
tuple msg
Definition: FdsRegistry.py:8
Message::setWidth
void setWidth(const std::string &formatArg) const
Set the width of a stream.
Definition: Message.cpp:429
Message::operator<
bool operator<(const Message &test)
Needed to build maps.
Definition: Message.cpp:150
operator==
bool operator==(const Message &a, const Message &b)
Insert the message into a stream.
Definition: Message.cpp:163
Gaudi::Time::current
static Time current(void)
Returns the current time.
Definition: Time.cpp:113
ThreadLocalContext.h
gaudirun.c
tuple c
Definition: gaudirun.py:391
MSG::DEBUG
Definition: IMessageSvc.h:18
Message::m_message
std::string m_message
The message.
Definition: Message.h:90
Message::setMessage
void setMessage(std::string msg)
Set the message string.
Definition: Message.cpp:82
std
STL namespace.
Message::setType
void setType(int msg_type)
Set the message type.
Definition: Message.cpp:104
std::string::end
T end(T...args)
Message::getType
int getType() const
Get the message type.
Definition: Message.cpp:93
SET
#define SET(x)
MSG::VERBOSE
Definition: IMessageSvc.h:17
Message::Message
Message()
Default constructor.
Definition: Message.cpp:30
Message::setSource
void setSource(std::string src)
Set the message source.
Definition: Message.cpp:126
Message::invalidFormat
void invalidFormat() const
Called when an invalid format string is encountered.
Definition: Message.cpp:404
std::string
STL class.
MSG::FATAL
Definition: IMessageSvc.h:22
gaudirun.type
string type
Definition: gaudirun.py:151
std::string::replace
T replace(T...args)
Message::getDefaultTimeFormat
static const std::string getDefaultTimeFormat()
Get the default time format string.
Definition: Message.cpp:226
std::ostringstream
STL class.
operator<<
std::ostream & operator<<(std::ostream &stream, const Message &msg)
Insert the message into a stream.
Definition: Message.cpp:137
Message::getDefaultFormat
static const std::string getDefaultFormat()
Get the default format string.
Definition: Message.cpp:187
MSG::NIL
Definition: IMessageSvc.h:16
std::ostringstream::str
T str(T...args)
IMessageSvc.h
Message::EVTNUM
static const char EVTNUM
Definition: Message.h:163
Time.h
std::string::clear
T clear(T...args)
std::move
T move(T...args)
LIKELY
#define LIKELY(x)
Definition: Kernel.h:125
Timing.h
Message::m_width
int m_width
The current field width.
Definition: Message.h:111
Message::TIME
static const char TIME
The character used to indicate that the message timestamp should be printed.
Definition: Message.h:134
Message::m_format
std::string m_format
The format string.
Definition: Message.h:96
Gaudi::Hive::currentContextEvt
GAUDI_API ContextIdType currentContextEvt()
Definition: ThreadLocalContext.cpp:11
std::string::length
T length(T...args)
Message::setFormat
void setFormat(std::string msg) const
Set the format string.
Definition: Message.cpp:200
Message::JUSTIFY_RIGHT
static const char JUSTIFY_RIGHT
The character used to indicate start of right text justification.
Definition: Message.h:125
Message::UTIME
static const char UTIME
The character used to indicate that the message timestamp should be printed in UTC time...
Definition: Message.h:138
Message
The Message class.
Definition: Message.h:14
Message::SLOT
static const char SLOT
For slot and event number from EventContext.
Definition: Message.h:162
std::string::begin
T begin(T...args)
Message::m_ecThrd
pthread_t m_ecThrd
Definition: Message.h:168
std::all_of
T all_of(T...args)
Message::FILL
static const char FILL
The character used to indicate that the previous character is to be used for padding out fields if th...
Definition: Message.h:146
Message::makeFormattedMsg
void makeFormattedMsg(const std::string &format) const
Format the message.
Definition: Message.cpp:251
MSG
Print levels enumeration.
Definition: IMessageSvc.h:14
Message::setTimeFormat
void setTimeFormat(std::string timeFormat) const
Set the time format string.
Definition: Message.cpp:239
std::hex
T hex(T...args)
MSG::ERROR
Definition: IMessageSvc.h:21
std::string::substr
T substr(T...args)
Message::sizeField
void sizeField(const std::string &text) const
Truncate or pad the output string to the field width as necessary.
Definition: Message.cpp:443
Message::getSource
const std::string & getSource() const
Get the message source.
Definition: Message.cpp:115
gaudirun.level
level
Definition: gaudirun.py:261
Message::getTimeFormat
const std::string & getTimeFormat() const
Get the time format string.
Definition: Message.cpp:215
MSG::WARNING
Definition: IMessageSvc.h:20
Message::DEFAULT_FORMAT
static constexpr const char * DEFAULT_FORMAT
The default message format.
Definition: Message.h:155
MSG::INFO
Definition: IMessageSvc.h:19
Message::FORMAT_PREFIX
static const char FORMAT_PREFIX
Formatting string characters.
Definition: Message.h:119
Message::m_source
std::string m_source
The source.
Definition: Message.h:93
ana.i
list i
Definition: ana.py:128
std::ostream
STL class.
Message::WIDTH
static const char WIDTH
The character used to indicate that the previous decimal characters should be taken as the field widt...
Definition: Message.h:151
std::stoi
T stoi(T...args)
Message::SOURCE
static const char SOURCE
The character used to indicate that the message source should be printed.
Definition: Message.h:141
MSG::ALWAYS
Definition: IMessageSvc.h:23
Message::DEFAULT_TIME_FORMAT
static constexpr const char * DEFAULT_TIME_FORMAT
The default time format.
Definition: Message.h:159
Gaudi::Time::format
std::string format(bool local, std::string spec="%c") const
Format the time using strftime.
Definition: Time.cpp:279
Message::getMessage
const std::string & getMessage() const
Get the message string.
Definition: Message.cpp:71
Message::m_type
int m_type
The type.
Definition: Message.h:102
Message.h