auditd.c revision 161863
1/*
2 * Copyright (c) 2004 Apple Computer, Inc.
3 * All rights reserved.
4 *
5 * @APPLE_BSD_LICENSE_HEADER_START@
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 *
11 * 1.  Redistributions of source code must retain the above copyright
12 *     notice, this list of conditions and the following disclaimer.
13 * 2.  Redistributions in binary form must reproduce the above copyright
14 *     notice, this list of conditions and the following disclaimer in the
15 *     documentation and/or other materials provided with the distribution.
16 * 3.  Neither the name of Apple Computer, Inc. ("Apple") nor the names of
17 *     its contributors may be used to endorse or promote products derived
18 *     from this software without specific prior written permission.
19 *
20 * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
21 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
22 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
23 * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
24 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
25 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
26 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
27 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
29 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30 *
31 * @APPLE_BSD_LICENSE_HEADER_END@
32 *
33 * $P4: //depot/projects/trustedbsd/openbsm/bin/auditd/auditd.c#18 $
34 */
35
36#include <sys/types.h>
37#include <sys/dirent.h>
38#include <sys/mman.h>
39#include <sys/queue.h>
40#include <sys/stat.h>
41#include <sys/wait.h>
42
43#include <bsm/audit.h>
44#include <bsm/audit_uevents.h>
45#include <bsm/libbsm.h>
46
47#include <err.h>
48#include <errno.h>
49#include <fcntl.h>
50#include <grp.h>
51#include <stdio.h>
52#include <stdlib.h>
53#include <time.h>
54#include <unistd.h>
55#include <signal.h>
56#include <string.h>
57#include <syslog.h>
58
59#include "auditd.h"
60
61#define	NA_EVENT_STR_SIZE	25
62
63static int	 ret, minval;
64static char	*lastfile = NULL;
65static int	 allhardcount = 0;
66static int	 triggerfd = 0;
67static int	 sigchlds, sigchlds_handled;
68static int	 sighups, sighups_handled;
69static int	 sigterms, sigterms_handled;
70static long	 global_flags;
71
72static TAILQ_HEAD(, dir_ent)	dir_q;
73
74static int	config_audit_controls(void);
75
76/*
77 * Error starting auditd
78 */
79static void
80fail_exit(void)
81{
82
83	audit_warn_nostart();
84	exit(1);
85}
86
87/*
88 * Free our local list of directory names.
89 */
90static void
91free_dir_q(void)
92{
93	struct dir_ent *dirent;
94
95	while ((dirent = TAILQ_FIRST(&dir_q))) {
96		TAILQ_REMOVE(&dir_q, dirent, dirs);
97		free(dirent->dirname);
98		free(dirent);
99	}
100}
101
102/*
103 * Generate the timestamp string.
104 */
105static int
106getTSstr(char *buf, int len)
107{
108	struct timeval ts;
109	struct timezone tzp;
110	time_t tt;
111
112	if (gettimeofday(&ts, &tzp) != 0)
113		return (-1);
114	tt = (time_t)ts.tv_sec;
115	if (!strftime(buf, len, "%Y%m%d%H%M%S", gmtime(&tt)))
116		return (-1);
117	return (0);
118}
119
120/*
121 * Concat the directory name to the given file name.
122 * XXX We should affix the hostname also
123 */
124static char *
125affixdir(char *name, struct dir_ent *dirent)
126{
127	char *fn;
128	char *curdir;
129	const char *sep = "/";
130
131	curdir = dirent->dirname;
132	syslog(LOG_DEBUG, "dir = %s", dirent->dirname);
133
134	fn = malloc(strlen(curdir) + strlen(sep) + (2 * POSTFIX_LEN) + 1);
135	if (fn == NULL)
136		return (NULL);
137	strcpy(fn, curdir);
138	strcat(fn, sep);
139	strcat(fn, name);
140	return (fn);
141}
142
143/*
144 * Close the previous audit trail file.
145 */
146static int
147close_lastfile(char *TS)
148{
149	char *ptr;
150	char *oldname;
151
152	if (lastfile != NULL) {
153		oldname = (char *)malloc(strlen(lastfile) + 1);
154		if (oldname == NULL)
155			return (-1);
156		strcpy(oldname, lastfile);
157
158		/* Rename the last file -- append timestamp. */
159		if ((ptr = strstr(lastfile, NOT_TERMINATED)) != NULL) {
160			*ptr = '.';
161			strcpy(ptr+1, TS);
162			if (rename(oldname, lastfile) != 0)
163				syslog(LOG_ERR, "Could not rename %s to %s",
164				    oldname, lastfile);
165			else
166				syslog(LOG_INFO, "renamed %s to %s",
167				    oldname, lastfile);
168		}
169		free(lastfile);
170		free(oldname);
171		lastfile = NULL;
172	}
173	return (0);
174}
175
176/*
177 * Create the new audit file with appropriate permissions and ownership.  Try
178 * to clean up if something goes wrong.
179 */
180static int
181#ifdef AUDIT_REVIEW_GROUP
182open_trail(const char *fname, uid_t uid, gid_t gid)
183#else
184open_trail(const char *fname)
185#endif
186{
187	int error, fd;
188
189	fd = open(fname, O_RDONLY | O_CREAT, S_IRUSR | S_IRGRP);
190	if (fd < 0)
191		return (-1);
192#ifdef AUDIT_REVIEW_GROUP
193	if (fchown(fd, uid, gid) < 0) {
194		error = errno;
195		close(fd);
196		(void)unlink(fname);
197		errno = error;
198		return (-1);
199	}
200#endif
201	return (fd);
202}
203
204/*
205 * Create the new file name, swap with existing audit file.
206 */
207static int
208swap_audit_file(void)
209{
210	char timestr[2 * POSTFIX_LEN];
211	char *fn;
212	char TS[POSTFIX_LEN];
213	struct dir_ent *dirent;
214#ifdef AUDIT_REVIEW_GROUP
215	struct group *grp;
216	gid_t gid;
217	uid_t uid;
218#endif
219	int error, fd;
220
221	if (getTSstr(TS, POSTFIX_LEN) != 0)
222		return (-1);
223
224	strcpy(timestr, TS);
225	strcat(timestr, NOT_TERMINATED);
226
227#ifdef AUDIT_REVIEW_GROUP
228	/*
229	 * XXXRW: Currently, this code falls back to the daemon gid, which is
230	 * likely the wheel group.  Is there a better way to deal with this?
231	 */
232	grp = getgrnam(AUDIT_REVIEW_GROUP);
233	if (grp == NULL) {
234		syslog(LOG_INFO,
235		    "Audit review group '%s' not available, using daemon gid",
236		    AUDIT_REVIEW_GROUP);
237		gid = -1;
238	} else
239		gid = grp->gr_gid;
240	uid = getuid();
241#endif
242
243	/* Try until we succeed. */
244	while ((dirent = TAILQ_FIRST(&dir_q))) {
245		if ((fn = affixdir(timestr, dirent)) == NULL) {
246			syslog(LOG_INFO, "Failed to swap log at time %s",
247				timestr);
248			return (-1);
249		}
250
251		/*
252		 * Create and open the file; then close and pass to the
253		 * kernel if all went well.
254		 */
255		syslog(LOG_INFO, "New audit file is %s", fn);
256#ifdef AUDIT_REVIEW_GROUP
257		fd = open_trail(fn, uid, gid);
258#else
259		fd = open_trail(fn);
260#endif
261		if (fd < 0)
262			warn("open(%s)", fn);
263		if (fd >= 0) {
264			error = auditctl(fn);
265			if (error) {
266				syslog(LOG_ERR,
267				    "auditctl failed setting log file! : %s",
268				    strerror(errno));
269				close(fd);
270			} else {
271				/* Success. */
272				close_lastfile(TS);
273				lastfile = fn;
274				close(fd);
275				return (0);
276			}
277		}
278
279		/*
280		 * Tell the administrator about lack of permissions for dir.
281		 */
282		audit_warn_getacdir(dirent->dirname);
283
284		/* Try again with a different directory. */
285		TAILQ_REMOVE(&dir_q, dirent, dirs);
286		free(dirent->dirname);
287		free(dirent);
288	}
289	syslog(LOG_ERR, "Log directories exhausted\n");
290	return (-1);
291}
292
293/*
294 * Read the audit_control file contents.
295 */
296static int
297read_control_file(void)
298{
299	char cur_dir[MAXNAMLEN];
300	struct dir_ent *dirent;
301	au_qctrl_t qctrl;
302
303	/*
304	 * Clear old values.  Force a re-read of the file the next time.
305	 */
306	free_dir_q();
307	endac();
308
309	/*
310	 * Read the list of directories into a local linked list.
311	 *
312	 * XXX We should use the reentrant interfaces once they are
313	 * available.
314	 */
315	while (getacdir(cur_dir, MAXNAMLEN) >= 0) {
316		dirent = (struct dir_ent *) malloc(sizeof(struct dir_ent));
317		if (dirent == NULL)
318			return (-1);
319		dirent->softlim = 0;
320		dirent->dirname = (char *) malloc(MAXNAMLEN);
321		if (dirent->dirname == NULL) {
322			free(dirent);
323			return (-1);
324		}
325		strcpy(dirent->dirname, cur_dir);
326		TAILQ_INSERT_TAIL(&dir_q, dirent, dirs);
327	}
328
329	allhardcount = 0;
330	if (swap_audit_file() == -1) {
331		syslog(LOG_ERR, "Could not swap audit file");
332		/*
333		 * XXX Faulty directory listing? - user should be given
334		 * XXX an opportunity to change the audit_control file
335		 * XXX switch to a reduced mode of auditing?
336		 */
337		return (-1);
338	}
339
340	/*
341	 * XXX There are synchronization problems here
342 	 * XXX what should we do if a trigger for the earlier limit
343	 * XXX is generated here?
344	 */
345	if (0 == (ret = getacmin(&minval))) {
346		syslog(LOG_DEBUG, "min free = %d\n", minval);
347		if (auditon(A_GETQCTRL, &qctrl, sizeof(qctrl)) != 0) {
348			syslog(LOG_ERR,
349			    "could not get audit queue settings");
350				return (-1);
351		}
352		qctrl.aq_minfree = minval;
353		if (auditon(A_SETQCTRL, &qctrl, sizeof(qctrl)) != 0) {
354			syslog(LOG_ERR,
355			    "could not set audit queue settings");
356			return (-1);
357		}
358	}
359
360	return (0);
361}
362
363/*
364 * Close all log files, control files, and tell the audit system.
365 */
366static int
367close_all(void)
368{
369	struct auditinfo ai;
370	int err_ret = 0;
371	char TS[POSTFIX_LEN];
372	int aufd;
373	token_t *tok;
374	long cond;
375
376	/* Generate an audit record. */
377	if ((aufd = au_open()) == -1)
378		syslog(LOG_ERR, "Could not create audit shutdown event.");
379	else {
380		if ((tok = au_to_text("auditd::Audit shutdown")) != NULL)
381			au_write(aufd, tok);
382		/*
383		 * XXX we need to implement extended subject tokens so we can
384		 * effectively represent terminal lines with this token type.
385		 */
386		bzero(&ai, sizeof(ai));
387		if ((tok = au_to_subject32(getuid(), geteuid(), getegid(),
388		    getuid(), getgid(), getpid(), getpid(), &ai.ai_termid))
389		    != NULL)
390			au_write(aufd, tok);
391		if ((tok = au_to_return32(0, 0)) != NULL)
392			au_write(aufd, tok);
393		if (au_close(aufd, 1, AUE_audit_shutdown) == -1)
394			syslog(LOG_ERR,
395			    "Could not close audit shutdown event.");
396	}
397
398	/* Flush contents. */
399	cond = AUC_DISABLED;
400	err_ret = auditon(A_SETCOND, &cond, sizeof(cond));
401	if (err_ret != 0) {
402		syslog(LOG_ERR, "Disabling audit failed! : %s",
403		    strerror(errno));
404		err_ret = 1;
405	}
406	if (getTSstr(TS, POSTFIX_LEN) == 0)
407		close_lastfile(TS);
408	if (lastfile != NULL)
409		free(lastfile);
410
411	free_dir_q();
412	if ((remove(AUDITD_PIDFILE) == -1) || err_ret) {
413		syslog(LOG_ERR, "Could not unregister");
414		audit_warn_postsigterm();
415		return (1);
416	}
417	endac();
418
419	if (close(triggerfd) != 0)
420		syslog(LOG_ERR, "Error closing control file");
421	syslog(LOG_INFO, "Finished");
422	return (0);
423}
424
425/*
426 * When we get a signal, we are often not at a clean point.  So, little can
427 * be done in the signal handler itself.  Instead,  we send a message to the
428 * main servicing loop to do proper handling from a non-signal-handler
429 * context.
430 */
431static void
432relay_signal(int signal)
433{
434
435	if (signal == SIGHUP)
436		sighups++;
437	if (signal == SIGTERM)
438		sigterms++;
439	if (signal == SIGCHLD)
440		sigchlds++;
441}
442
443/*
444 * Registering the daemon.
445 */
446static int
447register_daemon(void)
448{
449	FILE * pidfile;
450	int fd;
451	pid_t pid;
452
453	/* Set up the signal hander. */
454	if (signal(SIGTERM, relay_signal) == SIG_ERR) {
455		syslog(LOG_ERR,
456		    "Could not set signal handler for SIGTERM");
457		fail_exit();
458	}
459	if (signal(SIGCHLD, relay_signal) == SIG_ERR) {
460		syslog(LOG_ERR,
461		    "Could not set signal handler for SIGCHLD");
462		fail_exit();
463	}
464	if (signal(SIGHUP, relay_signal) == SIG_ERR) {
465		syslog(LOG_ERR,
466		    "Could not set signal handler for SIGHUP");
467		fail_exit();
468	}
469
470	if ((pidfile = fopen(AUDITD_PIDFILE, "a")) == NULL) {
471		syslog(LOG_ERR, "Could not open PID file");
472		audit_warn_tmpfile();
473		return (-1);
474	}
475
476	/* Attempt to lock the pid file; if a lock is present, exit. */
477	fd = fileno(pidfile);
478	if (flock(fd, LOCK_EX | LOCK_NB) < 0) {
479		syslog(LOG_ERR,
480		    "PID file is locked (is another auditd running?).");
481		audit_warn_ebusy();
482		return (-1);
483	}
484
485	pid = getpid();
486	ftruncate(fd, 0);
487	if (fprintf(pidfile, "%u\n", pid) < 0) {
488		/* Should not start the daemon. */
489		fail_exit();
490	}
491
492	fflush(pidfile);
493	return (0);
494}
495
496/*
497 * Suppress duplicate messages within a 30 second interval.   This should be
498 * enough to time to rotate log files without thrashing from soft warnings
499 * generated before the log is actually rotated.
500 */
501#define	DUPLICATE_INTERVAL	30
502static void
503handle_audit_trigger(int trigger)
504{
505	static int last_trigger;
506	static time_t last_time;
507	struct dir_ent *dirent;
508
509	/*
510	 * Suppres duplicate messages from the kernel within the specified
511	 * interval.
512	 */
513	struct timeval ts;
514	struct timezone tzp;
515	time_t tt;
516
517	if (gettimeofday(&ts, &tzp) == 0) {
518		tt = (time_t)ts.tv_sec;
519		if ((trigger == last_trigger) &&
520		    (tt < (last_time + DUPLICATE_INTERVAL)))
521			return;
522		last_trigger = trigger;
523		last_time = tt;
524	}
525
526	/*
527	 * Message processing is done here.
528 	 */
529	dirent = TAILQ_FIRST(&dir_q);
530	switch(trigger) {
531
532	case AUDIT_TRIGGER_LOW_SPACE:
533		syslog(LOG_INFO, "Got low space trigger");
534		if (dirent && (dirent->softlim != 1)) {
535			TAILQ_REMOVE(&dir_q, dirent, dirs);
536				/* Add this node to the end of the list. */
537				TAILQ_INSERT_TAIL(&dir_q, dirent, dirs);
538				audit_warn_soft(dirent->dirname);
539				dirent->softlim = 1;
540
541			if (TAILQ_NEXT(TAILQ_FIRST(&dir_q), dirs) != NULL &&
542			    swap_audit_file() == -1)
543				syslog(LOG_ERR, "Error swapping audit file");
544
545			/*
546			 * Check if the next dir has already reached its soft
547			 * limit.
548			 */
549			dirent = TAILQ_FIRST(&dir_q);
550			if (dirent->softlim == 1)  {
551				/* All dirs have reached their soft limit. */
552				audit_warn_allsoft();
553			}
554		} else {
555			/*
556			 * Continue auditing to the current file.  Also
557			 * generate  an allsoft warning.
558			 * XXX do we want to do this ?
559			 */
560			audit_warn_allsoft();
561		}
562		break;
563
564	case AUDIT_TRIGGER_NO_SPACE:
565		syslog(LOG_INFO, "Got no space trigger");
566
567		/* Delete current dir, go on to next. */
568		TAILQ_REMOVE(&dir_q, dirent, dirs);
569		audit_warn_hard(dirent->dirname);
570		free(dirent->dirname);
571		free(dirent);
572
573		if (swap_audit_file() == -1)
574			syslog(LOG_ERR, "Error swapping audit file");
575
576		/* We are out of log directories. */
577		audit_warn_allhard(++allhardcount);
578		break;
579
580	case AUDIT_TRIGGER_OPEN_NEW:
581		/*
582		 * Create a new file and swap with the one being used in
583		 * kernel
584		 */
585		syslog(LOG_INFO, "Got open new trigger");
586		if (swap_audit_file() == -1)
587			syslog(LOG_ERR, "Error swapping audit file");
588		break;
589
590	case AUDIT_TRIGGER_READ_FILE:
591		syslog(LOG_INFO, "Got read file trigger");
592		if (read_control_file() == -1)
593			syslog(LOG_ERR, "Error in audit control file");
594		if (config_audit_controls() == -1)
595			syslog(LOG_ERR, "Error setting audit controls");
596		break;
597
598	default:
599		syslog(LOG_ERR, "Got unknown trigger %d", trigger);
600		break;
601	}
602}
603
604static void
605handle_sighup(void)
606{
607
608	sighups_handled = sighups;
609	config_audit_controls();
610}
611
612/*
613 * Reap our children.
614 */
615static void
616reap_children(void)
617{
618	pid_t child;
619	int wstatus;
620
621	while ((child = waitpid(-1, &wstatus, WNOHANG)) > 0) {
622		if (!wstatus)
623			continue;
624		syslog(LOG_INFO, "warn process [pid=%d] %s %d.", child,
625		    ((WIFEXITED(wstatus)) ? "exited with non-zero status" :
626		    "exited as a result of signal"),
627		    ((WIFEXITED(wstatus)) ? WEXITSTATUS(wstatus) :
628		    WTERMSIG(wstatus)));
629	}
630}
631
632static void
633handle_sigchld(void)
634{
635
636	sigchlds_handled = sigchlds;
637	reap_children();
638}
639
640/*
641 * Read the control file for triggers/signals and handle appropriately.
642 */
643static int
644wait_for_events(void)
645{
646	int num;
647	unsigned int trigger;
648
649	for (;;) {
650		num = read(triggerfd, &trigger, sizeof(trigger));
651		if ((num == -1) && (errno != EINTR)) {
652			syslog(LOG_ERR, "%s: error %d", __FUNCTION__, errno);
653			return (-1);
654		}
655		if (sigterms != sigterms_handled) {
656			syslog(LOG_DEBUG, "%s: SIGTERM", __FUNCTION__);
657			break;
658		}
659		if (sigchlds != sigchlds_handled) {
660			syslog(LOG_DEBUG, "%s: SIGCHLD", __FUNCTION__);
661			handle_sigchld();
662		}
663		if (sighups != sighups_handled) {
664			syslog(LOG_DEBUG, "%s: SIGHUP", __FUNCTION__);
665			handle_sighup();
666		}
667		if ((num == -1) && (errno == EINTR))
668			continue;
669		if (num == 0) {
670			syslog(LOG_ERR, "%s: read EOF", __FUNCTION__);
671			return (-1);
672		}
673		syslog(LOG_DEBUG, "%s: read %d", __FUNCTION__, trigger);
674		if (trigger == AUDIT_TRIGGER_CLOSE_AND_DIE)
675			break;
676		else
677			handle_audit_trigger(trigger);
678	}
679	return (close_all());
680}
681
682/*
683 * Configure the audit controls in the kernel: the event to class mapping,
684 * kernel preselection mask, etc.
685 */
686static int
687config_audit_controls(void)
688{
689	au_event_ent_t ev, *evp;
690	au_evclass_map_t evc_map;
691	au_mask_t aumask;
692	int ctr = 0;
693	char naeventstr[NA_EVENT_STR_SIZE];
694
695	/*
696	 * Process the audit event file, obtaining a class mapping for each
697	 * event, and send that mapping into the kernel.
698	 * XXX There's a risk here that the BSM library will return NULL
699	 * for an event when it can't properly map it to a class. In that
700	 * case, we will not process any events beyond the one that failed,
701	 * but should. We need a way to get a count of the events.
702	*/
703	ev.ae_name = (char *)malloc(AU_EVENT_NAME_MAX);
704	ev.ae_desc = (char *)malloc(AU_EVENT_DESC_MAX);
705	if ((ev.ae_name == NULL) || (ev.ae_desc == NULL)) {
706		syslog(LOG_ERR,
707		    "Memory allocation error when configuring audit controls.");
708		return (-1);
709	}
710	evp = &ev;
711	setauevent();
712	while ((evp = getauevent_r(evp)) != NULL) {
713		evc_map.ec_number = evp->ae_number;
714		evc_map.ec_class = evp->ae_class;
715		if (auditon(A_SETCLASS, &evc_map, sizeof(au_evclass_map_t))
716		    != 0)
717			syslog(LOG_ERR,
718				"Failed to register class mapping for event %s",
719				 evp->ae_name);
720		else
721			ctr++;
722	}
723	endauevent();
724	free(ev.ae_name);
725	free(ev.ae_desc);
726	if (ctr == 0)
727		syslog(LOG_ERR, "No events to class mappings registered.");
728	else
729		syslog(LOG_DEBUG, "Registered %d event to class mappings.",
730		    ctr);
731
732	/*
733	 * Get the non-attributable event string and set the kernel mask from
734	 * that.
735	 */
736	if ((getacna(naeventstr, NA_EVENT_STR_SIZE) == 0) &&
737	    (getauditflagsbin(naeventstr, &aumask) == 0)) {
738		if (auditon(A_SETKMASK, &aumask, sizeof(au_mask_t)))
739			syslog(LOG_ERR,
740			    "Failed to register non-attributable event mask.");
741		else
742			syslog(LOG_DEBUG,
743			    "Registered non-attributable event mask.");
744	} else
745		syslog(LOG_ERR,
746		    "Failed to obtain non-attributable event mask.");
747
748	/*
749	 * Set the audit policy flags based on passed in parameter values.
750	 */
751	if (auditon(A_SETPOLICY, &global_flags, sizeof(global_flags)))
752		syslog(LOG_ERR, "Failed to set audit policy.");
753
754	return (0);
755}
756
757static void
758setup(void)
759{
760	struct auditinfo ai;
761	auditinfo_t auinfo;
762	int aufd;
763	token_t *tok;
764
765	if ((triggerfd = open(AUDIT_TRIGGER_FILE, O_RDONLY, 0)) < 0) {
766		syslog(LOG_ERR, "Error opening trigger file");
767		fail_exit();
768	}
769
770	/*
771	 * To provide event feedback cycles and avoid auditd becoming
772	 * stalled if auditing is suspended, auditd and its children run
773	 * without their events being audited.  We allow the uid, tid, and
774	 * mask fields to be implicitly set to zero, but do set the pid.  We
775	 * run this after opening the trigger device to avoid configuring
776	 * audit state without audit present in the system.
777	 *
778	 * XXXRW: Is there more to it than this?
779	 */
780	bzero(&auinfo, sizeof(auinfo));
781	auinfo.ai_asid = getpid();
782	if (setaudit(&auinfo) == -1) {
783		syslog(LOG_ERR, "Error setting audit stat");
784		fail_exit();
785	}
786
787	TAILQ_INIT(&dir_q);
788	if (read_control_file() == -1) {
789		syslog(LOG_ERR, "Error reading control file");
790		fail_exit();
791	}
792
793	/* Generate an audit record. */
794	if ((aufd = au_open()) == -1)
795		syslog(LOG_ERR, "Could not create audit startup event.");
796	else {
797		/*
798		 * XXXCSJP Perhaps we wan't more robust audit records for
799		 * audit start up and shutdown. This might include capturing
800		 * failures to initialize the audit subsystem?
801		 */
802		bzero(&ai, sizeof(ai));
803		if ((tok = au_to_subject32(getuid(), geteuid(), getegid(),
804		    getuid(), getgid(), getpid(), getpid(), &ai.ai_termid))
805		    != NULL)
806			au_write(aufd, tok);
807		if ((tok = au_to_text("auditd::Audit startup")) != NULL)
808			au_write(aufd, tok);
809		if ((tok = au_to_return32(0, 0)) != NULL)
810			au_write(aufd, tok);
811		if (au_close(aufd, 1, AUE_audit_startup) == -1)
812			syslog(LOG_ERR,
813			    "Could not close audit startup event.");
814	}
815
816	if (config_audit_controls() == 0)
817		syslog(LOG_INFO, "Audit controls init successful");
818	else
819		syslog(LOG_ERR, "Audit controls init failed");
820}
821
822int
823main(int argc, char **argv)
824{
825	int ch;
826	int debug = 0;
827	int rc;
828
829	global_flags |= AUDIT_CNT;
830	while ((ch = getopt(argc, argv, "dhs")) != -1) {
831		switch(ch) {
832		case 'd':
833			/* Debug option. */
834			debug = 1;
835			break;
836
837		case 's':
838			/* Fail-stop option. */
839			global_flags &= ~(AUDIT_CNT);
840			break;
841
842		case 'h':
843			/* Halt-stop option. */
844			global_flags |= AUDIT_AHLT;
845			break;
846
847		case '?':
848		default:
849			(void)fprintf(stderr,
850			    "usage: auditd [-h | -s] [-d] \n");
851			exit(1);
852		}
853	}
854
855#ifdef LOG_SECURITY
856	openlog("auditd", LOG_CONS | LOG_PID, LOG_SECURITY);
857#else
858	openlog("auditd", LOG_CONS | LOG_PID, LOG_AUTH);
859#endif
860	syslog(LOG_INFO, "starting...");
861
862	if (debug == 0 && daemon(0, 0) == -1) {
863		syslog(LOG_ERR, "Failed to daemonize");
864		exit(1);
865	}
866
867	if (register_daemon() == -1) {
868		syslog(LOG_ERR, "Could not register as daemon");
869		exit(1);
870	}
871
872	setup();
873
874	rc = wait_for_events();
875	syslog(LOG_INFO, "auditd exiting.");
876
877	exit(rc);
878}
879