From 7552d310f304af6c26d17c95a6a66bdfba6b367f Mon Sep 17 00:00:00 2001 From: Alex Rousskov Date: Tue, 3 Jun 2014 01:10:15 -0600 Subject: [PATCH] Fix leaked TcpAcceptor job on reconfiguration ... by monitoring and reacting to the listening socket closure. Every job that waits for Comm I/O must have a FD closure handler. --- src/comm/TcpAcceptor.cc | 20 ++++++++++++++++++++ src/comm/TcpAcceptor.h | 6 ++++++ 2 files changed, 26 insertions(+) diff --git a/src/comm/TcpAcceptor.cc b/src/comm/TcpAcceptor.cc index 0e703024fd..5582c37ced 100644 --- a/src/comm/TcpAcceptor.cc +++ b/src/comm/TcpAcceptor.cc @@ -122,6 +122,12 @@ Comm::TcpAcceptor::swanSong() { debugs(5,5, HERE); unsubscribe("swanSong"); + if (IsConnOpen(conn)) { + if (closer_ != NULL) + comm_remove_close_handler(conn->fd, closer_); + conn->close(); + } + conn = NULL; AcceptLimiter::Instance().removeDead(this); AsyncJob::swanSong(); @@ -182,6 +188,20 @@ Comm::TcpAcceptor::setListen() debugs(5, DBG_CRITICAL, "WARNING: accept_filter not supported on your OS"); #endif } + + typedef CommCbMemFunT Dialer; + closer_ = JobCallback(5, 4, Dialer, this, Comm::TcpAcceptor::handleClosure); + comm_add_close_handler(conn->fd, closer_); +} + +/// called when listening descriptor is closed by an external force +/// such as clientHttpConnectionsClose() +void +Comm::TcpAcceptor::handleClosure(const CommCloseCbParams &io) +{ + closer_ = NULL; + conn = NULL; + Must(done()); } /** diff --git a/src/comm/TcpAcceptor.h b/src/comm/TcpAcceptor.h index 48aee211ee..3ca2a9773a 100644 --- a/src/comm/TcpAcceptor.h +++ b/src/comm/TcpAcceptor.h @@ -7,6 +7,8 @@ #include "comm_err_t.h" #include "comm/forward.h" +class CommCloseCbParams; + namespace Comm { @@ -73,6 +75,9 @@ private: /// Reserved for read-only use. ConnectionPointer conn; + /// listen socket closure handler + AsyncCall::Pointer closer_; + /// Method to test if there are enough file descriptors to open a new client connection /// if not the accept() will be postponed static bool okToAccept(); @@ -83,6 +88,7 @@ private: void acceptOne(); comm_err_t oldAccept(Comm::ConnectionPointer &details); void setListen(); + void handleClosure(const CommCloseCbParams &io); CBDATA_CLASS2(TcpAcceptor); }; -- 2.47.2