xref: /netbsd-src/usr.sbin/syslogd/syslogd.c (revision b757af438b42b93f8c6571f026d8b8ef3eaf5fc9)
1 /*	$NetBSD: syslogd.c,v 1.106 2012/03/28 17:39:33 christos Exp $	*/
2 
3 /*
4  * Copyright (c) 1983, 1988, 1993, 1994
5  *	The Regents of the University of California.  All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  * 1. Redistributions of source code must retain the above copyright
11  *    notice, this list of conditions and the following disclaimer.
12  * 2. Redistributions in binary form must reproduce the above copyright
13  *    notice, this list of conditions and the following disclaimer in the
14  *    documentation and/or other materials provided with the distribution.
15  * 3. Neither the name of the University nor the names of its contributors
16  *    may be used to endorse or promote products derived from this software
17  *    without specific prior written permission.
18  *
19  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
20  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
23  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
24  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
25  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
26  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
27  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
28  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
29  * SUCH DAMAGE.
30  */
31 
32 #include <sys/cdefs.h>
33 #ifndef lint
34 __COPYRIGHT("@(#) Copyright (c) 1983, 1988, 1993, 1994\
35 	The Regents of the University of California.  All rights reserved.");
36 #endif /* not lint */
37 
38 #ifndef lint
39 #if 0
40 static char sccsid[] = "@(#)syslogd.c	8.3 (Berkeley) 4/4/94";
41 #else
42 __RCSID("$NetBSD: syslogd.c,v 1.106 2012/03/28 17:39:33 christos Exp $");
43 #endif
44 #endif /* not lint */
45 
46 /*
47  *  syslogd -- log system messages
48  *
49  * This program implements a system log. It takes a series of lines.
50  * Each line may have a priority, signified as "<n>" as
51  * the first characters of the line.  If this is
52  * not present, a default priority is used.
53  *
54  * To kill syslogd, send a signal 15 (terminate).  A signal 1 (hup) will
55  * cause it to reread its configuration file.
56  *
57  * Defined Constants:
58  *
59  * MAXLINE -- the maximimum line length that can be handled.
60  * DEFUPRI -- the default priority for user messages
61  * DEFSPRI -- the default priority for kernel messages
62  *
63  * Author: Eric Allman
64  * extensive changes by Ralph Campbell
65  * more extensive changes by Eric Allman (again)
66  * Extension to log by program name as well as facility and priority
67  *   by Peter da Silva.
68  * -U and -v by Harlan Stenn.
69  * Priority comparison code by Harlan Stenn.
70  * TLS, syslog-protocol, and syslog-sign code by Martin Schuette.
71  */
72 #define SYSLOG_NAMES
73 #include "syslogd.h"
74 #include "extern.h"
75 
76 #ifndef DISABLE_SIGN
77 #include "sign.h"
78 struct sign_global_t GlobalSign = {
79 	.rsid = 0,
80 	.sig2_delims = STAILQ_HEAD_INITIALIZER(GlobalSign.sig2_delims)
81 };
82 #endif /* !DISABLE_SIGN */
83 
84 #ifndef DISABLE_TLS
85 #include "tls.h"
86 #endif /* !DISABLE_TLS */
87 
88 #ifdef LIBWRAP
89 int allow_severity = LOG_AUTH|LOG_INFO;
90 int deny_severity = LOG_AUTH|LOG_WARNING;
91 #endif
92 
93 const char	*ConfFile = _PATH_LOGCONF;
94 char	ctty[] = _PATH_CONSOLE;
95 
96 /*
97  * Queue of about-to-be-dead processes we should watch out for.
98  */
99 TAILQ_HEAD(, deadq_entry) deadq_head = TAILQ_HEAD_INITIALIZER(deadq_head);
100 
101 typedef struct deadq_entry {
102 	pid_t				dq_pid;
103 	int				dq_timeout;
104 	TAILQ_ENTRY(deadq_entry)	dq_entries;
105 } *dq_t;
106 
107 /*
108  * The timeout to apply to processes waiting on the dead queue.	 Unit
109  * of measure is "mark intervals", i.e. 20 minutes by default.
110  * Processes on the dead queue will be terminated after that time.
111  */
112 #define DQ_TIMO_INIT	2
113 
114 /*
115  * Intervals at which we flush out "message repeated" messages,
116  * in seconds after previous message is logged.	 After each flush,
117  * we move to the next interval until we reach the largest.
118  */
119 int	repeatinterval[] = { 30, 120, 600 };	/* # of secs before flush */
120 #define MAXREPEAT ((sizeof(repeatinterval) / sizeof(repeatinterval[0])) - 1)
121 #define REPEATTIME(f)	((f)->f_time + repeatinterval[(f)->f_repeatcount])
122 #define BACKOFF(f)	{ if ((size_t)(++(f)->f_repeatcount) > MAXREPEAT) \
123 				 (f)->f_repeatcount = MAXREPEAT; \
124 			}
125 
126 /* values for f_type */
127 #define F_UNUSED	0		/* unused entry */
128 #define F_FILE		1		/* regular file */
129 #define F_TTY		2		/* terminal */
130 #define F_CONSOLE	3		/* console terminal */
131 #define F_FORW		4		/* remote machine */
132 #define F_USERS		5		/* list of users */
133 #define F_WALL		6		/* everyone logged on */
134 #define F_PIPE		7		/* pipe to program */
135 #define F_TLS		8
136 
137 struct TypeInfo {
138 	const char *name;
139 	char	   *queue_length_string;
140 	const char *default_length_string;
141 	char	   *queue_size_string;
142 	const char *default_size_string;
143 	int64_t	    queue_length;
144 	int64_t	    queue_size;
145 	int   max_msg_length;
146 } TypeInfo[] = {
147 	/* numeric values are set in init()
148 	 * -1 in length/size or max_msg_length means infinite */
149 	{"UNUSED",  NULL,    "0", NULL,	  "0", 0, 0,	 0},
150 	{"FILE",    NULL, "1024", NULL,	 "1M", 0, 0, 16384},
151 	{"TTY",	    NULL,    "0", NULL,	  "0", 0, 0,  1024},
152 	{"CONSOLE", NULL,    "0", NULL,	  "0", 0, 0,  1024},
153 	{"FORW",    NULL,    "0", NULL,	 "1M", 0, 0, 16384},
154 	{"USERS",   NULL,    "0", NULL,	  "0", 0, 0,  1024},
155 	{"WALL",    NULL,    "0", NULL,	  "0", 0, 0,  1024},
156 	{"PIPE",    NULL, "1024", NULL,	 "1M", 0, 0, 16384},
157 #ifndef DISABLE_TLS
158 	{"TLS",	    NULL,   "-1", NULL, "16M", 0, 0, 16384}
159 #endif /* !DISABLE_TLS */
160 };
161 
162 struct	filed *Files = NULL;
163 struct	filed consfile;
164 
165 time_t	now;
166 int	Debug = D_NONE;		/* debug flag */
167 int	daemonized = 0;		/* we are not daemonized yet */
168 char	*LocalFQDN = NULL;	       /* our FQDN */
169 char	*oldLocalFQDN = NULL;	       /* our previous FQDN */
170 char	LocalHostName[MAXHOSTNAMELEN]; /* our hostname */
171 struct socketEvent *finet;	/* Internet datagram sockets and events */
172 int   *funix;			/* Unix domain datagram sockets */
173 #ifndef DISABLE_TLS
174 struct socketEvent *TLS_Listen_Set; /* TLS/TCP sockets and events */
175 #endif /* !DISABLE_TLS */
176 int	Initialized = 0;	/* set when we have initialized ourselves */
177 int	ShuttingDown;		/* set when we die() */
178 int	MarkInterval = 20 * 60; /* interval between marks in seconds */
179 int	MarkSeq = 0;		/* mark sequence number */
180 int	SecureMode = 0;		/* listen only on unix domain socks */
181 int	UseNameService = 1;	/* make domain name queries */
182 int	NumForwards = 0;	/* number of forwarding actions in conf file */
183 char	**LogPaths;		/* array of pathnames to read messages from */
184 int	NoRepeat = 0;		/* disable "repeated"; log always */
185 int	RemoteAddDate = 0;	/* always add date to messages from network */
186 int	SyncKernel = 0;		/* write kernel messages synchronously */
187 int	UniquePriority = 0;	/* only log specified priority */
188 int	LogFacPri = 0;		/* put facility and priority in log messages: */
189 				/* 0=no, 1=numeric, 2=names */
190 bool	BSDOutputFormat = true;	/* if true emit traditional BSD Syslog lines,
191 				 * otherwise new syslog-protocol lines
192 				 *
193 				 * Open Issue: having a global flag is the
194 				 * easiest solution. If we get a more detailed
195 				 * config file this could/should be changed
196 				 * into a destination-specific flag.
197 				 * Most output code should be ready to handle
198 				 * this, it will only break some syslog-sign
199 				 * configurations (e.g. with SG="0").
200 				 */
201 char	appname[]   = "syslogd";/* the APPNAME for own messages */
202 char   *include_pid = NULL;	/* include PID in own messages */
203 
204 
205 /* init and setup */
206 void		usage(void) __attribute__((__noreturn__));
207 void		logpath_add(char ***, int *, int *, const char *);
208 void		logpath_fileadd(char ***, int *, int *, const char *);
209 void		init(int fd, short event, void *ev);  /* SIGHUP kevent dispatch routine */
210 struct socketEvent*
211 		socksetup(int, const char *);
212 int		getmsgbufsize(void);
213 char	       *getLocalFQDN(void);
214 void		trim_anydomain(char *);
215 /* pipe & subprocess handling */
216 int		p_open(char *, pid_t *);
217 void		deadq_enter(pid_t, const char *);
218 int		deadq_remove(pid_t);
219 void		log_deadchild(pid_t, int, const char *);
220 void		reapchild(int fd, short event, void *ev); /* SIGCHLD kevent dispatch routine */
221 /* input message parsing & formatting */
222 const char     *cvthname(struct sockaddr_storage *);
223 void		printsys(char *);
224 struct buf_msg *printline_syslogprotocol(const char*, char*, int, int);
225 struct buf_msg *printline_bsdsyslog(const char*, char*, int, int);
226 struct buf_msg *printline_kernelprintf(const char*, char*, int, int);
227 size_t		check_timestamp(unsigned char *, char **, bool, bool);
228 char	       *copy_utf8_ascii(char*, size_t);
229 uint_fast32_t	get_utf8_value(const char*);
230 unsigned	valid_utf8(const char *);
231 static unsigned check_sd(char*);
232 static unsigned check_msgid(char *);
233 /* event handling */
234 static void	dispatch_read_klog(int fd, short event, void *ev);
235 static void	dispatch_read_finet(int fd, short event, void *ev);
236 static void	dispatch_read_funix(int fd, short event, void *ev);
237 static void	domark(int fd, short event, void *ev); /* timer kevent dispatch routine */
238 /* log messages */
239 void		logmsg_async(int, const char *, const char *, int);
240 void		logmsg(struct buf_msg *);
241 int		matches_spec(const char *, const char *,
242 		char *(*)(const char *, const char *));
243 void		udp_send(struct filed *, char *, size_t);
244 void		wallmsg(struct filed *, struct iovec *, size_t);
245 /* buffer & queue functions */
246 size_t		message_queue_purge(struct filed *f, size_t, int);
247 size_t		message_allqueues_check(void);
248 static struct buf_queue *
249 		find_qentry_to_delete(const struct buf_queue_head *, int, bool);
250 struct buf_queue *
251 		message_queue_add(struct filed *, struct buf_msg *);
252 size_t		buf_queue_obj_size(struct buf_queue*);
253 /* configuration & parsing */
254 void		cfline(size_t, const char *, struct filed *, const char *,
255     const char *);
256 void		read_config_file(FILE*, struct filed**);
257 void		store_sign_delim_sg2(char*);
258 int		decode(const char *, CODE *);
259 bool		copy_config_value(const char *, char **, const char **,
260     const char *, int);
261 bool		copy_config_value_word(char **, const char **);
262 
263 /* config parsing */
264 #ifndef DISABLE_TLS
265 void		free_cred_SLIST(struct peer_cred_head *);
266 static inline void
267 		free_incoming_tls_sockets(void);
268 #endif /* !DISABLE_TLS */
269 
270 /* for make_timestamp() */
271 #define TIMESTAMPBUFSIZE 35
272 char timestamp[TIMESTAMPBUFSIZE];
273 
274 /*
275  * Global line buffer.	Since we only process one event at a time,
276  * a global one will do.  But for klog, we use own buffer so that
277  * partial line at the end of buffer can be deferred.
278  */
279 char *linebuf, *klog_linebuf;
280 size_t linebufsize, klog_linebufoff;
281 
282 static const char *bindhostname = NULL;
283 
284 #ifndef DISABLE_TLS
285 struct TLS_Incoming TLS_Incoming_Head = \
286 	SLIST_HEAD_INITIALIZER(TLS_Incoming_Head);
287 extern char *SSL_ERRCODE[];
288 struct tls_global_options_t tls_opt;
289 #endif /* !DISABLE_TLS */
290 
291 int
292 main(int argc, char *argv[])
293 {
294 	int ch, j, fklog;
295 	int funixsize = 0, funixmaxsize = 0;
296 	struct sockaddr_un sunx;
297 	char **pp;
298 	struct event *ev;
299 	uid_t uid = 0;
300 	gid_t gid = 0;
301 	char *user = NULL;
302 	char *group = NULL;
303 	const char *root = "/";
304 	char *endp;
305 	struct group   *gr;
306 	struct passwd  *pw;
307 	unsigned long l;
308 
309 	/* should we set LC_TIME="C" to ensure correct timestamps&parsing? */
310 	(void)setlocale(LC_ALL, "");
311 
312 	while ((ch = getopt(argc, argv, "b:dnsSf:m:o:p:P:ru:g:t:TUv")) != -1)
313 		switch(ch) {
314 		case 'b':
315 			bindhostname = optarg;
316 			break;
317 		case 'd':		/* debug */
318 			Debug = D_DEFAULT;
319 			/* is there a way to read the integer value
320 			 * for Debug as an optional argument? */
321 			break;
322 		case 'f':		/* configuration file */
323 			ConfFile = optarg;
324 			break;
325 		case 'g':
326 			group = optarg;
327 			if (*group == '\0')
328 				usage();
329 			break;
330 		case 'm':		/* mark interval */
331 			MarkInterval = atoi(optarg) * 60;
332 			break;
333 		case 'n':		/* turn off DNS queries */
334 			UseNameService = 0;
335 			break;
336 		case 'o':		/* message format */
337 #define EQ(a)		(strncmp(optarg, # a, sizeof(# a) - 1) == 0)
338 			if (EQ(bsd) || EQ(rfc3264))
339 				BSDOutputFormat = true;
340 			else if (EQ(syslog) || EQ(rfc5424))
341 				BSDOutputFormat = false;
342 			else
343 				usage();
344 			/* TODO: implement additional output option "osyslog"
345 			 *	 for old syslogd behaviour as introduced after
346 			 *	 FreeBSD PR#bin/7055.
347 			 */
348 			break;
349 		case 'p':		/* path */
350 			logpath_add(&LogPaths, &funixsize,
351 			    &funixmaxsize, optarg);
352 			break;
353 		case 'P':		/* file of paths */
354 			logpath_fileadd(&LogPaths, &funixsize,
355 			    &funixmaxsize, optarg);
356 			break;
357 		case 'r':		/* disable "repeated" compression */
358 			NoRepeat++;
359 			break;
360 		case 's':		/* no network listen mode */
361 			SecureMode++;
362 			break;
363 		case 'S':
364 			SyncKernel = 1;
365 			break;
366 		case 't':
367 			root = optarg;
368 			if (*root == '\0')
369 				usage();
370 			break;
371 		case 'T':
372 			RemoteAddDate = 1;
373 			break;
374 		case 'u':
375 			user = optarg;
376 			if (*user == '\0')
377 				usage();
378 			break;
379 		case 'U':		/* only log specified priority */
380 			UniquePriority = 1;
381 			break;
382 		case 'v':		/* log facility and priority */
383 			if (LogFacPri < 2)
384 				LogFacPri++;
385 			break;
386 		default:
387 			usage();
388 		}
389 	if ((argc -= optind) != 0)
390 		usage();
391 
392 	setlinebuf(stdout);
393 	tzset(); /* init TZ information for localtime. */
394 
395 	if (user != NULL) {
396 		if (isdigit((unsigned char)*user)) {
397 			errno = 0;
398 			endp = NULL;
399 			l = strtoul(user, &endp, 0);
400 			if (errno || *endp != '\0')
401 				goto getuser;
402 			uid = (uid_t)l;
403 			if (uid != l) {/* TODO: never executed */
404 				errno = 0;
405 				logerror("UID out of range");
406 				die(0, 0, NULL);
407 			}
408 		} else {
409 getuser:
410 			if ((pw = getpwnam(user)) != NULL) {
411 				uid = pw->pw_uid;
412 			} else {
413 				errno = 0;
414 				logerror("Cannot find user `%s'", user);
415 				die(0, 0, NULL);
416 			}
417 		}
418 	}
419 
420 	if (group != NULL) {
421 		if (isdigit((unsigned char)*group)) {
422 			errno = 0;
423 			endp = NULL;
424 			l = strtoul(group, &endp, 0);
425 			if (errno || *endp != '\0')
426 				goto getgroup;
427 			gid = (gid_t)l;
428 			if (gid != l) {/* TODO: never executed */
429 				errno = 0;
430 				logerror("GID out of range");
431 				die(0, 0, NULL);
432 			}
433 		} else {
434 getgroup:
435 			if ((gr = getgrnam(group)) != NULL) {
436 				gid = gr->gr_gid;
437 			} else {
438 				errno = 0;
439 				logerror("Cannot find group `%s'", group);
440 				die(0, 0, NULL);
441 			}
442 		}
443 	}
444 
445 	if (access(root, F_OK | R_OK)) {
446 		logerror("Cannot access `%s'", root);
447 		die(0, 0, NULL);
448 	}
449 
450 	consfile.f_type = F_CONSOLE;
451 	(void)strlcpy(consfile.f_un.f_fname, ctty,
452 	    sizeof(consfile.f_un.f_fname));
453 	linebufsize = getmsgbufsize();
454 	if (linebufsize < MAXLINE)
455 		linebufsize = MAXLINE;
456 	linebufsize++;
457 
458 	if (!(linebuf = malloc(linebufsize))) {
459 		logerror("Couldn't allocate buffer");
460 		die(0, 0, NULL);
461 	}
462 	if (!(klog_linebuf = malloc(linebufsize))) {
463 		logerror("Couldn't allocate buffer for klog");
464 		die(0, 0, NULL);
465 	}
466 
467 
468 #ifndef SUN_LEN
469 #define SUN_LEN(unp) (strlen((unp)->sun_path) + 2)
470 #endif
471 	if (funixsize == 0)
472 		logpath_add(&LogPaths, &funixsize,
473 		    &funixmaxsize, _PATH_LOG);
474 	funix = (int *)malloc(sizeof(int) * funixsize);
475 	if (funix == NULL) {
476 		logerror("Couldn't allocate funix descriptors");
477 		die(0, 0, NULL);
478 	}
479 	for (j = 0, pp = LogPaths; *pp; pp++, j++) {
480 		DPRINTF(D_NET, "Making unix dgram socket `%s'\n", *pp);
481 		unlink(*pp);
482 		memset(&sunx, 0, sizeof(sunx));
483 		sunx.sun_family = AF_LOCAL;
484 		(void)strncpy(sunx.sun_path, *pp, sizeof(sunx.sun_path));
485 		funix[j] = socket(AF_LOCAL, SOCK_DGRAM, 0);
486 		if (funix[j] < 0 || bind(funix[j],
487 		    (struct sockaddr *)&sunx, SUN_LEN(&sunx)) < 0 ||
488 		    chmod(*pp, 0666) < 0) {
489 			logerror("Cannot create `%s'", *pp);
490 			die(0, 0, NULL);
491 		}
492 		DPRINTF(D_NET, "Listening on unix dgram socket `%s'\n", *pp);
493 	}
494 
495 	if ((fklog = open(_PATH_KLOG, O_RDONLY, 0)) < 0) {
496 		DPRINTF(D_FILE, "Can't open `%s' (%d)\n", _PATH_KLOG, errno);
497 	} else {
498 		DPRINTF(D_FILE, "Listening on kernel log `%s' with fd %d\n",
499 		    _PATH_KLOG, fklog);
500 	}
501 
502 #if (!defined(DISABLE_TLS) && !defined(DISABLE_SIGN))
503 	/* basic OpenSSL init */
504 	SSL_load_error_strings();
505 	(void) SSL_library_init();
506 	OpenSSL_add_all_digests();
507 	/* OpenSSL PRNG needs /dev/urandom, thus initialize before chroot() */
508 	if (!RAND_status())
509 		logerror("Unable to initialize OpenSSL PRNG");
510 	else {
511 		DPRINTF(D_TLS, "Initializing PRNG\n");
512 	}
513 #endif /* (!defined(DISABLE_TLS) && !defined(DISABLE_SIGN)) */
514 #ifndef DISABLE_SIGN
515 	/* initialize rsid -- we will use that later to determine
516 	 * whether sign_global_init() was already called */
517 	GlobalSign.rsid = 0;
518 #endif /* !DISABLE_SIGN */
519 #if (IETF_NUM_PRIVALUES != (LOG_NFACILITIES<<3))
520 	logerror("Warning: system defines %d priority values, but "
521 	    "syslog-protocol/syslog-sign specify %d values",
522 	    LOG_NFACILITIES, SIGN_NUM_PRIVALS);
523 #endif
524 
525 	/*
526 	 * All files are open, we can drop privileges and chroot
527 	 */
528 	DPRINTF(D_MISC, "Attempt to chroot to `%s'\n", root);
529 	if (chroot(root)) {
530 		logerror("Failed to chroot to `%s'", root);
531 		die(0, 0, NULL);
532 	}
533 	DPRINTF(D_MISC, "Attempt to set GID/EGID to `%d'\n", gid);
534 	if (setgid(gid) || setegid(gid)) {
535 		logerror("Failed to set gid to `%d'", gid);
536 		die(0, 0, NULL);
537 	}
538 	DPRINTF(D_MISC, "Attempt to set UID/EUID to `%d'\n", uid);
539 	if (setuid(uid) || seteuid(uid)) {
540 		logerror("Failed to set uid to `%d'", uid);
541 		die(0, 0, NULL);
542 	}
543 	/*
544 	 * We cannot detach from the terminal before we are sure we won't
545 	 * have a fatal error, because error message would not go to the
546 	 * terminal and would not be logged because syslogd dies.
547 	 * All die() calls are behind us, we can call daemon()
548 	 */
549 	if (!Debug) {
550 		(void)daemon(0, 0);
551 		daemonized = 1;
552 		/* tuck my process id away, if i'm not in debug mode */
553 #ifdef __NetBSD_Version__
554 		pidfile(NULL);
555 #endif /* __NetBSD_Version__ */
556 	}
557 
558 #define MAX_PID_LEN 5
559 	include_pid = malloc(MAX_PID_LEN+1);
560 	snprintf(include_pid, MAX_PID_LEN+1, "%d", getpid());
561 
562 	/*
563 	 * Create the global kernel event descriptor.
564 	 *
565 	 * NOTE: We MUST do this after daemon(), bacause the kqueue()
566 	 * API dictates that kqueue descriptors are not inherited
567 	 * across forks (lame!).
568 	 */
569 	(void)event_init();
570 
571 	/*
572 	 * We must read the configuration file for the first time
573 	 * after the kqueue descriptor is created, because we install
574 	 * events during this process.
575 	 */
576 	init(0, 0, NULL);
577 
578 	/*
579 	 * Always exit on SIGTERM.  Also exit on SIGINT and SIGQUIT
580 	 * if we're debugging.
581 	 */
582 	(void)signal(SIGTERM, SIG_IGN);
583 	(void)signal(SIGINT, SIG_IGN);
584 	(void)signal(SIGQUIT, SIG_IGN);
585 
586 	ev = allocev();
587 	signal_set(ev, SIGTERM, die, ev);
588 	EVENT_ADD(ev);
589 
590 	if (Debug) {
591 		ev = allocev();
592 		signal_set(ev, SIGINT, die, ev);
593 		EVENT_ADD(ev);
594 		ev = allocev();
595 		signal_set(ev, SIGQUIT, die, ev);
596 		EVENT_ADD(ev);
597 	}
598 
599 	ev = allocev();
600 	signal_set(ev, SIGCHLD, reapchild, ev);
601 	EVENT_ADD(ev);
602 
603 	ev = allocev();
604 	schedule_event(&ev,
605 		&((struct timeval){TIMERINTVL, 0}),
606 		domark, ev);
607 
608 	(void)signal(SIGPIPE, SIG_IGN); /* We'll catch EPIPE instead. */
609 
610 	/* Re-read configuration on SIGHUP. */
611 	(void) signal(SIGHUP, SIG_IGN);
612 	ev = allocev();
613 	signal_set(ev, SIGHUP, init, ev);
614 	EVENT_ADD(ev);
615 
616 #ifndef DISABLE_TLS
617 	ev = allocev();
618 	signal_set(ev, SIGUSR1, dispatch_force_tls_reconnect, ev);
619 	EVENT_ADD(ev);
620 #endif /* !DISABLE_TLS */
621 
622 	if (fklog >= 0) {
623 		ev = allocev();
624 		DPRINTF(D_EVENT,
625 			"register klog for fd %d with ev@%p\n", fklog, ev);
626 		event_set(ev, fklog, EV_READ | EV_PERSIST,
627 			dispatch_read_klog, ev);
628 		EVENT_ADD(ev);
629 	}
630 	for (j = 0, pp = LogPaths; *pp; pp++, j++) {
631 		ev = allocev();
632 		event_set(ev, funix[j], EV_READ | EV_PERSIST,
633 			dispatch_read_funix, ev);
634 		EVENT_ADD(ev);
635 	}
636 
637 	DPRINTF(D_MISC, "Off & running....\n");
638 
639 	j = event_dispatch();
640 	/* normal termination via die(), reaching this is an error */
641 	DPRINTF(D_MISC, "event_dispatch() returned %d\n", j);
642 	die(0, 0, NULL);
643 	/*NOTREACHED*/
644 	return 0;
645 }
646 
647 void
648 usage(void)
649 {
650 
651 	(void)fprintf(stderr,
652 	    "usage: %s [-dnrSsTUv] [-b bind_address] [-f config_file] [-g group]\n"
653 	    "\t[-m mark_interval] [-P file_list] [-p log_socket\n"
654 	    "\t[-p log_socket2 ...]] [-t chroot_dir] [-u user]\n",
655 	    getprogname());
656 	exit(1);
657 }
658 
659 /*
660  * Dispatch routine for reading /dev/klog
661  *
662  * Note: slightly different semantic in dispatch_read functions:
663  *	 - read_klog() might give multiple messages in linebuf and
664  *	   leaves the task of splitting them to printsys()
665  *	 - all other read functions receive one message and
666  *	   then call printline() with one buffer.
667  */
668 static void
669 dispatch_read_klog(int fd, short event, void *ev)
670 {
671 	ssize_t rv;
672 	size_t resid = linebufsize - klog_linebufoff;
673 
674 	DPRINTF((D_CALL|D_EVENT), "Kernel log active (%d, %d, %p)"
675 		" with linebuf@%p, length %zu)\n", fd, event, ev,
676 		klog_linebuf, linebufsize);
677 
678 	rv = read(fd, &klog_linebuf[klog_linebufoff], resid - 1);
679 	if (rv > 0) {
680 		klog_linebuf[klog_linebufoff + rv] = '\0';
681 		printsys(klog_linebuf);
682 	} else if (rv < 0 && errno != EINTR) {
683 		/*
684 		 * /dev/klog has croaked.  Disable the event
685 		 * so it won't bother us again.
686 		 */
687 		logerror("klog failed");
688 		event_del(ev);
689 	}
690 }
691 
692 /*
693  * Dispatch routine for reading Unix domain sockets.
694  */
695 static void
696 dispatch_read_funix(int fd, short event, void *ev)
697 {
698 	struct sockaddr_un myname, fromunix;
699 	ssize_t rv;
700 	socklen_t sunlen;
701 
702 	sunlen = sizeof(myname);
703 	if (getsockname(fd, (struct sockaddr *)&myname, &sunlen) != 0) {
704 		/*
705 		 * This should never happen, so ensure that it doesn't
706 		 * happen again.
707 		 */
708 		logerror("getsockname() unix failed");
709 		event_del(ev);
710 		return;
711 	}
712 
713 	DPRINTF((D_CALL|D_EVENT|D_NET), "Unix socket (%.*s) active (%d, %d %p)"
714 		" with linebuf@%p, size %zu)\n", (int)(myname.sun_len
715 		- sizeof(myname.sun_len) - sizeof(myname.sun_family)),
716 		myname.sun_path, fd, event, ev, linebuf, linebufsize-1);
717 
718 	sunlen = sizeof(fromunix);
719 	rv = recvfrom(fd, linebuf, linebufsize-1, 0,
720 	    (struct sockaddr *)&fromunix, &sunlen);
721 	if (rv > 0) {
722 		linebuf[rv] = '\0';
723 		printline(LocalFQDN, linebuf, 0);
724 	} else if (rv < 0 && errno != EINTR) {
725 		logerror("recvfrom() unix `%.*s'",
726 			myname.sun_len, myname.sun_path);
727 	}
728 }
729 
730 /*
731  * Dispatch routine for reading Internet sockets.
732  */
733 static void
734 dispatch_read_finet(int fd, short event, void *ev)
735 {
736 #ifdef LIBWRAP
737 	struct request_info req;
738 #endif
739 	struct sockaddr_storage frominet;
740 	ssize_t rv;
741 	socklen_t len;
742 	int reject = 0;
743 
744 	DPRINTF((D_CALL|D_EVENT|D_NET), "inet socket active (%d, %d %p) "
745 		" with linebuf@%p, size %zu)\n",
746 		fd, event, ev, linebuf, linebufsize-1);
747 
748 #ifdef LIBWRAP
749 	request_init(&req, RQ_DAEMON, appname, RQ_FILE, fd, NULL);
750 	fromhost(&req);
751 	reject = !hosts_access(&req);
752 	if (reject)
753 		DPRINTF(D_NET, "access denied\n");
754 #endif
755 
756 	len = sizeof(frominet);
757 	rv = recvfrom(fd, linebuf, linebufsize-1, 0,
758 	    (struct sockaddr *)&frominet, &len);
759 	if (rv == 0 || (rv < 0 && errno == EINTR))
760 		return;
761 	else if (rv < 0) {
762 		logerror("recvfrom inet");
763 		return;
764 	}
765 
766 	linebuf[rv] = '\0';
767 	if (!reject)
768 		printline(cvthname(&frominet), linebuf,
769 		    RemoteAddDate ? ADDDATE : 0);
770 }
771 
772 /*
773  * given a pointer to an array of char *'s, a pointer to its current
774  * size and current allocated max size, and a new char * to add, add
775  * it, update everything as necessary, possibly allocating a new array
776  */
777 void
778 logpath_add(char ***lp, int *szp, int *maxszp, const char *new)
779 {
780 	char **nlp;
781 	int newmaxsz;
782 
783 	DPRINTF(D_FILE, "Adding `%s' to the %p logpath list\n", new, *lp);
784 	if (*szp == *maxszp) {
785 		if (*maxszp == 0) {
786 			newmaxsz = 4;	/* start of with enough for now */
787 			*lp = NULL;
788 		} else
789 			newmaxsz = *maxszp * 2;
790 		nlp = realloc(*lp, sizeof(char *) * (newmaxsz + 1));
791 		if (nlp == NULL) {
792 			logerror("Couldn't allocate line buffer");
793 			die(0, 0, NULL);
794 		}
795 		*lp = nlp;
796 		*maxszp = newmaxsz;
797 	}
798 	if (((*lp)[(*szp)++] = strdup(new)) == NULL) {
799 		logerror("Couldn't allocate logpath");
800 		die(0, 0, NULL);
801 	}
802 	(*lp)[(*szp)] = NULL;		/* always keep it NULL terminated */
803 }
804 
805 /* do a file of log sockets */
806 void
807 logpath_fileadd(char ***lp, int *szp, int *maxszp, const char *file)
808 {
809 	FILE *fp;
810 	char *line;
811 	size_t len;
812 
813 	fp = fopen(file, "r");
814 	if (fp == NULL) {
815 		logerror("Could not open socket file list `%s'", file);
816 		die(0, 0, NULL);
817 	}
818 
819 	while ((line = fgetln(fp, &len)) != NULL) {
820 		line[len - 1] = 0;
821 		logpath_add(lp, szp, maxszp, line);
822 	}
823 	fclose(fp);
824 }
825 
826 /*
827  * checks UTF-8 codepoint
828  * returns either its length in bytes or 0 if *input is invalid
829 */
830 unsigned
831 valid_utf8(const char *c) {
832 	unsigned rc, nb;
833 
834 	/* first byte gives sequence length */
835 	     if ((*c & 0x80) == 0x00) return 1; /* 0bbbbbbb -- ASCII */
836 	else if ((*c & 0xc0) == 0x80) return 0; /* 10bbbbbb -- trailing byte */
837 	else if ((*c & 0xe0) == 0xc0) nb = 2;	/* 110bbbbb */
838 	else if ((*c & 0xf0) == 0xe0) nb = 3;	/* 1110bbbb */
839 	else if ((*c & 0xf8) == 0xf0) nb = 4;	/* 11110bbb */
840 	else return 0; /* UTF-8 allows only up to 4 bytes */
841 
842 	/* catch overlong encodings */
843 	if ((*c & 0xfe) == 0xc0)
844 		return 0; /* 1100000b ... */
845 	else if (((*c & 0xff) == 0xe0) && ((*(c+1) & 0xe0) == 0x80))
846 		return 0; /* 11100000 100bbbbb ... */
847 	else if (((*c & 0xff) == 0xf0) && ((*(c+1) & 0xf0) == 0x80))
848 		return 0; /* 11110000 1000bbbb ... ... */
849 
850 	/* and also filter UTF-16 surrogates (=invalid in UTF-8) */
851 	if (((*c & 0xff) == 0xed) && ((*(c+1) & 0xe0) == 0xa0))
852 		return 0; /* 11101101 101bbbbb ... */
853 
854 	rc = nb;
855 	/* check trailing bytes */
856 	switch (nb) {
857 	default: return 0;
858 	case 4: if ((*(c+3) & 0xc0) != 0x80) return 0; /*FALLTHROUGH*/
859 	case 3: if ((*(c+2) & 0xc0) != 0x80) return 0; /*FALLTHROUGH*/
860 	case 2: if ((*(c+1) & 0xc0) != 0x80) return 0; /*FALLTHROUGH*/
861 	}
862 	return rc;
863 }
864 #define UTF8CHARMAX 4
865 
866 /*
867  * read UTF-8 value
868  * returns a the codepoint number
869  */
870 uint_fast32_t
871 get_utf8_value(const char *c) {
872 	uint_fast32_t sum;
873 	unsigned nb, i;
874 
875 	/* first byte gives sequence length */
876 	     if ((*c & 0x80) == 0x00) return *c;/* 0bbbbbbb -- ASCII */
877 	else if ((*c & 0xc0) == 0x80) return 0; /* 10bbbbbb -- trailing byte */
878 	else if ((*c & 0xe0) == 0xc0) {		/* 110bbbbb */
879 		nb = 2;
880 		sum = (*c & ~0xe0) & 0xff;
881 	} else if ((*c & 0xf0) == 0xe0) {	/* 1110bbbb */
882 		nb = 3;
883 		sum = (*c & ~0xf0) & 0xff;
884 	} else if ((*c & 0xf8) == 0xf0) {	/* 11110bbb */
885 		nb = 4;
886 		sum = (*c & ~0xf8) & 0xff;
887 	} else return 0; /* UTF-8 allows only up to 4 bytes */
888 
889 	/* check trailing bytes -- 10bbbbbb */
890 	i = 1;
891 	while (i < nb) {
892 		sum <<= 6;
893 		sum |= ((*(c+i) & ~0xc0) & 0xff);
894 		i++;
895 	}
896 	return sum;
897 }
898 
899 /* note previous versions transscribe
900  * control characters, e.g. \007 --> "^G"
901  * did anyone rely on that?
902  *
903  * this new version works on only one buffer and
904  * replaces control characters with a space
905  */
906 #define NEXTFIELD(ptr) if (*(p) == ' ') (p)++; /* SP */			\
907 		       else {						\
908 				DPRINTF(D_DATA, "format error\n");	\
909 				if (*(p) == '\0') start = (p);		\
910 				goto all_syslog_msg;			\
911 		       }
912 #define FORCE2ASCII(c) ((iscntrl((unsigned char)(c)) && (c) != '\t')	\
913 			? ((c) == '\n' ? ' ' : '?')			\
914 			: (c) & 0177)
915 
916 /* following syslog-protocol */
917 #define printusascii(ch) (ch >= 33 && ch <= 126)
918 #define sdname(ch) (ch != '=' && ch != ' ' \
919 		 && ch != ']' && ch != '"' \
920 		 && printusascii(ch))
921 
922 /* checks whether the first word of string p can be interpreted as
923  * a syslog-protocol MSGID and if so returns its length.
924  *
925  * otherwise returns 0
926  */
927 static unsigned
928 check_msgid(char *p)
929 {
930 	char *q = p;
931 
932 	/* consider the NILVALUE to be valid */
933 	if (*q == '-' && *(q+1) == ' ')
934 		return 1;
935 
936 	for (;;) {
937 		if (*q == ' ')
938 			return q - p;
939 		else if (*q == '\0' || !printusascii(*q) || q - p >= MSGID_MAX)
940 			return 0;
941 		else
942 			q++;
943 	}
944 }
945 
946 /*
947  * returns number of chars found in SD at beginning of string p
948  * thus returns 0 if no valid SD is found
949  *
950  * if ascii == true then substitute all non-ASCII chars
951  * otherwise use syslog-protocol rules to allow UTF-8 in values
952  * note: one pass for filtering and scanning, so a found SD
953  * is always filtered, but an invalid one could be partially
954  * filtered up to the format error.
955  */
956 static unsigned
957 check_sd(char* p)
958 {
959 	char *q = p;
960 	bool esc = false;
961 
962 	/* consider the NILVALUE to be valid */
963 	if (*q == '-' && (*(q+1) == ' ' || *(q+1) == '\0'))
964 		return 1;
965 
966 	for(;;) { /* SD-ELEMENT */
967 		if (*q++ != '[') return 0;
968 		/* SD-ID */
969 		if (!sdname(*q)) return 0;
970 		while (sdname(*q)) {
971 			*q = FORCE2ASCII(*q);
972 			q++;
973 		}
974 		for(;;) { /* SD-PARAM */
975 			if (*q == ']') {
976 				q++;
977 				if (*q == ' ' || *q == '\0') return q - p;
978 				else if (*q == '[') break;
979 			} else if (*q++ != ' ') return 0;
980 
981 			/* PARAM-NAME */
982 			if (!sdname(*q)) return 0;
983 			while (sdname(*q)) {
984 				*q = FORCE2ASCII(*q);
985 				q++;
986 			}
987 
988 			if (*q++ != '=') return 0;
989 			if (*q++ != '"') return 0;
990 
991 			for(;;) { /* PARAM-VALUE */
992 				if (esc) {
993 					esc = false;
994 					if (*q == '\\' || *q == '"' ||
995 					    *q == ']') {
996 						q++;
997 						continue;
998 					}
999 					/* no else because invalid
1000 					 * escape sequences are accepted */
1001 				}
1002 				else if (*q == '"') break;
1003 				else if (*q == '\0' || *q == ']') return 0;
1004 				else if (*q == '\\') esc = true;
1005 				else {
1006 					int i;
1007 					i = valid_utf8(q);
1008 					if (i == 0)
1009 						*q = '?';
1010 					else if (i == 1)
1011 						*q = FORCE2ASCII(*q);
1012 					else /* multi byte char */
1013 						q += (i-1);
1014 				}
1015 				q++;
1016 			}
1017 			q++;
1018 		}
1019 	}
1020 }
1021 
1022 struct buf_msg *
1023 printline_syslogprotocol(const char *hname, char *msg,
1024 	int flags, int pri)
1025 {
1026 	struct buf_msg *buffer;
1027 	char *p, *start;
1028 	unsigned sdlen = 0, i = 0;
1029 	bool utf8allowed = false; /* for some fields */
1030 
1031 	DPRINTF((D_CALL|D_BUFFER|D_DATA), "printline_syslogprotocol("
1032 	    "\"%s\", \"%s\", %d, %d)\n", hname, msg, flags, pri);
1033 
1034 	buffer = buf_msg_new(0);
1035 	p = msg;
1036 	p += check_timestamp((unsigned char*) p,
1037 		&buffer->timestamp, true, !BSDOutputFormat);
1038 	DPRINTF(D_DATA, "Got timestamp \"%s\"\n", buffer->timestamp);
1039 
1040 	if (flags & ADDDATE) {
1041 		FREEPTR(buffer->timestamp);
1042 		buffer->timestamp = strdup(make_timestamp(NULL,
1043 			!BSDOutputFormat));
1044 	}
1045 
1046 	start = p;
1047 	NEXTFIELD(p);
1048 	/* extract host */
1049 	for (start = p;; p++) {
1050 		if ((*p == ' ' || *p == '\0')
1051 		    && start == p-1 && *(p-1) == '-') {
1052 			/* NILVALUE */
1053 			break;
1054 		} else if ((*p == ' ' || *p == '\0')
1055 		    && (start != p-1 || *(p-1) != '-')) {
1056 			buffer->host = strndup(start, p - start);
1057 			break;
1058 		} else {
1059 			*p = FORCE2ASCII(*p);
1060 		}
1061 	}
1062 	/* p @ SP after host */
1063 	DPRINTF(D_DATA, "Got host \"%s\"\n", buffer->host);
1064 
1065 	/* extract app-name */
1066 	NEXTFIELD(p);
1067 	for (start = p;; p++) {
1068 		if ((*p == ' ' || *p == '\0')
1069 		    && start == p-1 && *(p-1) == '-') {
1070 			/* NILVALUE */
1071 			break;
1072 		} else if ((*p == ' ' || *p == '\0')
1073 		    && (start != p-1 || *(p-1) != '-')) {
1074 			buffer->prog = strndup(start, p - start);
1075 			break;
1076 		} else {
1077 			*p = FORCE2ASCII(*p);
1078 		}
1079 	}
1080 	DPRINTF(D_DATA, "Got prog \"%s\"\n", buffer->prog);
1081 
1082 	/* extract procid */
1083 	NEXTFIELD(p);
1084 	for (start = p;; p++) {
1085 		if ((*p == ' ' || *p == '\0')
1086 		    && start == p-1 && *(p-1) == '-') {
1087 			/* NILVALUE */
1088 			break;
1089 		} else if ((*p == ' ' || *p == '\0')
1090 		    && (start != p-1 || *(p-1) != '-')) {
1091 			buffer->pid = strndup(start, p - start);
1092 			start = p;
1093 			break;
1094 		} else {
1095 			*p = FORCE2ASCII(*p);
1096 		}
1097 	}
1098 	DPRINTF(D_DATA, "Got pid \"%s\"\n", buffer->pid);
1099 
1100 	/* extract msgid */
1101 	NEXTFIELD(p);
1102 	for (start = p;; p++) {
1103 		if ((*p == ' ' || *p == '\0')
1104 		    && start == p-1 && *(p-1) == '-') {
1105 			/* NILVALUE */
1106 			start = p+1;
1107 			break;
1108 		} else if ((*p == ' ' || *p == '\0')
1109 		    && (start != p-1 || *(p-1) != '-')) {
1110 			buffer->msgid = strndup(start, p - start);
1111 			start = p+1;
1112 			break;
1113 		} else {
1114 			*p = FORCE2ASCII(*p);
1115 		}
1116 	}
1117 	DPRINTF(D_DATA, "Got msgid \"%s\"\n", buffer->msgid);
1118 
1119 	/* extract SD */
1120 	NEXTFIELD(p);
1121 	start = p;
1122 	sdlen = check_sd(p);
1123 	DPRINTF(D_DATA, "check_sd(\"%s\") returned %d\n", p, sdlen);
1124 
1125 	if (sdlen == 1 && *p == '-') {
1126 		/* NILVALUE */
1127 		p++;
1128 	} else if (sdlen > 1) {
1129 		buffer->sd = strndup(p, sdlen);
1130 		p += sdlen;
1131 	} else {
1132 		DPRINTF(D_DATA, "format error\n");
1133 	}
1134 	if	(*p == '\0') start = p;
1135 	else if (*p == ' ')  start = ++p; /* SP */
1136 	DPRINTF(D_DATA, "Got SD \"%s\"\n", buffer->sd);
1137 
1138 	/* and now the message itself
1139 	 * note: move back to last start to check for BOM
1140 	 */
1141 all_syslog_msg:
1142 	p = start;
1143 
1144 	/* check for UTF-8-BOM */
1145 	if (IS_BOM(p)) {
1146 		DPRINTF(D_DATA, "UTF-8 BOM\n");
1147 		utf8allowed = true;
1148 		p += 3;
1149 	}
1150 
1151 	if (*p != '\0' && !utf8allowed) {
1152 		size_t msglen;
1153 
1154 		msglen = strlen(p);
1155 		assert(!buffer->msg);
1156 		buffer->msg = copy_utf8_ascii(p, msglen);
1157 		buffer->msgorig = buffer->msg;
1158 		buffer->msglen = buffer->msgsize = strlen(buffer->msg)+1;
1159 	} else if (*p != '\0' && utf8allowed) {
1160 		while (*p != '\0') {
1161 			i = valid_utf8(p);
1162 			if (i == 0)
1163 				*p++ = '?';
1164 			else if (i == 1)
1165 				*p = FORCE2ASCII(*p);
1166 			p += i;
1167 		}
1168 		assert(p != start);
1169 		assert(!buffer->msg);
1170 		buffer->msg = strndup(start, p - start);
1171 		buffer->msgorig = buffer->msg;
1172 		buffer->msglen = buffer->msgsize = 1 + p - start;
1173 	}
1174 	DPRINTF(D_DATA, "Got msg \"%s\"\n", buffer->msg);
1175 
1176 	buffer->recvhost = strdup(hname);
1177 	buffer->pri = pri;
1178 	buffer->flags = flags;
1179 
1180 	return buffer;
1181 }
1182 
1183 /* copies an input into a new ASCII buffer
1184  * ASCII controls are converted to format "^X"
1185  * multi-byte UTF-8 chars are converted to format "<ab><cd>"
1186  */
1187 #define INIT_BUFSIZE 512
1188 char *
1189 copy_utf8_ascii(char *p, size_t p_len)
1190 {
1191 	size_t idst = 0, isrc = 0, dstsize = INIT_BUFSIZE, i;
1192 	char *dst, *tmp_dst;
1193 
1194 	MALLOC(dst, dstsize);
1195 	while (isrc < p_len) {
1196 		if (dstsize < idst + 10) {
1197 			/* check for enough space for \0 and a UTF-8
1198 			 * conversion; longest possible is <U+123456> */
1199 			tmp_dst = realloc(dst, dstsize + INIT_BUFSIZE);
1200 			if (!tmp_dst)
1201 				break;
1202 			dst = tmp_dst;
1203 			dstsize += INIT_BUFSIZE;
1204 		}
1205 
1206 		i = valid_utf8(&p[isrc]);
1207 		if (i == 0) { /* invalid encoding */
1208 			dst[idst++] = '?';
1209 			isrc++;
1210 		} else if (i == 1) { /* check printable */
1211 			if (iscntrl((unsigned char)p[isrc])
1212 			 && p[isrc] != '\t') {
1213 				if (p[isrc] == '\n') {
1214 					dst[idst++] = ' ';
1215 					isrc++;
1216 				} else {
1217 					dst[idst++] = '^';
1218 					dst[idst++] = p[isrc++] ^ 0100;
1219 				}
1220 			} else
1221 				dst[idst++] = p[isrc++];
1222 		} else {  /* convert UTF-8 to ASCII */
1223 			dst[idst++] = '<';
1224 			idst += snprintf(&dst[idst], dstsize - idst, "U+%x",
1225 			    get_utf8_value(&p[isrc]));
1226 			isrc += i;
1227 			dst[idst++] = '>';
1228 		}
1229 	}
1230 	dst[idst] = '\0';
1231 
1232 	/* shrink buffer to right size */
1233 	tmp_dst = realloc(dst, idst+1);
1234 	if (tmp_dst)
1235 		return tmp_dst;
1236 	else
1237 		return dst;
1238 }
1239 
1240 struct buf_msg *
1241 printline_bsdsyslog(const char *hname, char *msg,
1242 	int flags, int pri)
1243 {
1244 	struct buf_msg *buffer;
1245 	char *p, *start;
1246 	unsigned msgidlen = 0, sdlen = 0;
1247 
1248 	DPRINTF((D_CALL|D_BUFFER|D_DATA), "printline_bsdsyslog("
1249 		"\"%s\", \"%s\", %d, %d)\n", hname, msg, flags, pri);
1250 
1251 	buffer = buf_msg_new(0);
1252 	p = msg;
1253 	p += check_timestamp((unsigned char*) p,
1254 		&buffer->timestamp, false, !BSDOutputFormat);
1255 	DPRINTF(D_DATA, "Got timestamp \"%s\"\n", buffer->timestamp);
1256 
1257 	if (flags & ADDDATE || !buffer->timestamp) {
1258 		FREEPTR(buffer->timestamp);
1259 		buffer->timestamp = strdup(make_timestamp(NULL,
1260 			!BSDOutputFormat));
1261 	}
1262 
1263 	if (*p == ' ') p++; /* SP */
1264 	else goto all_bsd_msg;
1265 	/* in any error case we skip header parsing and
1266 	 * treat all following data as message content */
1267 
1268 	/* extract host */
1269 	for (start = p;; p++) {
1270 		if (*p == ' ' || *p == '\0') {
1271 			buffer->host = strndup(start, p - start);
1272 			break;
1273 		} else if (*p == '[' || (*p == ':'
1274 			&& (*(p+1) == ' ' || *(p+1) == '\0'))) {
1275 			/* no host in message */
1276 			buffer->host = LocalFQDN;
1277 			buffer->prog = strndup(start, p - start);
1278 			break;
1279 		} else {
1280 			*p = FORCE2ASCII(*p);
1281 		}
1282 	}
1283 	DPRINTF(D_DATA, "Got host \"%s\"\n", buffer->host);
1284 	/* p @ SP after host, or @ :/[ after prog */
1285 
1286 	/* extract program */
1287 	if (!buffer->prog) {
1288 		if (*p == ' ') p++; /* SP */
1289 		else goto all_bsd_msg;
1290 
1291 		for (start = p;; p++) {
1292 			if (*p == ' ' || *p == '\0') { /* error */
1293 				goto all_bsd_msg;
1294 			} else if (*p == '[' || (*p == ':'
1295 				&& (*(p+1) == ' ' || *(p+1) == '\0'))) {
1296 				buffer->prog = strndup(start, p - start);
1297 				break;
1298 			} else {
1299 				*p = FORCE2ASCII(*p);
1300 			}
1301 		}
1302 	}
1303 	DPRINTF(D_DATA, "Got prog \"%s\"\n", buffer->prog);
1304 	start = p;
1305 
1306 	/* p @ :/[ after prog */
1307 	if (*p == '[') {
1308 		p++;
1309 		if (*p == ' ') p++; /* SP */
1310 		for (start = p;; p++) {
1311 			if (*p == ' ' || *p == '\0') { /* error */
1312 				goto all_bsd_msg;
1313 			} else if (*p == ']') {
1314 				buffer->pid = strndup(start, p - start);
1315 				break;
1316 			} else {
1317 				*p = FORCE2ASCII(*p);
1318 			}
1319 		}
1320 	}
1321 	DPRINTF(D_DATA, "Got pid \"%s\"\n", buffer->pid);
1322 
1323 	if (*p == ']') p++;
1324 	if (*p == ':') p++;
1325 	if (*p == ' ') p++;
1326 
1327 	/* p @ msgid, @ opening [ of SD or @ first byte of message
1328 	 * accept either case and try to detect MSGID and SD fields
1329 	 *
1330 	 * only limitation: we do not accept UTF-8 data in
1331 	 * BSD Syslog messages -- so all SD values are ASCII-filtered
1332 	 *
1333 	 * I have found one scenario with 'unexpected' behaviour:
1334 	 * if there is only a SD intended, but a) it is short enough
1335 	 * to be a MSGID and b) the first word of the message can also
1336 	 * be parsed as an SD.
1337 	 * example:
1338 	 * "<35>Jul  6 12:39:08 tag[123]: [exampleSDID@0] - hello"
1339 	 * --> parsed as
1340 	 *     MSGID = "[exampleSDID@0]"
1341 	 *     SD    = "-"
1342 	 *     MSG   = "hello"
1343 	 */
1344 	start = p;
1345 	msgidlen = check_msgid(p);
1346 	if (msgidlen) /* check for SD in 2nd field */
1347 		sdlen = check_sd(p+msgidlen+1);
1348 
1349 	if (msgidlen && sdlen) {
1350 		/* MSGID in 1st and SD in 2nd field
1351 		 * now check for NILVALUEs and copy */
1352 		if (msgidlen == 1 && *p == '-') {
1353 			p++; /* - */
1354 			p++; /* SP */
1355 			DPRINTF(D_DATA, "Got MSGID \"-\"\n");
1356 		} else {
1357 			/* only has ASCII chars after check_msgid() */
1358 			buffer->msgid = strndup(p, msgidlen);
1359 			p += msgidlen;
1360 			p++; /* SP */
1361 			DPRINTF(D_DATA, "Got MSGID \"%s\"\n",
1362 				buffer->msgid);
1363 		}
1364 	} else {
1365 		/* either no msgid or no SD in 2nd field
1366 		 * --> check 1st field for SD */
1367 		DPRINTF(D_DATA, "No MSGID\n");
1368 		sdlen = check_sd(p);
1369 	}
1370 
1371 	if (sdlen == 0) {
1372 		DPRINTF(D_DATA, "No SD\n");
1373 	} else if (sdlen > 1) {
1374 		buffer->sd = copy_utf8_ascii(p, sdlen);
1375 		DPRINTF(D_DATA, "Got SD \"%s\"\n", buffer->sd);
1376 	} else if (sdlen == 1 && *p == '-') {
1377 		p++;
1378 		DPRINTF(D_DATA, "Got SD \"-\"\n");
1379 	} else {
1380 		DPRINTF(D_DATA, "Error\n");
1381 	}
1382 
1383 	if (*p == ' ') p++;
1384 	start = p;
1385 	/* and now the message itself
1386 	 * note: do not reset start, because we might come here
1387 	 * by goto and want to have the incomplete field as part
1388 	 * of the msg
1389 	 */
1390 all_bsd_msg:
1391 	if (*p != '\0') {
1392 		size_t msglen = strlen(p);
1393 		buffer->msg = copy_utf8_ascii(p, msglen);
1394 		buffer->msgorig = buffer->msg;
1395 		buffer->msglen = buffer->msgsize = strlen(buffer->msg)+1;
1396 	}
1397 	DPRINTF(D_DATA, "Got msg \"%s\"\n", buffer->msg);
1398 
1399 	buffer->recvhost = strdup(hname);
1400 	buffer->pri = pri;
1401 	buffer->flags = flags | BSDSYSLOG;
1402 
1403 	return buffer;
1404 }
1405 
1406 struct buf_msg *
1407 printline_kernelprintf(const char *hname, char *msg,
1408 	int flags, int pri)
1409 {
1410 	struct buf_msg *buffer;
1411 	char *p;
1412 	unsigned sdlen = 0;
1413 
1414 	DPRINTF((D_CALL|D_BUFFER|D_DATA), "printline_kernelprintf("
1415 		"\"%s\", \"%s\", %d, %d)\n", hname, msg, flags, pri);
1416 
1417 	buffer = buf_msg_new(0);
1418 	buffer->timestamp = strdup(make_timestamp(NULL, !BSDOutputFormat));
1419 	buffer->pri = pri;
1420 	buffer->flags = flags;
1421 
1422 	/* assume there is no MSGID but there might be SD */
1423 	p = msg;
1424 	sdlen = check_sd(p);
1425 
1426 	if (sdlen == 0) {
1427 		DPRINTF(D_DATA, "No SD\n");
1428 	} else if (sdlen > 1) {
1429 		buffer->sd = copy_utf8_ascii(p, sdlen);
1430 		DPRINTF(D_DATA, "Got SD \"%s\"\n", buffer->sd);
1431 	} else if (sdlen == 1 && *p == '-') {
1432 		p++;
1433 		DPRINTF(D_DATA, "Got SD \"-\"\n");
1434 	} else {
1435 		DPRINTF(D_DATA, "Error\n");
1436 	}
1437 
1438 	if (*p == ' ') p++;
1439 	if (*p != '\0') {
1440 		size_t msglen = strlen(p);
1441 		buffer->msg = copy_utf8_ascii(p, msglen);
1442 		buffer->msgorig = buffer->msg;
1443 		buffer->msglen = buffer->msgsize = strlen(buffer->msg)+1;
1444 	}
1445 	DPRINTF(D_DATA, "Got msg \"%s\"\n", buffer->msg);
1446 
1447 	return buffer;
1448 }
1449 
1450 /*
1451  * Take a raw input line, read priority and version, call the
1452  * right message parsing function, then call logmsg().
1453  */
1454 void
1455 printline(const char *hname, char *msg, int flags)
1456 {
1457 	struct buf_msg *buffer;
1458 	int pri;
1459 	char *p, *q;
1460 	long n;
1461 	bool bsdsyslog = true;
1462 
1463 	DPRINTF((D_CALL|D_BUFFER|D_DATA),
1464 		"printline(\"%s\", \"%s\", %d)\n", hname, msg, flags);
1465 
1466 	/* test for special codes */
1467 	pri = DEFUPRI;
1468 	p = msg;
1469 	if (*p == '<') {
1470 		errno = 0;
1471 		n = strtol(p + 1, &q, 10);
1472 		if (*q == '>' && n >= 0 && n < INT_MAX && errno == 0) {
1473 			p = q + 1;
1474 			pri = (int)n;
1475 			/* check for syslog-protocol version */
1476 			if (*p == '1' && p[1] == ' ') {
1477 				p += 2;	 /* skip version and space */
1478 				bsdsyslog = false;
1479 			} else {
1480 				bsdsyslog = true;
1481 			}
1482 		}
1483 	}
1484 	if (pri & ~(LOG_FACMASK|LOG_PRIMASK))
1485 		pri = DEFUPRI;
1486 
1487 	/*
1488 	 * Don't allow users to log kernel messages.
1489 	 * NOTE: Since LOG_KERN == 0, this will also match
1490 	 *	 messages with no facility specified.
1491 	 */
1492 	if ((pri & LOG_FACMASK) == LOG_KERN)
1493 		pri = LOG_MAKEPRI(LOG_USER, LOG_PRI(pri));
1494 
1495 	if (bsdsyslog) {
1496 		buffer = printline_bsdsyslog(hname, p, flags, pri);
1497 	} else {
1498 		buffer = printline_syslogprotocol(hname, p, flags, pri);
1499 	}
1500 	logmsg(buffer);
1501 	DELREF(buffer);
1502 }
1503 
1504 /*
1505  * Take a raw input line from /dev/klog, split and format similar to syslog().
1506  */
1507 void
1508 printsys(char *msg)
1509 {
1510 	int n, is_printf, pri, flags;
1511 	char *p, *q;
1512 	struct buf_msg *buffer;
1513 
1514 	klog_linebufoff = 0;
1515 	for (p = msg; *p != '\0'; ) {
1516 		bool bsdsyslog = true;
1517 
1518 		is_printf = 1;
1519 		flags = ISKERNEL | ADDDATE | BSDSYSLOG;
1520 		if (SyncKernel)
1521 			flags |= SYNC_FILE;
1522 		if (is_printf) /* kernel printf's come out on console */
1523 			flags |= IGN_CONS;
1524 		pri = DEFSPRI;
1525 
1526 		if (*p == '<') {
1527 			errno = 0;
1528 			n = (int)strtol(p + 1, &q, 10);
1529 			if (*q == '>' && n >= 0 && n < INT_MAX && errno == 0) {
1530 				p = q + 1;
1531 				is_printf = 0;
1532 				pri = n;
1533 				if (*p == '1') { /* syslog-protocol version */
1534 					p += 2;	 /* skip version and space */
1535 					bsdsyslog = false;
1536 				} else {
1537 					bsdsyslog = true;
1538 				}
1539 			}
1540 		}
1541 		for (q = p; *q != '\0' && *q != '\n'; q++)
1542 			/* look for end of line; no further checks.
1543 			 * trust the kernel to send ASCII only */;
1544 		if (*q != '\0')
1545 			*q++ = '\0';
1546 		else {
1547 			memcpy(linebuf, p, klog_linebufoff = q - p);
1548 			break;
1549 		}
1550 
1551 		if (pri &~ (LOG_FACMASK|LOG_PRIMASK))
1552 			pri = DEFSPRI;
1553 
1554 		/* allow all kinds of input from kernel */
1555 		if (is_printf)
1556 			buffer = printline_kernelprintf(
1557 			    LocalFQDN, p, flags, pri);
1558 		else {
1559 			if (bsdsyslog)
1560 				buffer = printline_bsdsyslog(
1561 				    LocalFQDN, p, flags, pri);
1562 			else
1563 				buffer = printline_syslogprotocol(
1564 				    LocalFQDN, p, flags, pri);
1565 		}
1566 
1567 		/* set fields left open */
1568 		if (!buffer->prog)
1569 			buffer->prog = strdup(_PATH_UNIX);
1570 		if (!buffer->host)
1571 			buffer->host = LocalFQDN;
1572 		if (!buffer->recvhost)
1573 			buffer->recvhost = LocalFQDN;
1574 
1575 		logmsg(buffer);
1576 		DELREF(buffer);
1577 		p = q;
1578 	}
1579 }
1580 
1581 /*
1582  * Check to see if `name' matches the provided specification, using the
1583  * specified strstr function.
1584  */
1585 int
1586 matches_spec(const char *name, const char *spec,
1587     char *(*check)(const char *, const char *))
1588 {
1589 	const char *s;
1590 	const char *cursor;
1591 	char prev, next;
1592 	size_t len;
1593 
1594 	if (name[0] == '\0')
1595 		return 0;
1596 
1597 	if (strchr(name, ',')) /* sanity */
1598 		return 0;
1599 
1600 	len = strlen(name);
1601 	cursor = spec;
1602 	while ((s = (*check)(cursor, name)) != NULL) {
1603 		prev = s == spec ? ',' : *(s - 1);
1604 		cursor = s + len;
1605 		next = *cursor;
1606 
1607 		if (prev == ',' && (next == '\0' || next == ','))
1608 			return 1;
1609 	}
1610 
1611 	return 0;
1612 }
1613 
1614 /*
1615  * wrapper with old function signature,
1616  * keeps calling code shorter and hides buffer allocation
1617  */
1618 void
1619 logmsg_async(int pri, const char *sd, const char *msg, int flags)
1620 {
1621 	struct buf_msg *buffer;
1622 	size_t msglen;
1623 
1624 	DPRINTF((D_CALL|D_DATA), "logmsg_async(%d, \"%s\", \"%s\", %d)\n",
1625 	    pri, sd, msg, flags);
1626 
1627 	if (msg) {
1628 		msglen = strlen(msg);
1629 		msglen++;		/* adds \0 */
1630 		buffer = buf_msg_new(msglen);
1631 		buffer->msglen = strlcpy(buffer->msg, msg, msglen) + 1;
1632 	} else {
1633 		buffer = buf_msg_new(0);
1634 	}
1635 	if (sd) buffer->sd = strdup(sd);
1636 	buffer->timestamp = strdup(make_timestamp(NULL, !BSDOutputFormat));
1637 	buffer->prog = appname;
1638 	buffer->pid = include_pid;
1639 	buffer->recvhost = buffer->host = LocalFQDN;
1640 	buffer->pri = pri;
1641 	buffer->flags = flags;
1642 
1643 	logmsg(buffer);
1644 	DELREF(buffer);
1645 }
1646 
1647 /* read timestamp in from_buf, convert into a timestamp in to_buf
1648  *
1649  * returns length of timestamp found in from_buf (= number of bytes consumed)
1650  */
1651 size_t
1652 check_timestamp(unsigned char *from_buf, char **to_buf,
1653 	bool from_iso, bool to_iso)
1654 {
1655 	unsigned char *q;
1656 	int p;
1657 	bool found_ts = false;
1658 
1659 	DPRINTF((D_CALL|D_DATA), "check_timestamp(%p = \"%s\", from_iso=%d, "
1660 	    "to_iso=%d)\n", from_buf, from_buf, from_iso, to_iso);
1661 
1662 	if (!from_buf) return 0;
1663 	/*
1664 	 * Check to see if msg looks non-standard.
1665 	 * looks at every char because we do not have a msg length yet
1666 	 */
1667 	/* detailed checking adapted from Albert Mietus' sl_timestamp.c */
1668 	if (from_iso) {
1669 		if (from_buf[4] == '-' && from_buf[7] == '-'
1670 		    && from_buf[10] == 'T' && from_buf[13] == ':'
1671 		    && from_buf[16] == ':'
1672 		    && isdigit(from_buf[0]) && isdigit(from_buf[1])
1673 		    && isdigit(from_buf[2]) && isdigit(from_buf[3])  /* YYYY */
1674 		    && isdigit(from_buf[5]) && isdigit(from_buf[6])
1675 		    && isdigit(from_buf[8]) && isdigit(from_buf[9])  /* mm dd */
1676 		    && isdigit(from_buf[11]) && isdigit(from_buf[12]) /* HH */
1677 		    && isdigit(from_buf[14]) && isdigit(from_buf[15]) /* MM */
1678 		    && isdigit(from_buf[17]) && isdigit(from_buf[18]) /* SS */
1679 		    )  {
1680 			/* time-secfrac */
1681 			if (from_buf[19] == '.')
1682 				for (p=20; isdigit(from_buf[p]); p++) /* NOP*/;
1683 			else
1684 				p = 19;
1685 			/* time-offset */
1686 			if (from_buf[p] == 'Z'
1687 			 || ((from_buf[p] == '+' || from_buf[p] == '-')
1688 			    && from_buf[p+3] == ':'
1689 			    && isdigit(from_buf[p+1]) && isdigit(from_buf[p+2])
1690 			    && isdigit(from_buf[p+4]) && isdigit(from_buf[p+5])
1691 			 ))
1692 				found_ts = true;
1693 		}
1694 	} else {
1695 		if (from_buf[3] == ' ' && from_buf[6] == ' '
1696 		    && from_buf[9] == ':' && from_buf[12] == ':'
1697 		    && (from_buf[4] == ' ' || isdigit(from_buf[4]))
1698 		    && isdigit(from_buf[5]) /* dd */
1699 		    && isdigit(from_buf[7])  && isdigit(from_buf[8])   /* HH */
1700 		    && isdigit(from_buf[10]) && isdigit(from_buf[11])  /* MM */
1701 		    && isdigit(from_buf[13]) && isdigit(from_buf[14])  /* SS */
1702 		    && isupper(from_buf[0]) && islower(from_buf[1]) /* month */
1703 		    && islower(from_buf[2]))
1704 			found_ts = true;
1705 	}
1706 	if (!found_ts) {
1707 		if (from_buf[0] == '-' && from_buf[1] == ' ') {
1708 			/* NILVALUE */
1709 			if (to_iso) {
1710 				/* with ISO = syslog-protocol output leave
1711 			 	 * it as is, because it is better to have
1712 			 	 * no timestamp than a wrong one.
1713 			 	 */
1714 				*to_buf = strdup("-");
1715 			} else {
1716 				/* with BSD Syslog the field is reqired
1717 				 * so replace it with current time
1718 				 */
1719 				*to_buf = strdup(make_timestamp(NULL, false));
1720 			}
1721 			return 2;
1722 		}
1723 		return 0;
1724 	}
1725 
1726 	if (!from_iso && !to_iso) {
1727 		/* copy BSD timestamp */
1728 		DPRINTF(D_CALL, "check_timestamp(): copy BSD timestamp\n");
1729 		*to_buf = strndup((char *)from_buf, BSD_TIMESTAMPLEN);
1730 		return BSD_TIMESTAMPLEN;
1731 	} else if (from_iso && to_iso) {
1732 		/* copy ISO timestamp */
1733 		DPRINTF(D_CALL, "check_timestamp(): copy ISO timestamp\n");
1734 		if (!(q = (unsigned char *) strchr((char *)from_buf, ' ')))
1735 			q = from_buf + strlen((char *)from_buf);
1736 		*to_buf = strndup((char *)from_buf, q - from_buf);
1737 		return q - from_buf;
1738 	} else if (from_iso && !to_iso) {
1739 		/* convert ISO->BSD */
1740 		struct tm parsed;
1741 		time_t timeval;
1742 		char tsbuf[MAX_TIMESTAMPLEN];
1743 		int i = 0;
1744 
1745 		DPRINTF(D_CALL, "check_timestamp(): convert ISO->BSD\n");
1746 		for(i = 0; i < MAX_TIMESTAMPLEN && from_buf[i] != '\0'
1747 		    && from_buf[i] != '.' && from_buf[i] != ' '; i++)
1748 			tsbuf[i] = from_buf[i]; /* copy date & time */
1749 		for(; i < MAX_TIMESTAMPLEN && from_buf[i] != '\0'
1750 		    && from_buf[i] != '+' && from_buf[i] != '-'
1751 		    && from_buf[i] != 'Z' && from_buf[i] != ' '; i++)
1752 			;			   /* skip fraction digits */
1753 		for(; i < MAX_TIMESTAMPLEN && from_buf[i] != '\0'
1754 		    && from_buf[i] != ':' && from_buf[i] != ' ' ; i++)
1755 			tsbuf[i] = from_buf[i]; /* copy TZ */
1756 		if (from_buf[i] == ':') i++;	/* skip colon */
1757 		for(; i < MAX_TIMESTAMPLEN && from_buf[i] != '\0'
1758 		    && from_buf[i] != ' ' ; i++)
1759 			tsbuf[i] = from_buf[i]; /* copy TZ */
1760 
1761 		(void)memset(&parsed, 0, sizeof(parsed));
1762 		parsed.tm_isdst = -1;
1763 		(void)strptime(tsbuf, "%FT%T%z", &parsed);
1764 		timeval = mktime(&parsed);
1765 
1766 		*to_buf = strndup(make_timestamp(&timeval, false),
1767 		    BSD_TIMESTAMPLEN);
1768 		return i;
1769 	} else if (!from_iso && to_iso) {
1770 		/* convert BSD->ISO */
1771 		struct tm parsed;
1772 		struct tm *current;
1773 		time_t timeval;
1774 		char *rc;
1775 
1776 		(void)memset(&parsed, 0, sizeof(parsed));
1777 		parsed.tm_isdst = -1;
1778 		DPRINTF(D_CALL, "check_timestamp(): convert BSD->ISO\n");
1779 		rc = strptime((char *)from_buf, "%b %d %T", &parsed);
1780 		current = gmtime(&now);
1781 
1782 		/* use current year and timezone */
1783 		parsed.tm_isdst = current->tm_isdst;
1784 		parsed.tm_gmtoff = current->tm_gmtoff;
1785 		parsed.tm_year = current->tm_year;
1786 		if (current->tm_mon == 0 && parsed.tm_mon == 11)
1787 			parsed.tm_year--;
1788 
1789 		timeval = mktime(&parsed);
1790 		rc = make_timestamp(&timeval, true);
1791 		*to_buf = strndup(rc, MAX_TIMESTAMPLEN-1);
1792 
1793 		return BSD_TIMESTAMPLEN;
1794 	} else {
1795 		DPRINTF(D_MISC,
1796 			"Executing unreachable code in check_timestamp()\n");
1797 		return 0;
1798 	}
1799 }
1800 
1801 /*
1802  * Log a message to the appropriate log files, users, etc. based on
1803  * the priority.
1804  */
1805 void
1806 logmsg(struct buf_msg *buffer)
1807 {
1808 	struct filed *f;
1809 	int fac, omask, prilev;
1810 
1811 	DPRINTF((D_CALL|D_BUFFER), "logmsg: buffer@%p, pri 0%o/%d, flags 0x%x,"
1812 	    " timestamp \"%s\", from \"%s\", sd \"%s\", msg \"%s\"\n",
1813 	    buffer, buffer->pri, buffer->pri, buffer->flags,
1814 	    buffer->timestamp, buffer->recvhost, buffer->sd, buffer->msg);
1815 
1816 	omask = sigblock(sigmask(SIGHUP)|sigmask(SIGALRM));
1817 
1818 	/* sanity check */
1819 	assert(buffer->refcount == 1);
1820 	assert(buffer->msglen <= buffer->msgsize);
1821 	assert(buffer->msgorig <= buffer->msg);
1822 	assert((buffer->msg && buffer->msglen == strlen(buffer->msg)+1)
1823 	      || (!buffer->msg && !buffer->msglen));
1824 	if (!buffer->msg && !buffer->sd && !buffer->msgid)
1825 		DPRINTF(D_BUFFER, "Empty message?\n");
1826 
1827 	/* extract facility and priority level */
1828 	if (buffer->flags & MARK)
1829 		fac = LOG_NFACILITIES;
1830 	else
1831 		fac = LOG_FAC(buffer->pri);
1832 	prilev = LOG_PRI(buffer->pri);
1833 
1834 	/* log the message to the particular outputs */
1835 	if (!Initialized) {
1836 		f = &consfile;
1837 		f->f_file = open(ctty, O_WRONLY, 0);
1838 
1839 		if (f->f_file >= 0) {
1840 			DELREF(f->f_prevmsg);
1841 			f->f_prevmsg = NEWREF(buffer);
1842 			fprintlog(f, NEWREF(buffer), NULL);
1843 			DELREF(buffer);
1844 			(void)close(f->f_file);
1845 		}
1846 		(void)sigsetmask(omask);
1847 		return;
1848 	}
1849 
1850 	for (f = Files; f; f = f->f_next) {
1851 		/* skip messages that are incorrect priority */
1852 		if (!MATCH_PRI(f, fac, prilev)
1853 		    || f->f_pmask[fac] == INTERNAL_NOPRI)
1854 			continue;
1855 
1856 		/* skip messages with the incorrect host name */
1857 		/* do we compare with host (IMHO correct) or recvhost */
1858 		/* (compatible)? */
1859 		if (f->f_host != NULL && buffer->host != NULL) {
1860 			char shost[MAXHOSTNAMELEN + 1], *h;
1861 			if (!BSDOutputFormat) {
1862 				h = buffer->host;
1863 			} else {
1864 				(void)strlcpy(shost, buffer->host,
1865 				    sizeof(shost));
1866 				trim_anydomain(shost);
1867 				h = shost;
1868 			}
1869 			switch (f->f_host[0]) {
1870 			case '+':
1871 				if (! matches_spec(h, f->f_host + 1,
1872 				    strcasestr))
1873 					continue;
1874 				break;
1875 			case '-':
1876 				if (matches_spec(h, f->f_host + 1,
1877 				    strcasestr))
1878 					continue;
1879 				break;
1880 			}
1881 		}
1882 
1883 		/* skip messages with the incorrect program name */
1884 		if (f->f_program != NULL && buffer->prog != NULL) {
1885 			switch (f->f_program[0]) {
1886 			case '+':
1887 				if (!matches_spec(buffer->prog,
1888 				    f->f_program + 1, strstr))
1889 					continue;
1890 				break;
1891 			case '-':
1892 				if (matches_spec(buffer->prog,
1893 				    f->f_program + 1, strstr))
1894 					continue;
1895 				break;
1896 			default:
1897 				if (!matches_spec(buffer->prog,
1898 				    f->f_program, strstr))
1899 					continue;
1900 				break;
1901 			}
1902 		}
1903 
1904 		if (f->f_type == F_CONSOLE && (buffer->flags & IGN_CONS))
1905 			continue;
1906 
1907 		/* don't output marks to recently written files */
1908 		if ((buffer->flags & MARK)
1909 		 && (now - f->f_time) < MarkInterval / 2)
1910 			continue;
1911 
1912 		/*
1913 		 * suppress duplicate lines to this file unless NoRepeat
1914 		 */
1915 #define MSG_FIELD_EQ(x) ((!buffer->x && !f->f_prevmsg->x) ||	\
1916     (buffer->x && f->f_prevmsg->x && !strcmp(buffer->x, f->f_prevmsg->x)))
1917 
1918 		if ((buffer->flags & MARK) == 0 &&
1919 		    f->f_prevmsg &&
1920 		    buffer->msglen == f->f_prevmsg->msglen &&
1921 		    !NoRepeat &&
1922 		    MSG_FIELD_EQ(host) &&
1923 		    MSG_FIELD_EQ(sd) &&
1924 		    MSG_FIELD_EQ(msg)
1925 		    ) {
1926 			f->f_prevcount++;
1927 			DPRINTF(D_DATA, "Msg repeated %d times, %ld sec of %d\n",
1928 			    f->f_prevcount, (long)(now - f->f_time),
1929 			    repeatinterval[f->f_repeatcount]);
1930 			/*
1931 			 * If domark would have logged this by now,
1932 			 * flush it now (so we don't hold isolated messages),
1933 			 * but back off so we'll flush less often
1934 			 * in the future.
1935 			 */
1936 			if (now > REPEATTIME(f)) {
1937 				fprintlog(f, NEWREF(buffer), NULL);
1938 				DELREF(buffer);
1939 				BACKOFF(f);
1940 			}
1941 		} else {
1942 			/* new line, save it */
1943 			if (f->f_prevcount)
1944 				fprintlog(f, NULL, NULL);
1945 			f->f_repeatcount = 0;
1946 			DELREF(f->f_prevmsg);
1947 			f->f_prevmsg = NEWREF(buffer);
1948 			fprintlog(f, NEWREF(buffer), NULL);
1949 			DELREF(buffer);
1950 		}
1951 	}
1952 	(void)sigsetmask(omask);
1953 }
1954 
1955 /*
1956  * format one buffer into output format given by flag BSDOutputFormat
1957  * line is allocated and has to be free()d by caller
1958  * size_t pointers are optional, if not NULL then they will return
1959  *   different lenghts used for formatting and output
1960  */
1961 #define OUT(x) ((x)?(x):"-")
1962 bool
1963 format_buffer(struct buf_msg *buffer, char **line, size_t *ptr_linelen,
1964 	size_t *ptr_msglen, size_t *ptr_tlsprefixlen, size_t *ptr_prilen)
1965 {
1966 #define FPBUFSIZE 30
1967 	static char ascii_empty[] = "";
1968 	char fp_buf[FPBUFSIZE] = "\0";
1969 	char *hostname, *shorthostname = NULL;
1970 	char *ascii_sd = ascii_empty;
1971 	char *ascii_msg = ascii_empty;
1972 	size_t linelen, msglen, tlsprefixlen, prilen, j;
1973 
1974 	DPRINTF(D_CALL, "format_buffer(%p)\n", buffer);
1975 	if (!buffer) return false;
1976 
1977 	/* All buffer fields are set with strdup(). To avoid problems
1978 	 * on memory exhaustion we allow them to be empty and replace
1979 	 * the essential fields with already allocated generic values.
1980 	 */
1981 	if (!buffer->timestamp)
1982 		buffer->timestamp = timestamp;
1983 	if (!buffer->host && !buffer->recvhost)
1984 		buffer->host = LocalFQDN;
1985 
1986 	if (LogFacPri) {
1987 		const char *f_s = NULL, *p_s = NULL;
1988 		int fac = buffer->pri & LOG_FACMASK;
1989 		int pri = LOG_PRI(buffer->pri);
1990 		char f_n[5], p_n[5];
1991 
1992 		if (LogFacPri > 1) {
1993 			CODE *c;
1994 
1995 			for (c = facilitynames; c->c_name != NULL; c++) {
1996 				if (c->c_val == fac) {
1997 					f_s = c->c_name;
1998 					break;
1999 				}
2000 			}
2001 			for (c = prioritynames; c->c_name != NULL; c++) {
2002 				if (c->c_val == pri) {
2003 					p_s = c->c_name;
2004 					break;
2005 				}
2006 			}
2007 		}
2008 		if (f_s == NULL) {
2009 			snprintf(f_n, sizeof(f_n), "%d", LOG_FAC(fac));
2010 			f_s = f_n;
2011 		}
2012 		if (p_s == NULL) {
2013 			snprintf(p_n, sizeof(p_n), "%d", pri);
2014 			p_s = p_n;
2015 		}
2016 		snprintf(fp_buf, sizeof(fp_buf), "<%s.%s>", f_s, p_s);
2017 	}
2018 
2019 	/* hostname or FQDN */
2020 	hostname = (buffer->host ? buffer->host : buffer->recvhost);
2021 	if (BSDOutputFormat
2022 	 && (shorthostname = strdup(hostname))) {
2023 		/* if the previous BSD output format with "host [recvhost]:"
2024 		 * gets implemented, this is the right place to distinguish
2025 		 * between buffer->host and buffer->recvhost
2026 		 */
2027 		trim_anydomain(shorthostname);
2028 		hostname = shorthostname;
2029 	}
2030 
2031 	/* new message formatting:
2032 	 * instead of using iov always assemble one complete TLS-ready line
2033 	 * with length and priority (depending on BSDOutputFormat either in
2034 	 * BSD Syslog or syslog-protocol format)
2035 	 *
2036 	 * additionally save the length of the prefixes,
2037 	 * so UDP destinations can skip the length prefix and
2038 	 * file/pipe/wall destinations can omit length and priority
2039 	 */
2040 	/* first determine required space */
2041 	if (BSDOutputFormat) {
2042 		/* only output ASCII chars */
2043 		if (buffer->sd)
2044 			ascii_sd = copy_utf8_ascii(buffer->sd,
2045 				strlen(buffer->sd));
2046 		if (buffer->msg) {
2047 			if (IS_BOM(buffer->msg))
2048 				ascii_msg = copy_utf8_ascii(buffer->msg,
2049 					buffer->msglen - 1);
2050 			else /* assume already converted at input */
2051 				ascii_msg = buffer->msg;
2052 		}
2053 		msglen = snprintf(NULL, 0, "<%d>%s%.15s %s %s%s%s%s: %s%s%s",
2054 			     buffer->pri, fp_buf, buffer->timestamp,
2055 			     hostname, OUT(buffer->prog),
2056 			     buffer->pid ? "[" : "",
2057 			     buffer->pid ? buffer->pid : "",
2058 			     buffer->pid ? "]" : "", ascii_sd,
2059 			     (buffer->sd && buffer->msg ? " ": ""), ascii_msg);
2060 	} else
2061 		msglen = snprintf(NULL, 0, "<%d>1 %s%s %s %s %s %s %s%s%s",
2062 			     buffer->pri, fp_buf, buffer->timestamp,
2063 			     hostname, OUT(buffer->prog), OUT(buffer->pid),
2064 			     OUT(buffer->msgid), OUT(buffer->sd),
2065 			     (buffer->msg ? " ": ""),
2066 			     (buffer->msg ? buffer->msg: ""));
2067 	/* add space for length prefix */
2068 	tlsprefixlen = 0;
2069 	for (j = msglen; j; j /= 10)
2070 		tlsprefixlen++;
2071 	/* one more for the space */
2072 	tlsprefixlen++;
2073 
2074 	prilen = snprintf(NULL, 0, "<%d>", buffer->pri);
2075 	if (!BSDOutputFormat)
2076 		prilen += 2; /* version char and space */
2077 	MALLOC(*line, msglen + tlsprefixlen + 1);
2078 	if (BSDOutputFormat)
2079 		linelen = snprintf(*line,
2080 		     msglen + tlsprefixlen + 1,
2081 		     "%zu <%d>%s%.15s %s %s%s%s%s: %s%s%s",
2082 		     msglen, buffer->pri, fp_buf, buffer->timestamp,
2083 		     hostname, OUT(buffer->prog),
2084 		     (buffer->pid ? "[" : ""),
2085 		     (buffer->pid ? buffer->pid : ""),
2086 		     (buffer->pid ? "]" : ""), ascii_sd,
2087 		     (buffer->sd && buffer->msg ? " ": ""), ascii_msg);
2088 	else
2089 		linelen = snprintf(*line,
2090 		     msglen + tlsprefixlen + 1,
2091 		     "%zu <%d>1 %s%s %s %s %s %s %s%s%s",
2092 		     msglen, buffer->pri, fp_buf, buffer->timestamp,
2093 		     hostname, OUT(buffer->prog), OUT(buffer->pid),
2094 		     OUT(buffer->msgid), OUT(buffer->sd),
2095 		     (buffer->msg ? " ": ""),
2096 		     (buffer->msg ? buffer->msg: ""));
2097 	DPRINTF(D_DATA, "formatted %zu octets to: '%.*s' (linelen %zu, "
2098 	    "msglen %zu, tlsprefixlen %zu, prilen %zu)\n", linelen,
2099 	    (int)linelen, *line, linelen, msglen, tlsprefixlen, prilen);
2100 
2101 	FREEPTR(shorthostname);
2102 	if (ascii_sd != ascii_empty)
2103 		FREEPTR(ascii_sd);
2104 	if (ascii_msg != ascii_empty && ascii_msg != buffer->msg)
2105 		FREEPTR(ascii_msg);
2106 
2107 	if (ptr_linelen)      *ptr_linelen	= linelen;
2108 	if (ptr_msglen)	      *ptr_msglen	= msglen;
2109 	if (ptr_tlsprefixlen) *ptr_tlsprefixlen = tlsprefixlen;
2110 	if (ptr_prilen)	      *ptr_prilen	= prilen;
2111 	return true;
2112 }
2113 
2114 /*
2115  * if qentry == NULL: new message, if temporarily undeliverable it will be enqueued
2116  * if qentry != NULL: a temporarily undeliverable message will not be enqueued,
2117  *		    but after delivery be removed from the queue
2118  */
2119 void
2120 fprintlog(struct filed *f, struct buf_msg *passedbuffer, struct buf_queue *qentry)
2121 {
2122 	static char crnl[] = "\r\n";
2123 	struct buf_msg *buffer = passedbuffer;
2124 	struct iovec iov[4];
2125 	struct iovec *v = iov;
2126 	bool error = false;
2127 	int e = 0, len = 0;
2128 	size_t msglen, linelen, tlsprefixlen, prilen;
2129 	char *p, *line = NULL, *lineptr = NULL;
2130 #ifndef DISABLE_SIGN
2131 	bool newhash = false;
2132 #endif
2133 #define REPBUFSIZE 80
2134 	char greetings[200];
2135 #define ADDEV() do { v++; assert((size_t)(v - iov) < A_CNT(iov)); } while(/*CONSTCOND*/0)
2136 
2137 	DPRINTF(D_CALL, "fprintlog(%p, %p, %p)\n", f, buffer, qentry);
2138 
2139 	f->f_time = now;
2140 
2141 	/* increase refcount here and lower again at return.
2142 	 * this enables the buffer in the else branch to be freed
2143 	 * --> every branch needs one NEWREF() or buf_msg_new()! */
2144 	if (buffer) {
2145 		(void)NEWREF(buffer);
2146 	} else {
2147 		if (f->f_prevcount > 1) {
2148 			/* possible syslog-sign incompatibility:
2149 			 * assume destinations f1 and f2 share one SG and
2150 			 * get the same message sequence.
2151 			 *
2152 			 * now both f1 and f2 generate "repeated" messages
2153 			 * "repeated" messages are different due to different
2154 			 * timestamps
2155 			 * the SG will get hashes for the two "repeated" messages
2156 			 *
2157 			 * now both f1 and f2 are just fine, but a verification
2158 			 * will report that each 'lost' a message, i.e. the
2159 			 * other's "repeated" message
2160 			 *
2161 			 * conditions for 'safe configurations':
2162 			 * - use NoRepeat option,
2163 			 * - use SG 3, or
2164 			 * - have exactly one destination for every PRI
2165 			 */
2166 			buffer = buf_msg_new(REPBUFSIZE);
2167 			buffer->msglen = snprintf(buffer->msg, REPBUFSIZE,
2168 			    "last message repeated %d times", f->f_prevcount);
2169 			buffer->timestamp =
2170 				strdup(make_timestamp(NULL, !BSDOutputFormat));
2171 			buffer->pri = f->f_prevmsg->pri;
2172 			buffer->host = LocalFQDN;
2173 			buffer->prog = appname;
2174 			buffer->pid = include_pid;
2175 
2176 		} else {
2177 			buffer = NEWREF(f->f_prevmsg);
2178 		}
2179 	}
2180 
2181 	/* no syslog-sign messages to tty/console/... */
2182 	if ((buffer->flags & SIGN_MSG)
2183 	    && ((f->f_type == F_UNUSED)
2184 	    || (f->f_type == F_TTY)
2185 	    || (f->f_type == F_CONSOLE)
2186 	    || (f->f_type == F_USERS)
2187 	    || (f->f_type == F_WALL))) {
2188 		DELREF(buffer);
2189 		return;
2190 	}
2191 
2192 	/* buffering works only for few types */
2193 	if (qentry
2194 	    && (f->f_type != F_TLS)
2195 	    && (f->f_type != F_PIPE)
2196 	    && (f->f_type != F_FILE)) {
2197 		logerror("Warning: unexpected message in buffer");
2198 		DELREF(buffer);
2199 		return;
2200 	}
2201 
2202 	if (!format_buffer(buffer, &line,
2203 	    &linelen, &msglen, &tlsprefixlen, &prilen)) {
2204 		DPRINTF(D_CALL, "format_buffer() failed, skip message\n");
2205 		DELREF(buffer);
2206 		return;
2207 	}
2208 	/* assert maximum message length */
2209 	if (TypeInfo[f->f_type].max_msg_length != -1
2210 	    && (size_t)TypeInfo[f->f_type].max_msg_length
2211 	    < linelen - tlsprefixlen - prilen) {
2212 		linelen = TypeInfo[f->f_type].max_msg_length
2213 		    + tlsprefixlen + prilen;
2214 		DPRINTF(D_DATA, "truncating oversized message to %zu octets\n",
2215 		    linelen);
2216 	}
2217 
2218 #ifndef DISABLE_SIGN
2219 	/* keep state between appending the hash (before buffer is sent)
2220 	 * and possibly sending a SB (after buffer is sent): */
2221 	/* get hash */
2222 	if (!(buffer->flags & SIGN_MSG) && !qentry) {
2223 		char *hash = NULL;
2224 		struct signature_group_t *sg;
2225 
2226 		if ((sg = sign_get_sg(buffer->pri, f)) != NULL) {
2227 			if (sign_msg_hash(line + tlsprefixlen, &hash))
2228 				newhash = sign_append_hash(hash, sg);
2229 			else
2230 				DPRINTF(D_SIGN,
2231 					"Unable to hash line \"%s\"\n", line);
2232 		}
2233 	}
2234 #endif /* !DISABLE_SIGN */
2235 
2236 	/* set start and length of buffer and/or fill iovec */
2237 	switch (f->f_type) {
2238 	case F_UNUSED:
2239 		/* nothing */
2240 		break;
2241 	case F_TLS:
2242 		/* nothing, as TLS uses whole buffer to send */
2243 		lineptr = line;
2244 		len = linelen;
2245 		break;
2246 	case F_FORW:
2247 		lineptr = line + tlsprefixlen;
2248 		len = linelen - tlsprefixlen;
2249 		break;
2250 	case F_PIPE:
2251 	case F_FILE:  /* fallthrough */
2252 		if (f->f_flags & FFLAG_FULL) {
2253 			v->iov_base = line + tlsprefixlen;
2254 			v->iov_len = linelen - tlsprefixlen;
2255 		} else {
2256 			v->iov_base = line + tlsprefixlen + prilen;
2257 			v->iov_len = linelen - tlsprefixlen - prilen;
2258 		}
2259 		ADDEV();
2260 		v->iov_base = &crnl[1];
2261 		v->iov_len = 1;
2262 		ADDEV();
2263 		break;
2264 	case F_CONSOLE:
2265 	case F_TTY:
2266 		/* filter non-ASCII */
2267 		p = line;
2268 		while (*p) {
2269 			*p = FORCE2ASCII(*p);
2270 			p++;
2271 		}
2272 		v->iov_base = line + tlsprefixlen + prilen;
2273 		v->iov_len = linelen - tlsprefixlen - prilen;
2274 		ADDEV();
2275 		v->iov_base = crnl;
2276 		v->iov_len = 2;
2277 		ADDEV();
2278 		break;
2279 	case F_WALL:
2280 		v->iov_base = greetings;
2281 		v->iov_len = snprintf(greetings, sizeof(greetings),
2282 		    "\r\n\7Message from syslogd@%s at %s ...\r\n",
2283 		    (buffer->host ? buffer->host : buffer->recvhost),
2284 		    buffer->timestamp);
2285 		ADDEV();
2286 	case F_USERS: /* fallthrough */
2287 		/* filter non-ASCII */
2288 		p = line;
2289 		while (*p) {
2290 			*p = FORCE2ASCII(*p);
2291 			p++;
2292 		}
2293 		v->iov_base = line + tlsprefixlen + prilen;
2294 		v->iov_len = linelen - tlsprefixlen - prilen;
2295 		ADDEV();
2296 		v->iov_base = &crnl[1];
2297 		v->iov_len = 1;
2298 		ADDEV();
2299 		break;
2300 	}
2301 
2302 	/* send */
2303 	switch (f->f_type) {
2304 	case F_UNUSED:
2305 		DPRINTF(D_MISC, "Logging to %s\n", TypeInfo[f->f_type].name);
2306 		break;
2307 
2308 	case F_FORW:
2309 		DPRINTF(D_MISC, "Logging to %s %s\n",
2310 		    TypeInfo[f->f_type].name, f->f_un.f_forw.f_hname);
2311 		udp_send(f, lineptr, len);
2312 		break;
2313 
2314 #ifndef DISABLE_TLS
2315 	case F_TLS:
2316 		DPRINTF(D_MISC, "Logging to %s %s\n",
2317 		    TypeInfo[f->f_type].name,
2318 		    f->f_un.f_tls.tls_conn->hostname);
2319 		/* make sure every message gets queued once
2320 		 * it will be removed when sendmsg is sent and free()d */
2321 		if (!qentry)
2322 			qentry = message_queue_add(f, NEWREF(buffer));
2323 		(void)tls_send(f, lineptr, len, qentry);
2324 		break;
2325 #endif /* !DISABLE_TLS */
2326 
2327 	case F_PIPE:
2328 		DPRINTF(D_MISC, "Logging to %s %s\n",
2329 		    TypeInfo[f->f_type].name, f->f_un.f_pipe.f_pname);
2330 		if (f->f_un.f_pipe.f_pid == 0) {
2331 			/* (re-)open */
2332 			if ((f->f_file = p_open(f->f_un.f_pipe.f_pname,
2333 			    &f->f_un.f_pipe.f_pid)) < 0) {
2334 				f->f_type = F_UNUSED;
2335 				message_queue_freeall(f);
2336 				logerror("%s", f->f_un.f_pipe.f_pname);
2337 				break;
2338 			} else if (!qentry) /* prevent recursion */
2339 				SEND_QUEUE(f);
2340 		}
2341 		if (writev(f->f_file, iov, v - iov) < 0) {
2342 			e = errno;
2343 			if (f->f_un.f_pipe.f_pid > 0) {
2344 				(void) close(f->f_file);
2345 				deadq_enter(f->f_un.f_pipe.f_pid,
2346 				    f->f_un.f_pipe.f_pname);
2347 			}
2348 			f->f_un.f_pipe.f_pid = 0;
2349 			/*
2350 			 * If the error was EPIPE, then what is likely
2351 			 * has happened is we have a command that is
2352 			 * designed to take a single message line and
2353 			 * then exit, but we tried to feed it another
2354 			 * one before we reaped the child and thus
2355 			 * reset our state.
2356 			 *
2357 			 * Well, now we've reset our state, so try opening
2358 			 * the pipe and sending the message again if EPIPE
2359 			 * was the error.
2360 			 */
2361 			if (e == EPIPE) {
2362 				if ((f->f_file = p_open(f->f_un.f_pipe.f_pname,
2363 				     &f->f_un.f_pipe.f_pid)) < 0) {
2364 					f->f_type = F_UNUSED;
2365 					message_queue_freeall(f);
2366 					logerror("%s", f->f_un.f_pipe.f_pname);
2367 					break;
2368 				}
2369 				if (writev(f->f_file, iov, v - iov) < 0) {
2370 					e = errno;
2371 					if (f->f_un.f_pipe.f_pid > 0) {
2372 					    (void) close(f->f_file);
2373 					    deadq_enter(f->f_un.f_pipe.f_pid,
2374 						f->f_un.f_pipe.f_pname);
2375 					}
2376 					f->f_un.f_pipe.f_pid = 0;
2377 					error = true;	/* enqueue on return */
2378 				} else
2379 					e = 0;
2380 			}
2381 			if (e != 0 && !error) {
2382 				errno = e;
2383 				logerror("%s", f->f_un.f_pipe.f_pname);
2384 			}
2385 		}
2386 		if (e == 0 && qentry) { /* sent buffered msg */
2387 			message_queue_remove(f, qentry);
2388 		}
2389 		break;
2390 
2391 	case F_CONSOLE:
2392 		if (buffer->flags & IGN_CONS) {
2393 			DPRINTF(D_MISC, "Logging to %s (ignored)\n",
2394 				TypeInfo[f->f_type].name);
2395 			break;
2396 		}
2397 		/* FALLTHROUGH */
2398 
2399 	case F_TTY:
2400 	case F_FILE:
2401 		DPRINTF(D_MISC, "Logging to %s %s\n",
2402 			TypeInfo[f->f_type].name, f->f_un.f_fname);
2403 	again:
2404 		if (writev(f->f_file, iov, v - iov) < 0) {
2405 			e = errno;
2406 			if (f->f_type == F_FILE && e == ENOSPC) {
2407 				int lasterror = f->f_lasterror;
2408 				f->f_lasterror = e;
2409 				if (lasterror != e)
2410 					logerror("%s", f->f_un.f_fname);
2411 				error = true;	/* enqueue on return */
2412 			}
2413 			(void)close(f->f_file);
2414 			/*
2415 			 * Check for errors on TTY's due to loss of tty
2416 			 */
2417 			if ((e == EIO || e == EBADF) && f->f_type != F_FILE) {
2418 				f->f_file = open(f->f_un.f_fname,
2419 				    O_WRONLY|O_APPEND, 0);
2420 				if (f->f_file < 0) {
2421 					f->f_type = F_UNUSED;
2422 					logerror("%s", f->f_un.f_fname);
2423 					message_queue_freeall(f);
2424 				} else
2425 					goto again;
2426 			} else {
2427 				f->f_type = F_UNUSED;
2428 				errno = e;
2429 				f->f_lasterror = e;
2430 				logerror("%s", f->f_un.f_fname);
2431 				message_queue_freeall(f);
2432 			}
2433 		} else {
2434 			f->f_lasterror = 0;
2435 			if ((buffer->flags & SYNC_FILE)
2436 			 && (f->f_flags & FFLAG_SYNC))
2437 				(void)fsync(f->f_file);
2438 			/* Problem with files: We cannot check beforehand if
2439 			 * they would be writeable and call send_queue() first.
2440 			 * So we call send_queue() after a successful write,
2441 			 * which means the first message will be out of order.
2442 			 */
2443 			if (!qentry) /* prevent recursion */
2444 				SEND_QUEUE(f);
2445 			else if (qentry) /* sent buffered msg */
2446 				message_queue_remove(f, qentry);
2447 		}
2448 		break;
2449 
2450 	case F_USERS:
2451 	case F_WALL:
2452 		DPRINTF(D_MISC, "Logging to %s\n", TypeInfo[f->f_type].name);
2453 		wallmsg(f, iov, v - iov);
2454 		break;
2455 	}
2456 	f->f_prevcount = 0;
2457 
2458 	if (error && !qentry)
2459 		message_queue_add(f, NEWREF(buffer));
2460 #ifndef DISABLE_SIGN
2461 	if (newhash) {
2462 		struct signature_group_t *sg;
2463 		sg = sign_get_sg(buffer->pri, f);
2464 		(void)sign_send_signature_block(sg, false);
2465 	}
2466 #endif /* !DISABLE_SIGN */
2467 	/* this belongs to the ad-hoc buffer at the first if(buffer) */
2468 	DELREF(buffer);
2469 	/* TLS frees on its own */
2470 	if (f->f_type != F_TLS)
2471 		FREEPTR(line);
2472 }
2473 
2474 /* send one line by UDP */
2475 void
2476 udp_send(struct filed *f, char *line, size_t len)
2477 {
2478 	int lsent, fail, retry, j;
2479 	struct addrinfo *r;
2480 
2481 	DPRINTF((D_NET|D_CALL), "udp_send(f=%p, line=\"%s\", "
2482 	    "len=%zu) to dest.\n", f, line, len);
2483 
2484 	if (!finet)
2485 		return;
2486 
2487 	lsent = -1;
2488 	fail = 0;
2489 	assert(f->f_type == F_FORW);
2490 	for (r = f->f_un.f_forw.f_addr; r; r = r->ai_next) {
2491 		retry = 0;
2492 		for (j = 0; j < finet->fd; j++) {
2493 sendagain:
2494 			lsent = sendto(finet[j+1].fd, line, len, 0,
2495 			    r->ai_addr, r->ai_addrlen);
2496 			if (lsent == -1) {
2497 				switch (errno) {
2498 				case ENOBUFS:
2499 					/* wait/retry/drop */
2500 					if (++retry < 5) {
2501 						usleep(1000);
2502 						goto sendagain;
2503 					}
2504 					break;
2505 				case EHOSTDOWN:
2506 				case EHOSTUNREACH:
2507 				case ENETDOWN:
2508 					/* drop */
2509 					break;
2510 				default:
2511 					/* busted */
2512 					fail++;
2513 					break;
2514 				}
2515 			} else if ((size_t)lsent == len)
2516 				break;
2517 		}
2518 		if ((size_t)lsent != len && fail) {
2519 			f->f_type = F_UNUSED;
2520 			logerror("sendto() failed");
2521 		}
2522 	}
2523 }
2524 
2525 /*
2526  *  WALLMSG -- Write a message to the world at large
2527  *
2528  *	Write the specified message to either the entire
2529  *	world, or a list of approved users.
2530  */
2531 void
2532 wallmsg(struct filed *f, struct iovec *iov, size_t iovcnt)
2533 {
2534 #ifdef __NetBSD_Version__
2535 	static int reenter;			/* avoid calling ourselves */
2536 	int i;
2537 	char *p;
2538 	struct utmpentry *ep;
2539 
2540 	if (reenter++)
2541 		return;
2542 
2543 	(void)getutentries(NULL, &ep);
2544 	/* NOSTRICT */
2545 	for (; ep; ep = ep->next) {
2546 		if (f->f_type == F_WALL) {
2547 			if ((p = ttymsg(iov, iovcnt, ep->line, TTYMSGTIME))
2548 			    != NULL) {
2549 				errno = 0;	/* already in msg */
2550 				logerror("%s", p);
2551 			}
2552 			continue;
2553 		}
2554 		/* should we send the message to this user? */
2555 		for (i = 0; i < MAXUNAMES; i++) {
2556 			if (!f->f_un.f_uname[i][0])
2557 				break;
2558 			if (strcmp(f->f_un.f_uname[i], ep->name) == 0) {
2559 				if ((p = ttymsg(iov, iovcnt, ep->line,
2560 				    TTYMSGTIME)) != NULL) {
2561 					errno = 0;	/* already in msg */
2562 					logerror("%s", p);
2563 				}
2564 				break;
2565 			}
2566 		}
2567 	}
2568 	reenter = 0;
2569 #endif /* __NetBSD_Version__ */
2570 }
2571 
2572 void
2573 /*ARGSUSED*/
2574 reapchild(int fd, short event, void *ev)
2575 {
2576 	int status;
2577 	pid_t pid;
2578 	struct filed *f;
2579 
2580 	while ((pid = wait3(&status, WNOHANG, NULL)) > 0) {
2581 		if (!Initialized || ShuttingDown) {
2582 			/*
2583 			 * Be silent while we are initializing or
2584 			 * shutting down.
2585 			 */
2586 			continue;
2587 		}
2588 
2589 		if (deadq_remove(pid))
2590 			continue;
2591 
2592 		/* Now, look in the list of active processes. */
2593 		for (f = Files; f != NULL; f = f->f_next) {
2594 			if (f->f_type == F_PIPE &&
2595 			    f->f_un.f_pipe.f_pid == pid) {
2596 				(void) close(f->f_file);
2597 				f->f_un.f_pipe.f_pid = 0;
2598 				log_deadchild(pid, status,
2599 				    f->f_un.f_pipe.f_pname);
2600 				break;
2601 			}
2602 		}
2603 	}
2604 }
2605 
2606 /*
2607  * Return a printable representation of a host address (FQDN if available)
2608  */
2609 const char *
2610 cvthname(struct sockaddr_storage *f)
2611 {
2612 	int error;
2613 	int niflag = NI_DGRAM;
2614 	static char host[NI_MAXHOST], ip[NI_MAXHOST];
2615 
2616 	error = getnameinfo((struct sockaddr*)f, ((struct sockaddr*)f)->sa_len,
2617 	    ip, sizeof ip, NULL, 0, NI_NUMERICHOST|niflag);
2618 
2619 	DPRINTF(D_CALL, "cvthname(%s)\n", ip);
2620 
2621 	if (error) {
2622 		DPRINTF(D_NET, "Malformed from address %s\n",
2623 		    gai_strerror(error));
2624 		return "???";
2625 	}
2626 
2627 	if (!UseNameService)
2628 		return ip;
2629 
2630 	error = getnameinfo((struct sockaddr*)f, ((struct sockaddr*)f)->sa_len,
2631 	    host, sizeof host, NULL, 0, niflag);
2632 	if (error) {
2633 		DPRINTF(D_NET, "Host name for your address (%s) unknown\n", ip);
2634 		return ip;
2635 	}
2636 
2637 	return host;
2638 }
2639 
2640 void
2641 trim_anydomain(char *host)
2642 {
2643 	bool onlydigits = true;
2644 	int i;
2645 
2646 	if (!BSDOutputFormat)
2647 		return;
2648 
2649 	/* if non-digits found, then assume hostname and cut at first dot (this
2650 	 * case also covers IPv6 addresses which should not contain dots),
2651 	 * if only digits then assume IPv4 address and do not cut at all */
2652 	for (i = 0; host[i]; i++) {
2653 		if (host[i] == '.' && !onlydigits)
2654 			host[i] = '\0';
2655 		else if (!isdigit((unsigned char)host[i]) && host[i] != '.')
2656 			onlydigits = false;
2657 	}
2658 }
2659 
2660 static void
2661 /*ARGSUSED*/
2662 domark(int fd, short event, void *ev)
2663 {
2664 	struct event *ev_pass = (struct event *)ev;
2665 	struct filed *f;
2666 	dq_t q, nextq;
2667 	sigset_t newmask, omask;
2668 
2669 	schedule_event(&ev_pass,
2670 		&((struct timeval){TIMERINTVL, 0}),
2671 		domark, ev_pass);
2672 	DPRINTF((D_CALL|D_EVENT), "domark()\n");
2673 
2674 	BLOCK_SIGNALS(omask, newmask);
2675 	now = time(NULL);
2676 	MarkSeq += TIMERINTVL;
2677 	if (MarkSeq >= MarkInterval) {
2678 		logmsg_async(LOG_INFO, NULL, "-- MARK --", ADDDATE|MARK);
2679 		MarkSeq = 0;
2680 	}
2681 
2682 	for (f = Files; f; f = f->f_next) {
2683 		if (f->f_prevcount && now >= REPEATTIME(f)) {
2684 			DPRINTF(D_DATA, "Flush %s: repeated %d times, %d sec.\n",
2685 			    TypeInfo[f->f_type].name, f->f_prevcount,
2686 			    repeatinterval[f->f_repeatcount]);
2687 			fprintlog(f, NULL, NULL);
2688 			BACKOFF(f);
2689 		}
2690 	}
2691 	message_allqueues_check();
2692 	RESTORE_SIGNALS(omask);
2693 
2694 	/* Walk the dead queue, and see if we should signal somebody. */
2695 	for (q = TAILQ_FIRST(&deadq_head); q != NULL; q = nextq) {
2696 		nextq = TAILQ_NEXT(q, dq_entries);
2697 		switch (q->dq_timeout) {
2698 		case 0:
2699 			/* Already signalled once, try harder now. */
2700 			if (kill(q->dq_pid, SIGKILL) != 0)
2701 				(void) deadq_remove(q->dq_pid);
2702 			break;
2703 
2704 		case 1:
2705 			/*
2706 			 * Timed out on the dead queue, send terminate
2707 			 * signal.  Note that we leave the removal from
2708 			 * the dead queue to reapchild(), which will
2709 			 * also log the event (unless the process
2710 			 * didn't even really exist, in case we simply
2711 			 * drop it from the dead queue).
2712 			 */
2713 			if (kill(q->dq_pid, SIGTERM) != 0) {
2714 				(void) deadq_remove(q->dq_pid);
2715 				break;
2716 			}
2717 			/* FALLTHROUGH */
2718 
2719 		default:
2720 			q->dq_timeout--;
2721 		}
2722 	}
2723 #ifndef DISABLE_SIGN
2724 	if (GlobalSign.rsid) {	/* check if initialized */
2725 		struct signature_group_t *sg;
2726 		STAILQ_FOREACH(sg, &GlobalSign.SigGroups, entries) {
2727 			sign_send_certificate_block(sg);
2728 		}
2729 	}
2730 #endif /* !DISABLE_SIGN */
2731 }
2732 
2733 /*
2734  * Print syslogd errors some place.
2735  */
2736 void
2737 logerror(const char *fmt, ...)
2738 {
2739 	static int logerror_running;
2740 	va_list ap;
2741 	char tmpbuf[BUFSIZ];
2742 	char buf[BUFSIZ];
2743 	char *outbuf;
2744 
2745 	/* If there's an error while trying to log an error, give up. */
2746 	if (logerror_running)
2747 		return;
2748 	logerror_running = 1;
2749 
2750 	va_start(ap, fmt);
2751 	(void)vsnprintf(tmpbuf, sizeof(tmpbuf), fmt, ap);
2752 	va_end(ap);
2753 
2754 	if (errno) {
2755 		(void)snprintf(buf, sizeof(buf), "%s: %s",
2756 		    tmpbuf, strerror(errno));
2757 		outbuf = buf;
2758 	} else {
2759 		(void)snprintf(buf, sizeof(buf), "%s", tmpbuf);
2760 		outbuf = tmpbuf;
2761 	}
2762 
2763 	if (daemonized)
2764 		logmsg_async(LOG_SYSLOG|LOG_ERR, NULL, outbuf, ADDDATE);
2765 	if (!daemonized && Debug)
2766 		DPRINTF(D_MISC, "%s\n", outbuf);
2767 	if (!daemonized && !Debug)
2768 		printf("%s\n", outbuf);
2769 
2770 	logerror_running = 0;
2771 }
2772 
2773 /*
2774  * Print syslogd info some place.
2775  */
2776 void
2777 loginfo(const char *fmt, ...)
2778 {
2779 	va_list ap;
2780 	char buf[BUFSIZ];
2781 
2782 	va_start(ap, fmt);
2783 	(void)vsnprintf(buf, sizeof(buf), fmt, ap);
2784 	va_end(ap);
2785 
2786 	DPRINTF(D_MISC, "%s\n", buf);
2787 	logmsg_async(LOG_SYSLOG|LOG_INFO, NULL, buf, ADDDATE);
2788 }
2789 
2790 #ifndef DISABLE_TLS
2791 static inline void
2792 free_incoming_tls_sockets(void)
2793 {
2794 	struct TLS_Incoming_Conn *tls_in;
2795 	int i;
2796 
2797 	/*
2798 	 * close all listening and connected TLS sockets
2799 	 */
2800 	if (TLS_Listen_Set)
2801 		for (i = 0; i < TLS_Listen_Set->fd; i++) {
2802 			if (close(TLS_Listen_Set[i+1].fd) == -1)
2803 				logerror("close() failed");
2804 			DEL_EVENT(TLS_Listen_Set[i+1].ev);
2805 			FREEPTR(TLS_Listen_Set[i+1].ev);
2806 		}
2807 	FREEPTR(TLS_Listen_Set);
2808 	/* close/free incoming TLS connections */
2809 	while (!SLIST_EMPTY(&TLS_Incoming_Head)) {
2810 		tls_in = SLIST_FIRST(&TLS_Incoming_Head);
2811 		SLIST_REMOVE_HEAD(&TLS_Incoming_Head, entries);
2812 		FREEPTR(tls_in->inbuf);
2813 		free_tls_conn(tls_in->tls_conn);
2814 		free(tls_in);
2815 	}
2816 }
2817 #endif /* !DISABLE_TLS */
2818 
2819 void
2820 /*ARGSUSED*/
2821 die(int fd, short event, void *ev)
2822 {
2823 	struct filed *f, *next;
2824 	char **p;
2825 	sigset_t newmask, omask;
2826 	int i;
2827 	size_t j;
2828 
2829 	ShuttingDown = 1;	/* Don't log SIGCHLDs. */
2830 	/* prevent recursive signals */
2831 	BLOCK_SIGNALS(omask, newmask);
2832 
2833 	errno = 0;
2834 	if (ev != NULL)
2835 		logerror("Exiting on signal %d", fd);
2836 	else
2837 		logerror("Fatal error, exiting");
2838 
2839 	/*
2840 	 *  flush any pending output
2841 	 */
2842 	for (f = Files; f != NULL; f = f->f_next) {
2843 		/* flush any pending output */
2844 		if (f->f_prevcount)
2845 			fprintlog(f, NULL, NULL);
2846 		SEND_QUEUE(f);
2847 	}
2848 
2849 #ifndef DISABLE_TLS
2850 	free_incoming_tls_sockets();
2851 #endif /* !DISABLE_TLS */
2852 #ifndef DISABLE_SIGN
2853 	sign_global_free();
2854 #endif /* !DISABLE_SIGN */
2855 
2856 	/*
2857 	 *  Close all open log files.
2858 	 */
2859 	for (f = Files; f != NULL; f = next) {
2860 		message_queue_freeall(f);
2861 
2862 		switch (f->f_type) {
2863 		case F_FILE:
2864 		case F_TTY:
2865 		case F_CONSOLE:
2866 			(void)close(f->f_file);
2867 			break;
2868 		case F_PIPE:
2869 			if (f->f_un.f_pipe.f_pid > 0) {
2870 				(void)close(f->f_file);
2871 			}
2872 			f->f_un.f_pipe.f_pid = 0;
2873 			break;
2874 		case F_FORW:
2875 			if (f->f_un.f_forw.f_addr)
2876 				freeaddrinfo(f->f_un.f_forw.f_addr);
2877 			break;
2878 #ifndef DISABLE_TLS
2879 		case F_TLS:
2880 			free_tls_conn(f->f_un.f_tls.tls_conn);
2881 			break;
2882 #endif /* !DISABLE_TLS */
2883 		}
2884 		next = f->f_next;
2885 		DELREF(f->f_prevmsg);
2886 		FREEPTR(f->f_program);
2887 		FREEPTR(f->f_host);
2888 		DEL_EVENT(f->f_sq_event);
2889 		free((char *)f);
2890 	}
2891 
2892 	/*
2893 	 *  Close all open UDP sockets
2894 	 */
2895 	if (finet) {
2896 		for (i = 0; i < finet->fd; i++) {
2897 			if (close(finet[i+1].fd) < 0) {
2898 				logerror("close() failed");
2899 				die(0, 0, NULL);
2900 			}
2901 			DEL_EVENT(finet[i+1].ev);
2902 			FREEPTR(finet[i+1].ev);
2903 		}
2904 		FREEPTR(finet);
2905 	}
2906 
2907 	/* free config options */
2908 	for (j = 0; j < A_CNT(TypeInfo); j++) {
2909 		FREEPTR(TypeInfo[j].queue_length_string);
2910 		FREEPTR(TypeInfo[j].queue_size_string);
2911 	}
2912 
2913 #ifndef DISABLE_TLS
2914 	FREEPTR(tls_opt.CAdir);
2915 	FREEPTR(tls_opt.CAfile);
2916 	FREEPTR(tls_opt.keyfile);
2917 	FREEPTR(tls_opt.certfile);
2918 	FREEPTR(tls_opt.x509verify);
2919 	FREEPTR(tls_opt.bindhost);
2920 	FREEPTR(tls_opt.bindport);
2921 	FREEPTR(tls_opt.server);
2922 	FREEPTR(tls_opt.gen_cert);
2923 	free_cred_SLIST(&tls_opt.cert_head);
2924 	free_cred_SLIST(&tls_opt.fprint_head);
2925 	FREE_SSL_CTX(tls_opt.global_TLS_CTX);
2926 #endif /* !DISABLE_TLS */
2927 
2928 	FREEPTR(funix);
2929 	for (p = LogPaths; p && *p; p++)
2930 		unlink(*p);
2931 	exit(0);
2932 }
2933 
2934 #ifndef DISABLE_SIGN
2935 /*
2936  * get one "sign_delim_sg2" item, convert and store in ordered queue
2937  */
2938 void
2939 store_sign_delim_sg2(char *tmp_buf)
2940 {
2941 	struct string_queue *sqentry, *sqe1, *sqe2;
2942 
2943 	if(!(sqentry = malloc(sizeof(*sqentry)))) {
2944 		logerror("Unable to allocate memory");
2945 		return;
2946 	}
2947 	/*LINTED constcond/null effect */
2948 	assert(sizeof(int64_t) == sizeof(uint_fast64_t));
2949 	if (dehumanize_number(tmp_buf, (int64_t*) &(sqentry->key)) == -1
2950 	    || sqentry->key > (LOG_NFACILITIES<<3)) {
2951 		DPRINTF(D_PARSE, "invalid sign_delim_sg2: %s\n", tmp_buf);
2952 		free(sqentry);
2953 		FREEPTR(tmp_buf);
2954 		return;
2955 	}
2956 	sqentry->data = tmp_buf;
2957 
2958 	if (STAILQ_EMPTY(&GlobalSign.sig2_delims)) {
2959 		STAILQ_INSERT_HEAD(&GlobalSign.sig2_delims,
2960 		    sqentry, entries);
2961 		return;
2962 	}
2963 
2964 	/* keep delimiters sorted */
2965 	sqe1 = sqe2 = STAILQ_FIRST(&GlobalSign.sig2_delims);
2966 	if (sqe1->key > sqentry->key) {
2967 		STAILQ_INSERT_HEAD(&GlobalSign.sig2_delims,
2968 		    sqentry, entries);
2969 		return;
2970 	}
2971 
2972 	while ((sqe1 = sqe2)
2973 	   && (sqe2 = STAILQ_NEXT(sqe1, entries))) {
2974 		if (sqe2->key > sqentry->key) {
2975 			break;
2976 		} else if (sqe2->key == sqentry->key) {
2977 			DPRINTF(D_PARSE, "duplicate sign_delim_sg2: %s\n",
2978 			    tmp_buf);
2979 			FREEPTR(sqentry);
2980 			FREEPTR(tmp_buf);
2981 			return;
2982 		}
2983 	}
2984 	STAILQ_INSERT_AFTER(&GlobalSign.sig2_delims, sqe1, sqentry, entries);
2985 }
2986 #endif /* !DISABLE_SIGN */
2987 
2988 /*
2989  * read syslog.conf
2990  */
2991 void
2992 read_config_file(FILE *cf, struct filed **f_ptr)
2993 {
2994 	size_t linenum = 0;
2995 	size_t i;
2996 	struct filed *f, **nextp;
2997 	char cline[LINE_MAX];
2998 	char prog[NAME_MAX + 1];
2999 	char host[MAXHOSTNAMELEN];
3000 	const char *p;
3001 	char *q;
3002 	bool found_keyword;
3003 #ifndef DISABLE_TLS
3004 	struct peer_cred *cred = NULL;
3005 	struct peer_cred_head *credhead = NULL;
3006 #endif /* !DISABLE_TLS */
3007 #ifndef DISABLE_SIGN
3008 	char *sign_sg_str = NULL;
3009 #endif /* !DISABLE_SIGN */
3010 #if (!defined(DISABLE_TLS) || !defined(DISABLE_SIGN))
3011 	char *tmp_buf = NULL;
3012 #endif /* (!defined(DISABLE_TLS) || !defined(DISABLE_SIGN)) */
3013 	/* central list of recognized configuration keywords
3014 	 * and an address for their values as strings */
3015 	const struct config_keywords {
3016 		const char *keyword;
3017 		char **variable;
3018 	} config_keywords[] = {
3019 #ifndef DISABLE_TLS
3020 		/* TLS settings */
3021 		{"tls_ca",		  &tls_opt.CAfile},
3022 		{"tls_cadir",		  &tls_opt.CAdir},
3023 		{"tls_cert",		  &tls_opt.certfile},
3024 		{"tls_key",		  &tls_opt.keyfile},
3025 		{"tls_verify",		  &tls_opt.x509verify},
3026 		{"tls_bindport",	  &tls_opt.bindport},
3027 		{"tls_bindhost",	  &tls_opt.bindhost},
3028 		{"tls_server",		  &tls_opt.server},
3029 		{"tls_gen_cert",	  &tls_opt.gen_cert},
3030 		/* special cases in parsing */
3031 		{"tls_allow_fingerprints",&tmp_buf},
3032 		{"tls_allow_clientcerts", &tmp_buf},
3033 		/* buffer settings */
3034 		{"tls_queue_length",	  &TypeInfo[F_TLS].queue_length_string},
3035 		{"tls_queue_size",	  &TypeInfo[F_TLS].queue_size_string},
3036 #endif /* !DISABLE_TLS */
3037 		{"file_queue_length",	  &TypeInfo[F_FILE].queue_length_string},
3038 		{"pipe_queue_length",	  &TypeInfo[F_PIPE].queue_length_string},
3039 		{"file_queue_size",	  &TypeInfo[F_FILE].queue_size_string},
3040 		{"pipe_queue_size",	  &TypeInfo[F_PIPE].queue_size_string},
3041 #ifndef DISABLE_SIGN
3042 		/* syslog-sign setting */
3043 		{"sign_sg",		  &sign_sg_str},
3044 		/* also special case in parsing */
3045 		{"sign_delim_sg2",	  &tmp_buf},
3046 #endif /* !DISABLE_SIGN */
3047 	};
3048 
3049 	DPRINTF(D_CALL, "read_config_file()\n");
3050 
3051 	/* free all previous config options */
3052 	for (i = 0; i < A_CNT(TypeInfo); i++) {
3053 		if (TypeInfo[i].queue_length_string
3054 		    && TypeInfo[i].queue_length_string
3055 		    != TypeInfo[i].default_length_string) {
3056 			FREEPTR(TypeInfo[i].queue_length_string);
3057 			TypeInfo[i].queue_length_string =
3058 				strdup(TypeInfo[i].default_length_string);
3059 		 }
3060 		if (TypeInfo[i].queue_size_string
3061 		    && TypeInfo[i].queue_size_string
3062 		    != TypeInfo[i].default_size_string) {
3063 			FREEPTR(TypeInfo[i].queue_size_string);
3064 			TypeInfo[i].queue_size_string =
3065 				strdup(TypeInfo[i].default_size_string);
3066 		 }
3067 	}
3068 	for (i = 0; i < A_CNT(config_keywords); i++)
3069 		FREEPTR(*config_keywords[i].variable);
3070 	/*
3071 	 * global settings
3072 	 */
3073 	while (fgets(cline, sizeof(cline), cf) != NULL) {
3074 		linenum++;
3075 		for (p = cline; isspace((unsigned char)*p); ++p)
3076 			continue;
3077 		if ((*p == '\0') || (*p == '#'))
3078 			continue;
3079 
3080 		for (i = 0; i < A_CNT(config_keywords); i++) {
3081 			if (copy_config_value(config_keywords[i].keyword,
3082 			    config_keywords[i].variable, &p, ConfFile,
3083 			    linenum)) {
3084 				DPRINTF((D_PARSE|D_MEM),
3085 				    "found option %s, saved @%p\n",
3086 				    config_keywords[i].keyword,
3087 				    *config_keywords[i].variable);
3088 #ifndef DISABLE_SIGN
3089 				if (!strcmp("sign_delim_sg2",
3090 				    config_keywords[i].keyword))
3091 					do {
3092 						store_sign_delim_sg2(tmp_buf);
3093 					} while (copy_config_value_word(
3094 					    &tmp_buf, &p));
3095 
3096 #endif /* !DISABLE_SIGN */
3097 
3098 #ifndef DISABLE_TLS
3099 				/* special cases with multiple parameters */
3100 				if (!strcmp("tls_allow_fingerprints",
3101 				    config_keywords[i].keyword))
3102 					credhead = &tls_opt.fprint_head;
3103 				else if (!strcmp("tls_allow_clientcerts",
3104 				    config_keywords[i].keyword))
3105 					credhead = &tls_opt.cert_head;
3106 
3107 				if (credhead) do {
3108 					if(!(cred = malloc(sizeof(*cred)))) {
3109 						logerror("Unable to "
3110 							"allocate memory");
3111 						break;
3112 					}
3113 					cred->data = tmp_buf;
3114 					tmp_buf = NULL;
3115 					SLIST_INSERT_HEAD(credhead,
3116 						cred, entries);
3117 				} while /* additional values? */
3118 					(copy_config_value_word(&tmp_buf, &p));
3119 				credhead = NULL;
3120 				break;
3121 #endif /* !DISABLE_TLS */
3122 			}
3123 		}
3124 	}
3125 	/* convert strings to integer values */
3126 	for (i = 0; i < A_CNT(TypeInfo); i++) {
3127 		if (!TypeInfo[i].queue_length_string
3128 		    || dehumanize_number(TypeInfo[i].queue_length_string,
3129 		    &TypeInfo[i].queue_length) == -1)
3130 			TypeInfo[i].queue_length = strtol(
3131 			    TypeInfo[i].default_length_string, NULL, 10);
3132 		if (!TypeInfo[i].queue_size_string
3133 		    || dehumanize_number(TypeInfo[i].queue_size_string,
3134 		    &TypeInfo[i].queue_size) == -1)
3135 			TypeInfo[i].queue_size = strtol(
3136 			    TypeInfo[i].default_size_string, NULL, 10);
3137 	}
3138 
3139 #ifndef DISABLE_SIGN
3140 	if (sign_sg_str) {
3141 		if (sign_sg_str[1] == '\0'
3142 		    && (sign_sg_str[0] == '0' || sign_sg_str[0] == '1'
3143 		    || sign_sg_str[0] == '2' || sign_sg_str[0] == '3'))
3144 			GlobalSign.sg = sign_sg_str[0] - '0';
3145 		else {
3146 			GlobalSign.sg = SIGN_SG;
3147 			DPRINTF(D_MISC, "Invalid sign_sg value `%s', "
3148 			    "use default value `%d'\n",
3149 			    sign_sg_str, GlobalSign.sg);
3150 		}
3151 	} else	/* disable syslog-sign */
3152 		GlobalSign.sg = -1;
3153 #endif /* !DISABLE_SIGN */
3154 
3155 	rewind(cf);
3156 	linenum = 0;
3157 	/*
3158 	 *  Foreach line in the conf table, open that file.
3159 	 */
3160 	f = NULL;
3161 	nextp = &f;
3162 
3163 	strcpy(prog, "*");
3164 	strcpy(host, "*");
3165 	while (fgets(cline, sizeof(cline), cf) != NULL) {
3166 		linenum++;
3167 		found_keyword = false;
3168 		/*
3169 		 * check for end-of-section, comments, strip off trailing
3170 		 * spaces and newline character.  #!prog is treated specially:
3171 		 * following lines apply only to that program.
3172 		 */
3173 		for (p = cline; isspace((unsigned char)*p); ++p)
3174 			continue;
3175 		if (*p == '\0')
3176 			continue;
3177 		if (*p == '#') {
3178 			p++;
3179 			if (*p != '!' && *p != '+' && *p != '-')
3180 				continue;
3181 		}
3182 
3183 		for (i = 0; i < A_CNT(config_keywords); i++) {
3184 			if (!strncasecmp(p, config_keywords[i].keyword,
3185 				strlen(config_keywords[i].keyword))) {
3186 				DPRINTF(D_PARSE,
3187 				    "skip cline %zu with keyword %s\n",
3188 				    linenum, config_keywords[i].keyword);
3189 				found_keyword = true;
3190 			}
3191 		}
3192 		if (found_keyword)
3193 			continue;
3194 
3195 		if (*p == '+' || *p == '-') {
3196 			host[0] = *p++;
3197 			while (isspace((unsigned char)*p))
3198 				p++;
3199 			if (*p == '\0' || *p == '*') {
3200 				strcpy(host, "*");
3201 				continue;
3202 			}
3203 			/* the +hostname expression will continue
3204 			 * to use the LocalHostName, not the FQDN */
3205 			for (i = 1; i < MAXHOSTNAMELEN - 1; i++) {
3206 				if (*p == '@') {
3207 					(void)strncpy(&host[i], LocalHostName,
3208 					    sizeof(host) - 1 - i);
3209 					host[sizeof(host) - 1] = '\0';
3210 					i = strlen(host) - 1;
3211 					p++;
3212 					continue;
3213 				}
3214 				if (!isalnum((unsigned char)*p) &&
3215 				    *p != '.' && *p != '-' && *p != ',')
3216 					break;
3217 				host[i] = *p++;
3218 			}
3219 			host[i] = '\0';
3220 			continue;
3221 		}
3222 		if (*p == '!') {
3223 			p++;
3224 			while (isspace((unsigned char)*p))
3225 				p++;
3226 			if (*p == '\0' || *p == '*') {
3227 				strcpy(prog, "*");
3228 				continue;
3229 			}
3230 			for (i = 0; i < NAME_MAX; i++) {
3231 				if (!isprint((unsigned char)p[i]))
3232 					break;
3233 				prog[i] = p[i];
3234 			}
3235 			prog[i] = '\0';
3236 			continue;
3237 		}
3238 		for (q = strchr(cline, '\0'); isspace((unsigned char)*--q);)
3239 			continue;
3240 		*++q = '\0';
3241 		if ((f = calloc(1, sizeof(*f))) == NULL) {
3242 			logerror("alloc failed");
3243 			die(0, 0, NULL);
3244 		}
3245 		if (!*f_ptr) *f_ptr = f; /* return first node */
3246 		*nextp = f;
3247 		nextp = &f->f_next;
3248 		cfline(linenum, cline, f, prog, host);
3249 	}
3250 }
3251 
3252 /*
3253  *  INIT -- Initialize syslogd from configuration table
3254  */
3255 void
3256 /*ARGSUSED*/
3257 init(int fd, short event, void *ev)
3258 {
3259 	FILE *cf;
3260 	int i;
3261 	struct filed *f, *newf, **nextp, *f2;
3262 	char *p;
3263 	sigset_t newmask, omask;
3264 #ifndef DISABLE_TLS
3265 	char *tls_status_msg = NULL;
3266 	struct peer_cred *cred = NULL;
3267 #endif /* !DISABLE_TLS */
3268 
3269 	/* prevent recursive signals */
3270 	BLOCK_SIGNALS(omask, newmask);
3271 
3272 	DPRINTF((D_EVENT|D_CALL), "init\n");
3273 
3274 	/*
3275 	 * be careful about dependencies and order of actions:
3276 	 * 1. flush buffer queues
3277 	 * 2. flush -sign SBs
3278 	 * 3. flush/delete buffer queue again, in case an SB got there
3279 	 * 4. close files/connections
3280 	 */
3281 
3282 	/*
3283 	 *  flush any pending output
3284 	 */
3285 	for (f = Files; f != NULL; f = f->f_next) {
3286 		/* flush any pending output */
3287 		if (f->f_prevcount)
3288 			fprintlog(f, NULL, NULL);
3289 		SEND_QUEUE(f);
3290 	}
3291 	/* some actions only on SIGHUP and not on first start */
3292 	if (Initialized) {
3293 #ifndef DISABLE_SIGN
3294 		sign_global_free();
3295 #endif /* !DISABLE_SIGN */
3296 #ifndef DISABLE_TLS
3297 		free_incoming_tls_sockets();
3298 #endif /* !DISABLE_TLS */
3299 		Initialized = 0;
3300 	}
3301 	/*
3302 	 *  Close all open log files.
3303 	 */
3304 	for (f = Files; f != NULL; f = f->f_next) {
3305 		switch (f->f_type) {
3306 		case F_FILE:
3307 		case F_TTY:
3308 		case F_CONSOLE:
3309 			(void)close(f->f_file);
3310 			break;
3311 		case F_PIPE:
3312 			if (f->f_un.f_pipe.f_pid > 0) {
3313 				(void)close(f->f_file);
3314 				deadq_enter(f->f_un.f_pipe.f_pid,
3315 				    f->f_un.f_pipe.f_pname);
3316 			}
3317 			f->f_un.f_pipe.f_pid = 0;
3318 			break;
3319 		case F_FORW:
3320 			if (f->f_un.f_forw.f_addr)
3321 				freeaddrinfo(f->f_un.f_forw.f_addr);
3322 			break;
3323 #ifndef DISABLE_TLS
3324 		case F_TLS:
3325 			free_tls_sslptr(f->f_un.f_tls.tls_conn);
3326 			break;
3327 #endif /* !DISABLE_TLS */
3328 		}
3329 	}
3330 
3331 	/*
3332 	 *  Close all open UDP sockets
3333 	 */
3334 	if (finet) {
3335 		for (i = 0; i < finet->fd; i++) {
3336 			if (close(finet[i+1].fd) < 0) {
3337 				logerror("close() failed");
3338 				die(0, 0, NULL);
3339 			}
3340 			DEL_EVENT(finet[i+1].ev);
3341 			FREEPTR(finet[i+1].ev);
3342 		}
3343 		FREEPTR(finet);
3344 	}
3345 
3346 	/* get FQDN and hostname/domain */
3347 	FREEPTR(oldLocalFQDN);
3348 	oldLocalFQDN = LocalFQDN;
3349 	LocalFQDN = getLocalFQDN();
3350 	if ((p = strchr(LocalFQDN, '.')) != NULL)
3351 		(void)strlcpy(LocalHostName, LocalFQDN, 1+p-LocalFQDN);
3352 	else
3353 		(void)strlcpy(LocalHostName, LocalFQDN, sizeof(LocalHostName));
3354 
3355 	/*
3356 	 *  Reset counter of forwarding actions
3357 	 */
3358 
3359 	NumForwards=0;
3360 
3361 	/* new destination list to replace Files */
3362 	newf = NULL;
3363 	nextp = &newf;
3364 
3365 	/* open the configuration file */
3366 	if ((cf = fopen(ConfFile, "r")) == NULL) {
3367 		DPRINTF(D_FILE, "Cannot open `%s'\n", ConfFile);
3368 		*nextp = (struct filed *)calloc(1, sizeof(*f));
3369 		cfline(0, "*.ERR\t/dev/console", *nextp, "*", "*");
3370 		(*nextp)->f_next = (struct filed *)calloc(1, sizeof(*f));
3371 		cfline(0, "*.PANIC\t*", (*nextp)->f_next, "*", "*");
3372 		Initialized = 1;
3373 		RESTORE_SIGNALS(omask);
3374 		return;
3375 	}
3376 
3377 #ifndef DISABLE_TLS
3378 	/* init with new TLS_CTX
3379 	 * as far as I see one cannot change the cert/key of an existing CTX
3380 	 */
3381 	FREE_SSL_CTX(tls_opt.global_TLS_CTX);
3382 
3383 	free_cred_SLIST(&tls_opt.cert_head);
3384 	free_cred_SLIST(&tls_opt.fprint_head);
3385 #endif /* !DISABLE_TLS */
3386 
3387 	/* read and close configuration file */
3388 	read_config_file(cf, &newf);
3389 	newf = *nextp;
3390 	(void)fclose(cf);
3391 	DPRINTF(D_MISC, "read_config_file() returned newf=%p\n", newf);
3392 
3393 #define MOVE_QUEUE(dst, src) do {				\
3394 	struct buf_queue *buf;					\
3395 	STAILQ_CONCAT(&dst->f_qhead, &src->f_qhead);		\
3396 	STAILQ_FOREACH(buf, &dst->f_qhead, entries) {		\
3397 	      dst->f_qelements++;				\
3398 	      dst->f_qsize += buf_queue_obj_size(buf);		\
3399 	}							\
3400 	src->f_qsize = 0;					\
3401 	src->f_qelements = 0;					\
3402 } while (/*CONSTCOND*/0)
3403 
3404 	/*
3405 	 *  Free old log files.
3406 	 */
3407 	for (f = Files; f != NULL;) {
3408 		struct filed *ftmp;
3409 
3410 		/* check if a new logfile is equal, if so pass the queue */
3411 		for (f2 = newf; f2 != NULL; f2 = f2->f_next) {
3412 			if (f->f_type == f2->f_type
3413 			    && ((f->f_type == F_PIPE
3414 			    && !strcmp(f->f_un.f_pipe.f_pname,
3415 			    f2->f_un.f_pipe.f_pname))
3416 #ifndef DISABLE_TLS
3417 			    || (f->f_type == F_TLS
3418 			    && !strcmp(f->f_un.f_tls.tls_conn->hostname,
3419 			    f2->f_un.f_tls.tls_conn->hostname)
3420 			    && !strcmp(f->f_un.f_tls.tls_conn->port,
3421 			    f2->f_un.f_tls.tls_conn->port))
3422 #endif /* !DISABLE_TLS */
3423 			    || (f->f_type == F_FORW
3424 			    && !strcmp(f->f_un.f_forw.f_hname,
3425 			    f2->f_un.f_forw.f_hname)))) {
3426 				DPRINTF(D_BUFFER, "move queue from f@%p "
3427 				    "to f2@%p\n", f, f2);
3428 				MOVE_QUEUE(f2, f);
3429 			 }
3430 		}
3431 		message_queue_freeall(f);
3432 		DELREF(f->f_prevmsg);
3433 #ifndef DISABLE_TLS
3434 		if (f->f_type == F_TLS)
3435 			free_tls_conn(f->f_un.f_tls.tls_conn);
3436 #endif /* !DISABLE_TLS */
3437 		FREEPTR(f->f_program);
3438 		FREEPTR(f->f_host);
3439 		DEL_EVENT(f->f_sq_event);
3440 
3441 		ftmp = f->f_next;
3442 		free((char *)f);
3443 		f = ftmp;
3444 	}
3445 	Files = newf;
3446 	Initialized = 1;
3447 
3448 	if (Debug) {
3449 		for (f = Files; f; f = f->f_next) {
3450 			for (i = 0; i <= LOG_NFACILITIES; i++)
3451 				if (f->f_pmask[i] == INTERNAL_NOPRI)
3452 					printf("X ");
3453 				else
3454 					printf("%d ", f->f_pmask[i]);
3455 			printf("%s: ", TypeInfo[f->f_type].name);
3456 			switch (f->f_type) {
3457 			case F_FILE:
3458 			case F_TTY:
3459 			case F_CONSOLE:
3460 				printf("%s", f->f_un.f_fname);
3461 				break;
3462 
3463 			case F_FORW:
3464 				printf("%s", f->f_un.f_forw.f_hname);
3465 				break;
3466 #ifndef DISABLE_TLS
3467 			case F_TLS:
3468 				printf("[%s]", f->f_un.f_tls.tls_conn->hostname);
3469 				break;
3470 #endif /* !DISABLE_TLS */
3471 			case F_PIPE:
3472 				printf("%s", f->f_un.f_pipe.f_pname);
3473 				break;
3474 
3475 			case F_USERS:
3476 				for (i = 0;
3477 				    i < MAXUNAMES && *f->f_un.f_uname[i]; i++)
3478 					printf("%s, ", f->f_un.f_uname[i]);
3479 				break;
3480 			}
3481 			if (f->f_program != NULL)
3482 				printf(" (%s)", f->f_program);
3483 			printf("\n");
3484 		}
3485 	}
3486 
3487 	finet = socksetup(PF_UNSPEC, bindhostname);
3488 	if (finet) {
3489 		if (SecureMode) {
3490 			for (i = 0; i < finet->fd; i++) {
3491 				if (shutdown(finet[i+1].fd, SHUT_RD) < 0) {
3492 					logerror("shutdown() failed");
3493 					die(0, 0, NULL);
3494 				}
3495 			}
3496 		} else
3497 			DPRINTF(D_NET, "Listening on inet and/or inet6 socket\n");
3498 		DPRINTF(D_NET, "Sending on inet and/or inet6 socket\n");
3499 	}
3500 
3501 #ifndef DISABLE_TLS
3502 	/* TLS setup -- after all local destinations opened  */
3503 	DPRINTF(D_PARSE, "Parsed options: tls_ca: %s, tls_cadir: %s, "
3504 	    "tls_cert: %s, tls_key: %s, tls_verify: %s, "
3505 	    "bind: %s:%s, max. queue_lengths: %"
3506 	    PRId64 ", %" PRId64 ", %" PRId64 ", "
3507 	    "max. queue_sizes: %"
3508 	    PRId64 ", %" PRId64 ", %" PRId64 "\n",
3509 	    tls_opt.CAfile, tls_opt.CAdir,
3510 	    tls_opt.certfile, tls_opt.keyfile, tls_opt.x509verify,
3511 	    tls_opt.bindhost, tls_opt.bindport,
3512 	    TypeInfo[F_TLS].queue_length, TypeInfo[F_FILE].queue_length,
3513 	    TypeInfo[F_PIPE].queue_length,
3514 	    TypeInfo[F_TLS].queue_size, TypeInfo[F_FILE].queue_size,
3515 	    TypeInfo[F_PIPE].queue_size);
3516 	SLIST_FOREACH(cred, &tls_opt.cert_head, entries) {
3517 		DPRINTF(D_PARSE, "Accepting peer certificate "
3518 		    "from file: \"%s\"\n", cred->data);
3519 	}
3520 	SLIST_FOREACH(cred, &tls_opt.fprint_head, entries) {
3521 		DPRINTF(D_PARSE, "Accepting peer certificate with "
3522 		    "fingerprint: \"%s\"\n", cred->data);
3523 	}
3524 
3525 	/* Note: The order of initialization is important because syslog-sign
3526 	 * should use the TLS cert for signing. -- So we check first if TLS
3527 	 * will be used and initialize it before starting -sign.
3528 	 *
3529 	 * This means that if we are a client without TLS destinations TLS
3530 	 * will not be initialized and syslog-sign will generate a new key.
3531 	 * -- Even if the user has set a usable tls_cert.
3532 	 * Is this the expected behaviour? The alternative would be to always
3533 	 * initialize the TLS structures, even if they will not be needed
3534 	 * (or only needed to read the DSA key for -sign).
3535 	 */
3536 
3537 	/* Initialize TLS only if used */
3538 	if (tls_opt.server)
3539 		tls_status_msg = init_global_TLS_CTX();
3540 	else
3541 		for (f = Files; f; f = f->f_next) {
3542 			if (f->f_type != F_TLS)
3543 				continue;
3544 			tls_status_msg = init_global_TLS_CTX();
3545 			break;
3546 		}
3547 
3548 #endif /* !DISABLE_TLS */
3549 
3550 #ifndef DISABLE_SIGN
3551 	/* only initialize -sign if actually used */
3552 	if (GlobalSign.sg == 0 || GlobalSign.sg == 1 || GlobalSign.sg == 2)
3553 		(void)sign_global_init(Files);
3554 	else if (GlobalSign.sg == 3)
3555 		for (f = Files; f; f = f->f_next)
3556 			if (f->f_flags & FFLAG_SIGN) {
3557 				(void)sign_global_init(Files);
3558 				break;
3559 			}
3560 #endif /* !DISABLE_SIGN */
3561 
3562 #ifndef DISABLE_TLS
3563 	if (tls_status_msg) {
3564 		loginfo("%s", tls_status_msg);
3565 		free(tls_status_msg);
3566 	}
3567 	DPRINTF((D_NET|D_TLS), "Preparing sockets for TLS\n");
3568 	TLS_Listen_Set =
3569 		socksetup_tls(PF_UNSPEC, tls_opt.bindhost, tls_opt.bindport);
3570 
3571 	for (f = Files; f; f = f->f_next) {
3572 		if (f->f_type != F_TLS)
3573 			continue;
3574 		if (!tls_connect(f->f_un.f_tls.tls_conn)) {
3575 			logerror("Unable to connect to TLS server %s",
3576 			    f->f_un.f_tls.tls_conn->hostname);
3577 			/* Reconnect after x seconds  */
3578 			schedule_event(&f->f_un.f_tls.tls_conn->event,
3579 			    &((struct timeval){TLS_RECONNECT_SEC, 0}),
3580 			    tls_reconnect, f->f_un.f_tls.tls_conn);
3581 		}
3582 	}
3583 #endif /* !DISABLE_TLS */
3584 
3585 	loginfo("restart");
3586 	/*
3587 	 * Log a change in hostname, but only on a restart (we detect this
3588 	 * by checking to see if we're passed a kevent).
3589 	 */
3590 	if (oldLocalFQDN && strcmp(oldLocalFQDN, LocalFQDN) != 0)
3591 		loginfo("host name changed, \"%s\" to \"%s\"",
3592 		    oldLocalFQDN, LocalFQDN);
3593 
3594 	RESTORE_SIGNALS(omask);
3595 }
3596 
3597 /*
3598  * Crack a configuration file line
3599  */
3600 void
3601 cfline(size_t linenum, const char *line, struct filed *f, const char *prog,
3602     const char *host)
3603 {
3604 	struct addrinfo hints, *res;
3605 	int    error, i, pri, syncfile;
3606 	const char   *p, *q;
3607 	char *bp;
3608 	char   buf[MAXLINE];
3609 
3610 	DPRINTF((D_CALL|D_PARSE),
3611 		"cfline(%zu, \"%s\", f, \"%s\", \"%s\")\n",
3612 		linenum, line, prog, host);
3613 
3614 	errno = 0;	/* keep strerror() stuff out of logerror messages */
3615 
3616 	/* clear out file entry */
3617 	memset(f, 0, sizeof(*f));
3618 	for (i = 0; i <= LOG_NFACILITIES; i++)
3619 		f->f_pmask[i] = INTERNAL_NOPRI;
3620 	STAILQ_INIT(&f->f_qhead);
3621 
3622 	/*
3623 	 * There should not be any space before the log facility.
3624 	 * Check this is okay, complain and fix if it is not.
3625 	 */
3626 	q = line;
3627 	if (isblank((unsigned char)*line)) {
3628 		errno = 0;
3629 		logerror("Warning: `%s' space or tab before the log facility",
3630 		    line);
3631 		/* Fix: strip all spaces/tabs before the log facility */
3632 		while (*q++ && isblank((unsigned char)*q))
3633 			/* skip blanks */;
3634 		line = q;
3635 	}
3636 
3637 	/*
3638 	 * q is now at the first char of the log facility
3639 	 * There should be at least one tab after the log facility
3640 	 * Check this is okay, and complain and fix if it is not.
3641 	 */
3642 	q = line + strlen(line);
3643 	while (!isblank((unsigned char)*q) && (q != line))
3644 		q--;
3645 	if ((q == line) && strlen(line)) {
3646 		/* No tabs or space in a non empty line: complain */
3647 		errno = 0;
3648 		logerror(
3649 		    "Error: `%s' log facility or log target missing",
3650 		    line);
3651 		return;
3652 	}
3653 
3654 	/* save host name, if any */
3655 	if (*host == '*')
3656 		f->f_host = NULL;
3657 	else {
3658 		f->f_host = strdup(host);
3659 		trim_anydomain(f->f_host);
3660 	}
3661 
3662 	/* save program name, if any */
3663 	if (*prog == '*')
3664 		f->f_program = NULL;
3665 	else
3666 		f->f_program = strdup(prog);
3667 
3668 	/* scan through the list of selectors */
3669 	for (p = line; *p && !isblank((unsigned char)*p);) {
3670 		int pri_done, pri_cmp, pri_invert;
3671 
3672 		/* find the end of this facility name list */
3673 		for (q = p; *q && !isblank((unsigned char)*q) && *q++ != '.'; )
3674 			continue;
3675 
3676 		/* get the priority comparison */
3677 		pri_cmp = 0;
3678 		pri_done = 0;
3679 		pri_invert = 0;
3680 		if (*q == '!') {
3681 			pri_invert = 1;
3682 			q++;
3683 		}
3684 		while (! pri_done) {
3685 			switch (*q) {
3686 			case '<':
3687 				pri_cmp = PRI_LT;
3688 				q++;
3689 				break;
3690 			case '=':
3691 				pri_cmp = PRI_EQ;
3692 				q++;
3693 				break;
3694 			case '>':
3695 				pri_cmp = PRI_GT;
3696 				q++;
3697 				break;
3698 			default:
3699 				pri_done = 1;
3700 				break;
3701 			}
3702 		}
3703 
3704 		/* collect priority name */
3705 		for (bp = buf; *q && !strchr("\t ,;", *q); )
3706 			*bp++ = *q++;
3707 		*bp = '\0';
3708 
3709 		/* skip cruft */
3710 		while (strchr(",;", *q))
3711 			q++;
3712 
3713 		/* decode priority name */
3714 		if (*buf == '*') {
3715 			pri = LOG_PRIMASK + 1;
3716 			pri_cmp = PRI_LT | PRI_EQ | PRI_GT;
3717 		} else {
3718 			pri = decode(buf, prioritynames);
3719 			if (pri < 0) {
3720 				errno = 0;
3721 				logerror("Unknown priority name `%s'", buf);
3722 				return;
3723 			}
3724 		}
3725 		if (pri_cmp == 0)
3726 			pri_cmp = UniquePriority ? PRI_EQ
3727 						 : PRI_EQ | PRI_GT;
3728 		if (pri_invert)
3729 			pri_cmp ^= PRI_LT | PRI_EQ | PRI_GT;
3730 
3731 		/* scan facilities */
3732 		while (*p && !strchr("\t .;", *p)) {
3733 			for (bp = buf; *p && !strchr("\t ,;.", *p); )
3734 				*bp++ = *p++;
3735 			*bp = '\0';
3736 			if (*buf == '*')
3737 				for (i = 0; i < LOG_NFACILITIES; i++) {
3738 					f->f_pmask[i] = pri;
3739 					f->f_pcmp[i] = pri_cmp;
3740 				}
3741 			else {
3742 				i = decode(buf, facilitynames);
3743 				if (i < 0) {
3744 					errno = 0;
3745 					logerror("Unknown facility name `%s'",
3746 					    buf);
3747 					return;
3748 				}
3749 				f->f_pmask[i >> 3] = pri;
3750 				f->f_pcmp[i >> 3] = pri_cmp;
3751 			}
3752 			while (*p == ',' || *p == ' ')
3753 				p++;
3754 		}
3755 
3756 		p = q;
3757 	}
3758 
3759 	/* skip to action part */
3760 	while (isblank((unsigned char)*p))
3761 		p++;
3762 
3763 	/*
3764 	 * should this be "#ifndef DISABLE_SIGN" or is it a general option?
3765 	 * '+' before file destination: write with PRI field for later
3766 	 * verification
3767 	 */
3768 	if (*p == '+') {
3769 		f->f_flags |= FFLAG_FULL;
3770 		p++;
3771 	}
3772 	if (*p == '-') {
3773 		syncfile = 0;
3774 		p++;
3775 	} else
3776 		syncfile = 1;
3777 
3778 	switch (*p) {
3779 	case '@':
3780 #ifndef DISABLE_SIGN
3781 		if (GlobalSign.sg == 3)
3782 			f->f_flags |= FFLAG_SIGN;
3783 #endif /* !DISABLE_SIGN */
3784 #ifndef DISABLE_TLS
3785 		if (*(p+1) == '[') {
3786 			/* TLS destination */
3787 			if (!parse_tls_destination(p, f, linenum)) {
3788 				logerror("Unable to parse action %s", p);
3789 				break;
3790 			}
3791 			f->f_type = F_TLS;
3792 			break;
3793 		}
3794 #endif /* !DISABLE_TLS */
3795 		(void)strlcpy(f->f_un.f_forw.f_hname, ++p,
3796 		    sizeof(f->f_un.f_forw.f_hname));
3797 		memset(&hints, 0, sizeof(hints));
3798 		hints.ai_family = AF_UNSPEC;
3799 		hints.ai_socktype = SOCK_DGRAM;
3800 		hints.ai_protocol = 0;
3801 		error = getaddrinfo(f->f_un.f_forw.f_hname, "syslog", &hints,
3802 		    &res);
3803 		if (error) {
3804 			logerror("%s", gai_strerror(error));
3805 			break;
3806 		}
3807 		f->f_un.f_forw.f_addr = res;
3808 		f->f_type = F_FORW;
3809 		NumForwards++;
3810 		break;
3811 
3812 	case '/':
3813 #ifndef DISABLE_SIGN
3814 		if (GlobalSign.sg == 3)
3815 			f->f_flags |= FFLAG_SIGN;
3816 #endif /* !DISABLE_SIGN */
3817 		(void)strlcpy(f->f_un.f_fname, p, sizeof(f->f_un.f_fname));
3818 		if ((f->f_file = open(p, O_WRONLY|O_APPEND, 0)) < 0) {
3819 			f->f_type = F_UNUSED;
3820 			logerror("%s", p);
3821 			break;
3822 		}
3823 		if (syncfile)
3824 			f->f_flags |= FFLAG_SYNC;
3825 		if (isatty(f->f_file))
3826 			f->f_type = F_TTY;
3827 		else
3828 			f->f_type = F_FILE;
3829 		if (strcmp(p, ctty) == 0)
3830 			f->f_type = F_CONSOLE;
3831 		break;
3832 
3833 	case '|':
3834 #ifndef DISABLE_SIGN
3835 		if (GlobalSign.sg == 3)
3836 			f->f_flags |= FFLAG_SIGN;
3837 #endif
3838 		f->f_un.f_pipe.f_pid = 0;
3839 		(void) strlcpy(f->f_un.f_pipe.f_pname, p + 1,
3840 		    sizeof(f->f_un.f_pipe.f_pname));
3841 		f->f_type = F_PIPE;
3842 		break;
3843 
3844 	case '*':
3845 		f->f_type = F_WALL;
3846 		break;
3847 
3848 	default:
3849 		for (i = 0; i < MAXUNAMES && *p; i++) {
3850 			for (q = p; *q && *q != ','; )
3851 				q++;
3852 			(void)strncpy(f->f_un.f_uname[i], p, UT_NAMESIZE);
3853 			if ((q - p) > UT_NAMESIZE)
3854 				f->f_un.f_uname[i][UT_NAMESIZE] = '\0';
3855 			else
3856 				f->f_un.f_uname[i][q - p] = '\0';
3857 			while (*q == ',' || *q == ' ')
3858 				q++;
3859 			p = q;
3860 		}
3861 		f->f_type = F_USERS;
3862 		break;
3863 	}
3864 }
3865 
3866 
3867 /*
3868  *  Decode a symbolic name to a numeric value
3869  */
3870 int
3871 decode(const char *name, CODE *codetab)
3872 {
3873 	CODE *c;
3874 	char *p, buf[40];
3875 
3876 	if (isdigit((unsigned char)*name))
3877 		return atoi(name);
3878 
3879 	for (p = buf; *name && p < &buf[sizeof(buf) - 1]; p++, name++) {
3880 		if (isupper((unsigned char)*name))
3881 			*p = tolower((unsigned char)*name);
3882 		else
3883 			*p = *name;
3884 	}
3885 	*p = '\0';
3886 	for (c = codetab; c->c_name; c++)
3887 		if (!strcmp(buf, c->c_name))
3888 			return c->c_val;
3889 
3890 	return -1;
3891 }
3892 
3893 /*
3894  * Retrieve the size of the kernel message buffer, via sysctl.
3895  */
3896 int
3897 getmsgbufsize(void)
3898 {
3899 #ifdef __NetBSD_Version__
3900 	int msgbufsize, mib[2];
3901 	size_t size;
3902 
3903 	mib[0] = CTL_KERN;
3904 	mib[1] = KERN_MSGBUFSIZE;
3905 	size = sizeof msgbufsize;
3906 	if (sysctl(mib, 2, &msgbufsize, &size, NULL, 0) == -1) {
3907 		DPRINTF(D_MISC, "Couldn't get kern.msgbufsize\n");
3908 		return 0;
3909 	}
3910 	return msgbufsize;
3911 #else
3912 	return MAXLINE;
3913 #endif /* __NetBSD_Version__ */
3914 }
3915 
3916 /*
3917  * Retrieve the hostname, via sysctl.
3918  */
3919 char *
3920 getLocalFQDN(void)
3921 {
3922 	int mib[2];
3923 	char *hostname;
3924 	size_t len;
3925 
3926 	mib[0] = CTL_KERN;
3927 	mib[1] = KERN_HOSTNAME;
3928 	sysctl(mib, 2, NULL, &len, NULL, 0);
3929 
3930 	if (!(hostname = malloc(len))) {
3931 		logerror("Unable to allocate memory");
3932 		die(0,0,NULL);
3933 	} else if (sysctl(mib, 2, hostname, &len, NULL, 0) == -1) {
3934 		DPRINTF(D_MISC, "Couldn't get kern.hostname\n");
3935 		(void)gethostname(hostname, sizeof(len));
3936 	}
3937 	return hostname;
3938 }
3939 
3940 struct socketEvent *
3941 socksetup(int af, const char *hostname)
3942 {
3943 	struct addrinfo hints, *res, *r;
3944 	int error, maxs;
3945 	int on = 1;
3946 	struct socketEvent *s, *socks;
3947 
3948 	if(SecureMode && !NumForwards)
3949 		return NULL;
3950 
3951 	memset(&hints, 0, sizeof(hints));
3952 	hints.ai_flags = AI_PASSIVE;
3953 	hints.ai_family = af;
3954 	hints.ai_socktype = SOCK_DGRAM;
3955 	error = getaddrinfo(hostname, "syslog", &hints, &res);
3956 	if (error) {
3957 		logerror("%s", gai_strerror(error));
3958 		errno = 0;
3959 		die(0, 0, NULL);
3960 	}
3961 
3962 	/* Count max number of sockets we may open */
3963 	for (maxs = 0, r = res; r; r = r->ai_next, maxs++)
3964 		continue;
3965 	socks = calloc(maxs+1, sizeof(*socks));
3966 	if (!socks) {
3967 		logerror("Couldn't allocate memory for sockets");
3968 		die(0, 0, NULL);
3969 	}
3970 
3971 	socks->fd = 0;	 /* num of sockets counter at start of array */
3972 	s = socks + 1;
3973 	for (r = res; r; r = r->ai_next) {
3974 		s->fd = socket(r->ai_family, r->ai_socktype, r->ai_protocol);
3975 		if (s->fd < 0) {
3976 			logerror("socket() failed");
3977 			continue;
3978 		}
3979 		if (r->ai_family == AF_INET6 && setsockopt(s->fd, IPPROTO_IPV6,
3980 		    IPV6_V6ONLY, &on, sizeof(on)) < 0) {
3981 			logerror("setsockopt(IPV6_V6ONLY) failed");
3982 			close(s->fd);
3983 			continue;
3984 		}
3985 
3986 		if (!SecureMode) {
3987 			if (bind(s->fd, r->ai_addr, r->ai_addrlen) < 0) {
3988 				logerror("bind() failed");
3989 				close(s->fd);
3990 				continue;
3991 			}
3992 			s->ev = allocev();
3993 			event_set(s->ev, s->fd, EV_READ | EV_PERSIST,
3994 				dispatch_read_finet, s->ev);
3995 			if (event_add(s->ev, NULL) == -1) {
3996 				DPRINTF((D_EVENT|D_NET),
3997 				    "Failure in event_add()\n");
3998 			} else {
3999 				DPRINTF((D_EVENT|D_NET),
4000 				    "Listen on UDP port "
4001 				    "(event@%p)\n", s->ev);
4002 			}
4003 		}
4004 
4005 		socks->fd++;  /* num counter */
4006 		s++;
4007 	}
4008 
4009 	if (res)
4010 		freeaddrinfo(res);
4011 	if (socks->fd == 0) {
4012 		free (socks);
4013 		if(Debug)
4014 			return NULL;
4015 		else
4016 			die(0, 0, NULL);
4017 	}
4018 	return socks;
4019 }
4020 
4021 /*
4022  * Fairly similar to popen(3), but returns an open descriptor, as opposed
4023  * to a FILE *.
4024  */
4025 int
4026 p_open(char *prog, pid_t *rpid)
4027 {
4028 	static char sh[] = "sh", mc[] = "-c";
4029 	int pfd[2], nulldesc, i;
4030 	pid_t pid;
4031 	char *argv[4];	/* sh -c cmd NULL */
4032 	char errmsg[200];
4033 
4034 	if (pipe(pfd) == -1)
4035 		return -1;
4036 	if ((nulldesc = open(_PATH_DEVNULL, O_RDWR)) == -1) {
4037 		/* We are royally screwed anyway. */
4038 		return -1;
4039 	}
4040 
4041 	switch ((pid = fork())) {
4042 	case -1:
4043 		(void) close(nulldesc);
4044 		return -1;
4045 
4046 	case 0:
4047 		argv[0] = sh;
4048 		argv[1] = mc;
4049 		argv[2] = prog;
4050 		argv[3] = NULL;
4051 
4052 		(void) setsid();	/* avoid catching SIGHUPs. */
4053 
4054 		/*
4055 		 * Reset ignored signals to their default behavior.
4056 		 */
4057 		(void)signal(SIGTERM, SIG_DFL);
4058 		(void)signal(SIGINT, SIG_DFL);
4059 		(void)signal(SIGQUIT, SIG_DFL);
4060 		(void)signal(SIGPIPE, SIG_DFL);
4061 		(void)signal(SIGHUP, SIG_DFL);
4062 
4063 		dup2(pfd[0], STDIN_FILENO);
4064 		dup2(nulldesc, STDOUT_FILENO);
4065 		dup2(nulldesc, STDERR_FILENO);
4066 		for (i = getdtablesize(); i > 2; i--)
4067 			(void) close(i);
4068 
4069 		(void) execvp(_PATH_BSHELL, argv);
4070 		_exit(255);
4071 	}
4072 
4073 	(void) close(nulldesc);
4074 	(void) close(pfd[0]);
4075 
4076 	/*
4077 	 * Avoid blocking on a hung pipe.  With O_NONBLOCK, we are
4078 	 * supposed to get an EWOULDBLOCK on writev(2), which is
4079 	 * caught by the logic above anyway, which will in turn
4080 	 * close the pipe, and fork a new logging subprocess if
4081 	 * necessary.  The stale subprocess will be killed some
4082 	 * time later unless it terminated itself due to closing
4083 	 * its input pipe.
4084 	 */
4085 	if (fcntl(pfd[1], F_SETFL, O_NONBLOCK) == -1) {
4086 		/* This is bad. */
4087 		(void) snprintf(errmsg, sizeof(errmsg),
4088 		    "Warning: cannot change pipe to pid %d to "
4089 		    "non-blocking.", (int) pid);
4090 		logerror("%s", errmsg);
4091 	}
4092 	*rpid = pid;
4093 	return pfd[1];
4094 }
4095 
4096 void
4097 deadq_enter(pid_t pid, const char *name)
4098 {
4099 	dq_t p;
4100 	int status;
4101 
4102 	/*
4103 	 * Be paranoid: if we can't signal the process, don't enter it
4104 	 * into the dead queue (perhaps it's already dead).  If possible,
4105 	 * we try to fetch and log the child's status.
4106 	 */
4107 	if (kill(pid, 0) != 0) {
4108 		if (waitpid(pid, &status, WNOHANG) > 0)
4109 			log_deadchild(pid, status, name);
4110 		return;
4111 	}
4112 
4113 	p = malloc(sizeof(*p));
4114 	if (p == NULL) {
4115 		errno = 0;
4116 		logerror("panic: out of memory!");
4117 		exit(1);
4118 	}
4119 
4120 	p->dq_pid = pid;
4121 	p->dq_timeout = DQ_TIMO_INIT;
4122 	TAILQ_INSERT_TAIL(&deadq_head, p, dq_entries);
4123 }
4124 
4125 int
4126 deadq_remove(pid_t pid)
4127 {
4128 	dq_t q;
4129 
4130 	for (q = TAILQ_FIRST(&deadq_head); q != NULL;
4131 	     q = TAILQ_NEXT(q, dq_entries)) {
4132 		if (q->dq_pid == pid) {
4133 			TAILQ_REMOVE(&deadq_head, q, dq_entries);
4134 			free(q);
4135 			return 1;
4136 		}
4137 	}
4138 	return 0;
4139 }
4140 
4141 void
4142 log_deadchild(pid_t pid, int status, const char *name)
4143 {
4144 	int code;
4145 	char buf[256];
4146 	const char *reason;
4147 
4148 	/* Keep strerror() struff out of logerror messages. */
4149 	errno = 0;
4150 	if (WIFSIGNALED(status)) {
4151 		reason = "due to signal";
4152 		code = WTERMSIG(status);
4153 	} else {
4154 		reason = "with status";
4155 		code = WEXITSTATUS(status);
4156 		if (code == 0)
4157 			return;
4158 	}
4159 	(void) snprintf(buf, sizeof(buf),
4160 	    "Logging subprocess %d (%s) exited %s %d.",
4161 	    pid, name, reason, code);
4162 	logerror("%s", buf);
4163 }
4164 
4165 struct event *
4166 allocev(void)
4167 {
4168 	struct event *ev;
4169 
4170 	if (!(ev = calloc(1, sizeof(*ev))))
4171 		logerror("Unable to allocate memory");
4172 	return ev;
4173 }
4174 
4175 /* *ev is allocated if necessary */
4176 void
4177 schedule_event(struct event **ev, struct timeval *tv,
4178 	void (*cb)(int, short, void *), void *arg)
4179 {
4180 	if (!*ev && !(*ev = allocev())) {
4181 		return;
4182 	}
4183 	event_set(*ev, 0, 0, cb, arg);
4184 	DPRINTF(D_EVENT, "event_add(%s@%p)\n", "schedule_ev", *ev); \
4185 	if (event_add(*ev, tv) == -1) {
4186 		DPRINTF(D_EVENT, "Failure in event_add()\n");
4187 	}
4188 }
4189 
4190 #ifndef DISABLE_TLS
4191 /* abbreviation for freeing credential lists */
4192 void
4193 free_cred_SLIST(struct peer_cred_head *head)
4194 {
4195 	struct peer_cred *cred;
4196 
4197 	while (!SLIST_EMPTY(head)) {
4198 		cred = SLIST_FIRST(head);
4199 		SLIST_REMOVE_HEAD(head, entries);
4200 		FREEPTR(cred->data);
4201 		free(cred);
4202 	}
4203 }
4204 #endif /* !DISABLE_TLS */
4205 
4206 /*
4207  * send message queue after reconnect
4208  */
4209 /*ARGSUSED*/
4210 void
4211 send_queue(int fd, short event, void *arg)
4212 {
4213 	struct filed *f = (struct filed *) arg;
4214 	struct buf_queue *qentry;
4215 #define SQ_CHUNK_SIZE 250
4216 	size_t cnt = 0;
4217 
4218 #ifndef DISABLE_TLS
4219 	if (f->f_type == F_TLS) {
4220 		/* use a flag to prevent recursive calls to send_queue() */
4221 		if (f->f_un.f_tls.tls_conn->send_queue)
4222 			return;
4223 		else
4224 			f->f_un.f_tls.tls_conn->send_queue = true;
4225 	}
4226 	DPRINTF((D_DATA|D_CALL), "send_queue(f@%p with %zu msgs, "
4227 		"cnt@%p = %zu)\n", f, f->f_qelements, &cnt, cnt);
4228 #endif /* !DISABLE_TLS */
4229 
4230 	while ((qentry = STAILQ_FIRST(&f->f_qhead))) {
4231 #ifndef DISABLE_TLS
4232 		/* send_queue() might be called with an unconnected destination
4233 		 * from init() or die() or one message might take longer,
4234 		 * leaving the connection in state ST_WAITING and thus not
4235 		 * ready for the next message.
4236 		 * this check is a shortcut to skip these unnecessary calls */
4237 		if (f->f_type == F_TLS
4238 		    && f->f_un.f_tls.tls_conn->state != ST_TLS_EST) {
4239 			DPRINTF(D_TLS, "abort send_queue(cnt@%p = %zu) "
4240 			    "on TLS connection in state %d\n",
4241 			    &cnt, cnt, f->f_un.f_tls.tls_conn->state);
4242 			return;
4243 		 }
4244 #endif /* !DISABLE_TLS */
4245 		fprintlog(f, qentry->msg, qentry);
4246 
4247 		/* Sending a long queue can take some time during which
4248 		 * SIGHUP and SIGALRM are blocked and no events are handled.
4249 		 * To avoid that we only send SQ_CHUNK_SIZE messages at once
4250 		 * and then reschedule ourselves to continue. Thus the control
4251 		 * will return first from all signal-protected functions so a
4252 		 * possible SIGHUP/SIGALRM is handled and then back to the
4253 		 * main loop which can handle possible input.
4254 		 */
4255 		if (++cnt >= SQ_CHUNK_SIZE) {
4256 			if (!f->f_sq_event) { /* alloc on demand */
4257 				f->f_sq_event = allocev();
4258 				event_set(f->f_sq_event, 0, 0, send_queue, f);
4259 			}
4260 			if (event_add(f->f_sq_event, &((struct timeval){0, 1})) == -1) {
4261 				DPRINTF(D_EVENT, "Failure in event_add()\n");
4262 			}
4263 			break;
4264 		}
4265 	}
4266 #ifndef DISABLE_TLS
4267 	if (f->f_type == F_TLS)
4268 		f->f_un.f_tls.tls_conn->send_queue = false;
4269 #endif
4270 
4271 }
4272 
4273 /*
4274  * finds the next queue element to delete
4275  *
4276  * has stateful behaviour, before using it call once with reset = true
4277  * after that every call will return one next queue elemen to delete,
4278  * depending on strategy either the oldest or the one with the lowest priority
4279  */
4280 static struct buf_queue *
4281 find_qentry_to_delete(const struct buf_queue_head *head, int strategy,
4282     bool reset)
4283 {
4284 	static int pri;
4285 	static struct buf_queue *qentry_static;
4286 
4287 	struct buf_queue *qentry_tmp;
4288 
4289 	if (reset || STAILQ_EMPTY(head)) {
4290 		pri = LOG_DEBUG;
4291 		qentry_static = STAILQ_FIRST(head);
4292 		return NULL;
4293 	}
4294 
4295 	/* find elements to delete */
4296 	if (strategy == PURGE_BY_PRIORITY) {
4297 		qentry_tmp = qentry_static;
4298 		while ((qentry_tmp = STAILQ_NEXT(qentry_tmp, entries)) != NULL)
4299 		{
4300 			if (LOG_PRI(qentry_tmp->msg->pri) == pri) {
4301 				/* save the successor, because qentry_tmp
4302 				 * is probably deleted by the caller */
4303 				qentry_static = STAILQ_NEXT(qentry_tmp, entries);
4304 				return qentry_tmp;
4305 			}
4306 		}
4307 		/* nothing found in while loop --> next pri */
4308 		if (--pri)
4309 			return find_qentry_to_delete(head, strategy, false);
4310 		else
4311 			return NULL;
4312 	} else /* strategy == PURGE_OLDEST or other value */ {
4313 		qentry_tmp = qentry_static;
4314 		qentry_static = STAILQ_NEXT(qentry_tmp, entries);
4315 		return qentry_tmp;  /* is NULL on empty queue */
4316 	}
4317 }
4318 
4319 /* note on TAILQ: newest message added at TAIL,
4320  *		  oldest to be removed is FIRST
4321  */
4322 /*
4323  * checks length of a destination's message queue
4324  * if del_entries == 0 then assert queue length is
4325  *   less or equal to configured number of queue elements
4326  * otherwise del_entries tells how many entries to delete
4327  *
4328  * returns the number of removed queue elements
4329  * (which not necessarily means free'd messages)
4330  *
4331  * strategy PURGE_OLDEST to delete oldest entry, e.g. after it was resent
4332  * strategy PURGE_BY_PRIORITY to delete messages with lowest priority first,
4333  *	this is much slower but might be desirable when unsent messages have
4334  *	to be deleted, e.g. in call from domark()
4335  */
4336 size_t
4337 message_queue_purge(struct filed *f, size_t del_entries, int strategy)
4338 {
4339 	size_t removed = 0;
4340 	struct buf_queue *qentry = NULL;
4341 
4342 	DPRINTF((D_CALL|D_BUFFER), "purge_message_queue(%p, %zu, %d) with "
4343 	    "f_qelements=%zu and f_qsize=%zu\n",
4344 	    f, del_entries, strategy,
4345 	    f->f_qelements, f->f_qsize);
4346 
4347 	/* reset state */
4348 	(void)find_qentry_to_delete(&f->f_qhead, strategy, true);
4349 
4350 	while (removed < del_entries
4351 	    || (TypeInfo[f->f_type].queue_length != -1
4352 	    && (size_t)TypeInfo[f->f_type].queue_length > f->f_qelements)
4353 	    || (TypeInfo[f->f_type].queue_size != -1
4354 	    && (size_t)TypeInfo[f->f_type].queue_size > f->f_qsize)) {
4355 		qentry = find_qentry_to_delete(&f->f_qhead, strategy, 0);
4356 		if (message_queue_remove(f, qentry))
4357 			removed++;
4358 		else
4359 			break;
4360 	}
4361 	return removed;
4362 }
4363 
4364 /* run message_queue_purge() for all destinations to free memory */
4365 size_t
4366 message_allqueues_purge(void)
4367 {
4368 	size_t sum = 0;
4369 	struct filed *f;
4370 
4371 	for (f = Files; f; f = f->f_next)
4372 		sum += message_queue_purge(f,
4373 		    f->f_qelements/10, PURGE_BY_PRIORITY);
4374 
4375 	DPRINTF(D_BUFFER,
4376 	    "message_allqueues_purge(): removed %zu buffer entries\n", sum);
4377 	return sum;
4378 }
4379 
4380 /* run message_queue_purge() for all destinations to check limits */
4381 size_t
4382 message_allqueues_check(void)
4383 {
4384 	size_t sum = 0;
4385 	struct filed *f;
4386 
4387 	for (f = Files; f; f = f->f_next)
4388 		sum += message_queue_purge(f, 0, PURGE_BY_PRIORITY);
4389 	DPRINTF(D_BUFFER,
4390 	    "message_allqueues_check(): removed %zu buffer entries\n", sum);
4391 	return sum;
4392 }
4393 
4394 struct buf_msg *
4395 buf_msg_new(const size_t len)
4396 {
4397 	struct buf_msg *newbuf;
4398 
4399 	CALLOC(newbuf, sizeof(*newbuf));
4400 
4401 	if (len) { /* len = 0 is valid */
4402 		MALLOC(newbuf->msg, len);
4403 		newbuf->msgorig = newbuf->msg;
4404 		newbuf->msgsize = len;
4405 	}
4406 	return NEWREF(newbuf);
4407 }
4408 
4409 void
4410 buf_msg_free(struct buf_msg *buf)
4411 {
4412 	if (!buf)
4413 		return;
4414 
4415 	buf->refcount--;
4416 	if (buf->refcount == 0) {
4417 		FREEPTR(buf->timestamp);
4418 		/* small optimizations: the host/recvhost may point to the
4419 		 * global HostName/FQDN. of course this must not be free()d
4420 		 * same goes for appname and include_pid
4421 		 */
4422 		if (buf->recvhost != buf->host
4423 		    && buf->recvhost != LocalHostName
4424 		    && buf->recvhost != LocalFQDN
4425 		    && buf->recvhost != oldLocalFQDN)
4426 			FREEPTR(buf->recvhost);
4427 		if (buf->host != LocalHostName
4428 		    && buf->host != LocalFQDN
4429 		    && buf->host != oldLocalFQDN)
4430 			FREEPTR(buf->host);
4431 		if (buf->prog != appname)
4432 			FREEPTR(buf->prog);
4433 		if (buf->pid != include_pid)
4434 			FREEPTR(buf->pid);
4435 		FREEPTR(buf->msgid);
4436 		FREEPTR(buf->sd);
4437 		FREEPTR(buf->msgorig);	/* instead of msg */
4438 		FREEPTR(buf);
4439 	}
4440 }
4441 
4442 size_t
4443 buf_queue_obj_size(struct buf_queue *qentry)
4444 {
4445 	size_t sum = 0;
4446 
4447 	if (!qentry)
4448 		return 0;
4449 	sum += sizeof(*qentry)
4450 	    + sizeof(*qentry->msg)
4451 	    + qentry->msg->msgsize
4452 	    + SAFEstrlen(qentry->msg->timestamp)+1
4453 	    + SAFEstrlen(qentry->msg->msgid)+1;
4454 	if (qentry->msg->prog
4455 	    && qentry->msg->prog != include_pid)
4456 		sum += strlen(qentry->msg->prog)+1;
4457 	if (qentry->msg->pid
4458 	    && qentry->msg->pid != appname)
4459 		sum += strlen(qentry->msg->pid)+1;
4460 	if (qentry->msg->recvhost
4461 	    && qentry->msg->recvhost != LocalHostName
4462 	    && qentry->msg->recvhost != LocalFQDN
4463 	    && qentry->msg->recvhost != oldLocalFQDN)
4464 		sum += strlen(qentry->msg->recvhost)+1;
4465 	if (qentry->msg->host
4466 	    && qentry->msg->host != LocalHostName
4467 	    && qentry->msg->host != LocalFQDN
4468 	    && qentry->msg->host != oldLocalFQDN)
4469 		sum += strlen(qentry->msg->host)+1;
4470 
4471 	return sum;
4472 }
4473 
4474 bool
4475 message_queue_remove(struct filed *f, struct buf_queue *qentry)
4476 {
4477 	if (!f || !qentry || !qentry->msg)
4478 		return false;
4479 
4480 	assert(!STAILQ_EMPTY(&f->f_qhead));
4481 	STAILQ_REMOVE(&f->f_qhead, qentry, buf_queue, entries);
4482 	f->f_qelements--;
4483 	f->f_qsize -= buf_queue_obj_size(qentry);
4484 
4485 	DPRINTF(D_BUFFER, "msg @%p removed from queue @%p, new qlen = %zu\n",
4486 	    qentry->msg, f, f->f_qelements);
4487 	DELREF(qentry->msg);
4488 	FREEPTR(qentry);
4489 	return true;
4490 }
4491 
4492 /*
4493  * returns *qentry on success and NULL on error
4494  */
4495 struct buf_queue *
4496 message_queue_add(struct filed *f, struct buf_msg *buffer)
4497 {
4498 	struct buf_queue *qentry;
4499 
4500 	/* check on every call or only every n-th time? */
4501 	message_queue_purge(f, 0, PURGE_BY_PRIORITY);
4502 
4503 	while (!(qentry = malloc(sizeof(*qentry)))
4504 	    && message_queue_purge(f, 1, PURGE_OLDEST))
4505 		continue;
4506 	if (!qentry) {
4507 		logerror("Unable to allocate memory");
4508 		DPRINTF(D_BUFFER, "queue empty, no memory, msg dropped\n");
4509 		return NULL;
4510 	} else {
4511 		qentry->msg = buffer;
4512 		f->f_qelements++;
4513 		f->f_qsize += buf_queue_obj_size(qentry);
4514 		STAILQ_INSERT_TAIL(&f->f_qhead, qentry, entries);
4515 
4516 		DPRINTF(D_BUFFER, "msg @%p queued @%p, qlen = %zu\n",
4517 		    buffer, f, f->f_qelements);
4518 		return qentry;
4519 	}
4520 }
4521 
4522 void
4523 message_queue_freeall(struct filed *f)
4524 {
4525 	struct buf_queue *qentry;
4526 
4527 	if (!f) return;
4528 	DPRINTF(D_MEM, "message_queue_freeall(f@%p) with f_qhead@%p\n", f,
4529 	    &f->f_qhead);
4530 
4531 	while (!STAILQ_EMPTY(&f->f_qhead)) {
4532 		qentry = STAILQ_FIRST(&f->f_qhead);
4533 		STAILQ_REMOVE(&f->f_qhead, qentry, buf_queue, entries);
4534 		DELREF(qentry->msg);
4535 		FREEPTR(qentry);
4536 	}
4537 
4538 	f->f_qelements = 0;
4539 	f->f_qsize = 0;
4540 }
4541 
4542 #ifndef DISABLE_TLS
4543 /* utility function for tls_reconnect() */
4544 struct filed *
4545 get_f_by_conninfo(struct tls_conn_settings *conn_info)
4546 {
4547 	struct filed *f;
4548 
4549 	for (f = Files; f; f = f->f_next) {
4550 		if ((f->f_type == F_TLS) && f->f_un.f_tls.tls_conn == conn_info)
4551 			return f;
4552 	}
4553 	DPRINTF(D_TLS, "get_f_by_conninfo() called on invalid conn_info\n");
4554 	return NULL;
4555 }
4556 
4557 /*
4558  * Called on signal.
4559  * Lets the admin reconnect without waiting for the reconnect timer expires.
4560  */
4561 /*ARGSUSED*/
4562 void
4563 dispatch_force_tls_reconnect(int fd, short event, void *ev)
4564 {
4565 	struct filed *f;
4566 	DPRINTF((D_TLS|D_CALL|D_EVENT), "dispatch_force_tls_reconnect()\n");
4567 	for (f = Files; f; f = f->f_next) {
4568 		if (f->f_type == F_TLS &&
4569 		    f->f_un.f_tls.tls_conn->state == ST_NONE)
4570 			tls_reconnect(fd, event, f->f_un.f_tls.tls_conn);
4571 	}
4572 }
4573 #endif /* !DISABLE_TLS */
4574 
4575 /*
4576  * return a timestamp in a static buffer,
4577  * either format the timestamp given by parameter in_now
4578  * or use the current time if in_now is NULL.
4579  */
4580 char *
4581 make_timestamp(time_t *in_now, bool iso)
4582 {
4583 	int frac_digits = 6;
4584 	struct timeval tv;
4585 	time_t mytime;
4586 	struct tm ltime;
4587 	int len = 0;
4588 	int tzlen = 0;
4589 	/* uses global var: time_t now; */
4590 
4591 	if (in_now) {
4592 		mytime = *in_now;
4593 	} else {
4594 		gettimeofday(&tv, NULL);
4595 		mytime = now = (time_t) tv.tv_sec;
4596 	}
4597 
4598 	if (!iso) {
4599 		strlcpy(timestamp, ctime(&mytime) + 4, TIMESTAMPBUFSIZE);
4600 		timestamp[BSD_TIMESTAMPLEN] = '\0';
4601 		return timestamp;
4602 	}
4603 
4604 	localtime_r(&mytime, &ltime);
4605 	len += strftime(timestamp, TIMESTAMPBUFSIZE, "%FT%T", &ltime);
4606 	snprintf(&(timestamp[len]), frac_digits+2, ".%.*ld",
4607 		frac_digits, (long)tv.tv_usec);
4608 	len += frac_digits+1;
4609 	tzlen = strftime(&(timestamp[len]), TIMESTAMPBUFSIZE-len, "%z", &ltime);
4610 	len += tzlen;
4611 
4612 	if (tzlen == 5) {
4613 		/* strftime gives "+0200", but we need "+02:00" */
4614 		timestamp[len+1] = timestamp[len];
4615 		timestamp[len] = timestamp[len-1];
4616 		timestamp[len-1] = timestamp[len-2];
4617 		timestamp[len-2] = ':';
4618 	}
4619 	return timestamp;
4620 }
4621 
4622 /* auxillary code to allocate memory and copy a string */
4623 bool
4624 copy_string(char **mem, const char *p, const char *q)
4625 {
4626 	const size_t len = 1 + q - p;
4627 	if (!(*mem = malloc(len))) {
4628 		logerror("Unable to allocate memory for config");
4629 		return false;
4630 	}
4631 	strlcpy(*mem, p, len);
4632 	return true;
4633 }
4634 
4635 /* keyword has to end with ",  everything until next " is copied */
4636 bool
4637 copy_config_value_quoted(const char *keyword, char **mem, const char **p)
4638 {
4639 	const char *q;
4640 	if (strncasecmp(*p, keyword, strlen(keyword)))
4641 		return false;
4642 	q = *p += strlen(keyword);
4643 	if (!(q = strchr(*p, '"'))) {
4644 		logerror("unterminated \"\n");
4645 		return false;
4646 	}
4647 	if (!(copy_string(mem, *p, q)))
4648 		return false;
4649 	*p = ++q;
4650 	return true;
4651 }
4652 
4653 /* for config file:
4654  * following = required but whitespace allowed, quotes optional
4655  * if numeric, then conversion to integer and no memory allocation
4656  */
4657 bool
4658 copy_config_value(const char *keyword, char **mem,
4659 	const char **p, const char *file, int line)
4660 {
4661 	if (strncasecmp(*p, keyword, strlen(keyword)))
4662 		return false;
4663 	*p += strlen(keyword);
4664 
4665 	while (isspace((unsigned char)**p))
4666 		*p += 1;
4667 	if (**p != '=') {
4668 		logerror("expected \"=\" in file %s, line %d", file, line);
4669 		return false;
4670 	}
4671 	*p += 1;
4672 
4673 	return copy_config_value_word(mem, p);
4674 }
4675 
4676 /* copy next parameter from a config line */
4677 bool
4678 copy_config_value_word(char **mem, const char **p)
4679 {
4680 	const char *q;
4681 	while (isspace((unsigned char)**p))
4682 		*p += 1;
4683 	if (**p == '"')
4684 		return copy_config_value_quoted("\"", mem, p);
4685 
4686 	/* without quotes: find next whitespace or end of line */
4687 	(void)((q = strchr(*p, ' ')) || (q = strchr(*p, '\t'))
4688 	     || (q = strchr(*p, '\n')) || (q = strchr(*p, '\0')));
4689 
4690 	if (q-*p == 0 || !(copy_string(mem, *p, q)))
4691 		return false;
4692 
4693 	*p = ++q;
4694 	return true;
4695 }
4696