aboutsummaryrefslogtreecommitdiffstats
path: root/file.c
diff options
context:
space:
mode:
authorStig Bjørlykke <stig@bjorlykke.org>2016-02-16 22:34:12 +0100
committerStig Bjørlykke <stig@bjorlykke.org>2016-02-18 08:06:46 +0000
commit30d83e089c2f0b5d5d67892c6fc581ba9ce0a0a5 (patch)
treed746f24099cf6bdf108e9f64fc1aaf8df5bdd8fc /file.c
parentb77ffb9d36a9405943dadce3d4849c1106b2e361 (diff)
Qt: Add regex support in Find Packet
Add support for using regular expressions in the Search Frame when searching in packet list, packet details and packet bytes. This search is in many cases faster than plain string search. Change-Id: I2d8a709046f90d7b278fb39547fc4e2e420623bc Reviewed-on: https://code.wireshark.org/review/13981 Petri-Dish: Stig Bjørlykke <stig@bjorlykke.org> Tested-by: Petri Dish Buildbot <buildbot-no-reply@wireshark.org> Reviewed-by: Stig Bjørlykke <stig@bjorlykke.org>
Diffstat (limited to 'file.c')
-rw-r--r--file.c103
1 files changed, 73 insertions, 30 deletions
diff --git a/file.c b/file.c
index f576cb8d25..10290dd2c8 100644
--- a/file.c
+++ b/file.c
@@ -118,6 +118,8 @@ static match_result match_wide(capture_file *cf, frame_data *fdata,
void *criterion);
static match_result match_binary(capture_file *cf, frame_data *fdata,
void *criterion);
+static match_result match_regex(capture_file *cf, frame_data *fdata,
+ void *criterion);
static match_result match_dfilter(capture_file *cf, frame_data *fdata,
void *criterion);
static match_result match_marked(capture_file *cf, frame_data *fdata,
@@ -2896,22 +2898,30 @@ match_subtree_text(proto_node *node, gpointer data)
proto_item_fill_label(fi, label_str);
}
- /* Does that label match? */
- label_len = strlen(label_ptr);
- for (i = 0; i < label_len; i++) {
- c_char = label_ptr[i];
- if (cf->case_type)
- c_char = g_ascii_toupper(c_char);
- if (c_char == string[c_match]) {
- c_match++;
- if (c_match == string_len) {
- /* No need to look further; we have a match */
- mdata->frame_matched = TRUE;
- mdata->finfo = fi;
- return;
- }
- } else
- c_match = 0;
+ if (cf->regex) {
+ if (g_regex_match(cf->regex, label_ptr, (GRegexMatchFlags) 0, NULL)) {
+ mdata->frame_matched = TRUE;
+ mdata->finfo = fi;
+ return;
+ }
+ } else {
+ /* Does that label match? */
+ label_len = strlen(label_ptr);
+ for (i = 0; i < label_len; i++) {
+ c_char = label_ptr[i];
+ if (cf->case_type)
+ c_char = g_ascii_toupper(c_char);
+ if (c_char == string[c_match]) {
+ c_match++;
+ if (c_match == string_len) {
+ /* No need to look further; we have a match */
+ mdata->frame_matched = TRUE;
+ mdata->finfo = fi;
+ return;
+ }
+ } else
+ c_match = 0;
+ }
}
/* Recurse into the subtree, if it exists */
@@ -2963,18 +2973,25 @@ match_summary_line(capture_file *cf, frame_data *fdata, void *criterion)
/* Found it. See if we match. */
info_column = edt.pi.cinfo->columns[colx].col_data;
info_column_len = strlen(info_column);
- for (i = 0; i < info_column_len; i++) {
- c_char = info_column[i];
- if (cf->case_type)
- c_char = g_ascii_toupper(c_char);
- if (c_char == string[c_match]) {
- c_match++;
- if (c_match == string_len) {
- result = MR_MATCHED;
- break;
- }
- } else
- c_match = 0;
+ if (cf->regex) {
+ if (g_regex_match(cf->regex, info_column, (GRegexMatchFlags) 0, NULL)) {
+ result = MR_MATCHED;
+ break;
+ }
+ } else {
+ for (i = 0; i < info_column_len; i++) {
+ c_char = info_column[i];
+ if (cf->case_type)
+ c_char = g_ascii_toupper(c_char);
+ if (c_char == string[c_match]) {
+ c_match++;
+ if (c_match == string_len) {
+ result = MR_MATCHED;
+ break;
+ }
+ } else
+ c_match = 0;
+ }
}
break;
}
@@ -3008,8 +3025,11 @@ cf_find_packet_data(capture_file *cf, const guint8 *string, size_t string_size,
info.data = string;
info.data_len = string_size;
- /* String or hex search? */
- if (cf->string) {
+ /* Regex, String or hex search? */
+ if (cf->regex) {
+ /* Regular Expression search */
+ return find_packet(cf, match_regex, NULL, dir);
+ } else if (cf->string) {
/* String search - what type of string? */
switch (cf->scs_type) {
@@ -3214,6 +3234,29 @@ match_binary(capture_file *cf, frame_data *fdata, void *criterion)
return result;
}
+static match_result
+match_regex(capture_file *cf, frame_data *fdata, void *criterion _U_)
+{
+ match_result result = MR_NOTMATCHED;
+ GMatchInfo *match_info = NULL;
+
+ /* Load the frame's data. */
+ if (!cf_read_record(cf, fdata)) {
+ /* Attempt to get the packet failed. */
+ return MR_ERROR;
+ }
+
+ if (g_regex_match_full(cf->regex, ws_buffer_start_ptr(&cf->buf), fdata->cap_len,
+ 0, (GRegexMatchFlags) 0, &match_info, NULL))
+ {
+ gint start_pos = 0, end_pos = 0;
+ g_match_info_fetch_pos (match_info, 0, &start_pos, &end_pos);
+ cf->search_pos = end_pos; /* TODO: use start_pos to show correct length for regex */
+ result = MR_MATCHED;
+ }
+ return result;
+}
+
gboolean
cf_find_packet_dfilter(capture_file *cf, dfilter_t *sfcode,
search_direction dir)