[CMake] Get linker flags / include directories for a library target

Unknown ax487 at gmx.de
Sat Jan 5 08:42:19 EST 2019


On Sat, 2018-12-29 at 16:06 -0500, frodak17 wrote:
> On Fri, Dec 28, 2018 at 6:04 PM Unknown <ax487 at gmx.de> wrote:
> > I would like to thank all of you for your suggestions. I have
> > gathered
> > 
> > the following (correct me if I am wrong):
> > 
> > 
> > 
> > - The LINK_FLAGS target property is used in cmake 2.x, the
> > 
> >   INTERFACE_LINK_LIBRARIES in cmake 3.x, the latter contains a ;-
> > list
> > 
> >   of libraries.
> > 
> > - The list may contain generator expressions, it is however
> > 
> >   possible to to use file(GENERATE ..) to obtain evaluate those.
> > 
> > - In any case, the library list contains libraries having
> > different 
> > 
> >   formats (see [1]), full paths, (imported) targets, and plain
> > names.
> > 
> > - When Makefiles (or files for other build systems) are generated,
> > 
> >   the list is turned into -L/-l flags used by ld. This happens
> > 
> >   on the C++ side of things, the functionality is not exposed
> > 
> >   to cmake scripts.
> > 
> > 
> > 
> > As for automatic generation of a pkg-config .pc file, there have
> > 
> > been some inquiries ([2], [3], and [4]), the last one being rather
> > 
> > recent.
> > 
> > 
> > 
> > The answers point out that pkg-config files can be generated using
> > 
> > configure_file(...), that cmake has its own (imported target)
> > method
> > 
> > for handling dependencies.
> > 
> > 
> > 
> > I don't mean to be disrespectful or unappreciative of the work put
> > 
> > into cmake (in fact I think it is a vast improvement over
> > automake),
> > 
> > but since there is no way to obtain the required information
> > 
> > programatically, all users of my library have to either use
> > 
> > cmake themselves, or use non-portable workarounds which are prone
> > 
> > to break sooner than later. 
> > 
> > 
> > 
> > If I want to use an external tool (think setup.py) to build
> > 
> > extensions (in-place or not), the same problem occurs.
> > 
> > 
> > 
> > This is rather disappointing to be honest...
> > 
> > 
> > 
> > ax487
> > 
> > 
> > 
> > 
> 
> The answer to [2] was that the information required to automatically
> generate 
> a .pc file was not available. 
> https://linux.die.net/man/1/pkg-config
> https://people.freedesktop.org/~dbn/pkg-config-guide.html#writing 
> I don't see how CMake could know which packages your library
> conflicts with or which versions of which libraries are required.For
> example a library target can link against an imported target but it
> won't know that only imported target version 1.0.0 is compatible as
> opposed to versions >= 1.5.
> 
> 
> 
> 
> It seems that you are trying to provide more than how to link
> against 
> your library but also against everything your library wants to be
> linked
>  against.
> 
> For example the .pc file you want generated contains "Libs:
> -L${libdirbar} 
> -L${libdirfoo} 
> 
> -lbar -lfoo".But that isn't the proper way of a .pc file should
> reference separate libraries it should use the Requires field.
> 
> Also if your library is linking against an imported library
> `libbaz::libbaz` how is this library being provided to the people
> using your library?Are you trying to generate a .pc file for the
> imported library because it didn't provide one and incorporate the
> flags into library you are creating?
> I think that no one has volunteered to write a CMake package to
> create .pc files is because generating a .pc file is pretty simple.
> It's just a template and a configure_file() command.
> https://cmake.org/pipermail/cmake/2018-March/067293.html
> 
> 

Thank you for your reply,

As for the answer provided in [2]: I don't expect conflict or version
detection to be conducted automatically. Clearly, you have to require
the correct packages in the correct versions,
and you have to pass that information along to a generated pc file,
that much is clear. But I think that the same holds true for imported
targets, unless something really
clever happens in the background which I am not aware of.

You are quite right in assuming that I want to (mis-)use the Libs /
Libs.private field. I would of course prefer the Requires field, but
unfortunately a lot of my dependencies don't
generate pc files either, so I don't really see any other way to get
pkg-config working.

A dependency of the form libbaz::libbaz would be provided as an
imported target. That is, the authors of libbaz are using cmake as
well, and they are installing a target.
I am assuming that the users of my library have the dependency libbaz
installed as well. I simply want to pass that information along in a
format understood by pkg-config.
I would also go through the dependency libraries, but I doubt that any
contributions of pc file generators to those projects would be
accepted.

Regarding the fact that no one has written a generator for .pc files:
It is obviously possible to use configure_file templates. In fact it is
quite easy. But it hinges on the libraries as well.
The post you mention references a project which generates linker flags
by hand. You see that the CMakeLists.txt contains a lot of lines like
this one:


set(PKGCONF_LIBS_PRIV "${PKGCONF_LIBS_PRIV} -lbass -lbassmidi")

This works as long as all dependencies are in a precisely known format,
i.e. a list of -l flags. In fact, I think the approach would still work
if the authors were to use the built-in pkg-config 
find scripts for their dependencies. But this approach will break down
immediately once they add an imported target as a dependency. Note that
the authors also use the Libs.private
field instead of the Requires field :)


-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://cmake.org/pipermail/cmake/attachments/20190105/45248661/attachment.html>


More information about the CMake mailing list