From 7c0c580c4b0093437ee81e11934ef5b8d27a5bb4 Mon Sep 17 00:00:00 2001 From: Dario Lombardo Date: Sat, 4 Feb 2017 16:26:34 +0100 Subject: wiretap: add cleanup routine. The cleanup routine has been added to exit section of the applications. Those which required a exit restyle have been patched as well. Change-Id: I3a8787f0718ac7fef00dc58176869c7510fda7b1 Reviewed-on: https://code.wireshark.org/review/19949 Petri-Dish: Dario Lombardo Reviewed-by: Peter Wu Tested-by: Petri Dish Buildbot Reviewed-by: Dario Lombardo --- capinfos.c | 1 + capture_opts.c | 13 +++++- captype.c | 1 + debian/libwiretap0.symbols | 2 + debian/libwsutil0.symbols | 1 + editcap.c | 106 +++++++++++++++++++++++++++---------------- epan/column-utils.c | 3 ++ extcap/androiddump.c | 2 +- filter_files.c | 12 +++++ mergecap.c | 23 ++++++---- randpkt.c | 54 +++++++++++++++------- randpkt_core/randpkt_core.c | 11 +++-- randpkt_core/randpkt_core.h | 2 +- rawshark.c | 90 +++++++++++++++++++++---------------- reordercap.c | 28 ++++++++---- sharkd.c | 1 + tfshark.c | 107 ++++++++++++++++++++++++-------------------- tshark.c | 1 + ui/gtk/main.c | 1 + wireshark-qt.cpp | 1 + wiretap/merge.h | 3 +- wiretap/wtap.c | 18 ++++++++ wiretap/wtap.h | 3 ++ wiretap/wtap_opttypes.c | 20 +++++++++ wiretap/wtap_opttypes.h | 4 ++ wsutil/buffer.c | 10 +++++ wsutil/buffer.h | 2 + 27 files changed, 355 insertions(+), 165 deletions(-) diff --git a/capinfos.c b/capinfos.c index fcdbb1ff9c..2bce743d26 100644 --- a/capinfos.c +++ b/capinfos.c @@ -1709,6 +1709,7 @@ main(int argc, char *argv[]) exit: g_free(hash_buf); + wtap_cleanup(); return overall_error_status; } diff --git a/capture_opts.c b/capture_opts.c index 93cea2ab77..3b0f77c99e 100644 --- a/capture_opts.c +++ b/capture_opts.c @@ -124,8 +124,17 @@ capture_opts_init(capture_options *capture_opts) void capture_opts_cleanup(capture_options *capture_opts) { - g_array_free(capture_opts->ifaces, TRUE); - g_array_free(capture_opts->all_ifaces, TRUE); + if (!capture_opts) + return; + + if (capture_opts->ifaces) { + g_array_free(capture_opts->ifaces, TRUE); + capture_opts->ifaces = NULL; + } + if (capture_opts->all_ifaces) { + g_array_free(capture_opts->all_ifaces, TRUE); + capture_opts->all_ifaces = NULL; + } } /* log content of capture_opts */ diff --git a/captype.c b/captype.c index 1d83f573ef..5858a392f8 100644 --- a/captype.c +++ b/captype.c @@ -216,6 +216,7 @@ main(int argc, char *argv[]) } + wtap_cleanup(); return overall_error_status; } diff --git a/debian/libwiretap0.symbols b/debian/libwiretap0.symbols index 1724e9eb79..5904b5661e 100644 --- a/debian/libwiretap0.symbols +++ b/debian/libwiretap0.symbols @@ -107,10 +107,12 @@ libwiretap.so.0 libwiretap0 #MINVER# wtap_get_savable_file_types_subtypes@Base 1.12.0~rc1 wtap_has_open_info@Base 1.12.0~rc1 wtap_init@Base 2.3.0 + wtap_cleanup@Base 2.3.0 wtap_iscompressed@Base 1.9.1 wtap_open_offline@Base 1.9.1 wtap_opttype_register_custom_block_type@Base 2.1.2 wtap_opttypes_initialize@Base 2.1.2 + wtap_opttypes_cleanup@Base 2.3.0 wtap_pcap_encap_to_wtap_encap@Base 1.9.1 wtap_phdr@Base 1.9.1 wtap_phdr_cleanup@Base 1.99.2 diff --git a/debian/libwsutil0.symbols b/debian/libwsutil0.symbols index 8d864a9f9f..204b14d6da 100644 --- a/debian/libwsutil0.symbols +++ b/debian/libwsutil0.symbols @@ -177,6 +177,7 @@ libwsutil.so.0 libwsutil0 #MINVER# ws_buffer_free@Base 1.99.0 ws_buffer_init@Base 1.99.0 ws_buffer_remove_start@Base 1.99.0 + ws_buffer_cleanup@Base 2.3.0 ws_hexstrtou16@Base 2.3.0 ws_hexstrtou32@Base 2.3.0 ws_hexstrtou64@Base 2.3.0 diff --git a/editcap.c b/editcap.c index 43aa6a3b08..b209e4fad7 100644 --- a/editcap.c +++ b/editcap.c @@ -94,6 +94,9 @@ #include "ringbuffer.h" /* For RINGBUFFER_MAX_NUM_FILES */ +#define INVALID_OPTION 1 +#define INVALID_FILE 2 + /* * Some globals so we can pass things to various routines */ @@ -338,7 +341,7 @@ selected(guint recno) return 0; } -static void +static gboolean set_time_adjustment(char *optarg_str_p) { char *frac, *end; @@ -346,7 +349,7 @@ set_time_adjustment(char *optarg_str_p) size_t frac_digits; if (!optarg_str_p) - return; + return TRUE; /* skip leading whitespace */ while (*optarg_str_p == ' ' || *optarg_str_p == '\t') @@ -368,12 +371,12 @@ set_time_adjustment(char *optarg_str_p) || val == LONG_MIN || val == LONG_MAX) { fprintf(stderr, "editcap: \"%s\" isn't a valid time adjustment\n", optarg_str_p); - exit(1); + return FALSE; } if (val < 0) { /* implies '--' since we caught '-' above */ fprintf(stderr, "editcap: \"%s\" isn't a valid time adjustment\n", optarg_str_p); - exit(1); + return FALSE; } } time_adj.tv.secs = val; @@ -390,10 +393,10 @@ set_time_adjustment(char *optarg_str_p) || val > ONE_BILLION || val == LONG_MIN || val == LONG_MAX) { fprintf(stderr, "editcap: \"%s\" isn't a valid time adjustment\n", optarg_str_p); - exit(1); + return FALSE; } } else { - return; /* no fractional digits */ + return TRUE; /* no fractional digits */ } /* adjust fractional portion from fractional to numerator @@ -405,9 +408,10 @@ set_time_adjustment(char *optarg_str_p) } time_adj.tv.nsecs = (int)val; + return TRUE; } -static void +static gboolean set_strict_time_adj(char *optarg_str_p) { char *frac, *end; @@ -415,7 +419,7 @@ set_strict_time_adj(char *optarg_str_p) size_t frac_digits; if (!optarg_str_p) - return; + return TRUE; /* skip leading whitespace */ while (*optarg_str_p == ' ' || *optarg_str_p == '\t') @@ -441,12 +445,12 @@ set_strict_time_adj(char *optarg_str_p) || val == LONG_MIN || val == LONG_MAX) { fprintf(stderr, "editcap: \"%s\" isn't a valid time adjustment\n", optarg_str_p); - exit(1); + return FALSE; } if (val < 0) { /* implies '--' since we caught '-' above */ fprintf(stderr, "editcap: \"%s\" isn't a valid time adjustment\n", optarg_str_p); - exit(1); + return FALSE; } } strict_time_adj.tv.secs = val; @@ -463,10 +467,10 @@ set_strict_time_adj(char *optarg_str_p) || val > ONE_BILLION || val == LONG_MIN || val == LONG_MAX) { fprintf(stderr, "editcap: \"%s\" isn't a valid time adjustment\n", optarg_str_p); - exit(1); + return FALSE; } } else { - return; /* no fractional digits */ + return TRUE; /* no fractional digits */ } /* adjust fractional portion from fractional to numerator @@ -478,9 +482,10 @@ set_strict_time_adj(char *optarg_str_p) } strict_time_adj.tv.nsecs = (int)val; + return TRUE; } -static void +static gboolean set_rel_time(char *optarg_str_p) { char *frac, *end; @@ -488,7 +493,7 @@ set_rel_time(char *optarg_str_p) size_t frac_digits; if (!optarg_str_p) - return; + return TRUE; /* skip leading whitespace */ while (*optarg_str_p == ' ' || *optarg_str_p == '\t') @@ -508,12 +513,12 @@ set_rel_time(char *optarg_str_p) || val == LONG_MIN || val == LONG_MAX) { fprintf(stderr, "1: editcap: \"%s\" isn't a valid rel time value\n", optarg_str_p); - exit(1); + return FALSE; } if (val < 0) { /* implies '--' since we caught '-' above */ fprintf(stderr, "2: editcap: \"%s\" isn't a valid rel time value\n", optarg_str_p); - exit(1); + return FALSE; } } relative_time_window.secs = val; @@ -530,10 +535,10 @@ set_rel_time(char *optarg_str_p) || val > ONE_BILLION || val == LONG_MIN || val == LONG_MAX) { fprintf(stderr, "3: editcap: \"%s\" isn't a valid rel time value\n", optarg_str_p); - exit(1); + return FALSE; } } else { - return; /* no fractional digits */ + return TRUE; /* no fractional digits */ } /* adjust fractional portion from fractional to numerator @@ -545,6 +550,7 @@ set_rel_time(char *optarg_str_p) } relative_time_window.nsecs = (int)val; + return TRUE; } #define LINUX_SLL_OFFSETP 14 @@ -993,6 +999,7 @@ main(int argc, char *argv[]) GArray *shb_hdrs = NULL; GArray *nrb_hdrs = NULL; char *shb_user_appl; + int ret = EXIT_SUCCESS; cmdarg_err_init(failure_message, failure_message_cont); @@ -1069,7 +1076,8 @@ main(int argc, char *argv[]) if ((sscanf(optarg, "%u:%n", &frame_number, &string_start_index) < 1) || (string_start_index == 0)) { fprintf(stderr, "editcap: \"%s\" isn't a valid :\n\n", optarg); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } /* Lazily create the table */ @@ -1091,7 +1099,8 @@ main(int argc, char *argv[]) if (!strptime(optarg,"%Y-%m-%d %T", &starttm)) { fprintf(stderr, "editcap: \"%s\" isn't a valid time format\n\n", optarg); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } check_startstop = TRUE; @@ -1110,7 +1119,8 @@ main(int argc, char *argv[]) if (!strptime(optarg,"%Y-%m-%d %T", &stoptm)) { fprintf(stderr, "editcap: \"%s\" isn't a valid time format\n\n", optarg); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } check_startstop = TRUE; stoptm.tm_isdst = -1; @@ -1138,7 +1148,8 @@ main(int argc, char *argv[]) default: fprintf(stderr, "editcap: \"%s\" isn't a valid chop length or offset:length\n", optarg); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; break; } @@ -1171,7 +1182,8 @@ main(int argc, char *argv[]) if (dup_window > MAX_DUP_DEPTH) { fprintf(stderr, "editcap: \"%d\" duplicate window value must be between 0 and %d inclusive.\n", dup_window, MAX_DUP_DEPTH); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } break; @@ -1180,7 +1192,8 @@ main(int argc, char *argv[]) if (p == optarg || err_prob < 0.0 || err_prob > 1.0) { fprintf(stderr, "editcap: probability \"%s\" must be between 0.0 and 1.0\n", optarg); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } srand( (unsigned int) (time(NULL) + ws_getpid()) ); break; @@ -1191,7 +1204,8 @@ main(int argc, char *argv[]) fprintf(stderr, "editcap: \"%s\" isn't a valid capture file type\n\n", optarg); list_capture_types(); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } break; @@ -1201,7 +1215,7 @@ main(int argc, char *argv[]) "See https://www.wireshark.org for more information.\n", get_ws_vcs_version_info()); print_usage(stdout); - exit(0); + goto clean_exit; break; case 'i': /* break capture file based on time interval */ @@ -1229,12 +1243,18 @@ main(int argc, char *argv[]) break; case 'S': - set_strict_time_adj(optarg); + if (!set_strict_time_adj(optarg)) { + ret = INVALID_OPTION; + goto clean_exit; + } do_strict_time_adjustment = TRUE; break; case 't': - set_time_adjustment(optarg); + if (!set_time_adjustment(optarg)) { + ret = INVALID_OPTION; + goto clean_exit; + } break; case 'T': @@ -1243,7 +1263,8 @@ main(int argc, char *argv[]) fprintf(stderr, "editcap: \"%s\" isn't a valid encapsulation type\n\n", optarg); list_encap_types(); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } break; @@ -1257,14 +1278,17 @@ main(int argc, char *argv[]) show_version("Editcap (Wireshark)", comp_info_str, runtime_info_str); g_string_free(comp_info_str, TRUE); g_string_free(runtime_info_str, TRUE); - exit(0); + goto clean_exit; break; case 'w': dup_detect = FALSE; dup_detect_by_time = TRUE; dup_window = MAX_DUP_DEPTH; - set_rel_time(optarg); + if (!set_rel_time(optarg)) { + ret = INVALID_OPTION; + goto clean_exit; + } break; case '?': /* Bad options if GNU getopt */ @@ -1279,7 +1303,8 @@ main(int argc, char *argv[]) print_usage(stderr); break; } - exit(1); + ret = INVALID_OPTION; + goto clean_exit; break; } } /* processing commmand-line options */ @@ -1290,7 +1315,8 @@ main(int argc, char *argv[]) if ((argc - optind) < 1) { print_usage(stderr); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } if (check_startstop && !stoptime) { @@ -1309,13 +1335,15 @@ main(int argc, char *argv[]) if (starttime > stoptime) { fprintf(stderr, "editcap: start time is after the stop time\n"); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } if (split_packet_count != 0 && secs_per_block != 0) { fprintf(stderr, "editcap: can't split on both packet count and time interval\n"); fprintf(stderr, "editcap: at the same time\n"); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } wth = wtap_open_offline(argv[optind], WTAP_TYPE_AUTO, &read_err, &read_err_info, FALSE); @@ -1327,7 +1355,8 @@ main(int argc, char *argv[]) fprintf(stderr, "(%s)\n", read_err_info); g_free(read_err_info); } - exit(2); + ret = INVALID_FILE; + goto clean_exit; } if (verbose) { @@ -1867,8 +1896,9 @@ main(int argc, char *argv[]) wtap_block_array_free(nrb_hdrs); g_free(idb_inf); wtap_close(wth); - - return 0; +clean_exit: + wtap_cleanup(); + return ret; error_on_exit: wtap_block_array_free(shb_hdrs); diff --git a/epan/column-utils.c b/epan/column-utils.c index 175fbe7adb..b822a3c107 100644 --- a/epan/column-utils.c +++ b/epan/column-utils.c @@ -98,6 +98,9 @@ col_cleanup(column_info *cinfo) int i; col_item_t* col_item; + if (!cinfo) + return; + for (i = 0; i < cinfo->num_cols; i++) { col_item = &cinfo->columns[i]; g_free(col_item->fmt_matx); diff --git a/extcap/androiddump.c b/extcap/androiddump.c index 060c569eba..01b96f6185 100644 --- a/extcap/androiddump.c +++ b/extcap/androiddump.c @@ -2785,7 +2785,7 @@ int main(int argc, char **argv) { end: /* clean up stuff */ extcap_base_cleanup(&extcap_conf); - + wtap_cleanup(); return ret; } diff --git a/filter_files.c b/filter_files.c index 566c48e8e4..d48500f000 100644 --- a/filter_files.c +++ b/filter_files.c @@ -101,10 +101,22 @@ free_filter_entry(gpointer data) void free_filter_lists(void) { + if (capture_filters) { g_list_free_full(capture_filters, free_filter_entry); + capture_filters = NULL; + } + if (display_filters) { g_list_free_full(display_filters, free_filter_entry); + display_filters = NULL; + } + if (capture_edited_filters) { g_list_free_full(capture_edited_filters, free_filter_entry); + capture_edited_filters = NULL; + } + if (display_edited_filters) { g_list_free_full(display_edited_filters, free_filter_entry); + display_edited_filters = NULL; + } } static GList * diff --git a/mergecap.c b/mergecap.c index fd2c2838c3..41339a4e61 100644 --- a/mergecap.c +++ b/mergecap.c @@ -262,7 +262,7 @@ main(int argc, char *argv[]) gchar *err_info = NULL; int err_fileno; char *out_filename = NULL; - merge_result status; + merge_result status = MERGE_OK; idb_merge_mode mode = IDB_MERGE_MODE_MAX; gboolean use_stdout = FALSE; merge_progress_callback_t cb; @@ -338,7 +338,8 @@ main(int argc, char *argv[]) fprintf(stderr, "mergecap: \"%s\" isn't a valid capture file type\n", optarg); list_capture_types(); - exit(1); + status = MERGE_ERR_INVALID_OPTION; + goto clean_exit; } break; @@ -348,7 +349,7 @@ main(int argc, char *argv[]) "See https://www.wireshark.org for more information.\n", get_ws_vcs_version_info()); print_usage(stdout); - exit(0); + goto clean_exit; break; case 'I': @@ -357,7 +358,8 @@ main(int argc, char *argv[]) fprintf(stderr, "mergecap: \"%s\" isn't a valid IDB merge mode\n", optarg); list_idb_merge_modes(); - exit(1); + status = MERGE_ERR_INVALID_OPTION; + goto clean_exit; } break; @@ -375,7 +377,7 @@ main(int argc, char *argv[]) show_version("Mergecap (Wireshark)", comp_info_str, runtime_info_str); g_string_free(comp_info_str, TRUE); g_string_free(runtime_info_str, TRUE); - exit(0); + goto clean_exit; break; case 'w': @@ -393,7 +395,8 @@ main(int argc, char *argv[]) default: print_usage(stderr); } - exit(1); + status = MERGE_ERR_INVALID_OPTION; + goto clean_exit; break; } } @@ -408,7 +411,8 @@ main(int argc, char *argv[]) if (!out_filename) { fprintf(stderr, "mergecap: an output filename must be set with -w\n"); fprintf(stderr, " run with -h for help\n"); - return 1; + status = MERGE_ERR_INVALID_OPTION; + goto clean_exit; } if (in_file_count < 1) { fprintf(stderr, "mergecap: No input files were specified\n"); @@ -418,7 +422,8 @@ main(int argc, char *argv[]) /* setting IDB merge mode must use PCAPNG output */ if (mode != IDB_MERGE_MODE_MAX && file_type != WTAP_FILE_TYPE_SUBTYPE_PCAPNG) { fprintf(stderr, "The IDB merge mode can only be used with PCAPNG output format\n"); - return 1; + status = MERGE_ERR_INVALID_OPTION; + goto clean_exit; } /* if they didn't set IDB merge mode, set it to our default */ @@ -478,6 +483,8 @@ main(int argc, char *argv[]) g_free(err_info); +clean_exit: + wtap_cleanup(); return (status == MERGE_OK) ? 0 : 2; } diff --git a/randpkt.c b/randpkt.c index 5035fd3fec..d10c5d6e03 100644 --- a/randpkt.c +++ b/randpkt.c @@ -49,6 +49,10 @@ #include "randpkt_core/randpkt_core.h" +#define INVALID_OPTION 1 +#define INVALID_TYPE 2 +#define CLOSE_ERROR 2 + /* * General errors are reported with an console message in randpkt. */ @@ -104,9 +108,8 @@ usage(gboolean is_error) g_strfreev(longname_list); fprintf(output, "\nIf type is not specified, a random packet will be chosen\n\n"); - - exit(is_error ? 1 : 0); } + int main(int argc, char **argv) { @@ -120,6 +123,7 @@ main(int argc, char **argv) guint8* type = NULL; int allrandom = FALSE; wtap_dumper *savedump; + int ret = EXIT_SUCCESS; static const struct option long_options[] = { {"help", no_argument, NULL, 'h'}, {0, 0, 0, 0 } @@ -174,7 +178,8 @@ main(int argc, char **argv) produce_max_bytes = get_positive_int(optarg, "max bytes"); if (produce_max_bytes > 65536) { cmdarg_err("max bytes is > 65536"); - return 1; + ret = INVALID_OPTION; + goto clean_exit; } break; @@ -188,6 +193,7 @@ main(int argc, char **argv) case 'h': usage(FALSE); + goto clean_exit; break; case 'r': @@ -196,6 +202,8 @@ main(int argc, char **argv) default: usage(TRUE); + ret = INVALID_OPTION; + goto clean_exit; break; } } @@ -206,6 +214,8 @@ main(int argc, char **argv) } else { usage(TRUE); + ret = INVALID_OPTION; + goto clean_exit; } if (!allrandom) { @@ -213,22 +223,31 @@ main(int argc, char **argv) g_free(type); example = randpkt_find_example(produce_type); - if (!example) - return 1; + if (!example) { + ret = INVALID_OPTION; + goto clean_exit; + } - randpkt_example_init(example, produce_filename, produce_max_bytes); + ret = randpkt_example_init(example, produce_filename, produce_max_bytes); + if (ret != EXIT_SUCCESS) + goto clean_exit; randpkt_loop(example, produce_count); } else { if (type) { fprintf(stderr, "Can't set type in random mode\n"); - return 2; + ret = INVALID_TYPE; + goto clean_exit; } produce_type = randpkt_parse_type(NULL); example = randpkt_find_example(produce_type); - if (!example) - return 1; - randpkt_example_init(example, produce_filename, produce_max_bytes); + if (!example) { + ret = INVALID_OPTION; + goto clean_exit; + } + ret = randpkt_example_init(example, produce_filename, produce_max_bytes); + if (ret != EXIT_SUCCESS) + goto clean_exit; while (produce_count-- > 0) { randpkt_loop(example, 1); @@ -237,15 +256,20 @@ main(int argc, char **argv) savedump = example->dump; example = randpkt_find_example(produce_type); - if (!example) - return 1; + if (!example) { + ret = INVALID_OPTION; + goto clean_exit; + } example->dump = savedump; } } - if (!randpkt_example_close(example)) - return 2; - return 0; + if (!randpkt_example_close(example)) { + ret = CLOSE_ERROR; + } +clean_exit: + wtap_cleanup(); + return ret; } /* diff --git a/randpkt_core/randpkt_core.c b/randpkt_core/randpkt_core.c index e84cb39d3c..3233d625a9 100644 --- a/randpkt_core/randpkt_core.c +++ b/randpkt_core/randpkt_core.c @@ -34,6 +34,9 @@ #define array_length(x) (sizeof x / sizeof x[0]) +#define INVALID_LEN 1 +#define WRITE_ERROR 2 + GRand *pkt_rand = NULL; /* Types of produceable packets */ @@ -696,7 +699,7 @@ gboolean randpkt_example_close(randpkt_example* example) return ok; } -void randpkt_example_init(randpkt_example* example, char* produce_filename, int produce_max_bytes) +int randpkt_example_init(randpkt_example* example, char* produce_filename, int produce_max_bytes) { int err; @@ -718,7 +721,7 @@ void randpkt_example_init(randpkt_example* example, char* produce_filename, int } if (!example->dump) { fprintf(stderr, "randpkt: Error writing to %s\n", example->filename); - exit(2); + return WRITE_ERROR; } /* reduce max_bytes by # of bytes already in sample */ @@ -726,10 +729,12 @@ void randpkt_example_init(randpkt_example* example, char* produce_filename, int fprintf(stderr, "randpkt: Sample packet length is %d, which is greater than " "or equal to\n", example->sample_length); fprintf(stderr, "your requested max_bytes value of %d\n", produce_max_bytes); - exit(1); + return INVALID_LEN; } else { example->produce_max_bytes = produce_max_bytes - example->sample_length; } + + return EXIT_SUCCESS; } /* Parse command-line option "type" and return enum type */ diff --git a/randpkt_core/randpkt_core.h b/randpkt_core/randpkt_core.h index 4b5b73a276..36764764e8 100644 --- a/randpkt_core/randpkt_core.h +++ b/randpkt_core/randpkt_core.h @@ -55,7 +55,7 @@ int randpkt_parse_type(char *string); randpkt_example* randpkt_find_example(int type); /* Init a new example */ -void randpkt_example_init(randpkt_example* example, char* produce_filename, int produce_max_bytes); +int randpkt_example_init(randpkt_example* example, char* produce_filename, int produce_max_bytes); /* Loop the packet generation */ void randpkt_loop(randpkt_example* example, guint64 produce_count); diff --git a/rawshark.c b/rawshark.c index 0366c9f5d1..c5a9470a54 100644 --- a/rawshark.c +++ b/rawshark.c @@ -121,6 +121,12 @@ static const gchar decode_as_arg_template[] = "==,"; #endif +#define INVALID_OPTION 1 +#define INIT_ERROR 2 +#define INVALID_DFILTER 2 +#define OPEN_ERROR 2 +#define FORMAT_ERROR 2 + static guint32 cum_bytes; static const frame_data *ref; static frame_data ref_frame; @@ -442,6 +448,7 @@ main(int argc, char *argv[]) GPtrArray *disp_fields = g_ptr_array_new(); guint fc; gboolean skip_pcap_header = FALSE; + int ret = EXIT_SUCCESS; static const struct option long_options[] = { {"help", no_argument, NULL, 'h'}, {"version", no_argument, NULL, 'v'}, @@ -532,8 +539,10 @@ main(int argc, char *argv[]) dissectors, and we must do it before we read the preferences, in case any dissectors register preferences. */ if (!epan_init(register_all_protocols, register_all_protocol_handoffs, - NULL, NULL)) - return 2; + NULL, NULL)) { + ret = INIT_ERROR; + goto clean_exit; + } prefs_p = read_prefs(&gpf_open_errno, &gpf_read_errno, &gpf_path, &pf_open_errno, &pf_read_errno, &pf_path); @@ -613,7 +622,8 @@ main(int argc, char *argv[]) case 'd': /* Payload type */ if (!set_link_type(optarg)) { cmdarg_err("Invalid link type or protocol \"%s\"", optarg); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } break; case 'F': /* Read field to display */ @@ -625,7 +635,7 @@ main(int argc, char *argv[]) "See https://www.wireshark.org for more information.\n", get_ws_vcs_version_info()); print_usage(stdout); - exit(0); + goto clean_exit; break; case 'l': /* "Line-buffer" standard output */ /* This isn't line-buffering, strictly speaking, it's just @@ -647,10 +657,10 @@ main(int argc, char *argv[]) limit.rlim_cur = get_positive_int(optarg, "memory limit"); limit.rlim_max = get_positive_int(optarg, "memory limit"); - if(setrlimit(RLIMIT_AS, &limit) != 0) - { + if(setrlimit(RLIMIT_AS, &limit) != 0) { cmdarg_err("setrlimit() returned error"); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } break; #endif @@ -662,7 +672,8 @@ main(int argc, char *argv[]) if (badopt != '\0') { cmdarg_err("-N specifies unknown resolving option '%c'; valid options are 'd', m', 'n', 'N', and 't'", badopt); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } break; case 'o': /* Override preference from command line */ @@ -673,13 +684,15 @@ main(int argc, char *argv[]) case PREFS_SET_SYNTAX_ERR: cmdarg_err("Invalid -o flag \"%s\"", optarg); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; break; case PREFS_SET_NO_SUCH_PREF: case PREFS_SET_OBSOLETE: cmdarg_err("-o flag \"%s\" specifies unknown preference", optarg); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; break; } break; @@ -695,7 +708,8 @@ main(int argc, char *argv[]) } else { cmdarg_err("Too many display filters"); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } break; case 's': /* Skip PCAP header */ @@ -704,7 +718,8 @@ main(int argc, char *argv[]) case 'S': /* Print string representations */ if (!parse_field_string_format(optarg)) { cmdarg_err("Invalid field string format"); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } break; case 't': /* Time stamp type */ @@ -741,7 +756,8 @@ main(int argc, char *argv[]) "\"u\" for absolute UTC, \"ud\" for absolute UTC with YYYY-MM-DD date,"); cmdarg_err_cont( "or \"udoy\" for absolute UTC with YYYY/DOY date."); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } break; case 'v': /* Show version and exit */ @@ -749,13 +765,14 @@ main(int argc, char *argv[]) show_version("Rawshark (Wireshark)", comp_info_str, runtime_info_str); g_string_free(comp_info_str, TRUE); g_string_free(runtime_info_str, TRUE); - exit(0); + goto clean_exit; break; } default: case '?': /* Bad flag - print usage message */ print_usage(stderr); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; break; } } @@ -784,7 +801,8 @@ main(int argc, char *argv[]) if (n_rfilters != 0) { cmdarg_err("Read filters were specified both with \"-R\" " "and with additional command-line arguments"); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } rfilters[n_rfilters] = get_args_as_string(argc, argv, optind); } @@ -793,12 +811,14 @@ main(int argc, char *argv[]) /* Make sure we got a dissector handle for our payload. */ if (encap == WTAP_ENCAP_UNKNOWN) { cmdarg_err("No valid payload dissector specified."); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } if (arg_error) { print_usage(stderr); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } @@ -829,12 +849,8 @@ main(int argc, char *argv[]) if (!dfilter_compile(rfilters[i], &rfcodes[n_rfcodes], &err_msg)) { cmdarg_err("%s", err_msg); g_free(err_msg); - epan_free(cfile.epan); - epan_cleanup(); -#ifdef HAVE_EXTCAP - extcap_cleanup(); -#endif - exit(2); + ret = INVALID_DFILTER; + goto clean_exit; } n_rfcodes++; } @@ -853,12 +869,8 @@ main(int argc, char *argv[]) relinquish_special_privs_perm(); if (raw_cf_open(&cfile, pipe_name) != CF_OK) { - epan_free(cfile.epan); - epan_cleanup(); -#ifdef HAVE_EXTCAP - extcap_cleanup(); -#endif - exit(2); + ret = OPEN_ERROR; + goto clean_exit; } /* Do we need to PCAP header and magic? */ @@ -869,7 +881,8 @@ main(int argc, char *argv[]) ssize_t bytes = ws_read(fd, buf, (int)bytes_left); if (bytes <= 0) { cmdarg_err("Not enough bytes for pcap header."); - exit(2); + ret = FORMAT_ERROR; + goto clean_exit; } bytes_left -= bytes; } @@ -877,25 +890,24 @@ main(int argc, char *argv[]) /* Process the packets in the file */ if (!load_cap_file(&cfile)) { - epan_free(cfile.epan); - epan_cleanup(); -#ifdef HAVE_EXTCAP - extcap_cleanup(); -#endif - exit(2); + ret = OPEN_ERROR; + goto clean_exit; } } else { /* If you want to capture live packets, use TShark. */ cmdarg_err("Input file or pipe name not specified."); - exit(2); + ret = OPEN_ERROR; + goto clean_exit; } +clean_exit: epan_free(cfile.epan); epan_cleanup(); #ifdef HAVE_EXTCAP extcap_cleanup(); #endif - return 0; + wtap_cleanup(); + return ret; } /** diff --git a/reordercap.c b/reordercap.c index b56fcfdeed..006c33801e 100644 --- a/reordercap.c +++ b/reordercap.c @@ -51,6 +51,10 @@ #include +#define INVALID_OPTION 1 +#define OPEN_ERROR 2 +#define OUTPUT_FILE_ERROR 1 + /* Show command-line usage */ static void print_usage(FILE *output) @@ -182,6 +186,7 @@ main(int argc, char *argv[]) GArray *shb_hdrs = NULL; wtapng_iface_descriptions_t *idb_inf = NULL; GArray *nrb_hdrs = NULL; + int ret = EXIT_SUCCESS; GPtrArray *frames; FrameRecord_t *prevFrame = NULL; @@ -259,17 +264,18 @@ main(int argc, char *argv[]) "See https://www.wireshark.org for more information.\n", get_ws_vcs_version_info()); print_usage(stdout); - exit(0); + goto clean_exit; case 'v': comp_info_str = get_compiled_version_info(NULL, NULL); runtime_info_str = get_runtime_version_info(NULL); show_version("Reordercap (Wireshark)", comp_info_str, runtime_info_str); g_string_free(comp_info_str, TRUE); g_string_free(runtime_info_str, TRUE); - exit(0); + goto clean_exit; case '?': print_usage(stderr); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } } @@ -281,7 +287,8 @@ main(int argc, char *argv[]) } else { print_usage(stderr); - exit(1); + ret = INVALID_OPTION; + goto clean_exit; } /* Open infile */ @@ -295,7 +302,8 @@ main(int argc, char *argv[]) fprintf(stderr, "(%s)\n", err_info); g_free(err_info); } - exit(2); + ret = OPEN_ERROR; + goto clean_exit; } DEBUG_PRINT("file_type_subtype is %d\n", wtap_file_type_subtype(wth)); @@ -320,7 +328,8 @@ main(int argc, char *argv[]) outfile, wtap_strerror(err)); wtap_block_array_free(shb_hdrs); wtap_block_array_free(nrb_hdrs); - exit(1); + ret = OUTPUT_FILE_ERROR; + goto clean_exit; } /* Allocate the array of frame pointers. */ @@ -394,7 +403,8 @@ main(int argc, char *argv[]) wtap_strerror(err)); wtap_block_array_free(shb_hdrs); wtap_block_array_free(nrb_hdrs); - exit(1); + ret = OUTPUT_FILE_ERROR; + goto clean_exit; } wtap_block_array_free(shb_hdrs); wtap_block_array_free(nrb_hdrs); @@ -402,7 +412,9 @@ main(int argc, char *argv[]) /* Finally, close infile and release resources. */ wtap_close(wth); - return 0; +clean_exit: + wtap_cleanup(); + return ret; } /* diff --git a/sharkd.c b/sharkd.c index dae6111d9c..4ab49bf485 100644 --- a/sharkd.c +++ b/sharkd.c @@ -299,6 +299,7 @@ main(int argc, char *argv[]) clean_exit: col_cleanup(&cfile.cinfo); free_filter_lists(); + wtap_cleanup(); return ret; } diff --git a/tfshark.c b/tfshark.c index 3e736700f7..2ba0b8b127 100644 --- a/tfshark.c +++ b/tfshark.c @@ -94,6 +94,11 @@ #include #endif +#define INVALID_OPTION 1 +#define INIT_ERROR 2 +#define INVALID_FILTER 2 +#define OPEN_ERROR 2 + static guint32 cum_bytes; static const frame_data *ref; static frame_data ref_frame; @@ -519,8 +524,10 @@ main(int argc, char *argv[]) dissectors, and we must do it before we read the preferences, in case any dissectors register preferences. */ if (!epan_init(register_all_protocols, register_all_protocol_handoffs, NULL, - NULL)) - return 2; + NULL)) { + exit_status = INIT_ERROR; + goto clean_exit; + } /* Register all tap listeners; we do this before we parse the arguments, as the "-z" argument can specify a registered tap. */ @@ -588,10 +595,11 @@ main(int argc, char *argv[]) glossary_option_help(); else { cmdarg_err("Invalid \"%s\" option for -G flag, enter -G ? for more help.", argv[2]); - return 1; + exit_status = INVALID_OPTION; + goto clean_exit; } } - return 0; + goto clean_exit; } prefs_p = read_prefs(&gpf_open_errno, &gpf_read_errno, &gpf_path, @@ -698,7 +706,8 @@ main(int argc, char *argv[]) if (!output_fields_set_option(output_fields, optarg)) { cmdarg_err("\"%s\" is not a valid field output option=value pair.", optarg); output_fields_list_options(stderr); - return 1; + exit_status = INVALID_OPTION; + goto clean_exit; } break; @@ -708,7 +717,7 @@ main(int argc, char *argv[]) "See https://www.wireshark.org for more information.\n", get_ws_vcs_version_info()); print_usage(stdout); - return 0; + goto clean_exit; break; case 'l': /* "Line-buffer" standard output */ /* This isn't line-buffering, strictly speaking, it's just @@ -739,7 +748,8 @@ main(int argc, char *argv[]) case PREFS_SET_NO_SUCH_PREF: case PREFS_SET_OBSOLETE: cmdarg_err("-o flag \"%s\" specifies unknown preference", optarg); - return 1; + exit_status = INVALID_OPTION; + goto clean_exit; break; } break; @@ -796,7 +806,8 @@ main(int argc, char *argv[]) "\t packets, or a multi-line view of the details of each of the\n" "\t packets, depending on whether the -V flag was specified.\n" "\t This is the default."); - return 1; + exit_status = INVALID_OPTION; + goto clean_exit; } break; case 'v': /* Show version and exit */ @@ -805,16 +816,7 @@ main(int argc, char *argv[]) show_version("TFShark (Wireshark)", comp_info_str, runtime_info_str); g_string_free(comp_info_str, TRUE); g_string_free(runtime_info_str, TRUE); - /* We don't really have to cleanup here, but it's a convenient way to test - * start-up and shut-down of the epan library without any UI-specific - * cruft getting in the way. Makes the results of running - * $ ./tools/valgrind-wireshark -n - * much more useful. */ - epan_cleanup(); -#ifdef HAVE_EXTCAP - extcap_cleanup(); -#endif - return 0; + goto clean_exit; case 'O': /* Only output these protocols */ /* already processed; just ignore it now */ break; @@ -839,25 +841,29 @@ main(int argc, char *argv[]) if (strcmp("help", optarg) == 0) { fprintf(stderr, "tfshark: The available statistics for the \"-z\" option are:\n"); list_stat_cmd_args(); - return 0; + goto clean_exit; } if (!process_stat_cmd_arg(optarg)) { cmdarg_err("Invalid -z argument \"%s\"; it must be one of:", optarg); list_stat_cmd_args(); - return 1; + exit_status = INVALID_OPTION; + goto clean_exit; } break; case 'd': /* Decode as rule */ case 'K': /* Kerberos keytab file */ case 't': /* Time stamp type */ case 'u': /* Seconds type */ - if (!dissect_opts_handle_opt(opt, optarg)) - return 1; + if (!dissect_opts_handle_opt(opt, optarg)) { + exit_status = INVALID_OPTION; + goto clean_exit; + } break; default: case '?': /* Bad flag - print usage message */ print_usage(stderr); - return 1; + exit_status = INVALID_OPTION; + goto clean_exit; break; } } @@ -871,7 +877,8 @@ main(int argc, char *argv[]) cmdarg_err("\"-Tfields\" was specified, but no fields were " "specified with \"-e\"."); - return 1; + exit_status = INVALID_OPTION; + goto clean_exit; } /* If no capture filter or display filter has been specified, and there are @@ -883,7 +890,8 @@ main(int argc, char *argv[]) if (dfilter != NULL) { cmdarg_err("Display filters were specified both with \"-d\" " "and with additional command-line arguments."); - return 1; + exit_status = INVALID_OPTION; + goto clean_exit; } dfilter = get_args_as_string(argc, argv, optind); } @@ -895,13 +903,15 @@ main(int argc, char *argv[]) if (arg_error) { print_usage(stderr); - return 1; + exit_status = INVALID_OPTION; + goto clean_exit; } if (print_hex) { if (output_action != WRITE_TEXT) { cmdarg_err("Raw packet hex data can only be printed as text or PostScript"); - return 1; + exit_status = INVALID_OPTION; + goto clean_exit; } } @@ -910,7 +920,8 @@ main(int argc, char *argv[]) if (!print_details) { cmdarg_err("-O requires -V"); - return 1; + exit_status = INVALID_OPTION; + goto clean_exit; } output_only_tables = g_hash_table_new (g_str_hash, g_str_equal); @@ -921,7 +932,8 @@ main(int argc, char *argv[]) if (rfilter != NULL && !perform_two_pass_analysis) { cmdarg_err("-R without -2 is deprecated. For single-pass filtering use -Y."); - return 1; + exit_status = INVALID_OPTION; + goto clean_exit; } /* Notify all registered modules that have had any of their preferences @@ -948,11 +960,8 @@ main(int argc, char *argv[]) if (!dfilter_compile(rfilter, &rfcode, &err_msg)) { cmdarg_err("%s", err_msg); g_free(err_msg); - epan_cleanup(); -#ifdef HAVE_EXTCAP - extcap_cleanup(); -#endif - return 2; + exit_status = INVALID_FILTER; + goto clean_exit; } } cfile.rfcode = rfcode; @@ -961,11 +970,8 @@ main(int argc, char *argv[]) if (!dfilter_compile(dfilter, &dfcode, &err_msg)) { cmdarg_err("%s", err_msg); g_free(err_msg); - epan_cleanup(); -#ifdef HAVE_EXTCAP - extcap_cleanup(); -#endif - return 2; + exit_status = INVALID_FILTER; + goto clean_exit; } } cfile.dfcode = dfcode; @@ -1009,11 +1015,8 @@ main(int argc, char *argv[]) /* TODO: if tfshark is ever changed to give the user a choice of which open_routine reader to use, then the following needs to change. */ if (cf_open(&cfile, cf_name, WTAP_TYPE_AUTO, FALSE, &err) != CF_OK) { - epan_cleanup(); -#ifdef HAVE_EXTCAP - extcap_cleanup(); -#endif - return 2; + exit_status = OPEN_ERROR; + goto clean_exit; } /* Process the packets in the file */ @@ -1049,6 +1052,8 @@ main(int argc, char *argv[]) draw_tap_listeners(TRUE); funnel_dump_all_text_windows(); + +clean_exit: epan_free(cfile.epan); epan_cleanup(); #ifdef HAVE_EXTCAP @@ -1058,6 +1063,8 @@ main(int argc, char *argv[]) output_fields_free(output_fields); output_fields = NULL; + col_cleanup(&cfile.cinfo); + wtap_cleanup(); return exit_status; } @@ -1254,7 +1261,7 @@ process_packet_second_pass(capture_file *cf, epan_dissect_t *edt, frame_data *fd if (ferror(stdout)) { show_print_file_io_error(errno); - exit(2); + return FALSE; } } prev_dis = fdata; @@ -1445,7 +1452,8 @@ load_cap_file(capture_file *cf, int max_packet_count, gint64 max_byte_count) process_packet_second_pass(cf, edt, fdata, &cf->phdr, &buf, tap_flags); } #else - process_packet_second_pass(cf, edt, fdata, &cf->phdr, &buf, tap_flags); + if (!process_packet_second_pass(cf, edt, fdata, &cf->phdr, &buf, tap_flags)) + return 2; #endif } @@ -1479,8 +1487,9 @@ load_cap_file(capture_file *cf, int max_packet_count, gint64 max_byte_count) framenum++; - process_packet(cf, edt, data_offset, &file_phdr/*wtap_phdr(cf->wth)*/, - raw_data, tap_flags); + if (!process_packet(cf, edt, data_offset, &file_phdr/*wtap_phdr(cf->wth)*/, + raw_data, tap_flags)) + return 2; /* Stop reading if we have the maximum number of packets; * When the -c option has not been used, max_packet_count @@ -1673,7 +1682,7 @@ process_packet(capture_file *cf, epan_dissect_t *edt, gint64 offset, if (ferror(stdout)) { show_print_file_io_error(errno); - exit(2); + return FALSE; } } diff --git a/tshark.c b/tshark.c index ff803f1773..f02cb33c72 100644 --- a/tshark.c +++ b/tshark.c @@ -2202,6 +2202,7 @@ clean_exit: #endif col_cleanup(&cfile.cinfo); free_filter_lists(); + wtap_cleanup(); return exit_status; } diff --git a/ui/gtk/main.c b/ui/gtk/main.c index ff2751ea5b..bf3bc3b481 100644 --- a/ui/gtk/main.c +++ b/ui/gtk/main.c @@ -2816,6 +2816,7 @@ clean_exit: #endif col_cleanup(&cfile.cinfo); free_filter_lists(); + wtap_cleanup(); return ret; } diff --git a/wireshark-qt.cpp b/wireshark-qt.cpp index eaf2e0e307..4fcedd2d68 100644 --- a/wireshark-qt.cpp +++ b/wireshark-qt.cpp @@ -947,6 +947,7 @@ clean_exit: capture_opts_cleanup(&global_capture_opts); #endif col_cleanup(&CaptureFile::globalCapFile()->cinfo); + wtap_cleanup(); return ret_val; } diff --git a/wiretap/merge.h b/wiretap/merge.h index 502c0955d3..21d0861cd8 100644 --- a/wiretap/merge.h +++ b/wiretap/merge.h @@ -59,7 +59,8 @@ typedef enum { MERGE_ERR_CANT_READ_INFILE, MERGE_ERR_BAD_PHDR_INTERFACE_ID, MERGE_ERR_CANT_WRITE_OUTFILE, - MERGE_ERR_CANT_CLOSE_OUTFILE + MERGE_ERR_CANT_CLOSE_OUTFILE, + MERGE_ERR_INVALID_OPTION } merge_result; diff --git a/wiretap/wtap.c b/wiretap/wtap.c index e14953b624..6473d43ee9 100644 --- a/wiretap/wtap.c +++ b/wiretap/wtap.c @@ -936,6 +936,13 @@ static void wtap_init_encap_types(void) { g_array_append_vals(encap_table_arr,encap_table_base,wtap_num_encap_types); } +static void wtap_cleanup_encap_types(void) { + if (encap_table_arr) { + g_array_free(encap_table_arr, TRUE); + encap_table_arr = NULL; + } +} + int wtap_get_num_encap_types(void) { return wtap_num_encap_types; } @@ -1428,6 +1435,17 @@ wtap_init(void) #endif } +/* + * Cleanup the library + */ +void +wtap_cleanup(void) +{ + wtap_cleanup_encap_types(); + wtap_opttypes_cleanup(); + ws_buffer_cleanup(); +} + /* * Editor modelines - http://www.wireshark.org/tools/modelines.html * diff --git a/wiretap/wtap.h b/wiretap/wtap.h index 5ce3cf436a..d1ed5d7577 100644 --- a/wiretap/wtap.h +++ b/wiretap/wtap.h @@ -1972,6 +1972,9 @@ void wtap_deregister_file_type_subtype(const int file_type_subtype); WS_DLL_PUBLIC int wtap_register_encap_type(const char* name, const char* short_name); +/*** Cleanup the interal library structures */ +WS_DLL_PUBLIC +void wtap_cleanup(void); /** * Wiretap error codes. diff --git a/wiretap/wtap_opttypes.c b/wiretap/wtap_opttypes.c index 199280bfd6..6f09b1ba03 100644 --- a/wiretap/wtap_opttypes.c +++ b/wiretap/wtap_opttypes.c @@ -1231,3 +1231,23 @@ void wtap_opttypes_initialize(void) wtap_opttype_option_register(&isb_block, OPT_ISB_OSDROP, &isb_osdrop); wtap_opttype_option_register(&isb_block, OPT_ISB_USRDELIV, &isb_usrdeliv); } + +void wtap_opttypes_cleanup(void) +{ + if (blocktype_list[WTAP_BLOCK_NG_SECTION]->options) { + g_array_free(blocktype_list[WTAP_BLOCK_NG_SECTION]->options, TRUE); + blocktype_list[WTAP_BLOCK_NG_SECTION]->options = NULL; + } + if (blocktype_list[WTAP_BLOCK_IF_DESCR]->options) { + g_array_free(blocktype_list[WTAP_BLOCK_IF_DESCR]->options, TRUE); + blocktype_list[WTAP_BLOCK_IF_DESCR]->options = NULL; + } + if (blocktype_list[WTAP_BLOCK_NG_NRB]->options) { + g_array_free(blocktype_list[WTAP_BLOCK_NG_NRB]->options, TRUE); + blocktype_list[WTAP_BLOCK_NG_NRB]->options = NULL; + } + if (blocktype_list[WTAP_BLOCK_IF_STATS]->options) { + g_array_free(blocktype_list[WTAP_BLOCK_IF_STATS]->options, TRUE); + blocktype_list[WTAP_BLOCK_IF_STATS]->options = NULL; + } +} diff --git a/wiretap/wtap_opttypes.h b/wiretap/wtap_opttypes.h index 44c5f064dd..b508eb35af 100644 --- a/wiretap/wtap_opttypes.h +++ b/wiretap/wtap_opttypes.h @@ -520,6 +520,10 @@ WS_DLL_PUBLIC void wtap_block_foreach_option(wtap_block_t block, wtap_block_fore WS_DLL_PUBLIC int wtap_opttype_register_custom_block_type(const char* name, const char* description, wtap_block_create_func create, wtap_mand_free_func free_mand, wtap_mand_copy_func copy_mand); +/** Cleanup the internal structures + */ +WS_DLL_PUBLIC void wtap_opttypes_cleanup(void); + #ifdef __cplusplus } #endif /* __cplusplus */ diff --git a/wsutil/buffer.c b/wsutil/buffer.c index 7d9d44b1b4..5108ee8905 100644 --- a/wsutil/buffer.c +++ b/wsutil/buffer.c @@ -178,6 +178,16 @@ ws_buffer_append_buffer(Buffer* buffer, Buffer* src_buffer) } #endif +void +ws_buffer_cleanup(void) +{ + if (small_buffers) { + g_ptr_array_set_free_func(small_buffers, g_free); + g_ptr_array_free(small_buffers, TRUE); + small_buffers = NULL; + } +} + /* * Editor modelines - http://www.wireshark.org/tools/modelines.html * diff --git a/wsutil/buffer.h b/wsutil/buffer.h index d8047cd1fd..34caf2a332 100644 --- a/wsutil/buffer.h +++ b/wsutil/buffer.h @@ -48,6 +48,8 @@ WS_DLL_PUBLIC void ws_buffer_append(Buffer* buffer, guint8 *from, gsize bytes); WS_DLL_PUBLIC void ws_buffer_remove_start(Buffer* buffer, gsize bytes); +WS_DLL_PUBLIC +void ws_buffer_cleanup(void); #ifdef SOME_FUNCTIONS_ARE_DEFINES # define ws_buffer_clean(buffer) ws_buffer_remove_start((buffer), ws_buffer_length(buffer)) -- cgit v1.2.1