aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTobias Brunner <tobias@strongswan.org>2011-12-23 10:38:10 +0100
committerTobias Brunner <tobias@strongswan.org>2011-12-23 10:38:10 +0100
commitd6656f11e48d9b545738d5f40e59f3c3dd90ef97 (patch)
tree3babf39907d9dc1e233368a77751c221e51e51fd
parenta24f2241bc6b6a6d081ea9a413d8c79a4068d8a8 (diff)
downloadstrongswan-d6656f11e48d9b545738d5f40e59f3c3dd90ef97.tar.bz2
strongswan-d6656f11e48d9b545738d5f40e59f3c3dd90ef97.tar.xz
Fixed flush() method of trap_manager_t.
A segmentation fault could have happened during destruction of the trap manager after calling flush().
-rw-r--r--src/libcharon/sa/trap_manager.c12
1 files changed, 9 insertions, 3 deletions
diff --git a/src/libcharon/sa/trap_manager.c b/src/libcharon/sa/trap_manager.c
index bf9f8432c..c7a8a6e0c 100644
--- a/src/libcharon/sa/trap_manager.c
+++ b/src/libcharon/sa/trap_manager.c
@@ -353,15 +353,21 @@ METHOD(listener_t, child_state_change, bool,
METHOD(trap_manager_t, flush, void,
private_trap_manager_t *this)
{
- this->traps->invoke_function(this->traps, (void*)destroy_entry);
+ linked_list_t *traps;
+ /* since destroying the CHILD_SA results in events which require a read
+ * lock we cannot destroy the list while holding the write lock */
+ this->lock->write_lock(this->lock);
+ traps = this->traps;
+ this->traps = linked_list_create();
+ this->lock->unlock(this->lock);
+ traps->destroy_function(traps, (void*)destroy_entry);
}
METHOD(trap_manager_t, destroy, void,
private_trap_manager_t *this)
{
charon->bus->remove_listener(charon->bus, &this->listener.listener);
- this->traps->invoke_function(this->traps, (void*)destroy_entry);
- this->traps->destroy(this->traps);
+ this->traps->destroy_function(this->traps, (void*)destroy_entry);
this->lock->destroy(this->lock);
free(this);
}