diff --git a/src/plugins/debugger/debuggeractions.cpp b/src/plugins/debugger/debuggeractions.cpp index 520f6ee4b5ba7e79683f99bc66dc495fb8028e52..8a0eba727c50fe84956657131854c7d6932a842f 100644 --- a/src/plugins/debugger/debuggeractions.cpp +++ b/src/plugins/debugger/debuggeractions.cpp @@ -265,6 +265,14 @@ DebuggerSettings *DebuggerSettings::instance() item->setValue(true); instance->insertItem(ShowQtNamespace, item); + item = new SavedAction(instance); + item->setSettingsKey(debugModeGroup, QLatin1String("SortStructMembers")); + item->setText(tr("Sort Members of Classes and Structs Alphabetically")); + item->setCheckable(true); + item->setDefaultValue(true); + item->setValue(true); + instance->insertItem(SortStructMembers, item); + // // DebuggingHelper // diff --git a/src/plugins/debugger/debuggeractions.h b/src/plugins/debugger/debuggeractions.h index 0303c10bcb18cf1e7260dfa446e65c7cee839e4e..6fd56fb64faf085b45417e260060d41fb3bd1e8c 100644 --- a/src/plugins/debugger/debuggeractions.h +++ b/src/plugins/debugger/debuggeractions.h @@ -125,6 +125,7 @@ enum DebuggerActionCode // Watchers & Locals ShowStdNamespace, ShowQtNamespace, + SortStructMembers, // Source List ListSourceFiles, diff --git a/src/plugins/debugger/debuggerplugin.cpp b/src/plugins/debugger/debuggerplugin.cpp index 2e0ea359f4b31d5ccaf04a06586acb91162e54b9..ed6e86372278737de1a11c80271edc408c5c7f49 100644 --- a/src/plugins/debugger/debuggerplugin.cpp +++ b/src/plugins/debugger/debuggerplugin.cpp @@ -569,6 +569,7 @@ QWidget *CommonOptionsPage::createPage(QWidget *parent) m_ui.spinBoxMaximalStackDepth); m_group.insert(theDebuggerAction(ShowStdNamespace), 0); m_group.insert(theDebuggerAction(ShowQtNamespace), 0); + m_group.insert(theDebuggerAction(SortStructMembers), 0); m_group.insert(theDebuggerAction(LogTimeStamps), 0); m_group.insert(theDebuggerAction(VerboseLog), 0); m_group.insert(theDebuggerAction(UsePreciseBreakpoints), 0); @@ -2347,6 +2348,7 @@ void DebuggerPluginPrivate::updateState(DebuggerEngine *engine) const bool canDeref = actionsEnabled && (m_capabilities & AutoDerefPointersCapability); theDebuggerAction(AutoDerefPointers)->setEnabled(canDeref); + theDebuggerAction(AutoDerefPointers)->setEnabled(true); theDebuggerAction(ExpandStack)->setEnabled(actionsEnabled); theDebuggerAction(ExecuteCommand)->setEnabled(m_state == InferiorStopOk); diff --git a/src/plugins/debugger/gdb/classicgdbengine.cpp b/src/plugins/debugger/gdb/classicgdbengine.cpp index b199254c9f7fcc43026a1b5ac0fa0a74678a31e5..16d3a2685520156eb77e87c4e89cb03cff64d4c0 100644 --- a/src/plugins/debugger/gdb/classicgdbengine.cpp +++ b/src/plugins/debugger/gdb/classicgdbengine.cpp @@ -426,7 +426,9 @@ void GdbEngine::handleDebuggingHelperValue2Classic(const GdbResponse &response) setWatchDataDisplayedType(data, response.data.findChild("displaytype")); QList<WatchData> list; parseWatchData(watchHandler()->expandedINames(), - data, contents, &list); + data, contents, + theDebuggerBoolSetting(SortStructMembers), + &list); //for (int i = 0; i != list.size(); ++i) // qDebug() << "READ: " << list.at(i).toString(); watchHandler()->insertBulkData(list); diff --git a/src/plugins/debugger/gdb/gdbengine.cpp b/src/plugins/debugger/gdb/gdbengine.cpp index 29e7d7f22abf9615d4f4a3fbb5726e851cbfb51c..9782d8319d3ac53ac057716007b4e278aa123811 100644 --- a/src/plugins/debugger/gdb/gdbengine.cpp +++ b/src/plugins/debugger/gdb/gdbengine.cpp @@ -191,9 +191,11 @@ GdbEngine::GdbEngine(const DebuggerStartParameters &startParameters) m_gdbAdapter = createAdapter(); connect(theDebuggerAction(AutoDerefPointers), SIGNAL(valueChanged(QVariant)), - this, SLOT(setAutoDerefPointers(QVariant))); + SLOT(reloadLocals())); + connect(theDebuggerAction(SortStructMembers), SIGNAL(valueChanged(QVariant)), + SLOT(reloadLocals())); connect(theDebuggerAction(CreateFullBacktrace), SIGNAL(triggered()), - this, SLOT(createFullBacktrace())); + SLOT(createFullBacktrace())); } DebuggerStartMode GdbEngine::startMode() const @@ -3342,9 +3344,8 @@ void GdbEngine::setToolTipExpression(const QPoint &mousePos, // ////////////////////////////////////////////////////////////////////// -void GdbEngine::setAutoDerefPointers(const QVariant &on) +void GdbEngine::reloadLocals() { - Q_UNUSED(on) setTokenBarrier(); updateLocals(); } diff --git a/src/plugins/debugger/gdb/gdbengine.h b/src/plugins/debugger/gdb/gdbengine.h index 3e0f77e87db78815321a20fad3fddbfeb52cc46b..817ec77672df266e4afb0308ca2eb914d780ee36 100644 --- a/src/plugins/debugger/gdb/gdbengine.h +++ b/src/plugins/debugger/gdb/gdbengine.h @@ -122,7 +122,7 @@ private: ////////// General State ////////// void initializeVariables(); DebuggerStartMode startMode() const; - Q_SLOT void setAutoDerefPointers(const QVariant &on); + Q_SLOT void reloadLocals(); bool m_registerNamesListed; diff --git a/src/plugins/debugger/gdb/pythongdbengine.cpp b/src/plugins/debugger/gdb/pythongdbengine.cpp index b55c5e5d25a454384f99f9bb4d8b457839fbfecb..20e068869855b9bc8f09cbd270e10677fa246ad0 100644 --- a/src/plugins/debugger/gdb/pythongdbengine.cpp +++ b/src/plugins/debugger/gdb/pythongdbengine.cpp @@ -133,12 +133,14 @@ void GdbEngine::handleStackFramePython(const GdbResponse &response) GdbMi data = all.findChild("data"); QList<WatchData> list; + const bool sortMembers = theDebuggerBoolSetting(SortStructMembers); foreach (const GdbMi &child, data.children()) { WatchData dummy; dummy.iname = child.findChild("iname").data(); dummy.name = _(child.findChild("name").data()); //qDebug() << "CHILD: " << child.toString(); - parseWatchData(watchHandler()->expandedINames(), dummy, child, &list); + parseWatchData(watchHandler()->expandedINames(), dummy, child, + sortMembers, &list); } watchHandler()->insertBulkData(list); //for (int i = 0; i != list.size(); ++i) diff --git a/src/plugins/debugger/pdb/pdbengine.cpp b/src/plugins/debugger/pdb/pdbengine.cpp index db8ea433281bfaca3bff5bf014fb947e7bdfe55c..70fa64043db543b77d394e9525f3d6453633f5fe 100644 --- a/src/plugins/debugger/pdb/pdbengine.cpp +++ b/src/plugins/debugger/pdb/pdbengine.cpp @@ -827,12 +827,13 @@ void PdbEngine::handleListLocals(const PdbResponse &response) //GdbMi data = all.findChild("data"); QList<WatchData> list; WatchHandler *handler = watchHandler(); + bool sortMembers = theDebuggerBoolSetting(SortStructMembers); foreach (const GdbMi &child, all.children()) { WatchData dummy; dummy.iname = child.findChild("iname").data(); dummy.name = _(child.findChild("name").data()); //qDebug() << "CHILD: " << child.toString(); - parseWatchData(handler->expandedINames(), dummy, child, &list); + parseWatchData(handler->expandedINames(), dummy, child, sortMembers, &list); } handler->insertBulkData(list); } diff --git a/src/plugins/debugger/watchhandler.cpp b/src/plugins/debugger/watchhandler.cpp index 80a9a71fba42d8d895631391b17a8b56d4beb129..4f3104a99429b02c0f065e0ca0d4b5378b2df231 100644 --- a/src/plugins/debugger/watchhandler.cpp +++ b/src/plugins/debugger/watchhandler.cpp @@ -1206,6 +1206,8 @@ WatchHandler::WatchHandler(DebuggerEngine *engine) SIGNAL(triggered()), this, SLOT(emitAllChanged())); connect(theDebuggerAction(ShowQtNamespace), SIGNAL(triggered()), this, SLOT(emitAllChanged())); + connect(theDebuggerAction(SortStructMembers), + SIGNAL(triggered()), this, SLOT(emitAllChanged())); } void WatchHandler::beginCycle(bool fullCycle) diff --git a/src/plugins/debugger/watchutils.cpp b/src/plugins/debugger/watchutils.cpp index 515e7c5fe63a7d3e7a1b3b9a0859ddf2e39f5e5f..3e89ea9fafa94287fb9dd8b61d7901c6874c6cd0 100644 --- a/src/plugins/debugger/watchutils.cpp +++ b/src/plugins/debugger/watchutils.cpp @@ -1498,7 +1498,9 @@ static void gbdMiToWatchData(const GdbMi &root, } } if (w.name.isEmpty()) { - const QString msg = QString::fromLatin1("Internal error: Unable to determine name at level %1/%2 for %3").arg(ctx.recursionLevel).arg(w.iname, QLatin1String(root.toString(true, 2))); + const QString msg = QString::fromLatin1( + "Internal error: Unable to determine name at level %1/%2 for %3") + .arg(ctx.recursionLevel).arg(w.iname, QLatin1String(root.toString(true, 2))); qWarning("%s\n", qPrintable(msg)); } gdbMiGetStringValue(&w.displayedType, root, "displayedtype"); @@ -1551,14 +1553,13 @@ static void gbdMiToWatchData(const GdbMi &root, gdbMiGetStringValue(&nextLevelContext.childType, root, "childtype"); if (!gdbMiGetIntValue(&nextLevelContext.childNumChild, root, "childnumchild")) nextLevelContext.childNumChild = -1; - foreach(const GdbMi &child, children) { + foreach (const GdbMi &child, children) { gbdMiToWatchData(child, nextLevelContext, wl); nextLevelContext.childIndex++; } } -bool QtDumperHelper::parseValue(const char *data, - QList<WatchData> *l) +bool QtDumperHelper::parseValue(const char *data, QList<WatchData> *l) { l->clear(); GdbMi root; @@ -1664,7 +1665,8 @@ void setWatchDataDisplayedType(WatchData &data, const GdbMi &item) } void parseWatchData(const QSet<QByteArray> &expandedINames, - const WatchData &data0, const GdbMi &item, QList<WatchData> *list) + const WatchData &data0, const GdbMi &item, + bool sortMembers, QList<WatchData> *list) { //qDebug() << "HANDLE CHILDREN: " << data0.toString() << item.toString(); WatchData data = data0; @@ -1715,10 +1717,18 @@ void parseWatchData(const QSet<QByteArray> &expandedINames, else data1.name = QString::number(i); GdbMi iname = child.findChild("iname"); - if (iname.isValid()) + if (iname.isValid()) { data1.iname = iname.data(); - else - data1.iname = data.iname + '.' + data1.name.toLatin1(); + } else { + data1.iname = data.iname; + data1.iname += '.'; + if (!sortMembers) { + char buf[10]; + qsnprintf(buf, sizeof(buf) - 1, "%04d", i); + data1.iname += buf; + } + data1.iname += data1.name.toLatin1(); + } if (!data1.name.isEmpty() && data1.name.at(0).isDigit()) data1.name = _c('[') + data1.name + _c(']'); if (addressStep) { @@ -1737,7 +1747,7 @@ void parseWatchData(const QSet<QByteArray> &expandedINames, //data1.name += " (" + skey + ")"; data1.name = skey; } - parseWatchData(expandedINames, data1, child, list); + parseWatchData(expandedINames, data1, child, sortMembers, list); ++i; } } diff --git a/src/plugins/debugger/watchutils.h b/src/plugins/debugger/watchutils.h index e1da61a37ab109796aae844402e9a86dfb329177..61d3aa4c7fc19e5c0316ed26472391298a62720d 100644 --- a/src/plugins/debugger/watchutils.h +++ b/src/plugins/debugger/watchutils.h @@ -257,7 +257,7 @@ void setWatchDataType(WatchData &data, const GdbMi &mi); void setWatchDataDisplayedType(WatchData &data, const GdbMi &mi); void parseWatchData(const QSet<QByteArray> &expandedINames, - const WatchData &parent, const GdbMi &child, + const WatchData &parent, const GdbMi &child, bool sortMembers, QList<WatchData> *insertions); } // namespace Internal diff --git a/src/plugins/debugger/watchwindow.cpp b/src/plugins/debugger/watchwindow.cpp index 408c89c58b14fc5aa99886079c28c045aa2e189d..f459d2c35d519c4551090d4856a81a3018ecafb9 100644 --- a/src/plugins/debugger/watchwindow.cpp +++ b/src/plugins/debugger/watchwindow.cpp @@ -415,6 +415,7 @@ void WatchWindow::contextMenuEvent(QContextMenuEvent *ev) menu.addAction(theDebuggerAction(AutoDerefPointers)); menu.addAction(theDebuggerAction(ShowStdNamespace)); menu.addAction(theDebuggerAction(ShowQtNamespace)); + menu.addAction(theDebuggerAction(SortStructMembers)); QAction *actAdjustColumnWidths = menu.addAction(tr("Adjust Column Widths to Contents"));