Как подключить отладчик к запущенному процессу Perl?
У меня есть запущенный процесс Perl, который застрял, Id хотел бы высунуть внутри с помощью отладчика, чтобы понять, что не так. Я не могу перезапустить процесс. Могу ли я подключить отладчик к запущенному процессу? Я знаю, что могу сделать gdb -p
, но gdb
мне не помогает. Ive попытался Enbugger, но не удалось:
$ perl -e 'while (1) {}'&
[1] 86836
$ gdb -p 86836
…
Attaching to process 86836.
Reading symbols for shared libraries . done
Reading symbols for shared libraries ............................. done
Reading symbols for shared libraries + done
0x000000010c1694c6 in Perl_pp_stub ()
(gdb) call (void*)Perl_eval_pv("require Enbugger;Enbugger->stop;",0)
perl(86836) malloc: *** error for object 0x3: pointer being realloc'd was not allocated
*** set a breakpoint in malloc_error_break to debug
Program received signal SIGABRT, Aborted.
0x00007fff8269d82a in __kill ()
The program being debugged was signaled while in a function called from GDB.
GDB remains in the frame where the signal was received.
To change this behavior use "set unwindonsignal on"
Evaluation of the expression containing the function (Perl_eval_pv) will be abandoned.
(gdb)
Я делаю это неправильно? Существуют ли другие варианты?
P.S. Если вы считаете, что вы можете извлечь выгоду из отладчика, подключенного к запущенному процессу, вы можете вставить заднюю дверь отладчика, вызванную SIGUSR1:
use Enbugger::OnError 'USR1';
Тогда вы можете просто kill -USR1 pid
, и ваш процесс перейдет в отладчик.
Ответы
Ответ 1
Во-первых, используйте DEBUGGING perl, если вы хотите проверить его с помощью gdb.
Пожалуйста, определите "застрял". Занято или не занято ожидание (высокий или низкий процессор), есть память или нет?
Пока 1 занят, ожидание. Я обычно получаю ожидание (бесконечные циклы) при повреждении HV в Perl_hfree_next_entry() с 5.15. Ожидание ожидания без ожидания обычно ожидается при чтении блокировки IO.
Я правильно понял:
`0x00007fba15ab35c1 in Perl_runops_debug () at dump.c:2266`
`2266 } while ((PL_op = PL_op->op_ppaddr(aTHX)));`
и может проверять все, гораздо больше, чем с помощью простого отладчика perl. С не-threaded perl вы должны ввести меньше.
`(gdb) p Perl_op_dump(PL_op)`
и т.д.
Если вы имеете дело с perl: внутри функции pp_stub не рекомендуется вводить runloop Enbugger, вы должны быть в главной runloop в dump.c. Установите точку останова на указанную строку.
"ошибка для объекта 0x3" на звуке eval, например внутреннее повреждение в контексте, поэтому вы должны посмотреть на указатели cx и stack. Вероятно, потому что вы начали его в плохом контексте.
Ответ 2
Я никогда не использовал gdb, но, может быть, вы могли бы получить что-то полезное из strace?
strace -f -s512 -p <PID>
Ответ 3
http://metacpan.org/pod/App::Stacktrace
"perl-stacktrace печатает трассировки стека Perl стека потоков Perl для заданного процесса Perl. Для каждого кадра Perl печатается полное имя файла и номер строки".