From 3a44135ed0c43dd1f62b7cb93f32ea7f7a9ae73b Mon Sep 17 00:00:00 2001 From: Friedemann Kleint <Friedemann.Kleint@nokia.com> Date: Thu, 2 Sep 2010 16:46:39 +0200 Subject: [PATCH] Debugger[gdb/MS Windows/console]: Fix attaching Resume thread after attaching and ignore the signal-trap that follows it. Reviewed-by: hjk Task-number: QTCREATORBUG-1020 --- src/plugins/debugger/gdb/gdbengine.cpp | 14 ++--- src/plugins/debugger/gdb/termgdbadapter.cpp | 59 +++++++++++++++++++-- 2 files changed, 63 insertions(+), 10 deletions(-) diff --git a/src/plugins/debugger/gdb/gdbengine.cpp b/src/plugins/debugger/gdb/gdbengine.cpp index d40f1763ef5..4f79925636f 100644 --- a/src/plugins/debugger/gdb/gdbengine.cpp +++ b/src/plugins/debugger/gdb/gdbengine.cpp @@ -947,7 +947,8 @@ void GdbEngine::handleResultRecord(GdbResponse *response) if (!isExpectedResult) { #ifdef Q_OS_WIN // Ignore spurious 'running' responses to 'attach' - const bool warning = !(startParameters().startMode == AttachExternal + const bool warning = !((startParameters().startMode == AttachExternal + || startParameters().useTerminal) && cmd.command.startsWith("attach")); #else const bool warning = true; @@ -1368,14 +1369,15 @@ void GdbEngine::handleStop1(const GdbMi &data) QByteArray reason = data.findChild("reason").data(); - if (0 && m_gdbAdapter->isTrkAdapter() - && reason == "signal-received" - && data.findChild("signal-name").data() == "SIGTRAP") { - // Caused by "library load" message. - showMessage(_("INTERNAL CONTINUE")); +#ifdef Q_OS_WIN + if (startParameters().useTerminal && reason == "signal-received" + && data.findChild("signal-name").data() == "SIGTRAP") { + // Command line start up trap + showMessage(_("INTERNAL CONTINUE"), LogMisc); continueInferiorInternal(); return; } +#endif // This is for display only. if (m_modulesListOutdated) diff --git a/src/plugins/debugger/gdb/termgdbadapter.cpp b/src/plugins/debugger/gdb/termgdbadapter.cpp index fd109469db0..42c88676916 100644 --- a/src/plugins/debugger/gdb/termgdbadapter.cpp +++ b/src/plugins/debugger/gdb/termgdbadapter.cpp @@ -38,6 +38,11 @@ #include <QtGui/QMessageBox> +#ifdef Q_OS_WIN +# include <windows.h> +# include <utils/winutils.h> +#endif + namespace Debugger { namespace Internal { @@ -119,23 +124,69 @@ void TermGdbAdapter::setupInferior() { QTC_ASSERT(state() == InferiorSetupRequested, qDebug() << state()); const qint64 attachedPID = m_stubProc.applicationPID(); +#ifdef Q_OS_WIN + const qint64 attachedMainThreadID = m_stubProc.applicationMainThreadID(); + showMessage(QString::fromLatin1("Attaching to %1 (%2)").arg(attachedPID).arg(attachedMainThreadID), LogMisc); +#else + showMessage(QString::fromLatin1("Attaching to %1").arg(attachedPID), LogMisc); +#endif m_engine->notifyInferiorPid(attachedPID); m_engine->postCommand("attach " + QByteArray::number(attachedPID), CB(handleStubAttached)); } +#ifdef Q_OS_WIN +static bool resumeThread(DWORD dwThreadId) +{ + bool ok = false; + HANDLE handle = NULL; + do { + if (!dwThreadId) + break; + + handle = OpenThread(SYNCHRONIZE |THREAD_QUERY_INFORMATION |THREAD_SUSPEND_RESUME, + FALSE, dwThreadId); + if (handle==NULL) + break; + + ok = ResumeThread(handle) != DWORD(-1); + } while (false); + if (handle != NULL) + CloseHandle(handle); + return ok; +} +#endif // Q_OS_WIN + void TermGdbAdapter::handleStubAttached(const GdbResponse &response) { QTC_ASSERT(state() == InferiorSetupRequested, qDebug() << state()); - if (response.resultClass == GdbResultDone) { + switch (response.resultClass) { + case GdbResultDone: + case GdbResultRunning: +#ifdef Q_OS_WIN + // Resume thread that was suspended by console stub process (see stub code). + if (resumeThread(m_stubProc.applicationMainThreadID())) { + showMessage(QString::fromLatin1("Inferior attached, thread %1 resumed"). + arg(m_stubProc.applicationMainThreadID()), LogMisc); + } else { + showMessage(QString::fromLatin1("Inferior attached, unable to resume thread %1: %2"). + arg(m_stubProc.applicationMainThreadID()).arg(Utils::winErrorMessage(GetLastError())), + LogWarning); + } +#else showMessage(_("INFERIOR ATTACHED")); +#endif // Q_OS_WIN m_engine->handleInferiorPrepared(); #ifdef Q_OS_LINUX m_engine->postCommand("-stack-list-frames 0 0", CB(handleEntryPoint)); #endif - } else if (response.resultClass == GdbResultError) { - QString msg = QString::fromLocal8Bit(response.data.findChild("msg").data()); - m_engine->notifyInferiorSetupFailed(msg); + break; + case GdbResultError: + m_engine->notifyInferiorSetupFailed(QString::fromLocal8Bit(response.data.findChild("msg").data())); + break; + default: + m_engine->notifyInferiorSetupFailed(QString::fromLatin1("Invalid response %1").arg(response.resultClass)); + break; } } -- GitLab