Где символы gcov?
Я пытаюсь скомпилировать простое приложение с gcov и получить следующие ошибки ссылки:
gcc AllTests.o CuTestTest.o CuTest.o -o TestTest
AllTests.o: In function `global constructors keyed to 0_RunAllTests':
/home/p7539c/cutest/AllTests.c:26: undefined reference to `__gcov_init'
AllTests.o:(.data+0x44): undefined reference to `__gcov_merge_add'
CuTestTest.o: In function `global constructors keyed to 0_TestCuStringNew':
/home/p7539c/cutest/CuTestTest.c:30: undefined reference to `__gcov_init'
CuTestTest.o:(.data+0x64): undefined reference to `__gcov_merge_add'
CuTest.o: In function `global constructors keyed to 0_CuStrAlloc':
/home/p7539c/cutest/CuTest.c:379: undefined reference to `__gcov_init'
CuTest.o:(.data+0x184): undefined reference to `__gcov_merge_add'
collect2: ld returned 1 exit status
make: *** [TestTest] Error 1
Кажется, я не могу найти местоположение отсутствующих символов. gcov присутствует на машине с запущенной версией gcc версии 4.1.2
Любые идеи? Спасибо.
В редакторе:
Кажется, что все отлично работает при использовании gcov с приложением, которое состоит из одного файла .c. Когда у меня есть несколько файлов .c(следовательно, несколько файлов .o), у меня возникла проблема.
Этапы компиляции выглядят следующим образом:
cc -fprofile-arcs -ftest-coverage -g -c -o AllTests.o AllTests.c
cc -fprofile-arcs -ftest-coverage -g -c -o CuTestTest.o CuTestTest.c
cc -fprofile-arcs -ftest-coverage -g -c -o CuTest.o CuTest.c
Ответы
Ответ 1
Я просто потратил невероятное количество времени на отладку очень похожей ошибки. Вот что я узнал:
- При компиляции необходимо передать
-fprofile-arcs -ftest-coverage
.
- При связывании вы должны передать
-fprofile-arcs
.
-
При связывании по-прежнему возникают странные ошибки компоновщика. Они будут выглядеть так:
libname.a(objfile.o):(.ctors+0x0): undefined reference to 'global constructors keyed to long_name_of_file_and_function'
Это означает, что gconv имеет проблему с одним из ваших созданных компилятором конструкторов (в моем случае - конструктор-копия). Проверьте функцию, указанную в сообщении об ошибке, посмотрите, какие объекты она копирует-конструирует, и посмотрите, не имеет ли какой-либо из этих классов конструктор копирования. Добавьте один, и ошибка исчезнет.
Изменить: измените или не оптимизируйте. Попробуйте включить/выключить оптимизацию, если у вас возникли проблемы с ней.
Ответ 2
Флаг, который вы ищете, - lgcov при связывании. То есть, измените:
gcc AllTests.o CuTestTest.o CuTest.o -o TestTest
к
gcc -lgcov AllTests.o CuTestTest.o CuTest.o -o TestTest
Ответ 3
Вы должны указывать только --coverage
в командной строке при компиляции и компоновке.
Согласно man gcc
:
Этот параметр является синонимом -fprofile-arcs
-ftest-coverage
(когда компиляция) и -lgcov
(при связывании).
Ответ 4
Я нашел как предлагалось здесь, что добавление -lgcov в строку сборки при создании общей библиотеки, содержащей .o, созданный с помощью -fprofile -arcs -ftest-coverage решила это для меня. И, конечно, связывание исполняемого файла с -lgcov. Построил общую библиотеку следующим образом:
g++ -shared -o libMyLib.so src_a.o src_b.o src_c.o -lgcov
И исполняемый файл так:
g++ -o myExec myMain.o -lMyLib -lgcov
Добавление -lgov в сборку общей библиотеки (а не только exe), решило эту дополнительную ошибку для меня:
hidden symbol `__gcov_merge_add' in /usr/lib/gcc/x86_64-redhat-linux/4.1.2/libgcov.a(_gcov_merge_add.o) is referenced by DSO
/usr/bin/ld: final link failed: Nonrepresentable section on output
Обратите внимание, что -lgcov должна быть последней связанной библиотекой.
Ответ 5
Я попробовал простой тестовый файл с gcc -ftest-coverage -fprofile-arcs test.c
и не имел проблем, как вы описываете.
Я подозреваю, что gcc вносит в библиотеку gcov, если флаг -ftest-coverage
существует, когда он связывается. Попробуйте передать этот флаг в вашей командной строке gcc.
Ответ 6
Возможно, очевидно, что это точное сообщение об ошибке возникает при связывании с не-gcc-компоновщиком. Мы видим эту ошибку при связывании с ifort (потому что наш код включает в себя как модули Fortran, так и C). Переключение на соединение с gcc сделало трюк.
Ответ 7
Великий Макс Либберт,
В основном в случае использования autoconf добавить _LDADD = -lgcov...
Это решит проблему.
Ответ 8
Итак, я добавил - поделился с CFLAGS, и теперь он работает с несколькими файлами. Разумеется, это звучит в странном месте, поэтому я пока не знаю, что это значит.