From e3ebc253faaf6acd0f0678451d9ca361c9c8b53a Mon Sep 17 00:00:00 2001 From: Jingchen Date: Mon, 12 May 2025 15:54:01 +0100 Subject: [PATCH] fix: Ensure that coverage file generation is atomic. (#5426) Running unit tests in parallel and multiple threads can write into one file can corrupt output files, and then gcovr won't be able to parse the corrupted file. This change adds -fprofile-update=atomic as instructed by https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68080. --- .github/workflows/nix.yml | 2 +- cmake/CodeCoverage.cmake | 17 ++++++++++++++++- 2 files changed, 17 insertions(+), 2 deletions(-) diff --git a/.github/workflows/nix.yml b/.github/workflows/nix.yml index 8a8ba94e2d..de59e07761 100644 --- a/.github/workflows/nix.yml +++ b/.github/workflows/nix.yml @@ -247,7 +247,7 @@ jobs: mkdir -p ~/.conan tar -xzf conan.tar -C ~/.conan - name: install gcovr - run: pip install "gcovr>=7,<8" + run: pip install "gcovr>=7,<9" - name: check environment run: | echo ${PATH} | tr ':' '\n' diff --git a/cmake/CodeCoverage.cmake b/cmake/CodeCoverage.cmake index 323303c92d..ce1733988b 100644 --- a/cmake/CodeCoverage.cmake +++ b/cmake/CodeCoverage.cmake @@ -98,6 +98,9 @@ # 2024-04-03, Bronek Kozicki # - add support for output formats: jacoco, clover, lcov # +# 2025-05-12, Jingchen Wu +# - add -fprofile-update=atomic to ensure atomic profile generation +# # USAGE: # # 1. Copy this file into your cmake modules path. @@ -200,15 +203,27 @@ set(COVERAGE_COMPILER_FLAGS "-g --coverage" CACHE INTERNAL "") if(CMAKE_CXX_COMPILER_ID MATCHES "(GNU|Clang)") include(CheckCXXCompilerFlag) + include(CheckCCompilerFlag) + check_cxx_compiler_flag(-fprofile-abs-path HAVE_cxx_fprofile_abs_path) if(HAVE_cxx_fprofile_abs_path) set(COVERAGE_CXX_COMPILER_FLAGS "${COVERAGE_COMPILER_FLAGS} -fprofile-abs-path") endif() - include(CheckCCompilerFlag) + check_c_compiler_flag(-fprofile-abs-path HAVE_c_fprofile_abs_path) if(HAVE_c_fprofile_abs_path) set(COVERAGE_C_COMPILER_FLAGS "${COVERAGE_COMPILER_FLAGS} -fprofile-abs-path") endif() + + check_cxx_compiler_flag(-fprofile-update HAVE_cxx_fprofile_update) + if(HAVE_cxx_fprofile_update) + set(COVERAGE_CXX_COMPILER_FLAGS "${COVERAGE_COMPILER_FLAGS} -fprofile-update=atomic") + endif() + + check_c_compiler_flag(-fprofile-update HAVE_c_fprofile_update) + if(HAVE_c_fprofile_update) + set(COVERAGE_C_COMPILER_FLAGS "${COVERAGE_COMPILER_FLAGS} -fprofile-update=atomic") + endif() endif() set(CMAKE_Fortran_FLAGS_COVERAGE