Add systemtap markers to math function slow paths

Add systemtap probes to various slow paths in libm so that application
developers may use systemtap to find out if their applications are
hitting these slow paths.  We have added probes for pow, exp, log,
tan, atan and atan2.
This commit is contained in:
Siddhesh Poyarekar 2013-10-11 22:37:53 +05:30
parent 3d110c7c6e
commit 10e1cf6b73
8 changed files with 160 additions and 5 deletions

View file

@ -1,3 +1,20 @@
2013-10-11 Siddhesh Poyarekar <siddhesh@redhat.com>
Jeff Law <law@redhat.com>
* sysdeps/ieee754/dbl-64/e_atan2.c: Include stap-probe.h.
(atan2Mp): Add systemtap probe marker.
* sysdeps/ieee754/dbl-64/e_log.c: include stap-probe.h.
(__ieee754_log): Add systemtap probe marker.
* sysdeps/ieee754/dbl-64/s_atan.c: Include stap-probe.h.
(atanMp): Add systemtap probe marker.
* sysdeps/ieee754/dbl-64/s_tan.c: Include stap-probe.h.
(tanMp): Add systemtap probe marker.
* sysdeps/ieee754/dbl-64/slowexp.c: Include stap-probe.h.
(__slowexp): Add systemtap probe marker.
* sysdeps/ieee754/dbl-64/slowpow.c: Include stap-probe.h.
(__slowpow): Add systemtap probe marker.
* manual/probes.texi: Document probes.
2013-10-11 Eric Biggers <ebiggers3@gmail.com>
[BZ #15362]

View file

@ -16,6 +16,7 @@ arguments.
@menu
* Memory Allocation Probes:: Probes in the memory allocation subsystem
* Mathematical Function Probes:: Probes in mathematical functions
@end menu
@node Memory Allocation Probes
@ -255,3 +256,100 @@ This probe is triggered when function @code{free} decides to adjust the
dynamic brk/mmap thresholds. Argument @var{$arg1} and @var{$arg2} are
the adjusted mmap and trim thresholds, respectively.
@end deftp
@node Mathematical Function Probes
@section Mathematical Function Probes
Some mathematical functions fall back to multiple precision arithmetic for
some inputs to get last bit precision for their return values. This multiple
precision fallback is much slower than the default algorithms and may have a
significant impact on application performance. The systemtap probe markers
described in this section may help you determine if your application calls
mathematical functions with inputs that may result in multiple-precision
arithmetic.
Unless explicitly mentioned otherwise, a precision of 1 implies 24 bits of
precision in the mantissa of the multiple precision number. Hence, a precision
level of 32 implies 768 bits of precision in the mantissa.
@deftp Probe slowexp_p6 (double @var{$arg1}, double @var{$arg2})
This probe is hit when the @code{exp} function is called with an input that
results in multiple precision computation with precision 6. Argument
@var{$arg1} is the input value and @var{$arg2} is the computed output.
@end deftp
@deftp Probe slowexp_p32 (double @var{$arg1}, double @var{$arg2})
This probe is hit when the @code{exp} function is called with an input that
results in multiple precision computation with precision 32. Argument
@var{$arg1} is the input value and @var{$arg2} is the computed output.
@end deftp
@deftp Probe slowpow_p10 (double @var{$arg1}, double @var{$arg2}, double @var{$arg3}, double @var{$arg4})
This probe is hit when the @code{pow} function is called with inputs that
result in multiple precision computation with precision 10. Arguments
@var{$arg1} and @var{$arg2} are the input values, @code{$arg3} is the value
computed in the fast phase of the algorithm and @code{$arg4} is the final
accurate value.
@end deftp
@deftp Probe slowpow_p32 (double @var{$arg1}, double @var{$arg2}, double @var{$arg3}, double @var{$arg4})
This probe is hit when the @code{pow} function is called with an input that
results in multiple precision computation with precision 32. Arguments
@var{$arg1} and @var{$arg2} are the input values, @code{$arg3} is the value
computed in the fast phase of the algorithm and @code{$arg4} is the final
accurate value.
@end deftp
@deftp Probe slowlog (int @var{$arg1}, double @var{$arg2}, double @var{$arg3})
This probe is hit when the @code{log} function is called with an input that
results in multiple precision computation. Argument @var{$arg1} is the
precision with which the computation succeeded. Argument @var{$arg2} is the
input and @var{$arg3} is the computed output.
@end deftp
@deftp Probe slowlog_inexact (int @var{$arg1}, double @var{$arg2}, double @var{$arg3})
This probe is hit when the @code{log} function is called with an input that
results in multiple precision computation and none of the multiple precision
computations result in an accurate result. Argument @var{$arg1} is the maximum
precision with which computations were performed. Argument @var{$arg2} is the
input and @var{$arg3} is the computed output.
@end deftp
@deftp Probe slowatan2 (int @var{$arg1}, double @var{$arg2}, double @var{$arg3}, double @var{$arg4})
This probe is hit when the @code{atan2} function is called with an input that
results in multiple precision computation. Argument @var{$arg1} is the
precision with which computation succeeded. Arguments @var{$arg2} and
@var{$arg3} are inputs to the @code{atan2} function and @var{$arg4} is the
computed result.
@end deftp
@deftp Probe slowatan2_inexact (int @var{$arg1}, double @var{$arg2}, double @var{$arg3}, double @var{$arg4})
This probe is hit when the @code{atan} function is called with an input that
results in multiple precision computation and none of the multiple precision
computations result in an accurate result. Argument @var{$arg1} is the maximum
precision with which computations were performed. Arguments @var{$arg2} and
@var{$arg3} are inputs to the @code{atan2} function and @var{$arg4} is the
computed result.
@end deftp
@deftp Probe slowatan (int @var{$arg1}, double @var{$arg2}, double @var{$arg3})
This probe is hit when the @code{atan} function is called with an input that
results in multiple precision computation. Argument @var{$arg1} is the
precision with which computation succeeded. Argument @var{$arg2} is the
input to the @code{atan} function and @var{$arg3} is the computed result.
@end deftp
@deftp Probe slowatan_inexact (int @var{$arg1}, double @var{$arg2}, double @var{$arg3})
This probe is hit when the @code{atan} function is called with an input that
results in multiple precision computation and none of the multiple precision
computations result in an accurate result. Argument @var{$arg1} is the maximum
precision with which computations were performed. Argument @var{$arg2} is the
input to the @code{atan} function and @var{$arg3} is the computed result.
@end deftp
@deftp Probe slowtan (double @var{$arg1}, double @var{$arg2})
This probe is hit when the @code{tan} function is called with an input that
results in multiple precision computation with precision 32. Argument
@var{$arg1} is the input to the function and @var{$arg2} is the computed
result.
@end deftp

View file

@ -42,6 +42,7 @@
#include "uatan.tbl"
#include "atnat2.h"
#include <math_private.h>
#include <stap-probe.h>
#ifndef SECTION
# define SECTION
@ -597,7 +598,11 @@ atan2Mp (double x, double y, const int pr[])
__mp_dbl (&mpz1, &z1, p);
__mp_dbl (&mpz2, &z2, p);
if (z1 == z2)
return z1;
{
LIBC_PROBE (slowatan2, 4, &p, &x, &y, &z1);
return z1;
}
}
LIBC_PROBE (slowatan2_inexact, 4, &p, &x, &y, &z1);
return z1; /*if impossible to do exact computing */
}

View file

@ -39,6 +39,7 @@
#include "mpa.h"
#include "MathLib.h"
#include <math_private.h>
#include <stap-probe.h>
#ifndef SECTION
# define SECTION
@ -242,8 +243,12 @@ stage_n:
__mp_dbl (&mpy1, &y1, p);
__mp_dbl (&mpy2, &y2, p);
if (y1 == y2)
return y1;
{
LIBC_PROBE (slowlog, 3, &p, &x, &y1);
return y1;
}
}
LIBC_PROBE (slowlog_inexact, 3, &p, &x, &y1);
return y1;
}

View file

@ -42,6 +42,7 @@
#include "uatan.tbl"
#include "atnat.h"
#include <math.h>
#include <stap-probe.h>
void __mpatan (mp_no *, mp_no *, int); /* see definition in mpatan.c */
static double atanMp (double, const int[]);
@ -306,8 +307,12 @@ atanMp (double x, const int pr[])
__mp_dbl (&mpy1, &y1, p);
__mp_dbl (&mpy2, &y2, p);
if (y1 == y2)
return y1;
{
LIBC_PROBE (slowatan, 3, &p, &x, &y1);
return y1;
}
}
LIBC_PROBE (slowatan_inexact, 3, &p, &x, &y1);
return y1; /*if impossible to do exact computing */
}

View file

@ -41,6 +41,7 @@
#include <math.h>
#include <math_private.h>
#include <fenv.h>
#include <stap-probe.h>
#ifndef SECTION
# define SECTION
@ -838,6 +839,7 @@ tanMp (double x)
p = 32;
__mptan (x, &mpy, p);
__mp_dbl (&mpy, &y, p);
LIBC_PROBE (slowtan, 2, &x, &y);
return y;
}

View file

@ -29,6 +29,8 @@
/**************************************************************************/
#include <math_private.h>
#include <stap-probe.h>
#ifndef USE_LONG_DOUBLE_FOR_MP
# include "mpa.h"
void __mpexp (mp_no *x, mp_no *y, int p);
@ -60,13 +62,22 @@ __slowexp (double x)
__mp_dbl (&mpw, &w, p);
__mp_dbl (&mpz, &z, p);
if (w == z)
return w;
{
/* Track how often we get to the slow exp code plus
its input/output values. */
LIBC_PROBE (slowexp_p6, 2, &x, &w);
return w;
}
else
{
p = 32;
__dbl_mp (x, &mpx, p);
__mpexp (&mpx, &mpy, p);
__mp_dbl (&mpy, &res, p);
/* Track how often we get to the uber-slow exp code plus
its input/output values. */
LIBC_PROBE (slowexp_p32, 2, &x, &res);
return res;
}
#else

View file

@ -34,6 +34,8 @@
#include "mpa.h"
#include <math_private.h>
#include <stap-probe.h>
#ifndef SECTION
# define SECTION
#endif
@ -97,7 +99,12 @@ __slowpow (double x, double y, double z)
__sub (&mpp, &eps, &mpr1, p);
__mp_dbl (&mpr1, &res1, p);
if (res == res1)
return res;
{
/* Track how often we get to the slow pow code plus
its input/output values. */
LIBC_PROBE (slowpow_p10, 4, &x, &y, &z, &res);
return res;
}
/* If we don't, then we repeat using a higher precision. 768 bits of
precision ought to be enough for anybody. */
@ -109,5 +116,10 @@ __slowpow (double x, double y, double z)
__mul (&mpy, &mpz, &mpw, p);
__mpexp (&mpw, &mpp, p);
__mp_dbl (&mpp, &res, p);
/* Track how often we get to the uber-slow pow code plus
its input/output values. */
LIBC_PROBE (slowpow_p32, 4, &x, &y, &z, &res);
return res;
}