void GdbCoreEngine::handleTargetCore(const DebuggerResponse &response) { CHECK_STATE(EngineRunRequested); notifyEngineRunOkAndInferiorUnrunnable(); if (response.resultClass == ResultDone) { showMessage(tr("Attached to core."), StatusBar); // Due to the auto-solib-add off setting, we don't have any // symbols yet. Load them in order of importance. reloadStack(); reloadModulesInternal(); postCommand("p 5", NoFlags, CB(handleRoundTrip)); return; } showStatusMessage(tr("Attach to core \"%1\" failed:").arg(runParameters().coreFile) + QLatin1Char('\n') + QString::fromLocal8Bit(response.data["msg"].data())); notifyEngineIll(); }
void GdbCoreEngine::handleTargetCore(const DebuggerResponse &response) { CHECK_STATE(EngineRunRequested); notifyEngineRunOkAndInferiorUnrunnable(); showMessage(tr("Attached to core."), StatusBar); if (response.resultClass == ResultError) { // We'll accept any kind of error e.g. &"Cannot access memory at address 0x2abc2a24\n" // Even without the stack, the user can find interesting stuff by exploring // the memory, globals etc. showStatusMessage(tr("Attach to core \"%1\" failed:").arg(runParameters().coreFile) + QLatin1Char('\n') + QString::fromLocal8Bit(response.data["msg"].data()) + QLatin1Char('\n') + tr("Continuing nevertheless.")); } // Due to the auto-solib-add off setting, we don't have any // symbols yet. Load them in order of importance. reloadStack(); reloadModulesInternal(); runCommand({"p 5", NoFlags, CB(handleRoundTrip)}); }
void QmlCppEngine::slaveEngineStateChanged (DebuggerEngine *slaveEngine, const DebuggerState newState) { DebuggerEngine *otherEngine = (slaveEngine == m_cppEngine) ? m_qmlEngine : m_cppEngine; QTC_CHECK(otherEngine != slaveEngine); if (debug) { EDEBUG("GOT SLAVE STATE: " << slaveEngine << newState); EDEBUG(" OTHER ENGINE: " << otherEngine << otherEngine->state()); EDEBUG(" COMBINED ENGINE: " << this << state() << isDying()); } if (state() == DebuggerFinished) { // We are done and don't care about slave state changes anymore. return; } // Idea is to follow the state of the cpp engine, except where we are stepping in QML. // That is, when the QmlEngine moves between InferiorStopOk, and InferiorRunOk, InferiorStopOk ... // // Accordingly, the 'active engine' is the cpp engine until the qml engine enters the // InferiorStopOk state. The cpp engine becomes the active one again as soon as it itself enters // the InferiorStopOk state. if (slaveEngine == m_cppEngine) { switch (newState) { case DebuggerNotReady: { // Can this ever happen? break; } case EngineSetupRequested: { // Set by queueSetupEngine() CHECK_STATE(EngineSetupRequested); break; } case EngineSetupFailed: { qmlEngine()->quitDebugger(); notifyEngineSetupFailed(); break; } case EngineSetupOk: { notifyEngineSetupOk(); break; } case InferiorSetupRequested: { // Set by queueSetupInferior() CHECK_STATE(InferiorSetupRequested); break; } case InferiorSetupFailed: { qmlEngine()->quitDebugger(); notifyInferiorSetupFailed(); break; } case InferiorSetupOk: { notifyInferiorSetupOk(); break; } case EngineRunRequested: { // set by queueRunEngine() break; } case EngineRunFailed: { qmlEngine()->quitDebugger(); notifyEngineRunFailed(); break; } case InferiorUnrunnable: { qmlEngine()->quitDebugger(); notifyEngineRunOkAndInferiorUnrunnable(); break; } case InferiorRunRequested: { // Might be set already by notifyInferiorRunRequested() if (state() != InferiorRunRequested) { CHECK_STATE(InferiorStopOk); notifyInferiorRunRequested(); } break; } case InferiorRunOk: { if (state() == EngineRunRequested) notifyEngineRunAndInferiorRunOk(); else if (state() == InferiorRunRequested) notifyInferiorRunOk(); else QTC_ASSERT(false, qDebug() << state()); if (qmlEngine()->state() == InferiorStopOk) { // track qml engine again setState(InferiorStopRequested); notifyInferiorStopOk(); setActiveEngine(m_qmlEngine); } break; } case InferiorRunFailed: { qmlEngine()->quitDebugger(); notifyInferiorRunFailed(); break; } case InferiorStopRequested: { if (m_activeEngine == cppEngine()) { if (state() == InferiorRunOk) { setState(InferiorStopRequested); } else { // Might be set by doInterruptInferior() CHECK_STATE(InferiorStopRequested); } } else { // We're debugging qml, but got an interrupt, or abort if (state() == InferiorRunOk) { setState(InferiorStopRequested); } else if (state() == InferiorStopOk) { notifyInferiorRunRequested(); notifyInferiorRunOk(); setState(InferiorStopRequested); } else if (state() == InferiorRunRequested) { notifyInferiorRunOk(); setState(InferiorStopRequested); } else { QTC_ASSERT(false, qDebug() << state()); } // now track cpp engine setActiveEngine(m_cppEngine); } break; } case InferiorStopOk: { if (isDying()) { EDEBUG("... CPP ENGINE STOPPED DURING SHUTDOWN "); QTC_ASSERT(state() == InferiorStopRequested || state() == InferiorRunOk || state() == InferiorStopOk, qDebug() << state()); // Just to make sure, we're shutting down anyway ... setActiveEngine(m_cppEngine); if (state() == InferiorStopRequested) setState(InferiorStopOk); // otherwise we're probably inside notifyInferiorStopOk already } else { if (m_activeEngine != cppEngine()) { showStatusMessage(tr("C++ debugger activated")); setActiveEngine(m_cppEngine); } switch (state()) { case InferiorStopRequested: EDEBUG("... CPP ENGINE STOPPED EXPECTEDLY"); notifyInferiorStopOk(); break; case EngineRunRequested: EDEBUG("... CPP ENGINE STOPPED ON STARTUP"); notifyEngineRunAndInferiorStopOk(); break; case InferiorRunOk: EDEBUG("... CPP ENGINE STOPPED SPONTANEOUSLY"); notifyInferiorSpontaneousStop(); break; case InferiorRunRequested: // can happen if qml engine was active notifyInferiorRunFailed(); default: CHECK_STATE(InferiorStopOk); break; } } break; } case InferiorStopFailed: { CHECK_STATE(InferiorStopRequested); notifyInferiorStopFailed(); break; } case InferiorShutdownRequested: { if (state() == InferiorStopOk) { setState(InferiorShutdownRequested); } else { // might be set by queueShutdownInferior() already CHECK_STATE(InferiorShutdownRequested); } qmlEngine()->quitDebugger(); break; } case InferiorShutdownFailed: { CHECK_STATE(InferiorShutdownRequested); notifyInferiorShutdownFailed(); break; } case InferiorShutdownOk: { if (state() == InferiorShutdownRequested) { notifyInferiorShutdownOk(); } else { // we got InferiorExitOk before, but ignored it ... notifyInferiorExited(); } break; } case EngineShutdownRequested: { // set by queueShutdownEngine() CHECK_STATE(EngineShutdownRequested); break; } case EngineShutdownFailed: { CHECK_STATE(EngineShutdownRequested); notifyEngineShutdownFailed(); break; } case EngineShutdownOk: { CHECK_STATE(EngineShutdownRequested); notifyEngineShutdownOk(); break; } case DebuggerFinished: { // set by queueFinishDebugger() CHECK_STATE(DebuggerFinished); break; } } } else { // QML engine state change if (newState == InferiorStopOk) { if (isDying()) { EDEBUG("... QML ENGINE STOPPED DURING SHUTDOWN "); // Just to make sure, we're shutting down anyway ... setActiveEngine(m_cppEngine); if (state() == InferiorStopRequested) notifyInferiorStopOk(); // otherwise we're probably inside notifyInferiorStopOk already } else { if (m_activeEngine != qmlEngine()) { showStatusMessage(tr("QML debugger activated")); setActiveEngine(m_qmlEngine); } if (state() == InferiorRunOk) notifyInferiorSpontaneousStop(); else if (state() == InferiorStopRequested) notifyInferiorStopOk(); else CHECK_STATE(InferiorShutdownRequested); } } else if (newState == InferiorRunOk) { if (m_activeEngine == qmlEngine()) { CHECK_STATE(InferiorRunRequested); notifyInferiorRunOk(); } } } }