diff options
Diffstat (limited to 'plugins')
-rw-r--r-- | plugins/imrelp/imrelp.c | 5 | ||||
-rw-r--r-- | plugins/mmsnmptrapd/Makefile.am | 8 | ||||
-rw-r--r-- | plugins/mmsnmptrapd/mmsnmptrapd.c | 426 | ||||
-rw-r--r-- | plugins/omlibdbi/omlibdbi.c | 1 |
4 files changed, 435 insertions, 5 deletions
diff --git a/plugins/imrelp/imrelp.c b/plugins/imrelp/imrelp.c index 8650c86e..e40b4b1e 100644 --- a/plugins/imrelp/imrelp.c +++ b/plugins/imrelp/imrelp.c @@ -60,8 +60,6 @@ static prop_t *pInputName = NULL; /* there is only one global inputName for all /* config settings */ -static int iTCPSessMax = 200; /* max number of sessions */ - /* ------------------------------ callbacks ------------------------------ */ #if 0 @@ -173,7 +171,6 @@ ENDmodExit static rsRetVal resetConfigVariables(uchar __attribute__((unused)) *pp, void __attribute__((unused)) *pVal) { - iTCPSessMax = 200; return RS_RET_OK; } @@ -197,8 +194,6 @@ CODEmodInit_QueryRegCFSLineHdlr /* register config file handlers */ CHKiRet(omsdRegCFSLineHdlr((uchar *)"inputrelpserverrun", 0, eCmdHdlrGetWord, addListener, NULL, STD_LOADABLE_MODULE_ID, eConfObjGlobal)); - CHKiRet(omsdRegCFSLineHdlr((uchar *)"inputrelpmaxsessions", 0, eCmdHdlrInt, - NULL, &iTCPSessMax, STD_LOADABLE_MODULE_ID, eConfObjGlobal)); CHKiRet(omsdRegCFSLineHdlr((uchar *)"resetconfigvariables", 1, eCmdHdlrCustomHandler, resetConfigVariables, NULL, STD_LOADABLE_MODULE_ID, eConfObjGlobal)); ENDmodInit diff --git a/plugins/mmsnmptrapd/Makefile.am b/plugins/mmsnmptrapd/Makefile.am new file mode 100644 index 00000000..ca027ca7 --- /dev/null +++ b/plugins/mmsnmptrapd/Makefile.am @@ -0,0 +1,8 @@ +pkglib_LTLIBRARIES = mmsnmptrapd.la + +mmsnmptrapd_la_SOURCES = mmsnmptrapd.c +mmsnmptrapd_la_CPPFLAGS = $(RSRT_CFLAGS) $(PTHREADS_CFLAGS) +mmsnmptrapd_la_LDFLAGS = -module -avoid-version +mmsnmptrapd_la_LIBADD = + +EXTRA_DIST = diff --git a/plugins/mmsnmptrapd/mmsnmptrapd.c b/plugins/mmsnmptrapd/mmsnmptrapd.c new file mode 100644 index 00000000..54354830 --- /dev/null +++ b/plugins/mmsnmptrapd/mmsnmptrapd.c @@ -0,0 +1,426 @@ +/* mmsnmptrapd.c + * This is a message modification module. It takes messages generated + * from snmptrapd and modifies them so that the look like they + * originated from the real originator. + * + * NOTE: read comments in module-template.h for details on the calling interface! + * + * File begun on 2011-05-05 by RGerhards + * + * Copyright 2011 Rainer Gerhards and Adiscon GmbH. + * + * This file is part of rsyslog. + * + * Rsyslog 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 3 of the License, or + * (at your option) any later version. + * + * Rsyslog 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 Rsyslog. If not, see <http://www.gnu.org/licenses/>. + * + * A copy of the GPL can be found in the file "COPYING" in this distribution. + */ +#include "config.h" +#include "rsyslog.h" +#include <stdio.h> +#include <stdarg.h> +#include <stdlib.h> +#include <string.h> +#include <assert.h> +#include <signal.h> +#include <errno.h> +#include <unistd.h> +#include <ctype.h> +#include "conf.h" +#include "msg.h" +#include "syslogd-types.h" +#include "template.h" +#include "module-template.h" +#include "errmsg.h" +#include "cfsysline.h" +#include "unicode-helper.h" +#include "dirty.h" + +MODULE_TYPE_OUTPUT +MODULE_TYPE_NOKEEP + +static rsRetVal resetConfigVariables(uchar __attribute__((unused)) *pp, void __attribute__((unused)) *pVal); + +/* static data */ +DEFobjCurrIf(errmsg); + +/* internal structures + */ +DEF_OMOD_STATIC_DATA + +struct severMap_s { + uchar *name; + int code; + struct severMap_s *next; +}; + +typedef struct _instanceData { + uchar *pszTagName; + uchar *pszTagID; /* chaced: name plus trailing shlash (for compares) */ + int lenTagID; /* cached length of tag ID, for performance reasons */ + struct severMap_s *severMap; +} instanceData; + +typedef struct configSettings_s { + uchar *pszTagName; /**< name of tag start value that indicates snmptrapd initiated message */ + uchar *pszSeverityMapping; /**< severitystring to numerical code mapping for snmptrapd string */ +} configSettings_t; + +SCOPING_SUPPORT; /* must be set AFTER configSettings_t is defined */ + +BEGINinitConfVars /* (re)set config variables to default values */ +CODESTARTinitConfVars + cs.pszTagName = NULL; + cs.pszSeverityMapping = NULL; + resetConfigVariables(NULL, NULL); +ENDinitConfVars + + +BEGINcreateInstance +CODESTARTcreateInstance +ENDcreateInstance + + +BEGINisCompatibleWithFeature +CODESTARTisCompatibleWithFeature +ENDisCompatibleWithFeature + + +BEGINfreeInstance + struct severMap_s *node, *nodeDel; +CODESTARTfreeInstance + for(node = pData->severMap ; node != NULL ; ) { + nodeDel = node; + node = node->next; + free(nodeDel->name); + free(nodeDel); + } + free(pData->pszTagName); + free(pData->pszTagID); +ENDfreeInstance + + +BEGINdbgPrintInstInfo +CODESTARTdbgPrintInstInfo + dbgprintf("mmsnmptrapd\n"); +ENDdbgPrintInstInfo + + +BEGINtryResume +CODESTARTtryResume +ENDtryResume + + +/* check if a string is numeric (int) */ +static inline int +isNumeric(uchar *str) +{ + int r = 1; + if(*str == '-' || *str == '+') + ++str; + while(*str) { + if(!isdigit(*str)) { + r = 0; + goto done; + } + ++str; + } +done: + return r; +} + +/* get a substring delimited by a character (or end of string). The + * string is trimmed, that is leading and trailing spaces are removed. + * The caller must provide a buffer which shall receive the substring. + * String length is returned as result. The input string is updated + * on exit, so that it may be used for another query starting at that + * position. + */ +static int +getSubstring(uchar **psrc, uchar delim, uchar *dst, int lenDst) +{ + uchar *dstwrk = dst; + uchar *src = *psrc; + while(*src && isspace(*src)) { + ++src; /* trim leading spaces */ + } + while(*src && *src != delim && --lenDst > 0) { + *dstwrk++ = *src++; + } + dstwrk--; + while(dstwrk > dst && isspace(*dst)) + --dstwrk; /* trim trailing spaces */ + *++dstwrk = '\0'; + + /* final results */ + if(*src == delim) + ++src; + *psrc = src; + return(dstwrk - dst); +} + + +/* get string up to the next SP or '/'. Stops at max size. + * dst, lenDst (receive buffer) must be given. lenDst is + * max length on entry and actual length on exit. + */ +static int +getTagComponent(uchar *tag, uchar *dst, int *lenDst) +{ + int end = *lenDst - 1; /* -1 for NUL-char! */ + int i; + + i = 0; + if(tag[i] != '/') + goto done; + ++tag; + while(i < end && tag[i] != '\0' && tag[i] != ' ' && tag[i] != '/') { + dst[i] = tag[i]; + ++i; + } + dst[i] = '\0'; +dbgprintf("XXXX: getTagComponent dst on output: '%s', len %d\n", dst, i); + *lenDst = i; +done: + return i; +} + + +/* lookup severity code based on provided severity + * returns -1 if severity could not be found. + */ +static inline int +lookupSeverityCode(instanceData *pData, uchar *sever) +{ + struct severMap_s *node; + int sevCode = -1; + + for(node = pData->severMap ; node != NULL ; node = node->next) { + if(!ustrcmp(node->name, sever)) { + sevCode = node->code; + break; + } + } + return sevCode; +} + + +BEGINdoAction + int lenTAG; + int lenSever; + int lenHost; + int sevCode; + msg_t *pMsg; + uchar *pszTag; + uchar pszSever[512]; + uchar pszHost[512]; +CODESTARTdoAction + pMsg = (msg_t*) ppString[0]; + dbgprintf("XXXX: mmsnmptrapd called with pMsg %p\n", pMsg); + getTAG(pMsg, &pszTag, &lenTAG); + if(strncmp((char*)pszTag, (char*)pData->pszTagID, pData->lenTagID)) { + DBGPRINTF("tag '%s' not matching, mmsnmptrapd ignoring this message\n", + pszTag); + FINALIZE; + } + + lenSever = sizeof(pszSever); +dbgprintf("XXXX: pszTag: '%s', lenID %d\n", pszTag, pData->lenTagID); + getTagComponent(pszTag+pData->lenTagID-1, pszSever, &lenSever); + lenHost = sizeof(pszHost); + getTagComponent(pszTag+pData->lenTagID+lenSever, pszHost, &lenHost); + dbgprintf("XXXX: mmsnmptrapd sever '%s'(%d), host '%s'(%d)\n", pszSever, lenSever, pszHost,lenHost); + + if(pszHost[lenHost-1] == ':') { + pszHost[lenHost-1] = '\0'; + --lenHost; + } + sevCode = lookupSeverityCode(pData, pszSever); +dbgprintf("XXXX: severity for message is %d\n", sevCode); + /* now apply new settings */ + MsgSetTAG(pMsg, pData->pszTagName, pData->lenTagID); + MsgSetHOSTNAME(pMsg, pszHost, lenHost); + if(sevCode != -1) + pMsg->iSeverity = sevCode; /* we update like the parser does! */ +finalize_it: +ENDdoAction + + +/* Build the severity mapping table based on user-provided configuration + * settings. + */ +static inline rsRetVal +buildSeverityMapping(instanceData *pData) +{ + uchar pszSev[512]; + uchar pszSevCode[512]; + int sevCode; + uchar *mapping; + struct severMap_s *node; + DEFiRet; + + mapping = cs.pszSeverityMapping; + + while(1) { /* broken inside when all entries are processed */ + if(getSubstring(&mapping, '/', pszSev, sizeof(pszSev)) == 0) { + FINALIZE; + } + if(getSubstring(&mapping, ',', pszSevCode, sizeof(pszSevCode)) == 0) { + errmsg.LogError(0, RS_RET_ERR, "error: invalid severity mapping, cannot " + "extract code. given: '%s'\n", cs.pszSeverityMapping); + ABORT_FINALIZE(RS_RET_ERR); + } + sevCode = atoi((char*) pszSevCode); + if(!isNumeric(pszSevCode)) + sevCode = -1; + if(sevCode < 0 || sevCode > 7) { + errmsg.LogError(0, RS_RET_ERR, "error: severity code %d outside of valid " + "range 0..7 (was string '%s')\n", sevCode, pszSevCode); + ABORT_FINALIZE(RS_RET_ERR); + } + CHKmalloc(node = MALLOC(sizeof(struct severMap_s))); + CHKmalloc(node->name = ustrdup(pszSev)); + node->code = sevCode; + /* we enqueue at the top, so the two lines below do all we need! */ + node->next = pData->severMap; + pData->severMap = node; + DBGPRINTF("mmsnmptrapd: severity string '%s' mapped to code %d\n", + pszSev, sevCode); + } + +finalize_it: + RETiRet; +} + + +BEGINparseSelectorAct +CODESTARTparseSelectorAct +CODE_STD_STRING_REQUESTparseSelectorAct(1) + /* first check if this config line is actually for us */ + if(strncmp((char*) p, ":mmsnmptrapd:", sizeof(":mmsnmptrapd:") - 1)) { + ABORT_FINALIZE(RS_RET_CONFLINE_UNPROCESSED); + } + + /* ok, if we reach this point, we have something for us */ + p += sizeof(":mmsnmptrapd:") - 1; /* eat indicator sequence (-1 because of '\0'!) */ + CHKiRet(createInstance(&pData)); + + /* check if a non-standard template is to be applied */ + if(*(p-1) == ';') + --p; + /* we call the function below because we need to call it via our interface definition. However, + * the format specified (if any) is always ignored. + */ + CHKiRet(cflineParseTemplateName(&p, *ppOMSR, 0, OMSR_TPL_AS_MSG, (uchar*) "RSYSLOG_FileFormat")); + + /* finally build the instance */ + if(cs.pszTagName == NULL) { + pData->pszTagName = (uchar*) strdup("snmptrapd:"); + pData->pszTagID = (uchar*) strdup("snmptrapd/"); + } else { + int lenTag = ustrlen(cs.pszTagName); + /* new tag value (with colon at the end) */ + CHKmalloc(pData->pszTagName = MALLOC(lenTag + 2)); + memcpy(pData->pszTagName, cs.pszTagName, lenTag); + memcpy(pData->pszTagName+lenTag, ":", 2); + /* tag ID for comparisions */ + CHKmalloc(pData->pszTagID = MALLOC(lenTag + 2)); + memcpy(pData->pszTagID, cs.pszTagName, lenTag); + memcpy(pData->pszTagID+lenTag, "/", 2); + free(cs.pszTagName); /* no longer needed */ + } + pData->lenTagID = ustrlen(pData->pszTagID); + if(cs.pszSeverityMapping != NULL) { + CHKiRet(buildSeverityMapping(pData)); + } + + /* all config vars auto-reset! */ + cs.pszTagName = NULL; + free(cs.pszSeverityMapping); + cs.pszSeverityMapping = NULL; +CODE_STD_FINALIZERparseSelectorAct +ENDparseSelectorAct + + +BEGINmodExit +CODESTARTmodExit + objRelease(errmsg, CORE_COMPONENT); +ENDmodExit + + +BEGINqueryEtryPt +CODESTARTqueryEtryPt +CODEqueryEtryPt_STD_OMOD_QUERIES +ENDqueryEtryPt + + + +/* Reset config variables for this module to default values. + */ +static rsRetVal resetConfigVariables(uchar __attribute__((unused)) *pp, void __attribute__((unused)) *pVal) +{ + DEFiRet; + free(cs.pszTagName); + cs.pszTagName = NULL; + free(cs.pszSeverityMapping); + cs.pszSeverityMapping = NULL; + RETiRet; +} + + +BEGINmodInit() + rsRetVal localRet; + rsRetVal (*pomsrGetSupportedTplOpts)(unsigned long *pOpts); + unsigned long opts; + int bMsgPassingSupported; +CODESTARTmodInit +SCOPINGmodInit + *ipIFVersProvided = CURR_MOD_IF_VERSION; + /* we only support the current interface specification */ +CODEmodInit_QueryRegCFSLineHdlr + /* check if the rsyslog core supports parameter passing code */ + bMsgPassingSupported = 0; + localRet = pHostQueryEtryPt((uchar*)"OMSRgetSupportedTplOpts", + &pomsrGetSupportedTplOpts); + if(localRet == RS_RET_OK) { + /* found entry point, so let's see if core supports msg passing */ + CHKiRet((*pomsrGetSupportedTplOpts)(&opts)); + if(opts & OMSR_TPL_AS_MSG) + bMsgPassingSupported = 1; + } else if(localRet != RS_RET_ENTRY_POINT_NOT_FOUND) { + ABORT_FINALIZE(localRet); /* Something else went wrong, not acceptable */ + } + + if(!bMsgPassingSupported) { + DBGPRINTF("mmsnmptrapd: msg-passing is not supported by rsyslog core, " + "can not continue.\n"); + ABORT_FINALIZE(RS_RET_NO_MSG_PASSING); + } + + CHKiRet(objUse(errmsg, CORE_COMPONENT)); + + /* TODO: config vars ininit can be replaced by commented-out code above in v6 */ + cs.pszTagName = NULL; + cs.pszSeverityMapping = NULL; + + CHKiRet(omsdRegCFSLineHdlr((uchar *)"mmsnmptrapdtag", 0, eCmdHdlrInt, + NULL, &cs.pszTagName, STD_LOADABLE_MODULE_ID, eConfObjAction)); + CHKiRet(omsdRegCFSLineHdlr((uchar *)"mmsnmptrapdseveritymapping", 0, eCmdHdlrGetWord, + NULL, &cs.pszSeverityMapping, STD_LOADABLE_MODULE_ID, eConfObjAction)); + CHKiRet(omsdRegCFSLineHdlr((uchar *)"resetconfigvariables", 1, eCmdHdlrCustomHandler, + resetConfigVariables, NULL, STD_LOADABLE_MODULE_ID, eConfObjAction)); +ENDmodInit + +/* vi:set ai: + */ diff --git a/plugins/omlibdbi/omlibdbi.c b/plugins/omlibdbi/omlibdbi.c index 2142878c..c0bfed61 100644 --- a/plugins/omlibdbi/omlibdbi.c +++ b/plugins/omlibdbi/omlibdbi.c @@ -43,6 +43,7 @@ #include "dirty.h" #include "syslogd-types.h" #include "cfsysline.h" +#include "conf.h" #include "srUtils.h" #include "template.h" #include "module-template.h" |