Re: [CMake] Static Libraries and target_link_libraries

2019-01-28 Thread Puetz Kevin A
I often hit this, particularly with header-only INTERFACE libraries where I 
just want to pick up their defines/include paths, and then CMake ends up 
treating the target_link_libraries(PRIVATE as public anyway). So it would 
definitely be helpful to have a warning that this doesn’t do what you’d expect, 
and maybe a pointer to $ which seems to be the 
only way to actually have a private (not listed in the exported 
 dependency while building a static library.

From: CMake [mailto:cmake-boun...@cmake.org] On Behalf Of Marc CHEVRIER
Sent: Friday, January 25, 2019 8:54 AM
To: Cmake Mailing List ; Andrew Bell 
Subject: Re: [CMake] Static Libraries and target_link_libraries

It is quite inexact because a target can store many information like include 
directories or preprocessor definitions for example (through properties like 
INCLUDE_DIRECTORIES or COMPILE_DEFINITIONS).

So it make sense to enable to specify link libraries to a static library using 
PRIVATE or PUBLIC to ensure various settings are propagated to the static 
library compilation step.
Le 25 janv. 2019 à 15:46 +0100, Andrew Bell 
mailto:andrew.bell...@gmail.com>>, a écrit :


When creating a static library, you can still use the function 
"target_link_libraries" even though the static library is never linked, as 
such.  What you're doing is creating a dependency record for cmake so that 
target_link_libraries of a static library are included in a link of some other 
target which depends on the static library.  What seems confusing is that 
target_link_libraries accepts the keywords PUBLIC and PRIVATE as well as 
INTERFACE when used with a static library, since only INTERFACE really makes 
sense in this context.

Would it be beneficial to issue a warning when someone uses PUBLIC or PRIVATE 
with target_link_libraries on a static library to make it clear that they may 
not be understanding what's going on?

--
Andrew Bell
andrew.bell...@gmail.com
--

Powered by www.kitware.com

Please keep messages on-topic and check the CMake FAQ at: 
http://www.cmake.org/Wiki/CMake_FAQ

Kitware offers various services to support the CMake community. For more 
information on each offering, please visit:

CMake Support: http://cmake.org/cmake/help/support.html
CMake Consulting: http://cmake.org/cmake/help/consulting.html
CMake Training Courses: http://cmake.org/cmake/help/training.html

Visit other Kitware open-source projects at 
http://www.kitware.com/opensource/opensource.html

Follow this link to subscribe/unsubscribe:
https://cmake.org/mailman/listinfo/cmake
-- 

Powered by www.kitware.com

Please keep messages on-topic and check the CMake FAQ at: 
http://www.cmake.org/Wiki/CMake_FAQ

Kitware offers various services to support the CMake community. For more 
information on each offering, please visit:

CMake Support: http://cmake.org/cmake/help/support.html
CMake Consulting: http://cmake.org/cmake/help/consulting.html
CMake Training Courses: http://cmake.org/cmake/help/training.html

Visit other Kitware open-source projects at 
http://www.kitware.com/opensource/opensource.html

Follow this link to subscribe/unsubscribe:
https://cmake.org/mailman/listinfo/cmake


Re: [CMake] CMake 3.9 change to dependencies of object compilation

2017-08-04 Thread Puetz Kevin A
> -Original Message-
> From: Ben Boeckel [mailto:ben.boec...@kitware.com]
> Sent: Friday, August 04, 2017 12:55 PM
> To: Puetz Kevin A <puetzkev...@johndeere.com>
> Cc: cmake@cmake.org; Robert Maynard <robert.mayn...@kitware.com>
> Subject: Re: CMake 3.9 change to dependencies of object compilation
> 
> On Fri, Aug 04, 2017 at 17:35:53 +, Puetz Kevin A wrote:

> > > > 2. MSVC's #import construct which needs the indirect dependencies
> > > > (dependencies of the #import-ed dependency) be registered, which
> > > > is handled as part of the target using add_custom_command(TARGET
> > > > foo POST_BUILD COMMAND ...)
> > >
> > > So there's an issue here that there's a dependency between your
> > > build rules which CMake doesn't know about (though I don't know
> > > #import well enough, the docs don't state where the information
> *goes*).
> >
> > #import will load a COM typelib during preprocessing, possibly
> > following registry keys to locate other typelibs which the specified
> > one refers to. It will have the byproduct of creating .tlh/.tli files
> > next to the other compiler outputs (e.g. .o file) Arguably the
> > .tlh/.tli files should be listed in OBJECT_OUTPUTS, but I can't
> > because I don't know their location; CMake doesn't have a
> > variable/property/generator expression that reveals where it's going
> > to place the object files (i.e. /Fo$out), so I don't know where they
> > will end up. Luckily the .tlh/.tli files aren't important to list for
> > dependency resolution anyway, because the #import also automatically
> > #includes the just-generated headers, (though this is not mentioned in
> > /showIncludes). So CMake is at least *consistently* unaware of these
> > files, and they get regenerated any time they would have been read so
> > it doesn't really need to know.
> 
> OK, a genex for where object outputs may be useful anyways. I think there's
> something along those lines with Cuda's PTX file generation?

It would also be really nice for things like precompiled headers; I have some 
custom commands where it really feels right to put their outputs with the other 
object files for a target (this automatically getting things right for 
multi-configuration generators and such), but can't because there's no 
expression for that. Something like $ would be very welcome.

> > The important missing dependency is the one between
> > creating/regstering the typelib (we'll call this target COMServer) and
> > the #import that will read it in a source file in another target
> > (we'll call it COMClient).  I have a call add_custom_command(TARGET
> > COMServer POST_BUILD COMMAND regsvr32 $ COMServer>),
> > which will create the registry keys under HKEY_CLASSES_ROOT. This
> > needs to happen before the source file in COMClient can preprocess the
> > #import successfully. Prior to CMake 3.9, I could inform CMake of this
> > by just using add_dependencies(COMClient COMServer) to tell CMake that
> > it couldn't build (any of) Client until Server had been built (and
> > thus its POST_BUILD had also run to register it). But in 3.9,
> > add_dependencies has changed in meaning; although the documentation
> > still says "to ensure that they build before  does", in
> > practice this now only means "to ensure that they build before
> >  *links*"; these edges do not apply to object compilation or
> > add_custom_command rules.
> >
> > add_custom_command is no problem; it already had a DEPENDS argument
> > that allows target-level dependencies, and arguably such dependencies
> > needed to be stated there anyway since an add_custom_command output
> > can get reused by multiple targets in the same subdir. But object
> > compilation is a problem because there's nowhere to add them
> > per-source, and add_dependencies doesn't work anymore to add them
> > per-target.
> 
> It sounds like the logic may need fixing then. Do you have an example case
> where add_dependencies doesn't work anymore in Ninja?

CMakeLists.txt:
cmake_minimum_required(VERSION 3.7)

add_library(A SHARED a.c)

add_custom_command(TARGET A POST_BUILD
COMMENT "hello A"
COMMAND ${CMAKE_COMMAND} -E sleep 3
COMMAND ${CMAKE_COMMAND} -E echo "hello A")

add_custom_command(OUTPUT b.custom
COMMENT "hello B"
COMMAND ${CMAKE_COMMAND} -E touch b.custom)

add_executable(B b.c b.custom)
add_dependencies(B A)

a.c:
void foo() {}

b.c:
int main() { return 0; }

In CMake 3.7:

build cmake_order_depends_target_B: phony || A.dll b.custom
build b.custom: CUSTOM_COMMAND || A.dll
build CMakeFiles

Re: [CMake] CMake 3.9 change to dependencies of object compilation

2017-08-04 Thread Puetz Kevin A
> -Original Message-
> From: Robert Maynard [mailto:robert.mayn...@kitware.com]
> Sent: Friday, August 04, 2017 1:03 PM
> To: Ben Boeckel <ben.boec...@kitware.com>
> Cc: Puetz Kevin A <puetzkev...@johndeere.com>; cmake@cmake.org
> Subject: Re: CMake 3.9 change to dependencies of object compilation
> 
> You can find the location for object files by using
> $<TARGET_OBJECTS:${name}>. This can be used as the DEPENDS of a custom
> command. I would not try using OBJECT_OUTPUTS as IIRC that is only used by
> the makefile generator.

Isn't TARGET_OBJECTS  only for OBJECT libraries? I don't think it would give me 
a way to get the paths for the .o file that's going to result from a particular 
source file (in order to locate other files the compiler is going to generate 
alongside a .o file).

But and in any case, this was a little bit of an aside, just because Ben asked 
what #import generated. It would feel *correct* to inform that the .tlh/.tli 
files were OBJECT_OUTPUTS, but nothing in the processing really *needs* to 
know. The problem I'm having with 3.9 is the input dependency on registry keys 
(previously modeled as a dependency on the target whose POST_BUILD would create 
them), not on the outputs.
 
-- 

Powered by www.kitware.com

Please keep messages on-topic and check the CMake FAQ at: 
http://www.cmake.org/Wiki/CMake_FAQ

Kitware offers various services to support the CMake community. For more 
information on each offering, please visit:

CMake Support: http://cmake.org/cmake/help/support.html
CMake Consulting: http://cmake.org/cmake/help/consulting.html
CMake Training Courses: http://cmake.org/cmake/help/training.html

Visit other Kitware open-source projects at 
http://www.kitware.com/opensource/opensource.html

Follow this link to subscribe/unsubscribe:
http://public.kitware.com/mailman/listinfo/cmake


Re: [CMake] CMake 3.9 change to dependencies of object compilation

2017-08-04 Thread Puetz Kevin A
Thanks for the reply, questions/clarifications below.

> -Original Message-
> From: Ben Boeckel [mailto:ben.boec...@kitware.com]
> Sent: Thursday, August 03, 2017 10:59 AM
> To: cmake@cmake.org
> Cc: Robert Maynard <robert.mayn...@kitware.com>; Puetz Kevin A
> <puetzkev...@johndeere.com>
> Subject: Re: CMake 3.9 change to dependencies of object compilation
> 
> > . The Ninja generator has loosened the dependencies of object
> > compilation. Object compilation now depends only on custom targets and
> > custom commands associated with libraries on which the object's target
> > depends and no longer depends on the libraries themselves. Source
> > files in dependent targets may now compile without waiting for their
> > targets' dependencies to link.
> 
> Correct.
> 
> > We have a few cases where the object compilation really does depend on
> > the TARGET_FILE itself, e.g.
> > 1. An RC compiler embedding the resulting file of a custom target (I
> > think this one may still work, since custom targets appear to have
> > been exempted from the change)
> 
> Correct, though this issue:
> 
> https://gitlab.kitware.com/cmake/cmake/issues/17097
> 
> requests that that be fixed as well (though that is backwards compatible
> since the solution will likely involve ).

Sentence cut off? I assume you meant "will likely involve a new keyword"?

> > 2. MSVC's #import construct which needs the indirect dependencies
> > (dependencies of the #import-ed dependency) be registered, which is
> > handled as part of the target using add_custom_command(TARGET foo
> > POST_BUILD COMMAND ...)
> 
> So there's an issue here that there's a dependency between your build rules
> which CMake doesn't know about (though I don't know #import well
> enough, the docs don't state where the information *goes*).

#import will load a COM typelib during preprocessing, possibly following 
registry keys to locate other typelibs which the specified one refers to. It 
will have the byproduct of creating .tlh/.tli files next to the other compiler 
outputs (e.g. .o file) Arguably the .tlh/.tli files should be listed in 
OBJECT_OUTPUTS, but I can't because I don't know their location; CMake doesn't 
have a variable/property/generator expression that reveals where it's going to 
place the object files (i.e. /Fo$out), so I don't know where they will end up. 
Luckily the .tlh/.tli files aren't important to list for dependency resolution 
anyway, because the #import also automatically #includes the just-generated 
headers, (though this is not mentioned in /showIncludes). So CMake is at least 
*consistently* unaware of these files, and they get regenerated any time they 
would have been read so it doesn't really need to know.

The important missing dependency is the one between creating/regstering the 
typelib (we'll call this target COMServer) and the #import that will read it in 
a source file in another target (we'll call it COMClient).  I have a call 
add_custom_command(TARGET COMServer POST_BUILD COMMAND regsvr32 $), which will create the registry keys under HKEY_CLASSES_ROOT. This 
needs to happen before the source file in COMClient can preprocess the #import 
successfully. Prior to CMake 3.9, I could inform CMake of this by just using 
add_dependencies(COMClient COMServer) to tell CMake that it couldn't build (any 
of) Client until Server had been built (and thus its POST_BUILD had also run to 
register it). But in 3.9, add_dependencies has changed in meaning; although the 
documentation still says "to ensure that they build before  does", in 
practice this now only means "to ensure that they build before  
*links*"; these edges do not apply to object compilation or add_
 custom_command rules.

add_custom_command is no problem; it already had a DEPENDS argument that allows 
target-level dependencies, and arguably such dependencies needed to be stated 
there anyway since an add_custom_command output can get reused by multiple 
targets in the same subdir. But object compilation is a problem because there's 
nowhere to add them per-source, and add_dependencies doesn't work anymore to 
add them per-target.

> When adding
> this custom command, you may use the `BYPRODUCTS` argument
> (introduced in 3.2.0) to let CMake know what's going on here. It only affects
> Ninja, but the other generators do target-level dependencies anyways. That
> output can then be depended on via `OBJECT_DEPENDS` and the
> dependency should link up properly.

There is not an explicit file output, though I could do the usual workaround of 
a stamp/witness file listed in BYPRODUCTS to the add_custom_command(TARGET ... 
POST_BUILD ...). But I don't think that will work with most generators, since 
CMake doesn't generally allow file-level depends to set

[CMake] CMake 3.9 change to dependencies of object compilation

2017-07-27 Thread Puetz Kevin A
I saw the following in the CMake 3.9 release notes, but didn't immediately 
realize all the implications. Sorry for not catching this during the -rc 
phase...

. The Ninja generator has loosened the dependencies of object compilation. 
Object compilation now depends only on custom targets and custom commands 
associated with libraries on which the object's target depends and no longer 
depends on the libraries themselves. Source files in dependent targets may now 
compile without waiting for their targets' dependencies to link.

We have a few cases where the object compilation really does depend on the 
TARGET_FILE itself, e.g.
1. An RC compiler embedding the resulting file of a custom target (I think this 
one may still work, since custom targets appear to have been exempted from the 
change)

2. MSVC's #import construct which needs the indirect dependencies (dependencies 
of the #import-ed dependency) be registered, which is handled as part of the 
target using add_custom_command(TARGET foo POST_BUILD COMMAND ...)

So. I appreciate this loosening in most cases, it's greatly fixed some 
unnecessary stalls in our parallel build, and for dependencies acquired 
target_link_libraries this seems 100% correct to apply them only to the linker 
rule. But it seems the changes impacted add_dependencies as well, so now how do 
I now express a real dependency between a compile rule and another target (i.e. 
get a target listed at the same level as cmake_object_order_depend_*?

add_custom_command(OUTPUT... DEPENDS...) seemingly still allows target-level 
dependencies for a file compilation step, but I can't figure out what property 
has the same effect on a normal source file (that's going to be built by a 
"built-in" rule like CMAKE_RC_COMPILE_OBJECT, CMAKE_CXX_COMPILE_OBJECT, etc). 
AddFileDependencies(.) (aka OBJECT_DEPENDS) doesn't allow say it allows 
target-level dependencies, and it doesn't seem to work in practice either.

The best I've been able to come up with far requires an indirect SYMBOLIC 
output file to carry the dependency between a phony add_custom_command and the 
real source's OBJECT_DEPENDS

ADD_CUSTOM_COMMAND(OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/foo.depends 
DEPENDS bar)
SET_PROPERTY(SOURCE ${CMAKE_CURRENT_BINARY_DIR}/foo.depends PROPERTY 
SYMBOLIC 1)
SET_PROPERTY(SOURCE source.cpp APPEND PROPERTY OBJECT_DEPENDS 
${CMAKE_CURRENT_BINARY_DIR}/foo.depends)

That works, but it definitely feels more like a workaround than the intended 
solution. If the generators can handle this for add_custom_command, it seems 
like they should be able to handle it for language compile rules too. Any 
better suggestions?


-- 

Powered by www.kitware.com

Please keep messages on-topic and check the CMake FAQ at: 
http://www.cmake.org/Wiki/CMake_FAQ

Kitware offers various services to support the CMake community. For more 
information on each offering, please visit:

CMake Support: http://cmake.org/cmake/help/support.html
CMake Consulting: http://cmake.org/cmake/help/consulting.html
CMake Training Courses: http://cmake.org/cmake/help/training.html

Visit other Kitware open-source projects at 
http://www.kitware.com/opensource/opensource.html

Follow this link to subscribe/unsubscribe:
http://public.kitware.com/mailman/listinfo/cmake