diff --git a/CHANGELOG.rst b/CHANGELOG.rst index 0cea548..afcdd3c 100644 --- a/CHANGELOG.rst +++ b/CHANGELOG.rst @@ -2,6 +2,11 @@ Changelog for package code_coverage ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +0.4.5 (2021-09-29) +------------------ +* Added option to use Clang coverage tools. (`#30 `_) +* Contributors: Erki Suurjaak + 0.4.4 (2020-10-29) ------------------ * Added python3-coverage support and error if python*-coverage is missing. (`#27 `_) diff --git a/CMakeLists.txt b/CMakeLists.txt index eb2f568..7acc7cc 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -5,6 +5,10 @@ find_package(catkin REQUIRED) catkin_package(CFG_EXTRAS code_coverage-extras.cmake) +## Install Clang coverage tool wrapper +install(PROGRAMS scripts/llvm-gcov.sh + DESTINATION ${CATKIN_PACKAGE_BIN_DESTINATION}/scripts) + ## Install all cmake files install(DIRECTORY cmake/Modules DESTINATION ${CATKIN_PACKAGE_SHARE_DESTINATION}/cmake) diff --git a/README.md b/README.md index 5b212ec..7e4df67 100644 --- a/README.md +++ b/README.md @@ -34,6 +34,13 @@ To use this with your ROS package: endif() ``` + If you want to use Clang coverage tools: + + ``` + APPEND_COVERAGE_COMPILER_FLAGS(COMPILER clang) + ``` + + * Now you can build and run the tests (you need a debug build to get reasonable coverage numbers): - if using CATKIN_MAKE: diff --git a/cmake/Modules/CodeCoverage.cmake b/cmake/Modules/CodeCoverage.cmake index fb664b0..de30ffc 100644 --- a/cmake/Modules/CodeCoverage.cmake +++ b/cmake/Modules/CodeCoverage.cmake @@ -48,6 +48,9 @@ # 2020-10-28, Stefan Fabian # - Added python3-coverage support # +# 2021-09-29, Erki Suurjaak +# - Added option to use Clang coverage tools +# include(CMakeParseArguments) @@ -104,6 +107,9 @@ mark_as_advanced( CMAKE_EXE_LINKER_FLAGS_COVERAGE CMAKE_SHARED_LINKER_FLAGS_COVERAGE ) +set(GCOV_TOOL "${CMAKE_CURRENT_LIST_DIR}/../../../../lib/code_coverage/llvm-gcov.sh") +set(GCOV_TOOL_OVERRIDE OFF) + if(NOT CMAKE_BUILD_TYPE STREQUAL "Debug") message(WARNING "Code coverage results with an optimised (non-Debug) build may be misleading") endif() # NOT CMAKE_BUILD_TYPE STREQUAL "Debug" @@ -145,11 +151,15 @@ function(ADD_CODE_COVERAGE) endif() # Cleanup C++ counters + set(LCOV_BASELINE_OPTIONS_LIST -c -i -d . -o ${PROJECT_BINARY_DIR}/${Coverage_NAME}.base) + if(GCOV_TOOL_OVERRIDE) + list(APPEND LCOV_BASELINE_OPTIONS_LIST --gcov-tool ${GCOV_TOOL}) + endif() add_custom_target(${Coverage_NAME}_cleanup_cpp # Cleanup lcov COMMAND ${LCOV_PATH} --directory . --zerocounters # Create baseline to make sure untouched files show up in the report - COMMAND ${LCOV_PATH} -c -i -d . -o ${PROJECT_BINARY_DIR}/${Coverage_NAME}.base + COMMAND ${LCOV_PATH} ${LCOV_BASELINE_OPTIONS_LIST} WORKING_DIRECTORY ${PROJECT_BINARY_DIR} DEPENDS ${Coverage_DEPENDENCIES} COMMENT "Resetting CPP code coverage counters to zero." @@ -167,10 +177,14 @@ function(ADD_CODE_COVERAGE) add_dependencies(_run_tests_${PROJECT_NAME} ${Coverage_NAME}_cleanup_py) # Create C++ coverage report + set(LCOV_CAPTURE_OPTIONS_LIST --directory . --capture --output-file ${PROJECT_BINARY_DIR}/${Coverage_NAME}.info) + if(GCOV_TOOL_OVERRIDE) + list(APPEND LCOV_CAPTURE_OPTIONS_LIST --gcov-tool ${GCOV_TOOL}) + endif() add_custom_target(${Coverage_NAME}_cpp COMMAND export PYTHONIOENCODING=UTF-8 # Capturing lcov counters and generating report - COMMAND ${LCOV_PATH} --directory . --capture --output-file ${PROJECT_BINARY_DIR}/${Coverage_NAME}.info + COMMAND ${LCOV_PATH} ${LCOV_CAPTURE_OPTIONS_LIST} # add baseline counters COMMAND ${LCOV_PATH} -a ${PROJECT_BINARY_DIR}/${Coverage_NAME}.base -a ${PROJECT_BINARY_DIR}/${Coverage_NAME}.info --output-file ${PROJECT_BINARY_DIR}/${Coverage_NAME}.total || (exit 0) COMMAND ${LCOV_PATH} --remove ${PROJECT_BINARY_DIR}/${Coverage_NAME}.total ${COVERAGE_EXCLUDES} --output-file ${PROJECT_BINARY_DIR}/${Coverage_NAME}.info.removed || (exit 0) @@ -221,12 +235,29 @@ function(ADD_CODE_COVERAGE) endfunction() # SETUP_TARGET_FOR_COVERAGE +# Adds compiler flags for coverage instrumentation. +# +# Takes one optional named argument, COMPILER: +# +# APPEND_COVERAGE_COMPILER_FLAGS() # Use GCC coverage tools +# APPEND_COVERAGE_COMPILER_FLAGS(COMPILER clang) # Use Clang coverage tools function(APPEND_COVERAGE_COMPILER_FLAGS) # Set flags for all C++ builds set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${COVERAGE_COMPILER_FLAGS}" PARENT_SCOPE) set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${COVERAGE_COMPILER_FLAGS}" PARENT_SCOPE) # Turn on coverage in python nosetests (see README for requirements on rostests) set(ENV{CATKIN_TEST_COVERAGE} "1") + + # Set flag for using Clang tools if COMPILER is "clang" + set(oneValueArgs COMPILER) + cmake_parse_arguments(Flags "" "${oneValueArgs}" "" ${ARGN}) + if(DEFINED Flags_COMPILER) + string(TOLOWER "${Flags_COMPILER}" COMPILER) + if(COMPILER STREQUAL "clang") + set(GCOV_TOOL_OVERRIDE ON PARENT_SCOPE) + endif() + endif() + message(STATUS "Appending code coverage compiler flags: ${COVERAGE_COMPILER_FLAGS}") endfunction() # APPEND_COVERAGE_COMPILER_FLAGS diff --git a/package.xml b/package.xml index 40bdce7..c9f87fa 100644 --- a/package.xml +++ b/package.xml @@ -1,7 +1,7 @@ code_coverage - 0.4.4 + 0.4.5 CMake configuration to run coverage Michael Ferguson Michael Ferguson diff --git a/scripts/llvm-gcov.sh b/scripts/llvm-gcov.sh new file mode 100755 index 0000000..4e320d8 --- /dev/null +++ b/scripts/llvm-gcov.sh @@ -0,0 +1,2 @@ +#!/bin/bash +exec llvm-cov gcov "$@"