当使用“Step Into”使用调试器单步执行代码时,Xcode 将单步执行构造函数、析构函数和赋值运算符。当例程是由编译器提供时,这尤其令人沮丧。一旦函数经过调试并且没有错误,我希望能够在正常的“单步执行”过程中跳过它们。
给出这段代码:
#include <vector>
//-----------------------------------------------------------------------
class Object
{
Object() { };
};
//-----------------------------------------------------------------------
class ObjectList : public std::vector<Object>
{
public:
ObjectList() { };
};
//-----------------------------------------------------------------------
void TestFunction(ObjectList list)
{
}
//-----------------------------------------------------------------------
int main(int argc, const char * argv[])
{
ObjectList list;
TestFunction(list);
return 0;
}
单步执行上述代码时,当您“单步执行”TestFunction(ObjectList list) 时,如预期的那样,会出现“ObjectList”的复制构造。 Xcode 跳转到编译器生成的复制构造函数,指示正在调试的行是 class ObjectList : public std::vector 行,它没有告诉我任何信息。这使得“步入”变得很麻烦。
我知道您到达那里后可以“退出”,但这是一个额外的步骤,在迈出时必须认识到并采取行动,它会干扰流程,而不会增加任何好处。当然,TestFunction 签名可以重写为 void TestFunction(const ObjectList &list) 以避免这种情况下的复制构造,但我正在寻找一种通用方法来避免该问题。
调试完 ObjectList 和 Object 后,我想告诉 Xcode 不要进入任何 ObjectList 或 Object 函数 - 无论是在逐个函数的基础上还是在逐个类的基础上,有点像它们的样子如果它们位于您没有源代码的库中,则进行处理。
有没有办法告诉调试器,“我不想‘单步执行’这个函数”?
lldb 有几个设置可以执行此操作,具体取决于您感兴趣的级别。这两个设置是:
target.process.thread.step-avoid-libraries -- A list of libraries that source stepping won't stop in.
target.process.thread.step-avoid-regexp -- A regular expression defining functions step-in won't stop in.
听起来第二个就是你想要的。 这只是获取设置的正则表达式值并将其应用于分解的函数名称,如果该正则表达式匹配,我们就不会进入该函数。
默认情况下,这实现了不单步执行 C++ 标准库函数的策略(因为很多 std 都在头文件中,所以您实际上拥有库的大部分调试信息,并且在那里会遇到相同的问题。您可以看到以下内容:
(lldb) settings show target.process.thread.step-avoid-regexp
target.process.thread.step-avoid-regexp (regex) = ^std::
因此,制作这个
^std::|^ObjectList::|^Object::
应该可以达到您在示例中想要的效果。 没有任何 Xcode UI 来设置此变量,但您可以在 lldb 控制台中使用它,如果您获得喜欢的值,您可以将该值保存在 ~/.lldbinit 中,或者在 Xcode 中添加目标特定的 lldbinit 文件,并将其放在那里。