tutorial course c++ build makefile cmake output

c++ - course - CMake output/build directory



cmake course (5)

Soy bastante nuevo para cmake, y leí algunos tutoriales sobre cómo usarlo, y escribí un complicado script de 50 líneas CMake para hacer un programa para 3 compiladores diferentes. Esto probablemente concluya todo mi conocimiento en cmake.

Ahora mi problema es que tengo un código fuente, cuya carpeta no quiero tocar / perder cuando hago el programa. Quiero que todos hagan y creen archivos de salida y carpetas para entrar en ./Compile/, así que cambié algunas variables en mi script cmake para eso, y funcionó por algún tiempo cuando hice algo como esto en mi computadora portátil:

Compile$ cmake ../src Compile$ make

Donde con eso tuve un resultado limpio en la carpeta en la que estoy ahora, que es exactamente lo que estoy buscando.

Ahora me mudé a otra computadora, y recompuse CMake 2.8.11.2, ¡y estoy casi de vuelta en la primera casilla! Siempre compila la cosa en la carpeta src donde se encuentra mi CMakeLists.txt.

La parte donde elijo el directorio en mi script cmake es esta:

set(dir ${CMAKE_CURRENT_SOURCE_DIR}/../Compile/) set(EXECUTABLE_OUTPUT_PATH ${dir} CACHE PATH "Build directory" FORCE) set(LIBRARY_OUTPUT_PATH ${dir} CACHE PATH "Build directory" FORCE) set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${dir}) set(CMAKE_BUILD_FILES_DIRECTORY ${dir}) set(CMAKE_BUILD_DIRECTORY ${dir}) set(CMAKE_BINARY_DIR ${dir}) SET(EXECUTABLE_OUTPUT_PATH ${dir}) SET(LIBRARY_OUTPUT_PATH ${dir}lib) SET(CMAKE_CACHEFILE_DIR ${dir})

Y ahora siempre termina con:

-- Build files have been written to: /.../src

¿Me estoy perdiendo de algo?


A partir de CMake Wiki: http://www.cmake.org/Wiki/CMake_Useful_Variables

CMAKE_BINARY_DIR si está compilando in-source, esto es lo mismo que CMAKE_SOURCE_DIR, de lo contrario este es el directorio de nivel superior de su árbol de compilación

Compare estas dos variables para determinar si se inició la compilación fuera de la fuente


Convertir mi comentario en una respuesta:

En caso de que alguien hiciera lo que hice, que fue comenzar poniendo todos los archivos de compilación en el directorio fuente:

cd src cmake .

cmake colocará un grupo de archivos de compilación y caché ( CMakeCache.txt , CMakeFiles , cmake_install.cmake , etc.) en el directorio src .

Para cambiar a una compilación fuera de la fuente, tuve que eliminar todos esos archivos. Entonces podría hacer lo que @Agnew recomendara en su respuesta:

mkdir -p src/build cd src/build cmake ..


En primer lugar, no debe retransmitir el nombre del directorio de compilación en su secuencia de comandos. la línea con ../Compile debe ser cambiada.

Es porque depende del usuario dónde compilar.

En lugar de eso, use una de las variables predefinidas: http://www.cmake.org/Wiki/CMake_Useful_Variables (busque CMAKE_BINARY_DIR y CMAKE_CURRENT_BINARY_DIR)


Hay poca necesidad de establecer todas las variables que está configurando. CMake los establece en valores predeterminados razonables. Definitivamente no debe modificar CMAKE_BINARY_DIR o CMAKE_CACHEFILE_DIR . Trátelos como de solo lectura.

Primero elimine el archivo de caché problemático existente del directorio src:

cd src rm CMakeCache.txt cd ..

A continuación, elimine todos los comandos set() y haga lo siguiente:

cd Compile rm -rf * cmake ../src

Siempre que esté fuera del directorio de origen cuando ejecuta CMake, no modificará el directorio de origen a menos que su CMakeList lo indique explícitamente.

Una vez que tenga esto funcionando, puede ver dónde CMake coloca las cosas de forma predeterminada, y solo si no está satisfecho con las ubicaciones predeterminadas (como el valor predeterminado de EXECUTABLE_OUTPUT_PATH ), modifique solo las que necesita. Y trata de expresarlos en relación con CMAKE_BINARY_DIR , CMAKE_CURRENT_BINARY_DIR , PROJECT_BINARY_DIR , etc.

Si observa la documentación de CMake, verá las variables divididas en secciones semánticas. Excepto en circunstancias muy especiales, debe tratar a todos los enumerados en "Variables que brindan información" como de solo lectura dentro de CMakeLists.


Parece que quieres una construcción fuera de la fuente . Hay un par de formas en que puede crear una compilación fuera de la fuente.

  1. Haz lo que estabas haciendo, ejecuta

    cd /path/to/my/build/folder cmake /path/to/my/source/folder

    lo que hará que cmake genere un árbol de compilación en /path/to/my/build/folder para el árbol fuente en /path/to/my/source/folder .

    Una vez que lo haya creado, cmake recuerda dónde está la carpeta de origen, por lo que puede volver a ejecutar cmake en el árbol de compilación con

    cmake /path/to/my/build/folder

    o incluso

    cmake .

    si su directorio actual ya es la carpeta de compilación.

  2. Use algunas opciones no documentadas para configurar las carpetas de origen y compilación :

    cmake -B/path/to/my/build/folder -H/path/to/my/source/folder

    que hará exactamente lo mismo que (1), pero sin la dependencia del directorio de trabajo actual.

CMake coloca todos sus resultados en el árbol de compilación de forma predeterminada, por lo tanto, a menos que esté utilizando liberalmente ${CMAKE_SOURCE_DIR} o ${CMAKE_CURRENT_SOURCE_DIR} en sus archivos de cmake, no debería tocar el árbol de origen .

Lo más importante que puede salir mal es si previamente ha generado un árbol de compilación en su árbol fuente (es decir, tiene una compilación de origen ). Una vez que haya hecho esto, la segunda parte de (1) arriba se activará, y cmake no realizará ningún cambio en la fuente ni en las ubicaciones de compilación. Por lo tanto, no puede crear una compilación fuera de la fuente para un directorio de origen con una compilación en origen . Puede solucionar esto con bastante facilidad eliminando (como mínimo) CMakeCache.txt del directorio de origen. Hay algunos otros archivos (en su mayoría en el directorio CMakeFiles ) que CMake genera que también debe eliminar, pero estos no harán que cmake trate el árbol fuente como un árbol de compilación.

Debido a que las compilaciones fuera de la fuente son a menudo más deseables que las compilaciones en origen, es posible que desee modificar su cmake para que requiera desarrollos fuera de la fuente:

# Ensures that we do an out of source build MACRO(MACRO_ENSURE_OUT_OF_SOURCE_BUILD MSG) STRING(COMPARE EQUAL "${CMAKE_SOURCE_DIR}" "${CMAKE_BINARY_DIR}" insource) GET_FILENAME_COMPONENT(PARENTDIR ${CMAKE_SOURCE_DIR} PATH) STRING(COMPARE EQUAL "${CMAKE_SOURCE_DIR}" "${PARENTDIR}" insourcesubdir) IF(insource OR insourcesubdir) MESSAGE(FATAL_ERROR "${MSG}") ENDIF(insource OR insourcesubdir) ENDMACRO(MACRO_ENSURE_OUT_OF_SOURCE_BUILD) MACRO_ENSURE_OUT_OF_SOURCE_BUILD( "${CMAKE_PROJECT_NAME} requires an out of source build." )

La macro de arriba proviene de un módulo de uso común llamado MacroOutOfSourceBuild . Existen numerosas fuentes para MacroOutOfSourceBuild.cmake en google, pero parece que no puedo encontrar el original y es lo suficientemente breve como para incluirlo aquí en su totalidad.

Desafortunadamente, cmake usualmente ha escrito algunos archivos para cuando se invoca la macro, por lo tanto, aunque esto le impedirá realizar la compilación, deberá eliminar CMakeCache.txt y CMakeFiles .

Puede que le resulte útil establecer las rutas en las que se escriben los binarios, las bibliotecas compartidas y las estáticas, en cuyo caso, ¿cómo puedo convertir cmake en un directorio ''bin''? (Descargo de responsabilidad, tengo la respuesta más votado sobre esa pregunta ... pero así es como lo sé).