Получение backtrace другого потока

в Linux для получения backtrace вы можете использовать вызов библиотеки backtrace (), но он возвращает только backtrace текущего потока. Есть ли способ получить обратную связь какого-либо другого потока, предполагая, что я знаю, что это TID (или pthread_t), и я могу гарантировать, что он спит?

кажется, что libunwind (http://www.nongnu.org/libunwind/) проект может помочь. Проблема в том, что он не поддерживается CentOS, поэтому я предпочитаю не использовать его.

есть другие идеи? Спасибо.

3 ответов


обработка сигналов с помощью backtrace может решить вашу цель.

Я имею в виду, если у вас есть PID потока, вы можете поднять сигнал для этого потока. и в обработчике можно использовать след. поскольку обработчик будет выполняться в этом частичном потоке, backtrace там будет выводить то, что вам нужно.


я реализовал это сам здесь.

Первоначально я хотел реализовать что-то подобное, как было предложено здесь, т. е. как-то получить указатель верхнего кадра потока и размотать его вручную (связанный источник получен из яблок backtrace реализация, таким образом, может быть специфичной для Apple, но идея является общей).

однако, чтобы иметь этот сейф (и источник выше не и может быть даже сломан в любом случае), вы должны приостановить поток при доступе к его стеку. Я искал различные способы приостановить поток и нашел этой, этой и этой. В принципе, нет действительно хорошего способа. Общий Хак, также используется Hotspot JAVA VM, использовать сигналы и посылать изготовленный на заказ сигнал к вашему потоку через pthread_kill.

Так как мне нужен такой сигнал-взломать в любом случае, я могу иметь его немного проще и просто использовать backtrace внутри вызываемый обработчик сигнала, который выполняется в целевом потоке (как также предложено здесь sandeep). Это в основном то, что делает моя реализация.

Если вы также заинтересованы в печати backtrace, то есть получите полезную отладочную информацию (имя функции, имя файла исходного кода, номер строки исходного кода, ...), читать здесь о расширенном backtrace_symbols на основе libbfd. Или просто увидеть источник здесь.


gdb предоставляет следующие возможности для отладки многопоточных программ:

  • автоматическое уведомление о новых потоках
  • ' thread thread-id’, команда для переключения между потоками
  • ' info threads’, команда для запроса о существующих потоках
  • ‘thread apply [thread-id-list] [all] args’, команда для применения команды к списку потоков
  • специфические для потока точки останова
  • ' set Print thread-events’, который управляет печатью сообщений при запуске и выходе потока.
  • 'set libthread-db-search-path path', который позволяет пользователю указать, какой libthread_db использовать, если выбор по умолчанию несовместим с программой.

Так что просто goto требуется поток в GDB cmd: 'thread thread-id'. Затем сделайте " bt " в этом контексте потока, чтобы напечатать обратную трассировку потока.