简体   繁体   English

如何检查CodeWarrior调试器中的STL列表?

[英]How can I inspect an STL list in the CodeWarrior debugger?

Is there any easy way to view the data in an STL std::list<T> in the Metrowerks CodeWarrior debugger? 在Metrowerks CodeWarrior调试器中,是否有任何简单的方法可以在STL std::list<T>中查看数据? I can view data near the beginning or end of the list by looking at expressions such as 我可以通过查看以下表达式来查看列表开头或结尾附近的数据:

instances->__list_imp.__list_deleter.end_.compressed_pair_imp.second_.prev_->data_

I can expand the little '+' signs next to the struct members to walk the list an element at a time, but this is tedious, and after about 20-30 elements, the tree gets too wide for the debugger window. 我可以扩展struct成员旁边的小“ +”号来一次在列表中遍历一个元素,但这很繁琐,并且在大约20到30个元素之后,树对于调试器窗口来说变得太宽了。 The list I'm examining has over 2000 elements. 我正在检查的列表有2000多个元素。

The CodeWarrior debugger does not support calling functions in expressions, so I can't examine the value of (++(++instances.begin())) or somesuch. CodeWarrior调试器不支持在表达式中调用函数,因此我无法检查(++(++instances.begin()))或类似值。 I can only look at struct members, which have very long and inconvenient names. 我只能看一下具有非常长且不便命名的结构成员。

The debugger window is also limited to about 245 characters, so I can't write a script to generate a ridiculously long expression that will expand to the Nth node. 调试器窗口也限制为245个字符,因此我无法编写脚本来生成可扩展到第N个节点的可笑的长表达式。

I'm trying to debug a problem that requires several hours of soaking to reproduce, so anything that requires adding code incrementally, recompiling, and redebugging will not be very helpful. 我正在尝试调试一个问题,该问题需要几个小时的浸泡才能重现,因此任何需要增量添加代码,重新编译和重新调试的问题都将无济于事。 If there's no other option, though, then I may have to do that. 但是,如果没有其他选择,那么我可能必须这样做。

This definitely isn't an "easy way" (it may not be easier than what you're doing with "+"), but I do find it more helpful than dealing with the watch view in some cases. 这绝对不是一个“简单的方法”(它可能不会比您使用“ +”进行的操作更容易),但是在某些情况下,我确实发现它比处理监视视图更有用。 It also may allow you to debug in really bad circumstances (where the watch view is nearly non-functional for whatever reason, or where you just have a binary memory dump file). 它还可能允许您在非常糟糕的情况下进行调试(无论出于何种原因,监视视图几乎无法运行,或者您只有二进制内存转储文件)。

With a std::list, you typically have an implementation that looks something like this in memory (consult <list> for specifics if necessary): 使用std :: list时,您通常会在内存中实现一个类似以下的实现(如有必要,请咨询<list>以获得详细信息):

struct List
{
  Node * next;
  Node * prev;
  size_t size;
}

template 
struct Node
{
  Node * next;  // last node will point to list rather than another node
  Node * prev;  // first node will point to list rather than another node
  T payload; // e.g. in a std::list this would be a Foo * payload
}

Note that next and prev may be in the opposite order in your implementation. 请注意,next和prev在实现中的顺序可能相反。

&myList is basically equivalent to "end()" in most implementations. 在大多数实现中,&myList基本上等同于“ end()”。

If you use memory view, you can poke around near &myList. 如果使用内存视图,则可以在&myList附近浏览。 This will let you find the value of the myList.prev or myList.next pointer, then change memory view to look at that. 这将使您找到myList.prev或myList.next指针的值,然后更改内存视图以进行查看。 You've then gotten to the last or first node in your list, respectively. 然后,您分别到达列表中的最后一个或第一个节点。

Once you get to a node, you can look at prev, next, or payload, then go to prev or next; 到达节点后,您可以查看上一个,下一个或有效负载,然后转到上一个或下一个; lather, rinse, repeat. 泡沫,冲洗,重复。 If you end up back at &myList, you know you've traversed the whole thing. 如果您最终回到&myList,则说明您已经遍历了整个过程。

Painful and boring? 痛苦无聊吗? Possibly. 可能吧。 But you do get a lot of familiarity with your stl implementation, you can "see" possible stomps easily in some cases, and it's a useful skill to have when all other possibilities fly out the window. 但是您确实非常熟悉stl的实现,在某些情况下可以轻松地“看到”可能的踩踏现象,当所有其他可能性飞出窗口时,这是一项有用的技能。

(Keep notes of where you've been, it's really easy to get confused.) (记下您去过的地方,很容易感到困惑。)

Debuggers could certainly be a lot more STL-friendly. 调试器肯定对STL友好得多。 I'm not familiar with CodeWarrior specifically, but is it the case that you can't call any functions at all from the debug window? 我对CodeWarrior并不特别熟悉,但是是否确实无法从调试窗口调用任何函数呢? Or is it more like other debuggers I have used, where you (1) can't call functions if the program has already terminated (ABORT, segfault, ...), and (2) can't call functions that involve template expansions (which might need to add code to the image), but (3) can call statically-linked functions if the code is stopped at a breakpoint? 还是更像我使用过的其他调试器,您(1)在程序已经终止时无法调用函数(ABORT,segfault等),并且(2)无法调用涉及模板扩展的函数(可能需要向图像添加代码),但是(3)如果代码在断点处停止,可以调用静态链接的函数吗?

In the latter case, you might want to add one or more non-templated functions to your code that copy a list<T> into a C-style array of T, for the specific types you are interested in. If you can call that kind of function from your debug window, do that, and then examine the array elements to find out what's in your list. 在后一种情况下,您可能希望向您的代码中添加一个或多个非模板函数,以将list<T>复制到C样式的T数组中,以获取您感兴趣的特定类型。调试窗口中的某种功能,执行此操作,然后检查数组元素以找出列表中的内容。 If you can't call the function from the debug window, you may need to put some calls to that function in your code close to the point of error, and look at the results. 如果您无法从调试窗口中调用该函数,则可能需要在代码中靠近错误点的位置放置一些对该函数的调用,然后查看结果。 If possible, guard those calls so they only get called when you have some debug flag set. 如果可能,请保护这些调用,以便仅在设置了某些调试标志时才调用它们。

It turns out the problem I was having was due to the very fact that the list had several thousand elements -- it should only have had a couple dozen elements, max. 事实证明,我遇到的问题是由于该列表包含数千个元素-最多只能包含几十个元素。

In this particular STL implementation, the prev pointers were stored at offset 0 of each node, so I could follow back links by just repeatedly dereferencing. 在此特定的STL实现中, prev指针存储在每个节点的偏移量0处,因此我可以通过重复取消引用来跟踪链接。 The following monstrosity looks backwards 20 links: 以下怪兽向后看20个链接:

********************((Metrowerks::node_base**********************)instances->__list_imp.__list_deleter.end_.compressed_pair_imp.second_)

Following forward links is even uglier, since you have to offset by 4 bytes after each dereference. 跟随前向链接更加难看,因为每次取消引用后都必须偏移4个字节。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM