[CMake] custom target isn't rebuilt if depending on another custom target

Gerhard Stengel gerhards2 at ast.dfs.de
Tue Sep 14 05:56:18 EDT 2010


Hello Michael,

thanks, it sheds some light on the matter, but I'm not happy as it is, see comments below.

regards

Gerhard
...
> > 
> > If I create Demo.tar from a clean project, everything's fine. However,
> > the rebuilt isn't performed completely, that is if I touch Demo1.in,
> > just Demo1.out is rebuilt, but not Demo.tar that depends on it! [...]
> 
> Demo.tar does *not* depend on Demo1.out; it has no dependencies at all.
> As a proof - if on *nix - issue "find . -exec grep "Demo\.tar" {} \;"
> in the build directory after cmaking, and you'll see that Demo.tar's
> dependency line doesn't mention any prerequisites after the colon.
Well, I can confirm this, but I actually expected to see targets like cust1 and cust2 here.
(Maybe this is a naiive notion and it's not possible to list targets as dependencies, I'm no expert to make ;-)

> 
> > [...] This seems wrong to me because I
> > expect that if the target cust1 is rebuild, even the target cust3 has to
> > be rebuilt due to the relation established by the add_dependencies()
> > command!
> 
> Rebuilding cust3 doesn't regenerate Demo.tar due to its lack of
> dependencies if it already exists. So, Demo.tar is generated at
> the first time and that's it, unless the file is removed later.
But what is then the purpose of the add_dependencies command if it only works the *first* time and never again?

For me the term "cust3 depends on cust1" means two things when make checks cust3:
1) if cust1 (and all associated files) are not built yet, they shall be generated. Then cust3 is generated.
2) if cust1 has been updated, cust3 is re-generated

If add_dependencies() only covers case #1, it seems to me quite useless.

> 
> > The problem seems to be that add_dependencies() doesn't realize that if
> > cust1 or cust2 becomes out of date cust3 has to be rebuilt, too.
> 
> It does, but rebuilding cust3 doesn't do what you expect, see above.
> 
> > The solution using file level dependencies (see commented out command)
> > would work, [...]
> 
> ...and is the correct one...
> 
> > [...] but in my project it's not really
> > possible to do so because the "source" custom targets which the "final"
> > custom target takes as input contain lots of files.
> 
> First of all, is it possible to simplify your CMakeLists.txt? Unless
> you really need cust{1,2} as top-level targets they aren't necessary
> if Demo{1,2}.out are mentioned as dependencies in Demo.tar's custom
> command and if these commands all reside in the same CMakeLists.txt.
> Furthermore, you could even use
> 
> ADD_CUSTOM_TARGET(Demo.tar ALL
>   COMMAND ${CMAKE_COMMAND} -E tar cvf Demo.tar Demo1.out Demo2.out
>   DEPENDS Demo1.out Demo2.out)
> 
> instead of Demo.tar's custom command if you don't need Demo.tar as an
> ingredient for another target and, again, if these commands/targets
> are defined in the same CMakeLists.txt.
> 
Well, the problem is in fact that each custom target and the associated files reside in an own folder, and some of these 
custom targets resp. files depend on each other. To be more precise, when the *.out files are generated from the *.in 
files, the generator needs some other *.out files (from different folders). The *.in files include the *.out files and 
the generator tool reads this information. 
My idea was to "group" each folders *.out files into an own custom target. If the generation process needs certain files 
from a certain folder, I would just establish a target level dependency with add_dependencies() to this folder's custom 
target.

The beauty of this solution is that these targets are known globally. To exchange lists of files between folders in a 
tree structure becomes a pain with cmakes handling of variable scopes :-/ 
The only solution I can think of right now would be to use SET(VAR ... PARENT_SCOPE). Is there anything better?

> > Is there an easy workaround or is this a cmake bug?
> 
> No bug. ;) Without further knowledge of your project, the best advice
> one can give is to use lists, loops, functions and properties to cope
> with large numbers of files in the CMakeLists.txt.
> 
> 'hope that helps.
> 
> Regards,
> 
> Michael


More information about the CMake mailing list