xref: /openbsd-src/usr.sbin/bgpd/log.c (revision 9b2c1562932ce8ef5a9c88720f87a65f2e0ed290)
1*9b2c1562Sbluhm /*	$OpenBSD: log.c,v 1.64 2017/03/21 12:06:55 bluhm Exp $	*/
2a16c0992Shenning 
3a16c0992Shenning /*
4050527e1Shenning  * Copyright (c) 2003, 2004 Henning Brauer <henning@openbsd.org>
5a16c0992Shenning  *
6a16c0992Shenning  * Permission to use, copy, modify, and distribute this software for any
7a16c0992Shenning  * purpose with or without fee is hereby granted, provided that the above
8a16c0992Shenning  * copyright notice and this permission notice appear in all copies.
9a16c0992Shenning  *
10a16c0992Shenning  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11a16c0992Shenning  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
12a16c0992Shenning  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
13a16c0992Shenning  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
14a16c0992Shenning  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
15a16c0992Shenning  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
16a16c0992Shenning  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
17a16c0992Shenning  */
18a16c0992Shenning 
19a16c0992Shenning #include <stdio.h>
20a16c0992Shenning #include <stdlib.h>
215e3f6f95Sbenno #include <stdarg.h>
22a16c0992Shenning #include <string.h>
23ea8300d4Shenning #include <syslog.h>
245e3f6f95Sbenno #include <errno.h>
2514359072Shenning #include <time.h>
26a16c0992Shenning 
27bea482a9Shenning #include "log.h"
28a16c0992Shenning 
295e3f6f95Sbenno static int		 debug;
305e3f6f95Sbenno static int		 verbose;
315e3f6f95Sbenno static const char	*log_procname;
32a16c0992Shenning 
33a16c0992Shenning void
log_init(int n_debug,int facility)345e3f6f95Sbenno log_init(int n_debug, int facility)
35a16c0992Shenning {
365ed087acShenning 	extern char	*__progname;
375ed087acShenning 
38a16c0992Shenning 	debug = n_debug;
395e3f6f95Sbenno 	verbose = n_debug;
405e3f6f95Sbenno 	log_procinit(__progname);
41a16c0992Shenning 
42a16c0992Shenning 	if (!debug)
435e3f6f95Sbenno 		openlog(__progname, LOG_PID | LOG_NDELAY, facility);
4414359072Shenning 
4514359072Shenning 	tzset();
46a16c0992Shenning }
47a16c0992Shenning 
48a16c0992Shenning void
log_procinit(const char * procname)495e3f6f95Sbenno log_procinit(const char *procname)
505e3f6f95Sbenno {
515e3f6f95Sbenno 	if (procname != NULL)
525e3f6f95Sbenno 		log_procname = procname;
535e3f6f95Sbenno }
545e3f6f95Sbenno 
555e3f6f95Sbenno void
log_setverbose(int v)565e3f6f95Sbenno log_setverbose(int v)
57d6b35cfbSclaudio {
58d6b35cfbSclaudio 	verbose = v;
59d6b35cfbSclaudio }
60d6b35cfbSclaudio 
615e3f6f95Sbenno int
log_getverbose(void)625e3f6f95Sbenno log_getverbose(void)
635e3f6f95Sbenno {
645e3f6f95Sbenno 	return (verbose);
655e3f6f95Sbenno }
665e3f6f95Sbenno 
67d6b35cfbSclaudio void
logit(int pri,const char * fmt,...)68a16c0992Shenning logit(int pri, const char *fmt, ...)
69a16c0992Shenning {
70a16c0992Shenning 	va_list	ap;
71a16c0992Shenning 
72a16c0992Shenning 	va_start(ap, fmt);
73a16c0992Shenning 	vlog(pri, fmt, ap);
74a16c0992Shenning 	va_end(ap);
75a16c0992Shenning }
76a16c0992Shenning 
77a16c0992Shenning void
vlog(int pri,const char * fmt,va_list ap)78a16c0992Shenning vlog(int pri, const char *fmt, va_list ap)
79a16c0992Shenning {
801f975a75Shenning 	char	*nfmt;
815e3f6f95Sbenno 	int	 saved_errno = errno;
821f975a75Shenning 
83a16c0992Shenning 	if (debug) {
841f975a75Shenning 		/* best effort in out of mem situations */
851f975a75Shenning 		if (asprintf(&nfmt, "%s\n", fmt) == -1) {
86a16c0992Shenning 			vfprintf(stderr, fmt, ap);
87a16c0992Shenning 			fprintf(stderr, "\n");
881f975a75Shenning 		} else {
891f975a75Shenning 			vfprintf(stderr, nfmt, ap);
901f975a75Shenning 			free(nfmt);
911f975a75Shenning 		}
92ede7e4feShenning 		fflush(stderr);
93a16c0992Shenning 	} else
94a16c0992Shenning 		vsyslog(pri, fmt, ap);
955e3f6f95Sbenno 
965e3f6f95Sbenno 	errno = saved_errno;
97a16c0992Shenning }
98a16c0992Shenning 
99a16c0992Shenning void
log_warn(const char * emsg,...)1008013a801Shenning log_warn(const char *emsg, ...)
101c3187f2eShenning {
102c3187f2eShenning 	char		*nfmt;
103c3187f2eShenning 	va_list		 ap;
1045e3f6f95Sbenno 	int		 saved_errno = errno;
105c3187f2eShenning 
106c3187f2eShenning 	/* best effort to even work in out of memory situations */
107c3187f2eShenning 	if (emsg == NULL)
108*9b2c1562Sbluhm 		logit(LOG_ERR, "%s", strerror(saved_errno));
109c3187f2eShenning 	else {
1105336afd4Shenning 		va_start(ap, emsg);
1115336afd4Shenning 
1125e3f6f95Sbenno 		if (asprintf(&nfmt, "%s: %s", emsg,
1135e3f6f95Sbenno 		    strerror(saved_errno)) == -1) {
114c3187f2eShenning 			/* we tried it... */
115*9b2c1562Sbluhm 			vlog(LOG_ERR, emsg, ap);
116*9b2c1562Sbluhm 			logit(LOG_ERR, "%s", strerror(saved_errno));
1175336afd4Shenning 		} else {
118*9b2c1562Sbluhm 			vlog(LOG_ERR, nfmt, ap);
1195336afd4Shenning 			free(nfmt);
120c3187f2eShenning 		}
121c3187f2eShenning 		va_end(ap);
122c3187f2eShenning 	}
1235e3f6f95Sbenno 
1245e3f6f95Sbenno 	errno = saved_errno;
1255336afd4Shenning }
126c3187f2eShenning 
127c3187f2eShenning void
log_warnx(const char * emsg,...)128364326eeShenning log_warnx(const char *emsg, ...)
129364326eeShenning {
130364326eeShenning 	va_list	 ap;
131364326eeShenning 
132364326eeShenning 	va_start(ap, emsg);
133*9b2c1562Sbluhm 	vlog(LOG_ERR, emsg, ap);
134364326eeShenning 	va_end(ap);
135364326eeShenning }
136364326eeShenning 
137364326eeShenning void
log_info(const char * emsg,...)138364326eeShenning log_info(const char *emsg, ...)
139364326eeShenning {
140364326eeShenning 	va_list	 ap;
141364326eeShenning 
142364326eeShenning 	va_start(ap, emsg);
143364326eeShenning 	vlog(LOG_INFO, emsg, ap);
144364326eeShenning 	va_end(ap);
145364326eeShenning }
146364326eeShenning 
147364326eeShenning void
log_debug(const char * emsg,...)148ea8300d4Shenning log_debug(const char *emsg, ...)
149ea8300d4Shenning {
150ea8300d4Shenning 	va_list	 ap;
151ea8300d4Shenning 
152d6b35cfbSclaudio 	if (verbose) {
153ea8300d4Shenning 		va_start(ap, emsg);
154ea8300d4Shenning 		vlog(LOG_DEBUG, emsg, ap);
155ea8300d4Shenning 		va_end(ap);
156ea8300d4Shenning 	}
1574b69215fShenning }
158ea8300d4Shenning 
1595e3f6f95Sbenno static void
vfatalc(int code,const char * emsg,va_list ap)1605e3f6f95Sbenno vfatalc(int code, const char *emsg, va_list ap)
1615e3f6f95Sbenno {
1625e3f6f95Sbenno 	static char	s[BUFSIZ];
1635e3f6f95Sbenno 	const char	*sep;
1645e3f6f95Sbenno 
1655e3f6f95Sbenno 	if (emsg != NULL) {
1665e3f6f95Sbenno 		(void)vsnprintf(s, sizeof(s), emsg, ap);
1675e3f6f95Sbenno 		sep = ": ";
1685e3f6f95Sbenno 	} else {
1695e3f6f95Sbenno 		s[0] = '\0';
1705e3f6f95Sbenno 		sep = "";
1715e3f6f95Sbenno 	}
1725e3f6f95Sbenno 	if (code)
1735e3f6f95Sbenno 		logit(LOG_CRIT, "fatal in %s: %s%s%s",
1745e3f6f95Sbenno 		    log_procname, s, sep, strerror(code));
1755e3f6f95Sbenno 	else
1765e3f6f95Sbenno 		logit(LOG_CRIT, "fatal in %s%s%s", log_procname, sep, s);
1775e3f6f95Sbenno }
1785e3f6f95Sbenno 
179ea8300d4Shenning void
fatal(const char * emsg,...)18049db16b7Sbenno fatal(const char *emsg, ...)
181a16c0992Shenning {
18249db16b7Sbenno 	va_list	ap;
18349db16b7Sbenno 
18449db16b7Sbenno 	va_start(ap, emsg);
1855e3f6f95Sbenno 	vfatalc(errno, emsg, ap);
18649db16b7Sbenno 	va_end(ap);
1872e09f5e3Shenning 	exit(1);
188a16c0992Shenning }
189a16c0992Shenning 
190a16c0992Shenning void
fatalx(const char * emsg,...)1915e3f6f95Sbenno fatalx(const char *emsg, ...)
192f87a5020Shenning {
1935e3f6f95Sbenno 	va_list	ap;
1945e3f6f95Sbenno 
1955e3f6f95Sbenno 	va_start(ap, emsg);
1965e3f6f95Sbenno 	vfatalc(0, emsg, ap);
1975e3f6f95Sbenno 	va_end(ap);
1985e3f6f95Sbenno 	exit(1);
199f87a5020Shenning }
200