From: Sage Weil Date: Wed, 13 Mar 2013 02:44:20 +0000 (-0700) Subject: mds: mark con for closed session disposable X-Git-Tag: v0.60~80^2~2 X-Git-Url: http://git-server-git.apps.pok.os.sepia.ceph.com/?a=commitdiff_plain;h=dcda36694740dddc5fba9bd896c0f93e89ee0145;p=ceph.git mds: mark con for closed session disposable If there is a fault while delivering the message, close the con. This will clean up the Session state from memory. If the client doesn't get the CLOSED message, they will reconnect (from their perspective, it is still a lossless connection) and get a remote_reset event telling them that the session is gone. The client code already handles this case properly. Note that way back in 4ac45200f10e0409121948cea5226ca9e23bb5fb we removed this because the client would reuse the same connection when it reopened the session. Now the client never does that; it will mark_down the con as soon as it is closed and open a new one for a new session... which means the MDS will get a remote_reset and close out the old session. Signed-off-by: Sage Weil --- diff --git a/src/mds/MDS.cc b/src/mds/MDS.cc index bf56778b0f5f..6c5a3693c324 100644 --- a/src/mds/MDS.cc +++ b/src/mds/MDS.cc @@ -2050,6 +2050,17 @@ void MDS::ms_handle_remote_reset(Connection *con) case CEPH_ENTITY_TYPE_OSD: objecter->ms_handle_remote_reset(con); break; + + case CEPH_ENTITY_TYPE_CLIENT: + Session *session = static_cast(con->get_priv()); + if (session) { + if (session->is_closed()) { + messenger->mark_down(con); + sessionmap.remove_session(session); + } + session->put(); + } + break; } } diff --git a/src/mds/Server.cc b/src/mds/Server.cc index d3acd15a0fd6..ad3912bb0779 100644 --- a/src/mds/Server.cc +++ b/src/mds/Server.cc @@ -299,6 +299,14 @@ void Server::_session_logged(Session *session, uint64_t state_seq, bool open, ve } if (session->is_closing()) { + // mark con disposable. if there is a fault, we will get a + // reset and clean it up. if the client hasn't received the + // CLOSE message yet, they will reconnect and get an + // ms_handle_remote_reset() and realize they had in fact closed. + // do this *before* sending the message to avoid a possible + // race. + mds->messenger->mark_disposable(session->connection); + // reset session mds->send_message_client(new MClientSession(CEPH_SESSION_CLOSE), session); mds->sessionmap.set_state(session, Session::STATE_CLOSED);