MantisBT - CMake
View Issue Details
0009220CMakeCMakepublic2009-06-29 18:332016-06-10 14:30
Alan W. Irwin 
Kitware Robot 
normalminoralways
closedmoved 
CMake-2-6 
 
0009220: enable_language(.... OPTIONAL) signature does not work correctly
I have been testing the OPTIONAL signature for enable_language using the
following simple CMakeLists.txt file:

*******
cmake_minimum_required(VERSION 2.6.4)
project(test NONE)
enable_language(C OPTIONAL)
message(STATUS "CMAKE_C_COMPILER_WORKS = ${CMAKE_C_COMPILER_WORKS}")
*******

According to the documentation the OPTIONAL signature is to help CMake-based
build systems deal smoothly with bad/broken compilers by allowing them to
take their own actions to deal with the compiler issue based on the value of
CMAKE_<languageName>_COMPILER_WORKS. However, the OPTIONAL signature does
not work and bad/broken compilers error out before the above message command
can be reached. The same issue also occurs for C++ and Fortran.

To illustrate the issue as simply as possible, I emulate a missing/broken
compiler as follows:

software@raven> CC='gcc whatever' cmake ..
-- The C compiler identification is unknown
-- Check for working C compiler: /usr/bin/gcc
-- Check for working C compiler: /usr/bin/gcc -- broken
CMake Error at /home/software/cmake/install-2.6.4/share/cmake-2.6/Modules/CMakeTestCCompiler.cmake:32 (MESSAGE):
  The C compiler "/usr/bin/gcc" is not able to compile a simple test program.

  It fails with the following output:

   Change Dir: /tmp/build_dir/CMakeFiles/CMakeTmp

  

  Run Build Command:/usr/bin/make "cmTryCompileExec/fast"

  /usr/bin/make -f CMakeFiles/cmTryCompileExec.dir/build.make
  CMakeFiles/cmTryCompileExec.dir/build

  make[1]: Entering directory `/tmp/build_dir/CMakeFiles/CMakeTmp'

  /home/software/cmake/install-2.6.4/bin/cmake -E cmake_progress_report
  /tmp/build_dir/CMakeFiles/CMakeTmp/CMakeFiles 1

  Building C object CMakeFiles/cmTryCompileExec.dir/testCCompiler.c.o

  /usr/bin/gcc whatever -o CMakeFiles/cmTryCompileExec.dir/testCCompiler.c.o
  -c /tmp/build_dir/CMakeFiles/CMakeTmp/testCCompiler.c

  gcc: whatever: No such file or directory

  make[1]: Leaving directory `/tmp/build_dir/CMakeFiles/CMakeTmp'

  make[1]: *** [CMakeFiles/cmTryCompileExec.dir/testCCompiler.c.o] Error 1

  make: *** [cmTryCompileExec/fast] Error 2

  

  

  CMake will not be able to correctly generate this project.
Call Stack (most recent call first):
  CMakeLists.txt:3 (enable_language)


-- Configuring incomplete, errors occurred!

The "whatever" inserts an extra unknown file into the compilation process
which makes try_compile not work, and which therefore tests the OPTIONAL
signature. However, instead of returning properly to the original
CMakeLists.txt file to allow the build system to do something about
CMAKE_C_COMPILER_WORKS being false it errors out as above.

The source of the issue is line 32 of CMakeTestCCompiler.cmake which
uses message(FATAL_ERROR ...)

If you change that to message(STATUS ...) , then that solves the issue and
control is returned back to the originating CMakeLists.txt file with this
(correct) result

[...]
CMake will not be able to correctly generate this project.
-- CMAKE_C_COMPILER_WORKS = FALSE
-- Configuring done
-- Generating done
-- Build files have been written to: /tmp/build_dir

However, that is not a good general solution because the same fix means that
if you drop OPTIONAL, i.e., use "enable_language(C)" control is incorrectly
returned to the original CMakeLists.txt and the project is incorrectly
configured and generated without a CMake error.

I had a look at cmEnableLanguageCommand.cxx to see what it did with
OPTIONAL. It appears that it simply lets the Generator know that the
language is optional. I suggest it should also set a CMake variable that
CMakeTestCCompiler.cmake (and also CMakeTestCXXCompiler.cmake and
CMakeTestFortranCompiler.cmake) could use to send STATUS or FATAL_ERROR
messages as appropriate.

The reason I am bringing up these OPTIONAL C, C++, and Fortran language
support issues now is I am beginning to encounter reports from PLplot users
with broken compilers, and I would prefer to give them a much smoother
landing (disable that part of PLplot that depends on the compiler in
question with a warning message and keep going) than is possible now. Once
the OPTIONAL signature to enable_language actually works, I presume a
substantial number of other multi-language projects would find it useful as
well.
No tags attached.
related to 0008345closed  enable_language(fortran optional) fails if no fortran compiler is installed 
related to 0010227closed  OPTIONAL option for enable_language(FORTRAN) 
? language_support.cmake (1,285) 2009-07-16 19:45
https://public.kitware.com/Bug/file/2365/language_support.cmake
? language_support_v2.cmake (2,248) 2009-08-22 22:23
https://public.kitware.com/Bug/file/2421/language_support_v2.cmake
Issue History
2009-06-29 18:33Alan W. IrwinNew Issue
2009-06-29 19:45Alan W. IrwinNote Added: 0016780
2009-06-30 12:58Alex NeundorfStatusnew => assigned
2009-06-30 12:58Alex NeundorfAssigned To => Alex Neundorf
2009-07-16 19:45Alan W. IrwinFile Added: language_support.cmake
2009-07-16 19:52Alan W. IrwinNote Added: 0016887
2009-08-22 22:22Greg SharpNote Added: 0017180
2009-08-22 22:23Greg SharpFile Added: language_support_v2.cmake
2009-08-22 22:34Greg SharpNote Added: 0017181
2009-08-22 23:09Greg SharpNote Edited: 0017180
2009-08-22 23:09Greg SharpNote Deleted: 0017181
2009-08-22 23:09Greg SharpNote Edited: 0017180
2009-08-22 23:10Greg SharpNote Edited: 0017180
2009-11-25 18:13Marcel LooseNote Added: 0018597
2009-11-27 04:00Marcel LooseNote Added: 0018600
2010-06-18 12:51David ColeSummaryenable_language(.... OPTIONAL) signature does not work correctly => enable_language(.... OPTIONAL) signature does not work correctly
2011-04-14 14:28David ColeTarget Version => CMake 2.8.5
2011-05-25 16:59David ColeNote Added: 0026593
2011-05-25 16:59David ColeTarget VersionCMake 2.8.5 =>
2011-08-01 11:32David ColeAssigned ToAlex Neundorf => David Cole
2011-08-01 11:32David ColeTarget Version => CMake 2.8.6
2011-09-22 16:56David ColeNote Added: 0027476
2011-09-22 16:56David ColeTarget VersionCMake 2.8.6 =>
2012-05-18 10:12sleskeNote Added: 0029507
2012-05-18 10:39sleskeNote Added: 0029510
2012-05-21 08:20Marcel LooseNote Added: 0029517
2012-05-21 15:06sleskeNote Added: 0029533
2012-10-15 11:31David ColeRelationship addedrelated to 0010227
2012-10-15 11:32David ColeRelationship addedrelated to 0008345
2012-11-21 14:57David ColeNote Added: 0031650
2012-11-21 14:58David ColeAssigned ToDavid Cole =>
2012-11-21 15:11David ColeStatusassigned => new
2012-11-21 15:11David ColeNote Added: 0031671
2014-09-10 16:36sleskeNote Edited: 0029533bug_revision_view_page.php?bugnote_id=29533#r1566
2015-02-06 14:15Brad KingNote Added: 0037940
2015-02-12 08:35Brad KingNote Added: 0037958
2016-06-10 14:27Kitware RobotNote Added: 0041575
2016-06-10 14:27Kitware RobotStatusnew => resolved
2016-06-10 14:27Kitware RobotResolutionopen => moved
2016-06-10 14:27Kitware RobotAssigned To => Kitware Robot
2016-06-10 14:30Kitware RobotStatusresolved => closed

Notes
(0016780)
Alan W. Irwin   
2009-06-29 19:45   
Also CMakeDetermineCCompiler.cmake, CMakeDetermineCXXCompiler.cmake, CMakeDetermineFortranCompiler.cmake, and CMakeDetermineRCCompiler.cmake need to be dealt with as well since they generate FATAL_ERROR messages if the CC, etc., environment variables point to a non-existing compiler.
(0016887)
Alan W. Irwin   
2009-07-16 19:52   
The attached file, language_support.cmake contains a useful function called workaround_9220 which implements David Cole's idea of invoking a cmake session from within your principal cmake session to independently test language support for needed languages before optionally trying enable_language "for real". But the better solution, of course, is simply to fix this bug.
(0017180)
Greg Sharp   
2009-08-22 22:22   
(edited on: 2009-08-22 23:10)
Nice workaround airwin. Just what I needed. I have modified your workaround to address 0008345 as well (language_support_v2.cmake above).

On debian testing (cmake 2.6.2), I get return code zero when calling cmake the first time, but cmake crashes when running a second time as follows:

  -- The Fortran compiler identification is unknown
  CMake Error at /usr/share/cmake-2.6/Modules/CMakeFortranInformation.cmake:7 (GET_FILENAME_COMPONENT):
    get_filename_component called with incorrect number of arguments
  Call Stack (most recent call first):
    CMakeLists.txt:3 (enable_language)

My workaround is to invoke cmake twice. If both return codes are zero, then it is safe to invoke ENABLE_LANGUAGE(Fortran OPTIONAL)

(0018597)
Marcel Loose   
2009-11-25 18:13   
With respect to the "ENABLE_LANGUAGE(Fortran OPTIONAL)" and the "get_filename_component called with incorrect number of arguments" issue:
this happens because ${CMAKE_Fortran_COMPILER} is empty. I could resolve that by simply putting quotes around the argument ${CMAKE_Fortran_COMPILER} in the call to GET_FILENAME_COMPONENT() in CMakeFortranInformation.cmake. But I don't know if I'm overlooking all kinds of side effects.
(0018600)
Marcel Loose   
2009-11-27 04:00   
Here's a little work-around that I use to circumvent the error in GET_FILENAME_COMPONENT in CMakeFortranInformation.cmake. It seems to work fine.

# Work-around for CMake issue 0009220
if(DEFINED CMAKE_Fortran_COMPILER AND CMAKE_Fortran_COMPILER MATCHES "^$")
  set(CMAKE_Fortran_COMPILER CMAKE_Fortran_COMPILER-NOTFOUND)
endif(DEFINED CMAKE_Fortran_COMPILER AND CMAKE_Fortran_COMPILER MATCHES "^$")
(0026593)
David Cole   
2011-05-25 16:59   
Not for 2.8.5 - postponing until a future release
(0027476)
David Cole   
2011-09-22 16:56   
Not enough time left to address this issue before the 2.8.6 release. Deferred until a future release.
(0029507)
sleske   
2012-05-18 10:12   
Update: This bug still exists in CMake version 2.8.8.

Also, it not only manifests if the variable CC is set incorrectly, but also if the installed compiler really does not work.

For example, it is also reproducible (on Linux) by replacing /usr/bin/gcc with /bin/false. So the bug is not only triggered by an incorrect environment setting.
(0029510)
sleske   
2012-05-18 10:39   
Also, a note about the workaround by Marce Loose (comment 0018600):

This workaround allows the build to run, however it has a side effect.

When using the Makefile generator, the CMake configuration phase will be re-run on every invokation of "make". Usually invoking "make" should only run the actual build (unless CMakeLists.txt was modified).

This does not break the build, but for projects with complex CMake configuration, it significantly slows down the build, especially if only few files need to be rebuilt.
(0029517)
Marcel Loose   
2012-05-21 08:20   
If my solution (c18600) causes a rerun of CMake, then maybe CMAKE_Fortran_COMPILER should be set to CMAKE_Fortran_COMPILER-NOTFOUND in the cache. I've never experienced any problems, though.
(0029533)
sleske   
2012-05-21 15:06   
(edited on: 2014-09-10 16:36)
@Marcel Loose:

The problem is easy to reproduce.

CMakeLists.txt:

************
cmake_minimum_required(VERSION 2.6.4)
project(test NONE)
if(DEFINED CMAKE_Fortran_COMPILER AND CMAKE_Fortran_COMPILER MATCHES "^$")
    set(CMAKE_Fortran_COMPILER CMAKE_Fortran_COMPILER-NOTFOUND)
endif(DEFINED CMAKE_Fortran_COMPILER AND CMAKE_Fortran_COMPILER MATCHES "^$")
enable_language(Fortran OPTIONAL)
message(STATUS "CMAKE_Fortran_COMPILER_WORKS = ${CMAKE_Fortran_COMPILER_WORKS}")
************

If no Fortran compiler is installed:

$ cmake .
-- The Fortran compiler identification is unknown
-- CMAKE_C_COMPILER_WORKS =
-- Configuring done
-- Generating done
-- Build files have been written to: test-cmake
$ make
-- The Fortran compiler identification is unknown
-- CMAKE_Fortran_COMPILER_WORKS =
[... etc...]

Normally, invoking "make" should not rerun the CMake configuration phase.

Note: If the compiler is found, "make" does not rerun CMake, as expected.

*Update (2014-09-10):* I can reproduce this with CMake 2.6.4, but not with 2.8.12.2. Looks like it has been fixed :-).

(0031650)
David Cole   
2012-11-21 14:57   
Un-assigning bugs that are not on the active roadmap, which no developers are actively working on for the CMake 2.8.11 release.

If one gets put back on the roadmap, re-assign it appropriately at that time.
(0031671)
David Cole   
2012-11-21 15:11   
Re-setting status back to "new" for bugs that are "assigned" but not assigned to a specific developer. When/if these bugs go back on the roadmap for a specific version, assignment to an appropriate developer should take place then...
(0037940)
Brad King   
2015-02-06 14:15   
For reference, as of CMake 3.1 the enable_language documentation:

 http://www.cmake.org/cmake/help/v3.1/command/enable_language.html [^]

states that OPTIONAL is a placeholder that does not work. AFAICT it never worked, was only ever partially implemented, and was not considered during design of much of the more modern toolchain detection logic.

The "language_support" attachments use an approach like what CMake itself uses to decide whether to enable Fortran tests:

 http://www.cmake.org/gitweb?p=cmake.git;a=blob;f=Tests/CheckFortran.cmake;hb=v3.1.2 [^]

This is much like a try_compile check, and is the best approach available right now.
(0037958)
Brad King   
2015-02-12 08:35   
Relevant mailing list discussion thread:

 Fortran detection, issue 9220
 http://thread.gmane.org/gmane.comp.programming.tools.cmake.devel/12327 [^]
(0041575)
Kitware Robot   
2016-06-10 14:27   
Resolving issue as `moved`.

This issue tracker is no longer used. Further discussion of this issue may take place in the current CMake Issues page linked in the banner at the top of this page.