2016-03-23 6 views
11

Bei der Verwendung von CMake für das Cross Compiling wird generell eine Toolchain-Datei über die Option CMAKE_TOOLCHAIN_FILE angegeben. In GNU terminology kann das Host-Architektur-Toolset mit dieser Datei angegeben werden. Man kann jedoch im Allgemeinen nicht erwarten, etwas ausführen zu können, das mit dieser Toolchain erstellt wurde. So oft müssen einige Build-Tools für die Build-Architektur kompiliert werden.Wie CMake anweisen, den Build-Architektur-Compiler zu verwenden?

Betrachten Sie das folgende Setup. Ich habe zwei Quelldateien genfoo.c und bar.c. Während des Builds muss genfoo.c kompiliert und ausgeführt werden. Seine Ausgabe muss in foo.h geschrieben werden. Dann kann ich bar.c, die #include "foo.h" kompilieren. Da CMake standardmäßig die Toolchain der Host-Architektur verwendet, sind die Anweisungen für bar.c einfach. Aber wie sage ich es, um die Build-Architektur-Toolchain zum Kompilieren genfoo.c zu verwenden? Wenn Sie einfach add_executable(genfoo genfoo.c) sagen, wird der falsche Compiler verwendet.

+0

Wie Sie haben In GNU-Terminologie würden Sie den 'configure'-Befehl verwenden, um die Host-Architektur anzugeben. Und Sie müssten "configure" zweimal ausführen, wenn Sie für zwei verschiedene Host-Umgebungen erstellen möchten. Also sehe ich zwei Möglichkeiten mit CMake: benutze ein Build-Skript, das die zwei benötigten Umgebungen erstellt und ausführt (siehe [hier] (http://stackoverflow.com/questions/30999130/cmake-build-multiple-targets-in-different-) Build-Verzeichnisse)) oder verwenden Sie [ExternalProject_Add()] (https://cmake.org/cmake/help/v3.2/module/ExternalProject.html) und teilen Sie Ihre 'CMakeLists.txt' in dedizierte Teilprojekte auf. – Florian

+0

Nein, mit Autotools verwenden Sie einfach 'CC_FOR_BUILD'. Siehe 'ax_cc_for_build'. – Helmut

+0

Ok, wusste das nicht. Wenn ich richtig verstehe, sprechen wir über den Anwendungsfall, der in [CMake Cross Compiling - Ausführbare Dateien in dem während des Builds erstellten Build] beschrieben wird (https://cmake.org/Wiki/CMake_Cross_Compiling#Using_executables_in_the_build_created_during_the_build)? – Florian

Antwort

7

Drehen von mir in einer Antwort

CMake nur einen Compiler zu einer Zeit verarbeiten kann. Wenn Sie also den langen Weg nicht gehen, um den anderen Compiler als neue Sprache einzurichten, werden Sie zwei Konfigurationszyklen haben.

Ich sehe folgende Ansätze, diesen Prozess zu automatisieren:

  1. Am Beispiel "CMake Cross Compiling - Using executables in the build created during the build?" von den CMake Seiten als Ausgangspunkt Ich hol:

    CMakeLists.txt

    cmake_minimum_required(VERSION 3.0) 
    project(FooBarTest) 
    
    # when crosscompiling import the executable targets 
    if (CMAKE_CROSSCOMPILING) 
        set(IMPORT_PATH "IMPORTFILE-NOTFOUND" CACHE FILEPATH "Point it to the export file path from a native build") 
        file(TO_CMAKE_PATH "${IMPORT_PATH}" IMPORT_PATH_CMAKE) 
        include(${IMPORT_PATH_CMAKE}/genfooTargets.cmake) 
    
        # then use the target name as COMMAND, CMake >= 2.6 knows how to handle this 
        add_custom_command(
         OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/foo.h 
         COMMAND genfoo 
        ) 
    
        add_executable(bar bar.cpp ${CMAKE_CURRENT_BINARY_DIR}/foo.h) 
        target_include_directories(bar PRIVATE ${CMAKE_CURRENT_BINARY_DIR}) 
    endif() 
    
    # only build the generator if not crosscompiling 
    if (NOT CMAKE_CROSSCOMPILING) 
        add_executable(genfoo genfoo.cpp) 
        export(TARGETS genfoo FILE "${CMAKE_CURRENT_BINARY_DIR}/genfooTargets.cmake") 
    endif() 
    

    Dann mit einem Skript wie:

    build.sh

    #!/bin/bash 
    
    if [ ! -d hostBuild ]; then 
        cmake -E make_directory hostBuild 
        cmake -E chdir hostBuild cmake .. 
    fi 
    cmake --build hostBuild 
    
    if [ ! -d crossBuild ]; then 
        cmake -E make_directory crossBuild 
        cmake -E chdir crossBuild cmake .. -DIMPORT_PATH=${PWD}/hostBuild -DCMAKE_TOOLCHAIN_FILE=toolchain.cmake 
    fi 
    cmake --build crossBuild 
    

    Ich werde die gewünschten Ergebnisse erhalten, indem ./build.sh

  2. Splitting Aufruf der CMakeLists.txt und vielleicht sogar die export()/include() mit etwas ersetzen, wo ich den Ausgang Weg kenne meine Bauwerkzeuge zB von CMAKE_RUNTIME_OUTPUT_DIRECTORY mit würde die Dinge vereinfachen:

    CMakeLists.txt

    cmake_minimum_required(VERSION 3.0) 
    project(FooBarTest) 
    
    # then use the target name as COMMAND, CMake >= 2.6 knows how to handle this 
    add_custom_command(
        OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/foo.h 
        COMMAND genfoo 
    ) 
    
    add_executable(bar bar.cpp ${CMAKE_CURRENT_BINARY_DIR}/foo.h) 
    target_include_directories(bar PRIVATE ${CMAKE_CURRENT_BINARY_DIR}) 
    

    buildtools/CMakeLists.txt

    cmake_minimum_required(VERSION 3.0) 
    project(BuildTools) 
    
    add_executable(genfoo genfoo.cpp) 
    

    bauen. sh

    #!/bin/bash 
    
    if [ ! -d crossBuild ]; then 
        cmake -E make_directory crossBuild 
        cmake -E chdir crossBuild cmake .. -DCMAKE_TOOLCHAIN_FILE=toolchain.cmake 
    fi 
    if [ ! -d hostBuild ]; then 
        cmake -E make_directory hostBuild 
        cmake -E chdir hostBuild cmake ../buildTools -DCMAKE_RUNTIME_OUTPUT_DIRECTORY:PATH=${PWD}/crossBuild 
    fi 
    cmake --build hostBuild 
    cmake --build crossBuild 
    

Referenzen