summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAndreas Baumann <abaumann@yahoo.com>2012-09-05 13:54:49 +0200
committerAndreas Baumann <abaumann@yahoo.com>2012-09-05 13:54:49 +0200
commita91b86f9561ed80b31cbe6c1d16237f5f835f845 (patch)
tree6078d501bf3186e6b59cd9d2e2077d18156a4b64
parent9b45c403b8cadd58bdee9c64651de90c22a71995 (diff)
downloadcrawler-a91b86f9561ed80b31cbe6c1d16237f5f835f845.tar.gz
crawler-a91b86f9561ed80b31cbe6c1d16237f5f835f845.tar.bz2
added syslog logger sink
-rwxr-xr-xsrc/GNUmakefile1
-rw-r--r--src/Logger.cpp13
-rwxr-xr-xsrc/Logger.hpp1
-rwxr-xr-xsrc/Makefile.W322
-rw-r--r--src/SyslogSink.cpp91
-rwxr-xr-xsrc/SyslogSink.hpp25
-rw-r--r--src/win32/syslog_win32.c261
-rw-r--r--src/win32/syslog_win32.h171
-rw-r--r--tests/logger/test1.cpp1
9 files changed, 566 insertions, 0 deletions
diff --git a/src/GNUmakefile b/src/GNUmakefile
index 4cd1978..267e69c 100755
--- a/src/GNUmakefile
+++ b/src/GNUmakefile
@@ -34,6 +34,7 @@ CPP_OBJS = \
Logger.o \
ConsoleLogSink.o \
FileLogSink.o \
+ SyslogSink.o \
URL.o \
MIMEType.o \
SpoolRewindInputStream.o
diff --git a/src/Logger.cpp b/src/Logger.cpp
index 2a5dd6c..726b6fc 100644
--- a/src/Logger.cpp
+++ b/src/Logger.cpp
@@ -2,6 +2,7 @@
#include "LogSink.hpp"
#include "ConsoleLogSink.hpp"
#include "FileLogSink.hpp"
+#include "SyslogSink.hpp"
#include <algorithm>
#include <list>
@@ -38,6 +39,7 @@ class LoggerImpl
void openConsoleLog( const LogLevel level );
void openFileLog( const LogLevel level, const std::string &filename );
+ void openSyslog( const LogLevel level, const string &ident, const string &facility );
public:
LoggerImpl( );
@@ -92,6 +94,11 @@ void LoggerImpl::openFileLog( const LogLevel level, const string &filename )
addSink( new FileLogSink( level, filename ) );
}
+void LoggerImpl::openSyslog( const LogLevel level, const string &ident, const string &facility )
+{
+ addSink( new SyslogSink( level, ident, facility ) );
+}
+
string Logger::toString( const LogLevel level )
{
static const char* const buf[] = { "NONE", "FATAL", "CRITICAL", "ERROR", "WARNING", "NOTICE", "INFO", "DEBUG", "DEBUG1", "DEBUG2", "DEBUG3", "DEBUG4" };
@@ -150,3 +157,9 @@ void Logger::openFileLog( const LogLevel level, const std::string &filename )
{
m_impl->openFileLog( level, filename );
}
+
+void Logger::openSyslog( const LogLevel level, const string &ident, const string &facility )
+{
+ m_impl->openSyslog( level, ident, facility );
+}
+
diff --git a/src/Logger.hpp b/src/Logger.hpp
index dd23a06..ad75b2e 100755
--- a/src/Logger.hpp
+++ b/src/Logger.hpp
@@ -38,6 +38,7 @@ class Logger : public Singleton< Logger >
void openConsoleLog( const LogLevel level );
void openFileLog( const LogLevel level, const std::string &filename );
+ void openSyslog( const LogLevel level, const std::string &ident, const std::string &facility );
protected:
Logger( );
diff --git a/src/Makefile.W32 b/src/Makefile.W32
index 786bb09..fa6da19 100755
--- a/src/Makefile.W32
+++ b/src/Makefile.W32
@@ -17,9 +17,11 @@ INCLUDE_LIBS = \
LOCAL_STATIC_LIB_OBJS = \
win32\errormsg.obj \
win32\stringutils.obj \
+ win32\syslog_win32.obj \
Logger.obj \
ConsoleLogSink.obj \
FileLogSink.obj \
+ SyslogSink.obj \
URL.obj \
MIMEType.obj \
SpoolRewindInputStream.obj
diff --git a/src/SyslogSink.cpp b/src/SyslogSink.cpp
new file mode 100644
index 0000000..42b1ae3
--- /dev/null
+++ b/src/SyslogSink.cpp
@@ -0,0 +1,91 @@
+#include "SyslogSink.hpp"
+
+#ifndef _WIN32
+#include <syslog.h>
+#else
+#inclue "win32/syslog_win32.h"
+#endif
+
+using namespace std;
+
+SyslogSink::SyslogSink( const LogLevel level, const string &ident, const string &facility )
+ : LogSink( level ), m_ident( ident ), m_facility( facility )
+{
+ openlog( m_ident.c_str( ), LOG_PID, facilityFromString( m_facility ) );
+}
+
+SyslogSink::~SyslogSink( )
+{
+ closelog( );
+}
+
+void SyslogSink::log( const LogLevel level, const string &msg )
+{
+ if( level > reportingLevel( ) ) return;
+
+ syslog( levelToSyslogLevel( level ), "%s", msg.c_str( ) );
+}
+
+int SyslogSink::levelToSyslogLevel( const LogLevel level )
+{
+ switch( level ) {
+ case logFATAL: return LOG_ALERT;
+ case logCRITICAL: return LOG_CRIT;
+ case logERROR: return LOG_ERR;
+ case logWARNING: return LOG_WARNING;
+ case logNOTICE: return LOG_NOTICE;
+ case logINFO: return LOG_INFO;
+ case logDEBUG:
+ case logDEBUG1:
+ case logDEBUG2:
+ case logDEBUG3:
+ case logDEBUG4: return LOG_DEBUG;
+
+ case logNONE:
+ default:
+ LOG( logWARNING ) << "Unknown log level '" << level << "'. Using LOG)ERR level as syslog log level.";
+ return LOG_ERR;
+ }
+}
+
+int SyslogSink::facilityFromString( const std::string &facility )
+{
+ if( facility == "kern" ) return LOG_KERN;
+ else if( facility == "user" ) return LOG_USER;
+ else if( facility == "mail" ) return LOG_MAIL;
+ else if( facility == "daemon" ) return LOG_DAEMON;
+ else if( facility == "auth" ) return LOG_AUTH;
+ else if( facility == "syslog" ) return LOG_SYSLOG;
+ else if( facility == "lpr" ) return LOG_LPR;
+ else if( facility == "news" ) return LOG_NEWS;
+ else if( facility == "uucp" ) return LOG_UUCP;
+ else if( facility == "cron" ) return LOG_CRON;
+#ifdef LOG_AUTHPRIV
+ else if( facility == "authpriv" ) return LOG_AUTHPRIV;
+#endif
+#ifdef LOG_FTP
+ else if( facility == "ftp" ) return LOG_FTP;
+#endif
+#ifdef LOG_NTP
+ else if( facility == "ntp" ) return LOG_NTP;
+#endif
+#ifdef LOG_SECURITY
+ else if( facility == "security" ) return LOG_SECURITY;
+#endif
+#ifdef LOG_CONSOLE
+ else if( facility == "console" ) return LOG_CONSOLE;
+#endif
+#ifdef LOG_AUDIT
+ else if( facility == "audit" ) return LOG_AUDIT;
+#endif
+ else if( facility == "local0" ) return LOG_LOCAL0;
+ else if( facility == "local1" ) return LOG_LOCAL1;
+ else if( facility == "local2" ) return LOG_LOCAL2;
+ else if( facility == "local3" ) return LOG_LOCAL3;
+ else if( facility == "local4" ) return LOG_LOCAL4;
+ else if( facility == "local5" ) return LOG_LOCAL5;
+ else if( facility == "local6" ) return LOG_LOCAL6;
+ else if( facility == "local7" ) return LOG_LOCAL7;
+ else return LOG_USER;
+}
+
diff --git a/src/SyslogSink.hpp b/src/SyslogSink.hpp
new file mode 100755
index 0000000..5a879d5
--- /dev/null
+++ b/src/SyslogSink.hpp
@@ -0,0 +1,25 @@
+#ifndef __SYSLOG_LOGSINK_H
+#define __SYSLOG_LOGSINK_H
+
+#include "LogSink.hpp"
+
+#include <string>
+
+class SyslogSink : public LogSink
+{
+ public:
+ SyslogSink( const LogLevel level, const std::string &ident, const std::string &facility );
+
+ ~SyslogSink( );
+
+ void log( const LogLevel level, const std::string &msg );
+
+ static int levelToSyslogLevel( const LogLevel level );
+ static int facilityFromString( const std::string &facility );
+
+ private:
+ std::string m_ident;
+ std::string m_facility;
+};
+
+#endif
diff --git a/src/win32/syslog_win32.c b/src/win32/syslog_win32.c
new file mode 100644
index 0000000..e94bb9e
--- /dev/null
+++ b/src/win32/syslog_win32.c
@@ -0,0 +1,261 @@
+/************************************************************************
+
+ Copyright (C) 2011, 2012 Project Wolframe.
+ All rights reserved.
+
+ This file is part of Project Wolframe.
+
+ Commercial Usage
+ Licensees holding valid Project Wolframe Commercial licenses may
+ use this file in accordance with the Project Wolframe
+ Commercial License Agreement provided with the Software or,
+ alternatively, in accordance with the terms contained
+ in a written agreement between the licensee and Project Wolframe.
+
+ GNU General Public License Usage
+ Alternatively, you can redistribute this file and/or modify it
+ under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ Wolframe is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with Wolframe. If not, see <http://www.gnu.org/licenses/>.
+
+ If you have questions regarding the use of this file, please contact
+ Project Wolframe.
+
+************************************************************************/
+
+/*
+ * syslog-client.c - syslog client implementation for windows
+ *
+ * Created by Alexander Yaworsky
+ *
+ * THIS SOFTWARE IS NOT COPYRIGHTED
+ *
+ * This source code is offered for use in the public domain. You may
+ * use, modify or distribute it freely.
+ *
+ * This code is distributed in the hope that it will be useful but
+ * WITHOUT ANY WARRANTY. ALL WARRANTIES, EXPRESS OR IMPLIED ARE HEREBY
+ * DISCLAIMED. This includes but is not limited to warranties of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ */
+
+/**
+ * \file syslog_win32.c
+ * \brief implementation of a syslog client on Windows
+ *
+ * It is roughly based on the one of http://syslog-win32.sourceforge.net,
+ * changed in the way it's configured (we can't have a /etc/syslog.conf
+ * on Windows, host and port must be injectable through a function from
+ * the Wolframe configuration), in the way the messages are composed using
+ * newer string functions, using WSock2 funtions like getaddrinfo and
+ * some small other things like added documentation.
+*/
+
+/* TODOS:
+ * - reset logmask in openlog?
+ * - handle more options
+ */
+
+#include "syslog_win32.h"
+
+#include <Winsock2.h>
+#include <ws2tcpip.h>
+#include <string.h>
+#include <stdio.h>
+
+static BOOL initialized = FALSE;
+static BOOL wsa_initialized = FALSE;
+
+static int log_mask = 0xFF;
+static const char *syslog_ident = NULL;
+static int syslog_facility = 0;
+static char str_pid[40];
+static char local_hostname[MAX_COMPUTERNAME_LENGTH+4];
+
+static char syslog_hostname[256] = "localhost";
+static char syslog_service[256] = "514";
+
+/* UDP socket and data to use for sending messages */
+static SOCKADDR_STORAGE sa_logger;
+static SOCKET sock = INVALID_SOCKET;
+#define SYSLOG_DGRAM_SIZE 1024
+static char datagram[SYSLOG_DGRAM_SIZE];
+static int datagram_size = SYSLOG_DGRAM_SIZE;
+
+void openlog( const char* ident, int option, int facility )
+{
+ BOOL failed = TRUE;
+ WSADATA wsd;
+ struct addrinfo hints;
+ struct addrinfo *result = NULL;
+ SOCKADDR_IN sa_local;
+ int size;
+ DWORD n;
+
+ /* allow idempotent calls, first options are taken, use closelog
+ * before openlog if you want to reconfigure the syslog interface
+ */
+ if( initialized ) return;
+
+ /* Initialize Windows Socket DLL */
+ if( WSAStartup( MAKEWORD( 2, 2 ), &wsd ) != 0 ) goto DONE;
+ wsa_initialized = TRUE;
+
+ /* tell getaddrinfo what we want */
+ memset( &hints, 0, sizeof( struct addrinfo ) );
+ hints.ai_flags = 0;
+ hints.ai_family = AF_INET;
+ hints.ai_socktype = SOCK_DGRAM;
+ hints.ai_protocol = IPPROTO_UDP;
+
+ /* resolve the domain name into a list of addresses */
+ if( getaddrinfo( syslog_hostname, syslog_service, &hints, &result ) != 0 ) goto DONE;
+
+ /* Compose the socket address and port of the logging destination */
+ memset( &sa_logger, 0, sizeof( SOCKADDR_IN ) );
+ memcpy( &sa_logger, result->ai_addr, result->ai_addrlen );
+
+ /* Create a UDP socket */
+ sock = socket( result->ai_family, result->ai_socktype, result->ai_protocol );
+ if( sock == INVALID_SOCKET ) goto DONE;
+
+ /* from RFC 3164: The client should connect from a constant port, if possible
+ * also port 514.
+ *
+ * But if we are on the same machine with loopback the port is taken?
+ * Should we try 514 and if it is taken take a fixed different one?
+ */
+
+ /* bind to the socket */
+ memset( &sa_local, 0, sizeof( SOCKADDR_IN ) );
+ sa_local.sin_family = AF_INET;
+ if( bind( sock, (SOCKADDR *)&sa_local, sizeof( SOCKADDR_IN ) ) != 0 ) goto DONE;
+
+ /* determine the maximal size of a datagram packet we can send */
+ size = sizeof( datagram_size );
+ if( getsockopt( sock, SOL_SOCKET, SO_MAX_MSG_SIZE, (char *)&datagram_size, &size ) != 0 ) goto DONE;
+ if( datagram_size > sizeof( datagram ) ) datagram_size = sizeof( datagram );
+
+ /* set global facility and ident */
+ syslog_facility = facility ? facility : LOG_USER;
+ syslog_ident = ident;
+
+ /* by RFC 3164 we should put here the name of the local machine */
+ n = sizeof( local_hostname );
+ if( !GetComputerName( local_hostname, &n ) ) goto DONE;
+
+ /* interpret options, currently we use only LOG_PID */
+ if( option & LOG_PID )
+ _snprintf_s( str_pid, sizeof( str_pid ), _TRUNCATE, "[%lu]", GetCurrentProcessId( ) );
+ else
+ str_pid[0] = '\0';
+
+ /* install C cleanup function */
+ if( atexit( closelog ) ) goto DONE;
+
+ /* if we get here, everything's peachy */
+ failed = FALSE;
+
+DONE:
+ if( failed ) {
+ if( sock != INVALID_SOCKET ) {
+ closesocket( sock );
+ sock = INVALID_SOCKET;
+ }
+ if( wsa_initialized ) {
+ wsa_initialized = FALSE;
+ WSACleanup( );
+ }
+ }
+
+ initialized = !failed;
+}
+
+extern int setlogmask( int mask )
+{
+ /* set log mask, return old one */
+ int old_mask = log_mask;
+
+ if( mask ) log_mask = mask;
+
+ return old_mask;
+}
+
+void syslog( int pri, char* fmt, ... )
+{
+ va_list ap;
+ va_start( ap, fmt );
+ vsyslog( pri, fmt, ap );
+ va_end( ap );
+}
+
+void vsyslog( int pri, char* fmt, va_list ap )
+{
+ /* from RFC 3164: Mmm is the English language abbreviation for the month of the
+ * year with the first character in uppercase and the other two
+ * characters in lowercase. The following are the only acceptable
+ * values:
+ *
+ * Jan, Feb, Mar, Apr, May, Jun, Jul, Aug, Sep, Oct, Nov, Dec
+ */
+ static char *month[] = {"Jan", "Feb", "Mar", "Apr", "May", "Jun",
+ "Jul", "Aug", "Sep", "Oct", "Nov", "Dec" };
+
+ int len;
+ SYSTEMTIME t;
+
+ /* do not log if we are not inside the logging mask */
+ if( !( LOG_MASK( LOG_PRI( pri ) ) & log_mask ) ) return;
+
+ /* open default logger, will return immediatelly if already
+ * registered before */
+ openlog( NULL, 0, pri & LOG_FACMASK );
+
+ /* do not log if not initialized after opening a default log */
+ if( !initialized ) return;
+
+ if( !( pri & LOG_FACMASK ) ) pri |= syslog_facility;
+
+ /* from RFC 3164: .. hh:mm:ss is the local time. .. */
+ GetLocalTime( &t );
+
+ /* the PRI and the HEADER with TIMESTAMP and HOSTNAME as
+ * well as the TAG field of the MSG part
+ */
+ len = _snprintf_s( datagram, datagram_size, _TRUNCATE, "<%d>%s %2d %02d:%02d:%02d %s %s%s: ",
+ pri, month[t.wMonth-1], t.wDay, t.wHour, t.wMinute, t.wSecond,
+ local_hostname, syslog_ident ? syslog_ident : "", str_pid );
+
+ /* append now the formatted user message */
+ (void)_vsnprintf_s( datagram + len, datagram_size - len, _TRUNCATE, fmt, ap );
+
+ /* send as datagram, we are not really interested in errors here */
+ (void)sendto( sock, datagram, strlen( datagram ), 0, (SOCKADDR *)&sa_logger, sizeof( SOCKADDR_IN ) );
+}
+
+void closelog( )
+{
+ if( !initialized ) return;
+
+ if( sock != INVALID_SOCKET ) (void)closesocket( sock );
+ if( wsa_initialized ) WSACleanup( );
+
+ sock = INVALID_SOCKET;
+ wsa_initialized = FALSE;
+ initialized = FALSE;
+}
+
+void set_syslogd_destination( const char *hostname, const char *service )
+{
+ strncpy_s( syslog_hostname, 255, hostname, _TRUNCATE );
+ strncpy_s( syslog_service, 255, service, _TRUNCATE );
+}
diff --git a/src/win32/syslog_win32.h b/src/win32/syslog_win32.h
new file mode 100644
index 0000000..94157a1
--- /dev/null
+++ b/src/win32/syslog_win32.h
@@ -0,0 +1,171 @@
+/************************************************************************
+
+ Copyright (C) 2011, 2012 Project Wolframe.
+ All rights reserved.
+
+ This file is part of Project Wolframe.
+
+ Commercial Usage
+ Licensees holding valid Project Wolframe Commercial licenses may
+ use this file in accordance with the Project Wolframe
+ Commercial License Agreement provided with the Software or,
+ alternatively, in accordance with the terms contained
+ in a written agreement between the licensee and Project Wolframe.
+
+ GNU General Public License Usage
+ Alternatively, you can redistribute this file and/or modify it
+ under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ Wolframe is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with Wolframe. If not, see <http://www.gnu.org/licenses/>.
+
+ If you have questions regarding the use of this file, please contact
+ Project Wolframe.
+
+************************************************************************/
+
+/*
+ * Copyright (c) 1982, 1986, 1988, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 4. Neither the name of the University nor the names of its contributors
+ * may be used to endorse or promote products derived from this software
+ * without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * @(#)syslog.h 8.1 (Berkeley) 6/2/93
+ */
+
+///
+/// \file syslog_win32.h
+/// \brief syslog header file on Windows
+///
+
+#ifndef _SYSLOG_WIN32_HPP_INCLUDED
+#define _SYSLOG_WIN32_HPP_INCLUDED
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#include <stdarg.h>
+
+/*
+ * priorities/facilities are encoded into a single 32-bit quantity, where the
+ * bottom 3 bits are the priority (0-7) and the top 28 bits are the facility
+ * (0-big number). Both the priorities and the facilities map roughly
+ * one-to-one to strings in the syslogd(8) source code. This mapping is
+ * included in this file.
+ *
+ * priorities (these are ordered)
+ */
+#define LOG_EMERG 0 /* system is unusable */
+#define LOG_ALERT 1 /* action must be taken immediately */
+#define LOG_CRIT 2 /* critical conditions */
+#define LOG_ERR 3 /* error conditions */
+#define LOG_WARNING 4 /* warning conditions */
+#define LOG_NOTICE 5 /* normal but significant condition */
+#define LOG_INFO 6 /* informational */
+#define LOG_DEBUG 7 /* debug-level messages */
+
+#define LOG_PRIMASK 0x07 /* mask to extract priority part (internal) */
+ /* extract priority */
+#define LOG_PRI(p) ((p) & LOG_PRIMASK)
+#define LOG_MAKEPRI(fac, pri) (((fac) << 3) | (pri))
+
+/* facility codes */
+#define LOG_KERN (0<<3) /* kernel messages */
+#define LOG_USER (1<<3) /* random user-level messages */
+#define LOG_MAIL (2<<3) /* mail system */
+#define LOG_DAEMON (3<<3) /* system daemons */
+#define LOG_AUTH (4<<3) /* security/authorization messages */
+#define LOG_SYSLOG (5<<3) /* messages generated internally by syslogd */
+#define LOG_LPR (6<<3) /* line printer subsystem */
+#define LOG_NEWS (7<<3) /* network news subsystem */
+#define LOG_UUCP (8<<3) /* UUCP subsystem */
+#define LOG_CRON (9<<3) /* clock daemon */
+#define LOG_AUTHPRIV (10<<3) /* security/authorization messages (private) */
+#define LOG_FTP (11<<3) /* ftp daemon */
+
+ /* other codes through 15 reserved for system use */
+#define LOG_LOCAL0 (16<<3) /* reserved for local use */
+#define LOG_LOCAL1 (17<<3) /* reserved for local use */
+#define LOG_LOCAL2 (18<<3) /* reserved for local use */
+#define LOG_LOCAL3 (19<<3) /* reserved for local use */
+#define LOG_LOCAL4 (20<<3) /* reserved for local use */
+#define LOG_LOCAL5 (21<<3) /* reserved for local use */
+#define LOG_LOCAL6 (22<<3) /* reserved for local use */
+#define LOG_LOCAL7 (23<<3) /* reserved for local use */
+
+#define LOG_NFACILITIES 24 /* current number of facilities */
+#define LOG_FACMASK 0x03f8 /* mask to extract facility part */
+ /* facility of pri */
+#define LOG_FAC(p) (((p) & LOG_FACMASK) >> 3)
+
+/*
+ * arguments to setlogmask.
+ */
+#define LOG_MASK(pri) (1 << (pri)) /* mask for one priority */
+#define LOG_UPTO(pri) ((1 << ((pri)+1)) - 1) /* all priorities through pri */
+
+/*
+ * Option flags for openlog.
+ */
+#define LOG_PID 0x01 /* log the pid with each message */
+
+/* Close descriptor used to write to system logger.
+
+ This function is a possible cancellation point and therefore not
+ marked with __THROW. */
+extern void closelog (void);
+
+/* Open connection to system logger.
+
+ This function is a possible cancellation point and therefore not
+ marked with __THROW. */
+extern void openlog (const char *__ident, int __option, int __facility);
+
+/* Set the log mask level. */
+extern int setlogmask( int __mask );
+
+/* Generate a log message using FMT string and option arguments. */
+extern void syslog (int __pri, char *__fmt, ...);
+
+/* Generate a log message using FMT and using arguments pointed to by AP. */
+void vsyslog( int __pri, char* __fmt, va_list __ap );
+
+/* Wolframe specific function, set the hostname and port for logging through
+ * the configuration programatically */
+extern void set_syslogd_destination( const char *__hostname, const char *__service );
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif // _SYSLOG_WIN32_HPP_INCLUDED
diff --git a/tests/logger/test1.cpp b/tests/logger/test1.cpp
index eea3ff9..d334ec0 100644
--- a/tests/logger/test1.cpp
+++ b/tests/logger/test1.cpp
@@ -11,6 +11,7 @@ int main( void )
LogSink *sink = new ConsoleLogSink( logNOTICE );
Logger::instance( ).addSink( sink );
Logger::instance( ).openFileLog( logNOTICE, "test1.log" );
+ Logger::instance( ).openSyslog( logNOTICE, "test1", "user" );
LOG( logFATAL ) << "fatal error";
LOG( logCRITICAL ) << "critical error";