CMake build system status

313 views
Skip to first unread message

Alexey Kutumov

unread,
Mar 17, 2013, 6:24:49 AM3/17/13
to rypp...@googlegroups.com
Hi everybody!

I worked on the CMake build system. I partially finished the building documentation:
* the standalone documentation for all libraries was generated;
* the full documentation (doc/src/boost.xml) was generated;
* the PDF support is enabled via XEP (fop and DBLATEX seem to be unusable).

However, there are still some unresolved CMake issues including:
* testing support;
* documentation dependencies (css, static html, images);
* Double CMake invocation;
* xsltproc under win32 cannot process long input args (cannot process boost.xml);
** it prints following message: MAX_PATHS reached: too many paths
** maybe this issue can be fixed by rebuilding xsltproc.


Additionally, some work is necessary for the documentation:
* documentation for the CMake modules (I added documentation only for several CMake modules);
* some documentation still has issues, e.g.: missed images, wrong document structure. I think that documentation needs to be carefully reviewed.

I checked CMake support only under:
* Linux + gcc-4.7.2 (without PDF)
* Windows XP + MSVC-2008 (with PDF, without atomic and lockfree libs)

If we need more detailed report about current CMake status, I'll write it during this week.

Also, I'm going on vacation for a month in a week, so I'll continue to work with the CMake build system only in a month.

Bill Hoffman

unread,
Mar 18, 2013, 10:20:19 AM3/18/13
to rypp...@googlegroups.com
On 3/17/2013 6:24 AM, Alexey Kutumov wrote:
> * Double CMake invocation;
What is this issue?

Also, some folks at Kitware have tried this build and said that there is
no way to turn off modules. Is this still the case?

Thanks.

-Bill

Alexey Kutumov

unread,
Mar 18, 2013, 1:22:54 PM3/18/13
to rypp...@googlegroups.com


понедельник, 18 марта 2013 г., 21:20:19 UTC+7 пользователь Bill Hoffman написал:
On 3/17/2013 6:24 AM, Alexey Kutumov wrote:
> * Double CMake invocation;
What is this issue?
 
Also, some folks at Kitware have tried this build and said that there is
no way to turn off modules.   Is this still the case?
Yes, this can be an issue, i didn't have enough time before vacation to check various build configurations.
 
Thanks.

-Bill

Dave Abrahams

unread,
Mar 19, 2013, 11:45:59 PM3/19/13
to Alexey Kutumov, rypp...@googlegroups.com

on Mon Mar 18 2013, Alexey Kutumov <alexey.kutumov-AT-gmail.com> wrote:

> понедельник, 18 марта 2013 г., 21:20:19 UTC+7 пользователь Bill
> Hoffman написал:
>
> On 3/17/2013 6:24 AM, Alexey Kutumov wrote:
> > * Double CMake invocation;
> What is this issue?
>
> You can find more info here: https://groups.google.com/d/topic/
> ryppl-dev/EMIKsYZYaFE/discussion

Basically, it boils down to the fact that (ahem) we're waiting patiently
for CMake 2.8.11 so we can get rid of this hack. Months ago, Daniel
told me it was about to be released. Was there a snag?

> Also, some folks at Kitware have tried this build and said that
> there is no way to turn off modules. Is this still the case?
>
> Yes, this can be an issue, i didn't have enough time before vacation
> to check various build configurations.

What does "turn off modules" mean?

--
Dave Abrahams

Stephen Kelly

unread,
Mar 20, 2013, 8:58:30 AM3/20/13
to rypp...@googlegroups.com, Alexey Kutumov

On Wednesday, March 20, 2013 4:45:59 AM UTC+1, Dave Abrahams wrote:

on Mon Mar 18 2013, Alexey Kutumov <alexey.kutumov-AT-gmail.com> wrote:

> понедельник, 18 марта 2013 г., 21:20:19 UTC+7 пользователь Bill
> Hoffman написал:
>
>     On 3/17/2013 6:24 AM, Alexey Kutumov wrote:
>     > * Double CMake invocation;
>     What is this issue?
>
> You can find more info here: https://groups.google.com/d/topic/
> ryppl-dev/EMIKsYZYaFE/discussion

Basically, it boils down to the fact that (ahem) we're waiting patiently
for CMake 2.8.11 so we can get rid of this hack.  Months ago, Daniel
told me it was about to be released.  Was there a snag?



There is a release-candidate available for 2.8.11, but the 'interface
targets' feature discussed in the above thread is not part of it. It was
deferred to the following release.

 http://thread.gmane.org/gmane.comp.programming.tools.cmake.devel/6395

I'm not sure why that feature is needed to resolve the 'run cmake twice'
issue. I tried to build the current state of the boost-cmake stuff, but I'm
having trouble even finding the right repos and fighting with submodules. I
was going to wait until the git transition was done before bringing up the
cmake issue again.

Thanks,

Steve.
 

Bill Hoffman

unread,
Mar 20, 2013, 12:09:52 PM3/20/13
to rypp...@googlegroups.com
On 3/19/2013 11:45 PM, Dave Abrahams wrote:
>> Yes, this can be an issue, i didn't have enough time before vacation
>> >to check various build configurations.
> What does "turn off modules" mean?
I have heard that it either builds everything or nothing. There is no
way to turn of boost modules that you do not want to build. Say you
don't care about MPI, but have MPI on your system, it builds MPI boost
stuff.

-Bill

Alexey Kutumov

unread,
Mar 20, 2013, 12:11:52 PM3/20/13
to rypp...@googlegroups.com, Alexey Kutumov
You can find latest sources here: https://github.com/boost-cmake/boost-zero.



среда, 20 марта 2013 г., 19:58:30 UTC+7 пользователь Stephen Kelly написал:

Stephen Kelly

unread,
Mar 20, 2013, 12:51:51 PM3/20/13
to rypp...@googlegroups.com, Alexey Kutumov
Alexey Kutumov wrote:

> You can find latest sources here:
> https://github.com/boost-cmake/boost-zero.

I'm already using that remote master branch.

I think the problem is more about having adequate instructions. I've run

 git submodule foreach 'git checkout cmake/master'

where the cmake remote is of the form

 g...@github.com:boost-cmake/any.git

Except for the ryppl repo, where one has to checkout cmake/develop instead
(why the difference)?

Still, when I create a clean build dir and run cmake I get a lot of output
like this:

.
CMake Error at CMakeLists.txt:21 (add_subdirectory):
  add_subdirectory given source "doc" which is not an existing directory.


CMake Error at ryppl/cmake/Modules/RypplDocumentation.cmake:219
(add_dependencies):
  add_dependencies Adding dependency to non-existent target: documentation
Call Stack (most recent call first):
  ryppl/CMakeLists.txt:35 (export_documentation)


CMake Error at ryppl/cmake/Modules/RypplDocumentation.cmake:154
(add_dependencies):
  add_dependencies Adding dependency to non-existent target: documentation
Call Stack (most recent call first):
  ryppl/cmake/Modules/RypplDocumentation.cmake:325 (generate_standalone_doc)
  ryppl/CMakeLists.txt:35 (export_documentation)


CMake Error at ryppl/cmake/Modules/RypplDocumentation.cmake:219
(add_dependencies):
  add_dependencies Adding dependency to non-existent target: documentation
Call Stack (most recent call first):
  boost/accumulators/doc/CMakeLists.txt:153 (export_documentation)

 (continues)


Any idea what's going wrong?

Thanks,

Steve.

Dave Abrahams

unread,
Mar 20, 2013, 11:51:46 PM3/20/13
to Stephen Kelly, rypp...@googlegroups.com, Alexey Kutumov, Daniel Pfeifer

on Wed Mar 20 2013, Stephen Kelly <steveire-AT-gmail.com> wrote:

> On Wednesday, March 20, 2013 4:45:59 AM UTC+1, Dave Abrahams wrote:
>>
>>
>> on Mon Mar 18 2013, Alexey Kutumov <alexey.kutumov-AT-gmail.com> wrote:
>>
>> > понедельник, 18 марта 2013 г., 21:20:19 UTC+7 пользователь Bill
>> > Hoffman написал:
>> >
>> > On 3/17/2013 6:24 AM, Alexey Kutumov wrote:
>> > > * Double CMake invocation;
>> > What is this issue?
>> >
>> > You can find more info here: https://groups.google.com/d/topic/
>> > ryppl-dev/EMIKsYZYaFE/discussion
>>
>> Basically, it boils down to the fact that (ahem) we're waiting patiently
>> for CMake 2.8.11 so we can get rid of this hack. Months ago, Daniel
>> told me it was about to be released. Was there a snag?
>>
>>
>
> There is a release-candidate available for 2.8.11, but the 'interface
> targets' feature discussed in the above thread is not part of it. It was
> deferred to the following release.
>
> http://thread.gmane.org/gmane.comp.programming.tools.cmake.devel/6395

:(

> I'm not sure why that feature is needed to resolve the 'run cmake twice'
> issue.

Daniel is the one to answer that question, but I guess he's been kinda
busy lately.

> I tried to build the current state of the boost-cmake stuff, but I'm
> having trouble even finding the right repos and fighting with
> submodules.

Oh, I've been concentrating on other things for the past week but
generating the submodule references is now bumped to the top of my list.

> I was going to wait until the git transition was done before bringing
> up the cmake issue again.

It doesn't need to be completely /done/, but you might need the
submodules. Actually, even that isn't clear to me. I'd really love it
if Daniel could weigh in here.

--
Dave Abrahams

Dave Abrahams

unread,
Mar 20, 2013, 11:53:22 PM3/20/13
to Stephen Kelly, rypp...@googlegroups.com, Alexey Kutumov

on Wed Mar 20 2013, Stephen Kelly <steveire-AT-gmail.com> wrote:

> Alexey Kutumov wrote:
>
>> You can find latest sources here:
>> https://github.com/boost-cmake/boost-zero.
>
> I'm already using that remote master branch.
>
> I think the problem is more about having adequate instructions. I've
> run
>
> git submodule foreach 'git checkout cmake/master'
>
> where the cmake remote is of the form
>
> g...@github.com:boost-cmake/any.git
>
> Except for the ryppl repo, where one has to checkout cmake/develop
> instead
> (why the difference)?
>
> Still, when I create a clean build dir and run cmake I get a lot of
> output
> like this:
>
> .
> CMake Error at CMakeLists.txt:21 (add_subdirectory):
> add_subdirectory given source "doc" which is not an existing
> directory.

<snip>

> (continues)
>
> Any idea what's going wrong?

Are you missing a "git submodule update"?

--
Dave Abrahams

Dave Abrahams

unread,
Mar 20, 2013, 11:56:36 PM3/20/13
to Bill Hoffman, rypp...@googlegroups.com, Daniel Pfeifer
That would surprise me greatly, but again, I guess I need to hear from
Daniel. I know we're not far off because ryppl generates a
CMakeLists.txt that includes only the modules you need, and that works.
If there's some mechanism we're missing for turning individual modules
off when they're present in the source tree, I'm sure it's trivial to
add.

--
Dave Abrahams

Stephen Kelly

unread,
Mar 21, 2013, 9:13:07 AM3/21/13
to rypp...@googlegroups.com, Stephen Kelly, Alexey Kutumov


On Thursday, March 21, 2013 4:53:22 AM UTC+1, Dave Abrahams wrote:
>
> Any idea what's going wrong?

Are you missing a "git submodule update"?

Yes, it appears so, although I'm sure I ran that before too. Now it seems to have updated the doc submodule.

However, I get this with a clean build:

$ make
makeobj[0]: Entering directory `/home/stephen/dev/src/boost-zero/build'
make[2]: *** No rule to make target `boost/accumulators/doc/accumulators.pdf', needed by `boost/accumulators/doc/CMakeFiles/BoostAccumulators-pdf'.  Stop.
make[1]: *** [boost/accumulators/doc/CMakeFiles/BoostAccumulators-pdf.dir/all] Error 2
make[1]: *** Waiting for unfinished jobs....
make[2]: *** No rule to make target `ryppl/cmake.pdf', needed by `ryppl/CMakeFiles/Ryppl-pdf'.  Stop.
make[1]: *** [ryppl/CMakeFiles/Ryppl-pdf.dir/all] Error 2
make[2]: *** No rule to make target `boost/algorithm/string/doc/string_algo.pdf', needed by `boost/algorithm/string/doc/CMakeFiles/BoostStringAlgorithm-pdf'.  Stop.
make[1]: *** [boost/algorithm/string/doc/CMakeFiles/BoostStringAlgorithm-pdf.dir/all] Error 2
make[2]: *** No rule to make target `boost/bimap/doc/bimap.pdf', needed by `boost/bimap/doc/CMakeFiles/BoostBimap-pdf'.  Stop.
make[1]: *** [boost/bimap/doc/CMakeFiles/BoostBimap-pdf.dir/all] Error 2
[  0%] [  0%] Built target boost_system

I'm able to build with -DCMAKE_DISABLE_DOCS=True though.

Thanks,

Steve.



 

Stephen Kelly

unread,
Mar 21, 2013, 9:34:15 AM3/21/13
to rypp...@googlegroups.com, Stephen Kelly, Alexey Kutumov, Daniel Pfeifer

On Thursday, March 21, 2013 4:51:46 AM UTC+1, Dave Abrahams wrote:
> There is a release-candidate available for 2.8.11, but the 'interface
> targets' feature discussed in the above thread is not part of it. It was
> deferred to the following release.
>
>  http://thread.gmane.org/gmane.comp.programming.tools.cmake.devel/6395

:(


The good news is that all of the prerequisite 'supporting' features are done, so the likelyhood of getting this into CMake master shortly after the 2.8.11 release is quite high.
 
Thanks,

Steve.

Alexey Kutumov

unread,
Mar 21, 2013, 12:36:50 PM3/21/13
to rypp...@googlegroups.com, Bill Hoffman, Daniel Pfeifer
I didn't check ryppl support, so it can be broken. I was working only with documentation.

четверг, 21 марта 2013 г., 10:56:36 UTC+7 пользователь Dave Abrahams написал:

Alexey Kutumov

unread,
Mar 21, 2013, 2:00:28 PM3/21/13
to rypp...@googlegroups.com, Stephen Kelly, Alexey Kutumov
I've made some fixes (optional pdf generation and boost/accumulators issue), i've performed compilation and installation of project with documentation (without pdf) from scratch.

четверг, 21 марта 2013 г., 20:13:07 UTC+7 пользователь Stephen Kelly написал:

Eric Niebler

unread,
Mar 21, 2013, 2:04:10 PM3/21/13
to rypp...@googlegroups.com

The accumulators doc build is an unholy mess. I wouldn't be offended at
all if you guys just punted on this. I'm sure with some help from
someone who knows CMake/Doxygen/LaTex I could come up with something better.

Eric
> --
> You received this message because you are subscribed to the Google
> Groups "ryppl-dev" group.
> To unsubscribe from this group and stop receiving emails from it, send
> an email to ryppl-dev+...@googlegroups.com.
> For more options, visit https://groups.google.com/groups/opt_out.
>
>


--
Eric Niebler
BoostPro Computing
www.boostpro.com

signature.asc

Alexey Kutumov

unread,
Mar 23, 2013, 12:44:25 AM3/23/13
to rypp...@googlegroups.com
I think that not only accumulators needs to be reviewed, for example circular_buffer, units and some other libraries also have similar problems. Also there are many different input formats (quickbook, boostbook, docbook, rst), so almost every library has its own documentation building process. Maybe we need some standard for writing documentation?

пятница, 22 марта 2013 г., 1:04:10 UTC+7 пользователь Eric Niebler написал:

Daniel Pfeifer

unread,
Mar 23, 2013, 12:40:04 PM3/23/13
to rypp...@googlegroups.com, Stephen Kelly, Alexey Kutumov
2013/3/21 Dave Abrahams <da...@boostpro.com>

on Wed Mar 20 2013, Stephen Kelly <steveire-AT-gmail.com> wrote:

> On Wednesday, March 20, 2013 4:45:59 AM UTC+1, Dave Abrahams wrote:
>>
>>
>> on Mon Mar 18 2013, Alexey Kutumov <alexey.kutumov-AT-gmail.com> wrote:
>>
>> > понедельник, 18 марта 2013 г., 21:20:19 UTC+7 пользователь Bill
>> > Hoffman написал:
>> >
>> >     On 3/17/2013 6:24 AM, Alexey Kutumov wrote:
>> >     > * Double CMake invocation;
>> >     What is this issue?
>> >
>> > You can find more info here: https://groups.google.com/d/topic/
>> > ryppl-dev/EMIKsYZYaFE/discussion
>>
>> Basically, it boils down to the fact that (ahem) we're waiting patiently
>> for CMake 2.8.11 so we can get rid of this hack.  Months ago, Daniel
>> told me it was about to be released.  Was there a snag?
>>
>>
>
> There is a release-candidate available for 2.8.11, but the 'interface
> targets' feature discussed in the above thread is not part of it. It was
> deferred to the following release.
>
>  http://thread.gmane.org/gmane.comp.programming.tools.cmake.devel/6395

:(

> I'm not sure why that feature is needed to resolve the 'run cmake twice'
> issue.

I don't currently see this as an issue that needs to be resolved by a workaround.

Usage requirements need two passes. Currently, we use a cmake run for each pass.
This is neither the only possible way nor the best way.

Another way would be to write the usage requirements to special files that are read before any add_subdirectory() calls.
This workaround uses two passes internally, hence does not need two cmake runs.
It might be an improvement to the current approach, but I think it is wasted energy to implement it.

In my opinion the best way is to use Steve's generator expressions for usage requirements, hence using the generator run as the second pass.

> I tried to build the current state of the boost-cmake stuff, but I'm
> having trouble even finding the right repos and fighting with
> submodules.

Oh, I've been concentrating on other things for the past week but
generating the submodule references is now bumped to the top of my list.

> I was going to wait until the git transition was done before bringing
> up the cmake issue again.

It doesn't need to be completely /done/, but you might need the
submodules.  Actually, even that isn't clear to me.  I'd really love it
if Daniel could weigh in here.

Remember that our git transition currently does a "git push --mirror" to all repositories.
The repositories that are currently used for cmake-ification have no common history with the repositories that are created by the git transition. It *is* confusing. :-)
Waiting until the git transition is complete would be my recommendation.

cheers, Daniel

Daniel Pfeifer

unread,
Mar 23, 2013, 1:05:57 PM3/23/13
to rypp...@googlegroups.com, Bill Hoffman
2013/3/21 Dave Abrahams <da...@boostpro.com>
The meta repository is temporary. We use it to test all libraries.

In the future, ryppl will download all requested libraries and create a CMakeLists.txt file.
There will be no need to turn modules off. You won't get Boost.MPI unless you explicitly ask for it (or any other component that depends on it).

cheers. Daniel

Dave Abrahams

unread,
Mar 23, 2013, 2:23:29 PM3/23/13
to rypp...@googlegroups.com, rypp...@googlegroups.com, Bill Hoffman
I think if it's easy to add, we should implement the capability even. If it's "temporary."  We really don't know how long that arrangementmight stay in place

Sent from my moss-covered three-handled family gradunza
--

Stephen Kelly

unread,
Mar 24, 2013, 8:39:12 AM3/24/13
to rypp...@googlegroups.com, Alexey Kutumov

Daniel Pfeifer wrote:


>> > I'm not sure why that feature is needed to resolve the 'run cmake

>> > twice' issue.

>>

>

> I don't currently see this as an issue that needs to be resolved by a

> workaround.

>

> Usage requirements need two passes.


Why? This seems to be a boost-specific requirement. In general, CMake usage requirements does not require two-passes (unless you mean configure-step and generate-step, which you might, reading below), so I'd like to dig to find out the root cause of why boost does. I'd sort of like to understand from 'first principles' and your basic starting assumptions. Is this a temporary situation?


Is the reason a side effect of wanting to use find_package(BoostAny) for example to set the necessary variables and targets? For the purpose of discussion: Why not just set those variables in the top-level CMakeLists.txt file? Ryppl will generate that file anyway in your future vision, right?


> In my opinion the best way is to use Steve's generator expressions for

> usage requirements, hence using the generator run as the second pass.


I'm not really sure I understand what you wrote here and how it relates to a second pass. Maybe it will become clear when the above is cleared up though.


Thanks,


Steve.


Daniel Pfeifer

unread,
Mar 24, 2013, 5:10:09 PM3/24/13
to rypp...@googlegroups.com
2013/3/24 Stephen Kelly <stev...@gmail.com>

Daniel Pfeifer wrote:


>> > I'm not sure why that feature is needed to resolve the 'run cmake

>> > twice' issue.

>>

>

> I don't currently see this as an issue that needs to be resolved by a

> workaround.

>

> Usage requirements need two passes.


Why? This seems to be a boost-specific requirement. In general, CMake usage requirements does not require two-passes (unless you mean configure-step and generate-step, which you might, reading below), so I'd like to dig to find out the root cause of why boost does. I'd sort of like to understand from 'first principles' and your basic starting assumptions. Is this a temporary situation?


Yes, I see the generate-step as a second pass. It would not be necessary to separate generation from configuration if both could be done in one step, right?
 

Is the reason a side effect of wanting to use find_package(BoostAny) for example to set the necessary variables and targets?


It is rather an effect of wanting to let each target specify its direct requirements (only).

Lets say we have a target A that depends on a library B. As an implementation detail, B depends on C. C depends on a library D which also has a dependency to B.

The only direct depencency of A is B; thats all the author of A should need to care about. The libraries C and D are not used by A directly. B may even get rid of these dependencies without changing its public interface.

If this was not modern C++, B would hide C and D behind its binary interface. But if B, C, and D are header-only libraries, C and D are required to compile A.
Important: That does not change the fact that A does not directly depend on them!

A more concrete example: When I write a parser, I don't care whether Spirit uses Proto or not!

When CMake generates the target A, it needs to know the dependencies of A, B, C, and D.
B, C and D form a cluster; it is impossible to add them in topological order.

Currently, our script writes the dependencies to config files that are read by find_package(). These config files are incomplete until the first run is completed. A second run is necessary to actually use them.

With generator expressions, we can add the dependencies as target properties that are evaluated in the generator-step. No config files would be required.

Does that explain it a little bit better?

cheers, Daniel

Stephen Kelly

unread,
Mar 25, 2013, 5:27:47 AM3/25/13
to rypp...@googlegroups.com


On Sunday, March 24, 2013 10:10:09 PM UTC+1, Daniel Pfeifer wrote:
2013/3/24 Stephen Kelly <stev...@gmail.com>


Why? This seems to be a boost-specific requirement. In general, CMake usage requirements does not require two-passes (unless you mean configure-step and generate-step, which you might, reading below), so I'd like to dig to find out the root cause of why boost does. I'd sort of like to understand from 'first principles' and your basic starting assumptions. Is this a temporary situation?


Yes, I see the generate-step as a second pass. It would not be necessary to separate generation from configuration if both could be done in one step, right?

Both are done in one CMake run, yes. Partly you seem to need to do some generation before full configuration, right?
 
 

Is the reason a side effect of wanting to use find_package(BoostAny) for example to set the necessary variables and targets?


It is rather an effect of wanting to let each target specify its direct requirements (only).

Lets say we have a target A that depends on a library B. As an implementation detail, B depends on C. C depends on a library D which also has a dependency to B.

Ok, I think we need to get concrete, so I added a small test repo here: https://www.gitorious.org/cmake-targets

The first commit implements what you describe in the obvious way, and the second commit adds some subdirectories.
 

The only direct depencency of A is B; thats all the author of A should need to care about. The libraries C and D are not used by A directly. B may even get rid of these dependencies without changing its public interface.

If this was not modern C++, B would hide C and D behind its binary interface.

Just to be clear on you terms here, "not modern C++" == "not-header-only libraries" is what you mean, right?
 
But if B, C, and D are header-only libraries, C and D are required to compile A.
Important: That does not change the fact that A does not directly depend on them!

A more concrete example: When I write a parser, I don't care whether Spirit uses Proto or not!

When CMake generates the target A, it needs to know the dependencies of A, B, C, and D.
B, C and D form a cluster; it is impossible to add them in topological order.

That doesn't seem to be a problem so far in the test repo.
 

Currently, our script writes the dependencies to config files that are read by find_package(). These config files are incomplete until the first run is completed. A second run is necessary to actually use them.

With generator expressions, we can add the dependencies as target properties that are evaluated in the generator-step. No config files would be required.

What would that look like?
 

Does that explain it a little bit better?

A little bit. I'd still like to have a more-complete concrete example project to play with like the one I just created. I have some ideas of other features that might be useful to cases like boost, but it's hard to know what problems led you to the solution you currently have, so that we can solve the original problems, not the current ones.

Thanks,

Steve.

Daniel Pfeifer

unread,
Mar 25, 2013, 7:17:17 AM3/25/13
to rypp...@googlegroups.com
2013/3/25 Stephen Kelly <stev...@gmail.com>


On Sunday, March 24, 2013 10:10:09 PM UTC+1, Daniel Pfeifer wrote:
2013/3/24 Stephen Kelly <stev...@gmail.com>


Why? This seems to be a boost-specific requirement. In general, CMake usage requirements does not require two-passes (unless you mean configure-step and generate-step, which you might, reading below), so I'd like to dig to find out the root cause of why boost does. I'd sort of like to understand from 'first principles' and your basic starting assumptions. Is this a temporary situation?


Yes, I see the generate-step as a second pass. It would not be necessary to separate generation from configuration if both could be done in one step, right?

Both are done in one CMake run, yes. Partly you seem to need to do some generation before full configuration, right?

Currently, I DO some generation before full configuration. I hope this will no longer be needed.

Is the reason a side effect of wanting to use find_package(BoostAny) for example to set the necessary variables and targets?


It is rather an effect of wanting to let each target specify its direct requirements (only).

Lets say we have a target A that depends on a library B. As an implementation detail, B depends on C. C depends on a library D which also has a dependency to B.

Ok, I think we need to get concrete, so I added a small test repo here: https://www.gitorious.org/cmake-targets

The first commit implements what you describe in the obvious way, and the second commit adds some subdirectories.

Perfect. The attached patch adds some code and comments.

The only direct depencency of A is B; thats all the author of A should need to care about. The libraries C and D are not used by A directly. B may even get rid of these dependencies without changing its public interface.

If this was not modern C++, B would hide C and D behind its binary interface.

Just to be clear on you terms here, "not modern C++" == "not-header-only libraries" is what you mean, right?

Header-only libraries are an extreme (Complete implementation in header files). The other extreme would be to put only declarations in header files and no implementation at all. Most C++ libraries lie somewhere in between. Boost Libraries usually tend towards the header-only extreme. Even those Boost libraries with a binary component don't abstract all their dependencies behind the binary interface.

But if B, C, and D are header-only libraries, C and D are required to compile A.
Important: That does not change the fact that A does not directly depend on them!

A more concrete example: When I write a parser, I don't care whether Spirit uses Proto or not!

When CMake generates the target A, it needs to know the dependencies of A, B, C, and D.
B, C and D form a cluster; it is impossible to add them in topological order.

That doesn't seem to be a problem so far in the test repo.

Let me quote the CMake 2.8.11-rc1 changelog: "Targets can specify usage requirements for their consumers such as include directories and preprocessor definitions; previously only link dependencies were supported".

Your example uses link dependencies. To make this example work with include directories, we need 2.8.11 or 2.8.12.

Currently, our script writes the dependencies to config files that are read by find_package(). These config files are incomplete until the first run is completed. A second run is necessary to actually use them.

With generator expressions, we can add the dependencies as target properties that are evaluated in the generator-step. No config files would be required.

What would that look like?

You are the expert, Steve. I hope you can replace the TODOs in the test repo after applying my patch.

cheers, Daniel
0001-add-some-code-and-TODOs.patch

Stephen Kelly

unread,
Mar 25, 2013, 9:02:54 AM3/25/13
to rypp...@googlegroups.com


On Monday, March 25, 2013 12:17:17 PM UTC+1, Daniel Pfeifer wrote:

The only direct depencency of A is B; thats all the author of A should need to care about. The libraries C and D are not used by A directly. B may even get rid of these dependencies without changing its public interface.

If this was not modern C++, B would hide C and D behind its binary interface.

Just to be clear on you terms here, "not modern C++" == "not-header-only libraries" is what you mean, right?

Header-only libraries are an extreme (Complete implementation in header files). The other extreme would be to put only declarations in header files and no implementation at all. Most C++ libraries lie somewhere in between. Boost Libraries usually tend towards the header-only extreme. Even those Boost libraries with a binary component don't abstract all their dependencies behind the binary interface.

That's clear. Just the equating of using a binary interface to being 'not modern c++' is what I found odd in the use of the term.
 
When CMake generates the target A, it needs to know the dependencies of A, B, C, and D.
B, C and D form a cluster; it is impossible to add them in topological order.

That doesn't seem to be a problem so far in the test repo.

Let me quote the CMake 2.8.11-rc1 changelog: "Targets can specify usage requirements for their consumers such as include directories and preprocessor definitions; previously only link dependencies were supported".
 
Your example uses link dependencies. To make this example work with include directories, we need 2.8.11 or 2.8.12.


Yes, to be based on targets only, INTERFACE_LIBRARY types will be needed. I'm also considering adding some kind of ALIAS_TARGET, but I'm trying to figure out if that would be useful/beneficial to the boost case. Partly the answer to that will depend on how ryppl works in the end.
 

Currently, our script writes the dependencies to config files that are read by find_package(). These config files are incomplete until the first run is completed. A second run is necessary to actually use them.

With generator expressions, we can add the dependencies as target properties that are evaluated in the generator-step. No config files would be required.

What would that look like?

You are the expert, Steve. I hope you can replace the TODOs in the test repo after applying my patch.


I've applied your patch and a new patch to the repo. My new patch is the current only way to do what you want (and doesn't need to cmake runs). Is my new patch something that you in particular wanted to avoid doing? It can indeed be done better with INTERFACE_LIBRARY targets, but I'm trying to figure out if that was really the cause of the requirement for two cmake runs. You currently need two cmake runs, even though only variables are used (not INTERFACE libraries). Could you extend the test repo with the two cmake runs, which shows why it is needed and what is avoided by using the two cmake runs? That will likely help figure out what is missing in cmake to make that unnecessary.

Thanks,

Steve.

Dave Abrahams

unread,
Mar 28, 2013, 2:28:07 PM3/28/13
to rypp...@googlegroups.com


On Monday, March 25, 2013 6:02:54 AM UTC-7, Stephen Kelly wrote:

I've applied your patch and a new patch to the repo. My new patch is the current only way to do what you want (and doesn't need to cmake runs). Is my new patch something that you in particular wanted to avoid doing? 

Steve, as far as I can tell what you did requires encoding the entire object graph in the top level CMakeLists.txt file.  We want each subdirectory to declare its own dependencies.
Reply all
Reply to author
Forward
0 new messages