diff options
-rw-r--r-- | src/ChangeLog | 6 | ||||
-rw-r--r-- | src/xmenu.c | 31 |
2 files changed, 33 insertions, 4 deletions
diff --git a/src/ChangeLog b/src/ChangeLog index 458e8c89821..d006f58b8b6 100644 --- a/src/ChangeLog +++ b/src/ChangeLog @@ -1,3 +1,9 @@ +2011-10-31 YAMAMOTO Mitsuharu <mituharu@math.s.chiba-u.ac.jp> + + * xmenu.c (cleanup_widget_value_tree): New function. + (xmenu_show, xdialog_show): Use it in record_unwind_protect instead of + calling free_menubar_widget_value_tree directly (Bug#9830). + 2011-09-19 Andreas Schwab <schwab@linux-m68k.org> * keymap.c (Fsingle_key_description): Use make_specified_string diff --git a/src/xmenu.c b/src/xmenu.c index 5c6c2b0cfdd..bd3aea89e3a 100644 --- a/src/xmenu.c +++ b/src/xmenu.c @@ -1658,6 +1658,17 @@ create_and_show_popup_menu (f, first_wv, x, y, for_click, timestamp) #endif /* not USE_GTK */ +static Lisp_Object +cleanup_widget_value_tree (Lisp_Object arg) +{ + struct Lisp_Save_Value *p = XSAVE_VALUE (arg); + widget_value *wv = p->pointer; + + free_menubar_widget_value_tree (wv); + + return Qnil; +} + Lisp_Object xmenu_show (FRAME_PTR f, int x, int y, int for_click, int keymaps, Lisp_Object title, char **error, EMACS_UINT timestamp) @@ -1672,6 +1683,8 @@ xmenu_show (FRAME_PTR f, int x, int y, int for_click, int keymaps, int first_pane; + int specpdl_count = SPECPDL_INDEX (); + if (! FRAME_X_P (f)) abort (); @@ -1866,11 +1879,15 @@ xmenu_show (FRAME_PTR f, int x, int y, int for_click, int keymaps, /* No selection has been chosen yet. */ menu_item_selection = 0; + /* Make sure to free the widget_value objects we used to specify the + contents even with longjmp. */ + record_unwind_protect (cleanup_widget_value_tree, + make_save_value (first_wv, 0)); + /* Actually create and show the menu until popped down. */ create_and_show_popup_menu (f, first_wv, x, y, for_click, timestamp); - /* Free the widget_value objects we used to specify the contents. */ - free_menubar_widget_value_tree (first_wv); + unbind_to (specpdl_count, Qnil); /* Find the selected item, and its pane, to return the proper value. */ @@ -2064,6 +2081,8 @@ xdialog_show (f, keymaps, title, header, error_name) /* 1 means we've seen the boundary between left-hand elts and right-hand. */ int boundary_seen = 0; + int specpdl_count = SPECPDL_INDEX (); + if (! FRAME_X_P (f)) abort (); @@ -2177,11 +2196,15 @@ xdialog_show (f, keymaps, title, header, error_name) /* No selection has been chosen yet. */ menu_item_selection = 0; + /* Make sure to free the widget_value objects we used to specify the + contents even with longjmp. */ + record_unwind_protect (cleanup_widget_value_tree, + make_save_value (first_wv, 0)); + /* Actually create and show the dialog. */ create_and_show_dialog (f, first_wv); - /* Free the widget_value objects we used to specify the contents. */ - free_menubar_widget_value_tree (first_wv); + unbind_to (specpdl_count, Qnil); /* Find the selected item, and its pane, to return the proper value. */ |