From 5f76568d3707cbbadfa3767558ded52cf5f27f47 Mon Sep 17 00:00:00 2001 From: Rainer Gerhards Date: Fri, 4 Sep 2009 16:58:00 +0200 Subject: added new config option $InputUnixListenSocketCreatePath backport from v5-devel --- ChangeLog | 5 +++++ doc/imuxsock.html | 28 ++++++++++++++++++++++++++-- plugins/imuxsock/imuxsock.c | 14 ++++++++++++-- 3 files changed, 43 insertions(+), 4 deletions(-) diff --git a/ChangeLog b/ChangeLog index cbfb597b..34406f4a 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,5 +1,10 @@ --------------------------------------------------------------------------- Version 4.7.0 [v4-devel] (rgerhards), 2009-09-?? +- added new config option $InputUnixListenSocketCreatePath + to permit the auto-creation of pathes to additional log sockets. This + turns out to be useful if they reside on temporary file systems and + rsyslogd starts up before the daemons that create these sockets + (rsyslogd always creates the socket itself if it does not exist). - added $LogRSyslogStatusMessages configuration directive permitting to turn off rsyslog start/stop/HUP messages. See Debian ticket http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=463793 diff --git a/doc/imuxsock.html b/doc/imuxsock.html index 472470a0..15c365a6 100644 --- a/doc/imuxsock.html +++ b/doc/imuxsock.html @@ -46,6 +46,18 @@ Ignore timestamps included in the messages, applies to messages received via the
  • $SystemLogSocketName <name-of-socket> -- former -p option
  • $SystemLogFlowControl [on/off] - specifies if flow control should be applied to the system log socket.
  • +
  • $InputUnixListenSocketCreatePath [on/off] - create directories in the socket path +if they do not already exist. They are created with 0755 permissions with the owner being the process under +which rsyslogd runs. The default is not to create directories. Keep in mind, though, that rsyslogd always +creates the socket itself if it does not exist (just not the directories by default). +
    Note that this statement affects the +next $AddUnixListenSocket directive that follows in sequence in the configuration file. It never works +on the system log socket (where it is deemed unnecessary). Also note that it is automatically +being reset to "off" after the $AddUnixListenSocket directive, so if you would have it active +for two additional listen sockets, you need to specify it in front of each one. This option is primarily considered +useful for defining additional sockets that reside on non-permanent file systems. As rsyslogd probably starts +up before the daemons that create these sockets, it is a vehicle to enable rsyslogd to listen to those +sockets even though their directories do not yet exist. [available since 4.7.0 and 5.3.0]
  • $AddUnixListenSocket <name-of-socket> adds additional unix socket, default none -- former -a option
  • $InputUnixListenSocketHostName <hostname> permits to override the hostname that shall be used inside messages taken from the next $AddUnixListenSocket socket. Note that @@ -57,20 +69,32 @@ that the local hostname can be overridden in cases where that is desired.

  • This documentation is sparse and incomplete.

    Sample:

    -

    The following sample is the minimum setup required to accept syslog messages from applications running on the local system.
    +

    The following sample is the minimum setup required to accept syslog messages from applications running +on the local system.

    The following sample is a configuration where rsyslogd pulls logs from two jails, and assigns different hostnames to each of the jails:

    - +

    The following sample is a configuration where rsyslogd reads the openssh log +messages via a separate socket, but this socket is created on a temporary file +system. As rsyslogd starts up before the sshd, it needs to create the socket +directories, because it otherwise can not open the socket and thus not listen +to openssh messages. Note that it is vital not to place any other socket between +the $InputUnixListenSocketCreatePath and the $InputUnixListenSocketHostName.

    +

    [rsyslog.conf overview] [manual index] [rsyslog site]

    This documentation is part of the diff --git a/plugins/imuxsock/imuxsock.c b/plugins/imuxsock/imuxsock.c index 424d0904..c5fb0cc8 100644 --- a/plugins/imuxsock/imuxsock.c +++ b/plugins/imuxsock/imuxsock.c @@ -77,6 +77,7 @@ static int startIndexUxLocalSockets; /* process funix from that index on (used t */ static int funixParseHost[MAXFUNIX] = { 0, }; /* should parser parse host name? read-only after startup */ static int funixFlags[MAXFUNIX] = { IGNDATE, }; /* should parser parse host name? read-only after startup */ +static int funixCreateSockPath[MAXFUNIX] = { 0, }; /* auto-creation of socket directory? */ static uchar *funixn[MAXFUNIX] = { (uchar*) _PATH_LOG }; /* read-only after startup */ static uchar *funixHName[MAXFUNIX] = { NULL, }; /* host-name override - if set, use this instead of actual name */ static int funixFlowCtl[MAXFUNIX] = { eFLOWCTL_NO_DELAY, }; /* flow control settings for this socket */ @@ -89,6 +90,8 @@ static uchar *pLogSockName = NULL; static uchar *pLogHostName = NULL; /* host name to use with this socket */ static int bUseFlowCtl = 0; /* use flow control or not (if yes, only LIGHT is used! */ static int bIgnoreTimestamp = 1; /* ignore timestamps present in the incoming message? */ +#define DFLT_bCreateSockPath 0 +static int bCreateSockPath = DFLT_bCreateSockPath; /* auto-create socket path? */ /* set the timestamp ignore / not ignore option for the system @@ -132,6 +135,7 @@ static rsRetVal addLstnSocketName(void __attribute__((unused)) *pVal, uchar *pNe pLogHostName = NULL; /* re-init for next, not freed because funixHName[] now owns it */ funixFlowCtl[nfunix] = bUseFlowCtl ? eFLOWCTL_LIGHT_DELAY : eFLOWCTL_NO_DELAY; funixFlags[nfunix] = bIgnoreTimestamp ? IGNDATE : NOFLAG; + funixCreateSockPath[nfunix] = bCreateSockPath; funixn[nfunix++] = pNewVal; } else { @@ -165,7 +169,7 @@ static rsRetVal discardFunixn(void) } -static int create_unix_socket(const char *path) +static int create_unix_socket(const char *path, int bCreatePath) { struct sockaddr_un sunx; int fd; @@ -177,6 +181,9 @@ static int create_unix_socket(const char *path) memset(&sunx, 0, sizeof(sunx)); sunx.sun_family = AF_UNIX; + if(bCreatePath) { + makeFileParentDirs((uchar*)path, strlen(path), 0755, -1, -1, 0); + } (void) strncpy(sunx.sun_path, path, sizeof(sunx.sun_path)); fd = socket(AF_UNIX, SOCK_DGRAM, 0); if (fd < 0 || bind(fd, (struct sockaddr *) &sunx, SUN_LEN(&sunx)) < 0 || @@ -306,7 +313,7 @@ CODESTARTwillRun /* initialize and return if will run or not */ for (i = startIndexUxLocalSockets ; i < nfunix ; i++) { - if ((funix[i] = create_unix_socket((char*) funixn[i])) != -1) + if ((funix[i] = create_unix_socket((char*) funixn[i], funixCreateSockPath[i])) != -1) dbgprintf("Opened UNIX socket '%s' (fd %d).\n", funixn[i], funix[i]); } @@ -376,6 +383,7 @@ static rsRetVal resetConfigVariables(uchar __attribute__((unused)) *pp, void __a nfunix = 1; bIgnoreTimestamp = 1; bUseFlowCtl = 0; + bCreateSockPath = DFLT_bCreateSockPath; return RS_RET_OK; } @@ -409,6 +417,8 @@ CODEmodInit_QueryRegCFSLineHdlr NULL, &pLogHostName, STD_LOADABLE_MODULE_ID)); CHKiRet(omsdRegCFSLineHdlr((uchar *)"inputunixlistensocketflowcontrol", 0, eCmdHdlrBinary, NULL, &bUseFlowCtl, STD_LOADABLE_MODULE_ID)); + CHKiRet(omsdRegCFSLineHdlr((uchar *)"inputunixlistensocketcreatepath", 0, eCmdHdlrBinary, + NULL, &bCreateSockPath, STD_LOADABLE_MODULE_ID)); CHKiRet(omsdRegCFSLineHdlr((uchar *)"addunixlistensocket", 0, eCmdHdlrGetWord, addLstnSocketName, NULL, STD_LOADABLE_MODULE_ID)); CHKiRet(omsdRegCFSLineHdlr((uchar *)"resetconfigvariables", 1, eCmdHdlrCustomHandler, -- cgit v1.2.3 From bfac3c68f47b8769b0936fb80eeea8880793fd2d Mon Sep 17 00:00:00 2001 From: Rainer Gerhards Date: Fri, 11 Sep 2009 11:23:47 +0200 Subject: added new config directive $omfileForceChown to fix some broken system configs. See ticket for details: http://bugzilla.adiscon.com/show_bug.cgi?id=150 --- ChangeLog | 3 ++ doc/rsconf1_omfileforcechown.html | 64 +++++++++++++++++++++++++++++++++++++++ doc/rsyslog_conf_global.html | 1 + tools/omfile.c | 27 +++++++++++++++-- 4 files changed, 93 insertions(+), 2 deletions(-) create mode 100644 doc/rsconf1_omfileforcechown.html diff --git a/ChangeLog b/ChangeLog index 5b30621b..7ae02fd8 100644 --- a/ChangeLog +++ b/ChangeLog @@ -8,6 +8,9 @@ Version 4.7.0 [v4-devel] (rgerhards), 2009-09-?? - added $LogRSyslogStatusMessages configuration directive permitting to turn off rsyslog start/stop/HUP messages. See Debian ticket http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=463793 +- added new config directive $omfileForceChown to (try to) fix some broken + system configs. + See ticket for details: http://bugzilla.adiscon.com/show_bug.cgi?id=150 --------------------------------------------------------------------------- Version 4.5.3 [v4-beta] (rgerhards), 2009-08-?? - bugfix: repeated messages were incorrectly processed diff --git a/doc/rsconf1_omfileforcechown.html b/doc/rsconf1_omfileforcechown.html new file mode 100644 index 00000000..7415a6f6 --- /dev/null +++ b/doc/rsconf1_omfileforcechown.html @@ -0,0 +1,64 @@ + + +rsyslog.conf file + + +back + +

    $omfileForceChown

    +

    Type: global configuration directive

    +

    Parameter Values: boolean (on/off, yes/no)

    +

    Available since: 4.7.0+, 5.3.0+

    +

    Default: off

    +

    Description:

    +

    Forces rsyslogd to change the ownership for output files that already exist. Please note +that this tries to fix a potential problem that exists outside the scope of rsyslog. Actually, +it tries to fix invalid ownership/permission settings set by the original file creator. +

    Rsyslog changes the ownership during initial execution with root privileges. When a privelege +drop is configured, privileges are dropped after the file owner ship is changed. Not that this currently +is a limitation in rsyslog's privilege drop code, which is on the TODO list to be removed. See Caveats +section below for the important implications. +

    Caveats:

    +

    This directive tries to fix a problem that actually is outside the scope of rsyslog. As such, +there are a couple of restrictions and situations in which it will not work. Users are strongly +encouraged to fix their system instead of turning this directive on - it should only be used +as a last resort. +

    At least in the following scenario, this directive will fail expectedly: +

    It does not address +the situation that someone changes the ownership *after* rsyslogd has started. +Let's, for example, consider a log rotation script. +

    + +Please note that once the privilege drop code is refactored, this directive will +no longer work, because then privileges will be dropped before any action is performed, +and thus we will no longer be able to chown files that do not belong to the +user rsyslogd is configured to run under. + +

    So expect the directive to go away. It will not +be removed in version 4, but may disappear at any time for any version greater than 4. + +

    Sample:

    +

    $FileOwner loguser +
    $omfileForceChown on

    + +

    [rsyslog.conf overview] [manual +index] [rsyslog site]

    +

    This documentation is part of the +rsyslog project.
    +Copyright © 2007 by Rainer Gerhards and +Adiscon. Released under the GNU GPL +version 2 or higher.

    + + diff --git a/doc/rsyslog_conf_global.html b/doc/rsyslog_conf_global.html index 74255c54..5f80f92e 100644 --- a/doc/rsyslog_conf_global.html +++ b/doc/rsyslog_conf_global.html @@ -225,6 +225,7 @@ error recovery thus can handle write errors without data loss. Note that this op severely reduces the effect of zip compression and should be switched to off for that use case. Note that the default -off- is primarily an aid to preserve the traditional syslogd behaviour. +
  • $omfileForceChown - force ownership change for all files
  • $RepeatedMsgContainsOriginalMsg [on/off] - "last message repeated n times" messages, if generated, have a different format that contains the message that is being repeated. Note that only the first "n" characters are included, with n to be at least 80 characters, most diff --git a/tools/omfile.c b/tools/omfile.c index bb12b4b6..eaffa70e 100644 --- a/tools/omfile.c +++ b/tools/omfile.c @@ -88,11 +88,13 @@ typedef struct s_dynaFileCacheEntry dynaFileCacheEntry; #define IOBUF_DFLT_SIZE 1024 /* default size for io buffers */ #define FLUSH_INTRVL_DFLT 1 /* default buffer flush interval (in seconds) */ +#define DFLT_bForceChown 0 /* globals for default values */ static int iDynaFileCacheSize = 10; /* max cache for dynamic files */ static int fCreateMode = 0644; /* mode to use when creating files */ static int fDirCreateMode = 0700; /* mode to use when creating files */ static int bFailOnChown; /* fail if chown fails? */ +static int bForceChown = DFLT_bForceChown; /* Force chown() on existing files? */ static uid_t fileUID; /* UID to be used for newly created files */ static uid_t fileGID; /* GID to be used for newly created files */ static uid_t dirUID; /* UID to be used for newly created directories */ @@ -115,6 +117,7 @@ typedef struct _instanceData { int fDirCreateMode; /* creation mode for mkdir() */ int bCreateDirs; /* auto-create directories? */ int bSyncFile; /* should the file by sync()'ed? 1- yes, 0- no */ + bool bForceChown; /* force chown() on existing files? */ uid_t fileUID; /* IDs for creation */ uid_t dirUID; gid_t fileGID; @@ -152,12 +155,14 @@ CODESTARTdbgPrintInstInfo "\tcreate directories: %s\n" "\tfile owner %d, group %d\n" "\tdirectory owner %d, group %d\n" + "\tforce chown() for all files: %s\n" "\tfail if owner/group can not be set: %s\n", pData->f_fname, pData->iDynaFileCacheSize, pData->bCreateDirs ? "yes" : "no", pData->fileUID, pData->fileGID, pData->dirUID, pData->dirGID, + pData->bForceChown ? "yes" : "no", pData->bFailOnChown ? "yes" : "no" ); } else { /* regular file */ @@ -346,7 +351,22 @@ prepareFile(instanceData *pData, uchar *newFileName) int fd; DEFiRet; - if(access((char*)newFileName, F_OK) != 0) { + if(access((char*)newFileName, F_OK) == 0) { + if(pData->bForceChown) { + /* Try to fix wrong ownership set by someone else. Note that this code + * will no longer work once we have made the $PrivDrop code fully secure. + * This change is based on an idea of Michael Terry, provided as part of + * the effort to make rsyslogd the Ubuntu default syslogd. + * rgerhards, 2009-09-11 + */ + if(chown((char*)newFileName, pData->fileUID, pData->fileGID) != 0) { + if(pData->bFailOnChown) { + int eSave = errno; + errno = eSave; + } + } + } + } else { /* file does not exist, create it (and eventually parent directories */ fd = -1; if(pData->bCreateDirs) { @@ -367,7 +387,7 @@ prepareFile(instanceData *pData, uchar *newFileName) pData->fCreateMode); if(fd != -1) { /* check and set uid/gid */ - if(pData->fileUID != (uid_t)-1 || pData->fileGID != (gid_t) -1) { + if(pData->bForceChown || pData->fileUID != (uid_t)-1 || pData->fileGID != (gid_t) -1) { /* we need to set owner/group */ if(fchown(fd, pData->fileUID, pData->fileGID) != 0) { if(pData->bFailOnChown) { @@ -678,6 +698,7 @@ CODESTARTparseSelectorAct pData->fDirCreateMode = fDirCreateMode; pData->bCreateDirs = bCreateDirs; pData->bFailOnChown = bFailOnChown; + pData->bForceChown = bForceChown; pData->fileUID = fileUID; pData->fileGID = fileGID; pData->dirUID = dirUID; @@ -712,6 +733,7 @@ static rsRetVal resetConfigVariables(uchar __attribute__((unused)) *pp, void __a dirUID = -1; dirGID = -1; bFailOnChown = 1; + bForceChown = DFLT_bForceChown; iDynaFileCacheSize = 10; fCreateMode = 0644; fDirCreateMode = 0700; @@ -778,6 +800,7 @@ CODEmodInit_QueryRegCFSLineHdlr CHKiRet(omsdRegCFSLineHdlr((uchar *)"filecreatemode", 0, eCmdHdlrFileCreateMode, NULL, &fCreateMode, STD_LOADABLE_MODULE_ID)); CHKiRet(omsdRegCFSLineHdlr((uchar *)"createdirs", 0, eCmdHdlrBinary, NULL, &bCreateDirs, STD_LOADABLE_MODULE_ID)); CHKiRet(omsdRegCFSLineHdlr((uchar *)"failonchownfailure", 0, eCmdHdlrBinary, NULL, &bFailOnChown, STD_LOADABLE_MODULE_ID)); + CHKiRet(omsdRegCFSLineHdlr((uchar *)"omfileForceChown", 0, eCmdHdlrBinary, NULL, &bForceChown, STD_LOADABLE_MODULE_ID)); CHKiRet(omsdRegCFSLineHdlr((uchar *)"actionfileenablesync", 0, eCmdHdlrBinary, NULL, &bEnableSync, STD_LOADABLE_MODULE_ID)); CHKiRet(regCfSysLineHdlr((uchar *)"actionfiledefaulttemplate", 0, eCmdHdlrGetWord, NULL, &pszTplName, NULL)); CHKiRet(omsdRegCFSLineHdlr((uchar *)"resetconfigvariables", 1, eCmdHdlrCustomHandler, resetConfigVariables, NULL, STD_LOADABLE_MODULE_ID)); -- cgit v1.2.3