Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 10/13/2016 04:31 PM, Rainer Orth wrote: > Hi Martin, > >> Good! How does it look with the former solaris targets that does not support >> prioritized ctors? > > still no failures there, neither with ld (which lacks constructor > priority support) nor with gld (which has it). Only Solaris 12 shows > the failures, both with ld and gld (both of which support constructor > priorities). > > Rainer > I see. So please send me some example of a binary that still fails on Solaris 12. Thanks, Martin
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
Hi Martin, > Good! How does it look with the former solaris targets that does not support > prioritized ctors? still no failures there, neither with ld (which lacks constructor priority support) nor with gld (which has it). Only Solaris 12 shows the failures, both with ld and gld (both of which support constructor priorities). Rainer -- - Rainer Orth, Center for Biotechnology, Bielefeld University
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 10/13/2016 04:04 PM, Rainer Orth wrote: > no, it's from r240990 unlike I'm completely mistaken. However, current > trunk bootstraps are running as we speak. > > Rainer Good! How does it look with the former solaris targets that does not support prioritized ctors? Thanks, Martin
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
Hi Martin, > Just running my previous example (priotity.c), I can see with -S: > > _GLOBAL__sub_D_00099_1_foo: > jmp __gcov_exit > .size _GLOBAL__sub_D_00099_1_foo, .-_GLOBAL__sub_D_00099_1_foo > .section.fini_array.00099,"aw" > .align 4 > .long _GLOBAL__sub_D_00099_1_foo > .data > .align 4 > .type .LPBX1, @object > .size .LPBX1, 12 > > Which looks good. I guess the sent snippet is before r240857, where I fixed > the > priority to 99. Can you please test it with current trunk? no, it's from r240990 unlike I'm completely mistaken. However, current trunk bootstraps are running as we speak. Rainer -- - Rainer Orth, Center for Biotechnology, Bielefeld University
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 10/13/2016 03:46 PM, Rainer Orth wrote: > Hi Martin, > > sorry for the long delay: I've been extremely busy the last two weeks. Hello Never mind, still plenty of time before we'll release 7.1.0 :) > >> On 09/30/2016 02:31 PM, Rainer Orth wrote: >>> this would be i386-pc-solaris2.12. I'm not sure if the constructor >>> priority detection works in a cross scenario. >> >> Hi. >> >> By the way, I tried to test the cross-compiler: >> $ ../configure --disable-bootstrap --enable-languages=c,c++,fortran >> --enable-valgrind-annotations --prefix=/home/marxin/bin/gcc2 >> --disable-multilib --disable-libsanitizer --target=i386-pc-solaris2.12 >> >> and I get for: >> cat /tmp/priority.c >> void __attribute__ ((constructor(150))) foo() >> { >> } >> >> void __attribute__ ((constructor(151))) bar() >> { >> } >> >> int main() >> { >> return 0; >> } >> >> $ ./xgcc -B. /tmp/priority.c -fprofile-generate -S >> /tmp/priority.c:2:1: error: constructor priorities are not supported >> { >> ^ >> /tmp/priority.c:6:1: error: constructor priorities are not supported >> { >> ^ >> >> I guess even cross compiler should detect whether the target supports >> ctor/dtor priorities. > > maybe it could, but right now acinclude.m4 (gcc_AC_INITFINI_ARRAY) has > this for crosses: > > AC_MSG_CHECKING(cross compile... guessing) > gcc_cv_initfini_array=no > > You could work around this by overriding configure with > --enable-initfini-array. Good, I've just done that. > >> May I ask you for assembly file of a native compiler with the suggested >> patch? > > Sure: this time from an i386-pc-solaris2.12 compiler configured to use > gas and ld. > > Rainer > Just running my previous example (priotity.c), I can see with -S: _GLOBAL__sub_D_00099_1_foo: jmp __gcov_exit .size _GLOBAL__sub_D_00099_1_foo, .-_GLOBAL__sub_D_00099_1_foo .section.fini_array.00099,"aw" .align 4 .long _GLOBAL__sub_D_00099_1_foo .data .align 4 .type .LPBX1, @object .size .LPBX1, 12 Which looks good. I guess the sent snippet is before r240857, where I fixed the priority to 99. Can you please test it with current trunk? Thanks, Martin
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
Hi Martin, sorry for the long delay: I've been extremely busy the last two weeks. > On 09/30/2016 02:31 PM, Rainer Orth wrote: >> this would be i386-pc-solaris2.12. I'm not sure if the constructor >> priority detection works in a cross scenario. > > Hi. > > By the way, I tried to test the cross-compiler: > $ ../configure --disable-bootstrap --enable-languages=c,c++,fortran > --enable-valgrind-annotations --prefix=/home/marxin/bin/gcc2 > --disable-multilib --disable-libsanitizer --target=i386-pc-solaris2.12 > > and I get for: > cat /tmp/priority.c > void __attribute__ ((constructor(150))) foo() > { > } > > void __attribute__ ((constructor(151))) bar() > { > } > > int main() > { > return 0; > } > > $ ./xgcc -B. /tmp/priority.c -fprofile-generate -S > /tmp/priority.c:2:1: error: constructor priorities are not supported > { > ^ > /tmp/priority.c:6:1: error: constructor priorities are not supported > { > ^ > > I guess even cross compiler should detect whether the target supports > ctor/dtor priorities. maybe it could, but right now acinclude.m4 (gcc_AC_INITFINI_ARRAY) has this for crosses: AC_MSG_CHECKING(cross compile... guessing) gcc_cv_initfini_array=no You could work around this by overriding configure with --enable-initfini-array. > May I ask you for assembly file of a native compiler with the suggested patch? Sure: this time from an i386-pc-solaris2.12 compiler configured to use gas and ld. Rainer -- - Rainer Orth, Center for Biotechnology, Bielefeld University .file "pr16855.C" .globl a .bss .align 4 .type a, @object .size a, 4 a: .zero 4 .text .globl _Z3foov .type _Z3foov, @function _Z3foov: .LFB55: .cfi_startproc pushl %ebp .cfi_def_cfa_offset 8 .cfi_offset 5, -8 movl%esp, %ebp .cfi_def_cfa_register 5 movl__gcov0._Z3foov, %eax movl__gcov0._Z3foov+4, %edx addl$1, %eax adcl$0, %edx movl%eax, __gcov0._Z3foov movl%edx, __gcov0._Z3foov+4 movl$123, a nop popl%ebp .cfi_restore 5 .cfi_def_cfa 4, 4 ret .cfi_endproc .LFE55: .size _Z3foov, .-_Z3foov .data .align 4 .type _ZL16__gthread_active, @object .size _ZL16__gthread_active, 4 _ZL16__gthread_active: .long -1 .text .type _ZL17__gthread_triggerv, @function _ZL17__gthread_triggerv: .LFB336: .cfi_startproc pushl %ebp .cfi_def_cfa_offset 8 .cfi_offset 5, -8 movl%esp, %ebp .cfi_def_cfa_register 5 movl__gcov0._ZL17__gthread_triggerv, %eax movl__gcov0._ZL17__gthread_triggerv+4, %edx addl$1, %eax adcl$0, %edx movl%eax, __gcov0._ZL17__gthread_triggerv movl%edx, __gcov0._ZL17__gthread_triggerv+4 movl$1, _ZL16__gthread_active nop popl%ebp .cfi_restore 5 .cfi_def_cfa 4, 4 ret .cfi_endproc .LFE336: .size _ZL17__gthread_triggerv, .-_ZL17__gthread_triggerv .local _ZStL8__ioinit .comm _ZStL8__ioinit,1,1 .section.rodata .LC0: .string "In Test ctor" .section.text._ZN4TestC2Ev,"axG",@progbits,_ZN4TestC5Ev,comdat .align 2 .weak _ZN4TestC2Ev .type _ZN4TestC2Ev, @function _ZN4TestC2Ev: .LFB1086: .cfi_startproc pushl %ebp .cfi_def_cfa_offset 8 .cfi_offset 5, -8 movl%esp, %ebp .cfi_def_cfa_register 5 subl$8, %esp movl__gcov0._ZN4TestC2Ev, %eax movl__gcov0._ZN4TestC2Ev+4, %edx addl$1, %eax adcl$0, %edx movl%eax, __gcov0._ZN4TestC2Ev movl%edx, __gcov0._ZN4TestC2Ev+4 subl$8, %esp pushl $.LC0 pushl $_ZSt4cout call_ZStlsISt11char_traitsIcEERSt13basic_ostreamIcT_ES5_PKc addl$16, %esp movl%eax, %ecx movl__gcov0._ZN4TestC2Ev+8, %eax movl__gcov0._ZN4TestC2Ev+12, %edx addl$1, %eax adcl$0, %edx movl%eax, __gcov0._ZN4TestC2Ev+8 movl%edx, __gcov0._ZN4TestC2Ev+12 subl$8, %esp pushl $_ZSt4endlIcSt11char_traitsIcEERSt13basic_ostreamIT_T0_ES6_ pushl %ecx call_ZNSolsEPFRSoS_E addl$16, %esp movl__gcov0._ZN4TestC2Ev+16, %eax movl__gcov0._ZN4TestC2Ev+20, %edx addl$1, %eax adcl$0, %edx movl%eax, __gcov0._ZN4TestC2Ev+16 movl%edx, __gcov0._ZN4TestC2Ev+20 nop leave .cfi_restore 5 .cfi_def_cfa 4, 4 ret .cfi_endproc
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 09/30/2016 02:31 PM, Rainer Orth wrote: this would be i386-pc-solaris2.12. I'm not sure if the constructor priority detection works in a cross scenario. Hi. By the way, I tried to test the cross-compiler: $ ../configure --disable-bootstrap --enable-languages=c,c++,fortran --enable-valgrind-annotations --prefix=/home/marxin/bin/gcc2 --disable-multilib --disable-libsanitizer --target=i386-pc-solaris2.12 and I get for: cat /tmp/priority.c void __attribute__ ((constructor(150))) foo() { } void __attribute__ ((constructor(151))) bar() { } int main() { return 0; } $ ./xgcc -B. /tmp/priority.c -fprofile-generate -S /tmp/priority.c:2:1: error: constructor priorities are not supported { ^ /tmp/priority.c:6:1: error: constructor priorities are not supported { ^ I guess even cross compiler should detect whether the target supports ctor/dtor priorities. May I ask you for assembly file of a native compiler with the suggested patch? Thanks, Martin
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 10/03/2016 03:03 PM, Rainer Orth wrote: > Hi Martin, > >> On 09/30/2016 02:31 PM, Rainer Orth wrote: >>> this would be i386-pc-solaris2.12. I'm not sure if the constructor >>> priority detection works in a cross scenario. >>> >>> I'm attaching the resulting assembly (although for Solaris as, the gas >>> build is still running). >> >> Hi. Sorry, I have a stupid mistake in dtor priority >> (I used 65534 instead of desired 99). Please try to test it on Solaris 12 >> with the attached patch. I'll send the patch to ML soon. > > unfortunately, the patch makes no difference on Solaris 12. The test > even FAILs when using gas/gld, which is a different/independent > implementation of constructor priority. Ok, can you please send me x.S file for Solaris 12? > >> Can you please test whether it makes any change on a solaris target w/o >> prioritized ctors/dtors? > > It doesn't: the test PASSes on Solaris 10 and 11 with and without your > patch. I see, that would require the former approach using atexit, which would be chosen depending on whether target supports prioritized dtors or not. Martin > > Rainer >
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
Hi Martin, > On 09/30/2016 02:31 PM, Rainer Orth wrote: >> this would be i386-pc-solaris2.12. I'm not sure if the constructor >> priority detection works in a cross scenario. >> >> I'm attaching the resulting assembly (although for Solaris as, the gas >> build is still running). > > Hi. Sorry, I have a stupid mistake in dtor priority > (I used 65534 instead of desired 99). Please try to test it on Solaris 12 > with the attached patch. I'll send the patch to ML soon. unfortunately, the patch makes no difference on Solaris 12. The test even FAILs when using gas/gld, which is a different/independent implementation of constructor priority. > Can you please test whether it makes any change on a solaris target w/o > prioritized ctors/dtors? It doesn't: the test PASSes on Solaris 10 and 11 with and without your patch. Rainer -- - Rainer Orth, Center for Biotechnology, Bielefeld University
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
Hi Martin, > On 09/30/2016 02:31 PM, Rainer Orth wrote: >> this would be i386-pc-solaris2.12. I'm not sure if the constructor >> priority detection works in a cross scenario. >> >> I'm attaching the resulting assembly (although for Solaris as, the gas >> build is still running). > > Hi. Sorry, I have a stupid mistake in dtor priority > (I used 65534 instead of desired 99). Please try to test it on Solaris 12 > with the attached patch. I'll send the patch to ML soon. > > Can you please test whether it makes any change on a solaris target w/o > prioritized ctors/dtors? sure: I've added your patch to my source tree for the running bootstraps and will have builds on Solaris 12 (with constructor priority) and S10/11 (without) available in a few hours. Rainer -- - Rainer Orth, Center for Biotechnology, Bielefeld University
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 09/30/2016 02:31 PM, Rainer Orth wrote: > this would be i386-pc-solaris2.12. I'm not sure if the constructor > priority detection works in a cross scenario. > > I'm attaching the resulting assembly (although for Solaris as, the gas > build is still running). Hi. Sorry, I have a stupid mistake in dtor priority (I used 65534 instead of desired 99). Please try to test it on Solaris 12 with the attached patch. I'll send the patch to ML soon. Can you please test whether it makes any change on a solaris target w/o prioritized ctors/dtors? Thanks, Martin diff --git a/gcc/coverage.c b/gcc/coverage.c index 0b8c0b3..a759831 100644 --- a/gcc/coverage.c +++ b/gcc/coverage.c @@ -1078,7 +1078,7 @@ build_gcov_exit_decl (void) append_to_statement_list (stmt, ); /* Generate a destructor to run it (with priority 99). */ - cgraph_build_static_cdtor ('D', dtor, DEFAULT_INIT_PRIORITY - 1); + cgraph_build_static_cdtor ('D', dtor, MAX_RESERVED_INIT_PRIORITY - 1); } /* Create the gcov_info types and object. Generate the constructor
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
Hi Martin, >> understood. However, Solaris 12 *does* have support for constructor >> priorities and the testcase still fails, so there's more going on here. > > I see, however I don't have access to such a machine. I would appreciate > if you help me to debug what's going on. Can you please send me --target=x, > so that I can at least check created assembly? this would be i386-pc-solaris2.12. I'm not sure if the constructor priority detection works in a cross scenario. I'm attaching the resulting assembly (although for Solaris as, the gas build is still running). Here's the gcov -b pr16855.C output File '/vol/gcc/src/hg/trunk/local/gcc/testsuite/g++.dg/gcov/pr16855.C' Lines executed:73.91% of 23 Branches executed:100.00% of 4 Taken at least once:50.00% of 4 Calls executed:71.43% of 14 Creating 'pr16855.C.gcov' File '/var/gcc/regression/trunk/12-gcc/build/i386-pc-solaris2.12/amd64/libstdc++-v3/include/iostream' Lines executed:100.00% of 1 No branches Calls executed:100.00% of 2 Creating 'iostream.gcov' File '/var/gcc/regression/trunk/12-gcc/build/i386-pc-solaris2.12/amd64/libstdc++-v3/include/i386-pc-solaris2.12/bits/gthr-default.h' Lines executed:0.00% of 3 No branches No calls Creating 'gthr-default.h.gcov' compared to what I get on Linux/x86_64: File '/vol/gcc/src/hg/trunk/local/gcc/testsuite/g++.dg/gcov/pr16855.C' Lines executed:86.96% of 23 Branches executed:100.00% of 4 Taken at least once:50.00% of 4 Calls executed:85.71% of 14 Creating 'pr16855.C.gcov' File '/var/gcc/regression/trunk/4.7.4-gcc-gas-gld/build/x86_64-pc-linux-gnu/libstdc++-v3/include/iostream' Lines executed:100.00% of 1 No branches Calls executed:100.00% of 2 Creating 'iostream.gcov' Rainer -- - Rainer Orth, Center for Biotechnology, Bielefeld University .file "pr16855.C" .globl a .bss .align 4 .type a, @object .size a, 4 a: .zero 4 .text .globl _Z3foov .type _Z3foov, @function _Z3foov: .LFB5: pushq %rbp .LCFI0: movq%rsp, %rbp .LCFI1: movq__gcov0._Z3foov(%rip), %rax addq$1, %rax movq%rax, __gcov0._Z3foov(%rip) movl$123, a(%rip) nop popq%rbp .LCFI2: ret .LFE5: .size _Z3foov, .-_Z3foov .data .align 4 .type _ZL16__gthread_active, @object .size _ZL16__gthread_active, 4 _ZL16__gthread_active: .long -1 .text .type _ZL17__gthread_triggerv, @function _ZL17__gthread_triggerv: .LFB286: pushq %rbp .LCFI3: movq%rsp, %rbp .LCFI4: movq__gcov0._ZL17__gthread_triggerv(%rip), %rax addq$1, %rax movq%rax, __gcov0._ZL17__gthread_triggerv(%rip) movl$1, _ZL16__gthread_active(%rip) nop popq%rbp .LCFI5: ret .LFE286: .size _ZL17__gthread_triggerv, .-_ZL17__gthread_triggerv .local _ZStL8__ioinit .comm _ZStL8__ioinit,1,1 .section.rodata .LC0: .string "In Test ctor" .section.text._ZN4TestC2Ev%_ZN4TestC5Ev,"ax",@progbits .group _ZN4TestC5Ev,.text._ZN4TestC2Ev%_ZN4TestC5Ev,#comdat .align 2 .weak _ZN4TestC2Ev .type _ZN4TestC2Ev, @function _ZN4TestC2Ev: .LFB1036: pushq %rbp .LCFI6: movq%rsp, %rbp .LCFI7: subq$16, %rsp movq%rdi, -8(%rbp) movq__gcov0._ZN4TestC2Ev(%rip), %rax addq$1, %rax movq%rax, __gcov0._ZN4TestC2Ev(%rip) movl$.LC0, %esi movl$_ZSt4cout, %edi call_ZStlsISt11char_traitsIcEERSt13basic_ostreamIcT_ES5_PKc movq%rax, %rdx movq__gcov0._ZN4TestC2Ev+8(%rip), %rax addq$1, %rax movq%rax, __gcov0._ZN4TestC2Ev+8(%rip) movl$_ZSt4endlIcSt11char_traitsIcEERSt13basic_ostreamIT_T0_ES6_, %esi movq%rdx, %rdi call_ZNSolsEPFRSoS_E movq__gcov0._ZN4TestC2Ev+16(%rip), %rax addq$1, %rax movq%rax, __gcov0._ZN4TestC2Ev+16(%rip) nop leave .LCFI8: ret .LFE1036: .size _ZN4TestC2Ev, .-_ZN4TestC2Ev .weak _ZN4TestC1Ev .set_ZN4TestC1Ev,_ZN4TestC2Ev .section.rodata .LC1: .string "In Test dtor" .section.text._ZN4TestD2Ev%_ZN4TestD5Ev,"ax",@progbits .group _ZN4TestD5Ev,.text._ZN4TestD2Ev%_ZN4TestD5Ev,#comdat .align 2 .weak _ZN4TestD2Ev .type _ZN4TestD2Ev, @function _ZN4TestD2Ev: .LFB1039: pushq %rbp .LCFI9: movq%rsp, %rbp .LCFI10: subq$16, %rsp movq%rdi, -8(%rbp) movq__gcov0._ZN4TestD2Ev(%rip), %rax addq$1, %rax movq%rax, __gcov0._ZN4TestD2Ev(%rip) movl$.LC1, %esi
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 09/30/16 05:22, Rainer Orth wrote: While this would take care of the testsuite failures, this creates a terrible user experience outside of the testsuite: if we know that -fprofile-arcs -ftest-coverage cannot work on targets without constructor priority support, the compiler should error out with an appropriate message instead of just creating confusing non-working executables. It should either 1) emit a non-prioritized static ctor 2) or use the older atexit mechanism.
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 09/30/2016 11:22 AM, Rainer Orth wrote: > Hi Martin, > >>> the testcase FAILs on Solaris 12 (both SPARC and x86): >>> >>> +FAIL: g++.dg/gcov/pr16855.C -std=gnu++11 gcov: 1 failures in line >>> counts, 0 i >>> n branch percentages, 0 in return percentages, 0 in intermediate format >>> +FAIL: g++.dg/gcov/pr16855.C -std=gnu++11 line 21: is #:should be 1 >>> +FAIL: g++.dg/gcov/pr16855.C -std=gnu++14 gcov: 1 failures in line >>> counts, 0 i >>> n branch percentages, 0 in return percentages, 0 in intermediate format >>> +FAIL: g++.dg/gcov/pr16855.C -std=gnu++14 line 21: is #:should be 1 >>> +FAIL: g++.dg/gcov/pr16855.C -std=gnu++98 gcov: 1 failures in line >>> counts, 0 i >>> n branch percentages, 0 in return percentages, 0 in intermediate format >>> +FAIL: g++.dg/gcov/pr16855.C -std=gnu++98 line 21: is #:should be 1 >>> >>> I haven't looked closer yet, but notice that you require constructor >>> priority support which isn't available everywhere (it is on Solaris 12, >>> but not before). >>> >>> Rainer >>> >> >> Hello. >> >> Sorry for the test-breakage. The issue is really connected to fact that >> current trunk relies >> on support of dtor priority. The former implementation called the function >> __gcov_exit via atexit. >> If I understand correctly, fully support of static ctors/dtors, C++ >> ctors/dtors, with combination >> of atexit cannot be done on a target w/o ctor/dtor priorities. > > understood. However, Solaris 12 *does* have support for constructor > priorities and the testcase still fails, so there's more going on here. I see, however I don't have access to such a machine. I would appreciate if you help me to debug what's going on. Can you please send me --target=x, so that I can at least check created assembly? > >> Ideally we should have a macro for each target telling whether it supports >> priorities or not. >> However, we probably don't have? I would suggest to make the test >> conditional just for main >> targets which support priorities? >> >> Thoughts? > > While this would take care of the testsuite failures, this creates a > terrible user experience outside of the testsuite: if we know that > -fprofile-arcs -ftest-coverage cannot work on targets without > constructor priority support, the compiler should error out with an > appropriate message instead of just creating confusing non-working > executables. More precisely, it does not work reliably on constructor and destructors as we depend on an order how are ctor/dtors executed. We had the same behavior even before my patch, but documenting that definitely worth for doing. I'll do a patch. Martin > > Rainer >
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
Hi Martin, >> the testcase FAILs on Solaris 12 (both SPARC and x86): >> >> +FAIL: g++.dg/gcov/pr16855.C -std=gnu++11 gcov: 1 failures in line >> counts, 0 i >> n branch percentages, 0 in return percentages, 0 in intermediate format >> +FAIL: g++.dg/gcov/pr16855.C -std=gnu++11 line 21: is #:should be 1 >> +FAIL: g++.dg/gcov/pr16855.C -std=gnu++14 gcov: 1 failures in line >> counts, 0 i >> n branch percentages, 0 in return percentages, 0 in intermediate format >> +FAIL: g++.dg/gcov/pr16855.C -std=gnu++14 line 21: is #:should be 1 >> +FAIL: g++.dg/gcov/pr16855.C -std=gnu++98 gcov: 1 failures in line >> counts, 0 i >> n branch percentages, 0 in return percentages, 0 in intermediate format >> +FAIL: g++.dg/gcov/pr16855.C -std=gnu++98 line 21: is #:should be 1 >> >> I haven't looked closer yet, but notice that you require constructor >> priority support which isn't available everywhere (it is on Solaris 12, >> but not before). >> >> Rainer >> > > Hello. > > Sorry for the test-breakage. The issue is really connected to fact that > current trunk relies > on support of dtor priority. The former implementation called the function > __gcov_exit via atexit. > If I understand correctly, fully support of static ctors/dtors, C++ > ctors/dtors, with combination > of atexit cannot be done on a target w/o ctor/dtor priorities. understood. However, Solaris 12 *does* have support for constructor priorities and the testcase still fails, so there's more going on here. > Ideally we should have a macro for each target telling whether it supports > priorities or not. > However, we probably don't have? I would suggest to make the test > conditional just for main > targets which support priorities? > > Thoughts? While this would take care of the testsuite failures, this creates a terrible user experience outside of the testsuite: if we know that -fprofile-arcs -ftest-coverage cannot work on targets without constructor priority support, the compiler should error out with an appropriate message instead of just creating confusing non-working executables. Rainer -- - Rainer Orth, Center for Biotechnology, Bielefeld University
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 09/29/2016 03:00 PM, Nathan Sidwell wrote: > On 09/29/16 08:54, Nathan Sidwell wrote: >> On 09/29/16 08:49, Martin Liška wrote: >>> Ideally we should have a macro for each target telling whether it supports >>> priorities or not. >>> However, we probably don't have? I would suggest to make the test >>> conditional >>> just for main >>> targets which support priorities? >> >> or a dg_effective_target test. Probably overkill if there's exactly one >> target >> impacted. > > already there : effective_target_init_priority Nice that we have it. Looks it's going to be very first usage of the effective target. I'm suggesting patch which also changes debugging messages to make it more readable. Ready for trunk? Thanks, Martin >From cd66f6f9b9c68267698720dcf350b140d86f4201 Mon Sep 17 00:00:00 2001 From: marxinDate: Thu, 29 Sep 2016 15:39:08 +0200 Subject: [PATCH] Use effective target for pr16855 gcc/testsuite/ChangeLog: 2016-09-29 Martin Liska * g++.dg/gcov/pr16855.C: Add init_priority as an effective target. --- gcc/testsuite/g++.dg/gcov/pr16855.C | 15 --- 1 file changed, 8 insertions(+), 7 deletions(-) diff --git a/gcc/testsuite/g++.dg/gcov/pr16855.C b/gcc/testsuite/g++.dg/gcov/pr16855.C index 91801d4..8167176 100644 --- a/gcc/testsuite/g++.dg/gcov/pr16855.C +++ b/gcc/testsuite/g++.dg/gcov/pr16855.C @@ -1,13 +1,15 @@ /* { dg-options "-fprofile-arcs -ftest-coverage" } */ /* { dg-do run { target native } } */ +/* { dg-require-effective-target init_priority } */ #include +#include int a; void foo() { - a = 123; /* count(1) */ + fprintf (stderr, "atexit handler foo()\n"); /* count(1) */ } #include @@ -15,10 +17,10 @@ using namespace std; class Test { public: Test(void){ - cout<< "In Test ctor" << endl; /* count(1) */ + fprintf (stderr, "In Test ctor\n"); /* count(1) */ } ~Test(void){ - cout<< "In Test dtor" << endl; /* count(1) */ + fprintf (stderr, "In Test dtor\n"); /* count(1) */ } }T1; @@ -27,8 +29,7 @@ void uncalled(void){ } int main(void){ atexit (); -// Test T2; -cout<< "In main" << endl; /* count(1) */ +fprintf (stderr, "In main\n"); /* count(1) */ return 0; } @@ -36,12 +37,12 @@ return 0; __attribute__((constructor)) static void construct_navigationBarImages() { - fprintf (stderr, "((construct_navigationBarImages))"); /* count(1) */ + fprintf (stderr, "((construct_navigationBarImages))\n"); /* count(1) */ } __attribute__((destructor)) static void destroy_navigationBarImages() { - fprintf (stderr, "((destroy_navigationBarImages))"); /* count(1) */ + fprintf (stderr, "((destroy_navigationBarImages))\n"); /* count(1) */ } /* { dg-final { run-gcov branches { -b pr16855.C } } } */ -- 2.9.2
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 09/29/16 08:54, Nathan Sidwell wrote: On 09/29/16 08:49, Martin Liška wrote: Ideally we should have a macro for each target telling whether it supports priorities or not. However, we probably don't have? I would suggest to make the test conditional just for main targets which support priorities? or a dg_effective_target test. Probably overkill if there's exactly one target impacted. already there : effective_target_init_priority
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 09/29/16 08:49, Martin Liška wrote: Ideally we should have a macro for each target telling whether it supports priorities or not. However, we probably don't have? I would suggest to make the test conditional just for main targets which support priorities? or a dg_effective_target test. Probably overkill if there's exactly one target impacted. nathan
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 09/29/2016 11:00 AM, Rainer Orth wrote: > Hi Martin, > >> On 08/12/2016 04:08 PM, Martin Liška wrote: >>> On 08/10/2016 02:53 PM, Nathan Sidwell wrote: On 08/10/16 06:43, Martin Liška wrote: > Hello. > > There are multiple PRs (mentioned in ChangeLog) which suffer from > missing capability of gcov > to save counters for functions with constructor/destructor > attributes. I done that by simply > replacing atexit handler (gcov_exit) with a new static destructor > (__gcov_exit), which has > priority 99 (I did the same for __gcov_init). However, I'm not sure > whether it's possible > that a ctor defined in a source file can be potentially executed before > __gcov_init (w/ the default > priority)? > > Patch survives: > make check -k -j10 RUNTESTFLAGS="gcov.exp" > make check -k -j10 RUNTESTFLAGS="tree-prof.exp" > > I've just also verified that a DSO gcov dump works as before. I'm > attaching a test-case which > tests both static ctors/dtors, as well as C++ ctors/dtors. Does a coverage bootstrap (--enable-coverage) still succeed? >>> >>> Well, looks results are more unstable than I thought. >>> Even running 'make -j1' in objdir/x86_64-pc-linux-gnu/libgcc repeatedly >>> generates different results. >>> I'll dig in after weekend. >>> >>> Martin > [...] I think this is a good idea, but we should document the changed behavior. (I don't think the current behaviour's documented). >> >> I'm adding a new hunk that documents the behavior. >> >> Is the patch ready to be installed? > > the testcase FAILs on Solaris 12 (both SPARC and x86): > > +FAIL: g++.dg/gcov/pr16855.C -std=gnu++11 gcov: 1 failures in line counts, > 0 i > n branch percentages, 0 in return percentages, 0 in intermediate format > +FAIL: g++.dg/gcov/pr16855.C -std=gnu++11 line 21: is #:should be 1 > +FAIL: g++.dg/gcov/pr16855.C -std=gnu++14 gcov: 1 failures in line counts, > 0 i > n branch percentages, 0 in return percentages, 0 in intermediate format > +FAIL: g++.dg/gcov/pr16855.C -std=gnu++14 line 21: is #:should be 1 > +FAIL: g++.dg/gcov/pr16855.C -std=gnu++98 gcov: 1 failures in line counts, > 0 i > n branch percentages, 0 in return percentages, 0 in intermediate format > +FAIL: g++.dg/gcov/pr16855.C -std=gnu++98 line 21: is #:should be 1 > > I haven't looked closer yet, but notice that you require constructor > priority support which isn't available everywhere (it is on Solaris 12, > but not before). > > Rainer > Hello. Sorry for the test-breakage. The issue is really connected to fact that current trunk relies on support of dtor priority. The former implementation called the function __gcov_exit via atexit. If I understand correctly, fully support of static ctors/dtors, C++ ctors/dtors, with combination of atexit cannot be done on a target w/o ctor/dtor priorities. Ideally we should have a macro for each target telling whether it supports priorities or not. However, we probably don't have? I would suggest to make the test conditional just for main targets which support priorities? Thoughts?
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
Hi Martin, > On 08/12/2016 04:08 PM, Martin Liška wrote: >> On 08/10/2016 02:53 PM, Nathan Sidwell wrote: >>> On 08/10/16 06:43, Martin Liška wrote: Hello. There are multiple PRs (mentioned in ChangeLog) which suffer from missing capability of gcov to save counters for functions with constructor/destructor attributes. I done that by simply replacing atexit handler (gcov_exit) with a new static destructor (__gcov_exit), which has priority 99 (I did the same for __gcov_init). However, I'm not sure whether it's possible that a ctor defined in a source file can be potentially executed before __gcov_init (w/ the default priority)? Patch survives: make check -k -j10 RUNTESTFLAGS="gcov.exp" make check -k -j10 RUNTESTFLAGS="tree-prof.exp" I've just also verified that a DSO gcov dump works as before. I'm attaching a test-case which tests both static ctors/dtors, as well as C++ ctors/dtors. >>> >>> Does a coverage bootstrap (--enable-coverage) still succeed? >> >> Well, looks results are more unstable than I thought. >> Even running 'make -j1' in objdir/x86_64-pc-linux-gnu/libgcc repeatedly >> generates different results. >> I'll dig in after weekend. >> >> Martin [...] >>> I think this is a good idea, but we should document the changed >>> behavior. (I don't think the current behaviour's documented). > > I'm adding a new hunk that documents the behavior. > > Is the patch ready to be installed? the testcase FAILs on Solaris 12 (both SPARC and x86): +FAIL: g++.dg/gcov/pr16855.C -std=gnu++11 gcov: 1 failures in line counts, 0 i n branch percentages, 0 in return percentages, 0 in intermediate format +FAIL: g++.dg/gcov/pr16855.C -std=gnu++11 line 21: is #:should be 1 +FAIL: g++.dg/gcov/pr16855.C -std=gnu++14 gcov: 1 failures in line counts, 0 i n branch percentages, 0 in return percentages, 0 in intermediate format +FAIL: g++.dg/gcov/pr16855.C -std=gnu++14 line 21: is #:should be 1 +FAIL: g++.dg/gcov/pr16855.C -std=gnu++98 gcov: 1 failures in line counts, 0 i n branch percentages, 0 in return percentages, 0 in intermediate format +FAIL: g++.dg/gcov/pr16855.C -std=gnu++98 line 21: is #:should be 1 I haven't looked closer yet, but notice that you require constructor priority support which isn't available everywhere (it is on Solaris 12, but not before). Rainer -- - Rainer Orth, Center for Biotechnology, Bielefeld University
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 09/27/16 07:07, Martin Liška wrote: On 09/27/2016 12:55 PM, Nathan Sidwell wrote: "Instrumented applications use a static destructor with priority 99 to invoke the __gcov_dump function. Thus __gcov_dump is executed after all user defined static destructors, as well as handlers registered with atexit." ? Hello. I like your wording, I installed the patch as r240529. thanks!
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 09/27/2016 12:55 PM, Nathan Sidwell wrote: > > "Instrumented applications use a static destructor with priority 99 to invoke > the __gcov_dump function. Thus __gcov_dump is executed after all > user defined static destructors, as well as handlers registered with atexit." > > ? Hello. I like your wording, I installed the patch as r240529. Martin
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 09/26/16 11:22, Martin Liška wrote: Hi. So the I found reason of inconsistencies, running multiple times -fselftest is enough to find that memory allocation related functions can be executed different times. Small example: thanks for checking. @@ -598,6 +598,10 @@ facilities to restrict profile collection to the program region of interest. Calling @code{__gcov_reset(void)} will clear all profile counters to zero, and calling @code{__gcov_dump(void)} will cause the profile information collected at that point to be dumped to @file{.gcda} output files. +By default, every instrumented application calls __gcov_dump function +via a static destructor with priority equal to 99. That would guarantee +that all user defined destructors, as well as function handlers registered +by atexit, would be executed before gcov dump function is executed. 'by default' This suggests there's a non-default behaviour, but I can't see it nor how to enable it. Perhaps: "Instrumented applications use a static destructor with priority 99 to invoke the __gcov_dump function. Thus __gcov_dump is executed after all user defined static destructors, as well as handlers registered with atexit." ? nathan
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 08/12/2016 04:08 PM, Martin Liška wrote: > On 08/10/2016 02:53 PM, Nathan Sidwell wrote: >> On 08/10/16 06:43, Martin Liška wrote: >>> Hello. >>> >>> There are multiple PRs (mentioned in ChangeLog) which suffer from missing >>> capability of gcov >>> to save counters for functions with constructor/destructor attributes. I >>> done that by simply >>> replacing atexit handler (gcov_exit) with a new static destructor >>> (__gcov_exit), which has >>> priority 99 (I did the same for __gcov_init). However, I'm not sure whether >>> it's possible >>> that a ctor defined in a source file can be potentially executed before >>> __gcov_init (w/ the default >>> priority)? >>> >>> Patch survives: >>> make check -k -j10 RUNTESTFLAGS="gcov.exp" >>> make check -k -j10 RUNTESTFLAGS="tree-prof.exp" >>> >>> I've just also verified that a DSO gcov dump works as before. I'm attaching >>> a test-case which >>> tests both static ctors/dtors, as well as C++ ctors/dtors. >> >> Does a coverage bootstrap (--enable-coverage) still succeed? > > Well, looks results are more unstable than I thought. > Even running 'make -j1' in objdir/x86_64-pc-linux-gnu/libgcc repeatedly > generates different results. > I'll dig in after weekend. > > Martin Hi. So the I found reason of inconsistencies, running multiple times -fselftest is enough to find that memory allocation related functions can be executed different times. Small example: --- /tmp/r1/ggc-page.c.gcov 2016-09-26 16:54:53.060921496 +0200 +++ /tmp/r2/ggc-page.c.gcov 2016-09-26 16:55:52.470058958 +0200 @@ -636,8 +636,8 @@ -: 631:#else 307718: 632: page_table table = G.lookup; 307718: 633: uintptr_t high_bits = (uintptr_t) p & ~ (uintptr_t) 0x; - 307718: 634: while (table->high_bits != high_bits) -#: 635:table = table->next; + 307794: 634: while (table->high_bits != high_bits) + 38: 635:table = table->next; 307718: 636: base = >table[0]; -: 637:#endif -: 638: @@ -661,15 +661,15 @@ -: 656:#else -: 657: page_table table; 2134: 658: uintptr_t high_bits = (uintptr_t) p & ~ (uintptr_t) 0x; - 2134: 659: for (table = G.lookup; table; table = table->next) - 2133: 660:if (table->high_bits == high_bits) - 2133: 661: goto found; + 2322: 659: for (table = G.lookup; table; table = table->next) + 2320: 660:if (table->high_bits == high_bits) + 2132: 661: goto found; -: 662: -: 663: /* Not found -- allocate a new table. */ -1: 664: table = XCNEW (struct page_table_chain); -1: 665: table->next = G.lookup; -1: 666: table->high_bits = high_bits; -1: 667: G.lookup = table; +2: 664: table = XCNEW (struct page_table_chain); +2: 665: table->next = G.lookup; +2: 666: table->high_bits = high_bits; +2: 667: G.lookup = table; 2134: 668:found: 2134: 669: base = >table[0]; -: 670:#endif --- /tmp/r1/ggc-page.c.gcov 2016-09-26 16:54:53.060921496 +0200 +++ /tmp/r2/ggc-page.c.gcov 2016-09-26 16:58:22.440931009 +0200 @@ -679,7 +679,7 @@ 2134: 674: L2 = LOOKUP_L2 (p); -: 675: 2134: 676: if (base[L1] == NULL) -3: 677:base[L1] = XCNEWVEC (page_entry *, PAGE_L2_SIZE); +2: 677:base[L1] = XCNEWVEC (page_entry *, PAGE_L2_SIZE); -: 678: 2134: 679: base[L1][L2] = entry; 2134: 680:} It's reasonable to me that it can change. However, the patch I would like to install does not cause any new differences. Martin > >> >> I think this is a good idea, but we should document the changed behavior. (I >> don't think the current behaviour's documented). I'm adding a new hunk that documents the behavior. Is the patch ready to be installed? Thanks, Martin >> >> >> nathan > >From 686e65a923288c2c5055a9edb61e6f0648d6a2a3 Mon Sep 17 00:00:00 2001 From: marxinDate: Wed, 10 Aug 2016 12:18:45 +0200 Subject: [PATCH] gcov: dump in a static dtor instead of in an atexit handler gcc/testsuite/ChangeLog: 2016-08-10 Martin Liska PR gcov-profile/7970 PR gcov-profile/16855 PR gcov-profile/44779 * g++.dg/gcov/pr16855.C: New test. gcc/ChangeLog: 2016-08-10 Martin Liska PR gcov-profile/7970 PR gcov-profile/16855 PR gcov-profile/44779 * coverage.c (build_gcov_exit_decl): New function. (coverage_obj_init): Call the function and generate __gcov_exit destructor. * doc/gcov.texi: Document when __gcov_exit function is called. libgcc/ChangeLog: 2016-08-10 Martin Liska PR gcov-profile/7970 PR gcov-profile/16855 PR gcov-profile/44779 * libgcov-driver.c (__gcov_init): Do not register a atexit handler. (__gcov_exit): Rename from gcov_exit. * libgcov.h (__gcov_exit): Declare. --- gcc/coverage.c | 27 +++--
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 08/10/2016 02:53 PM, Nathan Sidwell wrote: > On 08/10/16 06:43, Martin Liška wrote: >> Hello. >> >> There are multiple PRs (mentioned in ChangeLog) which suffer from missing >> capability of gcov >> to save counters for functions with constructor/destructor attributes. I >> done that by simply >> replacing atexit handler (gcov_exit) with a new static destructor >> (__gcov_exit), which has >> priority 99 (I did the same for __gcov_init). However, I'm not sure whether >> it's possible >> that a ctor defined in a source file can be potentially executed before >> __gcov_init (w/ the default >> priority)? >> >> Patch survives: >> make check -k -j10 RUNTESTFLAGS="gcov.exp" >> make check -k -j10 RUNTESTFLAGS="tree-prof.exp" >> >> I've just also verified that a DSO gcov dump works as before. I'm attaching >> a test-case which >> tests both static ctors/dtors, as well as C++ ctors/dtors. > > Does a coverage bootstrap (--enable-coverage) still succeed? Well, looks results are more unstable than I thought. Even running 'make -j1' in objdir/x86_64-pc-linux-gnu/libgcc repeatedly generates different results. I'll dig in after weekend. Martin > > I think this is a good idea, but we should document the changed behavior. (I > don't think the current behaviour's documented). > > > nathan
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 08/10/16 08:53, Nathan Sidwell wrote: I think this is a good idea, but we should document the changed behavior. (I don't think the current behaviour's documented). oh, gcov_exit is a user callable routine. You'll have to keep it available.
Re: [PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
On 08/10/16 06:43, Martin Liška wrote: Hello. There are multiple PRs (mentioned in ChangeLog) which suffer from missing capability of gcov to save counters for functions with constructor/destructor attributes. I done that by simply replacing atexit handler (gcov_exit) with a new static destructor (__gcov_exit), which has priority 99 (I did the same for __gcov_init). However, I'm not sure whether it's possible that a ctor defined in a source file can be potentially executed before __gcov_init (w/ the default priority)? Patch survives: make check -k -j10 RUNTESTFLAGS="gcov.exp" make check -k -j10 RUNTESTFLAGS="tree-prof.exp" I've just also verified that a DSO gcov dump works as before. I'm attaching a test-case which tests both static ctors/dtors, as well as C++ ctors/dtors. Does a coverage bootstrap (--enable-coverage) still succeed? I think this is a good idea, but we should document the changed behavior. (I don't think the current behaviour's documented). nathan
[PATCH, RFC] gcov: dump in a static dtor instead of in an atexit handler
Hello. There are multiple PRs (mentioned in ChangeLog) which suffer from missing capability of gcov to save counters for functions with constructor/destructor attributes. I done that by simply replacing atexit handler (gcov_exit) with a new static destructor (__gcov_exit), which has priority 99 (I did the same for __gcov_init). However, I'm not sure whether it's possible that a ctor defined in a source file can be potentially executed before __gcov_init (w/ the default priority)? Patch survives: make check -k -j10 RUNTESTFLAGS="gcov.exp" make check -k -j10 RUNTESTFLAGS="tree-prof.exp" I've just also verified that a DSO gcov dump works as before. I'm attaching a test-case which tests both static ctors/dtors, as well as C++ ctors/dtors. Thoughts? Martin >From 0e7f660b77628533679e6302a3f4b444166fc365 Mon Sep 17 00:00:00 2001 From: marxinDate: Wed, 10 Aug 2016 12:18:45 +0200 Subject: [PATCH] gcov: dump in a static dtor instead of in an atexit handler gcc/testsuite/ChangeLog: 2016-08-10 Martin Liska PR gcov-profile/7970 PR gcov-profile/16855 PR gcov-profile/44779 * g++.dg/gcov/pr16855.C: New test. gcc/ChangeLog: 2016-08-10 Martin Liska PR gcov-profile/7970 PR gcov-profile/16855 PR gcov-profile/44779 * coverage.c (build_gcov_exit_decl): New function. (coverage_obj_init): Call the function and generate __gcov_exit destructor. libgcc/ChangeLog: 2016-08-10 Martin Liska PR gcov-profile/7970 PR gcov-profile/16855 PR gcov-profile/44779 * libgcov-driver.c (__gcov_init): Do not register a atexit handler. (__gcov_exit): Rename from gcov_exit. * libgcov.h (__gcov_exit): Declare. --- gcc/coverage.c | 27 +-- gcc/testsuite/g++.dg/gcov/pr16855.C | 37 + libgcc/libgcov-driver.c | 5 ++--- libgcc/libgcov.h| 3 +++ 4 files changed, 67 insertions(+), 5 deletions(-) create mode 100644 gcc/testsuite/g++.dg/gcov/pr16855.C diff --git a/gcc/coverage.c b/gcc/coverage.c index d4d371e..da7f915 100644 --- a/gcc/coverage.c +++ b/gcc/coverage.c @@ -1054,8 +1054,30 @@ build_init_ctor (tree gcov_info_type) stmt = build_call_expr (init_fn, 1, stmt); append_to_statement_list (stmt, ); - /* Generate a constructor to run it. */ - cgraph_build_static_cdtor ('I', ctor, DEFAULT_INIT_PRIORITY); + /* Generate a constructor to run it (with priority 99). */ + cgraph_build_static_cdtor ('I', ctor, DEFAULT_INIT_PRIORITY - 1); +} + +/* Generate the destructor function to call __gcov_exit. */ + +static void +build_gcov_exit_decl (void) +{ + tree init_fn = build_function_type_list (void_type_node, void_type_node, + NULL); + init_fn = build_decl (BUILTINS_LOCATION, FUNCTION_DECL, + get_identifier ("__gcov_exit"), init_fn); + TREE_PUBLIC (init_fn) = 1; + DECL_EXTERNAL (init_fn) = 1; + DECL_ASSEMBLER_NAME (init_fn); + + /* Generate a call to __gcov_exit (). */ + tree dtor = NULL; + tree stmt = build_call_expr (init_fn, 0); + append_to_statement_list (stmt, ); + + /* Generate a destructor to run it (with priority 99). */ + cgraph_build_static_cdtor ('D', dtor, DEFAULT_INIT_PRIORITY - 1); } /* Create the gcov_info types and object. Generate the constructor @@ -1113,6 +1135,7 @@ coverage_obj_init (void) DECL_NAME (gcov_info_var) = get_identifier (name_buf); build_init_ctor (gcov_info_type); + build_gcov_exit_decl (); return true; } diff --git a/gcc/testsuite/g++.dg/gcov/pr16855.C b/gcc/testsuite/g++.dg/gcov/pr16855.C new file mode 100644 index 000..ec72e99 --- /dev/null +++ b/gcc/testsuite/g++.dg/gcov/pr16855.C @@ -0,0 +1,37 @@ +/* { dg-options "-fprofile-arcs -ftest-coverage" } */ +/* { dg-do run { target native } } */ + +#include +using namespace std; +class Test { +public: + Test(void){ + cout<< "In Test ctor" << endl; /* count(1) */ + } + ~Test(void){ + cout<< "In Test dtor" << endl; /* count(1) */ + } +}T1; + +void uncalled(void){ + cout<< "In uncalled" << endl; /* count(#) */ +} +int main(void){ +// Test T2; +cout<< "In main" << endl; /* count(1) */ +return 0; +} + +#include + +__attribute__((constructor)) +static void construct_navigationBarImages() { + fprintf (stderr, "((construct_navigationBarImages))"); /* count(1) */ +} + +__attribute__((destructor)) +static void destroy_navigationBarImages() { + fprintf (stderr, "((destroy_navigationBarImages))"); /* count(1) */ +} + +/* { dg-final { run-gcov branches { -b pr16855.C } } } */ diff --git a/libgcc/libgcov-driver.c b/libgcc/libgcov-driver.c index d51397e..84471bd 100644 --- a/libgcc/libgcov-driver.c +++ b/libgcc/libgcov-driver.c @@ -872,8 +872,8 @@ struct gcov_root __gcov_root; struct gcov_master __gcov_master = {GCOV_VERSION, 0}; -static void -gcov_exit (void) +void +__gcov_exit (void) { __gcov_dump_one (&__gcov_root); if (__gcov_root.next) @@ -906,7 +906,6 @@ __gcov_init