1 /* Routines required for instrumenting a program. */
2 /* Compile this one with gcc. */
3 /* Copyright (C) 1989-2014 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/>. */
29 #if defined(inhibit_libc)
32 void __gcov_flush (void) {}
36 void __gcov_reset (void) {}
40 void __gcov_dump (void) {}
46 /* Some functions we want to bind in this dynamic object, but have an
47 overridable global alias. */
48 #define STRONG_ALIAS(src,dst) \
49 extern __typeof (src) dst __attribute__((alias (#src)))
51 extern __gthread_mutex_t __gcov_flush_mx ATTRIBUTE_HIDDEN
;
52 extern __gthread_mutex_t __gcov_flush_mx ATTRIBUTE_HIDDEN
;
55 #ifdef __GTHREAD_MUTEX_INIT
56 __gthread_mutex_t __gcov_flush_mx
= __GTHREAD_MUTEX_INIT
;
57 #define init_mx_once()
59 __gthread_mutex_t __gcov_flush_mx
;
64 __GTHREAD_MUTEX_INIT_FUNCTION (&__gcov_flush_mx
);
70 static __gthread_once_t once
= __GTHREAD_ONCE_INIT
;
71 __gthread_once (&once
, init_mx
);
75 /* Called before fork or exec - write out profile information gathered so
76 far and reset it to zero. This avoids duplication or loss of the
77 profile information gathered so far. */
83 __gthread_mutex_lock (&__gcov_flush_mx
);
85 __gcov_dump_one (&__gcov_root
);
88 __gthread_mutex_unlock (&__gcov_flush_mx
);
91 #endif /* L_gcov_flush */
95 /* Reset all counters to zero. */
98 gcov_clear (const struct gcov_info
*list
)
100 const struct gcov_info
*gi_ptr
;
102 for (gi_ptr
= list
; gi_ptr
; gi_ptr
= gi_ptr
->next
)
106 for (f_ix
= 0; f_ix
< gi_ptr
->n_functions
; f_ix
++)
109 const struct gcov_fn_info
*gfi_ptr
= gi_ptr
->functions
[f_ix
];
111 if (!gfi_ptr
|| gfi_ptr
->key
!= gi_ptr
)
113 const struct gcov_ctr_info
*ci_ptr
= gfi_ptr
->ctrs
;
114 for (t_ix
= 0; t_ix
!= GCOV_COUNTERS
; t_ix
++)
116 if (!gi_ptr
->merge
[t_ix
])
119 memset (ci_ptr
->values
, 0, sizeof (gcov_type
) * ci_ptr
->num
);
126 /* Function that can be called from application to reset counters to zero,
127 in order to collect profile in region of interest. */
130 __gcov_reset_int (void)
132 gcov_clear (__gcov_root
.list
);
133 __gcov_root
.dumped
= 0;
136 STRONG_ALIAS (__gcov_reset_int
, __gcov_reset
);
138 #endif /* L_gcov_reset */
141 /* Function that can be called from application to write profile collected
142 so far, in order to collect profile in region of interest. */
147 __gcov_dump_one (&__gcov_root
);
150 #endif /* L_gcov_dump */
153 /* A wrapper for the fork function. Flushes the accumulated profiling data, so
154 that they are not counted twice. */
163 __GTHREAD_MUTEX_INIT_FUNCTION (&__gcov_flush_mx
);
169 /* A wrapper for the execl function. Flushes the accumulated profiling data, so
170 that they are not lost. */
173 __gcov_execl (const char *path
, char *arg
, ...)
185 while (va_arg (ap
, char *))
189 args
= (char **) alloca (length
* sizeof (void *));
191 for (i
= 1; i
< length
; i
++)
192 args
[i
] = va_arg (aq
, char *);
195 return execv (path
, args
);
200 /* A wrapper for the execlp function. Flushes the accumulated
201 profiling data, so that they are not lost. */
204 __gcov_execlp (const char *path
, char *arg
, ...)
216 while (va_arg (ap
, char *))
220 args
= (char **) alloca (length
* sizeof (void *));
222 for (i
= 1; i
< length
; i
++)
223 args
[i
] = va_arg (aq
, char *);
226 return execvp (path
, args
);
231 /* A wrapper for the execle function. Flushes the accumulated
232 profiling data, so that they are not lost. */
235 __gcov_execle (const char *path
, char *arg
, ...)
248 while (va_arg (ap
, char *))
252 args
= (char **) alloca (length
* sizeof (void *));
254 for (i
= 1; i
< length
; i
++)
255 args
[i
] = va_arg (aq
, char *);
256 envp
= va_arg (aq
, char **);
259 return execve (path
, args
, envp
);
264 /* A wrapper for the execv function. Flushes the accumulated
265 profiling data, so that they are not lost. */
268 __gcov_execv (const char *path
, char *const argv
[])
271 return execv (path
, argv
);
276 /* A wrapper for the execvp function. Flushes the accumulated
277 profiling data, so that they are not lost. */
280 __gcov_execvp (const char *path
, char *const argv
[])
283 return execvp (path
, argv
);
288 /* A wrapper for the execve function. Flushes the accumulated
289 profiling data, so that they are not lost. */
292 __gcov_execve (const char *path
, char *const argv
[], char *const envp
[])
295 return execve (path
, argv
, envp
);
298 #endif /* inhibit_libc */