A very simple question

I have a simple, simple Hello World main() function in C++

It is called Katz.?? It is a simple file just 5 lines long. Katz.cpp

What can CMake do with it? Compile it? Make a “Makefile” for it? Nowhere
can I find a

clear and concise description of what CMake does. Instead a vague heap
of gibberish.

To compile and create a simple command-line executable you have a
monstrously complex product here.

Of all the inumerable values you have in CMakeLists.txt where is the
indication of where Katz.cpp lies?

Can you show a simple, simple example of how to use CMake with my
Katz.cpp file?

Thank you

D. Hall

1 Like

This is your CMakeLists.txt

cmake_minimum_required(VERSION 3.19)

project(SIMPLE
    LANGUAGES CXX
)

add_executable(katz)

target_sources(katz PRIVATE 
    main.cpp
    katz.cpp
    katz.h
)

This is all the cmake code you need to get going.

This CMakeLists.txt will be at the source directory of your project:

Say this is your folder ‘foo’

  • CMakeLists.txt
  • main.cpp
  • katz.cpp
  • katz.h

Here are now the cli steps:

# Go the directory where your CMakeLists.txt resides
cd foo

# This creates your build files and puts them in a folder called build, it will also create the folder if it didn't exist
cmake -S . -B build

# This builds your project files
cmake --build build

What can CMake do with it? Compile it? Make a “Makefile” for it?

CMake isn’t a build system, it’s a meta-build system

Essentially cmake doesn’t directly build the binaries.

It creates the build files for the generator you chose.

IE if you chose Visual Studio 2019 as your generator, it will build a Visual Studio 2019 solution.

CMake refers to the build systems as ‘generators’ since CMake generates their project files.

Popular Generators

  • Ninja
  • Visual Studio
  • Unix Makefiles
  • Xcode

Here is a full list of available generators

Why this is necessary?

C/C++ is a very split language with different customs and preferences chosen by platforms.

When these languages were created the build systems became an implementation detail. Resulting in the “variety” we have today.

Cmake is only a reflection of this fact.

Makefiles are the preferred way of doing things on Linux, Visual Studio is the preferred way of doing things on Windows, etc.

What’s the best generator?

If you don’t already have a preference Ninja is easily the fastest/smallest/cross-platform choice. And is highly recommended for CI purposes.

1 Like

‘Say this is your folder ‘foo’’ Do you mean ‘move this to your folder foo’?

Would it be true to say that CMake creates Makefiles?

Plain language would help users of CMake greatly.

A ‘generator’, normally thought of as something which ‘generates’, the active verb,
is a synonym for something which has already(!) been generated by another party. A ‘build system’ such as VS 2019 which is something that Bill Gates generated–not something that the user generated. As a user I ask you what will I, the user, generate when I use your generator?

‘It is a meta-system’ does not divulge any useful information. You are merely misguiding the user with a fancy but meaningless expression, ‘meta-system.’

My feet are meta-systems. The ball on the field is a build-system. But with these exotic descriptions I still don’t know how to play soccer.

‘…Ninja is easily the…’ Nothing about CMake so far is easy so I cannot trust your interpretation of the word ‘easily.’ Anyway, delving into yet another product full of meta-murkiness will not save me time.

I followed your instructions to my simple question it has resulted in this :

D:\hold\src>dir

Datenträger in Laufwerk D: ist DATA
Volumeseriennummer: 48DE-4E30

Verzeichnis von D:\hold\src

16.03.2021 12:44 .
16.03.2021 12:44 …
16.03.2021 12:42 272 CMakeLists.txt
15.03.2021 22:55 84 Katz.cpp
2 Datei(en), 356 Bytes
2 Verzeichnis(se), 136.586.108.928 Bytes frei

D:\hold\src>D:/CMake/bin/cmake -S . -B build
– Building for: NMake Makefiles
– The CXX compiler identification is GNU 10.2.0
– Detecting CXX compiler ABI info
CMake Error: Generator: execution of make failed. Make command was: nmake -f Makefile /nologo cmTC_46641\fast &&
– Detecting CXX compiler ABI info - failed
– Check for working CXX compiler: C:/msys64/mingw64/bin/g++.exe
CMake Error: Generator: execution of make failed. Make command was: nmake -f Makefile /nologo cmTC_57e08\fast &&
– Check for working CXX compiler: C:/msys64/mingw64/bin/g++.exe - broken
CMake Error at D:/CMake/share/cmake-3.20/Modules/CMakeTestCXXCompiler.cmake:59 (message):
The C++ compiler

"C:/msys64/mingw64/bin/g++.exe"

is not able to compile a simple test program.

It fails with the following output:

Change Dir: D:/hold/src/build/CMakeFiles/CMakeTmp

Run Build Command(s):nmake -f Makefile /nologo cmTC_57e08\fast && **Das System kann die angegebene Datei nicht finden**
Generator: execution of make **failed**. Make command was: nmake -f Makefile /nologo cmTC_57e08\fast &&

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

– Configuring incomplete, errors occurred!
See also “D:/hold/src/build/CMakeFiles/CMakeOutput.log”.
See also “D:/hold/src/build/CMakeFiles/CMakeError.log”.

“Would it be true to say that CMake creates Makefiles?”

Yes CMake can create Makefiles.

“meta build system”

Maybe this article can clear up what I meant about the terms “meta-build system” and “generator”. Are these perfect names. Probably not. But we have what we have.

“‘Nothing about CMake so far is easy”

I’ve played with every build system for C++. They all have pitfalls. Meson, bazel, premake, makefiles, etc. If you think CMake is complicated because it wants to confuse people you are wrong. CMake is complicated because every platform decided to do things differently.

I have found CMake to be very robust. Just like C++ it has a learning curve due to historical reasons. I can’t deny that. And just like C++ there is a modern CMake and old CMake. Which also doesn’t help the learning curve. C++98 looks nothing like C++20. CMake 2.x looks nothing like CMake 3.20.

But here is what I will say. Our company is switching from Makefiles to CMake. And you know what? 50% faster build times. Working intellisense. Integration into modern code sanitizers. Much better customer deliverables. Much less code maintenance. Developers can use CLion, Visual Studio Code, Visual Studio 2019, Vim, etc.

“Plain language would help users of CMake greatly.”

Sorry I wrote this up in a rush. Once you start getting absorbed and understanding a project deeply (CMake for me). You tend to forget how your tool looks like to beginners. Though I’d argue the same is true of C++/C.

Perhaps I could refer you to some tutorials instead of a long discourse post:
https://cliutils.gitlab.io/modern-cmake/

" is not able to compile a simple test program."

Seems like CMake was not able to find compilers in your mingw64 environment. CMake doesn’t provide compilers. You need to install the compilers seperately. Afterwards make sure the compilers are available in the path.

Does the following work?

g++ --version

I’d also like to mention that CMake’s extreme flexibility, documentation, and community made it the only tool for our company. Every other tool lacked a lot of functionality that just made them impossible to use.

CMake was the only tool that offered parity with every single niche need our company required. And let me tell you that’s huge. We are transferring 20 years of old build system code into modern CMake. And it’s paying huge dividends.

Also you are quite rude to someone trying to help you. You could just say I didn’t understand your explanation. I’d be willing to explain it a different way.

g++ --version
g++ (Rev9, Built by MSYS2 project) 10.2.0
Copyright © 2020 Free Software Foundation, Inc.
This is free software; see the source for copying conditions. There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.

That link you gave me showed how to do it.

1 install CMake into C:/CMake, this puts cmake.exe into C:/CMake/bin

  1. put C:/CMake/bin onto the end of the PATH environment variable

  2. create the environment variable CXX = the folder containing g++

  3. create a folder C:/hold and under that, C:/hold/src

  4. put a file katz.cpp into C:/hold/src

    katz.cpp =

    #include

    int main() {

    std::cout << “Hello World\n” << std::endl;

    return 0;
    }

  5. put a file CMakeLists.txt next to katz.cpp

    CMakeLists.txt =

    cmake_minimum_required(VERSION 3.14…3.18)

    project(MyKatz
    VERSION
    1.0
    DESCRIPTION
    “Very nice project”
    LANGUAGES
    CXX
    )

    add_executable(myapp katz.cpp)

  6. if C:/hold/build already exists full of files from an earlier build, remove these files

  7. using cmd.exe go into C:/hold

  8. enter > cmake -S src -B build

  9. enter > cmake --build build

The exe file myapp.exe is in C:/hold/build/Debug

And the exe actually outputs “Hello World”

1 Like