Re: [CMake] transitive linking with separate projects
On 03/07/2012 11:29 AM, Alexander Dahl wrote: > Hello Michael, > > Am 2012-03-06 16:46, schrieb Michael Hertling: >> or possibly better: >> >> # libbar/bar-config.cmake.in: >> FIND_PACKAGE(FOO PATHS @FOO_DIR@ NO_DEFAULT_PATH) > > I used > > FIND_PACKAGE(FOO 0.1.0 REQUIRED) > > in the package config file now, which works, too. Actually, FIND_PACKAGE(FOO PATHS @FOO_DIR@ NO_DEFAULT_PATH) is meant to ensure that bar-config.cmake loads the *same* foo-config.cmake as bar's CMakeLists.txt has before. Possibly, it's even the best to use exactly the same parameters - apart from PATHS and NO_DEFAULT_PATH - i.e., version, components, external variables etc., in order to guarantee that really the same foo-targets.cmake is included. >> BTW, find modules / config files should provide a *_LIBRARIES variable >> even if they use imported targets, e.g.: SET(FOO_LIBRARIES foo-shared) > > I added this. Let me guess, this is for convenience with find rules > using the same variables? Yes, in this way, it works with imported targets as well as full paths. >> PS: The baz project on GitHub only contains a README. > > I forgot to push this one. > > Thanks very much, I guess this solves this kind of problem with my > packages. :-) See also [1]. Regards, Michael [1] http://public.kitware.com/Bug/view.php?id=12588 -- Powered by www.kitware.com Visit other Kitware open-source projects at http://www.kitware.com/opensource/opensource.html Please keep messages on-topic and check the CMake FAQ at: http://www.cmake.org/Wiki/CMake_FAQ Follow this link to subscribe/unsubscribe: http://www.cmake.org/mailman/listinfo/cmake
Re: [CMake] transitive linking with separate projects
Hello Michael, Am 2012-03-06 16:46, schrieb Michael Hertling: > or possibly better: > > # libbar/bar-config.cmake.in: > FIND_PACKAGE(FOO PATHS @FOO_DIR@ NO_DEFAULT_PATH) I used FIND_PACKAGE(FOO 0.1.0 REQUIRED) in the package config file now, which works, too. > BTW, find modules / config files should provide a *_LIBRARIES variable > even if they use imported targets, e.g.: SET(FOO_LIBRARIES foo-shared) I added this. Let me guess, this is for convenience with find rules using the same variables? > PS: The baz project on GitHub only contains a README. I forgot to push this one. Thanks very much, I guess this solves this kind of problem with my packages. :-) Greets Alex -- »With the first link, the chain is forged. The first speech censured, the first thought forbidden, the first freedom denied, chains us all irrevocably.« (Jean-Luc Picard, quoting Judge Aaron Satie) *** GnuPG-FP: 02C8 A590 7FE5 CA5F 3601 D1D5 8FBA 7744 CC87 10D0 *** -- Powered by www.kitware.com Visit other Kitware open-source projects at http://www.kitware.com/opensource/opensource.html Please keep messages on-topic and check the CMake FAQ at: http://www.cmake.org/Wiki/CMake_FAQ Follow this link to subscribe/unsubscribe: http://www.cmake.org/mailman/listinfo/cmake
Re: [CMake] transitive linking with separate projects
On 03/06/2012 02:47 PM, Alexander Dahl wrote: > Hei hei, > > we faced a build problem with transitive linking of separate projects > where I can't find the right solution on my own. I hope someone can give > me a hint. I prepared a test case with two libraries libfoo and libbar > and an application baz. libfoo is on his own, libbar calls a function > from libfoo and baz calls the function from libbar calling libfoo. So > the dependencies are like this: > > baz -> libbar -> libfoo > > baz doesn't need to know of libfoo because it just calls libbar, so I > thought. > > Now the projects are separated and both libraries come with cmake > package configuration files. For linking libfoo in libbar I do the > following: > > find_package(FOO) > target_link_libraries(BAR_SRC foo-shared) > > foo-shared is the target libfoo exports via cmake package > configuration. This works and ldd shows libbar is correctly linked > against libfoo. > > Now when compiling baz I more or less do the same: > > find_package(BAR) > target_link_libraries(BAZ_SRC bar-shared) > > However building baz fails with the following error: > > % make > [100%] Building C object src/CMakeFiles/baz.dir/baz.c.o > Linking C executable baz > /usr/bin/ld: cannot find -lfoo-shared > collect2: ld returned 1 exit status > make[2]: *** [src/baz] Fehler 1 > make[1]: *** [src/CMakeFiles/baz.dir/all] Fehler 2 > make: *** [all] Fehler 2 > > It seems like cmake tries to link against libfoo here but does not know > anything about it. If I add find_package(FOO) to baz obviously the > target is imported from libfoo cmake package files. The question is, if > I know nothing about the requirements of libbar and want to avoid adding > find_package statements for those requirements to baz, how would I do > this? > > I put all the code on GitHub, so if someone maybe could have a look? > > https://github.com/LeSpocky/libfoo > https://github.com/LeSpocky/libbar > https://github.com/LeSpocky/baz > > Greets > Alex If you run "grep foo -r /lib/cmake/bar", you will see only one line which informs the user of bar-config.cmake that the bar-shared target has a prerequisite name foo-shared, but there is no more information. For this reason, it's passed as -lfoo-shared to the linker. You need to include foo-targets.cmake in bar-config.cmake in order to make the necessary information available, e.g. by # libbar/bar-config.cmake.in: INCLUDE(@FOO_CONFIG@) get_filename_component(_dir "${CMAKE_CURRENT_LIST_FILE}" PATH) get_filename_component(_prefix "${_dir}/../../.." ABSOLUTE) include("${_dir}/@PROJECT_NAME@-targets.cmake") set(BAR_INCLUDE_DIRS "${_prefix}/include/@PROJECT_NAME@") or possibly better: # libbar/bar-config.cmake.in: FIND_PACKAGE(FOO PATHS @FOO_DIR@ NO_DEFAULT_PATH) get_filename_component(_dir "${CMAKE_CURRENT_LIST_FILE}" PATH) get_filename_component(_prefix "${_dir}/../../.." ABSOLUTE) include("${_dir}/@PROJECT_NAME@-targets.cmake") set(BAR_INCLUDE_DIRS "${_prefix}/include/@PROJECT_NAME@") This will make the user of bar-config.cmake include the same foo- config.cmake and, thus, foo-targets.cmake that bar's CMakeLists.txt has included, too. See also FIND_PACKAGE()'s NAMES / CONFIGS clauses. BTW, find modules / config files should provide a *_LIBRARIES variable even if they use imported targets, e.g.: SET(FOO_LIBRARIES foo-shared) Regards, Michael PS: The baz project on GitHub only contains a README. -- Powered by www.kitware.com Visit other Kitware open-source projects at http://www.kitware.com/opensource/opensource.html Please keep messages on-topic and check the CMake FAQ at: http://www.cmake.org/Wiki/CMake_FAQ Follow this link to subscribe/unsubscribe: http://www.cmake.org/mailman/listinfo/cmake
[CMake] transitive linking with separate projects
Hei hei, we faced a build problem with transitive linking of separate projects where I can't find the right solution on my own. I hope someone can give me a hint. I prepared a test case with two libraries libfoo and libbar and an application baz. libfoo is on his own, libbar calls a function from libfoo and baz calls the function from libbar calling libfoo. So the dependencies are like this: baz -> libbar -> libfoo baz doesn't need to know of libfoo because it just calls libbar, so I thought. Now the projects are separated and both libraries come with cmake package configuration files. For linking libfoo in libbar I do the following: find_package(FOO) target_link_libraries(BAR_SRC foo-shared) foo-shared is the target libfoo exports via cmake package configuration. This works and ldd shows libbar is correctly linked against libfoo. Now when compiling baz I more or less do the same: find_package(BAR) target_link_libraries(BAZ_SRC bar-shared) However building baz fails with the following error: % make [100%] Building C object src/CMakeFiles/baz.dir/baz.c.o Linking C executable baz /usr/bin/ld: cannot find -lfoo-shared collect2: ld returned 1 exit status make[2]: *** [src/baz] Fehler 1 make[1]: *** [src/CMakeFiles/baz.dir/all] Fehler 2 make: *** [all] Fehler 2 It seems like cmake tries to link against libfoo here but does not know anything about it. If I add find_package(FOO) to baz obviously the target is imported from libfoo cmake package files. The question is, if I know nothing about the requirements of libbar and want to avoid adding find_package statements for those requirements to baz, how would I do this? I put all the code on GitHub, so if someone maybe could have a look? https://github.com/LeSpocky/libfoo https://github.com/LeSpocky/libbar https://github.com/LeSpocky/baz Greets Alex -- »With the first link, the chain is forged. The first speech censured, the first thought forbidden, the first freedom denied, chains us all irrevocably.« (Jean-Luc Picard, quoting Judge Aaron Satie) *** GnuPG-FP: 02C8 A590 7FE5 CA5F 3601 D1D5 8FBA 7744 CC87 10D0 *** -- Powered by www.kitware.com Visit other Kitware open-source projects at http://www.kitware.com/opensource/opensource.html Please keep messages on-topic and check the CMake FAQ at: http://www.cmake.org/Wiki/CMake_FAQ Follow this link to subscribe/unsubscribe: http://www.cmake.org/mailman/listinfo/cmake