From f97c90d12b9ae64a64cde84bb3fa3ca5ee207838 Mon Sep 17 00:00:00 2001 From: Rainer Gerhards Date: Tue, 24 Jul 2007 09:45:19 +0000 Subject: moved discard functionality to an output module --- Makefile.am | 2 +- modules.c | 5 +++ modules.h | 1 + omdiscard.c | 125 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++ omdiscard.h | 33 +++++++++++++++ omfile.c | 18 ++++++-- omfile.h | 3 -- omfwd.c | 18 ++++++-- omfwd.h | 1 - ommysql.c | 18 ++++++-- ommysql.h | 1 - omshell.c | 18 ++++++-- omshell.h | 1 - omusrmsg.c | 20 +++++++-- rsyslog.h | 2 + syslogd-types.h | 10 ++++- syslogd.c | 98 +++++++++++++++++++++----------------------- 17 files changed, 298 insertions(+), 76 deletions(-) create mode 100644 omdiscard.c create mode 100644 omdiscard.h diff --git a/Makefile.am b/Makefile.am index 1c2146a9..ef90b9dc 100644 --- a/Makefile.am +++ b/Makefile.am @@ -7,7 +7,7 @@ rfc3195d_SOURCES=rfc3195d.c rsyslog.h man_MANS = rfc3195d.8 rklogd.8 rsyslogd.8 rsyslog.conf.5 -rsyslogd_SOURCES=syslogd.c pidfile.c template.c outchannel.c stringbuf.c srUtils.c parse.c syslogd-types.h template.h outchannel.h syslogd.h stringbuf.h parse.h srUtils.h liblogging-stub.h net.c net.h msg.c msg.h omshell.c omshell.h omusrmsg.c omusrmsg.h ommysql.c ommysql.h omfwd.c omfwd.h tcpsyslog.c tcpsyslog.h omfile.h omfile.c modules.c modules.h +rsyslogd_SOURCES=syslogd.c pidfile.c template.c outchannel.c stringbuf.c srUtils.c parse.c syslogd-types.h template.h outchannel.h syslogd.h stringbuf.h parse.h srUtils.h liblogging-stub.h net.c net.h msg.c msg.h omshell.c omshell.h omusrmsg.c omusrmsg.h ommysql.c ommysql.h omfwd.c omfwd.h tcpsyslog.c tcpsyslog.h omfile.h omfile.c omdiscard.c omdiscard.h modules.c modules.h rsyslogd_CPPFLAGS=$(mysql_includes) rsyslogd_LDADD=$(mysql_libs) $(zlib_libs) $(pthreads_libs) diff --git a/modules.c b/modules.c index 58b1eec1..25f6b8cc 100644 --- a/modules.c +++ b/modules.c @@ -160,6 +160,11 @@ rsRetVal doModInit(rsRetVal (*modInit)(int, int*, rsRetVal(**)()), uchar *name) moduleDestruct(pNew); return iRet; } + if((iRet = (*pNew->modQueryEtryPt)((uchar*)"isCompatibleWithFeature", + &pNew->isCompatibleWithFeature)) != RS_RET_OK) { + moduleDestruct(pNew); + return iRet; + } /* later... if((iRet = (*pNew->modQueryEtryPt)((uchar*)"freeInstance", &pNew->freeInstance)) != RS_RET_OK) { moduleDestruct(pNew); diff --git a/modules.h b/modules.h index a57e99a7..98e60c1a 100644 --- a/modules.h +++ b/modules.h @@ -53,6 +53,7 @@ typedef struct moduleInfo { rsRetVal (*modInit)(int, int*, rsRetVal(**)()); /* initialize the module */ /* be sure to support version handshake! */ rsRetVal (*modQueryEtryPt)(uchar *name, rsRetVal (**EtryPoint)()); /* query entry point addresses */ + rsRetVal (*isCompatibleWithFeature)(syslogFeature); rsRetVal (*freeInstance)(struct filed*);/* called before termination or module unload */ rsRetVal (*modExit)(); /* called before termination or module unload */ /* below: parse a configuration line - return if processed diff --git a/omdiscard.c b/omdiscard.c new file mode 100644 index 00000000..7db4a8d4 --- /dev/null +++ b/omdiscard.c @@ -0,0 +1,125 @@ +/* omdiscard.c + * This is the implementation of the built-in discard output module. + * + * File begun on 2007-07-24 by RGerhards + * + * Copyright 2007 Rainer Gerhards and Adiscon GmbH. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program 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 this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * A copy of the GPL can be found in the file "COPYING" in this distribution. + */ +#include "config.h" +#include +#include +#include +#include +#include +#include "rsyslog.h" +#include "syslogd.h" +#include "syslogd-types.h" +#include "omdiscard.h" + + +/* query feature compatibility + */ +static rsRetVal isCompatibleWithFeature(syslogFeature __attribute__((unused)) eFeat) +{ + /* this module is incompatible with all currently-known optional + * syslog features. Turn them on if that changes over time. + */ + return RS_RET_INCOMPATIBLE; +} + + +/* call the shell action + */ +static rsRetVal doAction(__attribute__((unused)) selector_t *f) +{ + dprintf("Discarding message based on selector config\n"); + return RS_RET_DISCARDMSG; +} + + +/* try to process a selector action line. Checks if the action + * applies to this module and, if so, processed it. If not, it + * is left untouched. The driver will then call another module + */ +static rsRetVal parseSelectorAct(uchar **pp, selector_t *f) +{ + uchar *p; + rsRetVal iRet = RS_RET_CONFLINE_PROCESSED; + + assert(pp != NULL); + assert(f != NULL); + + p = *pp; + + if(*p == '~') { + /* TODO: check the rest of the selector line - error reporting */ + dprintf("discard\n"); + f->f_type = F_DISCARD; + } else { + iRet = RS_RET_CONFLINE_UNPROCESSED; + } + + if(iRet == RS_RET_CONFLINE_PROCESSED) + *pp = p; + return iRet; +} + +/* query an entry point + */ +static rsRetVal queryEtryPt(uchar *name, rsRetVal (**pEtryPoint)()) +{ + if((name == NULL) || (pEtryPoint == NULL)) + return RS_RET_PARAM_ERROR; + + *pEtryPoint = NULL; + if(!strcmp((char*) name, "doAction")) { + *pEtryPoint = doAction; + } else if(!strcmp((char*) name, "parseSelectorAct")) { + *pEtryPoint = parseSelectorAct; + } else if(!strcmp((char*) name, "isCompatibleWithFeature")) { + *pEtryPoint = isCompatibleWithFeature; + } /*else if(!strcmp((char*) name, "freeInstance")) { + *pEtryPoint = freeInstanceFile; + } */ + + return(*pEtryPoint == NULL) ? RS_RET_NOT_FOUND : RS_RET_OK; +} + +/* initialize the module + * + * Later, much more must be done. So far, we only return a pointer + * to the queryEtryPt() function + * TODO: do interface version checking & handshaking + * iIfVersRequeted is the version of the interface specification that the + * caller would like to see being used. ipIFVersProvided is what we + * decide to provide. + */ +rsRetVal modInitDiscard(int iIFVersRequested __attribute__((unused)), int *ipIFVersProvided, rsRetVal (**pQueryEtryPt)()) +{ + if((pQueryEtryPt == NULL) || (ipIFVersProvided == NULL)) + return RS_RET_PARAM_ERROR; + + *ipIFVersProvided = 1; /* so far, we only support the initial definition */ + + *pQueryEtryPt = queryEtryPt; + return RS_RET_OK; +} +/* + * vi:set ai: + */ diff --git a/omdiscard.h b/omdiscard.h new file mode 100644 index 00000000..6a7d150f --- /dev/null +++ b/omdiscard.h @@ -0,0 +1,33 @@ +/* omdiscard.h + * These are the definitions for the built-in discard output module. + * + * File begun on 2007-07-24 by RGerhards + * + * Copyright 2007 Rainer Gerhards and Adiscon GmbH. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program 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 this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * A copy of the GPL can be found in the file "COPYING" in this distribution. + */ +#ifndef OMDISCARD_H_INCLUDED +#define OMDISCARD_H_INCLUDED 1 + +/* prototypes */ +rsRetVal modInitDiscard(int iIFVersRequested, int *ipIFVersProvided, rsRetVal (**pQueryEtryPt)()); + +#endif /* #ifndef OMDISCARD_H_INCLUDED */ +/* + * vi:set ai: + */ diff --git a/omfile.c b/omfile.c index d335fc9d..61e4624a 100644 --- a/omfile.c +++ b/omfile.c @@ -48,6 +48,17 @@ #include "omfile.h" +/* query feature compatibility + */ +static rsRetVal isCompatibleWithFeature(syslogFeature eFeat) +{ + if(eFeat == sFEATURERepeatedMsgReduction) + return RS_RET_OK; + + return RS_RET_INCOMPATIBLE; +} + + /* Helper to cfline(). Parses a output channel name up until the first * comma and then looks for the template specifier. Tries * to find that template. Maps the output channel to the @@ -504,9 +515,8 @@ rsRetVal freeInstanceFile(selector_t *f) /* call the shell action - * returns 0 if it succeeds, something else otherwise */ -rsRetVal doActionFile(selector_t *f) +static rsRetVal doActionFile(selector_t *f) { assert(f != NULL); @@ -517,7 +527,7 @@ rsRetVal doActionFile(selector_t *f) */ if(f->f_un.f_file.bDynamicName || (f->f_file != -1)) writeFile(f); - return 0; + return RS_RET_OK; } /* try to process a selector action line. Checks if the action @@ -660,6 +670,8 @@ static rsRetVal queryEtryPt(uchar *name, rsRetVal (**pEtryPoint)()) *pEtryPoint = doActionFile; } else if(!strcmp((char*) name, "parseSelectorAct")) { *pEtryPoint = parseSelectorAct; + } else if(!strcmp((char*) name, "isCompatibleWithFeature")) { + *pEtryPoint = isCompatibleWithFeature; } else if(!strcmp((char*) name, "freeInstance")) { *pEtryPoint = freeInstanceFile; } diff --git a/omfile.h b/omfile.h index b60b8a9d..47aa17b7 100644 --- a/omfile.h +++ b/omfile.h @@ -25,9 +25,6 @@ #define OMFILE_H_INCLUDED 1 /* prototypes */ - -rsRetVal doActionFile(selector_t *f); -rsRetVal freeInstanceFile(selector_t *f); rsRetVal modInitFile(int iIFVersRequested, int *ipIFVersProvided, rsRetVal (**pQueryEtryPt)()); #endif /* #ifndef OMFILE_H_INCLUDED */ diff --git a/omfwd.c b/omfwd.c index 35159630..74b4c66e 100644 --- a/omfwd.c +++ b/omfwd.c @@ -64,10 +64,20 @@ static const char *sys_h_errlist[] = { "no address, look for MX record" /* NO_ADDRESS */ }; +/* query feature compatibility + */ +static rsRetVal isCompatibleWithFeature(syslogFeature eFeat) +{ + if(eFeat == sFEATURERepeatedMsgReduction) + return RS_RET_OK; + + return RS_RET_INCOMPATIBLE; +} + + /* call the shell action - * returns 0 if it succeeds, something else otherwise */ -int doActionFwd(selector_t *f) +static rsRetVal doActionFwd(selector_t *f) { char *psz; /* temporary buffering */ register unsigned l; @@ -238,7 +248,7 @@ int doActionFwd(selector_t *f) } break; } - return 0; + return RS_RET_OK; } @@ -446,6 +456,8 @@ static rsRetVal queryEtryPt(uchar *name, rsRetVal (**pEtryPoint)()) *pEtryPoint = doActionFwd; } else if(!strcmp((char*) name, "parseSelectorAct")) { *pEtryPoint = parseSelectorAct; + } else if(!strcmp((char*) name, "isCompatibleWithFeature")) { + *pEtryPoint = isCompatibleWithFeature; } /*else if(!strcmp((char*) name, "freeInstance")) { *pEtryPoint = freeInstanceFile; }*/ diff --git a/omfwd.h b/omfwd.h index 391c73c2..66f7d224 100644 --- a/omfwd.h +++ b/omfwd.h @@ -25,7 +25,6 @@ #define OMFWD_H_INCLUDED 1 /* prototypes */ -int doActionFwd(selector_t *f); rsRetVal modInitFwd(int iIFVersRequested __attribute__((unused)), int *ipIFVersProvided, rsRetVal (**pQueryEtryPt)()); #endif /* #ifndef OMFWD_H_INCLUDED */ diff --git a/ommysql.c b/ommysql.c index afa46906..d5613ce8 100644 --- a/ommysql.c +++ b/ommysql.c @@ -45,6 +45,17 @@ #include "mysql/errmsg.h" +/* query feature compatibility + */ +static rsRetVal isCompatibleWithFeature(syslogFeature eFeat) +{ + if(eFeat == sFEATURERepeatedMsgReduction) + return RS_RET_OK; + + return RS_RET_INCOMPATIBLE; +} + + /** * DBErrorHandler * @@ -258,15 +269,14 @@ void writeMySQL(register selector_t *f) } /* call the shell action - * returns 0 if it succeeds, something else otherwise */ -int doActionMySQL(selector_t *f) +static rsRetVal doActionMySQL(selector_t *f) { assert(f != NULL); dprintf("\n"); writeMySQL(f); - return 0; + return RS_RET_OK; } @@ -392,6 +402,8 @@ static rsRetVal queryEtryPt(uchar *name, rsRetVal (**pEtryPoint)()) *pEtryPoint = doActionMySQL; } else if(!strcmp((char*) name, "parseSelectorAct")) { *pEtryPoint = parseSelectorAct; + } else if(!strcmp((char*) name, "isCompatibleWithFeature")) { + *pEtryPoint = isCompatibleWithFeature; } /*else if(!strcmp((char*) name, "freeInstance")) { *pEtryPoint = freeInstanceFile; }*/ diff --git a/ommysql.h b/ommysql.h index 3b7015ea..7d828261 100644 --- a/ommysql.h +++ b/ommysql.h @@ -35,7 +35,6 @@ void closeMySQL(register selector_t *f); void reInitMySQL(register selector_t *f); int checkDBErrorState(register selector_t *f); rsRetVal modInitMySQL(int iIFVersRequested, int *ipIFVersProvided, rsRetVal (**pQueryEtryPt)()); -int doActionMySQL(selector_t *f); #endif /* #ifdef WITH_DB */ #endif /* #ifndef OMMYSQL_H_INCLUDED */ diff --git a/omshell.c b/omshell.c index 0718e66d..6b67dff4 100644 --- a/omshell.c +++ b/omshell.c @@ -40,10 +40,20 @@ #include "omshell.h" +/* query feature compatibility + */ +static rsRetVal isCompatibleWithFeature(syslogFeature eFeat) +{ + if(eFeat == sFEATURERepeatedMsgReduction) + return RS_RET_OK; + + return RS_RET_INCOMPATIBLE; +} + + /* call the shell action - * returns 0 if it succeeds, something else otherwise */ -int doActionShell(selector_t *f) +static rsRetVal doActionShell(selector_t *f) { uchar *psz; @@ -58,7 +68,7 @@ int doActionShell(selector_t *f) if(execProg((uchar*) f->f_un.f_file.f_fname, 1, (uchar*) psz) == 0) logerrorSz("Executing program '%s' failed", f->f_un.f_file.f_fname); - return 0; + return RS_RET_OK; } @@ -108,6 +118,8 @@ static rsRetVal queryEtryPt(uchar *name, rsRetVal (**pEtryPoint)()) *pEtryPoint = doActionShell; } else if(!strcmp((char*) name, "parseSelectorAct")) { *pEtryPoint = parseSelectorAct; + } else if(!strcmp((char*) name, "isCompatibleWithFeature")) { + *pEtryPoint = isCompatibleWithFeature; } /*else if(!strcmp((char*) name, "freeInstance")) { *pEtryPoint = freeInstanceFile; } */ diff --git a/omshell.h b/omshell.h index fa146eb8..d62f7373 100644 --- a/omshell.h +++ b/omshell.h @@ -25,7 +25,6 @@ #define ACTSHELL_H_INCLUDED 1 /* prototypes */ -int doActionShell(selector_t *f); rsRetVal modInitShell(int iIFVersRequested, int *ipIFVersProvided, rsRetVal (**pQueryEtryPt)()); #endif /* #ifndef ACTSHELL_H_INCLUDED */ diff --git a/omusrmsg.c b/omusrmsg.c index edd8c19e..da545f73 100644 --- a/omusrmsg.c +++ b/omusrmsg.c @@ -52,7 +52,18 @@ #include "omusrmsg.h" -jmp_buf ttybuf; +/* query feature compatibility + */ +static rsRetVal isCompatibleWithFeature(syslogFeature eFeat) +{ + if(eFeat == sFEATURERepeatedMsgReduction) + return RS_RET_OK; + + return RS_RET_INCOMPATIBLE; +} + + +static jmp_buf ttybuf; static void endtty() { @@ -203,15 +214,14 @@ static void wallmsg(selector_t *f) /* call the shell action - * returns 0 if it succeeds, something else otherwise */ -static int doAction(selector_t *f) +static rsRetVal doAction(selector_t *f) { assert(f != NULL); dprintf("\n"); wallmsg(f); - return 0; + return RS_RET_OK; } /* try to process a selector action line. Checks if the action @@ -313,6 +323,8 @@ static rsRetVal queryEtryPt(uchar *name, rsRetVal (**pEtryPoint)()) *pEtryPoint = doAction; } else if(!strcmp((char*) name, "parseSelectorAct")) { *pEtryPoint = parseSelectorAct; + } else if(!strcmp((char*) name, "isCompatibleWithFeature")) { + *pEtryPoint = isCompatibleWithFeature; } /*else if(!strcmp((char*) name, "freeInstance")) { *pEtryPoint = freeInstanceFile; }*/ diff --git a/rsyslog.h b/rsyslog.h index 3884635d..149627bc 100644 --- a/rsyslog.h +++ b/rsyslog.h @@ -50,6 +50,8 @@ enum rsRetVal_ /** return value. All methods return this if not specified oth /* return states for config file processing */ RS_RET_CONFLINE_PROCESSED = -2000, /**< config line was processed, do not pass to any other module */ RS_RET_CONFLINE_UNPROCESSED = -2001,/**< config line was not processed, pass to other module */ + RS_RET_DISCARDMSG = -2002, /**< discard message (no error state, processing request!) */ + RS_RET_INCOMPATIBLE = -2003, /**< function not compatible with requested feature */ RS_RET_OK = 0 /**< operation successful */ }; typedef enum rsRetVal_ rsRetVal; /**< friendly type for global return value */ diff --git a/syslogd-types.h b/syslogd-types.h index ee29c68a..2865b81d 100644 --- a/syslogd-types.h +++ b/syslogd-types.h @@ -53,6 +53,14 @@ #endif +/* we define features of the syslog code. This features can be used + * to check if modules are compatible with them - and possible other + * applications I do not yet envision. -- rgerhards, 2007-07-24 + */ +typedef enum _syslogFeature { + sFEATURERepeatedMsgReduction = 1 +} syslogFeature; + /* we define our own facility and severities */ /* facility and severity codes */ typedef struct _syslogCode { @@ -135,7 +143,7 @@ struct syslogTime { */ struct filed { struct filed *f_next; /* next in linked list */ - short f_type; /* entry type, see below */ + /*__attribute__((deprecated))*/ short f_type; /* entry type, see below */ short f_file; /* file descriptor */ time_t f_time; /* time this was last written */ /* filter properties */ diff --git a/syslogd.c b/syslogd.c index 61f2ee46..6b8bd148 100644 --- a/syslogd.c +++ b/syslogd.c @@ -220,6 +220,7 @@ #include "ommysql.h" #include "omfwd.h" #include "omfile.h" +#include "omdiscard.h" /* We define our own set of syslog defintions so that we * do not need to rely on (possibly different) implementations. @@ -664,7 +665,7 @@ static void *singleWorker(); /* REMOVEME later 2005-10-24 */ static char **crunch_list(char *list); static void printline(char *hname, char *msg, int iSource); static void logmsg(int pri, msg_t*, int flags); -static void fprintlog(register selector_t *f); +static rsRetVal fprintlog(register selector_t *f); static void reapchild(); static void debug_switch(); static rsRetVal cfline(char *line, register selector_t *f); @@ -2322,6 +2323,7 @@ int shouldProcessThisMessage(selector_t *f, msg_t *pMsg) static void processMsg(msg_t *pMsg) { selector_t *f; + int bContinue; assert(pMsg != NULL); @@ -2375,7 +2377,8 @@ static void processMsg(msg_t *pMsg) } #endif - for (f = Files; f != NULL ; f = f->f_next) { + bContinue = 1; + for (f = Files; f != NULL && bContinue ; f = f->f_next) { /* first, we need to check if this is a disabled (F_UNUSED) * entry. If so, we must not further process it, as the data * structure probably contains invalid pointers and other @@ -2398,16 +2401,6 @@ static void processMsg(msg_t *pMsg) continue; } - /* We now need to check a special case - F_DISCARD. If that - * action is specified in the selector line, no futher processing - * must be done. Thus, we stop the for-loop. - * 2005-09-09 rgerhards - */ - if(f->f_type == F_DISCARD) { - dprintf("Discarding message based on selector config\n"); - break; /* that's it for this message ;) */ - } - /* don't output marks to recently written files */ if ((pMsg->msgFlags & MARK) && (now - f->f_time) < MarkInterval / 2) continue; @@ -2427,7 +2420,8 @@ static void processMsg(msg_t *pMsg) * but back off so we'll flush less often in the future. */ if (now > REPEATTIME(f)) { - fprintlog(f); + if(fprintlog(f) == RS_RET_DISCARDMSG) + bContinue = 0; BACKOFF(f); } } else { @@ -2437,12 +2431,14 @@ static void processMsg(msg_t *pMsg) */ if(f->f_pMsg != NULL) { if(f->f_prevcount > 0) - fprintlog(f); + if(fprintlog(f) == RS_RET_DISCARDMSG) + bContinue = 0; MsgDestruct(f->f_pMsg); } f->f_pMsg = MsgAddRef(pMsg); /* call the output driver */ - fprintlog(f); + if(fprintlog(f) == RS_RET_DISCARDMSG) + bContinue = 0; } } } @@ -3265,18 +3261,14 @@ void iovCreate(selector_t *f) * semantics. The message is typically already contained in the * channel save buffer (f->f_prevline). This is not only the case * when a message was already repeated but also when a new message - * arrived. Parameter "msg", which sounds like the message content, - * actually contains the message only in those few cases where it - * was too large to fit into the channel save buffer. - * - * This whole function is probably about to change once we have the - * message abstraction. + * arrived. */ -void fprintlog(register selector_t *f) +rsRetVal fprintlog(register selector_t *f) { msg_t *pMsgSave; /* to save current message pointer, necessary to restore it in case it needs to be updated (e.g. repeated msgs) */ pMsgSave = NULL; /* indicate message poiner not saved */ + rsRetVal iRet = RS_RET_OK; /* first check if this is a regular message or the repeation of * a previous message. If so, we need to change the message text @@ -3295,7 +3287,7 @@ void fprintlog(register selector_t *f) if((pMsg = MsgDup(f->f_pMsg)) == NULL) { /* it failed - nothing we can do against it... */ dprintf("Message duplication failed, dropping repeat message.\n"); - return; + return RS_RET_ERR; } /* We now need to update the other message properties. @@ -3312,11 +3304,13 @@ void fprintlog(register selector_t *f) } dprintf("Called fprintlog, logging to %s", TypeNames[f->f_type]); + /*dprintf("Called fprintlog, logging to %s", modGetName(pMod)); // TODO: this does not work with unused!*/ - f->f_time = now; /* we need this for message repeation processing TODO: why must it be global now? */ + f->f_time = now; /* we need this for message repeation processing TODO: why must "now" be global? */ if(f->f_type != F_UNUSED) { - if(f->pMod->mod.om.doAction != NULL) /* safety check */ - f->pMod->mod.om.doAction(f); /* call configured action */ + if(f->pMod->mod.om.doAction != NULL) { /* safety check */ + iRet = f->pMod->mod.om.doAction(f); /* call configured action */ + } // TODO: this causes problems for the emergency logging system! } @@ -3337,7 +3331,7 @@ void fprintlog(register selector_t *f) f->f_pMsg = pMsgSave; /* restore it */ } - return; + return iRet; } @@ -5071,9 +5065,6 @@ static rsRetVal cfline(char *line, register selector_t *f) return iRet; } - /* common properties */ - f->f_ReduceRepeated = bReduceRepeatMsgs; - /* we now check if there are some global (BSD-style) filter conditions * and, if so, we copy them over. rgerhards, 2005-10-18 */ @@ -5089,30 +5080,31 @@ static rsRetVal cfline(char *line, register selector_t *f) dprintf("leading char in action: %c\n", *p); - if(*p == '~') { - /* for the time being, we must handle discard in a special way */ - dprintf ("discard\n"); - f->f_type = F_DISCARD; - } else { - /* loop through all modules and see if one picks up the line */ - pMod = omodGetNxt(NULL); - while(pMod != NULL) { - iRet = pMod->mod.om.parseSelectorAct(&p , f); - if(iRet == RS_RET_CONFLINE_PROCESSED) { - dprintf("Module %s processed this config line.\n", - modGetName(pMod)); - f->pMod = pMod; - break; - } - else if(iRet != RS_RET_CONFLINE_UNPROCESSED) { - /* we ignore any errors that might have occured - we can - * not do anything at all, and it would block other modules - * from initializing. -- rgerhards, 2007-07-24 - */ - dprintf("error %d parsing config line - continuing\n", (int) iRet); + /* loop through all modules and see if one picks up the line */ + pMod = omodGetNxt(NULL); + while(pMod != NULL) { + iRet = pMod->mod.om.parseSelectorAct(&p , f); + if(iRet == RS_RET_CONFLINE_PROCESSED) { + dprintf("Module %s processed this config line.\n", + modGetName(pMod)); + f->pMod = pMod; + /* now check if the module is compatible with select features */ + if(pMod->isCompatibleWithFeature(sFEATURERepeatedMsgReduction) == RS_RET_OK) + f->f_ReduceRepeated = bReduceRepeatMsgs; + else { + dprintf("module is incompatible with RepeatedMsgReduction - turned off\n"); + f->f_ReduceRepeated = 0; } - pMod = omodGetNxt(pMod); + break; } + else if(iRet != RS_RET_CONFLINE_UNPROCESSED) { + /* we ignore any errors that might have occured - we can + * not do anything at all, and it would block other modules + * from initializing. -- rgerhards, 2007-07-24 + */ + dprintf("error %d parsing config line - continuing\n", (int) iRet); + } + pMod = omodGetNxt(pMod); } return RS_RET_OK; @@ -5709,6 +5701,8 @@ static rsRetVal loadBuildInModules(void) if((iRet = doModInit(modInitMySQL, (uchar*) "builtin-mysql")) != RS_RET_OK) return iRet; # endif + if((iRet = doModInit(modInitDiscard, (uchar*) "builtin-discard")) != RS_RET_OK) + return iRet; /* dirty, but this must be for the time being: the usrmsg module must always be * loaded as last module. This is because it processes any time of action selector. -- cgit