summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorStef Walter <stef@memberwebs.com>2006-03-11 19:38:11 +0000
committerStef Walter <stef@memberwebs.com>2006-03-11 19:38:11 +0000
commit5f88ca4b71e02bfba1c708d6ca54cc720020dfa7 (patch)
tree6994fc45ebe34cae9ba91ead39085f6e191443c1
parent002625eac4f169cbcc36887075b10786c181835c (diff)
Regular expression pattern matching and replacements
-rw-r--r--src/bsnmp-regex.c120
1 files changed, 110 insertions, 10 deletions
diff --git a/src/bsnmp-regex.c b/src/bsnmp-regex.c
index 93b9ac2..72b12b2 100644
--- a/src/bsnmp-regex.c
+++ b/src/bsnmp-regex.c
@@ -123,7 +123,114 @@ strtrim (char* data)
}
/* -----------------------------------------------------------------------------
- * LOG READING AND MATCHING
+ * MATCHING
+ */
+
+static int
+process_match (struct data_entry *data, char *result)
+{
+fprintf (stderr, "match for %s: %s\n", data->descr, result ? result : "MATCH");
+ return 0;
+}
+
+static char*
+process_result (struct data_entry *data, char *line, int len,
+ int *ovector, int substrings)
+{
+ char *result;
+ char *p, *t;
+ int rlen, l;
+ int idx;
+
+ /* Some nice little optimizations */
+ if (!data->result)
+ return NULL;
+ if (strchr (data->result, '\\') == NULL)
+ return strdup (data->result);
+
+ /* Figure out the string length */
+ rlen = strlen (data->result) + 1;
+ for (p = data->result; *p; p++) {
+ if(p[0] == '\\') {
+ p++;
+ if(p[0] == '\\' || !isdigit(p[0]))
+ continue;
+ idx = p[0] - '0';
+ ASSERT (idx >= 0 && idx <= 9);
+ if (idx < substrings) {
+ ASSERT (ovector[(idx * 2) + 1] >= ovector[idx * 2]);
+ ASSERT (ovector[(idx * 2) + 1] < len);
+ ASSERT (ovector[idx * 2] < len);
+ rlen += (ovector[(idx * 2) + 1]) - (ovector[idx * 2]);
+ rlen += 1;
+ }
+ }
+ }
+
+ result = (char*)calloc(rlen, 1);
+ if (!result) {
+ emsg ("out of memory");
+ return NULL;
+ }
+
+ for (p = data->result, t = result; *p; p++) {
+ if (p[0] == '\\') {
+ p++;
+ if (isdigit(p[0])) {
+ idx = p[0] - '0';
+ if (idx < substrings) {
+ l = (ovector[(idx * 2) + 1]) - (ovector[idx * 2]);
+ memcpy (t, line + (ovector[idx * 2]), l);
+ t += l;
+ }
+ continue;
+ }
+ }
+
+ *t++ = *p;
+ }
+
+ *t = 0;
+ return result;
+}
+
+static void
+process_log (char *line, int len)
+{
+ struct data_entry *data;
+ int ovector[30];
+ char *result;
+ int r;
+
+ for (data = TAILQ_FIRST (&entries); data;
+ data = TAILQ_NEXT (data, link)) {
+
+ memset (ovector, 0, sizeof (ovector));
+ result = NULL;
+
+ r = pcre_exec (data->regex, data->extra, line, len, 0,
+ PCRE_NOTEMPTY | PCRE_NO_UTF8_CHECK, ovector, 30);
+
+ if (r == PCRE_ERROR_NOMATCH)
+ continue;
+ else if (r == PCRE_ERROR_NOMEMORY) {
+ emsg ("out of memory");
+ return;
+ } else if (r < 0) {
+ emsg ("internal error in matching code: %d", r);
+ return;
+ }
+
+ result = process_result (data, line, len, ovector, r);
+ process_match (data, result);
+ free (result);
+ }
+
+ fprintf (stderr, "log line: %s\n", line);
+}
+
+/* -----------------------------------------------------------------------------
+ * LOG READING
*/
static void
@@ -143,12 +250,6 @@ close_fifo ()
}
static void
-process_log (char *line)
-{
- fprintf (stderr, "log line: %s\n", line);
-}
-
-static void
receive_log (int fd, void *data)
{
char *t;
@@ -187,12 +288,12 @@ receive_log (int fd, void *data)
*t = 0;
if (line_buffer != t && *(t - 1) == '\r')
*(t - 1) = 0;
+ l = (t + 1) - line_buffer;
/* Send it off */
- process_log (line_buffer);
+ process_log (line_buffer, l);
/* Move data to front of buffer */
- l = (t + 1) - line_buffer;
ASSERT (l <= len);
memmove (line_buffer, t + 1, (len - l) + 1);
len -= l;
@@ -730,7 +831,6 @@ module_fini (void)
close_fifo ();
config_free_all ();
-
return 0;
}