diff options
author | Guy Harris <guy@alum.mit.edu> | 2011-11-15 04:26:38 +0000 |
---|---|---|
committer | Guy Harris <guy@alum.mit.edu> | 2011-11-15 04:26:38 +0000 |
commit | 70a8b27948bbe52d4be3e457b16516058510d7bb (patch) | |
tree | 6a43968c812f1038488954c987a9a36a4b96fd6f /epan/dfilter | |
parent | 91398db56b3244a6eea5993945be6da4ab41844a (diff) |
Get rid of the depth argument to dfilter_macro_apply(); have an internal
routine that does all the work and that takes a depth argumen, and an
external routine that calls that internal routine with a depth argument
of 0. The depth is only of use internally, to avoid infinite recursion.
When recursing with that routine, pass depth+1 as the depth value,
rather than passing depth and incrementing it afterwards; the latter
doesn't prevent infinite recursion. (Thanks and a tip of the hat to
Clang Cat for catching this.)
Squelch some other (harmless) warnings from Clang Cat.
Clean up indentation.
svn path=/trunk/; revision=39838
Diffstat (limited to 'epan/dfilter')
-rw-r--r-- | epan/dfilter/dfilter-macro.c | 230 | ||||
-rw-r--r-- | epan/dfilter/dfilter-macro.h | 2 | ||||
-rw-r--r-- | epan/dfilter/dfilter.c | 2 |
3 files changed, 120 insertions, 114 deletions
diff --git a/epan/dfilter/dfilter-macro.c b/epan/dfilter/dfilter-macro.c index c2699f8dd7..a0933fd692 100644 --- a/epan/dfilter/dfilter-macro.c +++ b/epan/dfilter/dfilter-macro.c @@ -217,7 +217,7 @@ static gchar* dfilter_macro_resolve(gchar* name, gchar** args, const gchar** err } -gchar* dfilter_macro_apply(const gchar* text, guint depth, const gchar** error) { +static gchar* dfilter_macro_apply_recurse(const gchar* text, guint depth, const gchar** error) { enum { OUTSIDE, STARTING, NAME, ARGS } state = OUTSIDE; GString* out; GString* name = NULL; @@ -241,150 +241,156 @@ gchar* dfilter_macro_apply(const gchar* text, guint depth, const gchar** error) if (args) { \ while(args->len) { void* p = g_ptr_array_remove_index_fast(args,0); if (p) g_free(p); } \ g_ptr_array_free(args,TRUE); \ - args = NULL; } } while(0) + args = NULL; \ + } \ + } while(0) - *error = NULL; - out = g_string_sized_new(64); - - while(1) { - c = *r++; - - switch(state) { - case OUTSIDE: { - switch(c) { - case '\0': { - goto finish; - } case '$': { - state = STARTING; - break; - } default: { - g_string_append_c(out,c); - break; - } + *error = NULL; + out = g_string_sized_new(64); + + while(1) { + c = *r++; + + switch(state) { + case OUTSIDE: { + switch(c) { + case '\0': { + goto finish; + } case '$': { + state = STARTING; + break; + } default: { + g_string_append_c(out,c); + break; } - break; - } case STARTING: { - switch (c) { - case '{': { - args = g_ptr_array_new(); - arg = g_string_sized_new(32); - name = g_string_sized_new(32); + } + break; + } case STARTING: { + switch (c) { + case '{': { + args = g_ptr_array_new(); + arg = g_string_sized_new(32); + name = g_string_sized_new(32); - state = NAME; + state = NAME; - break; - } case '\0': { - g_string_append_c(out,'$'); + break; + } case '\0': { + g_string_append_c(out,'$'); - goto finish; - } default: { - g_string_append_c(out,'$'); - g_string_append_c(out,c); + goto finish; + } default: { + g_string_append_c(out,'$'); + g_string_append_c(out,c); - state = OUTSIDE; + state = OUTSIDE; - break; - } + break; } - break; - } case NAME: { - if ( isalnum((int)c) || c == '_' || c == '-' || c == '.' ) { - g_string_append_c(name,c); - } else if ( c == ':') { - state = ARGS; - } else if ( c == '}') { - gchar* resolved; + } + break; + } case NAME: { + if ( isalnum((int)c) || c == '_' || c == '-' || c == '.' ) { + g_string_append_c(name,c); + } else if ( c == ':') { + state = ARGS; + } else if ( c == '}') { + gchar* resolved; - g_ptr_array_add(args,NULL); + g_ptr_array_add(args,NULL); - resolved = dfilter_macro_resolve(name->str, (gchar**)args->pdata, error); - if (*error) goto on_error; + resolved = dfilter_macro_resolve(name->str, (gchar**)args->pdata, error); + if (*error) goto on_error; - changed = TRUE; + changed = TRUE; - g_string_append(out,resolved); + g_string_append(out,resolved); - FREE_ALL(); + FREE_ALL(); - state = OUTSIDE; - } else if ( c == '\0') { + state = OUTSIDE; + } else if ( c == '\0') { + *error = "end of filter in the middle of a macro expression"; + goto on_error; + } else { + *error = "invalid char in macro name"; + goto on_error; + } + break; + } case ARGS: { + switch(c) { + case '\0': { *error = "end of filter in the middle of a macro expression"; goto on_error; - } else { - *error = "invalid char in macro name"; - goto on_error; - } - break; - } case ARGS: { - switch(c) { - case '\0': { - *error = "end of filter in the middle of a macro expression"; - goto on_error; - } case ';': { - g_ptr_array_add(args,arg->str); - g_string_free(arg,FALSE); + } case ';': { + g_ptr_array_add(args,arg->str); + g_string_free(arg,FALSE); - arg = g_string_sized_new(32); - break; - } case '\\': { - c = *r++; - if (c) { - g_string_append_c(arg,c); - break; - } else { - *error = "end of filter in the middle of a macro expression"; - goto on_error; - } - } default: { + arg = g_string_sized_new(32); + break; + } case '\\': { + c = *r++; + if (c) { g_string_append_c(arg,c); break; - } case '}': { - gchar* resolved; - g_ptr_array_add(args,arg->str); - g_ptr_array_add(args,NULL); + } else { + *error = "end of filter in the middle of a macro expression"; + goto on_error; + } + } default: { + g_string_append_c(arg,c); + break; + } case '}': { + gchar* resolved; + g_ptr_array_add(args,arg->str); + g_ptr_array_add(args,NULL); - g_string_free(arg,FALSE); - arg = NULL; + g_string_free(arg,FALSE); + arg = NULL; - resolved = dfilter_macro_resolve(name->str, (gchar**)args->pdata, error); - if (*error) goto on_error; + resolved = dfilter_macro_resolve(name->str, (gchar**)args->pdata, error); + if (*error) goto on_error; - changed = TRUE; + changed = TRUE; - g_string_append(out,resolved); + g_string_append(out,resolved); - FREE_ALL(); + FREE_ALL(); - state = OUTSIDE; - break; - } + state = OUTSIDE; + break; } - break; } + break; } } + } finish: - { - FREE_ALL(); + { + FREE_ALL(); - if (changed) { - gchar* resolved = dfilter_macro_apply(out->str, depth++, error); - g_string_free(out,TRUE); - return (*error) ? NULL : resolved; - } else { - gchar* out_str = ep_strdup(out->str); - g_string_free(out,TRUE); - return out_str; - } - } -on_error: - { - FREE_ALL(); - if (! *error) *error = "unknown error in macro expression"; + if (changed) { + gchar* resolved = dfilter_macro_apply_recurse(out->str, depth + 1, error); g_string_free(out,TRUE); - return NULL; + return (*error) ? NULL : resolved; + } else { + gchar* out_str = ep_strdup(out->str); + g_string_free(out,TRUE); + return out_str; } + } +on_error: + { + FREE_ALL(); + if (! *error) *error = "unknown error in macro expression"; + g_string_free(out,TRUE); + return NULL; + } +} + +gchar* dfilter_macro_apply(const gchar* text, const gchar** error) { + return dfilter_macro_apply_recurse(text, 0, error); } static void macro_update(void* mp, const gchar** error) { @@ -429,7 +435,7 @@ static void macro_update(void* mp, const gchar** error) { *(w++) = *(r++); break; case '\0': - *(w++) = *(r++); + *w = *r; goto done; case '\\': *(w++) = *(++r); diff --git a/epan/dfilter/dfilter-macro.h b/epan/dfilter/dfilter-macro.h index 9646570d7b..5e06aada38 100644 --- a/epan/dfilter/dfilter-macro.h +++ b/epan/dfilter/dfilter-macro.h @@ -48,7 +48,7 @@ void dfilter_macro_save(const gchar*, gchar**); void dfilter_macro_dump(void); /* applies all macros to the given text and returns the resulting string or NULL on failure */ -gchar* dfilter_macro_apply(const gchar* text, guint depth, const gchar** error); +gchar* dfilter_macro_apply(const gchar* text, const gchar** error); void dfilter_macro_init(void); diff --git a/epan/dfilter/dfilter.c b/epan/dfilter/dfilter.c index 143693123d..668d8191ad 100644 --- a/epan/dfilter/dfilter.c +++ b/epan/dfilter/dfilter.c @@ -230,7 +230,7 @@ dfilter_compile(const gchar *text, dfilter_t **dfp) dfilter_error_msg = NULL; - if ( !( text = dfilter_macro_apply(text, 0, &dfilter_error_msg) ) ) { + if ( !( text = dfilter_macro_apply(text, &dfilter_error_msg) ) ) { return FALSE; } |