Making a cross platform library with CMake? - c++

Is CMake difficult to use? I've been developing a library using Windows and MSVC++ . I tested my code in Linux and OSX by tediously making objects from each file and making a library out of this.
I have several Directories ex:
Agui
-> Widgets
->Button
->ListBox
-> Backends
-> Allegro
And what I'd like is, for example, if I'm on Windows, it auto generates an msvc project with all these directories and files included and ready to be compiled.
On Linux and OSX I'd like to be able to do something like
cmake
make
is this possible with CMake, and easy to do given my situation.
Thanks

Yes, that is exactly the reason CMake is made for. Huge projects like KDE use CMake.
And its easy to setup.

This is exactly what CMake was developed to do. CMake generates native build files and workspaces that can be used on your platform of choice. So on Unix this is normally Unix Makefiles, on Windows Visual Studio you can select your Visual Studio version to generate a solution that can be opened in the IDE, or use NMake Makefiles.
If you want to add a simple library, you just use the add_library function, giving it a library name and a list of source files. I would recommend taking a look at the CMake tutorial for a brief overview. There is also a book, Mastering CMake, along with many tutorial pages. You can ask the CMake command line for help too, 'cmake --help-command add_library' would show you the add_library documentation.

CMake will generate project files for a number of IDEs, but I find that automake+libtool tend to be easier to use. Here is an excellent tutorial: http://www.lrde.epita.fr/~adl/autotools.html
Don't be put off by the page count: most of it is step-by-step revealing of diagrams.

Related

How to setup complex project with Visual Studio 2022?

I have project that I was developing for years in Linux.
It depends on MKL, libxml++, GSL and armadillo library.
Its installation structure is done in CMake and project is formed by building a shared library and couple of executables that link to it. There are about 20 classes in the library.
Project structure is:
--src
--executable1.cpp
--executable2.cpp
--mysharedlib
--class1.h
--class1.cpp
--...
My question is how to install and run this code in Visual Studio in Windows.
I never used VS before and am still going through tutorials. I managed to run my code by installing Ubuntu on WSL, but I I'd like a VS solution as it'd be handy to pass to user not familiar with Linux.
I tried opening the project directory with VS, hoping CMAKE would do all the magic, but expectedly it cannot locate the dependent libraries, so I am now going through web looking how to integrate each to VS. I managed to find armadillo and mkl guide, but I am lost on how to link these libraries to my project codes and whether I should abandon its current cmake setup and start building the code structure differently in VS.
Any links to useful VS tutorials and advices how to this are greatly appreciated.
VS does have support for CMake, although I have no idea how well VS integrates CMake. If you're not set on using VS, you might want to look into an IDE that uses CMake at it's core, Clion comes to mind. That being said, when coming from Linux you don't have the (initial) luxury of simply installing all the dependencies via a preinstalled package manager.
In order for CMake to find your dependencies (assuming you've configured them by using find_package()) you should add the sources of your dependencies to your project in a thirdparty folder (name is up to you) and add these dependencies using add_subdirectory() instead. This will compile all your dependencies from source, so you might have to configure these dependencies yourself (look into the documentation of your dependencies on how to build them from source).
Another way is to use a package manager that is available on Windows to download, compile and provide your dependencies to your build tools. vcpkg comes to mind, claiming to integrate well with CMake by providing a toolchain file that you can pass to CMake when building your project. You might even be able to configure VS to automatically pass this toolchain to CMake whenever it's invoked.
From personal experience, there is no need to convert an existing project to the VS project structure. There's plenty of available solutions and tools available on Windows to work with CMake projects. Going with the cross-platform approach should be preferred unless you're only targeting Windows, using VS to it's fullest then might give you some additional quality of life.
If you have more specific questions regarding this, I suggest that you update your original post or to create separate, specific questions regarding the processes involved in setting up an existing CMake project on Windows.

Maintaining Makefiles and CMakeLists.txt

When you're working to very big projects with a large amount of people, maintaining both Makefiles and CMakeLists.txt could be very difficult. I know that CMakeLists.txt could generate Makefiles, but suppose that I want to compile my code by using make and in the same time, use an IDE to have a kind of intellisense. How can I achieve it?
In the scenario that I'm describing, CMakeLists.txt files will disappear, so I won't have the chance to generate solutions with them.
CMake is not a build manager!
It is a generator of files for other build managers!
So you can generate project for IDEs (Visual Studio, Xcode, CodeBlocks, ..) or generate MakeFile, or whatever you prefer and CMake supports. So I do not understand why do you maintain CMakeLists.txt and Makefiles at the same time.
Just maintain CMakeLists.txt and then generate respective Makefiles from it.
For details see CMake Documentation - generators:
Command-Line Build Tool Generators
These generators support command-line build tools. In order to use them, one must launch CMake from a command-line prompt whose environment is already configured for the chosen compiler and build tool.
Borland Makefiles
MSYS Makefiles
MinGW Makefiles
NMake Makefiles
NMake Makefiles JOM
Ninja
Unix Makefiles
Watcom WMake
Bottom line you should be able to generate files for IDE or Makefile for you favorite build manager without any complications.
In the scenario that I'm describing, CMakeLists.txt files will disappear, so I won't have the chance to generate solutions with them.
WAT? You are doing something very strange and most probably wrong and you didn't provide any details abut that.
Concerning intellisense I would say:
Visual Studio 2017 as built-in support for CMake, see announcement
CMake can generate a json file with all commands see CMAKE_EXPORT_COMPILE_COMMANDS
so you can use it to have smart clang based completion in vim
QtCreator as built-in support for CMake so you'll have completion too.
Extra tip at first: Do not try to mix both handmade make files and CMake over the whole time of the project.
The normal way is to create the make files using cmake. The extra of cmake is the cross platform and in your case the nativ support by some IDEs, eg. QtCreator, CLion(awaik). For a wide range of other IDE cmake can generate the project files.
Example Workflow using QtCreator:
Create a simple CMakeLists.txt, at least with the name of the project
Load this into QtCreator
Add source files, update the CMakeLists.txt from within QtCreator
Build from within QtCreator, repeat
But the same CMakeLists.txt will be used to create the make file on command line. Or on your build server or CI system.

C++ how to manage dependencies (use libraries from github for example)

I'm very new to C++ world, so please, sorry for such a dummy question. I googled a little, but wasn't able to find a proper answer.
My question is fairly simple - how should I use libraries in C++ world. For example in Java - there is maven and gradle for this task. In Python - I use pip. In javascript npm and bower do all the stuff. In C# you use nuget or just adding DLL lib to your project. But looks like in C++ things isn't such easy.
I found a tool, called conan but amount of libraries they have is pretty small and does not include any what I'm looking for.
So, for example - I want to use nlp lib meta but it seems like they don't provide any installer files. So I assume I need to get sources from Github. Should I compile them and then try to add the compiled files to my project or do I need to have a lib folder in my project, and put meta's sources in those folder and after operate with meta's sources as they are in my project?
My question isn't about how to install specific meta lib, but more from the source management point of view. If I use Visual Studio on Windows for example, but my colleague will be coding Clion under Linux. And I don't know the proper way of managing dependencies in C++ world.
C++ doesn't have anything like pip or npm/bower. I don't know if maven or gradle can be persuaded to handle C++ libraries.
In general, you are going to have to end up with
Header files in a directory somewhere
library files (either static libraries, or DLLs/shared objects). If the library is a header-only library like some of the boost libraries, then you won't need this.
You get hold of the library files, either by building them on your machine (typical for open source projects, and projects aimed at Linux platforms), or by downloading the pre-compiled binaries (typical for Windows libraries, particularly paid-for).
Hopefully, the instructions for building the library will be included on the library website. As noted in the comments, 'meta' seems to be quite good at that.
When you try to compile with the library, you may need a command line option (eg -I) to specify the directory containing the header files, and you may need a linker option (eg -l) to tell the linker to link against your library.
Cget will install any package that uses standard cmake, and works for linux and windows. It has shorten syntax for getting packages directly from github(such as cget install google/googletest).
In addition, dependencies can be automatically downloaded as well by listing them in a requirements.txt file.
There is also recipes for installing non-cmake packages and the repository here has over 300 libraries(and growing). So you can install curl with just cget install pfultz2/cget-recipes curl.
C++ sadly has no package manager for libraries. Some are out there and try to be one which are still small and scattered though (like conan).
In linux you have some "-dev" packages you can install but they are also not "all".
You most likely end up downloading them yourself. Next though is you have the problem of integrating those libraries. You have different build systems per operating system so you have to see how you build c++ files.
Like in windows with Visual studio you have to get a visual studio project or a nmake compatible makefile to build the libraries and then add them to your project. Same with linux makefiles.
There are several build frameworks who are higher level like cmake. The example you have in your post also works with CMake. So integrating that one into a cmake build environment would be easier but this only applies for other libraries also trying to use/integrate cmake build environments to it (e.g. boost / qt is doing this).
Yeah these are some thoughts to this. Sadly there won't be an easy/definitive answer to this because there is no real central c++ packet repository which is also integrated into a build system.
It appears to me that the Crascit/DownloadProject could be of help in your situation. It provides CMake plugins for downloading projects from a git repository by specifying tags, etc. Then you can use add_custom_target to run commands you need to have the project built.
There are a number of popular C++ released via nuget packages.
You can search on the gallery for them, usually using the native or c++ tags. Obviously you need a nuget manager for your OS, and I'm pretty sure that the C++ nuget packages rely on MSBuild for a lot of the grunt work, so you may have trouble getting a non-Visual Studio oriented setup to work nicely.
Also Gradle actually does have some support for native dependencies as well. I had a look at little while ago but the work on it was curtailed because the support for VS 2015 was lacking.
I recommend vcpkg for cross platform development. It has a number of IDE integrations. GitHub project is here.
I do cross platform development using tools like CMake, Visual Studio, WSL. vcpkg was incredibly helpful.
I started new project... in cureent time it's just "source package manager" you can provide some source code on github and then it will be just copy to you project (based on cmake + auto generating cmake files)
So links here:
https://github.com/wsjcpp/wsjcpp

Generate Embarcadero project files from CMake files

I have a C++ code base with a large number of projects. Usually I can use CMake to generate the required project files for QtCreator, XCode, Visual Studio, etc. Now I need to compile for Embarcadero, but it does not seem that CMake supports it.
Does CMake support Embarcadero? If not, is there maybe some set of projects that I could generate with CMake and then import into Embarcadero.
For a toy example it may work with the bcc and bcc32c, bcc64 is not supported at all.
Maybe the new "free" compiler will help to change that - the press release seems to imply this.
Personally, I would not put my hopes to high. So far, everything I have seen from the company Embarcadero was just a let down.
You can use CMake's "Borland Makefiles" generator and then use Embarcadero's clang based bcc32c to compile the project. Here's their blog post about it: https://community.embarcadero.com/blogs/entry/using-cmake-with-the-free-embarcadero-c-compiler
I didn't find a way to generate project files for their IDE yet, but I'm wondering if one could use one of the "Visual Studio" generators, then manually change the file extension (considering Embarcadero is using MSBuild). But that's just a wild guess.
According to the current CMake documentation on generators, no CMake does not produce Embarcadero project files. Instead, you could use one of the Makefile generators, and set your IDE to run cmake and make when you execute its "build" command.

Cmake support in Eclipse

According to this, I have 3 options to use cmake in Eclipse CDT for C++. None of them works.
The first is because I use out-of-source builds and the limitations of the generator is so lame. Also, it uses a hardcoded Eclipse project template, so it is fragile like hell. The second is the poor man's version of cmake support. It does not add any value to Eclipse, really. The third one simply does not work. I can't make an existing cmake project. I can create a new one, but not opening an existing one. Also, the cmake properties in the project properties windows throw an exception and that's it. Does not even show up.
Is there any GOOD support in Eclipse for cmake? Or any other powerful IDE? Like adding the CmakeList.txt and the corresponding project is created? I am mainly interested in having the proper include paths and the global make targets based on the cmake files. And of course it would be nice to have syntax colored editing of cmake files, etc.
We successfully use both Eclipse CDT and Qt Creator with a large CMake based project.
For Eclipse, we usually use option two exactly as described. There is also a CMake Eclipse plug-in called CMake Editor for syntax highlighting and command completion.
Personally, I am using QtCreator. It has quite good CMake support and is very fast. You should initially configure your project with the CMake GUI (using the Make or NMake Generator) and then open your top-level CMakeLists.txt file in QtCreator and point it to your already configured binary directory.
Have you taken a look at Qt Creator? It might have the features you are looking for.
I use CMake GUI for generating CDT project or Unix makefiles and then import it via Eclipse.
Also I use KDevelop 4 because it simply opens CMake projects and tightly integrates CMake support.
Congratulations, CLion http://www.jetbrains.com/clion/ new C++ IDE with CMake well integrated. See its features https://www.youtube.com/watch?feature=player_embedded&v=MY_Z90Tj6is
I tried all three and have found option 2 to be the only useful one. Option 1, the cmake CDT generator, is useless. I cannot get option 3 to work either.
Yes, option 2 is the "poor man's version" insofar as you must follow a series of steps when setting up a new project, rather than pressing a single button. But I have had good success with it for many projects in the past year. Like you, I always do out of source builds.
Also, to get syntax coloring of CMake files, use the excellent CMakeEd plugin for eclipse. It's beautiful.
CDT has official CMake support plugin currently. You can find through Help->Install menu of Eclipse.