From 4b2da9c371d02367607d33358d88ac5996fb5ea0 Mon Sep 17 00:00:00 2001 From: PulkoMandy Date: Sun, 3 Mar 2019 20:49:32 +0100 Subject: [PATCH] glibc: cleanup long double support - Add 128 bit long double support from current glibc and a few headers they need - Move the existing 80 bit float support in a sub directory of generic, it is not universal to all archs (see file added in docs/develop/arch). Also include some new .h files for x86 that are needed after these changes (from newer versions of the glibc). - Adjust Jamfiles for m68k, x86 and x86_64 to use the 80bit format - Do not adjust arm jamfiles, it was wrongly using 80bit long double and should be fixed to use 64bit instead (which means the double functions can be used with aliases) - Do not adjust powerpc jamfiles, because it uses yet another format and we build it without long double support anyways. Note that I moved only the files that were creating compile errors, quite likely more of the s_* and e_* files need to be moved to the specific directories, see glibc list here: https://sourceware.org/git/?p=glibc.git;a=tree;f=sysdeps/ieee754/ldbl-128 https://sourceware.org/git/?p=glibc.git;a=tree;f=sysdeps/ieee754/ldbl-96 Change-Id: Ic2d8a454ba9a3b99638e4fbb63daf02df0fea403 Reviewed-on: https://review.haiku-os.org/c/1143 Reviewed-by: waddlesplash --- docs/develop/arch/long double.md | 48 +++ src/system/libroot/os/arch/sparc/Jamfile | 8 + .../libroot/posix/glibc/arch/generic/e_sqrt.c | 141 ++++++++ .../posix/glibc/arch/generic/e_sqrtf.c | 86 +++++ .../posix/glibc/arch/generic/fraiseexcpt.c | 66 ---- .../arch/generic/longdouble/128bit/e_atan2l.c | 122 +++++++ .../arch/generic/longdouble/128bit/e_hypotl.c | 141 ++++++++ .../arch/generic/longdouble/128bit/s_atanl.c | 255 ++++++++++++++ .../generic/longdouble/128bit/s_copysignl.c | 40 +++ .../generic/longdouble/128bit/s_fpclassifyl.c | 44 +++ .../arch/generic/longdouble/128bit/s_isinfl.c | 29 ++ .../arch/generic/longdouble/128bit/s_isnanl.c | 38 ++ .../longdouble/128bit/s_issignalingl.c | 46 +++ .../generic/longdouble/128bit/s_signbitl.c | 27 ++ .../generic/{ => longdouble/80bit}/e_atan2l.c | 1 + .../generic/{ => longdouble/80bit}/e_hypotl.c | 0 .../generic/{ => longdouble/80bit}/s_atanl.c | 0 .../{ => longdouble/80bit}/s_copysignl.c | 0 .../{ => longdouble/80bit}/s_signbitl.c | 0 .../libroot/posix/glibc/arch/m68k/Jamfile | 4 +- .../libroot/posix/glibc/arch/sparc/Jamfile | 67 +++- .../libroot/posix/glibc/arch/sparc/add_n.S | 57 +++ .../libroot/posix/glibc/arch/sparc/addmul_1.S | 83 +++++ .../libroot/posix/glibc/arch/sparc/e_sqrtl.c | 31 ++ .../posix/glibc/arch/sparc/fegetround.c | 32 ++ .../posix/glibc/arch/sparc/feholdexcpt.c | 14 + .../libroot/posix/glibc/arch/sparc/fesetenv.c | 55 +++ .../posix/glibc/arch/sparc/fesetround.c | 39 +++ .../posix/glibc/arch/sparc/fraiseexcpt.c | 91 +++++ .../libroot/posix/glibc/arch/sparc/lshift.S | 95 +++++ .../libroot/posix/glibc/arch/sparc/mul_1.S | 82 +++++ .../libroot/posix/glibc/arch/sparc/rshift.S | 92 +++++ .../libroot/posix/glibc/arch/sparc/s_isnan.S | 33 ++ .../libroot/posix/glibc/arch/sparc/s_isnanf.S | 32 ++ .../libroot/posix/glibc/arch/sparc/sub_n.S | 54 +++ .../libroot/posix/glibc/arch/sparc/submul_1.S | 82 +++++ .../libroot/posix/glibc/arch/x86/Jamfile | 4 +- .../libroot/posix/glibc/arch/x86_64/Jamfile | 4 +- .../include/arch/generic/bits/floatn-common.h | 329 ++++++++++++++++++ .../posix/glibc/include/arch/generic/dla.h | 183 ++++++++++ .../include/arch/generic/libm-alias-ldouble.h | 65 ++++ .../include/arch/generic/nan-high-order-bit.h | 27 ++ .../glibc/include/arch/sparc/bits/fenv.h | 88 +++-- .../glibc/include/arch/sparc/bits/floatn.h | 97 ++++++ .../glibc/include/arch/sparc/bits/hwcap.h | 51 +++ .../include/arch/sparc/bits/long-double.h | 20 ++ .../posix/glibc/include/arch/sparc/config.h | 235 +++++++++++++ .../glibc/include/arch/sparc/fenv_private.h | 172 +++++++++ .../glibc/include/arch/sparc/math-underflow.h | 79 +++++ .../glibc/include/arch/sparc/math_ldbl.h | 120 ++++++- .../posix/glibc/include/arch/sparc/sysdep.h | 87 +++++ .../glibc/include/arch/x86/bits/floatn.h | 121 +++++++ .../posix/glibc/include/bits/long-double.h | 39 +++ src/system/libroot/posix/glibc/math/fenv.h | 10 + .../libroot/posix/glibc/math/math-barriers.h | 37 ++ src/system/libroot/posix/glibc/math/math.h | 84 +++++ .../libroot/posix/glibc/math/w_sqrtl_compat.c | 31 ++ 57 files changed, 3782 insertions(+), 136 deletions(-) create mode 100644 docs/develop/arch/long double.md create mode 100644 src/system/libroot/posix/glibc/arch/generic/e_sqrt.c create mode 100644 src/system/libroot/posix/glibc/arch/generic/e_sqrtf.c delete mode 100644 src/system/libroot/posix/glibc/arch/generic/fraiseexcpt.c create mode 100644 src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/e_atan2l.c create mode 100644 src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/e_hypotl.c create mode 100644 src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_atanl.c create mode 100644 src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_copysignl.c create mode 100644 src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_fpclassifyl.c create mode 100644 src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_isinfl.c create mode 100644 src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_isnanl.c create mode 100644 src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_issignalingl.c create mode 100644 src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_signbitl.c rename src/system/libroot/posix/glibc/arch/generic/{ => longdouble/80bit}/e_atan2l.c (99%) rename src/system/libroot/posix/glibc/arch/generic/{ => longdouble/80bit}/e_hypotl.c (100%) rename src/system/libroot/posix/glibc/arch/generic/{ => longdouble/80bit}/s_atanl.c (100%) rename src/system/libroot/posix/glibc/arch/generic/{ => longdouble/80bit}/s_copysignl.c (100%) rename src/system/libroot/posix/glibc/arch/generic/{ => longdouble/80bit}/s_signbitl.c (100%) create mode 100644 src/system/libroot/posix/glibc/arch/sparc/add_n.S create mode 100644 src/system/libroot/posix/glibc/arch/sparc/addmul_1.S create mode 100644 src/system/libroot/posix/glibc/arch/sparc/e_sqrtl.c create mode 100644 src/system/libroot/posix/glibc/arch/sparc/fegetround.c create mode 100644 src/system/libroot/posix/glibc/arch/sparc/feholdexcpt.c create mode 100644 src/system/libroot/posix/glibc/arch/sparc/fesetenv.c create mode 100644 src/system/libroot/posix/glibc/arch/sparc/fesetround.c create mode 100644 src/system/libroot/posix/glibc/arch/sparc/fraiseexcpt.c create mode 100644 src/system/libroot/posix/glibc/arch/sparc/lshift.S create mode 100644 src/system/libroot/posix/glibc/arch/sparc/mul_1.S create mode 100644 src/system/libroot/posix/glibc/arch/sparc/rshift.S create mode 100644 src/system/libroot/posix/glibc/arch/sparc/s_isnan.S create mode 100644 src/system/libroot/posix/glibc/arch/sparc/s_isnanf.S create mode 100644 src/system/libroot/posix/glibc/arch/sparc/sub_n.S create mode 100644 src/system/libroot/posix/glibc/arch/sparc/submul_1.S create mode 100644 src/system/libroot/posix/glibc/include/arch/generic/bits/floatn-common.h create mode 100644 src/system/libroot/posix/glibc/include/arch/generic/dla.h create mode 100644 src/system/libroot/posix/glibc/include/arch/generic/libm-alias-ldouble.h create mode 100644 src/system/libroot/posix/glibc/include/arch/generic/nan-high-order-bit.h create mode 100644 src/system/libroot/posix/glibc/include/arch/sparc/bits/floatn.h create mode 100644 src/system/libroot/posix/glibc/include/arch/sparc/bits/hwcap.h create mode 100644 src/system/libroot/posix/glibc/include/arch/sparc/bits/long-double.h create mode 100644 src/system/libroot/posix/glibc/include/arch/sparc/fenv_private.h create mode 100644 src/system/libroot/posix/glibc/include/arch/sparc/math-underflow.h create mode 100644 src/system/libroot/posix/glibc/include/arch/sparc/sysdep.h create mode 100644 src/system/libroot/posix/glibc/include/arch/x86/bits/floatn.h create mode 100644 src/system/libroot/posix/glibc/include/bits/long-double.h create mode 100644 src/system/libroot/posix/glibc/math/math-barriers.h create mode 100644 src/system/libroot/posix/glibc/math/w_sqrtl_compat.c diff --git a/docs/develop/arch/long double.md b/docs/develop/arch/long double.md new file mode 100644 index 0000000000..46ea470a61 --- /dev/null +++ b/docs/develop/arch/long double.md @@ -0,0 +1,48 @@ +Notes on long double support +============================ + +The "long double" type is different on each architecture. Depending on the +available hardware and ABI conventions, performance compromises, etc, there +may be many implementations of it. Here is a summary for our convenience. + +128-bit IEEE +------------ + +Platforms: Sparc, ARM64, RISC-V + +This is the standard long double type from IEEE754. It has 1 sign bit, +15 exponent bit, and 112 fractional part bits. It is the natural extension +of the 64bit double. + +Sparc specifies this type in their ABI but no implementation actually has +the instructions, they instead trigger a trap which would software emulate +them. However, gcc short circuits this by default and calls C library +support functions directly. + +64-bit IEEE +----------- + +Platforms: ARM + +This is the same representation as plain "double". ARM uses this for simplicity. + +80-bit +------ + +Platform: x86, x86\_64, m68k + +This intermediate format is used by x86 CPUs internally. It may end up being +faster than plain double there. It consists of a 64bit fractional part, 15 +exponent bits, and 1 sign bit. This is convenient because the fractional part +is a relatively easy to handle 64bit number. + +m68k uses a similar format, but padded to 96 bits (the extra 16 bits are unused). + +double double +------------- + +Platforms: PowerPC? + +This is also a 128bit type, but the representation is just two 64bit doubles. +The value is the sum of the two halves. This format allows faster emulation +than a "true" 128bit long double, and the precision is almost as good. diff --git a/src/system/libroot/os/arch/sparc/Jamfile b/src/system/libroot/os/arch/sparc/Jamfile index d33938b2e0..725be98c7d 100644 --- a/src/system/libroot/os/arch/sparc/Jamfile +++ b/src/system/libroot/os/arch/sparc/Jamfile @@ -13,8 +13,16 @@ for architectureObject in [ MultiArchSubDirSetup sparc ] { SEARCH_SOURCE += [ FDirName $(SUBDIR) $(DOTDOT) generic ] ; MergeObject <$(architecture)>os_arch_$(TARGET_ARCH).o : + stack_frame.c + system_time.c + thread.c + time.c tls.c + softfloat.c + fpu_add.c fpu_compare.c fpu_div.c fpu_explode.c fpu_implode.c + fpu_mul.c fpu_reg.S fpu_sqrt.c fpu_subr.c + generic_atomic.cpp generic_system_time_nsecs.cpp ; diff --git a/src/system/libroot/posix/glibc/arch/generic/e_sqrt.c b/src/system/libroot/posix/glibc/arch/generic/e_sqrt.c new file mode 100644 index 0000000000..ea1f05e69a --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/generic/e_sqrt.c @@ -0,0 +1,141 @@ +/* + * IBM Accurate Mathematical Library + * written by International Business Machines Corp. + * Copyright (C) 2001-2019 Free Software Foundation, Inc. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, see . + */ +/*********************************************************************/ +/* MODULE_NAME: uroot.c */ +/* */ +/* FUNCTION: usqrt */ +/* */ +/* FILES NEEDED: dla.h endian.h mydefs.h */ +/* uroot.tbl */ +/* */ +/* An ultimate sqrt routine. Given an IEEE double machine number x */ +/* it computes the correctly rounded (to nearest) value of square */ +/* root of x. */ +/* Assumption: Machine arithmetic operations are performed in */ +/* round to nearest mode of IEEE 754 standard. */ +/* */ +/*********************************************************************/ + +#include "endian.h" +#include "mydefs.h" +#include +#include "MathLib.h" +#include "root.tbl" +#include +#include +#include + +/*********************************************************************/ +/* An ultimate sqrt routine. Given an IEEE double machine number x */ +/* it computes the correctly rounded (to nearest) value of square */ +/* root of x. */ +/*********************************************************************/ +double +__ieee754_sqrt (double x) +{ + static const double + rt0 = 9.99999999859990725855365213134618E-01, + rt1 = 4.99999999495955425917856814202739E-01, + rt2 = 3.75017500867345182581453026130850E-01, + rt3 = 3.12523626554518656309172508769531E-01; + static const double big = 134217728.0; + double y, t, del, res, res1, hy, z, zz, p, hx, tx, ty, s; + mynumber a, c = { { 0, 0 } }; + int4 k; + + a.x = x; + k = a.i[HIGH_HALF]; + a.i[HIGH_HALF] = (k & 0x001fffff) | 0x3fe00000; + t = inroot[(k & 0x001fffff) >> 14]; + s = a.x; + /*----------------- 2^-1022 <= | x |< 2^1024 -----------------*/ + if (k > 0x000fffff && k < 0x7ff00000) + { + int rm = __fegetround (); + fenv_t env; + libc_feholdexcept_setround (&env, FE_TONEAREST); + double ret; + y = 1.0 - t * (t * s); + t = t * (rt0 + y * (rt1 + y * (rt2 + y * rt3))); + c.i[HIGH_HALF] = 0x20000000 + ((k & 0x7fe00000) >> 1); + y = t * s; + hy = (y + big) - big; + del = 0.5 * t * ((s - hy * hy) - (y - hy) * (y + hy)); + res = y + del; + if (res == (res + 1.002 * ((y - res) + del))) + ret = res * c.x; + else + { + res1 = res + 1.5 * ((y - res) + del); + EMULV (res, res1, z, zz, p, hx, tx, hy, ty); /* (z+zz)=res*res1 */ + res = ((((z - s) + zz) < 0) ? max (res, res1) : + min (res, res1)); + ret = res * c.x; + } + math_force_eval (ret); + libc_fesetenv (&env); + double dret = x / ret; + if (dret != ret) + { + double force_inexact = 1.0 / 3.0; + math_force_eval (force_inexact); + /* The square root is inexact, ret is the round-to-nearest + value which may need adjusting for other rounding + modes. */ + switch (rm) + { +#ifdef FE_UPWARD + case FE_UPWARD: + if (dret > ret) + ret = (res + 0x1p-1022) * c.x; + break; +#endif + +#ifdef FE_DOWNWARD + case FE_DOWNWARD: +#endif +#ifdef FE_TOWARDZERO + case FE_TOWARDZERO: +#endif +#if defined FE_DOWNWARD || defined FE_TOWARDZERO + if (dret < ret) + ret = (res - 0x1p-1022) * c.x; + break; +#endif + + default: + break; + } + } + /* Otherwise (x / ret == ret), either the square root was exact or + the division was inexact. */ + return ret; + } + else + { + if ((k & 0x7ff00000) == 0x7ff00000) + return x * x + x; /* sqrt(NaN)=NaN, sqrt(+inf)=+inf, sqrt(-inf)=sNaN */ + if (x == 0) + return x; /* sqrt(+0)=+0, sqrt(-0)=-0 */ + if (k < 0) + return (x - x) / (x - x); /* sqrt(-ve)=sNaN */ + return 0x1p-256 * __ieee754_sqrt (x * 0x1p512); + } +} +strong_alias (__ieee754_sqrt, __sqrt_finite) diff --git a/src/system/libroot/posix/glibc/arch/generic/e_sqrtf.c b/src/system/libroot/posix/glibc/arch/generic/e_sqrtf.c new file mode 100644 index 0000000000..6025da19cf --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/generic/e_sqrtf.c @@ -0,0 +1,86 @@ +/* e_sqrtf.c -- float version of e_sqrt.c. + * Conversion to float by Ian Lance Taylor, Cygnus Support, ian@cygnus.com. + */ + +/* + * ==================================================== + * Copyright (C) 1993 by Sun Microsystems, Inc. All rights reserved. + * + * Developed at SunPro, a Sun Microsystems, Inc. business. + * Permission to use, copy, modify, and distribute this + * software is freely granted, provided that this notice + * is preserved. + * ==================================================== + */ + +#include +#include + +static const float one = 1.0, tiny=1.0e-30; + +float +__ieee754_sqrtf(float x) +{ + float z; + int32_t sign = (int)0x80000000; + int32_t ix,s,q,m,t,i; + uint32_t r; + + GET_FLOAT_WORD(ix,x); + + /* take care of Inf and NaN */ + if((ix&0x7f800000)==0x7f800000) { + return x*x+x; /* sqrt(NaN)=NaN, sqrt(+inf)=+inf + sqrt(-inf)=sNaN */ + } + /* take care of zero */ + if(ix<=0) { + if((ix&(~sign))==0) return x;/* sqrt(+-0) = +-0 */ + else if(ix<0) + return (x-x)/(x-x); /* sqrt(-ve) = sNaN */ + } + /* normalize x */ + m = (ix>>23); + if(m==0) { /* subnormal x */ + for(i=0;(ix&0x00800000)==0;i++) ix<<=1; + m -= i-1; + } + m -= 127; /* unbias exponent */ + ix = (ix&0x007fffff)|0x00800000; + if(m&1) /* odd m, double x to make it even */ + ix += ix; + m >>= 1; /* m = [m/2] */ + + /* generate sqrt(x) bit by bit */ + ix += ix; + q = s = 0; /* q = sqrt(x) */ + r = 0x01000000; /* r = moving bit from right to left */ + + while(r!=0) { + t = s+r; + if(t<=ix) { + s = t+r; + ix -= t; + q += r; + } + ix += ix; + r>>=1; + } + + /* use floating add to find out rounding direction */ + if(ix!=0) { + z = one-tiny; /* trigger inexact flag */ + if (z>=one) { + z = one+tiny; + if (z>one) + q += 2; + else + q += (q&1); + } + } + ix = (q>>1)+0x3f000000; + ix += (m <<23); + SET_FLOAT_WORD(z,ix); + return z; +} +strong_alias (__ieee754_sqrtf, __sqrtf_finite) diff --git a/src/system/libroot/posix/glibc/arch/generic/fraiseexcpt.c b/src/system/libroot/posix/glibc/arch/generic/fraiseexcpt.c deleted file mode 100644 index dbe36c3d5a..0000000000 --- a/src/system/libroot/posix/glibc/arch/generic/fraiseexcpt.c +++ /dev/null @@ -1,66 +0,0 @@ -/* Raise given exceptions. - Copyright (C) 1997,99,2000,01,02 Free Software Foundation, Inc. - This file is part of the GNU C Library. - - The GNU C Library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - The GNU C Library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with the GNU C Library; if not, write to the Free - Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA - 02111-1307 USA. */ - -#include -#include - -#undef feraiseexcept -int -__feraiseexcept (int excepts) -{ - fenv_union_t u; - - /* Raise exceptions represented by EXCEPTS. It is the responsibility of - the OS to ensure that if multiple exceptions occur they are fed back - to this process in the proper way; this can happen in hardware, - anyway (in particular, inexact with overflow or underflow). */ - - /* Get the current state. */ - u.fenv = fegetenv_register (); - - /* Add the exceptions */ - u.l[1] = (u.l[1] - | (excepts & FPSCR_STICKY_BITS) - /* Turn FE_INVALID into FE_INVALID_SOFTWARE. */ - | (excepts >> ((31 - FPSCR_VX) - (31 - FPSCR_VXSOFT)) - & FE_INVALID_SOFTWARE)); - - /* Store the new status word (along with the rest of the environment), - triggering any appropriate exceptions. */ - fesetenv_register (u.fenv); - - if ((excepts & FE_INVALID) - /* For some reason, some PowerPC chips (the 601, in particular) - don't have FE_INVALID_SOFTWARE implemented. Detect this - case and raise FE_INVALID_SNAN instead. */ - && !fetestexcept (FE_INVALID)) - set_fpscr_bit (FPSCR_VXSNAN); - - /* Success. */ - return 0; -} - -#include -#if SHLIB_COMPAT (libm, GLIBC_2_1, GLIBC_2_2) -strong_alias (__feraiseexcept, __old_feraiseexcept) -compat_symbol (libm, BP_SYM (__old_feraiseexcept), BP_SYM (feraiseexcept), GLIBC_2_1); -#endif - -libm_hidden_ver (__feraiseexcept, feraiseexcept) -versioned_symbol (libm, BP_SYM (__feraiseexcept), BP_SYM (feraiseexcept), GLIBC_2_2); diff --git a/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/e_atan2l.c b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/e_atan2l.c new file mode 100644 index 0000000000..8b4afa4bd5 --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/e_atan2l.c @@ -0,0 +1,122 @@ +/* e_atan2l.c -- long double version of e_atan2.c. + * Conversion to long double by Jakub Jelinek, jj@ultra.linux.cz. + */ + +/* + * ==================================================== + * Copyright (C) 1993 by Sun Microsystems, Inc. All rights reserved. + * + * Developed at SunPro, a Sun Microsystems, Inc. business. + * Permission to use, copy, modify, and distribute this + * software is freely granted, provided that this notice + * is preserved. + * ==================================================== + */ + +/* __ieee754_atan2l(y,x) + * Method : + * 1. Reduce y to positive by atan2l(y,x)=-atan2l(-y,x). + * 2. Reduce x to positive by (if x and y are unexceptional): + * ARG (x+iy) = arctan(y/x) ... if x > 0, + * ARG (x+iy) = pi - arctan[y/(-x)] ... if x < 0, + * + * Special cases: + * + * ATAN2((anything), NaN ) is NaN; + * ATAN2(NAN , (anything) ) is NaN; + * ATAN2(+-0, +(anything but NaN)) is +-0 ; + * ATAN2(+-0, -(anything but NaN)) is +-pi ; + * ATAN2(+-(anything but 0 and NaN), 0) is +-pi/2; + * ATAN2(+-(anything but INF and NaN), +INF) is +-0 ; + * ATAN2(+-(anything but INF and NaN), -INF) is +-pi; + * ATAN2(+-INF,+INF ) is +-pi/4 ; + * ATAN2(+-INF,-INF ) is +-3pi/4; + * ATAN2(+-INF, (anything but,0,NaN, and INF)) is +-pi/2; + * + * Constants: + * The hexadecimal values are the intended ones for the following + * constants. The decimal values may be used, provided that the + * compiler will convert from decimal to binary accurately enough + * to produce the hexadecimal values shown. + */ + +#include +#include + +static const _Float128 +tiny = L(1.0e-4900), +zero = 0.0, +pi_o_4 = L(7.85398163397448309615660845819875699e-01), /* 3ffe921fb54442d18469898cc51701b8 */ +pi_o_2 = L(1.57079632679489661923132169163975140e+00), /* 3fff921fb54442d18469898cc51701b8 */ +pi = L(3.14159265358979323846264338327950280e+00), /* 4000921fb54442d18469898cc51701b8 */ +pi_lo = L(8.67181013012378102479704402604335225e-35); /* 3f8dcd129024e088a67cc74020bbea64 */ + +_Float128 +__ieee754_atan2l(_Float128 y, _Float128 x) +{ + _Float128 z; + int64_t k,m,hx,hy,ix,iy; + uint64_t lx,ly; + + GET_LDOUBLE_WORDS64(hx,lx,x); + ix = hx&0x7fffffffffffffffLL; + GET_LDOUBLE_WORDS64(hy,ly,y); + iy = hy&0x7fffffffffffffffLL; + if(((ix|((lx|-lx)>>63))>0x7fff000000000000LL)|| + ((iy|((ly|-ly)>>63))>0x7fff000000000000LL)) /* x or y is NaN */ + return x+y; + if(((hx-0x3fff000000000000LL)|lx)==0) return __atanl(y); /* x=1.0L */ + m = ((hy>>63)&1)|((hx>>62)&2); /* 2*sign(x)+sign(y) */ + + /* when y = 0 */ + if((iy|ly)==0) { + switch(m) { + case 0: + case 1: return y; /* atan(+-0,+anything)=+-0 */ + case 2: return pi+tiny;/* atan(+0,-anything) = pi */ + case 3: return -pi-tiny;/* atan(-0,-anything) =-pi */ + } + } + /* when x = 0 */ + if((ix|lx)==0) return (hy<0)? -pi_o_2-tiny: pi_o_2+tiny; + + /* when x is INF */ + if(ix==0x7fff000000000000LL) { + if(iy==0x7fff000000000000LL) { + switch(m) { + case 0: return pi_o_4+tiny;/* atan(+INF,+INF) */ + case 1: return -pi_o_4-tiny;/* atan(-INF,+INF) */ + case 2: return 3*pi_o_4+tiny;/*atan(+INF,-INF)*/ + case 3: return -3*pi_o_4-tiny;/*atan(-INF,-INF)*/ + } + } else { + switch(m) { + case 0: return zero ; /* atan(+...,+INF) */ + case 1: return -zero ; /* atan(-...,+INF) */ + case 2: return pi+tiny ; /* atan(+...,-INF) */ + case 3: return -pi-tiny ; /* atan(-...,-INF) */ + } + } + } + /* when y is INF */ + if(iy==0x7fff000000000000LL) return (hy<0)? -pi_o_2-tiny: pi_o_2+tiny; + + /* compute y/x */ + k = (iy-ix)>>48; + if(k > 120) z=pi_o_2+L(0.5)*pi_lo; /* |y/x| > 2**120 */ + else if(hx<0&&k<-120) z=0; /* |y|/x < -2**120 */ + else z=__atanl(fabsl(y/x)); /* safe to do y/x */ + switch (m) { + case 0: return z ; /* atan(+,+) */ + case 1: { + uint64_t zh; + GET_LDOUBLE_MSW64(zh,z); + SET_LDOUBLE_MSW64(z,zh ^ 0x8000000000000000ULL); + } + return z ; /* atan(-,+) */ + case 2: return pi-(z-pi_lo);/* atan(+,-) */ + default: /* case 3 */ + return (z-pi_lo)-pi;/* atan(-,-) */ + } +} +strong_alias (__ieee754_atan2l, __atan2l_finite) diff --git a/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/e_hypotl.c b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/e_hypotl.c new file mode 100644 index 0000000000..7bafd4ae29 --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/e_hypotl.c @@ -0,0 +1,141 @@ +/* e_hypotl.c -- long double version of e_hypot.c. + * Conversion to long double by Jakub Jelinek, jakub@redhat.com. + */ + +/* + * ==================================================== + * Copyright (C) 1993 by Sun Microsystems, Inc. All rights reserved. + * + * Developed at SunPro, a Sun Microsystems, Inc. business. + * Permission to use, copy, modify, and distribute this + * software is freely granted, provided that this notice + * is preserved. + * ==================================================== + */ + +/* __ieee754_hypotl(x,y) + * + * Method : + * If (assume round-to-nearest) z=x*x+y*y + * has error less than sqrtl(2)/2 ulp, than + * sqrtl(z) has error less than 1 ulp (exercise). + * + * So, compute sqrtl(x*x+y*y) with some care as + * follows to get the error below 1 ulp: + * + * Assume x>y>0; + * (if possible, set rounding to round-to-nearest) + * 1. if x > 2y use + * x1*x1+(y*y+(x2*(x+x1))) for x*x+y*y + * where x1 = x with lower 64 bits cleared, x2 = x-x1; else + * 2. if x <= 2y use + * t1*y1+((x-y)*(x-y)+(t1*y2+t2*y)) + * where t1 = 2x with lower 64 bits cleared, t2 = 2x-t1, + * y1= y with lower 64 bits chopped, y2 = y-y1. + * + * NOTE: scaling may be necessary if some argument is too + * large or too tiny + * + * Special cases: + * hypotl(x,y) is INF if x or y is +INF or -INF; else + * hypotl(x,y) is NAN if x or y is NAN. + * + * Accuracy: + * hypotl(x,y) returns sqrtl(x^2+y^2) with error less + * than 1 ulps (units in the last place) + */ + +#include +#include +#include + +_Float128 +__ieee754_hypotl(_Float128 x, _Float128 y) +{ + _Float128 a,b,t1,t2,y1,y2,w; + int64_t j,k,ha,hb; + + GET_LDOUBLE_MSW64(ha,x); + ha &= 0x7fffffffffffffffLL; + GET_LDOUBLE_MSW64(hb,y); + hb &= 0x7fffffffffffffffLL; + if(hb > ha) {a=y;b=x;j=ha; ha=hb;hb=j;} else {a=x;b=y;} + SET_LDOUBLE_MSW64(a,ha); /* a <- |a| */ + SET_LDOUBLE_MSW64(b,hb); /* b <- |b| */ + if((ha-hb)>0x78000000000000LL) {return a+b;} /* x/y > 2**120 */ + k=0; + if(ha > 0x5f3f000000000000LL) { /* a>2**8000 */ + if(ha >= 0x7fff000000000000LL) { /* Inf or NaN */ + uint64_t low; + w = a+b; /* for sNaN */ + if (issignaling (a) || issignaling (b)) + return w; + GET_LDOUBLE_LSW64(low,a); + if(((ha&0xffffffffffffLL)|low)==0) w = a; + GET_LDOUBLE_LSW64(low,b); + if(((hb^0x7fff000000000000LL)|low)==0) w = b; + return w; + } + /* scale a and b by 2**-9600 */ + ha -= 0x2580000000000000LL; + hb -= 0x2580000000000000LL; k += 9600; + SET_LDOUBLE_MSW64(a,ha); + SET_LDOUBLE_MSW64(b,hb); + } + if(hb < 0x20bf000000000000LL) { /* b < 2**-8000 */ + if(hb <= 0x0000ffffffffffffLL) { /* subnormal b or 0 */ + uint64_t low; + GET_LDOUBLE_LSW64(low,b); + if((hb|low)==0) return a; + t1=0; + SET_LDOUBLE_MSW64(t1,0x7ffd000000000000LL); /* t1=2^16382 */ + b *= t1; + a *= t1; + k -= 16382; + GET_LDOUBLE_MSW64 (ha, a); + GET_LDOUBLE_MSW64 (hb, b); + if (hb > ha) + { + t1 = a; + a = b; + b = t1; + j = ha; + ha = hb; + hb = j; + } + } else { /* scale a and b by 2^9600 */ + ha += 0x2580000000000000LL; /* a *= 2^9600 */ + hb += 0x2580000000000000LL; /* b *= 2^9600 */ + k -= 9600; + SET_LDOUBLE_MSW64(a,ha); + SET_LDOUBLE_MSW64(b,hb); + } + } + /* medium size a and b */ + w = a-b; + if (w>b) { + t1 = 0; + SET_LDOUBLE_MSW64(t1,ha); + t2 = a-t1; + w = sqrtl(t1*t1-(b*(-b)-t2*(a+t1))); + } else { + a = a+a; + y1 = 0; + SET_LDOUBLE_MSW64(y1,hb); + y2 = b - y1; + t1 = 0; + SET_LDOUBLE_MSW64(t1,ha+0x0001000000000000LL); + t2 = a - t1; + w = sqrtl(t1*y1-(w*(-w)-(t1*y2+t2*b))); + } + if(k!=0) { + uint64_t high; + t1 = 1; + GET_LDOUBLE_MSW64(high,t1); + SET_LDOUBLE_MSW64(t1,high+(k<<48)); + w *= t1; + math_check_force_underflow_nonneg (w); + return w; + } else return w; +} +strong_alias (__ieee754_hypotl, __hypotl_finite) diff --git a/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_atanl.c b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_atanl.c new file mode 100644 index 0000000000..022ccf4c45 --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_atanl.c @@ -0,0 +1,255 @@ +/* s_atanl.c + * + * Inverse circular tangent for 128-bit long double precision + * (arctangent) + * + * + * + * SYNOPSIS: + * + * long double x, y, atanl(); + * + * y = atanl( x ); + * + * + * + * DESCRIPTION: + * + * Returns radian angle between -pi/2 and +pi/2 whose tangent is x. + * + * The function uses a rational approximation of the form + * t + t^3 P(t^2)/Q(t^2), optimized for |t| < 0.09375. + * + * The argument is reduced using the identity + * arctan x - arctan u = arctan ((x-u)/(1 + ux)) + * and an 83-entry lookup table for arctan u, with u = 0, 1/8, ..., 10.25. + * Use of the table improves the execution speed of the routine. + * + * + * + * ACCURACY: + * + * Relative error: + * arithmetic domain # trials peak rms + * IEEE -19, 19 4e5 1.7e-34 5.4e-35 + * + * + * WARNING: + * + * This program uses integer operations on bit fields of floating-point + * numbers. It does not work with data structures other than the + * structure assumed. + * + */ + +/* Copyright 2001 by Stephen L. Moshier + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with this library; if not, see + . */ + + +#include +#include +#include +#include +#include + +/* arctan(k/8), k = 0, ..., 82 */ +static const _Float128 atantbl[84] = { + L(0.0000000000000000000000000000000000000000E0), + L(1.2435499454676143503135484916387102557317E-1), /* arctan(0.125) */ + L(2.4497866312686415417208248121127581091414E-1), + L(3.5877067027057222039592006392646049977698E-1), + L(4.6364760900080611621425623146121440202854E-1), + L(5.5859931534356243597150821640166127034645E-1), + L(6.4350110879328438680280922871732263804151E-1), + L(7.1882999962162450541701415152590465395142E-1), + L(7.8539816339744830961566084581987572104929E-1), + L(8.4415398611317100251784414827164750652594E-1), + L(8.9605538457134395617480071802993782702458E-1), + L(9.4200004037946366473793717053459358607166E-1), + L(9.8279372324732906798571061101466601449688E-1), + L(1.0191413442663497346383429170230636487744E0), + L(1.0516502125483736674598673120862998296302E0), + L(1.0808390005411683108871567292171998202703E0), + L(1.1071487177940905030170654601785370400700E0), + L(1.1309537439791604464709335155363278047493E0), + L(1.1525719972156675180401498626127513797495E0), + L(1.1722738811284763866005949441337046149712E0), + L(1.1902899496825317329277337748293183376012E0), + L(1.2068173702852525303955115800565576303133E0), + L(1.2220253232109896370417417439225704908830E0), + L(1.2360594894780819419094519711090786987027E0), + L(1.2490457723982544258299170772810901230778E0), + L(1.2610933822524404193139408812473357720101E0), + L(1.2722973952087173412961937498224804940684E0), + L(1.2827408797442707473628852511364955306249E0), + L(1.2924966677897852679030914214070816845853E0), + L(1.3016288340091961438047858503666855921414E0), + L(1.3101939350475556342564376891719053122733E0), + L(1.3182420510168370498593302023271362531155E0), + L(1.3258176636680324650592392104284756311844E0), + L(1.3329603993374458675538498697331558093700E0), + L(1.3397056595989995393283037525895557411039E0), + L(1.3460851583802539310489409282517796256512E0), + L(1.3521273809209546571891479413898128509842E0), + L(1.3578579772154994751124898859640585287459E0), + L(1.3633001003596939542892985278250991189943E0), + L(1.3684746984165928776366381936948529556191E0), + L(1.3734007669450158608612719264449611486510E0), + L(1.3780955681325110444536609641291551522494E0), + L(1.3825748214901258580599674177685685125566E0), + L(1.3868528702577214543289381097042486034883E0), + L(1.3909428270024183486427686943836432060856E0), + L(1.3948567013423687823948122092044222644895E0), + L(1.3986055122719575950126700816114282335732E0), + L(1.4021993871854670105330304794336492676944E0), + L(1.4056476493802697809521934019958079881002E0), + L(1.4089588955564736949699075250792569287156E0), + L(1.4121410646084952153676136718584891599630E0), + L(1.4152014988178669079462550975833894394929E0), + L(1.4181469983996314594038603039700989523716E0), + L(1.4209838702219992566633046424614466661176E0), + L(1.4237179714064941189018190466107297503086E0), + L(1.4263547484202526397918060597281265695725E0), + L(1.4288992721907326964184700745371983590908E0), + L(1.4313562697035588982240194668401779312122E0), + L(1.4337301524847089866404719096698873648610E0), + L(1.4360250423171655234964275337155008780675E0), + L(1.4382447944982225979614042479354815855386E0), + L(1.4403930189057632173997301031392126865694E0), + L(1.4424730991091018200252920599377292525125E0), + L(1.4444882097316563655148453598508037025938E0), + L(1.4464413322481351841999668424758804165254E0), + L(1.4483352693775551917970437843145232637695E0), + L(1.4501726582147939000905940595923466567576E0), + L(1.4519559822271314199339700039142990228105E0), + L(1.4536875822280323362423034480994649820285E0), + L(1.4553696664279718992423082296859928222270E0), + L(1.4570043196511885530074841089245667532358E0), + L(1.4585935117976422128825857356750737658039E0), + L(1.4601391056210009726721818194296893361233E0), + L(1.4616428638860188872060496086383008594310E0), + L(1.4631064559620759326975975316301202111560E0), + L(1.4645314639038178118428450961503371619177E0), + L(1.4659193880646627234129855241049975398470E0), + L(1.4672716522843522691530527207287398276197E0), + L(1.4685896086876430842559640450619880951144E0), + L(1.4698745421276027686510391411132998919794E0), + L(1.4711276743037345918528755717617308518553E0), + L(1.4723501675822635384916444186631899205983E0), + L(1.4735431285433308455179928682541563973416E0), /* arctan(10.25) */ + L(1.5707963267948966192313216916397514420986E0) /* pi/2 */ +}; + + +/* arctan t = t + t^3 p(t^2) / q(t^2) + |t| <= 0.09375 + peak relative error 5.3e-37 */ + +static const _Float128 + p0 = L(-4.283708356338736809269381409828726405572E1), + p1 = L(-8.636132499244548540964557273544599863825E1), + p2 = L(-5.713554848244551350855604111031839613216E1), + p3 = L(-1.371405711877433266573835355036413750118E1), + p4 = L(-8.638214309119210906997318946650189640184E-1), + q0 = L(1.285112506901621042780814422948906537959E2), + q1 = L(3.361907253914337187957855834229672347089E2), + q2 = L(3.180448303864130128268191635189365331680E2), + q3 = L(1.307244136980865800160844625025280344686E2), + q4 = L(2.173623741810414221251136181221172551416E1); + /* q5 = 1.000000000000000000000000000000000000000E0 */ + +static const _Float128 huge = L(1.0e4930); + +_Float128 +__atanl (_Float128 x) +{ + int k, sign; + _Float128 t, u, p, q; + ieee854_long_double_shape_type s; + + s.value = x; + k = s.parts32.w0; + if (k & 0x80000000) + sign = 1; + else + sign = 0; + + /* Check for IEEE special cases. */ + k &= 0x7fffffff; + if (k >= 0x7fff0000) + { + /* NaN. */ + if ((k & 0xffff) | s.parts32.w1 | s.parts32.w2 | s.parts32.w3) + return (x + x); + + /* Infinity. */ + if (sign) + return -atantbl[83]; + else + return atantbl[83]; + } + + if (k <= 0x3fc50000) /* |x| < 2**-58 */ + { + math_check_force_underflow (x); + /* Raise inexact. */ + if (huge + x > 0.0) + return x; + } + + if (k >= 0x40720000) /* |x| > 2**115 */ + { + /* Saturate result to {-,+}pi/2 */ + if (sign) + return -atantbl[83]; + else + return atantbl[83]; + } + + if (sign) + x = -x; + + if (k >= 0x40024800) /* 10.25 */ + { + k = 83; + t = -1.0/x; + } + else + { + /* Index of nearest table element. + Roundoff to integer is asymmetrical to avoid cancellation when t < 0 + (cf. fdlibm). */ + k = 8.0 * x + 0.25; + u = L(0.125) * k; + /* Small arctan argument. */ + t = (x - u) / (1.0 + x * u); + } + + /* Arctan of small argument t. */ + u = t * t; + p = ((((p4 * u) + p3) * u + p2) * u + p1) * u + p0; + q = ((((u + q4) * u + q3) * u + q2) * u + q1) * u + q0; + u = t * u * p / q + t; + + /* arctan x = arctan u + arctan t */ + u = atantbl[k] + u; + if (sign) + return (-u); + else + return u; +} + +libm_alias_ldouble (__atan, atan) diff --git a/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_copysignl.c b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_copysignl.c new file mode 100644 index 0000000000..a501139f71 --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_copysignl.c @@ -0,0 +1,40 @@ +/* s_copysignl.c -- long double version of s_copysign.c. + * Conversion to long double by Jakub Jelinek, jj@ultra.linux.cz. + */ + +/* + * ==================================================== + * Copyright (C) 1993 by Sun Microsystems, Inc. All rights reserved. + * + * Developed at SunPro, a Sun Microsystems, Inc. business. + * Permission to use, copy, modify, and distribute this + * software is freely granted, provided that this notice + * is preserved. + * ==================================================== + */ + +#if defined(LIBM_SCCS) && !defined(lint) +static char rcsid[] = "$NetBSD: $"; +#endif + +/* + * copysignl(long double x, long double y) + * copysignl(x,y) returns a value with the magnitude of x and + * with the sign bit of y. + */ + +#define NO_MATH_REDIRECT +#include +#include +#include + +_Float128 __copysignl(_Float128 x, _Float128 y) +{ + uint64_t hx,hy; + GET_LDOUBLE_MSW64(hx,x); + GET_LDOUBLE_MSW64(hy,y); + SET_LDOUBLE_MSW64(x,(hx&0x7fffffffffffffffULL) + |(hy&0x8000000000000000ULL)); + return x; +} +libm_alias_ldouble (__copysign, copysign) diff --git a/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_fpclassifyl.c b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_fpclassifyl.c new file mode 100644 index 0000000000..396d9b2fd4 --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_fpclassifyl.c @@ -0,0 +1,44 @@ +/* Return classification value corresponding to argument. + Copyright (C) 1997-2019 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Ulrich Drepper , 1997 and + Jakub Jelinek , 1999. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#include + +#include + + +int +__fpclassifyl (_Float128 x) +{ + uint64_t hx, lx; + int retval = FP_NORMAL; + + GET_LDOUBLE_WORDS64 (hx, lx, x); + lx |= (hx & 0x0000ffffffffffffLL); + hx &= 0x7fff000000000000LL; + if ((hx | lx) == 0) + retval = FP_ZERO; + else if (hx == 0) + retval = FP_SUBNORMAL; + else if (hx == 0x7fff000000000000LL) + retval = lx != 0 ? FP_NAN : FP_INFINITE; + + return retval; +} +libm_hidden_def (__fpclassifyl) diff --git a/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_isinfl.c b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_isinfl.c new file mode 100644 index 0000000000..82320569bf --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_isinfl.c @@ -0,0 +1,29 @@ +/* + * Written by J.T. Conklin . + * Change for long double by Jakub Jelinek + * Public domain. + */ + +#if defined(LIBM_SCCS) && !defined(lint) +static char rcsid[] = "$NetBSD: $"; +#endif + +/* + * isinfl(x) returns 1 if x is inf, -1 if x is -inf, else 0; + * no branching! + */ + +#include +#include + +int +__isinfl (_Float128 x) +{ + int64_t hx,lx; + GET_LDOUBLE_WORDS64(hx,lx,x); + lx |= (hx & 0x7fffffffffffffffLL) ^ 0x7fff000000000000LL; + lx |= -lx; + return ~(lx >> 63) & (hx >> 62); +} +//mathx_hidden_def (__isinfl) +//weak_alias (__isinfl, isinfl) diff --git a/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_isnanl.c b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_isnanl.c new file mode 100644 index 0000000000..f5f65d2d7b --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_isnanl.c @@ -0,0 +1,38 @@ +/* s_isnanl.c -- long double version of s_isnan.c. + * Conversion to long double by Jakub Jelinek, jj@ultra.linux.cz. + */ + +/* + * ==================================================== + * Copyright (C) 1993 by Sun Microsystems, Inc. All rights reserved. + * + * Developed at SunPro, a Sun Microsystems, Inc. business. + * Permission to use, copy, modify, and distribute this + * software is freely granted, provided that this notice + * is preserved. + * ==================================================== + */ + +#if defined(LIBM_SCCS) && !defined(lint) +static char rcsid[] = "$NetBSD: $"; +#endif + +/* + * isnanl(x) returns 1 is x is nan, else 0; + * no branching! + */ + +#include +#include + +int __isnanl(_Float128 x) +{ + int64_t hx,lx; + GET_LDOUBLE_WORDS64(hx,lx,x); + hx &= 0x7fffffffffffffffLL; + hx |= (uint64_t)(lx|(-lx))>>63; + hx = 0x7fff000000000000LL - hx; + return (int)((uint64_t)hx>>63); +} +//mathx_hidden_def (__isnanl) +//weak_alias (__isnanl, isnanl) diff --git a/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_issignalingl.c b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_issignalingl.c new file mode 100644 index 0000000000..b2b4764a5c --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_issignalingl.c @@ -0,0 +1,46 @@ +/* Test for signaling NaN. + Copyright (C) 2013-2019 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#include +#include +#include + +int +__issignalingl (_Float128 x) +{ + uint64_t hxi, lxi __attribute__ ((unused)); + GET_LDOUBLE_WORDS64 (hxi, lxi, x); +#if HIGH_ORDER_BIT_IS_SET_FOR_SNAN + /* We only have to care about the high-order bit of x's significand, because + having it set (sNaN) already makes the significand different from that + used to designate infinity. */ + return ((hxi & UINT64_C (0x7fff800000000000)) + == UINT64_C (0x7fff800000000000)); +#else + /* To keep the following comparison simple, toggle the quiet/signaling bit, + so that it is set for sNaNs. This is inverse to IEEE 754-2008 (as well as + common practice for IEEE 754-1985). */ + hxi ^= UINT64_C (0x0000800000000000); + /* If lxi != 0, then set any suitable bit of the significand in hxi. */ + hxi |= (lxi | -lxi) >> 63; + /* We have to compare for greater (instead of greater or equal), because x's + significand being all-zero designates infinity not NaN. */ + return (hxi & UINT64_C (0x7fffffffffffffff)) > UINT64_C (0x7fff800000000000); +#endif +} +libm_hidden_def (__issignalingl) diff --git a/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_signbitl.c b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_signbitl.c new file mode 100644 index 0000000000..1da3919bf1 --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/generic/longdouble/128bit/s_signbitl.c @@ -0,0 +1,27 @@ +/* Return nonzero value if number is negative. + Copyright (C) 1997-2019 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Ulrich Drepper , 1997. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#include +#include + +int +__signbitl (_Float128 x) +{ + return __builtin_signbitl (x); +} diff --git a/src/system/libroot/posix/glibc/arch/generic/e_atan2l.c b/src/system/libroot/posix/glibc/arch/generic/longdouble/80bit/e_atan2l.c similarity index 99% rename from src/system/libroot/posix/glibc/arch/generic/e_atan2l.c rename to src/system/libroot/posix/glibc/arch/generic/longdouble/80bit/e_atan2l.c index 0759458c2f..5df9d05ebf 100644 --- a/src/system/libroot/posix/glibc/arch/generic/e_atan2l.c +++ b/src/system/libroot/posix/glibc/arch/generic/longdouble/80bit/e_atan2l.c @@ -46,6 +46,7 @@ static char rcsid[] = "$NetBSD: $"; */ #include "math.h" +#include "math_ldbl.h" #include "math_private.h" #ifdef __STDC__ diff --git a/src/system/libroot/posix/glibc/arch/generic/e_hypotl.c b/src/system/libroot/posix/glibc/arch/generic/longdouble/80bit/e_hypotl.c similarity index 100% rename from src/system/libroot/posix/glibc/arch/generic/e_hypotl.c rename to src/system/libroot/posix/glibc/arch/generic/longdouble/80bit/e_hypotl.c diff --git a/src/system/libroot/posix/glibc/arch/generic/s_atanl.c b/src/system/libroot/posix/glibc/arch/generic/longdouble/80bit/s_atanl.c similarity index 100% rename from src/system/libroot/posix/glibc/arch/generic/s_atanl.c rename to src/system/libroot/posix/glibc/arch/generic/longdouble/80bit/s_atanl.c diff --git a/src/system/libroot/posix/glibc/arch/generic/s_copysignl.c b/src/system/libroot/posix/glibc/arch/generic/longdouble/80bit/s_copysignl.c similarity index 100% rename from src/system/libroot/posix/glibc/arch/generic/s_copysignl.c rename to src/system/libroot/posix/glibc/arch/generic/longdouble/80bit/s_copysignl.c diff --git a/src/system/libroot/posix/glibc/arch/generic/s_signbitl.c b/src/system/libroot/posix/glibc/arch/generic/longdouble/80bit/s_signbitl.c similarity index 100% rename from src/system/libroot/posix/glibc/arch/generic/s_signbitl.c rename to src/system/libroot/posix/glibc/arch/generic/longdouble/80bit/s_signbitl.c diff --git a/src/system/libroot/posix/glibc/arch/m68k/Jamfile b/src/system/libroot/posix/glibc/arch/m68k/Jamfile index c935dc15b5..111ab2e8f0 100644 --- a/src/system/libroot/posix/glibc/arch/m68k/Jamfile +++ b/src/system/libroot/posix/glibc/arch/m68k/Jamfile @@ -172,6 +172,8 @@ for architectureObject in [ MultiArchSubDirSetup m68k ] { SEARCH on [ FGristFiles $(genericSources) ] = [ FDirName $(HAIKU_TOP) src system libroot posix glibc arch - generic ] ; + generic ] + [ FDirName $(HAIKU_TOP) src system libroot posix glibc arch + generic longdouble 80bit ] ; } } diff --git a/src/system/libroot/posix/glibc/arch/sparc/Jamfile b/src/system/libroot/posix/glibc/arch/sparc/Jamfile index a0fb7e6b60..188fbe6d75 100644 --- a/src/system/libroot/posix/glibc/arch/sparc/Jamfile +++ b/src/system/libroot/posix/glibc/arch/sparc/Jamfile @@ -19,8 +19,10 @@ SubDirCcFlags -D_GNU_SOURCE -D_IEEE_LIBM ; local genericSources = branred.c cmp.c dbl2mpn.c divrem.c + doasin.c dosincos.c halfulp.c + ldbl2mpn.c memrchr.c mpa.c mpatan.c mpatan2.c mpexp.c mplog.c mpn2dbl.c mpn2flt.c mpn2ldbl.c mpsqrt.c mptan.c @@ -29,34 +31,39 @@ local genericSources = slowexp.c slowpow.c + e_acosf.c e_acosh.c e_acoshf.c # e_acoshl.c - e_atan2.c e_atan2f.c # e_atan2l.c + e_asin.c e_asinf.c + e_atan2.c e_atan2f.c e_atan2l.c e_atanh.c e_atanhf.c # e_atanhl.c e_cosh.c e_coshf.c # e_coshl.c e_exp.c e_expf.c e_fmod.c e_fmodf.c # e_fmodl.c e_gamma_r.c e_gammaf_r.c - e_hypot.c e_hypotf.c # e_hypotl.c + e_hypot.c e_hypotf.c e_hypotl.c e_j0.c e_j0f.c e_j1.c e_j1f.c e_jn.c e_jnf.c e_lgamma_r.c e_lgammaf_r.c - e_log.c e_logf.c + e_log.c e_logf.c e_logl.c e_log10.c e_log10f.c e_pow.c e_powf.c # e_powl.c e_rem_pio2f.c e_remainder.c e_remainderf.c # e_remainderl.c e_scalb.c e_scalbf.c # e_scalbl.c e_sinh.c e_sinhf.c # e_sinhl.c + e_sqrt.c e_sqrtf.c k_cos.c k_cosf.c k_sin.c k_sinf.c k_rem_pio2.c k_rem_pio2f.c # k_rem_pio2l.c k_tan.c k_tanf.c s_asinh.c s_asinhf.c # s_asinhl.c - s_atan.c s_atanf.c # s_atanl.c + s_atan.c s_atanf.c s_atanl.c s_cbrt.c s_cbrtf.c # s_cbrtl.c s_ceil.c s_ceilf.c # s_ceill.c - s_copysign.c s_copysignf.c # s_copysignl.c + s_clog.c s_clogf.c s_clogl.c + s_csqrt.c s_csqrtf.c s_csqrtl.c + s_copysign.c s_copysignf.c s_copysignl.c s_cos.c s_cosf.c s_erf.c s_erff.c # s_erfl.c s_expm1f.c s_expm1.c @@ -66,23 +73,26 @@ local genericSources = s_fma.c s_fmaf.c # s_fmal.c s_fmax.c s_fmaxf.c # s_fmaxl.c s_fmin.c s_fminf.c # s_fminl.c - s_fpclassify.c s_fpclassifyf.c # s_fpclassifyl.c + s_fpclassify.c s_fpclassifyf.c s_fpclassifyl.c s_frexp.c s_frexpf.c # s_frexpl.c s_ilogb.c s_ilogbf.c - s_isinf.c s_isinff.c # s_isinfl.c + s_isinf.c s_isinff.c s_isinfl.c + s_isnanl.c + s_issignalingl.c s_ldexp.c s_ldexpf.c # s_ldexpl.c s_llrint.c s_llrintf.c # s_llrintl.c - s_log1p.c s_log1pf.c + s_log1p.c s_log1pf.c s_log1pl.c s_logb.c s_logbf.c # s_logbl.c s_lrint.c s_lrintf.c # s_lrintl.c s_lround.c s_lroundf.c s_modf.c s_modff.c # s_modfl.c - s_nan.c s_nanf.c # s_nanl.c + s_nan.c s_nanf.c s_nanl.c s_nextafter.c s_nextafterf.c # s_nextafterl.c s_nexttoward.c # s_nexttowardf.c s_nexttowardl.c + s_rint.c s_rintf.c s_round.c s_roundf.c # s_roundl.c s_scalbn.c s_scalbnf.c # s_scalbnl.c - s_signbit.c s_signbitf.c # s_signbitl.c + s_signbit.c s_signbitf.c s_signbitl.c s_significand.c s_significandf.c s_signgam.c s_sin.c s_sinf.c # s_sinl.c @@ -93,14 +103,14 @@ local genericSources = t_exp.c w_acos.c w_acosf.c # w_acosl.c w_acosh.c w_acoshf.c # w_acoshl.c - w_atan2.c w_atan2f.c # w_atan2l.c + w_atan2.c w_atan2f.c w_atan2l.c w_asin.c w_asinf.c # w_asinl.c w_atanh.c w_atanhf.c # w_atanhl.c w_cosh.c w_coshf.c # w_coshl.c w_drem.c w_dremf.c # w_dreml.c w_exp.c w_expf.c # w_expl.c w_fmod.c w_fmodf.c # w_fmodl.c - w_hypot.c w_hypotf.c # w_hypotl.c + w_hypot.c w_hypotf.c w_hypotl.c w_j0.c w_j0f.c w_j1.c w_j1f.c w_jn.c w_jnf.c @@ -112,8 +122,8 @@ local genericSources = w_remainder.c w_remainderf.c # w_remainderl.c w_scalb.c w_scalbf.c # w_scalbl.c w_sinh.c w_sinhf.c # w_sinhl.c - # no asm for m68k in glibc w_sqrt.c w_sqrtf.c # w_sqrtl.c + w_sqrtl_compat.c ; @@ -122,18 +132,39 @@ MergeObject <$(TARGET_ARCH)>posix_gnu_arch_$(TARGET_ARCH)_generic.o : ; -#MergeObject <$(TARGET_ARCH)>posix_gnu_arch_$(TARGET_ARCH)_other.o : -# ; +MergeObject <$(TARGET_ARCH)>posix_gnu_arch_$(TARGET_ARCH)_e.o : + e_sqrtl.c + ; + +MergeObject <$(TARGET_ARCH)>posix_gnu_arch_$(TARGET_ARCH)_s.o : + s_isnan.S s_isnanf.S + ; + +MergeObject <$(TARGET_ARCH)>posix_gnu_arch_$(TARGET_ARCH)_other.o : + add_n.S + addmul_1.S + fegetround.c fesetround.c + feholdexcpt.c + fraiseexcpt.c + fesetenv.c + lshift.S rshift.S + mul_1.S + sub_n.S + submul_1.S + ; MergeObjectFromObjects <$(TARGET_ARCH)>posix_gnu_arch_$(TARGET_ARCH).o : : + <$(TARGET_ARCH)>posix_gnu_arch_$(TARGET_ARCH)_e.o + <$(TARGET_ARCH)>posix_gnu_arch_$(TARGET_ARCH)_s.o <$(TARGET_ARCH)>posix_gnu_arch_$(TARGET_ARCH)_generic.o - # <$(TARGET_ARCH)>posix_gnu_arch_$(TARGET_ARCH)_other.o + <$(TARGET_ARCH)>posix_gnu_arch_$(TARGET_ARCH)_other.o ; SEARCH on [ FGristFiles $(genericSources) ] = [ FDirName $(HAIKU_TOP) src system libroot posix glibc arch - generic ] ; - + generic ] + [ FDirName $(HAIKU_TOP) src system libroot posix glibc arch + generic longdouble 128bit ] ; diff --git a/src/system/libroot/posix/glibc/arch/sparc/add_n.S b/src/system/libroot/posix/glibc/arch/sparc/add_n.S new file mode 100644 index 0000000000..f804090c0d --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/sparc/add_n.S @@ -0,0 +1,57 @@ +/* SPARC v9 __mpn_add_n -- Add two limb vectors of the same length > 0 and + store sum in a third limb vector. + + Copyright (C) 1995-2018 Free Software Foundation, Inc. + + This file is part of the GNU MP Library. + + The GNU MP Library is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License as published by + the Free Software Foundation; either version 2.1 of the License, or (at your + option) any later version. + + The GNU MP Library is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU Lesser General Public License + along with the GNU MP Library; see the file COPYING.LIB. If not, + see . */ + + +#include + + +/* INPUT PARAMETERS + res_ptr %o0 + s1_ptr %o1 + s2_ptr %o2 + size %o3 */ + + +ENTRY(__mpn_add_n) + + sub %g0,%o3,%g5 + sllx %o3,3,%g1 + add %o1,%g1,%o1 ! make s1_ptr point at end + add %o2,%g1,%o2 ! make s2_ptr point at end + add %o0,%g1,%o0 ! make res_ptr point at end + mov 0,%o4 ! clear carry variable + sllx %g5,3,%o5 ! compute initial address index + +1: ldx [%o2+%o5],%g1 ! load s2 limb + add %g5,1,%g5 ! increment loop count + ldx [%o1+%o5],%o3 ! load s1 limb + addcc %g1,%o4,%g1 ! add s2 limb and carry variable + movcc %xcc,0,%o4 ! if carry-out, o4 was 1; clear it + addcc %g1,%o3,%g1 ! add s1 limb to sum + stx %g1,[%o0+%o5] ! store result + add %o5,8,%o5 ! increment address index + brnz,pt %g5,1b + movcs %xcc,1,%o4 ! if s1 add gave carry, record it + + retl + mov %o4,%o0 + +END(__mpn_add_n) diff --git a/src/system/libroot/posix/glibc/arch/sparc/addmul_1.S b/src/system/libroot/posix/glibc/arch/sparc/addmul_1.S new file mode 100644 index 0000000000..b36ce03764 --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/sparc/addmul_1.S @@ -0,0 +1,83 @@ +/* SPARC v9 __mpn_addmul_1 -- Multiply a limb vector with a single limb and + add the product to a second limb vector. + + Copyright (C) 1996-2018 Free Software Foundation, Inc. + + This file is part of the GNU MP Library. + + The GNU MP Library is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License as published by + the Free Software Foundation; either version 2.1 of the License, or (at your + option) any later version. + + The GNU MP Library is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU Lesser General Public License + along with the GNU MP Library; see the file COPYING.LIB. If not, + see . */ + +#include + + +/* INPUT PARAMETERS + res_ptr o0 + s1_ptr o1 + size o2 + s2_limb o3 */ + + +ENTRY(__mpn_addmul_1) + save %sp,-192,%sp + + sub %g0,%i2,%o7 + mov 0,%o0 ! zero cy_limb + sllx %o7,3,%o7 + sethi %hi(0x80000000),%o2 + srl %i3,0,%o1 ! extract low 32 bits of s2_limb + sub %i1,%o7,%o3 + srlx %i3,32,%i3 ! extract high 32 bits of s2_limb + sub %i0,%o7,%o4 + add %o2,%o2,%o2 ! o2 = 0x100000000 + + ! hi ! + ! mid-1 ! + ! mid-2 ! + ! lo ! +1: + ldx [%o3+%o7],%g5 + srl %g5,0,%i0 ! zero hi bits + ldx [%o4+%o7],%l1 + srlx %g5,32,%g5 + mulx %o1,%i0,%i4 ! lo product + mulx %i3,%i0,%i1 ! mid-1 product + mulx %o1,%g5,%l2 ! mid-2 product + mulx %i3,%g5,%i5 ! hi product + srlx %i4,32,%i0 ! extract high 32 bits of lo product... + add %i1,%i0,%i1 ! ...and add it to the mid-1 product + addcc %i1,%l2,%i1 ! add mid products + mov 0,%l0 ! we need the carry from that add... + movcs %xcc,%o2,%l0 ! ...compute it and... + sllx %i1,32,%i0 ! align low bits of mid product + add %i5,%l0,%i5 ! ...add to bit 32 of the hi product + srl %i4,0,%g5 ! zero high 32 bits of lo product + add %i0,%g5,%i0 ! combine into low 64 bits of result + srlx %i1,32,%i1 ! extract high bits of mid product... + addcc %i0,%o0,%i0 ! add cy_limb to low 64 bits of result + add %i5,%i1,%i1 ! ...and add them to the high result + mov 0,%g5 + movcs %xcc,1,%g5 + addcc %l1,%i0,%i0 + stx %i0,[%o4+%o7] + add %g5,1,%l1 + movcs %xcc,%l1,%g5 + addcc %o7,8,%o7 + bne,pt %xcc,1b + add %i1,%g5,%o0 ! compute new cy_limb + + jmpl %i7+8, %g0 + restore %o0,%g0,%o0 + +END(__mpn_addmul_1) diff --git a/src/system/libroot/posix/glibc/arch/sparc/e_sqrtl.c b/src/system/libroot/posix/glibc/arch/sparc/e_sqrtl.c new file mode 100644 index 0000000000..7742770148 --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/sparc/e_sqrtl.c @@ -0,0 +1,31 @@ +/* Long double square root, sparc64 version. + Copyright (C) 2000-2019 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Jakub Jelinek , 2000. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#include + +extern void _Qp_sqrt(long double *, const long double *); + +long double +__ieee754_sqrtl (long double x) +{ + long double ret; + _Qp_sqrt (&ret, &x); + return ret; +} +strong_alias (__ieee754_sqrtl, __sqrtl_finite) diff --git a/src/system/libroot/posix/glibc/arch/sparc/fegetround.c b/src/system/libroot/posix/glibc/arch/sparc/fegetround.c new file mode 100644 index 0000000000..ece7a713d5 --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/sparc/fegetround.c @@ -0,0 +1,32 @@ +/* Return current rounding direction. + Copyright (C) 1997-2018 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#include + +int +__fegetround (void) +{ + fenv_t tmp; + + __fenv_stfsr (tmp); + + return tmp & __FE_ROUND_MASK; +} +libm_hidden_def (__fegetround) +weak_alias (__fegetround, fegetround) +libm_hidden_weak (fegetround) diff --git a/src/system/libroot/posix/glibc/arch/sparc/feholdexcpt.c b/src/system/libroot/posix/glibc/arch/sparc/feholdexcpt.c new file mode 100644 index 0000000000..59b4180cd8 --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/sparc/feholdexcpt.c @@ -0,0 +1,14 @@ +#include + +int +feholdexcept (fenv_t *e) +{ + fenv_t etmp; + __fenv_stfsr(etmp); + *(e) = etmp; + etmp = etmp & ~((0x1f << 23) | FE_ALL_EXCEPT); + __fenv_ldfsr(etmp); + + return 0; +} + diff --git a/src/system/libroot/posix/glibc/arch/sparc/fesetenv.c b/src/system/libroot/posix/glibc/arch/sparc/fesetenv.c new file mode 100644 index 0000000000..297015da0c --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/sparc/fesetenv.c @@ -0,0 +1,55 @@ +/* Install given floating-point environment. + Copyright (C) 1997-2018 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#include +#include + +int +__fesetenv (const fenv_t *envp) +{ + fenv_t dummy; + + /* Put these constants in memory explicitly, so as to cope with a + -fPIC bug as of gcc 970624. Making them automatic is quicker + than loading up the pic register in this instance. */ + + if (envp == FE_DFL_ENV) + { + dummy = 0; + envp = &dummy; + } + else if (envp == FE_NOMASK_ENV) + { + dummy = 0x1f << 23; + envp = &dummy; + } + + __fenv_ldfsr (*envp); + + /* Success. */ + return 0; +} + +#if SHLIB_COMPAT (libm, GLIBC_2_1, GLIBC_2_2) +strong_alias (__fesetenv, __old_fesetenv) +compat_symbol (libm, __old_fesetenv, fesetenv, GLIBC_2_1); +#endif + +libm_hidden_def (__fesetenv) +libm_hidden_ver (__fesetenv, fesetenv) +versioned_symbol (libm, __fesetenv, fesetenv, GLIBC_2_2); diff --git a/src/system/libroot/posix/glibc/arch/sparc/fesetround.c b/src/system/libroot/posix/glibc/arch/sparc/fesetround.c new file mode 100644 index 0000000000..2d538f5856 --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/sparc/fesetround.c @@ -0,0 +1,39 @@ +/* Set current rounding direction. + Copyright (C) 1997-2018 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#include + +int +__fesetround (int round) +{ + fenv_t tmp; + + if ((round & ~__FE_ROUND_MASK) != 0) + /* ROUND is no valid rounding mode. */ + return 1; + + __fenv_stfsr (tmp); + tmp &= ~__FE_ROUND_MASK; + tmp |= round; + __fenv_ldfsr (tmp); + + return 0; +} +libm_hidden_def (__fesetround) +weak_alias (__fesetround, fesetround) +libm_hidden_weak (fesetround) diff --git a/src/system/libroot/posix/glibc/arch/sparc/fraiseexcpt.c b/src/system/libroot/posix/glibc/arch/sparc/fraiseexcpt.c new file mode 100644 index 0000000000..964c4f4ab2 --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/sparc/fraiseexcpt.c @@ -0,0 +1,91 @@ +/* Raise given exceptions. + Copyright (C) 1997-2018 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#include +#include +#include +#include + +int +__feraiseexcept (int excepts) +{ + static const struct { + double zero, one, max, min, pi; + } c = { + 0.0, 1.0, DBL_MAX, DBL_MIN, M_PI + }; + double d; + + /* Raise exceptions represented by EXPECTS. But we must raise only + one signal at a time. It is important the if the overflow/underflow + exception and the inexact exception are given at the same time, + the overflow/underflow exception follows the inexact exception. */ + + /* First: invalid exception. */ + if ((FE_INVALID & excepts) != 0) + { + /* One example of an invalid operation is 0/0. */ + __asm ("" : "=e" (d) : "0" (c.zero)); + d /= c.zero; + __asm __volatile ("" : : "e" (d)); + } + + /* Next: division by zero. */ + if ((FE_DIVBYZERO & excepts) != 0) + { + __asm ("" : "=e" (d) : "0" (c.one)); + d /= c.zero; + __asm __volatile ("" : : "e" (d)); + } + + /* Next: overflow. */ + if ((FE_OVERFLOW & excepts) != 0) + { + __asm ("" : "=e" (d) : "0" (c.max)); + d *= d; + __asm __volatile ("" : : "e" (d)); + } + + /* Next: underflow. */ + if ((FE_UNDERFLOW & excepts) != 0) + { + __asm ("" : "=e" (d) : "0" (c.min)); + d *= d; + __asm __volatile ("" : : "e" (d)); + } + + /* Last: inexact. */ + if ((FE_INEXACT & excepts) != 0) + { + __asm ("" : "=e" (d) : "0" (c.one)); + d /= c.pi; + __asm __volatile ("" : : "e" (d)); + } + + /* Success. */ + return 0; +} + +#if SHLIB_COMPAT (libm, GLIBC_2_1, GLIBC_2_2) +strong_alias (__feraiseexcept, __old_feraiseexcept) +compat_symbol (libm, __old_feraiseexcept, feraiseexcept, GLIBC_2_1); +#endif + +libm_hidden_def (__feraiseexcept) +libm_hidden_ver (__feraiseexcept, feraiseexcept) +versioned_symbol (libm, __feraiseexcept, feraiseexcept, GLIBC_2_2); diff --git a/src/system/libroot/posix/glibc/arch/sparc/lshift.S b/src/system/libroot/posix/glibc/arch/sparc/lshift.S new file mode 100644 index 0000000000..da6dc51fca --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/sparc/lshift.S @@ -0,0 +1,95 @@ +/* SPARC v9 __mpn_lshift -- + + Copyright (C) 1996-2018 Free Software Foundation, Inc. + + This file is part of the GNU MP Library. + + The GNU MP Library is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License as published by + the Free Software Foundation; either version 2.1 of the License, or (at your + option) any later version. + + The GNU MP Library is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU Lesser General Public License + along with the GNU MP Library; see the file COPYING.LIB. If not, + see . */ + +#include "sysdep.h" + +/* INPUT PARAMETERS + res_ptr %o0 + src_ptr %o1 + size %o2 + cnt %o3 */ + + .register %g2, #scratch + .register %g3, #scratch + +ENTRY(__mpn_lshift) + sllx %o2,3,%g1 + add %o1,%g1,%o1 ! make %o1 point at end of src + ldx [%o1-8],%g2 ! load first limb + sub %g0,%o3,%o5 ! negate shift count + add %o0,%g1,%o0 ! make %o0 point at end of res + add %o2,-1,%o2 + andcc %o2,4-1,%g4 ! number of limbs in first loop + srlx %g2,%o5,%g1 ! compute function result + be,pn %xcc,.L0 ! if multiple of 4 limbs, skip first loop + mov %g1,%g5 + + sub %o2,%g4,%o2 ! adjust count for main loop + +.Loop0: ldx [%o1-16],%g3 + add %o0,-8,%o0 + add %o1,-8,%o1 + sllx %g2,%o3,%o4 + addcc %g4,-1,%g4 + srlx %g3,%o5,%g1 + mov %g3,%g2 + or %o4,%g1,%o4 + bne,pt %xcc,.Loop0 + stx %o4,[%o0+0] + +.L0: brz,pn %o2,.Lend + nop + +.Loop: ldx [%o1-16],%g3 + add %o0,-32,%o0 + sllx %g2,%o3,%o4 + addcc %o2,-4,%o2 + srlx %g3,%o5,%g1 + + ldx [%o1-24],%g2 + sllx %g3,%o3,%g4 + or %o4,%g1,%o4 + stx %o4,[%o0+24] + srlx %g2,%o5,%g1 + + ldx [%o1-32],%g3 + sllx %g2,%o3,%o4 + or %g4,%g1,%g4 + stx %g4,[%o0+16] + srlx %g3,%o5,%g1 + + ldx [%o1-40],%g2 + sllx %g3,%o3,%g4 + or %o4,%g1,%o4 + stx %o4,[%o0+8] + srlx %g2,%o5,%g1 + + add %o1,-32,%o1 + or %g4,%g1,%g4 + bne,pt %xcc,.Loop + stx %g4,[%o0+0] + +.Lend: sllx %g2,%o3,%g2 + stx %g2,[%o0-8] + + jmpl %o7+8, %g0 + mov %g5,%o0 + +END(__mpn_lshift) diff --git a/src/system/libroot/posix/glibc/arch/sparc/mul_1.S b/src/system/libroot/posix/glibc/arch/sparc/mul_1.S new file mode 100644 index 0000000000..4b7f4dbbeb --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/sparc/mul_1.S @@ -0,0 +1,82 @@ +/* SPARC v9 __mpn_mul_1 -- Multiply a limb vector with a single limb and + store the product in a second limb vector. + + Copyright (C) 1995-2018 Free Software Foundation, Inc. + + This file is part of the GNU MP Library. + + The GNU MP Library is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License as published by + the Free Software Foundation; either version 2.1 of the License, or (at your + option) any later version. + + The GNU MP Library is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU Lesser General Public License + along with the GNU MP Library; see the file COPYING.LIB. If not, + see . */ + +#include + + +/* INPUT PARAMETERS + res_ptr o0 + s1_ptr o1 + size o2 + s2_limb o3 */ + +ENTRY(__mpn_mul_1) + !#PROLOGUE# 0 + save %sp,-192,%sp + !#PROLOGUE# 1 + + sub %g0,%i2,%o7 + sllx %o7,3,%g5 + sub %i1,%g5,%o3 + sub %i0,%g5,%o4 + mov 0,%o0 ! zero cy_limb + + srl %i3,0,%o1 ! extract low 32 bits of s2_limb + srlx %i3,32,%i3 ! extract high 32 bits of s2_limb + mov 1,%o2 + sllx %o2,32,%o2 ! o2 = 0x100000000 + + ! hi ! + ! mid-1 ! + ! mid-2 ! + ! lo ! +.Loop: + sllx %o7,3,%g1 + ldx [%o3+%g1],%g5 + srl %g5,0,%i0 ! zero hi bits + srlx %g5,32,%g5 + mulx %o1,%i0,%i4 ! lo product + mulx %i3,%i0,%i1 ! mid-1 product + mulx %o1,%g5,%l2 ! mid-2 product + mulx %i3,%g5,%i5 ! hi product + srlx %i4,32,%i0 ! extract high 32 bits of lo product... + add %i1,%i0,%i1 ! ...and add it to the mid-1 product + addcc %i1,%l2,%i1 ! add mid products + mov 0,%l0 ! we need the carry from that add... + movcs %xcc,%o2,%l0 ! ...compute it and... + add %i5,%l0,%i5 ! ...add to bit 32 of the hi product + sllx %i1,32,%i0 ! align low bits of mid product + srl %i4,0,%g5 ! zero high 32 bits of lo product + add %i0,%g5,%i0 ! combine into low 64 bits of result + srlx %i1,32,%i1 ! extract high bits of mid product... + add %i5,%i1,%i1 ! ...and add them to the high result + addcc %i0,%o0,%i0 ! add cy_limb to low 64 bits of result + mov 0,%g5 + movcs %xcc,1,%g5 + addcc %o7,1,%o7 + stx %i0,[%o4+%g1] + bne,pt %xcc,.Loop + add %i1,%g5,%o0 ! compute new cy_limb + + jmpl %i7+8,%g0 + restore %o0,%g0,%o0 + +END(__mpn_mul_1) diff --git a/src/system/libroot/posix/glibc/arch/sparc/rshift.S b/src/system/libroot/posix/glibc/arch/sparc/rshift.S new file mode 100644 index 0000000000..e3b5854d20 --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/sparc/rshift.S @@ -0,0 +1,92 @@ +/* SPARC v9 __mpn_rshift -- + + Copyright (C) 1996-2018 Free Software Foundation, Inc. + + This file is part of the GNU MP Library. + + The GNU MP Library is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License as published by + the Free Software Foundation; either version 2.1 of the License, or (at your + option) any later version. + + The GNU MP Library is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU Lesser General Public License + along with the GNU MP Library; see the file COPYING.LIB. If not, + see . */ + +#include "sysdep.h" + +/* INPUT PARAMETERS + res_ptr %o0 + src_ptr %o1 + size %o2 + cnt %o3 */ + + .register %g2, #scratch + .register %g3, #scratch + +ENTRY(__mpn_rshift) + ldx [%o1],%g2 ! load first limb + sub %g0,%o3,%o5 ! negate shift count + add %o2,-1,%o2 + andcc %o2,4-1,%g4 ! number of limbs in first loop + sllx %g2,%o5,%g1 ! compute function result + be,pn %xcc,.L0 ! if multiple of 4 limbs, skip first loop + mov %g1,%g5 + + sub %o2,%g4,%o2 ! adjust count for main loop + +.Loop0: ldx [%o1+8],%g3 + add %o0,8,%o0 + add %o1,8,%o1 + srlx %g2,%o3,%o4 + addcc %g4,-1,%g4 + sllx %g3,%o5,%g1 + mov %g3,%g2 + or %o4,%g1,%o4 + bne,pt %xcc,.Loop0 + stx %o4,[%o0-8] + +.L0: brz,pn %o2,.Lend + nop + +.Loop: ldx [%o1+8],%g3 + add %o0,32,%o0 + srlx %g2,%o3,%o4 + addcc %o2,-4,%o2 + sllx %g3,%o5,%g1 + + ldx [%o1+16],%g2 + srlx %g3,%o3,%g4 + or %o4,%g1,%o4 + stx %o4,[%o0-32] + sllx %g2,%o5,%g1 + + ldx [%o1+24],%g3 + srlx %g2,%o3,%o4 + or %g4,%g1,%g4 + stx %g4,[%o0-24] + sllx %g3,%o5,%g1 + + ldx [%o1+32],%g2 + srlx %g3,%o3,%g4 + or %o4,%g1,%o4 + stx %o4,[%o0-16] + sllx %g2,%o5,%g1 + + add %o1,32,%o1 + or %g4,%g1,%g4 + bne,pt %xcc,.Loop + stx %g4,[%o0-8] + +.Lend: srlx %g2,%o3,%g2 + stx %g2,[%o0-0] + + jmpl %o7+8,%g0 + mov %g5,%o0 + +END(__mpn_rshift) diff --git a/src/system/libroot/posix/glibc/arch/sparc/s_isnan.S b/src/system/libroot/posix/glibc/arch/sparc/s_isnan.S new file mode 100644 index 0000000000..47ac0cf247 --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/sparc/s_isnan.S @@ -0,0 +1,33 @@ +/* isnan(). sparc64 version. + Copyright (C) 2012-2018 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#include + +ENTRY (__isnan) + std %f0, [%sp + STACK_BIAS + 128] + sethi %hi(0x7ff00000), %g1 + ldx [%sp + STACK_BIAS + 128], %o0 + sllx %g1, 32, %g1 + sllx %o0, 1, %o0 + srlx %o0, 1, %o0 + sub %g1, %o0, %o0 + retl + srlx %o0, 63, %o0 +END (__isnan) +hidden_def (__isnan) +weak_alias (__isnan, isnan) diff --git a/src/system/libroot/posix/glibc/arch/sparc/s_isnanf.S b/src/system/libroot/posix/glibc/arch/sparc/s_isnanf.S new file mode 100644 index 0000000000..32e80219f7 --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/sparc/s_isnanf.S @@ -0,0 +1,32 @@ +/* isnanf(). sparc64 version. + Copyright (C) 2012-2018 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#include + +ENTRY (__isnanf) + st %f1, [%sp + STACK_BIAS + 128] + sethi %hi(0x7f800000), %g1 + lduw [%sp + STACK_BIAS + 128], %o0 + sll %o0, 1, %o0 + srl %o0, 1, %o0 + sub %g1, %o0, %o0 + retl + srl %o0, 31, %o0 +END (__isnanf) +hidden_def (__isnanf) +weak_alias (__isnanf, isnanf) diff --git a/src/system/libroot/posix/glibc/arch/sparc/sub_n.S b/src/system/libroot/posix/glibc/arch/sparc/sub_n.S new file mode 100644 index 0000000000..2c8eca17a0 --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/sparc/sub_n.S @@ -0,0 +1,54 @@ +/* SPARC v9 __mpn_sub_n -- Subtract two limb vectors of the same length > 0 + and store difference in a third limb vector. + + Copyright (C) 1995-2018 Free Software Foundation, Inc. + + This file is part of the GNU MP Library. + + The GNU MP Library is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License as published by + the Free Software Foundation; either version 2.1 of the License, or (at your + option) any later version. + + The GNU MP Library is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU Lesser General Public License + along with the GNU MP Library; see the file COPYING.LIB. If not, + see . */ + +#include + +/* INPUT PARAMETERS + res_ptr %o0 + s1_ptr %o1 + s2_ptr %o2 + size %o3 */ + +ENTRY(__mpn_sub_n) + + sub %g0,%o3,%g5 + sllx %o3,3,%g1 + add %o1,%g1,%o1 ! make s1_ptr point at end + add %o2,%g1,%o2 ! make s2_ptr point at end + add %o0,%g1,%o0 ! make res_ptr point at end + mov 0,%o4 ! clear carry variable + sllx %g5,3,%o5 ! compute initial address index + +1: ldx [%o2+%o5],%g1 ! load s2 limb + add %g5,1,%g5 ! increment loop count + ldx [%o1+%o5],%o3 ! load s1 limb + addcc %g1,%o4,%g1 ! add s2 limb and carry variable + movcc %xcc,0,%o4 ! if carry-out, o4 was 1; clear it + subcc %o3,%g1,%g1 ! subtract s1 limb from sum + stx %g1,[%o0+%o5] ! store result + add %o5,8,%o5 ! increment address index + brnz,pt %g5,1b + movcs %xcc,1,%o4 ! if s1 subtract gave carry, record it + + retl + mov %o4,%o0 + +END(__mpn_sub_n) diff --git a/src/system/libroot/posix/glibc/arch/sparc/submul_1.S b/src/system/libroot/posix/glibc/arch/sparc/submul_1.S new file mode 100644 index 0000000000..490988303d --- /dev/null +++ b/src/system/libroot/posix/glibc/arch/sparc/submul_1.S @@ -0,0 +1,82 @@ +/* SPARC v9 __mpn_submul_1 -- Multiply a limb vector with a single limb and + subtract the product from a second limb vector. + + Copyright (C) 1996-2018 Free Software Foundation, Inc. + + This file is part of the GNU MP Library. + + The GNU MP Library is free software; you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License as published by + the Free Software Foundation; either version 2.1 of the License, or (at your + option) any later version. + + The GNU MP Library is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU Lesser General Public License + along with the GNU MP Library; see the file COPYING.LIB. If not, + see . */ + +#include + + +/* INPUT PARAMETERS + res_ptr o0 + s1_ptr o1 + size o2 + s2_limb o3 */ + +ENTRY(__mpn_submul_1) + save %sp,-192,%sp + + sub %g0,%i2,%o7 + mov 0,%o0 ! zero cy_limb + sllx %o7,3,%o7 + sethi %hi(0x80000000),%o2 + srl %i3,0,%o1 ! extract low 32 bits of s2_limb + sub %i1,%o7,%o3 + srlx %i3,32,%i3 ! extract high 32 bits of s2_limb + sub %i0,%o7,%o4 + add %o2,%o2,%o2 ! o2 = 0x100000000 + + ! hi ! + ! mid-1 ! + ! mid-2 ! + ! lo ! +1: + ldx [%o3+%o7],%g5 + srl %g5,0,%i0 ! zero hi bits + ldx [%o4+%o7],%l1 + srlx %g5,32,%g5 + mulx %o1,%i0,%i4 ! lo product + mulx %i3,%i0,%i1 ! mid-1 product + mulx %o1,%g5,%l2 ! mid-2 product + mulx %i3,%g5,%i5 ! hi product + srlx %i4,32,%i0 ! extract high 32 bits of lo product... + add %i1,%i0,%i1 ! ...and add it to the mid-1 product + addcc %i1,%l2,%i1 ! add mid products + mov 0,%l0 ! we need the carry from that add... + movcs %xcc,%o2,%l0 ! ...compute it and... + sllx %i1,32,%i0 ! align low bits of mid product + add %i5,%l0,%i5 ! ...add to bit 32 of the hi product + srl %i4,0,%g5 ! zero high 32 bits of lo product + add %i0,%g5,%i0 ! combine into low 64 bits of result + srlx %i1,32,%i1 ! extract high bits of mid product... + addcc %i0,%o0,%i0 ! add cy_limb to low 64 bits of result + add %i5,%i1,%i1 ! ...and add them to the high result + mov 0,%g5 + movcs %xcc,1,%g5 + subcc %l1,%i0,%i0 + stx %i0,[%o4+%o7] + add %g5,1,%l1 + movcs %xcc,%l1,%g5 + addcc %o7,8,%o7 + bne,pt %xcc,1b + add %i1,%g5,%o0 ! compute new cy_limb + + jmpl %i7+8, %g0 + restore %o0,%g0,%o0 + +END(__mpn_submul_1) diff --git a/src/system/libroot/posix/glibc/arch/x86/Jamfile b/src/system/libroot/posix/glibc/arch/x86/Jamfile index 521e11066e..70750e6d5f 100644 --- a/src/system/libroot/posix/glibc/arch/x86/Jamfile +++ b/src/system/libroot/posix/glibc/arch/x86/Jamfile @@ -197,6 +197,8 @@ for architectureObject in [ MultiArchSubDirSetup x86 x86_gcc2 ] { SEARCH on [ FGristFiles $(genericSources) ] = [ FDirName $(HAIKU_TOP) src system libroot posix glibc arch - generic ] ; + generic ] + [ FDirName $(HAIKU_TOP) src system libroot posix glibc arch + generic longdouble 80bit ] ; } } diff --git a/src/system/libroot/posix/glibc/arch/x86_64/Jamfile b/src/system/libroot/posix/glibc/arch/x86_64/Jamfile index 80f50cee88..d92168d95e 100644 --- a/src/system/libroot/posix/glibc/arch/x86_64/Jamfile +++ b/src/system/libroot/posix/glibc/arch/x86_64/Jamfile @@ -140,6 +140,8 @@ for architectureObject in [ MultiArchSubDirSetup x86_64 ] { SEARCH on [ FGristFiles $(genericSources) ] = [ FDirName $(HAIKU_TOP) src system libroot posix glibc arch - generic ] ; + generic ] + [ FDirName $(HAIKU_TOP) src system libroot posix glibc arch + generic longdouble 80bit ] ; } } diff --git a/src/system/libroot/posix/glibc/include/arch/generic/bits/floatn-common.h b/src/system/libroot/posix/glibc/include/arch/generic/bits/floatn-common.h new file mode 100644 index 0000000000..980bfdaf89 --- /dev/null +++ b/src/system/libroot/posix/glibc/include/arch/generic/bits/floatn-common.h @@ -0,0 +1,329 @@ +/* Macros to control TS 18661-3 glibc features where the same + definitions are appropriate for all platforms. + Copyright (C) 2017-2019 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#ifndef _BITS_FLOATN_COMMON_H +#define _BITS_FLOATN_COMMON_H + +#include +#include + +/* This header should be included at the bottom of each bits/floatn.h. + It defines the following macros for each _FloatN and _FloatNx type, + where the same definitions, or definitions based only on the macros + in bits/floatn.h, are appropriate for all glibc configurations. */ + +/* Defined to 1 if the current compiler invocation provides a + floating-point type with the right format for this type, and this + glibc includes corresponding *fN or *fNx interfaces for it. */ +#define __HAVE_FLOAT16 0 +#define __HAVE_FLOAT32 1 +#define __HAVE_FLOAT64 1 +#define __HAVE_FLOAT32X 1 +#define __HAVE_FLOAT128X 0 + +/* Defined to 1 if the corresponding __HAVE_ macro is 1 and the + type is the first with its format in the sequence of (the default + choices for) float, double, long double, _Float16, _Float32, + _Float64, _Float128, _Float32x, _Float64x, _Float128x for this + glibc; that is, if functions present once per floating-point format + rather than once per type are present for this type. + + All configurations supported by glibc have _Float32 the same format + as float, _Float64 and _Float32x the same format as double, the + _Float64x the same format as either long double or _Float128. No + configurations support _Float128x or, as of GCC 7, have compiler + support for a type meeting the requirements for _Float128x. */ +#define __HAVE_DISTINCT_FLOAT16 __HAVE_FLOAT16 +#define __HAVE_DISTINCT_FLOAT32 0 +#define __HAVE_DISTINCT_FLOAT64 0 +#define __HAVE_DISTINCT_FLOAT32X 0 +#define __HAVE_DISTINCT_FLOAT64X 0 +#define __HAVE_DISTINCT_FLOAT128X __HAVE_FLOAT128X + +/* Defined to 1 if the corresponding _FloatN type is not binary compatible + with the corresponding ISO C type in the current compilation unit as + opposed to __HAVE_DISTINCT_FLOATN, which indicates the default types built + in glibc. */ +#define __HAVE_FLOAT128_UNLIKE_LDBL (__HAVE_DISTINCT_FLOAT128 \ + && __LDBL_MANT_DIG__ != 113) + +/* Defined to 1 if any _FloatN or _FloatNx types that are not + ABI-distinct are however distinct types at the C language level (so + for the purposes of __builtin_types_compatible_p and _Generic). */ +#if __GNUC_PREREQ (7, 0) && !defined __cplusplus +# define __HAVE_FLOATN_NOT_TYPEDEF 1 +#else +# define __HAVE_FLOATN_NOT_TYPEDEF 0 +#endif + +#ifndef __ASSEMBLER__ + +/* Defined to concatenate the literal suffix to be used with _FloatN + or _FloatNx types, if __HAVE_ is 1. The corresponding + literal suffixes exist since GCC 7, for C only. */ +# if __HAVE_FLOAT16 +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +/* No corresponding suffix available for this type. */ +# define __f16(x) ((_Float16) x##f) +# else +# define __f16(x) x##f16 +# endif +# endif + +# if __HAVE_FLOAT32 +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +# define __f32(x) x##f +# else +# define __f32(x) x##f32 +# endif +# endif + +# if __HAVE_FLOAT64 +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +# ifdef __NO_LONG_DOUBLE_MATH +# define __f64(x) x##l +# else +# define __f64(x) x +# endif +# else +# define __f64(x) x##f64 +# endif +# endif + +# if __HAVE_FLOAT32X +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +# define __f32x(x) x +# else +# define __f32x(x) x##f32x +# endif +# endif + +# if __HAVE_FLOAT64X +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +# if __HAVE_FLOAT64X_LONG_DOUBLE +# define __f64x(x) x##l +# else +# define __f64x(x) __f128 (x) +# endif +# else +# define __f64x(x) x##f64x +# endif +# endif + +# if __HAVE_FLOAT128X +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +# error "_Float128X supported but no constant suffix" +# else +# define __f128x(x) x##f128x +# endif +# endif + +/* Defined to a complex type if __HAVE_ is 1. */ +# if __HAVE_FLOAT16 +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +typedef _Complex float __cfloat16 __attribute__ ((__mode__ (__HC__))); +# define __CFLOAT16 __cfloat16 +# else +# define __CFLOAT16 _Complex _Float16 +# endif +# endif + +# if __HAVE_FLOAT32 +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +# define __CFLOAT32 _Complex float +# else +# define __CFLOAT32 _Complex _Float32 +# endif +# endif + +# if __HAVE_FLOAT64 +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +# ifdef __NO_LONG_DOUBLE_MATH +# define __CFLOAT64 _Complex long double +# else +# define __CFLOAT64 _Complex double +# endif +# else +# define __CFLOAT64 _Complex _Float64 +# endif +# endif + +# if __HAVE_FLOAT32X +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +# define __CFLOAT32X _Complex double +# else +# define __CFLOAT32X _Complex _Float32x +# endif +# endif + +# if __HAVE_FLOAT64X +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +# if __HAVE_FLOAT64X_LONG_DOUBLE +# define __CFLOAT64X _Complex long double +# else +# define __CFLOAT64X __CFLOAT128 +# endif +# else +# define __CFLOAT64X _Complex _Float64x +# endif +# endif + +# if __HAVE_FLOAT128X +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +# error "_Float128X supported but no complex type" +# else +# define __CFLOAT128X _Complex _Float128x +# endif +# endif + +/* The remaining of this file provides support for older compilers. */ +# if __HAVE_FLOAT16 + +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +typedef float _Float16 __attribute__ ((__mode__ (__HF__))); +# endif + +# if !__GNUC_PREREQ (7, 0) +# define __builtin_huge_valf16() ((_Float16) __builtin_huge_val ()) +# define __builtin_inff16() ((_Float16) __builtin_inf ()) +# define __builtin_nanf16(x) ((_Float16) __builtin_nan (x)) +# define __builtin_nansf16(x) ((_Float16) __builtin_nans (x)) +# endif + +# endif + +# if __HAVE_FLOAT32 + +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +typedef float _Float32; +# endif + +# if !__GNUC_PREREQ (7, 0) +# define __builtin_huge_valf32() (__builtin_huge_valf ()) +# define __builtin_inff32() (__builtin_inff ()) +# define __builtin_nanf32(x) (__builtin_nanf (x)) +# define __builtin_nansf32(x) (__builtin_nansf (x)) +# endif + +# endif + +# if __HAVE_FLOAT64 + +/* If double, long double and _Float64 all have the same set of + values, TS 18661-3 requires the usual arithmetic conversions on + long double and _Float64 to produce _Float64. For this to be the + case when building with a compiler without a distinct _Float64 + type, _Float64 must be a typedef for long double, not for + double. */ + +# ifdef __NO_LONG_DOUBLE_MATH + +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +typedef long double _Float64; +# endif + +# if !__GNUC_PREREQ (7, 0) +# define __builtin_huge_valf64() (__builtin_huge_vall ()) +# define __builtin_inff64() (__builtin_infl ()) +# define __builtin_nanf64(x) (__builtin_nanl (x)) +# define __builtin_nansf64(x) (__builtin_nansl (x)) +# endif + +# else + +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +typedef double _Float64; +# endif + +# if !__GNUC_PREREQ (7, 0) +# define __builtin_huge_valf64() (__builtin_huge_val ()) +# define __builtin_inff64() (__builtin_inf ()) +# define __builtin_nanf64(x) (__builtin_nan (x)) +# define __builtin_nansf64(x) (__builtin_nans (x)) +# endif + +# endif + +# endif + +# if __HAVE_FLOAT32X + +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +typedef double _Float32x; +# endif + +# if !__GNUC_PREREQ (7, 0) +# define __builtin_huge_valf32x() (__builtin_huge_val ()) +# define __builtin_inff32x() (__builtin_inf ()) +# define __builtin_nanf32x(x) (__builtin_nan (x)) +# define __builtin_nansf32x(x) (__builtin_nans (x)) +# endif + +# endif + +# if __HAVE_FLOAT64X + +# if __HAVE_FLOAT64X_LONG_DOUBLE + +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +typedef long double _Float64x; +# endif + +# if !__GNUC_PREREQ (7, 0) +# define __builtin_huge_valf64x() (__builtin_huge_vall ()) +# define __builtin_inff64x() (__builtin_infl ()) +# define __builtin_nanf64x(x) (__builtin_nanl (x)) +# define __builtin_nansf64x(x) (__builtin_nansl (x)) +# endif + +# else + +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +typedef _Float128 _Float64x; +# endif + +# if !__GNUC_PREREQ (7, 0) +# define __builtin_huge_valf64x() (__builtin_huge_valf128 ()) +# define __builtin_inff64x() (__builtin_inff128 ()) +# define __builtin_nanf64x(x) (__builtin_nanf128 (x)) +# define __builtin_nansf64x(x) (__builtin_nansf128 (x)) +# endif + +# endif + +# endif + +# if __HAVE_FLOAT128X + +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +# error "_Float128x supported but no type" +# endif + +# if !__GNUC_PREREQ (7, 0) +# define __builtin_huge_valf128x() ((_Float128x) __builtin_huge_val ()) +# define __builtin_inff128x() ((_Float128x) __builtin_inf ()) +# define __builtin_nanf128x(x) ((_Float128x) __builtin_nan (x)) +# define __builtin_nansf128x(x) ((_Float128x) __builtin_nans (x)) +# endif + +# endif + +#endif /* !__ASSEMBLER__. */ + +#endif /* _BITS_FLOATN_COMMON_H */ diff --git a/src/system/libroot/posix/glibc/include/arch/generic/dla.h b/src/system/libroot/posix/glibc/include/arch/generic/dla.h new file mode 100644 index 0000000000..d64bb1e246 --- /dev/null +++ b/src/system/libroot/posix/glibc/include/arch/generic/dla.h @@ -0,0 +1,183 @@ +/* + * IBM Accurate Mathematical Library + * Written by International Business Machines Corp. + * Copyright (C) 2001-2019 Free Software Foundation, Inc. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, see . + */ + +#include + +/***********************************************************************/ +/*MODULE_NAME: dla.h */ +/* */ +/* This file holds C language macros for 'Double Length Floating Point */ +/* Arithmetic'. The macros are based on the paper: */ +/* T.J.Dekker, "A floating-point Technique for extending the */ +/* Available Precision", Number. Math. 18, 224-242 (1971). */ +/* A Double-Length number is defined by a pair (r,s), of IEEE double */ +/* precision floating point numbers that satisfy, */ +/* */ +/* abs(s) <= abs(r+s)*2**(-53)/(1+2**(-53)). */ +/* */ +/* The computer arithmetic assumed is IEEE double precision in */ +/* round to nearest mode. All variables in the macros must be of type */ +/* IEEE double. */ +/***********************************************************************/ + +/* CN = 1+2**27 = '41a0000002000000' IEEE double format. Use it to split a + double for better accuracy. */ +#define CN 134217729.0 + + +/* Exact addition of two single-length floating point numbers, Dekker. */ +/* The macro produces a double-length number (z,zz) that satisfies */ +/* z+zz = x+y exactly. */ + +#define EADD(x,y,z,zz) \ + z=(x)+(y); zz=(fabs(x)>fabs(y)) ? (((x)-(z))+(y)) : (((y)-(z))+(x)); + + +/* Exact subtraction of two single-length floating point numbers, Dekker. */ +/* The macro produces a double-length number (z,zz) that satisfies */ +/* z+zz = x-y exactly. */ + +#define ESUB(x,y,z,zz) \ + z=(x)-(y); zz=(fabs(x)>fabs(y)) ? (((x)-(z))-(y)) : ((x)-((y)+(z))); + + +#ifdef __FP_FAST_FMA +# define DLA_FMS(x, y, z) __builtin_fma (x, y, -(z)) +#endif + +/* Exact multiplication of two single-length floating point numbers, */ +/* Veltkamp. The macro produces a double-length number (z,zz) that */ +/* satisfies z+zz = x*y exactly. p,hx,tx,hy,ty are temporary */ +/* storage variables of type double. */ + +#ifdef DLA_FMS +# define EMULV(x, y, z, zz, p, hx, tx, hy, ty) \ + z = x * y; zz = DLA_FMS (x, y, z); +#else +# define EMULV(x, y, z, zz, p, hx, tx, hy, ty) \ + p = CN * (x); hx = ((x) - p) + p; tx = (x) - hx; \ + p = CN * (y); hy = ((y) - p) + p; ty = (y) - hy; \ + z = (x) * (y); zz = (((hx * hy - z) + hx * ty) + tx * hy) + tx * ty; +#endif + + +/* Exact multiplication of two single-length floating point numbers, Dekker. */ +/* The macro produces a nearly double-length number (z,zz) (see Dekker) */ +/* that satisfies z+zz = x*y exactly. p,hx,tx,hy,ty,q are temporary */ +/* storage variables of type double. */ + +#ifdef DLA_FMS +# define MUL12(x,y,z,zz,p,hx,tx,hy,ty,q) \ + EMULV(x,y,z,zz,p,hx,tx,hy,ty) +#else +# define MUL12(x,y,z,zz,p,hx,tx,hy,ty,q) \ + p=CN*(x); hx=((x)-p)+p; tx=(x)-hx; \ + p=CN*(y); hy=((y)-p)+p; ty=(y)-hy; \ + p=hx*hy; q=hx*ty+tx*hy; z=p+q; zz=((p-z)+q)+tx*ty; +#endif + + +/* Double-length addition, Dekker. The macro produces a double-length */ +/* number (z,zz) which satisfies approximately z+zz = x+xx + y+yy. */ +/* An error bound: (abs(x+xx)+abs(y+yy))*4.94e-32. (x,xx), (y,yy) */ +/* are assumed to be double-length numbers. r,s are temporary */ +/* storage variables of type double. */ + +#define ADD2(x, xx, y, yy, z, zz, r, s) \ + r = (x) + (y); s = (fabs (x) > fabs (y)) ? \ + (((((x) - r) + (y)) + (yy)) + (xx)) : \ + (((((y) - r) + (x)) + (xx)) + (yy)); \ + z = r + s; zz = (r - z) + s; + + +/* Double-length subtraction, Dekker. The macro produces a double-length */ +/* number (z,zz) which satisfies approximately z+zz = x+xx - (y+yy). */ +/* An error bound: (abs(x+xx)+abs(y+yy))*4.94e-32. (x,xx), (y,yy) */ +/* are assumed to be double-length numbers. r,s are temporary */ +/* storage variables of type double. */ + +#define SUB2(x, xx, y, yy, z, zz, r, s) \ + r = (x) - (y); s = (fabs (x) > fabs (y)) ? \ + (((((x) - r) - (y)) - (yy)) + (xx)) : \ + ((((x) - ((y) + r)) + (xx)) - (yy)); \ + z = r + s; zz = (r - z) + s; + + +/* Double-length multiplication, Dekker. The macro produces a double-length */ +/* number (z,zz) which satisfies approximately z+zz = (x+xx)*(y+yy). */ +/* An error bound: abs((x+xx)*(y+yy))*1.24e-31. (x,xx), (y,yy) */ +/* are assumed to be double-length numbers. p,hx,tx,hy,ty,q,c,cc are */ +/* temporary storage variables of type double. */ + +#define MUL2(x, xx, y, yy, z, zz, p, hx, tx, hy, ty, q, c, cc) \ + MUL12 (x, y, c, cc, p, hx, tx, hy, ty, q) \ + cc = ((x) * (yy) + (xx) * (y)) + cc; z = c + cc; zz = (c - z) + cc; + + +/* Double-length division, Dekker. The macro produces a double-length */ +/* number (z,zz) which satisfies approximately z+zz = (x+xx)/(y+yy). */ +/* An error bound: abs((x+xx)/(y+yy))*1.50e-31. (x,xx), (y,yy) */ +/* are assumed to be double-length numbers. p,hx,tx,hy,ty,q,c,cc,u,uu */ +/* are temporary storage variables of type double. */ + +#define DIV2(x,xx,y,yy,z,zz,p,hx,tx,hy,ty,q,c,cc,u,uu) \ + c=(x)/(y); MUL12(c,y,u,uu,p,hx,tx,hy,ty,q) \ + cc=(((((x)-u)-uu)+(xx))-c*(yy))/(y); z=c+cc; zz=(c-z)+cc; + + +/* Double-length addition, slower but more accurate than ADD2. */ +/* The macro produces a double-length */ +/* number (z,zz) which satisfies approximately z+zz = (x+xx)+(y+yy). */ +/* An error bound: abs(x+xx + y+yy)*1.50e-31. (x,xx), (y,yy) */ +/* are assumed to be double-length numbers. r,rr,s,ss,u,uu,w */ +/* are temporary storage variables of type double. */ + +#define ADD2A(x, xx, y, yy, z, zz, r, rr, s, ss, u, uu, w) \ + r = (x) + (y); \ + if (fabs (x) > fabs (y)) { rr = ((x) - r) + (y); s = (rr + (yy)) + (xx); } \ + else { rr = ((y) - r) + (x); s = (rr + (xx)) + (yy); } \ + if (rr != 0.0) { \ + z = r + s; zz = (r - z) + s; } \ + else { \ + ss = (fabs (xx) > fabs (yy)) ? (((xx) - s) + (yy)) : (((yy) - s) + (xx));\ + u = r + s; \ + uu = (fabs (r) > fabs (s)) ? ((r - u) + s) : ((s - u) + r); \ + w = uu + ss; z = u + w; \ + zz = (fabs (u) > fabs (w)) ? ((u - z) + w) : ((w - z) + u); } + + +/* Double-length subtraction, slower but more accurate than SUB2. */ +/* The macro produces a double-length */ +/* number (z,zz) which satisfies approximately z+zz = (x+xx)-(y+yy). */ +/* An error bound: abs(x+xx - (y+yy))*1.50e-31. (x,xx), (y,yy) */ +/* are assumed to be double-length numbers. r,rr,s,ss,u,uu,w */ +/* are temporary storage variables of type double. */ + +#define SUB2A(x, xx, y, yy, z, zz, r, rr, s, ss, u, uu, w) \ + r = (x) - (y); \ + if (fabs (x) > fabs (y)) { rr = ((x) - r) - (y); s = (rr - (yy)) + (xx); } \ + else { rr = (x) - ((y) + r); s = (rr + (xx)) - (yy); } \ + if (rr != 0.0) { \ + z = r + s; zz = (r - z) + s; } \ + else { \ + ss = (fabs (xx) > fabs (yy)) ? (((xx) - s) - (yy)) : ((xx) - ((yy) + s)); \ + u = r + s; \ + uu = (fabs (r) > fabs (s)) ? ((r - u) + s) : ((s - u) + r); \ + w = uu + ss; z = u + w; \ + zz = (fabs (u) > fabs (w)) ? ((u - z) + w) : ((w - z) + u); } diff --git a/src/system/libroot/posix/glibc/include/arch/generic/libm-alias-ldouble.h b/src/system/libroot/posix/glibc/include/arch/generic/libm-alias-ldouble.h new file mode 100644 index 0000000000..4d5246fef7 --- /dev/null +++ b/src/system/libroot/posix/glibc/include/arch/generic/libm-alias-ldouble.h @@ -0,0 +1,65 @@ +/* Define aliases for libm long double functions. + Copyright (C) 2017-2019 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#ifndef _LIBM_ALIAS_LDOUBLE_H +#define _LIBM_ALIAS_LDOUBLE_H + +#include + +#if __HAVE_FLOAT128 && !__HAVE_DISTINCT_FLOAT128 +# define libm_alias_ldouble_other_r_f128(from, to, r) \ + weak_alias (from ## l ## r, to ## f128 ## r) +#else +# define libm_alias_ldouble_other_r_f128(from, to, r) +#endif + +#if __HAVE_FLOAT64X_LONG_DOUBLE +# define libm_alias_ldouble_other_r_f64x(from, to, r) \ + weak_alias (from ## l ## r, to ## f64x ## r) +#else +# define libm_alias_ldouble_other_r_f64x(from, to, r) +#endif + +/* Define _FloatN / _FloatNx aliases for a long double libm function + that has internal name FROM ## l ## R and public names TO ## suffix + ## R for each suffix of a supported _FloatN / _FloatNx + floating-point type with the same format as long double. */ +#define libm_alias_ldouble_other_r(from, to, r) \ + libm_alias_ldouble_other_r_f128 (from, to, r); \ + libm_alias_ldouble_other_r_f64x (from, to, r) + +/* Likewise, but without the R suffix. */ +#define libm_alias_ldouble_other(from, to) \ + libm_alias_ldouble_other_r (from, to, ) + +/* Define aliases for a long double libm function that has internal + name FROM ## l ## R and public names TO ## suffix ## R for each + suffix of a supported floating-point type with the same format as + long double. This should only be used for functions where such + public names exist for _FloatN types, not for + implementation-namespace exported names (where there is one name + per format, not per type) or for obsolescent functions not provided + for _FloatN types. */ +#define libm_alias_ldouble_r(from, to, r) \ + weak_alias (from ## l ## r, to ## l ## r); \ + libm_alias_ldouble_other_r (from, to, r) + +/* Likewise, but without the R suffix. */ +#define libm_alias_ldouble(from, to) libm_alias_ldouble_r (from, to, ) + +#endif diff --git a/src/system/libroot/posix/glibc/include/arch/generic/nan-high-order-bit.h b/src/system/libroot/posix/glibc/include/arch/generic/nan-high-order-bit.h new file mode 100644 index 0000000000..f3a87f0316 --- /dev/null +++ b/src/system/libroot/posix/glibc/include/arch/generic/nan-high-order-bit.h @@ -0,0 +1,27 @@ +/* Specify NaN high-order bit conventions. Generic version. + Copyright (C) 2016-2019 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#ifndef NAN_HIGH_ORDER_BIT_H +#define NAN_HIGH_ORDER_BIT_H 1 + +/* Define this macro to 1 if the high-order bit of a NaN's mantissa is + set for signaling NaNs and clear for quiet NaNs, 0 otherwise (the + preferred IEEE convention). */ +#define HIGH_ORDER_BIT_IS_SET_FOR_SNAN 0 + +#endif /* nan-high-order-bit.h */ diff --git a/src/system/libroot/posix/glibc/include/arch/sparc/bits/fenv.h b/src/system/libroot/posix/glibc/include/arch/sparc/bits/fenv.h index 90cfa2089f..77a2520114 100644 --- a/src/system/libroot/posix/glibc/include/arch/sparc/bits/fenv.h +++ b/src/system/libroot/posix/glibc/include/arch/sparc/bits/fenv.h @@ -1,4 +1,4 @@ -/* Copyright (C) 1997-2012 Free Software Foundation, Inc. +/* Copyright (C) 1997-2018 Free Software Foundation, Inc. This file is part of the GNU C Library. The GNU C Library is free software; you can redistribute it and/or @@ -19,70 +19,61 @@ # error "Never use directly; include instead." #endif +#include + + /* Define bits representing the exception. We use the bit positions - of the appropriate bits in the FPU control word. */ + of the appropriate accrued exception bits from the FSR. */ enum { - FE_INVALID = 0x01, -#define FE_INVALID FE_INVALID - __FE_DENORM = 0x02, - FE_DIVBYZERO = 0x04, -#define FE_DIVBYZERO FE_DIVBYZERO - FE_OVERFLOW = 0x08, -#define FE_OVERFLOW FE_OVERFLOW - FE_UNDERFLOW = 0x10, -#define FE_UNDERFLOW FE_UNDERFLOW - FE_INEXACT = 0x20 -#define FE_INEXACT FE_INEXACT + FE_INVALID = +#define FE_INVALID (1 << 9) + FE_INVALID, + FE_OVERFLOW = +#define FE_OVERFLOW (1 << 8) + FE_OVERFLOW, + FE_UNDERFLOW = +#define FE_UNDERFLOW (1 << 7) + FE_UNDERFLOW, + FE_DIVBYZERO = +#define FE_DIVBYZERO (1 << 6) + FE_DIVBYZERO, + FE_INEXACT = +#define FE_INEXACT (1 << 5) + FE_INEXACT }; #define FE_ALL_EXCEPT \ (FE_INEXACT | FE_DIVBYZERO | FE_UNDERFLOW | FE_OVERFLOW | FE_INVALID) -/* The ix87 FPU supports all of the four defined rounding modes. We +/* The Sparc FPU supports all of the four defined rounding modes. We use again the bit positions in the FPU control word as the values for the appropriate macros. */ enum { - FE_TONEAREST = 0, -#define FE_TONEAREST FE_TONEAREST - FE_DOWNWARD = 0x400, -#define FE_DOWNWARD FE_DOWNWARD - FE_UPWARD = 0x800, -#define FE_UPWARD FE_UPWARD - FE_TOWARDZERO = 0xc00 -#define FE_TOWARDZERO FE_TOWARDZERO + FE_TONEAREST = +#define FE_TONEAREST (0 << 30) + FE_TONEAREST, + FE_TOWARDZERO = +#define FE_TOWARDZERO (1 << 30) + FE_TOWARDZERO, + FE_UPWARD = +#define FE_UPWARD (-0x7fffffff - 1) /* (2 << 30) */ + FE_UPWARD, + FE_DOWNWARD = +#define FE_DOWNWARD (-0x40000000) /* (3 << 30) */ + FE_DOWNWARD }; +#define __FE_ROUND_MASK (3U << 30) + /* Type representing exception flags. */ -typedef unsigned short int fexcept_t; +typedef unsigned long int fexcept_t; -/* Type representing floating-point environment. This structure - corresponds to the layout of the block written by the `fstenv' - instruction and has additional fields for the contents of the MXCSR - register as written by the `stmxcsr' instruction. */ -typedef struct - { - unsigned short int __control_word; - unsigned short int __unused1; - unsigned short int __status_word; - unsigned short int __unused2; - unsigned short int __tags; - unsigned short int __unused3; - unsigned int __eip; - unsigned short int __cs_selector; - unsigned int __opcode:11; - unsigned int __unused4:5; - unsigned int __data_offset; - unsigned short int __data_selector; - unsigned short int __unused5; -#ifdef __x86_64__ - unsigned int __mxcsr; -#endif - } -fenv_t; +/* Type representing floating-point environment. */ +typedef unsigned long int fenv_t; /* If the default argument is used we use this value. */ #define FE_DFL_ENV ((const fenv_t *) -1) @@ -92,3 +83,6 @@ fenv_t; # define FE_NOMASK_ENV ((const fenv_t *) -2) #endif +/* For internal use only: access the fp state register. */ +# define __fenv_stfsr(X) __asm__ __volatile__ ("stx %%fsr,%0" : "=m" (X)) +# define __fenv_ldfsr(X) __asm__ __volatile__ ("ldx %0,%%fsr" : : "m" (X)) diff --git a/src/system/libroot/posix/glibc/include/arch/sparc/bits/floatn.h b/src/system/libroot/posix/glibc/include/arch/sparc/bits/floatn.h new file mode 100644 index 0000000000..fb31be29e6 --- /dev/null +++ b/src/system/libroot/posix/glibc/include/arch/sparc/bits/floatn.h @@ -0,0 +1,97 @@ +/* Macros to control TS 18661-3 glibc features on ldbl-128 platforms. + Copyright (C) 2017-2019 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#ifndef _BITS_FLOATN_H +#define _BITS_FLOATN_H + +#include +#include + +/* Defined to 1 if the current compiler invocation provides a + floating-point type with the IEEE 754 binary128 format, and this + glibc includes corresponding *f128 interfaces for it. */ +#ifndef __NO_LONG_DOUBLE_MATH +# define __HAVE_FLOAT128 1 +#else +/* glibc does not support _Float128 for platforms where long double is + normally binary128 when building with long double as binary64. + GCC's default for supported scalar modes does not support it either + in that case. */ +# define __HAVE_FLOAT128 0 +#endif + +/* Defined to 1 if __HAVE_FLOAT128 is 1 and the type is ABI-distinct + from the default float, double and long double types in this glibc. */ +#define __HAVE_DISTINCT_FLOAT128 0 + +/* Defined to 1 if the current compiler invocation provides a + floating-point type with the right format for _Float64x, and this + glibc includes corresponding *f64x interfaces for it. */ +#define __HAVE_FLOAT64X __HAVE_FLOAT128 + +/* Defined to 1 if __HAVE_FLOAT64X is 1 and _Float64x has the format + of long double. Otherwise, if __HAVE_FLOAT64X is 1, _Float64x has + the format of _Float128, which must be different from that of long + double. */ +#define __HAVE_FLOAT64X_LONG_DOUBLE __HAVE_FLOAT128 + +#ifndef __ASSEMBLER__ + +/* Defined to concatenate the literal suffix to be used with _Float128 + types, if __HAVE_FLOAT128 is 1. */ +# if __HAVE_FLOAT128 +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +/* The literal suffix f128 exists only since GCC 7.0. */ +# define __f128(x) x##l +# else +# define __f128(x) x##f128 +# endif +# endif + +/* Defined to a complex binary128 type if __HAVE_FLOAT128 is 1. */ +# if __HAVE_FLOAT128 +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +# define __CFLOAT128 _Complex long double +# else +# define __CFLOAT128 _Complex _Float128 +# endif +# endif + +/* The remaining of this file provides support for older compilers. */ +# if __HAVE_FLOAT128 + +/* The type _Float128 exists only since GCC 7.0. */ +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +typedef long double _Float128; +# endif + +/* Various built-in functions do not exist before GCC 7.0. */ +# if !__GNUC_PREREQ (7, 0) +# define __builtin_huge_valf128() (__builtin_huge_vall ()) +# define __builtin_inff128() (__builtin_infl ()) +# define __builtin_nanf128(x) (__builtin_nanl (x)) +# define __builtin_nansf128(x) (__builtin_nansl (x)) +# endif + +# endif + +#endif /* !__ASSEMBLER__. */ + +#include + +#endif /* _BITS_FLOATN_H */ diff --git a/src/system/libroot/posix/glibc/include/arch/sparc/bits/hwcap.h b/src/system/libroot/posix/glibc/include/arch/sparc/bits/hwcap.h new file mode 100644 index 0000000000..a991029f02 --- /dev/null +++ b/src/system/libroot/posix/glibc/include/arch/sparc/bits/hwcap.h @@ -0,0 +1,51 @@ +/* Defines for bits in AT_HWCAP. + Copyright (C) 2011-2018 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#if !defined(_SYS_AUXV_H) && !defined(_SYSDEPS_SYSDEP_H) +# error "Never include directly; use instead." +#endif + +#define HWCAP_SPARC_FLUSH 0x00000001 +#define HWCAP_SPARC_STBAR 0x00000002 +#define HWCAP_SPARC_SWAP 0x00000004 +#define HWCAP_SPARC_MULDIV 0x00000008 +#define HWCAP_SPARC_V9 0x00000010 +#define HWCAP_SPARC_ULTRA3 0x00000020 +#define HWCAP_SPARC_BLKINIT 0x00000040 +#define HWCAP_SPARC_N2 0x00000080 +#define HWCAP_SPARC_MUL32 0x00000100 +#define HWCAP_SPARC_DIV32 0x00000200 +#define HWCAP_SPARC_FSMULD 0x00000400 +#define HWCAP_SPARC_V8PLUS 0x00000800 +#define HWCAP_SPARC_POPC 0x00001000 +#define HWCAP_SPARC_VIS 0x00002000 +#define HWCAP_SPARC_VIS2 0x00004000 +#define HWCAP_SPARC_ASI_BLK_INIT 0x00008000 +#define HWCAP_SPARC_FMAF 0x00010000 +#define HWCAP_SPARC_VIS3 0x00020000 +#define HWCAP_SPARC_HPC 0x00040000 +#define HWCAP_SPARC_RANDOM 0x00080000 +#define HWCAP_SPARC_TRANS 0x00100000 +#define HWCAP_SPARC_FJFMAU 0x00200000 +#define HWCAP_SPARC_IMA 0x00400000 +#define HWCAP_SPARC_ASI_CACHE_SPARING \ + 0x00800000 +#define HWCAP_SPARC_PAUSE 0x01000000 +#define HWCAP_SPARC_CBCOND 0x02000000 +#define HWCAP_SPARC_CRYPTO 0x04000000 +#define HWCAP_SPARC_ADP 0x08000000 diff --git a/src/system/libroot/posix/glibc/include/arch/sparc/bits/long-double.h b/src/system/libroot/posix/glibc/include/arch/sparc/bits/long-double.h new file mode 100644 index 0000000000..df9d588df5 --- /dev/null +++ b/src/system/libroot/posix/glibc/include/arch/sparc/bits/long-double.h @@ -0,0 +1,20 @@ +/* Properties of long double type. ldbl-128 version. + Copyright (C) 2016-2019 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +/* long double is distinct from double, so there is nothing to + define here. */ diff --git a/src/system/libroot/posix/glibc/include/arch/sparc/config.h b/src/system/libroot/posix/glibc/include/arch/sparc/config.h index e69de29bb2..557c4695ed 100644 --- a/src/system/libroot/posix/glibc/include/arch/sparc/config.h +++ b/src/system/libroot/posix/glibc/include/arch/sparc/config.h @@ -0,0 +1,235 @@ +//#if !defined __ASSEMBLER__ && !defined _ISOMAC && !defined __OPTIMIZE__ +//# error "glibc cannot be compiled without optimization" +//#endif + +/* Another evil option when it comes to compiling the C library is + --ffast-math since it alters the ABI. */ +#if defined __FAST_MATH__ && !defined TEST_FAST_MATH +# error "glibc must not be compiled with -ffast-math" +#endif + +/* Define if using GNU ld, with support for weak symbols in a.out, + and for symbol set and warning messages extensions in a.out and ELF. + This implies HAVE_WEAK_SYMBOLS; set by --with-gnu-ld. */ +#define HAVE_GNU_LD 1 + +/* Define if using ELF, which supports weak symbols. + This implies HAVE_ASM_WEAK_DIRECTIVE set by --with-elf. */ +#define HAVE_ELF 1 + +/* Define if using XCOFF. Set by --with-xcoff. */ +#undef HAVE_XCOFF + +/* Define if weak symbols are available via the `.weak' directive. */ +#define HAVE_ASM_WEAK_DIRECTIVE 1 + +/* Define if weak symbols are available via the `.weakext' directive. */ +#undef HAVE_ASM_WEAKEXT_DIRECTIVE + +/* Define to the assembler line separator character for multiple + assembler instructions per line. Default is `;' */ +#undef ASM_LINE_SEP + +/* Define if not using ELF, but `.init' and `.fini' sections are available. */ +#undef HAVE_INITFINI + +/* Define if __attribute__((section("foo"))) puts quotes around foo. */ +/*#define HAVE_SECTION_QUOTES 1 + [zooey]: defining this causes assembler errors, and I don't think + that any BeOS-gcc actually produces quotes in sections... +*/ +#undef HAVE_SECTION_QUOTES + +/* Define if using the GNU assembler, gas. */ +#define HAVE_GNU_AS 1 + +/* Define if the assembler supports the `.set' directive. */ +#define HAVE_ASM_SET_DIRECTIVE 1 + +/* Define to the name of the assembler's directive for + declaring a symbol global (default `.globl'). */ +#define ASM_GLOBAL_DIRECTIVE .globl + +/* Define to the prefix before `object' or `function' in the + assembler's `.type' directive, if it has one. */ +#undef ASM_TYPE_DIRECTIVE_PREFIX + +/* Define a symbol_name as a global .symbol_name for ld. */ +#undef HAVE_ASM_GLOBAL_DOT_NAME + +/* Define if the assembler generates debugging information directly. */ +#undef HAVE_CPP_ASM_DEBUGINFO + +/* Define if _Unwind_Find_FDE should be exported from glibc. */ +#undef EXPORT_UNWIND_FIND_FDE + +/* Define to use GNU libio instead of GNU stdio. + This is defined by configure under --enable-libio. */ +#define USE_IN_LIBIO 1 + +/* Define if using ELF and the assembler supports the `.previous' + directive. */ +#define HAVE_ASM_PREVIOUS_DIRECTIVE 1 + +/* Define if using ELF and the assembler supports the `.popsection' + directive. */ +#undef HAVE_ASM_POPSECTION_DIRECTIVE + +/* Define if versioning of the library is wanted. */ +#undef DO_VERSIONING + +/* Defined to the oldest ABI we support, like 2.1. */ +#undef GLIBC_OLDEST_ABI + +/* Define if static NSS modules are wanted. */ +#undef DO_STATIC_NSS + +/* Define if gcc uses DWARF2 unwind information for exception support. */ +#define HAVE_DWARF2_UNWIND_INFO 1 + +/* Define if gcc uses DWARF2 unwind information for exception support + with static variable. */ +#define HAVE_DWARF2_UNWIND_INFO_STATIC 1 + +/* Define if the compiler supports __builtin_expect. */ +#undef HAVE_BUILTIN_EXPECT + +/* Define if the compiler supports __builtin_memset. */ +#undef HAVE_BUILTIN_MEMSET + +/* Define if the __thread keyword is supported. */ +#undef HAVE___THREAD + +/* Define if the compiler supports __attribute__((tls_model(""))). */ +#undef HAVE_TLS_MODEL_ATTRIBUTE + +/* Define if the regparm attribute shall be used for local functions + (gcc on ix86 only). */ +#define USE_REGPARMS 0 + +/* Defined on PowerPC if the GCC being used has a problem with clobbering + certain registers (CR0, MQ, CTR, LR) in asm statements. */ +#undef BROKEN_PPC_ASM_CR0 + +/* Defined on SPARC if ld doesn't handle R_SPARC_WDISP22 against .hidden + symbol. sysdeps/sparc/sparc32/elf/configure. */ +#undef BROKEN_SPARC_WDISP22 + +/* Define if the linker supports the -z combreloc option. */ +#undef HAVE_Z_COMBRELOC + +/* Define if the assembler supported .protected. */ +#undef HAVE_PROTECTED + +/* Define if the assembler supported .hidden. */ +#undef HAVE_HIDDEN + +/* Define if the compiler supports __attribute__ ((visibility (...))). */ +#undef HAVE_VISIBILITY_ATTRIBUTE + +/* Define if the compiler doesn't support __attribute__ ((visibility (...))) + together with __asm__ redirection properly. */ +#undef HAVE_BROKEN_VISIBILITY_ATTRIBUTE + +/* Define if the compiler doesn't support __attribute__ ((alias (...))) + together with __asm__ redirection properly. */ +#undef HAVE_BROKEN_ALIAS_ATTRIBUTE + +/* Define if _rtld_local structure should be forced into .sdata section. */ +#undef HAVE_SDATA_SECTION + +/* Define if binutils support TLS handling. */ +#undef HAVE_TLS_SUPPORT + +/* Define if the linker supports .preinit_array/.init_array/.fini_array + sections. */ +#undef HAVE_INITFINI_ARRAY + +/* Define if the access to static and hidden variables is position independent + and does not need relocations. */ +#undef PI_STATIC_AND_HIDDEN + +/* Define this to disable the `hidden_proto' et al macros in + include/libc-symbols.h that avoid PLT slots in the shared objects. */ +#undef NO_HIDDEN + + +/* Defined to some form of __attribute__ ((...)) if the compiler supports + a different, more efficient calling convention. */ +#if USE_REGPARMS && !defined PROF && !defined __BOUNDED_POINTERS__ +# define internal_function __attribute__ ((regparm (3), stdcall)) +#endif + +/* Linux specific: minimum supported kernel version. */ +#undef __LINUX_KERNEL_VERSION + +/* Override abi-tags ABI version if necessary. */ +#undef __ABI_TAG_VERSION + +/* An extension in gcc 2.96 and up allows the subtraction of two + local labels. */ +#undef HAVE_SUBTRACT_LOCAL_LABELS + +/* bash 2.0 introduced the _XXX_GNU_nonoption_argv_flags_ variable to help + getopt determine whether a parameter is a flag or not. This features + was disabled later since it caused trouble. We are by default therefore + disabling the support as well. */ +#undef USE_NONOPTION_FLAGS + +/* Mach/Hurd specific: define if mig supports the `retcode' keyword. */ +#undef HAVE_MIG_RETCODE + +/* Mach specific: define if the `host_page_size' RPC is available. */ +#undef HAVE_HOST_PAGE_SIZE + +/* Mach/i386 specific: define if the `i386_io_perm_*' RPCs are available. */ +#undef HAVE_I386_IO_PERM_MODIFY + +/* Mach/i386 specific: define if the `i386_set_gdt' RPC is available. */ +#undef HAVE_I386_SET_GDT + +/* + */ + +#ifndef _LIBC + +/* These symbols might be defined by some sysdeps configures. + They are used only in miscellaneous generator programs, not + in compiling libc itself. */ + +/* sysdeps/generic/configure.in */ +#undef HAVE_PSIGNAL + +/* sysdeps/unix/configure.in */ +#define HAVE_STRERROR + +/* sysdeps/unix/common/configure.in */ +#undef HAVE_SYS_SIGLIST +#undef HAVE__SYS_SIGLIST +#undef HAVE__CTYPE_ +#undef HAVE___CTYPE_ +#undef HAVE___CTYPE +#undef HAVE__CTYPE__ +#undef HAVE__CTYPE +#undef HAVE__LOCP + +#endif + +/* + */ + +#ifdef _LIBC + +/* The zic and zdump programs need these definitions. */ + +#define HAVE_STRERROR 1 + +/* The locale code needs these definitions. */ + +#define HAVE_REGEX 1 + +//#define HAVE_MMAP 1 +#undef HAVE_MMAP + +#endif + diff --git a/src/system/libroot/posix/glibc/include/arch/sparc/fenv_private.h b/src/system/libroot/posix/glibc/include/arch/sparc/fenv_private.h new file mode 100644 index 0000000000..634ca6668d --- /dev/null +++ b/src/system/libroot/posix/glibc/include/arch/sparc/fenv_private.h @@ -0,0 +1,172 @@ +#ifndef FENV_PRIVATE_H +#define FENV_PRIVATE_H 1 + +#include + +static __always_inline void +libc_fesetround (int r) +{ + fenv_t etmp; + __fenv_stfsr(etmp); + etmp = (etmp & ~__FE_ROUND_MASK) | (r); + __fenv_ldfsr(etmp); +} + +static __always_inline void +libc_feholdexcept_setround (fenv_t *e, int r) +{ + fenv_t etmp; + __fenv_stfsr(etmp); + *(e) = etmp; + etmp = etmp & ~((0x1f << 23) | FE_ALL_EXCEPT); + etmp = (etmp & ~__FE_ROUND_MASK) | (r); + __fenv_ldfsr(etmp); +} + +static __always_inline int +libc_fetestexcept (int e) +{ + fenv_t etmp; + __fenv_stfsr(etmp); + return etmp & (e) & FE_ALL_EXCEPT; +} + +static __always_inline void +libc_fesetenv (fenv_t *e) +{ + __fenv_ldfsr(*e); +} + +static __always_inline int +libc_feupdateenv_test (fenv_t *e, int ex) +{ + fenv_t etmp; + + __fenv_stfsr(etmp); + etmp &= FE_ALL_EXCEPT; + + __fenv_ldfsr(*e); + + __feraiseexcept (etmp); + + return etmp & ex; +} + +static __always_inline void +libc_feupdateenv (fenv_t *e) +{ + libc_feupdateenv_test (e, 0); +} + +static __always_inline void +libc_feholdsetround (fenv_t *e, int r) +{ + fenv_t etmp; + __fenv_stfsr(etmp); + *(e) = etmp; + etmp = (etmp & ~__FE_ROUND_MASK) | (r); + __fenv_ldfsr(etmp); +} + +static __always_inline void +libc_feresetround (fenv_t *e) +{ + fenv_t etmp; + __fenv_stfsr(etmp); + etmp = (etmp & ~__FE_ROUND_MASK) | (*e & __FE_ROUND_MASK); + __fenv_ldfsr(etmp); +} + +#define libc_feholdexceptf libc_feholdexcept +#define libc_fesetroundf libc_fesetround +#define libc_feholdexcept_setroundf libc_feholdexcept_setround +#define libc_fetestexceptf libc_fetestexcept +#define libc_fesetenvf libc_fesetenv +#define libc_feupdateenv_testf libc_feupdateenv_test +#define libc_feupdateenvf libc_feupdateenv +#define libc_feholdsetroundf libc_feholdsetround +#define libc_feresetroundf libc_feresetround +#define libc_feholdexcept libc_feholdexcept +#define libc_fesetround libc_fesetround +#define libc_feholdexcept_setround libc_feholdexcept_setround +#define libc_fetestexcept libc_fetestexcept +#define libc_fesetenv libc_fesetenv +#define libc_feupdateenv_test libc_feupdateenv_test +#define libc_feupdateenv libc_feupdateenv +#define libc_feholdsetround libc_feholdsetround +#define libc_feresetround libc_feresetround +#define libc_feholdexceptl libc_feholdexcept +#define libc_fesetroundl libc_fesetround +#define libc_feholdexcept_setroundl libc_feholdexcept_setround +#define libc_fetestexceptl libc_fetestexcept +#define libc_fesetenvl libc_fesetenv +#define libc_feupdateenv_testl libc_feupdateenv_test +#define libc_feupdateenvl libc_feupdateenv +#define libc_feholdsetroundl libc_feholdsetround +#define libc_feresetroundl libc_feresetround + +/* We have support for rounding mode context. */ +#define HAVE_RM_CTX 1 + +static __always_inline void +libc_feholdexcept_setround_sparc_ctx (struct rm_ctx *ctx, int round) +{ + fenv_t new; + + __fenv_stfsr(ctx->env); + new = ctx->env & ~((0x1f << 23) | FE_ALL_EXCEPT); + new = (new & ~__FE_ROUND_MASK) | round; + if (__glibc_unlikely (new != ctx->env)) + { + __fenv_ldfsr(new); + ctx->updated_status = true; + } + else + ctx->updated_status = false; +} + +static __always_inline void +libc_fesetenv_sparc_ctx (struct rm_ctx *ctx) +{ + libc_fesetenv(&ctx->env); +} + +static __always_inline void +libc_feupdateenv_sparc_ctx (struct rm_ctx *ctx) +{ + if (__glibc_unlikely (ctx->updated_status)) + libc_feupdateenv_test (&ctx->env, 0); +} + +static __always_inline void +libc_feholdsetround_sparc_ctx (struct rm_ctx *ctx, int round) +{ + fenv_t new; + + __fenv_stfsr(ctx->env); + new = (ctx->env & ~__FE_ROUND_MASK) | round; + if (__glibc_unlikely (new != ctx->env)) + { + __fenv_ldfsr(new); + ctx->updated_status = true; + } + else + ctx->updated_status = false; +} +#define libc_feholdexcept_setround_ctx libc_feholdexcept_setround_sparc_ctx +#define libc_feholdexcept_setroundf_ctx libc_feholdexcept_setround_sparc_ctx +#define libc_feholdexcept_setroundl_ctx libc_feholdexcept_setround_sparc_ctx +#define libc_fesetenv_ctx libc_fesetenv_sparc_ctx +#define libc_fesetenvf_ctx libc_fesetenv_sparc_ctx +#define libc_fesetenvl_ctx libc_fesetenv_sparc_ctx +#define libc_feupdateenv_ctx libc_feupdateenv_sparc_ctx +#define libc_feupdateenvf_ctx libc_feupdateenv_sparc_ctx +#define libc_feupdateenvl_ctx libc_feupdateenv_sparc_ctx +#define libc_feresetround_ctx libc_feupdateenv_sparc_ctx +#define libc_feresetroundf_ctx libc_feupdateenv_sparc_ctx +#define libc_feresetroundl_ctx libc_feupdateenv_sparc_ctx +#define libc_feholdsetround_ctx libc_feholdsetround_sparc_ctx +#define libc_feholdsetroundf_ctx libc_feholdsetround_sparc_ctx +#define libc_feholdsetroundl_ctx libc_feholdsetround_sparc_ctx + +#endif /* FENV_PRIVATE_H */ diff --git a/src/system/libroot/posix/glibc/include/arch/sparc/math-underflow.h b/src/system/libroot/posix/glibc/include/arch/sparc/math-underflow.h new file mode 100644 index 0000000000..c5e5c79768 --- /dev/null +++ b/src/system/libroot/posix/glibc/include/arch/sparc/math-underflow.h @@ -0,0 +1,79 @@ +/* Check for underflow and force underflow exceptions. + Copyright (C) 2015-2018 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#ifndef _MATH_UNDERFLOW_H +#define _MATH_UNDERFLOW_H 1 + +#include +#include + +#include + +#define fabs_tg(x) __MATH_TG ((x), (__typeof (x)) __builtin_fabs, (x)) + +/* These must be function-like macros because some __MATH_TG + implementations macro-expand the function-name argument before + concatenating a suffix to it. */ +#define min_of_type_f() FLT_MIN +#define min_of_type_() DBL_MIN +#define min_of_type_l() LDBL_MIN +#define min_of_type_f128() FLT128_MIN + +#define min_of_type(x) __MATH_TG ((x), (__typeof (x)) min_of_type_, ()) + +/* If X (which is not a NaN) is subnormal, force an underflow + exception. */ +#define math_check_force_underflow(x) \ + do \ + { \ + __typeof (x) force_underflow_tmp = (x); \ + if (fabs_tg (force_underflow_tmp) \ + < min_of_type (force_underflow_tmp)) \ + { \ + __typeof (force_underflow_tmp) force_underflow_tmp2 \ + = force_underflow_tmp * force_underflow_tmp; \ + math_force_eval (force_underflow_tmp2); \ + } \ + } \ + while (0) +/* Likewise, but X is also known to be nonnegative. */ +#define math_check_force_underflow_nonneg(x) \ + do \ + { \ + __typeof (x) force_underflow_tmp = (x); \ + if (force_underflow_tmp \ + < min_of_type (force_underflow_tmp)) \ + { \ + __typeof (force_underflow_tmp) force_underflow_tmp2 \ + = force_underflow_tmp * force_underflow_tmp; \ + math_force_eval (force_underflow_tmp2); \ + } \ + } \ + while (0) +/* Likewise, for both real and imaginary parts of a complex + result. */ +#define math_check_force_underflow_complex(x) \ + do \ + { \ + __typeof (x) force_underflow_complex_tmp = (x); \ + math_check_force_underflow (__real__ force_underflow_complex_tmp); \ + math_check_force_underflow (__imag__ force_underflow_complex_tmp); \ + } \ + while (0) + +#endif /* math-underflow.h */ diff --git a/src/system/libroot/posix/glibc/include/arch/sparc/math_ldbl.h b/src/system/libroot/posix/glibc/include/arch/sparc/math_ldbl.h index 1cd9d6752d..734da41b01 100644 --- a/src/system/libroot/posix/glibc/include/arch/sparc/math_ldbl.h +++ b/src/system/libroot/posix/glibc/include/arch/sparc/math_ldbl.h @@ -1,4 +1,120 @@ -#ifndef _MATH_PRIVATE_H_ -#error "Never use directly; include instead." +/* Manipulation of the bit representation of 'long double' quantities. + Copyright (C) 1999-2019 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#ifndef _MATH_LDBL_H_ +#define _MATH_LDBL_H_ 1 + +#include +#include + +/* A union which permits us to convert between a long double and + four 32 bit ints or two 64 bit ints. */ + +#if __FLOAT_WORD_ORDER == __BIG_ENDIAN + +typedef union +{ + long double value; + struct + { + uint64_t msw; + uint64_t lsw; + } parts64; + struct + { + uint32_t w0, w1, w2, w3; + } parts32; +} ieee854_long_double_shape_type; + #endif +#if __FLOAT_WORD_ORDER == __LITTLE_ENDIAN + +typedef union +{ + long double value; + struct + { + uint64_t lsw; + uint64_t msw; + } parts64; + struct + { + uint32_t w3, w2, w1, w0; + } parts32; +} ieee854_long_double_shape_type; + +#endif + +/* Get two 64 bit ints from a long double. */ + +#define GET_LDOUBLE_WORDS64(ix0,ix1,d) \ +do { \ + ieee854_long_double_shape_type qw_u; \ + qw_u.value = (d); \ + (ix0) = qw_u.parts64.msw; \ + (ix1) = qw_u.parts64.lsw; \ +} while (0) + +/* Set a long double from two 64 bit ints. */ + +#define SET_LDOUBLE_WORDS64(d,ix0,ix1) \ +do { \ + ieee854_long_double_shape_type qw_u; \ + qw_u.parts64.msw = (ix0); \ + qw_u.parts64.lsw = (ix1); \ + (d) = qw_u.value; \ +} while (0) + +/* Get the more significant 64 bits of a long double mantissa. */ + +#define GET_LDOUBLE_MSW64(v,d) \ +do { \ + ieee854_long_double_shape_type sh_u; \ + sh_u.value = (d); \ + (v) = sh_u.parts64.msw; \ +} while (0) + +/* Set the more significant 64 bits of a long double mantissa from an int. */ + +#define SET_LDOUBLE_MSW64(d,v) \ +do { \ + ieee854_long_double_shape_type sh_u; \ + sh_u.value = (d); \ + sh_u.parts64.msw = (v); \ + (d) = sh_u.value; \ +} while (0) + +/* Get the least significant 64 bits of a long double mantissa. */ + +#define GET_LDOUBLE_LSW64(v,d) \ +do { \ + ieee854_long_double_shape_type sh_u; \ + sh_u.value = (d); \ + (v) = sh_u.parts64.lsw; \ +} while (0) + +/* + On a platform already supporting a binary128 long double, + _Float128 will alias to long double. This transformation + makes aliasing *l functions to *f128 trivial. +*/ +#define _Float128 long double +#define L(x) x##L + +#endif /* math_ldbl.h */ diff --git a/src/system/libroot/posix/glibc/include/arch/sparc/sysdep.h b/src/system/libroot/posix/glibc/include/arch/sparc/sysdep.h new file mode 100644 index 0000000000..1da112ca80 --- /dev/null +++ b/src/system/libroot/posix/glibc/include/arch/sparc/sysdep.h @@ -0,0 +1,87 @@ +/* Copyright (C) 2011-2018 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#include_next + +#define _SYSDEPS_SYSDEP_H 1 +#include + +#ifdef __ASSEMBLER__ + +#define SPARC_PIC_THUNK(reg) \ + .ifndef __sparc_get_pc_thunk.reg; \ + .section .text.__sparc_get_pc_thunk.reg,"axG",@progbits,__sparc_get_pc_thunk.reg,comdat; \ + .align 32; \ + .weak __sparc_get_pc_thunk.reg; \ + .hidden __sparc_get_pc_thunk.reg; \ + .type __sparc_get_pc_thunk.reg, #function; \ +__sparc_get_pc_thunk.reg: \ + jmp %o7 + 8; \ + add %o7, %reg, %##reg; \ + .previous; \ + .endif; + +/* The "-4" and "+4" offsets against _GLOBAL_OFFSET_TABLE_ are + critical since they represent the offset from the thunk call to the + instruction containing the _GLOBAL_OFFSET_TABLE_ reference. + Therefore these instructions cannot be moved around without + appropriate adjustments to those offsets. + + Furthermore, these expressions are special in another regard. When + the assembler sees a reference to _GLOBAL_OFFSET_TABLE_ inside of + a %hi() or %lo(), it emits a PC-relative relocation. This causes + R_SPARC_HI22 to turn into R_SPARC_PC22, and R_SPARC_LO10 to turn into + R_SPARC_PC10, respectively. + + Even when v9 we use a call sequence instead of using "rd %pc" because + RDPC is extremely expensive and incurs a full pipeline flush. */ + +#define SPARC_PIC_THUNK_CALL(reg) \ + sethi %hi(_GLOBAL_OFFSET_TABLE_-4), %##reg; \ + call __sparc_get_pc_thunk.reg; \ + or %##reg, %lo(_GLOBAL_OFFSET_TABLE_+4), %##reg; + +#define SETUP_PIC_REG(reg) \ + SPARC_PIC_THUNK(reg) \ + SPARC_PIC_THUNK_CALL(reg) + +#define SETUP_PIC_REG_LEAF(reg, tmp) \ + SPARC_PIC_THUNK(reg) \ + mov %o7, %##tmp; \ + SPARC_PIC_THUNK_CALL(reg); \ + mov %##tmp, %o7; + +#undef ENTRY +#define ENTRY(name) \ + .align 4; \ + .global C_SYMBOL_NAME(name); \ + .type name, @function; \ +C_LABEL(name) \ + cfi_startproc; + +#undef END +#define END(name) \ + cfi_endproc; + +#undef LOC +#define LOC(name) .L##name + +#endif /* __ASSEMBLER__ */ + +/* This is the offset from the %sp to the backing store above the + * register windows. So if you poke stack memory directly you add this. */ +#define STACK_BIAS 2047 diff --git a/src/system/libroot/posix/glibc/include/arch/x86/bits/floatn.h b/src/system/libroot/posix/glibc/include/arch/x86/bits/floatn.h new file mode 100644 index 0000000000..49c75f26c5 --- /dev/null +++ b/src/system/libroot/posix/glibc/include/arch/x86/bits/floatn.h @@ -0,0 +1,121 @@ +/* Macros to control TS 18661-3 glibc features on x86. + Copyright (C) 2017-2018 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#ifndef _BITS_FLOATN_H +#define _BITS_FLOATN_H + +#include + +/* Defined to 1 if the current compiler invocation provides a + floating-point type with the IEEE 754 binary128 format, and this + glibc includes corresponding *f128 interfaces for it. The required + libgcc support was added some time after the basic compiler + support, for x86_64 and x86. */ +#if (defined __x86_64__ \ + ? __GNUC_PREREQ (4, 3) \ + : (defined __GNU__ ? __GNUC_PREREQ (4, 5) : __GNUC_PREREQ (4, 4))) +# define __HAVE_FLOAT128 1 +#else +# define __HAVE_FLOAT128 0 +#endif + +/* Defined to 1 if __HAVE_FLOAT128 is 1 and the type is ABI-distinct + from the default float, double and long double types in this glibc. */ +#if __HAVE_FLOAT128 +# define __HAVE_DISTINCT_FLOAT128 1 +#else +# define __HAVE_DISTINCT_FLOAT128 0 +#endif + +/* Defined to 1 if the current compiler invocation provides a + floating-point type with the right format for _Float64x, and this + glibc includes corresponding *f64x interfaces for it. */ +#define __HAVE_FLOAT64X 1 + +/* Defined to 1 if __HAVE_FLOAT64X is 1 and _Float64x has the format + of long double. Otherwise, if __HAVE_FLOAT64X is 1, _Float64x has + the format of _Float128, which must be different from that of long + double. */ +#define __HAVE_FLOAT64X_LONG_DOUBLE 1 + +#ifndef __ASSEMBLER__ + +/* Defined to concatenate the literal suffix to be used with _Float128 + types, if __HAVE_FLOAT128 is 1. */ +# if __HAVE_FLOAT128 +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +/* The literal suffix f128 exists only since GCC 7.0. */ +# define __f128(x) x##q +# else +# define __f128(x) x##f128 +# endif +# endif + +/* Defined to a complex binary128 type if __HAVE_FLOAT128 is 1. */ +# if __HAVE_FLOAT128 +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +/* Add a typedef for older GCC compilers which don't natively support + _Complex _Float128. */ +typedef _Complex float __cfloat128 __attribute__ ((__mode__ (__TC__))); +# define __CFLOAT128 __cfloat128 +# else +# define __CFLOAT128 _Complex _Float128 +# endif +# endif + +/* The remaining of this file provides support for older compilers. */ +# if __HAVE_FLOAT128 + +/* The type _Float128 exists only since GCC 7.0. */ +# if !__GNUC_PREREQ (7, 0) || defined __cplusplus +typedef __float128 _Float128; +# endif + +/* __builtin_huge_valf128 doesn't exist before GCC 7.0. */ +# if !__GNUC_PREREQ (7, 0) +# define __builtin_huge_valf128() ((_Float128) __builtin_huge_val ()) +# endif + +/* Older GCC has only a subset of built-in functions for _Float128 on + x86, and __builtin_infq is not usable in static initializers. + Converting a narrower sNaN to _Float128 produces a quiet NaN, so + attempts to use _Float128 sNaNs will not work properly with older + compilers. */ +# if !__GNUC_PREREQ (7, 0) +# define __builtin_copysignf128 __builtin_copysignq +# define __builtin_fabsf128 __builtin_fabsq +# define __builtin_inff128() ((_Float128) __builtin_inf ()) +# define __builtin_nanf128(x) ((_Float128) __builtin_nan (x)) +# define __builtin_nansf128(x) ((_Float128) __builtin_nans (x)) +# endif + +/* In math/math.h, __MATH_TG will expand signbit to __builtin_signbit*, + e.g.: __builtin_signbitf128, before GCC 6. However, there has never + been a __builtin_signbitf128 in GCC and the type-generic builtin is + only available since GCC 6. */ +# if !__GNUC_PREREQ (6, 0) +# define __builtin_signbitf128 __signbitf128 +# endif + +# endif + +#endif /* !__ASSEMBLER__. */ + +#include + +#endif /* _BITS_FLOATN_H */ diff --git a/src/system/libroot/posix/glibc/include/bits/long-double.h b/src/system/libroot/posix/glibc/include/bits/long-double.h new file mode 100644 index 0000000000..33b8dfc454 --- /dev/null +++ b/src/system/libroot/posix/glibc/include/bits/long-double.h @@ -0,0 +1,39 @@ +/* Properties of long double type. + Copyright (C) 2016-2018 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +/* This header is included by . + + If long double is ABI-compatible with double, it should define + __NO_LONG_DOUBLE_MATH to 1; otherwise, it should leave + __NO_LONG_DOUBLE_MATH undefined. + + If this build of the GNU C Library supports both long double + ABI-compatible with double and some other long double format not + ABI-compatible with double, it should define + __LONG_DOUBLE_MATH_OPTIONAL to 1; otherwise, it should leave + __LONG_DOUBLE_MATH_OPTIONAL undefined. + + If __NO_LONG_DOUBLE_MATH is already defined, this header must not + define anything; this is needed to work with the definition of + __NO_LONG_DOUBLE_MATH in nldbl-compat.h. */ + +/* In the default version of this header, long double is + ABI-compatible with double. */ +#ifndef __NO_LONG_DOUBLE_MATH +# define __NO_LONG_DOUBLE_MATH 1 +#endif diff --git a/src/system/libroot/posix/glibc/math/fenv.h b/src/system/libroot/posix/glibc/math/fenv.h index 8a06f024e4..b33f4442e1 100644 --- a/src/system/libroot/posix/glibc/math/fenv.h +++ b/src/system/libroot/posix/glibc/math/fenv.h @@ -23,6 +23,7 @@ #ifndef _FENV_H #define _FENV_H 1 +#include #include /* Get the architecture dependend definitions. The following definitions @@ -133,4 +134,13 @@ extern int fegetexcept (void) __THROW; __END_DECLS +/* Rounding mode context. This allows functions to set/restore rounding mode + * only when the desired rounding mode is different from the current rounding + * mode. */ +struct rm_ctx +{ + fenv_t env; + bool updated_status; +}; + #endif /* fenv.h */ diff --git a/src/system/libroot/posix/glibc/math/math-barriers.h b/src/system/libroot/posix/glibc/math/math-barriers.h new file mode 100644 index 0000000000..425173149c --- /dev/null +++ b/src/system/libroot/posix/glibc/math/math-barriers.h @@ -0,0 +1,37 @@ +/* Control when floating-point expressions are evaluated. Generic version. + Copyright (C) 2007-2018 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#ifndef _MATH_BARRIERS_H +#define _MATH_BARRIERS_H 1 + +/* math_opt_barrier evaluates and returns its floating-point argument + and ensures that the evaluation of any expression using the result + of math_opt_barrier is not moved before the call. math_force_eval + ensures that its floating-point argument is evaluated for its side + effects even if its value is apparently unused, and that the + evaluation of its argument is not moved after the call. Both these + macros are used to ensure the correct ordering of floating-point + expression evaluations with respect to accesses to the + floating-point environment. */ + +#define math_opt_barrier(x) \ + ({ __typeof (x) __x = (x); __asm ("" : "+m" (__x)); __x; }) +#define math_force_eval(x) \ + ({ __typeof (x) __x = (x); __asm __volatile__ ("" : : "m" (__x)); }) + +#endif /* math-barriers.h */ diff --git a/src/system/libroot/posix/glibc/math/math.h b/src/system/libroot/posix/glibc/math/math.h index 7d311462d9..f700d914fe 100644 --- a/src/system/libroot/posix/glibc/math/math.h +++ b/src/system/libroot/posix/glibc/math/math.h @@ -126,6 +126,71 @@ extern int signgam; #endif +/* Depending on the type of TG_ARG, call an appropriately suffixed + version of FUNC with arguments (including parentheses) ARGS. + Suffixed functions may not exist for long double if it has the same + format as double, or for other types with the same format as float, + double or long double. The behavior is undefined if the argument + does not have a real floating type. The definition may use a + conditional expression, so all suffixed versions of FUNC must + return the same type (FUNC may include a cast if necessary rather + than being a single identifier). */ +#ifdef __NO_LONG_DOUBLE_MATH +# if __HAVE_DISTINCT_FLOAT128 +# error "Distinct _Float128 without distinct long double not supported." +# endif +# define __MATH_TG(TG_ARG, FUNC, ARGS) \ + (sizeof (TG_ARG) == sizeof (float) ? FUNC ## f ARGS : FUNC ARGS) +#elif __HAVE_DISTINCT_FLOAT128 +# if __HAVE_GENERIC_SELECTION +# if __HAVE_FLOATN_NOT_TYPEDEF && __HAVE_FLOAT32 +# define __MATH_TG_F32(FUNC, ARGS) _Float32: FUNC ## f ARGS, +# else +# define __MATH_TG_F32(FUNC, ARGS) +# endif +# if __HAVE_FLOATN_NOT_TYPEDEF && __HAVE_FLOAT64X +# if __HAVE_FLOAT64X_LONG_DOUBLE +# define __MATH_TG_F64X(FUNC, ARGS) _Float64x: FUNC ## l ARGS, +# else +# define __MATH_TG_F64X(FUNC, ARGS) _Float64x: FUNC ## f128 ARGS, +# endif +# else +# define __MATH_TG_F64X(FUNC, ARGS) +# endif +# define __MATH_TG(TG_ARG, FUNC, ARGS) \ + _Generic ((TG_ARG), \ + float: FUNC ## f ARGS, \ + __MATH_TG_F32 (FUNC, ARGS) \ + default: FUNC ARGS, \ + long double: FUNC ## l ARGS, \ + __MATH_TG_F64X (FUNC, ARGS) \ + _Float128: FUNC ## f128 ARGS) +# else +# if __HAVE_FLOATN_NOT_TYPEDEF +# error "Non-typedef _FloatN but no _Generic." +# endif +# define __MATH_TG(TG_ARG, FUNC, ARGS) \ + __builtin_choose_expr \ + (__builtin_types_compatible_p (__typeof (TG_ARG), float), \ + FUNC ## f ARGS, \ + __builtin_choose_expr \ + (__builtin_types_compatible_p (__typeof (TG_ARG), double), \ + FUNC ARGS, \ + __builtin_choose_expr \ + (__builtin_types_compatible_p (__typeof (TG_ARG), long double), \ + FUNC ## l ARGS, \ + FUNC ## f128 ARGS))) +# endif +#else +# define __MATH_TG(TG_ARG, FUNC, ARGS) \ + (sizeof (TG_ARG) == sizeof (float) \ + ? FUNC ## f ARGS \ + : sizeof (TG_ARG) == sizeof (double) \ + ? FUNC ARGS \ + : FUNC ## l ARGS) +#endif + + /* ISO C99 defines some generic macros which work on any data type. */ #if __USE_ISOC99 @@ -247,6 +312,25 @@ enum #endif /* Use ISO C99. */ +/* Return nonzero value if X is a signaling NaN. */ +# ifndef __cplusplus +# define issignaling(x) __MATH_TG ((x), __issignaling, (x)) +# else + /* In C++ mode, __MATH_TG cannot be used, because it relies on + __builtin_types_compatible_p, which is a C-only builtin. */ +# ifdef __NO_LONG_DOUBLE_MATH +# define issignaling(x) \ + (sizeof (x) == sizeof (float) ? __issignalingf (x) : __issignaling (x)) +# else +# define issignaling(x) \ + (sizeof (x) == sizeof (float) \ + ? __issignalingf (x) \ + : sizeof (x) == sizeof (double) \ + ? __issignaling (x) : __issignalingl (x)) +# endif +# endif + + #ifdef __USE_MISC /* Support for various different standard error handling behaviors. */ typedef enum diff --git a/src/system/libroot/posix/glibc/math/w_sqrtl_compat.c b/src/system/libroot/posix/glibc/math/w_sqrtl_compat.c new file mode 100644 index 0000000000..b0cc24ea21 --- /dev/null +++ b/src/system/libroot/posix/glibc/math/w_sqrtl_compat.c @@ -0,0 +1,31 @@ +/* Copyright (C) 2011-2019 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Ulrich Drepper , 2011. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + . */ + +#define NO_MATH_REDIRECT +#include +#include +#include + + +/* wrapper sqrtl */ +long double +__sqrtl (long double x) +{ + return __ieee754_sqrtl (x); +} +libm_alias_ldouble (__sqrt, sqrt)