1

[alpine-devel] [PATCH] Segfault in bc

Jeff Pohlmeyer
Details
Message ID
<CAEuRe+0GLDDtGcTCYS1uKnx9TcqcucAPpap9q5bGLbueWLdqOg@mail.gmail.com>
Sender timestamp
1315377741
DKIM signature
missing
Download raw message
The bc program doesn't seem to like -Os optimization:

   % echo 2+2 | bc -l
   Segmentation fault


I'm still not sure how the whole git/email thing works yet,
so I'm sending the patch as an attachment...

 - Jeff
Natanael Copa
Details
Message ID
<20110909194728.22041f4e@alpinelinux.org>
In-Reply-To
<CAEuRe+0GLDDtGcTCYS1uKnx9TcqcucAPpap9q5bGLbueWLdqOg@mail.gmail.com> (view parent)
Sender timestamp
1315590448
DKIM signature
missing
Download raw message
On Wed, 7 Sep 2011 01:42:21 -0500
Jeff Pohlmeyer <yetanothergeek@gmail.com> wrote:

> The bc program doesn't seem to like -Os optimization:
> 
>    % echo 2+2 | bc -l
>    Segmentation fault

That's interesting.
 
> I'm still not sure how the whole git/email thing works yet,
> so I'm sending the patch as an attachment...

I think the patch is just brushing the bug under the rug. I think this
is a real bug in application that don't get detected with -O2. It
appears that there have not been any release for atleast 10 years.

I think you have found a very old bug :)


I had a short look at the code. First thing i did was build it with
debugging symbols (CFLAGS="-Os -g") and its still triggered with the
simple testcase you gave.

So i ran it in gdb and got a backtrace:

(gdb) bt
#0  0xf7ff22c7 in addbyte (byte=75 'K') at load.c:78
#1  addbyte (byte=75 'K') at load.c:54
#2  0xf7ff27e4 in load_code (code=0xf7ffb99a "K") at load.c:307
#3  0xf7ff3ec6 in generate (str=0xf7ffb99a "K") at util.c:278
#4  0xf7fefa20 in yyparse () at bc.y:545
#5  0xf7fee7ec in main (argc=2, argv=0xffffdd04) at main.c:259


So I added a debug printf:
  ...
  /* Calculate the segment and offset. */
  pc = load_adr.pc_addr++;
  f = &functions[load_adr.pc_func];

  printf("DEBUG: pc=%i, f->f_body_size=%i\n", pc, f->f_body_size);
  if (pc >= f->f_body_size)
    {
      f->f_body_size *= 2;
      new_body = (char *) bc_malloc (f->f_body_size);
      memcpy(new_body, f->f_body, f->f_body_size/2);
      free (f->f_body);
      f->f_body = new_body;
    }

  /* Store the byte. */
  f->f_body[pc] = byte;   <<<<< It segfaults HERE
  f->f_code_size++;
}

And guess what... the run would go like:
...
DEBUG: pc=248, f->f_body_size=1024
DEBUG: pc=249, f->f_body_size=1024
DEBUG: pc=250, f->f_body_size=1024
DEBUG: pc=251, f->f_body_size=1024
DEBUG: pc=-8273196, f->f_body_size=1024
Segmentation fault

Which makes sense. pc being negative will surely segfault things.

Then i rebuilt with -O2 and re-ran it:
...
DEBUG: pc=250, f->f_body_size=1024
DEBUG: pc=251, f->f_body_size=1024
DEBUG: pc=0, f->f_body_size=1024
DEBUG: pc=1, f->f_body_size=1024
DEBUG: pc=2, f->f_body_size=1024
DEBUG: pc=3, f->f_body_size=1024
DEBUG: pc=4, f->f_body_size=1024
DEBUG: pc=5, f->f_body_size=1024
DEBUG: pc=6, f->f_body_size=1024
DEBUG: pc=7, f->f_body_size=1024
4


Ok. This smells like a bug when resetting the counter.

I googled around and found out that gentoo has an updated version which
seems to work. (and I found another patch that gentoo uses)

I have pushed the 1.06.95 version + gentoo patch to "edge" and
cherry-picked it for 2.2-stable.

Thanks for reporting!
-nc


---
Unsubscribe:  alpine-devel+unsubscribe@lists.alpinelinux.org
Help:         alpine-devel+help@lists.alpinelinux.org
---