1 /* Copyright (C) 2009 Trend Micro Inc.
4 * This program is a free software; you can redistribute it
5 * and/or modify it under the terms of the GNU General Public
6 * License (version 2) as published by the FSF - Free Software
11 #include "logcollector.h"
16 /* Compile message from cache and send through queue */
17 static void audit_send_msg(char **cache, int top, const char *file, int drop_it) {
21 char message[OS_MAXSTR];
23 for (i = 0; i < top; i++) {
26 if (n + z + 1 < OS_MAXSTR) {
30 strncpy(message + n, cache[i], z);
40 if (SendMSG(logr_queue, message, file, LOCALFILE_MQ) < 0) {
41 merror(QUEUE_SEND, ARGV0);
43 if ((logr_queue = StartMQ(DEFAULTQPATH, WRITE)) < 0) {
44 ErrorExit(QUEUE_FATAL, ARGV0, DEFAULTQPATH);
50 void *read_audit(int pos, int *rc, int drop_it) {
51 char *cache[MAX_CACHE];
52 char header[MAX_HEADER] = { '\0' };
54 char buffer[OS_MAXSTR];
58 long offset = ftell(logff[pos].fp);
61 merror(FTELL_ERROR, ARGV0, logff[pos].file, errno, strerror(errno));
67 while (fgets(buffer, OS_MAXSTR, logff[pos].fp)) {
68 if ((p = strchr(buffer, '\n')))
71 if (strlen(buffer) == OS_MAXSTR - 1) {
72 // Message too large, discard line
73 while (fgets(buffer, OS_MAXSTR, logff[pos].fp) && !strchr(buffer, '\n'));
75 debug1("%s: Message not complete. Trying again: '%s'", ARGV0, buffer);
77 if (fseek(logff[pos].fp, offset, SEEK_SET) < 0) {
78 merror(FSEEK_ERROR, ARGV0, logff[pos].file, errno, strerror(errno));
86 // Extract header: "type=\.* msg=audit(\d+.\d+:\d+):"
88 if (strncmp(buffer, "type=", 5) || !((id = strstr(buffer + 5, "msg=audit(")) && (p = strstr(id += 10, "): ")))) {
89 merror("%s: ERROR: discarding audit message because of invalid syntax", ARGV0);
95 if (strncmp(id, header, z)) {
96 // Current message belongs to another event: send cached messages
98 audit_send_msg(cache, icache, logff[pos].file, drop_it);
100 // Store current event
101 *cache = strdup(buffer);
103 strncpy(header, id, z < MAX_HEADER ? z : MAX_HEADER - 1);
105 // The header is the same: store
106 if (icache == MAX_CACHE)
107 merror("%s: ERROR: discarding audit message because cache is full", ARGV0);
109 cache[icache++] = strdup(buffer);
114 audit_send_msg(cache, icache, logff[pos].file, drop_it);