diff options
author | Tobias Brunner <tobias@strongswan.org> | 2011-12-23 10:38:10 +0100 |
---|---|---|
committer | Tobias Brunner <tobias@strongswan.org> | 2011-12-23 10:38:10 +0100 |
commit | d6656f11e48d9b545738d5f40e59f3c3dd90ef97 (patch) | |
tree | 3babf39907d9dc1e233368a77751c221e51e51fd /src | |
parent | a24f2241bc6b6a6d081ea9a413d8c79a4068d8a8 (diff) | |
download | strongswan-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().
Diffstat (limited to 'src')
-rw-r--r-- | src/libcharon/sa/trap_manager.c | 12 |
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); } |