Almost Empty Function
The author began by saying that this is a real code example he found in Boolector.
// Forward declaration of the function. This function exists in another file:int boolector_main (int argc, char **argv);
// The executable programint main (int argc, char **argv){ return boolector_main (argc, argv);}
Here, the author talked about a very simple function, almost empty, called main().
All it really does is call another function named boolector_main and passes it the same parameters.
In other words, instead of writing all the code inside main,
he made main just an intermediary that calls boolector_main and returns its result.
The author mentioned that the reason could be that the actual function (boolector_main) is stored in another file or library (like a DLL or a shared library).
This is useful, for example, when the main program is being tested by a test suite,
and that test suite needs to call main just like the system normally does.
Then he explained that when this code is compiled before optimization, it looks like this:
main: push rbp ; save base pointer of previous stack frame mov rbp, rsp ; set base pointer for current stack frame sub rsp, 16 ; allocate 16 bytes on the stack for local variables mov DWORD PTR -4[rbp], edi ; move first argument (argc) to local variable mov QWORD PTR -16[rbp], rsi ; move second argument (argv) to local variable mov rdx, QWORD PTR -16[rbp] ; prepare rsi argument for call mov eax, DWORD PTR -4[rbp] ; prepare edi argument for call mov rsi, rdx ; move argv to rsi register mov edi, eax ; move argc to edi register call boolector_main ; call the actual main function leave ; restore previous stack frame ret ; return to callerBut let’s take a look at the optimized version:
Listing 1.46: Optimizing GCC 8.2 x64 (Assembly Output with Comments)
main: jmp boolector_main ; jump directly to the address of boolector_main, skipping prologue/epilogue
Very simply, the stack and registers are untouched, and boolector_main() receives the same arguments.
So all we need to do is just pass the execution flow to another address.
This is quite similar to the concept of a thunk function — a function that only performs redirection or forwarding.
If this article helped you, please share it with others!
Some information may be outdated





