Esempio n. 1
0
void MIFrameStackModel::handleThreadInfo(const ResultRecord& r)
{
    const Value& threads = r["threads"];

    // Traverse GDB threads in backward order -- since GDB
    // reports them in backward order. We want UI to
    // show thread IDs in the natural order.
    // FIXME: at least GDB 7.11 is reporting in the right order,
    // consider sort the list afterwards.

    QList<KDevelop::FrameStackModel::ThreadItem> threadsList;
    int gidx = threads.size()-1;
    for (; gidx >= 0; --gidx) {
        KDevelop::FrameStackModel::ThreadItem i;
        const Value & threadMI = threads[gidx];
        i.nr = threadMI["id"].toInt();
        if (threadMI["state"].literal() == "stopped") {
            i.name = getFunctionOrAddress(threads[gidx]["frame"]);
        } else {
            i.name = i18n("(running)");
        }
        threadsList << i;
    }
    setThreads(threadsList);
    if (r.hasField("current-thread-id")) {
        int currentThreadId = r["current-thread-id"].toInt();

        setCurrentThread(currentThreadId);

        if (session()->hasCrashed()) {
            setCrashedThreadIndex(currentThreadId);
        }
    }
}
Esempio n. 2
0
void MIFrameStackModel::handleThreadInfo(const ResultRecord& r)
{
    const Value& threads = r["threads"];

    QList<FrameStackModel::ThreadItem> threadsList;
    for (int i = 0; i!= threads.size(); ++i) {
        const auto &threadMI = threads[i];
        FrameStackModel::ThreadItem threadItem;
        threadItem.nr = threadMI["id"].toInt();
        if (threadMI["state"].literal() == "stopped") {
            threadItem.name = getFunctionOrAddress(threadMI["frame"]);
        } else {
            i18n("(running)");
        }
        threadsList << threadItem;
    }
    // Sort the list by id, some old version of GDB
    // reports them in backward order. We want UI to
    // show thread IDs in the natural order.
    std::sort(threadsList.begin(), threadsList.end(),
              [](const FrameStackModel::ThreadItem &a, const FrameStackModel::ThreadItem &b){
                  return a.nr < b.nr;
              });

    setThreads(threadsList);
    if (r.hasField("current-thread-id")) {
        int currentThreadId = r["current-thread-id"].toInt();

        setCurrentThread(currentThreadId);

        if (session()->hasCrashed()) {
            setCrashedThreadIndex(currentThreadId);
        }
    }
}
Esempio n. 3
0
    void handle(const ResultRecord &r) override
    {
        if (!m_variable) return;
        --m_activeCommands;

        MIVariable* variable = m_variable.data();

        if (r.hasField("children"))
        {
            const Value& children = r["children"];
            for (int i = 0; i < children.size(); ++i) {
                const Value& child = children[i];
                const QString& exp = child["exp"].literal();
                if (exp == "public" || exp == "protected" || exp == "private") {
                    ++m_activeCommands;
                    m_session->addCommand(VarListChildren,
                                          QString("--all-values \"%1\"").arg(child["name"].literal()),
                                          this/*use again as handler*/);
                } else {
                    variable->createChild(child);
                    // it's automatically appended to variable's children list
                }
            }
        }

        /* Note that we don't set hasMore to true if there are still active
           commands. The reason is that we don't want the user to have
           even theoretical ability to click on "..." item and confuse
           us.  */
        bool hasMore = false;
        if (r.hasField("has_more"))
            hasMore = r["has_more"].toInt();

        variable->setHasMore(hasMore);
        if (m_activeCommands == 0) {
            variable->emitAllChildrenFetched();
            delete this;
        }
    }
Esempio n. 4
0
    void handle(const ResultRecord &r) override
    {
        if (!m_variable) return;
        bool hasValue = false;
        MIVariable* variable = m_variable.data();
        variable->deleteChildren();
        variable->setInScope(true);
        if (r.reason == "error") {
            variable->setShowError(true);
        } else {
            variable->setVarobj(r["name"].literal());

            bool hasMore = false;
            if (r.hasField("has_more") && r["has_more"].toInt())
                // GDB swears there are more children. Trust it
                hasMore = true;
            else
                // There are no more children in addition to what
                // numchild reports. But, in KDevelop, the variable
                // is not yet expanded, and those numchild are not
                // fetched yet. So, if numchild != 0, hasMore should
                // be true.
                hasMore = r["numchild"].toInt() != 0;

            variable->setHasMore(hasMore);

            variable->setType(r["type"].literal());
            variable->setValue(variable->formatValue(r["value"].literal()));
            hasValue = !r["value"].literal().isEmpty();
            if (variable->isExpanded() && r["numchild"].toInt()) {
                variable->fetchMoreChildren();
            }

            if (variable->format() != KDevelop::Variable::Natural) {
                //TODO doesn't work for children as they are not yet loaded
                variable->formatChanged();
            }
        }

        if (m_callback && m_callbackMethod) {
            QMetaObject::invokeMethod(m_callback, m_callbackMethod, Q_ARG(bool, hasValue));
        }
    }
Esempio n. 5
0
void LldbFrameStackModel::handleThreadInfo(const ResultRecord& r)
{
    const Value& threads = r["threads"];

    QList<FrameStackModel::ThreadItem> threadsList;
    for (int gidx = 0; gidx != threads.size(); ++gidx) {
        FrameStackModel::ThreadItem i;
        const Value & threadMI = threads[gidx];
        i.nr = threadMI["id"].toInt();
        if (threadMI["state"].literal() == "stopped") {
            // lldb-mi returns multiple frame entry for each thread
            // so can't directly use threadMI["frame"]
            auto &th = dynamic_cast<const TupleValue&>(threadMI);
            Value *topFrame = nullptr;
            for (auto res : th.results) {
                if (res->variable == "frame") {
                    if (!topFrame || (*res->value)["level"].toInt() < (*topFrame)["level"].toInt()) {
                        topFrame = res->value;
                    }
                }
            }
            i.name = getFunctionOrAddress(*topFrame);
        } else {
            i.name = i18n("(running)");
        }
        threadsList << i;
    }
    setThreads(threadsList);
    if (r.hasField("current-thread-id")) {
        int currentThreadId = r["current-thread-id"].toInt();

        setCurrentThread(currentThreadId);

        if (session()->hasCrashed()) {
            setCrashedThreadIndex(currentThreadId);
        }
    }
    // lldb-mi doesn't have current-thread-id field. Use the thread-id field when inferiorStopped
    if (stoppedAtThread != -1) {
        setCurrentThread(stoppedAtThread);
    }
    stoppedAtThread = -1;
}
Esempio n. 6
0
 void handle(const ResultRecord &r) override
 {
     if(m_variable && r.hasField("value"))
         m_variable->setValue(m_variable->formatValue(r["value"].literal()));
 }