audit_tool.c
来自「<B>Digital的Unix操作系统VAX 4.2源码</B>」· C语言 代码 · 共 1,802 行 · 第 1/5 页
C
1,802 行
extern char *trustedevent[]; int match = 0; char *eventp; char *hostp; int i, j, k; /* search for a rule which matches current audit record */ for ( i = 0; i < ruleno; i++ ) { /* compare hostname against rules */ if ( RULE(i,host)[0] == '*' ) match = 1; else { hostp = gethost_l(af->ipaddr); for ( j = 0; RULE(i,host)[j] == hostp[j] && hostp[j]; j++ ); if ( RULE(i,host)[j] == '\0' && hostp[j] == '\0' ) match = 1; } /* compare auid, ruid against rules */ if ( match ) match = ((af->auid == RULE(i,auid)) || (RULE(i,auid) == -1)); if ( match ) match = ((af->ruid == RULE(i,ruid)) || (RULE(i,ruid) == -1)); /* compare event against rules */ if ( match ) { match = 0; if ( af->event == SYS_exit && af->login_proc ) eventp = _LOGOUT; else if ( af->event >= 0 && af->event <= NUM_SYSCALLS ) eventp = syscallnames[af->event]; else if ( af->event >= MIN_TRUSTED_EVENT && af->event < MIN_TRUSTED_EVENT + N_TRUSTED_EVENTS ) eventp = trustedevent[af->event-MIN_TRUSTED_EVENT]; else if ( af->event >= MIN_SPECIAL && af->event <= MAX_SPECIAL ) eventp = special_event[af->event-MIN_SPECIAL]; else { if ( af->flag == 0 ) af->flag = 1; return(0); } for ( k = 0; (eventp[k] == RULE(i,event)[k]) && eventp[k]; k++ ); if ( (eventp[k] == '\0' && RULE(i,event)[k] == '\0') || RULE(i,event)[k] == '*' ) match = 1; } /* compare string params against rules; allow '*' wildcard */ if ( match ) { if ( RULE(i,param)[0] == '*' ) match = 1; else for ( match = j = 0; j < af->charp_indx; j++ ) { for ( k = 0; (af->charparam[j][k] == RULE(i,param)[k]) && (k < af->charlen[j]); k++ ); if ( (k == af->charlen[j] && RULE(i,param)[k] == '\0') || RULE(i,param)[k] == '*' ) { match = 1; break; } } } /* compare operation against rules for open()'s (using 1st intparam) */ if ( match && af->event == SYS_open ) match = (af->intparam[0] == RULE(i,oprtn)) || (RULE(i,oprtn) == -1); if ( match ) return ( match ); } return(0);}/* fetch header file and update a_proc structure and state; return sort status */int fetch_hdr ( logfile, start_str, sort )char *logfile;char *start_str; /* user specified start time */int sort; /* 1: check sort status only */ /* 2: update sortflag in hdr */{ char logfilehdr[MAXPATHLEN]; struct a_proc *a_ptr; long start_time; /* start time from hdr file */ long end_time; /* end time from header file */ char nextlog[MAXPATHLEN]; /* next audit log filename */ int fd; int i, j; /* open first logfile header */ for ( i = 0; logfile[i] && i < MAXPATHLEN-5; i++ ); bcopy ( logfile, logfilehdr, i ); if ( strncmp ( &logfilehdr[i-2], ".Z", 2 ) == 0 ) i -= 2; bcopy ( ".hdr\0", &logfilehdr[i], 5 ); if ( (fd = open ( logfilehdr, 2 )) == -1 ) return(0); /* check/update sort status */ if ( sort == 2 ) { write ( fd, &sort, sizeof(int) ); return(0); } read ( fd, &sort_flag, sizeof(sort_flag) ); if ( sort == 1 ) return(sort_flag); /* open file which corresponds to user specified time */ if ( *start_str ) { j = 0; do { read ( fd, &start_time, sizeof(start_time) ); read ( fd, &end_time, sizeof(end_time) ); i = 0; do { read ( fd, &nextlog[i], 1 ); } while ( nextlog[i++] && i < MAXPATHLEN ); if ( start_time == 0 && end_time == 0 ) j = 1; else if ( (match_time ( start_str, start_time ) >= 0) && (match_time ( start_str, end_time ) <= 0) ) j = 1; /* get next logfile hdr */ else { bcopy ( nextlog, logfile, i ); close(fd); bcopy ( logfile, logfilehdr, i ); bcopy ( ".hdr\0", &logfilehdr[i-1], 5 ); if ( (fd = open ( logfilehdr, 0 )) == -1 ) return(0); } } while ( j == 0 ); }#define FETCHIT(obj,indx) \ read ( fd, &indx, sizeof(int) ); \ if ( indx ) { \ obj = aud_mem_op ( indx, (char *)0, 0, 0 ); \ if ( obj ) read ( fd, obj, indx ); \ else lseek ( fd, indx, L_INCR ); \ } /* read state information */ lseek ( fd, (sizeof start_time)*2+(sizeof sort_flag)+MAXPATHLEN, L_SET ); for ( ;; ) { a_ptr = aud_mem_proc ( 1, (struct a_proc *)0, -1, -1, 0 ); if ( a_ptr == (struct a_proc *)-1 ) break; if ( (i = read ( fd, (char *)a_ptr, A_PROC_HDR_SIZ )) != A_PROC_HDR_SIZ ) break; FETCHIT ( a_ptr->cwd, i ); FETCHIT ( a_ptr->root, i ); FETCHIT ( a_ptr->username, i ); for ( i = 0; i < _NFILE; i++ ) { FETCHIT ( a_ptr->fd_nm[i], j ); } } close ( fd ); return(0);}/* fetch records matching stated conditions; return record ptr; update rec_len */char *fetch_matching_rec ( audit_fields, selectn, cnt, flag, rec_len, fd_p )struct audit_fields *audit_fields; /* audit record fields */struct selectn *selectn; /* selection criteria */int *cnt; /* # records processed */int flag; /* misc options */int *rec_len; /* length of record */int *fd_p; /* data file descriptor */{ static char logfile[MAXPATHLEN]; struct stat sbuf; char *rec_ptr; int match; static int get_time = 1; static long time_l; static int cnt_l = 0; /* # records processed in current log */ static int auditd_event = 0; /* auditd audit log event occurred */ int pos1, pos2; int i; /* open auditlog datafile and header; use timestamp if provided */ if ( *fd_p == 0 ) { for ( i = 0; selectn->logfile[i]; i++ ); bcopy ( selectn->logfile, logfile, i+1 ); fetch_hdr ( logfile, selectn->time_start, 0 ); if ( stat ( logfile, &sbuf ) == -1 ) { for ( i = 0; logfile[i]; i++ ); if ( strncmp ( &logfile[i-2], ".Z", 2 ) ) bcopy ( ".Z\0", &logfile[i], 3 ); } compress ( 0, logfile ); if ( (*fd_p = open ( logfile, 0 )) == -1 ) { fprintf ( stderr, "failed to open %s\n", logfile ); return((char *)-1); } cnt_l = 0; if ( flag & FLAG_SORT ) audit_sort ( logfile ); } if ( *fd_p == -1 ) return((char *)-1); /* fetch records until selection criteria satisfied */ do { init_audit_fields ( audit_fields ); rec_ptr = fetch_rec ( fd_p, rec_len, audit_fields, flag&FLAG_FOLLOW, cnt_l ); if ( rec_ptr == (char *)-1 ) { if ( (flag&FLAG_OVERRIDE) == 0 ) compress ( 1, (char *)0 ); return ( (char *)-1 ); } (*cnt)++; cnt_l++; /* allow partial records after auditd event */ if ( auditd_event && audit_fields->flag == 2 ) audit_fields->flag = 0; /* parse data; maintain process state */ parse_rec ( rec_ptr, *rec_len, audit_fields ); state_maint ( audit_fields ); /* find records matching input params; deselect according to ruleset */ match = match_rec ( audit_fields, selectn ); if ( ruleno && match ) match = !deselect ( audit_fields, ruleno ); /* save first timestamp for logfile hdr */ if ( get_time ) { time_l = audit_fields->timeval.tv_sec; get_time = 0; } /* check for auditd change log messages */ if ( (audit_fields->event == AUDIT_LOG_CHANGE) && ((flag&FLAG_OVERRIDE) == 0) ) { pos1 = tell ( *fd_p ); lseek ( *fd_p, 0, L_XTND ); pos2 = tell ( *fd_p ); if ( pos1 == pos2 ) { change_log ( fd_p, logfile, time_l, audit_fields ); if ( flag & FLAG_SORT ) audit_sort ( logfile ); cnt_l = 0; get_time = 1; } else lseek ( *fd_p, pos1, L_SET ); } if ( (audit_fields->event == AUDIT_LOG_CREAT) || (audit_fields->event == AUDIT_LOG_OVERWRITE) || (audit_fields->event == AUDIT_SUSPEND) || (audit_fields->event == AUDIT_SHUTDOWN) || (audit_fields->event == AUDIT_XMIT_FAIL) ) auditd_event = 1; else auditd_event = 0; } while ( match == 0 ); return ( rec_ptr );}/* read audit record; return ptr; modify length */char *fetch_rec ( fd_p, rec_len, af, follow, cnt )int *fd_p; /* audit file descriptor */int *rec_len; /* length of audit record - returned */struct audit_fields *af; /* audit record fields */int follow; /* like tail -f */int cnt; /* # records processed from *fd_p */{ static char buf[AUD_BUF_SIZ]; static int recvr = 0; char rec_len_buf[sizeof *rec_len]; char token; int ptr = 0; int i, j; /* read record length */ do { /* find first LENGTH token */ do { j = read ( *fd_p, &token, sizeof token ); if ( token != T_LENGTH && j == sizeof token ) af->flag = 2; /* attempt recovery of split record */ /* assumes first record is remainder of split record */ if ( recvr && cnt == 0 ) { recvr = 0; if ( recover ( 1, buf, *rec_len, fd_p ) == 0 ) af->flag = 7; return ( buf ); } } while ( ((j == 0) && follow) || ((j > 0) && (token != T_LENGTH)) ); if ( j <= 0 ) return ( (char *)-1 ); bcopy ( &token, buf, sizeof token ); /* read length */ i = 0; do { j = read ( *fd_p, &rec_len_buf[i], 1 ); if ( j ) i++; } while ( ((j == 0) && follow) || ((j > 0) && (i < sizeof *rec_len)) ); bcopy ( rec_len_buf, rec_len, sizeof(int) ); if ( j <= 0 ) return ( (char *)-1 ); if ( (*rec_len < 0) | (*rec_len >= AUD_BUF_SIZ) ) af->flag = 3; } while ( (*rec_len < 0) || (*rec_len >= AUD_BUF_SIZ) ); bcopy ( rec_len, &buf[sizeof token], sizeof *rec_len ); /* read next char into start of data area */ do { j = read ( *fd_p, &buf[sizeof *rec_len + sizeof token], sizeof token ); } while ( (j == 0) && follow ); if ( j <= 0 ) return ( (char *)-1 ); /* if next char was another LENGTH token, read length again */ if ( buf[sizeof *rec_len + sizeof token] == T_LENGTH ) { i = 0; do { j = read ( *fd_p, &rec_len_buf[i], 1 ); if ( j ) i++; } while ( ((j == 0) && follow) || ((j > 0) && (i < sizeof *rec_len)) ); bcopy ( rec_len_buf, rec_len, sizeof(int) ); if ( j <= 0 ) return ( (char *)-1 ); bcopy ( rec_len, &buf[sizeof token], sizeof *rec_len ); } else ptr++; /* read data */ if ( (*rec_len < 0) || (*rec_len >= AUD_BUF_SIZ) ) { af->flag = 4; return ( buf ); }; i = *rec_len - (sizeof *rec_len + sizeof token + ptr); j = 0; do { j += read ( *fd_p, &buf[ptr + sizeof *rec_len + sizeof token + j], i-j ); } while ( (j < i) && follow ); if ( j < i ) return ( (char *)-1 ); /* consistency check */ bcopy ( &buf[*rec_len - (sizeof *rec_len)], &i, sizeof(int) ); if ( i != *rec_len && af->flag != 7 ) { i = recover ( 0, buf, *rec_len, fd_p ); if ( i == AUDIT_LOG_CHANGE ) { af->flag = 8; recvr = 1; } else if ( i == AUDIT_SUSPEND ) af->flag = 9; else if ( i == AUDIT_LOG_CREAT ) af->flag = 9; else if ( i == AUDIT_LOG_OVERWRITE ) af->flag = 9; else if ( i == AUDIT_SHUTDOWN ) af->flag = 9; else if ( i == AUDIT_XMIT_FAIL ) af->flag = 9; else af->flag = 5; *rec_len = 0; } return ( buf );}/* return hostname associated with ipaddr */char *gethost_l ( ipaddr )long ipaddr;{ struct hostent *hostp; static long ipaddr_prev = 0; static char h_name_prev[128]; int i; if ( ipaddr_prev && ipaddr == ipaddr_prev ) return ( h_name_prev ); if ( (hostp = gethostbyaddr ( (char *)&ipaddr, sizeof(long), AF_INET )) == (struct hostent *)0 ) return ( (char *)0 ); /* save hostname, ipaddr for next iteration */ ipaddr_prev = ipaddr; for ( i = 0; hostp->h_name[i]; i++ );
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?