On 4/17/11 6:28 AM, [email protected] wrote:
>
> Configuration Information [Automatically generated, do not change]:
> Machine: x86_64
> OS: linux-gnu
> Compiler: gcc
> Compilation CFLAGS: -DPROGRAM='bash' -DCONF_HOSTTYPE='x86_64'
> -DCONF_OSTYPE='linux-gnu' -DCONF_MACHTYPE='x86_64-redhat-linux-gnu'
> -DCONF_VENDOR='redhat' -DLOCALEDIR='/usr/share/locale' -DPACKAGE='bash'
> -DSHELL
> -DHAVE_CONFIG_H -I. -I. -I./include -I./lib -D_GNU_SOURCE -DRECYCLES_PIDS
> -O2 -g -pipe -Wall -Wp,-D_FORTIFY_SOURCE=2 -fexceptions -fstack-protector
> --param=ssp-buffer-size=4 -m64 -mtune=generic
> uname output: Linux dabbasciano 2.6.35.12-88.fc14.x86_64 #1 SMP Thu Mar 31
> 21:21:57 UTC 2011 x86_64 x86_64 x86_64 GNU/Linux
> Machine Type: x86_64-redhat-linux-gnu
>
> Bash Version: 4.1
> Patch Level: 7
> Release Status: release
>
> Description:
> I tried to write a simple bash script like this:
> #!/bin/bash
> fc -l -2
> When I run for the first time it works well, but if I execute again the
> script I
> receive a "Segmentation fault (core dumped)" and the bash die.
>
> Repeat-By:
> To reproduce the problem you must create a simple script with the follow 2
> lines:
> #!/bin/bash
> fc -l -2
> and then run the script for 2 time. The output is:
> $ . fc.sh
> 1000 cd prog/script/
> 1001 . fc.sh
> $ . fc.sh
> 1001 . fc.sh
> Segmentation fault (core dumped)
The problem has to do with bad calculations of the last history entry.
I've attached patches for bash-4.1 and bash-4.2. Please let me know if
they fix the problem; they seem to fix it for me.
Chet
--
``The lyf so short, the craft so long to lerne.'' - Chaucer
``Ars longa, vita brevis'' - Hippocrates
Chet Ramey, ITS, CWRU [email protected] http://cnswww.cns.cwru.edu/~chet/
*** ../bash-4.1-patched/builtins/fc.def 2009-03-21 14:03:43.000000000 -0400
--- builtins/fc.def 2011-04-19 15:46:17.000000000 -0400
***************
*** 304,307 ****
--- 304,317 ----
last_hist = i - rh - hist_last_line_added;
+ /* XXX */
+ if (i == last_hist && hlist[last_hist] == 0)
+ while (last_hist >= 0 && hlist[last_hist] == 0)
+ last_hist--;
+ if (last_hist < 0)
+ {
+ sh_erange ((char *)NULL, _("history specification"));
+ return (EXECUTION_FAILURE);
+ }
+
if (list)
{
***************
*** 466,470 ****
{
int sign, n, clen, rh;
! register int i, j;
register char *s;
--- 476,480 ----
{
int sign, n, clen, rh;
! register int i, j, last_hist;
register char *s;
***************
*** 486,490 ****
calculation as if it were on. */
rh = remember_on_history || ((subshell_environment & SUBSHELL_COMSUB) && enable_history_list);
! i -= rh + hist_last_line_added;
/* No specification defaults to most recent command. */
--- 496,508 ----
calculation as if it were on. */
rh = remember_on_history || ((subshell_environment & SUBSHELL_COMSUB) && enable_history_list);
! last_hist = i - rh - hist_last_line_added;
!
! if (i == last_hist && hlist[last_hist] == 0)
! while (last_hist >= 0 && hlist[last_hist] == 0)
! last_hist--;
! if (last_hist < 0)
! return (-1);
!
! i = last_hist;
/* No specification defaults to most recent command. */
*** ../bash-4.2-patched/builtins/fc.def 2010-05-30 18:25:38.000000000 -0400
--- builtins/fc.def 2011-04-19 15:46:17.000000000 -0400
***************
*** 305,309 ****
/* XXX */
! if (saved_command_line_count > 0 && i == last_hist && hlist[last_hist] == 0)
while (last_hist >= 0 && hlist[last_hist] == 0)
last_hist--;
--- 305,309 ----
/* XXX */
! if (i == last_hist && hlist[last_hist] == 0)
while (last_hist >= 0 && hlist[last_hist] == 0)
last_hist--;
***************
*** 476,480 ****
{
int sign, n, clen, rh;
! register int i, j;
register char *s;
--- 476,480 ----
{
int sign, n, clen, rh;
! register int i, j, last_hist;
register char *s;
***************
*** 496,500 ****
calculation as if it were on. */
rh = remember_on_history || ((subshell_environment & SUBSHELL_COMSUB) && enable_history_list);
! i -= rh + hist_last_line_added;
/* No specification defaults to most recent command. */
--- 496,508 ----
calculation as if it were on. */
rh = remember_on_history || ((subshell_environment & SUBSHELL_COMSUB) && enable_history_list);
! last_hist = i - rh - hist_last_line_added;
!
! if (i == last_hist && hlist[last_hist] == 0)
! while (last_hist >= 0 && hlist[last_hist] == 0)
! last_hist--;
! if (last_hist < 0)
! return (-1);
!
! i = last_hist;
/* No specification defaults to most recent command. */