=== modified file 'src/cache_cf.cc' --- src/cache_cf.cc 2008-07-11 19:32:10 +0000 +++ src/cache_cf.cc 2008-07-13 13:18:41 +0000 @@ -1850,7 +1850,7 @@ *head = p; - peerClearRR(p); + peerClearRRStart(); } static void === modified file 'src/neighbors.cc' --- src/neighbors.cc 2008-06-12 12:49:29 +0000 +++ src/neighbors.cc 2008-07-13 12:52:56 +0000 @@ -384,19 +384,67 @@ return q; } -/* This gets called every 5 minutes to clear the round-robin counter. */ -void -peerClearRR(void *data) -{ - peer *p = (peer *)data; - p->rr_count -= p->rr_lastcount; - - if (p->rr_count < 0) +/** + * This gets called every 5 minutes to clear the round-robin counter. + * The exact timing is an arbitrary default, set on estimate timing of a + * large number of requests in a high-performance environment during the + * period. The larger the number of requests between cycled resets the + * more balanced the operations. + * + \param data unused. + \todo Make the reset timing a selectable parameter in squid.conf + */ +static void +peerClearRRLoop(void *data) +{ + peerClearRR(); + eventAdd("peerClearRR", peerClearRRLoop, data, 5 * 60.0, 0); +} + +/** + * This gets called on startup and restart to kick off the peer round-robin + * maintenance event. It ensures that no matter how many times its called + * no more than one event is scheduled. + */ +void +peerClearRRStart(void) +{ + static int event_added = 0; + if (!event_added) { + peerClearRRLoop(NULL); + } +} + +/** + * Called whenever the round-robin counters need to be reset to a sane state. + * So far those times are: + \item On startup and reconfigure - to set the counters to sane initial settings. + \item When a peer has revived from dead, to prevent the revived peer being + * flooded with requests which it has 'missed' during the down period. + */ +void +peerClearRR() +{ + peer *p = NULL; + for (p = Config.peers; p; p = p->next) { p->rr_count = 0; - - p->rr_lastcount = p->rr_count; - - eventAdd("peerClearRR", peerClearRR, p, 5 * 60.0, 0); + } +} + +/** + * Perform all actions when a peer is detected revived. + */ +void +peerAlive(peer *p) +{ + if (p->stats.logged_state == PEER_DEAD && p->tcp_up) { + debugs(15, 1, "Detected REVIVED " << neighborTypeStr(p) << ": " << p->name); + p->stats.logged_state = PEER_ALIVE; + peerClearRR(); + } + + p->stats.last_reply = squid_curtime; + p->stats.probe_start = 0; } peer * @@ -862,13 +910,7 @@ static void neighborAlive(peer * p, const MemObject * mem, const icp_common_t * header) { - if (p->stats.logged_state == PEER_DEAD && p->tcp_up) { - debugs(15, 1, "Detected REVIVED " << neighborTypeStr(p) << ": " << p->name); - p->stats.logged_state = PEER_ALIVE; - } - - p->stats.last_reply = squid_curtime; - p->stats.probe_start = 0; + peerAlive(p); p->stats.pings_acked++; if ((icp_opcode) header->opcode <= ICP_END) @@ -906,14 +948,7 @@ static void neighborAliveHtcp(peer * p, const MemObject * mem, const htcpReplyData * htcp) { - if (p->stats.logged_state == PEER_DEAD && p->tcp_up) { - debugs(15, 1, "Detected REVIVED " << neighborTypeStr(p) << ": " << p->name); - p->stats.logged_state = PEER_ALIVE; - } - - p->stats.last_reply = squid_curtime; - p->stats.probe_start = 0; - p->stats.pings_acked++; + peerAlive(p); p->htcp.counts[htcp->hit ? 1 : 0]++; p->htcp.version = htcp->version; } @@ -1322,13 +1357,13 @@ { if (!p->tcp_up) { debugs(15, 2, "TCP connection to " << p->host << "/" << p->http_port << " succeded"); - debugs(15, 1, "Detected REVIVED " << neighborTypeStr(p) << ": " << p->name); - p->stats.logged_state = PEER_ALIVE; + p->tcp_up = PEER_TCP_MAGIC_COUNT; // NP: so peerAlive(p) works properly. + peerAlive(p); if (!p->n_addresses) ipcache_nbgethostbyname(p->host, peerDNSConfigure, p); } - - p->tcp_up = PEER_TCP_MAGIC_COUNT; + else + p->tcp_up = PEER_TCP_MAGIC_COUNT; } static void === modified file 'src/protos.h' --- src/protos.h 2008-07-11 19:32:10 +0000 +++ src/protos.h 2008-07-13 12:54:28 +0000 @@ -397,7 +397,8 @@ SQUIDCEXTERN peer *getDefaultParent(HttpRequest * request); SQUIDCEXTERN peer *getRoundRobinParent(HttpRequest * request); SQUIDCEXTERN peer *getWeightedRoundRobinParent(HttpRequest * request); -SQUIDCEXTERN void peerClearRR(void *); +SQUIDCEXTERN void peerClearRRStart(void); +SQUIDCEXTERN void peerClearRR(void); SQUIDCEXTERN peer *getAnyParent(HttpRequest * request); SQUIDCEXTERN lookup_t peerDigestLookup(peer * p, HttpRequest * request); SQUIDCEXTERN peer *neighborsDigestSelect(HttpRequest * request); === modified file 'src/structs.h' --- src/structs.h 2008-07-11 19:32:10 +0000 +++ src/structs.h 2008-07-13 12:47:40 +0000 @@ -961,7 +961,6 @@ IPAddress addresses[10]; int n_addresses; int rr_count; - int rr_lastcount; peer *next; int test_fd;