[PPL-devel] [GIT] ppl/ppl(floating_point): Do not use log2 to compute the base 2 logarithm of
Fabio Bossi
bossi at cs.unipr.it
Tue Aug 3 11:10:10 CEST 2010
Module: ppl/ppl
Branch: floating_point
Commit: f6167277a1078a7891e62097d4e034830001f373
URL: http://www.cs.unipr.it/git/gitweb.cgi?p=ppl/ppl.git;a=commit;h=f6167277a1078a7891e62097d4e034830001f373
Author: Fabio Bossi <bossi at cs.unipr.it>
Date: Tue Aug 3 11:09:28 2010 +0200
Do not use log2 to compute the base 2 logarithm of
an integer.
---
src/Float.defs.hh | 9 +++++++++
src/Float.inlines.hh | 33 +++++++++++++++++++++++++++++++++
src/Float.templates.hh | 3 +--
src/Linear_Form.templates.hh | 3 +--
4 files changed, 44 insertions(+), 4 deletions(-)
diff --git a/src/Float.defs.hh b/src/Float.defs.hh
index 4e66c05..b437184 100644
--- a/src/Float.defs.hh
+++ b/src/Float.defs.hh
@@ -369,6 +369,15 @@ public:
};
#endif
+// FIXME: is this the right place for this function?
+#ifdef PPL_DOXYGEN_INCLUDE_IMPLEMENTATION_DETAILS
+//! Returns the position of the most significative bit in \p a.
+#endif // defined(PPL_DOXYGEN_INCLUDE_IMPLEMENTATION_DETAILS)
+unsigned int ld2(unsigned long long a);
+
+/* FIXME: some of the following documentation should probably be
+ under PPL_DOXYGEN_INCLUDE_IMPLEMENTATION_DETAILS */
+
/*! \brief
Returns <CODE>true</CODE> if and only if there is some floating point
number that is representable by \p f2 but not by \p f1.
diff --git a/src/Float.inlines.hh b/src/Float.inlines.hh
index 219797b..2b9c3f2 100644
--- a/src/Float.inlines.hh
+++ b/src/Float.inlines.hh
@@ -451,6 +451,39 @@ is_less_precise_than(Floating_Point_Format f1, Floating_Point_Format f2) {
return f1 < f2;
}
+#if defined(__GNUC__)
+inline unsigned int ld2(unsigned long long a) {
+ return __builtin_clzll(a) ^ (sizeof(a)*8 - 1);
+}
+#else
+unsigned int ld2(unsigned long long v) {
+ unsigned r = 0;
+ if (v >= 0x100000000ULL) {
+ v >>= 32;
+ r += 32;
+ }
+ if (v >= 0x10000) {
+ v >>= 16;
+ r += 16;
+ }
+ if (v >= 0x100) {
+ v >>= 8;
+ r += 8;
+ }
+ if (v >= 0x10) {
+ v >>= 4;
+ r += 4;
+ }
+ if (v >= 4) {
+ v >>= 2;
+ r += 2;
+ }
+ if (v >= 2)
+ r++;
+ return r;
+}
+#endif
+
template <typename FP_Interval_Type>
inline void
affine_form_image(std::map<dimension_type,
diff --git a/src/Float.templates.hh b/src/Float.templates.hh
index f062fde..287fb4f 100644
--- a/src/Float.templates.hh
+++ b/src/Float.templates.hh
@@ -113,8 +113,7 @@ const FP_Interval_Type& compute_absolute_error(
// We assume that f_base is a power of 2.
analyzer_format omega;
- int power = static_cast<int>(log2(f_base)) *
- (1 - f_exponent_bias - f_mantissa_bits);
+ int power = ld2(f_base) * (1 - f_exponent_bias - f_mantissa_bits);
omega = std::max(static_cast<analyzer_format>(ldexpl(1.0, power)),
std::numeric_limits<analyzer_format>::denorm_min());
diff --git a/src/Linear_Form.templates.hh b/src/Linear_Form.templates.hh
index 5bb64c0..596e095 100644
--- a/src/Linear_Form.templates.hh
+++ b/src/Linear_Form.templates.hh
@@ -419,8 +419,7 @@ Linear_Form<C>::relative_error(
C error_propagator;
// We assume that f_base is a power of 2.
- int power = static_cast<int>(log2(f_base)) *
- (-f_mantissa_bits);
+ int power = ld2(f_base) * (-f_mantissa_bits);
analyzer_format lb = -static_cast<analyzer_format>(ldexpl(1.0, power));
error_propagator.build(i_constraint(GREATER_OR_EQUAL, lb),
More information about the PPL-devel
mailing list