base/math/logb.c

Go to the documentation of this file.
00001 #if defined(__ppc__)
00002 /*******************************************************************************
00003 *                                                                              *
00004 *      File logb.c,                                                            *
00005 *      Functions logb.                                                         *
00006 *      Implementation of logb for the PowerPC.                                 *
00007 *                                                                              *
00008 *      Copyright © 1991 Apple Computer, Inc.  All rights reserved.             *
00009 *                                                                              *
00010 *      Written by Ali Sazegari, started on June 1991,                          *
00011 *                                                                              *
00012 *      August   26 1991: removed CFront Version 1.1d17 warnings.               *
00013 *      August   27 1991: no errors reported by the test suite.                 *
00014 *      November 11 1991: changed CLASSEXTENDED to the macro CLASSIFY and       *
00015 *                        + or - infinity to constants.                         *
00016 *      November 18 1991: changed the macro CLASSIFY to CLASSEXTENDEDint to     *
00017 *                        improve performance.                                  *
00018 *      February 07 1992: changed bit operations to macros (  object size is    *
00019 *                        unchanged  ).                                         *
00020 *      September24 1992: took the "#include support.h" out.                    *
00021 *      December 03 1992: first rs/6000 port.                                   *
00022 *      August   30 1992: set the divide by zero for the zero argument case.    *
00023 *      October  05 1993: corrected the environment.                            *
00024 *      October  17 1994: replaced all environmental functions with __setflm.   *
00025 *      May      28 1997: made speed improvements.                              *
00026 *      April    30 2001: forst mac os x port using gcc.                        *
00027 *                                                                              *
00028 ********************************************************************************
00029 *     The C math library offers a similar function called "frexp".  It is      *
00030 *     different in details from logb, but similar in spirit.  This current     *
00031 *     implementation of logb follows the recommendation in IEEE Standard 854   *
00032 *     which is different in its handling of denormalized numbers from the IEEE *
00033 *     Standard 754.                                                            *
00034 *******************************************************************************/
00035 
00036 typedef union           
00037       { 
00038       struct {
00039 #if defined(__BIG_ENDIAN__)
00040         unsigned long int hi;
00041         unsigned long int lo;
00042 #else
00043         unsigned long int lo;
00044         unsigned long int hi;
00045 #endif
00046       } words;
00047       double dbl;
00048       } DblInHex;
00049 
00050 static const double twoTo52 = 4.50359962737049600e15;              // 0x1p52
00051 static const double klTod = 4503601774854144.0;                    // 0x1.000008p52
00052 static const unsigned long int signMask = 0x80000000ul;
00053 static const DblInHex minusInf  = {{ 0xFFF00000, 0x00000000 }};
00054 
00055 
00056 /*******************************************************************************
00057 ********************************************************************************
00058 *                                    L  O  G  B                                *
00059 ********************************************************************************
00060 *******************************************************************************/
00061 
00062 double logb (  double x  )
00063       {
00064       DblInHex xInHex;
00065       long int shiftedExp;
00066       
00067       xInHex.dbl = x;
00068       shiftedExp = ( xInHex.words.hi & 0x7ff00000UL ) >> 20;
00069       
00070       if ( shiftedExp == 2047 ) 
00071             {                                            // NaN or INF
00072             if ( ( ( xInHex.words.hi & signMask ) == 0 ) || ( x != x ) )
00073                   return x;                              // NaN or +INF return x
00074             else
00075                   return -x;                             // -INF returns +INF
00076             }
00077       
00078       if ( shiftedExp != 0 )                             // normal number
00079             shiftedExp -= 1023;                          // unbias exponent
00080       
00081       else if ( x == 0.0 ) 
00082             {                                            // zero
00083             xInHex.words.hi = 0x0UL;                      // return -infinity
00084             return (  minusInf.dbl  );
00085             }
00086       
00087       else 
00088             {                                            // subnormal number
00089             xInHex.dbl *= twoTo52;                       // scale up
00090             shiftedExp = ( xInHex.words.hi & 0x7ff00000UL ) >> 20;
00091             shiftedExp -= 1075;                          // unbias exponent
00092             }
00093       
00094       if ( shiftedExp == 0 )                             // zero result
00095             return ( 0.0 );
00096       
00097       else 
00098             {                                            // nonzero result
00099             xInHex.dbl = klTod;
00100             xInHex.words.lo += shiftedExp;
00101             return ( xInHex.dbl - klTod );
00102             }
00103       }
00104 #endif /* __ppc__ */

Generated on Tue Feb 2 17:46:05 2010 for RTAI API by  doxygen 1.4.7