Added debug-mode test of ignored return value
[asdcplib.git] / src / KM_log.cpp
index 3d34f1c8529af25e1083085d04498d192ca0bada..d820dba50df002aaf82e652c664d765e829dd386 100755 (executable)
@@ -1,5 +1,5 @@
 /*
-Copyright (c) 2004-2008, John Hurst
+Copyright (c) 2004-2011, John Hurst
 All rights reserved.
 
 Redistribution and use in source and binary forms, with or without
@@ -90,7 +90,8 @@ Kumu::DefaultLogSink()
 void
 Kumu::EntryListLogSink::WriteEntry(const LogEntry& Entry)
 {
-  AutoMutex L(m_Lock);
+  AutoMutex L(m_lock);
+  WriteEntryToListeners(Entry);
 
   if ( Entry.TestFilter(m_filter) )
     m_Target.push_back(Entry);
@@ -102,13 +103,15 @@ Kumu::EntryListLogSink::WriteEntry(const LogEntry& Entry)
 void
 Kumu::StdioLogSink::WriteEntry(const LogEntry& Entry)
 {
-  AutoMutex L(m_Lock);
   std::string buf;
+  AutoMutex L(m_lock);
+  WriteEntryToListeners(Entry);
 
   if ( Entry.TestFilter(m_filter) )
     {
       Entry.CreateStringWithOptions(buf, m_options);
       fputs(buf.c_str(), m_stream);
+      fflush(m_stream);
     }
 }
 
@@ -116,16 +119,19 @@ Kumu::StdioLogSink::WriteEntry(const LogEntry& Entry)
 
 #ifdef KM_WIN32
 //
+// http://www.codeguru.com/forum/showthread.php?t=231165
+//
 void
 Kumu::WinDbgLogSink::WriteEntry(const LogEntry& Entry)
 {
-  AutoMutex L(m_Lock);
   std::string buf;
+  AutoMutex L(m_lock);
+  WriteEntryToListeners(Entry);
 
   if ( Entry.TestFilter(m_filter) )
     {
       Entry.CreateStringWithOptions(buf, m_options);
-      ::OutputDebugString(buf.c_str());
+      ::OutputDebugStringA(buf.c_str());
     }
 }
 #endif
@@ -138,15 +144,94 @@ Kumu::WinDbgLogSink::WriteEntry(const LogEntry& Entry)
 void
 Kumu::StreamLogSink::WriteEntry(const LogEntry& Entry)
 {
-  AutoMutex L(m_Lock);
   std::string buf;
+  AutoMutex L(m_lock);
+  WriteEntryToListeners(Entry);
 
   if ( Entry.TestFilter(m_filter) )
     {
       Entry.CreateStringWithOptions(buf, m_options);
-      write(m_fd, buf.c_str(), buf.size());
+      ssize_t n = write(m_fd, buf.c_str(), buf.size());
+      assert(n==buf.size());
     }
 }
+
+// foolin with symbols
+//------------------------------------------------------------------------------------------
+#include <syslog.h>
+int const SYSLOG_ALERT = LOG_ALERT;
+int const SYSLOG_CRIT = LOG_CRIT;
+int const SYSLOG_ERR = LOG_ERR;
+int const SYSLOG_WARNING = LOG_WARNING;
+int const SYSLOG_NOTICE = LOG_NOTICE;
+int const SYSLOG_INFO = LOG_INFO;
+int const SYSLOG_DEBUG = LOG_DEBUG;
+#undef LOG_ALERT
+#undef LOG_CRIT
+#undef LOG_ERR
+#undef LOG_WARNING
+#undef LOG_NOTICE
+#undef LOG_INFO
+#undef LOG_DEBUG
+//------------------------------------------------------------------------------------------
+
+Kumu::SyslogLogSink::SyslogLogSink(const std::string& source_name, int facility)
+{
+  if ( facility == 0 )
+    facility = LOG_DAEMON;
+
+  openlog(source_name.c_str(), LOG_CONS|LOG_NDELAY||LOG_PID, facility);
+}
+
+Kumu::SyslogLogSink::~SyslogLogSink()
+{
+  closelog();
+}
+
+//
+void
+Kumu::SyslogLogSink::WriteEntry(const LogEntry& Entry)
+{
+  int priority;
+
+  switch ( Entry.Type )
+    {
+    case Kumu::LOG_ALERT:   priority = SYSLOG_ALERT; break;
+    case Kumu::LOG_CRIT:    priority = SYSLOG_CRIT; break;
+    case Kumu::LOG_ERROR:   priority = SYSLOG_ERR; break;
+    case Kumu::LOG_WARN:    priority = SYSLOG_WARNING; break;
+    case Kumu::LOG_NOTICE:  priority = SYSLOG_NOTICE; break;
+    case Kumu::LOG_INFO:    priority = SYSLOG_INFO; break;
+    case Kumu::LOG_DEBUG:   priority = SYSLOG_DEBUG; break;
+    }
+
+  AutoMutex L(m_lock);
+  WriteEntryToListeners(Entry);
+
+  if ( Entry.TestFilter(m_filter) )
+    {
+      syslog(priority, "%s", Entry.Msg.substr(0, Entry.Msg.size() - 1).c_str());
+    }
+}
+
+//
+int
+Kumu::SyslogNameToFacility(const std::string& facility_name)
+{
+  if ( facility_name == "LOG_DAEMON" ) return LOG_DAEMON;
+  if ( facility_name == "LOG_LOCAL0" ) return LOG_LOCAL0;
+  if ( facility_name == "LOG_LOCAL1" ) return LOG_LOCAL1;
+  if ( facility_name == "LOG_LOCAL2" ) return LOG_LOCAL2;
+  if ( facility_name == "LOG_LOCAL3" ) return LOG_LOCAL3;
+  if ( facility_name == "LOG_LOCAL4" ) return LOG_LOCAL4;
+  if ( facility_name == "LOG_LOCAL5" ) return LOG_LOCAL5;
+  if ( facility_name == "LOG_LOCAL6" ) return LOG_LOCAL6;
+  if ( facility_name == "LOG_LOCAL7" ) return LOG_LOCAL7;
+
+  DefaultLogSink().Error("Unsupported facility name: %s, using default value LOG_DAEMON\n", facility_name.c_str());
+  return LOG_DAEMON;
+}
+
 #endif
 
 //------------------------------------------------------------------------------------------