* [PATCH] [BZ #18422] elf/tst-audit tests fail without PLT entries
@ 2015-05-24 3:37 H.J. Lu
2015-05-24 15:40 ` Carlos O'Donell
0 siblings, 1 reply; 12+ messages in thread
From: H.J. Lu @ 2015-05-24 3:37 UTC (permalink / raw)
To: GNU C Library
PLT entries aren't required when -z now used. Linker on master with:
commit 25070364b0ce33eed46aa5d78ebebbec6accec7e
Author: H.J. Lu <hjl.tools@gmail.com>
Date: Sat May 16 07:00:21 2015 -0700
Don't generate PLT relocations for now binding
There is no need for PLT relocations with -z now. We can use GOT
relocations, which take less space, instead and replace 16-byte .plt
entres with 8-byte .plt.got entries.
bfd/
* elf32-i386.c (elf_i386_check_relocs): Create .plt.got section
for now binding.
(elf_i386_allocate_dynrelocs): Use .plt.got section for now
binding.
* elf64-x86-64.c (elf_x86_64_check_relocs): Create .plt.got
section for now binding.
(elf_x86_64_allocate_dynrelocs): Use .plt.got section for now
binding.
won't generate PLT entries with -z now. elf/tst-audit2.c has
/* This calloc definition will be called by the dynamic linker itself.
We test that it has initialized our TLS block by the time it does so.
*/
void *
calloc (size_t n, size_t m)
{
if (magic[0] != MAGIC1 || magic[1] != MAGIC2)
{
printf ("{%x, %x} != {%x, %x}\n", magic[0], magic[1], MAGIC1, MAGIC2);
abort ();
}
magic[0] = MAGIC2;
magic[1] = MAGIC1;
Since ld.so is built with -z now, there are no PLT relocations and this
calloc won't be used:
Relocation section '.rela.dyn' at offset 0x66c contains 16 entries:
Offset Info Type Sym.Value Sym. Name + Addend
00222e88 00000008 R_X86_64_RELATIVE 10970
00222e8c 00000008 R_X86_64_RELATIVE f8f0
00222e90 00000008 R_X86_64_RELATIVE f6c0
00222e94 00000008 R_X86_64_RELATIVE 11bd0
00222e98 00000008 R_X86_64_RELATIVE a1b0
00222e9c 00000008 R_X86_64_RELATIVE 130c0
00222ea0 00000008 R_X86_64_RELATIVE 13c50
00222ea4 00000008 R_X86_64_RELATIVE 15fc0
00222ea8 00000008 R_X86_64_RELATIVE 12cd0
00222eac 00000008 R_X86_64_RELATIVE 17f90
00222fbc 00000a06 R_X86_64_GLOB_DAT 00018230 __libc_memalign@@GLIBC_2.16 + 0
00222fc4 00001506 R_X86_64_GLOB_DAT 00018300 malloc@@GLIBC_2.16 + 0
00222fcc 00000d06 R_X86_64_GLOB_DAT 00018310 calloc@@GLIBC_2.16 + 0
00222fd4 00000506 R_X86_64_GLOB_DAT 000184a0 realloc@@GLIBC_2.16 + 0
00222fdc 00000706 R_X86_64_GLOB_DAT 002239a0 _r_debug@@GLIBC_2.16 + 0
00222fe4 00000406 R_X86_64_GLOB_DAT 00018340 free@@GLIBC_2.16 + 0
Assuming we do want to keep PLT relocations in ld.so so that malloc
functions in ld.so can be overridden, ld.so should be built with -z now.
There is no reason to build ld.so with -z now since ld.so is the one
doing BIND_NOW. The only thing we get with -z now on ld.so is DT tag:
0x0000000000000018 (BIND_NOW)
0x000000006ffffffb (FLAGS_1) Flags: NOW
This patch removes -Wl,-z,now from ld.so build.
OK for master?
H.J.
[BZ #18422]
* elf/Makefile (z-now-yes): Removed.
($(objpfx)ld.so): Remove $(z-now-$(bind-now)).
---
elf/Makefile | 4 +---
1 file changed, 1 insertion(+), 3 deletions(-)
diff --git a/elf/Makefile b/elf/Makefile
index 34450ea..324b4a2 100644
--- a/elf/Makefile
+++ b/elf/Makefile
@@ -349,13 +349,11 @@ $(objpfx)librtld.os: $(objpfx)dl-allobjs.os $(objpfx)rtld-libc.a
generated += librtld.map librtld.mk rtld-libc.a librtld.os.map
-z-now-yes = -Wl,-z,now
-
$(objpfx)ld.so: $(objpfx)librtld.os $(ld-map)
# Link into a temporary file so that we don't touch $@ at all
# if the sanity check below fails.
$(LINK.o) -nostdlib -nostartfiles -shared -o $@.new \
- $(LDFLAGS-rtld) -Wl,-z,defs $(z-now-$(bind-now)) \
+ $(LDFLAGS-rtld) -Wl,-z,defs \
$(filter-out $(map-file),$^) $(load-map-file) \
-Wl,-soname=$(rtld-installed-name) \
-Wl,-defsym=_begin=0
--
2.1.0
^ permalink raw reply [flat|nested] 12+ messages in thread
* Re: [PATCH] [BZ #18422] elf/tst-audit tests fail without PLT entries
2015-05-24 3:37 [PATCH] [BZ #18422] elf/tst-audit tests fail without PLT entries H.J. Lu
@ 2015-05-24 15:40 ` Carlos O'Donell
2015-05-24 16:32 ` H.J. Lu
2015-05-26 13:22 ` Florian Weimer
0 siblings, 2 replies; 12+ messages in thread
From: Carlos O'Donell @ 2015-05-24 15:40 UTC (permalink / raw)
To: H.J. Lu, GNU C Library, Florian Weimer, Adam Conrad,
Aurelien Jarno, Andreas Schwab
Cc: Jeff Law
On 05/23/2015 09:14 AM, H.J. Lu wrote:
> Since ld.so is built with -z now, there are no PLT relocations and this
> calloc won't be used:
Which is bad. We always want these functions to be interposable by all
of the analysis tools that want and need to track memory allocations.
Thus it is not just the test that matters.
> Relocation section '.rela.dyn' at offset 0x66c contains 16 entries:
> Offset Info Type Sym.Value Sym. Name + Addend
> 00222e88 00000008 R_X86_64_RELATIVE 10970
> 00222e8c 00000008 R_X86_64_RELATIVE f8f0
> 00222e90 00000008 R_X86_64_RELATIVE f6c0
> 00222e94 00000008 R_X86_64_RELATIVE 11bd0
> 00222e98 00000008 R_X86_64_RELATIVE a1b0
> 00222e9c 00000008 R_X86_64_RELATIVE 130c0
> 00222ea0 00000008 R_X86_64_RELATIVE 13c50
> 00222ea4 00000008 R_X86_64_RELATIVE 15fc0
> 00222ea8 00000008 R_X86_64_RELATIVE 12cd0
> 00222eac 00000008 R_X86_64_RELATIVE 17f90
> 00222fbc 00000a06 R_X86_64_GLOB_DAT 00018230 __libc_memalign@@GLIBC_2.16 + 0
> 00222fc4 00001506 R_X86_64_GLOB_DAT 00018300 malloc@@GLIBC_2.16 + 0
> 00222fcc 00000d06 R_X86_64_GLOB_DAT 00018310 calloc@@GLIBC_2.16 + 0
> 00222fd4 00000506 R_X86_64_GLOB_DAT 000184a0 realloc@@GLIBC_2.16 + 0
> 00222fdc 00000706 R_X86_64_GLOB_DAT 002239a0 _r_debug@@GLIBC_2.16 + 0
> 00222fe4 00000406 R_X86_64_GLOB_DAT 00018340 free@@GLIBC_2.16 + 0
Doesn't this also cause check-localplt to fail for ld.so given
that calloc and others are no longer R_X86_64_JUMP_SLOT?
> Assuming we do want to keep PLT relocations in ld.so so that malloc
> functions in ld.so can be overridden, ld.so should be built with -z now.
> There is no reason to build ld.so with -z now since ld.so is the one
> doing BIND_NOW. The only thing we get with -z now on ld.so is DT tag:
>
> 0x0000000000000018 (BIND_NOW)
> 0x000000006ffffffb (FLAGS_1) Flags: NOW
>
> This patch removes -Wl,-z,now from ld.so build.
>
> OK for master?
No. I'd like to see more discussion on this.
I don't see any other way forward, and I agree that DT_BIND_NOW seems
a bit silly for the linker since it itself is the component responsible
for that binding.
My worry is that the missing DT tag is going to have security implications.
I'm including several other distro people on the TO.
The first thing I'll have to explain is "Why doesn't ld.so meet full RELRO?"
Since full RELRO requires DT_BIND_NOW + RO segments. Does this mean ld.so
with your patch will by lazily bound and not mark it's own PLT immediately RO?
That seems wrong.
Given the wrongness I'd like to see more discussion, and it's late in my TZ
so I'm not up for a detailed response yet.
However, the first thing that pops into mind is that this wrong, but wrong
in the sense that I don't know if the static linker can even make this choice
(removing the PLT) without information from the user.
The notion of -z,now means "Bind symbols now, not lazily", but that doesn't
give you enough information to elide the PLT and use the GOT directly since
the interposition is still useful and relied upon semantic in ELF.
Cheers,
Carlos.
> H.J.
> [BZ #18422]
> * elf/Makefile (z-now-yes): Removed.
> ($(objpfx)ld.so): Remove $(z-now-$(bind-now)).
> ---
> elf/Makefile | 4 +---
> 1 file changed, 1 insertion(+), 3 deletions(-)
>
> diff --git a/elf/Makefile b/elf/Makefile
> index 34450ea..324b4a2 100644
> --- a/elf/Makefile
> +++ b/elf/Makefile
> @@ -349,13 +349,11 @@ $(objpfx)librtld.os: $(objpfx)dl-allobjs.os $(objpfx)rtld-libc.a
>
> generated += librtld.map librtld.mk rtld-libc.a librtld.os.map
>
> -z-now-yes = -Wl,-z,now
> -
> $(objpfx)ld.so: $(objpfx)librtld.os $(ld-map)
> # Link into a temporary file so that we don't touch $@ at all
> # if the sanity check below fails.
> $(LINK.o) -nostdlib -nostartfiles -shared -o $@.new \
> - $(LDFLAGS-rtld) -Wl,-z,defs $(z-now-$(bind-now)) \
> + $(LDFLAGS-rtld) -Wl,-z,defs \
> $(filter-out $(map-file),$^) $(load-map-file) \
> -Wl,-soname=$(rtld-installed-name) \
> -Wl,-defsym=_begin=0
>
^ permalink raw reply [flat|nested] 12+ messages in thread
* Re: [PATCH] [BZ #18422] elf/tst-audit tests fail without PLT entries
2015-05-24 15:40 ` Carlos O'Donell
@ 2015-05-24 16:32 ` H.J. Lu
2015-05-25 5:17 ` Carlos O'Donell
2015-05-26 13:22 ` Florian Weimer
1 sibling, 1 reply; 12+ messages in thread
From: H.J. Lu @ 2015-05-24 16:32 UTC (permalink / raw)
To: Carlos O'Donell
Cc: GNU C Library, Florian Weimer, Adam Conrad, Aurelien Jarno,
Andreas Schwab, Jeff Law
On Sat, May 23, 2015 at 8:37 PM, Carlos O'Donell <carlos@redhat.com> wrote:
> On 05/23/2015 09:14 AM, H.J. Lu wrote:
>> Since ld.so is built with -z now, there are no PLT relocations and this
>> calloc won't be used:
>
> Which is bad. We always want these functions to be interposable by all
> of the analysis tools that want and need to track memory allocations.
> Thus it is not just the test that matters.
>
...
>> 00222fc4 00001506 R_X86_64_GLOB_DAT 00018300 malloc@@GLIBC_2.16 + 0
>> 00222fcc 00000d06 R_X86_64_GLOB_DAT 00018310 calloc@@GLIBC_2.16 + 0
>> 00222fd4 00000506 R_X86_64_GLOB_DAT 000184a0 realloc@@GLIBC_2.16 + 0
>> 00222fdc 00000706 R_X86_64_GLOB_DAT 002239a0 _r_debug@@GLIBC_2.16 + 0
>> 00222fe4 00000406 R_X86_64_GLOB_DAT 00018340 free@@GLIBC_2.16 + 0
>
> Doesn't this also cause check-localplt to fail for ld.so given
> that calloc and others are no longer R_X86_64_JUMP_SLOT?
Yes.
>> Assuming we do want to keep PLT relocations in ld.so so that malloc
>> functions in ld.so can be overridden, ld.so should be built with -z now.
>> There is no reason to build ld.so with -z now since ld.so is the one
>> doing BIND_NOW. The only thing we get with -z now on ld.so is DT tag:
>>
>> 0x0000000000000018 (BIND_NOW)
>> 0x000000006ffffffb (FLAGS_1) Flags: NOW
>>
>> This patch removes -Wl,-z,now from ld.so build.
>>
>> OK for master?
>
> No. I'd like to see more discussion on this.
>
> I don't see any other way forward, and I agree that DT_BIND_NOW seems
> a bit silly for the linker since it itself is the component responsible
> for that binding.
>
> My worry is that the missing DT tag is going to have security implications.
> I'm including several other distro people on the TO.
>
> The first thing I'll have to explain is "Why doesn't ld.so meet full RELRO?"
> Since full RELRO requires DT_BIND_NOW + RO segments. Does this mean ld.so
> with your patch will by lazily bound and not mark it's own PLT immediately RO?
> That seems wrong.
My patch just doesn't use -z now to build ld.so when --enable-bind-now is
used and ld.so always gets PLT with/without --enable-bind-now. It is the
same as before when building glibc with the older ld. The only difference now
is we no long generate DT_BIND_NOW even when --enable-bind-now is used.
I don't believe DT_BIND_NOW should make a difference on ld.so. If it is, it is
a separate bug and we should fix it.
> Given the wrongness I'd like to see more discussion, and it's late in my TZ
> so I'm not up for a detailed response yet.
>
> However, the first thing that pops into mind is that this wrong, but wrong
> in the sense that I don't know if the static linker can even make this choice
> (removing the PLT) without information from the user.
Passing -z now tells ld that we don't do lazy bind, the only thing which PLT
is used for. ld also implemented an optimization to generate .plt.got, which
uses the GOT slot, instead of the GOTPLT slot, when we need the PLT entry
without PLT relocation.
https://groups.google.com/forum/#!topic/x86-64-abi/LDuYGdXGskY
> The notion of -z,now means "Bind symbols now, not lazily", but that doesn't
> give you enough information to elide the PLT and use the GOT directly since
> the interposition is still useful and relied upon semantic in ELF.
You still get the interposition with GOT, just not lazy bind, which needs PLT
relocation. GCC 6 even has a new option, -fno-plt, to avoid PLT:
https://gcc.gnu.org/ml/gcc-patches/2015-05/msg00231.html
ld.so is a special case and needs PLT for the interposition unless
ld.so re-applies
GOT relocations on itself after all modules are loaded.
--
H.J.
^ permalink raw reply [flat|nested] 12+ messages in thread
* Re: [PATCH] [BZ #18422] elf/tst-audit tests fail without PLT entries
2015-05-24 16:32 ` H.J. Lu
@ 2015-05-25 5:17 ` Carlos O'Donell
2015-05-25 20:53 ` H.J. Lu
0 siblings, 1 reply; 12+ messages in thread
From: Carlos O'Donell @ 2015-05-25 5:17 UTC (permalink / raw)
To: H.J. Lu
Cc: GNU C Library, Florian Weimer, Adam Conrad, Aurelien Jarno,
Andreas Schwab, Jeff Law
On 05/24/2015 08:45 AM, H.J. Lu wrote:
> On Sat, May 23, 2015 at 8:37 PM, Carlos O'Donell <carlos@redhat.com> wrote:
>> On 05/23/2015 09:14 AM, H.J. Lu wrote:
>>> Since ld.so is built with -z now, there are no PLT relocations and this
>>> calloc won't be used:
>>
>> Which is bad. We always want these functions to be interposable by all
>> of the analysis tools that want and need to track memory allocations.
>> Thus it is not just the test that matters.
>>
> ...
>>> 00222fc4 00001506 R_X86_64_GLOB_DAT 00018300 malloc@@GLIBC_2.16 + 0
>>> 00222fcc 00000d06 R_X86_64_GLOB_DAT 00018310 calloc@@GLIBC_2.16 + 0
>>> 00222fd4 00000506 R_X86_64_GLOB_DAT 000184a0 realloc@@GLIBC_2.16 + 0
>>> 00222fdc 00000706 R_X86_64_GLOB_DAT 002239a0 _r_debug@@GLIBC_2.16 + 0
>>> 00222fe4 00000406 R_X86_64_GLOB_DAT 00018340 free@@GLIBC_2.16 + 0
>>
>> Doesn't this also cause check-localplt to fail for ld.so given
>> that calloc and others are no longer R_X86_64_JUMP_SLOT?
>
> Yes.
Good.
>>> Assuming we do want to keep PLT relocations in ld.so so that malloc
>>> functions in ld.so can be overridden, ld.so should be built with -z now.
>>> There is no reason to build ld.so with -z now since ld.so is the one
>>> doing BIND_NOW. The only thing we get with -z now on ld.so is DT tag:
>>>
>>> 0x0000000000000018 (BIND_NOW)
>>> 0x000000006ffffffb (FLAGS_1) Flags: NOW
>>>
>>> This patch removes -Wl,-z,now from ld.so build.
>>>
>>> OK for master?
>>
>> No. I'd like to see more discussion on this.
>>
>> I don't see any other way forward, and I agree that DT_BIND_NOW seems
>> a bit silly for the linker since it itself is the component responsible
>> for that binding.
>>
>> My worry is that the missing DT tag is going to have security implications.
>> I'm including several other distro people on the TO.
>>
>> The first thing I'll have to explain is "Why doesn't ld.so meet full RELRO?"
>> Since full RELRO requires DT_BIND_NOW + RO segments. Does this mean ld.so
>> with your patch will by lazily bound and not mark it's own PLT immediately RO?
>> That seems wrong.
>
> My patch just doesn't use -z now to build ld.so when --enable-bind-now is
> used and ld.so always gets PLT with/without --enable-bind-now. It is the
> same as before when building glibc with the older ld. The only difference now
> is we no long generate DT_BIND_NOW even when --enable-bind-now is used.
> I don't believe DT_BIND_NOW should make a difference on ld.so. If it is, it is
> a separate bug and we should fix it.
The patch is a hack.
- ld.so should continue to have DT_BIND_NOW since we are requesting that
any symbol binding done in ld.so be done at startup and not lazily, and
generic security tools should be able to check all binaries including
ld.so to see that this is enabled and requested without making special
exceptions.
- ld.so can have no PLT if that is what happens as a result of a dynamic
loader optimization triggered by -Wl,-z,now. That seems like a useful
optimization which would be disabled by your suggested patch?
- ld.so should still support ELF symbol interposition, which is orthogonal
to lazy binding. Lazy binding and ELF symbol interposition should not be
conflated.
>> The notion of -z,now means "Bind symbols now, not lazily", but that doesn't
>> give you enough information to elide the PLT and use the GOT directly since
>> the interposition is still useful and relied upon semantic in ELF.
>
> You still get the interposition with GOT, just not lazy bind, which needs PLT
> relocation.
Good point.
> GCC 6 even has a new option, -fno-plt, to avoid PLT:
>
> https://gcc.gnu.org/ml/gcc-patches/2015-05/msg00231.html
GCC has many options that must be used with care and foresight.
> ld.so is a special case and needs PLT for the interposition unless
> ld.so re-applies GOT relocations on itself after all modules are loaded.
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 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?
Cheers,
Carlos.
^ permalink raw reply [flat|nested] 12+ messages in thread
* Re: [PATCH] [BZ #18422] elf/tst-audit tests fail without PLT entries
2015-05-25 5:17 ` Carlos O'Donell
@ 2015-05-25 20:53 ` H.J. Lu
2015-05-26 10:53 ` Carlos O'Donell
0 siblings, 1 reply; 12+ messages in thread
From: H.J. Lu @ 2015-05-25 20:53 UTC (permalink / raw)
To: Carlos O'Donell
Cc: GNU C Library, Florian Weimer, Adam Conrad, Aurelien Jarno,
Andreas Schwab, Jeff Law
[-- Attachment #1: Type: text/plain, Size: 4836 bytes --]
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.
[-- Attachment #2: 0001-Make-sure-that-calloc-is-called-at-least-once.patch --]
[-- Type: text/x-patch, Size: 6354 bytes --]
From 31d9cfee87edf3acf95640db262b950e3b0514f3 Mon Sep 17 00:00:00 2001
From: "H.J. Lu" <hjl.tools@gmail.com>
Date: Mon, 25 May 2015 11:30:57 -0700
Subject: [PATCH] Make sure that calloc is called at least once
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
PLT relocations aren't required when -z now used. Linker on master with:
commit 25070364b0ce33eed46aa5d78ebebbec6accec7e
Author: H.J. Lu <hjl.tools@gmail.com>
Date: Sat May 16 07:00:21 2015 -0700
Don't generate PLT relocations for now binding
There is no need for PLT relocations with -z now. We can use GOT
relocations, which take less space, instead and replace 16-byte .plt
entres with 8-byte .plt.got entries.
bfd/
* elf32-i386.c (elf_i386_check_relocs): Create .plt.got section
for now binding.
(elf_i386_allocate_dynrelocs): Use .plt.got section for now
binding.
* elf64-x86-64.c (elf_x86_64_check_relocs): Create .plt.got
section for now binding.
(elf_x86_64_allocate_dynrelocs): Use .plt.got section for now
binding.
won't generate PLT relocations with -z now. elf/tst-audit2.c expect
certain order of execution in ld.so. With PLT relocations, the GOTPLT
entry of calloc is update to calloc defined in tst-audit2:
(gdb) bt
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
out>,
nrelative=<optimized out>, relsize=<optimized out>,
reladdr=<optimized out>, map=<optimized out>) at do-rel.h:137
reloc_mode=reloc_mode@entry=0,
consider_profiling=1, consider_profiling@entry=0) at dl-reloc.c:258
user_entry=0xffffcf1c, auxv=0xffffd0a8) at rtld.c:2133
start_argptr=start_argptr@entry=0xffffcfb0,
dl_main=dl_main@entry=0xf7fda6f0 <dl_main>) at
../elf/dl-sysdep.c:249
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
reloc_mode=reloc_mode@entry=0, consider_profiling=1,
consider_profiling@entry=0) at dl-reloc.c:272
user_entry=0xffffcf1c, auxv=0xffffd0a8) at rtld.c:2133
start_argptr=start_argptr@entry=0xffffcfb0,
dl_main=dl_main@entry=0xf7fda6f0 <dl_main>) at
../elf/dl-sysdep.c:249
from /export/build/gnu/glibc-32bit/build-i686-linux/elf/ld.so
(gdb)
With GOT relocation, calloc in ld.so is called first:
(gdb) bt
consider_profiling=1) at dl-reloc.c:272
user_entry=0xffffcf0c, auxv=0xffffd098) at rtld.c:2074
start_argptr=start_argptr@entry=0xffffcfa0,
dl_main=dl_main@entry=0xf7fda6c0 <dl_main>) at
../elf/dl-sysdep.c:249
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
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
out>,
nrelative=<optimized out>, relsize=<optimized out>,
reladdr=<optimized out>, map=<optimized out>) at do-rel.h:137
reloc_mode=reloc_mode@entry=0,
consider_profiling=1, consider_profiling@entry=0) at dl-reloc.c:258
user_entry=0xffffcf0c, auxv=0xffffd098) at rtld.c:2133
start_argptr=start_argptr@entry=0xffffcfa0,
dl_main=dl_main@entry=0xf7fda6c0 <dl_main>) at
../elf/dl-sysdep.c:249
from /export/build/gnu/glibc-32bit-test/build-i686-linux/elf/ld.so
(gdb)
After that, since calloc isn't called from ld.so nor any other modules,
magic in tst-audit2 isn't updated. Both orders are correct. This patch
makes sure that calloc in tst-audit2.c is called at least once from ld.so.
[BZ #18422]
* Makefile ($(objpfx)tst-audit2): Depend on $(libdl).
($(objpfx)tst-audit2.out): Also depend on
$(objpfx)tst-auditmod9b.so.
* elf/tst-audit2.c: Include <dlfcn.h>.
(calloc_called): New.
(calloc): Allow to be called more than once.
(do_test): dllopen/dlclose $ORIGIN/tst-auditmod9b.so.
---
elf/Makefile | 3 ++-
elf/tst-audit2.c | 23 ++++++++++++++++++-----
2 files changed, 20 insertions(+), 6 deletions(-)
diff --git a/elf/Makefile b/elf/Makefile
index b06e0a7..dedf3c7 100644
--- a/elf/Makefile
+++ b/elf/Makefile
@@ -1034,7 +1034,8 @@ $(objpfx)tst-dlmopen3.out: $(objpfx)tst-dlmopen1mod.so
$(objpfx)tst-audit1.out: $(objpfx)tst-auditmod1.so
tst-audit1-ENV = LD_AUDIT=$(objpfx)tst-auditmod1.so
-$(objpfx)tst-audit2.out: $(objpfx)tst-auditmod1.so
+$(objpfx)tst-audit2: $(libdl)
+$(objpfx)tst-audit2.out: $(objpfx)tst-auditmod1.so $(objpfx)tst-auditmod9b.so
# Prevent GCC-5 from translating a malloc/memset pair into calloc
CFLAGS-tst-audit2.c += -fno-builtin
tst-audit2-ENV = LD_AUDIT=$(objpfx)tst-auditmod1.so
diff --git a/elf/tst-audit2.c b/elf/tst-audit2.c
index acad1b0..44c74d4 100644
--- a/elf/tst-audit2.c
+++ b/elf/tst-audit2.c
@@ -3,10 +3,12 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
+#include <dlfcn.h>
#define MAGIC1 0xabcdef72
#define MAGIC2 0xd8675309
static __thread unsigned int magic[] = { MAGIC1, MAGIC2 };
+static __thread int calloc_called;
#undef calloc
@@ -16,13 +18,19 @@ static __thread unsigned int magic[] = { MAGIC1, MAGIC2 };
void *
calloc (size_t n, size_t m)
{
- if (magic[0] != MAGIC1 || magic[1] != MAGIC2)
+ if (!calloc_called)
{
- printf ("{%x, %x} != {%x, %x}\n", magic[0], magic[1], MAGIC1, MAGIC2);
- abort ();
+ /* Allow our calloc to be called more than once. */
+ calloc_called = 1;
+ if (magic[0] != MAGIC1 || magic[1] != MAGIC2)
+ {
+ printf ("{%x, %x} != {%x, %x}\n",
+ magic[0], magic[1], MAGIC1, MAGIC2);
+ abort ();
+ }
+ magic[0] = MAGIC2;
+ magic[1] = MAGIC1;
}
- magic[0] = MAGIC2;
- magic[1] = MAGIC1;
n *= m;
void *ptr = malloc (n);
@@ -34,6 +42,11 @@ calloc (size_t n, size_t m)
static int
do_test (void)
{
+ /* Make sure that our calloc is called from the dynamic linker at least
+ once. */
+ void *h = dlopen("$ORIGIN/tst-auditmod9b.so", RTLD_LAZY);
+ if (h != NULL)
+ dlclose (h);
if (magic[1] != MAGIC1 || magic[0] != MAGIC2)
{
printf ("{%x, %x} != {%x, %x}\n", magic[0], magic[1], MAGIC2, MAGIC1);
--
2.1.0
^ permalink raw reply [flat|nested] 12+ messages in thread
* Re: [PATCH] [BZ #18422] elf/tst-audit tests fail without PLT entries
2015-05-25 20:53 ` H.J. Lu
@ 2015-05-26 10:53 ` Carlos O'Donell
2015-05-26 11:20 ` Andreas Schwab
0 siblings, 1 reply; 12+ messages in thread
From: Carlos O'Donell @ 2015-05-26 10:53 UTC (permalink / raw)
To: H.J. Lu
Cc: GNU C Library, Florian Weimer, Adam Conrad, Aurelien Jarno,
Andreas Schwab, Jeff Law
On 05/25/2015 02:54 PM, H.J. Lu wrote:
> 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:
Thank you very much for looking into this.
I'm glad to see that it does work, but that it is an ordering issue
between JUMP_SLOT and GOTPLT processing.
I have one question, please see below.
>
> (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:
This results in one more calloc from dl-minimal.c which has to be tracked
and not freed.
> (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:
OK.
> (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.
In the past before your ld optimization the JUMP_SLOT would have been
relocated to libc.so.6's version of calloc, or the test version of calloc,
correct?
The change from JUMP_SLOT -> GLOB_DAT for calloc means that we call calloc
one more time using the dl-minimal.c implementation. This seems dangerous to
me since in ld.so we take extreme caution not to attempt to free this result
because dl-minimal.c doesn't support freeing anything but the most recent
allocation. We also don't want to call free() from libc.so.6 with data that
was calloc'd from the dl-minimal.c implementation.
Are we certain that this additional calloc, now using dl-minimal.c, isn't
going to cause problems? When is it freed? What implementation of free is used?
>> > 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.
Well, right away if we have one more call of calloc to dl-minimal.c, that's
another allocation the tool can't track. It's not huegely problematic because
they already can't track all the early allocations via dl-minimal.c.
In summary:
- My next worry is about free of calloc'd data that is now using dl-minimal.c
If we can answer that question, then I think this patch to adjust tst-audit2.c
is the best solution.
Cheers,
Carlos.
^ permalink raw reply [flat|nested] 12+ messages in thread
* Re: [PATCH] [BZ #18422] elf/tst-audit tests fail without PLT entries
2015-05-26 10:53 ` Carlos O'Donell
@ 2015-05-26 11:20 ` Andreas Schwab
2015-05-26 13:03 ` H.J. Lu
2015-05-27 8:12 ` Carlos O'Donell
0 siblings, 2 replies; 12+ messages in thread
From: Andreas Schwab @ 2015-05-26 11:20 UTC (permalink / raw)
To: Carlos O'Donell
Cc: H.J. Lu, GNU C Library, Florian Weimer, Adam Conrad,
Aurelien Jarno, Jeff Law
"Carlos O'Donell" <carlos@redhat.com> writes:
> In summary:
> - My next worry is about free of calloc'd data that is now using dl-minimal.c
Anything allocated with dl-minimal must strictly be kept inside ld.so
and never be freed.
Andreas.
--
Andreas Schwab, SUSE Labs, schwab@suse.de
GPG Key fingerprint = 0196 BAD8 1CE9 1970 F4BE 1748 E4D4 88E3 0EEA B9D7
"And now for something completely different."
^ permalink raw reply [flat|nested] 12+ messages in thread
* Re: [PATCH] [BZ #18422] elf/tst-audit tests fail without PLT entries
2015-05-26 11:20 ` Andreas Schwab
@ 2015-05-26 13:03 ` H.J. Lu
2015-05-27 8:51 ` Carlos O'Donell
2015-05-27 8:12 ` Carlos O'Donell
1 sibling, 1 reply; 12+ messages in thread
From: H.J. Lu @ 2015-05-26 13:03 UTC (permalink / raw)
To: Andreas Schwab
Cc: Carlos O'Donell, GNU C Library, Florian Weimer, Adam Conrad,
Aurelien Jarno, Jeff Law
On Tue, May 26, 2015 at 1:00 AM, Andreas Schwab <schwab@suse.de> wrote:
> "Carlos O'Donell" <carlos@redhat.com> writes:
>
>> In summary:
>> - My next worry is about free of calloc'd data that is now using dl-minimal.c
>
> Anything allocated with dl-minimal must strictly be kept inside ld.so
> and never be freed.
The calloc call is made at:
if (__glibc_unlikely (consider_profiling)
&& l->l_info[DT_PLTRELSZ] != NULL)
{
/* Allocate the array which will contain the already found
relocations. If the shared object lacks a PLT (for example
if it only contains lead function) the l_info[DT_PLTRELSZ]
will be NULL. */
size_t sizeofrel = l->l_info[DT_PLTREL]->d_un.d_val == DT_RELA
? sizeof (ElfW(Rela))
: sizeof (ElfW(Rel));
size_t relcount = l->l_info[DT_PLTRELSZ]->d_un.d_val / sizeofrel;
l->l_reloc_result = calloc (sizeof (l->l_reloc_result[0]), relcount);
if (l->l_reloc_result == NULL)
{
errstring = N_("\
%s: out of memory to store relocation results for %s\n");
_dl_fatal_printf (errstring, RTLD_PROGNAME, l->l_name);
}
}
ld.so never frees l->l_reloc_result.
--
H.J.
^ permalink raw reply [flat|nested] 12+ messages in thread
* Re: [PATCH] [BZ #18422] elf/tst-audit tests fail without PLT entries
2015-05-24 15:40 ` Carlos O'Donell
2015-05-24 16:32 ` H.J. Lu
@ 2015-05-26 13:22 ` Florian Weimer
1 sibling, 0 replies; 12+ messages in thread
From: Florian Weimer @ 2015-05-26 13:22 UTC (permalink / raw)
To: Carlos O'Donell, H.J. Lu, GNU C Library, Adam Conrad,
Aurelien Jarno, Andreas Schwab
Cc: Jeff Law
On 05/24/2015 05:37 AM, Carlos O'Donell wrote:
> My worry is that the missing DT tag is going to have security implications.
> I'm including several other distro people on the TO.
I tried to raise awareness of this change here:
<http://www.openwall.com/lists/oss-security/2015/05/26/2>
Personally, I cannot offer much guidance on the potential impact of this
proposal at present, I'm afraid.
--
Florian Weimer / Red Hat Product Security
^ permalink raw reply [flat|nested] 12+ messages in thread
* Re: [PATCH] [BZ #18422] elf/tst-audit tests fail without PLT entries
2015-05-26 11:20 ` Andreas Schwab
2015-05-26 13:03 ` H.J. Lu
@ 2015-05-27 8:12 ` Carlos O'Donell
2015-05-27 8:44 ` H.J. Lu
1 sibling, 1 reply; 12+ messages in thread
From: Carlos O'Donell @ 2015-05-27 8:12 UTC (permalink / raw)
To: Andreas Schwab
Cc: H.J. Lu, GNU C Library, Florian Weimer, Adam Conrad,
Aurelien Jarno, Jeff Law
On 05/26/2015 04:00 AM, Andreas Schwab wrote:
> "Carlos O'Donell" <carlos@redhat.com> writes:
>
>> In summary:
>> - My next worry is about free of calloc'd data that is now using dl-minimal.c
>
> Anything allocated with dl-minimal must strictly be kept inside ld.so
> and never be freed.
I agree.
However, now that we are delaying the interposition until we process the
GOT relocs, the tst-audit2 test fails because what was once a call to libc.so's
calloc is now a call to dl-minimal. I haven't debugged this so I don't know if
we're tracking that calloc correctly such that we don't attempt to free it.
Did I get something wrong?
Cheers,
Carlos.
^ permalink raw reply [flat|nested] 12+ messages in thread
* Re: [PATCH] [BZ #18422] elf/tst-audit tests fail without PLT entries
2015-05-27 8:12 ` Carlos O'Donell
@ 2015-05-27 8:44 ` H.J. Lu
0 siblings, 0 replies; 12+ messages in thread
From: H.J. Lu @ 2015-05-27 8:44 UTC (permalink / raw)
To: Carlos O'Donell
Cc: Andreas Schwab, GNU C Library, Florian Weimer, Adam Conrad,
Aurelien Jarno, Jeff Law
On Tue, May 26, 2015 at 4:54 PM, Carlos O'Donell <carlos@redhat.com> wrote:
> On 05/26/2015 04:00 AM, Andreas Schwab wrote:
>> "Carlos O'Donell" <carlos@redhat.com> writes:
>>
>>> In summary:
>>> - My next worry is about free of calloc'd data that is now using dl-minimal.c
>>
>> Anything allocated with dl-minimal must strictly be kept inside ld.so
>> and never be freed.
>
> I agree.
>
> However, now that we are delaying the interposition until we process the
> GOT relocs, the tst-audit2 test fails because what was once a call to libc.so's
> calloc is now a call to dl-minimal. I haven't debugged this so I don't know if
> we're tracking that calloc correctly such that we don't attempt to free it.
See:
https://sourceware.org/ml/libc-alpha/2015-05/msg00632.html
--
H.J.
^ permalink raw reply [flat|nested] 12+ messages in thread
* Re: [PATCH] [BZ #18422] elf/tst-audit tests fail without PLT entries
2015-05-26 13:03 ` H.J. Lu
@ 2015-05-27 8:51 ` Carlos O'Donell
0 siblings, 0 replies; 12+ messages in thread
From: Carlos O'Donell @ 2015-05-27 8:51 UTC (permalink / raw)
To: H.J. Lu, Andreas Schwab
Cc: GNU C Library, Florian Weimer, Adam Conrad, Aurelien Jarno, Jeff Law
On 05/26/2015 07:19 AM, H.J. Lu wrote:
> On Tue, May 26, 2015 at 1:00 AM, Andreas Schwab <schwab@suse.de> wrote:
>> "Carlos O'Donell" <carlos@redhat.com> writes:
>>
>>> In summary:
>>> - My next worry is about free of calloc'd data that is now using dl-minimal.c
>>
>> Anything allocated with dl-minimal must strictly be kept inside ld.so
>> and never be freed.
>
> The calloc call is made at:
>
> if (__glibc_unlikely (consider_profiling)
> && l->l_info[DT_PLTRELSZ] != NULL)
> {
> /* Allocate the array which will contain the already found
> relocations. If the shared object lacks a PLT (for example
> if it only contains lead function) the l_info[DT_PLTRELSZ]
> will be NULL. */
> size_t sizeofrel = l->l_info[DT_PLTREL]->d_un.d_val == DT_RELA
> ? sizeof (ElfW(Rela))
> : sizeof (ElfW(Rel));
> size_t relcount = l->l_info[DT_PLTRELSZ]->d_un.d_val / sizeofrel;
> l->l_reloc_result = calloc (sizeof (l->l_reloc_result[0]), relcount);
>
> if (l->l_reloc_result == NULL)
> {
> errstring = N_("\
> %s: out of memory to store relocation results for %s\n");
> _dl_fatal_printf (errstring, RTLD_PROGNAME, l->l_name);
> }
> }
>
> ld.so never frees l->l_reloc_result.
Thanks.
The only other place I was worried about was TLS data structures, but
there we already use dl_initial_tls to indicate the data structure was
allocated early (specifically for use by auditors) and we do not pass
it to realloc because it was allocated by dl-minimal, thus we are OK
there also.
After your changes in binutils is the test at all useful?
We are no longer able to interpose calloc to catch early TLS init,
therefore we are no longer testing early TLS init and the comments
in the test need to be changed to match.
The new test is:
"Test that calloc is called at least once after dlopen and initialization
of TLS varibles in the DSO."
Why do we care about this?
Is there any way to still test that early TLS initialization has occurred
when using LD_AUDIT?
Would't such a test look like this?
- Create auditor that uses TLS in audit funciton.
- Interpose calloc.
- Check that things don't crash.
We already have a test for this, it's tst-audit9 (Bug 16613).
OK to checkin your change to tst-audit2 if you change the test comment
to reflect the change in what is being tested:
"Test that interposed calloc is called by the dynamic loader, and that
TLS is fully initialized by then."
Thanks for working through this.
Cheers,
Carlos.
^ permalink raw reply [flat|nested] 12+ messages in thread
end of thread, other threads:[~2015-05-27 0:44 UTC | newest]
Thread overview: 12+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2015-05-24 3:37 [PATCH] [BZ #18422] elf/tst-audit tests fail without PLT entries H.J. Lu
2015-05-24 15:40 ` Carlos O'Donell
2015-05-24 16:32 ` H.J. Lu
2015-05-25 5:17 ` Carlos O'Donell
2015-05-25 20:53 ` H.J. Lu
2015-05-26 10:53 ` Carlos O'Donell
2015-05-26 11:20 ` Andreas Schwab
2015-05-26 13:03 ` H.J. Lu
2015-05-27 8:51 ` Carlos O'Donell
2015-05-27 8:12 ` Carlos O'Donell
2015-05-27 8:44 ` H.J. Lu
2015-05-26 13:22 ` Florian Weimer
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).