5

I read a lot of related topics (like 1, 2, 3) but did not find the answer by myself so here I am.

I have a CMake project that builds and executable, let say "x". I created a shared library named "a.so" that depends on other shared library called "b.so". I want to use "a" in "x".

Here is my simplified "x" CMakelists.txt:

SET(ROOT_DIR ${CMAKE_CURRENT_SOURCE_DIR})

LINK_DIRECTORIES(${ROOT_DIR}/lib/a/bin/) # contains liba.so

INCLUDE_DIRECTORIES(${ROOT_DIR}/lib/a/include/) # contains "a" headers

ADD_EXECUTABLE(x ${SOURCE})

TARGET_LINK_LIBRARIES(x a)

"x" compilation output extract:

Linking CXX executable ../bin/x
/usr/bin/cmake -E cmake_link_script CMakeFiles/x.dir/link.txt --verbose=1
/usr/lib64/ccache/c++   -std=c++0x    CMakeFiles/x.dir/src/main /Main.cpp.o 
 ... -L/.../lib/a/bin -rdynamic  -la  -Wl,-rpath,/.../lib/a/bin 

"a" and "b" do compile.

The problem is when I want to compile x I get errors when linking: undefined reference to 'function name'. I tried to link against "b" too but it's still not working.

Here "b" also appears but I get the same error...

Linking CXX executable ../bin/x
/usr/bin/cmake -E cmake_link_script CMakeFiles/x.dir/link.txt --verbose=1 
/usr/lib64/ccache/c++   -std=c++0x    CMakeFiles/x.dir/src/main 
/Main.cpp.o -o ../bin/x  -L/.../lib/b/bin -L/.../lib/a/bin 
-rdynamic -lb -la -Wl,-rpath,/.../lib/b/bin:/.../lib/a/bin 

Here is the error output:

 $ make
 [ 20%] Automatic moc for target x
 Linking CXX executable ../bin/x
 /.../lib/b/bin/b.so: undefined reference to `snd_pcm_sw_params_set_start_threshold'
 /.../lib/b/bin/b.so: undefined reference to `snd_seq_delete_simple_port'
 /.../lib/b/bin/b.so: undefined reference to `snd_pcm_info_set_device'
 /.../lib/b/bin/b.so: undefined reference to `snd_pcm_sw_params'
 /.../lib/b/bin/b.so: undefined reference to `snd_pcm_sw_params_set_silence_threshold'
 /.../lib/b/bin/b.so: undefined reference to `snd_pcm_hw_params_any'
 /.../lib/b/bin/b.so: undefined reference to `snd_seq_drain_output'
 /.../lib/b/bin/b.so: undefined reference to `snd_ctl_pcm_next_device'

 ...

 collect2: error: ld returned 1 exit status
 CMakeFiles/x.dir/build.make:163: recipe for target '../bin/x' failed
 make[2]: *** [../bin/x] Error 1
 CMakeFiles/Makefile2:60: recipe for target 'CMakeFiles/x.dir/all' failed
 make[1]: *** [CMakeFiles/x.dir/all] Error 2
 Makefile:76: recipe for target 'all' failed
 make: *** [all] Error 2

I don't see what's wrong and I'm now confused as I tried many things to get the thing working... but nothing worked.

Any idea?

Thanks!

Community
  • 1
  • 1
lecoqlibre
  • 140
  • 2
  • 13
  • 1
    Your linker can't find `b.so`. You should add it to the linker path, too. Can you paste some output of the compiler/linker? – nils Mar 24 '15 at 17:15
  • Done. Effectively, "b" doesn't appear in the linker path. But even when I add `LINK_DIRECTORIES(${ROOT_DIR}/lib/b/bin/)` and `TARGET_LINK_LIBRARIES(x b a)` I get the same errors... – lecoqlibre Mar 24 '15 at 17:25
  • That's good, too, but with _output_ I actually meant the error messages. – nils Mar 24 '15 at 17:30
  • Ok, done ;) I put a shorter output than the real one. Just to let you know, in reality my library b refers to the library called [juce](http://www.juce.com). – lecoqlibre Mar 24 '15 at 17:42
  • It seems your `b.so` cannot find the ALSA library. – nils Mar 24 '15 at 17:44

2 Answers2

1

"b" was missing a specific dependant library. I added it via the FIND_PACKAGE CMake directive in the "b" CMakeLists.txt. It solved the problem.

The above "x" CMakeLists.txt is thus correct.

lecoqlibre
  • 140
  • 2
  • 13
1

I asked you for the error output in the comments above, because it can help to search the undefined symbols/references.

So, it seems that your b.so cannot find the ALSA library. If you use CMake 3.0 (and up) you can add it to your CMakeLists.txt via

find_package( ALSA )

and can append ${ALSA_INCLUDE_DIR} to your include path and ${ALSA_LIBRARY} to your linker path.

nils
  • 2,424
  • 1
  • 17
  • 31