[gold][patch] Fix gold plugins so cleanup handler is not called repeatedly
Cary Coutant
ccoutant@google.com
Wed Oct 28 00:53:00 GMT 2009
The attached patch fixes a problem that can occur when a plugin's
cleanup handler issues a fatal error through the linker's message API.
This moves the cleanup_done_ flag into each plugin and sets each
plugin's cleanup_done_ flag just before invoking the cleanup handler.
OK?
-cary
* plugin.h (Plugin::Plugin): Initialize cleanup_done_.
(Plugin::cleanup_done_): New member.
(Plugin_manager::Plugin_manager): Remove cleanup_done_.
(Plugin_manager::cleanup_done_): Remove.
* plugin.cc (Plugin::cleanup): Test and set cleanup_done_.
(Plugin_manager::cleanup): Remove use of cleanup_done_.
-------------- next part --------------
Index: plugin.cc
===================================================================
RCS file: /cvs/src/src/gold/plugin.cc,v
retrieving revision 1.22
diff -u -p -r1.22 plugin.cc
--- plugin.cc 12 Oct 2009 06:02:06 -0000 1.22
+++ plugin.cc 28 Oct 2009 00:50:05 -0000
@@ -238,8 +238,14 @@ Plugin::all_symbols_read()
inline void
Plugin::cleanup()
{
- if (this->cleanup_handler_ != NULL)
- (*this->cleanup_handler_)();
+ if (this->cleanup_handler_ != NULL && !this->cleanup_done_)
+ {
+ // Set this flag before calling to prevent a recursive plunge
+ // in the event that a plugin's cleanup handler issues a
+ // fatal error.
+ this->cleanup_done_ = true;
+ (*this->cleanup_handler_)();
+ }
}
// Plugin_manager methods.
@@ -350,13 +356,10 @@ Plugin_manager::layout_deferred_objects(
void
Plugin_manager::cleanup()
{
- if (this->cleanup_done_)
- return;
for (this->current_ = this->plugins_.begin();
this->current_ != this->plugins_.end();
++this->current_)
(*this->current_)->cleanup();
- this->cleanup_done_ = true;
}
// Make a new Pluginobj object. This is called when the plugin calls
Index: plugin.h
===================================================================
RCS file: /cvs/src/src/gold/plugin.h,v
retrieving revision 1.8
diff -u -p -r1.8 plugin.h
--- plugin.h 6 Oct 2009 20:15:09 -0000 1.8
+++ plugin.h 28 Oct 2009 00:50:05 -0000
@@ -54,7 +54,8 @@ class Plugin
args_(),
claim_file_handler_(NULL),
all_symbols_read_handler_(NULL),
- cleanup_handler_(NULL)
+ cleanup_handler_(NULL),
+ cleanup_done_(false)
{ }
~Plugin()
@@ -112,6 +113,8 @@ class Plugin
ld_plugin_claim_file_handler claim_file_handler_;
ld_plugin_all_symbols_read_handler all_symbols_read_handler_;
ld_plugin_cleanup_handler cleanup_handler_;
+ // TRUE if the cleanup handlers have been called.
+ bool cleanup_done_;
};
// A manager class for plugins.
@@ -121,7 +124,7 @@ class Plugin_manager
public:
Plugin_manager(const General_options& options)
: plugins_(), objects_(), deferred_layout_objects_(), input_file_(NULL),
- plugin_input_file_(), in_replacement_phase_(false), cleanup_done_(false),
+ plugin_input_file_(), in_replacement_phase_(false),
options_(options), workqueue_(NULL), task_(NULL), input_objects_(NULL),
symtab_(NULL), layout_(NULL), dirpath_(NULL), mapfile_(NULL),
this_blocker_(NULL)
@@ -263,9 +266,6 @@ class Plugin_manager
// placeholder symbols from the Pluginobj objects.
bool in_replacement_phase_;
- // TRUE if the cleanup handlers have been called.
- bool cleanup_done_;
-
const General_options& options_;
Workqueue* workqueue_;
Task* task_;
More information about the Binutils
mailing list