blob: 070e83def9af0ccf7fb14a0ce034763c54f80bca [file] [log] [blame]
Guido van Rossumf70e43a1991-02-19 12:39:46 +00001/***********************************************************
Guido van Rossum6610ad91995-01-04 19:07:38 +00002Copyright 1991-1995 by Stichting Mathematisch Centrum, Amsterdam,
3The Netherlands.
Guido van Rossumf70e43a1991-02-19 12:39:46 +00004
5 All Rights Reserved
6
Guido van Rossumd266eb41996-10-25 14:44:06 +00007Permission to use, copy, modify, and distribute this software and its
8documentation for any purpose and without fee is hereby granted,
Guido van Rossumf70e43a1991-02-19 12:39:46 +00009provided that the above copyright notice appear in all copies and that
Guido van Rossumd266eb41996-10-25 14:44:06 +000010both that copyright notice and this permission notice appear in
Guido van Rossumf70e43a1991-02-19 12:39:46 +000011supporting documentation, and that the names of Stichting Mathematisch
Guido van Rossumd266eb41996-10-25 14:44:06 +000012Centrum or CWI or Corporation for National Research Initiatives or
13CNRI not be used in advertising or publicity pertaining to
14distribution of the software without specific, written prior
15permission.
Guido van Rossumf70e43a1991-02-19 12:39:46 +000016
Guido van Rossumd266eb41996-10-25 14:44:06 +000017While CWI is the initial source for this software, a modified version
18is made available by the Corporation for National Research Initiatives
19(CNRI) at the Internet address ftp://ftp.python.org.
20
21STICHTING MATHEMATISCH CENTRUM AND CNRI DISCLAIM ALL WARRANTIES WITH
22REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
23MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL STICHTING MATHEMATISCH
24CENTRUM OR CNRI BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
25DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
26PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
27TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
28PERFORMANCE OF THIS SOFTWARE.
Guido van Rossumf70e43a1991-02-19 12:39:46 +000029
30******************************************************************/
31
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000032/* Float object implementation */
33
Guido van Rossum2a9096b1990-10-21 22:15:08 +000034/* XXX There should be overflow checks here, but it's hard to check
35 for any kind of float exception without losing portability. */
36
Guido van Rossumc0b618a1997-05-02 03:12:38 +000037#include "Python.h"
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000038
Guido van Rossum3f5da241990-12-20 15:06:42 +000039#include <ctype.h>
Guido van Rossum07e3a7e1995-02-27 10:13:37 +000040#include "mymath.h"
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000041
Guido van Rossum9575a441993-04-07 14:06:14 +000042#ifdef i860
43/* Cray APP has bogus definition of HUGE_VAL in <math.h> */
44#undef HUGE_VAL
45#endif
46
Guido van Rossum9d81b551996-06-26 18:27:19 +000047#if defined(HUGE_VAL) && !defined(CHECK)
Guido van Rossum7fa52f81991-12-16 15:43:14 +000048#define CHECK(x) if (errno != 0) ; \
49 else if (-HUGE_VAL <= (x) && (x) <= HUGE_VAL) ; \
50 else errno = ERANGE
Guido van Rossum9d81b551996-06-26 18:27:19 +000051#endif
52
53#ifndef CHECK
Guido van Rossum7fa52f81991-12-16 15:43:14 +000054#define CHECK(x) /* Don't know how to check */
55#endif
56
Guido van Rossum03093a21994-09-28 15:51:32 +000057#ifdef HAVE_LIMITS_H
58#include <limits.h>
59#endif
60
61#ifndef LONG_MAX
62#define LONG_MAX 0X7FFFFFFFL
63#endif
64
65#ifndef LONG_MIN
66#define LONG_MIN (-LONG_MAX-1)
67#endif
68
Guido van Rossum67ca7011995-02-13 16:38:41 +000069#ifdef __NeXT__
70#ifdef __sparc__
71/*
72 * This works around a bug in the NS/Sparc 3.3 pre-release
73 * limits.h header file.
74 * 10-Feb-1995 bwarsaw@cnri.reston.va.us
75 */
76#undef LONG_MIN
77#define LONG_MIN (-LONG_MAX-1)
78#endif
79#endif
80
Guido van Rossum07e3a7e1995-02-27 10:13:37 +000081#if !defined(__STDC__) && !defined(macintosh)
Guido van Rossumc0b618a1997-05-02 03:12:38 +000082extern double fmod Py_PROTO((double, double));
83extern double pow Py_PROTO((double, double));
Guido van Rossum6923e131990-11-02 17:50:43 +000084#endif
85
Guido van Rossum3c03fa81997-10-31 17:00:30 +000086#ifdef sun
87/* On SunOS4.1 only libm.a exists. Make sure that references to all
88 needed math functions exist in the executable, so that dynamic
89 loading of mathmodule does not fail. */
90double (*_Py_math_funcs_hack[])() = {
91 acos, asin, atan, atan2, ceil, cos, cosh, exp, fabs, floor,
92 fmod, log, log10, pow, sin, sinh, sqrt, tan, tanh
93};
94#endif
95
Guido van Rossum93ad0df1997-05-13 21:00:42 +000096/* Special free list -- see comments for same code in intobject.c. */
97static PyFloatObject *free_list = NULL;
98#define BLOCK_SIZE 1000 /* 1K less typical malloc overhead */
99#define N_FLOATOBJECTS (BLOCK_SIZE / sizeof(PyFloatObject))
100
101static PyFloatObject *
102fill_free_list()
103{
104 PyFloatObject *p, *q;
105 p = PyMem_NEW(PyFloatObject, N_FLOATOBJECTS);
106 if (p == NULL)
107 return (PyFloatObject *)PyErr_NoMemory();
108 q = p + N_FLOATOBJECTS;
109 while (--q > p)
110 *(PyFloatObject **)q = q-1;
111 *(PyFloatObject **)q = NULL;
112 return p + N_FLOATOBJECTS - 1;
113}
114
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000115PyObject *
Guido van Rossum07e3a7e1995-02-27 10:13:37 +0000116#ifdef __SC__
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000117PyFloat_FromDouble(double fval)
Guido van Rossum07e3a7e1995-02-27 10:13:37 +0000118#else
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000119PyFloat_FromDouble(fval)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000120 double fval;
Guido van Rossum07e3a7e1995-02-27 10:13:37 +0000121#endif
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000122{
Guido van Rossum93ad0df1997-05-13 21:00:42 +0000123 register PyFloatObject *op;
124 if (free_list == NULL) {
125 if ((free_list = fill_free_list()) == NULL)
126 return NULL;
127 }
128 op = free_list;
129 free_list = *(PyFloatObject **)free_list;
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000130 op->ob_type = &PyFloat_Type;
Guido van Rossum2a9096b1990-10-21 22:15:08 +0000131 op->ob_fval = fval;
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000132 _Py_NewReference(op);
133 return (PyObject *) op;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000134}
135
Guido van Rossum234f9421993-06-17 12:35:49 +0000136static void
Guido van Rossum3132a5a1992-03-27 17:28:44 +0000137float_dealloc(op)
Guido van Rossum93ad0df1997-05-13 21:00:42 +0000138 PyFloatObject *op;
Guido van Rossum3132a5a1992-03-27 17:28:44 +0000139{
Guido van Rossum93ad0df1997-05-13 21:00:42 +0000140 *(PyFloatObject **)op = free_list;
141 free_list = op;
Guido van Rossum3132a5a1992-03-27 17:28:44 +0000142}
143
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000144double
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000145PyFloat_AsDouble(op)
146 PyObject *op;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000147{
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000148 PyNumberMethods *nb;
149 PyFloatObject *fo;
Guido van Rossumb6775db1994-08-01 11:34:53 +0000150 double val;
151
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000152 if (op && PyFloat_Check(op))
153 return PyFloat_AS_DOUBLE((PyFloatObject*) op);
Guido van Rossumb6775db1994-08-01 11:34:53 +0000154
155 if (op == NULL || (nb = op->ob_type->tp_as_number) == NULL ||
156 nb->nb_float == NULL) {
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000157 PyErr_BadArgument();
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000158 return -1;
159 }
Guido van Rossumb6775db1994-08-01 11:34:53 +0000160
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000161 fo = (PyFloatObject*) (*nb->nb_float) (op);
Guido van Rossumb6775db1994-08-01 11:34:53 +0000162 if (fo == NULL)
163 return -1;
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000164 if (!PyFloat_Check(fo)) {
165 PyErr_SetString(PyExc_TypeError,
166 "nb_float should return float object");
Guido van Rossumb6775db1994-08-01 11:34:53 +0000167 return -1;
168 }
169
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000170 val = PyFloat_AS_DOUBLE(fo);
171 Py_DECREF(fo);
Guido van Rossumb6775db1994-08-01 11:34:53 +0000172
173 return val;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000174}
175
176/* Methods */
177
Guido van Rossum27dec7e1991-06-04 19:42:53 +0000178void
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000179PyFloat_AsString(buf, v)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000180 char *buf;
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000181 PyFloatObject *v;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000182{
183 register char *cp;
184 /* Subroutine for float_repr and float_print.
185 We want float numbers to be recognizable as such,
186 i.e., they should contain a decimal point or an exponent.
187 However, %g may print the number as an integer;
188 in such cases, we append ".0" to the string. */
189 sprintf(buf, "%.12g", v->ob_fval);
190 cp = buf;
191 if (*cp == '-')
192 cp++;
193 for (; *cp != '\0'; cp++) {
194 /* Any non-digit means it's not an integer;
195 this takes care of NAN and INF as well. */
Guido van Rossum9fa2c111995-02-10 17:00:37 +0000196 if (!isdigit(Py_CHARMASK(*cp)))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000197 break;
198 }
199 if (*cp == '\0') {
200 *cp++ = '.';
201 *cp++ = '0';
202 *cp++ = '\0';
203 }
204}
205
Guido van Rossum3132a5a1992-03-27 17:28:44 +0000206/* ARGSUSED */
Guido van Rossum90933611991-06-07 16:10:43 +0000207static int
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000208float_print(v, fp, flags)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000209 PyFloatObject *v;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000210 FILE *fp;
Guido van Rossum3132a5a1992-03-27 17:28:44 +0000211 int flags; /* Not used but required by interface */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000212{
213 char buf[100];
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000214 PyFloat_AsString(buf, v);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000215 fputs(buf, fp);
Guido van Rossum90933611991-06-07 16:10:43 +0000216 return 0;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000217}
218
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000219static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000220float_repr(v)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000221 PyFloatObject *v;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000222{
223 char buf[100];
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000224 PyFloat_AsString(buf, v);
225 return PyString_FromString(buf);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000226}
227
228static int
229float_compare(v, w)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000230 PyFloatObject *v, *w;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000231{
232 double i = v->ob_fval;
233 double j = w->ob_fval;
234 return (i < j) ? -1 : (i > j) ? 1 : 0;
235}
236
Guido van Rossum9bfef441993-03-29 10:43:31 +0000237static long
238float_hash(v)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000239 PyFloatObject *v;
Guido van Rossum9bfef441993-03-29 10:43:31 +0000240{
241 double intpart, fractpart;
242 int expo;
243 long x;
244 /* This is designed so that Python numbers with the same
245 value hash to the same value, otherwise comparisons
246 of mapping keys will turn out weird */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000247
248#ifdef MPW /* MPW C modf expects pointer to extended as second argument */
249{
250 extended e;
251 fractpart = modf(v->ob_fval, &e);
252 intpart = e;
253}
254#else
Guido van Rossum9bfef441993-03-29 10:43:31 +0000255 fractpart = modf(v->ob_fval, &intpart);
Guido van Rossumb6775db1994-08-01 11:34:53 +0000256#endif
257
Guido van Rossum9bfef441993-03-29 10:43:31 +0000258 if (fractpart == 0.0) {
259 if (intpart > 0x7fffffffL || -intpart > 0x7fffffffL) {
260 /* Convert to long int and use its hash... */
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000261 PyObject *w = PyLong_FromDouble(v->ob_fval);
Guido van Rossum9bfef441993-03-29 10:43:31 +0000262 if (w == NULL)
263 return -1;
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000264 x = PyObject_Hash(w);
265 Py_DECREF(w);
Guido van Rossum9bfef441993-03-29 10:43:31 +0000266 return x;
267 }
268 x = (long)intpart;
269 }
270 else {
Guido van Rossum919cf1a1997-01-11 19:26:21 +0000271 /* Note -- if you change this code, also change the copy
272 in complexobject.c */
273 long hipart;
Guido van Rossum9bfef441993-03-29 10:43:31 +0000274 fractpart = frexp(fractpart, &expo);
Guido van Rossum919cf1a1997-01-11 19:26:21 +0000275 fractpart = fractpart * 2147483648.0; /* 2**31 */
276 hipart = (long)fractpart; /* Take the top 32 bits */
277 fractpart = (fractpart - (double)hipart) * 2147483648.0;
278 /* Get the next 32 bits */
279 x = hipart + (long)fractpart + (long)intpart + (expo << 15);
280 /* Combine everything */
Guido van Rossum9bfef441993-03-29 10:43:31 +0000281 }
282 if (x == -1)
283 x = -2;
284 return x;
285}
286
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000287static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000288float_add(v, w)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000289 PyFloatObject *v;
290 PyFloatObject *w;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000291{
Guido van Rossum09e6ad01997-02-14 22:54:21 +0000292 double result;
293 PyFPE_START_PROTECT("add", return 0)
294 result = v->ob_fval + w->ob_fval;
Guido van Rossum45b83911997-03-14 04:32:50 +0000295 PyFPE_END_PROTECT(result)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000296 return PyFloat_FromDouble(result);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000297}
298
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000299static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000300float_sub(v, w)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000301 PyFloatObject *v;
302 PyFloatObject *w;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000303{
Guido van Rossum09e6ad01997-02-14 22:54:21 +0000304 double result;
305 PyFPE_START_PROTECT("subtract", return 0)
306 result = v->ob_fval - w->ob_fval;
Guido van Rossum45b83911997-03-14 04:32:50 +0000307 PyFPE_END_PROTECT(result)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000308 return PyFloat_FromDouble(result);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000309}
310
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000311static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000312float_mul(v, w)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000313 PyFloatObject *v;
314 PyFloatObject *w;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000315{
Guido van Rossum09e6ad01997-02-14 22:54:21 +0000316 double result;
317
318 PyFPE_START_PROTECT("multiply", return 0)
319 result = v->ob_fval * w->ob_fval;
Guido van Rossum45b83911997-03-14 04:32:50 +0000320 PyFPE_END_PROTECT(result)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000321 return PyFloat_FromDouble(result);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000322}
323
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000324static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000325float_div(v, w)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000326 PyFloatObject *v;
327 PyFloatObject *w;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000328{
Guido van Rossum09e6ad01997-02-14 22:54:21 +0000329 double result;
Guido van Rossum56cd67a1992-01-26 18:16:35 +0000330 if (w->ob_fval == 0) {
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000331 PyErr_SetString(PyExc_ZeroDivisionError, "float division");
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000332 return NULL;
333 }
Guido van Rossum09e6ad01997-02-14 22:54:21 +0000334 PyFPE_START_PROTECT("divide", return 0)
335 result = v->ob_fval / w->ob_fval;
Guido van Rossum45b83911997-03-14 04:32:50 +0000336 PyFPE_END_PROTECT(result)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000337 return PyFloat_FromDouble(result);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000338}
339
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000340static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000341float_rem(v, w)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000342 PyFloatObject *v;
343 PyFloatObject *w;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000344{
Guido van Rossum56cd67a1992-01-26 18:16:35 +0000345 double vx, wx;
Guido van Rossum3132a5a1992-03-27 17:28:44 +0000346 double /* div, */ mod;
Guido van Rossum56cd67a1992-01-26 18:16:35 +0000347 wx = w->ob_fval;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000348 if (wx == 0.0) {
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000349 PyErr_SetString(PyExc_ZeroDivisionError, "float modulo");
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000350 return NULL;
351 }
Guido van Rossum09e6ad01997-02-14 22:54:21 +0000352 PyFPE_START_PROTECT("modulo", return 0)
Guido van Rossum56cd67a1992-01-26 18:16:35 +0000353 vx = v->ob_fval;
354 mod = fmod(vx, wx);
Guido van Rossum3132a5a1992-03-27 17:28:44 +0000355 /* div = (vx - mod) / wx; */
Guido van Rossum56cd67a1992-01-26 18:16:35 +0000356 if (wx*mod < 0) {
357 mod += wx;
Guido van Rossum3132a5a1992-03-27 17:28:44 +0000358 /* div -= 1.0; */
Guido van Rossum56cd67a1992-01-26 18:16:35 +0000359 }
Guido van Rossum45b83911997-03-14 04:32:50 +0000360 PyFPE_END_PROTECT(mod)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000361 return PyFloat_FromDouble(mod);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000362}
363
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000364static PyObject *
Guido van Rossumeba1b5e1991-05-05 20:07:00 +0000365float_divmod(v, w)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000366 PyFloatObject *v;
367 PyFloatObject *w;
Guido van Rossumeba1b5e1991-05-05 20:07:00 +0000368{
Guido van Rossum15ecff41991-10-20 20:16:45 +0000369 double vx, wx;
370 double div, mod;
Guido van Rossum56cd67a1992-01-26 18:16:35 +0000371 wx = w->ob_fval;
Guido van Rossum15ecff41991-10-20 20:16:45 +0000372 if (wx == 0.0) {
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000373 PyErr_SetString(PyExc_ZeroDivisionError, "float divmod()");
Guido van Rossum15ecff41991-10-20 20:16:45 +0000374 return NULL;
375 }
Guido van Rossum09e6ad01997-02-14 22:54:21 +0000376 PyFPE_START_PROTECT("divmod", return 0)
Guido van Rossum15ecff41991-10-20 20:16:45 +0000377 vx = v->ob_fval;
378 mod = fmod(vx, wx);
379 div = (vx - mod) / wx;
380 if (wx*mod < 0) {
381 mod += wx;
382 div -= 1.0;
383 }
Guido van Rossum45b83911997-03-14 04:32:50 +0000384 PyFPE_END_PROTECT(div)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000385 return Py_BuildValue("(dd)", div, mod);
Guido van Rossumeba1b5e1991-05-05 20:07:00 +0000386}
387
Guido van Rossum363078a1996-05-24 20:45:01 +0000388static double powu(x, n)
Guido van Rossum39739ea1996-01-12 01:22:56 +0000389 double x;
390 long n;
391{
392 double r = 1.;
393 double p = x;
394 long mask = 1;
395 while (mask > 0 && n >= mask) {
396 if (n & mask)
397 r *= p;
398 mask <<= 1;
399 p *= p;
400 }
401 return r;
402}
403
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000404static PyObject *
Guido van Rossum0b7d02a1994-08-12 12:52:35 +0000405float_pow(v, w, z)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000406 PyFloatObject *v;
407 PyObject *w;
408 PyFloatObject *z;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000409{
410 double iv, iw, ix;
Guido van Rossum39739ea1996-01-12 01:22:56 +0000411 long intw;
Guido van Rossum0b7d02a1994-08-12 12:52:35 +0000412 /* XXX Doesn't handle overflows if z!=None yet; it may never do so :(
413 * The z parameter is really only going to be useful for integers and
414 * long integers. Maybe something clever with logarithms could be done.
415 * [AMK]
416 */
Guido van Rossum39739ea1996-01-12 01:22:56 +0000417 iv = v->ob_fval;
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000418 iw = ((PyFloatObject *)w)->ob_fval;
Guido van Rossum39739ea1996-01-12 01:22:56 +0000419 intw = (long)iw;
Guido van Rossumc13bcca1996-08-16 20:42:57 +0000420 if (iw == intw && -10000 < intw && intw < 10000) {
Guido van Rossum39739ea1996-01-12 01:22:56 +0000421 /* Sort out special cases here instead of relying on pow() */
Guido van Rossum86c04c21996-08-09 20:50:14 +0000422 if (intw == 0) { /* x**0 is 1, even 0**0 */
Guido van Rossum09e6ad01997-02-14 22:54:21 +0000423 PyFPE_START_PROTECT("pow", return 0)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000424 if ((PyObject *)z!=Py_None) {
Guido van Rossum39739ea1996-01-12 01:22:56 +0000425 ix=fmod(1.0, z->ob_fval);
426 if (ix!=0 && z->ob_fval<0) ix+=z->ob_fval;
427 }
428 else ix=1.0;
Guido van Rossum45b83911997-03-14 04:32:50 +0000429 PyFPE_END_PROTECT(ix)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000430 return PyFloat_FromDouble(ix);
Guido van Rossum70d93461991-05-28 21:57:39 +0000431 }
Guido van Rossum86c04c21996-08-09 20:50:14 +0000432 errno = 0;
Guido van Rossum09e6ad01997-02-14 22:54:21 +0000433 PyFPE_START_PROTECT("pow", return 0)
Guido van Rossumc13bcca1996-08-16 20:42:57 +0000434 if (intw > 0)
435 ix = powu(iv, intw);
436 else
437 ix = 1./powu(iv, -intw);
Guido van Rossum45b83911997-03-14 04:32:50 +0000438 PyFPE_END_PROTECT(ix)
Guido van Rossum86c04c21996-08-09 20:50:14 +0000439 }
440 else {
441 /* Sort out special cases here instead of relying on pow() */
Guido van Rossum39739ea1996-01-12 01:22:56 +0000442 if (iv == 0.0) {
443 if (iw < 0.0) {
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000444 PyErr_SetString(PyExc_ValueError,
Guido van Rossumc13bcca1996-08-16 20:42:57 +0000445 "0.0 to a negative power");
Guido van Rossum39739ea1996-01-12 01:22:56 +0000446 return NULL;
447 }
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000448 return PyFloat_FromDouble(0.0);
Guido van Rossum39739ea1996-01-12 01:22:56 +0000449 }
Guido van Rossumc13bcca1996-08-16 20:42:57 +0000450 if (iv < 0.0) {
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000451 PyErr_SetString(PyExc_ValueError,
Guido van Rossumc13bcca1996-08-16 20:42:57 +0000452 "negative number to a float power");
453 return NULL;
454 }
Guido van Rossum39739ea1996-01-12 01:22:56 +0000455 errno = 0;
Guido van Rossum09e6ad01997-02-14 22:54:21 +0000456 PyFPE_START_PROTECT("pow", return 0)
Guido van Rossum39739ea1996-01-12 01:22:56 +0000457 ix = pow(iv, iw);
Guido van Rossum45b83911997-03-14 04:32:50 +0000458 PyFPE_END_PROTECT(ix)
Guido van Rossum70d93461991-05-28 21:57:39 +0000459 }
Guido van Rossum7fa52f81991-12-16 15:43:14 +0000460 CHECK(ix);
Guido van Rossum2a9096b1990-10-21 22:15:08 +0000461 if (errno != 0) {
462 /* XXX could it be another type of error? */
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000463 PyErr_SetFromErrno(PyExc_OverflowError);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000464 return NULL;
Guido van Rossum2a9096b1990-10-21 22:15:08 +0000465 }
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000466 if ((PyObject *)z!=Py_None) {
Guido van Rossum09e6ad01997-02-14 22:54:21 +0000467 PyFPE_START_PROTECT("pow", return 0)
Guido van Rossum0b7d02a1994-08-12 12:52:35 +0000468 ix=fmod(ix, z->ob_fval); /* XXX To Be Rewritten */
469 if ( ix!=0 &&
470 ((iv<0 && z->ob_fval>0) || (iv>0 && z->ob_fval<0) )) {
471 ix+=z->ob_fval;
472 }
Guido van Rossum45b83911997-03-14 04:32:50 +0000473 PyFPE_END_PROTECT(ix)
Guido van Rossum0b7d02a1994-08-12 12:52:35 +0000474 }
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000475 return PyFloat_FromDouble(ix);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000476}
477
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000478static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000479float_neg(v)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000480 PyFloatObject *v;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000481{
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000482 return PyFloat_FromDouble(-v->ob_fval);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000483}
484
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000485static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000486float_pos(v)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000487 PyFloatObject *v;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000488{
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000489 Py_INCREF(v);
490 return (PyObject *)v;
Guido van Rossumeba1b5e1991-05-05 20:07:00 +0000491}
492
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000493static PyObject *
Guido van Rossumeba1b5e1991-05-05 20:07:00 +0000494float_abs(v)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000495 PyFloatObject *v;
Guido van Rossumeba1b5e1991-05-05 20:07:00 +0000496{
497 if (v->ob_fval < 0)
498 return float_neg(v);
499 else
500 return float_pos(v);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000501}
502
Guido van Rossum50b4ef61991-05-14 11:57:01 +0000503static int
504float_nonzero(v)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000505 PyFloatObject *v;
Guido van Rossum50b4ef61991-05-14 11:57:01 +0000506{
507 return v->ob_fval != 0.0;
508}
509
Guido van Rossum234f9421993-06-17 12:35:49 +0000510static int
Guido van Rossume6eefc21992-08-14 12:06:52 +0000511float_coerce(pv, pw)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000512 PyObject **pv;
513 PyObject **pw;
Guido van Rossume6eefc21992-08-14 12:06:52 +0000514{
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000515 if (PyInt_Check(*pw)) {
516 long x = PyInt_AsLong(*pw);
517 *pw = PyFloat_FromDouble((double)x);
518 Py_INCREF(*pv);
Guido van Rossume6eefc21992-08-14 12:06:52 +0000519 return 0;
520 }
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000521 else if (PyLong_Check(*pw)) {
522 *pw = PyFloat_FromDouble(PyLong_AsDouble(*pw));
523 Py_INCREF(*pv);
Guido van Rossume6eefc21992-08-14 12:06:52 +0000524 return 0;
525 }
526 return 1; /* Can't do it */
527}
528
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000529static PyObject *
Guido van Rossum1899c2e1992-09-12 11:09:23 +0000530float_int(v)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000531 PyObject *v;
Guido van Rossum1899c2e1992-09-12 11:09:23 +0000532{
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000533 double x = PyFloat_AsDouble(v);
Guido van Rossum03093a21994-09-28 15:51:32 +0000534 if (x < 0 ? (x = ceil(x)) < (double)LONG_MIN
535 : (x = floor(x)) > (double)LONG_MAX) {
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000536 PyErr_SetString(PyExc_OverflowError,
537 "float too large to convert");
Guido van Rossum03093a21994-09-28 15:51:32 +0000538 return NULL;
539 }
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000540 return PyInt_FromLong((long)x);
Guido van Rossum1899c2e1992-09-12 11:09:23 +0000541}
542
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000543static PyObject *
Guido van Rossum1899c2e1992-09-12 11:09:23 +0000544float_long(v)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000545 PyObject *v;
Guido van Rossum1899c2e1992-09-12 11:09:23 +0000546{
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000547 double x = PyFloat_AsDouble(v);
548 return PyLong_FromDouble(x);
Guido van Rossum1899c2e1992-09-12 11:09:23 +0000549}
550
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000551static PyObject *
Guido van Rossum1899c2e1992-09-12 11:09:23 +0000552float_float(v)
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000553 PyObject *v;
Guido van Rossum1899c2e1992-09-12 11:09:23 +0000554{
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000555 Py_INCREF(v);
Guido van Rossum1899c2e1992-09-12 11:09:23 +0000556 return v;
557}
558
559
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000560static PyNumberMethods float_as_number = {
Guido van Rossumb6775db1994-08-01 11:34:53 +0000561 (binaryfunc)float_add, /*nb_add*/
562 (binaryfunc)float_sub, /*nb_subtract*/
563 (binaryfunc)float_mul, /*nb_multiply*/
564 (binaryfunc)float_div, /*nb_divide*/
565 (binaryfunc)float_rem, /*nb_remainder*/
566 (binaryfunc)float_divmod, /*nb_divmod*/
Guido van Rossum0b7d02a1994-08-12 12:52:35 +0000567 (ternaryfunc)float_pow, /*nb_power*/
Guido van Rossumb6775db1994-08-01 11:34:53 +0000568 (unaryfunc)float_neg, /*nb_negative*/
569 (unaryfunc)float_pos, /*nb_positive*/
570 (unaryfunc)float_abs, /*nb_absolute*/
571 (inquiry)float_nonzero, /*nb_nonzero*/
Guido van Rossum27acb331991-10-24 14:55:28 +0000572 0, /*nb_invert*/
573 0, /*nb_lshift*/
574 0, /*nb_rshift*/
575 0, /*nb_and*/
576 0, /*nb_xor*/
577 0, /*nb_or*/
Guido van Rossumb6775db1994-08-01 11:34:53 +0000578 (coercion)float_coerce, /*nb_coerce*/
579 (unaryfunc)float_int, /*nb_int*/
580 (unaryfunc)float_long, /*nb_long*/
581 (unaryfunc)float_float, /*nb_float*/
Guido van Rossum1899c2e1992-09-12 11:09:23 +0000582 0, /*nb_oct*/
583 0, /*nb_hex*/
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000584};
585
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000586PyTypeObject PyFloat_Type = {
587 PyObject_HEAD_INIT(&PyType_Type)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000588 0,
589 "float",
Guido van Rossumc0b618a1997-05-02 03:12:38 +0000590 sizeof(PyFloatObject),
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000591 0,
Guido van Rossumb6775db1994-08-01 11:34:53 +0000592 (destructor)float_dealloc, /*tp_dealloc*/
593 (printfunc)float_print, /*tp_print*/
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000594 0, /*tp_getattr*/
595 0, /*tp_setattr*/
Guido van Rossumb6775db1994-08-01 11:34:53 +0000596 (cmpfunc)float_compare, /*tp_compare*/
597 (reprfunc)float_repr, /*tp_repr*/
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000598 &float_as_number, /*tp_as_number*/
599 0, /*tp_as_sequence*/
600 0, /*tp_as_mapping*/
Guido van Rossumb6775db1994-08-01 11:34:53 +0000601 (hashfunc)float_hash, /*tp_hash*/
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000602};
Guido van Rossumfbbd57e1997-08-05 02:16:08 +0000603
604void
605PyFloat_Fini()
606{
607 /* XXX Alas, the free list is not easily and safely freeable */
608}