summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSteve Hill <quagga@cheesy.sackheads.org>2009-06-02 14:28:16 +0100
committerPaul Jakma <paul@quagga.net>2009-06-02 14:28:16 +0100
commitacde4b861333d799b50d6e8a53214abc0d17ede3 (patch)
treee6fa104c7bfb45043aec82c9cab3941cb09459bd
parent5012bc3d217f4fff5759745ee689869fb5224b41 (diff)
[bgp] Fix crash on SIGHUP, deref of freed workqueues
* lib/workqueue.c: free-ing workqueues had never been tested obviously, queue's thread was not being stopped * bgpd/bgpd.c: null out freed workqueues, to prevent acting on freed workqueues
-rw-r--r--bgpd/bgpd.c12
-rw-r--r--lib/workqueue.c3
2 files changed, 12 insertions, 3 deletions
diff --git a/bgpd/bgpd.c b/bgpd/bgpd.c
index cebde0a4..1712c719 100644
--- a/bgpd/bgpd.c
+++ b/bgpd/bgpd.c
@@ -5150,9 +5150,15 @@ bgp_terminate ()
BGP_NOTIFY_CEASE_PEER_UNCONFIG);
bgp_cleanup_routes ();
+
if (bm->process_main_queue)
- work_queue_free (bm->process_main_queue);
+ {
+ work_queue_free (bm->process_main_queue);
+ bm->process_main_queue = NULL;
+ }
if (bm->process_rsclient_queue)
- work_queue_free (bm->process_rsclient_queue);
+ {
+ work_queue_free (bm->process_rsclient_queue);
+ bm->process_rsclient_queue = NULL;
+ }
}
-
diff --git a/lib/workqueue.c b/lib/workqueue.c
index 1d32d241..7c811edd 100644
--- a/lib/workqueue.c
+++ b/lib/workqueue.c
@@ -91,6 +91,9 @@ work_queue_new (struct thread_master *m, const char *queue_name)
void
work_queue_free (struct work_queue *wq)
{
+ if (wq->thread != NULL)
+ thread_cancel(wq->thread);
+
/* list_delete frees items via callback */
list_delete (wq->items);
listnode_delete (&work_queues, wq);