1 /* Routines required for instrumenting a program. */
2 /* Compile this one with gcc. */
3 /* Copyright (C) 1989-2018 Free Software Foundation, Inc.
5 This file is part of GCC.
7 GCC is free software; you can redistribute it and/or modify it under
8 the terms of the GNU General Public License as published by the Free
9 Software Foundation; either version 3, or (at your option) any later
12 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
13 WARRANTY; without even the implied warranty of MERCHANTABILITY or
14 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
17 Under Section 7 of GPL version 3, you are granted additional
18 permissions described in the GCC Runtime Library Exception, version
19 3.1, as published by the Free Software Foundation.
21 You should have received a copy of the GNU General Public License and
22 a copy of the GCC Runtime Library Exception along with this program;
23 see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
24 <http://www.gnu.org/licenses/>. */
28 #if defined(inhibit_libc)
29 /* If libc and its header files are not available, provide dummy functions. */
32 void __gcov_init (struct gcov_info
*p
__attribute__ ((unused
))) {}
35 #else /* inhibit_libc */
46 /* A utility function for outputting errors. */
47 static int gcov_error (const char *, ...);
50 static void gcov_error_exit (void);
57 struct gcov_fn_buffer
*next
;
59 struct gcov_fn_info info
;
60 /* note gcov_fn_info ends in a trailing array. */
63 struct gcov_summary_buffer
65 struct gcov_summary_buffer
*next
;
66 struct gcov_summary summary
;
69 /* A struct that bundles all the related information about the
74 char *filename
; /* filename buffer */
75 size_t max_length
; /* maximum filename length */
76 int strip
; /* leading chars to strip from filename */
77 size_t prefix
; /* chars to prepend to filename */
80 static struct gcov_fn_buffer
*
81 free_fn_data (const struct gcov_info
*gi_ptr
, struct gcov_fn_buffer
*buffer
,
84 struct gcov_fn_buffer
*next
;
85 unsigned ix
, n_ctr
= 0;
91 for (ix
= 0; ix
!= limit
; ix
++)
92 if (gi_ptr
->merge
[ix
])
93 free (buffer
->info
.ctrs
[n_ctr
++].values
);
98 static struct gcov_fn_buffer
**
99 buffer_fn_data (const char *filename
, const struct gcov_info
*gi_ptr
,
100 struct gcov_fn_buffer
**end_ptr
, unsigned fn_ix
)
102 unsigned n_ctrs
= 0, ix
= 0;
103 struct gcov_fn_buffer
*fn_buffer
;
106 for (ix
= GCOV_COUNTERS
; ix
--;)
107 if (gi_ptr
->merge
[ix
])
110 len
= sizeof (*fn_buffer
) + sizeof (fn_buffer
->info
.ctrs
[0]) * n_ctrs
;
111 fn_buffer
= (struct gcov_fn_buffer
*) xmalloc (len
);
117 fn_buffer
->fn_ix
= fn_ix
;
118 fn_buffer
->info
.ident
= gcov_read_unsigned ();
119 fn_buffer
->info
.lineno_checksum
= gcov_read_unsigned ();
120 fn_buffer
->info
.cfg_checksum
= gcov_read_unsigned ();
122 for (n_ctrs
= ix
= 0; ix
!= GCOV_COUNTERS
; ix
++)
124 gcov_unsigned_t length
;
127 if (!gi_ptr
->merge
[ix
])
130 if (gcov_read_unsigned () != GCOV_TAG_FOR_COUNTER (ix
))
136 length
= GCOV_TAG_COUNTER_NUM (gcov_read_unsigned ());
137 len
= length
* sizeof (gcov_type
);
138 values
= (gcov_type
*) xmalloc (len
);
142 fn_buffer
->info
.ctrs
[n_ctrs
].num
= length
;
143 fn_buffer
->info
.ctrs
[n_ctrs
].values
= values
;
146 *values
++ = gcov_read_counter ();
150 *end_ptr
= fn_buffer
;
151 return &fn_buffer
->next
;
154 gcov_error ("profiling:%s:Function %u %s %u \n", filename
, fn_ix
,
155 len
? "cannot allocate" : "counter mismatch", len
? len
: ix
);
157 return (struct gcov_fn_buffer
**)free_fn_data (gi_ptr
, fn_buffer
, ix
);
160 /* Add an unsigned value to the current crc */
162 static gcov_unsigned_t
163 crc32_unsigned (gcov_unsigned_t crc32
, gcov_unsigned_t value
)
167 for (ix
= 32; ix
--; value
<<= 1)
171 feedback
= (value
^ crc32
) & 0x80000000 ? 0x04c11db7 : 0;
179 /* Check if VERSION of the info block PTR matches libgcov one.
180 Return 1 on success, or zero in case of versions mismatch.
181 If FILENAME is not NULL, its value used for reporting purposes
182 instead of value from the info block. */
185 gcov_version (struct gcov_info
*ptr
, gcov_unsigned_t version
,
186 const char *filename
)
188 if (version
!= GCOV_VERSION
)
192 GCOV_UNSIGNED2STRING (v
, version
);
193 GCOV_UNSIGNED2STRING (e
, GCOV_VERSION
);
195 gcov_error ("profiling:%s:Version mismatch - expected %.4s got %.4s\n",
196 filename
? filename
: ptr
->filename
, e
, v
);
202 /* Insert counter VALUE into HISTOGRAM. */
205 gcov_histogram_insert(gcov_bucket_type
*histogram
, gcov_type value
)
209 i
= gcov_histo_index(value
);
210 histogram
[i
].num_counters
++;
211 histogram
[i
].cum_value
+= value
;
212 if (value
< histogram
[i
].min_value
)
213 histogram
[i
].min_value
= value
;
216 /* Computes a histogram of the arc counters to place in the summary SUM. */
219 gcov_compute_histogram (struct gcov_info
*list
, struct gcov_summary
*sum
)
221 struct gcov_info
*gi_ptr
;
222 const struct gcov_fn_info
*gfi_ptr
;
223 const struct gcov_ctr_info
*ci_ptr
;
227 /* First check if there are any counts recorded for this counter. */
231 for (h_ix
= 0; h_ix
< GCOV_HISTOGRAM_SIZE
; h_ix
++)
233 sum
->histogram
[h_ix
].num_counters
= 0;
234 sum
->histogram
[h_ix
].min_value
= sum
->run_max
;
235 sum
->histogram
[h_ix
].cum_value
= 0;
238 /* Walk through all the per-object structures and record each of
239 the count values in histogram. */
240 for (gi_ptr
= list
; gi_ptr
; gi_ptr
= gi_ptr
->next
)
242 for (f_ix
= 0; f_ix
!= gi_ptr
->n_functions
; f_ix
++)
244 gfi_ptr
= gi_ptr
->functions
[f_ix
];
246 if (!gfi_ptr
|| gfi_ptr
->key
!= gi_ptr
)
249 ci_ptr
= &gfi_ptr
->ctrs
[0];
250 for (ix
= 0; ix
< ci_ptr
->num
; ix
++)
251 gcov_histogram_insert (sum
->histogram
, ci_ptr
->values
[ix
]);
256 /* buffer for the fn_data from another program. */
257 static struct gcov_fn_buffer
*fn_buffer
;
258 /* buffer for summary from other programs to be written out. */
259 static struct gcov_summary_buffer
*sum_buffer
;
261 /* This function computes the program level summary and the histo-gram.
262 It computes and returns CRC32 and stored summary in THIS_PRG.
263 Also determines the longest filename length of the info files. */
269 compute_summary (struct gcov_info
*list
, struct gcov_summary
*this_prg
,
272 struct gcov_info
*gi_ptr
;
273 const struct gcov_fn_info
*gfi_ptr
;
274 const struct gcov_ctr_info
*ci_ptr
;
276 gcov_unsigned_t c_num
;
277 gcov_unsigned_t crc32
= 0;
279 /* Find the totals for this execution. */
280 memset (this_prg
, 0, sizeof (*this_prg
));
282 for (gi_ptr
= list
; gi_ptr
; gi_ptr
= gi_ptr
->next
)
284 size_t len
= strlen (gi_ptr
->filename
);
285 if (len
> *max_length
)
288 crc32
= crc32_unsigned (crc32
, gi_ptr
->stamp
);
289 crc32
= crc32_unsigned (crc32
, gi_ptr
->n_functions
);
291 for (f_ix
= 0; (unsigned)f_ix
!= gi_ptr
->n_functions
; f_ix
++)
293 gfi_ptr
= gi_ptr
->functions
[f_ix
];
295 if (gfi_ptr
&& gfi_ptr
->key
!= gi_ptr
)
298 crc32
= crc32_unsigned (crc32
, gfi_ptr
? gfi_ptr
->cfg_checksum
: 0);
299 crc32
= crc32_unsigned (crc32
,
300 gfi_ptr
? gfi_ptr
->lineno_checksum
: 0);
304 ci_ptr
= gfi_ptr
->ctrs
;
305 this_prg
->num
+= ci_ptr
->num
;
306 crc32
= crc32_unsigned (crc32
, ci_ptr
->num
);
308 for (c_num
= 0; c_num
< ci_ptr
->num
; c_num
++)
310 this_prg
->sum_all
+= ci_ptr
->values
[c_num
];
311 if (this_prg
->run_max
< ci_ptr
->values
[c_num
])
312 this_prg
->run_max
= ci_ptr
->values
[c_num
];
317 gcov_compute_histogram (list
, this_prg
);
321 /* Including system dependent components. */
322 #include "libgcov-driver-system.c"
324 /* This function merges counters in GI_PTR to an existing gcda file.
326 Return -1 on error. In this case, caller will goto read_fatal. */
329 merge_one_data (const char *filename
,
330 struct gcov_info
*gi_ptr
,
331 struct gcov_summary
*prg_p
,
332 struct gcov_summary
*this_prg
,
333 gcov_position_t
*summary_pos_p
,
334 gcov_position_t
*eof_pos_p
,
335 gcov_unsigned_t crc32
)
337 gcov_unsigned_t tag
, length
;
341 struct gcov_fn_buffer
**fn_tail
= &fn_buffer
;
342 struct gcov_summary_buffer
**sum_tail
= &sum_buffer
;
344 length
= gcov_read_unsigned ();
345 if (!gcov_version (gi_ptr
, length
, filename
))
348 length
= gcov_read_unsigned ();
349 if (length
!= gi_ptr
->stamp
)
351 /* Read from a different compilation. Overwrite the file. */
352 gcov_error ("profiling:%s:overwriting an existing profile data "
353 "with a different timestamp\n", filename
);
357 /* Look for program summary. */
360 struct gcov_summary tmp
;
362 *eof_pos_p
= gcov_position ();
363 tag
= gcov_read_unsigned ();
364 if (tag
!= GCOV_TAG_PROGRAM_SUMMARY
)
368 length
= gcov_read_unsigned ();
369 gcov_read_summary (&tmp
);
370 if ((error
= gcov_is_error ()))
374 /* Save all summaries after the one that will be
375 merged into below. These will need to be rewritten
376 as histogram merging may change the number of non-zero
377 histogram entries that will be emitted, and thus the
378 size of the merged summary. */
379 (*sum_tail
) = (struct gcov_summary_buffer
*)
380 xmalloc (sizeof(struct gcov_summary_buffer
));
381 (*sum_tail
)->summary
= tmp
;
382 (*sum_tail
)->next
= 0;
383 sum_tail
= &((*sum_tail
)->next
);
386 if (tmp
.checksum
!= crc32
)
389 if (tmp
.num
!= this_prg
->num
)
392 *summary_pos_p
= *eof_pos_p
;
397 /* Merge execution counts for each function. */
398 for (f_ix
= 0; (unsigned)f_ix
!= gi_ptr
->n_functions
;
399 f_ix
++, tag
= gcov_read_unsigned ())
401 const struct gcov_ctr_info
*ci_ptr
;
402 const struct gcov_fn_info
*gfi_ptr
= gi_ptr
->functions
[f_ix
];
404 if (tag
!= GCOV_TAG_FUNCTION
)
407 length
= gcov_read_unsigned ();
409 /* This function did not appear in the other program.
410 We have nothing to merge. */
413 if (length
!= GCOV_TAG_FUNCTION_LENGTH
)
416 if (!gfi_ptr
|| gfi_ptr
->key
!= gi_ptr
)
418 /* This function appears in the other program. We
419 need to buffer the information in order to write
420 it back out -- we'll be inserting data before
421 this point, so cannot simply keep the data in the
423 fn_tail
= buffer_fn_data (filename
, gi_ptr
, fn_tail
, f_ix
);
429 length
= gcov_read_unsigned ();
430 if (length
!= gfi_ptr
->ident
)
433 length
= gcov_read_unsigned ();
434 if (length
!= gfi_ptr
->lineno_checksum
)
437 length
= gcov_read_unsigned ();
438 if (length
!= gfi_ptr
->cfg_checksum
)
441 ci_ptr
= gfi_ptr
->ctrs
;
442 for (t_ix
= 0; t_ix
< GCOV_COUNTERS
; t_ix
++)
444 gcov_merge_fn merge
= gi_ptr
->merge
[t_ix
];
449 tag
= gcov_read_unsigned ();
450 length
= gcov_read_unsigned ();
451 if (tag
!= GCOV_TAG_FOR_COUNTER (t_ix
)
452 || length
!= GCOV_TAG_COUNTER_LENGTH (ci_ptr
->num
))
454 (*merge
) (ci_ptr
->values
, ci_ptr
->num
);
457 if ((error
= gcov_is_error ()))
464 gcov_error ("profiling:%s:Merge mismatch for %s %u\n",
465 filename
, f_ix
>= 0 ? "function" : "summary",
466 f_ix
< 0 ? -1 - f_ix
: f_ix
);
472 gcov_error ("profiling:%s:%s merging\n", filename
,
473 error
< 0 ? "Overflow": "Error");
477 /* Write counters in GI_PTR and the summary in PRG to a gcda file. In
478 the case of appending to an existing file, SUMMARY_POS will be non-zero.
479 We will write the file starting from SUMMAY_POS. */
482 write_one_data (const struct gcov_info
*gi_ptr
,
483 const struct gcov_summary
*prg_p
,
484 const gcov_position_t eof_pos
,
485 const gcov_position_t summary_pos
)
488 struct gcov_summary_buffer
*next_sum_buffer
;
490 /* Write out the data. */
493 gcov_write_tag_length (GCOV_DATA_MAGIC
, GCOV_VERSION
);
494 gcov_write_unsigned (gi_ptr
->stamp
);
498 gcov_seek (summary_pos
);
500 /* Generate whole program statistics. */
501 gcov_write_summary (GCOV_TAG_PROGRAM_SUMMARY
, prg_p
);
503 /* Rewrite all the summaries that were after the summary we merged
504 into. This is necessary as the merged summary may have a different
505 size due to the number of non-zero histogram entries changing after
510 gcov_write_summary (GCOV_TAG_PROGRAM_SUMMARY
, &sum_buffer
->summary
);
511 next_sum_buffer
= sum_buffer
->next
;
513 sum_buffer
= next_sum_buffer
;
516 /* Write execution counts for each function. */
517 for (f_ix
= 0; f_ix
!= gi_ptr
->n_functions
; f_ix
++)
519 unsigned buffered
= 0;
520 const struct gcov_fn_info
*gfi_ptr
;
521 const struct gcov_ctr_info
*ci_ptr
;
522 gcov_unsigned_t length
;
525 if (fn_buffer
&& fn_buffer
->fn_ix
== f_ix
)
527 /* Buffered data from another program. */
529 gfi_ptr
= &fn_buffer
->info
;
530 length
= GCOV_TAG_FUNCTION_LENGTH
;
534 gfi_ptr
= gi_ptr
->functions
[f_ix
];
535 if (gfi_ptr
&& gfi_ptr
->key
== gi_ptr
)
536 length
= GCOV_TAG_FUNCTION_LENGTH
;
541 gcov_write_tag_length (GCOV_TAG_FUNCTION
, length
);
545 gcov_write_unsigned (gfi_ptr
->ident
);
546 gcov_write_unsigned (gfi_ptr
->lineno_checksum
);
547 gcov_write_unsigned (gfi_ptr
->cfg_checksum
);
549 ci_ptr
= gfi_ptr
->ctrs
;
550 for (t_ix
= 0; t_ix
< GCOV_COUNTERS
; t_ix
++)
552 gcov_unsigned_t n_counts
;
555 if (!gi_ptr
->merge
[t_ix
])
558 n_counts
= ci_ptr
->num
;
559 gcov_write_tag_length (GCOV_TAG_FOR_COUNTER (t_ix
),
560 GCOV_TAG_COUNTER_LENGTH (n_counts
));
561 c_ptr
= ci_ptr
->values
;
563 gcov_write_counter (*c_ptr
++);
567 fn_buffer
= free_fn_data (gi_ptr
, fn_buffer
, GCOV_COUNTERS
);
570 gcov_write_unsigned (0);
573 /* Helper function for merging summary.
574 Return -1 on error. Return 0 on success. */
577 merge_summary (const char *filename
__attribute__ ((unused
)), int run_counted
,
578 struct gcov_summary
*prg
,
579 struct gcov_summary
*this_prg
, gcov_unsigned_t crc32
,
580 struct gcov_summary
*all_prg
__attribute__ ((unused
)))
583 /* summary for all instances of program. */
584 struct gcov_summary
*cs_all
;
587 /* Merge the summary. */
588 int first
= !prg
->runs
;
593 prg
->num
= this_prg
->num
;
594 prg
->sum_all
+= this_prg
->sum_all
;
595 if (prg
->run_max
< this_prg
->run_max
)
596 prg
->run_max
= this_prg
->run_max
;
597 prg
->sum_max
+= this_prg
->run_max
;
599 memcpy (prg
->histogram
, this_prg
->histogram
,
600 sizeof (gcov_bucket_type
) * GCOV_HISTOGRAM_SIZE
);
602 gcov_histogram_merge (prg
->histogram
, this_prg
->histogram
);
604 all
= &all_prg
->ctrs
[t_ix
];
605 if (!all
->runs
&& prg
->runs
)
608 all
->runs
= prg
->runs
;
609 all
->sum_all
= prg
->sum_all
;
610 all
->run_max
= prg
->run_max
;
611 all
->sum_max
= prg
->sum_max
;
613 else if (!all_prg
->checksum
614 /* Don't compare the histograms, which may have slight
615 variations depending on the order they were updated
616 due to the truncating integer divides used in the
618 && (all
->num
!= prg
->num
619 || all
->runs
!= prg
->runs
620 || all
->sum_all
!= prg
->sum_all
621 || all
->run_max
!= prg
->run_max
622 || all
->sum_max
!= prg
->sum_max
))
624 gcov_error ("profiling:%s:Data file mismatch - some "
625 "data files may have been concurrently "
626 "updated without locking support\n", filename
);
627 all_prg
->checksum
= ~0u;
631 prg
->checksum
= crc32
;
637 /* Sort N entries in VALUE_ARRAY in descending order.
638 Each entry in VALUE_ARRAY has two values. The sorting
639 is based on the second value. */
642 gcov_sort_n_vals (gcov_type
*value_array
, int n
)
646 for (j
= 2; j
< n
; j
+= 2)
648 gcov_type cur_ent
[2];
650 cur_ent
[0] = value_array
[j
];
651 cur_ent
[1] = value_array
[j
+ 1];
653 while (k
>= 0 && value_array
[k
+ 1] < cur_ent
[1])
655 value_array
[k
+ 2] = value_array
[k
];
656 value_array
[k
+ 3] = value_array
[k
+1];
659 value_array
[k
+ 2] = cur_ent
[0];
660 value_array
[k
+ 3] = cur_ent
[1];
664 /* Sort the profile counters for all indirect call sites. Counters
665 for each call site are allocated in array COUNTERS. */
668 gcov_sort_icall_topn_counter (const struct gcov_ctr_info
*counters
)
672 int n
= counters
->num
;
674 gcc_assert (!(n
% GCOV_ICALL_TOPN_NCOUNTS
));
675 values
= counters
->values
;
677 for (i
= 0; i
< n
; i
+= GCOV_ICALL_TOPN_NCOUNTS
)
679 gcov_type
*value_array
= &values
[i
+ 1];
680 gcov_sort_n_vals (value_array
, GCOV_ICALL_TOPN_NCOUNTS
- 1);
684 /* Sort topn indirect_call profile counters in GI_PTR. */
687 gcov_sort_topn_counter_arrays (const struct gcov_info
*gi_ptr
)
691 const struct gcov_fn_info
*gfi_ptr
;
692 const struct gcov_ctr_info
*ci_ptr
;
694 if (!gi_ptr
->merge
[GCOV_COUNTER_ICALL_TOPNV
])
697 for (f_ix
= 0; (unsigned)f_ix
!= gi_ptr
->n_functions
; f_ix
++)
699 gfi_ptr
= gi_ptr
->functions
[f_ix
];
700 ci_ptr
= gfi_ptr
->ctrs
;
701 for (i
= 0; i
< GCOV_COUNTERS
; i
++)
703 if (!gi_ptr
->merge
[i
])
705 if (i
== GCOV_COUNTER_ICALL_TOPNV
)
707 gcov_sort_icall_topn_counter (ci_ptr
);
715 /* Dump the coverage counts for one gcov_info object. We merge with existing
716 counts when possible, to avoid growing the .da files ad infinitum. We use
717 this program's checksum to make sure we only accumulate whole program
718 statistics to the correct summary. An object file might be embedded
719 in two separate programs, and we must keep the two program
720 summaries separate. */
723 dump_one_gcov (struct gcov_info
*gi_ptr
, struct gcov_filename
*gf
,
724 unsigned run_counted
,
725 gcov_unsigned_t crc32
, struct gcov_summary
*all_prg
,
726 struct gcov_summary
*this_prg
)
728 struct gcov_summary prg
; /* summary for this object over all program. */
731 gcov_position_t summary_pos
= 0;
732 gcov_position_t eof_pos
= 0;
737 gcov_sort_topn_counter_arrays (gi_ptr
);
739 error
= gcov_exit_open_gcda_file (gi_ptr
, gf
);
743 tag
= gcov_read_unsigned ();
746 /* Merge data from file. */
747 if (tag
!= GCOV_DATA_MAGIC
)
749 gcov_error ("profiling:%s:Not a gcov data file\n", gf
->filename
);
752 error
= merge_one_data (gf
->filename
, gi_ptr
, &prg
, this_prg
,
753 &summary_pos
, &eof_pos
, crc32
);
762 memset (&prg
, 0, sizeof (prg
));
763 summary_pos
= eof_pos
;
766 error
= merge_summary (gf
->filename
, run_counted
, &prg
, this_prg
,
771 write_one_data (gi_ptr
, &prg
, eof_pos
, summary_pos
);
776 fn_buffer
= free_fn_data (gi_ptr
, fn_buffer
, GCOV_COUNTERS
);
778 if ((error
= gcov_close ()))
779 gcov_error (error
< 0 ?
780 "profiling:%s:Overflow writing\n" :
781 "profiling:%s:Error writing\n",
786 /* Dump all the coverage counts for the program. It first computes program
787 summary and then traverses gcov_list list and dumps the gcov_info
788 objects one by one. */
794 gcov_do_dump (struct gcov_info
*list
, int run_counted
)
796 struct gcov_info
*gi_ptr
;
797 struct gcov_filename gf
;
798 gcov_unsigned_t crc32
;
799 struct gcov_summary all_prg
;
800 struct gcov_summary this_prg
;
802 crc32
= compute_summary (list
, &this_prg
, &gf
.max_length
);
804 allocate_filename_struct (&gf
);
806 memset (&all_prg
, 0, sizeof (all_prg
));
809 /* Now merge each file. */
810 for (gi_ptr
= list
; gi_ptr
; gi_ptr
= gi_ptr
->next
)
811 dump_one_gcov (gi_ptr
, &gf
, run_counted
, crc32
, &all_prg
, &this_prg
);
818 __attribute__ ((unused
))
819 gcov_get_filename (struct gcov_info
*list
)
821 return list
->filename
;
827 __gcov_dump_one (struct gcov_root
*root
)
832 gcov_do_dump (root
->list
, root
->run_counted
);
835 root
->run_counted
= 1;
838 /* Per-dynamic-object gcov state. */
839 struct gcov_root __gcov_root
;
841 /* Exactly one of these will be live in the process image. */
842 struct gcov_master __gcov_master
=
848 __gcov_dump_one (&__gcov_root
);
849 if (__gcov_root
.next
)
850 __gcov_root
.next
->prev
= __gcov_root
.prev
;
851 if (__gcov_root
.prev
)
852 __gcov_root
.prev
->next
= __gcov_root
.next
;
854 __gcov_master
.root
= __gcov_root
.next
;
859 /* Add a new object file onto the bb chain. Invoked automatically
860 when running an object file's global ctors. */
863 __gcov_init (struct gcov_info
*info
)
865 if (!info
->version
|| !info
->n_functions
)
867 if (gcov_version (info
, info
->version
, 0))
869 if (!__gcov_root
.list
)
871 /* Add to master list and at exit function. */
872 if (gcov_version (NULL
, __gcov_master
.version
, "<master>"))
874 __gcov_root
.next
= __gcov_master
.root
;
875 if (__gcov_master
.root
)
876 __gcov_master
.root
->prev
= &__gcov_root
;
877 __gcov_master
.root
= &__gcov_root
;
881 info
->next
= __gcov_root
.list
;
882 __gcov_root
.list
= info
;
885 #endif /* !IN_GCOV_TOOL */
887 #endif /* inhibit_libc */