From 76f6a004b7df2ea686536e5197b0a99d8522d55f Mon Sep 17 00:00:00 2001
From: Mamoru TASAKA <mtasaka@fedoraproject.org>
Date: Tue, 10 Feb 2015 09:23:08 +0900
Subject: [PATCH] flush_dialog_changes_and_save: strdup for TEXT entry
https://bugzilla.redhat.com/show_bug.cgi?id=1190846
Backtrace shows:
Thread 1 (Thread 0xb60f18c0 (LWP 15079)):
#0 0xb7767bac in __kernel_vsyscall ()
#1 0xb6683297 in __GI_raise (sig=6) at ../sysdeps/unix/sysv/linux/raise.c:55
#2 0xb6684b69 in __GI_abort () at abort.c:89
#3 0xb66c3ade in __libc_message (do_abort=2, fmt=0xb67ce84c "*** Error in `%s': %s: 0x%s ***\n") at ../sysdeps/posix/libc_fatal.c:175
#4 0xb66cb0d6 in malloc_printerr (ptr=<optimized out>, str=0xb67ce91c "double free or corruption (!prev)", action=<optimized out>) at malloc.c:4974
#5 _int_free (av=0xb681f840 <main_arena>, p=<optimized out>, have_lock=0) at malloc.c:3841
#6 0xb66cf346 in __GI___libc_free (mem=mem@entry=0x93fadb0) at malloc.c:2951
#7 0x0805b6a6 in flush_dialog_changes_and_save (s=s@entry=0xbfca5c3c) at ../../driver/demo-Gtk.c:1712
#8 0x0805e730 in pref_changed_cb (user_data=0x0, user_data@entry=0xbfca5c3c, widget=widget@entry=0x93c99a8) at ../../driver/demo-Gtk.c:1819
#9 pref_changed_event_cb (widget=widget@entry=0x93c99a8, event=0x968e5e8, user_data=user_data@entry=0x0) at ../../driver/demo-Gtk.c:1827
.....
Related lines:
1491 static Bool
1492 flush_dialog_changes_and_save (state *s)
1493 {
1554 # define PATHNAME(FIELD,NAME) \
1555 w = name_to_widget (s, (NAME)); \
1556 (FIELD) = normalize_directory (gtk_entry_get_text (GTK_ENTRY (w)))
1557
1558 # define TEXT(FIELD,NAME) \
1559 w = name_to_widget (s, (NAME)); \
1560 (FIELD) = (char *) gtk_entry_get_text (GTK_ENTRY (w)) <==========
1591 TEXT (p2->text_literal, "text_entry");
1592 PATHNAME (p2->text_file, "text_file_entry");
1593 PATHNAME (p2->text_program, "text_program_entry");
1594 PATHNAME (p2->text_program, "text_program_entry");
1595 TEXT (p2->text_url, "text_url_entry");
1694 # define COPYSTR(FIELD,NAME) \
1695 if (!p->FIELD || \
1696 !p2->FIELD || \
1697 strcmp(p->FIELD, p2->FIELD)) \
1698 { \
1699 changed = True; \
1700 if (s->debug_p) \
1701 fprintf (stderr, "%s: %s => \"%s\"\n", blurb(), NAME, p2->FIELD); \
1702 } \
1703 if (p->FIELD && p->FIELD != p2->FIELD) \
1704 free (p->FIELD); \ <==========
1705 p->FIELD = p2->FIELD; \
1706 p2->FIELD = 0
1708 COPYSTR(image_directory, "image_directory");
1709 COPYSTR(text_literal, "text_literal");
1710 COPYSTR(text_file, "text_file");
1711 COPYSTR(text_program, "text_program");
1712 COPYSTR(text_url, "text_url"); <==========
At the line 1712, this tries to free() a string returned by
gtk_entry_get_text(), but GTK manual says it must not be free()ed.
https://developer.gnome.org/gtk2/stable/GtkEntry.html#gtk-entry-get-text
Actually Chaning "Text" in "Text Manipulation" also causes this segv.
Note that for PATHNAME() string, the string returned by
gtk_entry_get_text() is passed to normalize_directory(), and
normalize_directory() returns malloc()ed buffer.
To fix this, use strdup()ed string for TEXT entry.
---
driver/demo-Gtk.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/driver/demo-Gtk.c b/driver/demo-Gtk.c
index d276ecc..27d2316 100644
--- a/driver/demo-Gtk.c
+++ b/driver/demo-Gtk.c
@@ -1557,7 +1557,7 @@ flush_dialog_changes_and_save (state *s)
# define TEXT(FIELD,NAME) \
w = name_to_widget (s, (NAME)); \
- (FIELD) = (char *) gtk_entry_get_text (GTK_ENTRY (w))
+ (FIELD) = (char *) g_strdup(gtk_entry_get_text (GTK_ENTRY (w)))
MINUTES (&p2->timeout, "timeout_spinbutton");
MINUTES (&p2->cycle, "cycle_spinbutton");
--
2.1.0