diff options
author | Alexander Bluhm <bluhm@cvs.openbsd.org> | 2019-07-02 13:17:28 +0000 |
---|---|---|
committer | Alexander Bluhm <bluhm@cvs.openbsd.org> | 2019-07-02 13:17:28 +0000 |
commit | 88a75432bbc224b7e7b736a0c33a9fde086c3433 (patch) | |
tree | 2ae7e4cc51a016af8ef66f609c05dd1fa804cd17 | |
parent | 7a45a8e363a4d336140980ca45165be8481f4d85 (diff) |
React properly to the very unlikely cases where snprintf(3) may
fail. Log the message without formating, that is the best syslogd(8)
can do.
OK deraadt@
-rw-r--r-- | usr.sbin/syslogd/syslogd.c | 48 |
1 files changed, 35 insertions, 13 deletions
diff --git a/usr.sbin/syslogd/syslogd.c b/usr.sbin/syslogd/syslogd.c index cd3ce8cc63a..b84454987d9 100644 --- a/usr.sbin/syslogd/syslogd.c +++ b/usr.sbin/syslogd/syslogd.c @@ -1,4 +1,4 @@ -/* $OpenBSD: syslogd.c,v 1.260 2019/06/28 13:32:51 deraadt Exp $ */ +/* $OpenBSD: syslogd.c,v 1.261 2019/07/02 13:17:27 bluhm Exp $ */ /* * Copyright (c) 2014-2017 Alexander Bluhm <bluhm@genua.de> @@ -1639,9 +1639,14 @@ printsys(char *msg) int c, pri, flags; char *lp, *p, *q, line[LOG_MAXLINE + 1]; size_t prilen; + int l; - (void)snprintf(line, sizeof line, "%s: ", _PATH_UNIX); - lp = line + strlen(line); + l = snprintf(line, sizeof(line), "%s: ", _PATH_UNIX); + if (l < 0 || l >= sizeof(line)) { + line[0] = '\0'; + l = 0; + } + lp = line + l; for (p = msg; *p != '\0'; ) { flags = SYNC_FILE | ADDDATE; /* fsync file after write */ pri = DEFSPRI; @@ -1666,11 +1671,15 @@ void vlogmsg(int pri, const char *proc, const char *fmt, va_list ap) { char msg[ERRBUFSIZE]; - size_t l; + int l; l = snprintf(msg, sizeof(msg), "%s[%d]: ", proc, getpid()); - if (l < sizeof(msg)) - vsnprintf(msg + l, sizeof(msg) - l, fmt, ap); + if (l < 0 || l >= sizeof(msg)) + l = 0; + l = vsnprintf(msg + l, sizeof(msg) - l, fmt, ap); + if (l < 0) + strlcpy(msg, fmt, sizeof(msg)); + if (!Started) { fprintf(stderr, "%s\n", msg); init_dropped++; @@ -1908,8 +1917,12 @@ fprintlog(struct filed *f, int flags, char *msg) l = snprintf(greetings, sizeof(greetings), "\r\n\7Message from syslogd@%s at %.24s ...\r\n", f->f_prevhost, ctime(&now.tv_sec)); - if (l < 0 || (size_t)l >= sizeof(greetings)) - l = strlen(greetings); + if (l < 0) + l = strlcpy(greetings, + "\r\n\7Message from syslogd ...\r\n", + sizeof(greetings)); + if (l >= sizeof(greetings)) + l = sizeof(greetings) - 1; v->iov_base = greetings; v->iov_len = l; v++; @@ -1953,8 +1966,11 @@ fprintlog(struct filed *f, int flags, char *msg) } else if (f->f_prevcount > 1) { l = snprintf(repbuf, sizeof(repbuf), "last message repeated %d times", f->f_prevcount); - if (l < 0 || (size_t)l >= sizeof(repbuf)) - l = strlen(repbuf); + if (l < 0) + l = strlcpy(repbuf, "last message repeated", + sizeof(repbuf)); + if (l >= sizeof(repbuf)) + l = sizeof(repbuf) - 1; v->iov_base = repbuf; v->iov_len = l; } else { @@ -1978,8 +1994,12 @@ fprintlog(struct filed *f, int flags, char *msg) IncludeHostname ? LocalHostName : "", IncludeHostname ? " " : "", (char *)iov[4].iov_base); - if (l < 0 || (size_t)l > MINIMUM(MAX_UDPMSG, sizeof(line))) - l = MINIMUM(MAX_UDPMSG, sizeof(line)); + if (l < 0) + l = strlcpy(line, iov[4].iov_base, sizeof(line)); + if (l >= sizeof(line)) + l = sizeof(line) - 1; + if (l >= MAX_UDPMSG + 1) + l = MAX_UDPMSG; if (sendto(f->f_file, line, l, 0, (struct sockaddr *)&f->f_un.f_forw.f_addr, f->f_un.f_forw.f_addr.ss_len) != l) { @@ -2149,9 +2169,11 @@ fprintlog(struct filed *f, int flags, char *msg) case F_MEMBUF: log_debug("%s", ""); - snprintf(line, sizeof(line), "%.32s %s %s", + l = snprintf(line, sizeof(line), "%.32s %s %s", (char *)iov[0].iov_base, (char *)iov[2].iov_base, (char *)iov[4].iov_base); + if (l < 0) + l = strlcpy(line, iov[4].iov_base, sizeof(line)); if (ringbuf_append_line(f->f_un.f_mb.f_rb, line) == 1) f->f_un.f_mb.f_overflow = 1; if (f->f_un.f_mb.f_attached) |