GCC Code Coverage Report
Directory: ./ Exec Total Coverage
File: usr.sbin/syslogd/syslogd.c Lines: 98 1723 5.7 %
Date: 2017-11-07 Branches: 50 1309 3.8 %

Line Branch Exec Source
1
/*	$OpenBSD: syslogd.c,v 1.250 2017/10/02 12:24:03 bluhm 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
/*
33
 *  syslogd -- log system messages
34
 *
35
 * This program implements a system log. It takes a series of lines.
36
 * Each line may have a priority, signified as "<n>" as
37
 * the first characters of the line.  If this is
38
 * not present, a default priority is used.
39
 *
40
 * To kill syslogd, send a signal 15 (terminate).  A signal 1 (hup) will
41
 * cause it to reread its configuration file.
42
 *
43
 * Defined Constants:
44
 *
45
 * MAXLINE -- the maximum line length that can be handled.
46
 * DEFUPRI -- the default priority for user messages
47
 * DEFSPRI -- the default priority for kernel messages
48
 *
49
 * Author: Eric Allman
50
 * extensive changes by Ralph Campbell
51
 * more extensive changes by Eric Allman (again)
52
 * memory buffer logging by Damien Miller
53
 * IPv6, libevent, syslog over TCP and TLS by Alexander Bluhm
54
 */
55
56
#define MAX_UDPMSG	1180		/* maximum UDP send size */
57
#define MIN_MEMBUF	(LOG_MAXLINE * 4) /* Minimum memory buffer size */
58
#define MAX_MEMBUF	(256 * 1024)	/* Maximum memory buffer size */
59
#define MAX_MEMBUF_NAME	64		/* Max length of membuf log name */
60
#define MAX_TCPBUF	(256 * 1024)	/* Maximum tcp event buffer size */
61
#define	MAXSVLINE	120		/* maximum saved line length */
62
#define FD_RESERVE	5		/* file descriptors not accepted */
63
#define DEFUPRI		(LOG_USER|LOG_NOTICE)
64
#define DEFSPRI		(LOG_KERN|LOG_CRIT)
65
#define TIMERINTVL	30		/* interval for checking flush, mark */
66
67
#include <sys/ioctl.h>
68
#include <sys/stat.h>
69
#include <sys/msgbuf.h>
70
#include <sys/queue.h>
71
#include <sys/sysctl.h>
72
#include <sys/un.h>
73
#include <sys/time.h>
74
#include <sys/resource.h>
75
76
#include <netinet/in.h>
77
#include <netdb.h>
78
#include <arpa/inet.h>
79
80
#include <ctype.h>
81
#include <err.h>
82
#include <errno.h>
83
#include <event.h>
84
#include <fcntl.h>
85
#include <limits.h>
86
#include <paths.h>
87
#include <signal.h>
88
#include <stdio.h>
89
#include <stdlib.h>
90
#include <string.h>
91
#include <tls.h>
92
#include <unistd.h>
93
#include <utmp.h>
94
#include <vis.h>
95
96
#define MAXIMUM(a, b)	(((a) > (b)) ? (a) : (b))
97
#define MINIMUM(a, b)	(((a) < (b)) ? (a) : (b))
98
99
#define SYSLOG_NAMES
100
#include <sys/syslog.h>
101
102
#include "log.h"
103
#include "syslogd.h"
104
#include "evbuffer_tls.h"
105
106
char *ConfFile = _PATH_LOGCONF;
107
const char ctty[] = _PATH_CONSOLE;
108
109
#define MAXUNAMES	20	/* maximum number of user names */
110
111
112
/*
113
 * Flags to logline().
114
 */
115
116
#define IGN_CONS	0x001	/* don't print on console */
117
#define SYNC_FILE	0x002	/* do fsync on file after printing */
118
#define ADDDATE		0x004	/* add a date to the message */
119
#define MARK		0x008	/* this message is a mark */
120
121
/*
122
 * This structure represents the files that will have log
123
 * copies printed.
124
 */
125
126
struct filed {
127
	SIMPLEQ_ENTRY(filed) f_next;	/* next in linked list */
128
	int	f_type;			/* entry type, see below */
129
	int	f_file;			/* file descriptor */
130
	time_t	f_time;			/* time this was last written */
131
	u_char	f_pmask[LOG_NFACILITIES+1];	/* priority mask */
132
	char	*f_program;		/* program this applies to */
133
	char	*f_hostname;		/* host this applies to */
134
	union {
135
		char	f_uname[MAXUNAMES][UT_NAMESIZE+1];
136
		struct {
137
			char	f_loghost[1+4+3+1+NI_MAXHOST+1+NI_MAXSERV];
138
				/* @proto46://[hostname]:servname\0 */
139
			struct sockaddr_storage	 f_addr;
140
			struct buffertls	 f_buftls;
141
			struct bufferevent	*f_bufev;
142
			struct tls		*f_ctx;
143
			char			*f_host;
144
			int			 f_reconnectwait;
145
			int			 f_dropped;
146
		} f_forw;		/* forwarding address */
147
		char	f_fname[PATH_MAX];
148
		struct {
149
			char	f_mname[MAX_MEMBUF_NAME];
150
			struct ringbuf *f_rb;
151
			int	f_overflow;
152
			int	f_attached;
153
			size_t	f_len;
154
		} f_mb;		/* Memory buffer */
155
	} f_un;
156
	char	f_prevline[MAXSVLINE];		/* last message logged */
157
	char	f_lasttime[33];			/* time of last occurrence */
158
	char	f_prevhost[HOST_NAME_MAX+1];	/* host from which recd. */
159
	int	f_prevpri;			/* pri of f_prevline */
160
	int	f_prevlen;			/* length of f_prevline */
161
	int	f_prevcount;			/* repetition cnt of prevline */
162
	unsigned int f_repeatcount;		/* number of "repeated" msgs */
163
	int	f_quick;			/* abort when matched */
164
	time_t	f_lasterrtime;			/* last error was reported */
165
};
166
167
/*
168
 * Intervals at which we flush out "message repeated" messages,
169
 * in seconds after previous message is logged.  After each flush,
170
 * we move to the next interval until we reach the largest.
171
 */
172
int	repeatinterval[] = { 30, 120, 600 };	/* # of secs before flush */
173
#define	MAXREPEAT ((sizeof(repeatinterval) / sizeof(repeatinterval[0])) - 1)
174
#define	REPEATTIME(f)	((f)->f_time + repeatinterval[(f)->f_repeatcount])
175
#define	BACKOFF(f)	{ if (++(f)->f_repeatcount > MAXREPEAT) \
176
				(f)->f_repeatcount = MAXREPEAT; \
177
			}
178
179
/* values for f_type */
180
#define F_UNUSED	0		/* unused entry */
181
#define F_FILE		1		/* regular file */
182
#define F_TTY		2		/* terminal */
183
#define F_CONSOLE	3		/* console terminal */
184
#define F_FORWUDP	4		/* remote machine via UDP */
185
#define F_USERS		5		/* list of users */
186
#define F_WALL		6		/* everyone logged on */
187
#define F_MEMBUF	7		/* memory buffer */
188
#define F_PIPE		8		/* pipe to external program */
189
#define F_FORWTCP	9		/* remote machine via TCP */
190
#define F_FORWTLS	10		/* remote machine via TLS */
191
192
char	*TypeNames[] = {
193
	"UNUSED",	"FILE",		"TTY",		"CONSOLE",
194
	"FORWUDP",	"USERS",	"WALL",		"MEMBUF",
195
	"PIPE",		"FORWTCP",	"FORWTLS",
196
};
197
198
SIMPLEQ_HEAD(filed_list, filed) Files;
199
struct	filed consfile;
200
201
int	nunix;			/* Number of Unix domain sockets requested */
202
char	**path_unix;		/* Paths to Unix domain sockets */
203
int	Debug;			/* debug flag */
204
int	Foreground;		/* run in foreground, instead of daemonizing */
205
char	LocalHostName[HOST_NAME_MAX+1];	/* our hostname */
206
char	*LocalDomain;		/* our local domain name */
207
int	Started = 0;		/* set after privsep */
208
int	Initialized = 0;	/* set when we have initialized ourselves */
209
210
int	MarkInterval = 20 * 60;	/* interval between marks in seconds */
211
int	MarkSeq = 0;		/* mark sequence number */
212
int	PrivChild = 0;		/* Exec the privileged parent process */
213
int	Repeat = 0;		/* 0 msg repeated, 1 in files only, 2 never */
214
int	SecureMode = 1;		/* when true, speak only unix domain socks */
215
int	NoDNS = 0;		/* when true, refrain from doing DNS lookups */
216
int	ZuluTime = 0;		/* display date and time in UTC ISO format */
217
int	IncludeHostname = 0;	/* include RFC 3164 hostnames when forwarding */
218
int	Family = PF_UNSPEC;	/* protocol family, may disable IPv4 or IPv6 */
219
char	*path_ctlsock = NULL;	/* Path to control socket */
220
221
struct	tls *server_ctx;
222
struct	tls_config *client_config, *server_config;
223
const char *CAfile = "/etc/ssl/cert.pem"; /* file containing CA certificates */
224
int	NoVerify = 0;		/* do not verify TLS server x509 certificate */
225
const char *ClientCertfile = NULL;
226
const char *ClientKeyfile = NULL;
227
const char *ServerCAfile = NULL;
228
int	tcpbuf_dropped = 0;	/* count messages dropped from TCP or TLS */
229
230
#define CTL_READING_CMD		1
231
#define CTL_WRITING_REPLY	2
232
#define CTL_WRITING_CONT_REPLY	3
233
int	ctl_state = 0;		/* What the control socket is up to */
234
int	membuf_drop = 0;	/* logs dropped in continuous membuf read */
235
236
/*
237
 * Client protocol NB. all numeric fields in network byte order
238
 */
239
#define CTL_VERSION		2
240
241
/* Request */
242
struct	{
243
	u_int32_t	version;
244
#define CMD_READ	1	/* Read out log */
245
#define CMD_READ_CLEAR	2	/* Read and clear log */
246
#define CMD_CLEAR	3	/* Clear log */
247
#define CMD_LIST	4	/* List available logs */
248
#define CMD_FLAGS	5	/* Query flags only */
249
#define CMD_READ_CONT	6	/* Read out log continuously */
250
	u_int32_t	cmd;
251
	u_int32_t	lines;
252
	char		logname[MAX_MEMBUF_NAME];
253
}	ctl_cmd;
254
255
size_t	ctl_cmd_bytes = 0;	/* number of bytes of ctl_cmd read */
256
257
/* Reply */
258
struct ctl_reply_hdr {
259
	u_int32_t	version;
260
#define CTL_HDR_FLAG_OVERFLOW	0x01
261
	u_int32_t	flags;
262
	/* Reply text follows, up to MAX_MEMBUF long */
263
};
264
265
#define CTL_HDR_LEN		(sizeof(struct ctl_reply_hdr))
266
#define CTL_REPLY_MAXSIZE	(CTL_HDR_LEN + MAX_MEMBUF)
267
#define CTL_REPLY_SIZE		(strlen(reply_text) + CTL_HDR_LEN)
268
269
char	*ctl_reply = NULL;	/* Buffer for control connection reply */
270
char	*reply_text;		/* Start of reply text in buffer */
271
size_t	ctl_reply_size = 0;	/* Number of bytes used in reply */
272
size_t	ctl_reply_offset = 0;	/* Number of bytes of reply written so far */
273
274
char	*linebuf;
275
int	 linesize;
276
277
int		 fd_ctlconn, fd_udp, fd_udp6, send_udp, send_udp6;
278
struct event	*ev_ctlaccept, *ev_ctlread, *ev_ctlwrite;
279
280
struct peer {
281
	struct buffertls	 p_buftls;
282
	struct bufferevent	*p_bufev;
283
	struct tls		*p_ctx;
284
	char			*p_peername;
285
	char			*p_hostname;
286
	int			 p_fd;
287
};
288
char hostname_unknown[] = "???";
289
290
void	 klog_readcb(int, short, void *);
291
void	 udp_readcb(int, short, void *);
292
void	 unix_readcb(int, short, void *);
293
int	 reserve_accept4(int, int, struct event *,
294
    void (*)(int, short, void *), struct sockaddr *, socklen_t *, int);
295
void	 tcp_acceptcb(int, short, void *);
296
void	 tls_acceptcb(int, short, void *);
297
void	 acceptcb(int, short, void *, int);
298
int	 octet_counting(struct evbuffer *, char **, int);
299
int	 non_transparent_framing(struct evbuffer *, char **);
300
void	 tcp_readcb(struct bufferevent *, void *);
301
void	 tcp_closecb(struct bufferevent *, short, void *);
302
int	 tcp_socket(struct filed *);
303
void	 tcp_dropcb(struct bufferevent *, void *);
304
void	 tcp_writecb(struct bufferevent *, void *);
305
void	 tcp_errorcb(struct bufferevent *, short, void *);
306
void	 tcp_connectcb(int, short, void *);
307
void	 tcp_connect_retry(struct bufferevent *, struct filed *);
308
int	 tcpbuf_countmsg(struct bufferevent *bufev);
309
void	 die_signalcb(int, short, void *);
310
void	 mark_timercb(int, short, void *);
311
void	 init_signalcb(int, short, void *);
312
void	 ctlsock_acceptcb(int, short, void *);
313
void	 ctlconn_readcb(int, short, void *);
314
void	 ctlconn_writecb(int, short, void *);
315
void	 ctlconn_logto(char *);
316
void	 ctlconn_cleanup(void);
317
318
struct filed *cfline(char *, char *, char *);
319
void	cvthname(struct sockaddr *, char *, size_t);
320
int	decode(const char *, const CODE *);
321
void	markit(void);
322
void	fprintlog(struct filed *, int, char *);
323
void	init(void);
324
void	logevent(int, const char *);
325
void	logline(int, int, char *, char *);
326
struct filed *find_dup(struct filed *);
327
size_t	parsepriority(const char *, int *);
328
void	printline(char *, char *);
329
void	printsys(char *);
330
void	usage(void);
331
void	wallmsg(struct filed *, struct iovec *);
332
int	loghost_parse(char *, char **, char **, char **);
333
int	getmsgbufsize(void);
334
void	address_alloc(const char *, const char *, char ***, char ***, int *);
335
int	socket_bind(const char *, const char *, const char *, int,
336
    int *, int *);
337
int	unix_socket(char *, int, mode_t);
338
void	double_sockbuf(int, int);
339
void	set_sockbuf(int);
340
void	tailify_replytext(char *, int);
341
342
int
343
main(int argc, char *argv[])
344
{
345
1748
	struct timeval	 to;
346
	struct event	*ev_klog, *ev_sendsys, *ev_udp, *ev_udp6,
347
			*ev_bind, *ev_listen, *ev_tls, *ev_unix,
348
			*ev_hup, *ev_int, *ev_quit, *ev_term, *ev_mark;
349
874
	sigset_t	 sigmask;
350
874
	const char	*errstr;
351
874
	char		*p;
352
	int		 ch, i;
353
874
	int		 lockpipe[2] = { -1, -1}, pair[2], nullfd, fd;
354
	int		 fd_ctlsock, fd_klog, fd_sendsys, *fd_bind, *fd_listen;
355
874
	int		*fd_tls, *fd_unix, nbind, nlisten, ntls;
356
874
	char		**bind_host, **bind_port, **listen_host, **listen_port;
357
874
	char		*tls_hostport, **tls_host, **tls_port;
358
359
	/* block signal until handler is set up */
360
874
	sigemptyset(&sigmask);
361
874
	sigaddset(&sigmask, SIGHUP);
362
874
	if (sigprocmask(SIG_SETMASK, &sigmask, NULL) == -1)
363
		err(1, "sigprocmask block");
364
365
874
	if ((path_unix = malloc(sizeof(*path_unix))) == NULL)
366
		err(1, "malloc %s", _PATH_LOG);
367
874
	path_unix[0] = _PATH_LOG;
368
874
	nunix = 1;
369
370
874
	bind_host = listen_host = tls_host = NULL;
371
874
	bind_port = listen_port = tls_port = NULL;
372
	tls_hostport = NULL;
373
874
	nbind = nlisten = ntls = 0;
374
375
11150
	while ((ch = getopt(argc, argv,
376
5138
	    "46a:C:c:dFf:hK:k:m:nP:p:rS:s:T:U:uVZ")) != -1) {
377






4264
		switch (ch) {
378
		case '4':		/* disable IPv6 */
379
20
			Family = PF_INET;
380
20
			break;
381
		case '6':		/* disable IPv4 */
382
20
			Family = PF_INET6;
383
20
			break;
384
		case 'a':
385
210
			if ((path_unix = reallocarray(path_unix, nunix + 1,
386
105
			    sizeof(*path_unix))) == NULL)
387
				err(1, "unix path %s", optarg);
388
105
			path_unix[nunix++] = optarg;
389
105
			break;
390
		case 'C':		/* file containing CA certificates */
391
45
			CAfile = optarg;
392
45
			break;
393
		case 'c':		/* file containing client certificate */
394
15
			ClientCertfile = optarg;
395
15
			break;
396
		case 'd':		/* debug */
397
860
			Debug++;
398
860
			break;
399
		case 'F':		/* foreground */
400
5
			Foreground = 1;
401
5
			break;
402
		case 'f':		/* configuration file */
403
870
			ConfFile = optarg;
404
870
			break;
405
		case 'h':		/* RFC 3164 hostnames */
406
5
			IncludeHostname = 1;
407
5
			break;
408
		case 'K':		/* verify client with CA file */
409
15
			ServerCAfile = optarg;
410
15
			break;
411
		case 'k':		/* file containing client key */
412
15
			ClientKeyfile = optarg;
413
15
			break;
414
		case 'm':		/* mark interval */
415
			MarkInterval = strtonum(optarg, 0, 365*24*60, &errstr);
416
			if (errstr)
417
				errx(1, "mark_interval %s: %s", errstr, optarg);
418
			MarkInterval *= 60;
419
			break;
420
		case 'n':		/* don't do DNS lookups */
421
85
			NoDNS = 1;
422
85
			break;
423
		case 'P':		/* used internally, exec the parent */
424
874
			PrivChild = strtonum(optarg, 2, INT_MAX, &errstr);
425
874
			if (errstr)
426
				errx(1, "priv child %s: %s", errstr, optarg);
427
			break;
428
		case 'p':		/* path */
429
10
			path_unix[0] = optarg;
430
10
			break;
431
		case 'r':
432
25
			Repeat++;
433
25
			break;
434
		case 'S':		/* allow tls and listen on address */
435
90
			if (tls_hostport == NULL)
436
80
				tls_hostport = optarg;
437
90
			address_alloc("tls", optarg, &tls_host, &tls_port,
438
			    &ntls);
439
90
			break;
440
		case 's':
441
50
			path_ctlsock = optarg;
442
50
			break;
443
		case 'T':		/* allow tcp and listen on address */
444
140
			address_alloc("listen", optarg, &listen_host,
445
			    &listen_port, &nlisten);
446
140
			break;
447
		case 'U':		/* allow udp only from address */
448
80
			address_alloc("bind", optarg, &bind_host, &bind_port,
449
			    &nbind);
450
80
			break;
451
		case 'u':		/* allow udp input port */
452
100
			SecureMode = 0;
453
100
			break;
454
		case 'V':		/* do not verify certificates */
455
820
			NoVerify = 1;
456
820
			break;
457
		case 'Z':		/* time stamps in UTC ISO format */
458
15
			ZuluTime = 1;
459
15
			break;
460
		default:
461
			usage();
462
		}
463
	}
464
874
	if (argc != optind)
465
		usage();
466
467
874
	log_init(Debug, LOG_SYSLOG);
468
874
	log_procinit("syslogd");
469
874
	if (Debug)
470
860
		setvbuf(stdout, NULL, _IOLBF, 0);
471
472
874
	if ((nullfd = open(_PATH_DEVNULL, O_RDWR)) == -1)
473
		fatal("open %s", _PATH_DEVNULL);
474
1748
	for (fd = nullfd + 1; fd <= STDERR_FILENO; fd++) {
475
		if (fcntl(fd, F_GETFL) == -1 && errno == EBADF)
476
			if (dup2(nullfd, fd) == -1)
477
				fatal("dup2 null");
478
	}
479
480
874
	if (PrivChild > 1)
481
		priv_exec(ConfFile, NoDNS, PrivChild, argc, argv);
482
483
	consfile.f_type = F_CONSOLE;
484
	(void)strlcpy(consfile.f_un.f_fname, ctty,
485
	    sizeof(consfile.f_un.f_fname));
486
	consfile.f_file = open(consfile.f_un.f_fname, O_WRONLY|O_NONBLOCK, 0);
487
	if (consfile.f_file == -1)
488
		log_warn("open %s", consfile.f_un.f_fname);
489
490
	(void)gethostname(LocalHostName, sizeof(LocalHostName));
491
	if ((p = strchr(LocalHostName, '.')) != NULL) {
492
		*p++ = '\0';
493
		LocalDomain = p;
494
	} else
495
		LocalDomain = "";
496
497
	/* Reserve space for kernel message buffer plus buffer full message. */
498
	linesize = getmsgbufsize() + 64;
499
	if (linesize < LOG_MAXLINE)
500
		linesize = LOG_MAXLINE;
501
	linesize++;
502
	if ((linebuf = malloc(linesize)) == NULL)
503
		fatal("allocate line buffer");
504
505
	if (socket_bind("udp", NULL, "syslog", SecureMode,
506
	    &fd_udp, &fd_udp6) == -1)
507
		log_warnx("socket bind * failed");
508
	if ((fd_bind = reallocarray(NULL, nbind, sizeof(*fd_bind))) == NULL)
509
		fatal("allocate bind fd");
510
	for (i = 0; i < nbind; i++) {
511
		if (socket_bind("udp", bind_host[i], bind_port[i], 0,
512
		    &fd_bind[i], &fd_bind[i]) == -1)
513
			log_warnx("socket bind udp failed");
514
	}
515
	if ((fd_listen = reallocarray(NULL, nlisten, sizeof(*fd_listen)))
516
	    == NULL)
517
		fatal("allocate listen fd");
518
	for (i = 0; i < nlisten; i++) {
519
		if (socket_bind("tcp", listen_host[i], listen_port[i], 0,
520
		    &fd_listen[i], &fd_listen[i]) == -1)
521
			log_warnx("socket listen tcp failed");
522
	}
523
	if ((fd_tls = reallocarray(NULL, ntls, sizeof(*fd_tls))) == NULL)
524
		fatal("allocate tls fd");
525
	for (i = 0; i < ntls; i++) {
526
		if (socket_bind("tls", tls_host[i], tls_port[i], 0,
527
		    &fd_tls[i], &fd_tls[i]) == -1)
528
			log_warnx("socket listen tls failed");
529
	}
530
531
	if ((fd_unix = reallocarray(NULL, nunix, sizeof(*fd_unix))) == NULL)
532
		fatal("allocate unix fd");
533
	for (i = 0; i < nunix; i++) {
534
		fd_unix[i] = unix_socket(path_unix[i], SOCK_DGRAM, 0666);
535
		if (fd_unix[i] == -1) {
536
			if (i == 0)
537
				log_warnx("log socket %s failed", path_unix[i]);
538
			continue;
539
		}
540
		double_sockbuf(fd_unix[i], SO_RCVBUF);
541
	}
542
543
	if (socketpair(AF_UNIX, SOCK_DGRAM, PF_UNSPEC, pair) == -1) {
544
		log_warn("socketpair sendsyslog");
545
		fd_sendsys = -1;
546
	} else {
547
		double_sockbuf(pair[0], SO_RCVBUF);
548
		double_sockbuf(pair[1], SO_SNDBUF);
549
		fd_sendsys = pair[0];
550
	}
551
552
	fd_ctlsock = fd_ctlconn = -1;
553
	if (path_ctlsock != NULL) {
554
		fd_ctlsock = unix_socket(path_ctlsock, SOCK_STREAM, 0600);
555
		if (fd_ctlsock == -1) {
556
			log_warnx("control socket %s failed", path_ctlsock);
557
		} else {
558
			if (listen(fd_ctlsock, 5) == -1) {
559
				log_warn("listen control socket");
560
				close(fd_ctlsock);
561
				fd_ctlsock = -1;
562
			}
563
		}
564
	}
565
566
	if ((fd_klog = open(_PATH_KLOG, O_RDONLY, 0)) == -1) {
567
		log_warn("open %s", _PATH_KLOG);
568
	} else if (fd_sendsys != -1) {
569
		/* Use /dev/klog to register sendsyslog(2) receiver. */
570
		if (ioctl(fd_klog, LIOCSFD, &pair[1]) == -1)
571
			log_warn("ioctl klog LIOCSFD sendsyslog");
572
	}
573
	if (fd_sendsys != -1)
574
		close(pair[1]);
575
576
	if (tls_init() == -1) {
577
		log_warn("tls_init");
578
	} else {
579
		if ((client_config = tls_config_new()) == NULL)
580
			log_warn("tls_config_new client");
581
		if (tls_hostport) {
582
			if ((server_config = tls_config_new()) == NULL)
583
				log_warn("tls_config_new server");
584
			if ((server_ctx = tls_server()) == NULL) {
585
				log_warn("tls_server");
586
				for (i = 0; i < ntls; i++)
587
					close(fd_tls[i]);
588
				free(fd_tls);
589
				fd_tls = NULL;
590
				free(tls_host);
591
				free(tls_port);
592
				tls_host = tls_port = NULL;
593
				ntls = 0;
594
			}
595
		}
596
	}
597
	if (client_config) {
598
		if (NoVerify) {
599
			tls_config_insecure_noverifycert(client_config);
600
			tls_config_insecure_noverifyname(client_config);
601
		} else {
602
			if (tls_config_set_ca_file(client_config,
603
			    CAfile) == -1) {
604
				log_warnx("load client TLS CA: %s",
605
				    tls_config_error(client_config));
606
				/* avoid reading default certs in chroot */
607
				tls_config_set_ca_mem(client_config, "", 0);
608
			} else
609
				log_debug("CAfile %s", CAfile);
610
		}
611
		if (ClientCertfile && ClientKeyfile) {
612
			if (tls_config_set_cert_file(client_config,
613
			    ClientCertfile) == -1)
614
				log_warnx("load client TLS cert: %s",
615
				    tls_config_error(client_config));
616
			else
617
				log_debug("ClientCertfile %s", ClientCertfile);
618
619
			if (tls_config_set_key_file(client_config,
620
			    ClientKeyfile) == -1)
621
				log_warnx("load client TLS key: %s",
622
				    tls_config_error(client_config));
623
			else
624
				log_debug("ClientKeyfile %s", ClientKeyfile);
625
		} else if (ClientCertfile || ClientKeyfile) {
626
			log_warnx("options -c and -k must be used together");
627
		}
628
		if (tls_config_set_protocols(client_config,
629
		    TLS_PROTOCOLS_ALL) != 0)
630
			log_warnx("set client TLS protocols: %s",
631
			    tls_config_error(client_config));
632
		if (tls_config_set_ciphers(client_config, "all") != 0)
633
			log_warnx("set client TLS ciphers: %s",
634
			    tls_config_error(client_config));
635
	}
636
	if (server_config && server_ctx) {
637
		const char *names[2];
638
639
		names[0] = tls_hostport;
640
		names[1] = tls_host[0];
641
642
		for (i = 0; i < 2; i++) {
643
			if (asprintf(&p, "/etc/ssl/private/%s.key", names[i])
644
			    == -1)
645
				continue;
646
			if (tls_config_set_key_file(server_config, p) == -1) {
647
				log_warnx("load server TLS key: %s",
648
				    tls_config_error(server_config));
649
				free(p);
650
				continue;
651
			}
652
			log_debug("Keyfile %s", p);
653
			free(p);
654
			if (asprintf(&p, "/etc/ssl/%s.crt", names[i]) == -1)
655
				continue;
656
			if (tls_config_set_cert_file(server_config, p) == -1) {
657
				log_warnx("load server TLS cert: %s",
658
				    tls_config_error(server_config));
659
				free(p);
660
				continue;
661
			}
662
			log_debug("Certfile %s", p);
663
			free(p);
664
			break;
665
		}
666
667
		if (ServerCAfile) {
668
			if (tls_config_set_ca_file(server_config,
669
			    ServerCAfile) == -1) {
670
				log_warnx("load server TLS CA: %s",
671
				    tls_config_error(server_config));
672
				/* avoid reading default certs in chroot */
673
				tls_config_set_ca_mem(server_config, "", 0);
674
			} else
675
				log_debug("Server CAfile %s", ServerCAfile);
676
			tls_config_verify_client(server_config);
677
		}
678
		if (tls_config_set_protocols(server_config,
679
		    TLS_PROTOCOLS_ALL) != 0)
680
			log_warnx("set server TLS protocols: %s",
681
			    tls_config_error(server_config));
682
		if (tls_config_set_ciphers(server_config, "compat") != 0)
683
			log_warnx("Set server TLS ciphers: %s",
684
			    tls_config_error(server_config));
685
		if (tls_configure(server_ctx, server_config) != 0) {
686
			log_warnx("tls_configure server: %s",
687
			    tls_error(server_ctx));
688
			tls_free(server_ctx);
689
			server_ctx = NULL;
690
			for (i = 0; i < ntls; i++)
691
				close(fd_tls[i]);
692
			free(fd_tls);
693
			fd_tls = NULL;
694
			free(tls_host);
695
			free(tls_port);
696
			tls_host = tls_port = NULL;
697
			ntls = 0;
698
		}
699
	}
700
701
	log_debug("off & running....");
702
703
	if (!Debug && !Foreground) {
704
		char c;
705
706
		pipe(lockpipe);
707
708
		switch(fork()) {
709
		case -1:
710
			err(1, "fork");
711
		case 0:
712
			setsid();
713
			close(lockpipe[0]);
714
			break;
715
		default:
716
			close(lockpipe[1]);
717
			read(lockpipe[0], &c, 1);
718
			_exit(0);
719
		}
720
	}
721
722
	/* tuck my process id away */
723
	if (!Debug) {
724
		FILE *fp;
725
726
		fp = fopen(_PATH_LOGPID, "w");
727
		if (fp != NULL) {
728
			fprintf(fp, "%ld\n", (long)getpid());
729
			(void) fclose(fp);
730
		}
731
	}
732
733
	/* Privilege separation begins here */
734
	priv_init(lockpipe[1], nullfd, argc, argv);
735
736
	if (pledge("stdio unix inet recvfd flock rpath cpath wpath", NULL) == -1)
737
		err(1, "pledge");
738
739
	Started = 1;
740
741
	/* Process is now unprivileged and inside a chroot */
742
	if (Debug)
743
		event_set_log_callback(logevent);
744
	event_init();
745
746
	if ((ev_ctlaccept = malloc(sizeof(struct event))) == NULL ||
747
	    (ev_ctlread = malloc(sizeof(struct event))) == NULL ||
748
	    (ev_ctlwrite = malloc(sizeof(struct event))) == NULL ||
749
	    (ev_klog = malloc(sizeof(struct event))) == NULL ||
750
	    (ev_sendsys = malloc(sizeof(struct event))) == NULL ||
751
	    (ev_udp = malloc(sizeof(struct event))) == NULL ||
752
	    (ev_udp6 = malloc(sizeof(struct event))) == NULL ||
753
	    (ev_bind = reallocarray(NULL, nbind, sizeof(struct event)))
754
		== NULL ||
755
	    (ev_listen = reallocarray(NULL, nlisten, sizeof(struct event)))
756
		== NULL ||
757
	    (ev_tls = reallocarray(NULL, ntls, sizeof(struct event)))
758
		== NULL ||
759
	    (ev_unix = reallocarray(NULL, nunix, sizeof(struct event)))
760
		== NULL ||
761
	    (ev_hup = malloc(sizeof(struct event))) == NULL ||
762
	    (ev_int = malloc(sizeof(struct event))) == NULL ||
763
	    (ev_quit = malloc(sizeof(struct event))) == NULL ||
764
	    (ev_term = malloc(sizeof(struct event))) == NULL ||
765
	    (ev_mark = malloc(sizeof(struct event))) == NULL)
766
		err(1, "malloc");
767
768
	event_set(ev_ctlaccept, fd_ctlsock, EV_READ|EV_PERSIST,
769
	    ctlsock_acceptcb, ev_ctlaccept);
770
	event_set(ev_ctlread, fd_ctlconn, EV_READ|EV_PERSIST,
771
	    ctlconn_readcb, ev_ctlread);
772
	event_set(ev_ctlwrite, fd_ctlconn, EV_WRITE|EV_PERSIST,
773
	    ctlconn_writecb, ev_ctlwrite);
774
	event_set(ev_klog, fd_klog, EV_READ|EV_PERSIST, klog_readcb, ev_klog);
775
	event_set(ev_sendsys, fd_sendsys, EV_READ|EV_PERSIST, unix_readcb,
776
	    ev_sendsys);
777
	event_set(ev_udp, fd_udp, EV_READ|EV_PERSIST, udp_readcb, ev_udp);
778
	event_set(ev_udp6, fd_udp6, EV_READ|EV_PERSIST, udp_readcb, ev_udp6);
779
	for (i = 0; i < nbind; i++)
780
		event_set(&ev_bind[i], fd_bind[i], EV_READ|EV_PERSIST,
781
		    udp_readcb, &ev_bind[i]);
782
	for (i = 0; i < nlisten; i++)
783
		event_set(&ev_listen[i], fd_listen[i], EV_READ|EV_PERSIST,
784
		    tcp_acceptcb, &ev_listen[i]);
785
	for (i = 0; i < ntls; i++)
786
		event_set(&ev_tls[i], fd_tls[i], EV_READ|EV_PERSIST,
787
		    tls_acceptcb, &ev_tls[i]);
788
	for (i = 0; i < nunix; i++)
789
		event_set(&ev_unix[i], fd_unix[i], EV_READ|EV_PERSIST,
790
		    unix_readcb, &ev_unix[i]);
791
792
	signal_set(ev_hup, SIGHUP, init_signalcb, ev_hup);
793
	signal_set(ev_int, SIGINT, die_signalcb, ev_int);
794
	signal_set(ev_quit, SIGQUIT, die_signalcb, ev_quit);
795
	signal_set(ev_term, SIGTERM, die_signalcb, ev_term);
796
797
	evtimer_set(ev_mark, mark_timercb, ev_mark);
798
799
	init();
800
801
	/* Allocate ctl socket reply buffer if we have a ctl socket */
802
	if (fd_ctlsock != -1 &&
803
	    (ctl_reply = malloc(CTL_REPLY_MAXSIZE)) == NULL)
804
		fatal("allocate control socket reply buffer");
805
	reply_text = ctl_reply + CTL_HDR_LEN;
806
807
	if (!Debug) {
808
		close(lockpipe[1]);
809
		dup2(nullfd, STDIN_FILENO);
810
		dup2(nullfd, STDOUT_FILENO);
811
		dup2(nullfd, STDERR_FILENO);
812
	}
813
	if (nullfd > 2)
814
		close(nullfd);
815
816
	/*
817
	 * Signal to the priv process that the initial config parsing is done
818
	 * so that it will reject any future attempts to open more files
819
	 */
820
	priv_config_parse_done();
821
822
	if (fd_ctlsock != -1)
823
		event_add(ev_ctlaccept, NULL);
824
	if (fd_klog != -1)
825
		event_add(ev_klog, NULL);
826
	if (fd_sendsys != -1)
827
		event_add(ev_sendsys, NULL);
828
	if (!SecureMode) {
829
		if (fd_udp != -1)
830
			event_add(ev_udp, NULL);
831
		if (fd_udp6 != -1)
832
			event_add(ev_udp6, NULL);
833
	} else {
834
		/*
835
		 * If generic UDP file descriptors are used neither
836
		 * for receiving nor for sending, close them.  Then
837
		 * there is no useless *.514 in netstat.
838
		 */
839
		if (fd_udp != -1 && !send_udp) {
840
			close(fd_udp);
841
			fd_udp = -1;
842
		}
843
		if (fd_udp6 != -1 && !send_udp6) {
844
			close(fd_udp6);
845
			fd_udp6 = -1;
846
		}
847
	}
848
	for (i = 0; i < nbind; i++)
849
		if (fd_bind[i] != -1)
850
			event_add(&ev_bind[i], NULL);
851
	for (i = 0; i < nlisten; i++)
852
		if (fd_listen[i] != -1)
853
			event_add(&ev_listen[i], NULL);
854
	for (i = 0; i < ntls; i++)
855
		if (fd_tls[i] != -1)
856
			event_add(&ev_tls[i], NULL);
857
	for (i = 0; i < nunix; i++)
858
		if (fd_unix[i] != -1)
859
			event_add(&ev_unix[i], NULL);
860
861
	signal_add(ev_hup, NULL);
862
	signal_add(ev_term, NULL);
863
	if (Debug) {
864
		signal_add(ev_int, NULL);
865
		signal_add(ev_quit, NULL);
866
	} else {
867
		(void)signal(SIGINT, SIG_IGN);
868
		(void)signal(SIGQUIT, SIG_IGN);
869
	}
870
	(void)signal(SIGCHLD, SIG_IGN);
871
	(void)signal(SIGPIPE, SIG_IGN);
872
873
	to.tv_sec = TIMERINTVL;
874
	to.tv_usec = 0;
875
	evtimer_add(ev_mark, &to);
876
877
	log_info(LOG_INFO, "start");
878
	log_debug("syslogd: started");
879
880
	sigemptyset(&sigmask);
881
	if (sigprocmask(SIG_SETMASK, &sigmask, NULL) == -1)
882
		err(1, "sigprocmask unblock");
883
884
	event_dispatch();
885
	/* NOTREACHED */
886
	return (0);
887
}
888
889
void
890
address_alloc(const char *name, const char *address, char ***host,
891
    char ***port, int *num)
892
{
893
	char *p;
894
895
	/* do not care about memory leak, argv has to be preserved */
896
620
	if ((p = strdup(address)) == NULL)
897
		err(1, "%s address %s", name, address);
898
310
	if ((*host = reallocarray(*host, *num + 1, sizeof(**host))) == NULL)
899
		err(1, "%s host %s", name, address);
900
310
	if ((*port = reallocarray(*port, *num + 1, sizeof(**port))) == NULL)
901
		err(1, "%s port %s", name, address);
902
310
	if (loghost_parse(p, NULL, *host + *num, *port + *num) == -1)
903
		errx(1, "bad %s address: %s", name, address);
904
310
	(*num)++;
905
310
}
906
907
int
908
socket_bind(const char *proto, const char *host, const char *port,
909
    int shutread, int *fd, int *fd6)
910
{
911
	struct addrinfo	 hints, *res, *res0;
912
	char		 hostname[NI_MAXHOST], servname[NI_MAXSERV];
913
	int		*fdp, error, reuseaddr;
914
915
	*fd = *fd6 = -1;
916
	if (proto == NULL)
917
		proto = "udp";
918
	if (port == NULL)
919
		port = strcmp(proto, "tls") == 0 ? "syslog-tls" : "syslog";
920
921
	memset(&hints, 0, sizeof(hints));
922
	hints.ai_family = Family;
923
	if (strcmp(proto, "udp") == 0) {
924
		hints.ai_socktype = SOCK_DGRAM;
925
		hints.ai_protocol = IPPROTO_UDP;
926
	} else {
927
		hints.ai_socktype = SOCK_STREAM;
928
		hints.ai_protocol = IPPROTO_TCP;
929
	}
930
	hints.ai_flags = AI_PASSIVE;
931
932
	if ((error = getaddrinfo(host, port, &hints, &res0))) {
933
		log_warnx("getaddrinfo proto %s, host %s, port %s: %s",
934
		    proto, host ? host : "*", port, gai_strerror(error));
935
		return (-1);
936
	}
937
938
	for (res = res0; res; res = res->ai_next) {
939
		switch (res->ai_family) {
940
		case AF_INET:
941
			fdp = fd;
942
			break;
943
		case AF_INET6:
944
			fdp = fd6;
945
			break;
946
		default:
947
			continue;
948
		}
949
		if (*fdp >= 0)
950
			continue;
951
952
		if ((*fdp = socket(res->ai_family,
953
		    res->ai_socktype | SOCK_NONBLOCK, res->ai_protocol)) == -1)
954
			continue;
955
956
		if (getnameinfo(res->ai_addr, res->ai_addrlen, hostname,
957
		    sizeof(hostname), servname, sizeof(servname),
958
		    NI_NUMERICHOST | NI_NUMERICSERV |
959
		    (res->ai_socktype == SOCK_DGRAM ? NI_DGRAM : 0)) != 0) {
960
			log_debug("Malformed bind address");
961
			hostname[0] = servname[0] = '\0';
962
		}
963
		if (shutread && shutdown(*fdp, SHUT_RD) == -1) {
964
			log_warn("shutdown SHUT_RD "
965
			    "protocol %d, address %s, portnum %s",
966
			    res->ai_protocol, hostname, servname);
967
			close(*fdp);
968
			*fdp = -1;
969
			continue;
970
		}
971
		if (!shutread && res->ai_protocol == IPPROTO_UDP)
972
			double_sockbuf(*fdp, SO_RCVBUF);
973
		else if (res->ai_protocol == IPPROTO_TCP)
974
			set_sockbuf(*fdp);
975
		reuseaddr = 1;
976
		if (setsockopt(*fdp, SOL_SOCKET, SO_REUSEADDR, &reuseaddr,
977
		    sizeof(reuseaddr)) == -1) {
978
			log_warn("setsockopt SO_REUSEADDR "
979
			    "protocol %d, address %s, portnum %s",
980
			    res->ai_protocol, hostname, servname);
981
			close(*fdp);
982
			*fdp = -1;
983
			continue;
984
		}
985
		if (bind(*fdp, res->ai_addr, res->ai_addrlen) == -1) {
986
			log_warn("bind protocol %d, address %s, portnum %s",
987
			    res->ai_protocol, hostname, servname);
988
			close(*fdp);
989
			*fdp = -1;
990
			continue;
991
		}
992
		if (!shutread && res->ai_protocol == IPPROTO_TCP &&
993
		    listen(*fdp, 10) == -1) {
994
			log_warn("listen protocol %d, address %s, portnum %s",
995
			    res->ai_protocol, hostname, servname);
996
			close(*fdp);
997
			*fdp = -1;
998
			continue;
999
		}
1000
	}
1001
1002
	freeaddrinfo(res0);
1003
1004
	if (*fd == -1 && *fd6 == -1)
1005
		return (-1);
1006
	return (0);
1007
}
1008
1009
void
1010
klog_readcb(int fd, short event, void *arg)
1011
{
1012
	struct event		*ev = arg;
1013
	ssize_t			 n;
1014
1015
	n = read(fd, linebuf, linesize - 1);
1016
	if (n > 0) {
1017
		linebuf[n] = '\0';
1018
		printsys(linebuf);
1019
	} else if (n < 0 && errno != EINTR) {
1020
		log_warn("read klog");
1021
		event_del(ev);
1022
	}
1023
}
1024
1025
void
1026
udp_readcb(int fd, short event, void *arg)
1027
{
1028
	struct sockaddr_storage	 sa;
1029
	socklen_t		 salen;
1030
	ssize_t			 n;
1031
1032
	salen = sizeof(sa);
1033
	n = recvfrom(fd, linebuf, LOG_MAXLINE, 0, (struct sockaddr *)&sa,
1034
	    &salen);
1035
	if (n > 0) {
1036
		char	 resolve[NI_MAXHOST];
1037
1038
		linebuf[n] = '\0';
1039
		cvthname((struct sockaddr *)&sa, resolve, sizeof(resolve));
1040
		log_debug("cvthname res: %s", resolve);
1041
		printline(resolve, linebuf);
1042
	} else if (n < 0 && errno != EINTR && errno != EWOULDBLOCK)
1043
		log_warn("recvfrom udp");
1044
}
1045
1046
void
1047
unix_readcb(int fd, short event, void *arg)
1048
{
1049
	struct sockaddr_un	 sa;
1050
	socklen_t		 salen;
1051
	ssize_t			 n;
1052
1053
	salen = sizeof(sa);
1054
	n = recvfrom(fd, linebuf, LOG_MAXLINE, 0, (struct sockaddr *)&sa,
1055
	    &salen);
1056
	if (n > 0) {
1057
		linebuf[n] = '\0';
1058
		printline(LocalHostName, linebuf);
1059
	} else if (n < 0 && errno != EINTR && errno != EWOULDBLOCK)
1060
		log_warn("recvfrom unix");
1061
}
1062
1063
int
1064
reserve_accept4(int lfd, int event, struct event *ev,
1065
    void (*cb)(int, short, void *),
1066
    struct sockaddr *sa, socklen_t *salen, int flags)
1067
{
1068
	struct timeval	 to = { 1, 0 };
1069
	int		 afd;
1070
1071
	if (event & EV_TIMEOUT) {
1072
		log_debug("Listen again");
1073
		/* Enable the listen event, there is no timeout anymore. */
1074
		event_set(ev, lfd, EV_READ|EV_PERSIST, cb, ev);
1075
		event_add(ev, NULL);
1076
		errno = EWOULDBLOCK;
1077
		return (-1);
1078
	}
1079
1080
	if (getdtablecount() + FD_RESERVE >= getdtablesize()) {
1081
		afd = -1;
1082
		errno = EMFILE;
1083
	} else
1084
		afd = accept4(lfd, sa, salen, flags);
1085
1086
	if (afd == -1 && (errno == ENFILE || errno == EMFILE)) {
1087
		log_info(LOG_WARNING, "accept deferred: %s", strerror(errno));
1088
		/*
1089
		 * Disable the listen event and convert it to a timeout.
1090
		 * Pass the listen file descriptor to the callback.
1091
		 */
1092
		event_del(ev);
1093
		event_set(ev, lfd, 0, cb, ev);
1094
		event_add(ev, &to);
1095
		return (-1);
1096
	}
1097
1098
	return (afd);
1099
}
1100
1101
void
1102
tcp_acceptcb(int lfd, short event, void *arg)
1103
{
1104
	acceptcb(lfd, event, arg, 0);
1105
}
1106
1107
void
1108
tls_acceptcb(int lfd, short event, void *arg)
1109
{
1110
	acceptcb(lfd, event, arg, 1);
1111
}
1112
1113
void
1114
acceptcb(int lfd, short event, void *arg, int usetls)
1115
{
1116
	struct event		*ev = arg;
1117
	struct peer		*p;
1118
	struct sockaddr_storage	 ss;
1119
	socklen_t		 sslen;
1120
	char			 hostname[NI_MAXHOST], servname[NI_MAXSERV];
1121
	char			*peername;
1122
	int			 fd;
1123
1124
	sslen = sizeof(ss);
1125
	if ((fd = reserve_accept4(lfd, event, ev, tcp_acceptcb,
1126
	    (struct sockaddr *)&ss, &sslen, SOCK_NONBLOCK)) == -1) {
1127
		if (errno != ENFILE && errno != EMFILE &&
1128
		    errno != EINTR && errno != EWOULDBLOCK &&
1129
		    errno != ECONNABORTED)
1130
			log_warn("accept tcp socket");
1131
		return;
1132
	}
1133
	log_debug("Accepting tcp connection");
1134
1135
	if (getnameinfo((struct sockaddr *)&ss, sslen, hostname,
1136
	    sizeof(hostname), servname, sizeof(servname),
1137
	    NI_NUMERICHOST | NI_NUMERICSERV) != 0 ||
1138
	    asprintf(&peername, ss.ss_family == AF_INET6 ?
1139
	    "[%s]:%s" : "%s:%s", hostname, servname) == -1) {
1140
		log_debug("Malformed accept address");
1141
		peername = hostname_unknown;
1142
	}
1143
	log_debug("Peer addresss and port %s", peername);
1144
	if ((p = malloc(sizeof(*p))) == NULL) {
1145
		log_warn("allocate \"%s\"", peername);
1146
		close(fd);
1147
		return;
1148
	}
1149
	p->p_fd = fd;
1150
	if ((p->p_bufev = bufferevent_new(fd, tcp_readcb, NULL, tcp_closecb,
1151
	    p)) == NULL) {
1152
		log_warn("bufferevent \"%s\"", peername);
1153
		free(p);
1154
		close(fd);
1155
		return;
1156
	}
1157
	p->p_ctx = NULL;
1158
	if (usetls) {
1159
		if (tls_accept_socket(server_ctx, &p->p_ctx, fd) < 0) {
1160
			log_warnx("tls_accept_socket \"%s\": %s",
1161
			    peername, tls_error(server_ctx));
1162
			bufferevent_free(p->p_bufev);
1163
			free(p);
1164
			close(fd);
1165
			return;
1166
		}
1167
		buffertls_set(&p->p_buftls, p->p_bufev, p->p_ctx, fd);
1168
		buffertls_accept(&p->p_buftls, fd);
1169
		log_debug("tcp accept callback: tls context success");
1170
	}
1171
	if (!NoDNS && peername != hostname_unknown &&
1172
	    priv_getnameinfo((struct sockaddr *)&ss, ss.ss_len, hostname,
1173
	    sizeof(hostname)) != 0) {
1174
		log_debug("Host name for accept address (%s) unknown",
1175
		    hostname);
1176
	}
1177
	if (peername == hostname_unknown ||
1178
	    (p->p_hostname = strdup(hostname)) == NULL)
1179
		p->p_hostname = hostname_unknown;
1180
	log_debug("Peer hostname %s", hostname);
1181
	p->p_peername = peername;
1182
	bufferevent_enable(p->p_bufev, EV_READ);
1183
1184
	log_info(LOG_DEBUG, "%s logger \"%s\" accepted",
1185
	    p->p_ctx ? "tls" : "tcp", peername);
1186
}
1187
1188
/*
1189
 * Syslog over TCP  RFC 6587  3.4.1. Octet Counting
1190
 */
1191
int
1192
octet_counting(struct evbuffer *evbuf, char **msg, int drain)
1193
{
1194
	char	*p, *buf, *end;
1195
	int	 len;
1196
1197
	buf = EVBUFFER_DATA(evbuf);
1198
	end = buf + EVBUFFER_LENGTH(evbuf);
1199
	/*
1200
	 * It can be assumed that octet-counting framing is used if a syslog
1201
	 * frame starts with a digit.
1202
	 */
1203
	if (buf >= end || !isdigit((unsigned char)*buf))
1204
		return (-1);
1205
	/*
1206
	 * SYSLOG-FRAME = MSG-LEN SP SYSLOG-MSG
1207
	 * MSG-LEN is the octet count of the SYSLOG-MSG in the SYSLOG-FRAME.
1208
	 * We support up to 5 digits in MSG-LEN, so the maximum is 99999.
1209
	 */
1210
	for (p = buf; p < end && p < buf + 5; p++) {
1211
		if (!isdigit((unsigned char)*p))
1212
			break;
1213
	}
1214
	if (buf >= p || p >= end || *p != ' ')
1215
		return (-1);
1216
	p++;
1217
	/* Using atoi() is safe as buf starts with 1 to 5 digits and a space. */
1218
	len = atoi(buf);
1219
	if (drain)
1220
		log_debugadd(" octet counting %d", len);
1221
	if (p + len > end)
1222
		return (0);
1223
	if (drain)
1224
		evbuffer_drain(evbuf, p - buf);
1225
	if (msg)
1226
		*msg = p;
1227
	return (len);
1228
}
1229
1230
/*
1231
 * Syslog over TCP  RFC 6587  3.4.2. Non-Transparent-Framing
1232
 */
1233
int
1234
non_transparent_framing(struct evbuffer *evbuf, char **msg)
1235
{
1236
	char	*p, *buf, *end;
1237
1238
	buf = EVBUFFER_DATA(evbuf);
1239
	end = buf + EVBUFFER_LENGTH(evbuf);
1240
	/*
1241
	 * The TRAILER has usually been a single character and most often
1242
	 * is ASCII LF (%d10).  However, other characters have also been
1243
	 * seen, with ASCII NUL (%d00) being a prominent example.
1244
	 */
1245
	for (p = buf; p < end; p++) {
1246
		if (*p == '\0' || *p == '\n')
1247
			break;
1248
	}
1249
	if (p + 1 - buf >= INT_MAX)
1250
		return (-1);
1251
	log_debugadd(" non transparent framing");
1252
	if (p >= end)
1253
		return (0);
1254
	/*
1255
	 * Some devices have also been seen to emit a two-character
1256
	 * TRAILER, which is usually CR and LF.
1257
	 */
1258
	if (buf < p && p[0] == '\n' && p[-1] == '\r')
1259
		p[-1] = '\0';
1260
	if (msg)
1261
		*msg = buf;
1262
	return (p + 1 - buf);
1263
}
1264
1265
void
1266
tcp_readcb(struct bufferevent *bufev, void *arg)
1267
{
1268
	struct peer		*p = arg;
1269
	char			*msg;
1270
	int			 len;
1271
1272
	while (EVBUFFER_LENGTH(bufev->input) > 0) {
1273
		log_debugadd("%s logger \"%s\"", p->p_ctx ? "tls" : "tcp",
1274
		    p->p_peername);
1275
		msg = NULL;
1276
		len = octet_counting(bufev->input, &msg, 1);
1277
		if (len < 0)
1278
			len = non_transparent_framing(bufev->input, &msg);
1279
		if (len < 0)
1280
			log_debugadd("unknown method");
1281
		if (msg == NULL) {
1282
			log_debugadd(", incomplete frame");
1283
			break;
1284
		}
1285
		log_debug(", use %d bytes", len);
1286
		if (len > 0 && msg[len-1] == '\n')
1287
			msg[len-1] = '\0';
1288
		if (len == 0 || msg[len-1] != '\0') {
1289
			memcpy(linebuf, msg, MINIMUM(len, LOG_MAXLINE));
1290
			linebuf[MINIMUM(len, LOG_MAXLINE)] = '\0';
1291
			msg = linebuf;
1292
		}
1293
		printline(p->p_hostname, msg);
1294
		evbuffer_drain(bufev->input, len);
1295
	}
1296
	/* Maximum frame has 5 digits, 1 space, MAXLINE chars, 1 new line. */
1297
	if (EVBUFFER_LENGTH(bufev->input) >= 5 + 1 + LOG_MAXLINE + 1) {
1298
		log_debug(", use %zu bytes", EVBUFFER_LENGTH(bufev->input));
1299
		printline(p->p_hostname, EVBUFFER_DATA(bufev->input));
1300
		evbuffer_drain(bufev->input, -1);
1301
	} else if (EVBUFFER_LENGTH(bufev->input) > 0)
1302
		log_debug(", buffer %zu bytes", EVBUFFER_LENGTH(bufev->input));
1303
}
1304
1305
void
1306
tcp_closecb(struct bufferevent *bufev, short event, void *arg)
1307
{
1308
	struct peer		*p = arg;
1309
1310
	if (event & EVBUFFER_EOF) {
1311
		log_info(LOG_DEBUG, "%s logger \"%s\" connection close",
1312
		    p->p_ctx ? "tls" : "tcp", p->p_peername);
1313
	} else {
1314
		log_info(LOG_NOTICE, "%s logger \"%s\" connection error: %s",
1315
		    p->p_ctx ? "tls" : "tcp", p->p_peername,
1316
		    p->p_ctx ? tls_error(p->p_ctx) : strerror(errno));
1317
	}
1318
1319
	if (p->p_peername != hostname_unknown)
1320
		free(p->p_peername);
1321
	if (p->p_hostname != hostname_unknown)
1322
		free(p->p_hostname);
1323
	bufferevent_free(p->p_bufev);
1324
	close(p->p_fd);
1325
	free(p);
1326
}
1327
1328
int
1329
tcp_socket(struct filed *f)
1330
{
1331
	int	 s;
1332
1333
	if ((s = socket(f->f_un.f_forw.f_addr.ss_family,
1334
	    SOCK_STREAM | SOCK_NONBLOCK, IPPROTO_TCP)) == -1) {
1335
		log_warn("socket \"%s\"", f->f_un.f_forw.f_loghost);
1336
		return (-1);
1337
	}
1338
	set_sockbuf(s);
1339
	if (connect(s, (struct sockaddr *)&f->f_un.f_forw.f_addr,
1340
	    f->f_un.f_forw.f_addr.ss_len) == -1 && errno != EINPROGRESS) {
1341
		log_warn("connect \"%s\"", f->f_un.f_forw.f_loghost);
1342
		close(s);
1343
		return (-1);
1344
	}
1345
	return (s);
1346
}
1347
1348
void
1349
tcp_dropcb(struct bufferevent *bufev, void *arg)
1350
{
1351
	struct filed	*f = arg;
1352
1353
	/*
1354
	 * Drop data received from the forward log server.
1355
	 */
1356
	log_debug("loghost \"%s\" did send %zu bytes back",
1357
	    f->f_un.f_forw.f_loghost, EVBUFFER_LENGTH(bufev->input));
1358
	evbuffer_drain(bufev->input, -1);
1359
}
1360
1361
void
1362
tcp_writecb(struct bufferevent *bufev, void *arg)
1363
{
1364
	struct filed	*f = arg;
1365
1366
	/*
1367
	 * Successful write, connection to server is good, reset wait time.
1368
	 */
1369
	log_debug("loghost \"%s\" successful write", f->f_un.f_forw.f_loghost);
1370
	f->f_un.f_forw.f_reconnectwait = 0;
1371
1372
	if (f->f_un.f_forw.f_dropped > 0 &&
1373
	    EVBUFFER_LENGTH(f->f_un.f_forw.f_bufev->output) < MAX_TCPBUF) {
1374
		log_info(LOG_WARNING, "dropped %d message%s to loghost \"%s\"",
1375
		    f->f_un.f_forw.f_dropped,
1376
		    f->f_un.f_forw.f_dropped == 1 ? "" : "s",
1377
		    f->f_un.f_forw.f_loghost);
1378
		f->f_un.f_forw.f_dropped = 0;
1379
	}
1380
}
1381
1382
void
1383
tcp_errorcb(struct bufferevent *bufev, short event, void *arg)
1384
{
1385
	struct filed	*f = arg;
1386
	char		*p, *buf, *end;
1387
	int		 l;
1388
	char		 ebuf[ERRBUFSIZE];
1389
1390
	if (event & EVBUFFER_EOF)
1391
		snprintf(ebuf, sizeof(ebuf), "loghost \"%s\" connection close",
1392
		    f->f_un.f_forw.f_loghost);
1393
	else
1394
		snprintf(ebuf, sizeof(ebuf),
1395
		    "loghost \"%s\" connection error: %s",
1396
		    f->f_un.f_forw.f_loghost, f->f_un.f_forw.f_ctx ?
1397
		    tls_error(f->f_un.f_forw.f_ctx) : strerror(errno));
1398
	log_debug("%s", ebuf);
1399
1400
	/* The SIGHUP handler may also close the socket, so invalidate it. */
1401
	if (f->f_un.f_forw.f_ctx) {
1402
		tls_close(f->f_un.f_forw.f_ctx);
1403
		tls_free(f->f_un.f_forw.f_ctx);
1404
		f->f_un.f_forw.f_ctx = NULL;
1405
	}
1406
	close(f->f_file);
1407
	f->f_file = -1;
1408
1409
	/*
1410
	 * The messages in the output buffer may be out of sync.
1411
	 * Check that the buffer starts with "1234 <1234 octets>\n".
1412
	 * Otherwise remove the partial message from the beginning.
1413
	 */
1414
	buf = EVBUFFER_DATA(bufev->output);
1415
	end = buf + EVBUFFER_LENGTH(bufev->output);
1416
	if (buf < end && !((l = octet_counting(bufev->output, &p, 0)) > 0 &&
1417
	    p[l-1] == '\n')) {
1418
		for (p = buf; p < end; p++) {
1419
			if (*p == '\n') {
1420
				evbuffer_drain(bufev->output, p - buf + 1);
1421
				break;
1422
			}
1423
		}
1424
		/* Without '\n' discard everything. */
1425
		if (p == end)
1426
			evbuffer_drain(bufev->output, -1);
1427
		log_debug("loghost \"%s\" dropped partial message",
1428
		    f->f_un.f_forw.f_loghost);
1429
		f->f_un.f_forw.f_dropped++;
1430
	}
1431
1432
	tcp_connect_retry(bufev, f);
1433
1434
	/* Log the connection error to the fresh buffer after reconnecting. */
1435
	log_info(LOG_WARNING, "%s", ebuf);
1436
}
1437
1438
void
1439
tcp_connectcb(int fd, short event, void *arg)
1440
{
1441
	struct filed		*f = arg;
1442
	struct bufferevent	*bufev = f->f_un.f_forw.f_bufev;
1443
	int			 s;
1444
1445
	if ((s = tcp_socket(f)) == -1) {
1446
		tcp_connect_retry(bufev, f);
1447
		return;
1448
	}
1449
	log_debug("tcp connect callback: socket success, event %#x", event);
1450
	f->f_file = s;
1451
1452
	bufferevent_setfd(bufev, s);
1453
	bufferevent_setcb(bufev, tcp_dropcb, tcp_writecb, tcp_errorcb, f);
1454
	/*
1455
	 * Although syslog is a write only protocol, enable reading from
1456
	 * the socket to detect connection close and errors.
1457
	 */
1458
	bufferevent_enable(bufev, EV_READ|EV_WRITE);
1459
1460
	if (f->f_type == F_FORWTLS) {
1461
		if ((f->f_un.f_forw.f_ctx = tls_client()) == NULL) {
1462
			log_warn("tls_client \"%s\"", f->f_un.f_forw.f_loghost);
1463
			goto error;
1464
		}
1465
		if (client_config &&
1466
		    tls_configure(f->f_un.f_forw.f_ctx, client_config) == -1) {
1467
			log_warnx("tls_configure \"%s\": %s",
1468
			    f->f_un.f_forw.f_loghost,
1469
			    tls_error(f->f_un.f_forw.f_ctx));
1470
			goto error;
1471
		}
1472
		if (tls_connect_socket(f->f_un.f_forw.f_ctx, s,
1473
		    f->f_un.f_forw.f_host) == -1) {
1474
			log_warnx("tls_connect_socket \"%s\": %s",
1475
			    f->f_un.f_forw.f_loghost,
1476
			    tls_error(f->f_un.f_forw.f_ctx));
1477
			goto error;
1478
		}
1479
		log_debug("tcp connect callback: tls context success");
1480
1481
		buffertls_set(&f->f_un.f_forw.f_buftls, bufev,
1482
		    f->f_un.f_forw.f_ctx, s);
1483
		buffertls_connect(&f->f_un.f_forw.f_buftls, s);
1484
	}
1485
1486
	return;
1487
1488
 error:
1489
	if (f->f_un.f_forw.f_ctx) {
1490
		tls_free(f->f_un.f_forw.f_ctx);
1491
		f->f_un.f_forw.f_ctx = NULL;
1492
	}
1493
	close(f->f_file);
1494
	f->f_file = -1;
1495
	tcp_connect_retry(bufev, f);
1496
}
1497
1498
void
1499
tcp_connect_retry(struct bufferevent *bufev, struct filed *f)
1500
{
1501
	struct timeval		 to;
1502
1503
	if (f->f_un.f_forw.f_reconnectwait == 0)
1504
		f->f_un.f_forw.f_reconnectwait = 1;
1505
	else
1506
		f->f_un.f_forw.f_reconnectwait <<= 1;
1507
	if (f->f_un.f_forw.f_reconnectwait > 600)
1508
		f->f_un.f_forw.f_reconnectwait = 600;
1509
	to.tv_sec = f->f_un.f_forw.f_reconnectwait;
1510
	to.tv_usec = 0;
1511
1512
	log_debug("tcp connect retry: wait %d",
1513
	    f->f_un.f_forw.f_reconnectwait);
1514
	bufferevent_setfd(bufev, -1);
1515
	/* We can reuse the write event as bufferevent is disabled. */
1516
	evtimer_set(&bufev->ev_write, tcp_connectcb, f);
1517
	evtimer_add(&bufev->ev_write, &to);
1518
}
1519
1520
int
1521
tcpbuf_countmsg(struct bufferevent *bufev)
1522
{
1523
	char	*p, *buf, *end;
1524
	int	 i = 0;
1525
1526
	buf = EVBUFFER_DATA(bufev->output);
1527
	end = buf + EVBUFFER_LENGTH(bufev->output);
1528
	for (p = buf; p < end; p++) {
1529
		if (*p == '\n')
1530
			i++;
1531
	}
1532
	return (i);
1533
}
1534
1535
void
1536
usage(void)
1537
{
1538
1539
	(void)fprintf(stderr,
1540
	    "usage: syslogd [-46dFhnruVZ] [-a path] [-C CAfile]\n"
1541
	    "\t[-c cert_file] [-f config_file] [-K CAfile] [-k key_file]\n"
1542
	    "\t[-m mark_interval] [-p log_socket] [-S listen_address]\n"
1543
	    "\t[-s reporting_socket] [-T listen_address] [-U bind_address]\n");
1544
	exit(1);
1545
}
1546
1547
/*
1548
 * Parse a priority code of the form "<123>" into pri, and return the
1549
 * length of the priority code including the surrounding angle brackets.
1550
 */
1551
size_t
1552
parsepriority(const char *msg, int *pri)
1553
{
1554
	size_t nlen;
1555
	char buf[11];
1556
	const char *errstr;
1557
	int maybepri;
1558
1559
	if (*msg++ == '<') {
1560
		nlen = strspn(msg, "1234567890");
1561
		if (nlen > 0 && nlen < sizeof(buf) && msg[nlen] == '>') {
1562
			strlcpy(buf, msg, nlen + 1);
1563
			maybepri = strtonum(buf, 0, INT_MAX, &errstr);
1564
			if (errstr == NULL) {
1565
				*pri = maybepri;
1566
				return nlen + 2;
1567
			}
1568
		}
1569
	}
1570
1571
	return 0;
1572
}
1573
1574
/*
1575
 * Take a raw input line, decode the message, and print the message
1576
 * on the appropriate log files.
1577
 */
1578
void
1579
printline(char *hname, char *msg)
1580
{
1581
	int pri;
1582
	char *p, *q, line[LOG_MAXLINE + 4 + 1];  /* message, encoding, NUL */
1583
1584
	/* test for special codes */
1585
	pri = DEFUPRI;
1586
	p = msg;
1587
	p += parsepriority(p, &pri);
1588
	if (pri &~ (LOG_FACMASK|LOG_PRIMASK))
1589
		pri = DEFUPRI;
1590
1591
	/*
1592
	 * Don't allow users to log kernel messages.
1593
	 * NOTE: since LOG_KERN == 0 this will also match
1594
	 * messages with no facility specified.
1595
	 */
1596
	if (LOG_FAC(pri) == LOG_KERN)
1597
		pri = LOG_USER | LOG_PRI(pri);
1598
1599
	for (q = line; *p && q < &line[LOG_MAXLINE]; p++) {
1600
		if (*p == '\n')
1601
			*q++ = ' ';
1602
		else
1603
			q = vis(q, *p, 0, 0);
1604
	}
1605
	line[LOG_MAXLINE] = *q = '\0';
1606
1607
	logline(pri, 0, hname, line);
1608
}
1609
1610
/*
1611
 * Take a raw input line from /dev/klog, split and format similar to syslog().
1612
 */
1613
void
1614
printsys(char *msg)
1615
{
1616
	int c, pri, flags;
1617
	char *lp, *p, *q, line[LOG_MAXLINE + 1];
1618
	size_t prilen;
1619
1620
	(void)snprintf(line, sizeof line, "%s: ", _PATH_UNIX);
1621
	lp = line + strlen(line);
1622
	for (p = msg; *p != '\0'; ) {
1623
		flags = SYNC_FILE | ADDDATE;	/* fsync file after write */
1624
		pri = DEFSPRI;
1625
		prilen = parsepriority(p, &pri);
1626
		p += prilen;
1627
		if (prilen == 0) {
1628
			/* kernel printf's come out on console */
1629
			flags |= IGN_CONS;
1630
		}
1631
		if (pri &~ (LOG_FACMASK|LOG_PRIMASK))
1632
			pri = DEFSPRI;
1633
1634
		q = lp;
1635
		while (*p && (c = *p++) != '\n' && q < &line[sizeof(line) - 4])
1636
			q = vis(q, c, 0, 0);
1637
1638
		logline(pri, flags, LocalHostName, line);
1639
	}
1640
}
1641
1642
void
1643
vlogmsg(int pri, const char *proc, const char *fmt, va_list ap)
1644
{
1645
	char	msg[ERRBUFSIZE];
1646
	size_t	l;
1647
1648
	l = snprintf(msg, sizeof(msg), "%s[%d]: ", proc, getpid());
1649
	if (l < sizeof(msg))
1650
		vsnprintf(msg + l, sizeof(msg) - l, fmt, ap);
1651
	if (!Started) {
1652
		fprintf(stderr, "%s\n", msg);
1653
		return;
1654
	}
1655
	logline(pri, ADDDATE, LocalHostName, msg);
1656
}
1657
1658
struct timeval	now;
1659
1660
/*
1661
 * Log a message to the appropriate log files, users, etc. based on
1662
 * the priority.
1663
 */
1664
void
1665
logline(int pri, int flags, char *from, char *msg)
1666
{
1667
	struct filed *f;
1668
	int fac, msglen, prilev, i;
1669
	char timestamp[33];
1670
	char prog[NAME_MAX+1];
1671
1672
	log_debug("logline: pri 0%o, flags 0x%x, from %s, msg %s",
1673
	    pri, flags, from, msg);
1674
1675
	/*
1676
	 * Check to see if msg looks non-standard.
1677
	 */
1678
	timestamp[0] = '\0';
1679
	msglen = strlen(msg);
1680
	if ((flags & ADDDATE) == 0) {
1681
		if (msglen >= 16 && msg[3] == ' ' && msg[6] == ' ' &&
1682
		    msg[9] == ':' && msg[12] == ':' && msg[15] == ' ') {
1683
			/* BSD syslog TIMESTAMP, RFC 3164 */
1684
			strlcpy(timestamp, msg, 16);
1685
			msg += 16;
1686
			msglen -= 16;
1687
			if (ZuluTime)
1688
				flags |= ADDDATE;
1689
		} else if (msglen >= 20 &&
1690
		    isdigit(msg[0]) && isdigit(msg[1]) && isdigit(msg[2]) &&
1691
		    isdigit(msg[3]) && msg[4] == '-' &&
1692
		    isdigit(msg[5]) && isdigit(msg[6]) && msg[7] == '-' &&
1693
		    isdigit(msg[8]) && isdigit(msg[9]) && msg[10] == 'T' &&
1694
		    isdigit(msg[11]) && isdigit(msg[12]) && msg[13] == ':' &&
1695
		    isdigit(msg[14]) && isdigit(msg[15]) && msg[16] == ':' &&
1696
		    isdigit(msg[17]) && isdigit(msg[18]) && (msg[19] == '.' ||
1697
		    msg[19] == 'Z' || msg[19] == '+' || msg[19] == '-')) {
1698
			/* FULL-DATE "T" FULL-TIME, RFC 5424 */
1699
			strlcpy(timestamp, msg, sizeof(timestamp));
1700
			msg += 19;
1701
			msglen -= 19;
1702
			i = 0;
1703
			if (msglen >= 3 && msg[0] == '.' && isdigit(msg[1])) {
1704
				/* TIME-SECFRAC */
1705
				msg += 2;
1706
				msglen -= 2;
1707
				i += 2;
1708
				while(i < 7 && msglen >= 1 && isdigit(msg[0])) {
1709
					msg++;
1710
					msglen--;
1711
					i++;
1712
				}
1713
			}
1714
			if (msglen >= 2 && msg[0] == 'Z' && msg[1] == ' ') {
1715
				/* "Z" */
1716
				timestamp[20+i] = '\0';
1717
				msg += 2;
1718
				msglen -= 2;
1719
			} else if (msglen >= 7 &&
1720
			    (msg[0] == '+' || msg[0] == '-') &&
1721
			    isdigit(msg[1]) && isdigit(msg[2]) &&
1722
			    msg[3] == ':' &&
1723
			    isdigit(msg[4]) && isdigit(msg[5]) &&
1724
			    msg[6] == ' ') {
1725
				/* TIME-NUMOFFSET */
1726
				timestamp[25+i] = '\0';
1727
				msg += 7;
1728
				msglen -= 7;
1729
			} else {
1730
				/* invalid time format, roll back */
1731
				timestamp[0] = '\0';
1732
				msg -= 19 + i;
1733
				msglen += 19 + i;
1734
				flags |= ADDDATE;
1735
			}
1736
		} else if (msglen >= 2 && msg[0] == '-' && msg[1] == ' ') {
1737
			/* NILVALUE, RFC 5424 */
1738
			msg += 2;
1739
			msglen -= 2;
1740
			flags |= ADDDATE;
1741
		} else
1742
			flags |= ADDDATE;
1743
	}
1744
1745
	(void)gettimeofday(&now, NULL);
1746
	if (flags & ADDDATE) {
1747
		if (ZuluTime) {
1748
			struct tm *tm;
1749
			size_t l;
1750
1751
			tm = gmtime(&now.tv_sec);
1752
			l = strftime(timestamp, sizeof(timestamp), "%FT%T", tm);
1753
			/*
1754
			 * Use only millisecond precision as some time has
1755
			 * passed since syslog(3) was called.
1756
			 */
1757
			snprintf(timestamp + l, sizeof(timestamp) - l,
1758
			    ".%03ldZ", now.tv_usec / 1000);
1759
		} else
1760
			strlcpy(timestamp, ctime(&now.tv_sec) + 4, 16);
1761
	}
1762
1763
	/* extract facility and priority level */
1764
	if (flags & MARK)
1765
		fac = LOG_NFACILITIES;
1766
	else {
1767
		fac = LOG_FAC(pri);
1768
		if (fac >= LOG_NFACILITIES || fac < 0)
1769
			fac = LOG_USER;
1770
	}
1771
	prilev = LOG_PRI(pri);
1772
1773
	/* extract program name */
1774
	while (isspace((unsigned char)*msg)) {
1775
		msg++;
1776
		msglen--;
1777
	}
1778
	for (i = 0; i < NAME_MAX; i++) {
1779
		if (!isalnum((unsigned char)msg[i]) && msg[i] != '-')
1780
			break;
1781
		prog[i] = msg[i];
1782
	}
1783
	prog[i] = 0;
1784
1785
	/* log the message to the particular outputs */
1786
	if (!Initialized) {
1787
		f = &consfile;
1788
		if (f->f_type == F_CONSOLE) {
1789
			strlcpy(f->f_lasttime, timestamp,
1790
			    sizeof(f->f_lasttime));
1791
			strlcpy(f->f_prevhost, from,
1792
			    sizeof(f->f_prevhost));
1793
			fprintlog(f, flags, msg);
1794
			/* May be set to F_UNUSED, try again next time. */
1795
			f->f_type = F_CONSOLE;
1796
		}
1797
		return;
1798
	}
1799
	SIMPLEQ_FOREACH(f, &Files, f_next) {
1800
		/* skip messages that are incorrect priority */
1801
		if (f->f_pmask[fac] < prilev ||
1802
		    f->f_pmask[fac] == INTERNAL_NOPRI)
1803
			continue;
1804
1805
		/* skip messages with the incorrect program or hostname */
1806
		if (f->f_program && strcmp(prog, f->f_program) != 0)
1807
			continue;
1808
		if (f->f_hostname && strcmp(from, f->f_hostname) != 0)
1809
			continue;
1810
1811
		if (f->f_type == F_CONSOLE && (flags & IGN_CONS))
1812
			continue;
1813
1814
		/* don't output marks to recently written files */
1815
		if ((flags & MARK) &&
1816
		    (now.tv_sec - f->f_time) < MarkInterval / 2)
1817
			continue;
1818
1819
		/*
1820
		 * suppress duplicate lines to this file
1821
		 */
1822
		if ((Repeat == 0 || (Repeat == 1 &&
1823
		    (f->f_type != F_PIPE && f->f_type != F_FORWUDP &&
1824
		    f->f_type != F_FORWTCP && f->f_type != F_FORWTLS))) &&
1825
		    (flags & MARK) == 0 && msglen == f->f_prevlen &&
1826
		    !strcmp(msg, f->f_prevline) &&
1827
		    !strcmp(from, f->f_prevhost)) {
1828
			strlcpy(f->f_lasttime, timestamp,
1829
			    sizeof(f->f_lasttime));
1830
			f->f_prevcount++;
1831
			log_debug("msg repeated %d times, %ld sec of %d",
1832
			    f->f_prevcount, (long)(now.tv_sec - f->f_time),
1833
			    repeatinterval[f->f_repeatcount]);
1834
			/*
1835
			 * If domark would have logged this by now,
1836
			 * flush it now (so we don't hold isolated messages),
1837
			 * but back off so we'll flush less often
1838
			 * in the future.
1839
			 */
1840
			if (now.tv_sec > REPEATTIME(f)) {
1841
				fprintlog(f, flags, (char *)NULL);
1842
				BACKOFF(f);
1843
			}
1844
		} else {
1845
			/* new line, save it */
1846
			if (f->f_prevcount)
1847
				fprintlog(f, 0, (char *)NULL);
1848
			f->f_repeatcount = 0;
1849
			f->f_prevpri = pri;
1850
			strlcpy(f->f_lasttime, timestamp,
1851
			    sizeof(f->f_lasttime));
1852
			strlcpy(f->f_prevhost, from,
1853
			    sizeof(f->f_prevhost));
1854
			if (msglen < MAXSVLINE) {
1855
				f->f_prevlen = msglen;
1856
				strlcpy(f->f_prevline, msg,
1857
				    sizeof(f->f_prevline));
1858
				fprintlog(f, flags, (char *)NULL);
1859
			} else {
1860
				f->f_prevline[0] = 0;
1861
				f->f_prevlen = 0;
1862
				fprintlog(f, flags, msg);
1863
			}
1864
		}
1865
1866
		if (f->f_quick)
1867
			break;
1868
	}
1869
}
1870
1871
void
1872
fprintlog(struct filed *f, int flags, char *msg)
1873
{
1874
	struct iovec iov[6];
1875
	struct iovec *v;
1876
	int l, retryonce;
1877
	char line[LOG_MAXLINE + 1], repbuf[80], greetings[500];
1878
1879
	v = iov;
1880
	if (f->f_type == F_WALL) {
1881
		l = snprintf(greetings, sizeof(greetings),
1882
		    "\r\n\7Message from syslogd@%s at %.24s ...\r\n",
1883
		    f->f_prevhost, ctime(&now.tv_sec));
1884
		if (l < 0 || (size_t)l >= sizeof(greetings))
1885
			l = strlen(greetings);
1886
		v->iov_base = greetings;
1887
		v->iov_len = l;
1888
		v++;
1889
		v->iov_base = "";
1890
		v->iov_len = 0;
1891
		v++;
1892
	} else if (f->f_lasttime[0] != '\0') {
1893
		v->iov_base = f->f_lasttime;
1894
		v->iov_len = strlen(f->f_lasttime);
1895
		v++;
1896
		v->iov_base = " ";
1897
		v->iov_len = 1;
1898
		v++;
1899
	} else {
1900
		v->iov_base = "";
1901
		v->iov_len = 0;
1902
		v++;
1903
		v->iov_base = "";
1904
		v->iov_len = 0;
1905
		v++;
1906
	}
1907
	if (f->f_prevhost[0] != '\0') {
1908
		v->iov_base = f->f_prevhost;
1909
		v->iov_len = strlen(v->iov_base);
1910
		v++;
1911
		v->iov_base = " ";
1912
		v->iov_len = 1;
1913
		v++;
1914
	} else {
1915
		v->iov_base = "";
1916
		v->iov_len = 0;
1917
		v++;
1918
		v->iov_base = "";
1919
		v->iov_len = 0;
1920
		v++;
1921
	}
1922
1923
	if (msg) {
1924
		v->iov_base = msg;
1925
		v->iov_len = strlen(msg);
1926
	} else if (f->f_prevcount > 1) {
1927
		l = snprintf(repbuf, sizeof(repbuf),
1928
		    "last message repeated %d times", f->f_prevcount);
1929
		if (l < 0 || (size_t)l >= sizeof(repbuf))
1930
			l = strlen(repbuf);
1931
		v->iov_base = repbuf;
1932
		v->iov_len = l;
1933
	} else {
1934
		v->iov_base = f->f_prevline;
1935
		v->iov_len = f->f_prevlen;
1936
	}
1937
	v++;
1938
1939
	log_debugadd("Logging to %s", TypeNames[f->f_type]);
1940
	f->f_time = now.tv_sec;
1941
1942
	switch (f->f_type) {
1943
	case F_UNUSED:
1944
		log_debug("%s", "");
1945
		break;
1946
1947
	case F_FORWUDP:
1948
		log_debug(" %s", f->f_un.f_forw.f_loghost);
1949
		l = snprintf(line, MINIMUM(MAX_UDPMSG + 1, sizeof(line)),
1950
		    "<%d>%.32s %s%s%s", f->f_prevpri, (char *)iov[0].iov_base,
1951
		    IncludeHostname ? LocalHostName : "",
1952
		    IncludeHostname ? " " : "",
1953
		    (char *)iov[4].iov_base);
1954
		if (l < 0 || (size_t)l > MINIMUM(MAX_UDPMSG, sizeof(line)))
1955
			l = MINIMUM(MAX_UDPMSG, sizeof(line));
1956
		if (sendto(f->f_file, line, l, 0,
1957
		    (struct sockaddr *)&f->f_un.f_forw.f_addr,
1958
		    f->f_un.f_forw.f_addr.ss_len) != l) {
1959
			switch (errno) {
1960
			case EADDRNOTAVAIL:
1961
			case EHOSTDOWN:
1962
			case EHOSTUNREACH:
1963
			case ENETDOWN:
1964
			case ENETUNREACH:
1965
			case ENOBUFS:
1966
			case EWOULDBLOCK:
1967
				/* silently dropped */
1968
				break;
1969
			default:
1970
				f->f_type = F_UNUSED;
1971
				log_warn("sendto \"%s\"",
1972
				    f->f_un.f_forw.f_loghost);
1973
				break;
1974
			}
1975
		}
1976
		break;
1977
1978
	case F_FORWTCP:
1979
	case F_FORWTLS:
1980
		log_debugadd(" %s", f->f_un.f_forw.f_loghost);
1981
		if (EVBUFFER_LENGTH(f->f_un.f_forw.f_bufev->output) >=
1982
		    MAX_TCPBUF) {
1983
			log_debug(" (dropped)");
1984
			f->f_un.f_forw.f_dropped++;
1985
			break;
1986
		}
1987
		/*
1988
		 * Syslog over TLS  RFC 5425  4.3.  Sending Data
1989
		 * Syslog over TCP  RFC 6587  3.4.1.  Octet Counting
1990
		 * Use an additional '\n' to split messages.  This allows
1991
		 * buffer synchronisation, helps legacy implementations,
1992
		 * and makes line based testing easier.
1993
		 */
1994
		l = snprintf(line, sizeof(line), "<%d>%.32s %s%s\n",
1995
		    f->f_prevpri, (char *)iov[0].iov_base,
1996
		    IncludeHostname ? LocalHostName : "",
1997
		    IncludeHostname ? " " : "");
1998
		if (l < 0) {
1999
			log_debug(" (dropped snprintf)");
2000
			f->f_un.f_forw.f_dropped++;
2001
			break;
2002
		}
2003
		l = evbuffer_add_printf(f->f_un.f_forw.f_bufev->output,
2004
		    "%zu <%d>%.32s %s%s%s\n",
2005
		    (size_t)l + strlen(iov[4].iov_base),
2006
		    f->f_prevpri, (char *)iov[0].iov_base,
2007
		    IncludeHostname ? LocalHostName : "",
2008
		    IncludeHostname ? " " : "",
2009
		    (char *)iov[4].iov_base);
2010
		if (l < 0) {
2011
			log_debug(" (dropped evbuffer_add_printf)");
2012
			f->f_un.f_forw.f_dropped++;
2013
			break;
2014
		}
2015
		bufferevent_enable(f->f_un.f_forw.f_bufev, EV_WRITE);
2016
		log_debug("%s", "");
2017
		break;
2018
2019
	case F_CONSOLE:
2020
		if (flags & IGN_CONS) {
2021
			log_debug(" (ignored)");
2022
			break;
2023
		}
2024
		/* FALLTHROUGH */
2025
2026
	case F_TTY:
2027
	case F_FILE:
2028
	case F_PIPE:
2029
		log_debug(" %s", f->f_un.f_fname);
2030
		if (f->f_type != F_FILE && f->f_type != F_PIPE) {
2031
			v->iov_base = "\r\n";
2032
			v->iov_len = 2;
2033
		} else {
2034
			v->iov_base = "\n";
2035
			v->iov_len = 1;
2036
		}
2037
		retryonce = 0;
2038
	again:
2039
		if (writev(f->f_file, iov, 6) < 0) {
2040
			int e = errno;
2041
2042
			/* pipe is non-blocking. log and drop message if full */
2043
			if (e == EAGAIN && f->f_type == F_PIPE) {
2044
				if (now.tv_sec - f->f_lasterrtime > 120) {
2045
					f->f_lasterrtime = now.tv_sec;
2046
					log_warn("writev \"%s\"",
2047
					    f->f_un.f_fname);
2048
				}
2049
				break;
2050
			}
2051
2052
			/*
2053
			 * Check for errors on TTY's or program pipes.
2054
			 * Errors happen due to loss of tty or died programs.
2055
			 */
2056
			if (e == EAGAIN) {
2057
				/*
2058
				 * Silently drop messages on blocked write.
2059
				 * This can happen when logging to a locked tty.
2060
				 */
2061
				break;
2062
			}
2063
2064
			(void)close(f->f_file);
2065
			if ((e == EIO || e == EBADF) &&
2066
			    f->f_type != F_FILE && f->f_type != F_PIPE &&
2067
			    !retryonce) {
2068
				f->f_file = priv_open_tty(f->f_un.f_fname);
2069
				retryonce = 1;
2070
				if (f->f_file < 0) {
2071
					f->f_type = F_UNUSED;
2072
					log_warn("priv_open_tty \"%s\"",
2073
					    f->f_un.f_fname);
2074
				} else
2075
					goto again;
2076
			} else if ((e == EPIPE || e == EBADF) &&
2077
			    f->f_type == F_PIPE && !retryonce) {
2078
				f->f_file = priv_open_log(f->f_un.f_fname);
2079
				retryonce = 1;
2080
				if (f->f_file < 0) {
2081
					f->f_type = F_UNUSED;
2082
					log_warn("priv_open_log \"%s\"",
2083
					    f->f_un.f_fname);
2084
				} else
2085
					goto again;
2086
			} else {
2087
				f->f_type = F_UNUSED;
2088
				f->f_file = -1;
2089
				errno = e;
2090
				log_warn("writev \"%s\"", f->f_un.f_fname);
2091
			}
2092
		} else if (flags & SYNC_FILE)
2093
			(void)fsync(f->f_file);
2094
		break;
2095
2096
	case F_USERS:
2097
	case F_WALL:
2098
		log_debug("%s", "");
2099
		v->iov_base = "\r\n";
2100
		v->iov_len = 2;
2101
		wallmsg(f, iov);
2102
		break;
2103
2104
	case F_MEMBUF:
2105
		log_debug("%s", "");
2106
		snprintf(line, sizeof(line), "%.32s %s %s",
2107
		    (char *)iov[0].iov_base, (char *)iov[2].iov_base,
2108
		    (char *)iov[4].iov_base);
2109
		if (ringbuf_append_line(f->f_un.f_mb.f_rb, line) == 1)
2110
			f->f_un.f_mb.f_overflow = 1;
2111
		if (f->f_un.f_mb.f_attached)
2112
			ctlconn_logto(line);
2113
		break;
2114
	}
2115
	f->f_prevcount = 0;
2116
}
2117
2118
/*
2119
 *  WALLMSG -- Write a message to the world at large
2120
 *
2121
 *	Write the specified message to either the entire
2122
 *	world, or a list of approved users.
2123
 */
2124
void
2125
wallmsg(struct filed *f, struct iovec *iov)
2126
{
2127
	struct utmp ut;
2128
	char utline[sizeof(ut.ut_line) + 1];
2129
	static int reenter;			/* avoid calling ourselves */
2130
	FILE *uf;
2131
	int i;
2132
2133
	if (reenter++)
2134
		return;
2135
	if ((uf = priv_open_utmp()) == NULL) {
2136
		log_warn("priv_open_utmp");
2137
		reenter = 0;
2138
		return;
2139
	}
2140
	while (fread(&ut, sizeof(ut), 1, uf) == 1) {
2141
		if (ut.ut_name[0] == '\0')
2142
			continue;
2143
		/* must use strncpy since ut_* may not be NUL terminated */
2144
		strncpy(utline, ut.ut_line, sizeof(utline) - 1);
2145
		utline[sizeof(utline) - 1] = '\0';
2146
		if (f->f_type == F_WALL) {
2147
			ttymsg(iov, 6, utline);
2148
			continue;
2149
		}
2150
		/* should we send the message to this user? */
2151
		for (i = 0; i < MAXUNAMES; i++) {
2152
			if (!f->f_un.f_uname[i][0])
2153
				break;
2154
			if (!strncmp(f->f_un.f_uname[i], ut.ut_name,
2155
			    UT_NAMESIZE)) {
2156
				ttymsg(iov, 6, utline);
2157
				break;
2158
			}
2159
		}
2160
	}
2161
	(void)fclose(uf);
2162
	reenter = 0;
2163
}
2164
2165
/*
2166
 * Return a printable representation of a host address.
2167
 */
2168
void
2169
cvthname(struct sockaddr *f, char *result, size_t res_len)
2170
{
2171
	if (getnameinfo(f, f->sa_len, result, res_len, NULL, 0,
2172
	    NI_NUMERICHOST|NI_NUMERICSERV|NI_DGRAM) != 0) {
2173
		log_debug("Malformed from address");
2174
		strlcpy(result, hostname_unknown, res_len);
2175
		return;
2176
	}
2177
	log_debug("cvthname(%s)", result);
2178
	if (NoDNS)
2179
		return;
2180
2181
	if (priv_getnameinfo(f, f->sa_len, result, res_len) != 0)
2182
		log_debug("Host name for from address (%s) unknown", result);
2183
}
2184
2185
void
2186
die_signalcb(int signum, short event, void *arg)
2187
{
2188
	die(signum);
2189
}
2190
2191
void
2192
mark_timercb(int unused, short event, void *arg)
2193
{
2194
	struct event		*ev = arg;
2195
	struct timeval		 to;
2196
2197
	markit();
2198
2199
	to.tv_sec = TIMERINTVL;
2200
	to.tv_usec = 0;
2201
	evtimer_add(ev, &to);
2202
}
2203
2204
void
2205
init_signalcb(int signum, short event, void *arg)
2206
{
2207
	init();
2208
	log_info(LOG_INFO, "restart");
2209
2210
	if (tcpbuf_dropped > 0) {
2211
		log_info(LOG_WARNING, "dropped %d message%s to remote loghost",
2212
		    tcpbuf_dropped, tcpbuf_dropped == 1 ? "" : "s");
2213
		tcpbuf_dropped = 0;
2214
	}
2215
	log_debug("syslogd: restarted");
2216
}
2217
2218
void
2219
logevent(int severity, const char *msg)
2220
{
2221
	log_debug("libevent: [%d] %s", severity, msg);
2222
}
2223
2224
__dead void
2225
die(int signo)
2226
{
2227
	struct filed *f;
2228
	int was_initialized = Initialized;
2229
2230
	Initialized = 0;		/* Don't log SIGCHLDs */
2231
	SIMPLEQ_FOREACH(f, &Files, f_next) {
2232
		/* flush any pending output */
2233
		if (f->f_prevcount)
2234
			fprintlog(f, 0, (char *)NULL);
2235
		if (f->f_type == F_FORWTLS || f->f_type == F_FORWTCP) {
2236
			tcpbuf_dropped += f->f_un.f_forw.f_dropped +
2237
			    tcpbuf_countmsg(f->f_un.f_forw.f_bufev);
2238
			f->f_un.f_forw.f_dropped = 0;
2239
		}
2240
	}
2241
	Initialized = was_initialized;
2242
2243
	if (tcpbuf_dropped > 0) {
2244
		log_info(LOG_WARNING, "dropped %d message%s to remote loghost",
2245
		    tcpbuf_dropped, tcpbuf_dropped == 1 ? "" : "s");
2246
		tcpbuf_dropped = 0;
2247
	}
2248
2249
	if (signo)
2250
		log_info(LOG_ERR, "exiting on signal %d", signo);
2251
	log_debug("syslogd: exited");
2252
	exit(0);
2253
}
2254
2255
/*
2256
 *  INIT -- Initialize syslogd from configuration table
2257
 */
2258
void
2259
init(void)
2260
{
2261
	char progblock[NAME_MAX+1], hostblock[NAME_MAX+1], *cline, *p, *q;
2262
	struct filed_list mb;
2263
	struct filed *f, *m;
2264
	FILE *cf;
2265
	int i;
2266
	size_t s;
2267
2268
	log_debug("init");
2269
2270
	/* If config file has been modified, then just die to restart */
2271
	if (priv_config_modified()) {
2272
		log_debug("config file changed: dying");
2273
		die(0);
2274
	}
2275
2276
	/*
2277
	 *  Close all open log files.
2278
	 */
2279
	Initialized = 0;
2280
	SIMPLEQ_INIT(&mb);
2281
	while (!SIMPLEQ_EMPTY(&Files)) {
2282
		f = SIMPLEQ_FIRST(&Files);
2283
		SIMPLEQ_REMOVE_HEAD(&Files, f_next);
2284
		/* flush any pending output */
2285
		if (f->f_prevcount)
2286
			fprintlog(f, 0, (char *)NULL);
2287
2288
		switch (f->f_type) {
2289
		case F_FORWTLS:
2290
			if (f->f_un.f_forw.f_ctx) {
2291
				tls_close(f->f_un.f_forw.f_ctx);
2292
				tls_free(f->f_un.f_forw.f_ctx);
2293
			}
2294
			free(f->f_un.f_forw.f_host);
2295
			/* FALLTHROUGH */
2296
		case F_FORWTCP:
2297
			tcpbuf_dropped += f->f_un.f_forw.f_dropped +
2298
			     tcpbuf_countmsg(f->f_un.f_forw.f_bufev);
2299
			bufferevent_free(f->f_un.f_forw.f_bufev);
2300
			/* FALLTHROUGH */
2301
		case F_FILE:
2302
		case F_TTY:
2303
		case F_CONSOLE:
2304
		case F_PIPE:
2305
			(void)close(f->f_file);
2306
			break;
2307
		}
2308
		free(f->f_program);
2309
		free(f->f_hostname);
2310
		if (f->f_type == F_MEMBUF) {
2311
			f->f_program = NULL;
2312
			f->f_hostname = NULL;
2313
			log_debug("add %p to mb", f);
2314
			SIMPLEQ_INSERT_HEAD(&mb, f, f_next);
2315
		} else
2316
			free(f);
2317
	}
2318
	SIMPLEQ_INIT(&Files);
2319
2320
	/* open the configuration file */
2321
	if ((cf = priv_open_config()) == NULL) {
2322
		log_debug("cannot open %s", ConfFile);
2323
		SIMPLEQ_INSERT_TAIL(&Files,
2324
		    cfline("*.ERR\t/dev/console", "*", "*"), f_next);
2325
		SIMPLEQ_INSERT_TAIL(&Files,
2326
		    cfline("*.PANIC\t*", "*", "*"), f_next);
2327
		Initialized = 1;
2328
		return;
2329
	}
2330
2331
	/*
2332
	 *  Foreach line in the conf table, open that file.
2333
	 */
2334
	cline = NULL;
2335
	s = 0;
2336
	strlcpy(progblock, "*", sizeof(progblock));
2337
	strlcpy(hostblock, "*", sizeof(hostblock));
2338
	while (getline(&cline, &s, cf) != -1) {
2339
		/*
2340
		 * check for end-of-section, comments, strip off trailing
2341
		 * spaces and newline character. !progblock and +hostblock
2342
		 * are treated specially: the following lines apply only to
2343
		 * that program.
2344
		 */
2345
		for (p = cline; isspace((unsigned char)*p); ++p)
2346
			continue;
2347
		if (*p == '\0' || *p == '#')
2348
			continue;
2349
		if (*p == '!' || *p == '+') {
2350
			q = (*p == '!') ? progblock : hostblock;
2351
			p++;
2352
			while (isspace((unsigned char)*p))
2353
				p++;
2354
			if (*p == '\0' || (*p == '*' && (p[1] == '\0' ||
2355
			    isspace((unsigned char)p[1])))) {
2356
				strlcpy(q, "*", NAME_MAX+1);
2357
				continue;
2358
			}
2359
			for (i = 0; i < NAME_MAX; i++) {
2360
				if (*p == '\0' || isspace((unsigned char)*p))
2361
					break;
2362
				*q++ = *p++;
2363
			}
2364
			*q = '\0';
2365
			continue;
2366
		}
2367
2368
		p = cline + strlen(cline);
2369
		while (p > cline)
2370
			if (!isspace((unsigned char)*--p)) {
2371
				p++;
2372
				break;
2373
			}
2374
		*p = '\0';
2375
		f = cfline(cline, progblock, hostblock);
2376
		if (f != NULL)
2377
			SIMPLEQ_INSERT_TAIL(&Files, f, f_next);
2378
	}
2379
	free(cline);
2380
	if (!feof(cf))
2381
		fatal("read config file");
2382
2383
	/* Match and initialize the memory buffers */
2384
	SIMPLEQ_FOREACH(f, &Files, f_next) {
2385
		if (f->f_type != F_MEMBUF)
2386
			continue;
2387
		log_debug("Initialize membuf %s at %p",
2388
		    f->f_un.f_mb.f_mname, f);
2389
2390
		SIMPLEQ_FOREACH(m, &mb, f_next) {
2391
			if (m->f_un.f_mb.f_rb == NULL)
2392
				continue;
2393
			if (strcmp(m->f_un.f_mb.f_mname,
2394
			    f->f_un.f_mb.f_mname) == 0)
2395
				break;
2396
		}
2397
		if (m == NULL) {
2398
			log_debug("Membuf no match");
2399
			f->f_un.f_mb.f_rb = ringbuf_init(f->f_un.f_mb.f_len);
2400
			if (f->f_un.f_mb.f_rb == NULL) {
2401
				f->f_type = F_UNUSED;
2402
				log_warn("allocate membuf");
2403
			}
2404
		} else {
2405
			log_debug("Membuf match f:%p, m:%p", f, m);
2406
			f->f_un = m->f_un;
2407
			m->f_un.f_mb.f_rb = NULL;
2408
		}
2409
	}
2410
2411
	/* make sure remaining buffers are freed */
2412
	while (!SIMPLEQ_EMPTY(&mb)) {
2413
		m = SIMPLEQ_FIRST(&mb);
2414
		SIMPLEQ_REMOVE_HEAD(&mb, f_next);
2415
		if (m->f_un.f_mb.f_rb != NULL) {
2416
			log_warnx("mismatched membuf");
2417
			ringbuf_free(m->f_un.f_mb.f_rb);
2418
		}
2419
		log_debug("Freeing membuf %p", m);
2420
2421
		free(m);
2422
	}
2423
2424
	/* close the configuration file */
2425
	(void)fclose(cf);
2426
2427
	Initialized = 1;
2428
2429
	if (Debug) {
2430
		SIMPLEQ_FOREACH(f, &Files, f_next) {
2431
			for (i = 0; i <= LOG_NFACILITIES; i++)
2432
				if (f->f_pmask[i] == INTERNAL_NOPRI)
2433
					printf("X ");
2434
				else
2435
					printf("%d ", f->f_pmask[i]);
2436
			printf("%s: ", TypeNames[f->f_type]);
2437
			switch (f->f_type) {
2438
			case F_FILE:
2439
			case F_TTY:
2440
			case F_CONSOLE:
2441
			case F_PIPE:
2442
				printf("%s", f->f_un.f_fname);
2443
				break;
2444
2445
			case F_FORWUDP:
2446
			case F_FORWTCP:
2447
			case F_FORWTLS:
2448
				printf("%s", f->f_un.f_forw.f_loghost);
2449
				break;
2450
2451
			case F_USERS:
2452
				for (i = 0; i < MAXUNAMES &&
2453
				    *f->f_un.f_uname[i]; i++)
2454
					printf("%s, ", f->f_un.f_uname[i]);
2455
				break;
2456
2457
			case F_MEMBUF:
2458
				printf("%s", f->f_un.f_mb.f_mname);
2459
				break;
2460
2461
			}
2462
			if (f->f_program || f->f_hostname)
2463
				printf(" (%s, %s)",
2464
				    f->f_program ? f->f_program : "*",
2465
				    f->f_hostname ? f->f_hostname : "*");
2466
			printf("\n");
2467
		}
2468
	}
2469
}
2470
2471
#define progmatches(p1, p2) \
2472
	(p1 == p2 || (p1 != NULL && p2 != NULL && strcmp(p1, p2) == 0))
2473
2474
/*
2475
 * Spot a line with a duplicate file, pipe, console, tty, or membuf target.
2476
 */
2477
struct filed *
2478
find_dup(struct filed *f)
2479
{
2480
	struct filed *list;
2481
2482
	SIMPLEQ_FOREACH(list, &Files, f_next) {
2483
		if (list->f_quick || f->f_quick)
2484
			continue;
2485
		switch (list->f_type) {
2486
		case F_FILE:
2487
		case F_TTY:
2488
		case F_CONSOLE:
2489
		case F_PIPE:
2490
			if (strcmp(list->f_un.f_fname, f->f_un.f_fname) == 0 &&
2491
			    progmatches(list->f_program, f->f_program) &&
2492
			    progmatches(list->f_hostname, f->f_hostname)) {
2493
				log_debug("duplicate %s", f->f_un.f_fname);
2494
				return (list);
2495
			}
2496
			break;
2497
		case F_MEMBUF:
2498
			if (strcmp(list->f_un.f_mb.f_mname,
2499
			    f->f_un.f_mb.f_mname) == 0 &&
2500
			    progmatches(list->f_program, f->f_program) &&
2501
			    progmatches(list->f_hostname, f->f_hostname)) {
2502
				log_debug("duplicate membuf %s",
2503
				    f->f_un.f_mb.f_mname);
2504
				return (list);
2505
			}
2506
			break;
2507
		}
2508
	}
2509
	return (NULL);
2510
}
2511
2512
/*
2513
 * Crack a configuration file line
2514
 */
2515
struct filed *
2516
cfline(char *line, char *progblock, char *hostblock)
2517
{
2518
	int i, pri;
2519
	size_t rb_len;
2520
	char *bp, *p, *q, *proto, *host, *port, *ipproto;
2521
	char buf[LOG_MAXLINE];
2522
	struct filed *xf, *f, *d;
2523
	struct timeval to;
2524
2525
	log_debug("cfline(\"%s\", f, \"%s\", \"%s\")",
2526
	    line, progblock, hostblock);
2527
2528
	if ((f = calloc(1, sizeof(*f))) == NULL)
2529
		fatal("allocate struct filed");
2530
	for (i = 0; i <= LOG_NFACILITIES; i++)
2531
		f->f_pmask[i] = INTERNAL_NOPRI;
2532
2533
	/* save program name if any */
2534
	f->f_quick = 0;
2535
	if (*progblock == '!') {
2536
		progblock++;
2537
		f->f_quick = 1;
2538
	}
2539
	if (*hostblock == '+') {
2540
		hostblock++;
2541
		f->f_quick = 1;
2542
	}
2543
	if (strcmp(progblock, "*") != 0)
2544
		f->f_program = strdup(progblock);
2545
	if (strcmp(hostblock, "*") != 0)
2546
		f->f_hostname = strdup(hostblock);
2547
2548
	/* scan through the list of selectors */
2549
	for (p = line; *p && *p != '\t' && *p != ' ';) {
2550
2551
		/* find the end of this facility name list */
2552
		for (q = p; *q && *q != '\t' && *q != ' ' && *q++ != '.'; )
2553
			continue;
2554
2555
		/* collect priority name */
2556
		for (bp = buf; *q && !strchr("\t,; ", *q); )
2557
			*bp++ = *q++;
2558
		*bp = '\0';
2559
2560
		/* skip cruft */
2561
		while (*q && strchr(",;", *q))
2562
			q++;
2563
2564
		/* decode priority name */
2565
		if (*buf == '*')
2566
			pri = LOG_PRIMASK + 1;
2567
		else {
2568
			/* ignore trailing spaces */
2569
			for (i=strlen(buf)-1; i >= 0 && buf[i] == ' '; i--) {
2570
				buf[i]='\0';
2571
			}
2572
2573
			pri = decode(buf, prioritynames);
2574
			if (pri < 0) {
2575
				log_warnx("unknown priority name \"%s\"", buf);
2576
				free(f);
2577
				return (NULL);
2578
			}
2579
		}
2580
2581
		/* scan facilities */
2582
		while (*p && !strchr("\t.; ", *p)) {
2583
			for (bp = buf; *p && !strchr("\t,;. ", *p); )
2584
				*bp++ = *p++;
2585
			*bp = '\0';
2586
			if (*buf == '*')
2587
				for (i = 0; i < LOG_NFACILITIES; i++)
2588
					f->f_pmask[i] = pri;
2589
			else {
2590
				i = decode(buf, facilitynames);
2591
				if (i < 0) {
2592
					log_warnx("unknown facility name "
2593
					    "\"%s\"", buf);
2594
					free(f);
2595
					return (NULL);
2596
				}
2597
				f->f_pmask[i >> 3] = pri;
2598
			}
2599
			while (*p == ',' || *p == ' ')
2600
				p++;
2601
		}
2602
2603
		p = q;
2604
	}
2605
2606
	/* skip to action part */
2607
	while (*p == '\t' || *p == ' ')
2608
		p++;
2609
2610
	switch (*p) {
2611
	case '@':
2612
		if ((strlcpy(f->f_un.f_forw.f_loghost, p,
2613
		    sizeof(f->f_un.f_forw.f_loghost)) >=
2614
		    sizeof(f->f_un.f_forw.f_loghost))) {
2615
			log_warnx("loghost too long \"%s\"", p);
2616
			break;
2617
		}
2618
		if (loghost_parse(++p, &proto, &host, &port) == -1) {
2619
			log_warnx("bad loghost \"%s\"",
2620
			    f->f_un.f_forw.f_loghost);
2621
			break;
2622
		}
2623
		if (proto == NULL)
2624
			proto = "udp";
2625
		ipproto = proto;
2626
		if (strcmp(proto, "udp") == 0) {
2627
			if (fd_udp == -1)
2628
				proto = "udp6";
2629
			if (fd_udp6 == -1)
2630
				proto = "udp4";
2631
			ipproto = proto;
2632
		} else if (strcmp(proto, "udp4") == 0) {
2633
			if (fd_udp == -1) {
2634
				log_warnx("no udp4 \"%s\"",
2635
				    f->f_un.f_forw.f_loghost);
2636
				break;
2637
			}
2638
		} else if (strcmp(proto, "udp6") == 0) {
2639
			if (fd_udp6 == -1) {
2640
				log_warnx("no udp6 \"%s\"",
2641
				    f->f_un.f_forw.f_loghost);
2642
				break;
2643
			}
2644
		} else if (strcmp(proto, "tcp") == 0 ||
2645
		    strcmp(proto, "tcp4") == 0 || strcmp(proto, "tcp6") == 0) {
2646
			;
2647
		} else if (strcmp(proto, "tls") == 0) {
2648
			ipproto = "tcp";
2649
		} else if (strcmp(proto, "tls4") == 0) {
2650
			ipproto = "tcp4";
2651
		} else if (strcmp(proto, "tls6") == 0) {
2652
			ipproto = "tcp6";
2653
		} else {
2654
			log_warnx("bad protocol \"%s\"",
2655
			    f->f_un.f_forw.f_loghost);
2656
			break;
2657
		}
2658
		if (strlen(host) >= NI_MAXHOST) {
2659
			log_warnx("host too long \"%s\"",
2660
			    f->f_un.f_forw.f_loghost);
2661
			break;
2662
		}
2663
		if (port == NULL)
2664
			port = strncmp(proto, "tls", 3) == 0 ?
2665
			    "syslog-tls" : "syslog";
2666
		if (strlen(port) >= NI_MAXSERV) {
2667
			log_warnx("port too long \"%s\"",
2668
			    f->f_un.f_forw.f_loghost);
2669
			break;
2670
		}
2671
		if (priv_getaddrinfo(ipproto, host, port,
2672
		    (struct sockaddr*)&f->f_un.f_forw.f_addr,
2673
		    sizeof(f->f_un.f_forw.f_addr)) != 0) {
2674
			log_warnx("bad hostname \"%s\"",
2675
			    f->f_un.f_forw.f_loghost);
2676
			break;
2677
		}
2678
		f->f_file = -1;
2679
		if (strncmp(proto, "udp", 3) == 0) {
2680
			switch (f->f_un.f_forw.f_addr.ss_family) {
2681
			case AF_INET:
2682
				send_udp = 1;
2683
				f->f_file = fd_udp;
2684
				break;
2685
			case AF_INET6:
2686
				send_udp6 = 1;
2687
				f->f_file = fd_udp6;
2688
				break;
2689
			}
2690
			f->f_type = F_FORWUDP;
2691
		} else if (strncmp(ipproto, "tcp", 3) == 0) {
2692
			if ((f->f_un.f_forw.f_bufev = bufferevent_new(-1,
2693
			    tcp_dropcb, tcp_writecb, tcp_errorcb, f)) == NULL) {
2694
				log_warn("bufferevent \"%s\"",
2695
				    f->f_un.f_forw.f_loghost);
2696
				break;
2697
			}
2698
			if (strncmp(proto, "tls", 3) == 0) {
2699
				f->f_un.f_forw.f_host = strdup(host);
2700
				f->f_type = F_FORWTLS;
2701
			} else {
2702
				f->f_type = F_FORWTCP;
2703
			}
2704
			/*
2705
			 * If we try to connect to a TLS server immediately
2706
			 * syslogd gets an SIGPIPE as the signal handlers have
2707
			 * not been set up.  Delay the connection until the
2708
			 * event loop is started.  We can reuse the write event
2709
			 * for that as bufferevent is still disabled.
2710
			 */
2711
			to.tv_sec = 0;
2712
			to.tv_usec = 1;
2713
			evtimer_set(&f->f_un.f_forw.f_bufev->ev_write,
2714
			    tcp_connectcb, f);
2715
			evtimer_add(&f->f_un.f_forw.f_bufev->ev_write, &to);
2716
		}
2717
		break;
2718
2719
	case '/':
2720
	case '|':
2721
		(void)strlcpy(f->f_un.f_fname, p, sizeof(f->f_un.f_fname));
2722
		d = find_dup(f);
2723
		if (d != NULL) {
2724
			for (i = 0; i <= LOG_NFACILITIES; i++)
2725
				if (f->f_pmask[i] != INTERNAL_NOPRI)
2726
					d->f_pmask[i] = f->f_pmask[i];
2727
			free(f);
2728
			return (NULL);
2729
		}
2730
		if (strcmp(p, ctty) == 0) {
2731
			f->f_file = priv_open_tty(p);
2732
			if (f->f_file < 0)
2733
				log_warn("priv_open_tty \"%s\"", p);
2734
		} else {
2735
			f->f_file = priv_open_log(p);
2736
			if (f->f_file < 0)
2737
				log_warn("priv_open_log \"%s\"", p);
2738
		}
2739
		if (f->f_file < 0) {
2740
			f->f_type = F_UNUSED;
2741
			break;
2742
		}
2743
		if (isatty(f->f_file)) {
2744
			if (strcmp(p, ctty) == 0)
2745
				f->f_type = F_CONSOLE;
2746
			else
2747
				f->f_type = F_TTY;
2748
		} else {
2749
			if (*p == '|')
2750
				f->f_type = F_PIPE;
2751
			else {
2752
				f->f_type = F_FILE;
2753
2754
				/* Clear O_NONBLOCK flag on f->f_file */
2755
				if ((i = fcntl(f->f_file, F_GETFL)) != -1) {
2756
					i &= ~O_NONBLOCK;
2757
					fcntl(f->f_file, F_SETFL, i);
2758
				}
2759
			}
2760
		}
2761
		break;
2762
2763
	case '*':
2764
		f->f_type = F_WALL;
2765
		break;
2766
2767
	case ':':
2768
		f->f_type = F_MEMBUF;
2769
2770
		/* Parse buffer size (in kb) */
2771
		errno = 0;
2772
		rb_len = strtoul(++p, &q, 0);
2773
		if (*p == '\0' || (errno == ERANGE && rb_len == ULONG_MAX) ||
2774
		    *q != ':' || rb_len == 0) {
2775
			f->f_type = F_UNUSED;
2776
			log_warnx("strtoul \"%s\"", p);
2777
			break;
2778
		}
2779
		q++;
2780
		rb_len *= 1024;
2781
2782
		/* Copy buffer name */
2783
		for(i = 0; (size_t)i < sizeof(f->f_un.f_mb.f_mname) - 1; i++) {
2784
			if (!isalnum((unsigned char)q[i]))
2785
				break;
2786
			f->f_un.f_mb.f_mname[i] = q[i];
2787
		}
2788
2789
		/* Make sure buffer name is unique */
2790
		xf = find_dup(f);
2791
2792
		/* Error on missing or non-unique name, or bad buffer length */
2793
		if (i == 0 || rb_len > MAX_MEMBUF || xf != NULL) {
2794
			f->f_type = F_UNUSED;
2795
			log_warnx("find_dup \"%s\"", p);
2796
			break;
2797
		}
2798
2799
		/* Set buffer length */
2800
		rb_len = MAXIMUM(rb_len, MIN_MEMBUF);
2801
		f->f_un.f_mb.f_len = rb_len;
2802
		f->f_un.f_mb.f_overflow = 0;
2803
		f->f_un.f_mb.f_attached = 0;
2804
		break;
2805
2806
	default:
2807
		for (i = 0; i < MAXUNAMES && *p; i++) {
2808
			for (q = p; *q && *q != ','; )
2809
				q++;
2810
			(void)strncpy(f->f_un.f_uname[i], p, UT_NAMESIZE);
2811
			if ((q - p) > UT_NAMESIZE)
2812
				f->f_un.f_uname[i][UT_NAMESIZE] = '\0';
2813
			else
2814
				f->f_un.f_uname[i][q - p] = '\0';
2815
			while (*q == ',' || *q == ' ')
2816
				q++;
2817
			p = q;
2818
		}
2819
		f->f_type = F_USERS;
2820
		break;
2821
	}
2822
	return (f);
2823
}
2824
2825
/*
2826
 * Parse the host and port parts from a loghost string.
2827
 */
2828
int
2829
loghost_parse(char *str, char **proto, char **host, char **port)
2830
{
2831
	char *prefix = NULL;
2832
2833

620
	if ((*host = strchr(str, ':')) &&
2834
255
	    (*host)[1] == '/' && (*host)[2] == '/') {
2835
		prefix = str;
2836
		**host = '\0';
2837
		str = *host + 3;
2838
	}
2839
310
	if (proto)
2840
		*proto = prefix;
2841
310
	else if (prefix)
2842
		return (-1);
2843
2844
310
	*host = str;
2845
310
	if (**host == '[') {
2846
65
		(*host)++;
2847
65
		str = strchr(*host, ']');
2848
65
		if (str == NULL)
2849
			return (-1);
2850
65
		*str++ = '\0';
2851
65
	}
2852
310
	*port = strrchr(str, ':');
2853
310
	if (*port != NULL)
2854
240
		*(*port)++ = '\0';
2855
2856
310
	return (0);
2857
310
}
2858
2859
/*
2860
 * Retrieve the size of the kernel message buffer, via sysctl.
2861
 */
2862
int
2863
getmsgbufsize(void)
2864
{
2865
	int msgbufsize, mib[2];
2866
	size_t size;
2867
2868
	mib[0] = CTL_KERN;
2869
	mib[1] = KERN_MSGBUFSIZE;
2870
	size = sizeof msgbufsize;
2871
	if (sysctl(mib, 2, &msgbufsize, &size, NULL, 0) == -1) {
2872
		log_debug("couldn't get kern.msgbufsize");
2873
		return (0);
2874
	}
2875
	return (msgbufsize);
2876
}
2877
2878
/*
2879
 *  Decode a symbolic name to a numeric value
2880
 */
2881
int
2882
decode(const char *name, const CODE *codetab)
2883
{
2884
	const CODE *c;
2885
	char *p, buf[40];
2886
2887
	for (p = buf; *name && p < &buf[sizeof(buf) - 1]; p++, name++) {
2888
		if (isupper((unsigned char)*name))
2889
			*p = tolower((unsigned char)*name);
2890
		else
2891
			*p = *name;
2892
	}
2893
	*p = '\0';
2894
	for (c = codetab; c->c_name; c++)
2895
		if (!strcmp(buf, c->c_name))
2896
			return (c->c_val);
2897
2898
	return (-1);
2899
}
2900
2901
void
2902
markit(void)
2903
{
2904
	struct filed *f;
2905
2906
	(void)gettimeofday(&now, NULL);
2907
	MarkSeq += TIMERINTVL;
2908
	if (MarkSeq >= MarkInterval) {
2909
		logline(LOG_INFO, ADDDATE|MARK, LocalHostName, "-- MARK --");
2910
		MarkSeq = 0;
2911
	}
2912
2913
	SIMPLEQ_FOREACH(f, &Files, f_next) {
2914
		if (f->f_prevcount && now.tv_sec >= REPEATTIME(f)) {
2915
			log_debug("flush %s: repeated %d times, %d sec",
2916
			    TypeNames[f->f_type], f->f_prevcount,
2917
			    repeatinterval[f->f_repeatcount]);
2918
			fprintlog(f, 0, (char *)NULL);
2919
			BACKOFF(f);
2920
		}
2921
	}
2922
}
2923
2924
int
2925
unix_socket(char *path, int type, mode_t mode)
2926
{
2927
	struct sockaddr_un s_un;
2928
	int fd, optval;
2929
	mode_t old_umask;
2930
2931
	memset(&s_un, 0, sizeof(s_un));
2932
	s_un.sun_family = AF_UNIX;
2933
	if (strlcpy(s_un.sun_path, path, sizeof(s_un.sun_path)) >=
2934
	    sizeof(s_un.sun_path)) {
2935
		log_warnx("socket path too long \"%s\"", path);
2936
		return (-1);
2937
	}
2938
2939
	if ((fd = socket(AF_UNIX, type, 0)) == -1) {
2940
		log_warn("socket unix \"%s\"", path);
2941
		return (-1);
2942
	}
2943
2944
	if (Debug) {
2945
		if (connect(fd, (struct sockaddr *)&s_un, sizeof(s_un)) == 0 ||
2946
		    errno == EPROTOTYPE) {
2947
			close(fd);
2948
			errno = EISCONN;
2949
			log_warn("connect unix \"%s\"", path);
2950
			return (-1);
2951
		}
2952
	}
2953
2954
	old_umask = umask(0177);
2955
2956
	unlink(path);
2957
	if (bind(fd, (struct sockaddr *)&s_un, sizeof(s_un)) == -1) {
2958
		log_warn("bind unix \"%s\"", path);
2959
		umask(old_umask);
2960
		close(fd);
2961
		return (-1);
2962
	}
2963
2964
	umask(old_umask);
2965
2966
	if (chmod(path, mode) == -1) {
2967
		log_warn("chmod unix \"%s\"", path);
2968
		close(fd);
2969
		unlink(path);
2970
		return (-1);
2971
	}
2972
2973
	optval = LOG_MAXLINE + PATH_MAX;
2974
	if (setsockopt(fd, SOL_SOCKET, SO_RCVBUF, &optval, sizeof(optval))
2975
	    == -1)
2976
		log_warn("setsockopt unix \"%s\"", path);
2977
2978
	return (fd);
2979
}
2980
2981
void
2982
double_sockbuf(int fd, int optname)
2983
{
2984
	socklen_t len;
2985
	int i, newsize, oldsize = 0;
2986
2987
	len = sizeof(oldsize);
2988
	if (getsockopt(fd, SOL_SOCKET, optname, &oldsize, &len) == -1)
2989
		log_warn("getsockopt bufsize");
2990
	len = sizeof(newsize);
2991
	newsize =  LOG_MAXLINE + 128;  /* data + control */
2992
	/* allow 8 full length messages */
2993
	for (i = 0; i < 4; i++, newsize *= 2) {
2994
		if (newsize <= oldsize)
2995
			continue;
2996
		if (setsockopt(fd, SOL_SOCKET, optname, &newsize, len) == -1)
2997
			log_warn("setsockopt bufsize %d", newsize);
2998
	}
2999
}
3000
3001
void
3002
set_sockbuf(int fd)
3003
{
3004
	int size = 65536;
3005
3006
	if (setsockopt(fd, SOL_SOCKET, SO_SNDBUF, &size, sizeof(size)) == -1)
3007
		log_warn("setsockopt sndbufsize %d", size);
3008
	if (setsockopt(fd, SOL_SOCKET, SO_RCVBUF, &size, sizeof(size)) == -1)
3009
		log_warn("setsockopt rcvbufsize %d", size);
3010
}
3011
3012
void
3013
ctlconn_cleanup(void)
3014
{
3015
	struct filed *f;
3016
3017
	close(fd_ctlconn);
3018
	fd_ctlconn = -1;
3019
	event_del(ev_ctlread);
3020
	event_del(ev_ctlwrite);
3021
	event_add(ev_ctlaccept, NULL);
3022
3023
	if (ctl_state == CTL_WRITING_CONT_REPLY)
3024
		SIMPLEQ_FOREACH(f, &Files, f_next)
3025
			if (f->f_type == F_MEMBUF)
3026
				f->f_un.f_mb.f_attached = 0;
3027
3028
	ctl_state = ctl_cmd_bytes = ctl_reply_offset = ctl_reply_size = 0;
3029
}
3030
3031
void
3032
ctlsock_acceptcb(int fd, short event, void *arg)
3033
{
3034
	struct event		*ev = arg;
3035
3036
	if ((fd = reserve_accept4(fd, event, ev, ctlsock_acceptcb,
3037
	    NULL, NULL, SOCK_NONBLOCK)) == -1) {
3038
		if (errno != ENFILE && errno != EMFILE &&
3039
		    errno != EINTR && errno != EWOULDBLOCK &&
3040
		    errno != ECONNABORTED)
3041
			log_warn("accept control socket");
3042
		return;
3043
	}
3044
	log_debug("Accepting control connection");
3045
3046
	if (fd_ctlconn != -1)
3047
		ctlconn_cleanup();
3048
3049
	/* Only one connection at a time */
3050
	event_del(ev);
3051
3052
	fd_ctlconn = fd;
3053
	/* file descriptor has changed, reset event */
3054
	event_set(ev_ctlread, fd_ctlconn, EV_READ|EV_PERSIST,
3055
	    ctlconn_readcb, ev_ctlread);
3056
	event_set(ev_ctlwrite, fd_ctlconn, EV_WRITE|EV_PERSIST,
3057
	    ctlconn_writecb, ev_ctlwrite);
3058
	event_add(ev_ctlread, NULL);
3059
	ctl_state = CTL_READING_CMD;
3060
	ctl_cmd_bytes = 0;
3061
}
3062
3063
static struct filed
3064
*find_membuf_log(const char *name)
3065
{
3066
	struct filed *f;
3067
3068
	SIMPLEQ_FOREACH(f, &Files, f_next) {
3069
		if (f->f_type == F_MEMBUF &&
3070
		    strcmp(f->f_un.f_mb.f_mname, name) == 0)
3071
			break;
3072
	}
3073
	return (f);
3074
}
3075
3076
void
3077
ctlconn_readcb(int fd, short event, void *arg)
3078
{
3079
	struct filed		*f;
3080
	struct ctl_reply_hdr	*reply_hdr = (struct ctl_reply_hdr *)ctl_reply;
3081
	ssize_t			 n;
3082
	u_int32_t		 flags = 0;
3083
3084
	if (ctl_state == CTL_WRITING_REPLY ||
3085
	    ctl_state == CTL_WRITING_CONT_REPLY) {
3086
		/* client has closed the connection */
3087
		ctlconn_cleanup();
3088
		return;
3089
	}
3090
3091
 retry:
3092
	n = read(fd, (char*)&ctl_cmd + ctl_cmd_bytes,
3093
	    sizeof(ctl_cmd) - ctl_cmd_bytes);
3094
	switch (n) {
3095
	case -1:
3096
		if (errno == EINTR)
3097
			goto retry;
3098
		if (errno == EWOULDBLOCK)
3099
			return;
3100
		log_warn("read control socket");
3101
		/* FALLTHROUGH */
3102
	case 0:
3103
		ctlconn_cleanup();
3104
		return;
3105
	default:
3106
		ctl_cmd_bytes += n;
3107
	}
3108
	if (ctl_cmd_bytes < sizeof(ctl_cmd))
3109
		return;
3110
3111
	if (ntohl(ctl_cmd.version) != CTL_VERSION) {
3112
		log_warnx("unknown client protocol version");
3113
		ctlconn_cleanup();
3114
		return;
3115
	}
3116
3117
	/* Ensure that logname is \0 terminated */
3118
	if (memchr(ctl_cmd.logname, '\0', sizeof(ctl_cmd.logname)) == NULL) {
3119
		log_warnx("corrupt control socket command");
3120
		ctlconn_cleanup();
3121
		return;
3122
	}
3123
3124
	*reply_text = '\0';
3125
3126
	ctl_reply_size = ctl_reply_offset = 0;
3127
	memset(reply_hdr, '\0', sizeof(*reply_hdr));
3128
3129
	ctl_cmd.cmd = ntohl(ctl_cmd.cmd);
3130
	log_debug("ctlcmd %x logname \"%s\"", ctl_cmd.cmd, ctl_cmd.logname);
3131
3132
	switch (ctl_cmd.cmd) {
3133
	case CMD_READ:
3134
	case CMD_READ_CLEAR:
3135
	case CMD_READ_CONT:
3136
	case CMD_FLAGS:
3137
		f = find_membuf_log(ctl_cmd.logname);
3138
		if (f == NULL) {
3139
			strlcpy(reply_text, "No such log\n", MAX_MEMBUF);
3140
		} else {
3141
			if (ctl_cmd.cmd != CMD_FLAGS) {
3142
				ringbuf_to_string(reply_text, MAX_MEMBUF,
3143
				    f->f_un.f_mb.f_rb);
3144
			}
3145
			if (f->f_un.f_mb.f_overflow)
3146
				flags |= CTL_HDR_FLAG_OVERFLOW;
3147
			if (ctl_cmd.cmd == CMD_READ_CLEAR) {
3148
				ringbuf_clear(f->f_un.f_mb.f_rb);
3149
				f->f_un.f_mb.f_overflow = 0;
3150
			}
3151
			if (ctl_cmd.cmd == CMD_READ_CONT) {
3152
				f->f_un.f_mb.f_attached = 1;
3153
				tailify_replytext(reply_text,
3154
				    ctl_cmd.lines > 0 ? ctl_cmd.lines : 10);
3155
			} else if (ctl_cmd.lines > 0) {
3156
				tailify_replytext(reply_text, ctl_cmd.lines);
3157
			}
3158
		}
3159
		break;
3160
	case CMD_CLEAR:
3161
		f = find_membuf_log(ctl_cmd.logname);
3162
		if (f == NULL) {
3163
			strlcpy(reply_text, "No such log\n", MAX_MEMBUF);
3164
		} else {
3165
			ringbuf_clear(f->f_un.f_mb.f_rb);
3166
			if (f->f_un.f_mb.f_overflow)
3167
				flags |= CTL_HDR_FLAG_OVERFLOW;
3168
			f->f_un.f_mb.f_overflow = 0;
3169
			strlcpy(reply_text, "Log cleared\n", MAX_MEMBUF);
3170
		}
3171
		break;
3172
	case CMD_LIST:
3173
		SIMPLEQ_FOREACH(f, &Files, f_next) {
3174
			if (f->f_type == F_MEMBUF) {
3175
				strlcat(reply_text, f->f_un.f_mb.f_mname,
3176
				    MAX_MEMBUF);
3177
				if (f->f_un.f_mb.f_overflow) {
3178
					strlcat(reply_text, "*", MAX_MEMBUF);
3179
					flags |= CTL_HDR_FLAG_OVERFLOW;
3180
				}
3181
				strlcat(reply_text, " ", MAX_MEMBUF);
3182
			}
3183
		}
3184
		strlcat(reply_text, "\n", MAX_MEMBUF);
3185
		break;
3186
	default:
3187
		log_warnx("unsupported control socket command");
3188
		ctlconn_cleanup();
3189
		return;
3190
	}
3191
	reply_hdr->version = htonl(CTL_VERSION);
3192
	reply_hdr->flags = htonl(flags);
3193
3194
	ctl_reply_size = CTL_REPLY_SIZE;
3195
	log_debug("ctlcmd reply length %lu", (u_long)ctl_reply_size);
3196
3197
	/* Otherwise, set up to write out reply */
3198
	ctl_state = (ctl_cmd.cmd == CMD_READ_CONT) ?
3199
	    CTL_WRITING_CONT_REPLY : CTL_WRITING_REPLY;
3200
3201
	event_add(ev_ctlwrite, NULL);
3202
3203
	/* another syslogc can kick us out */
3204
	if (ctl_state == CTL_WRITING_CONT_REPLY)
3205
		event_add(ev_ctlaccept, NULL);
3206
}
3207
3208
void
3209
ctlconn_writecb(int fd, short event, void *arg)
3210
{
3211
	struct event		*ev = arg;
3212
	ssize_t			 n;
3213
3214
	if (!(ctl_state == CTL_WRITING_REPLY ||
3215
	    ctl_state == CTL_WRITING_CONT_REPLY)) {
3216
		/* Shouldn't be here! */
3217
		log_warnx("control socket write with bad state");
3218
		ctlconn_cleanup();
3219
		return;
3220
	}
3221
3222
 retry:
3223
	n = write(fd, ctl_reply + ctl_reply_offset,
3224
	    ctl_reply_size - ctl_reply_offset);
3225
	switch (n) {
3226
	case -1:
3227
		if (errno == EINTR)
3228
			goto retry;
3229
		if (errno == EWOULDBLOCK)
3230
			return;
3231
		if (errno != EPIPE)
3232
			log_warn("write control socket");
3233
		/* FALLTHROUGH */
3234
	case 0:
3235
		ctlconn_cleanup();
3236
		return;
3237
	default:
3238
		ctl_reply_offset += n;
3239
	}
3240
	if (ctl_reply_offset < ctl_reply_size)
3241
		return;
3242
3243
	if (ctl_state != CTL_WRITING_CONT_REPLY) {
3244
		ctlconn_cleanup();
3245
		return;
3246
	}
3247
3248
	/*
3249
	 * Make space in the buffer for continous writes.
3250
	 * Set offset behind reply header to skip it
3251
	 */
3252
	*reply_text = '\0';
3253
	ctl_reply_offset = ctl_reply_size = CTL_REPLY_SIZE;
3254
3255
	/* Now is a good time to report dropped lines */
3256
	if (membuf_drop) {
3257
		strlcat(reply_text, "<ENOBUFS>\n", MAX_MEMBUF);
3258
		ctl_reply_size = CTL_REPLY_SIZE;
3259
		membuf_drop = 0;
3260
	} else {
3261
		/* Nothing left to write */
3262
		event_del(ev);
3263
	}
3264
}
3265
3266
/* Shorten replytext to number of lines */
3267
void
3268
tailify_replytext(char *replytext, int lines)
3269
{
3270
	char *start, *nl;
3271
	int count = 0;
3272
	start = nl = replytext;
3273
3274
	while ((nl = strchr(nl, '\n')) != NULL) {
3275
		nl++;
3276
		if (++count > lines) {
3277
			start = strchr(start, '\n');
3278
			start++;
3279
		}
3280
	}
3281
	if (start != replytext) {
3282
		int len = strlen(start);
3283
		memmove(replytext, start, len);
3284
		*(replytext + len) = '\0';
3285
	}
3286
}
3287
3288
void
3289
ctlconn_logto(char *line)
3290
{
3291
	size_t l;
3292
3293
	if (membuf_drop)
3294
		return;
3295
3296
	l = strlen(line);
3297
	if (l + 2 > (CTL_REPLY_MAXSIZE - ctl_reply_size)) {
3298
		/* remember line drops for later report */
3299
		membuf_drop = 1;
3300
		return;
3301
	}
3302
	memcpy(ctl_reply + ctl_reply_size, line, l);
3303
	memcpy(ctl_reply + ctl_reply_size + l, "\n", 2);
3304
	ctl_reply_size += l + 1;
3305
	event_add(ev_ctlwrite, NULL);
3306
}