5

I write my project in C using QtCreator as IDE and CMake for build. QtCreator ver. >= 4.0.0 include Clang static analyzer, that I try to use.

In my CMakeLists.txt set:

set(CMAKE_C_FLAGS "-std=gnu99 ${CMAKE_C_FLAGS}")

When I launch analysis in console get errors:

error: invalid argument '-std=gnu++11' not allowed with 'C/ObjC'

How to pass '-std=gnu99' to clang analyzer? Maybe it's hardcoded in QtCreator plugin sources?

UDP1: Seems like it's the QtCreator bug: https://bugreports.qt.io/browse/QTCREATORBUG-16290

trafalgarx
  • 702
  • 2
  • 10
  • 13
  • How have you specified the CMake project? When you are only doing C, use `project(myProject LANGUAGES C)`. This will tell CMake not to consider a C++ compiler. – Torbjörn Aug 18 '16 at 06:01
  • @Torbjörn Yes, I set lang in "project" command. Also note that for CMake ver. < 3.0 need write `project(myProject C)` – trafalgarx Aug 18 '16 at 09:30

2 Answers2

3

The variable CMAKE_C_FLAGS is for C code, and not for C++ code. You should be adding it to the CMAKE_CXX_FLAGS instead.

set(CMAKE_CXX_FLAGS "-std=gnu++11 ${CMAKE_CXX_FLAGS}")

and to retain -std=gnu99 for C code, you would add:

set(CMAKE_C_FLAGS "-std=gnu99 ${CMAKE_C_FLAGS}") 
Anya Shenanigans
  • 91,618
  • 3
  • 107
  • 122
  • 1
    … although this is a less than desirable way of doing this - you should be using [`target_compile_options`](http://stackoverflow.com/questions/23995019/what-is-the-modern-method-for-setting-general-compile-flags-in-cmake) although the semantics seem quite obtuse to me – Anya Shenanigans Aug 17 '16 at 16:51
3

The classic approach has been given in the answer by @Petesh.

If you just want to specify the exact C standard version the compiler should comply to, use the global variables CMAKE_C_STANDARD and CMAKE_C_STANDARD_REQUIRED.

In your case that would be

set(CMAKE_C_STANDARD 99)
set(CMAKE_C_STANDARD_REQUIRED TRUE)

CMake will then figure out the exact command options for the detected compiler on its own and add them to all invocations of the compiler.

To overwrite this global setting for a specific target, modify the corresponding target properties:

set_target_properties(myTarget
                      PROPERTIES C_STANDARD 11
                                 C_STANDARD_REQUIRED ON)

An in-depth description of the compile feature options is described in the official CMake documentation: target compile features. Via these compile features it's also possible to require that the detected compiler supports a specific set of language features independent of the language standard:

target_compile_features(myTarget
                        PUBLIC c_variadic_macros  # ISO/IEC 9899:1999
                        PRIVATE c_static_assert   # ISO/IEC 9899:2011
)
Torbjörn
  • 5,512
  • 7
  • 46
  • 73
  • How do I find this information from the manual? It seems CMake has millions of variables and I just have to guess it or look for them on SO. – nowox Aug 24 '17 at 09:32
  • @nowox This is the entry page for the [compile-features](https://cmake.org/cmake/help/latest/manual/cmake-compile-features.7.html). It's linked on the main page of the official CMake documentation, which has greatly improved in the recent years. – Torbjörn Aug 24 '17 at 10:18
  • Bear in mind that that's for the `C` standard and not the `C++` standard, which is defined by the `CMAKE_CXX_STANDARD` variable. The problem the OP was having was in relation to setting the standard flags for the C compiler, instead of the C++ compiler. – Anya Shenanigans Mar 05 '20 at 11:49