summaryrefslogtreecommitdiffstatsabout
path: root/utility/logparse.c
diff options
context:
space:
mode:
Diffstat (limited to 'utility/logparse.c')
-rw-r--r--utility/logparse.c89
1 files changed, 78 insertions, 11 deletions
diff --git a/utility/logparse.c b/utility/logparse.c
index 4d823ce..e9ca340 100644
--- a/utility/logparse.c
+++ b/utility/logparse.c
@@ -2,16 +2,70 @@
2#include "apr_file_info.h" 2#include "apr_file_info.h"
3#include "apr_file_io.h" 3#include "apr_file_io.h"
4#include "apr_strings.h" 4#include "apr_strings.h"
5#include "apr_time.h"
6
7#include "time.h"
8#include "stdlib.h"
5 9
6#include "util.h" 10#include "util.h"
11#include "ap_pcre.h"
12#include "database.h"
13
7 14
8apr_hash_t *g_parser_funcs; 15apr_hash_t *g_parser_funcs;
9 16
10static apr_status_t parser_func_regexmatch(config_t *cfg, const char *data, 17static apr_status_t parser_func_regexmatch(apr_pool_t *p, config_t *cfg,
11 int argc, const char **argv) 18 config_output_field_t *field, const char *value, char **ret)
12{ 19{
20 struct {
21 ap_regex_t *rx;
22 const char *substr;
23 } *data;
24 ap_regmatch_t regm[AP_MAX_REG_MATCH];
25 // Check if a regular expression configured
26 if (!field->args[0]) return APR_EINVAL;
27 if (!field->data) {
28 // pre compile the regex
29 data = apr_palloc(cfg->pool, sizeof(ap_regex_t)+sizeof(const char *));
30 data->rx = ap_pregcomp(cfg->pool, field->args[0],
31 AP_REG_EXTENDED|AP_REG_ICASE);
32 if (field->args[1]) {
33 data->substr = field->args[1];
34 } else {
35 data->substr = "$1";
36 }
37 if (!data->rx) return APR_EINVAL;
38 field->data = data;
39 } else data = field->data;
40
41 if (!ap_regexec(data->rx, value, AP_MAX_REG_MATCH, regm, 0)) {
42 *ret = ap_pregsub(p, data->substr, value, AP_MAX_REG_MATCH, regm);
43 }
44 //printf("We matched %s against %s to %s\n",value, field->args[0], *ret);
13 return APR_SUCCESS; 45 return APR_SUCCESS;
14} 46}
47
48static apr_status_t parser_func_totimestamp(apr_pool_t *p, config_t *cfg,
49 config_output_field_t *field, const char *value, char **ret)
50{
51 time_t time;
52 struct tm ts;
53
54
55 strptime(value, "%d/%b/%Y:%H:%M:%S %z", &ts);
56 time = mktime(&ts);
57
58 *ret = apr_itoa(p, time);
59 return APR_SUCCESS;
60}
61
62static apr_status_t parser_func_machineid(apr_pool_t *p, config_t *cfg,
63 config_output_field_t *field, const char *value, char **ret)
64{
65 *ret = apr_pstrdup(p,cfg->machineid);
66 return APR_SUCCESS;
67}
68
15parser_func_t parser_get_func(const char *name) 69parser_func_t parser_get_func(const char *name)
16{ 70{
17 return apr_hash_get(g_parser_funcs, name, APR_HASH_KEY_STRING); 71 return apr_hash_get(g_parser_funcs, name, APR_HASH_KEY_STRING);
@@ -29,6 +83,8 @@ static void parser_add_func(apr_pool_t *p, const char *const name,
29void parser_init(apr_pool_t *p) 83void parser_init(apr_pool_t *p)
30{ 84{
31 parser_add_func(p, "regexmatch", parser_func_regexmatch); 85 parser_add_func(p, "regexmatch", parser_func_regexmatch);
86 parser_add_func(p, "totimestamp", parser_func_totimestamp);
87 parser_add_func(p, "machineid", parser_func_machineid);
32} 88}
33 89
34void parser_find_logs(config_t *cfg) 90void parser_find_logs(config_t *cfg)
@@ -212,7 +268,7 @@ apr_status_t parse_logfile(config_t *cfg, const char *filename)
212 line_chomp(buff); 268 line_chomp(buff);
213 269
214 apr_pool_clear(targp); 270 apr_pool_clear(targp);
215 tokenize_logline(buff, &targv, targp, 1); 271 tokenize_logline(buff, &targv, targp, 0);
216 targc = 0; 272 targc = 0;
217 while (targv[targc]) targc++; 273 while (targv[targc]) targc++;
218 /** @todo Run Line Filters here */ 274 /** @todo Run Line Filters here */
@@ -239,6 +295,7 @@ apr_status_t parse_processline(apr_pool_t *ptemp, config_t *cfg, char **argv, in
239 config_output_field_t *ofields; 295 config_output_field_t *ofields;
240 apr_table_t *datain; 296 apr_table_t *datain;
241 apr_table_t *dataout; 297 apr_table_t *dataout;
298 apr_status_t rv;
242 int i; 299 int i;
243 300
244 fmt = apr_hash_get(cfg->log_formats, cfg->logformat, APR_HASH_KEY_STRING); 301 fmt = apr_hash_get(cfg->log_formats, cfg->logformat, APR_HASH_KEY_STRING);
@@ -257,20 +314,30 @@ apr_status_t parse_processline(apr_pool_t *ptemp, config_t *cfg, char **argv, in
257 // Convert input fields to output fields 314 // Convert input fields to output fields
258 ofields = (config_output_field_t *)cfg->output_fields->elts; 315 ofields = (config_output_field_t *)cfg->output_fields->elts;
259 for (i=0; i<cfg->output_fields->nelts; i++) { 316 for (i=0; i<cfg->output_fields->nelts; i++) {
260 const char *t; 317 const char *val;
318 val = apr_table_get(datain, ofields[i].source);
319 // If we can't find the source field just continue
320 if (!val && !(ofields[i].source[0]=='\0' && ofields[i].func)) {
321 apr_table_setn(dataout, ofields[i].field, ofields[i].def);
322 continue;
323 }
261 if (!ofields[i].func) { 324 if (!ofields[i].func) {
262 t = apr_table_get(datain, ofields[i].source); 325 apr_table_setn(dataout,ofields[i].field, val);
263 if (!t) { 326 //printf("S: %s = %s\n",ofields[i].field, val);
264 return APR_EINVAL;
265 }
266 apr_table_setn(dataout,ofields[i].field, t);
267 printf("S: %s = %s\n",ofields[i].source, t);
268 } else { 327 } else {
269 printf("S: %s, F: %p\n",ofields[i].source, ofields[i].func); 328 char *ret = NULL;
329 rv = ((parser_func_t)ofields[i].func)(ptemp, cfg, &ofields[i], val,
330 &ret);
331 if (rv) return rv;
332 apr_table_setn(dataout, ofields[i].field, ret);
333 //printf("S: %s = %s\n",ofields[i].field, ret);
270 } 334 }
271 } 335 }
272 336
273 /** @todo Run Post Filters here */ 337 /** @todo Run Post Filters here */
274 338
339 // Process DB Query
340 rv = database_insert(cfg, ptemp, dataout);
341 if (rv) return rv;
275 return APR_SUCCESS; 342 return APR_SUCCESS;
276} 343}