.. include:: ../../external-links.part.rst .. index:: single: HelloWorld; Building single: CMake ############################## Building HelloWorld with CMake ############################## In the Installation :ref:`test__install` section, the :ref:`helloworld_test` test used the files in the default installation. Another way is to use the |url::cmake_link| build tool. CMake is an open-source, cross-platform family of tools to build, test, and package software. It controls the software compilation process using simple platform and compiler-independent configuration files. It also generates the native makefiles, projects, and workspaces of your development environment. CMake's main strength is built portability. The same CMake input files can be built with GNU make, Visual Studio (6,7,8) IDEs, Borland make, nmake, and XCode, and so on. Another advantage of CMake is building out-of-source. It simply works out of the box. This facilitates: - Easy cleanup (no cluttering the source tree). Remove the build directory to start from scratch. - Multiple build targets. It is possible to have up-to-date debug and release targets without having to recompile the entire tree. It is easy for systems that do the cross-platform compilation to have up-to-date builds for the host and target platform. To use CMake, you must provide a ``CMakeLists.txt``, a copy of which, can be found in the ``examples/helloworld`` directory that comes with the **Hello World!** example. The content is shown below: The content of the ``CMakeLists.txt`` is: .. tabs:: .. group-tab:: Core DDS (C) .. literalinclude:: ../../../../examples/helloworld/CMakeLists.txt :language: cmake :linenos: .. group-tab:: C++ .. code-block:: cmake project(helloworld LANGUAGES C CXX) cmake_minimum_required(VERSION 3.5) if (NOT TARGET CycloneDDS CXX::ddscxx) find_package(CycloneDDS CXX REQUIRED) endif() # Convenience function, provided by the idlc backend for CXX that generates a CMake # target for the given IDL file. The function calls idlc to generate # source files and compiles them into a library. idlcxx_generate(TARGET ddscxxHelloWorldData_lib FILES HelloWorldData.idl WARNINGS no-implicit-extensibility) add_executable(ddscxxHelloworldPublisher publisher.cpp) add_executable(ddscxxHelloworldSubscriber subscriber.cpp) # Link both executables to IDL data type library and ddscxx. target_link_libraries(ddscxxHelloworldPublisher ddscxxHelloWorldData_lib CycloneDDS CXX::ddscxx) target_link_libraries(ddscxxHelloworldSubscriber ddscxxHelloWorldData_lib CycloneDDS CXX::ddscxx) set_property(TARGET ddscxxHelloworldPublisher PROPERTY CXX_STANDARD 11) set_property(TARGET ddscxxHelloworldSubscriber PROPERTY CXX_STANDARD 11) To build a |var-project-short| based application, you must link your business code to the following: .. tabs:: .. group-tab:: Core DDS (C) - The ``ddsc`` library that contains the DDS API for the application. - The helper functions and structures that represent your datatypes. These helpers are generated by the IDL compiler and can be accessed through the CMake (``idlc_generate``) call that takes the idl file (for example, ``HelloWorld.idl``) as input, then packages the datatyped helpers in a library (for example, ``HelloWorldData_lib``). The ``idlc_generate`` call makes use of how the IDL compiler generates the helpers' functions and structures. The following diagram shows the process: .. image:: /_static/gettingstarted-figures/dds-application-design.png The executables of the |var-project-short|-based application (``HelloworldPublisher`` and ``HelloworldSubscriber``) are linked to |var-project-short| with the CMake ``target_link_libraries()`` call. This call combines the ``ddsc`` lib, the datatype helper lib and the application code. .. note:: CMake attempts to find the ``CycloneDDS`` CMake package in the default system locations. If you experience problems with not being able to locate ``CycloneDDS`` it is often enough to include the |var-project-short| as CMake Prefix Path. For example: ``cmake -DCMAKE_PREFIX_PATH=``. If you have further issues, please refer to CMake's |url::cmake_dependencies|. .. group-tab:: C++ - ``|var-project-short| C++`` libraries that contain the DDS CXX API your application needs. - The wrapper classes and structures that represent your datatypes and the customized-DataWriter's and readers that can handle these data types. The CMake statement generates these classes ``idlcxx_generate()`` that incepts the IDL file invokes the IDL compiler and packages the datatype wrapper classes in a library (e.g. ``ddscxxHelloWorldData_lib``). This process is outlined as follows: .. image:: /_static/gettingstarted-figures/6.1.1-1.png Setting the property for the applications in the CMake ``set_property()`` statement compiles the application against the ``C++ 11`` standard. The application executable (``ddscxxHellowordPublisher``) is built with the CMake ``target_link_libraries()`` statement which links the ddscxx lib, the datatype wrapper classes lib (e.g ``ddscxxHelloWorldData_lib``) and the application code lib. CMake tries to find the ``CycloneDDS`` and ``CycloneDDSCXX`` CMake packages, the details regarding how to locate those packages are described in the next section. When the packages are found, every path and dependencies are automatically set. Building the HelloWorld Example =============================== .. note:: We recommend that to build examples or applications out-of-source, create a ``build`` directory inside the copy of the HelloWorld example directory. #. Open a terminal inside the directory with the HelloWorld files. #. Run: .. code-block:: console mkdir build cd build #. Configure the build environment: .. tabs:: .. group-tab:: Linux .. code-block:: console cmake -DCMAKE_PREFIX_PATH= .. .. group-tab:: macOS .. code-block:: console cmake -DCMAKE_PREFIX_PATH= .. .. group-tab:: Windows .. code-block:: console cmake -G -DCMAKE_PREFIX_PATH= .. On Windows you can build with one of several generators. Usually if you omit the ``-G `` it will pick a sensible default, but if it doesn't work or picks something unexpected you can go to the `CMake generators documentation `__. For example, "Visual Studio 15 2017 Win64" targets a 64-bit build using Visual Studio 2017. .. warning:: If manually specifying generators be careful about mixing and matching! If you compiled |var-project-short| with 32-bit libraries and you try to compile **Hello World!** as 64-bit or vice-versa it will not work. .. warning:: Weird things can happen if you mix ``-DCMAKE_BUILD_TYPE=Release``, ``-DCMAKE_BUILD_TYPE=RelWithDebInfo`` and ``-DCMAKE_BUILD_TYPE=Debug``, try to match what you picked for |var-project-short| in downstream projects. #. CMake uses the ``CMakeLists.txt`` in the HelloWorld directory to create "makefiles" that target the native platform. The |var-project-short| build directory is now ready to build the ``HelloworldPublisher`` and ``HelloworldSubscriber`` executables. Run: .. code-block:: console cmake --build . Your build directory now contains your executables (on Windows they may be in a ``Release`` or ``Debug`` subdirectory). Test the build ============== .. include:: helloworld_run.part.rst