[PATCH] [BZ #18422] elf/tst-audit tests fail without PLT entries

H.J. Lu hjl.tools@gmail.com
Mon May 25 20:53:00 GMT 2015


On Sun, May 24, 2015 at 7:06 PM, Carlos O'Donell <carlos@redhat.com> wrote:

> And that is the *real* bug. Please fix that instead of removing -Wl,-z,now.
> It should be a net-zero performance chance since either you are doing
> relocations for the GOT and then the PLT, or the GOT twice?

I did a closer look.  Nothing is wrong, except for that tst-audit2 expects
certain order in ld.so.  With JUMP_SLOT relocation, the GOTPLT entry of
calloc is update to calloc defined in tst-audit2:

(gdb) bt
#0  0xf7fe56bd in elf_machine_rel (reloc=<optimized out>,
    skip_ifunc=<optimized out>, reloc_addr_arg=<optimized out>,
    version=<optimized out>, sym=<optimized out>, map=<optimized out>)
    at ../sysdeps/i386/dl-machine.h:329
#1  elf_dynamic_do_Rel (skip_ifunc=<optimized out>, lazy=<optimized out>,
    nrelative=<optimized out>, relsize=<optimized out>,
    reladdr=<optimized out>, map=<optimized out>) at do-rel.h:137
#2  _dl_relocate_object (scope=0xf7ffdab8, reloc_mode=reloc_mode@entry=0,
    consider_profiling=1, consider_profiling@entry=0) at dl-reloc.c:258
#3  0xf7fdc648 in dl_main (phdr=<optimized out>, phnum=<optimized out>,
    user_entry=0xffffcf1c, auxv=0xffffd0a8) at rtld.c:2133
#4  0xf7ff0de7 in _dl_sysdep_start (
    start_argptr=start_argptr@entry=0xffffcfb0,
    dl_main=dl_main@entry=0xf7fda6f0 <dl_main>) at ../elf/dl-sysdep.c:249
#5  0xf7fddd05 in _dl_start_final (arg=0xffffcfb0) at rtld.c:308
#6  _dl_start (arg=0xffffcfb0) at rtld.c:414
#7  0xf7fd9a87 in _start ()
   from /export/build/gnu/glibc-32bit/build-i686-linux/elf/ld.so
(gdb)

and then calloc is called:

(gdb) c
Continuing.

Breakpoint 4, calloc (n=n@entry=20, m=4) at tst-audit2.c:18
18 {
(gdb) bt
#0  calloc (n=n@entry=20, m=4) at tst-audit2.c:18
#1  0xf7fe668d in _dl_relocate_object (scope=0xf7ffdab8,
    reloc_mode=reloc_mode@entry=0, consider_profiling=1,
    consider_profiling@entry=0) at dl-reloc.c:272
#2  0xf7fdc648 in dl_main (phdr=<optimized out>, phnum=<optimized out>,
    user_entry=0xffffcf1c, auxv=0xffffd0a8) at rtld.c:2133
#3  0xf7ff0de7 in _dl_sysdep_start (
    start_argptr=start_argptr@entry=0xffffcfb0,
    dl_main=dl_main@entry=0xf7fda6f0 <dl_main>) at ../elf/dl-sysdep.c:249
#4  0xf7fddd05 in _dl_start_final (arg=0xffffcfb0) at rtld.c:308
#5  _dl_start (arg=0xffffcfb0) at rtld.c:414
#6  0xf7fd9a87 in _start ()
   from /export/build/gnu/glibc-32bit/build-i686-linux/elf/ld.so
(gdb)

With GLOB_DAT relocation, calloc in ld.so is called first:

(gdb) bt
#0  calloc (nmemb=20, size=4) at dl-minimal.c:102
#1  0xf7fe665d in _dl_relocate_object (scope=0xf7fcfb20, reloc_mode=1,
    consider_profiling=1) at dl-reloc.c:272
#2  0xf7fdc500 in dl_main (phdr=<optimized out>, phnum=<optimized out>,
    user_entry=0xffffcf0c, auxv=0xffffd098) at rtld.c:2074
#3  0xf7ff0db7 in _dl_sysdep_start (
    start_argptr=start_argptr@entry=0xffffcfa0,
    dl_main=dl_main@entry=0xf7fda6c0 <dl_main>) at ../elf/dl-sysdep.c:249
#4  0xf7fddcd5 in _dl_start_final (arg=0xffffcfa0) at rtld.c:308
#5  _dl_start (arg=0xffffcfa0) at rtld.c:414
#6  0xf7fd9a57 in _start ()
   from /export/build/gnu/glibc-32bit-test/build-i686-linux/elf/ld.so
(gdb)

and then the GOT entry of calloc is updated:

(gdb) bt
#0  0xf7fe568d in elf_machine_rel (reloc=<optimized out>,
    skip_ifunc=<optimized out>, reloc_addr_arg=<optimized out>,
    version=<optimized out>, sym=<optimized out>, map=<optimized out>)
    at ../sysdeps/i386/dl-machine.h:329
#1  elf_dynamic_do_Rel (skip_ifunc=<optimized out>, lazy=<optimized out>,
    nrelative=<optimized out>, relsize=<optimized out>,
    reladdr=<optimized out>, map=<optimized out>) at do-rel.h:137
#2  _dl_relocate_object (scope=0xf7ffdab8, reloc_mode=reloc_mode@entry=0,
    consider_profiling=1, consider_profiling@entry=0) at dl-reloc.c:258
#3  0xf7fdc618 in dl_main (phdr=<optimized out>, phnum=<optimized out>,
    user_entry=0xffffcf0c, auxv=0xffffd098) at rtld.c:2133
#4  0xf7ff0db7 in _dl_sysdep_start (
    start_argptr=start_argptr@entry=0xffffcfa0,
    dl_main=dl_main@entry=0xf7fda6c0 <dl_main>) at ../elf/dl-sysdep.c:249
#5  0xf7fddcd5 in _dl_start_final (arg=0xffffcfa0) at rtld.c:308
#6  _dl_start (arg=0xffffcfa0) at rtld.c:414
#7  0xf7fd9a57 in _start ()
   from /export/build/gnu/glibc-32bit-test/build-i686-linux/elf/ld.so
(gdb)

After, calloc isn't called and magic in tst-audit2 isn't updated.  Both
orders are correct.  Here is a patch to make sure that calloc in tst-audit2.c is
called at least once from ld.so.

> I think it is important we continue to build ld.so with -Wl,-z,now, both
> for the optimizations, and for consistency among our security tooling.
>
> I'm happy to hear input from others.
>
> Have you checked to see how your patch to remove the PLT impacts analysis
> tooling like Asan and Valgrind?
>

No, i didn't test them nor I expect any problems.



-- 
H.J.
-------------- next part --------------
A non-text attachment was scrubbed...
Name: 0001-Make-sure-that-calloc-is-called-at-least-once.patch
Type: text/x-patch
Size: 6354 bytes
Desc: not available
URL: <http://sourceware.org/pipermail/libc-alpha/attachments/20150525/d83b9c54/attachment.bin>


More information about the Libc-alpha mailing list