[Lazarus] triggered by the frontend / Representation of an "watch" [[was: Re: Playing with debuggers]]
Martin Frb
lazarus at mfriebe.de
Sun Nov 21 17:23:59 CET 2021
> 1) Events to be more frontend centric.
> 2) Actions (eval watch) to be triggered by the frontend
> 3) Representation of an "watch" (Should methods be on the Watch
> object, or the Debugger object)
=====> 2) Actions (eval watch) to be triggered by the frontend
The evaluation of a watch is triggered when the frontend attempts to
access it. The backend then gets a call to
TWatchesSupplier.InternalRequestData(AWatchValue: TWatchValue)
for that one watch.
For all I can see neither gdb, nor Fp backends will evaluate any watch,
unless the frontend asks.
=====> 3) Representation of an "watch" (Should methods be on the Watch
object, or the Debugger object)
You introduced a new method to get a watch value.
Debugger.EvaluateExpression(S, Debugger.GetCurrentFrameID,
FLatestRef, @EvaluateCallback)
and then in the callback the data is in an object:
TLazDebugExtensionVariable
TLazDebugExtensionVariable has a reference, where the debugger can store
any data it wants: integer or object
I am trying to see, what advantage this should bring over the current
system:
* TIdeWatch / TCurrentWatch
=> those can nicely store all the data a frontend needs to store with
the watch (any options the user did chose).
=> this also stores (as TWatchValue) the result returned from the
debugger.
=> Each frontend can subclass it as it wants.
* The frontend decides when it wants the data. The backend then receives
a single call for this/each watch.
* The backend then send a notification for the frontend, when the data
is there.
Same flow? Main difference is that the methods to invoke the evaluation
are on the TWatch.
--------------
So far so good.
- The TWatch class is currently quite big. It might benefit from some
cut down, but that is not related to any of the things you implemented.
- An advantage is, that a watch eval can be aborted.
Your concept is to discard unwanted results, but the backend still
spends time on evaluating it. Of course you could add
dbg.AbortEval(reference);
In the end, I prefer to encapsulate this into the TWatch.
- Watches are stored in a list.
That is needed by the frontend. Because the History wants to know about
the watches.
However, this may not be needed by the backend. That can be reviewed.
--------------
Collapsing / Expanding
Currently watches can only be added by the frontend. That may need to be
changed.
Each watch needs a way to ask the debugger for the TWatchValue data of
its children.
=> For that the Watch could call the backend
dbg.GetChildren(self);
=> The backend would then for each child call
watch.GetChildWatch
and the backend would put the data in.
Something like that.....
As for the TWatches list:
The watch window would know, which watches are visible (expanded) and
evaluate them.
For the history, each watch could have a "parent" and/or
"CurrentVisible" field. Or the watch has an "Owner" (the window), which
can be asked.
On 14/09/2021 16:11, Joost van der Sluis via lazarus wrote:
> The big advantage of the tree-view, is that you do not evaluate
> sub-watches, only when they have to be shown. So only those fields
> that need to be shown have to be evaluated by gdb. (It also solves the
> endless loop you sometimes have)
Well at latest when the debugger is idle, evaluation of watches "not
scrolled in" should start.
So when the user starts scrolling, values can be shown immediately.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.lazarus-ide.org/pipermail/lazarus/attachments/20211121/5d77d122/attachment.html>
More information about the lazarus
mailing list