src/libm/math_private.h
author Ryan C. Gordon <icculus@icculus.org>
Tue, 26 May 2015 21:19:23 -0400
changeset 9649 d7762e30ba24
parent 9080 2e4e71ec140f
child 11683 48bcba563d9c
permissions -rw-r--r--
Stack hint should look for 0, not -1, and not care about environment variables.
     1 /*
     2  * ====================================================
     3  * Copyright (C) 1993 by Sun Microsystems, Inc. All rights reserved.
     4  *
     5  * Developed at SunPro, a Sun Microsystems, Inc. business.
     6  * Permission to use, copy, modify, and distribute this
     7  * software is freely granted, provided that this notice
     8  * is preserved.
     9  * ====================================================
    10  */
    11 
    12 /*
    13  * from: @(#)fdlibm.h 5.1 93/09/24
    14  * $Id: math_private.h,v 1.3 2004/02/09 07:10:38 andersen Exp $
    15  */
    16 
    17 #ifndef _MATH_PRIVATE_H_
    18 #define _MATH_PRIVATE_H_
    19 
    20 /* #include <endian.h> */
    21 #include "SDL_endian.h"
    22 /* #include <sys/types.h> */
    23 
    24 #define attribute_hidden
    25 #define libm_hidden_proto(x)
    26 #define libm_hidden_def(x)
    27 
    28 #ifndef __HAIKU__ /* already defined in a system header. */
    29 typedef unsigned int u_int32_t;
    30 #endif
    31 
    32 #define atan            SDL_uclibc_atan
    33 #define __ieee754_atan2 SDL_uclibc_atan2
    34 #define copysign        SDL_uclibc_copysign
    35 #define cos             SDL_uclibc_cos
    36 #define fabs            SDL_uclibc_fabs
    37 #define floor           SDL_uclibc_floor
    38 #define __ieee754_log   SDL_uclibc_log
    39 #define __ieee754_pow   SDL_uclibc_pow
    40 #define scalbn          SDL_uclibc_scalbn
    41 #define sin             SDL_uclibc_sin
    42 #define __ieee754_sqrt  SDL_uclibc_sqrt
    43 #define tan             SDL_uclibc_tan
    44 
    45 /* The original fdlibm code used statements like:
    46 	n0 = ((*(int*)&one)>>29)^1;		* index of high word *
    47 	ix0 = *(n0+(int*)&x);			* high word of x *
    48 	ix1 = *((1-n0)+(int*)&x);		* low word of x *
    49    to dig two 32 bit words out of the 64 bit IEEE floating point
    50    value.  That is non-ANSI, and, moreover, the gcc instruction
    51    scheduler gets it wrong.  We instead use the following macros.
    52    Unlike the original code, we determine the endianness at compile
    53    time, not at run time; I don't see much benefit to selecting
    54    endianness at run time.  */
    55 
    56 /* A union which permits us to convert between a double and two 32 bit
    57    ints.  */
    58 
    59 /*
    60  * Math on arm is special:
    61  * For FPA, float words are always big-endian.
    62  * For VFP, floats words follow the memory system mode.
    63  */
    64 
    65 #if (SDL_BYTEORDER == SDL_BIG_ENDIAN)
    66 
    67 typedef union
    68 {
    69     double value;
    70     struct
    71     {
    72         u_int32_t msw;
    73         u_int32_t lsw;
    74     } parts;
    75 } ieee_double_shape_type;
    76 
    77 #else
    78 
    79 typedef union
    80 {
    81     double value;
    82     struct
    83     {
    84         u_int32_t lsw;
    85         u_int32_t msw;
    86     } parts;
    87 } ieee_double_shape_type;
    88 
    89 #endif
    90 
    91 /* Get two 32 bit ints from a double.  */
    92 
    93 #define EXTRACT_WORDS(ix0,ix1,d)				\
    94 do {								\
    95   ieee_double_shape_type ew_u;					\
    96   ew_u.value = (d);						\
    97   (ix0) = ew_u.parts.msw;					\
    98   (ix1) = ew_u.parts.lsw;					\
    99 } while (0)
   100 
   101 /* Get the more significant 32 bit int from a double.  */
   102 
   103 #define GET_HIGH_WORD(i,d)					\
   104 do {								\
   105   ieee_double_shape_type gh_u;					\
   106   gh_u.value = (d);						\
   107   (i) = gh_u.parts.msw;						\
   108 } while (0)
   109 
   110 /* Get the less significant 32 bit int from a double.  */
   111 
   112 #define GET_LOW_WORD(i,d)					\
   113 do {								\
   114   ieee_double_shape_type gl_u;					\
   115   gl_u.value = (d);						\
   116   (i) = gl_u.parts.lsw;						\
   117 } while (0)
   118 
   119 /* Set a double from two 32 bit ints.  */
   120 
   121 #define INSERT_WORDS(d,ix0,ix1)					\
   122 do {								\
   123   ieee_double_shape_type iw_u;					\
   124   iw_u.parts.msw = (ix0);					\
   125   iw_u.parts.lsw = (ix1);					\
   126   (d) = iw_u.value;						\
   127 } while (0)
   128 
   129 /* Set the more significant 32 bits of a double from an int.  */
   130 
   131 #define SET_HIGH_WORD(d,v)					\
   132 do {								\
   133   ieee_double_shape_type sh_u;					\
   134   sh_u.value = (d);						\
   135   sh_u.parts.msw = (v);						\
   136   (d) = sh_u.value;						\
   137 } while (0)
   138 
   139 /* Set the less significant 32 bits of a double from an int.  */
   140 
   141 #define SET_LOW_WORD(d,v)					\
   142 do {								\
   143   ieee_double_shape_type sl_u;					\
   144   sl_u.value = (d);						\
   145   sl_u.parts.lsw = (v);						\
   146   (d) = sl_u.value;						\
   147 } while (0)
   148 
   149 /* A union which permits us to convert between a float and a 32 bit
   150    int.  */
   151 
   152 typedef union
   153 {
   154     float value;
   155     u_int32_t word;
   156 } ieee_float_shape_type;
   157 
   158 /* Get a 32 bit int from a float.  */
   159 
   160 #define GET_FLOAT_WORD(i,d)					\
   161 do {								\
   162   ieee_float_shape_type gf_u;					\
   163   gf_u.value = (d);						\
   164   (i) = gf_u.word;						\
   165 } while (0)
   166 
   167 /* Set a float from a 32 bit int.  */
   168 
   169 #define SET_FLOAT_WORD(d,i)					\
   170 do {								\
   171   ieee_float_shape_type sf_u;					\
   172   sf_u.word = (i);						\
   173   (d) = sf_u.value;						\
   174 } while (0)
   175 
   176 /* ieee style elementary functions */
   177 extern double
   178 __ieee754_sqrt(double)
   179     attribute_hidden;
   180      extern double __ieee754_acos(double) attribute_hidden;
   181      extern double __ieee754_acosh(double) attribute_hidden;
   182      extern double __ieee754_log(double) attribute_hidden;
   183      extern double __ieee754_atanh(double) attribute_hidden;
   184      extern double __ieee754_asin(double) attribute_hidden;
   185      extern double __ieee754_atan2(double, double) attribute_hidden;
   186      extern double __ieee754_exp(double) attribute_hidden;
   187      extern double __ieee754_cosh(double) attribute_hidden;
   188      extern double __ieee754_fmod(double, double) attribute_hidden;
   189      extern double __ieee754_pow(double, double) attribute_hidden;
   190      extern double __ieee754_lgamma_r(double, int *) attribute_hidden;
   191      extern double __ieee754_gamma_r(double, int *) attribute_hidden;
   192      extern double __ieee754_lgamma(double) attribute_hidden;
   193      extern double __ieee754_gamma(double) attribute_hidden;
   194      extern double __ieee754_log10(double) attribute_hidden;
   195      extern double __ieee754_sinh(double) attribute_hidden;
   196      extern double __ieee754_hypot(double, double) attribute_hidden;
   197      extern double __ieee754_j0(double) attribute_hidden;
   198      extern double __ieee754_j1(double) attribute_hidden;
   199      extern double __ieee754_y0(double) attribute_hidden;
   200      extern double __ieee754_y1(double) attribute_hidden;
   201      extern double __ieee754_jn(int, double) attribute_hidden;
   202      extern double __ieee754_yn(int, double) attribute_hidden;
   203      extern double __ieee754_remainder(double, double) attribute_hidden;
   204      extern int __ieee754_rem_pio2(double, double *) attribute_hidden;
   205 #if defined(_SCALB_INT)
   206      extern double __ieee754_scalb(double, int) attribute_hidden;
   207 #else
   208      extern double __ieee754_scalb(double, double) attribute_hidden;
   209 #endif
   210 
   211 /* fdlibm kernel function */
   212 #ifndef _IEEE_LIBM
   213      extern double __kernel_standard(double, double, int) attribute_hidden;
   214 #endif
   215      extern double __kernel_sin(double, double, int) attribute_hidden;
   216      extern double __kernel_cos(double, double) attribute_hidden;
   217      extern double __kernel_tan(double, double, int) attribute_hidden;
   218      extern int __kernel_rem_pio2(double *, double *, int, int, int,
   219                                   const int *) attribute_hidden;
   220 
   221 #endif /* _MATH_PRIVATE_H_ */