View Issue Details Jump to Notes ] Print ]
IDProjectCategoryView StatusDate SubmittedLast Update
0010395CMakeCMakepublic2010-03-09 11:062015-03-27 15:56
ReporterAlex Neundorf 
Assigned ToBrad King 
PrioritynormalSeverityminorReproducibilityalways
StatusclosedResolutionfixed 
PlatformOSOS Version
Product VersionCMake-2-8 
Target VersionCMake 2.8.4Fixed in VersionCMake 2.8.4 
Summary0010395: cannot use add_dependencies() for imported libraries (together with externalproject_add())
DescriptionHi,

I want to use externalproject_add(), and in order to make sure that the external project (log4cplus) is built before my targets which link against it, I tried to create the dependency by creating an imported library, which depends on the externalproject-target, and then link against this imported library:

externalproject_add(EP_log4cplus
       SOURCE_DIR ${CMAKE_SOURCE_DIR}/Packages/log4cplus/log4cplus-1.0.3
       DOWNLOAD_COMMAND ""
       INSTALL_DIR ${CMAKE_BINARY_DIR}/Packages/Install
       CONFIGURE_COMMAND <SOURCE_DIR>/configure --prefix=<INSTALL_DIR>
       BUILD_COMMAND make -j4
       )

add_library(log4cplus UNKNOWN IMPORTED)
set_property(TARGET log4cplus PROPERTY
  IMPORTED_LOCATION ${CMAKE_BINARY_DIR}/Packages/Install/lib/liblog4cplus.so )
add_dependencies(log4cplus EP_log4cplus)

...
add_executable(foo main.cpp)
target_link_libraries(foo log4cplus)

When I try to do this, cmake complains:
trunk/build-281/shared/tests/SystemInformation> make
CMake Error at CMakeLists.txt:31 (add_dependencies):
  add_dependencies Adding dependency to non-existent target: log4cplus


It would be nice if this could be made to work.
Otherwise I didn't find an easier way than additionally to linking against the library, also make the target dependent on the external project target:

target_link_libraries(foo -llog4cplus)
add_dependencies(foo EP_log4cplus)

It would be much more elegant if I could avoid the add_dependencies() call here and instead just use the imported library.

Alex
TagsNo tags attached.
Attached Filestxt file icon CMakeLists.txt [^] (227 bytes) 2010-03-09 16:02 [Show Content]

 Relationships
related to 0011598closedBrad King Two 'ALL_BUILD' projects into generated solution 
related to 0015414closedBrad King Consider add_dependencies for INTERFACE libraries. 

  Notes
(0019782)
Alex Neundorf (developer)
2010-03-09 16:07

The attached CMakeLists.txt basically shows what I want to do.
(for real use I would not want to make it depend on the "hello" target but on the external-project target).
I understand that cmake says it can't do this, because it doesn't have any rules for the imported target. Still it would be nice if this was possible.
Maybe something like a custom target could be created for each imported target, but with an empty body (does nothing, depends on nothing).
Then add_dependencies() could be used to add dependencies.

Alex
(0021499)
Brad King (manager)
2010-07-27 15:49

We just need a target property on the imported target that names another target known to provide it (the external project target in this case). For example:

  set_property(TARGET log4cplus PROPERTY DEPENDS EP_log4cplus)

says that in order to use log4cplus the EP_log4cplus target must be up to date.
When add_dependencies is asked to depend on log4cplus it can replace it with EP_log4cplus automatically.
(0021502)
Alex Neundorf (developer)
2010-07-27 16:03

" set_property(TARGET log4cplus PROPERTY DEPENDS EP_log4cplus)
 
says that in order to use log4cplus the EP_log4cplus target must be up to date."

Isn't that the same as
"add_dependencies(log4cplus EP_log4cplus)" tries to express ?

With the following cmake code:

add_library(log4cplus UNKNOWN IMPORTED)
set_property(TARGET log4cplus PROPERTY
   IMPORTED_LOCATION
   ${CMAKE_BINARY_DIR}/Packages/Install/lib/liblog4cplus.so )
add_dependencies(log4cplus EP_log4cplus) "
 
I wanted to make it work that
target_link_libraries(foo log4cplus)
automatically triggers building EP_log4cplus.
So the target_link_libraries() would then actually have to check that target property, not add_dependencies(), right ?
I mean, I wouldn't need the add_dependencies() then anymore, right ?

Alex
(0021503)
Brad King (manager)
2010-07-27 16:14

Yes, add_dependencies can be an interface to accomplish the same goal. I was thinking in the mindset that all information for an imported target is always set as properties.

Other than teaching add_dependencies() to accept imported targets as their first (but not second or later) argument, the place to change is cmComputeTargetDepends::AddTargetDepend. The code

  // Check the target's makefile first.
  cmTarget* dependee =
    depender->GetMakefile()->FindTarget(dependee_name);

  // Then search globally.
  if(!dependee)
    {
    dependee = this->GlobalGenerator->FindTarget(0, dependee_name);
    }

should be replaced with

  cmTarget* dependee =
    depender->GetMakefile()->FindTargetToUse(dependee_name);

Then the rest of the method must be taught to deal with imported targets.
(0021504)
Brad King (manager)
2010-07-27 16:16

Actually the rest of cmComputeTargetDepends::AddTargetDepend should not try to deal directly with imported targets. Instead, if it sees that it got an imported target from FindTargetToUse, it should recursively invoke itself on the GetUtilities() entries of the imported target and then return.
(0021505)
Brad King (manager)
2010-07-27 16:20

It looks like some of the VS generators have not been updated to use the results of cmComputeTargetDepends. Places like cmGlobalVisualStudio71Generator::WriteProjectDepends will also need to be taught to follow dependencies through imported targets and leave out the imported targets themselves.
(0021528)
Nicole Aucoin (reporter)
2010-07-28 16:00

I'm struggling with this issue as well, I have a custom target that I'm adding that has to be run after a few external projects have finished. I've added the target properties to the custom target, but it's still running and failing before the output of the external project build steps are done.
Should I just try to craft another external project for my custom command?
(0021529)
Brad King (manager)
2010-07-28 16:03

If it is not an imported target then it is not the same as this issue. For a custom target, just use

  add_dependencies(mycustomtarget myexternalproject)
(0021530)
Nicole Aucoin (reporter)
2010-07-28 16:11

Apologies, from the code snippet above it seemed that I had a similar issue with an external project. Your add_dependencies suggestion fixed my problem, thanks!

For reference: The DEPENDS in the add custom target can't point at an external project, so this doesn't work:
ExternalProject_Add(
  myexternalproject
[...]
)
ADD_CUSTOM_TARGET (mycustomtarget ALL
[...]
DEPENDS myexternalproject
[...]
)
(0021591)
devurandom (reporter)
2010-08-01 17:17

I am also experiencing this issue: http://www.cmake.org/pipermail/cmake/2010-August/038646.html [^]
Would be nice to have a solution, however it may look like.
(0022218)
David Cole (manager)
2010-09-14 09:19

We will not be addressing this for the upcoming CMake 2.8.3 release. Partial progress towards this goal, but ran out of time. Changing target release value back to empty for now.
(0023477)
Brad King (manager)
2010-11-22 09:16

After some major rework of target dependencies in the VS generators to use cmComputeTargetDepends results, this feature is now possible:

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=e01cce28 [^]

 Issue History
Date Modified Username Field Change
2010-03-09 11:06 Alex Neundorf New Issue
2010-03-09 11:06 Alex Neundorf Status new => assigned
2010-03-09 11:06 Alex Neundorf Assigned To => Brad King
2010-03-09 11:09 Bill Hoffman Assigned To Brad King => David Cole
2010-03-09 16:02 Alex Neundorf File Added: CMakeLists.txt
2010-03-09 16:07 Alex Neundorf Note Added: 0019782
2010-07-27 15:49 Brad King Note Added: 0021499
2010-07-27 16:03 Alex Neundorf Note Added: 0021502
2010-07-27 16:14 Brad King Note Added: 0021503
2010-07-27 16:16 Brad King Note Added: 0021504
2010-07-27 16:20 Brad King Note Added: 0021505
2010-07-28 16:00 Nicole Aucoin Note Added: 0021528
2010-07-28 16:03 Brad King Note Added: 0021529
2010-07-28 16:11 Nicole Aucoin Note Added: 0021530
2010-08-01 17:17 devurandom Note Added: 0021591
2010-08-18 00:32 David Cole Assigned To David Cole => Brad King
2010-08-31 17:54 David Cole Target Version => CMake 2.8.3
2010-09-14 09:19 David Cole Note Added: 0022218
2010-09-14 09:19 David Cole Target Version CMake 2.8.3 =>
2010-11-10 12:58 David Cole Target Version => CMake 2.8.4
2010-11-22 09:16 Brad King Note Added: 0023477
2010-11-22 09:17 Brad King Status assigned => closed
2010-11-22 09:17 Brad King Resolution open => fixed
2010-12-13 08:53 Brad King Relationship added related to 0011598
2011-01-12 07:24 David Cole Fixed in Version => CMake 2.8.4
2015-03-27 15:56 Brad King Relationship added related to 0015414


Copyright © 2000 - 2018 MantisBT Team