david/ipxe
david
/
ipxe
Archived
1
0
Fork 0

[compiler] Prevent empty weak function stubs from being removed

Even with the noinline specifier added by commit 1a260f8, gcc may skip
calls to non-inlinable functions that it knows have no side
effects. This caused the get_cached_dhcpack() call in start_dhcp(),
the weak stub of which has no code in its body, to be removed,
preventing cached DHCP from working.

Fix by adding a __keepme macro to compiler.h expanding to asm(""), as
recommended by gcc's info page, and using it in the weak stub for
get_cached_dhcpack().

Reported-by: Aaron Brooks <aaron@brooks1.net>
Tested-by: Aaron Brooks <aaron@brooks1.net>
Signed-off-by: Joshua Oreman <oremanj@rwcr.net>
Signed-off-by: Michael Brown <mcb30@ipxe.org>
This commit is contained in:
Joshua Oreman 2010-08-18 16:37:22 -07:00 committed by Michael Brown
parent 059c11e1e6
commit 49d6f57005
2 changed files with 9 additions and 1 deletions

View File

@ -191,6 +191,14 @@ REQUEST_EXPANDED ( CONFIG_SYMBOL );
*/
#define __weak __attribute__ (( weak, noinline ))
/** Prevent a function from being optimized away without inlining
*
* Calls to functions with void return type that contain no code in their body
* may be removed by gcc's optimizer even when inlining is inhibited. Placing
* this macro in the body of the function prevents that from occurring.
*/
#define __keepme asm("");
#endif
/** @defgroup dbg Debugging infrastructure

View File

@ -1389,7 +1389,7 @@ static struct sockaddr dhcp_peer = {
/**
* Get cached DHCPACK where none exists
*/
__weak void get_cached_dhcpack ( void ) {}
__weak void get_cached_dhcpack ( void ) { __keepme }
/**
* Start DHCP state machine on a network device