CMake: Compilar un Hola Mundo!

Arco

Esta receta explica cómo compilar un programa trivial con CMake.

Software necesario

El ejemplo que vamos a utilizar puedes descargarlo utilizando subversion desde:

svn co https://arco.esi.uclm.es/svn/public/samples/cmake/single_binary

El directorio 'single_binary' contiene una implementación (hello.cpp) de un "Hola Mundo" en C++ y el archivo CMakeLists.txt.

Versión "quick" y no tan "dirty"

El contenido del archivo es el siguiente:

CMAKE_MINIMUM_REQUIRED(VERSION 2.8)
PROJECT(hello)
ADD_EXECUTABLE(hello hello.cpp)

En primer lugar, se especifica la versión mínima de CMake que se debe utilizar. A continuación, se debe dar un nombre al proyecto utilizando el comando PROJECT.

Como se trata de un proyecto archi-sencillo, sólo consta de un ejecutable y éste se debe generar a partir del fichero "hello.cpp" (su dependencia). El comando ADD_EXECUTABLE acepta una lista de dependencias. Como puedes ver, prácticamente es una regla de Makefile pero más abstracta de forma que sea posible no sólo crear Makefiles sino también exportar a proyectos de Eclipse y otros entornos de desarrollo privativos (a los cuales no recomiendo exportar).

Versión "paranoic"

En el ejemplo anterior, desde un punto de vista ortodoxo, hemos supuesto muchas cosas. Por ejemplo, en el fichero "hello.cpp" se incluye la cabecera "iostream". ¿Hemos comprobado que está instalada? El compilador de C++ que utilizamos, ¿tiene soporte para que se pueda utilizar el namespace "std"? Como ves, hay muchas cosas que se han dado por supuestas en el ejemplo anterior.

Aunque para este ejemplo no sea necesario, veamos una versión del archivo CMakeLists.txt más avanzada:

CMAKE_MINIMUM_REQUIRED(VERSION 2.8)
 
PROJECT(hello)
 
INCLUDE(TestForSTDNamespace)
IF (CMAKE_NO_STD_NAMESPACE)
  MESSAGE(FATAL_ERROR "** El compilador no soporta std:: en clases STL")
ENDIF()
 
INCLUDE(CheckIncludeFileCXX)
CHECK_INCLUDE_FILE_CXX(iostream IS_OSTREAM)
 
IF(NOT IS_OSTREAM)
  MESSAGE(FATAL_ERROR "** No se encuentra la cabecera 'iostream'")
ENDIF()
 
ADD_EXECUTABLE(hello hello.cpp)

En este ejemplo se introduce el uso de módulos que se proporcionan en la distribución de CMake 2.8 en Debian:

  • TestForSTDNamespace: incluye el código necesario para comprobar que existe el compilador soporta el uso del espacio de nombres std. Esta macro modifica una variable global (CMAKE_NO_STD_NAMESPACE) con el resultado de dicho test.
  • CheckIncludeFileCXX: se trata de un módulo que contiene el comando CHECK_INCLUDE_FILE_CXX que acepta como primer parámetro el nombre del archivo a incluir y, como segundo parámetro, una variable donde almacenar el resultado. De esta forma, utilizando un IF podemos comprobar que efectivamente se encuentra instalada la cabecera iostream.

Referencias