xref: /openbsd/usr.sbin/radiusd/log.c (revision 592c444d)
1*592c444dSbluhm /*	$OpenBSD: log.c,v 1.2 2017/03/29 18:01:51 bluhm Exp $ */
2a7ca44b8Syasuoka 
3a7ca44b8Syasuoka /*
4a7ca44b8Syasuoka  * Copyright (c) 2003, 2004 Henning Brauer <henning@openbsd.org>
5a7ca44b8Syasuoka  *
6a7ca44b8Syasuoka  * Permission to use, copy, modify, and distribute this software for any
7a7ca44b8Syasuoka  * purpose with or without fee is hereby granted, provided that the above
8a7ca44b8Syasuoka  * copyright notice and this permission notice appear in all copies.
9a7ca44b8Syasuoka  *
10a7ca44b8Syasuoka  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11a7ca44b8Syasuoka  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
12a7ca44b8Syasuoka  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
13a7ca44b8Syasuoka  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
14*592c444dSbluhm  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
15*592c444dSbluhm  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
16*592c444dSbluhm  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
17a7ca44b8Syasuoka  */
18a7ca44b8Syasuoka 
19a7ca44b8Syasuoka #include <errno.h>
20a7ca44b8Syasuoka #include <stdarg.h>
21a7ca44b8Syasuoka #include <stdio.h>
22a7ca44b8Syasuoka #include <stdlib.h>
23a7ca44b8Syasuoka #include <string.h>
24a7ca44b8Syasuoka #include <syslog.h>
25a7ca44b8Syasuoka #include <time.h>
26a7ca44b8Syasuoka 
27a7ca44b8Syasuoka #include "log.h"
28a7ca44b8Syasuoka 
29a7ca44b8Syasuoka int		 log_debug_use_syslog = 0;
30a7ca44b8Syasuoka static int	 log_initialized = 0;
31a7ca44b8Syasuoka static int	 debug = 0;
32a7ca44b8Syasuoka 
33a7ca44b8Syasuoka void	 logit(int, const char *, ...);
34a7ca44b8Syasuoka 
35a7ca44b8Syasuoka void
36a7ca44b8Syasuoka log_init(int n_debug)
37a7ca44b8Syasuoka {
38a7ca44b8Syasuoka 	extern char	*__progname;
39a7ca44b8Syasuoka 
40a7ca44b8Syasuoka 	debug = n_debug;
41a7ca44b8Syasuoka 
42a7ca44b8Syasuoka 	if (!debug)
43a7ca44b8Syasuoka 		openlog(__progname, LOG_PID | LOG_NDELAY, LOG_DAEMON);
44a7ca44b8Syasuoka 
45a7ca44b8Syasuoka 	tzset();
46a7ca44b8Syasuoka 	log_initialized++;
47a7ca44b8Syasuoka }
48a7ca44b8Syasuoka 
49a7ca44b8Syasuoka void
50a7ca44b8Syasuoka logit(int pri, const char *fmt, ...)
51a7ca44b8Syasuoka {
52a7ca44b8Syasuoka 	va_list	ap;
53a7ca44b8Syasuoka 
54a7ca44b8Syasuoka 	va_start(ap, fmt);
55a7ca44b8Syasuoka 	vlog(pri, fmt, ap);
56a7ca44b8Syasuoka 	va_end(ap);
57a7ca44b8Syasuoka }
58a7ca44b8Syasuoka 
59a7ca44b8Syasuoka void
60a7ca44b8Syasuoka vlog(int pri, const char *fmt, va_list ap)
61a7ca44b8Syasuoka {
62a7ca44b8Syasuoka 	char			 fmtbuf[1024];
63a7ca44b8Syasuoka 	time_t			 curr;
64a7ca44b8Syasuoka 	struct tm		 tm;
65a7ca44b8Syasuoka 	u_int			 i = 0, j;
66a7ca44b8Syasuoka 	static struct {
67a7ca44b8Syasuoka 		int		 v;
68a7ca44b8Syasuoka 		const char	*l;
69a7ca44b8Syasuoka 	} syslog_prionames[] = {
70a7ca44b8Syasuoka #define	NV(_l)	{ _l, #_l }
71a7ca44b8Syasuoka 		NV(LOG_DEBUG),
72a7ca44b8Syasuoka 		NV(LOG_INFO),
73a7ca44b8Syasuoka 		NV(LOG_NOTICE),
74a7ca44b8Syasuoka 		NV(LOG_WARNING),
75a7ca44b8Syasuoka 		NV(LOG_ERR),
76a7ca44b8Syasuoka 		NV(LOG_ALERT),
77a7ca44b8Syasuoka 		NV(LOG_CRIT),
78a7ca44b8Syasuoka #undef NV
79a7ca44b8Syasuoka 		{ -1, NULL }
80a7ca44b8Syasuoka 	};
81a7ca44b8Syasuoka 
82a7ca44b8Syasuoka 	if (log_initialized && !debug) {
83a7ca44b8Syasuoka 		vsyslog(pri, fmt, ap);
84a7ca44b8Syasuoka 		return;
85a7ca44b8Syasuoka 	}
86a7ca44b8Syasuoka 	if (log_initialized) {
87a7ca44b8Syasuoka 		time(&curr);
88a7ca44b8Syasuoka 		localtime_r(&curr, &tm);
89a7ca44b8Syasuoka 		strftime(fmtbuf, sizeof(fmtbuf), "%Y-%m-%d %H:%M:%S:", &tm);
90a7ca44b8Syasuoka 		for (i = 0; syslog_prionames[i].v != -1; i++) {
91a7ca44b8Syasuoka 			if (syslog_prionames[i].v == LOG_PRI(pri)) {
92a7ca44b8Syasuoka 				strlcat(fmtbuf, syslog_prionames[i].l + 4,
93a7ca44b8Syasuoka 				    sizeof(fmtbuf));
94a7ca44b8Syasuoka 				strlcat(fmtbuf, ": ", sizeof(fmtbuf));
95a7ca44b8Syasuoka 				break;
96a7ca44b8Syasuoka 			}
97a7ca44b8Syasuoka 		}
98a7ca44b8Syasuoka 		i = strlen(fmtbuf);
99a7ca44b8Syasuoka 	}
100a7ca44b8Syasuoka 	for (j = 0; i < sizeof(fmtbuf) - 2 && fmt[j] != '\0'; j++) {
101a7ca44b8Syasuoka 		if (fmt[j] == '%' && fmt[j + 1] == 'm') {
102a7ca44b8Syasuoka 			++j;
103a7ca44b8Syasuoka 			fmtbuf[i] = '\0';
104a7ca44b8Syasuoka 			strlcat(fmtbuf, strerror(errno), sizeof(fmtbuf) - 1);
105a7ca44b8Syasuoka 			i = strlen(fmtbuf);
106a7ca44b8Syasuoka 		} else
107a7ca44b8Syasuoka 			fmtbuf[i++] = fmt[j];
108a7ca44b8Syasuoka 	}
109a7ca44b8Syasuoka 	fmtbuf[i++] = '\n';
110a7ca44b8Syasuoka 	fmtbuf[i++] = '\0';
111a7ca44b8Syasuoka 
112a7ca44b8Syasuoka 	vfprintf(stderr, fmtbuf, ap);
113a7ca44b8Syasuoka }
114a7ca44b8Syasuoka 
115a7ca44b8Syasuoka 
116a7ca44b8Syasuoka void
117a7ca44b8Syasuoka log_warn(const char *emsg, ...)
118a7ca44b8Syasuoka {
119a7ca44b8Syasuoka 	char	*nfmt;
120a7ca44b8Syasuoka 	va_list	 ap;
121a7ca44b8Syasuoka 
122a7ca44b8Syasuoka 	/* best effort to even work in out of memory situations */
123a7ca44b8Syasuoka 	if (emsg == NULL)
124a7ca44b8Syasuoka 		logit(LOG_WARNING, "%s", strerror(errno));
125a7ca44b8Syasuoka 	else {
126a7ca44b8Syasuoka 		va_start(ap, emsg);
127a7ca44b8Syasuoka 
128a7ca44b8Syasuoka 		if (asprintf(&nfmt, "%s: %s", emsg, strerror(errno)) == -1) {
129a7ca44b8Syasuoka 			/* we tried it... */
130a7ca44b8Syasuoka 			vlog(LOG_WARNING, emsg, ap);
131a7ca44b8Syasuoka 			logit(LOG_WARNING, "%s", strerror(errno));
132a7ca44b8Syasuoka 		} else {
133a7ca44b8Syasuoka 			vlog(LOG_WARNING, nfmt, ap);
134a7ca44b8Syasuoka 			free(nfmt);
135a7ca44b8Syasuoka 		}
136a7ca44b8Syasuoka 		va_end(ap);
137a7ca44b8Syasuoka 	}
138a7ca44b8Syasuoka }
139a7ca44b8Syasuoka 
140a7ca44b8Syasuoka void
141a7ca44b8Syasuoka log_warnx(const char *emsg, ...)
142a7ca44b8Syasuoka {
143a7ca44b8Syasuoka 	va_list	 ap;
144a7ca44b8Syasuoka 
145a7ca44b8Syasuoka 	va_start(ap, emsg);
146a7ca44b8Syasuoka 	vlog(LOG_WARNING, emsg, ap);
147a7ca44b8Syasuoka 	va_end(ap);
148a7ca44b8Syasuoka }
149a7ca44b8Syasuoka 
150a7ca44b8Syasuoka void
151a7ca44b8Syasuoka log_info(const char *emsg, ...)
152a7ca44b8Syasuoka {
153a7ca44b8Syasuoka 	va_list	 ap;
154a7ca44b8Syasuoka 
155a7ca44b8Syasuoka 	va_start(ap, emsg);
156a7ca44b8Syasuoka 	vlog(LOG_INFO, emsg, ap);
157a7ca44b8Syasuoka 	va_end(ap);
158a7ca44b8Syasuoka }
159a7ca44b8Syasuoka 
160a7ca44b8Syasuoka void
161a7ca44b8Syasuoka log_debug(const char *emsg, ...)
162a7ca44b8Syasuoka {
163a7ca44b8Syasuoka 	va_list	 ap;
164a7ca44b8Syasuoka 
165a7ca44b8Syasuoka 	if (debug || log_debug_use_syslog) {
166a7ca44b8Syasuoka 		va_start(ap, emsg);
167a7ca44b8Syasuoka 		vlog(LOG_DEBUG, emsg, ap);
168a7ca44b8Syasuoka 		va_end(ap);
169a7ca44b8Syasuoka 	}
170a7ca44b8Syasuoka }
171a7ca44b8Syasuoka 
172a7ca44b8Syasuoka void
173a7ca44b8Syasuoka fatal(const char *emsg)
174a7ca44b8Syasuoka {
175a7ca44b8Syasuoka 	if (emsg == NULL)
176a7ca44b8Syasuoka 		logit(LOG_CRIT, "fatal: %s", strerror(errno));
177a7ca44b8Syasuoka 	else
178a7ca44b8Syasuoka 		if (errno)
179a7ca44b8Syasuoka 			logit(LOG_CRIT, "fatal: %s: %s",
180a7ca44b8Syasuoka 			    emsg, strerror(errno));
181a7ca44b8Syasuoka 		else
182a7ca44b8Syasuoka 			logit(LOG_CRIT, "fatal: %s", emsg);
183a7ca44b8Syasuoka 
184a7ca44b8Syasuoka 	exit(1);
185a7ca44b8Syasuoka }
186a7ca44b8Syasuoka 
187a7ca44b8Syasuoka void
188a7ca44b8Syasuoka fatalx(const char *emsg)
189a7ca44b8Syasuoka {
190a7ca44b8Syasuoka 	errno = 0;
191a7ca44b8Syasuoka 	fatal(emsg);
192a7ca44b8Syasuoka }
193