You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Report struct/union/array members in -var-update response
Fixes#25.
Before this commit, when LLDB-MI would get a -var-update request for a
complex variable (struct, union, array), it would analyze if value
changed and if it is, then it would return a changelist for this this
value only, which in case of struct and unions means `{...}`. Child
member value were not reported even when changed - MI client would need
to request them individually. This is different from GDB behavior, where
complex object is not reported at all, but child values are reported.
This was causing troubles for Eclipse Variables view which was written
under assumption that -var-update for a complex variable returns
changelist for all children - as a result values of struct fields were
not updated when changed, view continued to show obsolete value.
The fix is complicated by the fact that response should include children
only if they have been listed with -var-list-children. What is more,
according to GDB MI docs [1] range specified to -var-list-children
shouldn't affect -var-update, instead -var-set-update-range should be
used to specify range of children to be reported in -var-update
response, however LLDB-MI doesn't support the -var-set-update-range
request at all - so instead this commit implementation relies on
-var-list-children. It is also not clear how to efficiently identify
which children have been listed and which not - complex var objects
don't contain links to children, instead they exist in a flat namespace,
where children-parent relationship is established through a name.
Therefore in this commit child will be added to the changelist if it's
value changed and there is an existing var object with the same name.
Probably it would be faster to iterate through known var objects and
compare their names with a name of a root object, but
CMICmnLLDBDebugSessionInfoVarObj doesn't provide an interface to iterate
through objects and changing this class was out of scope for my fix -
fix relies only on existing public functions.
Additional noticable problem is recursion, if children objects contain a
pointer to the parent object, however LLDB-MI doesn't has to stop it
itself. A user may "open up" loop of parent/children in the
infinite fashion as much as they want - LLDB-MI and Eclipse GUI would
just print as many nested levels as needed. Note that
CMICmdCmdVarUpdate::ExamineSBValueForChange explicitly halts on pointers
and references, because it scans through SBValue children and doesn't
know which children will be printed or not - structure with unlisted
children still will be reported as one that changed its value.
The one case where this code still doesn't work, if we had construct
like
struct S { int i; }
struct S s = { 1 };
struct S *ps = NULL;
Then a variable will be created for ps->i, and because ps is NULL, that
variable will have a printed value of `??`. If later application does
ps = &s;
Then ps->i will effectively change its value, but this will not be
reported in the changelist, because SBValue::GetValueDidChange() returns
false for this value. Apparantly change from "invalid" value to a valid
one is not considered a "value change" in API, but this disagreese how
this should be represented in the Eclipse GUI. The only way to fix this
in MI, I think is to compare "old" and "new" string value in MI, which
means need to store old string value - and that is not very effective,
so I don't want to try to fix this problem in this commit. As far as I
observe this is specific to cases with NULL pointer, if pointer was
pointing to a valid structure, than started to point to another -
changes in children values will be properly reported by SBValue, and
this will make their way into the changelist.
[1] https://sourceware.org/gdb/onlinedocs/gdb/GDB_002fMI-Variable-Objects.html#The-_002dvar_002dlist_002dchildren-Command
0 commit comments