ports/bash4 --enable-static fails

Craig Rodrigues rodrigc at crodrigues.org
Thu May 10 04:20:13 UTC 2012


On Wed, May 9, 2012 at 2:37 PM, Sean Bruno <seanbru at yahoo-inc.com> wrote:
> I'm assuming that the recent jemalloc updates have broken something
> subtly that is now causing static symbol compilation to fail.
>
> ports/bash4 isn't the simplest case, but its the most obvious one that
> is in my face.
>
>
> http://people.freebsd.org/~sbruno/bash4_jemalloc.txt
>

Hi,

The problem is here:
==============================================================================================
./lib/malloc/libmalloc.a(malloc.o):/usr/ports/shells/bash/work/bash-4.2/lib/malloc/malloc.c:1269:
first defined here
/usr/lib/libc.a(jemalloc_jemalloc.o): In function `realloc':
jemalloc_jemalloc.c:(.text+0x2350): multiple definition of `realloc'
./lib/malloc/libmalloc.a(malloc.o):/usr/ports/shells/bash/work/bash-4.2/lib/malloc/malloc.c:1262:
first defined here
/usr/lib/libc.a(jemalloc_jemalloc.o): In function `calloc':
jemalloc_jemalloc.c:(.text+0x24d0): multiple definition of `calloc'
./lib/malloc/libmalloc.a(malloc.o):/usr/ports/shells/bash/work/bash-4.2/lib/malloc/malloc.c:1294:
first defined here
/usr/lib/libc.a(jemalloc_jemalloc.o): In function `malloc':
jemalloc_jemalloc.c:(.text+0x27a0): multiple definition of `malloc'
./lib/malloc/libmalloc.a(malloc.o):/usr/ports/shells/bash/work/bash-4.2/lib/malloc/malloc.c:1254:
first defined here
==============================================================================================

Bash is trying to override the malloc() functions in libc with its own
implementation in lib/malloc/malloc.c .
I have seen this type of trick before 3rd party code that tries to
override the libc implementation of malloc() / free() with its own.

kan@ explained this to me before, but I don't know if I can explain it
as well as him, because it has to do
with how static linking works. :)

Basically, the malloc.o object from bash, *must* have implementations of
*all* the relevant functions in jemalloc_jemalloc.o in order for
malloc.o to properly override jemalloc_jemalloc.o.

If you have something like:
jemalloc_jemalloc.o  (libc)                   malloc.o (Bash)
===============                           =============
malloc()                                              malloc()
free()                                                   free()
calloc()
realloc()


the static linker will not be able to replace jemalloc_jemalloc.o from
libc with malloc.o from Bash,
because calloc() and realloc() symbols in jemalloc_jemalloc.o (libc)
do not exist malloc.o (Bash).

Since the linker can only deal with whole objects (.o files), it will
try to pull in both
jemalloc_jemalloc.o and malloc.o when doing static linking.

I may have got some of the details/explanation wrong, but I have fixed
something similar
to this in 3rd party code, when the layout of malloc() functions in
libc changed between FreeBSD 4 and FreeBSD 6.

What you need to do is:
   (1)  run nm or readelf on jemalloc_jemalloc.o,   then run nm or
readelf on malloc.o
   (2)  Look at the symbols in both
   (3)  Add the missing symbols to malloc.c in Bash

-- 
Craig Rodrigues
rodrigc at crodrigues.org


More information about the freebsd-current mailing list