获取其他线程的回溯

发布于 2024-11-16 06:59:26 字数 216 浏览 3 评论 0原文

在Linux中,要获取回溯,您可以使用backtrace()库调用,但它仅返回当前线程的回溯。有没有办法获得其他线程的回溯,假设我知道它是 TID(或 pthread_t)并且我可以保证它休眠?

看来 libunwind (http://www.nongnu.org/libunwind/) 项目可以提供帮助。问题是 CentOS 不支持它,所以我不想使用它。

还有其他想法吗? 谢谢。

In Linux, to get a backtrace you can use backtrace() library call, but it only returns backtrace of current thread. Is there any way to get a backtrace of some other thread, assuming I know it's TID (or pthread_t) and I can guarantee it sleeps?

It seems that libunwind (http://www.nongnu.org/libunwind/) project can help. The problem is that it is not supported by CentOS, so I prefer not to use it.

Any other ideas?
Thanks.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

顾挽 2024-11-23 06:59:26

我自己在此处实现了这一点。

最初,我想实现类似于此处建议的东西,即以某种方式获取线程的顶部帧指针并手动展开它(链接的源代码源自 Apple 的 backtrace 实现,因此可能是 Apple 特定的,但这个想法是通用的)。

但是,为了保证安全(上面的源代码不是安全的,甚至可能会被破坏),您必须在访问其堆栈时挂起线程。我四处寻找挂起线程的不同方法,发现 这个这个这个。基本上没有什么特别好的办法。常见的技巧也是Hotspot JAVA VM 使用的,即使用信号并通过 < a href="http://pubs.opengroup.org/onlinepubs/7908799/xsh/pthread_kill.html" rel="noreferrer">pthread_kill。

因此,由于无论如何我都需要这样的信号破解,我可以让它更简单一点,只需在目标线程中执行的被调用信号处理程序中使用 backtrace (也建议 此处作者:sandeep)。这基本上就是我的实现正在做的事情。

如果您也有兴趣打印回溯,即获取一些有用的调试信息(函数名称、源代码文件名、源代码行号等),请阅读 此处介绍基于 libbfd 的扩展 backtrace_symbols。或者只需在此处查看源代码。

I implemented that myself here.

Initially, I wanted to implement something similar as suggested here, i.e. getting somehow the top frame pointer of the thread and unwinding it manually (the linked source is derived from Apples backtrace implementation, thus might be Apple-specific, but the idea is generic).

However, to have that safe (and the source above is not and may even be broken anyway), you must suspend the thread while you access its stack. I searched around for different ways to suspend a thread and found this, this and this. Basically, there is no really good way. The common hack, also used by the Hotspot JAVA VM, is to use signals and sending a custom signal to your thread via pthread_kill.

So, as I would need such signal-hack anyway, I can have it a bit simpler and just use backtrace inside the called signal handler which is executed in the target thread (as also suggested here by sandeep). This is basically what my implementation is doing.

If you are also interested in printing the backtrace, i.e. get some useful debugging information (function name, source code filename, source code line number, ...), read here about an extended backtrace_symbols based on libbfd. Or just see the source here.

櫻之舞 2024-11-23 06:59:26

借助回溯进行信号处理可以解决您的目的。

我的意思是,如果您有线程的 PID,您可以为该线程发出信号。在处理程序中,您可以使用回溯。由于处理程序将在该特定线程中执行,因此回溯将输出您需要的内容。

Signal Handling with the help of backtrace can solve your purpose.

I mean if you have a PID of the Thread, you can raise a signal for that thread. and in the handler you can use the backtrace. since the handler would be executing in that partucular thread, the backtrace there would be the output what you are needed.

素罗衫 2024-11-23 06:59:26

gdb 为调试多线程程序提供了这些工具:

  • 新线程的自动通知
  • “thread thread-id”、在线程之间切换的命令
  • “infothreads”、查询现有线程的命令“
  • thread apply [thread-id-list” ] [all] args',一个将命令应用于线程
  • 特定断点
  • 列表的命令'set print thread-events',它控制线程启动和退出时消息的打印。
  • “set libthread-db-search-path path”,如果默认选择与程序不兼容,用户可以指定要使用的 libthread_db。

因此只需通过 cmd: 'thread thread-id' 转到 GDB 中所需的线程即可。
然后在该线程上下文中执行“bt”以打印线程回溯。

gdb provides these facilities for debugging multi-thread programs:

  • automatic notification of new threads
  • ‘thread thread-id’, a command to switch among threads
  • ‘info threads’, a command to inquire about existing threads
  • ‘thread apply [thread-id-list] [all] args’, a command to apply a command to a list of threads
  • thread-specific breakpoints
  • ‘set print thread-events’, which controls printing of messages on thread start and exit.
  • ‘set libthread-db-search-path path’, which lets the user specify which libthread_db to use if the default choice isn't compatible with the program.

So just goto required thread in GDB by cmd: 'thread thread-id'.
Then do 'bt' in that thread context to print the thread backtrace.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文