https://gcc.gnu.org/bugzilla/show_bug.cgi?id=107537

            Bug ID: 107537
           Summary: gcov skips throw/fallthrough annotations for 'never
                    executed' branches
           Product: gcc
           Version: unknown
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: gcov-profile
          Assignee: unassigned at gcc dot gnu.org
          Reporter: grregd at gmail dot com
                CC: marxin at gcc dot gnu.org
  Target Milestone: ---

$ gcc -v

Using built-in specs.
COLLECT_GCC=gcc
COLLECT_LTO_WRAPPER=/usr/lib/gcc/x86_64-linux-gnu/11/lto-wrapper
OFFLOAD_TARGET_NAMES=nvptx-none:amdgcn-amdhsa
OFFLOAD_TARGET_DEFAULT=1
Target: x86_64-linux-gnu
Configured with: ../src/configure -v --with-pkgversion='Ubuntu
11.3.0-1ubuntu1~22.04' --with-bugurl=file:///usr/share/doc/gcc-11/README.Bugs
--enable-languages=c,ada,c++,go,brig,d,fortran,objc,obj-c++,m2 --prefix=/usr
--with-gcc-major-version-only --program-suffix=-11
--program-prefix=x86_64-linux-gnu- --enable-shared --enable-linker-build-id
--libexecdir=/usr/lib --without-included-gettext --enable-threads=posix
--libdir=/usr/lib --enable-nls --enable-bootstrap --enable-clocale=gnu
--enable-libstdcxx-debug --enable-libstdcxx-time=yes
--with-default-libstdcxx-abi=new --enable-gnu-unique-object
--disable-vtable-verify --enable-plugin --enable-default-pie --with-system-zlib
--enable-libphobos-checking=release --with-target-system-zlib=auto
--enable-objc-gc=auto --enable-multiarch --disable-werror --enable-cet
--with-arch-32=i686 --with-abi=m64 --with-multilib-list=m32,m64,mx32
--enable-multilib --with-tune=generic
--enable-offload-targets=nvptx-none=/build/gcc-11-xKiWfi/gcc-11-11.3.0/debian/tmp-nvptx/usr,amdgcn-amdhsa=/build/gcc-11-xKiWfi/gcc-11-11.3.0/debian/tmp-gcn/usr
--without-cuda-driver --enable-checking=release --build=x86_64-linux-gnu
--host=x86_64-linux-gnu --target=x86_64-linux-gnu
--with-build-config=bootstrap-lto-lean --enable-link-serialization=2
Thread model: posix
Supported LTO compression algorithms: zlib zstd
gcc version 11.3.0 (Ubuntu 11.3.0-1ubuntu1~22.04) 

$ gcov -v
gcov (Ubuntu 11.3.0-1ubuntu1~22.04) 11.3.0

$ cat prog.cpp
#include <iostream>
void foo1()
{
    try { 
        std::cout << "here\n";
    }
    catch (...) {}
}
void foo2()
{
    try {
        std::cout << "there\n";
    }
    catch (...) {}
}
int main()
{
    foo1();
}


$ g++ --coverage prog.cpp -o prog && ./prog && gcov -b -o . prog && cat
prog.cpp.gcov
here
File 'prog.cpp'
Lines executed:54.55% of 11
Branches executed:50.00% of 4
Taken at least once:25.00% of 4
Calls executed:40.00% of 5
Creating 'prog.cpp.gcov'

File '/usr/include/c++/11/iostream'
No executable lines
No branches
No calls

Removing 'iostream.gcov'

Lines executed:54.55% of 11
        -:    0:Source:prog.cpp
        -:    0:Graph:./prog.gcno
        -:    0:Data:./prog.gcda
        -:    0:Runs:1
        -:    1:#include <iostream>
        -:    2:
function _Z4foo1v called 1 returned 100% blocks executed 60%
        1:    3:void foo1()
        -:    4:{
        -:    5:    try { 
        1:    6:        std::cout << "here\n";
call    0 returned 100%
branch  1 taken 100% (fallthrough)
branch  2 taken 0% (throw)
        -:    7:    }
    =====:    8:    catch (...) {}
call    0 never executed
        1:    9:}
        -:   10:
function _Z4foo2v called 0 returned 0% blocks executed 0%
    #####:   11:void foo2()
        -:   12:{
        -:   13:    try {
    #####:   14:        std::cout << "there\n";
call    0 never executed
branch  1 never executed
branch  2 never executed
        -:   15:    }
    =====:   16:    catch (...) {}
call    0 never executed
    #####:   17:}
        -:   18:
function main called 1 returned 100% blocks executed 100%
        1:   19:int main()
        -:   20:{
        1:   21:    foo1();
call    0 returned 100%
        1:   22:}


Both functions foo1 and foo2 are essentially the same. foo1 is called once,
foo2 is never called. foo1 contains 2 branches in line 6, both branches labeled
with annotations (fallthrough/throw). The same code in foo2 in line 14 also has
2 branches, however these are not labeled with annotations.

Accoding to the source code of gcov it always skips throw/fallthrough
annotations for 'never executed' branches
(https://github.com/gcc-mirror/gcc/blob/50bc9185c2821350f0b785d6e23a6e9dcde58466/gcc/gcov.c#L2861)

Is there any reason why gcov skips throw/fallthrough annotations for branches
which were never executed?

According to my investigation, those flags are there and after modifying gcov
to print annotations always, it produces output with annotations for those
never executed branches. But perhaps those flags are invalid in this case and
can't be used?

In some specific conditions, those annotations would be very helpful for tools
like lcov or gcovr. Problem that occurrs in gcovr is described here -
https://github.com/gcovr/gcovr/issues/677#issuecomment-1282355159

Reply via email to