gdb catch throw,这个线程

gdb catch throw, this thread

我的二进制文件(从 C++ 生成)有两个线程。当我关心异常时,我关心其中一个(工作人员)抛出的异常,而不是另一个抛出的异常。

有没有办法告诉 gdb 在使用 catch throw 时只关注其中一个线程? gdb 手册(texinfo 文档)和谷歌搜索向我建议这是不可能的,尽管我认为我可以请求捕获特定类型的异常,希望只有一个线程会抛出,使用 catch throw REGEXP.

Is there a way to tell gdb only to pay attention to one of the threads

catch throw 实际上只是在 __cxxabiv1::__cxa_throw (或类似的)上设置断点的一种奇特方式,您 可以 设置断点条件线程数,达到相同的结果。

示例:

#include <pthread.h>
#include <unistd.h>

void *fn(void *)
{
  while(true) {
    try {
      throw 1;
    } catch (...) {}
    sleep(1);
  }
  return nullptr;
}

int main() {
  pthread_t tid;
  pthread_create(&tid, nullptr, fn, nullptr);
  fn(nullptr);
  return 0;
}

g++ -g -pthread t.cc

使用 catch throw,您将在 main 和第二个线程上触发断点。但是使用 break ... thread 2 你只会得到你关心的一个断点:

gdb -q a.out
Reading symbols from a.out...

(gdb) start
Temporary breakpoint 1 at 0x11d6: file t.cc, line 17.
Starting program: /tmp/a.out
[Thread debugging using libthread_db enabled]
Using host libthread_db library "/lib/x86_64-linux-gnu/libthread_db.so.1".

Temporary breakpoint 1, main () at t.cc:17
17        pthread_create(&tid, nullptr, fn, nullptr);
(gdb) n
[New Thread 0x7ffff7a4c640 (LWP 1225199)]

  ## Note: GDB refuses to set thread-specific breakpoint until the thread actually exists.

18        fn(nullptr);
(gdb) break __cxxabiv1::__cxa_throw thread 2
Breakpoint 2 at 0x7ffff7e40370: file ../../../../src/libstdc++-v3/libsupc++/eh_throw.cc, line 77.
(gdb) c
Continuing.
[Switching to Thread 0x7ffff7a4c640 (LWP 1225199)]

Thread 2 "a.out" hit Breakpoint 2, __cxxabiv1::__cxa_throw (obj=0x7ffff0000be0, tinfo=0x555555557dc8 <typeinfo for int@CXXABI_1.3>, dest=0x0) at ../../../../src/libstdc++-v3/libsupc++/eh_throw.cc:77
77      ../../../../src/libstdc++-v3/libsupc++/eh_throw.cc: No such file or directory.
(gdb) bt
#0  __cxxabiv1::__cxa_throw (obj=0x7ffff0000be0, tinfo=0x555555557dc8 <typeinfo for int@CXXABI_1.3>, dest=0x0) at ../../../../src/libstdc++-v3/libsupc++/eh_throw.cc:77
#1  0x00005555555551b5 in fn () at t.cc:8
#2  0x00007ffff7d7eeae in start_thread (arg=0x7ffff7a4c640) at pthread_create.c:463
#3  0x00007ffff7caea5f in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:95
(gdb) c
Continuing.

Thread 2 "a.out" hit Breakpoint 2, __cxxabiv1::__cxa_throw (obj=0x7ffff0000be0, tinfo=0x555555557dc8 <typeinfo for int@CXXABI_1.3>, dest=0x0) at ../../../../src/libstdc++-v3/libsupc++/eh_throw.cc:77
77      in ../../../../src/libstdc++-v3/libsupc++/eh_throw.cc
(gdb) bt
#0  __cxxabiv1::__cxa_throw (obj=0x7ffff0000be0, tinfo=0x555555557dc8 <typeinfo for int@CXXABI_1.3>, dest=0x0) at ../../../../src/libstdc++-v3/libsupc++/eh_throw.cc:77
#1  0x00005555555551b5 in fn () at t.cc:8
#2  0x00007ffff7d7eeae in start_thread (arg=0x7ffff7a4c640) at pthread_create.c:463
#3  0x00007ffff7caea5f in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:95

Voilà -- 线程特定 catch throw 等效。