summaryrefslogtreecommitdiff
path: root/epan/disabled_protos.c
diff options
context:
space:
mode:
authorMichael Mann <mmann78@netscape.net>2016-12-23 15:20:31 -0500
committerMichael Mann <mmann78@netscape.net>2016-12-24 02:30:21 +0000
commitc302812566373c5ac7383b825bea830b716778a5 (patch)
tree28bd309d9392e366bafe4ab7126615a9a0d3e7db /epan/disabled_protos.c
parentfb9a4d7413e7cf10cfce432e0d19e60c2f3acfe5 (diff)
downloadwireshark-c302812566373c5ac7383b825bea830b716778a5.tar.gz
Add enabled protocol list for dissectors who are disabled by default
We save a list of dissectors that are disabled through the Enabled Protocols dialog. This is because we assume dissectors are enabled by default. For dissectors that are disabled by default, we have no way to keep them enabled through the Enabled Protocols dialog. A dissector that defaults to being disabled has to be reset to enabled each time Wireshark is launched. Add a list similar to the disabled list for enabling dissectors that are disabled by default. This mostly applies to post-dissectors. Change-Id: I31a8d97a9fdbc472fe2a8666384e0f8786bb8e9f Reviewed-on: https://code.wireshark.org/review/19405 Petri-Dish: Michael Mann <mmann78@netscape.net> Tested-by: Petri Dish Buildbot <buildbot-no-reply@wireshark.org> Reviewed-by: Michael Mann <mmann78@netscape.net>
Diffstat (limited to 'epan/disabled_protos.c')
-rw-r--r--epan/disabled_protos.c516
1 files changed, 321 insertions, 195 deletions
diff --git a/epan/disabled_protos.c b/epan/disabled_protos.c
index 38aef4c1c7..3744f9d282 100644
--- a/epan/disabled_protos.c
+++ b/epan/disabled_protos.c
@@ -1,5 +1,6 @@
/* disabled_protos.c
- * Code for reading and writing the disabled protocols file.
+ * Declarations of routines for reading and writing protocols file that determine
+ * enabling and disabling of protocols.
*
* Wireshark - Network traffic analyzer
* By Gerald Combs <gerald@wireshark.org>
@@ -36,7 +37,8 @@
#include <wsutil/file_util.h>
#include <wsutil/ws_printf.h> /* ws_g_warning */
-#define PROTOCOLS_FILE_NAME "disabled_protos"
+#define ENABLED_PROTOCOLS_FILE_NAME "enabled_protos"
+#define DISABLED_PROTOCOLS_FILE_NAME "disabled_protos"
#define HEURISTICS_FILE_NAME "heuristic_protos"
/*
@@ -60,6 +62,11 @@ typedef struct {
static GList *global_disabled_protos = NULL;
static GList *disabled_protos = NULL;
/*
+ * List of enabled protocols (that are disabled by default)
+ */
+static GList *global_enabled_protos = NULL;
+static GList *enabled_protos = NULL;
+/*
* List of disabled heuristics
*/
static GList *global_disabled_heuristics = NULL;
@@ -106,96 +113,162 @@ heur_discard_existing_list (GList **flp)
}
/*
- * Read in a list of disabled protocols.
+ * Enable/Disable protocols as per the stored configuration
+ */
+static void
+set_protos_list(GList *protos_list, GList *global_protos_list, gboolean enable)
+{
+ gint i;
+ GList *fl_ent;
+ protocol_def *prot;
+
+ /*
+ * Assume no protocols disabled by default wants to be enabled
+ */
+ if (protos_list == NULL)
+ goto skip;
+
+ fl_ent = g_list_first(protos_list);
+
+ while (fl_ent != NULL) {
+ prot = (protocol_def *) fl_ent->data;
+ i = proto_get_id_by_filter_name(prot->name);
+ if (i == -1) {
+ /* XXX - complain here? */
+ } else {
+ if (proto_can_toggle_protocol(i))
+ proto_set_decoding(i, enable);
+ }
+
+ fl_ent = fl_ent->next;
+ }
+
+skip:
+ if (global_protos_list == NULL)
+ return;
+
+ fl_ent = g_list_first(global_protos_list);
+
+ while (fl_ent != NULL) {
+ prot = (protocol_def *) fl_ent->data;
+ i = proto_get_id_by_filter_name(prot->name);
+ if (i == -1) {
+ /* XXX - complain here? */
+ } else {
+ if (proto_can_toggle_protocol(i)) {
+ proto_set_decoding(i, enable);
+ proto_set_cant_toggle(i);
+ }
+ }
+
+ fl_ent = fl_ent->next;
+ }
+}
+
+/*
+ * Write out a list of protocols based on condition
*
* On success, "*pref_path_return" is set to NULL.
* On error, "*pref_path_return" is set to point to the pathname of
* the file we tried to read - it should be freed by our caller -
- * and "*open_errno_return" is set to the error if an open failed
- * or "*read_errno_return" is set to the error if a read failed.
+ * and "*errno_return" is set to the error.
*/
+static void
+save_protos_list(char **pref_path_return, int *errno_return, const char* filename,
+ const char* header_comment, gboolean (*protocol_check)(protocol_t *protocol))
+{
+ gchar *ff_path, *ff_path_new;
+ FILE *ff;
+ gint i;
+ protocol_t *protocol;
+ void *cookie;
+ gboolean first = TRUE;
-static int read_disabled_protos_list_file(const char *ff_path, FILE *ff,
- GList **flp);
+ *pref_path_return = NULL; /* assume no error */
-void
-read_disabled_protos_list(char **gpath_return, int *gopen_errno_return,
- int *gread_errno_return,
- char **path_return, int *open_errno_return,
- int *read_errno_return)
-{
- int err;
- char *gff_path, *ff_path;
- FILE *ff;
+ ff_path = get_persconffile_path(filename, TRUE);
- /* Construct the pathname of the global disabled protocols file. */
- gff_path = get_datafile_path(PROTOCOLS_FILE_NAME);
+ /* Write to "XXX.new", and rename if that succeeds.
+ That means we don't trash the file if we fail to write it out
+ completely. */
+ ff_path_new = g_strdup_printf("%s.new", ff_path);
- /* If we already have a list of protocols, discard it. */
- discard_existing_list (&global_disabled_protos);
+ if ((ff = ws_fopen(ff_path_new, "w")) == NULL) {
+ *pref_path_return = ff_path;
+ *errno_return = errno;
+ g_free(ff_path_new);
+ return;
+ }
- /* Read the global disabled protocols file, if it exists. */
- *gpath_return = NULL;
- if ((ff = ws_fopen(gff_path, "r")) != NULL) {
- /* We succeeded in opening it; read it. */
- err = read_disabled_protos_list_file(gff_path, ff,
- &global_disabled_protos);
- if (err != 0) {
- /* We had an error reading the file; return the errno and the
- pathname, so our caller can report the error. */
- *gopen_errno_return = 0;
- *gread_errno_return = err;
- *gpath_return = gff_path;
- } else
- g_free(gff_path);
- fclose(ff);
- } else {
- /* We failed to open it. If we failed for some reason other than
- "it doesn't exist", return the errno and the pathname, so our
- caller can report the error. */
- if (errno != ENOENT) {
- *gopen_errno_return = errno;
- *gread_errno_return = 0;
- *gpath_return = gff_path;
- } else
- g_free(gff_path);
+ /* Iterate over all the protocols */
+ for (i = proto_get_first_protocol(&cookie); i != -1;
+ i = proto_get_next_protocol(&cookie)) {
+
+ if (!proto_can_toggle_protocol(i)) {
+ continue;
+ }
+
+ protocol = find_protocol_by_id(i);
+ if (protocol_check(protocol) == FALSE)
+ continue;
+
+ if (first) {
+ if (header_comment != NULL) {
+ /* Write out a comment explaining what the file is */
+ fprintf(ff, "%s\n", header_comment);
+ }
+ first = FALSE;
+ }
+
+ /* Write out the protocol name. */
+ fprintf(ff, "%s\n", proto_get_protocol_filter_name(i));
}
- /* Construct the pathname of the user's disabled protocols file. */
- ff_path = get_persconffile_path(PROTOCOLS_FILE_NAME, TRUE);
+ if (fclose(ff) == EOF) {
+ *pref_path_return = ff_path;
+ *errno_return = errno;
+ ws_unlink(ff_path_new);
+ g_free(ff_path_new);
+ return;
+ }
- /* If we already have a list of protocols, discard it. */
- discard_existing_list (&disabled_protos);
+#ifdef _WIN32
+ /* ANSI C doesn't say whether "rename()" removes the target if it
+ exists; the Win32 call to rename files doesn't do so, which I
+ infer is the reason why the MSVC++ "rename()" doesn't do so.
+ We must therefore remove the target file first, on Windows.
- /* Read the user's disabled protocols file, if it exists. */
- *path_return = NULL;
- if ((ff = ws_fopen(ff_path, "r")) != NULL) {
- /* We succeeded in opening it; read it. */
- err = read_disabled_protos_list_file(ff_path, ff, &disabled_protos);
- if (err != 0) {
- /* We had an error reading the file; return the errno and the
- pathname, so our caller can report the error. */
- *open_errno_return = 0;
- *read_errno_return = err;
- *path_return = ff_path;
- } else
- g_free(ff_path);
- fclose(ff);
- } else {
- /* We failed to open it. If we failed for some reason other than
- "it doesn't exist", return the errno and the pathname, so our
- caller can report the error. */
- if (errno != ENOENT) {
- *open_errno_return = errno;
- *read_errno_return = 0;
- *path_return = ff_path;
- } else
- g_free(ff_path);
+ XXX - ws_rename() should be ws_stdio_rename() on Windows,
+ and ws_stdio_rename() uses MoveFileEx() with MOVEFILE_REPLACE_EXISTING,
+ so it should remove the target if it exists, so this stuff
+ shouldn't be necessary. Perhaps it dates back to when we were
+ calling rename(), with that being a wrapper around Microsoft's
+ _rename(), which didn't remove the target. */
+ if (ws_remove(ff_path) < 0 && errno != ENOENT) {
+ /* It failed for some reason other than "it's not there"; if
+ it's not there, we don't need to remove it, so we just
+ drive on. */
+ *pref_path_return = ff_path;
+ *errno_return = errno;
+ ws_unlink(ff_path_new);
+ g_free(ff_path_new);
+ return;
}
+#endif
+
+ if (ws_rename(ff_path_new, ff_path) < 0) {
+ *pref_path_return = ff_path;
+ *errno_return = errno;
+ ws_unlink(ff_path_new);
+ g_free(ff_path_new);
+ return;
+ }
+ g_free(ff_path_new);
+ g_free(ff_path);
}
static int
-read_disabled_protos_list_file(const char *ff_path, FILE *ff,
+read_protos_list_file(const char *ff_path, FILE *ff,
GList **flp)
{
protocol_def *prot;
@@ -204,6 +277,7 @@ read_disabled_protos_list_file(const char *ff_path, FILE *ff,
int prot_name_len;
int prot_name_index;
int line = 1;
+ gboolean in_comment = FALSE;
/* Allocate the protocol name buffer. */
@@ -238,8 +312,10 @@ read_disabled_protos_list_file(const char *ff_path, FILE *ff,
break; /* End of file, or I/O error */
if (g_ascii_isspace(c))
break; /* Trailing white space, or end of line. */
- if (c == '#')
+ if (c == '#') {
+ in_comment = TRUE;
break; /* Start of comment, running to end of line. */
+ }
/* Add this character to the protocol name string. */
if (prot_name_index >= prot_name_len) {
/* protocol name buffer isn't long enough; double its length. */
@@ -261,7 +337,7 @@ read_disabled_protos_list_file(const char *ff_path, FILE *ff,
ff_path, line);
}
}
- if (c != EOF && c != '\n') {
+ if (c != EOF && c != '\n' && in_comment == TRUE) {
/* Skip to end of line. */
while ((c = ws_getc_unlocked(ff)) != EOF && c != '\n')
;
@@ -278,6 +354,11 @@ read_disabled_protos_list_file(const char *ff_path, FILE *ff,
break; /* nothing more to read */
}
+ if (in_comment) {
+ in_comment = FALSE;
+ continue;
+ }
+
/* Null-terminate the protocol name. */
if (prot_name_index >= prot_name_len) {
/* protocol name buffer isn't long enough; double its length. */
@@ -300,62 +381,121 @@ error:
}
/*
- * Disable protocols as per the stored configuration
+ * Read in a list of protocols.
+ *
+ * On success, "*pref_path_return" is set to NULL.
+ * On error, "*pref_path_return" is set to point to the pathname of
+ * the file we tried to read - it should be freed by our caller -
+ * and "*open_errno_return" is set to the error if an open failed
+ * or "*read_errno_return" is set to the error if a read failed.
*/
void
-set_disabled_protos_list(void)
+read_protos_list(char **gpath_return, int *gopen_errno_return,
+ int *gread_errno_return,
+ char **path_return, int *open_errno_return,
+ int *read_errno_return, const char* filename,
+ GList **protos_list, GList **global_protos_list)
{
- gint i;
- GList *fl_ent;
- protocol_def *prot;
-
- /*
- * assume all protocols are enabled by default
- */
- if (disabled_protos == NULL)
- goto skip;
+ int err;
+ char *gff_path, *ff_path;
+ FILE *ff;
- fl_ent = g_list_first(disabled_protos);
+ /* Construct the pathname of the global disabled protocols file. */
+ gff_path = get_datafile_path(filename);
- while (fl_ent != NULL) {
- prot = (protocol_def *) fl_ent->data;
- i = proto_get_id_by_filter_name(prot->name);
- if (i == -1) {
- /* XXX - complain here? */
- } else {
- if (proto_can_toggle_protocol(i))
- proto_set_decoding(i, FALSE);
- }
+ /* If we already have a list of protocols, discard it. */
+ discard_existing_list (global_protos_list);
- fl_ent = fl_ent->next;
+ /* Read the global disabled protocols file, if it exists. */
+ *gpath_return = NULL;
+ if ((ff = ws_fopen(gff_path, "r")) != NULL) {
+ /* We succeeded in opening it; read it. */
+ err = read_protos_list_file(gff_path, ff,
+ global_protos_list);
+ if (err != 0) {
+ /* We had an error reading the file; return the errno and the
+ pathname, so our caller can report the error. */
+ *gopen_errno_return = 0;
+ *gread_errno_return = err;
+ *gpath_return = gff_path;
+ } else
+ g_free(gff_path);
+ fclose(ff);
+ } else {
+ /* We failed to open it. If we failed for some reason other than
+ "it doesn't exist", return the errno and the pathname, so our
+ caller can report the error. */
+ if (errno != ENOENT) {
+ *gopen_errno_return = errno;
+ *gread_errno_return = 0;
+ *gpath_return = gff_path;
+ } else
+ g_free(gff_path);
}
-skip:
- if (global_disabled_protos == NULL)
- return;
-
- fl_ent = g_list_first(global_disabled_protos);
+ /* Construct the pathname of the user's disabled protocols file. */
+ ff_path = get_persconffile_path(filename, TRUE);
- while (fl_ent != NULL) {
- prot = (protocol_def *) fl_ent->data;
- i = proto_get_id_by_filter_name(prot->name);
- if (i == -1) {
- /* XXX - complain here? */
- } else {
- if (proto_can_toggle_protocol(i)) {
- proto_set_decoding(i, FALSE);
- proto_set_cant_toggle(i);
- }
- }
+ /* If we already have a list of protocols, discard it. */
+ discard_existing_list (protos_list);
- fl_ent = fl_ent->next;
+ /* Read the user's disabled protocols file, if it exists. */
+ *path_return = NULL;
+ if ((ff = ws_fopen(ff_path, "r")) != NULL) {
+ /* We succeeded in opening it; read it. */
+ err = read_protos_list_file(ff_path, ff, protos_list);
+ if (err != 0) {
+ /* We had an error reading the file; return the errno and the
+ pathname, so our caller can report the error. */
+ *open_errno_return = 0;
+ *read_errno_return = err;
+ *path_return = ff_path;
+ } else
+ g_free(ff_path);
+ fclose(ff);
+ } else {
+ /* We failed to open it. If we failed for some reason other than
+ "it doesn't exist", return the errno and the pathname, so our
+ caller can report the error. */
+ if (errno != ENOENT) {
+ *open_errno_return = errno;
+ *read_errno_return = 0;
+ *path_return = ff_path;
+ } else
+ g_free(ff_path);
}
}
+/************************************************************************
+ * Disabling dissectors
+ ************************************************************************/
+
/*
- * Disable a particular protocol by name
+ * Read in a list of disabled protocols.
*/
+void
+read_disabled_protos_list(char **gpath_return, int *gopen_errno_return,
+ int *gread_errno_return,
+ char **path_return, int *open_errno_return,
+ int *read_errno_return)
+{
+ read_protos_list(gpath_return, gopen_errno_return, gread_errno_return,
+ path_return, open_errno_return, read_errno_return,
+ DISABLED_PROTOCOLS_FILE_NAME, &disabled_protos, &global_disabled_protos);
+}
+/*
+ * Disable protocols as per the stored configuration
+ */
+void
+set_disabled_protos_list(void)
+{
+ set_protos_list(disabled_protos, global_disabled_protos, FALSE);
+}
+
+/*
+ * Disable a particular protocol by name
+ */
void
proto_disable_proto_by_name(const char *name)
{
@@ -373,99 +513,85 @@ proto_disable_proto_by_name(const char *name)
}
}
-/*
- * Write out a list of disabled protocols.
- *
- * On success, "*pref_path_return" is set to NULL.
- * On error, "*pref_path_return" is set to point to the pathname of
- * the file we tried to read - it should be freed by our caller -
- * and "*errno_return" is set to the error.
- */
-void
-save_disabled_protos_list(char **pref_path_return, int *errno_return)
+static gboolean disable_proto_list_check(protocol_t *protocol)
{
- gchar *ff_path, *ff_path_new;
- FILE *ff;
- gint i;
- protocol_t *protocol;
- void *cookie;
+ if (proto_is_protocol_enabled(protocol) == FALSE)
+ return TRUE;
- *pref_path_return = NULL; /* assume no error */
-
- ff_path = get_persconffile_path(PROTOCOLS_FILE_NAME, TRUE);
+ return FALSE;
+}
- /* Write to "XXX.new", and rename if that succeeds.
- That means we don't trash the file if we fail to write it out
- completely. */
- ff_path_new = g_strdup_printf("%s.new", ff_path);
+void
+save_disabled_protos_list(char **pref_path_return, int *errno_return)
+{
+ save_protos_list(pref_path_return, errno_return, DISABLED_PROTOCOLS_FILE_NAME,
+ NULL, disable_proto_list_check);
+}
- if ((ff = ws_fopen(ff_path_new, "w")) == NULL) {
- *pref_path_return = ff_path;
- *errno_return = errno;
- g_free(ff_path_new);
- return;
- }
+/************************************************************************
+ * Enabling dissectors (that are disabled by default)
+ ************************************************************************/
+void
+set_enabled_protos_list(void)
+{
+ set_protos_list(enabled_protos, global_enabled_protos, TRUE);
+}
- /* Iterate over all the protocols */
- for (i = proto_get_first_protocol(&cookie); i != -1;
- i = proto_get_next_protocol(&cookie)) {
+WS_DLL_PUBLIC void
+proto_enable_proto_by_name(const char *name)
+{
+ protocol_t *protocol;
+ int proto_id;
- if (!proto_can_toggle_protocol(i)) {
- continue;
+ proto_id = proto_get_id_by_filter_name(name);
+ if (proto_id >= 0 ) {
+ protocol = find_protocol_by_id(proto_id);
+ if ((proto_is_protocol_enabled_by_default(protocol) == FALSE) &&
+ (proto_is_protocol_enabled(protocol) == FALSE)) {
+ if (proto_can_toggle_protocol(proto_id) == TRUE) {
+ proto_set_decoding(proto_id, TRUE);
+ }
+ }
}
+}
- protocol = find_protocol_by_id(i);
- if (proto_is_protocol_enabled(protocol)) {
- continue;
- }
+static gboolean enable_proto_list_check(protocol_t *protocol)
+{
+ if ((proto_is_protocol_enabled_by_default(protocol) == FALSE) &&
+ (proto_is_protocol_enabled(protocol) == TRUE))
+ return TRUE;
- /* Write out the protocol name. */
- fprintf(ff, "%s\n", proto_get_protocol_filter_name(i));
- }
+ return FALSE;
+}
- if (fclose(ff) == EOF) {
- *pref_path_return = ff_path;
- *errno_return = errno;
- ws_unlink(ff_path_new);
- g_free(ff_path_new);
- return;
- }
+void
+save_enabled_protos_list(char **pref_path_return, int *errno_return)
+{
+ save_protos_list(pref_path_return, errno_return, ENABLED_PROTOCOLS_FILE_NAME,
+ "#This file is for enabling protocols that are disabled by default",
+ enable_proto_list_check);
+}
-#ifdef _WIN32
- /* ANSI C doesn't say whether "rename()" removes the target if it
- exists; the Win32 call to rename files doesn't do so, which I
- infer is the reason why the MSVC++ "rename()" doesn't do so.
- We must therefore remove the target file first, on Windows.
+/*
+ * Read in a list of enabled protocols (that are disabled by default).
+ */
+void
+read_enabled_protos_list(char **gpath_return, int *gopen_errno_return,
+ int *gread_errno_return,
+ char **path_return, int *open_errno_return,
+ int *read_errno_return)
+{
+ read_protos_list(gpath_return, gopen_errno_return, gread_errno_return,
+ path_return, open_errno_return, read_errno_return,
+ ENABLED_PROTOCOLS_FILE_NAME, &enabled_protos, &global_enabled_protos);
+}
- XXX - ws_rename() should be ws_stdio_rename() on Windows,
- and ws_stdio_rename() uses MoveFileEx() with MOVEFILE_REPLACE_EXISTING,
- so it should remove the target if it exists, so this stuff
- shouldn't be necessary. Perhaps it dates back to when we were
- calling rename(), with that being a wrapper around Microsoft's
- _rename(), which didn't remove the target. */
- if (ws_remove(ff_path) < 0 && errno != ENOENT) {
- /* It failed for some reason other than "it's not there"; if
- it's not there, we don't need to remove it, so we just
- drive on. */
- *pref_path_return = ff_path;
- *errno_return = errno;
- ws_unlink(ff_path_new);
- g_free(ff_path_new);
- return;
- }
-#endif
- if (ws_rename(ff_path_new, ff_path) < 0) {
- *pref_path_return = ff_path;
- *errno_return = errno;
- ws_unlink(ff_path_new);
- g_free(ff_path_new);
- return;
- }
- g_free(ff_path_new);
- g_free(ff_path);
-}
+/************************************************************************
+ * Heuristic dissectors
+ ************************************************************************/
+
void
set_disabled_heur_dissector_list(void)