Consolidate option parsing for syslog.conf rules

This patch changes the syntax for per-rule log rotation and makes it
possible to have enable log rotation and RFC5424 output formatting.

The new syntax looks like this:

    	EXPR		ACTION			;OPT,OPT,...

Example:

	*.notice	-/var/log/messages	;rotate=1M:5,RFC5424

Signed-off-by: Joachim Nilsson <troglobit@gmail.com>
This commit is contained in:
Joachim Nilsson 2019-11-03 12:15:05 +01:00
parent 4066a1e9bf
commit 84aa897628
2 changed files with 103 additions and 51 deletions

View File

@ -38,20 +38,38 @@ Every rule has at least two fields, a
.Em selector
field and an
.Em action .
They may also have an optional flag or setting that applies only to
that rule. E.g,
.Em logrotate
settings or output format flag. A rule may be divided into several
lines if the leading line ends with a single backslash ('\\') character.
They may also have an
.Em option
field for a setting that applies only to that rule. Fields are
separated by one or more spaces or tabs. A rule may be divided into
several lines if the leading line ends with a single backslash ('\\')
character.
.Bd -literal -offset indent
RULE := SELECTOR ACTION [;OPTION]
SELECTOR := [SELECTOR;]facility[,facility].[!=]severity
ACTION := /path/to/file
|= |/path/to/named/pipe
|= @remote[.host.tld]
OPTION := [OPTION,]
|= RFC3164
|= RFC5424
|= rotate=SIZE:COUNT
.Ed
.Pp
The fields are separated by one or more spaces or tabs. The
selector field specifies a pattern of facilities and priorities
belonging to the specified action. The action details where or what to
do with the selected input. The optional logrotate field is only for
files and details the max SIZE:COUNT a file can reach before it is
rotated, and later compressed. The log rotated feature is mostly
intended for embedded systems that do not want to have cron and a
separate log rotate daemon.
The
.Em selector
field specifies a pattern of facilities and priorities belonging to the
specified action. The
.Em action
details where or what to do with the selected input. The
.Em option
field currently supports log formattaing and log rotation. The default
log format is the traditional RFC3164 (included here for completeness),
RFC5424 has a new format with RFC3339 time stamps, msgid, structured
data, and more. The log rotation, which is only relevant for files,
details the max SIZE:COUNT a file can reach before it is rotated, and
later compressed. This feature is mostly intended for embedded systems
that do not want to have cron or a separate log rotate daemon.
.Pp
Comments, lines starting with a hash mark ('#'), and empty lines are
ignored. If an error occurs during parsing the whole line is ignored.
@ -272,6 +290,17 @@ that something strange is happening with the system. To specify this
feature use an asterisk ('*').
.Sh EXAMPLES
This section lists some examples, partially from actual site setups.
.Ss Catch Everything
This example matches all facilities and priorities and stores everything
in the file
.Pa /var/log/syslog
in RFC5424 format. Every time the file reaches 10 MiB it is rotated and
five files in total are kept, including the non-rotated file.
.Bd -literal -offset indent
# Match all log messages, store in RC5424 format and rotate every 10 MiB
#
*.* /var/log/critical ;rotate=10M:5,RFC5424
.Ed
.Ss Critical
This stores all messages of priority
.Ql crit
@ -437,10 +466,10 @@ argument takes the same modifiers as the
command line option,
.Fl R .
.Bd -literal -offset indent
# Log all messages, including kernel, to messages file
# rotated every 100 kB and keep up to 10 aged out and
# compressed files.
*.*;kern.none -/log/messages 100k:10
# Log all messages, including kernel, to messages file rotated
# every 100 kB and keep up to 10 aged out and compressed files
#
*.*;kern.none -/var/log/messages ;rotate=100k:10
.Ed
.Ss Logging to Remote Syslog Server
This rule redirects all messages to a remote host called
@ -449,7 +478,7 @@ with RFC5424 style formatting. This is useful especially in a cluster
of machines where all syslog messages will be stored on only one
machine.
.Bd -literal -offset indent
*.* @finlandia;RFC5424
*.* @finlandia ;RFC5424
.Ed
.Sh FILES
.Bl -tag -compact -width /etc/syslog.d/*.conf

View File

@ -2437,6 +2437,59 @@ void init(void)
logit("syslogd: restarted.\n");
}
static void cfrot(char *ptr, struct filed *f)
{
char *c;
int sz = 0, cnt = 0;
c = strchr(ptr, ':');
if (c) {
*c++ = 0;
cnt = atoi(c);
}
sz = strtobytes(ptr);
if (sz > 0 && cnt > 0) {
logit("Set rotate size %d bytes, %d rotations\n", sz, cnt);
f->f_rotatecount = cnt;
f->f_rotatesz = sz;
}
}
static int cfopt(char **ptr, const char *opt)
{
size_t len;
len = strlen(opt);
if (!strncasecmp(*ptr, opt, len)) {
logit("Found %s\n", opt);
*ptr += len;
return 1;
}
return 0;
}
/*
* Option processing
*/
static void cfopts(char *ptr, struct filed *f)
{
char *opt;
opt = strtok(ptr, ";");
while (opt) {
if (cfopt(&opt, "RFC5424"))
f->f_flags |= RFC5424;
else if (cfopt(&opt, "RFC3164"))
f->f_flags &= ~RFC5424;
else if (cfopt(&opt, "rotate="))
cfrot(opt, f);
opt = strtok(NULL, ",");
}
}
/*
* Crack a configuration file line
*/
@ -2595,16 +2648,8 @@ static struct filed *cfline(char *line)
logit("leading char in action: %c\n", *p);
switch (*p) {
case '@':
bp = p;
while ((q = strchr(bp, ';'))) {
*q++ = 0;
if (q) {
if (!strncmp(q, "RFC5424", 7))
f->f_flags |= RFC5424;
/* More flags can be added here */
}
bp = q;
}
cfopts(p, f);
(void)strcpy(f->f_un.f_forw.f_hname, ++p);
logit("forwarding host: %s\n", p); /*ASP*/
memset(&hints, 0, sizeof(hints));
@ -2629,29 +2674,7 @@ static struct filed *cfline(char *line)
case '|':
case '/':
/* Look for optional per-file rotate BYTES:COUNT */
for (q = p; *q && !isspace(*q); q++)
;
if (isspace(*q)) {
char *c;
int sz = 0, cnt = 0;
*q++ = 0;
while (*q && isspace(*q))
q++;
c = strchr(q, ':');
if (c) {
*c++ = 0;
cnt = atoi(c);
}
sz = strtobytes(q);
if (sz > 0 && cnt > 0) {
f->f_rotatecount = cnt;
f->f_rotatesz = sz;
}
}
cfopts(p, f);
(void)strcpy(f->f_un.f_fname, p);
logit("filename: %s\n", p); /*ASP*/