diff --git a/share/qtcreator/debugger/cdbbridge.py b/share/qtcreator/debugger/cdbbridge.py index 16ec84c5cac..07a3814b6bb 100644 --- a/share/qtcreator/debugger/cdbbridge.py +++ b/share/qtcreator/debugger/cdbbridge.py @@ -267,11 +267,9 @@ class Dumper(DumperBase): self.anonNumber = 0 variables = [] - for val in cdbext.listOfLocals(): - self.currentContextValue = val - name = val.name() + for val in cdbext.listOfLocals(self.partialVariable): value = self.fromNativeValue(val) - value.name = name + value.name = val.name() variables.append(value) self.handleLocals(variables) diff --git a/src/libs/qtcreatorcdbext/pycdbextmodule.cpp b/src/libs/qtcreatorcdbext/pycdbextmodule.cpp index 63ab6f60701..5a4dbfc436c 100644 --- a/src/libs/qtcreatorcdbext/pycdbextmodule.cpp +++ b/src/libs/qtcreatorcdbext/pycdbextmodule.cpp @@ -105,18 +105,47 @@ static PyObject *cdbext_lookupType(PyObject *, PyObject *args) // -> Type return lookupType(type); } -static PyObject *cdbext_listOfLocals(PyObject *, PyObject *) // -> [ Value ] +static PyObject *cdbext_listOfLocals(PyObject *, PyObject *args) // -> [ Value ] { + char *partialVariablesC; + if (!PyArg_ParseTuple(args, "s", &partialVariablesC)) + Py_RETURN_NONE; + + const std::string partialVariable(partialVariablesC); + IDebugSymbolGroup2 *symbolGroup = nullptr; auto locals = PyList_New(0); - IDebugSymbolGroup2 *sg; - CIDebugSymbols *symbols = ExtensionCommandContext::instance()->symbols(); - if (FAILED(symbols->GetScopeSymbolGroup2(DEBUG_SCOPE_GROUP_ALL, NULL, &sg))) - return locals; + if (partialVariable.empty()) { + symbolGroup = currentSymbolGroup.create(); + if (symbolGroup == nullptr) + return locals; + } else { + symbolGroup = currentSymbolGroup.get(); + if (symbolGroup == nullptr) + return locals; + + ULONG scopeEnd; + if (FAILED(symbolGroup->GetNumberSymbols(&scopeEnd))) + return locals; + + std::vector inameTokens; + split(partialVariable, '.', std::back_inserter(inameTokens)); + auto currentPartialIname = inameTokens.begin(); + ++currentPartialIname; // skip "local" part + + ULONG symbolGroupIndex = 0; + for (;symbolGroupIndex < scopeEnd; ++symbolGroupIndex) { + if (getSymbolName(symbolGroup, symbolGroupIndex) == *currentPartialIname) { + PyList_Append(locals, createValue(symbolGroupIndex, symbolGroup)); + return locals; + } + } + } + ULONG symbolCount; - if (FAILED(sg->GetNumberSymbols(&symbolCount))) + if (FAILED(symbolGroup->GetNumberSymbols(&symbolCount))) return locals; for (ULONG index = 0; index < symbolCount; ++index) - PyList_Append(locals, createValue(index, sg)); + PyList_Append(locals, createValue(index, symbolGroup)); return locals; } @@ -196,7 +225,7 @@ static PyMethodDef cdbextMethods[] = { "Returns value of expression or None if the expression can not be resolved"}, {"lookupType", cdbext_lookupType, METH_VARARGS, "Returns type object or None if the type can not be resolved"}, - {"listOfLocals", cdbext_listOfLocals, METH_NOARGS, + {"listOfLocals", cdbext_listOfLocals, METH_VARARGS, "Returns list of values that are currently in scope"}, {"pointerSize", cdbext_pointerSize, METH_NOARGS, "Returns the size of a pointer"}, diff --git a/src/libs/qtcreatorcdbext/pyvalue.h b/src/libs/qtcreatorcdbext/pyvalue.h index e7aac4e29fe..15236d3e9fc 100644 --- a/src/libs/qtcreatorcdbext/pyvalue.h +++ b/src/libs/qtcreatorcdbext/pyvalue.h @@ -41,3 +41,4 @@ struct Value PyTypeObject *value_pytype(); void initValue(Value *value); PyObject *createValue(ULONG index, CIDebugSymbolGroup *symbolGroup); +std::string getSymbolName(CIDebugSymbolGroup *sg, ULONG index);