Имя и адрес функции отсутствуют в Linux System.map - PullRequest
2 голосов
/ 20 февраля 2010

Я занимаюсь разработкой встраиваемых систем на плате AT91SAM9263 и столкнулся со странной проблемой. Он работает под ядром Debian Linux 2.6.18.4 и кросс-компилируется с arm-linux-gcc 3.4.6 и использует uClibc-0.9.28 для библиотеки C. Я отлаживаю драйвер устройства ядра, а в файле System.map не отображается определенная функция. Понятно, что поэтому я не могу установить точку останова на этом. Как ни странно, если я взломаю вызывающую функцию, я не смогу войти в нее - команда nexti из gdb выполняет ее, но пропускает мимо источника. Функция atmel_rx_chars (struct uart_port * port). Это статическая функция void, объявленная в atmel_serial.c, пример которой приведен в [1]. В том же файле есть другие статические функции void (например, atmel_tx_chars (struct uart_port * port)), которые объявлены в том же файле и фактически проиндексированы в файле System.map. Согласно [2], «System.map создается с помощью nm vmlinux», а ненужные или неинтересные символы вырезаются ». Я попытался использовать nm (а также objdump) для просмотра всех символов, и он все еще не отображается в выходных данных. Тем не менее, когда я grep atmel_rx_chars vmlinux, он возвращает совпадение. Раньше я считал себя опытным пользователем, но после этого я действительно озадачен. Любой совет будет наиболее ценным.

Спасибо,

Jayce

[1] http://lxr.free -electrons.com / source / drivers / serial / atmel_serial.c # L379
[2] http://www.faqs.org/docs/Linux-HOWTO/Kernel-HOWTO.html#systemmap

Ответы [ 2 ]

2 голосов
/ 21 июля 2010

Причина, по которой вы этого не видите, заключается в том, что компилятор встроил эту функцию. Он объявлен как static и вызывается только в одном месте, поэтому компилятор указывает его. Если вы хотите установить на нем точку останова, измените источник, чтобы он больше не объявлялся статическим, и перекомпилируйте.

0 голосов
/ 24 февраля 2010

Для тех, кто может быть заинтересован, я не мог понять, почему он не отображает atmel_rx_chars на адрес в System.map. Вы все еще можете установить точку останова как обычную для отладки в этой ситуации. Я полагаю, это должно было быть более очевидным, когда я искал ответы. В любом случае в командной строке GDB введите

b source_file.c:line#

так что в этом примере это будет

b atmel_serial.c:381

и оно будет прерываться всякий раз, когда вы нажимаете «пропущенную» процедуру. Это все еще неполное решение, все же. Разбивка на определенную строку работает, но она не оставляет стековый фрейм вызывающей функции (atmel_handle_receive), поэтому локальные переменные atmel_rx_chars недоступны для GDB. Как всегда, любая помощь или понимание будут оценены. Надеюсь, что это послужит хорошей отправной точкой, если кто-то еще столкнется с этой проблемой или кому-то подобному.

Спасибо,

Jayce

...