]> git.proxmox.com Git - ceph.git/blobdiff - ceph/src/mgr/PyState.cc
update sources to v12.1.0
[ceph.git] / ceph / src / mgr / PyState.cc
index ca62c762b94d94dee3cbbc5c7c30483aaa95ba77..ce71dcd3f7003e2e1dfcb4bddb7b2db37d559f63 100644 (file)
 #include "Mgr.h"
 
 #include "mon/MonClient.h"
+#include "common/errno.h"
 #include "common/version.h"
 
 #include "PyState.h"
+#include "Gil.h"
 
 #define dout_context g_ceph_context
+#define dout_subsys ceph_subsys_mgr
 
 PyModules *global_handle = NULL;
 
@@ -32,13 +35,14 @@ class MonCommandCompletion : public Context
 {
   PyObject *python_completion;
   const std::string tag;
+  PyThreadState *pThreadState;
 
 public:
   std::string outs;
   bufferlist outbl;
 
-  MonCommandCompletion(PyObject* ev, const std::string &tag_)
-    : python_completion(ev), tag(tag_)
+  MonCommandCompletion(PyObject* ev, const std::string &tag_, PyThreadState *ts_)
+    : python_completion(ev), tag(tag_), pThreadState(ts_)
   {
     assert(python_completion != nullptr);
     Py_INCREF(python_completion);
@@ -51,28 +55,28 @@ public:
 
   void finish(int r) override
   {
-    PyGILState_STATE gstate;
-    gstate = PyGILState_Ensure();
-
-    auto set_fn = PyObject_GetAttrString(python_completion, "complete");
-    assert(set_fn != nullptr);
-
-    auto pyR = PyInt_FromLong(r);
-    auto pyOutBl = PyString_FromString(outbl.to_str().c_str());
-    auto pyOutS = PyString_FromString(outs.c_str());
-    auto args = PyTuple_Pack(3, pyR, pyOutBl, pyOutS);
-    Py_DECREF(pyR);
-    Py_DECREF(pyOutBl);
-    Py_DECREF(pyOutS);
-
-    auto rtn = PyObject_CallObject(set_fn, args);
-    if (rtn != nullptr) {
-      Py_DECREF(rtn);
+    dout(10) << "MonCommandCompletion::finish()" << dendl;
+    {
+      // Scoped so the Gil is released before calling notify_all()
+      Gil gil(pThreadState);
+
+      auto set_fn = PyObject_GetAttrString(python_completion, "complete");
+      assert(set_fn != nullptr);
+
+      auto pyR = PyInt_FromLong(r);
+      auto pyOutBl = PyString_FromString(outbl.to_str().c_str());
+      auto pyOutS = PyString_FromString(outs.c_str());
+      auto args = PyTuple_Pack(3, pyR, pyOutBl, pyOutS);
+      Py_DECREF(pyR);
+      Py_DECREF(pyOutBl);
+      Py_DECREF(pyOutS);
+
+      auto rtn = PyObject_CallObject(set_fn, args);
+      if (rtn != nullptr) {
+       Py_DECREF(rtn);
+      }
+      Py_DECREF(args);
     }
-    Py_DECREF(args);
-
-    PyGILState_Release(gstate);
-
     global_handle->notify_all("command", tag);
   }
 };
@@ -105,7 +109,7 @@ ceph_send_command(PyObject *self, PyObject *args)
   }
   Py_DECREF(set_fn);
 
-  auto c = new MonCommandCompletion(completion, tag);
+  auto c = new MonCommandCompletion(completion, tag, PyThreadState_Get());
   if (std::string(type) == "mon") {
     global_handle->get_monc().start_mon_command(
         {cmd_json},
@@ -117,7 +121,10 @@ ceph_send_command(PyObject *self, PyObject *args)
     std::string err;
     uint64_t osd_id = strict_strtoll(name, 10, &err);
     if (!err.empty()) {
-      // TODO: raise exception
+      delete c;
+      string msg("invalid osd_id: ");
+      msg.append("\"").append(name).append("\"");
+      PyErr_SetString(PyExc_ValueError, msg.c_str());
       return nullptr;
     }
 
@@ -139,14 +146,18 @@ ceph_send_command(PyObject *self, PyObject *args)
         &c->outs,
         c);
     if (r != 0) {
-      // TODO: raise exception
+      string msg("failed to send command to mds: ");
+      msg.append(cpp_strerror(r));
+      PyErr_SetString(PyExc_RuntimeError, msg.c_str());
       return nullptr;
     }
   } else if (std::string(type) == "pg") {
     // TODO: expose objecter::pg_command
     return nullptr;
   } else {
-    // TODO: raise exception
+    string msg("unknown service type: ");
+    msg.append(type);
+    PyErr_SetString(PyExc_ValueError, msg.c_str());
     return nullptr;
   }
 
@@ -183,6 +194,12 @@ ceph_get_server(PyObject *self, PyObject *args)
   }
 }
 
+static PyObject*
+ceph_get_mgr_id(PyObject *self, PyObject *args)
+{
+  return PyString_FromString(g_conf->name.get_id().c_str());
+}
+
 static PyObject*
 ceph_config_get(PyObject *self, PyObject *args)
 {
@@ -196,14 +213,27 @@ ceph_config_get(PyObject *self, PyObject *args)
   std::string value;
   bool found = global_handle->get_config(handle, what, &value);
   if (found) {
-    derr << "Found" << dendl;
+    dout(10) << "ceph_config_get " << what << " found: " << value.c_str() << dendl;
     return PyString_FromString(value.c_str());
   } else {
-    derr << "Not found" << dendl;
+    derr << "ceph_config_get " << what << " not found " << dendl;
     Py_RETURN_NONE;
   }
 }
 
+static PyObject*
+ceph_config_get_prefix(PyObject *self, PyObject *args)
+{
+  char *handle = nullptr;
+  char *prefix = nullptr;
+  if (!PyArg_ParseTuple(args, "ss:ceph_config_get", &handle, &prefix)) {
+    derr << "Invalid args!" << dendl;
+    return nullptr;
+  }
+
+  return global_handle->get_config_prefix(handle, prefix);
+}
+
 static PyObject*
 ceph_config_set(PyObject *self, PyObject *args)
 {
@@ -310,8 +340,12 @@ PyMethodDef CephStateMethods[] = {
      "Get a service's metadata"},
     {"send_command", ceph_send_command, METH_VARARGS,
      "Send a mon command"},
+    {"get_mgr_id", ceph_get_mgr_id, METH_NOARGS,
+     "Get the mgr id"},
     {"get_config", ceph_config_get, METH_VARARGS,
      "Get a configuration value"},
+    {"get_config_prefix", ceph_config_get_prefix, METH_VARARGS,
+     "Get all configuration values with a given prefix"},
     {"set_config", ceph_config_set, METH_VARARGS,
      "Set a configuration value"},
     {"get_counter", get_counter, METH_VARARGS,