Merge PR #24797 into master

* refs/pull/24797/head:
	mds: handle state change race

Reviewed-by: Patrick Donnelly <pdonnell@redhat.com>
This commit is contained in:
Patrick Donnelly 2018-12-22 12:33:19 -08:00
commit 7b08cd79fe
No known key found for this signature in database
GPG Key ID: 3A2A7E25BEA8AADB
4 changed files with 20 additions and 3 deletions

View File

@ -2242,7 +2242,13 @@ void Locker::request_inode_file_caps(CInode *in)
void Locker::handle_inode_file_caps(const MInodeFileCaps::const_ref &m)
{
// nobody should be talking to us during recovery.
ceph_assert(mds->is_clientreplay() || mds->is_active() || mds->is_stopping());
if (mds->get_state() < MDSMap::STATE_CLIENTREPLAY) {
if (mds->get_want_state() >= MDSMap::STATE_CLIENTREPLAY) {
mds->wait_for_replay(new C_MDS_RetryMessage(mds, m));
return;
}
ceph_abort_msg("got unexpected message during recovery");
}
// ok
CInode *in = mdcache->get_inode(m->get_ino());

View File

@ -4653,7 +4653,13 @@ void MDCache::handle_cache_rejoin_strong(const MMDSCacheRejoin::const_ref &stron
mds_rank_t from = mds_rank_t(strong->get_source().num());
// only a recovering node will get a strong rejoin.
ceph_assert(mds->is_rejoin());
if (!mds->is_rejoin()) {
if (mds->get_want_state() == MDSMap::STATE_REJOIN) {
mds->wait_for_rejoin(new C_MDS_RetryMessage(mds, strong));
return;
}
ceph_abort_msg("got unexpected rejoin message during recovery");
}
// assimilate any potentially dirty scatterlock state
for (const auto &p : strong->inode_scatterlocks) {

View File

@ -1842,6 +1842,7 @@ void MDSRank::rejoin_start()
{
dout(1) << "rejoin_start" << dendl;
mdcache->rejoin_start(new C_MDS_VoidFn(this, &MDSRank::rejoin_done));
finish_contexts(g_ceph_context, waiting_for_rejoin);
}
void MDSRank::rejoin_done()
{

View File

@ -274,7 +274,8 @@ class MDSRank {
ceph_tid_t last_tid; // for mds-initiated requests (e.g. stray rename)
MDSInternalContextBase::vec waiting_for_active, waiting_for_replay, waiting_for_reconnect, waiting_for_resolve;
MDSInternalContextBase::vec waiting_for_active, waiting_for_replay, waiting_for_rejoin,
waiting_for_reconnect, waiting_for_resolve;
MDSInternalContextBase::vec waiting_for_any_client_connection;
MDSInternalContextBase::que replay_queue;
map<mds_rank_t, MDSInternalContextBase::vec > waiting_for_active_peer;
@ -407,6 +408,9 @@ class MDSRank {
void wait_for_replay(MDSInternalContextBase *c) {
waiting_for_replay.push_back(c);
}
void wait_for_rejoin(MDSInternalContextBase *c) {
waiting_for_rejoin.push_back(c);
}
void wait_for_reconnect(MDSInternalContextBase *c) {
waiting_for_reconnect.push_back(c);
}