fixes for host gcc 4.6.1
[zpugcc/jano.git] / toolchain / gcc / newlib / libm / math / w_pow.c
blobd54cd3adb4cb66b7b27ec1dfe6a56c642ad964c7
3 /* @(#)w_pow.c 5.2 93/10/01 */
4 /*
5 * ====================================================
6 * Copyright (C) 1993 by Sun Microsystems, Inc. All rights reserved.
8 * Developed at SunPro, a Sun Microsystems, Inc. business.
9 * Permission to use, copy, modify, and distribute this
10 * software is freely granted, provided that this notice
11 * is preserved.
12 * ====================================================
16 FUNCTION
17 <<pow>>, <<powf>>---x to the power y
18 INDEX
19 pow
20 INDEX
21 powf
24 ANSI_SYNOPSIS
25 #include <math.h>
26 double pow(double <[x]>, double <[y]>);
27 float pow(float <[x]>, float <[y]>);
29 TRAD_SYNOPSIS
30 #include <math.h>
31 double pow(<[x]>, <[y]>);
32 double <[x]>, <[y]>;
34 float pow(<[x]>, <[y]>);
35 float <[x]>, <[y]>;
37 DESCRIPTION
38 <<pow>> and <<powf>> calculate <[x]> raised to the exponent <[y]>.
39 @tex
40 (That is, $x^y$.)
41 @end tex
43 RETURNS
44 On success, <<pow>> and <<powf>> return the value calculated.
46 When the argument values would produce overflow, <<pow>>
47 returns <<HUGE_VAL>> and set <<errno>> to <<ERANGE>>. If the
48 argument <[x]> passed to <<pow>> or <<powf>> is a negative
49 noninteger, and <[y]> is also not an integer, then <<errno>>
50 is set to <<EDOM>>. If <[x]> and <[y]> are both 0, then
51 <<pow>> and <<powf>> return <<1>>.
53 You can modify error handling for these functions using <<matherr>>.
55 PORTABILITY
56 <<pow>> is ANSI C. <<powf>> is an extension. */
58 /*
59 * wrapper pow(x,y) return x**y
62 #include "fdlibm.h"
63 #include <errno.h>
65 #ifndef _DOUBLE_IS_32BITS
67 #ifdef __STDC__
68 double pow(double x, double y) /* wrapper pow */
69 #else
70 double pow(x,y) /* wrapper pow */
71 double x,y;
72 #endif
74 #ifdef _IEEE_LIBM
75 return __ieee754_pow(x,y);
76 #else
77 double z;
78 #ifndef HUGE_VAL
79 #define HUGE_VAL inf
80 double inf = 0.0;
82 SET_HIGH_WORD(inf,0x7ff00000); /* set inf to infinite */
83 #endif
84 struct exception exc;
85 z=__ieee754_pow(x,y);
86 if(_LIB_VERSION == _IEEE_|| isnan(y)) return z;
87 if(isnan(x)) {
88 if(y==0.0) {
89 /* pow(NaN,0.0) */
90 /* error only if _LIB_VERSION == _SVID_ & _XOPEN_ */
91 exc.type = DOMAIN;
92 exc.name = "pow";
93 exc.err = 0;
94 exc.arg1 = x;
95 exc.arg2 = y;
96 exc.retval = x;
97 if (_LIB_VERSION == _IEEE_ ||
98 _LIB_VERSION == _POSIX_) exc.retval = 1.0;
99 else if (!matherr(&exc)) {
100 errno = EDOM;
102 if (exc.err != 0)
103 errno = exc.err;
104 return exc.retval;
105 } else
106 return z;
108 if(x==0.0){
109 if(y==0.0) {
110 /* pow(0.0,0.0) */
111 /* error only if _LIB_VERSION == _SVID_ */
112 exc.type = DOMAIN;
113 exc.name = "pow";
114 exc.err = 0;
115 exc.arg1 = x;
116 exc.arg2 = y;
117 exc.retval = 0.0;
118 if (_LIB_VERSION != _SVID_) exc.retval = 1.0;
119 else if (!matherr(&exc)) {
120 errno = EDOM;
122 if (exc.err != 0)
123 errno = exc.err;
124 return exc.retval;
126 if(finite(y)&&y<0.0) {
127 /* 0**neg */
128 exc.type = DOMAIN;
129 exc.name = "pow";
130 exc.err = 0;
131 exc.arg1 = x;
132 exc.arg2 = y;
133 if (_LIB_VERSION == _SVID_)
134 exc.retval = 0.0;
135 else
136 exc.retval = -HUGE_VAL;
137 if (_LIB_VERSION == _POSIX_)
138 errno = EDOM;
139 else if (!matherr(&exc)) {
140 errno = EDOM;
142 if (exc.err != 0)
143 errno = exc.err;
144 return exc.retval;
146 return z;
148 if(!finite(z)) {
149 if(finite(x)&&finite(y)) {
150 if(isnan(z)) {
151 /* neg**non-integral */
152 exc.type = DOMAIN;
153 exc.name = "pow";
154 exc.err = 0;
155 exc.arg1 = x;
156 exc.arg2 = y;
157 if (_LIB_VERSION == _SVID_)
158 exc.retval = 0.0;
159 else
160 exc.retval = 0.0/0.0; /* X/Open allow NaN */
161 if (_LIB_VERSION == _POSIX_)
162 errno = EDOM;
163 else if (!matherr(&exc)) {
164 errno = EDOM;
166 if (exc.err != 0)
167 errno = exc.err;
168 return exc.retval;
169 } else {
170 /* pow(x,y) overflow */
171 exc.type = OVERFLOW;
172 exc.name = "pow";
173 exc.err = 0;
174 exc.arg1 = x;
175 exc.arg2 = y;
176 if (_LIB_VERSION == _SVID_) {
177 exc.retval = HUGE;
178 y *= 0.5;
179 if(x<0.0&&rint(y)!=y) exc.retval = -HUGE;
180 } else {
181 exc.retval = HUGE_VAL;
182 y *= 0.5;
183 if(x<0.0&&rint(y)!=y) exc.retval = -HUGE_VAL;
185 if (_LIB_VERSION == _POSIX_)
186 errno = ERANGE;
187 else if (!matherr(&exc)) {
188 errno = ERANGE;
190 if (exc.err != 0)
191 errno = exc.err;
192 return exc.retval;
196 if(z==0.0&&finite(x)&&finite(y)) {
197 /* pow(x,y) underflow */
198 exc.type = UNDERFLOW;
199 exc.name = "pow";
200 exc.err = 0;
201 exc.arg1 = x;
202 exc.arg2 = y;
203 exc.retval = 0.0;
204 if (_LIB_VERSION == _POSIX_)
205 errno = ERANGE;
206 else if (!matherr(&exc)) {
207 errno = ERANGE;
209 if (exc.err != 0)
210 errno = exc.err;
211 return exc.retval;
213 return z;
214 #endif
217 #endif /* defined(_DOUBLE_IS_32BITS) */