Comm::AcceptLimiter::defer(Comm::ConnAcceptor *afd)
{
afd->isLimited++;
- debugs(5, 5, HERE << "FD " << afd->conn->fd << " x" << afd->isLimited);
+ debugs(5, 5, HERE << afd->conn << " x" << afd->isLimited);
deferred.push_back(afd);
}
+void
+Comm::AcceptLimiter::removeDead(Comm::ConnAcceptor *afd)
+{
+ for (unsigned int i = 0; i < deferred.size() && afd->isLimited > 0; i++) {
+ if (deferred[i] == afd) {
+ deferred[i] = NULL;
+ afd->isLimited--;
+ debugs(5, 5, HERE << afd->conn << " x" << afd->isLimited);
+ }
+ }
+}
+
void
Comm::AcceptLimiter::kick()
{
debugs(5, 5, HERE << " size=" << deferred.size());
- if (deferred.size() > 0 && fdNFree() >= RESERVED_FD) {
- debugs(5, 5, HERE << " doing one.");
+ while (deferred.size() > 0 && fdNFree() >= RESERVED_FD) {
/* NP: shift() is equivalent to pop_front(). Giving us a FIFO queue. */
ConnAcceptor *temp = deferred.shift();
- temp->isLimited--;
- temp->acceptNext();
+ if (temp != NULL) {
+ debugs(5, 5, HERE << " doing one.");
+ temp->isLimited--;
+ temp->acceptNext();
+ break;
+ }
}
}
* new connection. These handlers are awaiting some FD to become free.
*
* defer - used only by Comm layer ConnAcceptor adding themselves when FD are limited.
+ * removeDead - used only by Comm layer ConnAcceptor to remove themselves when dying.
* kick - used by Comm layer when FD are closed.
*/
class AcceptLimiter
/** delay accepting a new client connection. */
void defer(Comm::ConnAcceptor *afd);
+ /** remove all records of an acceptor. Only to be called by the ConnAcceptor::swanSong() */
+ void removeDead(Comm::ConnAcceptor *afd);
+
/** try to accept and begin processing any delayed client connections. */
void kick();