From: Patrick Donnelly Date: Mon, 13 Nov 2023 19:23:54 +0000 (-0500) Subject: mds: add command to kill request X-Git-Tag: v19.1.0~193^2~41 X-Git-Url: http://git.apps.os.sepia.ceph.com/?a=commitdiff_plain;h=e9b482f4aa300808220d49fd53b5c4bfd6130d08;p=ceph.git mds: add command to kill request Fixes: https://tracker.ceph.com/issues/63374 Signed-off-by: Patrick Donnelly (cherry picked from commit 9956f9ad78a3b6ebe520dcd10e33a59c361c4d91) --- diff --git a/src/mds/MDCache.cc b/src/mds/MDCache.cc index 84e743af82fcf..38df8e3b03e3f 100644 --- a/src/mds/MDCache.cc +++ b/src/mds/MDCache.cc @@ -9904,6 +9904,11 @@ void MDCache::request_cleanup(const MDRequestRef& mdr) void MDCache::request_kill(const MDRequestRef& mdr) { + if (mdr->killed) { + /* ignore duplicate kills */ + return; + } + // rollback peer requests is tricky. just let the request proceed. if (mdr->has_more() && (!mdr->more()->witnessed.empty() || !mdr->more()->waiting_on_peer.empty())) { diff --git a/src/mds/MDSDaemon.cc b/src/mds/MDSDaemon.cc index e59419d1533e5..850e9e700c41b 100644 --- a/src/mds/MDSDaemon.cc +++ b/src/mds/MDSDaemon.cc @@ -265,6 +265,11 @@ void MDSDaemon::set_up_admin_socket() ,asok_hook ,"show the ops currently in flight"); ceph_assert(r == 0); + r = admin_socket->register_command("op kill " + "name=id,type=CephString,req=true", + asok_hook, + "kill op"); + ceph_assert(r == 0); r = admin_socket->register_command("dump_blocked_ops", asok_hook, "show the blocked ops currently in flight"); diff --git a/src/mds/MDSRank.cc b/src/mds/MDSRank.cc index e8486b1344b17..8ab77f23a66f9 100644 --- a/src/mds/MDSRank.cc +++ b/src/mds/MDSRank.cc @@ -2693,6 +2693,36 @@ void MDSRankDispatcher::handle_asok_command( *css << "op_tracker disabled; set mds_enable_op_tracker=true to enable"; } } + } else if (command == "op kill") { + std::string id; + if(!cmd_getval(cmdmap, "id", id)) { + *css << "malformed id"; + r = -CEPHFS_EINVAL; + goto out; + } + metareqid_t mrid; + try { + mrid = metareqid_t(id); + } catch (const std::exception& e) { + *css << "malformed id: " << e.what(); + r = -CEPHFS_EINVAL; + goto out; + } + std::lock_guard l(mds_lock); + if (!mdcache->have_request(mrid)) { + *css << "request does not exist"; + r = -CEPHFS_ENOENT; + goto out; + } + auto mdr = mdcache->request_get(mrid); + { + f->open_object_section("result"); + f->dump_int("result", 0); + f->dump_object("request", *mdr); + f->close_section(); + } + mdcache->request_kill(mdr); + r = 0; } else if (command == "dump_blocked_ops") { if (!op_tracker.dump_ops_in_flight(f, true)) { *css << "op_tracker disabled; set mds_enable_op_tracker=true to enable"; diff --git a/src/mds/mdstypes.h b/src/mds/mdstypes.h index a39ec5abbd5d0..272ae76cac18d 100644 --- a/src/mds/mdstypes.h +++ b/src/mds/mdstypes.h @@ -8,6 +8,7 @@ #include #include #include +#include #include #include "common/config.h" @@ -600,6 +601,22 @@ WRITE_CLASS_ENCODER(mds_table_pending_t) struct metareqid_t { metareqid_t() {} metareqid_t(entity_name_t n, ceph_tid_t t) : name(n), tid(t) {} + metareqid_t(std::string_view sv) { + auto p = sv.find(':'); + if (p == std::string::npos) { + throw std::invalid_argument("invalid format: expected colon"); + } + if (!name.parse(sv.substr(0, p))) { + throw std::invalid_argument("invalid format: invalid entity name"); + } + try { + tid = std::stoul(std::string(sv.substr(p+1)), nullptr, 0); + } catch (const std::invalid_argument& e) { + throw std::invalid_argument("invalid format: tid is not a number"); + } catch (const std::out_of_range& e) { + throw std::invalid_argument("invalid format: tid is out of range"); + } + } void encode(ceph::buffer::list& bl) const { using ceph::encode; encode(name, bl);