From 05397e405f552bb720e12b9c0557b4c9234ffaa0 Mon Sep 17 00:00:00 2001 From: "Yan, Zheng" Date: Mon, 11 Dec 2017 08:43:57 +0800 Subject: [PATCH] osdc/Journaler: add 'stopping' check to various finish callbacks These callbacks are executed by finisher. When they are being executed, Journaler can be in stopping state. Fixes: http://tracker.ceph.com/issues/22360 Signed-off-by: "Yan, Zheng" (cherry picked from commit 7ffa87e6a2ab8fb2c64588411c6c2ebff2f91f93) --- src/osdc/Journaler.cc | 36 +++++++++++++++++++++++++++++++++++- 1 file changed, 35 insertions(+), 1 deletion(-) diff --git a/src/osdc/Journaler.cc b/src/osdc/Journaler.cc index fe9a6e9cdaf2b..85e29e61c3d1a 100644 --- a/src/osdc/Journaler.cc +++ b/src/osdc/Journaler.cc @@ -215,6 +215,10 @@ void Journaler::_reread_head(Context *onfinish) void Journaler::_finish_reread_head(int r, bufferlist& bl, Context *finish) { lock_guard l(lock); + if (stopping) { + finish->complete(-EAGAIN); + return; + } //read on-disk header into assert(bl.length() || r < 0 ); @@ -243,6 +247,8 @@ void Journaler::_finish_reread_head(int r, bufferlist& bl, Context *finish) void Journaler::_finish_read_head(int r, bufferlist& bl) { lock_guard l(lock); + if (stopping) + return; assert(state == STATE_READHEAD); @@ -333,6 +339,10 @@ void Journaler::_finish_reprobe(int r, uint64_t new_end, C_OnFinisher *onfinish) { lock_guard l(lock); + if (stopping) { + onfinish->complete(-EAGAIN); + return; + } assert(new_end >= write_pos || r < 0); ldout(cct, 1) << "_finish_reprobe new_end = " << new_end @@ -346,6 +356,8 @@ void Journaler::_finish_reprobe(int r, uint64_t new_end, void Journaler::_finish_probe_end(int r, uint64_t end) { lock_guard l(lock); + if (stopping) + return; assert(state == STATE_PROBING); if (r < 0) { // error in probing @@ -398,6 +410,10 @@ void Journaler::_finish_reread_head_and_probe(int r, C_OnFinisher *onfinish) { // Expect to be called back from finish_reread_head, which already takes lock // lock is locked + if (stopping) { + onfinish->complete(-EAGAIN); + return; + } assert(!r); //if we get an error, we're boned _reprobe(onfinish); @@ -589,6 +605,8 @@ uint64_t Journaler::append_entry(bufferlist& bl) void Journaler::_do_flush(unsigned amount) { + if (stopping) + return; if (write_pos == flush_pos) return; assert(write_pos > flush_pos); @@ -711,6 +729,10 @@ void Journaler::_wait_for_flush(Context *onsafe) void Journaler::flush(Context *onsafe) { lock_guard l(lock); + if (stopping) { + onsafe->complete(-EAGAIN); + return; + } _flush(wrap_finisher(onsafe)); } @@ -1018,6 +1040,9 @@ void Journaler::_issue_read(uint64_t len) void Journaler::_prefetch() { + if (stopping) + return; + ldout(cct, 10) << "_prefetch" << dendl; // prefetch uint64_t pf; @@ -1163,6 +1188,10 @@ void Journaler::erase(Context *completion) void Journaler::_finish_erase(int data_result, C_OnFinisher *completion) { lock_guard l(lock); + if (stopping) { + completion->complete(-EAGAIN); + return; + } if (data_result == 0) { // Async delete the journal header @@ -1270,6 +1299,9 @@ void Journaler::trim() void Journaler::_trim() { + if (stopping) + return; + assert(!readonly); uint64_t period = get_layout_period(); uint64_t trim_to = last_committed.expire_pos; @@ -1531,7 +1563,9 @@ void Journaler::shutdown() f->complete(-EAGAIN); } - finish_contexts(cct, waitfor_recover, -ESHUTDOWN); + list ls; + ls.swap(waitfor_recover); + finish_contexts(cct, ls, -ESHUTDOWN); std::map >::iterator i; for (i = waitfor_safe.begin(); i != waitfor_safe.end(); ++i) { -- 2.39.5