Summary: | [4.7 regression] Rev181994 causes tramp3d-v4 profiled build failure | ||
---|---|---|---|
Product: | gcc | Reporter: | Markus Trippelsdorf <octoploid> |
Component: | gcov-profile | Assignee: | Nathan Sidwell <nathan> |
Status: | RESOLVED FIXED | ||
Severity: | normal | CC: | nathan, veksler |
Priority: | P1 | ||
Version: | 4.7.0 | ||
Target Milestone: | 4.7.0 | ||
Host: | Target: | ||
Build: | Known to work: | ||
Known to fail: | Last reconfirmed: | 2011-12-07 00:00:00 |
Description
Markus Trippelsdorf
2011-12-07 13:31:15 UTC
Here is a (somewhat) reduced testcase: % cat test.ii extern "C" { typedef long unsigned int size_t; } namespace std __attribute__ ((__visibility__ ("default"))) { template < typename _Alloc > class allocator; template < class _CharT > struct char_traits; template < typename _CharT, typename _Traits = char_traits < _CharT >, typename _Alloc = allocator < _CharT > >class basic_string; typedef basic_string < char >string; template < typename _CharT, typename _Traits = char_traits < _CharT > >class basic_ostream; typedef basic_ostream < char >ostream; typedef struct { } __pthread_unwind_buf_t __attribute__ ((__aligned__)); } namespace __gnu_cxx __attribute__ ((__visibility__ ("default"))) { template < typename _Tp > class new_allocator { public: typedef size_t size_type; typedef _Tp *pointer; typedef _Tp & reference; }; } namespace std __attribute__ ((__visibility__ ("default"))) { template < typename _Tp > class allocator:public __gnu_cxx::new_allocator < _Tp > { public: typedef size_t size_type; template < typename _Tp1 > struct rebind { typedef allocator < _Tp1 > other; }; }; class ios_base { }; template < typename _CharT, typename _Traits > class basic_ios:public ios_base { }; template < typename _CharT, typename _Traits > class basic_ostream:virtual public basic_ios < _CharT, _Traits > { public: typedef _CharT char_type; typedef basic_ostream < _CharT, _Traits > __ostream_type; __ostream_type & operator<< (long __n) { return _M_insert (__n); } __ostream_type & operator<< (bool __n) { } template < typename _ValueT > __ostream_type & _M_insert (_ValueT __v); }; extern template class basic_ostream < char >; } namespace __gnu_cxx __attribute__ ((__visibility__ ("default"))) { template < typename _Alloc > struct __alloc_traits { typedef typename _Alloc::pointer pointer; typedef typename _Alloc::reference reference; template < typename _Tp > struct rebind { typedef typename _Alloc::template rebind < _Tp >::other other; }; }; } class Inform { public: typedef int ID_t; std::ostream & stream () { } }; namespace std { extern Inform & endl (Inform &); } template < class T > inline Inform & operator<< (Inform & o, const T & val) { o.stream () << val; } namespace std __attribute__ ((__visibility__ ("default"))) { template < typename _Tp, typename _Alloc > struct _Vector_base { typedef typename __gnu_cxx::__alloc_traits < _Alloc >::template rebind < _Tp >::other _Tp_alloc_type; typedef typename __gnu_cxx::__alloc_traits < _Tp_alloc_type >::pointer pointer; struct _Vector_impl:public _Tp_alloc_type { pointer _M_start; pointer _M_finish; }; public: _Vector_impl _M_impl; }; template < typename _Tp, typename _Alloc = std::allocator < _Tp > >class vector:protected _Vector_base < _Tp, _Alloc > { typedef _Vector_base < _Tp, _Alloc > _Base; typedef typename _Base::_Tp_alloc_type _Tp_alloc_type; typedef __gnu_cxx::__alloc_traits < _Tp_alloc_type > _Alloc_traits; public: typedef _Tp value_type; typedef typename _Alloc_traits::reference reference; typedef size_t size_type; size_type size () const { return size_type (this->_M_impl._M_finish - this->_M_impl._M_start); } reference operator[] (size_type __n) { } }; struct _Setw { }; inline _Setw setw (int __n) { } template < typename _CharT, typename _Traits > inline basic_ostream < _CharT, _Traits > &operator<< (basic_ostream < _CharT, _Traits > &__os, _Setw __f) { } class StatisticsData { public: const std::string & description () const { } long value () const { } }; class Statistics { private: static long defaultFilter (long val); void print (Inform &, long (*filter) (long) = defaultFilter); private: std::vector < StatisticsData * >statList_m; }; void Statistics::print (Inform & o, long (*filter) (long)) { int i, j; for (i = 0; i < statList_m.size (); ++i) { o << " " << std::setw (12) << filter (statList_m[i]-> value ()); } } } int main(){} markus@x4 /tmp % g++ test.ii -O0 -fprofile-generate markus@x4 /tmp % g++ test.ii -O1 -fprofile-generate /tmp/ccvdpINQ.o:test.ii:function std::Statistics::print(Inform&, long (*)(long)): error: undefined reference to '__gcov0__ZNSolsEl' /tmp/ccvdpINQ.o:test.ii:function std::Statistics::print(Inform&, long (*)(long)): error: undefined reference to '__gcov0__ZNSolsEl' /tmp/ccvdpINQ.o:test.ii:function Inform& operator<< <long>(Inform&, long const&): error: undefined reference to '__gcov0__ZNSolsEl' /tmp/ccvdpINQ.o:test.ii:function Inform& operator<< <long>(Inform&, long const&): error: undefined reference to '__gcov0__ZNSolsEl' collect2: error: ld returned 1 exit status markus@x4 /tmp % g++ test.ii -O2 -fprofile-generate /tmp/ccW16Rwo.o:test.ii:function std::Statistics::print(Inform&, long (*)(long)): error: undefined reference to '__gcov0__ZNSolsEl' /tmp/ccW16Rwo.o:test.ii:function std::Statistics::print(Inform&, long (*)(long)): error: undefined reference to '__gcov0__ZNSolsEl' collect2: error: ld returned 1 exit status markus@x4 /tmp % g++ test.ii -O3 -fprofile-generate /tmp/ccgKTIgz.o:test.ii:function std::Statistics::print(Inform&, long (*)(long)): error: undefined reference to '__gcov0__ZNSolsEl' /tmp/ccgKTIgz.o:test.ii:function std::Statistics::print(Inform&, long (*)(long)): error: undefined reference to '__gcov0__ZNSolsEl' collect2: error: ld returned 1 exit status markus@x4 /tmp % g++ test.ii -O3 markus@x4 /tmp % Crud, not doing very well, am I? Here's a reduced testcase: template <typename T> struct TPL { int Baz (); int Foo () { return Baz (); } }; extern template struct TPL<char>; void Bar (TPL<char> *ptr) { ptr->Foo (); } nathan@cartagia:53>./cc1plus -fprofile-arcs tpl.ii -Ofast nathan@cartagia:53>grep gcov0 tpl.s addl $1, __gcov0__Z3BarP3TPLIcE adcl $0, __gcov0__Z3BarP3TPLIcE+4 addl $1, __gcov0__ZN3TPLIcE3FooEv adcl $0, __gcov0__ZN3TPLIcE3FooEv+4 addl $1, __gcov0__ZN3TPLIcE3FooEv+8 adcl $0, __gcov0__ZN3TPLIcE3FooEv+12 addl $1, __gcov0__Z3BarP3TPLIcE+8 adcl $0, __gcov0__Z3BarP3TPLIcE+12 .local __gcov0__Z3BarP3TPLIcE .comm __gcov0__Z3BarP3TPLIcE,16,8 .long __gcov0__Z3BarP3TPLIcE Notice __gcov0__ZN3TPLIcE3FooEv is referenced but not defined. *** Bug 51484 has been marked as a duplicate of this bug. *** Author: nathan Date: Sat Dec 10 08:32:34 2011 New Revision: 182184 URL: http://gcc.gnu.org/viewcvs?root=gcc&view=rev&rev=182184 Log: PR gcov-profile/51449 * coverage.c (coverage_end_function): Always process the coverage variables. testsuite/ * g++.dg/gcov/gcov-14.C: New. Added: trunk/gcc/testsuite/g++.dg/gcov/gcov-14.C Modified: trunk/gcc/ChangeLog trunk/gcc/coverage.c trunk/gcc/testsuite/ChangeLog I've committed the attached patch to resolve 51449. Even though the function is entirely inlined, we need to emit its coverage counters. tested in i686-pc-linux-gnu with profiled bootstrap. |