从SWIG包装的C ++函数中获取当前的Python调用堆栈

时间:2015-09-03 04:15:16

标签: python swig callstack traceback python-extensions

如果我从Python调用SWIG包装的C / C ++函数,是否可以获得当前的调用堆栈?我想要类似于''.join(traceback.format_stack())的结果,但我不想将它从Python传递给我的C / C ++函数,因为我并不总是需要它。因此,如果我的C / C ++方面出现错误,我想在运行中获取并打印它。

1 个答案:

答案 0 :(得分:1)

我在this post之后找到了一个解决方案,虽然如果有的话,我仍然更喜欢更自然的方法来获得相同的东西。

// This is similar to the python code:
//   def GetScriptingLanguageCallStack():
//     import traceback
//     return ''.join(traceback.format_stack())
string GetScriptingLanguageCallStack() {
  string result;

  PyObject* module_name = PyString_FromString("traceback");
  PyObject* pyth_module = PyImport_Import(module_name);
  Py_DECREF(module_name);

  if (pyth_module != nullptr) {
    PyObject* pyth_func = PyObject_GetAttrString(pyth_module, "format_stack");
    if (pyth_func != nullptr) {
      if (PyCallable_Check(pyth_func)) {
        PyObject* pyth_val = PyObject_CallFunctionObjArgs(pyth_func, 0);
        if (pyth_val != nullptr) {
          if (PyList_Check(pyth_val)) {
            const int size = PyList_GET_SIZE(pyth_val);
            for (int i = 0; i < size; ++i) {
              PyObject* pyth_line = PyList_GET_ITEM(pyth_val, i);
              result += PyString_AsString(pyth_line);
            }
          }
          Py_DECREF(pyth_val);
        }
      }
      Py_DECREF(pyth_func);
    }
    Py_DECREF(pyth_module);
  }
  return result;
}

顺便说一句,我不喜欢使用框架对象的链接帖子中的方法,因为给定的行号不是指向进一步函数调用的确切行,而是仅在包含函数名称的行上