2017-01-17 08:54:37 +01:00

219 lines
6.0 KiB
C

/**
* The rfc3195 input module.
*
* Please note that this file replaces the rfc3195d daemon that was
* also present in pre-v3 versions of rsyslog.
*
* WARNING: due to no demand at all for RFC3195, we have converted rfc3195d
* to this input module, but we have NOT conducted any testing. Also,
* the module does not yet properly handle the recovery case. If someone
* intends to put this module into production, good testing should be
* made and it also is a good idea to notify me that you intend to use
* it in production. In this case, I'll probably give the module another
* cleanup. I don't do this now because so far it looks just like a big
* waste of time. -- rgerhards, 2008-04-16
*
* \author Rainer Gerhards <rgerhards@adiscon.com>
*
* Copyright (C) 2003-2012 Adiscon GmbH.
*
* This file is part of rsyslog.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
* -or-
* see COPYING.ASL20 in the source distribution
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include "config.h"
#include <stdio.h>
#include <unistd.h>
#include <sys/errno.h>
#include <assert.h>
#include "rsyslog.h"
#include "dirty.h"
#include "liblogging/liblogging.h"
#include "liblogging/srAPI.h"
#include "liblogging/syslogmessage.h"
#include "module-template.h"
#include "cfsysline.h"
#include "msg.h"
#include "errmsg.h"
#include "unicode-helper.h"
MODULE_TYPE_INPUT
MODULE_TYPE_NOKEEP
MODULE_CNFNAME("im3195")
/* Module static data */
DEF_IMOD_STATIC_DATA
DEFobjCurrIf(errmsg)
DEFobjCurrIf(prop)
/* configuration settings */
struct modConfData_s {
EMPTY_STRUCT;
};
static int listenPort = 601;
/* we use a global API object below, because this listener is
* not very complex. As such, this hack should not harm anything.
* rgerhards, 2005-10-12
*/
static srAPIObj* pAPI;
static prop_t *pInputName = NULL;
/* there is only one global inputName for all messages generated by this module */
/* This method is called when a message has been fully received.
* It passes the received message to the rsyslog main message
* queue. Please note that this callback is synchronous, thus
* liblogging will be on hold until it returns. This is important
* to note because in an error case we might stay in this code
* for an extended amount of time. So far, we think this is the
* best solution, but real-world experience might tell us a
* different truth ;)
*/
void OnReceive(srAPIObj __attribute__((unused)) *pMyAPI, srSLMGObj* pSLMG)
{
uchar *pszRawMsg;
uchar *fromHost = (uchar*) "[unset]"; /* TODO: get hostname */
uchar *fromHostIP = (uchar*) "[unset]"; /* TODO: get hostname */
srSLMGGetRawMSG(pSLMG, &pszRawMsg);
parseAndSubmitMessage(fromHost, fromHostIP, pszRawMsg, strlen((char*)pszRawMsg),
PARSE_HOSTNAME, eFLOWCTL_FULL_DELAY, pInputName, NULL, 0, NULL);
}
#if 0
BEGINbeginCnfLoad
CODESTARTbeginCnfLoad
ENDbeginCnfLoad
BEGINendCnfLoad
CODESTARTendCnfLoad
ENDendCnfLoad
BEGINcheckCnf
CODESTARTcheckCnf
ENDcheckCnf
BEGINactivateCnf
CODESTARTactivateCnf
ENDactivateCnf
BEGINfreeCnf
CODESTARTfreeCnf
ENDfreeCnf
#endif
BEGINrunInput
CODESTARTrunInput
/* this is an endless loop - it is terminated when the thread is
* signalled to do so. This, however, is handled by the framework,
* right into the sleep below.
*/
while(!pThrd->bShallStop) {
/* now move the listener to running state. Control will only
* return after SIGUSR1.
*/
if((iRet = srAPIRunListener(pAPI)) != SR_RET_OK) {
errmsg.LogError(0, NO_ERRCODE, "error %d running liblogging listener - im3195 is defunct", iRet);
FINALIZE; /* this causes im3195 to become defunct; TODO: recovery handling */
}
}
finalize_it:
ENDrunInput
BEGINwillRun
CODESTARTwillRun
if((pAPI = srAPIInitLib()) == NULL) {
errmsg.LogError(0, NO_ERRCODE, "error initializing liblogging - im3195 is defunct");
ABORT_FINALIZE(RS_RET_ERR);
}
if((iRet = srAPISetOption(pAPI, srOPTION_BEEP_LISTENPORT, listenPort)) != SR_RET_OK) {
errmsg.LogError(0, NO_ERRCODE, "error %d setting liblogging listen port - im3195 is defunct", iRet);
FINALIZE;
}
if((iRet = srAPISetupListener(pAPI, OnReceive)) != SR_RET_OK) {
errmsg.LogError(0, NO_ERRCODE, "error %d setting up liblogging listener - im3195 is defunct", iRet);
FINALIZE;
}
finalize_it:
ENDwillRun
BEGINafterRun
CODESTARTafterRun
dbgprintf("Shutting down rfc3195d. Be patient, this can take up to 30 seconds...\n");
srAPIShutdownListener(pAPI);
ENDafterRun
BEGINmodExit
CODESTARTmodExit
srAPIExitLib(pAPI); /* terminate liblogging */
/* global variable cleanup */
if(pInputName != NULL)
prop.Destruct(&pInputName);
/* release objects we used */
objRelease(errmsg, CORE_COMPONENT);
objRelease(prop, CORE_COMPONENT);
ENDmodExit
BEGINqueryEtryPt
CODESTARTqueryEtryPt
CODEqueryEtryPt_STD_IMOD_QUERIES
ENDqueryEtryPt
static rsRetVal resetConfigVariables(uchar __attribute__((unused)) *pp, void __attribute__((unused)) *pVal)
{
listenPort = 601;
return RS_RET_OK;
}
BEGINmodInit()
CODESTARTmodInit
*ipIFVersProvided = CURR_MOD_IF_VERSION; /* we only support the current interface specification */
CODEmodInit_QueryRegCFSLineHdlr
CHKiRet(objUse(errmsg, CORE_COMPONENT));
CHKiRet(objUse(prop, CORE_COMPONENT));
CHKiRet(omsdRegCFSLineHdlr((uchar *)"input3195listenport", 0, eCmdHdlrInt, NULL, &listenPort,
STD_LOADABLE_MODULE_ID));
CHKiRet(omsdRegCFSLineHdlr((uchar *)"resetconfigvariables", 1, eCmdHdlrCustomHandler, resetConfigVariables,
NULL, STD_LOADABLE_MODULE_ID));
CHKiRet(prop.Construct(&pInputName));
CHKiRet(prop.SetString(pInputName, UCHAR_CONSTANT("im3195"), sizeof("im3195") - 1));
CHKiRet(prop.ConstructFinalize(pInputName));
ENDmodInit
/* vim:set ai:
*/