diff --git a/docs/Build.rst b/docs/Build.rst index 3174ca5..fd9aec9 100755 --- a/docs/Build.rst +++ b/docs/Build.rst @@ -1,348 +1,352 @@ =========================== Building the RoSA Framework =========================== .. contents:: :local: Build Dependencies ================== In order to build RoSA, the following tools are required: * `CMake `_ (minimum version 3.6.0 if clang-tidy is used, 2.8.8 otherwise); * Build system of your choice that can be targeted by CMake -- including a compiler supporting *C++14*. * Clang/LLVM -- minimum version 3.9.0 [#f-clang_template_argument_deduction_DeluxeAgent]_ The following additional tools are required to generate documentation: * `Doxygen `_ -- for generating API documentation; * `Graphviz `_ -- not necessary, but the API documentation has nicer graphics when `dot` is available; * `Sphinx `_ (with *Python 2*) -- for generating documentation. The following additional tools are required to check and possibly enforce coding standard: * `clang-tidy `_ * `clang-format `_ General notes ============= * The framework is delivered with a CMake project, which can be used to generate build projects to build the framework. * The provided CMake project supports out-of-tree builds only, i.e. one must use a separate build directory outside of the RoSA source directory. +* Doxygen warnings -- typically indicating actual errors -- are printed to + `stderr`, do check that when generating API documentation which is under + development. + .. _cmake-variables: CMake Variables =============== Beyond the usual CMake variables, the following project-related options are available: `ROSA_INCLUDE_TOOLS` Generate build targets for RoSA tools. The tools are also built when the option is set to `ON`, which is the default setting. `ROSA_INCLUDE_EXAMPLES` Generate build targets for RoSA examples. The examples are also built when the option is set to `ON`, which is the default setting. `ROSA_ENABLE_PEDANTIC` Compile the framework with using `-pedantic` for GCC-compatible compilers, otherwise ignored. The option defaults to `ON`. `ROSA_ENABLE_ASSERTIONS` Enable assertions for non-Debug builds, which defaults to `OFF`. Note that assertions are always enabled for Debug builds and this option is ignored for such builds. .. _CMake_clang_tidy: `ROSA_ENABLE_CLANG_TIDY` Run *clang-tidy* checks when building RoSA, which defaults to `OFF`. When the variable is enabled, build targets created by *Makefile* and *Ninja* generators include calls for clang-tidy. Other generators ignore this option. Note that CMake variables `CMAKE__CLANG_TIDY` are set when enabled. Settings for clang-tidy are defined by the file `.clang-tidy` in the RoSA source directory. Consider the following options when the option is enabled: `ROSA_CLANG_TIDY_PATH` Custom path for `clang-tidy` executable. In order to use clang-tidy, CMake needs to find the `clang-tidy` executable. If `clang-tidy` to be used is available via `PATH`, just leave the option empty -- which is default. Set the absolute path of the directory containing the `clang-tidy` executable otherwise, in which case no default path is searched for `clang-tidy`. `ROSA_CLANG_TIDY_FIX` Apply suggested clang-tidy fixes to the sources, which defaults to `OFF`. Enable the option only if you know what you are doing. .. _CMake_clang_format: `ROSA_INCLUDE_CLANG_FORMAT` **[experimental]** Generate build target -- `format-rosa` -- for formatting RoSA sources with *clang-format*, which defatuls to `OFF`. When the variable is enabled and *CMake is not running on a Windows host*, a build target is generated which can be used to have all the RoSA sources formatted with clang-format. Settings for clang-format are defined by the file `.clang-format` in the RoSA source directory. Note that executing build target `format-rosa` will reformat all the source files *inplace*. Consider the following option when a build target for clang-format is to be generated: `ROSA_CLANG_FORMAT_PATH` Custom path for `clang-format` executable. In order to use clang-format, CMake needs to find the `clang-format` executable. If `clang-format` to be used is available via `PATH`, just leave the option empty -- which is default. Set the absolute path of the directory containing the `clang-format` executable otherwise, in which case no default path is search for `clang-format`. `ROSA_LOG_LEVEL` Level of logging to be used, use one of the following valid integer values. ======== ========= Variable Log Level ======== ========= `0` `ERROR` `1` `WARNING` `2` `INFO` `3` `DEBUG` `4` `TRACE` `5` *disabled* ======== ========= Level of logging defaults to *disabled*. `ROSA_INCLUDE_DOCS` Generate build targets for RoSA documentation, defaults to `ON`. Note that the automatic execution of the generated build targets is controlled by the option `ROSA_BUILD_DOCS`. The actual documentations to build are controlled by the options `ROSA_ENABLE_DOXYGEN` and `ROSA_ENABLE_SPHINX`. `ROSA_BUILD_DOCS` Build RoSA documentation automatically as part of the build process. The option defaults to `OFF` and takes effect only if the option `ROSA_INCLUDE_DOCS` is enabled. .. _CMake_doxygen: `ROSA_ENABLE_DOXYGEN` Use *doxygen* to generate RoSA API documentation. The option defaults to `OFF` and takes effect only if the option `ROSA_INCLUDE_DOCS` is enabled. Doxygen documentation may be generated by executing build target `doxygen-rosa`, which is done as part of the default build process if `ROSA_BUILD_DOCS` is enabled. Doxygen must be available via `PATH` if the option is enabled. The following options are also available to tune doxygen: `ROSA_DOXYGEN_SVG` Use *svg* instead of *png* files for doxygen graphs. The option defaults to `OFF` and takes effect if the tool *dot* is available via `PATH` to be used to generated graph images. `ROSA_DOXYGEN_EXTERNAL_SEARCH` Enable doxygen external search, which defatuls to `OFF`. The following options need to be set if the option is enabled: `ROSA_DOXYGEN_SEARCHENGINE_URL` URL to use for external search. `ROSA_DOXYGEN_SEARCH_MAPPINGS` Doxygen Search Mappings. .. _CMake_sphinx: `ROSA_ENABLE_SPHINX` Use *Sphinx* to generate RoSA documentation. The option defaults to `OFF` and takes effect only if the option `ROSA_INCLUDE_DOCS` is enabled. Sphinx must be available via `PATH` if the option is enabled. The following options are also available to tune Sphinx: `SPHINX_OUTPUT_HTML` Output standalone HTML files. The option defaults to `ON`. Documentation may be generated by executing build target `docs-rosa-html`, which is done as part of the default build process if `ROSA_BUILD_DOCS` is enabled. `SPHINX_OUTPUT_MAN` Output man pages for RoSA tools. The option defaults to `ON`. Man pages may be generated by executing build target `docs-rosa-man`, which is done as part of the default build process if `ROSA_BUILD_DOCS` is enabled. `SPHINX_WARNINGS_AS_ERRORS` When building documentation, treat Sphinx warnings as errors. The option defaults to `ON`. Building RoSA Step-by-Step ========================== Building on Linux with Make --------------------------- Configuring and building the framework on Linux using *Make* is a straightforward process which does not require performing any tricks. Set C and C++ compilers with the variables `CC` and `CXX`, respectively. Use the CMake variable `CMAKE_BUILD_TYPE` to set the type of build: `Debug`, `Release`. Follows an example on building the framework with all options turned on. CMake variables may be skipped as necessary. You need to have RoSA sources on your computer.:: rosa-src$ cd .. $ mkdir rosa-build $ cd rosa-build rosa-build$ CC= CXX= -G "Unix Makefiles" -DROSA_ENABLE_CLANG_TIDY=ON -DROSA_CLANG_TIDY_PATH= -DROSA_INCLUDE_CLANG_FORMAT=ON -DROSA_CLANG_FORMAT_PATH= -DROSA_LOG_LEVEL=4 -DROSA_ENABLE_DOXYGEN=ON -DROSA_DOXYGEN_SVG=ON -DROSA_ENABLE_SPHINX=ON -DCMAKE_BUILD_TYPE=Debug ../rosa-src [CMake configures and generates without errors] $ make [Make builds the project] You just need to re-run Make in order to re-build the project after changing the source code and the CMake project. In case the CMake project is changed, Make automatically calls CMake to update the build project. In order to build documentation and enforce coding standard, refer to corresponding :ref:`cmake-variables`. .. _Build_VS: Building on Windows with Visual Studio -------------------------------------- Unfortunately, the native MSVC compiler cannot compile the framework. One needs to use Clang with Visual Studio in order to build the framework. Microsoft recently started to bundle a special version of Clang to Visual Studio as the *Clang/C2* module. That compiler is, however, several versions behind the official LLVM releases as of Visual Studio 2017. Therefore, it is necessary to use *LLVM for Windows* as an external toolset for Visual Studio. For using *LLVM for Windows*, one downloads the official binary release from http://llvm.org and consults with its documentation. The release provides integration for Visual Studio starting from Visual Studio 2010. Prepare your toolchain like this: #. Install Visual Studio. * If installing Visual Studio 2017, make sure the component *VC++ 2015.3 v140 toolset (x86,x64)* on the *Individual components* tab is selected in *Visual Studio Installer*. Installing the older *v140 toolset* is necessary because the LLVM integration (as of version 4.0.1) does not support the *v141 toolset*, which is default for Visual Studio 2017. * Otherwise, default installation of Visual Studio should go. #. Install *LLVM for Windows*. #. Install the integration by executing as *Administrator*:: > \tools\msbuild\install.bat Having your build system prepared and RoSA sources fetched to your computer, configure and build the framework like this: #. Generate Visual Studio solution with CMake: #. Start CMake. #. Define *source directory* and a separate *build directory* in CMake. #. Click *Configure*. #. Select the proper *generator* for your version of Visual Studio. #. Define your optional toolset (argument for `-T`) as `LLVM-vs`. * Note that `` refers to the version of Visual Studio: `2010`, `2012`, `2013`, and `2014`. Visual Studio 2017 with the *v140 toolset* uses `2014`. #. Click *Finish*. #. Tune CMake variables as you wish. * Note that Visual Studio Generators are multi-configuration generators, hence you cannot set `CMAKE_BUILD_TYPE`. You need to select a configuration to build in Visual Studio. #. Click *Generate*. #. Build the framework with Visual Studio: #. Open the generated `RoSA.sln` from the build directory with Visual Studio. #. Build the project `ALL_BUILD`. You just need to re-build the project in Visual Studio after changing the source code and the CMake project. In case the CMake project is changed, Visual Studio automatically calls CMake the update the build project. Build Result ============ The build process works in the build directory. After a successful build, one can find the following final outputs there -- besides some intermediate files. .. _Build_Result_Software: Software -------- In the build directory, `include` contains header files which are generated by CMake and provide configuration-specific information. The build process generates static libraries in `lib` and executables -- examples and tools -- in `bin`. Projects generated by a multi-configuration generator result in the actual libraries and executables being located in subdirectories corresponding to different build configurations. .. _Build_Result_Documentation: Documentation ------------- Documentation is generated in `docs`. The general documentation can be found in `docs/html`. Man pages for tools can be found in `docs/man`. The API documentation can be found in `docs/doxygen/html`. .. rubric:: Footnotes .. [#f-clang_template_argument_deduction_DeluxeAgent] Clang breaks on template argument deduction when instantiating the class `rosa::deluxe::DeluxeAgent`, the issue is gone with clang version 3.9.0 and newer. Check the documentation on the relevant constructor for more details. diff --git a/docs/Issues.rst b/docs/Issues.rst index f575d46..1e5a920 100755 --- a/docs/Issues.rst +++ b/docs/Issues.rst @@ -1,38 +1,45 @@ ================================================================== Known Issues with the Current Implementation of the RoSA Framework ================================================================== .. contents:: :local: TODO ==== * Project logo - `docs/_themes/rosa-theme/static/logo.png` * License? * Packaging with `CPack `_. * What about design documentation on the basics of RoSA? * What about testing the framework? Known Issues ============ * CMake * VS2017 generates intermediate files for the `ZERO_CHECK` project out of the build directory, see `CMake issue #16458`_. * C++ * Mangled names of function pointers with non-throwing exception specification in function signature will change in C++17. That renders binaries generated with C++14 and C++17 incompatible (for linking). * Since version 4.0.0, Clang warns about this compatibility issue as part of `-Wc++1z-compat`. That warning is turned off in the build scripts. * The langauge standard for building RoSA libraries and applications needs to be lockstepped: now use C++14 only and step to C++17 later when it is properly supported by all major compilers. +* Doxygen + + * There are some strange warnings reported by doxygen when generating + documentation. + * There are some entities for which no or partial documentation is generated, + but no indication of any problem is reported by doxygen. + .. _CMake issue #16458: https://gitlab.kitware.com/cmake/cmake/issues/16458 diff --git a/docs/Release.rst b/docs/Release.rst index bc79b67..e530e43 100755 --- a/docs/Release.rst +++ b/docs/Release.rst @@ -1,60 +1,61 @@ ============================================= Releasing a new version of the RoSA Framework ============================================= .. contents:: :local: Before Releasing ================ :ref:`General recommendations ` should be applied continually for each separate commit. Nevertheless, check the current state of sources against those recommendations before creating a release. Make sure that the changelog is reasonably updated. Validate that the project builds and the framework can be executed without errors on all supported platforms. Generating a Release ==================== Once it is decided to generate a release, follow the steps below. #. Set version number of the new release: * CMake variables in the main `CMakeLists.txt`: `ROSA_VERSION_MAJOR`, `ROSA_VERSION_MINOR`, `ROSA_VERSION_PATCH`; * Sphinx configuration in `docs/conf.py`: * `version` as "`ROSA_VERSION_MAJOR.ROSA_VERSION_MINOR`", * `release` as "`ROSA_VERSION_MAJOR.ROSA_VERSION_MINOR.ROSA_VERSION_PATH`"; * Changelog in `docs/Changelog.rst`. #. Commit the version number update and tag the release. #. Create packages: * source package -- just the source directory; * binary packages for supported platform: .. _Release_create_build: * create `RELEASE` build without assertions and without logging, .. _Release_package_content: * the package contains: - * all generated documentation in `docs`, + * all generated documentation in `docs` -- use `doxygen-rosa`, + `docs-rosa-html`, and `docs-rosa-man` targets for *make*, * public headers -- `include` from source and build directories -- in `include`, * libraries in `lib`, * tool executables in `tools`. #. Publish on website: * HTML documentation as is; * packages for download. diff --git a/include/rosa/support/atom.hpp b/include/rosa/support/atom.hpp index 4369bc5..60fbe06 100644 --- a/include/rosa/support/atom.hpp +++ b/include/rosa/support/atom.hpp @@ -1,179 +1,179 @@ //===-- rosa/support/atom.hpp -----------------------------------*- C++ -*-===// // // The RoSA Framework // //===----------------------------------------------------------------------===// /// /// \file rosa/support/atom.hpp /// /// \author David Juhasz (david.juhasz@tuwien.ac.at) /// /// \date 2017 /// /// \brief Facility for *atoms*, short strings statically encoded as integers. /// /// \note This implementation is based on the \c atom implementation of CAF. /// \todo Check license. /// /// *Atoms* can be used to turn short string literals into statically generated /// types. The literals may consist of at most \c 10 non-special characters, /// legal characters are \c _0-9A-Za-z and the whitespace character. Special /// characters are turned into whitespace, which may result in different string /// literals being encoded into the same integer value, if any of those contain /// at least one special character. /// /// \note The usage of special characters in the string literals used to create /// *atoms* cannot be checked by the compiler. /// /// Example: /// /// \code /// constexpr AtomValue NameValue = atom("name"); /// using NameAtom = AtomConstant; /// /// [](NameAtom){ std::cout << "Argument of type NameAtom"; }(NameAtom::Value) /// \endcode /// //===----------------------------------------------------------------------===// #ifndef ROSA_SUPPORT_ATOM_HPP #define ROSA_SUPPORT_ATOM_HPP #include "rosa/support/debug.hpp" namespace rosa { /// Maximal length of valid atom strings. constexpr size_t MaxAtomLength = 10; /// Underlying integer type of atom values. using atom_t = uint64_t; /// Turn \c rosa::atom_t into a strongly typed enumeration. /// /// Values of \c rosa::atom_t casted to \c rosa::AtomValue may be used in a /// type-safe way. enum class AtomValue : atom_t {}; /// Anonymous namespace with implementational details, consider it private. namespace { // clang-format off /// Encodes ASCII characters to 6-bit encoding. constexpr unsigned char AtomEncodingTable[] = { /* ..0 ..1 ..2 ..3 ..4 ..5 ..6 ..7 ..8 ..9 ..A ..B ..C ..D ..E ..F */ /* 0.. */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* 1.. */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* 2.. */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* 3.. */ 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 0, 0, 0, 0, 0, 0, /* 4.. */ 0, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, /* 5.. */ 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 0, 0, 0, 0, 37, /* 6.. */ 0, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, /* 7.. */ 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 0, 0, 0, 0, 0}; // clang-format on /// Decodes 6-bit characters to ASCII constexpr char AtomDecodingTable[] = " 0123456789" "ABCDEFGHIJKLMNOPQRSTUVWXYZ_" "abcdefghijklmnopqrstuvwxyz"; /// Encodes one character and updates the integer representation. /// /// \param Current an encoded value /// \param CharCode a character to add to \p Current /// /// \return \p Current updated with \p CharCode constexpr atom_t nextInterim(atom_t Current, size_t CharCode) { return (Current << 6) | AtomEncodingTable[(CharCode <= 0x7F) ? CharCode : 0]; } /// Encodes a C-string into an integer value to be used as \c rosa::AtomValue. /// /// \param CStr a string to encode /// \param Interim encoded value to add \p CStr to it /// /// \return \p Interim updated with \p CStr constexpr atom_t atomValue(const char *CStr, atom_t Interim = 0xF) { return (*CStr == '\0') ? Interim : atomValue(CStr + 1, nextInterim(Interim, static_cast(*CStr))); } } // End namespace /// Converts a \c rosa::AtomValue into \c std::string. /// /// \param What value to convert /// /// \return \c std::string encoded in \p What std::string to_string(const AtomValue &What); /// Converts a \c std::string into a \c rosa::AtomValue. /// /// \param S \c std::string to convert /// /// \return \c rosa::AtomValue representing \p S AtomValue atom_from_string(const std::string &S); /// Converts a string-literal into a \c rosa::AtomValue. /// /// \tparam Size the length of \p Str /// /// \param Str the string-literal to convert /// /// \return \c rosa::AtomValue representating \p Str /// -/// \pre \P Str is not too long:\code +/// \pre \p Str is not too long:\code /// Size <= MaxAtomLength + 1 /// \endcode template constexpr AtomValue atom(char const (&Str)[Size]) { // Last character is the NULL terminator. STATIC_ASSERT(Size <= MaxAtomLength + 1, "Too many characters in atom definition"); return static_cast(atomValue(Str)); } /// Lifts a \c rosa::AtomValue to a compile-time constant. /// /// \tparam V \c rosa::AtomValue to lift template struct AtomConstant { /// Constructor has to do nothing. constexpr AtomConstant(void) {} /// Returns the wrapped value. /// /// \return \p V constexpr operator AtomValue(void) const { return V; } /// Returns the wrapped value as of type \c rosa::atom_t. /// /// \return \c rosa::atom_t value from \p V static constexpr atom_t value() { return static_cast(V); } /// An instance *of this constant* (*not* a \c rosa::AtomValue). static const AtomConstant Value; }; // Implementation of the static member field \c rosa::AtomConstant::Value. template const AtomConstant AtomConstant::Value = AtomConstant{}; /// Converts a \c rosa::AtomConstant into \c std::string. /// /// \tparam V \c rosa::AtomValue to convert /// /// \note The actual argument of type `const rosa::AtomConstant` is ignored /// because the \c rosa::AtomValue to convert is encoded in the type itself. /// /// \return the original string encoded in \p V template std::string to_string(const AtomConstant &) { return to_string(V); } } // End namespace rosa #endif // ROSA_SUPPORT_ATOM_HPP