[cmake-developers] Modern cross-platform buildsystem design requirements
Stephen Kelly
steveire at gmail.com
Wed Sep 10 11:49:54 EDT 2014
Brad King wrote:
> On 09/09/2014 06:32 PM, Stephen Kelly wrote:
>> I saw the addition of the VS_WINRT_COMPONENT property. This seems to be
>> an attribute to mark an executable specially so that it is built with
>> appropriate flags for the WinRT platform.
>
> Yes. It is similar to the WIN32_EXECUTABLE target property.
>
>> http://thread.gmane.org/gmane.comp.programming.tools.cmake.devel/9728
>> Building executables as libraries (2014-03-21)
>
> FYI, in my Github fork you can see a WIP branch adding support for
> NVIDIA's Nsight Tegra Visual Studio Edition. It links executables
> as shared libraries unless they are marked with an ANDROID_GUI target
> property.
I notice there is also a ANDROID_API target property. Presumably that allows
things like
foreach(api 16 19)
add_library(mylib-android-${api} mylib.cpp)
set_property(TARGET mylib-android-${api} PROPERTY ANDROID_API ${api})
endforeach()
I wonder if it would instead make sense to provide some INTERFACE targets
with INTERFACE_ANDROID_API set and then
target_link_libraries(mylib cmake::android-16)
for example. This has the disadvantage of requiring the android-${api}
targets to be predefined, but maybe a use-story of
set(CMAKE_ANDROID_APIS 16 19)
include(CMakeAndroidTargets)
would avoid a need to hardcode them. The INTERFACE_ANDROID_API, along with
compatibility requirements, would prevent mistakes (?) like
add_library(lib1 ...)
add_library(lib2 ...)
set_property(TARGET lib1 PROPERTY
ANDROID_API 16)
set_property(TARGET lib1 PROPERTY
ANDROID_API 19)
target_link_libraries(lib1 lib2) # Not the same API version.
> The property activates creation of a .apk.
The approach I prototyped for BB10 .bar packages was to generate them with
cpack.
https://gitorious.org/cmake/steveires-cmake/commit/c7715486
This has the effect that the description of build-targets and their
dependencies etc is mostly 'normal' and free from BB10-specific stuff, and
there is a list of cpack/BAR-related variables in the cpack section of the
CMakeLists (where there could also be a list of cpack/android-related
variables).
Should there be some merging of functionality from cpack into cmake?
>
>> Today, I think 'cross-platform' includes a few mobile platforms as first-
>> class targets, and cross-compiling is part of what cross-platform means.
>> So, I wonder what a cross-platform buildsystem necessarily looks like
>> today, and whether it can be done better/abstracted with more first class
>> features.
>
> Good question. I think support for each mobile target will have to be
> added on an incremental basis. If some common themes emerge over time
> then perhaps we can identify some abstractions.
It seems that with these changes, a project aiming to be 'cross-platform'
would end up writing a macro like
macro(set_properties_for_platform tgt)
if (CROSS_COMPILING)
if (ANDROID)
set_property(TARGET ${tgt} ...)
elseif (BLACKBERRY)
set_property(TARGET ${tgt} ...)
elseif (WinRT)
set_property(TARGET ${tgt} ...)
endif()
endif()
endmacro()
# This now looks 'normal' and 'cross platform'
add_executable(hello_world main.cpp)
# Call this for each target:
set_properties_for_platform(hello_world)
That's assuming such a macro has all the information it would need to set
the appropriate properties...
> However, each of these
> platforms requires some kind of app manifest, and that is a different
> file/format for each target platform. Projects will at least have to
> add such manifest files for each platform they want to support.
Do each such files have the same or similar content? Author, url, siging key
etc? That might be a good avenue to explore for a cross-platform
abstraction.
>
>> I'm reminded of the previous proposal for multiple toolchain use.
>>
>> http://thread.gmane.org/gmane.comp.programming.tools.cmake.devel/7272
>>
>> Partly that discussion was aborted because we already had the large topic
>> of designing and implementing usage-requirements to deal with. As that is
>> now complete as designed, it might be worthwhile to re-consider and
>> discuss/design how multiple toolchains could be used at once, whether
>> that would require or benefit from a new language for cmake (another
>> orthogoal known possible future-direction for cmake) etc.
>
> The main challenge here is that CMake exposes a lot of information about
> "the one" toolchain per language selected during configuration in the
> CMake language as variables. Your "toolchain scope" proposal would
> provide a context for code that will see the toolchain information
> for each enabled target toolchain. However, perhaps it would be better
> in the long run to consider something more declarative and with a
> new language.
Yes, perhaps. A new language creates a lot of sunk-cost for people porting
and learning it though of course. There would need to be enough
justification for doing it. This could be designed to be part of that
justification. I think there may be other justifications for designing a new
language too. Are you still thinking of a 'pure'-Lua-based (not via
CMakeLists which loads Lua somehow) system as an end-goal?
I believe part of the motivation for qbs (the next Qt build tool) is
multiple architecture support, which I believe is preferred by some to
create Android APKs targeting multiple architectures
http://blog.qt.digia.com/blog/2014/03/26/qt-weekly-3-qt-for-android-tips-and-tricks/#comment-1193255
So, that's at least how this stuff in this thread fits together and can be
considered together. I don't understand the motivation to put multiple
architectures into one package (everyone downloading the package gets N-1
times the amount of stuff they need), but so it is.
Anyway the above problem is not solved with the suggestion below.
> When cross-compiling it is common to build some tools for the host
> system to be used during the build itself. There is always exactly
> one host platform, so perhaps we can design a new mode of support for
> cross-compiling that configures "the one" toolchain for the *host*
> system only. Then provide some kind of declarative or delayed-until-
> generate-time specification, perhaps using a new language, for the
> cross-compiled pieces. Eventually that spec could be used for the
> host system too.
Yes, that would be a good intermediate goal. There are many interesting
design requirements even for that, such as the example from Daniel of
building a library for both host and target, and whether find_package would
need multiple modes of operation etc. For example, in a single cmake
buildsystem I would need two Qt5Core packages - one host used by a generator
and one target. Currently there is only one cache and one possible
Qt5Core_DIR etc.
When you refer to 'a new language' here, do you mean in the same sense of
how generator expressions were a new language (without a departure from the
current cmake language as a whole), or do you mean something different?
Thanks,
Steve.
More information about the cmake-developers
mailing list