Deleted Added
sdiff udiff text old ( 186647 ) new ( 189279 )
full compact
1/*-
2 * Copyright (c) 2004,2009 Apple Inc.
3 * Copyright (c) 2006 Robert N. M. Watson
4 * All rights reserved.
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
8 * are met:
9 * 1. Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.

--- 11 unchanged lines hidden (view full) ---

22 * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
23 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
24 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
25 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
26 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
27 * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
28 * POSSIBILITY OF SUCH DAMAGE.
29 *
30 * $P4: //depot/projects/trustedbsd/openbsm/libbsm/bsm_control.c#28 $
31 */
32
33#include <config/config.h>
34
35#include <bsm/libbsm.h>
36
37#include <ctype.h>
38#include <errno.h>
39#include <string.h>
40#ifdef HAVE_PTHREAD_MUTEX_LOCK
41#include <pthread.h>
42#endif
43#include <stdio.h>
44#include <stdlib.h>
45

--- 15 unchanged lines hidden (view full) ---

61static char inacdir = 0;
62static char ptrmoved = 0;
63
64#ifdef HAVE_PTHREAD_MUTEX_LOCK
65static pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
66#endif
67
68/*
69 * Audit policy string token table for au_poltostr() and au_strtopol().
70 */
71struct audit_polstr {
72 long ap_policy;
73 const char *ap_str;
74};
75
76static struct audit_polstr au_polstr[] = {
77 { AUDIT_CNT, "cnt" },
78 { AUDIT_AHLT, "ahlt" },
79 { AUDIT_ARGV, "argv" },
80 { AUDIT_ARGE, "arge" },
81 { AUDIT_SEQ, "seq" },
82 { AUDIT_WINDATA, "windata" },
83 { AUDIT_USER, "user" },
84 { AUDIT_GROUP, "group" },
85 { AUDIT_TRAIL, "trail" },
86 { AUDIT_PATH, "path" },
87 { AUDIT_SCNT, "scnt" },
88 { AUDIT_PUBLIC, "public" },
89 { AUDIT_ZONENAME, "zonename" },
90 { AUDIT_PERZONE, "perzone" },
91 { -1, NULL }
92};
93
94/*
95 * Returns the string value corresponding to the given label from the
96 * configuration file.
97 *
98 * Must be called with mutex held.
99 */
100static int
101getstrfromtype_locked(char *name, char **str)
102{

--- 31 unchanged lines hidden (view full) ---

134 }
135 return (0); /* Success */
136 }
137 }
138 }
139}
140
141/*
142 * Convert a given time value with a multiplier (seconds, hours, days, years) to
143 * seconds. Return 0 on success.
144 */
145static int
146au_timetosec(time_t *seconds, u_long value, char mult)
147{
148 if (NULL == seconds)
149 return (-1);
150
151 switch(mult) {
152 case 's':
153 /* seconds */
154 *seconds = (time_t)value;
155 break;
156
157 case 'h':
158 /* hours */
159 *seconds = (time_t)value * 60 * 60;
160 break;
161
162 case 'd':
163 /* days */
164 *seconds = (time_t)value * 60 * 60 * 24;
165 break;
166
167 case 'y':
168 /* years. Add a day for each 4th (leap) year. */
169 *seconds = (time_t)value * 60 * 60 * 24 * 364 +
170 ((time_t)value / 4) * 60 * 60 * 24;
171 break;
172
173 default:
174 return (-1);
175 }
176 return (0);
177}
178
179/*
180 * Convert a given disk space value with a multiplier (bytes, kilobytes,
181 * megabytes, gigabytes) to bytes. Return 0 on success.
182 */
183static int
184au_spacetobytes(size_t *bytes, u_long value, char mult)
185{
186 if (NULL == bytes)
187 return (-1);
188
189 switch(mult) {
190 case 'B':
191 case ' ':
192 /* Bytes */
193 *bytes = (size_t)value;
194 break;
195
196 case 'K':
197 /* Kilobytes */
198 *bytes = (size_t)value * 1024;
199 break;
200
201 case 'M':
202 /* Megabytes */
203 *bytes = (size_t)value * 1024 * 1024;
204 break;
205
206 case 'G':
207 /* Gigabytes */
208 *bytes = (size_t)value * 1024 * 1024 * 1024;
209 break;
210
211 default:
212 return (-1);
213 }
214 return (0);
215}
216
217/*
218 * Convert a policy to a string. Return -1 on failure, or >= 0 representing
219 * the actual size of the string placed in the buffer (excluding terminating
220 * nul).
221 */
222ssize_t
223au_poltostr(long policy, size_t maxsize, char *buf)
224{
225 int first = 1;
226 int i = 0;
227
228 if (maxsize < 1)
229 return (-1);
230 buf[0] = '\0';
231
232 do {
233 if (policy & au_polstr[i].ap_policy) {
234 if (!first && strlcat(buf, ",", maxsize) >= maxsize)
235 return (-1);
236 if (strlcat(buf, au_polstr[i].ap_str, maxsize) >=
237 maxsize)
238 return (-1);
239 first = 0;
240 }
241 } while (NULL != au_polstr[++i].ap_str);
242
243 return (strlen(buf));
244}
245
246/*
247 * Convert a string to a policy. Return -1 on failure (with errno EINVAL,
248 * ENOMEM) or 0 on success.
249 */
250int
251au_strtopol(const char *polstr, long *policy)
252{
253 char *bufp, *string;
254 char *buffer;
255 int i, matched;
256
257 *policy = 0;
258 buffer = strdup(polstr);
259 if (buffer == NULL)
260 return (-1);
261
262 bufp = buffer;
263 while ((string = strsep(&bufp, ",")) != NULL) {
264 matched = i = 0;
265
266 do {
267 if (strcmp(string, au_polstr[i].ap_str) == 0) {
268 *policy |= au_polstr[i].ap_policy;
269 matched = 1;
270 break;
271 }
272 } while (NULL != au_polstr[++i].ap_str);
273
274 if (!matched) {
275 free(buffer);
276 errno = EINVAL;
277 return (-1);
278 }
279 }
280 free(buffer);
281 return (0);
282}

--- 122 unchanged lines hidden (view full) ---

405}
406
407/*
408 * Return the desired trail rotation size from the audit control file.
409 */
410int
411getacfilesz(size_t *filesz_val)
412{
413 char *str;
414 size_t val;
415 char mult;
416 int nparsed;
417
418#ifdef HAVE_PTHREAD_MUTEX_LOCK
419 pthread_mutex_lock(&mutex);
420#endif
421 setac_locked();
422 if (getstrfromtype_locked(FILESZ_CONTROL_ENTRY, &str) < 0) {
423#ifdef HAVE_PTHREAD_MUTEX_LOCK
424 pthread_mutex_unlock(&mutex);
425#endif
426 return (-2);
427 }
428 if (str == NULL) {
429#ifdef HAVE_PTHREAD_MUTEX_LOCK
430 pthread_mutex_unlock(&mutex);
431#endif
432 errno = EINVAL;
433 return (1);
434 }
435
436 /* Trim off any leading white space. */
437 while (*str == ' ' || *str == '\t')
438 str++;
439
440 nparsed = sscanf(str, "%ju%c", (uintmax_t *)&val, &mult);
441
442 switch (nparsed) {
443 case 1:
444 /* If no multiplier then assume 'B' (bytes). */
445 mult = 'B';
446 /* fall through */
447 case 2:
448 if (au_spacetobytes(filesz_val, val, mult) == 0)
449 break;
450 /* fall through */
451 default:
452 errno = EINVAL;
453#ifdef HAVE_PTHREAD_MUTEX_LOCK
454 pthread_mutex_unlock(&mutex);
455#endif
456 return (-1);
457 }
458
459 /*
460 * The file size must either be 0 or >= MIN_AUDIT_FILE_SIZE. 0
461 * indicates no rotation size.
462 */
463 if (*filesz_val < 0 || (*filesz_val > 0 &&
464 *filesz_val < MIN_AUDIT_FILE_SIZE)) {
465#ifdef HAVE_PTHREAD_MUTEX_LOCK
466 pthread_mutex_unlock(&mutex);
467#endif
468 filesz_val = 0L;
469 errno = EINVAL;
470 return (-1);
471 }
472#ifdef HAVE_PTHREAD_MUTEX_LOCK
473 pthread_mutex_unlock(&mutex);
474#endif
475 return (0);
476}
477
478/*
479 * Return the system audit value from the audit contol file.

--- 128 unchanged lines hidden (view full) ---

608 return (1);
609 }
610 if (strlen(str) >= len) {
611#ifdef HAVE_PTHREAD_MUTEX_LOCK
612 pthread_mutex_unlock(&mutex);
613#endif
614 return (-3);
615 }
616 strlcpy(auditstr, str, len);
617#ifdef HAVE_PTHREAD_MUTEX_LOCK
618 pthread_mutex_unlock(&mutex);
619#endif
620 return (0);
621}
622
623/*
624 * Set expiration conditions.
625 */
626static int
627setexpirecond(time_t *age, size_t *size, u_long value, char mult)
628{
629
630 if (isupper(mult) || ' ' == mult)
631 return (au_spacetobytes(size, value, mult));
632 else
633 return (au_timetosec(age, value, mult));
634}
635
636/*
637 * Return the expire-after field from the audit control file.
638 */
639int
640getacexpire(int *andflg, time_t *age, size_t *size)
641{
642 char *str;
643 int nparsed;
644 u_long val1, val2;
645 char mult1, mult2;
646 char andor[AU_LINE_MAX];
647
648 *age = 0L;
649 *size = 0LL;
650 *andflg = 0;
651
652#ifdef HAVE_PTHREAD_MUTEX_LOCK
653 pthread_mutex_lock(&mutex);
654#endif
655 setac_locked();
656 if (getstrfromtype_locked(EXPIRE_AFTER_CONTROL_ENTRY, &str) < 0) {
657#ifdef HAVE_PTHREAD_MUTEX_LOCK
658 pthread_mutex_unlock(&mutex);
659#endif
660 return (-2);
661 }
662 if (str == NULL) {
663#ifdef HAVE_PTHREAD_MUTEX_LOCK
664 pthread_mutex_unlock(&mutex);
665#endif
666 return (1);
667 }
668
669 /* First, trim off any leading white space. */
670 while (*str == ' ' || *str == '\t')
671 str++;
672
673 nparsed = sscanf(str, "%lu%c%[ \tadnorADNOR]%lu%c", &val1, &mult1,
674 andor, &val2, &mult2);
675
676 switch (nparsed) {
677 case 1:
678 /* If no multiplier then assume 'B' (Bytes). */
679 mult1 = 'B';
680 /* fall through */
681 case 2:
682 /* One expiration condition. */
683 if (setexpirecond(age, size, val1, mult1) != 0) {
684#ifdef HAVE_PTHREAD_MUTEX_LOCK
685 pthread_mutex_unlock(&mutex);
686#endif
687 return (-1);
688 }
689 break;
690
691 case 5:
692 /* Two expiration conditions. */
693 if (setexpirecond(age, size, val1, mult1) != 0 ||
694 setexpirecond(age, size, val2, mult2) != 0) {
695#ifdef HAVE_PTHREAD_MUTEX_LOCK
696 pthread_mutex_unlock(&mutex);
697#endif
698 return (-1);
699 }
700 if (strcasestr(andor, "and") != NULL)
701 *andflg = 1;
702 else if (strcasestr(andor, "or") != NULL)
703 *andflg = 0;
704 else {
705#ifdef HAVE_PTHREAD_MUTEX_LOCK
706 pthread_mutex_unlock(&mutex);
707#endif
708 return (-1);
709 }
710 break;
711
712 default:
713#ifdef HAVE_PTHREAD_MUTEX_LOCK
714 pthread_mutex_unlock(&mutex);
715#endif
716 return (-1);
717 }
718
719#ifdef HAVE_PTHREAD_MUTEX_LOCK
720 pthread_mutex_unlock(&mutex);
721#endif
722 return (0);
723}