1 /*_############################################################################
6 _## -----------------------------------------------
7 _## Copyright (c) 2001-2010 Jochen Katz, Frank Fock
9 _## This software is based on SNMP++2.6 from Hewlett Packard:
11 _## Copyright (c) 1996
12 _## Hewlett-Packard Company
14 _## ATTENTION: USE OF THIS SOFTWARE IS SUBJECT TO THE FOLLOWING TERMS.
15 _## Permission to use, copy, modify, distribute and/or sell this software
16 _## and/or its documentation is hereby granted without fee. User agrees
17 _## to display the above copyright notice and this license notice in all
18 _## copies of the software and any documentation of the software. User
19 _## agrees to assume all liability for the use of the software;
20 _## Hewlett-Packard and Jochen Katz make no representations about the
21 _## suitability of this software for any purpose. It is provided
22 _## "AS-IS" without warranty of any kind, either express or implied. User
23 _## hereby grants a royalty-free license to any and all derivatives based
24 _## upon this software code base.
26 _## Stuttgart, Germany, Thu Sep 2 00:07:47 CEST 2010
28 _##########################################################################*/
41 #include <snmp_pp/log.h>
45 #define _getpid getpid
49 #if defined (CPU) && CPU == PPC603
53 #ifdef SNMP_PP_NAMESPACE
54 using namespace Snmp_pp;
57 // default log filter: logs with level less or equal filter value are logged
58 // error, warning, event, info, debug:
59 static unsigned char default_logfilter[] = { 9, 9, 4, 6, 7, 15};
64 /*--------------------------- class LogEntry --------------------------*/
67 * Initialize a log entry, showing timestamp, class, and level.
70 void LogEntry::init(void)
74 #elif defined (CPU) && CPU == PPC603
75 int pid = taskIdSelf();
86 sprintf(buf, "(%X)", get_level());
89 switch (type & 0xF0) {
90 case DEBUG_LOG: add_string("DEBUG : "); break;
91 case INFO_LOG: add_string("INFO : "); break;
92 case WARNING_LOG: add_string("WARNING: "); break;
93 case ERROR_LOG: add_string("ERROR : "); break;
94 case EVENT_LOG: add_string("EVENT : "); break;
95 case USER_LOG: add_string("USER : "); break;
99 // indent log by level
100 for (int i=0; i<(type & 0x0F); i++)
106 * Add a string value to the log entry.
108 * @param l - A numeric value.
110 LogEntry& LogEntry::operator+=(const char* s)
112 // The convention for Agent++ log messages is that the
113 // timestamp, etc. is followed by the class and method name,
114 // then by the list of arguments.
132 * Add a numeric value to the log entry.
134 * @param l - A numeric value.
136 LogEntry& LogEntry::operator+=(const long l)
151 * Add an integer to the log.
153 * @param s - An integer value.
154 * @return TRUE if the value has been added and FALSE if the log
157 bool LogEntry::add_integer(long l)
160 sprintf(buf, "%ld", l);
161 return add_string(buf);
165 * Add the current time to the log entry.
167 bool LogEntry::add_timestamp(void)
169 return add_string(DefaultLog::log()->now());
173 /*------------------------- class LogEntryImpl ------------------------*/
176 * Constructor for the standard log entry implementation.
178 LogEntryImpl::LogEntryImpl(unsigned char t) : LogEntry(t)
180 value = new char[MAX_LOG_SIZE];
183 output_stopped = FALSE;
187 * Destructor for the standard log entry implementation.
189 LogEntryImpl::~LogEntryImpl()
195 * Add a string to the log.
197 * @param s - A string value.
198 * @return TRUE if the value has been added and FALSE if the log
201 bool LogEntryImpl::add_string(const char* s)
206 size_t len = strlen(s);
207 if (len <= bytes_left()) {
213 if (bytes_left() >= 3) {
217 output_stopped = TRUE;
222 /*-------------------------- class AgentLog ---------------------------*/
225 * Default constructor.
229 for (int i=0; i<LOG_TYPES; i++)
230 logfilter[i] = default_logfilter[i];
233 void AgentLog::set_filter(int logclass, unsigned char filter)
235 int idx = (logclass/16)-1;
236 if ((idx >=0) && (idx < LOG_TYPES) && (filter<16))
237 logfilter[idx] = filter;
240 unsigned char AgentLog::get_filter(int logclass) const
242 int idx = (logclass/16)-1;
243 if ((idx >= 0) && (idx < LOG_TYPES)) {
244 return logfilter[idx];
249 const char* AgentLog::now(char* buf)
251 if (buf == NULL) buf = static_buf;
255 struct tm *stm = localtime(&t);
257 strftime(buf, 18, "%Y%m%d.%H:%M:%S", localtime(&t));
263 /*static*/ const char* AgentLog::get_current_time()
265 char* buf = new char[18];
266 strcpy(buf, DefaultLog::log()->now());
271 /*------------------------ class AgentLogImpl -------------------------*/
274 * Default constructor. Log is directed to stdout.
276 AgentLogImpl::AgentLogImpl(FILE* fp) : AgentLog()
282 * Constructor with file name of a log file. Log is directed
285 * @param fname - The file name of a log file.
287 AgentLogImpl::AgentLogImpl(const char* fname) : AgentLog()
295 AgentLogImpl::~AgentLogImpl()
297 if (close_needed) fclose(logfile);
301 * Set destination of logs to a given file.
303 * @param fname - A file name. "" directs logs to stdout.
305 void AgentLogImpl::set_dest(const char* fname)
307 close_needed = FALSE;
308 if ((!fname) || (strlen(fname) == 0))
311 logfile = fopen(fname, "a");
320 * Set destination of logs to a given file.
322 * @param fname - A pointer to an open log file. 0 directs logs to stdout.
324 void AgentLogImpl::set_dest(FILE* fp)
326 logfile = fp ? fp : stdout;
327 close_needed = FALSE;
331 * Create a new LogEntry.
333 * @param t - The type of the log entry.
334 * @return A new instance of LogEntry (or of a derived class).
336 LogEntry* AgentLogImpl::create_log_entry(unsigned char t) const
338 return new LogEntryImpl(t);
342 * Add a LogEntry to the receiver Log.
344 * @param log - A log entry.
345 * @return The receiver log itself.
347 AgentLog& AgentLogImpl::operator+=(const LogEntry* log)
349 fprintf(logfile, "%s\n", log->get_value());
351 // check if critical error
352 if ((log->get_class() == ERROR_LOG) && (log->get_level() == 0))
354 fprintf(logfile, "Exiting now\n");
362 // define the default logs
365 #ifndef _WIN32THREADS
366 #if !(defined (CPU) && CPU == PPC603)
367 pthread_mutex_t logmutex = PTHREAD_MUTEX_INITIALIZER;
372 AgentLog* DefaultLog::instance = 0;
373 LogEntry* DefaultLog::entry = 0;
374 SnmpSynchronized DefaultLog::mutex;
376 /*------------------------ class DefaultLog -------------------------*/
378 void DefaultLog::cleanup()
381 if (instance) delete instance;
386 AgentLog* DefaultLog::init_ts(AgentLog* logger)
388 AgentLog* r = instance;
400 AgentLog* DefaultLog::log()
402 AgentLog* r = instance;
404 r = new AgentLogImpl();
405 AgentLog* l = init_ts(r);
406 if (r != l) delete r;