aboutsummaryrefslogtreecommitdiffstats
path: root/gtk
diff options
context:
space:
mode:
authorChris Maynard <Christopher.Maynard@GTECH.COM>2010-11-08 16:53:11 +0000
committerChris Maynard <Christopher.Maynard@GTECH.COM>2010-11-08 16:53:11 +0000
commit803910c1aa72c56f2ff8d6fcb7dc1633c253b5aa (patch)
treeff48a1a5b0007909386fe212ce79bf4d1494bcc4 /gtk
parentcab0cef11dbd45bf3f8fd212c5136ce59d95dd88 (diff)
Allow objects to be saved that otherwise couldn't be due to invalid characters
in the filename, excessive filename lengths or duplicate filenames. Fixes bug 1671. svn path=/trunk/; revision=34805
Diffstat (limited to 'gtk')
-rw-r--r--gtk/export_object.c93
1 files changed, 90 insertions, 3 deletions
diff --git a/gtk/export_object.c b/gtk/export_object.c
index ff4bbfab72..fd1b13c36d 100644
--- a/gtk/export_object.c
+++ b/gtk/export_object.c
@@ -53,6 +53,7 @@
#include <gtk/main.h>
#include <gtk/stock_icons.h>
#include "gtk/export_object.h"
+#include <string.h>
enum {
EO_PKT_NUM_COLUMN,
@@ -218,6 +219,78 @@ eo_save_clicked_cb(GtkWidget *widget _U_, gpointer arg)
window_destroy(save_as_w);
}
+#define HINIBBLE(x) (((x) >> 4) & 0xf)
+#define LONIBBLE(x) ((x) & 0xf)
+#define HEXTOASCII(x) (((x) < 10) ? ((x) + '0') : ((x) - 10 + 'a'))
+#define MAXFILELEN 255
+
+static GString *eo_rename(GString *gstr, gchar dup)
+{
+ gchar tmp[4] = "( )";
+ gchar *tmp_ptr;
+ GString *ext_str;
+
+ tmp[1] = dup;
+ if ( (tmp_ptr = strrchr(gstr->str, '.')) != NULL ) {
+ /* Retain the extension */
+ ext_str = g_string_new(tmp_ptr);
+ gstr = g_string_truncate(gstr, gstr->len - ext_str->len);
+ if ( gstr->len >= (MAXFILELEN - (strlen(tmp) + ext_str->len)) )
+ gstr = g_string_truncate(gstr, MAXFILELEN - (strlen(tmp) + ext_str->len));
+ gstr = g_string_append(gstr, tmp);
+ gstr = g_string_append(gstr, ext_str->str);
+ g_string_free(ext_str, TRUE);
+ }
+ else {
+ if ( gstr->len >= (MAXFILELEN - strlen(tmp)) )
+ gstr = g_string_truncate(gstr, MAXFILELEN - strlen(tmp));
+ gstr = g_string_append(gstr, tmp);
+ }
+ return gstr;
+}
+
+static GString *
+eo_massage_str(const gchar *in_str, guint maxlen, gchar dup)
+{
+ gchar *tmp_ptr;
+ /* The characters in "reject" come from:
+ * http://msdn.microsoft.com/en-us/library/aa365247%28VS.85%29.aspx.
+ * Add to the list as necessary for other OS's.
+ */
+ const gchar *reject = "<>:\"/\\|?*"
+ "\x01\x02\x03\x04\x05\x06\x07\x08\x09\x0a"
+ "\x0b\x0c\x0d\x0e\x0f\x10\x11\x12\x13\x14"
+ "\x15\x16\x17\x18\x19\x1a\x1b\x1c\x1d\x1e\x1f";
+ GString *out_str;
+ GString *ext_str;
+
+ out_str = g_string_new("");
+
+ /* Find all disallowed characters/bytes and replace them with %xx */
+ while ( (tmp_ptr = strpbrk(in_str, reject)) != NULL ) {
+ out_str = g_string_append_len(out_str, in_str, tmp_ptr - in_str);
+ out_str = g_string_append_c(out_str, '%');
+ out_str = g_string_append_c(out_str, HEXTOASCII(HINIBBLE(*tmp_ptr)));
+ out_str = g_string_append_c(out_str, HEXTOASCII(LONIBBLE(*tmp_ptr)));
+ in_str = tmp_ptr + 1;
+ }
+ out_str = g_string_append(out_str, in_str);
+ if ( out_str->len > maxlen ) {
+ if ( (tmp_ptr = strrchr(out_str->str, '.')) != NULL ) {
+ /* Retain the extension */
+ ext_str = g_string_new(tmp_ptr);
+ out_str = g_string_truncate(out_str, maxlen - ext_str->len);
+ out_str = g_string_append(out_str, ext_str->str);
+ g_string_free(ext_str, TRUE);
+ }
+ else
+ out_str = g_string_truncate(out_str, maxlen);
+ }
+ if ( dup != '0' )
+ out_str = eo_rename(out_str, dup);
+ return out_str;
+}
+
static void
eo_save_all_clicked_cb(GtkWidget *widget _U_, gpointer arg)
{
@@ -227,6 +300,9 @@ eo_save_all_clicked_cb(GtkWidget *widget _U_, gpointer arg)
GtkWidget *save_in_w;
GSList *slist = object_list->entries;
gboolean all_saved = TRUE;
+ gchar *save_in_path;
+ GString *safe_filename;
+ int count = 0;
save_in_w = file_selection_new("Wireshark: Save All Objects In ...",
FILE_SELECTION_CREATE_FOLDER);
@@ -238,9 +314,20 @@ eo_save_all_clicked_cb(GtkWidget *widget _U_, gpointer arg)
while(slist) {
entry = slist->data;
- save_as_fullpath = g_build_filename(gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(save_in_w)), entry->filename, NULL);
-
- if (!eo_save_entry(save_as_fullpath, entry, FALSE))
+ save_in_path = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(save_in_w));
+ if ( strlen(save_in_path) < MAXFILELEN ) {
+ do {
+ safe_filename = eo_massage_str(entry->filename,
+ MAXFILELEN - strlen(save_in_path), count | 0x30);
+ save_as_fullpath = g_build_filename(
+ save_in_path, safe_filename->str, NULL);
+ g_string_free(safe_filename, TRUE);
+ } while ( g_file_test(save_as_fullpath, G_FILE_TEST_EXISTS) && (++count < 10) );
+ count = 0;
+ if (!eo_save_entry(save_as_fullpath, entry, TRUE))
+ all_saved = FALSE;
+ }
+ else
all_saved = FALSE;
slist = slist->next;