Link error about sbrk
Jeff Johnston
jjohnstn@redhat.com
Tue Nov 17 00:43:00 GMT 2009
On 15/11/09 10:53 AM, loody wrote:
> Dear all:
> I cross-compile newlib as mips target, but when I link the libraries I
> build in libgloss, I get the error as below:
>
> # make TOOLCHAIN=mipsel-unknown-elf-
> mipsel-unknown-elf-ld -T ./link.xn -o TestCode.elf -Map TestCode.map
> --oformat elf32-littlemips init.o reset.o atexit.o -static -nostdlib
> -L/media/sdb1/newlib-1.17.0/mipsel/libgloss/libnosys
> -L/media/sdb1/newlib-1.17.0/mipsel/libgloss/mips/libidt.a
> -L/media/sdb1/newlib-1.17.0/mipsel/newlib -lnosys -lc
> /media/sdb1/newlib-1.17.0/mipsel/newlib/libc.a(lib_a-sbrkr.o): In
> function `_sbrk_r':
> (.text+0x14): undefined reference to `sbrk'
> /media/sdb1/newlib-1.17.0/mipsel/newlib/libc.a(lib_a-sbrkr.o): In
> function `_sbrk_r':
> (.text+0x14): relocation truncated to fit: R_MIPS_26 against `sbrk'
> make: *** [TestCode.elf] Error 1
> #
>
> My questions are:
> 1. take mips for example, why we have to build some many different libraries as
> libcfe.a
> libidt.a
> liblsi.a
> libnullmon.a
> libpmon.a
> instead of build a bare one?
> ( all of them are just different combinations of the .o files)
> if we ar all .o files as one library, linker will link what we need
> automatically, right?
No, they are different libraries and there is functional overlap. For
example, libnullmon.a is a stub library. libcfe is for MIPS boards
running cfe. libpmon.a is for boards running the PMON monitor. For
example, how do you expect the linker to magically know which version of
the read syscall you actually mean? From libnullmon.a read is a stub
which does nothing whereas from libpmon.a it will access a magic slot in
the PMON vector. The latter choice expects that you are running the
PMON monitor on your board.
>
> 2. the files I need to modify, system calls that act as 'glue' between
> newlib and my OS, are all located at libgloss/mips, right? If so, I
> have checked that sbrk is located at syscalls.c and it is ared at
> libidt.a, but why linker still complain he cannot find the sbrk? did I
> miss something?
>
Your -L option should specify a directory path, not the library itself
(you have libidt.a at the end). You should then specify -Tidt.ld or
-Tidt32.ld as your linker script and it will bring in libidt.a for you.
It is highly recommended that you use gcc to do your linking and specify
-Tidt.ld or -Tidt32.ld. This simplifies things when you build/install
newlib and gcc in the same source tree because you don't need to specify
-L statements and you automatically pick up the correct C library for
your compiler options. For example, the little-endian vs the big-endian
version of the newlib library. When you use gcc to link, it knows which
options you specify and maps them to the directories which contain the
appropriate library built with the same options. If you use ld, you
have to manually specify the library locations yourself and you might
get them wrong.
-- Jeff J.
> appreciate your help,
> miloody
More information about the Newlib
mailing list