]> git.apps.os.sepia.ceph.com Git - ceph.git/commitdiff
crimson/osd: handle pg ops with do_pg_ops()
authorKefu Chai <kchai@redhat.com>
Wed, 18 Sep 2019 14:54:37 +0000 (22:54 +0800)
committerKefu Chai <kchai@redhat.com>
Wed, 18 Sep 2019 14:54:39 +0000 (22:54 +0800)
currently, OpsExecuter tries to load the object info for all ops to be
executed, but the PG ops do not require the existence of object
specified by op. so we need to specialize for them.

in this change,

* `OpsExecuter::execute_pg_op()` is added to handle pg ops without
  loading object info first.
* `pgnls` and `pgnls_filter` are handled by
  `OpsExecuter::execute_pg_op()`.

Signed-off-by: Kefu Chai <kchai@redhat.com>
src/crimson/osd/ops_executer.cc
src/crimson/osd/ops_executer.h
src/crimson/osd/pg.cc
src/crimson/osd/pg.h

index cd455cdd9d2f9c348fe779ddd5396e78ce7bbb05..c49e38bfb17e0aef74df3dde923ee31b1143d27b 100644 (file)
@@ -386,14 +386,6 @@ OpsExecuter::execute_osd_op(OSDOp& osd_op)
     return do_write_op([&osd_op] (auto& backend, auto& os, auto& txn) {
       return backend.setxattr(os, osd_op, txn);
     });
-  case CEPH_OSD_OP_PGNLS_FILTER:
-    return do_pg_op([&osd_op] (const auto& pg, const auto& nspace) {
-      return do_pgnls_filtered(pg, nspace, osd_op);
-    });
-  case CEPH_OSD_OP_PGNLS:
-    return do_pg_op([&osd_op] (const auto& pg, const auto& nspace) {
-      return do_pgnls(pg, nspace, osd_op);
-    });
   case CEPH_OSD_OP_DELETE:
     return do_write_op([&osd_op] (auto& backend, auto& os, auto& txn) {
       return backend.remove(os, txn);
@@ -446,4 +438,24 @@ OpsExecuter::execute_osd_op(OSDOp& osd_op)
   }
 }
 
+seastar::future<>
+OpsExecuter::execute_pg_op(OSDOp& osd_op)
+{
+  logger().warn("handling op {}", ceph_osd_op_name(osd_op.op.op));
+  switch (const ceph_osd_op& op = osd_op.op; op.op) {
+  case CEPH_OSD_OP_PGNLS:
+    return do_pg_op([&osd_op] (const auto& pg, const auto& nspace) {
+      return do_pgnls(pg, nspace, osd_op);
+    });
+  case CEPH_OSD_OP_PGNLS_FILTER:
+    return do_pg_op([&osd_op] (const auto& pg, const auto& nspace) {
+      return do_pgnls_filtered(pg, nspace, osd_op);
+    });
+  default:
+    logger().warn("unknown op {}", ceph_osd_op_name(op.op));
+    throw std::runtime_error(
+      fmt::format("op '{}' not supported", ceph_osd_op_name(op.op)));
+  }
+}
+
 } // namespace ceph::osd
index 81b8d718da52c9af099a6d2ea7f27328f884a3e1..61f1d5b73714d7aafb0a8ce75df12c9301321724 100644 (file)
@@ -103,8 +103,12 @@ public:
       backend(pg.get_backend()),
       msg(std::move(msg)) {
   }
+  OpsExecuter(PG& pg, Ref<MOSDOp> msg)
+    : OpsExecuter{PGBackend::cached_os_t{}, pg, std::move(msg)}
+  {}
 
   seastar::future<> execute_osd_op(class OSDOp& osd_op);
+  seastar::future<> execute_pg_op(class OSDOp& osd_op);
 
   template <typename Func>
   seastar::future<> submit_changes(Func&& f) &&;
index 33ffb32a0ba8e453f06e3c6ed1a939fde32dbd10..e63b2e6fbcff35e0fca84803de463c6cfde4dde2 100644 (file)
@@ -394,6 +394,28 @@ seastar::future<Ref<MOSDOpReply>> PG::do_osd_ops(Ref<MOSDOp> m)
   });
 }
 
+seastar::future<Ref<MOSDOpReply>> PG::do_pg_ops(Ref<MOSDOp> m)
+{
+  return seastar::do_with(OpsExecuter{*this/* as const& */, m},
+                          [this, m] (auto& ox) {
+    return seastar::do_for_each(m->ops, [this, &ox](OSDOp& osd_op) {
+      logger().debug("will be handling pg op {}", ceph_osd_op_name(osd_op.op.op));
+      return ox.execute_pg_op(osd_op);
+    });
+  }).then([m, this] {
+    auto reply = make_message<MOSDOpReply>(m.get(), 0, get_osdmap_epoch(),
+                                           CEPH_OSD_FLAG_ACK | CEPH_OSD_FLAG_ONDISK,
+                                           false);
+    return seastar::make_ready_future<Ref<MOSDOpReply>>(std::move(reply));
+  }).handle_exception_type([=](const ceph::osd::error& e) {
+    auto reply = make_message<MOSDOpReply>(
+      m.get(), -e.code().value(), get_osdmap_epoch(), 0, false);
+    reply->set_enoent_reply_versions(peering_state.get_info().last_update,
+                                    peering_state.get_info().last_user_version);
+    return seastar::make_ready_future<Ref<MOSDOpReply>>(std::move(reply));
+  });
+}
+
 seastar::future<> PG::handle_op(ceph::net::Connection* conn,
                                 Ref<MOSDOp> m)
 {
@@ -401,7 +423,12 @@ seastar::future<> PG::handle_op(ceph::net::Connection* conn,
     if (m->finish_decode()) {
       m->clear_payload();
     }
-    return do_osd_ops(m);
+    if (std::any_of(begin(m->ops), end(m->ops),
+                   [](auto& op) { return ceph_osd_op_type_pg(op.op.op); })) {
+      return do_pg_ops(m);
+    } else {
+      return do_osd_ops(m);
+    }
   }).then([conn](Ref<MOSDOpReply> reply) {
     return conn->send(reply);
   });
index e6aeff7e72f7ba1d994798869f9b8d6cf8908d77..689d78dd251f602413565bc55ba907667e3c850f 100644 (file)
@@ -443,6 +443,7 @@ private:
     const boost::statechart::event_base &evt,
     PeeringCtx &rctx);
   seastar::future<Ref<MOSDOpReply>> do_osd_ops(Ref<MOSDOp> m);
+  seastar::future<Ref<MOSDOpReply>> do_pg_ops(Ref<MOSDOp> m);
   seastar::future<> do_osd_op(
     ObjectState& os,
     OSDOp& op,