xref: /csrg-svn/lib/libm/common_source/floor.c (revision 34931)
1 /*
2  * Copyright (c) 1985 Regents of the University of California.
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms are permitted
6  * provided that the above copyright notice and this paragraph are
7  * duplicated in all such forms and that any documentation,
8  * advertising materials, and other materials related to such
9  * distribution and use acknowledge that the software was developed
10  * by the University of California, Berkeley.  The name of the
11  * University may not be used to endorse or promote products derived
12  * from this software without specific prior written permission.
13  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
14  * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
15  * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
16  *
17  * All recipients should regard themselves as participants in an ongoing
18  * research project and hence should feel obligated to report their
19  * experiences (good or bad) with these elementary function codes, using
20  * the sendbug(8) program, to the authors.
21  */
22 
23 #ifndef lint
24 static char sccsid[] = "@(#)floor.c	5.4 (Berkeley) 06/30/88";
25 #endif /* not lint */
26 
27 #if defined(vax)||defined(tahoe)
28 #ifdef vax
29 #define _0x(A,B)	0x/**/A/**/B
30 #else	/* vax */
31 #define _0x(A,B)	0x/**/B/**/A
32 #endif	/* vax */
33 static long Lx[] = {_0x(0000,5c00),_0x(0000,0000)};	/* 2**55 */
34 #define L *(double *) Lx
35 #else	/* defined(vax)||defined(tahoe) */
36 static double L = 4503599627370496.0E0;		/* 2**52 */
37 #endif	/* defined(vax)||defined(tahoe) */
38 
39 /*
40  * floor(x) := the largest integer no larger than x;
41  * ceil(x) := -floor(-x), for all real x.
42  *
43  * Note: Inexact will be signaled if x is not an integer, as is
44  *	customary for IEEE 754.  No other signal can be emitted.
45  */
46 double
47 floor(x)
48 double x;
49 {
50 	double y,ceil();
51 
52 	if (
53 #if !defined(vax)&&!defined(tahoe)
54 		x != x ||	/* NaN */
55 #endif	/* !defined(vax)&&!defined(tahoe) */
56 		x >= L)		/* already an even integer */
57 		return x;
58 	else if (x < (double)0)
59 		return -ceil(-x);
60 	else {			/* now 0 <= x < L */
61 		y = L+x;		/* destructive store must be forced */
62 		y -= L;			/* an integer, and |x-y| < 1 */
63 		return x < y ? y-(double)1 : y;
64 	}
65 }
66 
67 double
68 ceil(x)
69 double x;
70 {
71 	double y,floor();
72 
73 	if (
74 #if !defined(vax)&&!defined(tahoe)
75 		x != x ||	/* NaN */
76 #endif	/* !defined(vax)&&!defined(tahoe) */
77 		x >= L)		/* already an even integer */
78 		return x;
79 	else if (x < (double)0)
80 		return -floor(-x);
81 	else {			/* now 0 <= x < L */
82 		y = L+x;		/* destructive store must be forced */
83 		y -= L;			/* an integer, and |x-y| < 1 */
84 		return x > y ? y+(double)1 : y;
85 	}
86 }
87 
88 #ifndef national			/* rint() is in ./NATIONAL/support.s */
89 /*
90  * algorithm for rint(x) in pseudo-pascal form ...
91  *
92  * real rint(x): real x;
93  *	... delivers integer nearest x in direction of prevailing rounding
94  *	... mode
95  * const	L = (last consecutive integer)/2
96  * 	  = 2**55; for VAX D
97  * 	  = 2**52; for IEEE 754 Double
98  * real	s,t;
99  * begin
100  * 	if x != x then return x;		... NaN
101  * 	if |x| >= L then return x;		... already an integer
102  * 	s := copysign(L,x);
103  * 	t := x + s;				... = (x+s) rounded to integer
104  * 	return t - s
105  * end;
106  *
107  * Note: Inexact will be signaled if x is not an integer, as is
108  *	customary for IEEE 754.  No other signal can be emitted.
109  */
110 double
111 rint(x)
112 double x;
113 {
114 	double s,t,one = 1.0,copysign();
115 #if !defined(vax)&&!defined(tahoe)
116 	if (x != x)				/* NaN */
117 		return (x);
118 #endif	/* !defined(vax)&&!defined(tahoe) */
119 	if (copysign(x,one) >= L)		/* already an integer */
120 	    return (x);
121 	s = copysign(L,x);
122 	t = x + s;				/* x+s rounded to integer */
123 	return (t - s);
124 }
125 #endif	/* not national */
126