From 5bd252c44fd47ccf95ed6cedfa8759ac1c1c9dae Mon Sep 17 00:00:00 2001 From: Gerald Combs Date: Sat, 29 Dec 2012 01:39:02 +0000 Subject: [PATCH] Remove some duplicate code from ui/profile.c and move in more code from ui/gtk/profile_dialog.c. Use the correct profile list in profile_dialog.c so that deletion works. Add a profile dialog to the Qt port. For some reason it crashes when changing configuration profiles, which might be related to bug 7722. Move the Qt configuration profile initialization from main.cpp to wireshark_application.cpp. Make sure QMenuBar doesn't grab the configuration profiles action on OS X. Add more role color names to tango_colors.h. svn path=/trunk/; revision=46834 --- epan/prefs.c | 7 + ui/gtk/main_menubar.c | 4 +- ui/gtk/profile_dlg.c | 130 +-------------- ui/profile.c | 154 +++++++++++++++-- ui/profile.h | 13 ++ ui/qt/QtShark.pro | 8 +- ui/qt/main.cpp | 123 +------------- ui/qt/main_window.cpp | 4 + ui/qt/main_window.h | 7 +- ui/qt/main_window.ui | 22 ++- ui/qt/main_window_slots.cpp | 35 +++- ui/qt/profile_dialog.cpp | 287 ++++++++++++++++++++++++++++++++ ui/qt/profile_dialog.h | 58 +++++++ ui/qt/profile_dialog.ui | 168 +++++++++++++++++++ ui/qt/syntax_line_edit.cpp | 8 +- ui/qt/tango_colors.h | 7 + ui/qt/time_shift_dialog.cpp | 12 +- ui/qt/wireshark_application.cpp | 219 +++++++++++++++++++++++- ui/qt/wireshark_application.h | 7 + ui/recent.h | 6 +- 20 files changed, 995 insertions(+), 284 deletions(-) create mode 100644 ui/qt/profile_dialog.cpp create mode 100644 ui/qt/profile_dialog.h create mode 100644 ui/qt/profile_dialog.ui diff --git a/epan/prefs.c b/epan/prefs.c index 84775b84da..55a53dd306 100644 --- a/epan/prefs.c +++ b/epan/prefs.c @@ -189,11 +189,13 @@ free_pref(gpointer data, gpointer user_data _U_) g_free((char *)*pref->varp.string); *pref->varp.string = NULL; g_free(pref->default_val.string); + pref->default_val.string = NULL; break; case PREF_RANGE: g_free(*pref->varp.range); *pref->varp.range = NULL; g_free(pref->default_val.range); + pref->default_val.range = NULL; break; case PREF_CUSTOM: pref->custom_cbs.free_cb(pref); @@ -1270,6 +1272,7 @@ static void column_hidden_free_cb(pref_t* pref) g_free((char *)*pref->varp.string); *pref->varp.string = NULL; g_free(pref->default_val.string); + pref->default_val.string = NULL; } static void column_hidden_reset_cb(pref_t* pref) @@ -1288,6 +1291,8 @@ static prefs_set_pref_e column_hidden_set_cb(pref_t* pref, const gchar* value, g *changed = TRUE; g_free((void *)*pref->varp.string); *pref->varp.string = g_strdup(value); + } else { + *pref->varp.string = NULL; } /* @@ -1698,6 +1703,8 @@ static void colorized_frame_free_cb(pref_t* pref) g_free((char *)*pref->varp.string); *pref->varp.string = NULL; g_free(pref->default_val.string); + pref->default_val.string = NULL; + } static void colorized_frame_reset_cb(pref_t* pref) diff --git a/ui/gtk/main_menubar.c b/ui/gtk/main_menubar.c index 511ae29d2c..d92947d250 100644 --- a/ui/gtk/main_menubar.c +++ b/ui/gtk/main_menubar.c @@ -606,9 +606,9 @@ timestamp_seconds_time_cb(GtkAction *action _U_, gpointer user_data _U_) static void timestamp_format_new_cb (GtkRadioAction *action, GtkRadioAction *current _U_, gpointer user_data _U_) { - gint value; + ts_type value; - value = gtk_radio_action_get_current_value (action); + value = (ts_type) gtk_radio_action_get_current_value (action); if (recent.gui_time_format != value) { timestamp_set_type(value); recent.gui_time_format = value; diff --git a/ui/gtk/profile_dlg.c b/ui/gtk/profile_dlg.c index 25c061b45b..f8fea7fc12 100644 --- a/ui/gtk/profile_dlg.c +++ b/ui/gtk/profile_dlg.c @@ -77,7 +77,8 @@ fill_list(GtkWidget *main_w) profile_l = GTK_TREE_VIEW(g_object_get_data(G_OBJECT(main_w), E_PROF_PROFILE_L_KEY)); store = GTK_LIST_STORE(gtk_tree_view_get_model(profile_l)); - fl_entry = current_profile_list(); + init_profile_list(); + fl_entry = edited_profile_list(); while (fl_entry && fl_entry->data) { profile = (profile_def *) fl_entry->data; gtk_list_store_append(store, &iter); @@ -135,132 +136,13 @@ profile_select(GtkWidget *main_w, GtkTreeView *profile_l, gboolean destroy) static void profile_apply(GtkWidget *main_w, GtkTreeView *profile_l, gboolean destroy) { - char *pf_dir_path, *pf_dir_path2, *pf_filename; - GList *fl1, *fl2; - profile_def *profile1, *profile2; - gboolean found; const gchar *err_msg; - /* First validate all profile names */ - fl1 = edited_profile_list(); - while (fl1) { - profile1 = (profile_def *) fl1->data; - g_strstrip(profile1->name); - if ((err_msg = profile_name_is_valid(profile1->name)) != NULL) { - simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, "%s", err_msg); - return; - } - fl1 = g_list_next(fl1); + if ((err_msg = apply_profile_changes()) != NULL) { + simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, "%s", err_msg); + return; } - /* Then do all copy profiles */ - fl1 = edited_profile_list(); - while (fl1) { - profile1 = (profile_def *) fl1->data; - g_strstrip(profile1->name); - if (profile1->status == PROF_STAT_COPY) { - if (create_persconffile_profile(profile1->name, &pf_dir_path) == -1) { - simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, - "Can't create directory\n\"%s\":\n%s.", - pf_dir_path, g_strerror(errno)); - - g_free(pf_dir_path); - } - profile1->status = PROF_STAT_EXISTS; - - if (profile1->reference) { - if (copy_persconffile_profile(profile1->name, profile1->reference, profile1->from_global, - &pf_filename, &pf_dir_path, &pf_dir_path2) == -1) { - simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, - "Can't copy file \"%s\" in directory\n\"%s\" to\n\"%s\":\n%s.", - pf_filename, pf_dir_path2, pf_dir_path, g_strerror(errno)); - - g_free(pf_filename); - g_free(pf_dir_path); - g_free(pf_dir_path2); - } - } - - g_free (profile1->reference); - profile1->reference = g_strdup(profile1->name); - } - fl1 = g_list_next(fl1); - } - - - /* Then create new and rename changed */ - fl1 = edited_profile_list(); - while (fl1) { - profile1 = (profile_def *) fl1->data; - g_strstrip(profile1->name); - if (profile1->status == PROF_STAT_NEW) { - /* We do not create a directory for the default profile */ - if (strcmp(profile1->name, DEFAULT_PROFILE)!=0) { - if (create_persconffile_profile(profile1->name, &pf_dir_path) == -1) { - simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, - "Can't create directory\n\"%s\":\n%s.", - pf_dir_path, g_strerror(errno)); - - g_free(pf_dir_path); - } - profile1->status = PROF_STAT_EXISTS; - - g_free (profile1->reference); - profile1->reference = g_strdup(profile1->name); - } - } else if (profile1->status == PROF_STAT_CHANGED) { - if (strcmp(profile1->reference, profile1->name)!=0) { - /* Rename old profile directory to new */ - if (rename_persconffile_profile(profile1->reference, profile1->name, - &pf_dir_path, &pf_dir_path2) == -1) { - simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, - "Can't rename directory\n\"%s\" to\n\"%s\":\n%s.", - pf_dir_path, pf_dir_path2, g_strerror(errno)); - - g_free(pf_dir_path); - g_free(pf_dir_path2); - } - profile1->status = PROF_STAT_EXISTS; - g_free (profile1->reference); - profile1->reference = g_strdup(profile1->name); - } - } - fl1 = g_list_next(fl1); - } - - /* Last remove deleted */ - fl1 = current_profile_list(); - while (fl1) { - found = FALSE; - profile1 = (profile_def *) fl1->data; - fl2 = edited_profile_list(); - while (fl2) { - profile2 = (profile_def *) fl2->data; - if (!profile2->is_global) { - if (strcmp(profile1->name, profile2->name)==0) { - /* Profile exists in both lists */ - found = TRUE; - } else if (strcmp(profile1->name, profile2->reference)==0) { - /* Profile has been renamed */ - found = TRUE; - } - } - fl2 = g_list_next(fl2); - } - if (!found) { - /* Exists in existing list and not in edited, this is a deleted profile */ - if (delete_persconffile_profile(profile1->name, &pf_dir_path) == -1) { - simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, - "Can't delete profile directory\n\"%s\":\n%s.", - pf_dir_path, g_strerror(errno)); - - g_free(pf_dir_path); - } - } - fl1 = g_list_next(fl1); - } - - copy_profile_list(); profile_select(main_w, profile_l, destroy); } @@ -899,7 +781,7 @@ profile_name_edit_ok (GtkWidget *w _U_, gpointer parent_w) g_free(pf_dir_path); } else if (strlen (profile_name) && copy_persconffile_profile(new_name, profile_name, from_global, &pf_filename, - &pf_dir_path, &pf_dir_path2) == -1) + &pf_dir_path, &pf_dir_path2) != 0) { simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, "Can't copy file \"%s\" in directory\n\"%s\" to\n\"%s\":\n%s.", diff --git a/ui/profile.c b/ui/profile.c index cb27885ba4..3d737960a4 100644 --- a/ui/profile.c +++ b/ui/profile.c @@ -33,30 +33,19 @@ #include #include +#include "profile.h" + #include "ui/recent.h" +#include "ui/simple_dialog.h" #include static GList *current_profiles = NULL; static GList *edited_profiles = NULL; -#define PROF_STAT_DEFAULT 1 -#define PROF_STAT_EXISTS 2 -#define PROF_STAT_NEW 3 -#define PROF_STAT_CHANGED 4 -#define PROF_STAT_COPY 5 - #define PROF_OPERATION_NEW 1 #define PROF_OPERATION_EDIT 2 -typedef struct { - char *name; /* profile name */ - char *reference; /* profile reference */ - int status; - gboolean is_global; - gboolean from_global; -} profile_def; - GList * current_profile_list(void) { return g_list_first(current_profiles); } @@ -71,7 +60,7 @@ add_profile_entry(GList *fl, const char *profilename, const char *reference, int { profile_def *profile; - profile = (profile_def *) g_malloc(sizeof(profile_def)); + profile = (profile_def *) g_malloc0(sizeof(profile_def)); profile->name = g_strdup(profilename); profile->reference = g_strdup(reference); profile->status = status; @@ -124,6 +113,137 @@ get_profile_parent (const gchar *profilename) return profilename; } +const gchar *apply_profile_changes(void) { + char *pf_dir_path, *pf_dir_path2, *pf_filename; + GList *fl1, *fl2; + profile_def *profile1, *profile2; + gboolean found; + emem_strbuf_t *message = ep_strbuf_new(NULL); + const gchar *err_msg; + + /* First validate all profile names */ + fl1 = edited_profile_list(); + while (fl1) { + profile1 = (profile_def *) fl1->data; + g_strstrip(profile1->name); + if ((err_msg = profile_name_is_valid(profile1->name)) != NULL) { + ep_strbuf_printf(message, "%s", err_msg); + return message->str; + } + fl1 = g_list_next(fl1); + } + + /* Then do all copy profiles */ + fl1 = edited_profile_list(); + while (fl1) { + profile1 = (profile_def *) fl1->data; + g_strstrip(profile1->name); + if (profile1->status == PROF_STAT_COPY) { + if (create_persconffile_profile(profile1->name, &pf_dir_path) == -1) { + ep_strbuf_printf(message, + "Can't create directory\n\"%s\":\n%s.", + pf_dir_path, g_strerror(errno)); + + g_free(pf_dir_path); + } + profile1->status = PROF_STAT_EXISTS; + + if (profile1->reference) { + if (copy_persconffile_profile(profile1->name, profile1->reference, profile1->from_global, + &pf_filename, &pf_dir_path, &pf_dir_path2) == -1) { + simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, + "Can't copy file \"%s\" in directory\n\"%s\" to\n\"%s\":\n%s.", + pf_filename, pf_dir_path2, pf_dir_path, g_strerror(errno)); + + g_free(pf_filename); + g_free(pf_dir_path); + g_free(pf_dir_path2); + } + } + + g_free (profile1->reference); + profile1->reference = g_strdup(profile1->name); + } + fl1 = g_list_next(fl1); + } + + + /* Then create new and rename changed */ + fl1 = edited_profile_list(); + while (fl1) { + profile1 = (profile_def *) fl1->data; + g_strstrip(profile1->name); + if (profile1->status == PROF_STAT_NEW) { + /* We do not create a directory for the default profile */ + if (strcmp(profile1->name, DEFAULT_PROFILE)!=0) { + if (create_persconffile_profile(profile1->name, &pf_dir_path) == -1) { + simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, + "Can't create directory\n\"%s\":\n%s.", + pf_dir_path, g_strerror(errno)); + + g_free(pf_dir_path); + } + profile1->status = PROF_STAT_EXISTS; + + g_free (profile1->reference); + profile1->reference = g_strdup(profile1->name); + } + } else if (profile1->status == PROF_STAT_CHANGED) { + if (strcmp(profile1->reference, profile1->name)!=0) { + /* Rename old profile directory to new */ + if (rename_persconffile_profile(profile1->reference, profile1->name, + &pf_dir_path, &pf_dir_path2) == -1) { + simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, + "Can't rename directory\n\"%s\" to\n\"%s\":\n%s.", + pf_dir_path, pf_dir_path2, g_strerror(errno)); + + g_free(pf_dir_path); + g_free(pf_dir_path2); + } + profile1->status = PROF_STAT_EXISTS; + g_free (profile1->reference); + profile1->reference = g_strdup(profile1->name); + } + } + fl1 = g_list_next(fl1); + } + + /* Last remove deleted */ + fl1 = current_profile_list(); + while (fl1) { + found = FALSE; + profile1 = (profile_def *) fl1->data; + fl2 = edited_profile_list(); + while (fl2) { + profile2 = (profile_def *) fl2->data; + if (!profile2->is_global) { + if (strcmp(profile1->name, profile2->name)==0) { + /* Profile exists in both lists */ + found = TRUE; + } else if (strcmp(profile1->name, profile2->reference)==0) { + /* Profile has been renamed */ + found = TRUE; + } + } + fl2 = g_list_next(fl2); + } + if (!found) { + /* Exists in existing list and not in edited, this is a deleted profile */ + if (delete_persconffile_profile(profile1->name, &pf_dir_path) == -1) { + simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, + "Can't delete profile directory\n\"%s\":\n%s.", + pf_dir_path, g_strerror(errno)); + + g_free(pf_dir_path); + } + } + fl1 = g_list_next(fl1); + } + + copy_profile_list(); + return NULL; +} + GList * add_to_profile_list(const char *name, const char *expression, int status, gboolean is_global, gboolean from_global) @@ -191,15 +311,13 @@ init_profile_list(void) { WS_DIR *dir; /* scanned directory */ WS_DIRENT *file; /* current file */ - /*GList *fl_entry;*/ - /*profile_def *profile;*/ const gchar *profiles_dir, *name; gchar *filename; empty_profile_list(TRUE); /* Default entry */ - /*fl_entry =*/ add_to_profile_list(DEFAULT_PROFILE, DEFAULT_PROFILE, PROF_STAT_DEFAULT, FALSE, FALSE); + add_to_profile_list(DEFAULT_PROFILE, DEFAULT_PROFILE, PROF_STAT_DEFAULT, FALSE, FALSE); /* Local (user) profiles */ profiles_dir = get_profiles_dir(); diff --git a/ui/profile.h b/ui/profile.h index fc14cd0bcf..01a8a2c536 100644 --- a/ui/profile.h +++ b/ui/profile.h @@ -26,6 +26,10 @@ #ifndef __PROFILE_H__ #define __PROFILE_H__ +#ifdef __cplusplus +extern "C" { +#endif /* __cplusplus */ + /** @file * "Configuration Profiles" dialog box * @ingroup dialog_group @@ -95,6 +99,11 @@ GList * current_profile_list(void); */ GList * edited_profile_list(void); +/** Apply the changes in the edited profile list + * @return NULL if the operation was successful or an error message otherwise. + */ +const gchar *apply_profile_changes(void); + /** Given a profile name, return the name of its parent profile. * * @param profilename Child profile name @@ -110,4 +119,8 @@ const gchar *get_profile_parent (const gchar *profilename); */ const gchar *profile_name_is_valid(const gchar *name); +#ifdef __cplusplus +} +#endif /* __cplusplus */ + #endif /* __PROFILE_H__ */ diff --git a/ui/qt/QtShark.pro b/ui/qt/QtShark.pro index 56a48f0f2b..5184e667d0 100644 --- a/ui/qt/QtShark.pro +++ b/ui/qt/QtShark.pro @@ -192,7 +192,8 @@ FORMS += main_window.ui \ print_dialog.ui \ search_frame.ui \ splash_overlay.ui \ - time_shift_dialog.ui + time_shift_dialog.ui \ + profile_dialog.ui win32 { ## These should be in config.pri ?? !isEmpty(PORTAUDIO_DIR) { @@ -225,7 +226,7 @@ HEADERS += $$HEADERS_WS_C \ search_frame.h \ splash_overlay.h \ tango_colors.h \ - time_shift_dialog.h + profile_dialog.h win32 { OBJECTS_WS_C = $$SOURCES_WS_C @@ -442,4 +443,5 @@ SOURCES += \ splash_overlay.cpp \ syntax_line_edit.cpp \ time_shift_dialog.cpp \ - wireshark_application.cpp + wireshark_application.cpp \ + profile_dialog.cpp diff --git a/ui/qt/main.cpp b/ui/qt/main.cpp index 983fe8b0b0..c8f4700890 100644 --- a/ui/qt/main.cpp +++ b/ui/qt/main.cpp @@ -65,7 +65,6 @@ /* general (not Qt specific) */ #include "file.h" #include "summary.h" -#include "filters.h" #include "disabled_protos.h" #include "color.h" #include "color_filters.h" @@ -161,110 +160,6 @@ main_cf_callback(gint event, gpointer data, gpointer user_data ) wsApp->captureFileCallback(event, data); } -// XXX Copied from ui/gtk/main.c. This should be moved to a common location. -static e_prefs * -read_configuration_files(char **gdp_path, char **dp_path) -{ - int gpf_open_errno, gpf_read_errno; - int cf_open_errno, df_open_errno; - int gdp_open_errno, gdp_read_errno; - int dp_open_errno, dp_read_errno; - char *gpf_path, *pf_path; - char *cf_path, *df_path; - int pf_open_errno, pf_read_errno; - e_prefs *prefs_p; - - /* Read the preference files. */ - prefs_p = read_prefs(&gpf_open_errno, &gpf_read_errno, &gpf_path, - &pf_open_errno, &pf_read_errno, &pf_path); - - if (gpf_path != NULL) { - if (gpf_open_errno != 0) { - simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, - "Could not open global preferences file\n\"%s\": %s.", gpf_path, - g_strerror(gpf_open_errno)); - } - if (gpf_read_errno != 0) { - simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, - "I/O error reading global preferences file\n\"%s\": %s.", gpf_path, - g_strerror(gpf_read_errno)); - } - } - if (pf_path != NULL) { - if (pf_open_errno != 0) { - simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, - "Could not open your preferences file\n\"%s\": %s.", pf_path, - g_strerror(pf_open_errno)); - } - if (pf_read_errno != 0) { - simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, - "I/O error reading your preferences file\n\"%s\": %s.", pf_path, - g_strerror(pf_read_errno)); - } - g_free(pf_path); - pf_path = NULL; - } - -#ifdef _WIN32 - /* if the user wants a console to be always there, well, we should open one for him */ - if (prefs_p->gui_console_open == console_open_always) { - create_console(); - } -#endif - - /* Read the capture filter file. */ - read_filter_list(CFILTER_LIST, &cf_path, &cf_open_errno); - if (cf_path != NULL) { - simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, - "Could not open your capture filter file\n\"%s\": %s.", cf_path, - g_strerror(cf_open_errno)); - g_free(cf_path); - } - - /* Read the display filter file. */ - read_filter_list(DFILTER_LIST, &df_path, &df_open_errno); - if (df_path != NULL) { - simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, - "Could not open your display filter file\n\"%s\": %s.", df_path, - g_strerror(df_open_errno)); - g_free(df_path); - } - - /* Read the disabled protocols file. */ - read_disabled_protos_list(gdp_path, &gdp_open_errno, &gdp_read_errno, - dp_path, &dp_open_errno, &dp_read_errno); - if (*gdp_path != NULL) { - if (gdp_open_errno != 0) { - simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, - "Could not open global disabled protocols file\n\"%s\": %s.", - *gdp_path, g_strerror(gdp_open_errno)); - } - if (gdp_read_errno != 0) { - simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, - "I/O error reading global disabled protocols file\n\"%s\": %s.", - *gdp_path, g_strerror(gdp_read_errno)); - } - g_free(*gdp_path); - *gdp_path = NULL; - } - if (*dp_path != NULL) { - if (dp_open_errno != 0) { - simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, - "Could not open your disabled protocols file\n\"%s\": %s.", *dp_path, - g_strerror(dp_open_errno)); - } - if (dp_read_errno != 0) { - simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, - "I/O error reading your disabled protocols file\n\"%s\": %s.", *dp_path, - g_strerror(dp_read_errno)); - } - g_free(*dp_path); - *dp_path = NULL; - } - - return prefs_p; -} - /* update the main window */ void main_window_update(void) { @@ -585,8 +480,8 @@ get_gui_runtime_info(GString *str) /* And now our feature presentation... [ fade to music ] */ int main(int argc, char *argv[]) { - WiresharkApplication a(argc, argv); - MainWindow *w; + WiresharkApplication ws_app(argc, argv); + MainWindow *main_w; // char *init_progfile_dir_error; // char *s; @@ -637,24 +532,24 @@ int main(int argc, char *argv[]) g_log(NULL, G_LOG_LEVEL_DEBUG, "Translator %s", locale.toStdString().c_str()); QTranslator translator; translator.load(QString(":/i18n/qtshark_") + locale); - a.installTranslator(&translator); + ws_app.installTranslator(&translator); QTranslator qtTranslator; qtTranslator.load("qt_" + QLocale::system().name(), QLibraryInfo::location(QLibraryInfo::TranslationsPath)); - a.installTranslator(&qtTranslator); + ws_app.installTranslator(&qtTranslator); // Hopefully we won't have to use QString::fromUtf8() in as many places. QTextCodec *utf8codec = QTextCodec::codecForName("UTF-8"); QTextCodec::setCodecForCStrings(utf8codec); QTextCodec::setCodecForTr(utf8codec); - w = new(MainWindow); + main_w = new(MainWindow); // w->setEnabled(false); - w->show(); + main_w->show(); // We may not need a queued connection here but it would seem to make sense // to force the issue. - w->connect(&a, SIGNAL(openCaptureFile(QString&)), - w, SLOT(openCaptureFile(QString&))); + main_w->connect(&ws_app, SIGNAL(openCaptureFile(QString&)), + main_w, SLOT(openCaptureFile(QString&))); // XXX Should the remaining code be in WiresharkApplcation::WiresharkApplication? #ifdef HAVE_LIBPCAP @@ -946,7 +841,7 @@ int main(int argc, char *argv[]) splash_update(RA_PREFERENCES, NULL, NULL); - prefs_p = read_configuration_files (&gdp_path, &dp_path); + prefs_p = ws_app.readConfigurationFiles (&gdp_path, &dp_path); /* Removed thread code: * http://anonsvn.wireshark.org/viewvc/viewvc.cgi?view=rev&revision=35027 */ diff --git a/ui/qt/main_window.cpp b/ui/qt/main_window.cpp index 5bf58d8b9c..0e78e59b4d 100644 --- a/ui/qt/main_window.cpp +++ b/ui/qt/main_window.cpp @@ -109,6 +109,10 @@ MainWindow::MainWindow(QWidget *parent) : main_ui_->actionFileClose->setIcon( QIcon().fromTheme("process-stop", style()->standardIcon(QStyle::SP_DialogCloseButton))); + // If we use the name "Configuration Profiles" OS X QMenuBar will match "config" and + // use the "profiles" action as the default preferences item. + main_ui_->actionEditConfigurationProfiles->setText(main_ui_->actionEditConfigurationProfiles->iconText()); + // In Qt4 multiple toolbars and "pretty" are mutually exculsive on OS X. If // unifiedTitleAndToolBarOnMac is enabled everything ends up in the same row. // https://bugreports.qt-project.org/browse/QTBUG-22433 diff --git a/ui/qt/main_window.h b/ui/qt/main_window.h index 447664b907..73e6093a85 100644 --- a/ui/qt/main_window.h +++ b/ui/qt/main_window.h @@ -158,6 +158,8 @@ public slots: void captureFileClosing(const capture_file *cf); void captureFileClosed(const capture_file *cf); + void configurationProfileChanged(const gchar *profile_name); + private slots: // in main_window_slots.cpp void startCapture(); @@ -210,8 +212,8 @@ private slots: void on_actionEditMarkPacket_triggered(); void on_actionEditMarkAllDisplayed_triggered(); void on_actionEditUnmarkAllDisplayed_triggered(); - void on_actionEditFindNextMark_triggered(); - void on_actionEditFindPreviousMark_triggered(); + void on_actionEditNextMark_triggered(); + void on_actionEditPreviousMark_triggered(); void on_actionEditIgnorePacket_triggered(); void on_actionEditIgnoreAllDisplayed_triggered(); void on_actionEditUnignoreAllDisplayed_triggered(); @@ -221,6 +223,7 @@ private slots: void on_actionEditPreviousTimeReference_triggered(); void on_actionEditTimeShift_triggered(); void on_actionEditPacketComment_triggered(); + void on_actionEditConfigurationProfiles_triggered(); void on_actionGoGoToPacket_triggered(); void resetPreviousFocus(); diff --git a/ui/qt/main_window.ui b/ui/qt/main_window.ui index 3f0384227f..64d3e0d642 100644 --- a/ui/qt/main_window.ui +++ b/ui/qt/main_window.ui @@ -371,6 +371,9 @@ Ctrl+Q + + QAction::QuitRole + @@ -532,6 +535,9 @@ &About Wireshark + + QAction::AboutRole + true @@ -1140,19 +1146,28 @@ + + false + + Name set in iconText to keep QMenuBar from grabbing it on OS X + + Configuration Profiles... - Manage configuration profiles + Manage your configuration profiles Ctrl+Shift+A + + QAction::NoRole + - Preferences... + &Preferences... Manage Wireshark's preferences @@ -1160,6 +1175,9 @@ Ctrl+Shift+P + + QAction::PreferencesRole + diff --git a/ui/qt/main_window_slots.cpp b/ui/qt/main_window_slots.cpp index eca548976c..00389d4c6d 100644 --- a/ui/qt/main_window_slots.cpp +++ b/ui/qt/main_window_slots.cpp @@ -64,6 +64,7 @@ #include "print_dialog.h" #include "time_shift_dialog.h" #include "packet_comment_dialog.h" +#include "profile_dialog.h" #include #include @@ -344,6 +345,24 @@ void MainWindow::captureFileClosed(const capture_file *cf) { setMenusForSelectedTreeRow(); } +void MainWindow::configurationProfileChanged(const gchar *profile_name) { + Q_UNUSED(profile_name); + /* Update window view and redraw the toolbar */ +// main_titlebar_update(); +// filter_expression_reinit(FILTER_EXPRESSION_REINIT_CREATE); +// toolbar_redraw_all(); + + /* Reload list of interfaces on welcome page */ +// welcome_if_panel_reload(); + + /* Recreate the packet list according to new preferences */ +// packet_list_recreate (); + if (cap_file_) cap_file_->columns_changed = FALSE; /* Reset value */ + + /* Reload pane geometry, must be done after recreating the list */ +// main_pane_load_window_geometry(); +} + // // Private slots // @@ -902,7 +921,6 @@ void MainWindow::redissectPackets() main_ui_->statusBar->expertUpdate(); } - // File Menu void MainWindow::on_actionFileOpen_triggered() @@ -1047,8 +1065,8 @@ void MainWindow::on_actionFileExportSSLSessionKeys_triggered() return; } - save_title.append("Wireshark: Export SSL Session Keys (%1 key%2"). - arg(keylist_len).arg(plurality(keylist_len, "", "s")); + save_title.append(QString("Wireshark: Export SSL Session Keys (%1 key%2"). + arg(keylist_len).arg(plurality(keylist_len, "", "s"))); file_name = QFileDialog::getSaveFileName(this, save_title, wsApp->lastOpenDir().canonicalPath(), @@ -1212,13 +1230,13 @@ void MainWindow::on_actionEditUnmarkAllDisplayed_triggered() packet_list_->markAllDisplayedFrames(false); } -void MainWindow::on_actionEditFindNextMark_triggered() +void MainWindow::on_actionEditNextMark_triggered() { if (cap_file_) cf_find_packet_marked(cap_file_, SD_FORWARD); } -void MainWindow::on_actionEditFindPreviousMark_triggered() +void MainWindow::on_actionEditPreviousMark_triggered() { if (cap_file_) cf_find_packet_marked(cap_file_, SD_BACKWARD); @@ -1278,6 +1296,13 @@ void MainWindow::on_actionEditPacketComment_triggered() } } +void MainWindow::on_actionEditConfigurationProfiles_triggered() +{ + ProfileDialog cp_dialog; + + cp_dialog.exec(); +} + // View Menu // Expand / collapse slots in proto_tree diff --git a/ui/qt/profile_dialog.cpp b/ui/qt/profile_dialog.cpp new file mode 100644 index 0000000000..25b20966af --- /dev/null +++ b/ui/qt/profile_dialog.cpp @@ -0,0 +1,287 @@ +/* profile_dialog.cpp + * + * $Id$ + * + * Wireshark - Network traffic analyzer + * By Gerald Combs + * Copyright 1998 Gerald Combs + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + */ + +#include "config.h" +#include + +#include "epan/filesystem.h" +#include "epan/prefs.h" + +#include "ui/profile.h" + +#include "profile_dialog.h" +#include "ui_profile_dialog.h" +#include "wireshark_application.h" +#include "tango_colors.h" + +#include +#include +#include +#include +#include + +Q_DECLARE_METATYPE(GList *) + +ProfileDialog::ProfileDialog(QWidget *parent) : + QDialog(parent), + pd_ui_(new Ui::ProfileDialog), + ok_button_(NULL) +{ + GList *fl_entry; + profile_def *profile; + const gchar *profile_name = get_profile_name(); + + pd_ui_->setupUi(this); + ok_button_ = pd_ui_->buttonBox->button(QDialogButtonBox::Ok); + + // XXX - Use NSImageNameAddTemplate and NSImageNameRemoveTemplate to set stock + // icons on OS X. + // Are there equivalent stock icons on Windows? +#ifdef Q_WS_MAC + pd_ui_->newToolButton->setAttribute(Qt::WA_MacSmallSize, true); + pd_ui_->deleteToolButton->setAttribute(Qt::WA_MacSmallSize, true); + pd_ui_->copyToolButton->setAttribute(Qt::WA_MacSmallSize, true); + pd_ui_->pathLabel->setAttribute(Qt::WA_MacSmallSize, true); +#endif + + init_profile_list(); + fl_entry = edited_profile_list(); + pd_ui_->profileTreeWidget->blockSignals(true); + while (fl_entry && fl_entry->data) { + profile = (profile_def *) fl_entry->data; + QTreeWidgetItem *item = new QTreeWidgetItem(pd_ui_->profileTreeWidget); + item->setText(0, profile->name); + item->setData(0, Qt::UserRole, qVariantFromValue(fl_entry)); + + if (profile->is_global || profile->status == PROF_STAT_DEFAULT) { + QFont ti_font = item->font(0); + ti_font.setItalic(true); + item->setFont(0, ti_font); + } else { + if (profile->name && strcmp(profile_name, profile->name) == 0) { + pd_ui_->profileTreeWidget->setCurrentItem(item); + } + item->setFlags(item->flags() | Qt::ItemIsEditable); + } + + fl_entry = g_list_next(fl_entry); + } + pd_ui_->profileTreeWidget->blockSignals(false); + + connect(pd_ui_->profileTreeWidget->itemDelegate(), SIGNAL(closeEditor(QWidget*, QAbstractItemDelegate::EndEditHint)), + this, SLOT(editingFinished())); + updateWidgets(); +} + +ProfileDialog::~ProfileDialog() +{ + delete pd_ui_; + empty_profile_list (TRUE); +} + +void ProfileDialog::updateWidgets() +{ + QTreeWidgetItem *item = pd_ui_->profileTreeWidget->currentItem(); + bool enable_new = false; + bool enable_del = false; + bool enable_copy = false; + bool enable_ok = true; + profile_def *current_profile = NULL; + + if (item) { + current_profile = (profile_def *) item->data(0, Qt::UserRole).value()->data; + enable_new = true; + enable_copy = true; + if (!current_profile->is_global || current_profile->status != PROF_STAT_DEFAULT) { + enable_del = true; + } + } + + if (current_profile && current_profile->status != PROF_STAT_DEFAULT) { + QString profile_path = current_profile->is_global ? get_global_profiles_dir() : get_profiles_dir(); + QString elided_path = pd_ui_->pathLabel->fontMetrics().elidedText(profile_path, Qt::ElideMiddle, pd_ui_->pathLabel->width()); + pd_ui_->pathLabel->setText(QString("%2") + .arg(QUrl::fromLocalFile(profile_path).toString()) + .arg(elided_path)); + pd_ui_->pathLabel->setToolTip(tr("Go to") + profile_path); + pd_ui_->pathLabel->setEnabled(true); + pd_ui_->pathLabel->show(); + } else { + pd_ui_->pathLabel->hide(); + } + + if (pd_ui_->profileTreeWidget->topLevelItemCount() > 0) { + profile_def *profile; + for (int i = 0; i < pd_ui_->profileTreeWidget->topLevelItemCount(); i++) { + item = pd_ui_->profileTreeWidget->topLevelItem(i); + profile = (profile_def *) item->data(0, Qt::UserRole).value()->data; + if (profile->is_global) continue; + if (current_profile && !current_profile->is_global && profile != current_profile && strcmp(profile->name, current_profile->name) == 0) { + item->setToolTip(0, tr("A profile already exists with that name.")); + item->setBackground(0, QColor(ws_syntax_invalid_background)); + item->setForeground(0, QColor(ws_syntax_invalid_foreground)); + enable_ok = false; + } else { + item->setBackground(0, QBrush()); + item->setForeground(0, QBrush()); + } + } + } + + pd_ui_->profileTreeWidget->resizeColumnToContents(0); + pd_ui_->newToolButton->setEnabled(enable_new); + pd_ui_->deleteToolButton->setEnabled(enable_del); + pd_ui_->copyToolButton->setEnabled(enable_copy); + ok_button_->setEnabled(enable_ok); +} + +void ProfileDialog::on_profileTreeWidget_currentItemChanged(QTreeWidgetItem *current, QTreeWidgetItem *previous) +{ + Q_UNUSED(current); + Q_UNUSED(previous); + if (pd_ui_->profileTreeWidget->updatesEnabled()) updateWidgets(); +} + +void ProfileDialog::on_newToolButton_clicked() +{ + QTreeWidgetItem *item = new QTreeWidgetItem(); + profile_def *profile; + const gchar *name = "New profile"; + GList *fl_entry = add_to_profile_list(name, "", PROF_STAT_NEW, FALSE, FALSE); + + profile = (profile_def *) fl_entry->data; + item->setText(0, profile->name); + item->setData(0, Qt::UserRole, qVariantFromValue(fl_entry)); + item->setFlags(item->flags() | Qt::ItemIsEditable); + pd_ui_->profileTreeWidget->addTopLevelItem(item); + pd_ui_->profileTreeWidget->setCurrentItem(item); + pd_ui_->profileTreeWidget->editItem(item, 0); +} + +void ProfileDialog::on_deleteToolButton_clicked() +{ + QTreeWidgetItem *item = pd_ui_->profileTreeWidget->currentItem(); + + if (item) { + GList *fl_entry = item->data(0, Qt::UserRole).value(); + // Select the default + pd_ui_->profileTreeWidget->setCurrentItem(pd_ui_->profileTreeWidget->topLevelItem(0)); + + remove_from_profile_list(fl_entry); + delete item; + } +} + +void ProfileDialog::on_copyToolButton_clicked() +{ + QTreeWidgetItem *cur_item = pd_ui_->profileTreeWidget->currentItem(); + profile_def *cur_profile = (profile_def *) cur_item->data(0, Qt::UserRole).value()->data; + + if (!cur_item || !cur_profile) return; + + QTreeWidgetItem *new_item = new QTreeWidgetItem(); + GList *fl_entry; + const gchar *parent; + gchar *new_name; + profile_def *new_profile; + + if (cur_profile->is_global) { + parent = cur_profile->name; + } else { + parent = get_profile_parent (cur_profile->name); + } + + if (cur_profile->is_global && !profile_exists (parent, FALSE)) { + new_name = g_strdup (cur_profile->name); + } else { + new_name = g_strdup_printf ("%s (copy)", cur_profile->name); + } + + /* Add a new entry to the profile list. */ + fl_entry = add_to_profile_list(new_name, parent, PROF_STAT_COPY, FALSE, cur_profile->from_global); + new_profile = (profile_def *) fl_entry->data; + new_item->setText(0, new_profile->name); + new_item->setData(0, Qt::UserRole, qVariantFromValue(fl_entry)); + new_item->setFlags(new_item->flags() | Qt::ItemIsEditable); + pd_ui_->profileTreeWidget->addTopLevelItem(new_item); + pd_ui_->profileTreeWidget->setCurrentItem(new_item); + pd_ui_->profileTreeWidget->editItem(new_item, 0); +} + +void ProfileDialog::on_buttonBox_accepted() +{ + const gchar *err_msg; +// QTreeWidgetItem *item = pd_ui_->profileTreeWidget->currentItem(); + + if ((err_msg = apply_profile_changes()) != NULL) { + QMessageBox::critical(this, tr("Profile Error"), + err_msg, + QMessageBox::Ok); + return; + } + +// if (item) { +// profile_def *profile = (profile_def *) item->data(0, Qt::UserRole).value()->data; +// if (profile_exists (profile->name, FALSE) || profile_exists (profile->name, TRUE)) { +// /* The new profile exists, change */ +// wsApp->setConfigurationProfile (profile->name); +// } else if (!profile_exists (get_profile_name(), FALSE)) { +// /* The new profile does not exist, and the previous profile has +// been deleted. Change to the default profile */ +// wsApp->setConfigurationProfile (NULL); +// } +// } +} + +void ProfileDialog::on_buttonBox_helpRequested() +{ + wsApp->helpTopicAction(HELP_CONFIG_PROFILES_DIALOG); +} + +void ProfileDialog::editingFinished() +{ + QTreeWidgetItem *item = pd_ui_->profileTreeWidget->currentItem(); + + if (item) { + profile_def *profile = (profile_def *) item->data(0, Qt::UserRole).value()->data; + if (item->text(0).compare(profile->name) != 0) { + g_free(profile->name); + profile->name = g_strdup(item->text(0).toUtf8().constData()); + } + } + updateWidgets(); +} + +/* + * Editor modelines + * + * Local Variables: + * c-basic-offset: 4 + * tab-width: 8 + * indent-tabs-mode: nil + * End: + * + * ex: set shiftwidth=4 tabstop=8 expandtab: + * :indentSize=4:tabSize=8:noTabs=true: + */ + diff --git a/ui/qt/profile_dialog.h b/ui/qt/profile_dialog.h new file mode 100644 index 0000000000..72fac2106e --- /dev/null +++ b/ui/qt/profile_dialog.h @@ -0,0 +1,58 @@ +/* profile_dialog.h + * + * $Id$ + * + * Wireshark - Network traffic analyzer + * By Gerald Combs + * Copyright 1998 Gerald Combs + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + */ + +#ifndef PROFILE_DIALOG_H +#define PROFILE_DIALOG_H + +#include +#include +#include + +namespace Ui { +class ProfileDialog; +} + +class ProfileDialog : public QDialog +{ + Q_OBJECT + +public: + explicit ProfileDialog(QWidget *parent = 0); + ~ProfileDialog(); + +private: + void updateWidgets(); + Ui::ProfileDialog *pd_ui_; + QPushButton *ok_button_; + +private slots: + void on_profileTreeWidget_currentItemChanged(QTreeWidgetItem *current, QTreeWidgetItem *previous); + void on_newToolButton_clicked(); + void on_deleteToolButton_clicked(); + void on_copyToolButton_clicked(); + void on_buttonBox_accepted(); + void on_buttonBox_helpRequested(); + void editingFinished(); +}; + +#endif // PROFILE_DIALOG_H diff --git a/ui/qt/profile_dialog.ui b/ui/qt/profile_dialog.ui new file mode 100644 index 0000000000..8f336840c3 --- /dev/null +++ b/ui/qt/profile_dialog.ui @@ -0,0 +1,168 @@ + + + ProfileDialog + + + + 0 + 0 + 470 + 300 + + + + Wireshark: Configuration Profiles + + + + + + false + + + true + + + false + + + true + + + false + + + 1 + + + + Name + + + + + + + + + + Create a new profile using default settings. + + + + + + + :/stock/plus-8.png:/stock/plus-8.png + + + + + + + Remove this profile. + + + + :/stock/minus-8.png:/stock/minus-8.png + + + + + + + Copy this profile. + + + + + + + :/stock/copy-8.png:/stock/copy-8.png + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + 1 + 0 + + + + + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + true + + + + + + + + + Qt::Horizontal + + + QDialogButtonBox::Cancel|QDialogButtonBox::Help|QDialogButtonBox::Ok + + + + + + + + + + + buttonBox + accepted() + ProfileDialog + accept() + + + 248 + 254 + + + 157 + 274 + + + + + buttonBox + rejected() + ProfileDialog + reject() + + + 316 + 260 + + + 286 + 274 + + + + + diff --git a/ui/qt/syntax_line_edit.cpp b/ui/qt/syntax_line_edit.cpp index 24e59ff617..92ac540f10 100644 --- a/ui/qt/syntax_line_edit.cpp +++ b/ui/qt/syntax_line_edit.cpp @@ -25,10 +25,10 @@ SyntaxLineEdit::SyntaxLineEdit(QWidget *parent) : .arg(Invalid) .arg(Deprecated) .arg(Valid) - .arg(tango_aluminium_6, 6, 16, QChar('0')) // Foreground - .arg(tango_scarlet_red_1, 6, 16, QChar('0')) // Invalid - .arg(tango_butter_1, 6, 16, QChar('0')) // Deprecated - .arg(tango_chameleon_1, 6, 16, QChar('0')) // Valid + .arg(ws_syntax_invalid_foreground, 6, 16, QChar('0')) // Foreground + .arg(ws_syntax_invalid_background, 6, 16, QChar('0')) // Invalid + .arg(ws_syntax_deprecated_background, 6, 16, QChar('0')) // Deprecated + .arg(ws_syntax_valid_background, 6, 16, QChar('0')) // Valid ; setStyleSheet(tr("")); setSyntaxState(); diff --git a/ui/qt/tango_colors.h b/ui/qt/tango_colors.h index 7a4432f190..f58a98e140 100644 --- a/ui/qt/tango_colors.h +++ b/ui/qt/tango_colors.h @@ -85,6 +85,13 @@ const QRgb tango_sky_blue_4 = 0x3465a4; const QRgb tango_sky_blue_5 = 0x204a87; const QRgb tango_sky_blue_6 = 0x0a3050; +const QRgb ws_syntax_invalid_background = tango_scarlet_red_1; +const QRgb ws_syntax_invalid_foreground = tango_aluminium_6; +const QRgb ws_syntax_deprecated_background = tango_butter_1; +const QRgb ws_syntax_deprecated_foreground = tango_aluminium_6; +const QRgb ws_syntax_valid_background = tango_chameleon_1; +const QRgb ws_syntax_valid_foreground = tango_aluminium_6; + const QRgb ws_css_warn_background = tango_butter_2; const QRgb ws_css_warn_text = tango_aluminium_6; diff --git a/ui/qt/time_shift_dialog.cpp b/ui/qt/time_shift_dialog.cpp index 02127d125b..141a85e264 100644 --- a/ui/qt/time_shift_dialog.cpp +++ b/ui/qt/time_shift_dialog.cpp @@ -29,7 +29,6 @@ #include #include "tango_colors.h" -#include TimeShiftDialog::TimeShiftDialog(QWidget *parent, capture_file *cf) : QDialog(parent), @@ -78,7 +77,7 @@ TimeShiftDialog::~TimeShiftDialog() void TimeShiftDialog::enableWidgets() { bool enable_two = ts_ui_->setOneButton->isChecked(); - bool enable_ok = false; + bool enable_apply = false; ts_ui_->setTwoCheckBox->setEnabled(enable_two); ts_ui_->setTwoFrameLineEdit->setEnabled(enable_two); @@ -88,7 +87,7 @@ void TimeShiftDialog::enableWidgets() if (ts_ui_->shiftAllButton->isChecked()) { if (ts_ui_->shiftAllTimeLineEdit->syntaxState() == SyntaxLineEdit::Valid) - enable_ok = true; + enable_apply = true; } else if (ts_ui_->setOneButton->isChecked()) { bool set_two_valid = false; if (ts_ui_->setTwoCheckBox->isChecked()) { @@ -102,10 +101,10 @@ void TimeShiftDialog::enableWidgets() if (set_two_valid && ts_ui_->setOneFrameLineEdit->syntaxState() == SyntaxLineEdit::Valid && ts_ui_->setOneTimeLineEdit->syntaxState() == SyntaxLineEdit::Valid) { - enable_ok = true; + enable_apply = true; } } else if (ts_ui_->unshiftAllButton->isChecked()) { - enable_ok = true; + enable_apply = true; } if (syntax_err_.isEmpty()) { @@ -124,7 +123,7 @@ void TimeShiftDialog::enableWidgets() .arg(ws_css_warn_background, 6, 16, QChar('0')) ); } - apply_button_->setEnabled(enable_ok); + apply_button_->setEnabled(enable_apply); } void TimeShiftDialog::checkFrameNumber(SyntaxLineEdit &frame_le) @@ -294,4 +293,3 @@ void TimeShiftDialog::on_buttonBox_helpRequested() * ex: set shiftwidth=4 tabstop=8 expandtab: * :indentSize=4:tabSize=8:noTabs=true: */ - diff --git a/ui/qt/wireshark_application.cpp b/ui/qt/wireshark_application.cpp index 02de38bdb0..65f45e985e 100644 --- a/ui/qt/wireshark_application.cpp +++ b/ui/qt/wireshark_application.cpp @@ -23,14 +23,23 @@ #include "wireshark_application.h" -#include +#include +#include + +#include "ui/recent.h" +#include "ui/simple_dialog.h" #include "qt_ui_utils.h" #include "capture.h" +#include "color_filters.h" +#include "disabled_protos.h" +#include "filters.h" #include "log.h" #include "recent_file_status.h" +#include "ui/capture_globals.h" + #include #include #include @@ -293,6 +302,112 @@ void WiresharkApplication::helpTopicAction(topic_action_e action) } } +void WiresharkApplication::setConfigurationProfile(const gchar *profile_name) +{ + char *gdp_path, *dp_path; + char *rf_path; + int rf_open_errno; + + /* First check if profile exists */ + if (!profile_exists(profile_name, FALSE)) { + if (profile_exists(profile_name, TRUE)) { + char *pf_dir_path, *pf_dir_path2, *pf_filename; + /* Copy from global profile */ + if (create_persconffile_profile(profile_name, &pf_dir_path) == -1) { + simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, + "Can't create directory\n\"%s\":\n%s.", + pf_dir_path, g_strerror(errno)); + + g_free(pf_dir_path); + } + + if (copy_persconffile_profile(profile_name, profile_name, TRUE, &pf_filename, + &pf_dir_path, &pf_dir_path2) == -1) { + simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, + "Can't copy file \"%s\" in directory\n\"%s\" to\n\"%s\":\n%s.", + pf_filename, pf_dir_path2, pf_dir_path, g_strerror(errno)); + + g_free(pf_filename); + g_free(pf_dir_path); + g_free(pf_dir_path2); + } + } else { + /* No personal and no global profile exists */ + return; + } + } + + /* Then check if changing to another profile */ + if (profile_name && strcmp (profile_name, get_profile_name()) == 0) { + return; + } + + /* Get the current geometry, before writing it to disk */ +// main_save_window_geometry(top_level); + + if (profile_exists(get_profile_name(), FALSE)) { + /* Write recent file for profile we are leaving, if it still exists */ + write_profile_recent(); + } + + /* Set profile name and update the status bar */ + set_profile_name (profile_name); + emit configurationProfileChanged(profile_name); +// filter_expression_reinit(FILTER_EXPRESSION_REINIT_DESTROY); + + /* Reset current preferences and apply the new */ + prefs_reset(); +// menu_prefs_reset(); + + (void) readConfigurationFiles (&gdp_path, &dp_path); + + recent_read_profile_static(&rf_path, &rf_open_errno); + if (rf_path != NULL && rf_open_errno != 0) { + simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, + "Could not open common recent file\n\"%s\": %s.", + rf_path, g_strerror(rf_open_errno)); + } + if (recent.gui_fileopen_remembered_dir && + test_for_directory(recent.gui_fileopen_remembered_dir) == EISDIR) { + set_last_open_dir(recent.gui_fileopen_remembered_dir); + } + timestamp_set_type (recent.gui_time_format); + timestamp_set_seconds_type (recent.gui_seconds_format); + color_filters_enable(recent.packet_list_colorize); + + prefsToCaptureOpts(); + prefs_apply_all(); +// macros_post_update(); + + /* Enable all protocols and disable from the disabled list */ + proto_enable_all(); + if (gdp_path == NULL && dp_path == NULL) { + set_disabled_protos_list(); + } + + /* Reload color filters */ + color_filters_reload(); + +// user_font_apply(); + + /* Update menus with new recent values */ +// menu_recent_read_finished(); + +} + +void WiresharkApplication::prefsToCaptureOpts() +{ +#ifdef HAVE_LIBPCAP + /* Set promiscuous mode from the preferences setting. */ + /* the same applies to other preferences settings as well. */ + global_capture_opts.default_options.promisc_mode = prefs.capture_prom_mode; + global_capture_opts.use_pcapng = prefs.capture_pcap_ng; + global_capture_opts.show_info = prefs.capture_show_info; + global_capture_opts.real_time_mode = prefs.capture_real_time; +// auto_scroll_live = prefs.capture_auto_scroll; +#endif /* HAVE_LIBPCAP */ +} + void WiresharkApplication::setLastOpenDir(const char *dir_name) { qint64 len; @@ -421,6 +536,108 @@ void WiresharkApplication::applyAllPreferences() emit updatePreferences(); } +e_prefs * WiresharkApplication::readConfigurationFiles(char **gdp_path, char **dp_path) +{ + int gpf_open_errno, gpf_read_errno; + int cf_open_errno, df_open_errno; + int gdp_open_errno, gdp_read_errno; + int dp_open_errno, dp_read_errno; + char *gpf_path, *pf_path; + char *cf_path, *df_path; + int pf_open_errno, pf_read_errno; + e_prefs *prefs_p; + + /* Read the preference files. */ + prefs_p = read_prefs(&gpf_open_errno, &gpf_read_errno, &gpf_path, + &pf_open_errno, &pf_read_errno, &pf_path); + + if (gpf_path != NULL) { + if (gpf_open_errno != 0) { + simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, + "Could not open global preferences file\n\"%s\": %s.", gpf_path, + g_strerror(gpf_open_errno)); + } + if (gpf_read_errno != 0) { + simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, + "I/O error reading global preferences file\n\"%s\": %s.", gpf_path, + g_strerror(gpf_read_errno)); + } + } + if (pf_path != NULL) { + if (pf_open_errno != 0) { + simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, + "Could not open your preferences file\n\"%s\": %s.", pf_path, + g_strerror(pf_open_errno)); + } + if (pf_read_errno != 0) { + simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, + "I/O error reading your preferences file\n\"%s\": %s.", pf_path, + g_strerror(pf_read_errno)); + } + g_free(pf_path); + pf_path = NULL; + } + +#ifdef _WIN32 + /* if the user wants a console to be always there, well, we should open one for him */ + if (prefs_p->gui_console_open == console_open_always) { + create_console(); + } +#endif + + /* Read the capture filter file. */ + read_filter_list(CFILTER_LIST, &cf_path, &cf_open_errno); + if (cf_path != NULL) { + simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, + "Could not open your capture filter file\n\"%s\": %s.", cf_path, + g_strerror(cf_open_errno)); + g_free(cf_path); + } + + /* Read the display filter file. */ + read_filter_list(DFILTER_LIST, &df_path, &df_open_errno); + if (df_path != NULL) { + simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, + "Could not open your display filter file\n\"%s\": %s.", df_path, + g_strerror(df_open_errno)); + g_free(df_path); + } + + /* Read the disabled protocols file. */ + read_disabled_protos_list(gdp_path, &gdp_open_errno, &gdp_read_errno, + dp_path, &dp_open_errno, &dp_read_errno); + if (*gdp_path != NULL) { + if (gdp_open_errno != 0) { + simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, + "Could not open global disabled protocols file\n\"%s\": %s.", + *gdp_path, g_strerror(gdp_open_errno)); + } + if (gdp_read_errno != 0) { + simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, + "I/O error reading global disabled protocols file\n\"%s\": %s.", + *gdp_path, g_strerror(gdp_read_errno)); + } + g_free(*gdp_path); + *gdp_path = NULL; + } + if (*dp_path != NULL) { + if (dp_open_errno != 0) { + simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, + "Could not open your disabled protocols file\n\"%s\": %s.", *dp_path, + g_strerror(dp_open_errno)); + } + if (dp_read_errno != 0) { + simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK, + "I/O error reading your disabled protocols file\n\"%s\": %s.", *dp_path, + g_strerror(dp_read_errno)); + } + g_free(*dp_path); + *dp_path = NULL; + } + + return prefs_p; +} + QList WiresharkApplication::recentItems() const { return recent_items; } diff --git a/ui/qt/wireshark_application.h b/ui/qt/wireshark_application.h index 68f991b019..219c33d171 100644 --- a/ui/qt/wireshark_application.h +++ b/ui/qt/wireshark_application.h @@ -28,6 +28,8 @@ #include +#include "epan/prefs.h" + #include "capture_opts.h" #include "file.h" #include "register.h" @@ -61,6 +63,7 @@ public: void registerUpdate(register_action_e action, const char *message); void allSystemsGo(); void applyAllPreferences(); + e_prefs * readConfigurationFiles(char **gdp_path, char **dp_path); QList recentItems() const; void addRecentItem(const QString &filename, qint64 size, bool accessible); #ifdef HAVE_LIBPCAP @@ -72,9 +75,12 @@ public: void setLastOpenDir(QString *dir_str); void helpTopicAction(topic_action_e action); QFont monospaceFont(bool bold = false); + void setConfigurationProfile(const gchar *profile_name); private: + void prefsToCaptureOpts(); + bool initialized_; QTimer *recent_timer_; QList pending_open_files_; @@ -88,6 +94,7 @@ signals: void updateRecentItemStatus(const QString &filename, qint64 size, bool accessible); void splashUpdate(register_action_e action, const char *message); void updatePreferences(); + void configurationProfileChanged(const gchar *profile_name); #ifdef HAVE_LIBPCAP // XXX It might make more sense to move these to main.cpp or main_window.cpp or their own class. diff --git a/ui/recent.h b/ui/recent.h index dba023e395..7b22a6a8cc 100644 --- a/ui/recent.h +++ b/ui/recent.h @@ -32,6 +32,8 @@ extern "C" { #include +#include "epan/timestamp.h" + /** @file * Recent user interface settings. * @ingroup main_window_group @@ -73,9 +75,9 @@ typedef struct recent_settings_tag { gboolean byte_view_show; gboolean statusbar_show; gboolean packet_list_colorize; - gint gui_time_format; + ts_type gui_time_format; gint gui_time_precision; - gint gui_seconds_format; + ts_seconds_type gui_seconds_format; gint gui_zoom_level; gint gui_bytes_view;