[SOLVED] libcheck fails with /usr/bin/ld: cannot find @[email protected]: No such file or directory

Issue

I’m trying to follow the check tutorial here to try and setup a test suite. My project structure is like

root
  |-----src
         |----- foo.h, foo.c
        test
         |----- root_test.h, root_test.c, foo_test.c
        Makefile.am
        configure.ac

My foo.h:

#ifndef FOO_H
#define FOO_H

int func();

#endif

foo.c:

#include "foo.h"

int func() { return 0; }

root_test.h:

#ifndef ROOT_TEST_H
#define ROOT_TEST_H

#include <check.h>

Suite *foo_suite();

#endif

root_test.c:

#include <check.h>
#include <stdlib.h>

#include "root_test.h"

int main() {
  int fc;
  SRunner *sr;

  sr = srunner_create(foo_suite());

  srunner_run_all(sr, CK_NORMAL);
  fc = srunner_ntests_failed(sr);
  srunner_free(sr);

  return fc == 0 ? EXIT_SUCCESS : EXIT_FAILURE;
}

foo_test.c:

#include <check.h>

#include "../src/foo.h"
#include "root_test.h"

START_TEST(foo_func) { ck_assert_int_eq(func(), 0); }
END_TEST

Suite *foo_suite() {
  Suite *s;
  TCase *tc;

  s = suite_create("Foo");
  tc = tcase_create("Core");

  tcase_add_test(tc, foo_func);

  suite_add_tcase(s, tc);
  return s;
}

My Makefile.am:

ACLOCAL_AMFLAGS = -I m4

lib_LTLIBRARIES = libroot.la

HFILES =\
  src/foo.h       

CFILES =\
  src/foo.c

libroot_la_SOURCES = $(HFILES) $(CFILES)

TESTS = libroot_test
check_PROGRAMS = libroot_test
libroot_test_SOURCES = $(HFILES) test/root_test.h test/root_test.c test/foo_test.c
libroot_test_CFLAGS = @[email protected]
libroot_test_LDADD = libroot.la @[email protected]

noinst_PROGRAMS = libroot_test

and my configure.ac:

AC_PREREQ([2.71])
AC_INIT([libroot], [0.0.1], [[email protected]])
AC_CONFIG_AUX_DIR([build])
AC_CONFIG_MACRO_DIRS([m4])
AC_CONFIG_SRCDIR([src/foo.h])
AC_CONFIG_HEADERS([config.h])
AM_INIT_AUTOMAKE([-Wall -Werror foreign subdir-objects])
AM_PROG_AR

LT_INIT

# Checks for programs.
AC_PROG_CC

# Checks for libraries.

# Checks for header files.

# Checks for typedefs, structures, and compiler characteristics.
AC_TYPE_SIZE_T

# Checks for library functions.
AC_FUNC_MALLOC
AC_FUNC_REALLOC

AC_CONFIG_FILES([Makefile])
AC_OUTPUT

My autoreconf -i and ./configure run without any issues. When I run make check I get the following output with error:

/bin/sh ./libtool  --tag=CC   --mode=link gcc @[email protected] -g -O2   -o libroot_test  test/libroot_test-libroot_test.o test/libroot_test-foo_test.o libroot.la @[email protected] 
libtool: link: gcc @[email protected] -g -O2 -o .libs/libroot_test test/libroot_test-libroot_test.o test/libroot_test-foo_test.o @[email protected]  ./.libs/libroot.so -Wl,-rpath -Wl,/usr/local/lib
/usr/bin/ld: cannot find @[email protected]: No such file or directory
/usr/bin/ld: cannot find @[email protected]: No such file or directory
collect2: error: ld returned 1 exit status
make: *** [Makefile:687: libroot_test] Error 1

Solution

The @[email protected] and @[email protected] strings appearing in your Makefile.am are placeholders for the values of Autoconf output variables, but your original configure.ac does not contain anything that would set such output variables. As a result, the placeholders are carried through unchanged to generated makefiles, where they cause builds to fail with the observed error.

The Check documentation contains a section about integrating libcheck with Autotools-based build systems. Its recommendation is to use the the PKG_CHECK_MODULES provided by pkg-config. For example,

# ...

# Checks for libraries.
PKG_CHECK_MODULES([CHECK], [check >= 0.9.6])

# ...

The second macro parameter specifies the minimum acceptable version of Check, and it may be omitted if you do not wish to specify a minimum version.

Note also that older versions of PKG_CHECK_MODULES do not automatically make the relevant variables Autoconf output variables. If you were saddled with such a version and were unable to update, then you would also want to add

AC_SUBST([CHECK_CFLAGS])
AC_SUBST([CHECK_LIBS])

after PKG_CHECK_MODULES.

If you do not have pkg-config or do not want your package build to rely on it then there is also an AM_PATH_CHECK() macro provided by Check itself that can serve the purpose. That macro is deprecated, however, and therefore may be removed from some future version of Check. Refer to the documentation for more information on this macro.

Answered By – John Bollinger

Answer Checked By – Candace Johnson (BugsFixing Volunteer)

Leave a Reply

Your email address will not be published.