我正在学习如何使用GDB调试多线程C++11程序。
这是我的测试代码:
void func()
{
int i = 0;
while (true) {
std::cout << std::this_thread::get_id() << ": " << (i++) <<std::endl;
std::this_thread::sleep_for(std::chrono::milliseconds(1000));
}
}
int main()
{
std::thread t1(func);
std::thread t2(func);
t1.join();
t2.join();
return 0;
}
嗯,这很简单:两个无限循环,每个循环都由一个线程执行。
我执行g++ -std=c++11 test.cpp -g -lpthread
并得到一个二进制文件a.out
.
运行后a.out
在终端 A 上,我打开另一个终端 B 以使用 gdb
连接到它。 :gdb -p <PID_of_a.out>
.
现在的输出是a.out
终端A按预期停止。
然后,我执行info thread
在终端B上:
(gdb) info threads
Id Target Id Frame
* 1 Thread 0x7f3b10c24740 (LWP 62395) "a.out" 0x00007f3b10803d2d in __GI___pthread_timedjoin_ex (threadid=139891642771200, thread_return=0x0, abstime=0x0,
block=<optimized out>) at pthread_join_common.c:89
2 Thread 0x7f3b0faca700 (LWP 62396) "a.out" 0x00007f3b1080cc70 in __GI___nanosleep (requested_time=0x7f3b0fac9d90, remaining=0x7f3b0fac9d90)
at ../sysdeps/unix/sysv/linux/nanosleep.c:28
3 Thread 0x7f3b0f2c9700 (LWP 62397) "a.out" 0x00007f3b1080cc70 in __GI___nanosleep (requested_time=0x7f3b0f2c8d90, remaining=0x7f3b0f2c8d90)
at ../sysdeps/unix/sysv/linux/nanosleep.c:28
所以线程1是main函数,线程2和线程3是func
的两个线程.
然后我执行thread 2
切换到线程2。
现在,我继续输入 n
使线程2运行。
我想做的是让线程2运行,同时让线程3保持停止。然而,线程 3 似乎也被执行了,因为输入 n
在线程 2 上。这是终端 A 的输出:
139891642771200: 17
139891634378496: 17
139891642771200: 18
139891634378496: 18
139891642771200: 19
139891634378496: 19
139891634378496: 20
139891634378496: 21
139891634378496: 22
139891634378496: 23
139891642771200: 20
139891634378496: 24
139891634378496: 25
您可以看到最后第三行:139891642771200: 20
,它来自线程3。
所以我的问题是是否可以让 GDB 只运行一个线程?如果可以的话我能做什么?
最佳答案
对于单步执行程序(step
、next
)GDB 支持将调度程序锁定到当前线程:
set scheduler-locking step
当然,只有当线程能够取得进展(即没有其他线程持有锁等)时,这样的单步执行才会起作用
据我所知,运行程序不存在这种可能性(运行
、继续
、完成
).
关于c++ - GDB是否可以只运行一个线程,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/63884680/