From 90418ab9685dd06aeb5a46f2616b5d687d13e6c5 Mon Sep 17 00:00:00 2001 From: wmayer Date: Sat, 29 Dec 2012 17:07:02 +0100 Subject: [PATCH] Fixes on built-in Python debugger --- src/Gui/CommandMacro.cpp | 37 ++++++++++++++++++++++--- src/Gui/EditorView.cpp | 2 +- src/Gui/PythonDebugger.cpp | 55 ++++++++++++++++++++++++++++++++++---- src/Gui/PythonDebugger.h | 2 ++ src/Gui/PythonEditor.h | 2 +- src/Gui/Workbench.cpp | 3 ++- 6 files changed, 89 insertions(+), 12 deletions(-) diff --git a/src/Gui/CommandMacro.cpp b/src/Gui/CommandMacro.cpp index 3c8f13f94..50e09f842 100644 --- a/src/Gui/CommandMacro.cpp +++ b/src/Gui/CommandMacro.cpp @@ -164,14 +164,16 @@ StdCmdMacroStartDebug::StdCmdMacroStartDebug() void StdCmdMacroStartDebug::activated(int iMsg) { - doCommand(Command::Gui,"Gui.SendMsgToActiveView(\"StartDebug\")"); + PythonDebugger* dbg = Application::Instance->macroManager()->debugger(); + if (!dbg->isRunning()) + doCommand(Command::Gui,"Gui.SendMsgToActiveView(\"StartDebug\")"); + else + dbg->stepRun(); } bool StdCmdMacroStartDebug::isActive(void) { - static PythonDebugger* dbg = Application::Instance->macroManager()->debugger(); - return (!dbg->isRunning() && - getGuiApplication()->sendHasMsgToActiveView("StartDebug")); + return getGuiApplication()->sendHasMsgToActiveView("StartDebug"); } DEF_STD_CMD_A(StdCmdMacroStopDebug); @@ -226,6 +228,32 @@ bool StdCmdMacroStepOver::isActive(void) return dbg->isRunning(); } +DEF_STD_CMD_A(StdCmdMacroStepInto); + +StdCmdMacroStepInto::StdCmdMacroStepInto() + : Command("Std_MacroStepInto") +{ + sGroup = QT_TR_NOOP("Macro"); + sMenuText = QT_TR_NOOP("Step into"); + sToolTipText = QT_TR_NOOP("Step into"); + //sWhatsThis = "Std_MacroStepOver"; + sStatusTip = QT_TR_NOOP("Step into"); + sPixmap = 0; + sAccel = "F11"; + eType = 0; +} + +void StdCmdMacroStepInto::activated(int iMsg) +{ + Application::Instance->macroManager()->debugger()->stepInto(); +} + +bool StdCmdMacroStepInto::isActive(void) +{ + static PythonDebugger* dbg = Application::Instance->macroManager()->debugger(); + return dbg->isRunning(); +} + DEF_STD_CMD_A(StdCmdToggleBreakpoint); StdCmdToggleBreakpoint::StdCmdToggleBreakpoint() @@ -263,6 +291,7 @@ void CreateMacroCommands(void) rcCmdMgr.addCommand(new StdCmdMacroStartDebug()); rcCmdMgr.addCommand(new StdCmdMacroStopDebug()); rcCmdMgr.addCommand(new StdCmdMacroStepOver()); + rcCmdMgr.addCommand(new StdCmdMacroStepInto()); rcCmdMgr.addCommand(new StdCmdToggleBreakpoint()); } diff --git a/src/Gui/EditorView.cpp b/src/Gui/EditorView.cpp index 4566a4117..034564a3f 100644 --- a/src/Gui/EditorView.cpp +++ b/src/Gui/EditorView.cpp @@ -507,7 +507,7 @@ bool PythonEditorView::onMsg(const char* pMsg,const char** ppReturn) return true; } else if (strcmp(pMsg,"StartDebug")==0) { - startDebug(); + QTimer::singleShot(300, this, SLOT(startDebug())); return true; } else if (strcmp(pMsg,"ToggleBreakpoint")==0) { diff --git a/src/Gui/PythonDebugger.cpp b/src/Gui/PythonDebugger.cpp index fc7b432c8..45952dc60 100644 --- a/src/Gui/PythonDebugger.cpp +++ b/src/Gui/PythonDebugger.cpp @@ -236,9 +236,10 @@ Py::Object PythonDebugStderr::repr() Py::Object PythonDebugStderr::write(const Py::Tuple& args) { char *msg; - PyObject* pObj; + //PyObject* pObj; //args contains a single parameter which is the string to write. - if (!PyArg_ParseTuple(args.ptr(), "Os:OutputDebugString", &pObj, &msg)) + //if (!PyArg_ParseTuple(args.ptr(), "Os:OutputDebugString", &pObj, &msg)) + if (!PyArg_ParseTuple(args.ptr(), "s:OutputDebugString", &msg)) throw Py::Exception(); if (strlen(msg) > 0) @@ -248,6 +249,7 @@ Py::Object PythonDebugStderr::write(const Py::Tuple& args) //send it to the debugger as well //g_DebugSocket.SendMessage(eMSG_TRACE, msg); + Base::Console().Error("%s", msg); } return Py::None(); @@ -417,9 +419,42 @@ void PythonDebugger::runFile(const QString& fn) { try { RunningState state(d->running); - Base::Interpreter().runFile((const char*)fn.toUtf8(), true); + QByteArray pxFileName = fn.toUtf8(); +#ifdef FC_OS_WIN32 + Base::FileInfo fi((const char*)pxFileName); + FILE *fp = _wfopen(fi.toStdWString().c_str(),L"r"); +#else + FILE *fp = fopen((const char*)pxFileName,"r"); +#endif + if (!fp) return; + + Base::PyGILStateLocker locker; + PyObject *module, *dict; + module = PyImport_AddModule("__main__"); + dict = PyModule_GetDict(module); + dict = PyDict_Copy(dict); + if (PyDict_GetItemString(dict, "__file__") == NULL) { + PyObject *f = PyString_FromString((const char*)pxFileName); + if (f == NULL) + return; + if (PyDict_SetItemString(dict, "__file__", f) < 0) { + Py_DECREF(f); + return; + } + Py_DECREF(f); + } + + PyObject *result = PyRun_File(fp, (const char*)pxFileName, Py_file_input, dict, dict); + fclose(fp); + Py_DECREF(dict); + + if (!result) + PyErr_Print(); + else + Py_DECREF(result); } - catch (const Base::PyException&) { + catch (const Base::PyException&/* e*/) { + //PySys_WriteStderr("Exception: %s\n", e.what()); } catch (...) { Base::Console().Warning("Unknown exception thrown during macro debugging\n"); @@ -474,6 +509,16 @@ void PythonDebugger::stepOver() signalNextStep(); } +void PythonDebugger::stepInto() +{ + signalNextStep(); +} + +void PythonDebugger::stepRun() +{ + signalNextStep(); +} + void PythonDebugger::showDebugMarker(const QString& fn, int line) { PythonEditorView* edit = 0; @@ -524,7 +569,7 @@ int PythonDebugger::tracer_callback(PyObject *obj, PyFrameObject *frame, int wha //int no; //no = frame->f_tstate->recursion_depth; - //char* name = PyString_AsString(frame->f_code->co_name); + //std::string funcname = PyString_AsString(frame->f_code->co_name); QString file = QString::fromUtf8(PyString_AsString(frame->f_code->co_filename)); switch (what) { case PyTrace_CALL: diff --git a/src/Gui/PythonDebugger.h b/src/Gui/PythonDebugger.h index a42ff5a56..e3af16ebe 100644 --- a/src/Gui/PythonDebugger.h +++ b/src/Gui/PythonDebugger.h @@ -169,6 +169,8 @@ public: bool stop(); void tryStop(); void stepOver(); + void stepInto(); + void stepRun(); void showDebugMarker(const QString&, int line); void hideDebugMarker(const QString&); diff --git a/src/Gui/PythonEditor.h b/src/Gui/PythonEditor.h index f64e9ddf5..0db11c9e0 100644 --- a/src/Gui/PythonEditor.h +++ b/src/Gui/PythonEditor.h @@ -45,7 +45,6 @@ public: PythonEditor(QWidget *parent = 0); ~PythonEditor(); - void startDebug(); void toggleBreakpoint(); void showDebugMarker(int line); void hideDebugMarker(); @@ -62,6 +61,7 @@ public Q_SLOTS: */ void onUncomment(); void setFileName(const QString&); + void startDebug(); protected: /** Pops up the context menu with some extensions */ diff --git a/src/Gui/Workbench.cpp b/src/Gui/Workbench.cpp index 33e0942bb..f3580a814 100644 --- a/src/Gui/Workbench.cpp +++ b/src/Gui/Workbench.cpp @@ -499,7 +499,8 @@ MenuItem* StdWorkbench::setupMenuBar() const macro->setCommand("&Macro"); *macro << "Std_DlgMacroRecord" << "Std_MacroStopRecord" << "Std_DlgMacroExecute" << "Separator" << "Std_DlgMacroExecuteDirect" << "Std_MacroStartDebug" - << "Std_MacroStopDebug" << "Std_MacroStepOver" << "Std_ToggleBreakpoint"; + << "Std_MacroStopDebug" << "Std_MacroStepOver" << "Std_MacroStepInto" + << "Std_ToggleBreakpoint"; // Windows MenuItem* wnd = new MenuItem( menuBar );