diff --git a/.github/workflows/build-macos.yml b/.github/workflows/build-macos.yml index 837963b..6a2a18d 100644 --- a/.github/workflows/build-macos.yml +++ b/.github/workflows/build-macos.yml @@ -125,7 +125,7 @@ jobs: # Step: Test - name: Test - run: ${{ steps.paths.outputs.build_dir }}/bin/UGridApiTests + run: ${{ steps.paths.outputs.build_dir }}/tests/api/UGridAPITests # Step: Install - name: Install diff --git a/.github/workflows/style-check.yml b/.github/workflows/style-check.yml index 91768a6..273c5fe 100644 --- a/.github/workflows/style-check.yml +++ b/.github/workflows/style-check.yml @@ -18,7 +18,13 @@ jobs: - name: Run clang-format and report result run: | - declare -a directories=("src" "include" "tests") + declare -a directories=( + "libs/UGrid/src" + "libs/UGrid/include" + "libs/UGridAPI/src" + "libs/UGridAPI/include" + "tests" + ) # Parse full lines export IFS=$'\n' for directory in "${directories[@]}"; do diff --git a/CMakeLists.txt b/CMakeLists.txt index 331ce32..6a12e51 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,130 +1,44 @@ -# Works with 3.14 and tested through 3.18 -cmake_minimum_required(VERSION 3.16...3.18) - -# Set compiler flags -enable_language(C CXX) - -option(PRODUCE_CODE_COVERAGE "Produce code coverage files under GNU compilers" OFF) - -# Project name and a few useful settings. Other commands can pick up the results -project( - UGrid - VERSION 0.0.0 - DESCRIPTION "Library for reading/writing UGrid files." - LANGUAGES CXX C) - -# Make sure all executables and shared libraries end up in one directory, -# otherwise the executables won't run under Windows. This will cause -# the build to fail. -set(LIBRARY_OUTPUT_PATH "${CMAKE_BINARY_DIR}/bin") -set(EXECUTABLE_OUTPUT_PATH "${CMAKE_BINARY_DIR}/bin") - -# Create position independent binaries -set(CMAKE_POSITION_INDEPENDENT_CODE ON) -# Require C++17 -set(CMAKE_CXX_STANDARD 17) -set(CMAKE_CXX_STANDARD_REQUIRED ON) -# Disable compiler specific extensions -set(CMAKE_CXX_EXTENSIONS OFF) -# Set cmake installation prefix, so UGrid library gets installed under /UGrid -SET(CMAKE_INSTALL_PREFIX "${CMAKE_INSTALL_PREFIX}/UGrid") - -if(CMAKE_PROJECT_NAME STREQUAL PROJECT_NAME) - if(CMAKE_CXX_COMPILER_ID STREQUAL "GNU") - set(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS_RELEASE} -g -O2 -std=c++17 -Werror -Wall -Wextra -pedantic -Wno-unused-function") - set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} -g -std=c++17") - else() - set(CMAKE_CXX_FLAGS_RELEASE - "${CMAKE_CXX_FLAGS_RELEASE} /EHsc /MP /std:c++17") - set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} /EHsc /MP /std:c++17") - endif() - - # Create position independent binaries - set(CMAKE_POSITION_INDEPENDENT_CODE ON) - - # Disable compiler specific extensions - set(CMAKE_CXX_EXTENSIONS OFF) - - # Let's nicely support folders in IDEs - set_property(GLOBAL PROPERTY USE_FOLDERS ON) - - # Note this needs to be done in the main CMakeLists since it calls - # enable_testing, which must be in the main CMakeLists. - - include(FetchContent) - set(FETCHCONTENT_QUIET off) - - FetchContent_Declare( - googletest - GIT_REPOSITORY https://github.com/google/googletest.git - GIT_TAG v1.13.0 - ) - if(WIN32) - set(gtest_force_shared_crt ON CACHE BOOL "" FORCE) - endif() - - FetchContent_GetProperties(googletest) - if(NOT googletest_POPULATED) - FetchContent_Populate(googletest) - add_subdirectory(${googletest_SOURCE_DIR} ${googletest_BINARY_DIR} EXCLUDE_FROM_ALL) - endif() - - include(CTest) - - # Docs only available if this is the main app - add_subdirectory(docs) - -endif() - -# Determine version suffix from environment variable -if(DEFINED ENV{VERSION_SUFFIX}) - set(VERSION_SUFFIX $ENV{VERSION_SUFFIX}) -else() - set(VERSION_SUFFIX .0) -endif() - -# Boost -if(WIN32) - # In windows use static libraries - set(Boost_USE_STATIC_LIBS ON) -endif() -find_package(Boost REQUIRED COMPONENTS system filesystem) -include_directories(${Boost_INCLUDE_DIR}) - -# Use NetCDF -find_package(netCDF REQUIRED COMPONENTS C) -if (netCDF_FOUND) - message(STATUS "Found NetCDF ${netCDF_VERSION}") -else() - message(FATAL_ERROR "Could not find NetCDF" ) -endif() - -# Use NetCDF-cxx -find_package(netCDFCxx REQUIRED) -if (netCDFCxx_FOUND) - message(STATUS "Found NetCDFCxx ${netCDFCxx_VERSION}") - else() - message(FATAL_ERROR "Could not find NetCDFCxx") -endif() - -find_package(hdf5 REQUIRED) -if (hdf5_FOUND) - message(STATUS "Found HDF5 ${hdf5_VERSION}") -endif() - -# Run packaging scripts -add_subdirectory(package) - -# The version file -add_subdirectory(include/Version) - -# The static library -add_subdirectory(src/UGrid) - -# The dynamic library -add_subdirectory(src/UGridApi) - -# Testing only available if this is the main app. -if(CMAKE_PROJECT_NAME STREQUAL PROJECT_NAME) - add_subdirectory(tests) -endif() \ No newline at end of file +cmake_minimum_required(VERSION 3.23) + +set(UGRID_VERSION 0.0.0) + +project( + UGrid + VERSION ${UGRID_VERSION} + DESCRIPTION "Library for reading and writing UGrid files." + LANGUAGES CXX C +) + +# configuration options +if (NOT WIN32) + message(NOTICE "Build type: ${CMAKE_BUILD_TYPE}") +endif() + +# configuration options +include(cmake/user_config_options.cmake) + +# configure the compiler +include(cmake/compiler_config.cmake) + +# fetch dependencies, must appear after options.cmake +include(cmake/fetch_contents.cmake) + +# find required packages +include(cmake/find_packages.cmake) + +# organize targets into folders, can be remove in version > 3.26 (ON by default) +set_property(GLOBAL PROPERTY USE_FOLDERS ON) + +# Docs only available if this is the main app +add_subdirectory(docs) + +# Run packaging scripts: requires semantic version +add_subdirectory(package) + +# Libraries +add_subdirectory(libs) + +# Add unit tests +if(ENABLE_UNIT_TESTING) + add_subdirectory(tests) +endif() diff --git a/cmake/compiler_config.cmake b/cmake/compiler_config.cmake new file mode 100644 index 0000000..e1762f2 --- /dev/null +++ b/cmake/compiler_config.cmake @@ -0,0 +1,32 @@ +# Set the C++ standard +set(CMAKE_CXX_STANDARD 20) +set(CMAKE_CXX_STANDARD_REQUIRED ON) + +# Disable compiler-specific extensions +set(CMAKE_CXX_EXTENSIONS OFF) + +# Create position-independent executables and shared libraries +set(CMAKE_POSITION_INDEPENDENT_CODE ON) + +# Add compiler-specific options and definitions per supported platform +if (UNIX) + if(CMAKE_CXX_COMPILER_ID STREQUAL "GNU") + add_compile_options("-fvisibility=hidden;-Werror;-Wall;-Wextra;-pedantic;-Wno-unused-function") + add_compile_options("$<$:-O2>") + add_compile_options("$<$:-g>") + else() + message(FATAL_ERROR "Unsupported compiler. Only GNU is supported under Linux. Found ${CMAKE_CXX_COMPILER_ID}.") + endif() +elseif(WIN32) + if(CMAKE_CXX_COMPILER_ID STREQUAL "MSVC") + add_compile_options("/EHsc;/MP;/W3;/WX") + add_compile_options("$<$:/O2>") + add_compile_options("$<$:/Od;/DEBUG>") + add_compile_definitions("_USE_MATH_DEFINES") + add_compile_definitions("_CRT_SECURE_NO_WARNINGS") + else() + message(FATAL_ERROR "Unsupported compiler. Only MSVC is supported under Windows. Found ${CMAKE_CXX_COMPILER_ID}.") + endif() +else() + message(FATAL_ERROR "Unsupported platform. Only Linux and Windows are supported.") +endif() diff --git a/cmake/fetch_contents.cmake b/cmake/fetch_contents.cmake new file mode 100644 index 0000000..270cd2d --- /dev/null +++ b/cmake/fetch_contents.cmake @@ -0,0 +1,23 @@ +include(FetchContent) +set(FETCHCONTENT_QUIET off) + +if(ENABLE_UNIT_TESTING) + # Fetch google test + FetchContent_Declare( + googletest + GIT_REPOSITORY https://github.com/google/googletest.git + GIT_TAG v1.13.0 + ) + + if(WIN32) + set(gtest_force_shared_crt ON CACHE BOOL "" FORCE) + endif() + + FetchContent_GetProperties(googletest) + if(NOT googletest_POPULATED) + FetchContent_Populate(googletest) + add_subdirectory(${googletest_SOURCE_DIR} ${googletest_BINARY_DIR} EXCLUDE_FROM_ALL) + endif() + + include(CTest) +endif() diff --git a/cmake/find_packages.cmake b/cmake/find_packages.cmake new file mode 100644 index 0000000..ef1bd1f --- /dev/null +++ b/cmake/find_packages.cmake @@ -0,0 +1,28 @@ +# Boost +set(BOOST_MIN_REQ_VERSION "1.78.0") +find_package(Boost ${BOOST_MIN_REQ_VERSION} REQUIRED) +if (NOT Boost_FOUND) + message(FATAL_ERROR "Could not find Boost (minimum required version is ${BOOST_MIN_REQ_VERSION})") +endif() + +# netCDF +find_package(netCDF REQUIRED COMPONENTS C) +if (netCDF_FOUND) + message(STATUS "Found NetCDF ${netCDF_VERSION}") +else() + message(FATAL_ERROR "Could not find NetCDF" ) +endif() + +# netCDFCxx +find_package(netCDFCxx REQUIRED) +if (netCDFCxx_FOUND) + message(STATUS "Found NetCDFCxx ${netCDFCxx_VERSION}") + else() + message(FATAL_ERROR "Could not find NetCDFCxx") +endif() + +# hdf5 +find_package(hdf5 REQUIRED) +if (hdf5_FOUND) + message(STATUS "Found HDF5 ${hdf5_VERSION}") +endif() diff --git a/cmake/user_config_options.cmake b/cmake/user_config_options.cmake new file mode 100644 index 0000000..319ccf6 --- /dev/null +++ b/cmake/user_config_options.cmake @@ -0,0 +1,15 @@ +# unit testing option +option( + ENABLE_UNIT_TESTING + "Enables building the unit test executables" + ON +) + +# code coverage option +if(LINUX AND CMAKE_CXX_COMPILER_ID STREQUAL "GNU") + option( + ENABLE_CODE_COVERAGE + "Generates code coverage statistics." + OFF + ) +endif() diff --git a/docs/CMakeLists.txt b/docs/CMakeLists.txt index 69ece58..4b8d29c 100644 --- a/docs/CMakeLists.txt +++ b/docs/CMakeLists.txt @@ -6,8 +6,8 @@ endif() set(DOXYGEN_INPUT_LIST "${CMAKE_CURRENT_SOURCE_DIR}/main_page.md \ - ${PROJECT_SOURCE_DIR}/include/UGrid \ - ${PROJECT_SOURCE_DIR}/include/UGridApi") + ${PROJECT_SOURCE_DIR}/libs/UGrid/include/UGrid \ + ${PROJECT_SOURCE_DIR}/libs/UGridAPI/include/UGridAPI") set(DOXYGEN_OUTPUT_DIR ${CMAKE_CURRENT_BINARY_DIR}) set(DOXYGEN_INDEX_FILE ${DOXYGEN_OUTPUT_DIR}/html/index.html) set(DOXYFILE_IN ${CMAKE_CURRENT_SOURCE_DIR}/Doxyfile.in) @@ -25,11 +25,11 @@ file(MAKE_DIRECTORY ${DOXYGEN_OUTPUT_DIR}) # UGrid headers file(GLOB UGrid_HEADER_LIST CONFIGURE_DEPENDS - "${PROJECT_SOURCE_DIR}/include/UGrid/*.hpp") + "${PROJECT_SOURCE_DIR}/libs/UGrid/include/UGrid/*.hpp") # UGridapi headers file(GLOB UGridAPI_HEADER_LIST CONFIGURE_DEPENDS - "${PROJECT_SOURCE_DIR}/include/UGridApi/*.hpp") + "${PROJECT_SOURCE_DIR}/libs/UGridAPI/include/UGridAPI/*.hpp") # markdown file file(GLOB DOXYGEN_MARKDOWN_FILES CONFIGURE_DEPENDS @@ -41,7 +41,7 @@ add_custom_command( DEPENDS ${UGrid_HEADER_LIST} ${UGridAPI_HEADER_LIST} ${DOXYGEN_MARKDOWN_FILES} COMMAND ${DOXYGEN_EXECUTABLE} ${DOXYFILE_OUT} - WORKING_DIRECTORY "${PROJECT_SOURCE_DIR}/include" + WORKING_DIRECTORY "${PROJECT_SOURCE_DIR}/libs" MAIN_DEPENDENCY ${DOXYFILE_OUT} ${DOXYFILE_IN} COMMENT "Generating docs") diff --git a/include/Version/CMakeLists.txt b/include/Version/CMakeLists.txt deleted file mode 100644 index 22624cb..0000000 --- a/include/Version/CMakeLists.txt +++ /dev/null @@ -1,3 +0,0 @@ -# Configure version file -configure_file("${CMAKE_CURRENT_SOURCE_DIR}/Version.hpp.in" - "${CMAKE_CURRENT_SOURCE_DIR}/Version.hpp" @ONLY) diff --git a/libs/CMakeLists.txt b/libs/CMakeLists.txt new file mode 100644 index 0000000..1feedb6 --- /dev/null +++ b/libs/CMakeLists.txt @@ -0,0 +1,5 @@ +# Add UGrid static lib +add_subdirectory(UGrid) + +# Add UGridAPI dynamic lib +add_subdirectory(UGridAPI) diff --git a/libs/UGrid/CMakeLists.txt b/libs/UGrid/CMakeLists.txt new file mode 100644 index 0000000..fe8bd8c --- /dev/null +++ b/libs/UGrid/CMakeLists.txt @@ -0,0 +1,109 @@ +# project name +project( + UGrid + VERSION ${CMAKE_PROJECT_VERSION} + DESCRIPTION "UGrid static library" + LANGUAGES CXX C +) + +# target name +set(TARGET_NAME ${PROJECT_NAME}) + +# static library +add_library(${TARGET_NAME} STATIC) + +# source directories +set(SRC_DIR ${PROJECT_SOURCE_DIR}/src) + +# include directories +set(INC_DIR ${PROJECT_SOURCE_DIR}/include) +set(DOMAIN_INC_DIR ${INC_DIR}/UGrid) + +# list of target sources +set( + SRC_LIST + ${SRC_DIR}/Contacts.cpp + ${SRC_DIR}/Mesh1D.cpp + ${SRC_DIR}/Mesh2D.cpp + ${SRC_DIR}/Network1D.cpp + ${SRC_DIR}/UGridEntity.cpp +) + +# list of target headers +set( + INC_LIST + ${DOMAIN_INC_DIR}/Constants.hpp + ${DOMAIN_INC_DIR}/Contacts.hpp + ${DOMAIN_INC_DIR}/Mesh1D.hpp + ${DOMAIN_INC_DIR}/Mesh2D.hpp + ${DOMAIN_INC_DIR}/Network1D.hpp + ${DOMAIN_INC_DIR}/Operations.hpp + ${DOMAIN_INC_DIR}/UGridEntity.hpp + ${DOMAIN_INC_DIR}/UGridVarAttributeStringBuilder.hpp +) + +# add sources to target +target_sources( + ${TARGET_NAME} + PRIVATE + ${SRC_LIST} + PUBLIC + FILE_SET HEADERS + BASE_DIRS + ${INC_DIR} + FILES + ${INC_LIST} +) + +# Add precompiled header +target_precompile_headers( + ${TARGET_NAME} + PRIVATE + + + + + + + + + +) + +# Expose the interface of the static lib +target_include_directories(${TARGET_NAME} PUBLIC ${INC_DIR} ${PROJECT_SOURCE_DIR}/../UGridAPI/include) + +# Boost +target_include_directories(${TARGET_NAME} SYSTEM PUBLIC ${Boost_INCLUDE_DIR}) + +# link required libraries +target_link_libraries( + ${TARGET_NAME} + LINK_PUBLIC + netCDF::netcdf + netCDF::netcdf-cxx4 +) + +# Make sure that coverage information is produced when using gcc +if(ENABLE_CODE_COVERAGE AND CMAKE_CXX_COMPILER_ID STREQUAL "GNU") + target_compile_options( + ${TARGET_NAME} + PRIVATE + --coverage # equivalent to -f profile-arcs -ftest-coverage + -static-libgcc + -static-libstdc++ + ) + target_link_libraries(${TARGET_NAME} PRIVATE gcov) +endif() + +install(TARGETS ${TARGET_NAME} FILE_SET HEADERS DESTINATION "include") + +# group the sources in IDE tree +source_group("Source Files" FILES ${SRC_LIST}) +# group the headers in IDE tree +source_group("Header Files" FILES ${INC_LIST}) + +# Add unit tests +# if(ENABLE_UNIT_TESTING) +# add_subdirectory(tests) +# endif() diff --git a/include/UGrid/Constants.hpp b/libs/UGrid/include/UGrid/Constants.hpp similarity index 100% rename from include/UGrid/Constants.hpp rename to libs/UGrid/include/UGrid/Constants.hpp diff --git a/include/UGrid/Contacts.hpp b/libs/UGrid/include/UGrid/Contacts.hpp similarity index 99% rename from include/UGrid/Contacts.hpp rename to libs/UGrid/include/UGrid/Contacts.hpp index 8844141..032d46f 100644 --- a/include/UGrid/Contacts.hpp +++ b/libs/UGrid/include/UGrid/Contacts.hpp @@ -28,7 +28,7 @@ #pragma once #include -#include +#include /// \namespace ugrid /// @brief Contains the logic of the C++ static library diff --git a/include/UGrid/Mesh1D.hpp b/libs/UGrid/include/UGrid/Mesh1D.hpp similarity index 99% rename from include/UGrid/Mesh1D.hpp rename to libs/UGrid/include/UGrid/Mesh1D.hpp index b334517..4a44f06 100644 --- a/include/UGrid/Mesh1D.hpp +++ b/libs/UGrid/include/UGrid/Mesh1D.hpp @@ -27,7 +27,7 @@ #pragma once -#include +#include #include diff --git a/include/UGrid/Mesh2D.hpp b/libs/UGrid/include/UGrid/Mesh2D.hpp similarity index 99% rename from include/UGrid/Mesh2D.hpp rename to libs/UGrid/include/UGrid/Mesh2D.hpp index 308572a..d73b266 100644 --- a/include/UGrid/Mesh2D.hpp +++ b/libs/UGrid/include/UGrid/Mesh2D.hpp @@ -27,7 +27,7 @@ #pragma once -#include +#include #include diff --git a/include/UGrid/Network1D.hpp b/libs/UGrid/include/UGrid/Network1D.hpp similarity index 99% rename from include/UGrid/Network1D.hpp rename to libs/UGrid/include/UGrid/Network1D.hpp index 1bd6cbe..a4e8470 100644 --- a/include/UGrid/Network1D.hpp +++ b/libs/UGrid/include/UGrid/Network1D.hpp @@ -28,7 +28,7 @@ #pragma once #include -#include +#include /// \namespace ugrid /// @brief Contains the logic of the C++ static library diff --git a/include/UGrid/Operations.hpp b/libs/UGrid/include/UGrid/Operations.hpp similarity index 100% rename from include/UGrid/Operations.hpp rename to libs/UGrid/include/UGrid/Operations.hpp diff --git a/include/UGrid/UGridEntity.hpp b/libs/UGrid/include/UGrid/UGridEntity.hpp similarity index 96% rename from include/UGrid/UGridEntity.hpp rename to libs/UGrid/include/UGrid/UGridEntity.hpp index cac6d75..4cb849c 100644 --- a/include/UGrid/UGridEntity.hpp +++ b/libs/UGrid/include/UGrid/UGridEntity.hpp @@ -240,11 +240,11 @@ namespace ugrid std::map m_related_variables; ///< Additional variables related to the entity (foe example defined on node, edge or face) std::string m_entity_name = ""; ///< The name of the entity - bool m_spherical_coordinates = false; ///< If it is a spherical entity - int m_start_index = 0; ///< The start index - int m_int_fill_value = int_missing_value; ///< The fill value for arrays of int - int m_double_fill_value = double_missing_value; ///< The fill value for arrays of double - int m_epsg_code = 0; ///< The epsg code + bool m_spherical_coordinates = false; ///< If it is a spherical entity + int m_start_index = 0; ///< The start index + int m_int_fill_value = int_missing_value; ///< The fill value for arrays of int + double m_double_fill_value = double_missing_value; ///< The fill value for arrays of double + int m_epsg_code = 0; ///< The epsg code private: /// @brief Produces the attribute variables related to coordinate locations diff --git a/include/UGrid/UGridVarAttributeStringBuilder.hpp b/libs/UGrid/include/UGrid/UGridVarAttributeStringBuilder.hpp similarity index 100% rename from include/UGrid/UGridVarAttributeStringBuilder.hpp rename to libs/UGrid/include/UGrid/UGridVarAttributeStringBuilder.hpp diff --git a/src/UGrid/Contacts.cpp b/libs/UGrid/src/Contacts.cpp similarity index 98% rename from src/UGrid/Contacts.cpp rename to libs/UGrid/src/Contacts.cpp index 4c6f602..89b6df0 100644 --- a/src/UGrid/Contacts.cpp +++ b/libs/UGrid/src/Contacts.cpp @@ -28,7 +28,7 @@ #include #include #include -#include +#include using ugrid::Contacts; @@ -196,7 +196,7 @@ void Contacts::inquire(ugridapi::Contacts& contacts) const { if (auto const it = m_topology_attribute_variables.find("contact_type"); it != m_topology_attribute_variables.end()) { - contacts.num_contacts = it->second.at(0).getDim(0).getSize(); + contacts.num_contacts = static_cast(it->second.at(0).getDim(0).getSize()); } } diff --git a/src/UGrid/Mesh1D.cpp b/libs/UGrid/src/Mesh1D.cpp similarity index 98% rename from src/UGrid/Mesh1D.cpp rename to libs/UGrid/src/Mesh1D.cpp index ae201bf..e7cfa2d 100644 --- a/src/UGrid/Mesh1D.cpp +++ b/libs/UGrid/src/Mesh1D.cpp @@ -28,7 +28,6 @@ #include #include #include -#include using ugrid::Mesh1D; @@ -212,11 +211,11 @@ void Mesh1D::inquire(ugridapi::Mesh1D& mesh1d) const { if (m_dimensions.find(UGridFileDimensions::node) != m_dimensions.end()) { - mesh1d.num_nodes = m_dimensions.at(UGridFileDimensions::node).getSize(); + mesh1d.num_nodes = static_cast(m_dimensions.at(UGridFileDimensions::node).getSize()); } if (m_dimensions.find(UGridFileDimensions::edge) != m_dimensions.end()) { - mesh1d.num_edges = m_dimensions.at(UGridFileDimensions::edge).getSize(); + mesh1d.num_edges = static_cast(m_dimensions.at(UGridFileDimensions::edge).getSize()); } } diff --git a/src/UGrid/Mesh2D.cpp b/libs/UGrid/src/Mesh2D.cpp similarity index 97% rename from src/UGrid/Mesh2D.cpp rename to libs/UGrid/src/Mesh2D.cpp index 54145ce..2820ec8 100644 --- a/src/UGrid/Mesh2D.cpp +++ b/libs/UGrid/src/Mesh2D.cpp @@ -261,19 +261,19 @@ void Mesh2D::inquire(ugridapi::Mesh2D& mesh2d) const { if (m_dimensions.find(UGridFileDimensions::node) != m_dimensions.end()) { - mesh2d.num_nodes = m_dimensions.at(UGridFileDimensions::node).getSize(); + mesh2d.num_nodes = static_cast(m_dimensions.at(UGridFileDimensions::node).getSize()); } if (m_dimensions.find(UGridFileDimensions::edge) != m_dimensions.end()) { - mesh2d.num_edges = m_dimensions.at(UGridFileDimensions::edge).getSize(); + mesh2d.num_edges = static_cast(m_dimensions.at(UGridFileDimensions::edge).getSize()); } if (m_dimensions.find(UGridFileDimensions::face) != m_dimensions.end()) { - mesh2d.num_faces = m_dimensions.at(UGridFileDimensions::face).getSize(); + mesh2d.num_faces = static_cast(m_dimensions.at(UGridFileDimensions::face).getSize()); } if (m_dimensions.find(UGridFileDimensions::max_face_node) != m_dimensions.end()) { - mesh2d.num_face_nodes_max = m_dimensions.at(UGridFileDimensions::max_face_node).getSize(); + mesh2d.num_face_nodes_max = static_cast(m_dimensions.at(UGridFileDimensions::max_face_node).getSize()); } } diff --git a/src/UGrid/Network1D.cpp b/libs/UGrid/src/Network1D.cpp similarity index 98% rename from src/UGrid/Network1D.cpp rename to libs/UGrid/src/Network1D.cpp index b7b0068..f7eabff 100644 --- a/src/UGrid/Network1D.cpp +++ b/libs/UGrid/src/Network1D.cpp @@ -311,16 +311,16 @@ void Network1D::inquire(ugridapi::Network1D& network1d) const { if (m_dimensions.find(UGridFileDimensions::node) != m_dimensions.end()) { - network1d.num_nodes = m_dimensions.at(UGridFileDimensions::node).getSize(); + network1d.num_nodes = static_cast(m_dimensions.at(UGridFileDimensions::node).getSize()); } if (m_dimensions.find(UGridFileDimensions::edge) != m_dimensions.end()) { - network1d.num_edges = m_dimensions.at(UGridFileDimensions::edge).getSize(); + network1d.num_edges = static_cast(m_dimensions.at(UGridFileDimensions::edge).getSize()); } // get network dimensions if (auto const it = m_network_geometry_attribute_variables.find("node_coordinates"); it != m_network_geometry_attribute_variables.end()) { - network1d.num_geometry_nodes = it->second.at(0).getDim(0).getSize(); + network1d.num_geometry_nodes = static_cast(it->second.at(0).getDim(0).getSize()); } } diff --git a/src/UGrid/UGridEntity.cpp b/libs/UGrid/src/UGridEntity.cpp similarity index 100% rename from src/UGrid/UGridEntity.cpp rename to libs/UGrid/src/UGridEntity.cpp diff --git a/libs/UGridAPI/CMakeLists.txt b/libs/UGridAPI/CMakeLists.txt new file mode 100644 index 0000000..0d0b542 --- /dev/null +++ b/libs/UGridAPI/CMakeLists.txt @@ -0,0 +1,97 @@ +project( + UGridAPI + VERSION ${CMAKE_PROJECT_VERSION} + DESCRIPTION "UGridAPI shared library" + LANGUAGES CXX C +) + +# target name +set(TARGET_NAME ${PROJECT_NAME}) + +# shared library +add_library(${TARGET_NAME} SHARED ${CMAKE_BINARY_DIR}/version.rc) + +# source directory +set(SRC_DIR ${PROJECT_SOURCE_DIR}/src) + +# include directory +set(INC_DIR ${PROJECT_SOURCE_DIR}/include) +set(DOMAIN_INC_DIR ${INC_DIR}/UGridAPI) +set(VERSION_INC_DIR ${CMAKE_SOURCE_DIR}/package) + +# list of target sources +set(SRC_LIST ${SRC_DIR}/UGrid.cpp) + +# list of target headers +set( + INC_LIST + ${DOMAIN_INC_DIR}/Contacts.hpp + ${DOMAIN_INC_DIR}/Mesh1D.hpp + ${DOMAIN_INC_DIR}/Mesh2D.hpp + ${DOMAIN_INC_DIR}/Network1D.hpp + ${DOMAIN_INC_DIR}/UGrid.hpp + ${DOMAIN_INC_DIR}/UGridState.hpp + ${VERSION_INC_DIR}/Version/Version.hpp +) + +# add sources to target +target_sources( + ${TARGET_NAME} + PRIVATE + ${SRC_LIST} + PUBLIC + FILE_SET HEADERS + BASE_DIRS + ${INC_DIR} ${VERSION_INC_DIR} + FILES + ${INC_LIST} +) + +# Expose the interface of the shared lib +target_include_directories(${TARGET_NAME} PUBLIC ${INC_DIR}) + +# link to static MeshKernel library +target_link_libraries(${TARGET_NAME} PUBLIC UGrid) + +# link required libraries +target_link_libraries( + ${TARGET_NAME} + PRIVATE + netCDF::netcdf + netCDF::netcdf-cxx4 +) + +# Make sure that coverage information is produced when using gcc +if(ENABLE_CODE_COVERAGE AND CMAKE_CXX_COMPILER_ID STREQUAL "GNU") + target_compile_options( + ${TARGET_NAME} + PRIVATE + --coverage # equivalent to -fprofile-arcs -ftest-coverage + -static-libgcc + -static-libstdc++ + ) + target_link_libraries(${TARGET_NAME} PRIVATE gcov) +endif() + +# Add precompiled header to speed up compilation +target_precompile_headers( + ${TARGET_NAME} + PRIVATE + + + + + + + + + +) + +install(TARGETS ${TARGET_NAME} FILE_SET HEADERS DESTINATION "include") + +# group the sources in IDE tree +source_group("Source Files" FILES ${SRC_LIST}) + +# group the headers in IDE tree +source_group("Header Files" FILES ${INC_LIST}) diff --git a/include/UGridApi/Contacts.hpp b/libs/UGridAPI/include/UGridAPI/Contacts.hpp similarity index 100% rename from include/UGridApi/Contacts.hpp rename to libs/UGridAPI/include/UGridAPI/Contacts.hpp diff --git a/include/UGridApi/Mesh1D.hpp b/libs/UGridAPI/include/UGridAPI/Mesh1D.hpp similarity index 100% rename from include/UGridApi/Mesh1D.hpp rename to libs/UGridAPI/include/UGridAPI/Mesh1D.hpp diff --git a/include/UGridApi/Mesh2D.hpp b/libs/UGridAPI/include/UGridAPI/Mesh2D.hpp similarity index 100% rename from include/UGridApi/Mesh2D.hpp rename to libs/UGridAPI/include/UGridAPI/Mesh2D.hpp diff --git a/include/UGridApi/Network1D.hpp b/libs/UGridAPI/include/UGridAPI/Network1D.hpp similarity index 100% rename from include/UGridApi/Network1D.hpp rename to libs/UGridAPI/include/UGridAPI/Network1D.hpp diff --git a/include/UGridApi/UGrid.hpp b/libs/UGridAPI/include/UGridAPI/UGrid.hpp similarity index 99% rename from include/UGridApi/UGrid.hpp rename to libs/UGridAPI/include/UGridAPI/UGrid.hpp index 4341374..866e71d 100644 --- a/include/UGridApi/UGrid.hpp +++ b/libs/UGridAPI/include/UGridAPI/UGrid.hpp @@ -35,10 +35,10 @@ #define UGRID_API __attribute__((visibility("default"))) #endif -#include -#include -#include -#include +#include +#include +#include +#include /// \namespace ugridapi /// @brief Contains all structs and functions exposed at the API level diff --git a/include/UGridApi/UGridState.hpp b/libs/UGridAPI/include/UGridAPI/UGridState.hpp similarity index 100% rename from include/UGridApi/UGridState.hpp rename to libs/UGridAPI/include/UGridAPI/UGridState.hpp diff --git a/src/UGridApi/UGrid.cpp b/libs/UGridAPI/src/UGrid.cpp similarity index 98% rename from src/UGridApi/UGrid.cpp rename to libs/UGridAPI/src/UGrid.cpp index 58c436e..3b9b398 100644 --- a/src/UGridApi/UGrid.cpp +++ b/libs/UGridAPI/src/UGrid.cpp @@ -43,8 +43,8 @@ #include #include #include -#include -#include +#include +#include /// \namespace ugridapi /// @brief Contains all structs and functions exposed at the API level @@ -281,7 +281,7 @@ namespace ugridapi auto const data_variables_names = topology->get_data_variables_names(location_string); // count data variables - data_variable_count = data_variables_names.size(); + data_variable_count = static_cast(data_variables_names.size()); } catch (...) { @@ -387,7 +387,7 @@ namespace ugridapi } // Get the dimensions - attributes_count = it->second.getAtts().size(); + attributes_count = static_cast(it->second.getAtts().size()); } catch (...) { @@ -493,7 +493,7 @@ namespace ugridapi } // Get the dimensions - dimensions_count = it->second.getDims().size(); + dimensions_count = static_cast(it->second.getDims().size()); } catch (...) { @@ -529,7 +529,7 @@ namespace ugridapi auto const dimensions = it->second.getDims(); for (size_t i = 0; i < dimensions.size(); ++i) { - dimension_vec[i] = dimensions[i].getSize(); + dimension_vec[i] = static_cast(dimensions[i].getSize()); } } catch (...) @@ -671,7 +671,7 @@ namespace ugridapi ugrid::Network1D network1d(ugrid_states[file_id].m_ncFile); network1d.define(network1d_api); ugrid_states[file_id].m_network1d.emplace_back(network1d); - topology_id = ugrid_states[file_id].m_network1d.size() - 1; + topology_id = static_cast(ugrid_states[file_id].m_network1d.size()) - 1; } catch (...) { @@ -745,7 +745,7 @@ namespace ugridapi ugrid::Mesh1D mesh1d(ugrid_states[file_id].m_ncFile); mesh1d.define(mesh1d_api); ugrid_states[file_id].m_mesh1d.emplace_back(mesh1d); - topology_id = ugrid_states[file_id].m_mesh1d.size() - 1; + topology_id = static_cast(ugrid_states[file_id].m_mesh1d.size()) - 1; } catch (...) { @@ -824,7 +824,7 @@ namespace ugridapi ugrid::Mesh2D mesh2d(ugrid_states[file_id].m_ncFile); mesh2d.define(mesh2d_api); ugrid_states[file_id].m_mesh2d.emplace_back(mesh2d); - topology_id = ugrid_states[file_id].m_mesh2d.size() - 1; + topology_id = static_cast(ugrid_states[file_id].m_mesh2d.size()) - 1; } catch (...) { @@ -898,7 +898,7 @@ namespace ugridapi ugrid::Contacts contacts(ugrid_states[file_id].m_ncFile); contacts.define(contacts_api); ugrid_states[file_id].m_contacts.emplace_back(contacts); - topology_id = ugrid_states[file_id].m_contacts.size() - 1; + topology_id = static_cast(ugrid_states[file_id].m_contacts.size()) - 1; } catch (...) { diff --git a/package/CMakeLists.txt b/package/CMakeLists.txt index cf08f39..3c1be66 100644 --- a/package/CMakeLists.txt +++ b/package/CMakeLists.txt @@ -1,20 +1,32 @@ -configure_file(${CMAKE_CURRENT_SOURCE_DIR}/version.rc.in - ${CMAKE_BINARY_DIR}/version.rc @ONLY) +# Determine version suffix (current build number) from environment variable +if(DEFINED ENV{VERSION_SUFFIX}) + set(VERSION_SUFFIX $ENV{VERSION_SUFFIX}) +else() + set(VERSION_SUFFIX 0) +endif() +# Configure DLL version configure_file( - ${CMAKE_CURRENT_SOURCE_DIR}/Deltares.UGrid.Native.nuspec.in - ${CMAKE_BINARY_DIR}/package/Deltares.UGrid.Native.nuspec @ONLY) + ${CMAKE_CURRENT_SOURCE_DIR}/version.rc.in + ${CMAKE_BINARY_DIR}/version.rc @ONLY +) +# Configure the nuspec files configure_file( - ${CMAKE_CURRENT_SOURCE_DIR}/Deltares.UGrid.Devel.nuspec.in - ${CMAKE_BINARY_DIR}/package/Deltares.UGrid.Devel.nuspec @ONLY) + ${CMAKE_CURRENT_SOURCE_DIR}/nuget/Deltares.UGrid.Development.nuspec.in + ${CMAKE_BINARY_DIR}/package/nuget/Deltares.UGrid.Development.nuspec @ONLY +) configure_file( - ${CMAKE_CURRENT_SOURCE_DIR}/Deltares.UGrid.Release.nuspec.in - ${CMAKE_BINARY_DIR}/package/Deltares.UGrid.Release.nuspec @ONLY) + ${CMAKE_CURRENT_SOURCE_DIR}/nuget/Deltares.UGrid.Release.nuspec.in + ${CMAKE_BINARY_DIR}/package/nuget/Deltares.UGrid.Release.nuspec @ONLY +) -configure_file(Deltares.UGrid.targets - ${CMAKE_BINARY_DIR}/package/Deltares.UGrid.targets COPYONLY) +configure_file( + ${CMAKE_CURRENT_SOURCE_DIR}/nuget/Deltares.UGrid.targets + ${CMAKE_BINARY_DIR}/package/nuget/Deltares.UGrid.targets COPYONLY +) -configure_file(Deltares.UGrid.Native.targets - ${CMAKE_BINARY_DIR}/package/Deltares.UGrid.Native.targets COPYONLY) \ No newline at end of file +# Configure the version header file +configure_file(${CMAKE_CURRENT_SOURCE_DIR}/Version/Version.hpp.in + ${CMAKE_CURRENT_SOURCE_DIR}/Version/Version.hpp @ONLY) \ No newline at end of file diff --git a/package/Deltares.UGrid.Devel.nuspec.in b/package/Deltares.UGrid.Devel.nuspec.in deleted file mode 100644 index 06c7071..0000000 --- a/package/Deltares.UGrid.Devel.nuspec.in +++ /dev/null @@ -1,15 +0,0 @@ - - - - Deltares.UGridIO - @PROJECT_VERSION_MAJOR@.@PROJECT_VERSION_MINOR@.@PROJECT_VERSION_PATCH@@VERSION_SUFFIX@ - Deltares - Deltares - Deltares back end for reading/writing UGrid meshes - Copyright 2021 - - - - - - diff --git a/package/Deltares.UGrid.Native.nuspec.in b/package/Deltares.UGrid.Native.nuspec.in deleted file mode 100644 index 244aef1..0000000 --- a/package/Deltares.UGrid.Native.nuspec.in +++ /dev/null @@ -1,17 +0,0 @@ - - - - Deltares.UGrid - @PROJECT_VERSION_MAJOR@.@PROJECT_VERSION_MINOR@.@PROJECT_VERSION_PATCH@@VERSION_SUFFIX@ - Deltares - Deltares - Deltares back end for reading/writing UGrid meshes - Copyright 2021 - native - - - - - - - diff --git a/package/Deltares.UGrid.Native.targets b/package/Deltares.UGrid.Native.targets deleted file mode 100644 index f41d782..0000000 --- a/package/Deltares.UGrid.Native.targets +++ /dev/null @@ -1,18 +0,0 @@ - - - - - <_FilesToCopyUGridLibs Include="$(MSBuildThisFileDirectory)..\..\runtimes\**\*"/> - - - - - - - - <_OriginalFilesUGrid Include="$(MSBuildThisFileDirectory)..\..\runtimes\**\*"/> - <_FilesToCleanUGrid Include="$(OutDir)\%(_OriginalFilesDimrLibs.RecursiveDir)%(_OriginalFilesDimrLibs.FileName)%(_OriginalFilesDimrLibs.Extension)"/> - - - - \ No newline at end of file diff --git a/package/Deltares.UGrid.Release.nuspec.in b/package/Deltares.UGrid.Release.nuspec.in deleted file mode 100644 index cd87a81..0000000 --- a/package/Deltares.UGrid.Release.nuspec.in +++ /dev/null @@ -1,15 +0,0 @@ - - - - Deltares.UGrid - @PROJECT_VERSION_MAJOR@.@PROJECT_VERSION_MINOR@.@PROJECT_VERSION_PATCH@.0 - Deltares - Deltares - Deltares back end for reading/writing UGrid meshes (C++ version) - Copyright 2021 - - - - - - diff --git a/package/Version/Version.hpp b/package/Version/Version.hpp new file mode 100644 index 0000000..fb3363e --- /dev/null +++ b/package/Version/Version.hpp @@ -0,0 +1,29 @@ +//---- GPL --------------------------------------------------------------------- +// +// Copyright (C) Stichting Deltares, 2011-2021. +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation version 3. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// +// contact: delft3d.support@deltares.nl +// Stichting Deltares +// P.O. Box 177 +// 2600 MH Delft, The Netherlands +// +// All indications and logos of, and references to, "Delft3D" and "Deltares" +// are registered trademarks of Stichting Deltares, and remain the property of +// Stichting Deltares. All rights reserved. +// +//------------------------------------------------------------------------------ + +// Only modify `Version.hpp.in`, never `Version.hpp` +static char versionString[64] = "0.0.0.0"; diff --git a/include/Version/Version.hpp.in b/package/Version/Version.hpp.in similarity index 95% rename from include/Version/Version.hpp.in rename to package/Version/Version.hpp.in index 46d3dba..4373558 100644 --- a/include/Version/Version.hpp.in +++ b/package/Version/Version.hpp.in @@ -26,4 +26,4 @@ //------------------------------------------------------------------------------ // Only modify `Version.hpp.in`, never `Version.hpp` -static char versionString[64] = "@PROJECT_VERSION_MAJOR@.@PROJECT_VERSION_MINOR@.@PROJECT_VERSION_PATCH@@VERSION_SUFFIX@"; +static char versionString[64] = "@PROJECT_VERSION_MAJOR@.@PROJECT_VERSION_MINOR@.@PROJECT_VERSION_PATCH@.@VERSION_SUFFIX@"; diff --git a/package/nuget/Deltares.UGrid.Development.nuspec.in b/package/nuget/Deltares.UGrid.Development.nuspec.in new file mode 100644 index 0000000..90febeb --- /dev/null +++ b/package/nuget/Deltares.UGrid.Development.nuspec.in @@ -0,0 +1,16 @@ + + + + Deltares.UGrid + @PROJECT_VERSION_MAJOR@.@PROJECT_VERSION_MINOR@.@PROJECT_VERSION_PATCH@.@VERSION_SUFFIX@-dev + Deltares + Deltares + Deltares back end for reading and writing UGrid meshes + Copyright 2024 + development + + + + + + diff --git a/package/nuget/Deltares.UGrid.Release.nuspec.in b/package/nuget/Deltares.UGrid.Release.nuspec.in new file mode 100644 index 0000000..c4ade8e --- /dev/null +++ b/package/nuget/Deltares.UGrid.Release.nuspec.in @@ -0,0 +1,16 @@ + + + + Deltares.UGrid + @PROJECT_VERSION_MAJOR@.@PROJECT_VERSION_MINOR@.@PROJECT_VERSION_PATCH@.@VERSION_SUFFIX@ + Deltares + Deltares + Deltares back end for reading and writing UGrid meshes + Copyright 2024 + signed + + + + + + diff --git a/package/Deltares.UGrid.targets b/package/nuget/Deltares.UGrid.targets similarity index 75% rename from package/Deltares.UGrid.targets rename to package/nuget/Deltares.UGrid.targets index d953cd6..b760885 100644 --- a/package/Deltares.UGrid.targets +++ b/package/nuget/Deltares.UGrid.targets @@ -2,17 +2,17 @@ - <_FilesToCopyUGridLibs Include="$(MSBuildThisFileDirectory)..\..\native\**\*"/> + <_FilesToCopyUGridLibs Include="$(MSBuildThisFileDirectory)..\..\runtimes\**\*"/> - - + + - + - <_OriginalFilesUGrid Include="$(MSBuildThisFileDirectory)..\..\native\**\*"/> - <_FilesToCleanUGrid Include="$(OutDir)\%(_OriginalFilesDimrLibs.RecursiveDir)%(_OriginalFilesDimrLibs.FileName)%(_OriginalFilesDimrLibs.Extension)"/> + <_OriginalFilesUGrid Include="$(MSBuildThisFileDirectory)..\..\runtimes\**\*"/> + <_FilesToCleanUGrid Include="$(OutDir)\%(_OriginalFilesDimrLibs.RecursiveDir)%(_OriginalFilesDimrLibs.FileName)%(_OriginalFilesDimrLibs.Extension)"/> - + - \ No newline at end of file + diff --git a/package/version.rc.in b/package/version.rc.in index 33d25fc..3bff4d8 100644 --- a/package/version.rc.in +++ b/package/version.rc.in @@ -72,7 +72,7 @@ BEGIN VALUE "FileDescription", "UGrid" VALUE "FileVersion", VER_FILEVERSION_STR VALUE "InternalName", "UGrid" - VALUE "LegalCopyright", "Copyright (c) 2020 Deltares" + VALUE "LegalCopyright", "Copyright (c) 2024 Deltares" VALUE "OriginalFilename", "UGrid.dll" VALUE "ProductName", "UGrid" VALUE "ProductVersion", VER_PRODUCTVERSION_STR diff --git a/scripts/docker/Dockerfile b/scripts/docker/Dockerfile index 6909c1c..89d8d86 100644 --- a/scripts/docker/Dockerfile +++ b/scripts/docker/Dockerfile @@ -7,8 +7,8 @@ COPY . /workspace/ RUN chmod +x /workspace/dnf_install.sh RUN /workspace/dnf_install.sh -ARG THIRD_PARTY_WORK_DIR=/app/third_party/work -ARG THIRD_PARTY_INSTALL_DIR=/app/third_party/install +ARG THIRD_PARTY_WORK_DIR=/third_party/work +ARG THIRD_PARTY_INSTALL_DIR=/third_party/install ENV THIRD_PARTY_INSTALL_DIR=${THIRD_PARTY_INSTALL_DIR} RUN chmod +x /workspace/install_netcdf_cxx4.sh @@ -17,6 +17,10 @@ RUN /workspace/install_netcdf_cxx4.sh \ --install_dir ${THIRD_PARTY_INSTALL_DIR} \ --clean -ENV CLEAN_BUILD=false +ENV CLEAN_BUILD="false" + +ENV BUILD_TYPE="Release" + +ENV VERBOSE_BUILD="false" ENTRYPOINT ["bash", "/workspace/scripts/docker/main.sh"] diff --git a/scripts/docker/dnf_install.sh b/scripts/docker/dnf_install.sh index 11625c7..19d1370 100644 --- a/scripts/docker/dnf_install.sh +++ b/scripts/docker/dnf_install.sh @@ -4,6 +4,11 @@ set -e source error.sh +dnf install -y epel-release +dnf config-manager --enable epel +dnf install -y dnf-utils +dnf config-manager --set-enabled powertools + dnf update -y dev_toolset="gcc-toolset-12" @@ -11,7 +16,7 @@ dev_toolset="gcc-toolset-12" packages=( "git" "cmake" - "boost-devel" + "boost1.78-devel.x86_64" "m4" "perl" "openssl" diff --git a/scripts/docker/main.sh b/scripts/docker/main.sh index 8429be0..9f5fadd 100644 --- a/scripts/docker/main.sh +++ b/scripts/docker/main.sh @@ -3,17 +3,46 @@ set -e source /workspace/scripts/docker/error.sh +source /workspace/scripts/docker/utilities.sh export netCDFCxx_DIR=${THIRD_PARTY_INSTALL_DIR}/netcdf_cxx4/lib64/cmake/netCDF/ build_dir="/workspace/build" -if ${CLEAN_BUILD}; then + +if [[ "${CLEAN_BUILD}" = "true" && -d ${build_dir} ]]; then + print_text_box "Clean build" + # cmake --build ${build_dir} --target clean || + # error "[cmake] Failed to clean project" rm -fr ${build_dir} fi -cmake -S . -B ${build_dir} -DCMAKE_BUILD_TYPE=Release -DCMAKE_PREFIX_PATH="${THIRD_PARTY_INSTALL_DIR}" || +# configure +print_text_box "Configure build" +cmake \ + -S . \ + -B ${build_dir} \ + -DCMAKE_BUILD_TYPE=${BUILD_TYPE} \ + -DCMAKE_PREFIX_PATH="${THIRD_PARTY_INSTALL_DIR}" || error "[cmake] Failed to configure project" -cmake --build ${build_dir} --config Release --parallel || + +verbose_switch="" +if [ "${VERBOSE_BUILD}" = "true" ]; then + verbose_switch="--verbose" +fi + +# build +print_text_box "Build" +cmake \ + --build ${build_dir} \ + --config ${BUILD_TYPE} \ + --parallel \ + ${verbose_switch} || error "[cmake] Failed to build project" -${build_dir}/bin/UGridApiTests +# run tests +print_text_box "Test" +ctest --output-on-failure --extra-verbose --test-dir ${build_dir} + +# install +print_text_box "Install" +cmake --install ${build_dir} --prefix ${build_dir}/install diff --git a/scripts/docker/utilities.sh b/scripts/docker/utilities.sh new file mode 100644 index 0000000..ae4573c --- /dev/null +++ b/scripts/docker/utilities.sh @@ -0,0 +1,50 @@ +#!/usr/bin/env bash + +function col_echo() { + local color=$1 + local text=$2 + if ! [[ ${color} =~ '^[0-9]$' ]]; then + case $(echo ${color} | tr '[:upper:]' '[:lower:]') in + --black | -k) + color=0 + ;; + --red | -r) + color=1 + ;; + --green | -g) + color=2 + ;; + --yellow | -y) + color=3 + ;; + --blue | -b) + color=4 + ;; + --magenta | -m) + color=5 + ;; + --cyan | -c) + color=6 + ;; + --white | -w) + color=7 + ;; + *) # default color + color=9 + ;; + esac + fi + tput -T xterm setaf ${color} + echo ${text} + tput -T xterm sgr0 +} + +function print_text_box() { + local string="$1" + local length=${#string} + local border="+-$(printf "%${length}s" | tr ' ' '-')-+" + + col_echo --green "$border" + col_echo --green "| $string |" + col_echo --green "$border" +} diff --git a/scripts/doxygen_ci.py b/scripts/doxygen_ci.py index 5c85536..9260aa9 100644 --- a/scripts/doxygen_ci.py +++ b/scripts/doxygen_ci.py @@ -25,8 +25,12 @@ def configure_doxyfile( doxyfile_data = file.read() doxyfile_data = doxyfile_data.replace("@DOXYGEN_INPUT_LIST@", doxygen_input_list) - doxyfile_data = doxyfile_data.replace("@DOXYGEN_OUTPUT_DIR@", str(output_dir.resolve())) - doxyfile_data = doxyfile_data.replace("@CMAKE_CURRENT_SOURCE_DIR@", str(docs_dir.resolve())) + doxyfile_data = doxyfile_data.replace( + "@DOXYGEN_OUTPUT_DIR@", str(output_dir.resolve()) + ) + doxyfile_data = doxyfile_data.replace( + "@CMAKE_CURRENT_SOURCE_DIR@", str(docs_dir.resolve()) + ) doxyfile_data = doxyfile_data.replace( "@DOXYGEN_WARN_LOG_FILE@", str(doxygen_log_path) ) @@ -51,8 +55,8 @@ def print_file(file: Path): # Set dirs root_dir = Path(__file__).parent.parent -UGrid_include_dir = root_dir / "include" / "UGrid" -UGridapi_include_dir = root_dir / "include" / "UGridApi" +UGrid_include_dir = root_dir / "libs" / "UGrid" / "include" / "UGrid" +UGridapi_include_dir = root_dir / "libs" / "UGridAPI" / "include" / "UGridAPI" output_dir = root_dir / "build" / "docs" docs_dir = root_dir / "docs" diff --git a/scripts/module_load.sh b/scripts/module_load.sh deleted file mode 100644 index 81bb36c..0000000 --- a/scripts/module_load.sh +++ /dev/null @@ -1,10 +0,0 @@ -# Script that is meant to be sourced in the CI -# It includes the necessary module loads to build MeshKernel on Deltares Linux machines - -module --verbose load gcc/12.2.0_gcc12.2.0 -module --verbose load cmake/3.26.4_gcc12.2.0 -module --verbose load boost/1.83.0_gcc12.2.0 -module --verbose load hdf5/1.10.11_gcc12.2.0 -module --verbose load netcdf/4.8.1_gcc12.2.0 -module --verbose load netcdf-cxx/4.3.2_gcc12.2.0 -module --verbose load curl/8.9.1_gcc12.2.0 diff --git a/src/UGrid/CMakeLists.txt b/src/UGrid/CMakeLists.txt deleted file mode 100644 index 6365efc..0000000 --- a/src/UGrid/CMakeLists.txt +++ /dev/null @@ -1,42 +0,0 @@ -# Set library files -file(GLOB HEADER_LIST CONFIGURE_DEPENDS "${PROJECT_SOURCE_DIR}/include/UGrid/*.hpp") -file(GLOB SOURCE_LIST CONFIGURE_DEPENDS "${PROJECT_SOURCE_DIR}/src/UGrid/*.cpp") - -# Create the static lib -set(target_name UGrid) -add_library(${target_name} STATIC ${SOURCE_LIST} ${HEADER_LIST}) - -# define the public header -set_target_properties(${target_name} PROPERTIES PUBLIC_HEADER "${HEADER_LIST}") - -# Make sure that coverage information is produced when using gcc -if(PRODUCE_CODE_COVERAGE AND CMAKE_CXX_COMPILER_ID STREQUAL "GNU") - set_target_properties(${target_name} PROPERTIES COMPILE_FLAGS "-fprofile-arcs -ftest-coverage -static-libgcc -static-libstdc++") - set_target_properties(${target_name} PROPERTIES LINK_FLAGS "-ldl -lgcov --coverage") -endif() - -# NetCDF CPP wrapper -target_include_directories(${target_name} PUBLIC "${PROJECT_SOURCE_DIR}/include" ${netCDF_INCLUDE_DIR} "${NETCDFCXX_PATH}/cxx4") - -# Add target link dependencies -target_link_directories(${target_name} PRIVATE ${netCDF_LIB_DIR}) -target_link_libraries(${target_name} PRIVATE netCDF::netcdf-cxx4 netcdf) - -# Add precompiled header -target_precompile_headers(${target_name} PRIVATE - - - - - - - - ) - -# IDEs should put the headers in a nice place -source_group( - TREE "${PROJECT_SOURCE_DIR}/include/UGrid" - PREFIX "Header Files" - FILES ${HEADER_LIST}) - -install(TARGETS ${target_name} PUBLIC_HEADER DESTINATION "include/${target_name}") \ No newline at end of file diff --git a/src/UGridApi/CMakeLists.txt b/src/UGridApi/CMakeLists.txt deleted file mode 100644 index 58e15cc..0000000 --- a/src/UGridApi/CMakeLists.txt +++ /dev/null @@ -1,48 +0,0 @@ -# Set api files -file(GLOB HEADER_LIST CONFIGURE_DEPENDS - "${PROJECT_SOURCE_DIR}/include/UGridApi/*.hpp") - -file(GLOB SOURCE_LIST CONFIGURE_DEPENDS - "${PROJECT_SOURCE_DIR}/src/UGridApi/*.cpp") - - -# Make a shared library -set(target_name UGridApi) -add_library(${target_name} SHARED ${SOURCE_LIST} ${HEADER_LIST} ${CMAKE_BINARY_DIR}/version.rc) -add_dependencies(${target_name} UGrid) - -# define the public header -set_target_properties(${target_name} PROPERTIES PUBLIC_HEADER "${HEADER_LIST}") - -# Expose the interface of the shared lib -target_include_directories(${target_name} PUBLIC "${PROJECT_SOURCE_DIR}/include" ${netCDF_INCLUDE_DIR} ) - -# Make sure that coverage information is produced when using gcc -if(PRODUCE_CODE_COVERAGE AND CMAKE_CXX_COMPILER_ID STREQUAL "GNU") - set_target_properties(${target_name} PROPERTIES COMPILE_FLAGS "-fprofile-arcs -ftest-coverage -static-libgcc -static-libstdc++") - set_target_properties(${target_name} PROPERTIES LINK_FLAGS "-ldl -lgcov --coverage") -endif() - -# Link shared lib to static lib, but don't expose it -target_link_directories(${target_name} PRIVATE ${netCDF_LIB_DIR}) -target_link_libraries(${target_name} PRIVATE UGrid netCDF::netcdf-cxx4 netcdf) - -# Add precompiled header -target_precompile_headers(${target_name} PRIVATE - - - - - - - - ) - -# IDEs should put the headers in a nice place -source_group( - TREE "${PROJECT_SOURCE_DIR}/include/UGridApi" - PREFIX "Header Files" - FILES ${HEADER_LIST}) - -# define the public header -install(TARGETS ${target_name} PUBLIC_HEADER DESTINATION "include/${target_name}") diff --git a/tests/CMakeLists.txt b/tests/CMakeLists.txt index f6fabcf..796ce19 100644 --- a/tests/CMakeLists.txt +++ b/tests/CMakeLists.txt @@ -1,19 +1,6 @@ -# Download google test -# FetchContent_Declare( -# googletest -# GIT_REPOSITORY https://github.com/google/googletest.git -# GIT_TAG v1.15.0 -# ) - -# FetchContent_GetProperties(googletest) - -# if(NOT googletest_POPULATED) -# FetchContent_Populate(googletest) -# add_subdirectory(${googletest_SOURCE_DIR} ${googletest_BINARY_DIR} EXCLUDE_FROM_ALL) -# endif() - set(TEST_FOLDER "${CMAKE_CURRENT_SOURCE_DIR}") configure_file("${CMAKE_CURRENT_SOURCE_DIR}/utils/include/TestUtils/Definitions.hpp.in" "${CMAKE_CURRENT_SOURCE_DIR}/utils/include/TestUtils/Definitions.hpp") add_subdirectory(utils) + add_subdirectory(api) diff --git a/tests/api/CMakeLists.txt b/tests/api/CMakeLists.txt index a2cb7fb..4c367cc 100644 --- a/tests/api/CMakeLists.txt +++ b/tests/api/CMakeLists.txt @@ -1,46 +1,63 @@ -# Tests need to be added as executables first -file(GLOB API_TEST_LIST CONFIGURE_DEPENDS "*.cpp") +# project name +project( + UGridAPITests + VERSION ${CMAKE_PROJECT_VERSION} + DESCRIPTION "UGridAPI tests" + LANGUAGES CXX C +) + +# target name +set(TARGET_NAME ${PROJECT_NAME}) # Make a test executable -set(target_name UGridApiTests) -add_executable(${target_name} ${API_TEST_LIST}) - -# Add a dependency to ensure the correct build order -add_dependencies(${target_name} UGridApi) - -# Add precompiled header -target_precompile_headers(${target_name} PRIVATE - - - - - - - - - ) +add_executable(${TARGET_NAME}) -# Should be linked to the main library, as well as the google test library -target_link_libraries(${target_name} PRIVATE UGridApi UtilsStatic GTest::gmock GTest::gtest_main) +# source directory +set(SRC_DIR ${CMAKE_CURRENT_SOURCE_DIR}/src) + +# include directory +set(INC_DIR ${CMAKE_CURRENT_SOURCE_DIR}/include) + +# list of target sources +set(SRC_LIST + ${SRC_DIR}/APITests.cpp +) + +set(INC_LIST) -# Make sure that coverage information is produced when using gcc -if(CMAKE_CXX_COMPILER_ID STREQUAL "GNU") - set_target_properties(${target_name} PROPERTIES COMPILE_FLAGS "-fprofile-arcs -ftest-coverage -static-libgcc -static-libstdc++") - set_target_properties(${target_name} PROPERTIES LINK_FLAGS "-ldl -lgcov --coverage") -endif() +# add sources to target +target_sources(${TARGET_NAME} PRIVATE ${SRC_LIST} ${INC_LIST}) -# Link shared lib to static lib, but don't expose it -target_link_directories(${target_name} PRIVATE ${netCDF_LIB_DIR}) -target_link_libraries(${target_name} PRIVATE UGrid netCDF::netcdf-cxx4 netcdf) +# Expose the interface of the shared lib +target_include_directories(${TARGET_NAME} PUBLIC ${INC_DIR}) + +# Should be linked to the main library, as well as the google test library +target_link_libraries( + ${TARGET_NAME} + PRIVATE + UGridAPI + TestUtils + GTest::gmock + GTest::gtest_main +) # If you register a test, then ctest and make test will run it. You can also run # examples and check the output, as well. Command can be a target. -add_test(NAME ${target_name} COMMAND UGridApiTests) +add_test( + NAME ${TARGET_NAME} + COMMAND ${TARGET_NAME} +) -# Copy the UGrid shared library to the target directory +# Copy the UGridAPI shared library to the target directory add_custom_command( - TARGET ${target_name} + TARGET ${TARGET_NAME} POST_BUILD - COMMAND ${CMAKE_COMMAND} -E copy_if_different "$" - "$" - COMMENT "Copying UGrid shared library") + COMMAND ${CMAKE_COMMAND} -E copy_if_different "$" "$" + COMMENT "Copy $ to $" +) + +# group the sources in IDE tree +source_group("Source Files" FILES ${SRC_LIST}) + +# group the headers in IDE tree +source_group("Header Files" FILES ${INC_LIST}) diff --git a/tests/api/ApiTests.cpp b/tests/api/src/APITests.cpp similarity index 98% rename from tests/api/ApiTests.cpp rename to tests/api/src/APITests.cpp index b80bd21..0998558 100644 --- a/tests/api/ApiTests.cpp +++ b/tests/api/src/APITests.cpp @@ -3,7 +3,7 @@ #include #include -#include +#include static void define_variable_attributes(int file_id, std::string const& variable_name, std::string const& attribute_name, std::vector const& attribute_values) { @@ -22,7 +22,7 @@ static void define_variable_attributes(int file_id, std::string const& variable_ variable_name_ptr.get(), attribute_name_ptr.get(), &attribute_values[0], - attribute_values.size()); + static_cast(attribute_values.size())); ASSERT_EQ(ugridapi::UGridioApiErrors::Success, error_code); } @@ -43,7 +43,7 @@ static void define_variable_attributes(int file_id, std::string const& variable_ variable_name_ptr.get(), attribute_name_ptr.get(), &attribute_values[0], - attribute_values.size()); + static_cast(attribute_values.size())); ASSERT_EQ(ugridapi::UGridioApiErrors::Success, error_code); } @@ -64,7 +64,7 @@ static void define_variable_attributes(int file_id, std::string const& variable_ variable_name_ptr.get(), attribute_name_ptr.get(), attribute_value.c_str(), - attribute_value.length()); + static_cast(attribute_value.length())); ASSERT_EQ(ugridapi::UGridioApiErrors::Success, error_code); } @@ -78,7 +78,10 @@ static void define_global_attributes(int file_id, std::string const& attribute_n std::unique_ptr const attribute_name_ptr(new char[name_long_length]); string_to_char_array(attribute_name, name_long_length, attribute_name_ptr.get()); - error_code = ugridapi::ug_attribute_global_char_define(file_id, attribute_name_ptr.get(), attribute_value.c_str(), attribute_value.length()); + error_code = ugridapi::ug_attribute_global_char_define(file_id, + attribute_name_ptr.get(), + attribute_value.c_str(), + static_cast(attribute_value.length())); ASSERT_EQ(ugridapi::UGridioApiErrors::Success, error_code); } diff --git a/tests/utils/CMakeLists.txt b/tests/utils/CMakeLists.txt index 107b166..2555966 100644 --- a/tests/utils/CMakeLists.txt +++ b/tests/utils/CMakeLists.txt @@ -1,15 +1,56 @@ -# Note that headers are optional, and do not affect add_library, but they will -# not show up in IDEs unless they are listed in add_library. -file(GLOB UTILS_HEADER_LIST CONFIGURE_DEPENDS - "${CMAKE_CURRENT_SOURCE_DIR}/include/TestUtils/*.hpp") -file(GLOB UTILS_SOURCE_LIST CONFIGURE_DEPENDS - "${CMAKE_CURRENT_SOURCE_DIR}/src/*.cpp") +# project name +project( + TestUtils + VERSION ${CMAKE_PROJECT_VERSION} + DESCRIPTION "Test utilities" + LANGUAGES CXX +) -# Create the utils library -add_library(UtilsStatic STATIC ${UTILS_HEADER_LIST} ${UTILS_SOURCE_LIST}) +# target name +set(TARGET_NAME ${PROJECT_NAME}) -# Should be linked to the main (static) library -target_link_libraries(UtilsStatic PRIVATE UGrid) +# static library +add_library(${TARGET_NAME} STATIC) -# Expose the interface of the utils library -target_include_directories(UtilsStatic PUBLIC include) +# source directory +set(SRC_DIR ${CMAKE_CURRENT_SOURCE_DIR}/src) + +# include directory +set(INC_DIR ${CMAKE_CURRENT_SOURCE_DIR}/include) +set(DOMAIN_INC_DIR ${INC_DIR}/TestUtils) + +# list of target sources +set(SRC_LIST + ${SRC_DIR}/Utils.cpp +) + +set(INC_LIST + ${DOMAIN_INC_DIR}/Utils.hpp + ${DOMAIN_INC_DIR}/Definitions.hpp +) + +# add sources to target +# add sources to target +target_sources( + ${TARGET_NAME} + PRIVATE + ${SRC_LIST} + PUBLIC + FILE_SET HEADERS + BASE_DIRS + ${INC_DIR} + FILES + ${INC_LIST} +) + +# Expose the interface of the shared lib +target_include_directories(${TARGET_NAME} PUBLIC ${INC_DIR}) + +# Should be linked to the main library, as well as the google test library +target_link_libraries(${TARGET_NAME} PRIVATE UGrid) + +# group the sources in IDE tree +source_group("Source Files" FILES ${SRC_LIST}) + +# group the headers in IDE tree +source_group("Header Files" FILES ${INC_LIST}) diff --git a/tests/utils/include/TestUtils/Utils.hpp b/tests/utils/include/TestUtils/Utils.hpp index e1ca8cc..1c7fc3e 100644 --- a/tests/utils/include/TestUtils/Utils.hpp +++ b/tests/utils/include/TestUtils/Utils.hpp @@ -26,7 +26,6 @@ //------------------------------------------------------------------------------ #pragma once -#include /// @brief Performs right trim of single string /// @param str [in] The input string