Ripped from Debian # DP: Fix bug utilising the ``reverse-search-history'' feature of the readline # DP: library, if the search string matches a previously entered command (ie # DP: history) and must overflow the current screen width. From: Chet Ramey To: doko@cs.tu-berlin.de Cc: chet@po.cwru.edu Subject: Re: Bug#288940: bash-3.0 segfault in readline when Control-R'ing long lines (forwarded from epl@unimelb.edu.au) Date: Tue, 11 Jan 2005 15:25:15 -0500 > Chet Ramey writes: > > > Package: bash > > > Version: 3.0-12 > > > Severity: normal > > > Tags: sid > > > > > > I have found a bug where Debian unstable's bash-3.0 will segfault when > > > utilising the ``reverse-search-history'' feature of the readline library. > > > In particular, the search string must match a previously entered command > > > (ie history) and must overflow the current screen width. > > > > Thanks, I fixed this one. > > as this is a segfault, could you provide the patch? The changes in display.c are extensive enough that it is a fairly large patch. Here are the essentials. I will more than likely not be releasing this as an official patch. Chet *** ../bash-3.0-patched/lib/readline/display.c Wed Sep 8 11:07:51 2004 --- lib/readline/display.c Sat Jan 8 21:51:40 2005 *************** *** 181,184 **** --- 186,201 ---- static int prompt_physical_chars; + /* Variables to save and restore prompt and display information. */ + + /* These are getting numerous enough that it's time to create a struct. */ + + static char *saved_local_prompt; + static char *saved_local_prefix; + static int saved_last_invisible; + static int saved_visible_length; + static int saved_prefix_length; + static int saved_invis_chars_first_line; + static int saved_physical_chars; + /* Expand the prompt string S and return the number of visible characters in *LP, if LP is not null. This is currently more-or-less *************** *** 1797,1803 **** return ((ISPRINT (uc)) ? 1 : 2); } - /* How to print things in the "echo-area". The prompt is treated as a mini-modeline. */ #if defined (USE_VARARGS) --- 1825,1831 ---- return ((ISPRINT (uc)) ? 1 : 2); } /* How to print things in the "echo-area". The prompt is treated as a mini-modeline. */ + static int msg_saved_prompt = 0; #if defined (USE_VARARGS) *************** *** 1830,1835 **** --- 1858,1874 ---- va_end (args); + if (saved_local_prompt == 0) + { + rl_save_prompt (); + msg_saved_prompt = 1; + } rl_display_prompt = msg_buf; + local_prompt = expand_prompt (msg_buf, &prompt_visible_length, + &prompt_last_invisible, + &prompt_invis_chars_first_line, + &prompt_physical_chars); + local_prompt_prefix = (char *)NULL; (*rl_redisplay_function) (); + return 0; } *************** *** 1841,1846 **** --- 1880,1897 ---- sprintf (msg_buf, format, arg1, arg2); msg_buf[sizeof(msg_buf) - 1] = '\0'; /* overflow? */ + rl_display_prompt = msg_buf; + if (saved_local_prompt == 0) + { + rl_save_prompt (); + msg_saved_prompt = 1; + } + local_prompt = expand_prompt (msg_buf, &prompt_visible_length, + &prompt_last_invisible, + &prompt_invis_chars_first_line, + &prompt_physical_chars); + local_prompt_prefix = (char *)NULL; (*rl_redisplay_function) (); + return 0; } *************** *** 1852,1855 **** --- 1903,1911 ---- { rl_display_prompt = rl_prompt; + if (msg_saved_prompt) + { + rl_restore_prompt (); + msg_saved_prompt = 0; + } (*rl_redisplay_function) (); return 0; *************** *** 1866,1878 **** } - /* These are getting numerous enough that it's time to create a struct. */ - - static char *saved_local_prompt; - static char *saved_local_prefix; - static int saved_last_invisible; - static int saved_visible_length; - static int saved_invis_chars_first_line; - static int saved_physical_chars; - void rl_save_prompt () --- 1922,1925 ---- *************** *** 1880,1883 **** --- 1927,1931 ---- saved_local_prompt = local_prompt; saved_local_prefix = local_prompt_prefix; + saved_prefix_length = prompt_prefix_length; saved_last_invisible = prompt_last_invisible; saved_visible_length = prompt_visible_length; *************** *** 1886,1890 **** local_prompt = local_prompt_prefix = (char *)0; ! prompt_last_invisible = prompt_visible_length = 0; prompt_invis_chars_first_line = prompt_physical_chars = 0; } --- 1934,1938 ---- local_prompt = local_prompt_prefix = (char *)0; ! prompt_last_invisible = prompt_visible_length = prompt_prefix_length = 0; prompt_invis_chars_first_line = prompt_physical_chars = 0; } *************** *** 1898,1905 **** --- 1946,1959 ---- local_prompt = saved_local_prompt; local_prompt_prefix = saved_local_prefix; + prompt_prefix_length = saved_prefix_length; prompt_last_invisible = saved_last_invisible; prompt_visible_length = saved_visible_length; prompt_invis_chars_first_line = saved_invis_chars_first_line; prompt_physical_chars = saved_physical_chars; + + /* can test saved_local_prompt to see if prompt info has been saved. */ + saved_local_prompt = saved_local_prefix = (char *)0; + saved_last_invisible = saved_visible_length = saved_prefix_length = 0; + saved_invis_chars_first_line = saved_physical_chars = 0; } -- ``The lyf so short, the craft so long to lerne.'' - Chaucer ( ``Discere est Dolere'' -- chet ) Live...Laugh...Love Chet Ramey, ITS, CWRU chet@po.cwru.edu http://tiswww.tis.cwru.edu/~chet/