From 4458dd4410207fcdf8dec6789f0397adc6ce7b01 Mon Sep 17 00:00:00 2001 From: Derrick Brashear Date: Sat, 15 Nov 2003 03:08:10 +0000 Subject: [PATCH] callback-rxcon-protection-20031114 FIXES 2498 CheckHost() sets the HOSTDELETED flag on a host, does its touch, calls H_UNLOCK at the end of its function; AddCallBCal1 in a different thread grabs the lock, does its thing. Gets to GetSomeSpace_r(), which calls h_Enumerate_r; the host in question isn't held, so h_Enumerate_r calls h_Hold_r and h_Release_r on the host that CheckHost() set the HOSTDELETED flag on; h_Release_r sees the HOSTDELETED flag and calls h_TossStuff_r, poof, we have our broken host entry for ClearHostCallbacks_r to trip --- src/viced/callback.c | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) diff --git a/src/viced/callback.c b/src/viced/callback.c index 10e8e9ec2..55af2b9eb 100644 --- a/src/viced/callback.c +++ b/src/viced/callback.c @@ -1534,16 +1534,22 @@ CleanupTimedOutCallBacks_r(void) } static struct host *lih_host; +static int lih_host_held = 0; static int lih_r(register struct host *host, register int held, register struct host *hostp) { + lih_host_held = 0; if (host->cblist && ((hostp && host != hostp) || (!held && !h_OtherHolds_r(host))) && (!lih_host || host->ActiveCall < lih_host->ActiveCall)) { lih_host = host; } + if (!held) { + held = 1; + lih_host_held = 1; + } return held; } @@ -1571,8 +1577,13 @@ GetSomeSpace_r(struct host *hostp, int locked) hp = lih_host; if (hp) { cbstuff.GSS4++; - if (!ClearHostCallbacks_r(hp, 0 /* not locked or held */ )) + if (!ClearHostCallbacks_r(hp, 0 /* not locked or held */ )) { + if (lih_host_held) + h_Release_r(hp); return 0; + } + if (lih_host_held) + h_Release_r(hp); hp2 = hp->next; } else { hp2 = hostList; -- 2.39.5