[lldb-dev] logging in lldb

Pavel Labath via lldb-dev lldb-dev at lists.llvm.org
Wed Dec 7 09:03:36 PST 2016


Sorry, I have been derailed today by trying to make format member
detection work more reasonably. I plan to come up with the next
iteration of the proposal soon, but I am not sure if it will be today,
as it is quite late here already. I do think this needs to be done in
incremental steps, but I'd like to make the iterations slightly bigger
to avoid code churn.

pl

On 7 December 2016 at 16:56, Zachary Turner <zturner at google.com> wrote:
> Pavel: You might start this effort to improve logging by just adding a
> Formatv member function to log to replace printf.
>
> I suspect many call sites would be made much less verbose this way. I think
> we'll still need to do the rest too, but this seems like the least amount of
> work to make incremental progress
> On Tue, Dec 6, 2016 at 11:13 AM Zachary Turner <zturner at google.com> wrote:
>>
>> On Tue, Dec 6, 2016 at 10:31 AM Greg Clayton <gclayton at apple.com> wrote:
>>>
>>>
>>>
>>>
>>> It should be a formatter option for collections to allow you to print out
>>> different ranges. If I have a target and a target knows how to print the
>>> process and the process knows how to print the threads and the threads know
>>> how to print the stack frames, it doesn't mean I always want to see
>>> everything. Sounds like we can easily control this in the llvm::formatv case
>>> with extra formatting options:
>>>
>>> This might print just a summary of the target:
>>>
>>> llvm::formatv("{0}", target);
>>>
>>> This might print the target and info about the process:
>>>
>>> llvm::formatv("{0;process}", target);
>>>
>>> The question becomes, can we then forward arguments into the "Process"
>>> logger to control if the threads are displayed?
>>>
>>> llvm::formatv("{0;process{threads{frames}}}", target);
>>>
>>> This would allow recursive formatters to be called with specified
>>> arguments. Just a thought, but if we are going to delve into recursive
>>> formatters, we might need to think about that.
>>
>>
>> A formatter can literally do anything with the style string.  So for
>> example, suppose you have formatters defined for Process and Thread.  each
>> of these ultimately boils down to a function:
>>
>> void format(llvm::raw_ostream &Out, const Process &P, StringRef Style);
>> void format(llvm::raw_ostream &Out, const Thread &P, StringRef Style);
>>
>> We implement each of these, so Process can define its own Style language,
>> as can Target, as can Thread.  We can come up with something better than
>> this, but say for the sake of illustration Thread's style string worked like
>> this: If empty, print thread id, otherwise treat each alphabetic character
>> as representing a "code" of what to print.  P = process, T = thread id, N =
>> thread name.  So "P - T - N" would print the process id, then the thread id,
>> then the thread name, separated by dashes.
>>
>> Now suppose you want to print a process.  If style string is empty, it
>> prints only the process id, otherwise if it equals T then it prints the
>> first thread, or if it equals T* it prints all threads.  T or T* can
>> optionally be followed by arguments to forward to the thread in square
>> brackets.  So you could have:
>>
>> formatv("Process {0;P - T*[N]}", process);
>>
>> There's obviously a balance between flexibility and conciseness, but I
>> guess that's no different than C++.  It's as flexible as you could possibly
>> need, sometimes to the point of allowing you to make bad design decisions :)
>>
>> In the beginning probably best to just define some simple formatters that
>> don't do anything recursive, and then some obvious patterns might start to
>> fall out and we can refine the styles we support for all of the various LLDB
>> types.


More information about the lldb-dev mailing list