使LLDB重新解释地址作为指向类型为模板实例的对象的指针

问题描述:

调试时,我有一个地址进入内存并知道驻留在该地址的对象的类型,并且我希望调试器显示该实例物体。这可以通过打印命令来完成,这些类型不是模板,但对于模板实例化的类型似乎失败。使LLDB重新解释地址作为指向类型为模板实例的对象的指针

请参见本示例代码:

template<typename T> 
class X 
{ 
public: 
    X() { 
     printf("a\n"); 
    } 
}; 

class Y 
{ 
public: 
    Y() { 
     printf("a\n"); 
    } 
}; 



int main(void) 
{ 
    X<int> x; 
    Y y; 

    return 1; 
} 

当我运行该程序,打破主,试图解释随机有效地址为指针,以X和Y的对象,前者失败:

(lldb) p *(Y*)0x0000000100000ee6 
(Y) $0 = {} 
(lldb) p *(X<int>*)0x0000000100000ee6 
warning: could not load any Objective-C class information. This will significantly reduce the quality of type information available. 
error: use of undeclared identifier 'X' 
error: expected '(' for function-style cast or type construction 
error: expected expression 

有没有办法如何在lldb中做到这一点? (编辑:Mac OS X lldb-360.1.65和lldb-310.2.37)

C++的调试信息当前不代表抽象中的模板,它只涉及程序中存在的特定模板实例。但lldb的表达式命令使用了一个真正的C++解析器(clang),它在解析像你尝试过的表达式时,首先需要将X看作一个抽象模板。由于我们不知道它们,所以我们无法完成clang对X的类型请求,并且 - 这就是为什么您看到的错误是“未声明的标识符X”。

你可以通过为你想要以这种方式施放的指针类型做一个typedef来解决这个问题。这不太令人满意,因为你必须先完成它,而且你必须在你的代码中使用typedef,因为 - 为了保持调试信息的大小可管理 - clang不会发出调试信息用过的。但它确实有效,例如我添加到您的示例代码:

typedef X<int> * x_int_ptr; 

再后来就在主:

x_int_ptr bar = (x_int_ptr) &x; 

,以确保它被记录下来,然后在六味地黄丸,我可以这样做:

(lldb) expr *((x_int_ptr) 0x00007fff5fbff798) 
(X<int>) $1 = {}