[lldb-dev] Printing non-truncated stdlib collections?

Dun Peal dunpealer at gmail.com
Wed Nov 6 09:21:15 PST 2013


I have filed a bug about the last issue I mentioned in this thread, the one
manifesting in "error: Couldn't materialize struct: size of variable rects
disagrees with the ValueObject's size".

I hope to be able to use LLDB in the future, it looks like it has a lot of
potential!

Thanks, D.


On Mon, Nov 4, 2013 at 4:24 PM, Dun Peal <dunpealer at gmail.com> wrote:

> Great, `frame variable vec[0]` works, although it still manifests the bug
> I reported, showing the vector size to be 4294967295 when it's actually 4.
>
> One final question in this kitchensink thread: I get
>
> (lldb) p rects
> error: Couldn't materialize struct: size of variable rects disagrees with
> the ValueObject's size
> Errored out in Execute, couldn't PrepareToExecuteJITExpression
>
> On line 14 of the following code snippet (commented). Why is that?​
>
>
> #include <iostream>
> #include <vector>
>
> using namespace std;
> typedef pair<int, int> Rect;
> typedef vector<Rect> Rects;
>
> static int all_permutations(Rects rects) {
>     for (Rects::iterator rect_it = rects.begin(); rect_it != rects.end();
> ++rect_it) {
>         cout << rect_it->first << ' ' << rect_it->second << endl;
>     }
>     return 0;  // break here, `p rects` in lldb
> }
>
> int main() {
>     Rects rects;
>     for (int i=0; i < 4; ++i) {
>         Rect rect = make_pair(i, i+1);
>         rects.push_back(rect);
>     }
>     all_permutations(rects);
>     return 0;
> }
>
> On Mon, Nov 4, 2013 at 4:00 PM, Enrico Granata <egranata at apple.com> wrote:
>
>> This one is not an issue. It's by design.
>>
>> ​​
>> Solution: try
>>
>> (lldb) frame variable vec[0]
>>
>> Explanation: the expression command is using the compiler, clang, to
>> generate code that runs in your inferior process. This requires the
>> operator[] defined by your implementation of the STL to be around. If that
>> is nowhere suitable to be find in the debug info (e.g. You never used it in
>> your code) that expression will not be compilable since essentially it is
>> as-if no vector::operator[] existed at all.
>> The way in which children in a vector are generated is totally unrelated
>> to this. LLDB knows enough about the internals of the std::vector class to
>> generate child variables as-if they were being accessed by indexing, but
>> all without running code in your process. They are called "synthetic
>> children" and are a debugger artifact essentially. Which is why sometimes
>> we get it wrong: since we are not relying on anything but introspecting
>> memory, we are more easily "fooled".
>> Our expression parser explicitly disallows such synthetic children for
>> kicking in. Imagine if they did. Now your operator[] would not be invoked
>> because the synthetic children feature would kick in and return a result.
>> But what if you said
>>
>> (lldb) expr vec[0] = 1
>>
>> The synthetic children are a snapshot of memory so they don't know how to
>> assign back to themselves. Hence why you don't want expressions to mix with
>> synthetic children. It's a tricky business to get right.
>>
>>
>> Sent from the iPhone of
>> *Enrico Granata* <egranata@🍎.com>
>>
>> On Nov 4, 2013, at 3:47 PM, Dun Peal <dunpealer at gmail.com> wrote:
>>
>> OK, I posted the original question of this thread as the following bug:
>> http://llvm.org/bugs/show_bug.cgi?id=17805
>>
>> Another issue I just stumbled across:
>>
>> (lldb) p vec[0]
>> error: call to a function 'std::vector<std::vector<std::pair<int, int>,
>> std::allocator<std::pair<int, int> > >,
>> std::allocator<std::vector<std::pair<int, int>,
>> std::allocator<std::pair<int, int> > > > >::operator[](unsigned long)'
>> ('_ZNSt6vectorIS_ISt4pairIiiESaIS1_EESaIS3_EEixEm') that is not present in
>> the target
>> error: The expression could not be prepared to run in the target
>>
>>
>> On Mon, Nov 4, 2013 at 2:59 PM, Enrico Granata <egranata at apple.com>wrote:
>>
>>> The latter one I think is an expression parser issue.
>>> It should be fixed in ToT already, but I CC’ed on this email Sean
>>> Callanan who works on this part of LLDB and might have more insights for you
>>>
>>> I tried to reproduce your issue on OSX Mavericks, but in spite of me
>>> trying to print ~11.000 pairs (I raised your 300 to 900 and put 12 pairs in
>>> each sub-vectors instead of 4), it took about 5 seconds to print everything
>>>
>>> If you do file a bug, which you totally should, more details on your
>>> environment might be interesting: OS, compiler, standard library, revision
>>> of LLDB, ..
>>>
>>>  Enrico Granata
>>> 📩 egranata@.com
>>> ☎️ 27683
>>>
>>> On Nov 4, 2013, at 2:36 PM, Dun Peal <dunpealer at gmail.com> wrote:
>>>
>>> If it's trying to create 4 billion non-existing elements per vector,
>>> there's probably no need to sample. It explains the lost time pretty well.
>>>
>>> Let me know if you want me to file a bug. I'm encountering other issues,
>>> for instance sometimes trying to `p some_name`, I get:
>>>
>>> error: Couldn't materialize struct: size of variable some_name disagrees
>>> with the ValueObject's size
>>> Errored out in Execute, couldn't PrepareToExecuteJITExpression
>>>
>>> Perhaps lldb simply isn't production ready for non-OSX platforms?
>>>
>>>
>>> On Mon, Nov 4, 2013 at 2:14 PM, Enrico Granata <egranata at apple.com>wrote:
>>>
>>>> Replies inlined
>>>>
>>>>  Enrico Granata
>>>> 📩 egranata@.com
>>>> ☎️ 27683
>>>>
>>>> On Nov 4, 2013, at 1:48 PM, Dun Peal <dunpealer at gmail.com> wrote:
>>>>
>>>> In my case, it's a vector of vectors of pairs of ints, i.e.
>>>> vector<vector<pair<int,int>>>.
>>>>
>>>> I'm not sure what "a sample of lldb taken while it's sitting there"
>>>> means. Sorry, I'm an LLVM newbie.
>>>>
>>>>
>>>> If you are on OSX, it simply means typing *sample lldb* at a bash
>>>> prompt :)
>>>> It will periodically look at the state of LLDB and generate a report of
>>>> what is most likely taking up all that time
>>>>
>>>> On Linux/Windows/.. I suppose there are equivalent facilities. Google
>>>> is your friend. A process sample has nothing to do with LLVM specifically.
>>>>
>>>> I have reproduced the problem with minimal code, posted below. Two
>>>> interesting observations:
>>>>
>>>> 1) For some reason, lldb prints each vector<pair<int,int>> as:
>>>>
>>>>   [0] = size=4294967295 {
>>>>     [0] = (first = 0, second = 1)
>>>>     [1] = (first = 1, second = 2)
>>>>     [2] = (first = 2, second = 3)
>>>>     [3] = (first = 3, second = 4)
>>>>     ...
>>>>   }
>>>>
>>>> Since each of those vectors is exactly 4 pairs, it is printed in its
>>>> entirety, so I'm not sure why there's an ellipsis there.
>>>>
>>>>
>>>> It looks like something is wrong with this data structure and we
>>>> believe its size to be the large number
>>>> That value is not just a placeholder, it’s how many elements LLDB
>>>> actually thinks are in the vector!
>>>> Most likely we end up realizing those are not valid and so we omit
>>>> printing them, but we still believe they exist, and since you likely asked
>>>> to see all of them, we are trying to create 4 billion elements and failing.
>>>> Here your 300 seconds
>>>> Why we end up with malformed data like that is an interesting question.
>>>> I will try to repro
>>>>
>>>> 2) The times I quoted above are surprisingly preserved with this sample
>>>> code. For example, printing the first 256 elements is still about 8
>>>> seconds. Printing all 300 elements, which is only about 20% more, takes 300
>>>> seconds, i.e. almost x40 the time!  Curious.
>>>>
>>>> #include <iostream>
>>>> #include <vector>
>>>>
>>>> using namespace std;
>>>>
>>>> int main() {
>>>>     vector<vector<pair<int,int> > > vec;
>>>>     for (int i=0; i < 300; ++i) {
>>>>         vector<pair<int,int> > v;
>>>>         for (int j=0; j < 4; ++j) {
>>>>             v.push_back(make_pair(i+j, i+j+1));
>>>>         }
>>>>         vec.push_back(v);
>>>>     }
>>>>     return 0;  // to reproduce, put a breakpoint in this line, and `p
>>>> vec`
>>>> }
>>>>
>>>>
>>>> On Mon, Nov 4, 2013 at 12:49 PM, Enrico Granata <egranata at apple.com>wrote:
>>>>
>>>>> Yes please. Possibly with a sample of lldb taken while it's sitting
>>>>> there.
>>>>> From your email, it sounds like the repro case is just a vector of
>>>>> pairs of int and int, with about 400 elements. Is that all?
>>>>>
>>>>> Sent from the iPhone of
>>>>> *Enrico Granata* <egranata@🍎.com>
>>>>>
>>>>> On Nov 4, 2013, at 12:42 PM, Dun Peal <dunpealer at gmail.com> wrote:
>>>>>
>>>>> Thanks!  This works, though surprisingly slow; I just printed a
>>>>> vector<vector<pair<int,int>>> of 384 elements, and it blocked for about 390
>>>>> seconds (6:30 minutes!) before rendering.
>>>>>
>>>>> The print only blocks for about 8 seconds when rendering the first 256
>>>>> elements (i.e. without the settings change).
>>>>>
>>>>> This is LLDB 3.4 from the LLVM aptitude repo, running on a high end
>>>>> Xubuntu Linux 13.04 developer workstation.
>>>>>
>>>>> This is obviously a major usability issue for me with LLDB. Should I
>>>>> file a bug for this?
>>>>>
>>>>>
>>>>> On Mon, Nov 4, 2013 at 10:05 AM, Greg Clayton <gclayton at apple.com>wrote:
>>>>>
>>>>>> (lldb) settings show target.max-children-count
>>>>>> target.max-children-count (int) = 256
>>>>>> (lldb) settings set target.max-children-count 10000
>>>>>>
>>>>>>
>>>>>> You can then add this line to your ~/.lldbinit file if you want the
>>>>>> setting to always be increased.
>>>>>>
>>>>>>
>>>>>> On Nov 3, 2013, at 7:57 PM, Dun Peal <dunpealer at gmail.com> wrote:
>>>>>>
>>>>>> > Hi,
>>>>>> >
>>>>>> > When I do:
>>>>>> >
>>>>>> > (lldb) p some_vector
>>>>>> >
>>>>>> > It seems LLDB only actually prints the first 256 values. How do I
>>>>>> get it to print the entire vector?
>>>>>> >
>>>>>> > Thanks, D.
>>>>>> > _______________________________________________
>>>>>> > lldb-dev mailing list
>>>>>> > lldb-dev at cs.uiuc.edu
>>>>>> > http://lists.cs.uiuc.edu/mailman/listinfo/lldb-dev
>>>>>>
>>>>>>
>>>>> _______________________________________________
>>>>> lldb-dev mailing list
>>>>> lldb-dev at cs.uiuc.edu
>>>>> http://lists.cs.uiuc.edu/mailman/listinfo/lldb-dev
>>>>>
>>>>>
>>>>
>>>>
>>>
>>>
>>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/lldb-dev/attachments/20131106/2ed1180d/attachment.html>


More information about the lldb-dev mailing list