extcap: Add Save functionality to options dialog
This patch creates the functionality of saving all parameters for extcap devices in the general preference section. For now, multiselect and fileselect do not save their values but patches for this will be provided in the future Also, all preferences are stored as strings to make handling easier. This might change in the future, but for the first version it will stick. Restore to Defaults is not implemented as of yet, and will be in a future version, once the preference storing is finalized Bug: 11666 Change-Id: I178346405146d2e43f4f3481c05c92c0b3595af5 Reviewed-on: https://code.wireshark.org/review/13451 Petri-Dish: Roland Knall <rknall@gmail.com> Tested-by: Petri Dish Buildbot <buildbot-no-reply@wireshark.org> Reviewed-by: Roland Knall <rknall@gmail.com>
This commit is contained in:
parent
5e89f93322
commit
927ffaa794
|
@ -150,7 +150,8 @@ These options do have types, for which the following types are being supported:
|
|||
the user input for validity beyond normal data type or range checks. Back-slashes
|
||||
must be escaped (as in \\b for \b)
|
||||
|
||||
* PASSWORD - Let the user provide a masked string to the capture
|
||||
* PASSWORD - Let the user provide a masked string to the capture. Password strings are
|
||||
not saved, when the extcap configuration is being saved
|
||||
|
||||
arg {number=0}{call=--password}{display=The user password}{tooltip=The password for the connection}{type=password}
|
||||
|
||||
|
|
|
@ -78,7 +78,10 @@ def extcap_config(interface):
|
|||
args.append ( (2, '--verify', 'Verify', 'Verify package content', 'boolflag', '{default=yes}') )
|
||||
args.append ( (3, '--remote', 'Remote Channel', 'Remote Channel Selector', 'selector', ''))
|
||||
args.append ( (4, '--fake_ip', 'Fake IP Address', 'Use this ip address as sender', 'string', '{save=false}{validation=\\b(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\b}'))
|
||||
args.append ( (5, '--password', 'Password', 'Package message password', 'password', '') )
|
||||
args.append ( (5, '--ltest', 'Long Test', 'Long Test Value', 'long', '{default=123123123123123123}'))
|
||||
args.append ( (6, '--d1test', 'Double 1 Test', 'Long Test Value', 'double', '{default=123.456}'))
|
||||
args.append ( (7, '--d2test', 'Double 2 Test', 'Long Test Value', 'double', '{default= 123,456}'))
|
||||
args.append ( (8, '--password', 'Password', 'Package message password', 'password', '') )
|
||||
|
||||
values.append ( (3, "if1", "Remote1", "true" ) )
|
||||
values.append ( (3, "if2", "Remote2", "false" ) )
|
||||
|
|
22
epan/prefs.c
22
epan/prefs.c
|
@ -2082,6 +2082,10 @@ prefs_register_modules(void)
|
|||
{
|
||||
module_t *printing, *capture_module, *console_module,
|
||||
*gui_layout_module, *gui_font_module;
|
||||
#ifdef HAVE_EXTCAP
|
||||
module_t *extcap_module;
|
||||
#endif
|
||||
|
||||
struct pref_custom_cbs custom_cbs;
|
||||
|
||||
if (protocols_module != NULL) {
|
||||
|
@ -2089,6 +2093,24 @@ prefs_register_modules(void)
|
|||
return;
|
||||
}
|
||||
|
||||
#ifdef HAVE_EXTCAP
|
||||
/* GUI
|
||||
* These are "simple" GUI preferences that can be read/written using the
|
||||
* preference module API. These preferences still use their own
|
||||
* configuration screens for access, but this cuts down on the
|
||||
* preference "string compare list" in set_pref()
|
||||
*/
|
||||
extcap_module = prefs_register_module(NULL, "extcap", "Extcap Utilities",
|
||||
"Extcap Utilities", NULL, FALSE);
|
||||
|
||||
/* Setting default value to true */
|
||||
prefs.extcap_save_on_start = TRUE;
|
||||
prefs_register_bool_preference(extcap_module, "gui_save_on_start",
|
||||
"Save arguments on start of capture",
|
||||
"Save arguments on start of capture",
|
||||
&prefs.extcap_save_on_start);
|
||||
#endif
|
||||
|
||||
/* GUI
|
||||
* These are "simple" GUI preferences that can be read/written using the
|
||||
* preference module API. These preferences still use their own
|
||||
|
|
|
@ -236,6 +236,9 @@ typedef struct _e_prefs {
|
|||
gint st_sort_defcolflag;
|
||||
gboolean st_sort_defdescending;
|
||||
gboolean st_sort_showfullname;
|
||||
#ifdef HAVE_EXTCAP
|
||||
gboolean extcap_save_on_start;
|
||||
#endif
|
||||
} e_prefs;
|
||||
|
||||
WS_DLL_PUBLIC e_prefs prefs;
|
||||
|
|
144
extcap.c
144
extcap.c
|
@ -40,6 +40,9 @@
|
|||
#include <glib.h>
|
||||
#include <log.h>
|
||||
|
||||
#include <epan/prefs.h>
|
||||
#include <epan/prefs-int.h>
|
||||
|
||||
#include <wsutil/file_util.h>
|
||||
#include <wsutil/filesystem.h>
|
||||
#include <wsutil/tempfile.h>
|
||||
|
@ -69,7 +72,7 @@ static GHashTable *ifaces = NULL;
|
|||
static GHashTable *tools = NULL;
|
||||
|
||||
/* Callback definition for extcap_foreach */
|
||||
typedef gboolean (*extcap_cb_t)(const gchar *extcap, gchar *output, void *data,
|
||||
typedef gboolean (*extcap_cb_t)(const gchar *extcap, const gchar *ifname, gchar *output, void *data,
|
||||
gchar **err_str);
|
||||
|
||||
/* #define ARG_DEBUG */
|
||||
|
@ -201,7 +204,7 @@ static void extcap_foreach(gint argc, gchar **args, extcap_cb_t cb,
|
|||
&command_output, NULL, &exit_status, &error);
|
||||
|
||||
if (status && exit_status == 0)
|
||||
keep_going = cb(extcap_path->str, command_output, cb_data, err_str);
|
||||
keep_going = cb(extcap_path->str, ifname, command_output, cb_data, err_str);
|
||||
|
||||
g_free(argv[0]);
|
||||
g_free(command_output);
|
||||
|
@ -217,7 +220,7 @@ static void extcap_foreach(gint argc, gchar **args, extcap_cb_t cb,
|
|||
g_free(argv);
|
||||
}
|
||||
|
||||
static gboolean dlt_cb(const gchar *extcap _U_, gchar *output, void *data,
|
||||
static gboolean dlt_cb(const gchar *extcap _U_, const gchar *ifname _U_, gchar *output, void *data,
|
||||
char **err_str) {
|
||||
extcap_token_sentence *tokens;
|
||||
extcap_dlt *dlts, *dlt_iter, *next;
|
||||
|
@ -300,7 +303,7 @@ extcap_get_if_dlts(const gchar *ifname, char **err_str) {
|
|||
return caps;
|
||||
}
|
||||
|
||||
static gboolean interfaces_cb(const gchar *extcap, gchar *output, void *data,
|
||||
static gboolean interfaces_cb(const gchar *extcap, const gchar *ifname _U_, gchar *output, void *data,
|
||||
char **err_str _U_) {
|
||||
GList **il = (GList **) data;
|
||||
extcap_token_sentence *tokens;
|
||||
|
@ -422,6 +425,27 @@ static void extcap_free_arg_elem(gpointer data, gpointer user_data _U_) {
|
|||
g_free(data);
|
||||
}
|
||||
|
||||
void extcap_register_preferences(void)
|
||||
{
|
||||
GList * interfaces = NULL;
|
||||
|
||||
module_t * dev_module = prefs_find_module("extcap");
|
||||
|
||||
if ( !dev_module )
|
||||
return;
|
||||
|
||||
if ( ! ifaces || g_hash_table_size(ifaces) == 0 )
|
||||
extcap_interface_list(NULL);
|
||||
|
||||
interfaces = g_hash_table_get_keys(ifaces);
|
||||
|
||||
while ( interfaces ) {
|
||||
extcap_get_if_configuration((gchar *)interfaces->data);
|
||||
|
||||
interfaces = g_list_next(interfaces);
|
||||
}
|
||||
}
|
||||
|
||||
static void extcap_free_if_configuration(GList *list)
|
||||
{
|
||||
GList *elem, *sl;
|
||||
|
@ -438,11 +462,12 @@ static void extcap_free_if_configuration(GList *list)
|
|||
g_list_free(list);
|
||||
}
|
||||
|
||||
static gboolean search_cb(const gchar *extcap _U_, gchar *output, void *data,
|
||||
static gboolean search_cb(const gchar *extcap _U_, const gchar *ifname _U_, gchar *output, void *data,
|
||||
char **err_str _U_) {
|
||||
extcap_token_sentence *tokens = NULL;
|
||||
GList *arguments = NULL;
|
||||
GList **il = (GList **) data;
|
||||
module_t * dev_module = NULL;
|
||||
|
||||
tokens = extcap_tokenize_sentences(output);
|
||||
arguments = extcap_parse_args(tokens);
|
||||
|
@ -453,6 +478,45 @@ static gboolean search_cb(const gchar *extcap _U_, gchar *output, void *data,
|
|||
extcap_debug_arguments ( arguments );
|
||||
#endif
|
||||
|
||||
dev_module = prefs_find_module("extcap");
|
||||
|
||||
if ( dev_module ) {
|
||||
GList * walker = arguments;
|
||||
|
||||
GRegex * regex = g_regex_new ("[-]+", (GRegexCompileFlags) 0, (GRegexMatchFlags) 0, NULL );
|
||||
if (regex) {
|
||||
while ( walker != NULL ) {
|
||||
extcap_arg * arg = (extcap_arg *)walker->data;
|
||||
|
||||
if ( arg->save ) {
|
||||
struct preference * pref = NULL;
|
||||
|
||||
gchar * pref_name = g_regex_replace(regex, arg->call, strlen(arg->call), 0, "", (GRegexMatchFlags) 0, NULL );
|
||||
gchar * pref_ifname = g_strdup(g_strconcat(ifname, ".", pref_name, NULL));
|
||||
|
||||
if ( ( pref = prefs_find_preference(dev_module, pref_ifname) ) == NULL ) {
|
||||
/* Set an initial value */
|
||||
if ( ! arg->storeval && arg->default_complex )
|
||||
arg->storeval = g_strdup(arg->default_complex->_val);
|
||||
|
||||
prefs_register_string_preference(dev_module, g_strdup(pref_ifname),
|
||||
arg->display, arg->display, (const gchar **)&(arg->storeval));
|
||||
} else {
|
||||
/* Been here before, restore stored value */
|
||||
if (! arg->storeval && pref->varp.string)
|
||||
arg->storeval = g_strdup(*(pref->varp.string));
|
||||
}
|
||||
|
||||
g_free(pref_name);
|
||||
g_free(pref_ifname);
|
||||
}
|
||||
|
||||
walker = g_list_next(walker);
|
||||
}
|
||||
g_regex_unref(regex);
|
||||
}
|
||||
}
|
||||
|
||||
*il = g_list_append(*il, arguments);
|
||||
|
||||
/* By returning false, extcap_foreach will break on first found */
|
||||
|
@ -494,16 +558,33 @@ extcap_has_configuration(const char * ifname, gboolean is_required) {
|
|||
arguments = extcap_get_if_configuration((const char *)( ifname ) );
|
||||
walker = g_list_first(arguments);
|
||||
|
||||
while ( walker != NULL && ! found )
|
||||
{
|
||||
while ( walker != NULL && ! found ) {
|
||||
item = g_list_first((GList *)(walker->data));
|
||||
while ( item != NULL && ! found )
|
||||
{
|
||||
if ( (extcap_arg *)(item->data) != NULL )
|
||||
{
|
||||
while ( item != NULL && ! found ) {
|
||||
if ( (extcap_arg *)(item->data) != NULL ) {
|
||||
extcap_arg * arg = (extcap_arg *)(item->data);
|
||||
/* Should required options be present, or any kind of options */
|
||||
if ( ! is_required || ((extcap_arg *)(item->data))->is_required )
|
||||
if ( ! is_required )
|
||||
found = TRUE;
|
||||
else if ( arg->is_required ) {
|
||||
gchar * stored = NULL;
|
||||
gchar * defval = NULL;
|
||||
|
||||
if ( arg->storeval != NULL )
|
||||
stored = arg->storeval;
|
||||
|
||||
if ( arg->default_complex != NULL && arg->default_complex->_val != NULL )
|
||||
defval = arg->default_complex->_val;
|
||||
|
||||
if ( arg->is_required ) {
|
||||
/* If stored and defval is identical and the argument is required,
|
||||
* configuration is needed */
|
||||
if ( defval && stored && g_strcmp0(stored, defval) == 0 )
|
||||
found = TRUE;
|
||||
else if ( ! defval && (!stored || strlen(g_strchomp(stored)) <= (size_t)0) )
|
||||
found = TRUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
item = item->next;
|
||||
|
@ -574,8 +655,8 @@ void extcap_cleanup(capture_options * capture_opts) {
|
|||
}
|
||||
}
|
||||
|
||||
static void
|
||||
extcap_arg_cb(gpointer key, gpointer value, gpointer data) {
|
||||
static gboolean
|
||||
extcap_add_arg_and_remove_cb(gpointer key, gpointer value, gpointer data) {
|
||||
GPtrArray *args = (GPtrArray *)data;
|
||||
|
||||
if ( key != NULL )
|
||||
|
@ -584,7 +665,11 @@ extcap_arg_cb(gpointer key, gpointer value, gpointer data) {
|
|||
|
||||
if ( value != NULL )
|
||||
g_ptr_array_add(args, g_strdup((const gchar*)value));
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
static void extcap_child_watch_cb(GPid pid, gint status _U_, gpointer user_data)
|
||||
|
@ -650,7 +735,7 @@ extcap_init_interfaces(capture_options *capture_opts)
|
|||
}
|
||||
add_arg(EXTCAP_ARGUMENT_RUN_PIPE);
|
||||
add_arg(interface_opts.extcap_fifo);
|
||||
if (interface_opts.extcap_args == NULL)
|
||||
if (interface_opts.extcap_args == NULL || g_hash_table_size(interface_opts.extcap_args) == 0)
|
||||
{
|
||||
/* User did not perform interface configuration.
|
||||
*
|
||||
|
@ -672,18 +757,29 @@ extcap_init_interfaces(capture_options *capture_opts)
|
|||
}
|
||||
|
||||
arg_list = g_list_first((GList *)elem->data);
|
||||
while (arg_list != NULL)
|
||||
{
|
||||
while (arg_list != NULL) {
|
||||
gchar * stored = NULL, * defval = NULL;
|
||||
/* In case of boolflags only first element in arg_list is relevant. */
|
||||
arg_iter = (extcap_arg*) (arg_list->data);
|
||||
if ( arg_iter->storeval != NULL )
|
||||
stored = arg_iter->storeval;
|
||||
|
||||
if (arg_iter->arg_type == EXTCAP_ARG_BOOLFLAG)
|
||||
{
|
||||
if (arg_iter->default_complex != NULL
|
||||
&& extcap_complex_get_bool(arg_iter->default_complex))
|
||||
{
|
||||
add_arg(arg_iter->call);
|
||||
if ( arg_iter->default_complex != NULL && arg_iter->default_complex->_val != NULL )
|
||||
defval = arg_iter->default_complex->_val;
|
||||
|
||||
/* Different data in storage then set for default */
|
||||
if ( g_strcmp0(stored, defval) != 0 ) {
|
||||
if ( arg_iter->arg_type == EXTCAP_ARG_BOOLFLAG ) {
|
||||
if ( g_strcmp0(stored, "true") == 0 )
|
||||
add_arg(arg_iter->call);
|
||||
} else {
|
||||
gchar * call = g_strconcat(arg_iter->call, " ", stored, NULL);
|
||||
add_arg(call);
|
||||
g_free(call);
|
||||
}
|
||||
} else if (arg_iter->arg_type == EXTCAP_ARG_BOOLFLAG) {
|
||||
if (extcap_complex_get_bool(arg_iter->default_complex))
|
||||
add_arg(arg_iter->call);
|
||||
}
|
||||
|
||||
arg_list = arg_list->next;
|
||||
|
@ -694,7 +790,7 @@ extcap_init_interfaces(capture_options *capture_opts)
|
|||
}
|
||||
else
|
||||
{
|
||||
g_hash_table_foreach(interface_opts.extcap_args, extcap_arg_cb, args);
|
||||
g_hash_table_foreach_remove(interface_opts.extcap_args, extcap_add_arg_and_remove_cb, args);
|
||||
}
|
||||
add_arg(NULL);
|
||||
#undef add_arg
|
||||
|
|
4
extcap.h
4
extcap.h
|
@ -63,6 +63,10 @@ typedef struct _extcap_info {
|
|||
extern "C" {
|
||||
#endif /* __cplusplus */
|
||||
|
||||
/* Registers preferences for all interfaces */
|
||||
void
|
||||
extcap_register_preferences(void);
|
||||
|
||||
/* try to get if capabilities from extcap */
|
||||
if_capabilities_t *
|
||||
extcap_get_if_dlts(const gchar * ifname, char ** err_str);
|
||||
|
|
|
@ -353,6 +353,7 @@ void extcap_free_arg(extcap_arg *a) {
|
|||
g_free(a->tooltip);
|
||||
g_free(a->fileextension);
|
||||
g_free(a->regexp);
|
||||
g_free(a->storeval);
|
||||
|
||||
if (a->range_start != NULL)
|
||||
extcap_free_complex(a->range_start);
|
||||
|
@ -404,6 +405,7 @@ extcap_arg *extcap_parse_arg_sentence(GList * args, extcap_token_sentence *s) {
|
|||
if (sent == EXTCAP_SENTENCE_ARG) {
|
||||
target_arg = g_new0(extcap_arg, 1);
|
||||
target_arg->arg_type = EXTCAP_ARG_UNKNOWN;
|
||||
target_arg->save = TRUE;
|
||||
|
||||
if ((v = extcap_find_param_by_type(s->param_list, EXTCAP_PARAM_ARGNUM))
|
||||
== NULL) {
|
||||
|
@ -489,7 +491,7 @@ extcap_arg *extcap_parse_arg_sentence(GList * args, extcap_token_sentence *s) {
|
|||
} else if (g_ascii_strcasecmp(v->value, "password") == 0) {
|
||||
target_arg->arg_type = EXTCAP_ARG_PASSWORD;
|
||||
/* default setting is to not save passwords */
|
||||
target_arg->do_not_save = TRUE;
|
||||
target_arg->save = FALSE;
|
||||
} else if (g_ascii_strcasecmp(v->value, "fileselect") == 0) {
|
||||
target_arg->arg_type = EXTCAP_ARG_FILESELECT;
|
||||
} else if (g_ascii_strcasecmp(v->value, "multicheck") == 0) {
|
||||
|
@ -502,7 +504,7 @@ extcap_arg *extcap_parse_arg_sentence(GList * args, extcap_token_sentence *s) {
|
|||
|
||||
if ((v = extcap_find_param_by_type(s->param_list, EXTCAP_PARAM_SAVE))
|
||||
!= NULL) {
|
||||
target_arg->do_not_save = ! g_regex_match_simple(EXTCAP_BOOLEAN_REGEX, v->value, G_REGEX_CASELESS, (GRegexMatchFlags)0 );
|
||||
target_arg->save = g_regex_match_simple(EXTCAP_BOOLEAN_REGEX, v->value, G_REGEX_CASELESS, (GRegexMatchFlags)0 );
|
||||
}
|
||||
|
||||
if ((v = extcap_find_param_by_type(s->param_list, EXTCAP_PARAM_RANGE))
|
||||
|
|
|
@ -107,7 +107,7 @@ typedef struct _extcap_arg {
|
|||
gboolean fileexists;
|
||||
|
||||
gboolean is_required;
|
||||
gboolean do_not_save;
|
||||
gboolean save;
|
||||
|
||||
gchar * regexp;
|
||||
|
||||
|
@ -117,6 +117,8 @@ typedef struct _extcap_arg {
|
|||
extcap_complex *range_end;
|
||||
extcap_complex *default_complex;
|
||||
|
||||
gchar * storeval;
|
||||
|
||||
GList * values;
|
||||
} extcap_arg;
|
||||
|
||||
|
|
|
@ -48,6 +48,10 @@
|
|||
#include <zlib.h> /* to get the libz version number */
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_EXTCAP
|
||||
#include <extcap.h>
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_LIBPORTAUDIO
|
||||
#include <portaudio.h>
|
||||
#endif /* HAVE_LIBPORTAUDIO */
|
||||
|
@ -2591,6 +2595,10 @@ main(int argc, char *argv[])
|
|||
register_all_plugin_tap_listeners();
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_EXTCAP
|
||||
extcap_register_preferences();
|
||||
#endif
|
||||
|
||||
register_all_tap_listeners();
|
||||
conversation_table_set_gui_info(init_conversation_table);
|
||||
hostlist_table_set_gui_info(init_hostlist_table);
|
||||
|
|
|
@ -40,9 +40,12 @@
|
|||
#include <QStandardItem>
|
||||
#include <QStandardItemModel>
|
||||
#include <QItemSelectionModel>
|
||||
#include <QRegExp>
|
||||
|
||||
#include <glib.h>
|
||||
#include <log.h>
|
||||
|
||||
#include <extcap.h>
|
||||
#include <epan/prefs.h>
|
||||
#include <color_utils.h>
|
||||
|
||||
|
@ -57,6 +60,7 @@ QWidget * ExtArgSelector::createEditor(QWidget * parent)
|
|||
{
|
||||
int counter = 0;
|
||||
int selected = -1;
|
||||
QString stored = _argument->storeval ? QString(_argument->storeval) : QString();
|
||||
|
||||
boxSelection = new QComboBox(parent);
|
||||
|
||||
|
@ -67,7 +71,10 @@ QWidget * ExtArgSelector::createEditor(QWidget * parent)
|
|||
while ( iter != values.constEnd() )
|
||||
{
|
||||
boxSelection->addItem((*iter).value(), (*iter).call());
|
||||
if ( (*iter).isDefault() )
|
||||
|
||||
if ( ! _argument->storeval && (*iter).isDefault() )
|
||||
selected = counter;
|
||||
else if ( _argument->storeval && stored.compare((*iter).call()) == 0 )
|
||||
selected = counter;
|
||||
|
||||
counter++;
|
||||
|
@ -135,7 +142,7 @@ QWidget * ExtArgRadio::createEditor(QWidget * parent)
|
|||
ExtcapValueList::const_iterator iter = values.constBegin();
|
||||
|
||||
while ( iter != values.constEnd() )
|
||||
{
|
||||
{
|
||||
QRadioButton * radio = new QRadioButton((*iter).value());
|
||||
QString callString = (*iter).call();
|
||||
callStrings->append(callString);
|
||||
|
@ -219,6 +226,15 @@ QWidget * ExtArgBool::createEditor(QWidget * parent)
|
|||
if ( _argument->tooltip != NULL )
|
||||
boolBox->setToolTip(QString().fromUtf8(_argument->tooltip));
|
||||
|
||||
if ( _argument->storeval )
|
||||
{
|
||||
QRegExp regexp(EXTCAP_BOOLEAN_REGEX);
|
||||
|
||||
bool savedstate = ( regexp.indexIn(QString(_argument->storeval[0]), 0) != -1 );
|
||||
if ( savedstate != state )
|
||||
state = savedstate;
|
||||
}
|
||||
|
||||
boolBox->setCheckState(state ? Qt::Checked : Qt::Unchecked );
|
||||
|
||||
connect (boolBox, SIGNAL(stateChanged(int)), SLOT(onIntChanged(int)));
|
||||
|
@ -244,6 +260,13 @@ QString ExtArgBool::value()
|
|||
return QString(boolBox->checkState() == Qt::Checked ? "true" : "false");
|
||||
}
|
||||
|
||||
QString ExtArgBool::prefValue()
|
||||
{
|
||||
if ( boolBox == NULL )
|
||||
return QString("false");
|
||||
return QString(boolBox->checkState() == Qt::Checked ? "true" : "false");
|
||||
}
|
||||
|
||||
bool ExtArgBool::isValid()
|
||||
{
|
||||
/* A bool is allways valid, but the base function checks on string length,
|
||||
|
@ -279,8 +302,17 @@ ExtArgText::ExtArgText(extcap_arg * argument) :
|
|||
|
||||
QWidget * ExtArgText::createEditor(QWidget * parent)
|
||||
{
|
||||
QString storeValue;
|
||||
QString text = defaultValue();
|
||||
|
||||
if ( _argument->storeval )
|
||||
{
|
||||
QString storeValue = _argument->storeval;
|
||||
|
||||
if ( storeValue.length() > 0 && storeValue.compare(text) != 0 )
|
||||
text = storeValue.trimmed();
|
||||
}
|
||||
|
||||
textBox = new QLineEdit(text, parent);
|
||||
|
||||
if ( _argument->tooltip != NULL )
|
||||
|
@ -334,7 +366,17 @@ ExtArgNumber::ExtArgNumber(extcap_arg * argument) :
|
|||
|
||||
QWidget * ExtArgNumber::createEditor(QWidget * parent)
|
||||
{
|
||||
QString storeValue;
|
||||
QString text = defaultValue();
|
||||
|
||||
if ( _argument->storeval )
|
||||
{
|
||||
QString storeValue = _argument->storeval;
|
||||
|
||||
if ( storeValue.length() > 0 && storeValue.compare(text) != 0 )
|
||||
text = storeValue;
|
||||
}
|
||||
|
||||
textBox = (QLineEdit *)ExtArgText::createEditor(parent);
|
||||
textBox->disconnect(SIGNAL(textChanged(QString)));
|
||||
|
||||
|
@ -525,6 +567,10 @@ QString ExtcapArgument::value()
|
|||
return QString();
|
||||
}
|
||||
|
||||
QString ExtcapArgument::prefValue()
|
||||
{
|
||||
return value();
|
||||
}
|
||||
|
||||
bool ExtcapArgument::isValid()
|
||||
{
|
||||
|
@ -544,10 +590,17 @@ QString ExtcapArgument::defaultValue()
|
|||
if ( str != 0 )
|
||||
return QString(str);
|
||||
}
|
||||
|
||||
return QString();
|
||||
}
|
||||
|
||||
QString ExtcapArgument::prefKey()
|
||||
{
|
||||
if ( ! _argument->save )
|
||||
return QString();
|
||||
|
||||
return QString(_argument->call).replace("-", "");
|
||||
}
|
||||
|
||||
bool ExtcapArgument::isRequired()
|
||||
{
|
||||
if ( _argument != NULL )
|
||||
|
|
|
@ -98,6 +98,9 @@ public:
|
|||
bool isValid();
|
||||
bool isRequired();
|
||||
|
||||
QString prefKey();
|
||||
virtual QString prefValue();
|
||||
|
||||
static ExtcapArgument * create(extcap_arg * argument = 0);
|
||||
|
||||
Q_SIGNALS:
|
||||
|
@ -189,6 +192,7 @@ public:
|
|||
virtual QString value();
|
||||
virtual bool isValid();
|
||||
virtual QString defaultValue();
|
||||
virtual QString prefValue();
|
||||
|
||||
private:
|
||||
|
||||
|
|
|
@ -54,6 +54,11 @@
|
|||
|
||||
#include "qt_ui_utils.h"
|
||||
|
||||
#include <epan/prefs.h>
|
||||
#include <ui/preference_utils.h>
|
||||
|
||||
#include <ui/qt/wireshark_application.h>
|
||||
|
||||
#include <ui/qt/extcap_argument.h>
|
||||
#include <ui/qt/extcap_argument_file.h>
|
||||
#include <ui/qt/extcap_argument_multiselect.h>
|
||||
|
@ -68,6 +73,7 @@ ExtcapOptionsDialog::ExtcapOptionsDialog(QWidget *parent) :
|
|||
|
||||
setWindowTitle(wsApp->windowTitleString(tr("Extcap Interface Options")));
|
||||
|
||||
ui->checkSaveOnStart->setCheckState(prefs.extcap_save_on_start ? Qt::Checked : Qt::Unchecked);
|
||||
|
||||
ui->buttonBox->button(QDialogButtonBox::Ok)->setText(tr("Start"));
|
||||
}
|
||||
|
@ -118,6 +124,12 @@ ExtcapOptionsDialog::~ExtcapOptionsDialog()
|
|||
void ExtcapOptionsDialog::on_buttonBox_accepted()
|
||||
{
|
||||
if (saveOptionToCaptureInfo()) {
|
||||
/* Starting a new capture with those values */
|
||||
prefs.extcap_save_on_start = ui->checkSaveOnStart->checkState() == Qt::Checked;
|
||||
|
||||
if ( prefs.extcap_save_on_start )
|
||||
storeValues();
|
||||
|
||||
accept();
|
||||
}
|
||||
}
|
||||
|
@ -281,7 +293,7 @@ bool ExtcapOptionsDialog::saveOptionToCaptureInfo()
|
|||
device = g_array_index(global_capture_opts.all_ifaces, interface_t, device_idx);
|
||||
global_capture_opts.all_ifaces = g_array_remove_index(global_capture_opts.all_ifaces, device_idx);
|
||||
|
||||
ret_args = g_hash_table_new(g_str_hash, g_str_equal);
|
||||
ret_args = g_hash_table_new_full(g_str_hash, g_str_equal, g_free, g_free);
|
||||
|
||||
ExtcapArgumentList::const_iterator iter;
|
||||
|
||||
|
@ -301,6 +313,7 @@ bool ExtcapOptionsDialog::saveOptionToCaptureInfo()
|
|||
|
||||
gchar * call_string = g_strdup(call.toStdString().c_str());
|
||||
gchar * value_string = g_strdup(value.toStdString().c_str());
|
||||
|
||||
g_hash_table_insert(ret_args, call_string, value_string );
|
||||
}
|
||||
|
||||
|
@ -313,6 +326,77 @@ bool ExtcapOptionsDialog::saveOptionToCaptureInfo()
|
|||
return true;
|
||||
}
|
||||
|
||||
void ExtcapOptionsDialog::storeValues()
|
||||
{
|
||||
GHashTable * entries = g_hash_table_new(g_str_hash, g_str_equal);
|
||||
ExtcapArgumentList::const_iterator iter;
|
||||
|
||||
QString value;
|
||||
|
||||
/* All arguments are being iterated, to ensure, that any error handling catches all arguments */
|
||||
for(iter = extcapArguments.constBegin(); iter != extcapArguments.constEnd(); ++iter)
|
||||
{
|
||||
ExtcapArgument * argument = (ExtcapArgument *)(*iter);
|
||||
|
||||
/* The dynamic casts are necessary, because we come here using the Signal/Slot system
|
||||
* of Qt, and -in short- Q_OBJECT classes cannot be multiple inherited. Another possibility
|
||||
* would be to use Q_INTERFACE, but this causes way more nightmares, and we really just
|
||||
* need here an explicit cast for the check functionality */
|
||||
if ( dynamic_cast<ExtArgBool *>((*iter)) != NULL)
|
||||
{
|
||||
value = ((ExtArgBool *)*iter)->prefValue();
|
||||
}
|
||||
else if ( dynamic_cast<ExtArgRadio *>((*iter)) != NULL)
|
||||
{
|
||||
value = ((ExtArgRadio *)*iter)->prefValue();
|
||||
}
|
||||
else if ( dynamic_cast<ExtArgSelector *>((*iter)) != NULL)
|
||||
{
|
||||
value = ((ExtArgSelector *)*iter)->prefValue();
|
||||
}
|
||||
else if ( dynamic_cast<ExtArgMultiSelect *>((*iter)) != NULL)
|
||||
{
|
||||
value = ((ExtArgMultiSelect *)*iter)->prefValue();
|
||||
}
|
||||
else if ( dynamic_cast<ExtcapArgumentFileSelection *>((*iter)) != NULL)
|
||||
{
|
||||
value = ((ExtcapArgumentFileSelection *)*iter)->prefValue();
|
||||
}
|
||||
else if ( dynamic_cast<ExtArgNumber *>((*iter)) != NULL)
|
||||
{
|
||||
value = ((ExtArgNumber *)*iter)->prefValue();
|
||||
}
|
||||
else if ( dynamic_cast<ExtArgText *>((*iter)) != NULL)
|
||||
{
|
||||
value = ((ExtArgText *)*iter)->prefValue();
|
||||
}
|
||||
else
|
||||
value = (*iter)->prefValue();
|
||||
|
||||
QString prefKey = QString("%1.%2").arg(device_name).arg(argument->prefKey());
|
||||
if ( prefKey.length() > 0 )
|
||||
{
|
||||
gchar * key = g_strdup(prefKey.toStdString().c_str());
|
||||
gchar * val = g_strdup(value.length() == 0 ? " " : value.toStdString().c_str());
|
||||
|
||||
/* Setting the internally stored value for the preference to the new value */
|
||||
(*iter)->argument()->storeval = g_strdup(val);
|
||||
|
||||
g_hash_table_insert(entries, key, val);
|
||||
}
|
||||
}
|
||||
|
||||
if ( g_hash_table_size(entries) > 0 )
|
||||
{
|
||||
if ( prefs_store_ext_multiple("extcap", entries) )
|
||||
{
|
||||
wsApp->emitAppSignal(WiresharkApplication::PacketDissectionChanged);
|
||||
wsApp->emitAppSignal(WiresharkApplication::PreferencesChanged);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#endif /* HAVE_LIBPCAP */
|
||||
|
||||
/*
|
||||
|
|
|
@ -70,6 +70,7 @@ private:
|
|||
ExtcapArgumentList extcapArguments;
|
||||
|
||||
bool saveOptionToCaptureInfo();
|
||||
void storeValues();
|
||||
};
|
||||
|
||||
#endif /* HAVE_EXTCAP */
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>600</width>
|
||||
<height>55</height>
|
||||
<height>92</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="minimumSize">
|
||||
|
@ -20,6 +20,23 @@
|
|||
<item>
|
||||
<layout class="QVBoxLayout" name="verticalLayout"/>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="Line" name="line">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QCheckBox" name="checkSaveOnStart">
|
||||
<property name="text">
|
||||
<string>Save parameter on capture start</string>
|
||||
</property>
|
||||
<property name="checked">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QDialogButtonBox" name="buttonBox">
|
||||
<property name="standardButtons">
|
||||
|
|
|
@ -70,6 +70,10 @@
|
|||
#include <codecs/codecs.h>
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_EXTCAP
|
||||
#include <extcap.h>
|
||||
#endif
|
||||
|
||||
/* general (not Qt specific) */
|
||||
#include "file.h"
|
||||
#include "epan/color_filters.h"
|
||||
|
@ -839,6 +843,10 @@ int main(int argc, char *argv[])
|
|||
register_all_plugin_tap_listeners();
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_EXTCAP
|
||||
extcap_register_preferences();
|
||||
#endif
|
||||
|
||||
register_all_tap_listeners();
|
||||
conversation_table_set_gui_info(init_conversation_table);
|
||||
hostlist_table_set_gui_info(init_endpoint_table);
|
||||
|
|
Loading…
Reference in New Issue