Fix filter for "Next Packet in Conversation"

The "Previous/Next Packet in Conversation" actions accidentally
overwrites more specific filters (like TCP port matching) by less
specific ones (like IP addresses). This resulted in strange behavior
where packets from different TCP streams were selected.

Change-Id: Ifa93064e1db3777fa3c12e2220bbb0b36b9478fe
Reported-by: Christian Landström
Reviewed-on: https://code.wireshark.org/review/22274
Reviewed-by: Pascal Quantin <pascal.quantin@gmail.com>
Reviewed-by: Peter Wu <peter@lekensteyn.nl>
This commit is contained in:
Peter Wu 2017-06-20 14:08:39 -04:00
parent e6883c15ac
commit 4deb97f31f
5 changed files with 32 additions and 76 deletions

View File

@ -148,6 +148,7 @@ libwireshark.so.0 libwireshark0 #MINVER#
conv_filter_list@Base 2.0.0
conversation_add_proto_data@Base 1.9.1
conversation_delete_proto_data@Base 1.9.1
conversation_filter_from_packet@Base 2.2.8
conversation_get_dissector@Base 2.0.0
conversation_get_proto_data@Base 1.9.1
conversation_new@Base 1.9.1

View File

@ -73,6 +73,24 @@ void conversation_filters_cleanup(void)
g_list_free(conv_filter_list);
}
gchar *conversation_filter_from_packet(struct _packet_info *pinfo)
{
const char *layers[] = { "tcp", "udp", "ip", "ipv6", "eth" };
conversation_filter_t *conv_filter;
gchar *filter;
size_t i;
for (i = 0; i < G_N_ELEMENTS(layers); i++) {
conv_filter = find_conversation_filter(layers[i]);
if (conv_filter && conv_filter->is_filter_valid(pinfo)) {
if ((filter = conv_filter->build_filter_string(pinfo)) != NULL)
return filter;
}
}
return NULL;
}
/*
* Editor modelines - http://www.wireshark.org/tools/modelines.html
*

View File

@ -49,6 +49,15 @@ WS_DLL_PUBLIC struct conversation_filter_s* find_conversation_filter(const char
/* Cleanup internal structures */
extern void conversation_filters_cleanup(void);
/**
* Tries to build a suitable display filter for the conversation in the current
* packet. More specific matches are tried first (like TCP ports) followed by
* less specific ones (IP addresses). NULL is returned when no filter is found.
*
* The returned filter should be freed with g_free.
*/
WS_DLL_PUBLIC gchar *conversation_filter_from_packet(struct _packet_info *pinfo);
/*** THE FOLLOWING SHOULD NOT BE USED BY ANY DISSECTORS!!! ***/
typedef struct conversation_filter_s {

View File

@ -206,29 +206,7 @@ colorize_conversation_cb(conversation_filter_t* color_filter, int action_num)
* or through an accelerator key. Try to build a conversation
* filter in the order TCP, UDP, IP, Ethernet and apply the
* coloring */
color_filter = find_conversation_filter("tcp");
if ((color_filter != NULL) && (color_filter->is_filter_valid(pi)))
filter = color_filter->build_filter_string(pi);
if (filter == NULL) {
color_filter = find_conversation_filter("udp");
if ((color_filter != NULL) && (color_filter->is_filter_valid(pi)))
filter = color_filter->build_filter_string(pi);
}
if (filter == NULL) {
color_filter = find_conversation_filter("ip");
if ((color_filter != NULL) && (color_filter->is_filter_valid(pi)))
filter = color_filter->build_filter_string(pi);
}
if (filter == NULL) {
color_filter = find_conversation_filter("ipv6");
if ((color_filter != NULL) && (color_filter->is_filter_valid(pi)))
filter = color_filter->build_filter_string(pi);
}
if (filter == NULL) {
color_filter = find_conversation_filter("eth");
if ((color_filter != NULL) && (color_filter->is_filter_valid(pi)))
filter = color_filter->build_filter_string(pi);
}
filter = conversation_filter_from_packet(pi);
if( filter == NULL ) {
simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, "Unable to build conversation filter.");
return;
@ -260,24 +238,11 @@ goto_conversation_frame(gboolean dir)
dfilter_t *dfcode = NULL;
gboolean found_packet = FALSE;
packet_info *pi = &cfile.edt->pi;
conversation_filter_t* conv_filter;
/* Try to build a conversation
* filter in the order TCP, UDP, IP, Ethernet and apply the
* coloring */
conv_filter = find_conversation_filter("tcp");
if ((conv_filter != NULL) && (conv_filter->is_filter_valid(pi)))
filter = conv_filter->build_filter_string(pi);
conv_filter = find_conversation_filter("udp");
if ((conv_filter != NULL) && (conv_filter->is_filter_valid(pi)))
filter = conv_filter->build_filter_string(pi);
conv_filter = find_conversation_filter("ip");
if ((conv_filter != NULL) && (conv_filter->is_filter_valid(pi)))
filter = conv_filter->build_filter_string(pi);
conv_filter = find_conversation_filter("ipv6");
if ((conv_filter != NULL) && (conv_filter->is_filter_valid(pi)))
filter = conv_filter->build_filter_string(pi);
filter = conversation_filter_from_packet(pi);
if( filter == NULL ) {
statusbar_push_temporary_msg("Unable to build conversation filter.");
g_free(filter);

View File

@ -2505,31 +2505,7 @@ void MainWindow::colorizeConversation(bool create_rule)
if (capture_file_.capFile() && capture_file_.capFile()->current_frame) {
packet_info *pi = capture_file_.packetInfo();
guint8 cc_num = colorize_action->data().toUInt();
gchar *filter = NULL;
const conversation_filter_t *color_filter = find_conversation_filter("tcp");
if ((color_filter != NULL) && (color_filter->is_filter_valid(pi)))
filter = color_filter->build_filter_string(pi);
if (filter == NULL) {
color_filter = find_conversation_filter("udp");
if ((color_filter != NULL) && (color_filter->is_filter_valid(pi)))
filter = color_filter->build_filter_string(pi);
}
if (filter == NULL) {
color_filter = find_conversation_filter("ip");
if ((color_filter != NULL) && (color_filter->is_filter_valid(pi)))
filter = color_filter->build_filter_string(pi);
}
if (filter == NULL) {
color_filter = find_conversation_filter("ipv6");
if ((color_filter != NULL) && (color_filter->is_filter_valid(pi)))
filter = color_filter->build_filter_string(pi);
}
if (filter == NULL) {
color_filter = find_conversation_filter("eth");
if ((color_filter != NULL) && (color_filter->is_filter_valid(pi)))
filter = color_filter->build_filter_string(pi);
}
gchar *filter = conversation_filter_from_packet(pi);
if (filter == NULL) {
main_ui_->statusBar->pushTemporaryStatus(tr("Unable to build conversation filter."));
return;
@ -3636,24 +3612,11 @@ void MainWindow::goToConversationFrame(bool go_next) {
dfilter_t *dfcode = NULL;
gboolean found_packet = FALSE;
packet_info *pi = &(capture_file_.capFile()->edt->pi);
conversation_filter_t* conv_filter;
/* Try to build a conversation
* filter in the order TCP, UDP, IP, Ethernet and apply the
* coloring */
conv_filter = find_conversation_filter("tcp");
if ((conv_filter != NULL) && (conv_filter->is_filter_valid(pi)))
filter = conv_filter->build_filter_string(pi);
conv_filter = find_conversation_filter("udp");
if ((conv_filter != NULL) && (conv_filter->is_filter_valid(pi)))
filter = conv_filter->build_filter_string(pi);
conv_filter = find_conversation_filter("ip");
if ((conv_filter != NULL) && (conv_filter->is_filter_valid(pi)))
filter = conv_filter->build_filter_string(pi);
conv_filter = find_conversation_filter("ipv6");
if ((conv_filter != NULL) && (conv_filter->is_filter_valid(pi)))
filter = conv_filter->build_filter_string(pi);
filter = conversation_filter_from_packet(pi);
if (filter == NULL) {
main_ui_->statusBar->pushTemporaryStatus(tr("Unable to build conversation filter."));
g_free(filter);