summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRainer Gerhards <rgerhards@adiscon.com>2009-06-29 16:53:26 +0200
committerRainer Gerhards <rgerhards@adiscon.com>2009-06-29 16:53:26 +0200
commitde84a12f8a5f140c0f7b8e00f4cac92ef13cd866 (patch)
treeeae06778ee37276778efe93db12f1172ba71b840
parent151c22e579d6de345d9ac7971ba1ba2f41b88976 (diff)
downloadrsyslog-de84a12f8a5f140c0f7b8e00f4cac92ef13cd866.tar.gz
rsyslog-de84a12f8a5f140c0f7b8e00f4cac92ef13cd866.tar.xz
rsyslog-de84a12f8a5f140c0f7b8e00f4cac92ef13cd866.zip
introduced the idea of detached properties
some things inside the message can be used over a large number of messages and need to to be allocated and re-written every time. I now begin to implement this as a "prop_t" object, first use for the inputName. Some input modules are already converted, some others to go. Will do a little performance check on the new method before I go further. Also, this commit has some cleanup and a few bug fixes that prevented compiliation in debug mode (I overlooked this as I did not compile for debug, what I normally do, and the automatted test also does not do that)
-rw-r--r--plugins/imdiag/imdiag.c2
-rw-r--r--plugins/imfile/imfile.c2
-rw-r--r--plugins/imklog/imklog.c2
-rw-r--r--plugins/imklog/linux.c7
-rw-r--r--plugins/imudp/imudp.c16
-rw-r--r--runtime/datetime.c5
-rw-r--r--runtime/datetime.h2
-rw-r--r--runtime/msg.c91
-rw-r--r--runtime/msg.h11
-rw-r--r--runtime/prop.c63
-rw-r--r--runtime/prop.h11
-rw-r--r--runtime/rsyslog.c3
-rw-r--r--runtime/rsyslog.h1
-rw-r--r--runtime/stringbuf.h2
-rw-r--r--tcps_sess.c8
-rw-r--r--tcpsrv.c15
-rw-r--r--tcpsrv.h4
-rw-r--r--tests/nettester.c5
-rw-r--r--tools/syslogd.c5
19 files changed, 200 insertions, 55 deletions
diff --git a/plugins/imdiag/imdiag.c b/plugins/imdiag/imdiag.c
index bfb4a2e5..4b004bc4 100644
--- a/plugins/imdiag/imdiag.c
+++ b/plugins/imdiag/imdiag.c
@@ -206,7 +206,7 @@ doInjectMsg(int iNum)
/* we now create our own message object and submit it to the queue */
CHKiRet(msgConstructWithTime(&pMsg, &stTime, ttGenTime));
MsgSetRawMsg(pMsg, (char*) szMsg, ustrlen(szMsg));
- MsgSetInputName(pMsg, UCHAR_CONSTANT("imdiag"), sizeof("imdiag")-1);
+ MsgSetInputNameStr(pMsg, UCHAR_CONSTANT("imdiag"), sizeof("imdiag")-1);
MsgSetFlowControlType(pMsg, eFLOWCTL_NO_DELAY);
pMsg->msgFlags = NEEDS_PARSING | PARSE_HOSTNAME;
pMsg->bParseHOSTNAME = 1;
diff --git a/plugins/imfile/imfile.c b/plugins/imfile/imfile.c
index 631d02ff..fdd0c5f0 100644
--- a/plugins/imfile/imfile.c
+++ b/plugins/imfile/imfile.c
@@ -97,7 +97,7 @@ static rsRetVal enqLine(fileInfo_t *pInfo, cstr_t *cstrLine)
CHKiRet(msgConstruct(&pMsg));
MsgSetFlowControlType(pMsg, eFLOWCTL_FULL_DELAY);
- MsgSetInputName(pMsg, UCHAR_CONSTANT("imfile"), sizeof("imfile")-1);
+ MsgSetInputNameStr(pMsg, UCHAR_CONSTANT("imfile"), sizeof("imfile")-1);
MsgSetRawMsg(pMsg, (char*)rsCStrGetSzStr(cstrLine), cstrLen(cstrLine));
MsgSetMSGoffs(pMsg, 0); /* we do not have a header... */
MsgSetHOSTNAME(pMsg, glbl.GetLocalHostName(), ustrlen(glbl.GetLocalHostName()));
diff --git a/plugins/imklog/imklog.c b/plugins/imklog/imklog.c
index ab806183..21744c4b 100644
--- a/plugins/imklog/imklog.c
+++ b/plugins/imklog/imklog.c
@@ -97,7 +97,7 @@ enqMsg(uchar *msg, uchar* pszTag, int iFacility, int iSeverity)
CHKiRet(msgConstruct(&pMsg));
MsgSetFlowControlType(pMsg, eFLOWCTL_LIGHT_DELAY);
- MsgSetInputName(pMsg, UCHAR_CONSTANT("imklog"), sizeof("imklog")-1);
+ MsgSetInputNameStr(pMsg, UCHAR_CONSTANT("imklog"), sizeof("imklog")-1);
MsgSetRawMsgWOSize(pMsg, (char*)msg);
MsgSetMSGoffs(pMsg, 0); /* we do not have a header... */
MsgSetRcvFrom(pMsg, glbl.GetLocalHostName());
diff --git a/plugins/imklog/linux.c b/plugins/imklog/linux.c
index fcd9d6cd..977395ea 100644
--- a/plugins/imklog/linux.c
+++ b/plugins/imklog/linux.c
@@ -37,6 +37,7 @@
#include "msg.h"
#include "module-template.h"
#include "imklog.h"
+#include "unicode-helper.h"
/* Includes. */
@@ -86,7 +87,7 @@ extern int ksyslog(int type, char *buf, int len);
static uchar *GetPath(void)
{
- return pszPath ? pszPath : _PATH_KLOG;
+ return pszPath ? pszPath : UCHAR_CONSTANT(_PATH_KLOG);
}
static void CloseLogSrc(void)
@@ -140,7 +141,7 @@ static enum LOGSRC GetKernelLogSrc(void)
* file system is available to get kernel messages from.
*/
if ( use_syscall ||
- ((stat(GetPath(), &sb) < 0) && (errno == ENOENT)) )
+ ((stat((char*)GetPath(), &sb) < 0) && (errno == ENOENT)) )
{
/* Initialize kernel logging. */
ksyslog(1, NULL, 0);
@@ -149,7 +150,7 @@ static enum LOGSRC GetKernelLogSrc(void)
return(kernel);
}
- if ( (kmsg = open(GetPath(), O_RDONLY|O_CLOEXEC)) < 0 )
+ if ( (kmsg = open((char*)GetPath(), O_RDONLY|O_CLOEXEC)) < 0 )
{
imklogLogIntMsg(LOG_ERR, "imklog: Cannot open proc file system, %d.\n", errno);
ksyslog(7, NULL, 0); /* TODO: check this, implement more */
diff --git a/plugins/imudp/imudp.c b/plugins/imudp/imudp.c
index 2340aac4..828b9636 100644
--- a/plugins/imudp/imudp.c
+++ b/plugins/imudp/imudp.c
@@ -43,6 +43,7 @@
#include "msg.h"
#include "parser.h"
#include "datetime.h"
+#include "prop.h"
#include "unicode-helper.h"
MODULE_TYPE_INPUT
@@ -55,6 +56,7 @@ DEFobjCurrIf(errmsg)
DEFobjCurrIf(glbl)
DEFobjCurrIf(net)
DEFobjCurrIf(datetime)
+DEFobjCurrIf(prop)
static int iMaxLine; /* maximum UDP message size supported */
static time_t ttLastDiscard = 0; /* timestamp when a message from a non-permitted sender was last discarded
@@ -68,6 +70,7 @@ static uchar *pRcvBuf = NULL; /* receive buffer (for a single packet). We use a
* it so that we can check available memory in willRun() and request
* termination if we can not get it. -- rgerhards, 2007-12-27
*/
+static prop_t *pInputName = NULL; /* our inputName currently is always "imudp", and this will hold it */
// TODO: static ruleset_t *pBindRuleset = NULL; /* ruleset to bind listener to (use system default if unspecified) */
#define TIME_REQUERY_DFLT 2
static int iTimeRequery = TIME_REQUERY_DFLT;/* how often is time to be queried inside tight recv loop? 0=always */
@@ -242,7 +245,8 @@ processSocket(int fd, struct sockaddr_storage *frominetPrev, int *pbIsPermitted,
/* we now create our own message object and submit it to the queue */
CHKiRet(msgConstructWithTime(&pMsg, &stTime, ttGenTime));
MsgSetRawMsg(pMsg, (char*)pRcvBuf, lenRcvBuf);
- MsgSetInputName(pMsg, UCHAR_CONSTANT("imudp"), sizeof("imudp")-1);
+ prop.AddRef(pInputName);
+ MsgSetInputName(pMsg, pInputName);
MsgSetFlowControlType(pMsg, eFLOWCTL_NO_DELAY);
pMsg->msgFlags = NEEDS_PARSING | PARSE_HOSTNAME;
pMsg->bParseHOSTNAME = 1;
@@ -338,6 +342,12 @@ ENDrunInput
/* initialize and return if will run or not */
BEGINwillRun
CODESTARTwillRun
+ /* we need to create the inputName property (only once during our lifetime) */
+ CHKiRet(prop.Construct(&pInputName));
+ CHKiRet(prop.SetString(pInputName, UCHAR_CONSTANT("imudp"), sizeof("imudp") - 1));
+ CHKiRet(prop.ConstructFinalize(pInputName));
+ prop.AddRef(pInputName);
+
net.PrintAllowedSenders(1); /* UDP */
/* if we could not set up any listners, there is no point in running... */
@@ -365,6 +375,8 @@ CODESTARTafterRun
free(pRcvBuf);
pRcvBuf = NULL;
}
+ if(pInputName != NULL)
+ prop.Destruct(&pInputName);
ENDafterRun
@@ -374,6 +386,7 @@ CODESTARTmodExit
objRelease(errmsg, CORE_COMPONENT);
objRelease(glbl, CORE_COMPONENT);
objRelease(datetime, CORE_COMPONENT);
+ objRelease(prop, CORE_COMPONENT);
objRelease(net, LM_NET_FILENAME);
ENDmodExit
@@ -405,6 +418,7 @@ CODEmodInit_QueryRegCFSLineHdlr
CHKiRet(objUse(errmsg, CORE_COMPONENT));
CHKiRet(objUse(glbl, CORE_COMPONENT));
CHKiRet(objUse(datetime, CORE_COMPONENT));
+ CHKiRet(objUse(prop, CORE_COMPONENT));
CHKiRet(objUse(net, LM_NET_FILENAME));
/* register config file handlers */
diff --git a/runtime/datetime.c b/runtime/datetime.c
index e0f3f5fa..ea67eec5 100644
--- a/runtime/datetime.c
+++ b/runtime/datetime.c
@@ -556,7 +556,6 @@ int formatTimestampToMySQL(struct syslogTime *ts, char* pBuf)
*/
assert(ts != NULL);
assert(pBuf != NULL);
- assert(iLenDst >= 15);
pBuf[0] = (ts->year / 1000) % 10 + '0';
pBuf[1] = (ts->year / 100) % 10 + '0';
@@ -582,7 +581,6 @@ int formatTimestampToPgSQL(struct syslogTime *ts, char *pBuf)
/* see note in formatTimestampToMySQL, applies here as well */
assert(ts != NULL);
assert(pBuf != NULL);
- assert(iLenDst >= 20);
pBuf[0] = (ts->year / 1000) % 10 + '0';
pBuf[1] = (ts->year / 100) % 10 + '0';
@@ -665,7 +663,6 @@ int formatTimestamp3339(struct syslogTime *ts, char* pBuf)
BEGINfunc
assert(ts != NULL);
assert(pBuf != NULL);
- assert(iLenBuf >= 33);
/* start with fixed parts */
/* year yyyy */
@@ -740,8 +737,6 @@ int formatTimestamp3164(struct syslogTime *ts, char* pBuf)
assert(ts != NULL);
assert(pBuf != NULL);
- assert(iLenBuf >= 16);
-
pBuf[0] = monthNames[(ts->month - 1)% 12][0];
pBuf[1] = monthNames[(ts->month - 1) % 12][1];
pBuf[2] = monthNames[(ts->month - 1) % 12][2];
diff --git a/runtime/datetime.h b/runtime/datetime.h
index 79a86d05..58f368e7 100644
--- a/runtime/datetime.h
+++ b/runtime/datetime.h
@@ -23,8 +23,6 @@
#ifndef INCLUDED_DATETIME_H
#define INCLUDED_DATETIME_H
-#include "datetime.h"
-
/* TODO: define error codes */
#define NO_ERRCODE -1
diff --git a/runtime/msg.c b/runtime/msg.c
index c4ba18df..47b4ed85 100644
--- a/runtime/msg.c
+++ b/runtime/msg.c
@@ -48,6 +48,7 @@
#include "atomic.h"
#include "unicode-helper.h"
#include "ruleset.h"
+#include "prop.h"
/* static data */
DEFobjStaticHelpers
@@ -55,6 +56,7 @@ DEFobjCurrIf(var)
DEFobjCurrIf(datetime)
DEFobjCurrIf(glbl)
DEFobjCurrIf(regexp)
+DEFobjCurrIf(prop)
static struct {
uchar *pszName;
@@ -273,12 +275,26 @@ static char *syslog_number_names[24] = { "0", "1", "2", "3", "4", "5", "6", "7",
/* some forward declarations */
static int getAPPNAMELen(msg_t *pM, bool bLockMutex);
+
static inline int getProtocolVersion(msg_t *pM)
{
return(pM->iProtocolVersion);
}
+static inline void
+getInputName(msg_t *pM, uchar **ppsz, int *plen)
+{
+ BEGINfunc
+ if(pM == NULL) {
+ *ppsz = UCHAR_CONSTANT("");
+ *plen = 0;
+ } else {
+ prop.GetString(pM->pInputName, ppsz, plen);
+ }
+ ENDfunc
+}
+
/* The following functions will support advanced output module
* multithreading, once this is implemented. Currently, we
* include them as hooks only. The idea is that we need to guard
@@ -431,7 +447,6 @@ static inline rsRetVal msgBaseConstruct(msg_t **ppThis)
pM->iFacility = -1;
pM->offAfterPRI = 0;
pM->offMSG = -1;
- pM->iLenInputName = 0;
pM->iProtocolVersion = 0;
pM->msgFlags = 0;
pM->iLenRawMsg = 0;
@@ -444,7 +459,6 @@ static inline rsRetVal msgBaseConstruct(msg_t **ppThis)
pM->pszHOSTNAME = NULL;
pM->pszRcvFrom = NULL;
pM->pszRcvFromIP = NULL;
- pM->pszInputName = NULL;
pM->pszRcvdAt3164 = NULL;
pM->pszRcvdAt3339 = NULL;
pM->pszRcvdAt_MySQL = NULL;
@@ -458,6 +472,7 @@ static inline rsRetVal msgBaseConstruct(msg_t **ppThis)
pM->pCSAPPNAME = NULL;
pM->pCSPROCID = NULL;
pM->pCSMSGID = NULL;
+ pM->pInputName = NULL;
pM->pRuleset = NULL;
memset(&pM->tRcvdAt, 0, sizeof(pM->tRcvdAt));
memset(&pM->tTIMESTAMP, 0, sizeof(pM->tTIMESTAMP));
@@ -556,7 +571,8 @@ CODESTARTobjDestruct(msg)
free(pThis->pszRawMsg);
freeTAG(pThis);
freeHOSTNAME(pThis);
- free(pThis->pszInputName);
+ if(pThis->pInputName != NULL)
+ prop.Destruct(&pThis->pInputName);
free(pThis->pszRcvFrom);
free(pThis->pszRcvFromIP);
free(pThis->pszRcvdAt3164);
@@ -719,11 +735,16 @@ msg_t* MsgDup(msg_t* pOld)
*/
static rsRetVal MsgSerialize(msg_t *pThis, strm_t *pStrm)
{
+ uchar *psz;
+ int len;
DEFiRet;
assert(pThis != NULL);
assert(pStrm != NULL);
+ /* "pump" some property values into strings */
+
+ /* then serialize elements */
CHKiRet(obj.BeginSerialize(pStrm, (obj_t*) pThis));
objSerializeSCALAR(pStrm, iProtocolVersion, SHORT);
objSerializeSCALAR(pStrm, iSeverity, SHORT);
@@ -743,7 +764,9 @@ static rsRetVal MsgSerialize(msg_t *pThis, strm_t *pStrm)
objSerializePTR(pStrm, pszRawMsg, PSZ);
objSerializePTR(pStrm, pszHOSTNAME, PSZ);
- objSerializePTR(pStrm, pszInputName, PSZ);
+ getInputName(pThis, &psz, &len);
+ objSerializeSCALAR_VAR(pStrm, "pszInputName", PSZ, psz);
+ //objSerializePTR(pStrm, pszInputName, PSZ);
objSerializePTR(pStrm, pszRcvFrom, PSZ);
objSerializePTR(pStrm, pszRcvFromIP, PSZ);
@@ -1427,18 +1450,6 @@ char *getHOSTNAME(msg_t *pM)
}
-static uchar *getInputName(msg_t *pM)
-{
- if(pM == NULL)
- return (uchar*) "";
- else
- if(pM->pszInputName == NULL)
- return (uchar*) "";
- else
- return pM->pszInputName;
-}
-
-
uchar *getRcvFrom(msg_t *pM)
{
if(pM == NULL)
@@ -1598,14 +1609,31 @@ static int getAPPNAMELen(msg_t *pM, bool bLockMutex)
/* rgerhards 2008-09-10: set pszInputName in msg object
* rgerhards, 2009-06-16
*/
-void MsgSetInputName(msg_t *pMsg, uchar* pszInputName, size_t lenInputName)
+void MsgSetInputName(msg_t *pThis, prop_t *inputName)
{
- assert(pMsg != NULL);
- free(pMsg->pszInputName);
- pMsg->iLenInputName = lenInputName;
- if((pMsg->pszInputName = malloc(pMsg->iLenInputName + 1)) != NULL) {
- memcpy(pMsg->pszInputName, pszInputName, pMsg->iLenInputName + 1);
- }
+ assert(pThis != NULL);
+
+ if(pThis->pInputName != NULL)
+ prop.Destruct(&pThis->pInputName);
+ pThis->pInputName = inputName;
+}
+
+/* to be removed soon: work-around for those tht can not natively generate an
+ * input name.
+ * rgerhards, 2009-06-29
+ */
+void MsgSetInputNameStr(msg_t *pThis, uchar *psz, int len)
+{
+ prop_t *pProp;
+ assert(pThis != NULL);
+
+ /* we need to create a property */
+ prop.Construct(&pProp);
+ prop.SetString(pProp, psz, len);
+ prop.ConstructFinalize(pProp);
+ prop.AddRef(pProp);
+ MsgSetInputName(pThis, pProp);
+ prop.Destruct(&pProp);
}
/* rgerhards 2004-11-16: set pszRcvFrom in msg object
@@ -1875,6 +1903,7 @@ char *MsgGetProp(msg_t *pMsg, struct templateEntry *pTpe,
short iOffs;
BEGINfunc
+dbgprintf("XXXX: msgGetProp for %d\n", propID);
assert(pMsg != NULL);
assert(pbMustBeFreed != NULL);
@@ -1910,7 +1939,10 @@ char *MsgGetProp(msg_t *pMsg, struct templateEntry *pTpe,
break;
*/
case PROP_INPUTNAME:
- pRes = (char*) getInputName(pMsg);
+RUNLOG;
+ getInputName(pMsg, ((uchar**) &pRes), &bufLen);
+RUNLOG;
+RUNLOG_VAR("%p", pRes);
break;
case PROP_FROMHOST:
pRes = (char*) getRcvFrom(pMsg);
@@ -2738,6 +2770,7 @@ rsRetVal propNameToID(cstr_t *pCSPropName, propid_t *pPropID)
#define isProp(name) !rsCStrSzStrCmp(pProp->pcsName, (uchar*) name, sizeof(name) - 1)
rsRetVal MsgSetProperty(msg_t *pThis, var_t *pProp)
{
+ prop_t *myProp;
DEFiRet;
ISOBJ_TYPE_assert(pThis, msg);
@@ -2765,7 +2798,13 @@ rsRetVal MsgSetProperty(msg_t *pThis, var_t *pProp)
} else if(isProp("pszTAG")) {
MsgSetTAG(pThis, rsCStrGetSzStrNoNULL(pProp->val.pStr), cstrLen(pProp->val.pStr));
} else if(isProp("pszInputName")) {
- MsgSetInputName(pThis, rsCStrGetSzStrNoNULL(pProp->val.pStr), rsCStrLen(pProp->val.pStr));
+ /* we need to create a property */
+ CHKiRet(prop.Construct(&myProp));
+ CHKiRet(prop.SetString(myProp, rsCStrGetSzStrNoNULL(pProp->val.pStr), rsCStrLen(pProp->val.pStr)));
+ CHKiRet(prop.ConstructFinalize(myProp));
+ prop.AddRef(myProp);
+ MsgSetInputName(pThis, myProp);
+ prop.Destruct(&myProp);
} else if(isProp("pszRcvFromIP")) {
MsgSetRcvFromIP(pThis, rsCStrGetSzStrNoNULL(pProp->val.pStr));
} else if(isProp("pszRcvFrom")) {
@@ -2790,6 +2829,7 @@ rsRetVal MsgSetProperty(msg_t *pThis, var_t *pProp)
dbgprintf("no longer supported property pszMSG silently ignored\n");
}
+finalize_it:
RETiRet;
}
#undef isProp
@@ -2833,6 +2873,7 @@ BEGINObjClassInit(msg, 1, OBJ_IS_CORE_MODULE)
CHKiRet(objUse(var, CORE_COMPONENT));
CHKiRet(objUse(datetime, CORE_COMPONENT));
CHKiRet(objUse(glbl, CORE_COMPONENT));
+ CHKiRet(objUse(prop, CORE_COMPONENT));
/* set our own handlers */
OBJSetMethodHandler(objMethod_SERIALIZE, MsgSerialize);
diff --git a/runtime/msg.h b/runtime/msg.h
index e6b25e6c..a1fc535b 100644
--- a/runtime/msg.h
+++ b/runtime/msg.h
@@ -72,7 +72,6 @@ struct msg {
short iFacility; /* Facility code 0 .. 23*/
short offAfterPRI; /* offset, at which raw message WITHOUT PRI part starts in pszRawMsg */
short offMSG; /* offset at which the MSG part starts in pszRawMsg */
- short iLenInputName; /* Length of pszInputName */
short iProtocolVersion;/* protocol version of message received 0 - legacy, 1 syslog-protocol) */
int msgFlags; /* flags associated with this message */
int iLenRawMsg; /* length of raw message */
@@ -86,7 +85,6 @@ struct msg {
uchar *pszHOSTNAME; /* HOSTNAME from syslog message */
uchar *pszRcvFrom; /* System message was received from */
uchar *pszRcvFromIP; /* IP of system message was received from */
- uchar *pszInputName; /* name of the input module that submitted this message */
char *pszRcvdAt3164; /* time as RFC3164 formatted string (always 15 charcters) */
char *pszRcvdAt3339; /* time as RFC3164 formatted string (32 charcters at most) */
char *pszRcvdAt_MySQL; /* rcvdAt as MySQL formatted string (always 14 charcters) */
@@ -100,6 +98,7 @@ struct msg {
cstr_t *pCSAPPNAME; /* APP-NAME */
cstr_t *pCSPROCID; /* PROCID */
cstr_t *pCSMSGID; /* MSGID */
+ prop_t *pInputName; /* input name property */
ruleset_t *pRuleset; /* ruleset to be used for processing this message */
time_t ttGenTime; /* time msg object was generated, same as tRcvdAt, but a Unix timestamp.
While this field looks redundant, it is required because a Unix timestamp
@@ -144,7 +143,7 @@ rsRetVal msgDestruct(msg_t **ppM);
msg_t* MsgDup(msg_t* pOld);
msg_t *MsgAddRef(msg_t *pM);
void setProtocolVersion(msg_t *pM, int iNewVersion);
-void MsgSetInputName(msg_t *pMsg, uchar*, size_t);
+void MsgSetInputName(msg_t *pMsg, prop_t*);
rsRetVal MsgSetAPPNAME(msg_t *pMsg, char* pszAPPNAME);
rsRetVal MsgSetPROCID(msg_t *pMsg, char* pszPROCID);
rsRetVal MsgSetMSGID(msg_t *pMsg, char* pszMSGID);
@@ -166,6 +165,12 @@ char *textpri(char *pRes, size_t pResLen, int pri);
rsRetVal msgGetMsgVar(msg_t *pThis, cstr_t *pstrPropName, var_t **ppVar);
rsRetVal MsgEnableThreadSafety(void);
+
+// REMOVE:
+void MsgSetInputNameStr(msg_t *pThis, uchar *psz, int len);
+
+
+
/* TODO: remove these five (so far used in action.c) */
char *getMSG(msg_t *pM);
char *getHOSTNAME(msg_t *pM);
diff --git a/runtime/prop.c b/runtime/prop.c
index 02be315f..989657dd 100644
--- a/runtime/prop.c
+++ b/runtime/prop.c
@@ -36,9 +36,12 @@
#include "config.h"
#include <stdlib.h>
#include <assert.h>
+#include <string.h>
#include "rsyslog.h"
#include "obj.h"
+#include "obj-types.h"
+#include "atomic.h"
#include "prop.h"
/* static data */
@@ -48,8 +51,45 @@ DEFobjStaticHelpers
/* Standard-Constructor
*/
BEGINobjConstruct(prop) /* be sure to specify the object type also in END macro! */
+ pThis->iRefCount = 1;
ENDobjConstruct(prop)
+/* set string, we make our own private copy! This MUST only be called BEFORE
+ * ConstructFinalize()!
+ */
+static rsRetVal SetString(prop_t *pThis, uchar *psz, int len)
+{
+ DEFiRet;
+ ISOBJ_TYPE_assert(pThis, prop);
+ if(pThis->len >= CONF_PROP_BUFSIZE)
+ free(pThis->szVal.psz);
+ pThis->len = len;
+ if(len < CONF_PROP_BUFSIZE) {
+ memcpy(pThis->szVal.sz, psz, len + 1);
+ } else {
+ CHKmalloc(pThis->szVal.psz = malloc(len + 1));
+ memcpy(pThis->szVal.sz, psz, len + 1);
+ }
+
+finalize_it:
+ RETiRet;
+}
+
+
+/* get string */
+static rsRetVal GetString(prop_t *pThis, uchar **ppsz, int *plen)
+{
+ BEGINfunc
+ ISOBJ_TYPE_assert(pThis, prop);
+ if(pThis->len < CONF_PROP_BUFSIZE)
+ *ppsz = pThis->szVal.sz;
+ else
+ *ppsz = pThis->szVal.psz;
+ *plen = pThis->len;
+ ENDfunc
+ return RS_RET_OK;
+}
+
/* ConstructionFinalizer
* rgerhards, 2008-01-09
@@ -63,9 +103,29 @@ propConstructFinalize(prop_t __attribute__((unused)) *pThis)
}
+/* add a new reference. It is VERY IMPORTANT to call this function whenever
+ * the property is handed over to some entitiy that later call Destruct() on it.
+ */
+static rsRetVal AddRef(prop_t *pThis)
+{
+ ATOMIC_INC(pThis->iRefCount);
+ return RS_RET_OK;
+}
+
+
/* destructor for the prop object */
BEGINobjDestruct(prop) /* be sure to specify the object type also in END and CODESTART macros! */
+ int currRefCount;
CODESTARTobjDestruct(prop)
+ currRefCount = ATOMIC_DEC_AND_FETCH(pThis->iRefCount);
+ if(currRefCount == 0) {
+ /* (only) in this case we need to actually destruct the object */
+dbgprintf("XXXXX: propDestruct: ptr %p, pThis %p, len %d\n", pThis->szVal.psz, pThis, pThis->len);
+ if(pThis->len >= CONF_PROP_BUFSIZE)
+ free(pThis->szVal.psz);
+ } else {
+ pThis = NULL; /* tell framework NOT to destructing the object! */
+ }
ENDobjDestruct(prop)
@@ -94,6 +154,9 @@ CODESTARTobjQueryInterface(prop)
pIf->ConstructFinalize = propConstructFinalize;
pIf->Destruct = propDestruct;
pIf->DebugPrint = propDebugPrint;
+ pIf->SetString = SetString;
+ pIf->GetString = GetString;
+ pIf->AddRef = AddRef;
finalize_it:
ENDobjQueryInterface(prop)
diff --git a/runtime/prop.h b/runtime/prop.h
index 7fc466b5..1d18c650 100644
--- a/runtime/prop.h
+++ b/runtime/prop.h
@@ -28,14 +28,23 @@
/* the prop object */
struct prop_s {
BEGINobjInstance; /* Data to implement generic object - MUST be the first data element! */
+ int iRefCount; /* reference counter */
+ union {
+ uchar *psz; /* stored string */
+ uchar sz[CONF_PROP_BUFSIZE];
+ } szVal;
+ int len; /* we use int intentionally, otherwise we may get some troubles... */
};
/* interfaces */
BEGINinterface(prop) /* name must also be changed in ENDinterface macro! */
INTERFACEObjDebugPrint(prop);
rsRetVal (*Construct)(prop_t **ppThis);
- rsRetVal (*ConstructFinalize)(prop_t __attribute__((unused)) *pThis);
+ rsRetVal (*ConstructFinalize)(prop_t *pThis);
rsRetVal (*Destruct)(prop_t **ppThis);
+ rsRetVal (*SetString)(prop_t *pThis, uchar* psz, int len);
+ rsRetVal (*GetString)(prop_t *pThis, uchar** ppsz, int *plen);
+ rsRetVal (*AddRef)(prop_t *pThis);
ENDinterface(prop)
#define propCURR_IF_VERSION 1 /* increment whenever you change the interface structure! */
diff --git a/runtime/rsyslog.c b/runtime/rsyslog.c
index 6f732f0e..faa74427 100644
--- a/runtime/rsyslog.c
+++ b/runtime/rsyslog.c
@@ -77,6 +77,7 @@
#include "conf.h"
#include "glbl.h"
#include "errmsg.h"
+#include "prop.h"
#include "rule.h"
#include "ruleset.h"
@@ -150,6 +151,8 @@ rsrtInit(char **ppErrObj, obj_if_t *pObjIF)
CHKiRet(glblClassInit(NULL));
if(ppErrObj != NULL) *ppErrObj = "datetime";
CHKiRet(datetimeClassInit(NULL));
+ if(ppErrObj != NULL) *ppErrObj = "prop";
+ CHKiRet(propClassInit(NULL));
if(ppErrObj != NULL) *ppErrObj = "msg";
CHKiRet(msgClassInit(NULL));
if(ppErrObj != NULL) *ppErrObj = "ctok_token";
diff --git a/runtime/rsyslog.h b/runtime/rsyslog.h
index 4e0f6e6c..8a043dde 100644
--- a/runtime/rsyslog.h
+++ b/runtime/rsyslog.h
@@ -39,6 +39,7 @@
#define CONF_RAWMSG_BUFSIZE 101
#define CONF_TAG_BUFSIZE 32
#define CONF_HOSTNAME_BUFSIZE 32
+#define CONF_PROP_BUFSIZE 16 /* should be close to sizeof(ptr) or lighly above it */
/* ############################################################# *
diff --git a/runtime/stringbuf.h b/runtime/stringbuf.h
index 400c74eb..c5130238 100644
--- a/runtime/stringbuf.h
+++ b/runtime/stringbuf.h
@@ -35,6 +35,7 @@
#ifndef _STRINGBUF_H_INCLUDED__
#define _STRINGBUF_H_INCLUDED__ 1
+#include <assert.h>
/**
* The dynamic string buffer object.
@@ -48,7 +49,6 @@ typedef struct cstr_s
uchar *pszBuf; /**< pointer to the sz version of the string (after it has been created )*/
size_t iBufSize; /**< current maximum size of the string buffer */
size_t iStrLen; /**< length of the string in characters. */
- bool bIsForeignBuf; /**< is pBuf a buffer provided by someone else? */
} cstr_t;
diff --git a/tcps_sess.c b/tcps_sess.c
index e0bec949..4786e154 100644
--- a/tcps_sess.c
+++ b/tcps_sess.c
@@ -45,6 +45,7 @@
#include "netstrm.h"
#include "msg.h"
#include "datetime.h"
+#include "prop.h"
/* static data */
@@ -52,6 +53,7 @@ DEFobjStaticHelpers
DEFobjCurrIf(glbl)
DEFobjCurrIf(errmsg)
DEFobjCurrIf(netstrm)
+DEFobjCurrIf(prop)
DEFobjCurrIf(datetime)
static int iMaxLine; /* maximum size of a single message */
@@ -234,9 +236,9 @@ defaultDoSubmitMessage(tcps_sess_t *pThis, struct syslogTime *stTime, time_t ttG
/* we now create our own message object and submit it to the queue */
CHKiRet(msgConstructWithTime(&pMsg, stTime, ttGenTime));
-dbgprintf("defaultDoSubmit, iMsg %d\n", pThis->iMsg);
MsgSetRawMsg(pMsg, (char*)pThis->pMsg, pThis->iMsg);
- MsgSetInputName(pMsg, pThis->pLstnInfo->pszInputName, pThis->pLstnInfo->lenInputName);
+ prop.AddRef(pThis->pLstnInfo->pInputName);
+ MsgSetInputName(pMsg, pThis->pLstnInfo->pInputName);
MsgSetFlowControlType(pMsg, eFLOWCTL_LIGHT_DELAY);
pMsg->msgFlags = NEEDS_PARSING | PARSE_HOSTNAME;
pMsg->bParseHOSTNAME = 1;
@@ -520,6 +522,7 @@ CODESTARTObjClassExit(tcps_sess)
objRelease(errmsg, CORE_COMPONENT);
objRelease(netstrm, LM_NETSTRMS_FILENAME);
objRelease(datetime, CORE_COMPONENT);
+ objRelease(prop, CORE_COMPONENT);
ENDObjClassExit(tcps_sess)
@@ -532,6 +535,7 @@ BEGINObjClassInit(tcps_sess, 1, OBJ_IS_CORE_MODULE) /* class, version - CHANGE c
CHKiRet(objUse(errmsg, CORE_COMPONENT));
CHKiRet(objUse(netstrm, LM_NETSTRMS_FILENAME));
CHKiRet(objUse(datetime, CORE_COMPONENT));
+ CHKiRet(objUse(prop, CORE_COMPONENT));
CHKiRet(objUse(glbl, CORE_COMPONENT));
iMaxLine = glbl.GetMaxLine(); /* get maximum size we currently support */
diff --git a/tcpsrv.c b/tcpsrv.c
index 119aea91..e8ea2b98 100644
--- a/tcpsrv.c
+++ b/tcpsrv.c
@@ -89,6 +89,7 @@ DEFobjCurrIf(net)
DEFobjCurrIf(netstrms)
DEFobjCurrIf(netstrm)
DEFobjCurrIf(nssel)
+DEFobjCurrIf(prop)
/* add new listener port to listener port list
@@ -107,8 +108,11 @@ addNewLstnPort(tcpsrv_t *pThis, uchar *pszPort)
pEntry->pszPort = pszPort;
pEntry->pSrv = pThis;
pEntry->pRuleset = pThis->pRuleset;
- CHKmalloc(pEntry->pszInputName = ustrdup(pThis->pszInputName));
- pEntry->lenInputName = ustrlen(pEntry->pszInputName);
+
+ /* we need to create a property */
+ CHKiRet(prop.Construct(&pEntry->pInputName));
+ CHKiRet(prop.SetString(pEntry->pInputName, pThis->pszInputName, ustrlen(pThis->pszInputName)));
+ CHKiRet(prop.ConstructFinalize(pEntry->pInputName));
/* and add to list */
pEntry->pNext = pThis->pLstnPorts;
@@ -250,7 +254,7 @@ static void deinit_tcp_listener(tcpsrv_t *pThis)
pEntry = pThis->pLstnPorts;
while(pEntry != NULL) {
free(pEntry->pszPort);
- free(pEntry->pszInputName);
+ prop.Destruct(&pEntry->pInputName);
pDel = pEntry;
pEntry = pEntry->pNext;
free(pDel);
@@ -477,6 +481,7 @@ Run(tcpsrv_t *pThis)
* this thread. Thus, we also need to instantiate a cancel cleanup handler
* to prevent us from leaking anything. -- rgerharsd, 20080-04-24
*/
+RUNLOG_STR("XXXX: tcp server runs\n");
pthread_cleanup_push(RunCancelCleanup, (void*) &pSel);
while(1) {
CHKiRet(nssel.Construct(&pSel));
@@ -497,6 +502,7 @@ Run(tcpsrv_t *pThis)
iTCPSess = TCPSessGetNxtSess(pThis, iTCPSess);
}
+RUNLOG_STR("XXXX: tcp server select\n");
/* wait for io to become ready */
CHKiRet(nssel.Wait(pSel, &nfds));
@@ -508,6 +514,7 @@ Run(tcpsrv_t *pThis)
--nfds; /* indicate we have processed one */
}
}
+RUNLOG_STR("XXXX: tcp server post select\n");
/* now check the sessions */
iTCPSess = TCPSessGetNxtSess(pThis, -1);
@@ -883,6 +890,7 @@ CODESTARTObjClassExit(tcpsrv)
/* release objects we no longer need */
objRelease(tcps_sess, DONT_LOAD_LIB);
objRelease(conf, CORE_COMPONENT);
+ objRelease(prop, CORE_COMPONENT);
objRelease(ruleset, CORE_COMPONENT);
objRelease(glbl, CORE_COMPONENT);
objRelease(errmsg, CORE_COMPONENT);
@@ -908,6 +916,7 @@ BEGINObjClassInit(tcpsrv, 1, OBJ_IS_LOADABLE_MODULE) /* class, version - CHANGE
CHKiRet(objUse(conf, CORE_COMPONENT));
CHKiRet(objUse(glbl, CORE_COMPONENT));
CHKiRet(objUse(ruleset, CORE_COMPONENT));
+ CHKiRet(objUse(prop, CORE_COMPONENT));
/* set our own handlers */
OBJSetMethodHandler(objMethod_DEBUGPRINT, tcpsrvDebugPrint);
diff --git a/tcpsrv.h b/tcpsrv.h
index e2170bef..70682398 100644
--- a/tcpsrv.h
+++ b/tcpsrv.h
@@ -23,6 +23,7 @@
#define INCLUDED_TCPSRV_H
#include "obj.h"
+#include "prop.h"
#include "tcps_sess.h"
/* support for framing anomalies */
@@ -36,8 +37,7 @@ typedef enum ETCPsyslogFramingAnomaly {
/* list of tcp listen ports */
struct tcpLstnPortList_s {
uchar *pszPort; /**< the ports the listener shall listen on */
- uchar *pszInputName; /**< value to be used as input name */
- size_t lenInputName; /**< length of inputName */
+ prop_t *pInputName;
tcpsrv_t *pSrv; /**< pointer to higher-level server instance */
ruleset_t *pRuleset; /**< associated ruleset */
tcpLstnPortList_t *pNext; /**< next port or NULL */
diff --git a/tests/nettester.c b/tests/nettester.c
index c9a978c5..dbfb4db3 100644
--- a/tests/nettester.c
+++ b/tests/nettester.c
@@ -128,11 +128,12 @@ tcpSend(char *buf, int lenBuf)
if(connect(sock, (struct sockaddr*)&addr, sizeof(addr)) == 0) {
break;
} else {
- if(retries++ == 3) {
+ if(retries++ == 30) {
+ ++iFailed;
fprintf(stderr, "connect() failed\n");
return(1);
} else {
- sleep(1);
+ usleep(100);
}
}
}
diff --git a/tools/syslogd.c b/tools/syslogd.c
index 3204d94e..2fe949ac 100644
--- a/tools/syslogd.c
+++ b/tools/syslogd.c
@@ -580,7 +580,7 @@ static inline rsRetVal printline(uchar *hname, uchar *hnameIP, uchar *msg, int f
CHKiRet(msgConstructWithTime(&pMsg, stTime, ttGenTime));
}
if(pszInputName != NULL)
- MsgSetInputName(pMsg, pszInputName, ustrlen(pszInputName));
+ MsgSetInputNameStr(pMsg, pszInputName, ustrlen(pszInputName));
MsgSetFlowControlType(pMsg, flowCtlType);
MsgSetRawMsgWOSize(pMsg, (char*)msg);
@@ -881,7 +881,7 @@ logmsgInternal(int iErr, int pri, uchar *msg, int flags)
DEFiRet;
CHKiRet(msgConstruct(&pMsg));
- MsgSetInputName(pMsg, UCHAR_CONSTANT("rsyslogd"), sizeof("rsyslogd")-1);
+ MsgSetInputNameStr(pMsg, UCHAR_CONSTANT("rsyslogd"), sizeof("rsyslogd")-1);
MsgSetRawMsgWOSize(pMsg, (char*)msg);
MsgSetHOSTNAME(pMsg, glbl.GetLocalHostName(), ustrlen(glbl.GetLocalHostName()));
MsgSetRcvFrom(pMsg, glbl.GetLocalHostName());
@@ -2089,6 +2089,7 @@ runInputModules(void)
{
modInfo_t *pMod;
+ BEGINfunc
/* loop through all modules and activate them (brr...) */
pMod = module.GetNxtType(NULL, eMOD_IN);
while(pMod != NULL) {