Встречая в командной строке флаг -g
1.4.2. Запуск отладчика
Отладчик gdb
% gdb reciprocal
После запуска появится строка приглашения такого вида:
(gdb)
В первую очередь необходимо запустить программу под отладчиком. Для этого введите команду run
(gdb) run
Starting program: reciprocal
Program received signal SIGSEGV, Segmentation fault.
__strtol_internal (nptr=0x0, endptr=0x0, base=10, group=0)
at strtol.c:287
287 strtol.c: No such file or directory.
(gdb)
Проблема заключается в том, что в функции main()
SIGSEGV
означает крах программы. Отладчик определяет, что причина краха находится в функции __strtol_internal()
. Эта функция является частью стандартной библиотеки, но ее исходный файл отсутствует. Вот почему появляется сообщение "No such file or directory". С помощью команды where
можно просмотреть содержимое стека:(gdb) where
#0 __strtol_internal (nptr=0x0, endptr=0x0, base=10, group=0)
at strtol.c:287
#1 0x40096fb6 in atoi (nptr=0x0) at ../stdlib/stdlib.h:251
#2 0x804863e in main (argc=1, argv=0xbffff5e4) at main.c:8
Как нетрудно заметить, функция main()
atoi()
, передав ей нулевой указатель, что и стало причиной ошибки.С помощью команды up
main()
:(gdb) up 2
#2 0x804863е in main (argc=1, argv=0xbffff5e4) at main.c:8
8 i = atoi(argv[1]);
Заметьте, что отладчик нашел исходный файл main.c
print
:(gdb) print argv[1]
$2 = 0x0
Это подтверждает нашу догадку о том, что причина ошибки — передача функции atoi()
NULL
.Установка контрольной точки осуществляется посредством команды break
(gdb) break main
Breakpoint 1 at 0x804862e: file main.c, line 8.
В данном случае контрольная точка размещена в первой строке функции main()
(gdb) run 7
Starting program: reciprocal 7
Breakpoint 1, main (argc=2, argv=0xbffff5e4) at main.c:8
8 i = atoi(argv[1]);
Как видите, отладчик остановился на контрольной точке- Перейти на следующую строку можно с помощью команды next
(gdb) next
9 printf("The reciprocal of %d is %g\n", i,
reciprocal(i));
Если требуется узнать, что происходит внутри функции reciprocal()
step
:(gdb) step
reciprocal (i=7) at reciprocal.cpp:6
6 assert(i != 0);
Иногда удобнее запускать отладчик gdb
M-x gdb
. Когда отладчик останавливается в контрольной точке, редактор Emacs автоматически открывает соответствующий исходный файл. Не правда ли. проще разобраться в происходящем, глядя на весь файл, а не на одну его строку?1.5. Поиск дополнительной информации
В каждый дистрибутив Linux входит масса полезной документации. В ней можно прочесть почти все из того, о чем говорится в этой книге (хотя это, очевидно, займет больше времени). Документация не всегда хорошо организована, поэтому поиск нужной информации требует определенной изобретательности. Иногда представленные факты оказываются устаревшими, так что не стоит всему слепо верить.
Ниже описаны наиболее полезные источники информации о программировании в Linux.
1.5.1. Интерактивная документация