This is the mail archive of the libc-help@sourceware.org mailing list for the glibc project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: I think I can answer my own question ...


On Tue, Jun 5, 2012 at 3:50 PM, Bryan Ischo <bryan@ischo.com> wrote:
> I managed to dig into the glibc source code and found an interesting
> function:
>
> int
> __register_atfork (prepare, parent, child, dso_handle)
> ? ? void (*prepare) (void);
> ? ? void (*parent) (void);
> ? ? void (*child) (void);
> ? ? void *dso_handle;
>
> I used my LD_PRELOAD trick to define this to a dummy function that does
> nothing other than print out a message saying that the call is being
> ignored.
>
> When I run my program using this dummy __register_atfork, it seems to fix
> the problem. ?It appears that __register_atfork is called twice. ?I have
> managed to get a stack trace from both of these; they are:
>
> (gdb) where
> #0 ?0x00007fa82c8b8b40 in __nanosleep_nocancel () from /lib/libc.so.6
> #1 ?0x00007fa82c8b8a01 in sleep () from /lib/libc.so.6
> #2 ?0x00007fa82e66681c in __register_atfork () from /home/bji/nvidia_fix.so
> #3 ?0x00007fa82d66752a in ?? () from /usr/lib/libGL.so.1
> #4 ?0x00007fa82d6414ec in ?? () from /usr/lib/libGL.so.1
> #5 ?0x00007fa82e875902 in call_init () from /lib/ld-linux-x86-64.so.2
> #6 ?0x00007fa82e875a2a in _dl_init_internal () from
> /lib/ld-linux-x86-64.so.2
> #7 ?0x00007fa82e8685fa in _dl_start_user () from /lib/ld-linux-x86-64.so.2
> #8 ?0x0000000000000002 in ?? ()
> #9 ?0x00007fff5b43db1c in ?? ()
> #10 0x00007fff5b43db47 in ?? ()
> #11 0x0000000000000000 in ?? ()
> (gdb) c
> ?C-c C-c
> Program received signal SIGINT, Interrupt.
> 0x00007fa82c8b8b40 in __nanosleep_nocancel () from /lib/libc.so.6
> (gdb) where
> #0 ?0x00007fa82c8b8b40 in __nanosleep_nocancel () from /lib/libc.so.6
> #1 ?0x00007fa82c8b8a01 in sleep () from /lib/libc.so.6
> #2 ?0x00007fa82e66681c in __register_atfork () from /home/bji/nvidia_fix.so
> #3 ?0x00007fa82d6414b1 in ?? () from /usr/lib/libGL.so.1
> #4 ?0x00007fa82e875902 in call_init () from /lib/ld-linux-x86-64.so.2
> #5 ?0x00007fa82e875a2a in _dl_init_internal () from
> /lib/ld-linux-x86-64.so.2
> #6 ?0x00007fa82e8685fa in _dl_start_user () from /lib/ld-linux-x86-64.so.2
> #7 ?0x0000000000000002 in ?? ()
> #8 ?0x00007fff5b43db1c in ?? ()
> #9 ?0x00007fff5b43db47 in ?? ()
> #10 0x0000000000000000 in ?? ()
>
> (I got the stack trace by putting a sleep(10) inside my dummy
> __register_atfork and then breaking into the debugger; a cheesy but
> effective technique).
>
> Can someone explain __register_atfork to me? ?Why would NVidia call that
> function directly instead of pthread_atfork()? ?And is this really valid for
> NVidia to be doing?
>
> Is there any better way to disable these (in my opinion, broken) calls into
> __register_atfork than using an LD_PRELOAD trick?

They did call pthread_atfork().

It's just that pthread_atfork is an alias for __pthread_atfork which
is implemented by __register_atfork.

Your best tool here is latrace, or to use the library auditing
interfaces directly to inspect which functions are being called in
what order. That will allow you to detect invalid pthread API call
sequences.

You can then use the library auditing interface to intercept only
certain calls and adjust parameters on the fly.

Cheers,
Carlos.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]