afs-checkservers-improve-lock-granularity-20011102

work harder to release afs_xserver and afs_xsrvAddr locks in afs_CheckServers
when not needed
This commit is contained in:
Nickolai Zeldovich 2001-11-02 08:07:58 +00:00 committed by Derrick Brashear
parent 9cbe95a1af
commit ea77b04c29

View File

@ -504,13 +504,15 @@ void afs_CheckServers(adown, acellp)
struct server *ts;
struct srvAddr *sa;
struct conn *tc;
afs_int32 i;
afs_int32 i, j;
afs_int32 code;
afs_int32 start, end, delta;
osi_timeval_t tv;
int setTimer;
struct unixuser *tu;
char tbuffer[CVBS];
int srvAddrCount;
struct srvAddr **addrs;
XSTATS_DECLS;
AFS_STATCNT(afs_CheckServers);
@ -518,20 +520,41 @@ void afs_CheckServers(adown, acellp)
ObtainReadLock(&afs_xserver); /* Necessary? */
ObtainReadLock(&afs_xsrvAddr);
srvAddrCount = 0;
for (i=0;i<NSERVERS;i++) {
for (sa = afs_srvAddrs[i]; sa; sa = sa->next_bkt) {
srvAddrCount++;
}
}
addrs = afs_osi_Alloc(srvAddrCount * sizeof(*addrs));
j = 0;
for (i=0;i<NSERVERS;i++) {
for (sa = afs_srvAddrs[i]; sa; sa = sa->next_bkt) {
if (j >= srvAddrCount) break;
addrs[j++] = sa;
}
}
ReleaseReadLock(&afs_xsrvAddr);
ReleaseReadLock(&afs_xserver);
for (i=0; i<j; i++) {
sa = addrs[i];
ts = sa->server;
if (!ts)
continue;
/* See if a cell to check was specified. If it is spec'd and not
* this server's cell, just skip the server.
*/
if (acellp && acellp != ts->cell)
continue;
if ((!adown && (sa->sa_flags & SRVADDR_ISDOWN))
|| (adown && !(sa->sa_flags & SRVADDR_ISDOWN)))
if ((!adown && (sa->sa_flags & SRVADDR_ISDOWN)) ||
(adown && !(sa->sa_flags & SRVADDR_ISDOWN)))
continue;
/* check vlserver with special code */
if (sa->sa_portal == AFS_VLPORT) {
CheckVLServer(sa, &treq);
@ -546,16 +569,17 @@ void afs_CheckServers(adown, acellp)
tc = afs_ConnBySA(sa, ts->cell->fsport, ts->cell->cell, tu,
1/*force*/, 1/*create*/, SHARED_LOCK);
afs_PutUser(tu, SHARED_LOCK);
if (!tc)
continue;
if (!tc) continue;
if ((sa->sa_flags & SRVADDR_ISDOWN) || HaveCallBacksFrom(ts) ||
(tc->srvr->server == afs_setTimeHost)) {
if (sa->sa_flags & SRVADDR_ISDOWN) {
rx_SetConnDeadTime(tc->id, 3);
setTimer = 1;
} else
} else {
setTimer = 0;
}
XSTATS_START_TIME(AFS_STATS_FS_RPCIDX_GETTIME);
start = osi_Time(); /* time the gettimeofday call */
#ifdef RX_ENABLE_LOCKS
@ -581,6 +605,7 @@ void afs_CheckServers(adown, acellp)
*/
(afs_setTimeHost == (struct server *)0 &&
(ts->cell->cell == 1 || (ts->cell->states&CPrimary))))) {
char msgbuf[90]; /* strlen("afs: setting clock...") + slop */
/* set the time */
delta = end - tv.tv_sec; /* how many secs fast we are */
@ -604,8 +629,7 @@ void afs_CheckServers(adown, acellp)
afs_strcat(msgbuf, " seconds (via ");
print_internet_address(msgbuf, sa, ").", 0);
}
}
else {
} else {
strcpy(msgbuf, "afs: setting clock ahead ");
afs_strcat(msgbuf, afs_cv2string(&tbuffer[CVBS], -delta));
afs_strcat(msgbuf, " seconds (via ");
@ -619,27 +643,29 @@ void afs_CheckServers(adown, acellp)
if (code >= 0 && (sa->sa_flags & SRVADDR_ISDOWN) && (tc->srvr == sa)) {
/* server back up */
print_internet_address("afs: file server ", sa, " is back up", 2);
/*
* XXX We should hold a server write lock here XXX
*/
ObtainWriteLock(&afs_xserver, 244);
ObtainWriteLock(&afs_xsrvAddr, 245);
afs_MarkServerUpOrDown(sa, 0);
ReleaseWriteLock(&afs_xsrvAddr);
ReleaseWriteLock(&afs_xserver);
if (afs_waitForeverCount) {
afs_osi_Wakeup(&afs_waitForever);
}
}
else
} else {
if (code < 0) {
/* server crashed */
afs_ServerDown(sa);
ForceNewConnections(sa); /* multi homed clients */
}
}
}
afs_PutConn(tc, SHARED_LOCK); /* done with it now */
} /* for each server loop */
} /* for each server hash bucket loop */
ReleaseReadLock(&afs_xsrvAddr);
ReleaseReadLock(&afs_xserver);
} /* Outer loop over addrs */
afs_osi_Free(addrs, srvAddrCount * sizeof(*addrs));
} /*afs_CheckServers*/