Imported Upstream version 2.5.1
[ossec-hids.git] / src / shared / read-alert.c
1 /* @(#) $Id$ */
2
3 /* Copyright (C) 2009 Trend Micro Inc.
4  * All right reserved.
5  *
6  * This program is a free software; you can redistribute it
7  * and/or modify it under the terms of the GNU General Public
8  * License (version 2) as published by the FSF - Free Software
9  * Foundation
10  *
11  * License details at the LICENSE file included with OSSEC or
12  * online at: http://www.ossec.net/en/licensing.html
13  */
14
15
16 /* File monitoring functions */
17
18 #include "shared.h"
19 #include "read-alert.h"
20
21
22 /* ** Alert xyz: email active-response ** */
23
24 #define ALERT_BEGIN     "** Alert"
25 #define ALERT_BEGIN_SZ  8
26 #define RULE_BEGIN      "Rule: "
27 #define RULE_BEGIN_SZ   6
28 #define SRCIP_BEGIN     "Src IP: "
29 #define SRCIP_BEGIN_SZ  8
30 #define USER_BEGIN      "User: "
31 #define USER_BEGIN_SZ   6
32 #define ALERT_MAIL      "mail"
33 #define ALERT_MAIL_SZ   4
34 #define ALERT_AR        "active-response"
35
36
37 /** void FreeAlertData(alert_data *al_data)
38  * Free alert data.
39  */
40 void FreeAlertData(alert_data *al_data)
41 {
42     if(al_data->date)
43     {
44         free(al_data->date);
45     }
46     if(al_data->location)
47     {
48         free(al_data->location);
49     }
50     if(al_data->comment)
51     {
52         free(al_data->comment);
53     }
54     if(al_data->group)
55     {
56         free(al_data->group);
57     }
58     if(al_data->srcip)
59     {
60         free(al_data->srcip);
61     }
62     if(al_data->user)
63     {
64         free(al_data->user);
65     }
66     if(al_data->log)
67     {
68         while(*(al_data->log))
69         {
70             free(*(al_data->log));
71             al_data->log++;
72         }
73     }
74     free(al_data);
75     al_data = NULL;
76 }
77
78
79 /** alert_data *GetAlertData(FILE *fp)
80  * Returns alert data for the file specified
81  */
82 alert_data *GetAlertData(int flag, FILE *fp)
83 {
84     int _r = 0, log_size;
85     char *p;
86
87     char *date = NULL;
88     char *comment = NULL;
89     char *location = NULL;
90     char *srcip = NULL;
91     char *user = NULL;
92     char *group = NULL;
93     char **log = NULL;
94     int level, rule;
95     
96     char str[OS_BUFFER_SIZE+1];
97     str[OS_BUFFER_SIZE]='\0';
98
99
100     while(fgets(str, OS_BUFFER_SIZE, fp) != NULL)
101     {
102         
103         /* Enf of alert */
104         if(strcmp(str, "\n") == 0)
105         {
106             /* Found in here */
107             if(_r == 2)
108             {
109                 alert_data *al_data;
110                 os_calloc(1, sizeof(alert_data), al_data);
111                 al_data->level = level;
112                 al_data->rule = rule;
113                 al_data->location = location;
114                 al_data->comment = comment;
115                 al_data->group = group;
116                 al_data->log = log;
117                 al_data->srcip = srcip;
118                 al_data->user = user;
119                 al_data->date = date;
120                
121                 return(al_data);
122             }
123             _r = 0;
124         }
125         
126         
127         /* Checking for the header */
128         if(strncmp(ALERT_BEGIN, str, ALERT_BEGIN_SZ) == 0)
129         {
130             p = str + ALERT_BEGIN_SZ + 1;
131             
132             /* Searching for email flag */
133             p = strchr(p, ' ');
134             if(!p)
135             {
136                 continue;
137             }
138
139             p++;
140         
141         
142             /* Checking for the flags */    
143             if((flag & CRALERT_MAIL_SET) && 
144                (strncmp(ALERT_MAIL, p, ALERT_MAIL_SZ) != 0))
145             {
146                 continue;
147             }
148
149             p = strchr(p, '-');
150             if(p)
151             {
152                 p++;
153                 os_strdup(p, group);
154
155                 /* Cleaning new line from group */
156                 os_clearnl(group, p);
157             }
158
159
160             /* Searching for active-response flag */
161             _r = 1;
162             continue;
163         }
164
165         if(_r < 1)
166             continue;
167             
168             
169         /*** Extract information from the event ***/
170         
171         /* r1 means: 2006 Apr 13 16:15:17 /var/log/auth.log */
172         if(_r == 1)
173         {
174             /* Clear new line */
175             os_clearnl(str, p);
176              
177             p = strchr(str, ':');
178             if(p)
179             {
180                 p = strchr(p, ' ');
181                 if(p)
182                 {
183                     *p = '\0';
184                     p++;
185                 }
186                 else
187                 {
188                     /* If p is null it is because strchr failed */
189                     merror("ZZZ: 1() Merror date or location not NULL");
190                     _r = 0;
191                     goto l_error;
192                 }
193             }
194
195
196             /* If not, str is date and p is the location */
197             if(date || location)
198                 merror("ZZZ Merror date or location not NULL");
199             
200             os_strdup(str, date);
201             os_strdup(p, location);    
202             _r = 2;
203             log_size = 0;
204             continue;
205         }
206
207         
208         else if(_r == 2)
209         {
210             /* Rule begin */
211             if(strncmp(RULE_BEGIN, str, RULE_BEGIN_SZ) == 0)
212             {
213                 os_clearnl(str,p);
214                 
215                 p = str + RULE_BEGIN_SZ;
216                 rule = atoi(p);
217
218                 p = strchr(p, ' ');
219                 if(p)
220                 {
221                     p++;
222                     p = strchr(p, ' ');
223                     if(p)
224                         p++;
225                 }
226
227                 if(!p)
228                     goto l_error;
229                 
230                 level = atoi(p);
231                 
232                 /* Getting the comment */
233                 p = strchr(p, '\'');
234                 if(!p)
235                     goto l_error;
236                 
237                 p++;
238                 os_strdup(p, comment);
239                 
240                 /* Must have the closing \' */
241                 p = strrchr(comment, '\'');
242                 if(p)
243                 {
244                     *p = '\0';
245                 }
246                 else
247                 {
248                     goto l_error;
249                 }
250             }
251             
252             /* srcip */
253             else if(strncmp(SRCIP_BEGIN, str, SRCIP_BEGIN_SZ) == 0)
254             {
255                 os_clearnl(str,p);
256                 
257                 p = str + SRCIP_BEGIN_SZ;
258                 os_strdup(p, srcip);
259             }
260             /* username */
261             else if(strncmp(USER_BEGIN, str, USER_BEGIN_SZ) == 0)
262             {
263                 os_clearnl(str,p);
264                 
265                 p = str + USER_BEGIN_SZ;
266                 os_strdup(p, user);
267             }
268             /* It is a log message */
269             else if(log_size < 20)
270             {
271                 os_clearnl(str,p);
272                 
273                 os_realloc(log, (log_size +2)*sizeof(char *), log);
274                 os_strdup(str, log[log_size]); 
275                 log_size++;
276                 log[log_size] = NULL;
277             }
278         }
279
280         continue;
281         l_error:
282         
283         /* Freeing the memory */
284         _r = 0;
285         if(date)
286         {
287             free(date);
288             date = NULL;
289         }
290         if(location)
291         {
292             free(location);
293             location = NULL;
294         }
295         if(comment)
296         {
297             free(comment);
298             comment = NULL;
299         }
300         if(srcip)
301         {
302             free(srcip);
303             srcip = NULL;
304         }
305         if(user)
306         {
307             free(user);
308             user = NULL;
309         }
310         if(group)
311         {
312             free(group);
313             group = NULL;
314         }
315         while(log_size > 0)
316         {
317             log_size--;
318             if(log[log_size])
319             {
320                 free(log[log_size]);
321                 log[log_size] = NULL;
322             }
323         }
324     }
325
326     /* We need to clean end of file before returning */
327     clearerr(fp);
328     return(NULL);
329 }
330
331
332 /* EOF */