Add systemtap markers to math function slow paths
authorSiddhesh Poyarekar <siddhesh@redhat.com>
Fri, 11 Oct 2013 17:07:53 +0000 (22:37 +0530)
committerSiddhesh Poyarekar <siddhesh@redhat.com>
Fri, 11 Oct 2013 17:07:53 +0000 (22:37 +0530)
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.

ChangeLog
manual/probes.texi
sysdeps/ieee754/dbl-64/e_atan2.c
sysdeps/ieee754/dbl-64/e_log.c
sysdeps/ieee754/dbl-64/s_atan.c
sysdeps/ieee754/dbl-64/s_tan.c
sysdeps/ieee754/dbl-64/slowexp.c
sysdeps/ieee754/dbl-64/slowpow.c

index c4a5d8490a04586ecad08e4e995da8c684db79b6..5090784cf05b50b844d5121237ba74daa662bf4f 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -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]
index 1a45c69b9148e92bbb6b5bd0bc644c1d6c093525..5492bb79ff697c076e5c688d6df0fb386c443bde 100644 (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
index 4ebe9c01f96c8cfba41832a7c9862ab1b49d6a73..40756223ce2aece28ea47f63872230d3a0b20f7b 100644 (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 */
 }
index f9300f9cefe406b503e9e8342802a2fe2b04de37..17ab75aa3919ec2870d321adec1e7f796c8215c8 100644 (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;
 }
 
index 7b6c83ffb6b9075293cf2d8b86c792538c6e516b..35ab5c192671d880b76e46dfaf998e4d58d74c45 100644 (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 */
 }
 
index 54f863e5441d60ab8bd6cfaca0490db2652dcfb6..cc0dbbbc9fda1d997bcac2e173b74392ab902913 100644 (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;
 }
 
index 8f353f634fad70646d3ad9f70caf2e3905cd2650..525224f44a18d8c3624600bc93dfb2bf2faf7b66 100644 (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
index a379728b1461d58be4b0c911a49412b5d9cf5fc2..d200c39e594cad9983b369dae41799acc0519ff5 100644 (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;
 }