1 1.9 riastrad /* $NetBSD: n_floor.c,v 1.9 2024/05/08 02:08:11 riastradh Exp $ */ 2 1.1 ragge /* 3 1.1 ragge * Copyright (c) 1985, 1993 4 1.1 ragge * The Regents of the University of California. All rights reserved. 5 1.1 ragge * 6 1.1 ragge * Redistribution and use in source and binary forms, with or without 7 1.1 ragge * modification, are permitted provided that the following conditions 8 1.1 ragge * are met: 9 1.1 ragge * 1. Redistributions of source code must retain the above copyright 10 1.1 ragge * notice, this list of conditions and the following disclaimer. 11 1.1 ragge * 2. Redistributions in binary form must reproduce the above copyright 12 1.1 ragge * notice, this list of conditions and the following disclaimer in the 13 1.1 ragge * documentation and/or other materials provided with the distribution. 14 1.5 agc * 3. Neither the name of the University nor the names of its contributors 15 1.1 ragge * may be used to endorse or promote products derived from this software 16 1.1 ragge * without specific prior written permission. 17 1.1 ragge * 18 1.1 ragge * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 19 1.1 ragge * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 20 1.1 ragge * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 21 1.1 ragge * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 22 1.1 ragge * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 23 1.1 ragge * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 24 1.1 ragge * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 25 1.1 ragge * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 26 1.1 ragge * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 27 1.1 ragge * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 28 1.1 ragge * SUCH DAMAGE. 29 1.1 ragge */ 30 1.1 ragge 31 1.1 ragge #ifndef lint 32 1.2 ragge #if 0 33 1.1 ragge static char sccsid[] = "@(#)floor.c 8.1 (Berkeley) 6/4/93"; 34 1.2 ragge #endif 35 1.1 ragge #endif /* not lint */ 36 1.1 ragge 37 1.4 matt #define _LIBM_STATIC 38 1.1 ragge #include "mathimpl.h" 39 1.1 ragge 40 1.1 ragge vc(L, 4503599627370496.0E0 ,0000,5c00,0000,0000, 55, 1.0) /* 2**55 */ 41 1.1 ragge 42 1.1 ragge ic(L, 4503599627370496.0E0, 52, 1.0) /* 2**52 */ 43 1.1 ragge 44 1.1 ragge #ifdef vccast 45 1.1 ragge #define L vccast(L) 46 1.1 ragge #endif 47 1.1 ragge 48 1.9 riastrad __weak_alias(ceill, ceil) 49 1.9 riastrad __weak_alias(floorl, floor) 50 1.9 riastrad __weak_alias(truncl, trunc) 51 1.9 riastrad __weak_alias(rintl, rint) 52 1.8 martin 53 1.1 ragge /* 54 1.1 ragge * floor(x) := the largest integer no larger than x; 55 1.1 ragge * ceil(x) := -floor(-x), for all real x. 56 1.1 ragge * 57 1.1 ragge * Note: Inexact will be signaled if x is not an integer, as is 58 1.1 ragge * customary for IEEE 754. No other signal can be emitted. 59 1.1 ragge */ 60 1.1 ragge double 61 1.4 matt floor(double x) 62 1.1 ragge { 63 1.1 ragge volatile double y; 64 1.1 ragge 65 1.1 ragge if ( 66 1.3 matt #if !defined(__vax__)&&!defined(tahoe) 67 1.1 ragge x != x || /* NaN */ 68 1.3 matt #endif /* !defined(__vax__)&&!defined(tahoe) */ 69 1.1 ragge x >= L) /* already an even integer */ 70 1.1 ragge return x; 71 1.1 ragge else if (x < (double)0) 72 1.1 ragge return -ceil(-x); 73 1.1 ragge else { /* now 0 <= x < L */ 74 1.1 ragge y = L+x; /* destructive store must be forced */ 75 1.1 ragge y -= L; /* an integer, and |x-y| < 1 */ 76 1.1 ragge return x < y ? y-(double)1 : y; 77 1.1 ragge } 78 1.1 ragge } 79 1.1 ragge 80 1.6 mhitch float 81 1.6 mhitch floorf(float x) 82 1.6 mhitch { 83 1.6 mhitch return floor((double)x); 84 1.6 mhitch } 85 1.6 mhitch 86 1.1 ragge double 87 1.4 matt ceil(double x) 88 1.1 ragge { 89 1.1 ragge volatile double y; 90 1.1 ragge 91 1.1 ragge if ( 92 1.3 matt #if !defined(__vax__)&&!defined(tahoe) 93 1.1 ragge x != x || /* NaN */ 94 1.3 matt #endif /* !defined(__vax__)&&!defined(tahoe) */ 95 1.1 ragge x >= L) /* already an even integer */ 96 1.1 ragge return x; 97 1.1 ragge else if (x < (double)0) 98 1.1 ragge return -floor(-x); 99 1.1 ragge else { /* now 0 <= x < L */ 100 1.1 ragge y = L+x; /* destructive store must be forced */ 101 1.1 ragge y -= L; /* an integer, and |x-y| < 1 */ 102 1.1 ragge return x > y ? y+(double)1 : y; 103 1.1 ragge } 104 1.1 ragge } 105 1.1 ragge 106 1.6 mhitch float 107 1.6 mhitch ceilf(float x) 108 1.6 mhitch { 109 1.6 mhitch return ceil((double)x); 110 1.6 mhitch } 111 1.6 mhitch 112 1.1 ragge /* 113 1.1 ragge * algorithm for rint(x) in pseudo-pascal form ... 114 1.1 ragge * 115 1.1 ragge * real rint(x): real x; 116 1.1 ragge * ... delivers integer nearest x in direction of prevailing rounding 117 1.1 ragge * ... mode 118 1.1 ragge * const L = (last consecutive integer)/2 119 1.1 ragge * = 2**55; for VAX D 120 1.1 ragge * = 2**52; for IEEE 754 Double 121 1.1 ragge * real s,t; 122 1.1 ragge * begin 123 1.1 ragge * if x != x then return x; ... NaN 124 1.1 ragge * if |x| >= L then return x; ... already an integer 125 1.1 ragge * s := copysign(L,x); 126 1.1 ragge * t := x + s; ... = (x+s) rounded to integer 127 1.1 ragge * return t - s 128 1.1 ragge * end; 129 1.1 ragge * 130 1.1 ragge * Note: Inexact will be signaled if x is not an integer, as is 131 1.1 ragge * customary for IEEE 754. No other signal can be emitted. 132 1.1 ragge */ 133 1.1 ragge double 134 1.4 matt rint(double x) 135 1.1 ragge { 136 1.1 ragge double s; 137 1.1 ragge volatile double t; 138 1.1 ragge const double one = 1.0; 139 1.1 ragge 140 1.3 matt #if !defined(__vax__)&&!defined(tahoe) 141 1.1 ragge if (x != x) /* NaN */ 142 1.1 ragge return (x); 143 1.3 matt #endif /* !defined(__vax__)&&!defined(tahoe) */ 144 1.1 ragge if (copysign(x,one) >= L) /* already an integer */ 145 1.1 ragge return (x); 146 1.1 ragge s = copysign(L,x); 147 1.1 ragge t = x + s; /* x+s rounded to integer */ 148 1.1 ragge return (t - s); 149 1.1 ragge } 150 1.9 riastrad 151 1.9 riastrad float 152 1.9 riastrad rintf(float x) 153 1.9 riastrad { 154 1.9 riastrad return rint((double)x); 155 1.9 riastrad } 156 1.7 abs 157 1.7 abs long 158 1.7 abs lrint(double x) 159 1.7 abs { 160 1.7 abs double s; 161 1.7 abs volatile double t; 162 1.7 abs const double one = 1.0; 163 1.7 abs 164 1.7 abs #if !defined(__vax__)&&!defined(tahoe) 165 1.7 abs if (x != x) /* NaN */ 166 1.7 abs return (x); 167 1.7 abs #endif /* !defined(__vax__)&&!defined(tahoe) */ 168 1.7 abs if (copysign(x,one) >= L) /* already an integer */ 169 1.7 abs return (x); 170 1.7 abs s = copysign(L,x); 171 1.7 abs t = x + s; /* x+s rounded to integer */ 172 1.7 abs return (t - s); 173 1.7 abs } 174 1.7 abs 175 1.7 abs long long 176 1.7 abs llrint(double x) 177 1.7 abs { 178 1.7 abs double s; 179 1.7 abs volatile double t; 180 1.7 abs const double one = 1.0; 181 1.7 abs 182 1.7 abs #if !defined(__vax__)&&!defined(tahoe) 183 1.7 abs if (x != x) /* NaN */ 184 1.7 abs return (x); 185 1.7 abs #endif /* !defined(__vax__)&&!defined(tahoe) */ 186 1.7 abs if (copysign(x,one) >= L) /* already an integer */ 187 1.7 abs return (x); 188 1.7 abs s = copysign(L,x); 189 1.7 abs t = x + s; /* x+s rounded to integer */ 190 1.7 abs return (t - s); 191 1.7 abs } 192 1.7 abs 193 1.7 abs long 194 1.7 abs lrintf(float x) 195 1.7 abs { 196 1.7 abs float s; 197 1.7 abs volatile float t; 198 1.7 abs const float one = 1.0; 199 1.7 abs 200 1.7 abs #if !defined(__vax__)&&!defined(tahoe) 201 1.7 abs if (x != x) /* NaN */ 202 1.7 abs return (x); 203 1.7 abs #endif /* !defined(__vax__)&&!defined(tahoe) */ 204 1.7 abs if (copysign(x,one) >= L) /* already an integer */ 205 1.7 abs return (x); 206 1.7 abs s = copysign(L,x); 207 1.7 abs t = x + s; /* x+s rounded to integer */ 208 1.7 abs return (t - s); 209 1.7 abs } 210 1.7 abs 211 1.7 abs long long 212 1.7 abs llrintf(float x) 213 1.7 abs { 214 1.7 abs float s; 215 1.7 abs volatile float t; 216 1.7 abs const float one = 1.0; 217 1.7 abs 218 1.7 abs #if !defined(__vax__)&&!defined(tahoe) 219 1.7 abs if (x != x) /* NaN */ 220 1.7 abs return (x); 221 1.7 abs #endif /* !defined(__vax__)&&!defined(tahoe) */ 222 1.7 abs if (copysign(x,one) >= L) /* already an integer */ 223 1.7 abs return (x); 224 1.7 abs s = copysign(L,x); 225 1.7 abs t = x + s; /* x+s rounded to integer */ 226 1.7 abs return (t - s); 227 1.7 abs } 228 1.8 martin 229 1.8 martin double 230 1.8 martin trunc(double x) 231 1.8 martin { 232 1.8 martin return x < 0 ? ceil(x) : floor(x); 233 1.8 martin } 234 1.8 martin 235 1.8 martin float 236 1.8 martin truncf(float x) 237 1.8 martin { 238 1.8 martin return x < 0 ? ceilf(x) : floorf(x); 239 1.8 martin } 240