Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

LD_PRELOAD does not work as expected

Consider the following library which can be preloaded before any program execution:

// g++ -std=c++11 -shared -fPIC preload.cpp -o preload.so // LD_PRELOAD=./preload.so <command> #include <iostream>  struct Goodbye {     Goodbye() {std::cout << "Hello\n";}     ~Goodbye() {std::cout << "Goodbye!\n";} } goodbye; 

The problem is that, while the constructor of the global variable goodbye is always called, the destructor is not called for some programs, like ls:

$ LD_PRELOAD=./preload.so ls Hello 

For some other programs, the destructor is called as expected:

$ LD_PRELOAD=./preload.so man Hello What manual page do you want? Goodbye! 

Can you explain why the destructor is not called in the first case? EDIT: the above question has been already answered, that is a program might well use _exit(), abort() to exit.

However:

Is there a way to force a given function being called when a preloaded program exits?

like image 875
Martin Avatar asked May 24 '14 23:05

Martin


1 Answers

ls has atexit (close_stdout); as its initialisation code. When it finishes, it closes stdout (i.e. close(1)), so your cout, printf or write(1, ... operations will not print anything. It doesn't mean destructor isn't called. You can verify this by e.g. creating a new file in your destructor.

http://git.savannah.gnu.org/cgit/coreutils.git/tree/src/ls.c#n1285 here is the line in GNU coreutils ls.

It is not just ls, most of coreutils do that. Unfortunately, I don't know exact reason why they prefer to close it.

Side note on how this could be found (or at least what I did) - may help next time or with program with no source code access:

Destructor message is printed with /bin/true (simplest program I could think of), but isn't printed with ls or df. I started with strace /bin/true and strace /bin/ls and compared latest system calls. It shown close(1) and close(2) for ls, but none for true. After that things started to make sense and I just had to verify that destructor is called.

like image 70
keltar Avatar answered Sep 18 '22 11:09

keltar