diff options
Diffstat (limited to 'REORG.TODO/soft-fp')
97 files changed, 11045 insertions, 0 deletions
diff --git a/REORG.TODO/soft-fp/Banner b/REORG.TODO/soft-fp/Banner new file mode 100644 index 0000000000..940395cfe3 --- /dev/null +++ b/REORG.TODO/soft-fp/Banner @@ -0,0 +1 @@ +software FPU emulation by Richard Henderson, Jakub Jelinek and others diff --git a/REORG.TODO/soft-fp/Makefile b/REORG.TODO/soft-fp/Makefile new file mode 100644 index 0000000000..b7718f3906 --- /dev/null +++ b/REORG.TODO/soft-fp/Makefile @@ -0,0 +1,40 @@ +# Copyright (C) 1997-2017 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 +# <http://www.gnu.org/licenses/>. + +# +# Makefile for software floating-point routines +# +subdir := soft-fp + +include ../Makeconfig + +gcc-single-routines := negsf2 addsf3 subsf3 mulsf3 divsf3 eqsf2 \ + lesf2 gesf2 unordsf2 fixsfsi fixunssfsi floatsisf fixsfdi \ + fixunssfdi floatdisf sqrtsf2 floatunsisf floatundisf + +gcc-double-routines := negdf2 adddf3 subdf3 muldf3 divdf3 eqdf2 \ + ledf2 gedf2 unorddf2 fixdfsi fixunsdfsi floatsidf fixdfdi \ + fixunsdfdi floatdidf extendsfdf2 truncdfsf2 sqrtdf2 floatunsidf \ + floatundidf + +gcc-quad-routines := negtf2 addtf3 subtf3 multf3 divtf3 eqtf2 \ + letf2 getf2 unordtf2 fixtfsi fixunstfsi floatsitf fixtfdi \ + fixunstfdi floatditf extendsftf2 trunctfsf2 extenddftf2 \ + trunctfdf2 sqrttf2 floatunsitf floatunditf + +include ../Rules diff --git a/REORG.TODO/soft-fp/adddf3.c b/REORG.TODO/soft-fp/adddf3.c new file mode 100644 index 0000000000..7e6cabfa18 --- /dev/null +++ b/REORG.TODO/soft-fp/adddf3.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return a + b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +DFtype +__adddf3 (DFtype a, DFtype b) +{ + FP_DECL_EX; + FP_DECL_D (A); + FP_DECL_D (B); + FP_DECL_D (R); + DFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_SEMIRAW_D (A, a); + FP_UNPACK_SEMIRAW_D (B, b); + FP_ADD_D (R, A, B); + FP_PACK_SEMIRAW_D (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/addsf3.c b/REORG.TODO/soft-fp/addsf3.c new file mode 100644 index 0000000000..c7bec00542 --- /dev/null +++ b/REORG.TODO/soft-fp/addsf3.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return a + b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +SFtype +__addsf3 (SFtype a, SFtype b) +{ + FP_DECL_EX; + FP_DECL_S (A); + FP_DECL_S (B); + FP_DECL_S (R); + SFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_SEMIRAW_S (A, a); + FP_UNPACK_SEMIRAW_S (B, b); + FP_ADD_S (R, A, B); + FP_PACK_SEMIRAW_S (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/addtf3.c b/REORG.TODO/soft-fp/addtf3.c new file mode 100644 index 0000000000..ad8071696b --- /dev/null +++ b/REORG.TODO/soft-fp/addtf3.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return a + b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +TFtype +__addtf3 (TFtype a, TFtype b) +{ + FP_DECL_EX; + FP_DECL_Q (A); + FP_DECL_Q (B); + FP_DECL_Q (R); + TFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_SEMIRAW_Q (A, a); + FP_UNPACK_SEMIRAW_Q (B, b); + FP_ADD_Q (R, A, B); + FP_PACK_SEMIRAW_Q (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/divdf3.c b/REORG.TODO/soft-fp/divdf3.c new file mode 100644 index 0000000000..93bc3e0b04 --- /dev/null +++ b/REORG.TODO/soft-fp/divdf3.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return a / b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +DFtype +__divdf3 (DFtype a, DFtype b) +{ + FP_DECL_EX; + FP_DECL_D (A); + FP_DECL_D (B); + FP_DECL_D (R); + DFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_D (A, a); + FP_UNPACK_D (B, b); + FP_DIV_D (R, A, B); + FP_PACK_D (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/divsf3.c b/REORG.TODO/soft-fp/divsf3.c new file mode 100644 index 0000000000..ccf4f9dfc6 --- /dev/null +++ b/REORG.TODO/soft-fp/divsf3.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return a / b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +SFtype +__divsf3 (SFtype a, SFtype b) +{ + FP_DECL_EX; + FP_DECL_S (A); + FP_DECL_S (B); + FP_DECL_S (R); + SFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_S (A, a); + FP_UNPACK_S (B, b); + FP_DIV_S (R, A, B); + FP_PACK_S (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/divtf3.c b/REORG.TODO/soft-fp/divtf3.c new file mode 100644 index 0000000000..2321579904 --- /dev/null +++ b/REORG.TODO/soft-fp/divtf3.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return a / b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +TFtype +__divtf3 (TFtype a, TFtype b) +{ + FP_DECL_EX; + FP_DECL_Q (A); + FP_DECL_Q (B); + FP_DECL_Q (R); + TFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_Q (A, a); + FP_UNPACK_Q (B, b); + FP_DIV_Q (R, A, B); + FP_PACK_Q (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/double.h b/REORG.TODO/soft-fp/double.h new file mode 100644 index 0000000000..055d9da6bc --- /dev/null +++ b/REORG.TODO/soft-fp/double.h @@ -0,0 +1,323 @@ +/* Software floating-point emulation. + Definitions for IEEE Double Precision + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com), + Jakub Jelinek (jj@ultra.linux.cz), + David S. Miller (davem@redhat.com) and + Peter Maydell (pmaydell@chiark.greenend.org.uk). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#ifndef SOFT_FP_DOUBLE_H +#define SOFT_FP_DOUBLE_H 1 + +#if _FP_W_TYPE_SIZE < 32 +# error "Here's a nickel kid. Go buy yourself a real computer." +#endif + +#if _FP_W_TYPE_SIZE < 64 +# define _FP_FRACTBITS_D (2 * _FP_W_TYPE_SIZE) +# define _FP_FRACTBITS_DW_D (4 * _FP_W_TYPE_SIZE) +#else +# define _FP_FRACTBITS_D _FP_W_TYPE_SIZE +# define _FP_FRACTBITS_DW_D (2 * _FP_W_TYPE_SIZE) +#endif + +#define _FP_FRACBITS_D 53 +#define _FP_FRACXBITS_D (_FP_FRACTBITS_D - _FP_FRACBITS_D) +#define _FP_WFRACBITS_D (_FP_WORKBITS + _FP_FRACBITS_D) +#define _FP_WFRACXBITS_D (_FP_FRACTBITS_D - _FP_WFRACBITS_D) +#define _FP_EXPBITS_D 11 +#define _FP_EXPBIAS_D 1023 +#define _FP_EXPMAX_D 2047 + +#define _FP_QNANBIT_D \ + ((_FP_W_TYPE) 1 << (_FP_FRACBITS_D-2) % _FP_W_TYPE_SIZE) +#define _FP_QNANBIT_SH_D \ + ((_FP_W_TYPE) 1 << (_FP_FRACBITS_D-2+_FP_WORKBITS) % _FP_W_TYPE_SIZE) +#define _FP_IMPLBIT_D \ + ((_FP_W_TYPE) 1 << (_FP_FRACBITS_D-1) % _FP_W_TYPE_SIZE) +#define _FP_IMPLBIT_SH_D \ + ((_FP_W_TYPE) 1 << (_FP_FRACBITS_D-1+_FP_WORKBITS) % _FP_W_TYPE_SIZE) +#define _FP_OVERFLOW_D \ + ((_FP_W_TYPE) 1 << _FP_WFRACBITS_D % _FP_W_TYPE_SIZE) + +#define _FP_WFRACBITS_DW_D (2 * _FP_WFRACBITS_D) +#define _FP_WFRACXBITS_DW_D (_FP_FRACTBITS_DW_D - _FP_WFRACBITS_DW_D) +#define _FP_HIGHBIT_DW_D \ + ((_FP_W_TYPE) 1 << (_FP_WFRACBITS_DW_D - 1) % _FP_W_TYPE_SIZE) + +typedef float DFtype __attribute__ ((mode (DF))); + +#if _FP_W_TYPE_SIZE < 64 + +union _FP_UNION_D +{ + DFtype flt; + struct _FP_STRUCT_LAYOUT + { +# if __BYTE_ORDER == __BIG_ENDIAN + unsigned sign : 1; + unsigned exp : _FP_EXPBITS_D; + unsigned frac1 : _FP_FRACBITS_D - (_FP_IMPLBIT_D != 0) - _FP_W_TYPE_SIZE; + unsigned frac0 : _FP_W_TYPE_SIZE; +# else + unsigned frac0 : _FP_W_TYPE_SIZE; + unsigned frac1 : _FP_FRACBITS_D - (_FP_IMPLBIT_D != 0) - _FP_W_TYPE_SIZE; + unsigned exp : _FP_EXPBITS_D; + unsigned sign : 1; +# endif + } bits __attribute__ ((packed)); +}; + +# define FP_DECL_D(X) _FP_DECL (2, X) +# define FP_UNPACK_RAW_D(X, val) _FP_UNPACK_RAW_2 (D, X, (val)) +# define FP_UNPACK_RAW_DP(X, val) _FP_UNPACK_RAW_2_P (D, X, (val)) +# define FP_PACK_RAW_D(val, X) _FP_PACK_RAW_2 (D, (val), X) +# define FP_PACK_RAW_DP(val, X) \ + do \ + { \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_2_P (D, (val), X); \ + } \ + while (0) + +# define FP_UNPACK_D(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_2 (D, X, (val)); \ + _FP_UNPACK_CANONICAL (D, 2, X); \ + } \ + while (0) + +# define FP_UNPACK_DP(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_2_P (D, X, (val)); \ + _FP_UNPACK_CANONICAL (D, 2, X); \ + } \ + while (0) + +# define FP_UNPACK_SEMIRAW_D(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_2 (D, X, (val)); \ + _FP_UNPACK_SEMIRAW (D, 2, X); \ + } \ + while (0) + +# define FP_UNPACK_SEMIRAW_DP(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_2_P (D, X, (val)); \ + _FP_UNPACK_SEMIRAW (D, 2, X); \ + } \ + while (0) + +# define FP_PACK_D(val, X) \ + do \ + { \ + _FP_PACK_CANONICAL (D, 2, X); \ + _FP_PACK_RAW_2 (D, (val), X); \ + } \ + while (0) + +# define FP_PACK_DP(val, X) \ + do \ + { \ + _FP_PACK_CANONICAL (D, 2, X); \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_2_P (D, (val), X); \ + } \ + while (0) + +# define FP_PACK_SEMIRAW_D(val, X) \ + do \ + { \ + _FP_PACK_SEMIRAW (D, 2, X); \ + _FP_PACK_RAW_2 (D, (val), X); \ + } \ + while (0) + +# define FP_PACK_SEMIRAW_DP(val, X) \ + do \ + { \ + _FP_PACK_SEMIRAW (D, 2, X); \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_2_P (D, (val), X); \ + } \ + while (0) + +# define FP_ISSIGNAN_D(X) _FP_ISSIGNAN (D, 2, X) +# define FP_NEG_D(R, X) _FP_NEG (D, 2, R, X) +# define FP_ADD_D(R, X, Y) _FP_ADD (D, 2, R, X, Y) +# define FP_SUB_D(R, X, Y) _FP_SUB (D, 2, R, X, Y) +# define FP_MUL_D(R, X, Y) _FP_MUL (D, 2, R, X, Y) +# define FP_DIV_D(R, X, Y) _FP_DIV (D, 2, R, X, Y) +# define FP_SQRT_D(R, X) _FP_SQRT (D, 2, R, X) +# define _FP_SQRT_MEAT_D(R, S, T, X, Q) _FP_SQRT_MEAT_2 (R, S, T, X, (Q)) +# define FP_FMA_D(R, X, Y, Z) _FP_FMA (D, 2, 4, R, X, Y, Z) + +# define FP_CMP_D(r, X, Y, un, ex) _FP_CMP (D, 2, (r), X, Y, (un), (ex)) +# define FP_CMP_EQ_D(r, X, Y, ex) _FP_CMP_EQ (D, 2, (r), X, Y, (ex)) +# define FP_CMP_UNORD_D(r, X, Y, ex) _FP_CMP_UNORD (D, 2, (r), X, Y, (ex)) + +# define FP_TO_INT_D(r, X, rsz, rsg) _FP_TO_INT (D, 2, (r), X, (rsz), (rsg)) +# define FP_TO_INT_ROUND_D(r, X, rsz, rsg) \ + _FP_TO_INT_ROUND (D, 2, (r), X, (rsz), (rsg)) +# define FP_FROM_INT_D(X, r, rs, rt) _FP_FROM_INT (D, 2, X, (r), (rs), rt) + +# define _FP_FRAC_HIGH_D(X) _FP_FRAC_HIGH_2 (X) +# define _FP_FRAC_HIGH_RAW_D(X) _FP_FRAC_HIGH_2 (X) + +# define _FP_FRAC_HIGH_DW_D(X) _FP_FRAC_HIGH_4 (X) + +#else + +union _FP_UNION_D +{ + DFtype flt; + struct _FP_STRUCT_LAYOUT + { +# if __BYTE_ORDER == __BIG_ENDIAN + unsigned sign : 1; + unsigned exp : _FP_EXPBITS_D; + _FP_W_TYPE frac : _FP_FRACBITS_D - (_FP_IMPLBIT_D != 0); +# else + _FP_W_TYPE frac : _FP_FRACBITS_D - (_FP_IMPLBIT_D != 0); + unsigned exp : _FP_EXPBITS_D; + unsigned sign : 1; +# endif + } bits __attribute__ ((packed)); +}; + +# define FP_DECL_D(X) _FP_DECL (1, X) +# define FP_UNPACK_RAW_D(X, val) _FP_UNPACK_RAW_1 (D, X, (val)) +# define FP_UNPACK_RAW_DP(X, val) _FP_UNPACK_RAW_1_P (D, X, (val)) +# define FP_PACK_RAW_D(val, X) _FP_PACK_RAW_1 (D, (val), X) +# define FP_PACK_RAW_DP(val, X) \ + do \ + { \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_1_P (D, (val), X); \ + } \ + while (0) + +# define FP_UNPACK_D(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_1 (D, X, (val)); \ + _FP_UNPACK_CANONICAL (D, 1, X); \ + } \ + while (0) + +# define FP_UNPACK_DP(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_1_P (D, X, (val)); \ + _FP_UNPACK_CANONICAL (D, 1, X); \ + } \ + while (0) + +# define FP_UNPACK_SEMIRAW_D(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_1 (D, X, (val)); \ + _FP_UNPACK_SEMIRAW (D, 1, X); \ + } \ + while (0) + +# define FP_UNPACK_SEMIRAW_DP(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_1_P (D, X, (val)); \ + _FP_UNPACK_SEMIRAW (D, 1, X); \ + } \ + while (0) + +# define FP_PACK_D(val, X) \ + do \ + { \ + _FP_PACK_CANONICAL (D, 1, X); \ + _FP_PACK_RAW_1 (D, (val), X); \ + } \ + while (0) + +# define FP_PACK_DP(val, X) \ + do \ + { \ + _FP_PACK_CANONICAL (D, 1, X); \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_1_P (D, (val), X); \ + } \ + while (0) + +# define FP_PACK_SEMIRAW_D(val, X) \ + do \ + { \ + _FP_PACK_SEMIRAW (D, 1, X); \ + _FP_PACK_RAW_1 (D, (val), X); \ + } \ + while (0) + +# define FP_PACK_SEMIRAW_DP(val, X) \ + do \ + { \ + _FP_PACK_SEMIRAW (D, 1, X); \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_1_P (D, (val), X); \ + } \ + while (0) + +# define FP_ISSIGNAN_D(X) _FP_ISSIGNAN (D, 1, X) +# define FP_NEG_D(R, X) _FP_NEG (D, 1, R, X) +# define FP_ADD_D(R, X, Y) _FP_ADD (D, 1, R, X, Y) +# define FP_SUB_D(R, X, Y) _FP_SUB (D, 1, R, X, Y) +# define FP_MUL_D(R, X, Y) _FP_MUL (D, 1, R, X, Y) +# define FP_DIV_D(R, X, Y) _FP_DIV (D, 1, R, X, Y) +# define FP_SQRT_D(R, X) _FP_SQRT (D, 1, R, X) +# define _FP_SQRT_MEAT_D(R, S, T, X, Q) _FP_SQRT_MEAT_1 (R, S, T, X, (Q)) +# define FP_FMA_D(R, X, Y, Z) _FP_FMA (D, 1, 2, R, X, Y, Z) + +/* The implementation of _FP_MUL_D and _FP_DIV_D should be chosen by + the target machine. */ + +# define FP_CMP_D(r, X, Y, un, ex) _FP_CMP (D, 1, (r), X, Y, (un), (ex)) +# define FP_CMP_EQ_D(r, X, Y, ex) _FP_CMP_EQ (D, 1, (r), X, Y, (ex)) +# define FP_CMP_UNORD_D(r, X, Y, ex) _FP_CMP_UNORD (D, 1, (r), X, Y, (ex)) + +# define FP_TO_INT_D(r, X, rsz, rsg) _FP_TO_INT (D, 1, (r), X, (rsz), (rsg)) +# define FP_TO_INT_ROUND_D(r, X, rsz, rsg) \ + _FP_TO_INT_ROUND (D, 1, (r), X, (rsz), (rsg)) +# define FP_FROM_INT_D(X, r, rs, rt) _FP_FROM_INT (D, 1, X, (r), (rs), rt) + +# define _FP_FRAC_HIGH_D(X) _FP_FRAC_HIGH_1 (X) +# define _FP_FRAC_HIGH_RAW_D(X) _FP_FRAC_HIGH_1 (X) + +# define _FP_FRAC_HIGH_DW_D(X) _FP_FRAC_HIGH_2 (X) + +#endif /* W_TYPE_SIZE < 64 */ + +#endif /* !SOFT_FP_DOUBLE_H */ diff --git a/REORG.TODO/soft-fp/eqdf2.c b/REORG.TODO/soft-fp/eqdf2.c new file mode 100644 index 0000000000..8797747065 --- /dev/null +++ b/REORG.TODO/soft-fp/eqdf2.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return 0 iff a == b, 1 otherwise + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +CMPtype +__eqdf2 (DFtype a, DFtype b) +{ + FP_DECL_EX; + FP_DECL_D (A); + FP_DECL_D (B); + CMPtype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_D (A, a); + FP_UNPACK_RAW_D (B, b); + FP_CMP_EQ_D (r, A, B, 1); + FP_HANDLE_EXCEPTIONS; + + return r; +} + +strong_alias (__eqdf2, __nedf2); diff --git a/REORG.TODO/soft-fp/eqsf2.c b/REORG.TODO/soft-fp/eqsf2.c new file mode 100644 index 0000000000..ac3f294efd --- /dev/null +++ b/REORG.TODO/soft-fp/eqsf2.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return 0 iff a == b, 1 otherwise + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +CMPtype +__eqsf2 (SFtype a, SFtype b) +{ + FP_DECL_EX; + FP_DECL_S (A); + FP_DECL_S (B); + CMPtype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_S (A, a); + FP_UNPACK_RAW_S (B, b); + FP_CMP_EQ_S (r, A, B, 1); + FP_HANDLE_EXCEPTIONS; + + return r; +} + +strong_alias (__eqsf2, __nesf2); diff --git a/REORG.TODO/soft-fp/eqtf2.c b/REORG.TODO/soft-fp/eqtf2.c new file mode 100644 index 0000000000..ccccdd1204 --- /dev/null +++ b/REORG.TODO/soft-fp/eqtf2.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return 0 iff a == b, 1 otherwise + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +CMPtype +__eqtf2 (TFtype a, TFtype b) +{ + FP_DECL_EX; + FP_DECL_Q (A); + FP_DECL_Q (B); + CMPtype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_Q (A, a); + FP_UNPACK_RAW_Q (B, b); + FP_CMP_EQ_Q (r, A, B, 1); + FP_HANDLE_EXCEPTIONS; + + return r; +} + +strong_alias (__eqtf2, __netf2); diff --git a/REORG.TODO/soft-fp/extenddftf2.c b/REORG.TODO/soft-fp/extenddftf2.c new file mode 100644 index 0000000000..a8132b4296 --- /dev/null +++ b/REORG.TODO/soft-fp/extenddftf2.c @@ -0,0 +1,55 @@ +/* Software floating-point emulation. + Return a converted to IEEE quad + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#define FP_NO_EXACT_UNDERFLOW +#include "soft-fp.h" +#include "double.h" +#include "quad.h" + +TFtype +__extenddftf2 (DFtype a) +{ + FP_DECL_EX; + FP_DECL_D (A); + FP_DECL_Q (R); + TFtype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_D (A, a); +#if (2 * _FP_W_TYPE_SIZE) < _FP_FRACBITS_Q + FP_EXTEND (Q, D, 4, 2, R, A); +#else + FP_EXTEND (Q, D, 2, 1, R, A); +#endif + FP_PACK_RAW_Q (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/extended.h b/REORG.TODO/soft-fp/extended.h new file mode 100644 index 0000000000..da285a6ecb --- /dev/null +++ b/REORG.TODO/soft-fp/extended.h @@ -0,0 +1,517 @@ +/* Software floating-point emulation. + Definitions for IEEE Extended Precision. + Copyright (C) 1999-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#ifndef SOFT_FP_EXTENDED_H +#define SOFT_FP_EXTENDED_H 1 + +#if _FP_W_TYPE_SIZE < 32 +# error "Here's a nickel, kid. Go buy yourself a real computer." +#endif + +#if _FP_W_TYPE_SIZE < 64 +# define _FP_FRACTBITS_E (4*_FP_W_TYPE_SIZE) +# define _FP_FRACTBITS_DW_E (8*_FP_W_TYPE_SIZE) +#else +# define _FP_FRACTBITS_E (2*_FP_W_TYPE_SIZE) +# define _FP_FRACTBITS_DW_E (4*_FP_W_TYPE_SIZE) +#endif + +#define _FP_FRACBITS_E 64 +#define _FP_FRACXBITS_E (_FP_FRACTBITS_E - _FP_FRACBITS_E) +#define _FP_WFRACBITS_E (_FP_WORKBITS + _FP_FRACBITS_E) +#define _FP_WFRACXBITS_E (_FP_FRACTBITS_E - _FP_WFRACBITS_E) +#define _FP_EXPBITS_E 15 +#define _FP_EXPBIAS_E 16383 +#define _FP_EXPMAX_E 32767 + +#define _FP_QNANBIT_E \ + ((_FP_W_TYPE) 1 << (_FP_FRACBITS_E-2) % _FP_W_TYPE_SIZE) +#define _FP_QNANBIT_SH_E \ + ((_FP_W_TYPE) 1 << (_FP_FRACBITS_E-2+_FP_WORKBITS) % _FP_W_TYPE_SIZE) +#define _FP_IMPLBIT_E \ + ((_FP_W_TYPE) 1 << (_FP_FRACBITS_E-1) % _FP_W_TYPE_SIZE) +#define _FP_IMPLBIT_SH_E \ + ((_FP_W_TYPE) 1 << (_FP_FRACBITS_E-1+_FP_WORKBITS) % _FP_W_TYPE_SIZE) +#define _FP_OVERFLOW_E \ + ((_FP_W_TYPE) 1 << (_FP_WFRACBITS_E % _FP_W_TYPE_SIZE)) + +#define _FP_WFRACBITS_DW_E (2 * _FP_WFRACBITS_E) +#define _FP_WFRACXBITS_DW_E (_FP_FRACTBITS_DW_E - _FP_WFRACBITS_DW_E) +#define _FP_HIGHBIT_DW_E \ + ((_FP_W_TYPE) 1 << (_FP_WFRACBITS_DW_E - 1) % _FP_W_TYPE_SIZE) + +typedef float XFtype __attribute__ ((mode (XF))); + +#if _FP_W_TYPE_SIZE < 64 + +union _FP_UNION_E +{ + XFtype flt; + struct _FP_STRUCT_LAYOUT + { +# if __BYTE_ORDER == __BIG_ENDIAN + unsigned long pad1 : _FP_W_TYPE_SIZE; + unsigned long pad2 : (_FP_W_TYPE_SIZE - 1 - _FP_EXPBITS_E); + unsigned long sign : 1; + unsigned long exp : _FP_EXPBITS_E; + unsigned long frac1 : _FP_W_TYPE_SIZE; + unsigned long frac0 : _FP_W_TYPE_SIZE; +# else + unsigned long frac0 : _FP_W_TYPE_SIZE; + unsigned long frac1 : _FP_W_TYPE_SIZE; + unsigned exp : _FP_EXPBITS_E; + unsigned sign : 1; +# endif /* not bigendian */ + } bits __attribute__ ((packed)); +}; + + +# define FP_DECL_E(X) _FP_DECL (4, X) + +# define FP_UNPACK_RAW_E(X, val) \ + do \ + { \ + union _FP_UNION_E FP_UNPACK_RAW_E_flo; \ + FP_UNPACK_RAW_E_flo.flt = (val); \ + \ + X##_f[2] = 0; \ + X##_f[3] = 0; \ + X##_f[0] = FP_UNPACK_RAW_E_flo.bits.frac0; \ + X##_f[1] = FP_UNPACK_RAW_E_flo.bits.frac1; \ + X##_f[1] &= ~_FP_IMPLBIT_E; \ + X##_e = FP_UNPACK_RAW_E_flo.bits.exp; \ + X##_s = FP_UNPACK_RAW_E_flo.bits.sign; \ + } \ + while (0) + +# define FP_UNPACK_RAW_EP(X, val) \ + do \ + { \ + union _FP_UNION_E *FP_UNPACK_RAW_EP_flo \ + = (union _FP_UNION_E *) (val); \ + \ + X##_f[2] = 0; \ + X##_f[3] = 0; \ + X##_f[0] = FP_UNPACK_RAW_EP_flo->bits.frac0; \ + X##_f[1] = FP_UNPACK_RAW_EP_flo->bits.frac1; \ + X##_f[1] &= ~_FP_IMPLBIT_E; \ + X##_e = FP_UNPACK_RAW_EP_flo->bits.exp; \ + X##_s = FP_UNPACK_RAW_EP_flo->bits.sign; \ + } \ + while (0) + +# define FP_PACK_RAW_E(val, X) \ + do \ + { \ + union _FP_UNION_E FP_PACK_RAW_E_flo; \ + \ + if (X##_e) \ + X##_f[1] |= _FP_IMPLBIT_E; \ + else \ + X##_f[1] &= ~(_FP_IMPLBIT_E); \ + FP_PACK_RAW_E_flo.bits.frac0 = X##_f[0]; \ + FP_PACK_RAW_E_flo.bits.frac1 = X##_f[1]; \ + FP_PACK_RAW_E_flo.bits.exp = X##_e; \ + FP_PACK_RAW_E_flo.bits.sign = X##_s; \ + \ + (val) = FP_PACK_RAW_E_flo.flt; \ + } \ + while (0) + +# define FP_PACK_RAW_EP(val, X) \ + do \ + { \ + if (!FP_INHIBIT_RESULTS) \ + { \ + union _FP_UNION_E *FP_PACK_RAW_EP_flo \ + = (union _FP_UNION_E *) (val); \ + \ + if (X##_e) \ + X##_f[1] |= _FP_IMPLBIT_E; \ + else \ + X##_f[1] &= ~(_FP_IMPLBIT_E); \ + FP_PACK_RAW_EP_flo->bits.frac0 = X##_f[0]; \ + FP_PACK_RAW_EP_flo->bits.frac1 = X##_f[1]; \ + FP_PACK_RAW_EP_flo->bits.exp = X##_e; \ + FP_PACK_RAW_EP_flo->bits.sign = X##_s; \ + } \ + } \ + while (0) + +# define FP_UNPACK_E(X, val) \ + do \ + { \ + FP_UNPACK_RAW_E (X, (val)); \ + _FP_UNPACK_CANONICAL (E, 4, X); \ + } \ + while (0) + +# define FP_UNPACK_EP(X, val) \ + do \ + { \ + FP_UNPACK_RAW_EP (X, (val)); \ + _FP_UNPACK_CANONICAL (E, 4, X); \ + } \ + while (0) + +# define FP_UNPACK_SEMIRAW_E(X, val) \ + do \ + { \ + FP_UNPACK_RAW_E (X, (val)); \ + _FP_UNPACK_SEMIRAW (E, 4, X); \ + } \ + while (0) + +# define FP_UNPACK_SEMIRAW_EP(X, val) \ + do \ + { \ + FP_UNPACK_RAW_EP (X, (val)); \ + _FP_UNPACK_SEMIRAW (E, 4, X); \ + } \ + while (0) + +# define FP_PACK_E(val, X) \ + do \ + { \ + _FP_PACK_CANONICAL (E, 4, X); \ + FP_PACK_RAW_E ((val), X); \ + } \ + while (0) + +# define FP_PACK_EP(val, X) \ + do \ + { \ + _FP_PACK_CANONICAL (E, 4, X); \ + FP_PACK_RAW_EP ((val), X); \ + } \ + while (0) + +# define FP_PACK_SEMIRAW_E(val, X) \ + do \ + { \ + _FP_PACK_SEMIRAW (E, 4, X); \ + FP_PACK_RAW_E ((val), X); \ + } \ + while (0) + +# define FP_PACK_SEMIRAW_EP(val, X) \ + do \ + { \ + _FP_PACK_SEMIRAW (E, 4, X); \ + FP_PACK_RAW_EP ((val), X); \ + } \ + while (0) + +# define FP_ISSIGNAN_E(X) _FP_ISSIGNAN (E, 4, X) +# define FP_NEG_E(R, X) _FP_NEG (E, 4, R, X) +# define FP_ADD_E(R, X, Y) _FP_ADD (E, 4, R, X, Y) +# define FP_SUB_E(R, X, Y) _FP_SUB (E, 4, R, X, Y) +# define FP_MUL_E(R, X, Y) _FP_MUL (E, 4, R, X, Y) +# define FP_DIV_E(R, X, Y) _FP_DIV (E, 4, R, X, Y) +# define FP_SQRT_E(R, X) _FP_SQRT (E, 4, R, X) +# define FP_FMA_E(R, X, Y, Z) _FP_FMA (E, 4, 8, R, X, Y, Z) + +/* Square root algorithms: + We have just one right now, maybe Newton approximation + should be added for those machines where division is fast. + This has special _E version because standard _4 square + root would not work (it has to start normally with the + second word and not the first), but as we have to do it + anyway, we optimize it by doing most of the calculations + in two UWtype registers instead of four. */ + +# define _FP_SQRT_MEAT_E(R, S, T, X, q) \ + do \ + { \ + (q) = (_FP_W_TYPE) 1 << (_FP_W_TYPE_SIZE - 1); \ + _FP_FRAC_SRL_4 (X, (_FP_WORKBITS)); \ + while (q) \ + { \ + T##_f[1] = S##_f[1] + (q); \ + if (T##_f[1] <= X##_f[1]) \ + { \ + S##_f[1] = T##_f[1] + (q); \ + X##_f[1] -= T##_f[1]; \ + R##_f[1] += (q); \ + } \ + _FP_FRAC_SLL_2 (X, 1); \ + (q) >>= 1; \ + } \ + (q) = (_FP_W_TYPE) 1 << (_FP_W_TYPE_SIZE - 1); \ + while (q) \ + { \ + T##_f[0] = S##_f[0] + (q); \ + T##_f[1] = S##_f[1]; \ + if (T##_f[1] < X##_f[1] \ + || (T##_f[1] == X##_f[1] \ + && T##_f[0] <= X##_f[0])) \ + { \ + S##_f[0] = T##_f[0] + (q); \ + S##_f[1] += (T##_f[0] > S##_f[0]); \ + _FP_FRAC_DEC_2 (X, T); \ + R##_f[0] += (q); \ + } \ + _FP_FRAC_SLL_2 (X, 1); \ + (q) >>= 1; \ + } \ + _FP_FRAC_SLL_4 (R, (_FP_WORKBITS)); \ + if (X##_f[0] | X##_f[1]) \ + { \ + if (S##_f[1] < X##_f[1] \ + || (S##_f[1] == X##_f[1] \ + && S##_f[0] < X##_f[0])) \ + R##_f[0] |= _FP_WORK_ROUND; \ + R##_f[0] |= _FP_WORK_STICKY; \ + } \ + } \ + while (0) + +# define FP_CMP_E(r, X, Y, un, ex) _FP_CMP (E, 4, (r), X, Y, (un), (ex)) +# define FP_CMP_EQ_E(r, X, Y, ex) _FP_CMP_EQ (E, 4, (r), X, Y, (ex)) +# define FP_CMP_UNORD_E(r, X, Y, ex) _FP_CMP_UNORD (E, 4, (r), X, Y, (ex)) + +# define FP_TO_INT_E(r, X, rsz, rsg) _FP_TO_INT (E, 4, (r), X, (rsz), (rsg)) +# define FP_TO_INT_ROUND_E(r, X, rsz, rsg) \ + _FP_TO_INT_ROUND (E, 4, (r), X, (rsz), (rsg)) +# define FP_FROM_INT_E(X, r, rs, rt) _FP_FROM_INT (E, 4, X, (r), (rs), rt) + +# define _FP_FRAC_HIGH_E(X) (X##_f[2]) +# define _FP_FRAC_HIGH_RAW_E(X) (X##_f[1]) + +# define _FP_FRAC_HIGH_DW_E(X) (X##_f[4]) + +#else /* not _FP_W_TYPE_SIZE < 64 */ +union _FP_UNION_E +{ + XFtype flt; + struct _FP_STRUCT_LAYOUT + { +# if __BYTE_ORDER == __BIG_ENDIAN + _FP_W_TYPE pad : (_FP_W_TYPE_SIZE - 1 - _FP_EXPBITS_E); + unsigned sign : 1; + unsigned exp : _FP_EXPBITS_E; + _FP_W_TYPE frac : _FP_W_TYPE_SIZE; +# else + _FP_W_TYPE frac : _FP_W_TYPE_SIZE; + unsigned exp : _FP_EXPBITS_E; + unsigned sign : 1; +# endif + } bits; +}; + +# define FP_DECL_E(X) _FP_DECL (2, X) + +# define FP_UNPACK_RAW_E(X, val) \ + do \ + { \ + union _FP_UNION_E FP_UNPACK_RAW_E_flo; \ + FP_UNPACK_RAW_E_flo.flt = (val); \ + \ + X##_f0 = FP_UNPACK_RAW_E_flo.bits.frac; \ + X##_f0 &= ~_FP_IMPLBIT_E; \ + X##_f1 = 0; \ + X##_e = FP_UNPACK_RAW_E_flo.bits.exp; \ + X##_s = FP_UNPACK_RAW_E_flo.bits.sign; \ + } \ + while (0) + +# define FP_UNPACK_RAW_EP(X, val) \ + do \ + { \ + union _FP_UNION_E *FP_UNPACK_RAW_EP_flo \ + = (union _FP_UNION_E *) (val); \ + \ + X##_f0 = FP_UNPACK_RAW_EP_flo->bits.frac; \ + X##_f0 &= ~_FP_IMPLBIT_E; \ + X##_f1 = 0; \ + X##_e = FP_UNPACK_RAW_EP_flo->bits.exp; \ + X##_s = FP_UNPACK_RAW_EP_flo->bits.sign; \ + } \ + while (0) + +# define FP_PACK_RAW_E(val, X) \ + do \ + { \ + union _FP_UNION_E FP_PACK_RAW_E_flo; \ + \ + if (X##_e) \ + X##_f0 |= _FP_IMPLBIT_E; \ + else \ + X##_f0 &= ~(_FP_IMPLBIT_E); \ + FP_PACK_RAW_E_flo.bits.frac = X##_f0; \ + FP_PACK_RAW_E_flo.bits.exp = X##_e; \ + FP_PACK_RAW_E_flo.bits.sign = X##_s; \ + \ + (val) = FP_PACK_RAW_E_flo.flt; \ + } \ + while (0) + +# define FP_PACK_RAW_EP(fs, val, X) \ + do \ + { \ + if (!FP_INHIBIT_RESULTS) \ + { \ + union _FP_UNION_E *FP_PACK_RAW_EP_flo \ + = (union _FP_UNION_E *) (val); \ + \ + if (X##_e) \ + X##_f0 |= _FP_IMPLBIT_E; \ + else \ + X##_f0 &= ~(_FP_IMPLBIT_E); \ + FP_PACK_RAW_EP_flo->bits.frac = X##_f0; \ + FP_PACK_RAW_EP_flo->bits.exp = X##_e; \ + FP_PACK_RAW_EP_flo->bits.sign = X##_s; \ + } \ + } \ + while (0) + + +# define FP_UNPACK_E(X, val) \ + do \ + { \ + FP_UNPACK_RAW_E (X, (val)); \ + _FP_UNPACK_CANONICAL (E, 2, X); \ + } \ + while (0) + +# define FP_UNPACK_EP(X, val) \ + do \ + { \ + FP_UNPACK_RAW_EP (X, (val)); \ + _FP_UNPACK_CANONICAL (E, 2, X); \ + } \ + while (0) + +# define FP_UNPACK_SEMIRAW_E(X, val) \ + do \ + { \ + FP_UNPACK_RAW_E (X, (val)); \ + _FP_UNPACK_SEMIRAW (E, 2, X); \ + } \ + while (0) + +# define FP_UNPACK_SEMIRAW_EP(X, val) \ + do \ + { \ + FP_UNPACK_RAW_EP (X, (val)); \ + _FP_UNPACK_SEMIRAW (E, 2, X); \ + } \ + while (0) + +# define FP_PACK_E(val, X) \ + do \ + { \ + _FP_PACK_CANONICAL (E, 2, X); \ + FP_PACK_RAW_E ((val), X); \ + } \ + while (0) + +# define FP_PACK_EP(val, X) \ + do \ + { \ + _FP_PACK_CANONICAL (E, 2, X); \ + FP_PACK_RAW_EP ((val), X); \ + } \ + while (0) + +# define FP_PACK_SEMIRAW_E(val, X) \ + do \ + { \ + _FP_PACK_SEMIRAW (E, 2, X); \ + FP_PACK_RAW_E ((val), X); \ + } \ + while (0) + +# define FP_PACK_SEMIRAW_EP(val, X) \ + do \ + { \ + _FP_PACK_SEMIRAW (E, 2, X); \ + FP_PACK_RAW_EP ((val), X); \ + } \ + while (0) + +# define FP_ISSIGNAN_E(X) _FP_ISSIGNAN (E, 2, X) +# define FP_NEG_E(R, X) _FP_NEG (E, 2, R, X) +# define FP_ADD_E(R, X, Y) _FP_ADD (E, 2, R, X, Y) +# define FP_SUB_E(R, X, Y) _FP_SUB (E, 2, R, X, Y) +# define FP_MUL_E(R, X, Y) _FP_MUL (E, 2, R, X, Y) +# define FP_DIV_E(R, X, Y) _FP_DIV (E, 2, R, X, Y) +# define FP_SQRT_E(R, X) _FP_SQRT (E, 2, R, X) +# define FP_FMA_E(R, X, Y, Z) _FP_FMA (E, 2, 4, R, X, Y, Z) + +/* Square root algorithms: + We have just one right now, maybe Newton approximation + should be added for those machines where division is fast. + We optimize it by doing most of the calculations + in one UWtype registers instead of two, although we don't + have to. */ +# define _FP_SQRT_MEAT_E(R, S, T, X, q) \ + do \ + { \ + (q) = (_FP_W_TYPE) 1 << (_FP_W_TYPE_SIZE - 1); \ + _FP_FRAC_SRL_2 (X, (_FP_WORKBITS)); \ + while (q) \ + { \ + T##_f0 = S##_f0 + (q); \ + if (T##_f0 <= X##_f0) \ + { \ + S##_f0 = T##_f0 + (q); \ + X##_f0 -= T##_f0; \ + R##_f0 += (q); \ + } \ + _FP_FRAC_SLL_1 (X, 1); \ + (q) >>= 1; \ + } \ + _FP_FRAC_SLL_2 (R, (_FP_WORKBITS)); \ + if (X##_f0) \ + { \ + if (S##_f0 < X##_f0) \ + R##_f0 |= _FP_WORK_ROUND; \ + R##_f0 |= _FP_WORK_STICKY; \ + } \ + } \ + while (0) + +# define FP_CMP_E(r, X, Y, un, ex) _FP_CMP (E, 2, (r), X, Y, (un), (ex)) +# define FP_CMP_EQ_E(r, X, Y, ex) _FP_CMP_EQ (E, 2, (r), X, Y, (ex)) +# define FP_CMP_UNORD_E(r, X, Y, ex) _FP_CMP_UNORD (E, 2, (r), X, Y, (ex)) + +# define FP_TO_INT_E(r, X, rsz, rsg) _FP_TO_INT (E, 2, (r), X, (rsz), (rsg)) +# define FP_TO_INT_ROUND_E(r, X, rsz, rsg) \ + _FP_TO_INT_ROUND (E, 2, (r), X, (rsz), (rsg)) +# define FP_FROM_INT_E(X, r, rs, rt) _FP_FROM_INT (E, 2, X, (r), (rs), rt) + +# define _FP_FRAC_HIGH_E(X) (X##_f1) +# define _FP_FRAC_HIGH_RAW_E(X) (X##_f0) + +# define _FP_FRAC_HIGH_DW_E(X) (X##_f[2]) + +#endif /* not _FP_W_TYPE_SIZE < 64 */ + +#endif /* !SOFT_FP_EXTENDED_H */ diff --git a/REORG.TODO/soft-fp/extendhftf2.c b/REORG.TODO/soft-fp/extendhftf2.c new file mode 100644 index 0000000000..962b32da02 --- /dev/null +++ b/REORG.TODO/soft-fp/extendhftf2.c @@ -0,0 +1,53 @@ +/* Software floating-point emulation. + Return an IEEE half converted to IEEE quad + Copyright (C) 1997-2017 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#define FP_NO_EXACT_UNDERFLOW +#include "soft-fp.h" +#include "half.h" +#include "quad.h" + +TFtype +__extendhftf2 (HFtype a) +{ + FP_DECL_EX; + FP_DECL_H (A); + FP_DECL_Q (R); + TFtype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_H (A, a); +#if (2 * _FP_W_TYPE_SIZE) < _FP_FRACBITS_Q + FP_EXTEND (Q, H, 4, 1, R, A); +#else + FP_EXTEND (Q, H, 2, 1, R, A); +#endif + FP_PACK_RAW_Q (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/extendsfdf2.c b/REORG.TODO/soft-fp/extendsfdf2.c new file mode 100644 index 0000000000..67343ef77c --- /dev/null +++ b/REORG.TODO/soft-fp/extendsfdf2.c @@ -0,0 +1,55 @@ +/* Software floating-point emulation. + Return a converted to IEEE double + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#define FP_NO_EXACT_UNDERFLOW +#include "soft-fp.h" +#include "single.h" +#include "double.h" + +DFtype +__extendsfdf2 (SFtype a) +{ + FP_DECL_EX; + FP_DECL_S (A); + FP_DECL_D (R); + DFtype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_S (A, a); +#if _FP_W_TYPE_SIZE < _FP_FRACBITS_D + FP_EXTEND (D, S, 2, 1, R, A); +#else + FP_EXTEND (D, S, 1, 1, R, A); +#endif + FP_PACK_RAW_D (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/extendsftf2.c b/REORG.TODO/soft-fp/extendsftf2.c new file mode 100644 index 0000000000..b960db9105 --- /dev/null +++ b/REORG.TODO/soft-fp/extendsftf2.c @@ -0,0 +1,55 @@ +/* Software floating-point emulation. + Return a converted to IEEE quad + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#define FP_NO_EXACT_UNDERFLOW +#include "soft-fp.h" +#include "single.h" +#include "quad.h" + +TFtype +__extendsftf2 (SFtype a) +{ + FP_DECL_EX; + FP_DECL_S (A); + FP_DECL_Q (R); + TFtype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_S (A, a); +#if (2 * _FP_W_TYPE_SIZE) < _FP_FRACBITS_Q + FP_EXTEND (Q, S, 4, 1, R, A); +#else + FP_EXTEND (Q, S, 2, 1, R, A); +#endif + FP_PACK_RAW_Q (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/extendxftf2.c b/REORG.TODO/soft-fp/extendxftf2.c new file mode 100644 index 0000000000..fecf7d31ec --- /dev/null +++ b/REORG.TODO/soft-fp/extendxftf2.c @@ -0,0 +1,53 @@ +/* Software floating-point emulation. + Return a converted to IEEE quad + Copyright (C) 2007-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Uros Bizjak (ubizjak@gmail.com). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "extended.h" +#include "quad.h" + +TFtype +__extendxftf2 (XFtype a) +{ + FP_DECL_EX; + FP_DECL_E (A); + FP_DECL_Q (R); + TFtype r; + + FP_INIT_TRAPPING_EXCEPTIONS; + FP_UNPACK_RAW_E (A, a); +#if (2 * _FP_W_TYPE_SIZE) < _FP_FRACBITS_Q + FP_EXTEND (Q, E, 4, 4, R, A); +#else + FP_EXTEND (Q, E, 2, 2, R, A); +#endif + FP_PACK_RAW_Q (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixdfdi.c b/REORG.TODO/soft-fp/fixdfdi.c new file mode 100644 index 0000000000..b29f8969f5 --- /dev/null +++ b/REORG.TODO/soft-fp/fixdfdi.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a to 64bit signed integer + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +DItype +__fixdfdi (DFtype a) +{ + FP_DECL_EX; + FP_DECL_D (A); + UDItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_D (A, a); + FP_TO_INT_D (r, A, DI_BITS, 1); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixdfsi.c b/REORG.TODO/soft-fp/fixdfsi.c new file mode 100644 index 0000000000..a1a17c35f4 --- /dev/null +++ b/REORG.TODO/soft-fp/fixdfsi.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a to 32bit signed integer + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +SItype +__fixdfsi (DFtype a) +{ + FP_DECL_EX; + FP_DECL_D (A); + USItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_D (A, a); + FP_TO_INT_D (r, A, SI_BITS, 1); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixdfti.c b/REORG.TODO/soft-fp/fixdfti.c new file mode 100644 index 0000000000..1caa5d1349 --- /dev/null +++ b/REORG.TODO/soft-fp/fixdfti.c @@ -0,0 +1,46 @@ +/* Software floating-point emulation. + Convert IEEE double to 128bit signed integer + Copyright (C) 2007-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Uros Bizjak (ubizjak@gmail.com). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +TItype +__fixdfti (DFtype a) +{ + FP_DECL_EX; + FP_DECL_D (A); + UTItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_D (A, a); + FP_TO_INT_D (r, A, TI_BITS, 1); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixhfti.c b/REORG.TODO/soft-fp/fixhfti.c new file mode 100644 index 0000000000..b415b74517 --- /dev/null +++ b/REORG.TODO/soft-fp/fixhfti.c @@ -0,0 +1,45 @@ +/* Software floating-point emulation. + Convert IEEE half to 128bit signed integer + Copyright (C) 2007-2017 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "half.h" + +TItype +__fixhfti (HFtype a) +{ + FP_DECL_EX; + FP_DECL_H (A); + UTItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_H (A, a); + FP_TO_INT_H (r, A, TI_BITS, 1); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixsfdi.c b/REORG.TODO/soft-fp/fixsfdi.c new file mode 100644 index 0000000000..bf3ccd6fde --- /dev/null +++ b/REORG.TODO/soft-fp/fixsfdi.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a to 64bit signed integer + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +DItype +__fixsfdi (SFtype a) +{ + FP_DECL_EX; + FP_DECL_S (A); + UDItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_S (A, a); + FP_TO_INT_S (r, A, DI_BITS, 1); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixsfsi.c b/REORG.TODO/soft-fp/fixsfsi.c new file mode 100644 index 0000000000..34f99ab14c --- /dev/null +++ b/REORG.TODO/soft-fp/fixsfsi.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a to 32bit signed integer + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +SItype +__fixsfsi (SFtype a) +{ + FP_DECL_EX; + FP_DECL_S (A); + USItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_S (A, a); + FP_TO_INT_S (r, A, SI_BITS, 1); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixsfti.c b/REORG.TODO/soft-fp/fixsfti.c new file mode 100644 index 0000000000..d88bb9baa1 --- /dev/null +++ b/REORG.TODO/soft-fp/fixsfti.c @@ -0,0 +1,46 @@ +/* Software floating-point emulation. + Convert IEEE single to 128bit signed integer + Copyright (C) 2007-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Uros Bizjak (ubizjak@gmail.com). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +TItype +__fixsfti (SFtype a) +{ + FP_DECL_EX; + FP_DECL_S (A); + UTItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_S (A, a); + FP_TO_INT_S (r, A, TI_BITS, 1); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixtfdi.c b/REORG.TODO/soft-fp/fixtfdi.c new file mode 100644 index 0000000000..2c7ce6b3f6 --- /dev/null +++ b/REORG.TODO/soft-fp/fixtfdi.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a to 64bit signed integer + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +DItype +__fixtfdi (TFtype a) +{ + FP_DECL_EX; + FP_DECL_Q (A); + UDItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_Q (A, a); + FP_TO_INT_Q (r, A, DI_BITS, 1); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixtfsi.c b/REORG.TODO/soft-fp/fixtfsi.c new file mode 100644 index 0000000000..bdcc6261ba --- /dev/null +++ b/REORG.TODO/soft-fp/fixtfsi.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a to 32bit signed integer + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +SItype +__fixtfsi (TFtype a) +{ + FP_DECL_EX; + FP_DECL_Q (A); + USItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_Q (A, a); + FP_TO_INT_Q (r, A, SI_BITS, 1); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixtfti.c b/REORG.TODO/soft-fp/fixtfti.c new file mode 100644 index 0000000000..a235839058 --- /dev/null +++ b/REORG.TODO/soft-fp/fixtfti.c @@ -0,0 +1,46 @@ +/* Software floating-point emulation. + Convert IEEE quad to 128bit signed integer + Copyright (C) 2007-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Uros Bizjak (ubizjak@gmail.com). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +TItype +__fixtfti (TFtype a) +{ + FP_DECL_EX; + FP_DECL_Q (A); + UTItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_Q (A, a); + FP_TO_INT_Q (r, A, TI_BITS, 1); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixunsdfdi.c b/REORG.TODO/soft-fp/fixunsdfdi.c new file mode 100644 index 0000000000..f95c5ab2b0 --- /dev/null +++ b/REORG.TODO/soft-fp/fixunsdfdi.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a to 64bit unsigned integer + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +UDItype +__fixunsdfdi (DFtype a) +{ + FP_DECL_EX; + FP_DECL_D (A); + UDItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_D (A, a); + FP_TO_INT_D (r, A, DI_BITS, 0); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixunsdfsi.c b/REORG.TODO/soft-fp/fixunsdfsi.c new file mode 100644 index 0000000000..bf6a54ea61 --- /dev/null +++ b/REORG.TODO/soft-fp/fixunsdfsi.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a to 32bit unsigned integer + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +USItype +__fixunsdfsi (DFtype a) +{ + FP_DECL_EX; + FP_DECL_D (A); + USItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_D (A, a); + FP_TO_INT_D (r, A, SI_BITS, 0); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixunsdfti.c b/REORG.TODO/soft-fp/fixunsdfti.c new file mode 100644 index 0000000000..958794e855 --- /dev/null +++ b/REORG.TODO/soft-fp/fixunsdfti.c @@ -0,0 +1,46 @@ +/* Software floating-point emulation. + Convert IEEE double to 128bit unsigned integer + Copyright (C) 2007-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Uros Bizjak (ubizjak@gmail.com). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +UTItype +__fixunsdfti (DFtype a) +{ + FP_DECL_EX; + FP_DECL_D (A); + UTItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_D (A, a); + FP_TO_INT_D (r, A, TI_BITS, 0); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixunshfti.c b/REORG.TODO/soft-fp/fixunshfti.c new file mode 100644 index 0000000000..3fce1ec042 --- /dev/null +++ b/REORG.TODO/soft-fp/fixunshfti.c @@ -0,0 +1,45 @@ +/* Software floating-point emulation. + Convert IEEE half to 128bit unsigned integer + Copyright (C) 2007-2017 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "half.h" + +UTItype +__fixunshfti (HFtype a) +{ + FP_DECL_EX; + FP_DECL_H (A); + UTItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_H (A, a); + FP_TO_INT_H (r, A, TI_BITS, 0); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixunssfdi.c b/REORG.TODO/soft-fp/fixunssfdi.c new file mode 100644 index 0000000000..567b87a8f4 --- /dev/null +++ b/REORG.TODO/soft-fp/fixunssfdi.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a to 64bit unsigned integer + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +UDItype +__fixunssfdi (SFtype a) +{ + FP_DECL_EX; + FP_DECL_S (A); + UDItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_S (A, a); + FP_TO_INT_S (r, A, DI_BITS, 0); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixunssfsi.c b/REORG.TODO/soft-fp/fixunssfsi.c new file mode 100644 index 0000000000..85b756b943 --- /dev/null +++ b/REORG.TODO/soft-fp/fixunssfsi.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a to 32bit unsigned integer + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +USItype +__fixunssfsi (SFtype a) +{ + FP_DECL_EX; + FP_DECL_S (A); + USItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_S (A, a); + FP_TO_INT_S (r, A, SI_BITS, 0); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixunssfti.c b/REORG.TODO/soft-fp/fixunssfti.c new file mode 100644 index 0000000000..363e6fcc11 --- /dev/null +++ b/REORG.TODO/soft-fp/fixunssfti.c @@ -0,0 +1,46 @@ +/* Software floating-point emulation. + Convert IEEE single to 128bit unsigned integer + Copyright (C) 2007-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Uros Bizjak (ubizjak@gmail.com). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +UTItype +__fixunssfti (SFtype a) +{ + FP_DECL_EX; + FP_DECL_S (A); + UTItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_S (A, a); + FP_TO_INT_S (r, A, TI_BITS, 0); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixunstfdi.c b/REORG.TODO/soft-fp/fixunstfdi.c new file mode 100644 index 0000000000..5f70228c1c --- /dev/null +++ b/REORG.TODO/soft-fp/fixunstfdi.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a to 64bit unsigned integer + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +UDItype +__fixunstfdi (TFtype a) +{ + FP_DECL_EX; + FP_DECL_Q (A); + UDItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_Q (A, a); + FP_TO_INT_Q (r, A, DI_BITS, 0); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixunstfsi.c b/REORG.TODO/soft-fp/fixunstfsi.c new file mode 100644 index 0000000000..06fd297ee2 --- /dev/null +++ b/REORG.TODO/soft-fp/fixunstfsi.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a to 32bit unsigned integer + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +USItype +__fixunstfsi (TFtype a) +{ + FP_DECL_EX; + FP_DECL_Q (A); + USItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_Q (A, a); + FP_TO_INT_Q (r, A, SI_BITS, 0); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/fixunstfti.c b/REORG.TODO/soft-fp/fixunstfti.c new file mode 100644 index 0000000000..1b948c1506 --- /dev/null +++ b/REORG.TODO/soft-fp/fixunstfti.c @@ -0,0 +1,46 @@ +/* Software floating-point emulation. + Convert IEEE quad to 128bit unsigned integer + Copyright (C) 2007-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Uros Bizjak (ubizjak@gmail.com). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +UTItype +__fixunstfti (TFtype a) +{ + FP_DECL_EX; + FP_DECL_Q (A); + UTItype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_Q (A, a); + FP_TO_INT_Q (r, A, TI_BITS, 0); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/floatdidf.c b/REORG.TODO/soft-fp/floatdidf.c new file mode 100644 index 0000000000..57621c461d --- /dev/null +++ b/REORG.TODO/soft-fp/floatdidf.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a 64bit signed integer to IEEE double + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +DFtype +__floatdidf (DItype i) +{ + FP_DECL_EX; + FP_DECL_D (A); + DFtype a; + + FP_INIT_ROUNDMODE; + FP_FROM_INT_D (A, i, DI_BITS, UDItype); + FP_PACK_RAW_D (a, A); + FP_HANDLE_EXCEPTIONS; + + return a; +} diff --git a/REORG.TODO/soft-fp/floatdisf.c b/REORG.TODO/soft-fp/floatdisf.c new file mode 100644 index 0000000000..2f88af0780 --- /dev/null +++ b/REORG.TODO/soft-fp/floatdisf.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a 64bit signed integer to IEEE single + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +SFtype +__floatdisf (DItype i) +{ + FP_DECL_EX; + FP_DECL_S (A); + SFtype a; + + FP_INIT_ROUNDMODE; + FP_FROM_INT_S (A, i, DI_BITS, UDItype); + FP_PACK_RAW_S (a, A); + FP_HANDLE_EXCEPTIONS; + + return a; +} diff --git a/REORG.TODO/soft-fp/floatditf.c b/REORG.TODO/soft-fp/floatditf.c new file mode 100644 index 0000000000..987a318529 --- /dev/null +++ b/REORG.TODO/soft-fp/floatditf.c @@ -0,0 +1,45 @@ +/* Software floating-point emulation. + Convert a 64bit signed integer to IEEE quad + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#define FP_NO_EXCEPTIONS +#include "soft-fp.h" +#include "quad.h" + +TFtype +__floatditf (DItype i) +{ + FP_DECL_Q (A); + TFtype a; + + FP_FROM_INT_Q (A, i, DI_BITS, UDItype); + FP_PACK_RAW_Q (a, A); + + return a; +} diff --git a/REORG.TODO/soft-fp/floatsidf.c b/REORG.TODO/soft-fp/floatsidf.c new file mode 100644 index 0000000000..268ce2da69 --- /dev/null +++ b/REORG.TODO/soft-fp/floatsidf.c @@ -0,0 +1,45 @@ +/* Software floating-point emulation. + Convert a 32bit signed integer to IEEE double + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#define FP_NO_EXCEPTIONS +#include "soft-fp.h" +#include "double.h" + +DFtype +__floatsidf (SItype i) +{ + FP_DECL_D (A); + DFtype a; + + FP_FROM_INT_D (A, i, SI_BITS, USItype); + FP_PACK_RAW_D (a, A); + + return a; +} diff --git a/REORG.TODO/soft-fp/floatsisf.c b/REORG.TODO/soft-fp/floatsisf.c new file mode 100644 index 0000000000..18ed338219 --- /dev/null +++ b/REORG.TODO/soft-fp/floatsisf.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a 32bit signed integer to IEEE single + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +SFtype +__floatsisf (SItype i) +{ + FP_DECL_EX; + FP_DECL_S (A); + SFtype a; + + FP_INIT_ROUNDMODE; + FP_FROM_INT_S (A, i, SI_BITS, USItype); + FP_PACK_RAW_S (a, A); + FP_HANDLE_EXCEPTIONS; + + return a; +} diff --git a/REORG.TODO/soft-fp/floatsitf.c b/REORG.TODO/soft-fp/floatsitf.c new file mode 100644 index 0000000000..303e4a8336 --- /dev/null +++ b/REORG.TODO/soft-fp/floatsitf.c @@ -0,0 +1,45 @@ +/* Software floating-point emulation. + Convert a 32bit signed integer to IEEE quad + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#define FP_NO_EXCEPTIONS +#include "soft-fp.h" +#include "quad.h" + +TFtype +__floatsitf (SItype i) +{ + FP_DECL_Q (A); + TFtype a; + + FP_FROM_INT_Q (A, i, SI_BITS, USItype); + FP_PACK_RAW_Q (a, A); + + return a; +} diff --git a/REORG.TODO/soft-fp/floattidf.c b/REORG.TODO/soft-fp/floattidf.c new file mode 100644 index 0000000000..c2a3290a79 --- /dev/null +++ b/REORG.TODO/soft-fp/floattidf.c @@ -0,0 +1,46 @@ +/* Software floating-point emulation. + Convert a 128bit signed integer to IEEE double + Copyright (C) 2007-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Uros Bizjak (ubizjak@gmail.com). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +DFtype +__floattidf (TItype i) +{ + FP_DECL_EX; + FP_DECL_D (A); + DFtype a; + + FP_INIT_ROUNDMODE; + FP_FROM_INT_D (A, i, TI_BITS, UTItype); + FP_PACK_RAW_D (a, A); + FP_HANDLE_EXCEPTIONS; + + return a; +} diff --git a/REORG.TODO/soft-fp/floattihf.c b/REORG.TODO/soft-fp/floattihf.c new file mode 100644 index 0000000000..632d3d698a --- /dev/null +++ b/REORG.TODO/soft-fp/floattihf.c @@ -0,0 +1,45 @@ +/* Software floating-point emulation. + Convert a 128bit signed integer to IEEE half + Copyright (C) 2007-2017 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "half.h" + +HFtype +__floattihf (TItype i) +{ + FP_DECL_EX; + FP_DECL_H (A); + HFtype a; + + FP_INIT_ROUNDMODE; + FP_FROM_INT_H (A, i, TI_BITS, UTItype); + FP_PACK_RAW_H (a, A); + FP_HANDLE_EXCEPTIONS; + + return a; +} diff --git a/REORG.TODO/soft-fp/floattisf.c b/REORG.TODO/soft-fp/floattisf.c new file mode 100644 index 0000000000..0d0f82a296 --- /dev/null +++ b/REORG.TODO/soft-fp/floattisf.c @@ -0,0 +1,46 @@ +/* Software floating-point emulation. + Convert a 128bit signed integer to IEEE single + Copyright (C) 2007-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Uros Bizjak (ubizjak@gmail.com). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +SFtype +__floattisf (TItype i) +{ + FP_DECL_EX; + FP_DECL_S (A); + SFtype a; + + FP_INIT_ROUNDMODE; + FP_FROM_INT_S (A, i, TI_BITS, UTItype); + FP_PACK_RAW_S (a, A); + FP_HANDLE_EXCEPTIONS; + + return a; +} diff --git a/REORG.TODO/soft-fp/floattitf.c b/REORG.TODO/soft-fp/floattitf.c new file mode 100644 index 0000000000..7c4b6a9113 --- /dev/null +++ b/REORG.TODO/soft-fp/floattitf.c @@ -0,0 +1,46 @@ +/* Software floating-point emulation. + Convert a 128bit signed integer to IEEE quad + Copyright (C) 2007-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Uros Bizjak (ubizjak@gmail.com). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +TFtype +__floattitf (TItype i) +{ + FP_DECL_EX; + FP_DECL_Q (A); + TFtype a; + + FP_INIT_ROUNDMODE; + FP_FROM_INT_Q (A, i, TI_BITS, UTItype); + FP_PACK_RAW_Q (a, A); + FP_HANDLE_EXCEPTIONS; + + return a; +} diff --git a/REORG.TODO/soft-fp/floatundidf.c b/REORG.TODO/soft-fp/floatundidf.c new file mode 100644 index 0000000000..0260666b77 --- /dev/null +++ b/REORG.TODO/soft-fp/floatundidf.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a 64bit unsigned integer to IEEE double + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +DFtype +__floatundidf (UDItype i) +{ + FP_DECL_EX; + FP_DECL_D (A); + DFtype a; + + FP_INIT_ROUNDMODE; + FP_FROM_INT_D (A, i, DI_BITS, UDItype); + FP_PACK_RAW_D (a, A); + FP_HANDLE_EXCEPTIONS; + + return a; +} diff --git a/REORG.TODO/soft-fp/floatundisf.c b/REORG.TODO/soft-fp/floatundisf.c new file mode 100644 index 0000000000..b3a7a2e0bc --- /dev/null +++ b/REORG.TODO/soft-fp/floatundisf.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a 64bit unsigned integer to IEEE single + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +SFtype +__floatundisf (UDItype i) +{ + FP_DECL_EX; + FP_DECL_S (A); + SFtype a; + + FP_INIT_ROUNDMODE; + FP_FROM_INT_S (A, i, DI_BITS, UDItype); + FP_PACK_RAW_S (a, A); + FP_HANDLE_EXCEPTIONS; + + return a; +} diff --git a/REORG.TODO/soft-fp/floatunditf.c b/REORG.TODO/soft-fp/floatunditf.c new file mode 100644 index 0000000000..e5eaa50d8f --- /dev/null +++ b/REORG.TODO/soft-fp/floatunditf.c @@ -0,0 +1,45 @@ +/* Software floating-point emulation. + Convert a 64bit unsigned integer to IEEE quad + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#define FP_NO_EXCEPTIONS +#include "soft-fp.h" +#include "quad.h" + +TFtype +__floatunditf (UDItype i) +{ + FP_DECL_Q (A); + TFtype a; + + FP_FROM_INT_Q (A, i, DI_BITS, UDItype); + FP_PACK_RAW_Q (a, A); + + return a; +} diff --git a/REORG.TODO/soft-fp/floatunsidf.c b/REORG.TODO/soft-fp/floatunsidf.c new file mode 100644 index 0000000000..d0ab17cc3c --- /dev/null +++ b/REORG.TODO/soft-fp/floatunsidf.c @@ -0,0 +1,45 @@ +/* Software floating-point emulation. + Convert a 32bit unsigned integer to IEEE double + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#define FP_NO_EXCEPTIONS +#include "soft-fp.h" +#include "double.h" + +DFtype +__floatunsidf (USItype i) +{ + FP_DECL_D (A); + DFtype a; + + FP_FROM_INT_D (A, i, SI_BITS, USItype); + FP_PACK_RAW_D (a, A); + + return a; +} diff --git a/REORG.TODO/soft-fp/floatunsisf.c b/REORG.TODO/soft-fp/floatunsisf.c new file mode 100644 index 0000000000..f5c559b326 --- /dev/null +++ b/REORG.TODO/soft-fp/floatunsisf.c @@ -0,0 +1,47 @@ +/* Software floating-point emulation. + Convert a 32bit unsigned integer to IEEE single + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +SFtype +__floatunsisf (USItype i) +{ + FP_DECL_EX; + FP_DECL_S (A); + SFtype a; + + FP_INIT_ROUNDMODE; + FP_FROM_INT_S (A, i, SI_BITS, USItype); + FP_PACK_RAW_S (a, A); + FP_HANDLE_EXCEPTIONS; + + return a; +} diff --git a/REORG.TODO/soft-fp/floatunsitf.c b/REORG.TODO/soft-fp/floatunsitf.c new file mode 100644 index 0000000000..658bc82347 --- /dev/null +++ b/REORG.TODO/soft-fp/floatunsitf.c @@ -0,0 +1,45 @@ +/* Software floating-point emulation. + Convert a 32bit unsigned integer to IEEE quad + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#define FP_NO_EXCEPTIONS +#include "soft-fp.h" +#include "quad.h" + +TFtype +__floatunsitf (USItype i) +{ + FP_DECL_Q (A); + TFtype a; + + FP_FROM_INT_Q (A, i, SI_BITS, USItype); + FP_PACK_RAW_Q (a, A); + + return a; +} diff --git a/REORG.TODO/soft-fp/floatuntidf.c b/REORG.TODO/soft-fp/floatuntidf.c new file mode 100644 index 0000000000..cac314da78 --- /dev/null +++ b/REORG.TODO/soft-fp/floatuntidf.c @@ -0,0 +1,46 @@ +/* Software floating-point emulation. + Convert a 128bit unsigned integer to IEEE double + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Uros Bizjak (ubizjak@gmail.com). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +DFtype +__floatuntidf (UTItype i) +{ + FP_DECL_EX; + FP_DECL_D (A); + DFtype a; + + FP_INIT_ROUNDMODE; + FP_FROM_INT_D (A, i, TI_BITS, UTItype); + FP_PACK_RAW_D (a, A); + FP_HANDLE_EXCEPTIONS; + + return a; +} diff --git a/REORG.TODO/soft-fp/floatuntihf.c b/REORG.TODO/soft-fp/floatuntihf.c new file mode 100644 index 0000000000..6abd0724a4 --- /dev/null +++ b/REORG.TODO/soft-fp/floatuntihf.c @@ -0,0 +1,45 @@ +/* Software floating-point emulation. + Convert a 128bit unsigned integer to IEEE half. + Copyright (C) 2007-2017 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "half.h" + +HFtype +__floatuntihf (UTItype i) +{ + FP_DECL_EX; + FP_DECL_H (A); + HFtype a; + + FP_INIT_ROUNDMODE; + FP_FROM_INT_H (A, i, TI_BITS, UTItype); + FP_PACK_RAW_H (a, A); + FP_HANDLE_EXCEPTIONS; + + return a; +} diff --git a/REORG.TODO/soft-fp/floatuntisf.c b/REORG.TODO/soft-fp/floatuntisf.c new file mode 100644 index 0000000000..9b7c17f4a8 --- /dev/null +++ b/REORG.TODO/soft-fp/floatuntisf.c @@ -0,0 +1,46 @@ +/* Software floating-point emulation. + Convert a 128bit unsigned integer to IEEE single + Copyright (C) 2007-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Uros Bizjak (ubizjak@gmail.com). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +SFtype +__floatuntisf (UTItype i) +{ + FP_DECL_EX; + FP_DECL_S (A); + SFtype a; + + FP_INIT_ROUNDMODE; + FP_FROM_INT_S (A, i, TI_BITS, UTItype); + FP_PACK_RAW_S (a, A); + FP_HANDLE_EXCEPTIONS; + + return a; +} diff --git a/REORG.TODO/soft-fp/floatuntitf.c b/REORG.TODO/soft-fp/floatuntitf.c new file mode 100644 index 0000000000..8855980ea7 --- /dev/null +++ b/REORG.TODO/soft-fp/floatuntitf.c @@ -0,0 +1,46 @@ +/* Software floating-point emulation. + Convert a 128bit unsigned integer to IEEE quad + Copyright (C) 2007-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Uros Bizjak (ubizjak@gmail.com). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +TFtype +__floatuntitf (UTItype i) +{ + FP_DECL_EX; + FP_DECL_Q (A); + TFtype a; + + FP_INIT_ROUNDMODE; + FP_FROM_INT_Q (A, i, TI_BITS, UTItype); + FP_PACK_RAW_Q (a, A); + FP_HANDLE_EXCEPTIONS; + + return a; +} diff --git a/REORG.TODO/soft-fp/fmadf4.c b/REORG.TODO/soft-fp/fmadf4.c new file mode 100644 index 0000000000..74e2360eb7 --- /dev/null +++ b/REORG.TODO/soft-fp/fmadf4.c @@ -0,0 +1,72 @@ +/* Implement fma using soft-fp. + Copyright (C) 2013-2017 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include <math.h> +#include <libc-diag.h> + +/* R_e is not set in cases where it is not used in packing, but the + compiler does not see that it is set in all cases where it is + used, resulting in warnings that it may be used uninitialized. + The location of the warning differs in different versions of GCC, + it may be where R is defined using a macro or it may be where the + macro is defined. */ +DIAG_PUSH_NEEDS_COMMENT; +DIAG_IGNORE_NEEDS_COMMENT (4.9, "-Wmaybe-uninitialized"); + +#include "soft-fp.h" +#include "double.h" + +double +__fma (double a, double b, double c) +{ + FP_DECL_EX; + FP_DECL_D (A); + FP_DECL_D (B); + FP_DECL_D (C); + FP_DECL_D (R); + double r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_D (A, a); + FP_UNPACK_D (B, b); + FP_UNPACK_D (C, c); + FP_FMA_D (R, A, B, C); + FP_PACK_D (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} +DIAG_POP_NEEDS_COMMENT; + +#ifndef __fma +weak_alias (__fma, fma) +#endif + +#ifdef NO_LONG_DOUBLE +strong_alias (__fma, __fmal) +weak_alias (__fmal, fmal) +#endif diff --git a/REORG.TODO/soft-fp/fmasf4.c b/REORG.TODO/soft-fp/fmasf4.c new file mode 100644 index 0000000000..2d3120eda9 --- /dev/null +++ b/REORG.TODO/soft-fp/fmasf4.c @@ -0,0 +1,67 @@ +/* Implement fmaf using soft-fp. + Copyright (C) 2013-2017 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include <math.h> +#include <libc-diag.h> + +/* R_e is not set in cases where it is not used in packing, but the + compiler does not see that it is set in all cases where it is + used, resulting in warnings that it may be used uninitialized. + The location of the warning differs in different versions of GCC, + it may be where R is defined using a macro or it may be where the + macro is defined. */ +DIAG_PUSH_NEEDS_COMMENT; +DIAG_IGNORE_NEEDS_COMMENT (4.9, "-Wmaybe-uninitialized"); + +#include "soft-fp.h" +#include "single.h" + +float +__fmaf (float a, float b, float c) +{ + FP_DECL_EX; + FP_DECL_S (A); + FP_DECL_S (B); + FP_DECL_S (C); + FP_DECL_S (R); + float r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_S (A, a); + FP_UNPACK_S (B, b); + FP_UNPACK_S (C, c); + FP_FMA_S (R, A, B, C); + FP_PACK_S (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} +DIAG_POP_NEEDS_COMMENT; + +#ifndef __fmaf +weak_alias (__fmaf, fmaf) +#endif diff --git a/REORG.TODO/soft-fp/fmatf4.c b/REORG.TODO/soft-fp/fmatf4.c new file mode 100644 index 0000000000..553a7ad3f8 --- /dev/null +++ b/REORG.TODO/soft-fp/fmatf4.c @@ -0,0 +1,65 @@ +/* Implement fmal using soft-fp. + Copyright (C) 2013-2017 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include <math.h> +#include <libc-diag.h> + +/* R_e is not set in cases where it is not used in packing, but the + compiler does not see that it is set in all cases where it is + used, resulting in warnings that it may be used uninitialized. + The location of the warning differs in different versions of GCC, + it may be where R is defined using a macro or it may be where the + macro is defined. */ +DIAG_PUSH_NEEDS_COMMENT; +DIAG_IGNORE_NEEDS_COMMENT (4.9, "-Wmaybe-uninitialized"); + +#include "soft-fp.h" +#include "quad.h" + +long double +__fmal (long double a, long double b, long double c) +{ + FP_DECL_EX; + FP_DECL_Q (A); + FP_DECL_Q (B); + FP_DECL_Q (C); + FP_DECL_Q (R); + long double r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_Q (A, a); + FP_UNPACK_Q (B, b); + FP_UNPACK_Q (C, c); + FP_FMA_Q (R, A, B, C); + FP_PACK_Q (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} +DIAG_POP_NEEDS_COMMENT; + +weak_alias (__fmal, fmal) diff --git a/REORG.TODO/soft-fp/gedf2.c b/REORG.TODO/soft-fp/gedf2.c new file mode 100644 index 0000000000..404d59265d --- /dev/null +++ b/REORG.TODO/soft-fp/gedf2.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return 0 iff a == b, 1 iff a > b, -2 iff a ? b, -1 iff a < b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +CMPtype +__gedf2 (DFtype a, DFtype b) +{ + FP_DECL_EX; + FP_DECL_D (A); + FP_DECL_D (B); + CMPtype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_D (A, a); + FP_UNPACK_RAW_D (B, b); + FP_CMP_D (r, A, B, -2, 2); + FP_HANDLE_EXCEPTIONS; + + return r; +} + +strong_alias (__gedf2, __gtdf2); diff --git a/REORG.TODO/soft-fp/gesf2.c b/REORG.TODO/soft-fp/gesf2.c new file mode 100644 index 0000000000..1b011f5514 --- /dev/null +++ b/REORG.TODO/soft-fp/gesf2.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return 0 iff a == b, 1 iff a > b, -2 iff a ? b, -1 iff a < b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +CMPtype +__gesf2 (SFtype a, SFtype b) +{ + FP_DECL_EX; + FP_DECL_S (A); + FP_DECL_S (B); + CMPtype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_S (A, a); + FP_UNPACK_RAW_S (B, b); + FP_CMP_S (r, A, B, -2, 2); + FP_HANDLE_EXCEPTIONS; + + return r; +} + +strong_alias (__gesf2, __gtsf2); diff --git a/REORG.TODO/soft-fp/getf2.c b/REORG.TODO/soft-fp/getf2.c new file mode 100644 index 0000000000..0b8fd6c189 --- /dev/null +++ b/REORG.TODO/soft-fp/getf2.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return 0 iff a == b, 1 iff a > b, -2 iff a ? b, -1 iff a < b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +CMPtype +__getf2 (TFtype a, TFtype b) +{ + FP_DECL_EX; + FP_DECL_Q (A); + FP_DECL_Q (B); + CMPtype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_Q (A, a); + FP_UNPACK_RAW_Q (B, b); + FP_CMP_Q (r, A, B, -2, 2); + FP_HANDLE_EXCEPTIONS; + + return r; +} + +strong_alias (__getf2, __gttf2); diff --git a/REORG.TODO/soft-fp/half.h b/REORG.TODO/soft-fp/half.h new file mode 100644 index 0000000000..60fcc0d035 --- /dev/null +++ b/REORG.TODO/soft-fp/half.h @@ -0,0 +1,170 @@ +/* Software floating-point emulation. + Definitions for IEEE Half Precision. + Copyright (C) 1997-2017 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#ifndef SOFT_FP_HALF_H +#define SOFT_FP_HALF_H 1 + +#if _FP_W_TYPE_SIZE < 32 +# error "Here's a nickel kid. Go buy yourself a real computer." +#endif + +#define _FP_FRACTBITS_H (_FP_W_TYPE_SIZE) + +#define _FP_FRACTBITS_DW_H (_FP_W_TYPE_SIZE) + +#define _FP_FRACBITS_H 11 +#define _FP_FRACXBITS_H (_FP_FRACTBITS_H - _FP_FRACBITS_H) +#define _FP_WFRACBITS_H (_FP_WORKBITS + _FP_FRACBITS_H) +#define _FP_WFRACXBITS_H (_FP_FRACTBITS_H - _FP_WFRACBITS_H) +#define _FP_EXPBITS_H 5 +#define _FP_EXPBIAS_H 15 +#define _FP_EXPMAX_H 31 + +#define _FP_QNANBIT_H ((_FP_W_TYPE) 1 << (_FP_FRACBITS_H-2)) +#define _FP_QNANBIT_SH_H ((_FP_W_TYPE) 1 << (_FP_FRACBITS_H-2+_FP_WORKBITS)) +#define _FP_IMPLBIT_H ((_FP_W_TYPE) 1 << (_FP_FRACBITS_H-1)) +#define _FP_IMPLBIT_SH_H ((_FP_W_TYPE) 1 << (_FP_FRACBITS_H-1+_FP_WORKBITS)) +#define _FP_OVERFLOW_H ((_FP_W_TYPE) 1 << (_FP_WFRACBITS_H)) + +#define _FP_WFRACBITS_DW_H (2 * _FP_WFRACBITS_H) +#define _FP_WFRACXBITS_DW_H (_FP_FRACTBITS_DW_H - _FP_WFRACBITS_DW_H) +#define _FP_HIGHBIT_DW_H \ + ((_FP_W_TYPE) 1 << (_FP_WFRACBITS_DW_H - 1) % _FP_W_TYPE_SIZE) + +/* The implementation of _FP_MUL_MEAT_H and _FP_DIV_MEAT_H should be + chosen by the target machine. */ + +typedef float HFtype __attribute__ ((mode (HF))); + +union _FP_UNION_H +{ + HFtype flt; + struct _FP_STRUCT_LAYOUT + { +#if __BYTE_ORDER == __BIG_ENDIAN + unsigned sign : 1; + unsigned exp : _FP_EXPBITS_H; + unsigned frac : _FP_FRACBITS_H - (_FP_IMPLBIT_H != 0); +#else + unsigned frac : _FP_FRACBITS_H - (_FP_IMPLBIT_H != 0); + unsigned exp : _FP_EXPBITS_H; + unsigned sign : 1; +#endif + } bits __attribute__ ((packed)); +}; + +#define FP_DECL_H(X) _FP_DECL (1, X) +#define FP_UNPACK_RAW_H(X, val) _FP_UNPACK_RAW_1 (H, X, (val)) +#define FP_UNPACK_RAW_HP(X, val) _FP_UNPACK_RAW_1_P (H, X, (val)) +#define FP_PACK_RAW_H(val, X) _FP_PACK_RAW_1 (H, (val), X) +#define FP_PACK_RAW_HP(val, X) \ + do \ + { \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_1_P (H, (val), X); \ + } \ + while (0) + +#define FP_UNPACK_H(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_1 (H, X, (val)); \ + _FP_UNPACK_CANONICAL (H, 1, X); \ + } \ + while (0) + +#define FP_UNPACK_HP(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_1_P (H, X, (val)); \ + _FP_UNPACK_CANONICAL (H, 1, X); \ + } \ + while (0) + +#define FP_UNPACK_SEMIRAW_H(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_1 (H, X, (val)); \ + _FP_UNPACK_SEMIRAW (H, 1, X); \ + } \ + while (0) + +#define FP_UNPACK_SEMIRAW_HP(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_1_P (H, X, (val)); \ + _FP_UNPACK_SEMIRAW (H, 1, X); \ + } \ + while (0) + +#define FP_PACK_H(val, X) \ + do \ + { \ + _FP_PACK_CANONICAL (H, 1, X); \ + _FP_PACK_RAW_1 (H, (val), X); \ + } \ + while (0) + +#define FP_PACK_HP(val, X) \ + do \ + { \ + _FP_PACK_CANONICAL (H, 1, X); \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_1_P (H, (val), X); \ + } \ + while (0) + +#define FP_PACK_SEMIRAW_H(val, X) \ + do \ + { \ + _FP_PACK_SEMIRAW (H, 1, X); \ + _FP_PACK_RAW_1 (H, (val), X); \ + } \ + while (0) + +#define FP_PACK_SEMIRAW_HP(val, X) \ + do \ + { \ + _FP_PACK_SEMIRAW (H, 1, X); \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_1_P (H, (val), X); \ + } \ + while (0) + +#define FP_TO_INT_H(r, X, rsz, rsg) _FP_TO_INT (H, 1, (r), X, (rsz), (rsg)) +#define FP_TO_INT_ROUND_H(r, X, rsz, rsg) \ + _FP_TO_INT_ROUND (H, 1, (r), X, (rsz), (rsg)) +#define FP_FROM_INT_H(X, r, rs, rt) _FP_FROM_INT (H, 1, X, (r), (rs), rt) + +/* HFmode arithmetic is not implemented. */ + +#define _FP_FRAC_HIGH_H(X) _FP_FRAC_HIGH_1 (X) +#define _FP_FRAC_HIGH_RAW_H(X) _FP_FRAC_HIGH_1 (X) +#define _FP_FRAC_HIGH_DW_H(X) _FP_FRAC_HIGH_1 (X) + +#endif /* !SOFT_FP_HALF_H */ diff --git a/REORG.TODO/soft-fp/ledf2.c b/REORG.TODO/soft-fp/ledf2.c new file mode 100644 index 0000000000..1ab258d0bf --- /dev/null +++ b/REORG.TODO/soft-fp/ledf2.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return 0 iff a == b, 1 iff a > b, 2 iff a ? b, -1 iff a < b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +CMPtype +__ledf2 (DFtype a, DFtype b) +{ + FP_DECL_EX; + FP_DECL_D (A); + FP_DECL_D (B); + CMPtype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_D (A, a); + FP_UNPACK_RAW_D (B, b); + FP_CMP_D (r, A, B, 2, 2); + FP_HANDLE_EXCEPTIONS; + + return r; +} + +strong_alias (__ledf2, __ltdf2); diff --git a/REORG.TODO/soft-fp/lesf2.c b/REORG.TODO/soft-fp/lesf2.c new file mode 100644 index 0000000000..eced0f44cb --- /dev/null +++ b/REORG.TODO/soft-fp/lesf2.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return 0 iff a == b, 1 iff a > b, 2 iff a ? b, -1 iff a < b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +CMPtype +__lesf2 (SFtype a, SFtype b) +{ + FP_DECL_EX; + FP_DECL_S (A); + FP_DECL_S (B); + CMPtype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_S (A, a); + FP_UNPACK_RAW_S (B, b); + FP_CMP_S (r, A, B, 2, 2); + FP_HANDLE_EXCEPTIONS; + + return r; +} + +strong_alias (__lesf2, __ltsf2); diff --git a/REORG.TODO/soft-fp/letf2.c b/REORG.TODO/soft-fp/letf2.c new file mode 100644 index 0000000000..eb0152894b --- /dev/null +++ b/REORG.TODO/soft-fp/letf2.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return 0 iff a == b, 1 iff a > b, 2 iff a ? b, -1 iff a < b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +CMPtype +__letf2 (TFtype a, TFtype b) +{ + FP_DECL_EX; + FP_DECL_Q (A); + FP_DECL_Q (B); + CMPtype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_Q (A, a); + FP_UNPACK_RAW_Q (B, b); + FP_CMP_Q (r, A, B, 2, 2); + FP_HANDLE_EXCEPTIONS; + + return r; +} + +strong_alias (__letf2, __lttf2); diff --git a/REORG.TODO/soft-fp/muldf3.c b/REORG.TODO/soft-fp/muldf3.c new file mode 100644 index 0000000000..5f5056f3e7 --- /dev/null +++ b/REORG.TODO/soft-fp/muldf3.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return a * b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +DFtype +__muldf3 (DFtype a, DFtype b) +{ + FP_DECL_EX; + FP_DECL_D (A); + FP_DECL_D (B); + FP_DECL_D (R); + DFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_D (A, a); + FP_UNPACK_D (B, b); + FP_MUL_D (R, A, B); + FP_PACK_D (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/mulsf3.c b/REORG.TODO/soft-fp/mulsf3.c new file mode 100644 index 0000000000..6cc675a225 --- /dev/null +++ b/REORG.TODO/soft-fp/mulsf3.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return a * b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +SFtype +__mulsf3 (SFtype a, SFtype b) +{ + FP_DECL_EX; + FP_DECL_S (A); + FP_DECL_S (B); + FP_DECL_S (R); + SFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_S (A, a); + FP_UNPACK_S (B, b); + FP_MUL_S (R, A, B); + FP_PACK_S (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/multf3.c b/REORG.TODO/soft-fp/multf3.c new file mode 100644 index 0000000000..10b63a3741 --- /dev/null +++ b/REORG.TODO/soft-fp/multf3.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return a * b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +TFtype +__multf3 (TFtype a, TFtype b) +{ + FP_DECL_EX; + FP_DECL_Q (A); + FP_DECL_Q (B); + FP_DECL_Q (R); + TFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_Q (A, a); + FP_UNPACK_Q (B, b); + FP_MUL_Q (R, A, B); + FP_PACK_Q (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/negdf2.c b/REORG.TODO/soft-fp/negdf2.c new file mode 100644 index 0000000000..cbfbb942e6 --- /dev/null +++ b/REORG.TODO/soft-fp/negdf2.c @@ -0,0 +1,46 @@ +/* Software floating-point emulation. + Return -a + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +DFtype +__negdf2 (DFtype a) +{ + FP_DECL_D (A); + FP_DECL_D (R); + DFtype r; + + FP_UNPACK_RAW_D (A, a); + FP_NEG_D (R, A); + FP_PACK_RAW_D (r, R); + + return r; +} diff --git a/REORG.TODO/soft-fp/negsf2.c b/REORG.TODO/soft-fp/negsf2.c new file mode 100644 index 0000000000..4090d35e40 --- /dev/null +++ b/REORG.TODO/soft-fp/negsf2.c @@ -0,0 +1,46 @@ +/* Software floating-point emulation. + Return -a + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +SFtype +__negsf2 (SFtype a) +{ + FP_DECL_S (A); + FP_DECL_S (R); + SFtype r; + + FP_UNPACK_RAW_S (A, a); + FP_NEG_S (R, A); + FP_PACK_RAW_S (r, R); + + return r; +} diff --git a/REORG.TODO/soft-fp/negtf2.c b/REORG.TODO/soft-fp/negtf2.c new file mode 100644 index 0000000000..49b775b188 --- /dev/null +++ b/REORG.TODO/soft-fp/negtf2.c @@ -0,0 +1,46 @@ +/* Software floating-point emulation. + Return -a + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +TFtype +__negtf2 (TFtype a) +{ + FP_DECL_Q (A); + FP_DECL_Q (R); + TFtype r; + + FP_UNPACK_RAW_Q (A, a); + FP_NEG_Q (R, A); + FP_PACK_RAW_Q (r, R); + + return r; +} diff --git a/REORG.TODO/soft-fp/op-1.h b/REORG.TODO/soft-fp/op-1.h new file mode 100644 index 0000000000..e1e39664d1 --- /dev/null +++ b/REORG.TODO/soft-fp/op-1.h @@ -0,0 +1,369 @@ +/* Software floating-point emulation. + Basic one-word fraction declaration and manipulation. + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com), + Jakub Jelinek (jj@ultra.linux.cz), + David S. Miller (davem@redhat.com) and + Peter Maydell (pmaydell@chiark.greenend.org.uk). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#ifndef SOFT_FP_OP_1_H +#define SOFT_FP_OP_1_H 1 + +#define _FP_FRAC_DECL_1(X) _FP_W_TYPE X##_f _FP_ZERO_INIT +#define _FP_FRAC_COPY_1(D, S) (D##_f = S##_f) +#define _FP_FRAC_SET_1(X, I) (X##_f = I) +#define _FP_FRAC_HIGH_1(X) (X##_f) +#define _FP_FRAC_LOW_1(X) (X##_f) +#define _FP_FRAC_WORD_1(X, w) (X##_f) + +#define _FP_FRAC_ADDI_1(X, I) (X##_f += I) +#define _FP_FRAC_SLL_1(X, N) \ + do \ + { \ + if (__builtin_constant_p (N) && (N) == 1) \ + X##_f += X##_f; \ + else \ + X##_f <<= (N); \ + } \ + while (0) +#define _FP_FRAC_SRL_1(X, N) (X##_f >>= N) + +/* Right shift with sticky-lsb. */ +#define _FP_FRAC_SRST_1(X, S, N, sz) __FP_FRAC_SRST_1 (X##_f, S, (N), (sz)) +#define _FP_FRAC_SRS_1(X, N, sz) __FP_FRAC_SRS_1 (X##_f, (N), (sz)) + +#define __FP_FRAC_SRST_1(X, S, N, sz) \ + do \ + { \ + S = (__builtin_constant_p (N) && (N) == 1 \ + ? X & 1 \ + : (X << (_FP_W_TYPE_SIZE - (N))) != 0); \ + X = X >> (N); \ + } \ + while (0) + +#define __FP_FRAC_SRS_1(X, N, sz) \ + (X = (X >> (N) | (__builtin_constant_p (N) && (N) == 1 \ + ? X & 1 \ + : (X << (_FP_W_TYPE_SIZE - (N))) != 0))) + +#define _FP_FRAC_ADD_1(R, X, Y) (R##_f = X##_f + Y##_f) +#define _FP_FRAC_SUB_1(R, X, Y) (R##_f = X##_f - Y##_f) +#define _FP_FRAC_DEC_1(X, Y) (X##_f -= Y##_f) +#define _FP_FRAC_CLZ_1(z, X) __FP_CLZ ((z), X##_f) + +/* Predicates. */ +#define _FP_FRAC_NEGP_1(X) ((_FP_WS_TYPE) X##_f < 0) +#define _FP_FRAC_ZEROP_1(X) (X##_f == 0) +#define _FP_FRAC_OVERP_1(fs, X) (X##_f & _FP_OVERFLOW_##fs) +#define _FP_FRAC_CLEAR_OVERP_1(fs, X) (X##_f &= ~_FP_OVERFLOW_##fs) +#define _FP_FRAC_HIGHBIT_DW_1(fs, X) (X##_f & _FP_HIGHBIT_DW_##fs) +#define _FP_FRAC_EQ_1(X, Y) (X##_f == Y##_f) +#define _FP_FRAC_GE_1(X, Y) (X##_f >= Y##_f) +#define _FP_FRAC_GT_1(X, Y) (X##_f > Y##_f) + +#define _FP_ZEROFRAC_1 0 +#define _FP_MINFRAC_1 1 +#define _FP_MAXFRAC_1 (~(_FP_WS_TYPE) 0) + +/* Unpack the raw bits of a native fp value. Do not classify or + normalize the data. */ + +#define _FP_UNPACK_RAW_1(fs, X, val) \ + do \ + { \ + union _FP_UNION_##fs _FP_UNPACK_RAW_1_flo; \ + _FP_UNPACK_RAW_1_flo.flt = (val); \ + \ + X##_f = _FP_UNPACK_RAW_1_flo.bits.frac; \ + X##_e = _FP_UNPACK_RAW_1_flo.bits.exp; \ + X##_s = _FP_UNPACK_RAW_1_flo.bits.sign; \ + } \ + while (0) + +#define _FP_UNPACK_RAW_1_P(fs, X, val) \ + do \ + { \ + union _FP_UNION_##fs *_FP_UNPACK_RAW_1_P_flo \ + = (union _FP_UNION_##fs *) (val); \ + \ + X##_f = _FP_UNPACK_RAW_1_P_flo->bits.frac; \ + X##_e = _FP_UNPACK_RAW_1_P_flo->bits.exp; \ + X##_s = _FP_UNPACK_RAW_1_P_flo->bits.sign; \ + } \ + while (0) + +/* Repack the raw bits of a native fp value. */ + +#define _FP_PACK_RAW_1(fs, val, X) \ + do \ + { \ + union _FP_UNION_##fs _FP_PACK_RAW_1_flo; \ + \ + _FP_PACK_RAW_1_flo.bits.frac = X##_f; \ + _FP_PACK_RAW_1_flo.bits.exp = X##_e; \ + _FP_PACK_RAW_1_flo.bits.sign = X##_s; \ + \ + (val) = _FP_PACK_RAW_1_flo.flt; \ + } \ + while (0) + +#define _FP_PACK_RAW_1_P(fs, val, X) \ + do \ + { \ + union _FP_UNION_##fs *_FP_PACK_RAW_1_P_flo \ + = (union _FP_UNION_##fs *) (val); \ + \ + _FP_PACK_RAW_1_P_flo->bits.frac = X##_f; \ + _FP_PACK_RAW_1_P_flo->bits.exp = X##_e; \ + _FP_PACK_RAW_1_P_flo->bits.sign = X##_s; \ + } \ + while (0) + + +/* Multiplication algorithms: */ + +/* Basic. Assuming the host word size is >= 2*FRACBITS, we can do the + multiplication immediately. */ + +#define _FP_MUL_MEAT_DW_1_imm(wfracbits, R, X, Y) \ + do \ + { \ + R##_f = X##_f * Y##_f; \ + } \ + while (0) + +#define _FP_MUL_MEAT_1_imm(wfracbits, R, X, Y) \ + do \ + { \ + _FP_MUL_MEAT_DW_1_imm ((wfracbits), R, X, Y); \ + /* Normalize since we know where the msb of the multiplicands \ + were (bit B), we know that the msb of the of the product is \ + at either 2B or 2B-1. */ \ + _FP_FRAC_SRS_1 (R, (wfracbits)-1, 2*(wfracbits)); \ + } \ + while (0) + +/* Given a 1W * 1W => 2W primitive, do the extended multiplication. */ + +#define _FP_MUL_MEAT_DW_1_wide(wfracbits, R, X, Y, doit) \ + do \ + { \ + doit (R##_f1, R##_f0, X##_f, Y##_f); \ + } \ + while (0) + +#define _FP_MUL_MEAT_1_wide(wfracbits, R, X, Y, doit) \ + do \ + { \ + _FP_FRAC_DECL_2 (_FP_MUL_MEAT_1_wide_Z); \ + _FP_MUL_MEAT_DW_1_wide ((wfracbits), _FP_MUL_MEAT_1_wide_Z, \ + X, Y, doit); \ + /* Normalize since we know where the msb of the multiplicands \ + were (bit B), we know that the msb of the of the product is \ + at either 2B or 2B-1. */ \ + _FP_FRAC_SRS_2 (_FP_MUL_MEAT_1_wide_Z, (wfracbits)-1, \ + 2*(wfracbits)); \ + R##_f = _FP_MUL_MEAT_1_wide_Z_f0; \ + } \ + while (0) + +/* Finally, a simple widening multiply algorithm. What fun! */ + +#define _FP_MUL_MEAT_DW_1_hard(wfracbits, R, X, Y) \ + do \ + { \ + _FP_W_TYPE _FP_MUL_MEAT_DW_1_hard_xh, _FP_MUL_MEAT_DW_1_hard_xl; \ + _FP_W_TYPE _FP_MUL_MEAT_DW_1_hard_yh, _FP_MUL_MEAT_DW_1_hard_yl; \ + _FP_FRAC_DECL_2 (_FP_MUL_MEAT_DW_1_hard_a); \ + \ + /* Split the words in half. */ \ + _FP_MUL_MEAT_DW_1_hard_xh = X##_f >> (_FP_W_TYPE_SIZE/2); \ + _FP_MUL_MEAT_DW_1_hard_xl \ + = X##_f & (((_FP_W_TYPE) 1 << (_FP_W_TYPE_SIZE/2)) - 1); \ + _FP_MUL_MEAT_DW_1_hard_yh = Y##_f >> (_FP_W_TYPE_SIZE/2); \ + _FP_MUL_MEAT_DW_1_hard_yl \ + = Y##_f & (((_FP_W_TYPE) 1 << (_FP_W_TYPE_SIZE/2)) - 1); \ + \ + /* Multiply the pieces. */ \ + R##_f0 = _FP_MUL_MEAT_DW_1_hard_xl * _FP_MUL_MEAT_DW_1_hard_yl; \ + _FP_MUL_MEAT_DW_1_hard_a_f0 \ + = _FP_MUL_MEAT_DW_1_hard_xh * _FP_MUL_MEAT_DW_1_hard_yl; \ + _FP_MUL_MEAT_DW_1_hard_a_f1 \ + = _FP_MUL_MEAT_DW_1_hard_xl * _FP_MUL_MEAT_DW_1_hard_yh; \ + R##_f1 = _FP_MUL_MEAT_DW_1_hard_xh * _FP_MUL_MEAT_DW_1_hard_yh; \ + \ + /* Reassemble into two full words. */ \ + if ((_FP_MUL_MEAT_DW_1_hard_a_f0 += _FP_MUL_MEAT_DW_1_hard_a_f1) \ + < _FP_MUL_MEAT_DW_1_hard_a_f1) \ + R##_f1 += (_FP_W_TYPE) 1 << (_FP_W_TYPE_SIZE/2); \ + _FP_MUL_MEAT_DW_1_hard_a_f1 \ + = _FP_MUL_MEAT_DW_1_hard_a_f0 >> (_FP_W_TYPE_SIZE/2); \ + _FP_MUL_MEAT_DW_1_hard_a_f0 \ + = _FP_MUL_MEAT_DW_1_hard_a_f0 << (_FP_W_TYPE_SIZE/2); \ + _FP_FRAC_ADD_2 (R, R, _FP_MUL_MEAT_DW_1_hard_a); \ + } \ + while (0) + +#define _FP_MUL_MEAT_1_hard(wfracbits, R, X, Y) \ + do \ + { \ + _FP_FRAC_DECL_2 (_FP_MUL_MEAT_1_hard_z); \ + _FP_MUL_MEAT_DW_1_hard ((wfracbits), \ + _FP_MUL_MEAT_1_hard_z, X, Y); \ + \ + /* Normalize. */ \ + _FP_FRAC_SRS_2 (_FP_MUL_MEAT_1_hard_z, \ + (wfracbits) - 1, 2*(wfracbits)); \ + R##_f = _FP_MUL_MEAT_1_hard_z_f0; \ + } \ + while (0) + + +/* Division algorithms: */ + +/* Basic. Assuming the host word size is >= 2*FRACBITS, we can do the + division immediately. Give this macro either _FP_DIV_HELP_imm for + C primitives or _FP_DIV_HELP_ldiv for the ISO function. Which you + choose will depend on what the compiler does with divrem4. */ + +#define _FP_DIV_MEAT_1_imm(fs, R, X, Y, doit) \ + do \ + { \ + _FP_W_TYPE _FP_DIV_MEAT_1_imm_q, _FP_DIV_MEAT_1_imm_r; \ + X##_f <<= (X##_f < Y##_f \ + ? R##_e--, _FP_WFRACBITS_##fs \ + : _FP_WFRACBITS_##fs - 1); \ + doit (_FP_DIV_MEAT_1_imm_q, _FP_DIV_MEAT_1_imm_r, X##_f, Y##_f); \ + R##_f = _FP_DIV_MEAT_1_imm_q | (_FP_DIV_MEAT_1_imm_r != 0); \ + } \ + while (0) + +/* GCC's longlong.h defines a 2W / 1W => (1W,1W) primitive udiv_qrnnd + that may be useful in this situation. This first is for a primitive + that requires normalization, the second for one that does not. Look + for UDIV_NEEDS_NORMALIZATION to tell which your machine needs. */ + +#define _FP_DIV_MEAT_1_udiv_norm(fs, R, X, Y) \ + do \ + { \ + _FP_W_TYPE _FP_DIV_MEAT_1_udiv_norm_nh; \ + _FP_W_TYPE _FP_DIV_MEAT_1_udiv_norm_nl; \ + _FP_W_TYPE _FP_DIV_MEAT_1_udiv_norm_q; \ + _FP_W_TYPE _FP_DIV_MEAT_1_udiv_norm_r; \ + _FP_W_TYPE _FP_DIV_MEAT_1_udiv_norm_y; \ + \ + /* Normalize Y -- i.e. make the most significant bit set. */ \ + _FP_DIV_MEAT_1_udiv_norm_y = Y##_f << _FP_WFRACXBITS_##fs; \ + \ + /* Shift X op correspondingly high, that is, up one full word. */ \ + if (X##_f < Y##_f) \ + { \ + R##_e--; \ + _FP_DIV_MEAT_1_udiv_norm_nl = 0; \ + _FP_DIV_MEAT_1_udiv_norm_nh = X##_f; \ + } \ + else \ + { \ + _FP_DIV_MEAT_1_udiv_norm_nl = X##_f << (_FP_W_TYPE_SIZE - 1); \ + _FP_DIV_MEAT_1_udiv_norm_nh = X##_f >> 1; \ + } \ + \ + udiv_qrnnd (_FP_DIV_MEAT_1_udiv_norm_q, \ + _FP_DIV_MEAT_1_udiv_norm_r, \ + _FP_DIV_MEAT_1_udiv_norm_nh, \ + _FP_DIV_MEAT_1_udiv_norm_nl, \ + _FP_DIV_MEAT_1_udiv_norm_y); \ + R##_f = (_FP_DIV_MEAT_1_udiv_norm_q \ + | (_FP_DIV_MEAT_1_udiv_norm_r != 0)); \ + } \ + while (0) + +#define _FP_DIV_MEAT_1_udiv(fs, R, X, Y) \ + do \ + { \ + _FP_W_TYPE _FP_DIV_MEAT_1_udiv_nh, _FP_DIV_MEAT_1_udiv_nl; \ + _FP_W_TYPE _FP_DIV_MEAT_1_udiv_q, _FP_DIV_MEAT_1_udiv_r; \ + if (X##_f < Y##_f) \ + { \ + R##_e--; \ + _FP_DIV_MEAT_1_udiv_nl = X##_f << _FP_WFRACBITS_##fs; \ + _FP_DIV_MEAT_1_udiv_nh = X##_f >> _FP_WFRACXBITS_##fs; \ + } \ + else \ + { \ + _FP_DIV_MEAT_1_udiv_nl = X##_f << (_FP_WFRACBITS_##fs - 1); \ + _FP_DIV_MEAT_1_udiv_nh = X##_f >> (_FP_WFRACXBITS_##fs + 1); \ + } \ + udiv_qrnnd (_FP_DIV_MEAT_1_udiv_q, _FP_DIV_MEAT_1_udiv_r, \ + _FP_DIV_MEAT_1_udiv_nh, _FP_DIV_MEAT_1_udiv_nl, \ + Y##_f); \ + R##_f = _FP_DIV_MEAT_1_udiv_q | (_FP_DIV_MEAT_1_udiv_r != 0); \ + } \ + while (0) + + +/* Square root algorithms: + We have just one right now, maybe Newton approximation + should be added for those machines where division is fast. */ + +#define _FP_SQRT_MEAT_1(R, S, T, X, q) \ + do \ + { \ + while ((q) != _FP_WORK_ROUND) \ + { \ + T##_f = S##_f + (q); \ + if (T##_f <= X##_f) \ + { \ + S##_f = T##_f + (q); \ + X##_f -= T##_f; \ + R##_f += (q); \ + } \ + _FP_FRAC_SLL_1 (X, 1); \ + (q) >>= 1; \ + } \ + if (X##_f) \ + { \ + if (S##_f < X##_f) \ + R##_f |= _FP_WORK_ROUND; \ + R##_f |= _FP_WORK_STICKY; \ + } \ + } \ + while (0) + +/* Assembly/disassembly for converting to/from integral types. + No shifting or overflow handled here. */ + +#define _FP_FRAC_ASSEMBLE_1(r, X, rsize) ((r) = X##_f) +#define _FP_FRAC_DISASSEMBLE_1(X, r, rsize) (X##_f = (r)) + + +/* Convert FP values between word sizes. */ + +#define _FP_FRAC_COPY_1_1(D, S) (D##_f = S##_f) + +#endif /* !SOFT_FP_OP_1_H */ diff --git a/REORG.TODO/soft-fp/op-2.h b/REORG.TODO/soft-fp/op-2.h new file mode 100644 index 0000000000..c010afa3e3 --- /dev/null +++ b/REORG.TODO/soft-fp/op-2.h @@ -0,0 +1,705 @@ +/* Software floating-point emulation. + Basic two-word fraction declaration and manipulation. + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com), + Jakub Jelinek (jj@ultra.linux.cz), + David S. Miller (davem@redhat.com) and + Peter Maydell (pmaydell@chiark.greenend.org.uk). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#ifndef SOFT_FP_OP_2_H +#define SOFT_FP_OP_2_H 1 + +#define _FP_FRAC_DECL_2(X) \ + _FP_W_TYPE X##_f0 _FP_ZERO_INIT, X##_f1 _FP_ZERO_INIT +#define _FP_FRAC_COPY_2(D, S) (D##_f0 = S##_f0, D##_f1 = S##_f1) +#define _FP_FRAC_SET_2(X, I) __FP_FRAC_SET_2 (X, I) +#define _FP_FRAC_HIGH_2(X) (X##_f1) +#define _FP_FRAC_LOW_2(X) (X##_f0) +#define _FP_FRAC_WORD_2(X, w) (X##_f##w) + +#define _FP_FRAC_SLL_2(X, N) \ + (void) (((N) < _FP_W_TYPE_SIZE) \ + ? ({ \ + if (__builtin_constant_p (N) && (N) == 1) \ + { \ + X##_f1 = X##_f1 + X##_f1 + (((_FP_WS_TYPE) (X##_f0)) < 0); \ + X##_f0 += X##_f0; \ + } \ + else \ + { \ + X##_f1 = X##_f1 << (N) | X##_f0 >> (_FP_W_TYPE_SIZE - (N)); \ + X##_f0 <<= (N); \ + } \ + 0; \ + }) \ + : ({ \ + X##_f1 = X##_f0 << ((N) - _FP_W_TYPE_SIZE); \ + X##_f0 = 0; \ + })) + + +#define _FP_FRAC_SRL_2(X, N) \ + (void) (((N) < _FP_W_TYPE_SIZE) \ + ? ({ \ + X##_f0 = X##_f0 >> (N) | X##_f1 << (_FP_W_TYPE_SIZE - (N)); \ + X##_f1 >>= (N); \ + }) \ + : ({ \ + X##_f0 = X##_f1 >> ((N) - _FP_W_TYPE_SIZE); \ + X##_f1 = 0; \ + })) + +/* Right shift with sticky-lsb. */ +#define _FP_FRAC_SRST_2(X, S, N, sz) \ + (void) (((N) < _FP_W_TYPE_SIZE) \ + ? ({ \ + S = (__builtin_constant_p (N) && (N) == 1 \ + ? X##_f0 & 1 \ + : (X##_f0 << (_FP_W_TYPE_SIZE - (N))) != 0); \ + X##_f0 = (X##_f1 << (_FP_W_TYPE_SIZE - (N)) | X##_f0 >> (N)); \ + X##_f1 >>= (N); \ + }) \ + : ({ \ + S = ((((N) == _FP_W_TYPE_SIZE \ + ? 0 \ + : (X##_f1 << (2*_FP_W_TYPE_SIZE - (N)))) \ + | X##_f0) != 0); \ + X##_f0 = (X##_f1 >> ((N) - _FP_W_TYPE_SIZE)); \ + X##_f1 = 0; \ + })) + +#define _FP_FRAC_SRS_2(X, N, sz) \ + (void) (((N) < _FP_W_TYPE_SIZE) \ + ? ({ \ + X##_f0 = (X##_f1 << (_FP_W_TYPE_SIZE - (N)) | X##_f0 >> (N) \ + | (__builtin_constant_p (N) && (N) == 1 \ + ? X##_f0 & 1 \ + : (X##_f0 << (_FP_W_TYPE_SIZE - (N))) != 0)); \ + X##_f1 >>= (N); \ + }) \ + : ({ \ + X##_f0 = (X##_f1 >> ((N) - _FP_W_TYPE_SIZE) \ + | ((((N) == _FP_W_TYPE_SIZE \ + ? 0 \ + : (X##_f1 << (2*_FP_W_TYPE_SIZE - (N)))) \ + | X##_f0) != 0)); \ + X##_f1 = 0; \ + })) + +#define _FP_FRAC_ADDI_2(X, I) \ + __FP_FRAC_ADDI_2 (X##_f1, X##_f0, I) + +#define _FP_FRAC_ADD_2(R, X, Y) \ + __FP_FRAC_ADD_2 (R##_f1, R##_f0, X##_f1, X##_f0, Y##_f1, Y##_f0) + +#define _FP_FRAC_SUB_2(R, X, Y) \ + __FP_FRAC_SUB_2 (R##_f1, R##_f0, X##_f1, X##_f0, Y##_f1, Y##_f0) + +#define _FP_FRAC_DEC_2(X, Y) \ + __FP_FRAC_DEC_2 (X##_f1, X##_f0, Y##_f1, Y##_f0) + +#define _FP_FRAC_CLZ_2(R, X) \ + do \ + { \ + if (X##_f1) \ + __FP_CLZ ((R), X##_f1); \ + else \ + { \ + __FP_CLZ ((R), X##_f0); \ + (R) += _FP_W_TYPE_SIZE; \ + } \ + } \ + while (0) + +/* Predicates. */ +#define _FP_FRAC_NEGP_2(X) ((_FP_WS_TYPE) X##_f1 < 0) +#define _FP_FRAC_ZEROP_2(X) ((X##_f1 | X##_f0) == 0) +#define _FP_FRAC_OVERP_2(fs, X) (_FP_FRAC_HIGH_##fs (X) & _FP_OVERFLOW_##fs) +#define _FP_FRAC_CLEAR_OVERP_2(fs, X) (_FP_FRAC_HIGH_##fs (X) &= ~_FP_OVERFLOW_##fs) +#define _FP_FRAC_HIGHBIT_DW_2(fs, X) \ + (_FP_FRAC_HIGH_DW_##fs (X) & _FP_HIGHBIT_DW_##fs) +#define _FP_FRAC_EQ_2(X, Y) (X##_f1 == Y##_f1 && X##_f0 == Y##_f0) +#define _FP_FRAC_GT_2(X, Y) \ + (X##_f1 > Y##_f1 || (X##_f1 == Y##_f1 && X##_f0 > Y##_f0)) +#define _FP_FRAC_GE_2(X, Y) \ + (X##_f1 > Y##_f1 || (X##_f1 == Y##_f1 && X##_f0 >= Y##_f0)) + +#define _FP_ZEROFRAC_2 0, 0 +#define _FP_MINFRAC_2 0, 1 +#define _FP_MAXFRAC_2 (~(_FP_WS_TYPE) 0), (~(_FP_WS_TYPE) 0) + +/* Internals. */ + +#define __FP_FRAC_SET_2(X, I1, I0) (X##_f0 = I0, X##_f1 = I1) + +#define __FP_CLZ_2(R, xh, xl) \ + do \ + { \ + if (xh) \ + __FP_CLZ ((R), xh); \ + else \ + { \ + __FP_CLZ ((R), xl); \ + (R) += _FP_W_TYPE_SIZE; \ + } \ + } \ + while (0) + +#if 0 + +# ifndef __FP_FRAC_ADDI_2 +# define __FP_FRAC_ADDI_2(xh, xl, i) \ + (xh += ((xl += i) < i)) +# endif +# ifndef __FP_FRAC_ADD_2 +# define __FP_FRAC_ADD_2(rh, rl, xh, xl, yh, yl) \ + (rh = xh + yh + ((rl = xl + yl) < xl)) +# endif +# ifndef __FP_FRAC_SUB_2 +# define __FP_FRAC_SUB_2(rh, rl, xh, xl, yh, yl) \ + (rh = xh - yh - ((rl = xl - yl) > xl)) +# endif +# ifndef __FP_FRAC_DEC_2 +# define __FP_FRAC_DEC_2(xh, xl, yh, yl) \ + do \ + { \ + UWtype __FP_FRAC_DEC_2_t = xl; \ + xh -= yh + ((xl -= yl) > __FP_FRAC_DEC_2_t); \ + } \ + while (0) +# endif + +#else + +# undef __FP_FRAC_ADDI_2 +# define __FP_FRAC_ADDI_2(xh, xl, i) add_ssaaaa (xh, xl, xh, xl, 0, i) +# undef __FP_FRAC_ADD_2 +# define __FP_FRAC_ADD_2 add_ssaaaa +# undef __FP_FRAC_SUB_2 +# define __FP_FRAC_SUB_2 sub_ddmmss +# undef __FP_FRAC_DEC_2 +# define __FP_FRAC_DEC_2(xh, xl, yh, yl) \ + sub_ddmmss (xh, xl, xh, xl, yh, yl) + +#endif + +/* Unpack the raw bits of a native fp value. Do not classify or + normalize the data. */ + +#define _FP_UNPACK_RAW_2(fs, X, val) \ + do \ + { \ + union _FP_UNION_##fs _FP_UNPACK_RAW_2_flo; \ + _FP_UNPACK_RAW_2_flo.flt = (val); \ + \ + X##_f0 = _FP_UNPACK_RAW_2_flo.bits.frac0; \ + X##_f1 = _FP_UNPACK_RAW_2_flo.bits.frac1; \ + X##_e = _FP_UNPACK_RAW_2_flo.bits.exp; \ + X##_s = _FP_UNPACK_RAW_2_flo.bits.sign; \ + } \ + while (0) + +#define _FP_UNPACK_RAW_2_P(fs, X, val) \ + do \ + { \ + union _FP_UNION_##fs *_FP_UNPACK_RAW_2_P_flo \ + = (union _FP_UNION_##fs *) (val); \ + \ + X##_f0 = _FP_UNPACK_RAW_2_P_flo->bits.frac0; \ + X##_f1 = _FP_UNPACK_RAW_2_P_flo->bits.frac1; \ + X##_e = _FP_UNPACK_RAW_2_P_flo->bits.exp; \ + X##_s = _FP_UNPACK_RAW_2_P_flo->bits.sign; \ + } \ + while (0) + + +/* Repack the raw bits of a native fp value. */ + +#define _FP_PACK_RAW_2(fs, val, X) \ + do \ + { \ + union _FP_UNION_##fs _FP_PACK_RAW_2_flo; \ + \ + _FP_PACK_RAW_2_flo.bits.frac0 = X##_f0; \ + _FP_PACK_RAW_2_flo.bits.frac1 = X##_f1; \ + _FP_PACK_RAW_2_flo.bits.exp = X##_e; \ + _FP_PACK_RAW_2_flo.bits.sign = X##_s; \ + \ + (val) = _FP_PACK_RAW_2_flo.flt; \ + } \ + while (0) + +#define _FP_PACK_RAW_2_P(fs, val, X) \ + do \ + { \ + union _FP_UNION_##fs *_FP_PACK_RAW_2_P_flo \ + = (union _FP_UNION_##fs *) (val); \ + \ + _FP_PACK_RAW_2_P_flo->bits.frac0 = X##_f0; \ + _FP_PACK_RAW_2_P_flo->bits.frac1 = X##_f1; \ + _FP_PACK_RAW_2_P_flo->bits.exp = X##_e; \ + _FP_PACK_RAW_2_P_flo->bits.sign = X##_s; \ + } \ + while (0) + + +/* Multiplication algorithms: */ + +/* Given a 1W * 1W => 2W primitive, do the extended multiplication. */ + +#define _FP_MUL_MEAT_DW_2_wide(wfracbits, R, X, Y, doit) \ + do \ + { \ + _FP_FRAC_DECL_2 (_FP_MUL_MEAT_DW_2_wide_b); \ + _FP_FRAC_DECL_2 (_FP_MUL_MEAT_DW_2_wide_c); \ + \ + doit (_FP_FRAC_WORD_4 (R, 1), _FP_FRAC_WORD_4 (R, 0), \ + X##_f0, Y##_f0); \ + doit (_FP_MUL_MEAT_DW_2_wide_b_f1, _FP_MUL_MEAT_DW_2_wide_b_f0, \ + X##_f0, Y##_f1); \ + doit (_FP_MUL_MEAT_DW_2_wide_c_f1, _FP_MUL_MEAT_DW_2_wide_c_f0, \ + X##_f1, Y##_f0); \ + doit (_FP_FRAC_WORD_4 (R, 3), _FP_FRAC_WORD_4 (R, 2), \ + X##_f1, Y##_f1); \ + \ + __FP_FRAC_ADD_3 (_FP_FRAC_WORD_4 (R, 3), _FP_FRAC_WORD_4 (R, 2), \ + _FP_FRAC_WORD_4 (R, 1), 0, \ + _FP_MUL_MEAT_DW_2_wide_b_f1, \ + _FP_MUL_MEAT_DW_2_wide_b_f0, \ + _FP_FRAC_WORD_4 (R, 3), _FP_FRAC_WORD_4 (R, 2), \ + _FP_FRAC_WORD_4 (R, 1)); \ + __FP_FRAC_ADD_3 (_FP_FRAC_WORD_4 (R, 3), _FP_FRAC_WORD_4 (R, 2), \ + _FP_FRAC_WORD_4 (R, 1), 0, \ + _FP_MUL_MEAT_DW_2_wide_c_f1, \ + _FP_MUL_MEAT_DW_2_wide_c_f0, \ + _FP_FRAC_WORD_4 (R, 3), _FP_FRAC_WORD_4 (R, 2), \ + _FP_FRAC_WORD_4 (R, 1)); \ + } \ + while (0) + +#define _FP_MUL_MEAT_2_wide(wfracbits, R, X, Y, doit) \ + do \ + { \ + _FP_FRAC_DECL_4 (_FP_MUL_MEAT_2_wide_z); \ + \ + _FP_MUL_MEAT_DW_2_wide ((wfracbits), _FP_MUL_MEAT_2_wide_z, \ + X, Y, doit); \ + \ + /* Normalize since we know where the msb of the multiplicands \ + were (bit B), we know that the msb of the of the product is \ + at either 2B or 2B-1. */ \ + _FP_FRAC_SRS_4 (_FP_MUL_MEAT_2_wide_z, (wfracbits)-1, \ + 2*(wfracbits)); \ + R##_f0 = _FP_FRAC_WORD_4 (_FP_MUL_MEAT_2_wide_z, 0); \ + R##_f1 = _FP_FRAC_WORD_4 (_FP_MUL_MEAT_2_wide_z, 1); \ + } \ + while (0) + +/* Given a 1W * 1W => 2W primitive, do the extended multiplication. + Do only 3 multiplications instead of four. This one is for machines + where multiplication is much more expensive than subtraction. */ + +#define _FP_MUL_MEAT_DW_2_wide_3mul(wfracbits, R, X, Y, doit) \ + do \ + { \ + _FP_FRAC_DECL_2 (_FP_MUL_MEAT_DW_2_wide_3mul_b); \ + _FP_FRAC_DECL_2 (_FP_MUL_MEAT_DW_2_wide_3mul_c); \ + _FP_W_TYPE _FP_MUL_MEAT_DW_2_wide_3mul_d; \ + int _FP_MUL_MEAT_DW_2_wide_3mul_c1; \ + int _FP_MUL_MEAT_DW_2_wide_3mul_c2; \ + \ + _FP_MUL_MEAT_DW_2_wide_3mul_b_f0 = X##_f0 + X##_f1; \ + _FP_MUL_MEAT_DW_2_wide_3mul_c1 \ + = _FP_MUL_MEAT_DW_2_wide_3mul_b_f0 < X##_f0; \ + _FP_MUL_MEAT_DW_2_wide_3mul_b_f1 = Y##_f0 + Y##_f1; \ + _FP_MUL_MEAT_DW_2_wide_3mul_c2 \ + = _FP_MUL_MEAT_DW_2_wide_3mul_b_f1 < Y##_f0; \ + doit (_FP_MUL_MEAT_DW_2_wide_3mul_d, _FP_FRAC_WORD_4 (R, 0), \ + X##_f0, Y##_f0); \ + doit (_FP_FRAC_WORD_4 (R, 2), _FP_FRAC_WORD_4 (R, 1), \ + _FP_MUL_MEAT_DW_2_wide_3mul_b_f0, \ + _FP_MUL_MEAT_DW_2_wide_3mul_b_f1); \ + doit (_FP_MUL_MEAT_DW_2_wide_3mul_c_f1, \ + _FP_MUL_MEAT_DW_2_wide_3mul_c_f0, X##_f1, Y##_f1); \ + \ + _FP_MUL_MEAT_DW_2_wide_3mul_b_f0 \ + &= -_FP_MUL_MEAT_DW_2_wide_3mul_c2; \ + _FP_MUL_MEAT_DW_2_wide_3mul_b_f1 \ + &= -_FP_MUL_MEAT_DW_2_wide_3mul_c1; \ + __FP_FRAC_ADD_3 (_FP_FRAC_WORD_4 (R, 3), _FP_FRAC_WORD_4 (R, 2), \ + _FP_FRAC_WORD_4 (R, 1), \ + (_FP_MUL_MEAT_DW_2_wide_3mul_c1 \ + & _FP_MUL_MEAT_DW_2_wide_3mul_c2), 0, \ + _FP_MUL_MEAT_DW_2_wide_3mul_d, \ + 0, _FP_FRAC_WORD_4 (R, 2), _FP_FRAC_WORD_4 (R, 1)); \ + __FP_FRAC_ADDI_2 (_FP_FRAC_WORD_4 (R, 3), _FP_FRAC_WORD_4 (R, 2), \ + _FP_MUL_MEAT_DW_2_wide_3mul_b_f0); \ + __FP_FRAC_ADDI_2 (_FP_FRAC_WORD_4 (R, 3), _FP_FRAC_WORD_4 (R, 2), \ + _FP_MUL_MEAT_DW_2_wide_3mul_b_f1); \ + __FP_FRAC_DEC_3 (_FP_FRAC_WORD_4 (R, 3), _FP_FRAC_WORD_4 (R, 2), \ + _FP_FRAC_WORD_4 (R, 1), \ + 0, _FP_MUL_MEAT_DW_2_wide_3mul_d, \ + _FP_FRAC_WORD_4 (R, 0)); \ + __FP_FRAC_DEC_3 (_FP_FRAC_WORD_4 (R, 3), _FP_FRAC_WORD_4 (R, 2), \ + _FP_FRAC_WORD_4 (R, 1), 0, \ + _FP_MUL_MEAT_DW_2_wide_3mul_c_f1, \ + _FP_MUL_MEAT_DW_2_wide_3mul_c_f0); \ + __FP_FRAC_ADD_2 (_FP_FRAC_WORD_4 (R, 3), _FP_FRAC_WORD_4 (R, 2), \ + _FP_MUL_MEAT_DW_2_wide_3mul_c_f1, \ + _FP_MUL_MEAT_DW_2_wide_3mul_c_f0, \ + _FP_FRAC_WORD_4 (R, 3), _FP_FRAC_WORD_4 (R, 2)); \ + } \ + while (0) + +#define _FP_MUL_MEAT_2_wide_3mul(wfracbits, R, X, Y, doit) \ + do \ + { \ + _FP_FRAC_DECL_4 (_FP_MUL_MEAT_2_wide_3mul_z); \ + \ + _FP_MUL_MEAT_DW_2_wide_3mul ((wfracbits), \ + _FP_MUL_MEAT_2_wide_3mul_z, \ + X, Y, doit); \ + \ + /* Normalize since we know where the msb of the multiplicands \ + were (bit B), we know that the msb of the of the product is \ + at either 2B or 2B-1. */ \ + _FP_FRAC_SRS_4 (_FP_MUL_MEAT_2_wide_3mul_z, \ + (wfracbits)-1, 2*(wfracbits)); \ + R##_f0 = _FP_FRAC_WORD_4 (_FP_MUL_MEAT_2_wide_3mul_z, 0); \ + R##_f1 = _FP_FRAC_WORD_4 (_FP_MUL_MEAT_2_wide_3mul_z, 1); \ + } \ + while (0) + +#define _FP_MUL_MEAT_DW_2_gmp(wfracbits, R, X, Y) \ + do \ + { \ + _FP_W_TYPE _FP_MUL_MEAT_DW_2_gmp_x[2]; \ + _FP_W_TYPE _FP_MUL_MEAT_DW_2_gmp_y[2]; \ + _FP_MUL_MEAT_DW_2_gmp_x[0] = X##_f0; \ + _FP_MUL_MEAT_DW_2_gmp_x[1] = X##_f1; \ + _FP_MUL_MEAT_DW_2_gmp_y[0] = Y##_f0; \ + _FP_MUL_MEAT_DW_2_gmp_y[1] = Y##_f1; \ + \ + mpn_mul_n (R##_f, _FP_MUL_MEAT_DW_2_gmp_x, \ + _FP_MUL_MEAT_DW_2_gmp_y, 2); \ + } \ + while (0) + +#define _FP_MUL_MEAT_2_gmp(wfracbits, R, X, Y) \ + do \ + { \ + _FP_FRAC_DECL_4 (_FP_MUL_MEAT_2_gmp_z); \ + \ + _FP_MUL_MEAT_DW_2_gmp ((wfracbits), _FP_MUL_MEAT_2_gmp_z, X, Y); \ + \ + /* Normalize since we know where the msb of the multiplicands \ + were (bit B), we know that the msb of the of the product is \ + at either 2B or 2B-1. */ \ + _FP_FRAC_SRS_4 (_FP_MUL_MEAT_2_gmp_z, (wfracbits)-1, \ + 2*(wfracbits)); \ + R##_f0 = _FP_MUL_MEAT_2_gmp_z_f[0]; \ + R##_f1 = _FP_MUL_MEAT_2_gmp_z_f[1]; \ + } \ + while (0) + +/* Do at most 120x120=240 bits multiplication using double floating + point multiplication. This is useful if floating point + multiplication has much bigger throughput than integer multiply. + It is supposed to work for _FP_W_TYPE_SIZE 64 and wfracbits + between 106 and 120 only. + Caller guarantees that X and Y has (1LLL << (wfracbits - 1)) set. + SETFETZ is a macro which will disable all FPU exceptions and set rounding + towards zero, RESETFE should optionally reset it back. */ + +#define _FP_MUL_MEAT_2_120_240_double(wfracbits, R, X, Y, setfetz, resetfe) \ + do \ + { \ + static const double _const[] = \ + { \ + /* 2^-24 */ 5.9604644775390625e-08, \ + /* 2^-48 */ 3.5527136788005009e-15, \ + /* 2^-72 */ 2.1175823681357508e-22, \ + /* 2^-96 */ 1.2621774483536189e-29, \ + /* 2^28 */ 2.68435456e+08, \ + /* 2^4 */ 1.600000e+01, \ + /* 2^-20 */ 9.5367431640625e-07, \ + /* 2^-44 */ 5.6843418860808015e-14, \ + /* 2^-68 */ 3.3881317890172014e-21, \ + /* 2^-92 */ 2.0194839173657902e-28, \ + /* 2^-116 */ 1.2037062152420224e-35 \ + }; \ + double _a240, _b240, _c240, _d240, _e240, _f240, \ + _g240, _h240, _i240, _j240, _k240; \ + union { double d; UDItype i; } _l240, _m240, _n240, _o240, \ + _p240, _q240, _r240, _s240; \ + UDItype _t240, _u240, _v240, _w240, _x240, _y240 = 0; \ + \ + _FP_STATIC_ASSERT ((wfracbits) >= 106 && (wfracbits) <= 120, \ + "wfracbits out of range"); \ + \ + setfetz; \ + \ + _e240 = (double) (long) (X##_f0 & 0xffffff); \ + _j240 = (double) (long) (Y##_f0 & 0xffffff); \ + _d240 = (double) (long) ((X##_f0 >> 24) & 0xffffff); \ + _i240 = (double) (long) ((Y##_f0 >> 24) & 0xffffff); \ + _c240 = (double) (long) (((X##_f1 << 16) & 0xffffff) | (X##_f0 >> 48)); \ + _h240 = (double) (long) (((Y##_f1 << 16) & 0xffffff) | (Y##_f0 >> 48)); \ + _b240 = (double) (long) ((X##_f1 >> 8) & 0xffffff); \ + _g240 = (double) (long) ((Y##_f1 >> 8) & 0xffffff); \ + _a240 = (double) (long) (X##_f1 >> 32); \ + _f240 = (double) (long) (Y##_f1 >> 32); \ + _e240 *= _const[3]; \ + _j240 *= _const[3]; \ + _d240 *= _const[2]; \ + _i240 *= _const[2]; \ + _c240 *= _const[1]; \ + _h240 *= _const[1]; \ + _b240 *= _const[0]; \ + _g240 *= _const[0]; \ + _s240.d = _e240*_j240; \ + _r240.d = _d240*_j240 + _e240*_i240; \ + _q240.d = _c240*_j240 + _d240*_i240 + _e240*_h240; \ + _p240.d = _b240*_j240 + _c240*_i240 + _d240*_h240 + _e240*_g240; \ + _o240.d = _a240*_j240 + _b240*_i240 + _c240*_h240 + _d240*_g240 + _e240*_f240; \ + _n240.d = _a240*_i240 + _b240*_h240 + _c240*_g240 + _d240*_f240; \ + _m240.d = _a240*_h240 + _b240*_g240 + _c240*_f240; \ + _l240.d = _a240*_g240 + _b240*_f240; \ + _k240 = _a240*_f240; \ + _r240.d += _s240.d; \ + _q240.d += _r240.d; \ + _p240.d += _q240.d; \ + _o240.d += _p240.d; \ + _n240.d += _o240.d; \ + _m240.d += _n240.d; \ + _l240.d += _m240.d; \ + _k240 += _l240.d; \ + _s240.d -= ((_const[10]+_s240.d)-_const[10]); \ + _r240.d -= ((_const[9]+_r240.d)-_const[9]); \ + _q240.d -= ((_const[8]+_q240.d)-_const[8]); \ + _p240.d -= ((_const[7]+_p240.d)-_const[7]); \ + _o240.d += _const[7]; \ + _n240.d += _const[6]; \ + _m240.d += _const[5]; \ + _l240.d += _const[4]; \ + if (_s240.d != 0.0) \ + _y240 = 1; \ + if (_r240.d != 0.0) \ + _y240 = 1; \ + if (_q240.d != 0.0) \ + _y240 = 1; \ + if (_p240.d != 0.0) \ + _y240 = 1; \ + _t240 = (DItype) _k240; \ + _u240 = _l240.i; \ + _v240 = _m240.i; \ + _w240 = _n240.i; \ + _x240 = _o240.i; \ + R##_f1 = ((_t240 << (128 - (wfracbits - 1))) \ + | ((_u240 & 0xffffff) >> ((wfracbits - 1) - 104))); \ + R##_f0 = (((_u240 & 0xffffff) << (168 - (wfracbits - 1))) \ + | ((_v240 & 0xffffff) << (144 - (wfracbits - 1))) \ + | ((_w240 & 0xffffff) << (120 - (wfracbits - 1))) \ + | ((_x240 & 0xffffff) >> ((wfracbits - 1) - 96)) \ + | _y240); \ + resetfe; \ + } \ + while (0) + +/* Division algorithms: */ + +#define _FP_DIV_MEAT_2_udiv(fs, R, X, Y) \ + do \ + { \ + _FP_W_TYPE _FP_DIV_MEAT_2_udiv_n_f2; \ + _FP_W_TYPE _FP_DIV_MEAT_2_udiv_n_f1; \ + _FP_W_TYPE _FP_DIV_MEAT_2_udiv_n_f0; \ + _FP_W_TYPE _FP_DIV_MEAT_2_udiv_r_f1; \ + _FP_W_TYPE _FP_DIV_MEAT_2_udiv_r_f0; \ + _FP_W_TYPE _FP_DIV_MEAT_2_udiv_m_f1; \ + _FP_W_TYPE _FP_DIV_MEAT_2_udiv_m_f0; \ + if (_FP_FRAC_GE_2 (X, Y)) \ + { \ + _FP_DIV_MEAT_2_udiv_n_f2 = X##_f1 >> 1; \ + _FP_DIV_MEAT_2_udiv_n_f1 \ + = X##_f1 << (_FP_W_TYPE_SIZE - 1) | X##_f0 >> 1; \ + _FP_DIV_MEAT_2_udiv_n_f0 \ + = X##_f0 << (_FP_W_TYPE_SIZE - 1); \ + } \ + else \ + { \ + R##_e--; \ + _FP_DIV_MEAT_2_udiv_n_f2 = X##_f1; \ + _FP_DIV_MEAT_2_udiv_n_f1 = X##_f0; \ + _FP_DIV_MEAT_2_udiv_n_f0 = 0; \ + } \ + \ + /* Normalize, i.e. make the most significant bit of the \ + denominator set. */ \ + _FP_FRAC_SLL_2 (Y, _FP_WFRACXBITS_##fs); \ + \ + udiv_qrnnd (R##_f1, _FP_DIV_MEAT_2_udiv_r_f1, \ + _FP_DIV_MEAT_2_udiv_n_f2, _FP_DIV_MEAT_2_udiv_n_f1, \ + Y##_f1); \ + umul_ppmm (_FP_DIV_MEAT_2_udiv_m_f1, _FP_DIV_MEAT_2_udiv_m_f0, \ + R##_f1, Y##_f0); \ + _FP_DIV_MEAT_2_udiv_r_f0 = _FP_DIV_MEAT_2_udiv_n_f0; \ + if (_FP_FRAC_GT_2 (_FP_DIV_MEAT_2_udiv_m, _FP_DIV_MEAT_2_udiv_r)) \ + { \ + R##_f1--; \ + _FP_FRAC_ADD_2 (_FP_DIV_MEAT_2_udiv_r, Y, \ + _FP_DIV_MEAT_2_udiv_r); \ + if (_FP_FRAC_GE_2 (_FP_DIV_MEAT_2_udiv_r, Y) \ + && _FP_FRAC_GT_2 (_FP_DIV_MEAT_2_udiv_m, \ + _FP_DIV_MEAT_2_udiv_r)) \ + { \ + R##_f1--; \ + _FP_FRAC_ADD_2 (_FP_DIV_MEAT_2_udiv_r, Y, \ + _FP_DIV_MEAT_2_udiv_r); \ + } \ + } \ + _FP_FRAC_DEC_2 (_FP_DIV_MEAT_2_udiv_r, _FP_DIV_MEAT_2_udiv_m); \ + \ + if (_FP_DIV_MEAT_2_udiv_r_f1 == Y##_f1) \ + { \ + /* This is a special case, not an optimization \ + (_FP_DIV_MEAT_2_udiv_r/Y##_f1 would not fit into UWtype). \ + As _FP_DIV_MEAT_2_udiv_r is guaranteed to be < Y, \ + R##_f0 can be either (UWtype)-1 or (UWtype)-2. But as we \ + know what kind of bits it is (sticky, guard, round), \ + we don't care. We also don't care what the reminder is, \ + because the guard bit will be set anyway. -jj */ \ + R##_f0 = -1; \ + } \ + else \ + { \ + udiv_qrnnd (R##_f0, _FP_DIV_MEAT_2_udiv_r_f1, \ + _FP_DIV_MEAT_2_udiv_r_f1, \ + _FP_DIV_MEAT_2_udiv_r_f0, Y##_f1); \ + umul_ppmm (_FP_DIV_MEAT_2_udiv_m_f1, \ + _FP_DIV_MEAT_2_udiv_m_f0, R##_f0, Y##_f0); \ + _FP_DIV_MEAT_2_udiv_r_f0 = 0; \ + if (_FP_FRAC_GT_2 (_FP_DIV_MEAT_2_udiv_m, \ + _FP_DIV_MEAT_2_udiv_r)) \ + { \ + R##_f0--; \ + _FP_FRAC_ADD_2 (_FP_DIV_MEAT_2_udiv_r, Y, \ + _FP_DIV_MEAT_2_udiv_r); \ + if (_FP_FRAC_GE_2 (_FP_DIV_MEAT_2_udiv_r, Y) \ + && _FP_FRAC_GT_2 (_FP_DIV_MEAT_2_udiv_m, \ + _FP_DIV_MEAT_2_udiv_r)) \ + { \ + R##_f0--; \ + _FP_FRAC_ADD_2 (_FP_DIV_MEAT_2_udiv_r, Y, \ + _FP_DIV_MEAT_2_udiv_r); \ + } \ + } \ + if (!_FP_FRAC_EQ_2 (_FP_DIV_MEAT_2_udiv_r, \ + _FP_DIV_MEAT_2_udiv_m)) \ + R##_f0 |= _FP_WORK_STICKY; \ + } \ + } \ + while (0) + + +/* Square root algorithms: + We have just one right now, maybe Newton approximation + should be added for those machines where division is fast. */ + +#define _FP_SQRT_MEAT_2(R, S, T, X, q) \ + do \ + { \ + while (q) \ + { \ + T##_f1 = S##_f1 + (q); \ + if (T##_f1 <= X##_f1) \ + { \ + S##_f1 = T##_f1 + (q); \ + X##_f1 -= T##_f1; \ + R##_f1 += (q); \ + } \ + _FP_FRAC_SLL_2 (X, 1); \ + (q) >>= 1; \ + } \ + (q) = (_FP_W_TYPE) 1 << (_FP_W_TYPE_SIZE - 1); \ + while ((q) != _FP_WORK_ROUND) \ + { \ + T##_f0 = S##_f0 + (q); \ + T##_f1 = S##_f1; \ + if (T##_f1 < X##_f1 \ + || (T##_f1 == X##_f1 && T##_f0 <= X##_f0)) \ + { \ + S##_f0 = T##_f0 + (q); \ + S##_f1 += (T##_f0 > S##_f0); \ + _FP_FRAC_DEC_2 (X, T); \ + R##_f0 += (q); \ + } \ + _FP_FRAC_SLL_2 (X, 1); \ + (q) >>= 1; \ + } \ + if (X##_f0 | X##_f1) \ + { \ + if (S##_f1 < X##_f1 \ + || (S##_f1 == X##_f1 && S##_f0 < X##_f0)) \ + R##_f0 |= _FP_WORK_ROUND; \ + R##_f0 |= _FP_WORK_STICKY; \ + } \ + } \ + while (0) + + +/* Assembly/disassembly for converting to/from integral types. + No shifting or overflow handled here. */ + +#define _FP_FRAC_ASSEMBLE_2(r, X, rsize) \ + (void) (((rsize) <= _FP_W_TYPE_SIZE) \ + ? ({ (r) = X##_f0; }) \ + : ({ \ + (r) = X##_f1; \ + (r) <<= _FP_W_TYPE_SIZE; \ + (r) += X##_f0; \ + })) + +#define _FP_FRAC_DISASSEMBLE_2(X, r, rsize) \ + do \ + { \ + X##_f0 = (r); \ + X##_f1 = ((rsize) <= _FP_W_TYPE_SIZE \ + ? 0 \ + : (r) >> _FP_W_TYPE_SIZE); \ + } \ + while (0) + +/* Convert FP values between word sizes. */ + +#define _FP_FRAC_COPY_1_2(D, S) (D##_f = S##_f0) + +#define _FP_FRAC_COPY_2_1(D, S) ((D##_f0 = S##_f), (D##_f1 = 0)) + +#define _FP_FRAC_COPY_2_2(D, S) _FP_FRAC_COPY_2 (D, S) + +#endif /* !SOFT_FP_OP_2_H */ diff --git a/REORG.TODO/soft-fp/op-4.h b/REORG.TODO/soft-fp/op-4.h new file mode 100644 index 0000000000..5034667e36 --- /dev/null +++ b/REORG.TODO/soft-fp/op-4.h @@ -0,0 +1,875 @@ +/* Software floating-point emulation. + Basic four-word fraction declaration and manipulation. + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com), + Jakub Jelinek (jj@ultra.linux.cz), + David S. Miller (davem@redhat.com) and + Peter Maydell (pmaydell@chiark.greenend.org.uk). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#ifndef SOFT_FP_OP_4_H +#define SOFT_FP_OP_4_H 1 + +#define _FP_FRAC_DECL_4(X) _FP_W_TYPE X##_f[4] +#define _FP_FRAC_COPY_4(D, S) \ + (D##_f[0] = S##_f[0], D##_f[1] = S##_f[1], \ + D##_f[2] = S##_f[2], D##_f[3] = S##_f[3]) +#define _FP_FRAC_SET_4(X, I) __FP_FRAC_SET_4 (X, I) +#define _FP_FRAC_HIGH_4(X) (X##_f[3]) +#define _FP_FRAC_LOW_4(X) (X##_f[0]) +#define _FP_FRAC_WORD_4(X, w) (X##_f[w]) + +#define _FP_FRAC_SLL_4(X, N) \ + do \ + { \ + _FP_I_TYPE _FP_FRAC_SLL_4_up, _FP_FRAC_SLL_4_down; \ + _FP_I_TYPE _FP_FRAC_SLL_4_skip, _FP_FRAC_SLL_4_i; \ + _FP_FRAC_SLL_4_skip = (N) / _FP_W_TYPE_SIZE; \ + _FP_FRAC_SLL_4_up = (N) % _FP_W_TYPE_SIZE; \ + _FP_FRAC_SLL_4_down = _FP_W_TYPE_SIZE - _FP_FRAC_SLL_4_up; \ + if (!_FP_FRAC_SLL_4_up) \ + for (_FP_FRAC_SLL_4_i = 3; \ + _FP_FRAC_SLL_4_i >= _FP_FRAC_SLL_4_skip; \ + --_FP_FRAC_SLL_4_i) \ + X##_f[_FP_FRAC_SLL_4_i] \ + = X##_f[_FP_FRAC_SLL_4_i-_FP_FRAC_SLL_4_skip]; \ + else \ + { \ + for (_FP_FRAC_SLL_4_i = 3; \ + _FP_FRAC_SLL_4_i > _FP_FRAC_SLL_4_skip; \ + --_FP_FRAC_SLL_4_i) \ + X##_f[_FP_FRAC_SLL_4_i] \ + = ((X##_f[_FP_FRAC_SLL_4_i-_FP_FRAC_SLL_4_skip] \ + << _FP_FRAC_SLL_4_up) \ + | (X##_f[_FP_FRAC_SLL_4_i-_FP_FRAC_SLL_4_skip-1] \ + >> _FP_FRAC_SLL_4_down)); \ + X##_f[_FP_FRAC_SLL_4_i--] = X##_f[0] << _FP_FRAC_SLL_4_up; \ + } \ + for (; _FP_FRAC_SLL_4_i >= 0; --_FP_FRAC_SLL_4_i) \ + X##_f[_FP_FRAC_SLL_4_i] = 0; \ + } \ + while (0) + +/* This one was broken too. */ +#define _FP_FRAC_SRL_4(X, N) \ + do \ + { \ + _FP_I_TYPE _FP_FRAC_SRL_4_up, _FP_FRAC_SRL_4_down; \ + _FP_I_TYPE _FP_FRAC_SRL_4_skip, _FP_FRAC_SRL_4_i; \ + _FP_FRAC_SRL_4_skip = (N) / _FP_W_TYPE_SIZE; \ + _FP_FRAC_SRL_4_down = (N) % _FP_W_TYPE_SIZE; \ + _FP_FRAC_SRL_4_up = _FP_W_TYPE_SIZE - _FP_FRAC_SRL_4_down; \ + if (!_FP_FRAC_SRL_4_down) \ + for (_FP_FRAC_SRL_4_i = 0; \ + _FP_FRAC_SRL_4_i <= 3-_FP_FRAC_SRL_4_skip; \ + ++_FP_FRAC_SRL_4_i) \ + X##_f[_FP_FRAC_SRL_4_i] \ + = X##_f[_FP_FRAC_SRL_4_i+_FP_FRAC_SRL_4_skip]; \ + else \ + { \ + for (_FP_FRAC_SRL_4_i = 0; \ + _FP_FRAC_SRL_4_i < 3-_FP_FRAC_SRL_4_skip; \ + ++_FP_FRAC_SRL_4_i) \ + X##_f[_FP_FRAC_SRL_4_i] \ + = ((X##_f[_FP_FRAC_SRL_4_i+_FP_FRAC_SRL_4_skip] \ + >> _FP_FRAC_SRL_4_down) \ + | (X##_f[_FP_FRAC_SRL_4_i+_FP_FRAC_SRL_4_skip+1] \ + << _FP_FRAC_SRL_4_up)); \ + X##_f[_FP_FRAC_SRL_4_i++] = X##_f[3] >> _FP_FRAC_SRL_4_down; \ + } \ + for (; _FP_FRAC_SRL_4_i < 4; ++_FP_FRAC_SRL_4_i) \ + X##_f[_FP_FRAC_SRL_4_i] = 0; \ + } \ + while (0) + + +/* Right shift with sticky-lsb. + What this actually means is that we do a standard right-shift, + but that if any of the bits that fall off the right hand side + were one then we always set the LSbit. */ +#define _FP_FRAC_SRST_4(X, S, N, size) \ + do \ + { \ + _FP_I_TYPE _FP_FRAC_SRST_4_up, _FP_FRAC_SRST_4_down; \ + _FP_I_TYPE _FP_FRAC_SRST_4_skip, _FP_FRAC_SRST_4_i; \ + _FP_W_TYPE _FP_FRAC_SRST_4_s; \ + _FP_FRAC_SRST_4_skip = (N) / _FP_W_TYPE_SIZE; \ + _FP_FRAC_SRST_4_down = (N) % _FP_W_TYPE_SIZE; \ + _FP_FRAC_SRST_4_up = _FP_W_TYPE_SIZE - _FP_FRAC_SRST_4_down; \ + for (_FP_FRAC_SRST_4_s = _FP_FRAC_SRST_4_i = 0; \ + _FP_FRAC_SRST_4_i < _FP_FRAC_SRST_4_skip; \ + ++_FP_FRAC_SRST_4_i) \ + _FP_FRAC_SRST_4_s |= X##_f[_FP_FRAC_SRST_4_i]; \ + if (!_FP_FRAC_SRST_4_down) \ + for (_FP_FRAC_SRST_4_i = 0; \ + _FP_FRAC_SRST_4_i <= 3-_FP_FRAC_SRST_4_skip; \ + ++_FP_FRAC_SRST_4_i) \ + X##_f[_FP_FRAC_SRST_4_i] \ + = X##_f[_FP_FRAC_SRST_4_i+_FP_FRAC_SRST_4_skip]; \ + else \ + { \ + _FP_FRAC_SRST_4_s \ + |= X##_f[_FP_FRAC_SRST_4_i] << _FP_FRAC_SRST_4_up; \ + for (_FP_FRAC_SRST_4_i = 0; \ + _FP_FRAC_SRST_4_i < 3-_FP_FRAC_SRST_4_skip; \ + ++_FP_FRAC_SRST_4_i) \ + X##_f[_FP_FRAC_SRST_4_i] \ + = ((X##_f[_FP_FRAC_SRST_4_i+_FP_FRAC_SRST_4_skip] \ + >> _FP_FRAC_SRST_4_down) \ + | (X##_f[_FP_FRAC_SRST_4_i+_FP_FRAC_SRST_4_skip+1] \ + << _FP_FRAC_SRST_4_up)); \ + X##_f[_FP_FRAC_SRST_4_i++] \ + = X##_f[3] >> _FP_FRAC_SRST_4_down; \ + } \ + for (; _FP_FRAC_SRST_4_i < 4; ++_FP_FRAC_SRST_4_i) \ + X##_f[_FP_FRAC_SRST_4_i] = 0; \ + S = (_FP_FRAC_SRST_4_s != 0); \ + } \ + while (0) + +#define _FP_FRAC_SRS_4(X, N, size) \ + do \ + { \ + int _FP_FRAC_SRS_4_sticky; \ + _FP_FRAC_SRST_4 (X, _FP_FRAC_SRS_4_sticky, (N), (size)); \ + X##_f[0] |= _FP_FRAC_SRS_4_sticky; \ + } \ + while (0) + +#define _FP_FRAC_ADD_4(R, X, Y) \ + __FP_FRAC_ADD_4 (R##_f[3], R##_f[2], R##_f[1], R##_f[0], \ + X##_f[3], X##_f[2], X##_f[1], X##_f[0], \ + Y##_f[3], Y##_f[2], Y##_f[1], Y##_f[0]) + +#define _FP_FRAC_SUB_4(R, X, Y) \ + __FP_FRAC_SUB_4 (R##_f[3], R##_f[2], R##_f[1], R##_f[0], \ + X##_f[3], X##_f[2], X##_f[1], X##_f[0], \ + Y##_f[3], Y##_f[2], Y##_f[1], Y##_f[0]) + +#define _FP_FRAC_DEC_4(X, Y) \ + __FP_FRAC_DEC_4 (X##_f[3], X##_f[2], X##_f[1], X##_f[0], \ + Y##_f[3], Y##_f[2], Y##_f[1], Y##_f[0]) + +#define _FP_FRAC_ADDI_4(X, I) \ + __FP_FRAC_ADDI_4 (X##_f[3], X##_f[2], X##_f[1], X##_f[0], I) + +#define _FP_ZEROFRAC_4 0, 0, 0, 0 +#define _FP_MINFRAC_4 0, 0, 0, 1 +#define _FP_MAXFRAC_4 (~(_FP_WS_TYPE) 0), (~(_FP_WS_TYPE) 0), (~(_FP_WS_TYPE) 0), (~(_FP_WS_TYPE) 0) + +#define _FP_FRAC_ZEROP_4(X) ((X##_f[0] | X##_f[1] | X##_f[2] | X##_f[3]) == 0) +#define _FP_FRAC_NEGP_4(X) ((_FP_WS_TYPE) X##_f[3] < 0) +#define _FP_FRAC_OVERP_4(fs, X) (_FP_FRAC_HIGH_##fs (X) & _FP_OVERFLOW_##fs) +#define _FP_FRAC_HIGHBIT_DW_4(fs, X) \ + (_FP_FRAC_HIGH_DW_##fs (X) & _FP_HIGHBIT_DW_##fs) +#define _FP_FRAC_CLEAR_OVERP_4(fs, X) (_FP_FRAC_HIGH_##fs (X) &= ~_FP_OVERFLOW_##fs) + +#define _FP_FRAC_EQ_4(X, Y) \ + (X##_f[0] == Y##_f[0] && X##_f[1] == Y##_f[1] \ + && X##_f[2] == Y##_f[2] && X##_f[3] == Y##_f[3]) + +#define _FP_FRAC_GT_4(X, Y) \ + (X##_f[3] > Y##_f[3] \ + || (X##_f[3] == Y##_f[3] \ + && (X##_f[2] > Y##_f[2] \ + || (X##_f[2] == Y##_f[2] \ + && (X##_f[1] > Y##_f[1] \ + || (X##_f[1] == Y##_f[1] \ + && X##_f[0] > Y##_f[0])))))) + +#define _FP_FRAC_GE_4(X, Y) \ + (X##_f[3] > Y##_f[3] \ + || (X##_f[3] == Y##_f[3] \ + && (X##_f[2] > Y##_f[2] \ + || (X##_f[2] == Y##_f[2] \ + && (X##_f[1] > Y##_f[1] \ + || (X##_f[1] == Y##_f[1] \ + && X##_f[0] >= Y##_f[0])))))) + + +#define _FP_FRAC_CLZ_4(R, X) \ + do \ + { \ + if (X##_f[3]) \ + __FP_CLZ ((R), X##_f[3]); \ + else if (X##_f[2]) \ + { \ + __FP_CLZ ((R), X##_f[2]); \ + (R) += _FP_W_TYPE_SIZE; \ + } \ + else if (X##_f[1]) \ + { \ + __FP_CLZ ((R), X##_f[1]); \ + (R) += _FP_W_TYPE_SIZE*2; \ + } \ + else \ + { \ + __FP_CLZ ((R), X##_f[0]); \ + (R) += _FP_W_TYPE_SIZE*3; \ + } \ + } \ + while (0) + + +#define _FP_UNPACK_RAW_4(fs, X, val) \ + do \ + { \ + union _FP_UNION_##fs _FP_UNPACK_RAW_4_flo; \ + _FP_UNPACK_RAW_4_flo.flt = (val); \ + X##_f[0] = _FP_UNPACK_RAW_4_flo.bits.frac0; \ + X##_f[1] = _FP_UNPACK_RAW_4_flo.bits.frac1; \ + X##_f[2] = _FP_UNPACK_RAW_4_flo.bits.frac2; \ + X##_f[3] = _FP_UNPACK_RAW_4_flo.bits.frac3; \ + X##_e = _FP_UNPACK_RAW_4_flo.bits.exp; \ + X##_s = _FP_UNPACK_RAW_4_flo.bits.sign; \ + } \ + while (0) + +#define _FP_UNPACK_RAW_4_P(fs, X, val) \ + do \ + { \ + union _FP_UNION_##fs *_FP_UNPACK_RAW_4_P_flo \ + = (union _FP_UNION_##fs *) (val); \ + \ + X##_f[0] = _FP_UNPACK_RAW_4_P_flo->bits.frac0; \ + X##_f[1] = _FP_UNPACK_RAW_4_P_flo->bits.frac1; \ + X##_f[2] = _FP_UNPACK_RAW_4_P_flo->bits.frac2; \ + X##_f[3] = _FP_UNPACK_RAW_4_P_flo->bits.frac3; \ + X##_e = _FP_UNPACK_RAW_4_P_flo->bits.exp; \ + X##_s = _FP_UNPACK_RAW_4_P_flo->bits.sign; \ + } \ + while (0) + +#define _FP_PACK_RAW_4(fs, val, X) \ + do \ + { \ + union _FP_UNION_##fs _FP_PACK_RAW_4_flo; \ + _FP_PACK_RAW_4_flo.bits.frac0 = X##_f[0]; \ + _FP_PACK_RAW_4_flo.bits.frac1 = X##_f[1]; \ + _FP_PACK_RAW_4_flo.bits.frac2 = X##_f[2]; \ + _FP_PACK_RAW_4_flo.bits.frac3 = X##_f[3]; \ + _FP_PACK_RAW_4_flo.bits.exp = X##_e; \ + _FP_PACK_RAW_4_flo.bits.sign = X##_s; \ + (val) = _FP_PACK_RAW_4_flo.flt; \ + } \ + while (0) + +#define _FP_PACK_RAW_4_P(fs, val, X) \ + do \ + { \ + union _FP_UNION_##fs *_FP_PACK_RAW_4_P_flo \ + = (union _FP_UNION_##fs *) (val); \ + \ + _FP_PACK_RAW_4_P_flo->bits.frac0 = X##_f[0]; \ + _FP_PACK_RAW_4_P_flo->bits.frac1 = X##_f[1]; \ + _FP_PACK_RAW_4_P_flo->bits.frac2 = X##_f[2]; \ + _FP_PACK_RAW_4_P_flo->bits.frac3 = X##_f[3]; \ + _FP_PACK_RAW_4_P_flo->bits.exp = X##_e; \ + _FP_PACK_RAW_4_P_flo->bits.sign = X##_s; \ + } \ + while (0) + +/* Multiplication algorithms: */ + +/* Given a 1W * 1W => 2W primitive, do the extended multiplication. */ + +#define _FP_MUL_MEAT_DW_4_wide(wfracbits, R, X, Y, doit) \ + do \ + { \ + _FP_FRAC_DECL_2 (_FP_MUL_MEAT_DW_4_wide_b); \ + _FP_FRAC_DECL_2 (_FP_MUL_MEAT_DW_4_wide_c); \ + _FP_FRAC_DECL_2 (_FP_MUL_MEAT_DW_4_wide_d); \ + _FP_FRAC_DECL_2 (_FP_MUL_MEAT_DW_4_wide_e); \ + _FP_FRAC_DECL_2 (_FP_MUL_MEAT_DW_4_wide_f); \ + \ + doit (_FP_FRAC_WORD_8 (R, 1), _FP_FRAC_WORD_8 (R, 0), \ + X##_f[0], Y##_f[0]); \ + doit (_FP_MUL_MEAT_DW_4_wide_b_f1, _FP_MUL_MEAT_DW_4_wide_b_f0, \ + X##_f[0], Y##_f[1]); \ + doit (_FP_MUL_MEAT_DW_4_wide_c_f1, _FP_MUL_MEAT_DW_4_wide_c_f0, \ + X##_f[1], Y##_f[0]); \ + doit (_FP_MUL_MEAT_DW_4_wide_d_f1, _FP_MUL_MEAT_DW_4_wide_d_f0, \ + X##_f[1], Y##_f[1]); \ + doit (_FP_MUL_MEAT_DW_4_wide_e_f1, _FP_MUL_MEAT_DW_4_wide_e_f0, \ + X##_f[0], Y##_f[2]); \ + doit (_FP_MUL_MEAT_DW_4_wide_f_f1, _FP_MUL_MEAT_DW_4_wide_f_f0, \ + X##_f[2], Y##_f[0]); \ + __FP_FRAC_ADD_3 (_FP_FRAC_WORD_8 (R, 3), _FP_FRAC_WORD_8 (R, 2), \ + _FP_FRAC_WORD_8 (R, 1), 0, \ + _FP_MUL_MEAT_DW_4_wide_b_f1, \ + _FP_MUL_MEAT_DW_4_wide_b_f0, \ + 0, 0, _FP_FRAC_WORD_8 (R, 1)); \ + __FP_FRAC_ADD_3 (_FP_FRAC_WORD_8 (R, 3), _FP_FRAC_WORD_8 (R, 2), \ + _FP_FRAC_WORD_8 (R, 1), 0, \ + _FP_MUL_MEAT_DW_4_wide_c_f1, \ + _FP_MUL_MEAT_DW_4_wide_c_f0, \ + _FP_FRAC_WORD_8 (R, 3), _FP_FRAC_WORD_8 (R, 2), \ + _FP_FRAC_WORD_8 (R, 1)); \ + __FP_FRAC_ADD_3 (_FP_FRAC_WORD_8 (R, 4), _FP_FRAC_WORD_8 (R, 3), \ + _FP_FRAC_WORD_8 (R, 2), 0, \ + _FP_MUL_MEAT_DW_4_wide_d_f1, \ + _FP_MUL_MEAT_DW_4_wide_d_f0, \ + 0, _FP_FRAC_WORD_8 (R, 3), _FP_FRAC_WORD_8 (R, 2)); \ + __FP_FRAC_ADD_3 (_FP_FRAC_WORD_8 (R, 4), _FP_FRAC_WORD_8 (R, 3), \ + _FP_FRAC_WORD_8 (R, 2), 0, \ + _FP_MUL_MEAT_DW_4_wide_e_f1, \ + _FP_MUL_MEAT_DW_4_wide_e_f0, \ + _FP_FRAC_WORD_8 (R, 4), _FP_FRAC_WORD_8 (R, 3), \ + _FP_FRAC_WORD_8 (R, 2)); \ + __FP_FRAC_ADD_3 (_FP_FRAC_WORD_8 (R, 4), _FP_FRAC_WORD_8 (R, 3), \ + _FP_FRAC_WORD_8 (R, 2), 0, \ + _FP_MUL_MEAT_DW_4_wide_f_f1, \ + _FP_MUL_MEAT_DW_4_wide_f_f0, \ + _FP_FRAC_WORD_8 (R, 4), _FP_FRAC_WORD_8 (R, 3), \ + _FP_FRAC_WORD_8 (R, 2)); \ + doit (_FP_MUL_MEAT_DW_4_wide_b_f1, \ + _FP_MUL_MEAT_DW_4_wide_b_f0, X##_f[0], Y##_f[3]); \ + doit (_FP_MUL_MEAT_DW_4_wide_c_f1, \ + _FP_MUL_MEAT_DW_4_wide_c_f0, X##_f[3], Y##_f[0]); \ + doit (_FP_MUL_MEAT_DW_4_wide_d_f1, _FP_MUL_MEAT_DW_4_wide_d_f0, \ + X##_f[1], Y##_f[2]); \ + doit (_FP_MUL_MEAT_DW_4_wide_e_f1, _FP_MUL_MEAT_DW_4_wide_e_f0, \ + X##_f[2], Y##_f[1]); \ + __FP_FRAC_ADD_3 (_FP_FRAC_WORD_8 (R, 5), _FP_FRAC_WORD_8 (R, 4), \ + _FP_FRAC_WORD_8 (R, 3), 0, \ + _FP_MUL_MEAT_DW_4_wide_b_f1, \ + _FP_MUL_MEAT_DW_4_wide_b_f0, \ + 0, _FP_FRAC_WORD_8 (R, 4), _FP_FRAC_WORD_8 (R, 3)); \ + __FP_FRAC_ADD_3 (_FP_FRAC_WORD_8 (R, 5), _FP_FRAC_WORD_8 (R, 4), \ + _FP_FRAC_WORD_8 (R, 3), 0, \ + _FP_MUL_MEAT_DW_4_wide_c_f1, \ + _FP_MUL_MEAT_DW_4_wide_c_f0, \ + _FP_FRAC_WORD_8 (R, 5), _FP_FRAC_WORD_8 (R, 4), \ + _FP_FRAC_WORD_8 (R, 3)); \ + __FP_FRAC_ADD_3 (_FP_FRAC_WORD_8 (R, 5), _FP_FRAC_WORD_8 (R, 4), \ + _FP_FRAC_WORD_8 (R, 3), 0, \ + _FP_MUL_MEAT_DW_4_wide_d_f1, \ + _FP_MUL_MEAT_DW_4_wide_d_f0, \ + _FP_FRAC_WORD_8 (R, 5), _FP_FRAC_WORD_8 (R, 4), \ + _FP_FRAC_WORD_8 (R, 3)); \ + __FP_FRAC_ADD_3 (_FP_FRAC_WORD_8 (R, 5), _FP_FRAC_WORD_8 (R, 4), \ + _FP_FRAC_WORD_8 (R, 3), 0, \ + _FP_MUL_MEAT_DW_4_wide_e_f1, \ + _FP_MUL_MEAT_DW_4_wide_e_f0, \ + _FP_FRAC_WORD_8 (R, 5), _FP_FRAC_WORD_8 (R, 4), \ + _FP_FRAC_WORD_8 (R, 3)); \ + doit (_FP_MUL_MEAT_DW_4_wide_b_f1, _FP_MUL_MEAT_DW_4_wide_b_f0, \ + X##_f[2], Y##_f[2]); \ + doit (_FP_MUL_MEAT_DW_4_wide_c_f1, _FP_MUL_MEAT_DW_4_wide_c_f0, \ + X##_f[1], Y##_f[3]); \ + doit (_FP_MUL_MEAT_DW_4_wide_d_f1, _FP_MUL_MEAT_DW_4_wide_d_f0, \ + X##_f[3], Y##_f[1]); \ + doit (_FP_MUL_MEAT_DW_4_wide_e_f1, _FP_MUL_MEAT_DW_4_wide_e_f0, \ + X##_f[2], Y##_f[3]); \ + doit (_FP_MUL_MEAT_DW_4_wide_f_f1, _FP_MUL_MEAT_DW_4_wide_f_f0, \ + X##_f[3], Y##_f[2]); \ + __FP_FRAC_ADD_3 (_FP_FRAC_WORD_8 (R, 6), _FP_FRAC_WORD_8 (R, 5), \ + _FP_FRAC_WORD_8 (R, 4), 0, \ + _FP_MUL_MEAT_DW_4_wide_b_f1, \ + _FP_MUL_MEAT_DW_4_wide_b_f0, \ + 0, _FP_FRAC_WORD_8 (R, 5), _FP_FRAC_WORD_8 (R, 4)); \ + __FP_FRAC_ADD_3 (_FP_FRAC_WORD_8 (R, 6), _FP_FRAC_WORD_8 (R, 5), \ + _FP_FRAC_WORD_8 (R, 4), 0, \ + _FP_MUL_MEAT_DW_4_wide_c_f1, \ + _FP_MUL_MEAT_DW_4_wide_c_f0, \ + _FP_FRAC_WORD_8 (R, 6), _FP_FRAC_WORD_8 (R, 5), \ + _FP_FRAC_WORD_8 (R, 4)); \ + __FP_FRAC_ADD_3 (_FP_FRAC_WORD_8 (R, 6), _FP_FRAC_WORD_8 (R, 5), \ + _FP_FRAC_WORD_8 (R, 4), 0, \ + _FP_MUL_MEAT_DW_4_wide_d_f1, \ + _FP_MUL_MEAT_DW_4_wide_d_f0, \ + _FP_FRAC_WORD_8 (R, 6), _FP_FRAC_WORD_8 (R, 5), \ + _FP_FRAC_WORD_8 (R, 4)); \ + __FP_FRAC_ADD_3 (_FP_FRAC_WORD_8 (R, 7), _FP_FRAC_WORD_8 (R, 6), \ + _FP_FRAC_WORD_8 (R, 5), 0, \ + _FP_MUL_MEAT_DW_4_wide_e_f1, \ + _FP_MUL_MEAT_DW_4_wide_e_f0, \ + 0, _FP_FRAC_WORD_8 (R, 6), _FP_FRAC_WORD_8 (R, 5)); \ + __FP_FRAC_ADD_3 (_FP_FRAC_WORD_8 (R, 7), _FP_FRAC_WORD_8 (R, 6), \ + _FP_FRAC_WORD_8 (R, 5), 0, \ + _FP_MUL_MEAT_DW_4_wide_f_f1, \ + _FP_MUL_MEAT_DW_4_wide_f_f0, \ + _FP_FRAC_WORD_8 (R, 7), _FP_FRAC_WORD_8 (R, 6), \ + _FP_FRAC_WORD_8 (R, 5)); \ + doit (_FP_MUL_MEAT_DW_4_wide_b_f1, _FP_MUL_MEAT_DW_4_wide_b_f0, \ + X##_f[3], Y##_f[3]); \ + __FP_FRAC_ADD_2 (_FP_FRAC_WORD_8 (R, 7), _FP_FRAC_WORD_8 (R, 6), \ + _FP_MUL_MEAT_DW_4_wide_b_f1, \ + _FP_MUL_MEAT_DW_4_wide_b_f0, \ + _FP_FRAC_WORD_8 (R, 7), _FP_FRAC_WORD_8 (R, 6)); \ + } \ + while (0) + +#define _FP_MUL_MEAT_4_wide(wfracbits, R, X, Y, doit) \ + do \ + { \ + _FP_FRAC_DECL_8 (_FP_MUL_MEAT_4_wide_z); \ + \ + _FP_MUL_MEAT_DW_4_wide ((wfracbits), _FP_MUL_MEAT_4_wide_z, \ + X, Y, doit); \ + \ + /* Normalize since we know where the msb of the multiplicands \ + were (bit B), we know that the msb of the of the product is \ + at either 2B or 2B-1. */ \ + _FP_FRAC_SRS_8 (_FP_MUL_MEAT_4_wide_z, (wfracbits)-1, \ + 2*(wfracbits)); \ + __FP_FRAC_SET_4 (R, _FP_FRAC_WORD_8 (_FP_MUL_MEAT_4_wide_z, 3), \ + _FP_FRAC_WORD_8 (_FP_MUL_MEAT_4_wide_z, 2), \ + _FP_FRAC_WORD_8 (_FP_MUL_MEAT_4_wide_z, 1), \ + _FP_FRAC_WORD_8 (_FP_MUL_MEAT_4_wide_z, 0)); \ + } \ + while (0) + +#define _FP_MUL_MEAT_DW_4_gmp(wfracbits, R, X, Y) \ + do \ + { \ + mpn_mul_n (R##_f, _x_f, _y_f, 4); \ + } \ + while (0) + +#define _FP_MUL_MEAT_4_gmp(wfracbits, R, X, Y) \ + do \ + { \ + _FP_FRAC_DECL_8 (_FP_MUL_MEAT_4_gmp_z); \ + \ + _FP_MUL_MEAT_DW_4_gmp ((wfracbits), _FP_MUL_MEAT_4_gmp_z, X, Y); \ + \ + /* Normalize since we know where the msb of the multiplicands \ + were (bit B), we know that the msb of the of the product is \ + at either 2B or 2B-1. */ \ + _FP_FRAC_SRS_8 (_FP_MUL_MEAT_4_gmp_z, (wfracbits)-1, \ + 2*(wfracbits)); \ + __FP_FRAC_SET_4 (R, _FP_FRAC_WORD_8 (_FP_MUL_MEAT_4_gmp_z, 3), \ + _FP_FRAC_WORD_8 (_FP_MUL_MEAT_4_gmp_z, 2), \ + _FP_FRAC_WORD_8 (_FP_MUL_MEAT_4_gmp_z, 1), \ + _FP_FRAC_WORD_8 (_FP_MUL_MEAT_4_gmp_z, 0)); \ + } \ + while (0) + +/* Helper utility for _FP_DIV_MEAT_4_udiv: + * pppp = m * nnn. */ +#define umul_ppppmnnn(p3, p2, p1, p0, m, n2, n1, n0) \ + do \ + { \ + UWtype umul_ppppmnnn_t; \ + umul_ppmm (p1, p0, m, n0); \ + umul_ppmm (p2, umul_ppppmnnn_t, m, n1); \ + __FP_FRAC_ADDI_2 (p2, p1, umul_ppppmnnn_t); \ + umul_ppmm (p3, umul_ppppmnnn_t, m, n2); \ + __FP_FRAC_ADDI_2 (p3, p2, umul_ppppmnnn_t); \ + } \ + while (0) + +/* Division algorithms: */ + +#define _FP_DIV_MEAT_4_udiv(fs, R, X, Y) \ + do \ + { \ + int _FP_DIV_MEAT_4_udiv_i; \ + _FP_FRAC_DECL_4 (_FP_DIV_MEAT_4_udiv_n); \ + _FP_FRAC_DECL_4 (_FP_DIV_MEAT_4_udiv_m); \ + _FP_FRAC_SET_4 (_FP_DIV_MEAT_4_udiv_n, _FP_ZEROFRAC_4); \ + if (_FP_FRAC_GE_4 (X, Y)) \ + { \ + _FP_DIV_MEAT_4_udiv_n_f[3] \ + = X##_f[0] << (_FP_W_TYPE_SIZE - 1); \ + _FP_FRAC_SRL_4 (X, 1); \ + } \ + else \ + R##_e--; \ + \ + /* Normalize, i.e. make the most significant bit of the \ + denominator set. */ \ + _FP_FRAC_SLL_4 (Y, _FP_WFRACXBITS_##fs); \ + \ + for (_FP_DIV_MEAT_4_udiv_i = 3; ; _FP_DIV_MEAT_4_udiv_i--) \ + { \ + if (X##_f[3] == Y##_f[3]) \ + { \ + /* This is a special case, not an optimization \ + (X##_f[3]/Y##_f[3] would not fit into UWtype). \ + As X## is guaranteed to be < Y, \ + R##_f[_FP_DIV_MEAT_4_udiv_i] can be either \ + (UWtype)-1 or (UWtype)-2. */ \ + R##_f[_FP_DIV_MEAT_4_udiv_i] = -1; \ + if (!_FP_DIV_MEAT_4_udiv_i) \ + break; \ + __FP_FRAC_SUB_4 (X##_f[3], X##_f[2], X##_f[1], X##_f[0], \ + Y##_f[2], Y##_f[1], Y##_f[0], 0, \ + X##_f[2], X##_f[1], X##_f[0], \ + _FP_DIV_MEAT_4_udiv_n_f[_FP_DIV_MEAT_4_udiv_i]); \ + _FP_FRAC_SUB_4 (X, Y, X); \ + if (X##_f[3] > Y##_f[3]) \ + { \ + R##_f[_FP_DIV_MEAT_4_udiv_i] = -2; \ + _FP_FRAC_ADD_4 (X, Y, X); \ + } \ + } \ + else \ + { \ + udiv_qrnnd (R##_f[_FP_DIV_MEAT_4_udiv_i], \ + X##_f[3], X##_f[3], X##_f[2], Y##_f[3]); \ + umul_ppppmnnn (_FP_DIV_MEAT_4_udiv_m_f[3], \ + _FP_DIV_MEAT_4_udiv_m_f[2], \ + _FP_DIV_MEAT_4_udiv_m_f[1], \ + _FP_DIV_MEAT_4_udiv_m_f[0], \ + R##_f[_FP_DIV_MEAT_4_udiv_i], \ + Y##_f[2], Y##_f[1], Y##_f[0]); \ + X##_f[2] = X##_f[1]; \ + X##_f[1] = X##_f[0]; \ + X##_f[0] \ + = _FP_DIV_MEAT_4_udiv_n_f[_FP_DIV_MEAT_4_udiv_i]; \ + if (_FP_FRAC_GT_4 (_FP_DIV_MEAT_4_udiv_m, X)) \ + { \ + R##_f[_FP_DIV_MEAT_4_udiv_i]--; \ + _FP_FRAC_ADD_4 (X, Y, X); \ + if (_FP_FRAC_GE_4 (X, Y) \ + && _FP_FRAC_GT_4 (_FP_DIV_MEAT_4_udiv_m, X)) \ + { \ + R##_f[_FP_DIV_MEAT_4_udiv_i]--; \ + _FP_FRAC_ADD_4 (X, Y, X); \ + } \ + } \ + _FP_FRAC_DEC_4 (X, _FP_DIV_MEAT_4_udiv_m); \ + if (!_FP_DIV_MEAT_4_udiv_i) \ + { \ + if (!_FP_FRAC_EQ_4 (X, _FP_DIV_MEAT_4_udiv_m)) \ + R##_f[0] |= _FP_WORK_STICKY; \ + break; \ + } \ + } \ + } \ + } \ + while (0) + + +/* Square root algorithms: + We have just one right now, maybe Newton approximation + should be added for those machines where division is fast. */ + +#define _FP_SQRT_MEAT_4(R, S, T, X, q) \ + do \ + { \ + while (q) \ + { \ + T##_f[3] = S##_f[3] + (q); \ + if (T##_f[3] <= X##_f[3]) \ + { \ + S##_f[3] = T##_f[3] + (q); \ + X##_f[3] -= T##_f[3]; \ + R##_f[3] += (q); \ + } \ + _FP_FRAC_SLL_4 (X, 1); \ + (q) >>= 1; \ + } \ + (q) = (_FP_W_TYPE) 1 << (_FP_W_TYPE_SIZE - 1); \ + while (q) \ + { \ + T##_f[2] = S##_f[2] + (q); \ + T##_f[3] = S##_f[3]; \ + if (T##_f[3] < X##_f[3] \ + || (T##_f[3] == X##_f[3] && T##_f[2] <= X##_f[2])) \ + { \ + S##_f[2] = T##_f[2] + (q); \ + S##_f[3] += (T##_f[2] > S##_f[2]); \ + __FP_FRAC_DEC_2 (X##_f[3], X##_f[2], \ + T##_f[3], T##_f[2]); \ + R##_f[2] += (q); \ + } \ + _FP_FRAC_SLL_4 (X, 1); \ + (q) >>= 1; \ + } \ + (q) = (_FP_W_TYPE) 1 << (_FP_W_TYPE_SIZE - 1); \ + while (q) \ + { \ + T##_f[1] = S##_f[1] + (q); \ + T##_f[2] = S##_f[2]; \ + T##_f[3] = S##_f[3]; \ + if (T##_f[3] < X##_f[3] \ + || (T##_f[3] == X##_f[3] \ + && (T##_f[2] < X##_f[2] \ + || (T##_f[2] == X##_f[2] \ + && T##_f[1] <= X##_f[1])))) \ + { \ + S##_f[1] = T##_f[1] + (q); \ + S##_f[2] += (T##_f[1] > S##_f[1]); \ + S##_f[3] += (T##_f[2] > S##_f[2]); \ + __FP_FRAC_DEC_3 (X##_f[3], X##_f[2], X##_f[1], \ + T##_f[3], T##_f[2], T##_f[1]); \ + R##_f[1] += (q); \ + } \ + _FP_FRAC_SLL_4 (X, 1); \ + (q) >>= 1; \ + } \ + (q) = (_FP_W_TYPE) 1 << (_FP_W_TYPE_SIZE - 1); \ + while ((q) != _FP_WORK_ROUND) \ + { \ + T##_f[0] = S##_f[0] + (q); \ + T##_f[1] = S##_f[1]; \ + T##_f[2] = S##_f[2]; \ + T##_f[3] = S##_f[3]; \ + if (_FP_FRAC_GE_4 (X, T)) \ + { \ + S##_f[0] = T##_f[0] + (q); \ + S##_f[1] += (T##_f[0] > S##_f[0]); \ + S##_f[2] += (T##_f[1] > S##_f[1]); \ + S##_f[3] += (T##_f[2] > S##_f[2]); \ + _FP_FRAC_DEC_4 (X, T); \ + R##_f[0] += (q); \ + } \ + _FP_FRAC_SLL_4 (X, 1); \ + (q) >>= 1; \ + } \ + if (!_FP_FRAC_ZEROP_4 (X)) \ + { \ + if (_FP_FRAC_GT_4 (X, S)) \ + R##_f[0] |= _FP_WORK_ROUND; \ + R##_f[0] |= _FP_WORK_STICKY; \ + } \ + } \ + while (0) + + +/* Internals. */ + +#define __FP_FRAC_SET_4(X, I3, I2, I1, I0) \ + (X##_f[3] = I3, X##_f[2] = I2, X##_f[1] = I1, X##_f[0] = I0) + +#ifndef __FP_FRAC_ADD_3 +# define __FP_FRAC_ADD_3(r2, r1, r0, x2, x1, x0, y2, y1, y0) \ + do \ + { \ + _FP_W_TYPE __FP_FRAC_ADD_3_c1, __FP_FRAC_ADD_3_c2; \ + r0 = x0 + y0; \ + __FP_FRAC_ADD_3_c1 = r0 < x0; \ + r1 = x1 + y1; \ + __FP_FRAC_ADD_3_c2 = r1 < x1; \ + r1 += __FP_FRAC_ADD_3_c1; \ + __FP_FRAC_ADD_3_c2 |= r1 < __FP_FRAC_ADD_3_c1; \ + r2 = x2 + y2 + __FP_FRAC_ADD_3_c2; \ + } \ + while (0) +#endif + +#ifndef __FP_FRAC_ADD_4 +# define __FP_FRAC_ADD_4(r3, r2, r1, r0, x3, x2, x1, x0, y3, y2, y1, y0) \ + do \ + { \ + _FP_W_TYPE __FP_FRAC_ADD_4_c1, __FP_FRAC_ADD_4_c2; \ + _FP_W_TYPE __FP_FRAC_ADD_4_c3; \ + r0 = x0 + y0; \ + __FP_FRAC_ADD_4_c1 = r0 < x0; \ + r1 = x1 + y1; \ + __FP_FRAC_ADD_4_c2 = r1 < x1; \ + r1 += __FP_FRAC_ADD_4_c1; \ + __FP_FRAC_ADD_4_c2 |= r1 < __FP_FRAC_ADD_4_c1; \ + r2 = x2 + y2; \ + __FP_FRAC_ADD_4_c3 = r2 < x2; \ + r2 += __FP_FRAC_ADD_4_c2; \ + __FP_FRAC_ADD_4_c3 |= r2 < __FP_FRAC_ADD_4_c2; \ + r3 = x3 + y3 + __FP_FRAC_ADD_4_c3; \ + } \ + while (0) +#endif + +#ifndef __FP_FRAC_SUB_3 +# define __FP_FRAC_SUB_3(r2, r1, r0, x2, x1, x0, y2, y1, y0) \ + do \ + { \ + _FP_W_TYPE __FP_FRAC_SUB_3_c1, __FP_FRAC_SUB_3_c2; \ + r0 = x0 - y0; \ + __FP_FRAC_SUB_3_c1 = r0 > x0; \ + r1 = x1 - y1; \ + __FP_FRAC_SUB_3_c2 = r1 > x1; \ + r1 -= __FP_FRAC_SUB_3_c1; \ + __FP_FRAC_SUB_3_c2 |= __FP_FRAC_SUB_3_c1 && (y1 == x1); \ + r2 = x2 - y2 - __FP_FRAC_SUB_3_c2; \ + } \ + while (0) +#endif + +#ifndef __FP_FRAC_SUB_4 +# define __FP_FRAC_SUB_4(r3, r2, r1, r0, x3, x2, x1, x0, y3, y2, y1, y0) \ + do \ + { \ + _FP_W_TYPE __FP_FRAC_SUB_4_c1, __FP_FRAC_SUB_4_c2; \ + _FP_W_TYPE __FP_FRAC_SUB_4_c3; \ + r0 = x0 - y0; \ + __FP_FRAC_SUB_4_c1 = r0 > x0; \ + r1 = x1 - y1; \ + __FP_FRAC_SUB_4_c2 = r1 > x1; \ + r1 -= __FP_FRAC_SUB_4_c1; \ + __FP_FRAC_SUB_4_c2 |= __FP_FRAC_SUB_4_c1 && (y1 == x1); \ + r2 = x2 - y2; \ + __FP_FRAC_SUB_4_c3 = r2 > x2; \ + r2 -= __FP_FRAC_SUB_4_c2; \ + __FP_FRAC_SUB_4_c3 |= __FP_FRAC_SUB_4_c2 && (y2 == x2); \ + r3 = x3 - y3 - __FP_FRAC_SUB_4_c3; \ + } \ + while (0) +#endif + +#ifndef __FP_FRAC_DEC_3 +# define __FP_FRAC_DEC_3(x2, x1, x0, y2, y1, y0) \ + do \ + { \ + UWtype __FP_FRAC_DEC_3_t0, __FP_FRAC_DEC_3_t1; \ + UWtype __FP_FRAC_DEC_3_t2; \ + __FP_FRAC_DEC_3_t0 = x0; \ + __FP_FRAC_DEC_3_t1 = x1; \ + __FP_FRAC_DEC_3_t2 = x2; \ + __FP_FRAC_SUB_3 (x2, x1, x0, __FP_FRAC_DEC_3_t2, \ + __FP_FRAC_DEC_3_t1, __FP_FRAC_DEC_3_t0, \ + y2, y1, y0); \ + } \ + while (0) +#endif + +#ifndef __FP_FRAC_DEC_4 +# define __FP_FRAC_DEC_4(x3, x2, x1, x0, y3, y2, y1, y0) \ + do \ + { \ + UWtype __FP_FRAC_DEC_4_t0, __FP_FRAC_DEC_4_t1; \ + UWtype __FP_FRAC_DEC_4_t2, __FP_FRAC_DEC_4_t3; \ + __FP_FRAC_DEC_4_t0 = x0; \ + __FP_FRAC_DEC_4_t1 = x1; \ + __FP_FRAC_DEC_4_t2 = x2; \ + __FP_FRAC_DEC_4_t3 = x3; \ + __FP_FRAC_SUB_4 (x3, x2, x1, x0, __FP_FRAC_DEC_4_t3, \ + __FP_FRAC_DEC_4_t2, __FP_FRAC_DEC_4_t1, \ + __FP_FRAC_DEC_4_t0, y3, y2, y1, y0); \ + } \ + while (0) +#endif + +#ifndef __FP_FRAC_ADDI_4 +# define __FP_FRAC_ADDI_4(x3, x2, x1, x0, i) \ + do \ + { \ + UWtype __FP_FRAC_ADDI_4_t; \ + __FP_FRAC_ADDI_4_t = ((x0 += i) < i); \ + x1 += __FP_FRAC_ADDI_4_t; \ + __FP_FRAC_ADDI_4_t = (x1 < __FP_FRAC_ADDI_4_t); \ + x2 += __FP_FRAC_ADDI_4_t; \ + __FP_FRAC_ADDI_4_t = (x2 < __FP_FRAC_ADDI_4_t); \ + x3 += __FP_FRAC_ADDI_4_t; \ + } \ + while (0) +#endif + +/* Convert FP values between word sizes. This appears to be more + complicated than I'd have expected it to be, so these might be + wrong... These macros are in any case somewhat bogus because they + use information about what various FRAC_n variables look like + internally [eg, that 2 word vars are X_f0 and x_f1]. But so do + the ones in op-2.h and op-1.h. */ +#define _FP_FRAC_COPY_1_4(D, S) (D##_f = S##_f[0]) + +#define _FP_FRAC_COPY_2_4(D, S) \ + do \ + { \ + D##_f0 = S##_f[0]; \ + D##_f1 = S##_f[1]; \ + } \ + while (0) + +/* Assembly/disassembly for converting to/from integral types. + No shifting or overflow handled here. */ +/* Put the FP value X into r, which is an integer of size rsize. */ +#define _FP_FRAC_ASSEMBLE_4(r, X, rsize) \ + do \ + { \ + if ((rsize) <= _FP_W_TYPE_SIZE) \ + (r) = X##_f[0]; \ + else if ((rsize) <= 2*_FP_W_TYPE_SIZE) \ + { \ + (r) = X##_f[1]; \ + (r) = ((rsize) <= _FP_W_TYPE_SIZE \ + ? 0 \ + : (r) << _FP_W_TYPE_SIZE); \ + (r) += X##_f[0]; \ + } \ + else \ + { \ + /* I'm feeling lazy so we deal with int == 3words \ + (implausible) and int == 4words as a single case. */ \ + (r) = X##_f[3]; \ + (r) = ((rsize) <= _FP_W_TYPE_SIZE \ + ? 0 \ + : (r) << _FP_W_TYPE_SIZE); \ + (r) += X##_f[2]; \ + (r) = ((rsize) <= _FP_W_TYPE_SIZE \ + ? 0 \ + : (r) << _FP_W_TYPE_SIZE); \ + (r) += X##_f[1]; \ + (r) = ((rsize) <= _FP_W_TYPE_SIZE \ + ? 0 \ + : (r) << _FP_W_TYPE_SIZE); \ + (r) += X##_f[0]; \ + } \ + } \ + while (0) + +/* "No disassemble Number Five!" */ +/* Move an integer of size rsize into X's fractional part. We rely on + the _f[] array consisting of words of size _FP_W_TYPE_SIZE to avoid + having to mask the values we store into it. */ +#define _FP_FRAC_DISASSEMBLE_4(X, r, rsize) \ + do \ + { \ + X##_f[0] = (r); \ + X##_f[1] = ((rsize) <= _FP_W_TYPE_SIZE \ + ? 0 \ + : (r) >> _FP_W_TYPE_SIZE); \ + X##_f[2] = ((rsize) <= 2*_FP_W_TYPE_SIZE \ + ? 0 \ + : (r) >> 2*_FP_W_TYPE_SIZE); \ + X##_f[3] = ((rsize) <= 3*_FP_W_TYPE_SIZE \ + ? 0 \ + : (r) >> 3*_FP_W_TYPE_SIZE); \ + } \ + while (0) + +#define _FP_FRAC_COPY_4_1(D, S) \ + do \ + { \ + D##_f[0] = S##_f; \ + D##_f[1] = D##_f[2] = D##_f[3] = 0; \ + } \ + while (0) + +#define _FP_FRAC_COPY_4_2(D, S) \ + do \ + { \ + D##_f[0] = S##_f0; \ + D##_f[1] = S##_f1; \ + D##_f[2] = D##_f[3] = 0; \ + } \ + while (0) + +#define _FP_FRAC_COPY_4_4(D, S) _FP_FRAC_COPY_4 (D, S) + +#endif /* !SOFT_FP_OP_4_H */ diff --git a/REORG.TODO/soft-fp/op-8.h b/REORG.TODO/soft-fp/op-8.h new file mode 100644 index 0000000000..1f424e102d --- /dev/null +++ b/REORG.TODO/soft-fp/op-8.h @@ -0,0 +1,150 @@ +/* Software floating-point emulation. + Basic eight-word fraction declaration and manipulation. + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com), + Jakub Jelinek (jj@ultra.linux.cz) and + Peter Maydell (pmaydell@chiark.greenend.org.uk). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#ifndef SOFT_FP_OP_8_H +#define SOFT_FP_OP_8_H 1 + +/* We need just a few things from here for op-4, if we ever need some + other macros, they can be added. */ +#define _FP_FRAC_DECL_8(X) _FP_W_TYPE X##_f[8] +#define _FP_FRAC_HIGH_8(X) (X##_f[7]) +#define _FP_FRAC_LOW_8(X) (X##_f[0]) +#define _FP_FRAC_WORD_8(X, w) (X##_f[w]) + +#define _FP_FRAC_SLL_8(X, N) \ + do \ + { \ + _FP_I_TYPE _FP_FRAC_SLL_8_up, _FP_FRAC_SLL_8_down; \ + _FP_I_TYPE _FP_FRAC_SLL_8_skip, _FP_FRAC_SLL_8_i; \ + _FP_FRAC_SLL_8_skip = (N) / _FP_W_TYPE_SIZE; \ + _FP_FRAC_SLL_8_up = (N) % _FP_W_TYPE_SIZE; \ + _FP_FRAC_SLL_8_down = _FP_W_TYPE_SIZE - _FP_FRAC_SLL_8_up; \ + if (!_FP_FRAC_SLL_8_up) \ + for (_FP_FRAC_SLL_8_i = 7; \ + _FP_FRAC_SLL_8_i >= _FP_FRAC_SLL_8_skip; \ + --_FP_FRAC_SLL_8_i) \ + X##_f[_FP_FRAC_SLL_8_i] \ + = X##_f[_FP_FRAC_SLL_8_i-_FP_FRAC_SLL_8_skip]; \ + else \ + { \ + for (_FP_FRAC_SLL_8_i = 7; \ + _FP_FRAC_SLL_8_i > _FP_FRAC_SLL_8_skip; \ + --_FP_FRAC_SLL_8_i) \ + X##_f[_FP_FRAC_SLL_8_i] \ + = ((X##_f[_FP_FRAC_SLL_8_i-_FP_FRAC_SLL_8_skip] \ + << _FP_FRAC_SLL_8_up) \ + | (X##_f[_FP_FRAC_SLL_8_i-_FP_FRAC_SLL_8_skip-1] \ + >> _FP_FRAC_SLL_8_down)); \ + X##_f[_FP_FRAC_SLL_8_i--] = X##_f[0] << _FP_FRAC_SLL_8_up; \ + } \ + for (; _FP_FRAC_SLL_8_i >= 0; --_FP_FRAC_SLL_8_i) \ + X##_f[_FP_FRAC_SLL_8_i] = 0; \ + } \ + while (0) + +#define _FP_FRAC_SRL_8(X, N) \ + do \ + { \ + _FP_I_TYPE _FP_FRAC_SRL_8_up, _FP_FRAC_SRL_8_down; \ + _FP_I_TYPE _FP_FRAC_SRL_8_skip, _FP_FRAC_SRL_8_i; \ + _FP_FRAC_SRL_8_skip = (N) / _FP_W_TYPE_SIZE; \ + _FP_FRAC_SRL_8_down = (N) % _FP_W_TYPE_SIZE; \ + _FP_FRAC_SRL_8_up = _FP_W_TYPE_SIZE - _FP_FRAC_SRL_8_down; \ + if (!_FP_FRAC_SRL_8_down) \ + for (_FP_FRAC_SRL_8_i = 0; \ + _FP_FRAC_SRL_8_i <= 7-_FP_FRAC_SRL_8_skip; \ + ++_FP_FRAC_SRL_8_i) \ + X##_f[_FP_FRAC_SRL_8_i] \ + = X##_f[_FP_FRAC_SRL_8_i+_FP_FRAC_SRL_8_skip]; \ + else \ + { \ + for (_FP_FRAC_SRL_8_i = 0; \ + _FP_FRAC_SRL_8_i < 7-_FP_FRAC_SRL_8_skip; \ + ++_FP_FRAC_SRL_8_i) \ + X##_f[_FP_FRAC_SRL_8_i] \ + = ((X##_f[_FP_FRAC_SRL_8_i+_FP_FRAC_SRL_8_skip] \ + >> _FP_FRAC_SRL_8_down) \ + | (X##_f[_FP_FRAC_SRL_8_i+_FP_FRAC_SRL_8_skip+1] \ + << _FP_FRAC_SRL_8_up)); \ + X##_f[_FP_FRAC_SRL_8_i++] = X##_f[7] >> _FP_FRAC_SRL_8_down; \ + } \ + for (; _FP_FRAC_SRL_8_i < 8; ++_FP_FRAC_SRL_8_i) \ + X##_f[_FP_FRAC_SRL_8_i] = 0; \ + } \ + while (0) + + +/* Right shift with sticky-lsb. + What this actually means is that we do a standard right-shift, + but that if any of the bits that fall off the right hand side + were one then we always set the LSbit. */ +#define _FP_FRAC_SRS_8(X, N, size) \ + do \ + { \ + _FP_I_TYPE _FP_FRAC_SRS_8_up, _FP_FRAC_SRS_8_down; \ + _FP_I_TYPE _FP_FRAC_SRS_8_skip, _FP_FRAC_SRS_8_i; \ + _FP_W_TYPE _FP_FRAC_SRS_8_s; \ + _FP_FRAC_SRS_8_skip = (N) / _FP_W_TYPE_SIZE; \ + _FP_FRAC_SRS_8_down = (N) % _FP_W_TYPE_SIZE; \ + _FP_FRAC_SRS_8_up = _FP_W_TYPE_SIZE - _FP_FRAC_SRS_8_down; \ + for (_FP_FRAC_SRS_8_s = _FP_FRAC_SRS_8_i = 0; \ + _FP_FRAC_SRS_8_i < _FP_FRAC_SRS_8_skip; \ + ++_FP_FRAC_SRS_8_i) \ + _FP_FRAC_SRS_8_s |= X##_f[_FP_FRAC_SRS_8_i]; \ + if (!_FP_FRAC_SRS_8_down) \ + for (_FP_FRAC_SRS_8_i = 0; \ + _FP_FRAC_SRS_8_i <= 7-_FP_FRAC_SRS_8_skip; \ + ++_FP_FRAC_SRS_8_i) \ + X##_f[_FP_FRAC_SRS_8_i] \ + = X##_f[_FP_FRAC_SRS_8_i+_FP_FRAC_SRS_8_skip]; \ + else \ + { \ + _FP_FRAC_SRS_8_s \ + |= X##_f[_FP_FRAC_SRS_8_i] << _FP_FRAC_SRS_8_up; \ + for (_FP_FRAC_SRS_8_i = 0; \ + _FP_FRAC_SRS_8_i < 7-_FP_FRAC_SRS_8_skip; \ + ++_FP_FRAC_SRS_8_i) \ + X##_f[_FP_FRAC_SRS_8_i] \ + = ((X##_f[_FP_FRAC_SRS_8_i+_FP_FRAC_SRS_8_skip] \ + >> _FP_FRAC_SRS_8_down) \ + | (X##_f[_FP_FRAC_SRS_8_i+_FP_FRAC_SRS_8_skip+1] \ + << _FP_FRAC_SRS_8_up)); \ + X##_f[_FP_FRAC_SRS_8_i++] = X##_f[7] >> _FP_FRAC_SRS_8_down; \ + } \ + for (; _FP_FRAC_SRS_8_i < 8; ++_FP_FRAC_SRS_8_i) \ + X##_f[_FP_FRAC_SRS_8_i] = 0; \ + /* Don't fix the LSB until the very end when we're sure f[0] is \ + stable. */ \ + X##_f[0] |= (_FP_FRAC_SRS_8_s != 0); \ + } \ + while (0) + +#endif /* !SOFT_FP_OP_8_H */ diff --git a/REORG.TODO/soft-fp/op-common.h b/REORG.TODO/soft-fp/op-common.h new file mode 100644 index 0000000000..f52194ecd1 --- /dev/null +++ b/REORG.TODO/soft-fp/op-common.h @@ -0,0 +1,2134 @@ +/* Software floating-point emulation. Common operations. + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com), + Jakub Jelinek (jj@ultra.linux.cz), + David S. Miller (davem@redhat.com) and + Peter Maydell (pmaydell@chiark.greenend.org.uk). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#ifndef SOFT_FP_OP_COMMON_H +#define SOFT_FP_OP_COMMON_H 1 + +#define _FP_DECL(wc, X) \ + _FP_I_TYPE X##_c __attribute__ ((unused)) _FP_ZERO_INIT; \ + _FP_I_TYPE X##_s __attribute__ ((unused)) _FP_ZERO_INIT; \ + _FP_I_TYPE X##_e __attribute__ ((unused)) _FP_ZERO_INIT; \ + _FP_FRAC_DECL_##wc (X) + +/* Test whether the qNaN bit denotes a signaling NaN. */ +#define _FP_FRAC_SNANP(fs, X) \ + ((_FP_QNANNEGATEDP) \ + ? (_FP_FRAC_HIGH_RAW_##fs (X) & _FP_QNANBIT_##fs) \ + : !(_FP_FRAC_HIGH_RAW_##fs (X) & _FP_QNANBIT_##fs)) +#define _FP_FRAC_SNANP_SEMIRAW(fs, X) \ + ((_FP_QNANNEGATEDP) \ + ? (_FP_FRAC_HIGH_##fs (X) & _FP_QNANBIT_SH_##fs) \ + : !(_FP_FRAC_HIGH_##fs (X) & _FP_QNANBIT_SH_##fs)) + +/* Finish truly unpacking a native fp value by classifying the kind + of fp value and normalizing both the exponent and the fraction. */ + +#define _FP_UNPACK_CANONICAL(fs, wc, X) \ + do \ + { \ + switch (X##_e) \ + { \ + default: \ + _FP_FRAC_HIGH_RAW_##fs (X) |= _FP_IMPLBIT_##fs; \ + _FP_FRAC_SLL_##wc (X, _FP_WORKBITS); \ + X##_e -= _FP_EXPBIAS_##fs; \ + X##_c = FP_CLS_NORMAL; \ + break; \ + \ + case 0: \ + if (_FP_FRAC_ZEROP_##wc (X)) \ + X##_c = FP_CLS_ZERO; \ + else if (FP_DENORM_ZERO) \ + { \ + X##_c = FP_CLS_ZERO; \ + _FP_FRAC_SET_##wc (X, _FP_ZEROFRAC_##wc); \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + } \ + else \ + { \ + /* A denormalized number. */ \ + _FP_I_TYPE _FP_UNPACK_CANONICAL_shift; \ + _FP_FRAC_CLZ_##wc (_FP_UNPACK_CANONICAL_shift, \ + X); \ + _FP_UNPACK_CANONICAL_shift -= _FP_FRACXBITS_##fs; \ + _FP_FRAC_SLL_##wc (X, (_FP_UNPACK_CANONICAL_shift \ + + _FP_WORKBITS)); \ + X##_e -= (_FP_EXPBIAS_##fs - 1 \ + + _FP_UNPACK_CANONICAL_shift); \ + X##_c = FP_CLS_NORMAL; \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + } \ + break; \ + \ + case _FP_EXPMAX_##fs: \ + if (_FP_FRAC_ZEROP_##wc (X)) \ + X##_c = FP_CLS_INF; \ + else \ + { \ + X##_c = FP_CLS_NAN; \ + /* Check for signaling NaN. */ \ + if (_FP_FRAC_SNANP (fs, X)) \ + FP_SET_EXCEPTION (FP_EX_INVALID \ + | FP_EX_INVALID_SNAN); \ + } \ + break; \ + } \ + } \ + while (0) + +/* Finish unpacking an fp value in semi-raw mode: the mantissa is + shifted by _FP_WORKBITS but the implicit MSB is not inserted and + other classification is not done. */ +#define _FP_UNPACK_SEMIRAW(fs, wc, X) _FP_FRAC_SLL_##wc (X, _FP_WORKBITS) + +/* Check whether a raw or semi-raw input value should be flushed to + zero, and flush it to zero if so. */ +#define _FP_CHECK_FLUSH_ZERO(fs, wc, X) \ + do \ + { \ + if (FP_DENORM_ZERO \ + && X##_e == 0 \ + && !_FP_FRAC_ZEROP_##wc (X)) \ + { \ + _FP_FRAC_SET_##wc (X, _FP_ZEROFRAC_##wc); \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + } \ + } \ + while (0) + +/* A semi-raw value has overflowed to infinity. Adjust the mantissa + and exponent appropriately. */ +#define _FP_OVERFLOW_SEMIRAW(fs, wc, X) \ + do \ + { \ + if (FP_ROUNDMODE == FP_RND_NEAREST \ + || (FP_ROUNDMODE == FP_RND_PINF && !X##_s) \ + || (FP_ROUNDMODE == FP_RND_MINF && X##_s)) \ + { \ + X##_e = _FP_EXPMAX_##fs; \ + _FP_FRAC_SET_##wc (X, _FP_ZEROFRAC_##wc); \ + } \ + else \ + { \ + X##_e = _FP_EXPMAX_##fs - 1; \ + _FP_FRAC_SET_##wc (X, _FP_MAXFRAC_##wc); \ + } \ + FP_SET_EXCEPTION (FP_EX_INEXACT); \ + FP_SET_EXCEPTION (FP_EX_OVERFLOW); \ + } \ + while (0) + +/* Check for a semi-raw value being a signaling NaN and raise the + invalid exception if so. */ +#define _FP_CHECK_SIGNAN_SEMIRAW(fs, wc, X) \ + do \ + { \ + if (X##_e == _FP_EXPMAX_##fs \ + && !_FP_FRAC_ZEROP_##wc (X) \ + && _FP_FRAC_SNANP_SEMIRAW (fs, X)) \ + FP_SET_EXCEPTION (FP_EX_INVALID | FP_EX_INVALID_SNAN); \ + } \ + while (0) + +/* Choose a NaN result from an operation on two semi-raw NaN + values. */ +#define _FP_CHOOSENAN_SEMIRAW(fs, wc, R, X, Y, OP) \ + do \ + { \ + /* _FP_CHOOSENAN expects raw values, so shift as required. */ \ + _FP_FRAC_SRL_##wc (X, _FP_WORKBITS); \ + _FP_FRAC_SRL_##wc (Y, _FP_WORKBITS); \ + _FP_CHOOSENAN (fs, wc, R, X, Y, OP); \ + _FP_FRAC_SLL_##wc (R, _FP_WORKBITS); \ + } \ + while (0) + +/* Make the fractional part a quiet NaN, preserving the payload + if possible, otherwise make it the canonical quiet NaN and set + the sign bit accordingly. */ +#define _FP_SETQNAN(fs, wc, X) \ + do \ + { \ + if (_FP_QNANNEGATEDP) \ + { \ + _FP_FRAC_HIGH_RAW_##fs (X) &= _FP_QNANBIT_##fs - 1; \ + if (_FP_FRAC_ZEROP_##wc (X)) \ + { \ + X##_s = _FP_NANSIGN_##fs; \ + _FP_FRAC_SET_##wc (X, _FP_NANFRAC_##fs); \ + } \ + } \ + else \ + _FP_FRAC_HIGH_RAW_##fs (X) |= _FP_QNANBIT_##fs; \ + } \ + while (0) +#define _FP_SETQNAN_SEMIRAW(fs, wc, X) \ + do \ + { \ + if (_FP_QNANNEGATEDP) \ + { \ + _FP_FRAC_HIGH_##fs (X) &= _FP_QNANBIT_SH_##fs - 1; \ + if (_FP_FRAC_ZEROP_##wc (X)) \ + { \ + X##_s = _FP_NANSIGN_##fs; \ + _FP_FRAC_SET_##wc (X, _FP_NANFRAC_##fs); \ + _FP_FRAC_SLL_##wc (X, _FP_WORKBITS); \ + } \ + } \ + else \ + _FP_FRAC_HIGH_##fs (X) |= _FP_QNANBIT_SH_##fs; \ + } \ + while (0) + +/* Test whether a biased exponent is normal (not zero or maximum). */ +#define _FP_EXP_NORMAL(fs, wc, X) (((X##_e + 1) & _FP_EXPMAX_##fs) > 1) + +/* Prepare to pack an fp value in semi-raw mode: the mantissa is + rounded and shifted right, with the rounding possibly increasing + the exponent (including changing a finite value to infinity). */ +#define _FP_PACK_SEMIRAW(fs, wc, X) \ + do \ + { \ + int _FP_PACK_SEMIRAW_is_tiny \ + = X##_e == 0 && !_FP_FRAC_ZEROP_##wc (X); \ + if (_FP_TININESS_AFTER_ROUNDING \ + && _FP_PACK_SEMIRAW_is_tiny) \ + { \ + FP_DECL_##fs (_FP_PACK_SEMIRAW_T); \ + _FP_FRAC_COPY_##wc (_FP_PACK_SEMIRAW_T, X); \ + _FP_PACK_SEMIRAW_T##_s = X##_s; \ + _FP_PACK_SEMIRAW_T##_e = X##_e; \ + _FP_FRAC_SLL_##wc (_FP_PACK_SEMIRAW_T, 1); \ + _FP_ROUND (wc, _FP_PACK_SEMIRAW_T); \ + if (_FP_FRAC_OVERP_##wc (fs, _FP_PACK_SEMIRAW_T)) \ + _FP_PACK_SEMIRAW_is_tiny = 0; \ + } \ + _FP_ROUND (wc, X); \ + if (_FP_PACK_SEMIRAW_is_tiny) \ + { \ + if ((FP_CUR_EXCEPTIONS & FP_EX_INEXACT) \ + || (FP_TRAPPING_EXCEPTIONS & FP_EX_UNDERFLOW)) \ + FP_SET_EXCEPTION (FP_EX_UNDERFLOW); \ + } \ + if (_FP_FRAC_HIGH_##fs (X) \ + & (_FP_OVERFLOW_##fs >> 1)) \ + { \ + _FP_FRAC_HIGH_##fs (X) &= ~(_FP_OVERFLOW_##fs >> 1); \ + X##_e++; \ + if (X##_e == _FP_EXPMAX_##fs) \ + _FP_OVERFLOW_SEMIRAW (fs, wc, X); \ + } \ + _FP_FRAC_SRL_##wc (X, _FP_WORKBITS); \ + if (X##_e == _FP_EXPMAX_##fs && !_FP_FRAC_ZEROP_##wc (X)) \ + { \ + if (!_FP_KEEPNANFRACP) \ + { \ + _FP_FRAC_SET_##wc (X, _FP_NANFRAC_##fs); \ + X##_s = _FP_NANSIGN_##fs; \ + } \ + else \ + _FP_SETQNAN (fs, wc, X); \ + } \ + } \ + while (0) + +/* Before packing the bits back into the native fp result, take care + of such mundane things as rounding and overflow. Also, for some + kinds of fp values, the original parts may not have been fully + extracted -- but that is ok, we can regenerate them now. */ + +#define _FP_PACK_CANONICAL(fs, wc, X) \ + do \ + { \ + switch (X##_c) \ + { \ + case FP_CLS_NORMAL: \ + X##_e += _FP_EXPBIAS_##fs; \ + if (X##_e > 0) \ + { \ + _FP_ROUND (wc, X); \ + if (_FP_FRAC_OVERP_##wc (fs, X)) \ + { \ + _FP_FRAC_CLEAR_OVERP_##wc (fs, X); \ + X##_e++; \ + } \ + _FP_FRAC_SRL_##wc (X, _FP_WORKBITS); \ + if (X##_e >= _FP_EXPMAX_##fs) \ + { \ + /* Overflow. */ \ + switch (FP_ROUNDMODE) \ + { \ + case FP_RND_NEAREST: \ + X##_c = FP_CLS_INF; \ + break; \ + case FP_RND_PINF: \ + if (!X##_s) \ + X##_c = FP_CLS_INF; \ + break; \ + case FP_RND_MINF: \ + if (X##_s) \ + X##_c = FP_CLS_INF; \ + break; \ + } \ + if (X##_c == FP_CLS_INF) \ + { \ + /* Overflow to infinity. */ \ + X##_e = _FP_EXPMAX_##fs; \ + _FP_FRAC_SET_##wc (X, _FP_ZEROFRAC_##wc); \ + } \ + else \ + { \ + /* Overflow to maximum normal. */ \ + X##_e = _FP_EXPMAX_##fs - 1; \ + _FP_FRAC_SET_##wc (X, _FP_MAXFRAC_##wc); \ + } \ + FP_SET_EXCEPTION (FP_EX_OVERFLOW); \ + FP_SET_EXCEPTION (FP_EX_INEXACT); \ + } \ + } \ + else \ + { \ + /* We've got a denormalized number. */ \ + int _FP_PACK_CANONICAL_is_tiny = 1; \ + if (_FP_TININESS_AFTER_ROUNDING && X##_e == 0) \ + { \ + FP_DECL_##fs (_FP_PACK_CANONICAL_T); \ + _FP_FRAC_COPY_##wc (_FP_PACK_CANONICAL_T, X); \ + _FP_PACK_CANONICAL_T##_s = X##_s; \ + _FP_PACK_CANONICAL_T##_e = X##_e; \ + _FP_ROUND (wc, _FP_PACK_CANONICAL_T); \ + if (_FP_FRAC_OVERP_##wc (fs, _FP_PACK_CANONICAL_T)) \ + _FP_PACK_CANONICAL_is_tiny = 0; \ + } \ + X##_e = -X##_e + 1; \ + if (X##_e <= _FP_WFRACBITS_##fs) \ + { \ + _FP_FRAC_SRS_##wc (X, X##_e, _FP_WFRACBITS_##fs); \ + _FP_ROUND (wc, X); \ + if (_FP_FRAC_HIGH_##fs (X) \ + & (_FP_OVERFLOW_##fs >> 1)) \ + { \ + X##_e = 1; \ + _FP_FRAC_SET_##wc (X, _FP_ZEROFRAC_##wc); \ + FP_SET_EXCEPTION (FP_EX_INEXACT); \ + } \ + else \ + { \ + X##_e = 0; \ + _FP_FRAC_SRL_##wc (X, _FP_WORKBITS); \ + } \ + if (_FP_PACK_CANONICAL_is_tiny \ + && ((FP_CUR_EXCEPTIONS & FP_EX_INEXACT) \ + || (FP_TRAPPING_EXCEPTIONS \ + & FP_EX_UNDERFLOW))) \ + FP_SET_EXCEPTION (FP_EX_UNDERFLOW); \ + } \ + else \ + { \ + /* Underflow to zero. */ \ + X##_e = 0; \ + if (!_FP_FRAC_ZEROP_##wc (X)) \ + { \ + _FP_FRAC_SET_##wc (X, _FP_MINFRAC_##wc); \ + _FP_ROUND (wc, X); \ + _FP_FRAC_LOW_##wc (X) >>= (_FP_WORKBITS); \ + } \ + FP_SET_EXCEPTION (FP_EX_UNDERFLOW); \ + } \ + } \ + break; \ + \ + case FP_CLS_ZERO: \ + X##_e = 0; \ + _FP_FRAC_SET_##wc (X, _FP_ZEROFRAC_##wc); \ + break; \ + \ + case FP_CLS_INF: \ + X##_e = _FP_EXPMAX_##fs; \ + _FP_FRAC_SET_##wc (X, _FP_ZEROFRAC_##wc); \ + break; \ + \ + case FP_CLS_NAN: \ + X##_e = _FP_EXPMAX_##fs; \ + if (!_FP_KEEPNANFRACP) \ + { \ + _FP_FRAC_SET_##wc (X, _FP_NANFRAC_##fs); \ + X##_s = _FP_NANSIGN_##fs; \ + } \ + else \ + _FP_SETQNAN (fs, wc, X); \ + break; \ + } \ + } \ + while (0) + +/* This one accepts raw argument and not cooked, returns + 1 if X is a signaling NaN. */ +#define _FP_ISSIGNAN(fs, wc, X) \ + ({ \ + int _FP_ISSIGNAN_ret = 0; \ + if (X##_e == _FP_EXPMAX_##fs) \ + { \ + if (!_FP_FRAC_ZEROP_##wc (X) \ + && _FP_FRAC_SNANP (fs, X)) \ + _FP_ISSIGNAN_ret = 1; \ + } \ + _FP_ISSIGNAN_ret; \ + }) + + + + + +/* Addition on semi-raw values. */ +#define _FP_ADD_INTERNAL(fs, wc, R, X, Y, OP) \ + do \ + { \ + _FP_CHECK_FLUSH_ZERO (fs, wc, X); \ + _FP_CHECK_FLUSH_ZERO (fs, wc, Y); \ + if (X##_s == Y##_s) \ + { \ + /* Addition. */ \ + __label__ add1, add2, add3, add_done; \ + R##_s = X##_s; \ + int _FP_ADD_INTERNAL_ediff = X##_e - Y##_e; \ + if (_FP_ADD_INTERNAL_ediff > 0) \ + { \ + R##_e = X##_e; \ + if (Y##_e == 0) \ + { \ + /* Y is zero or denormalized. */ \ + if (_FP_FRAC_ZEROP_##wc (Y)) \ + { \ + _FP_CHECK_SIGNAN_SEMIRAW (fs, wc, X); \ + _FP_FRAC_COPY_##wc (R, X); \ + goto add_done; \ + } \ + else \ + { \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + _FP_ADD_INTERNAL_ediff--; \ + if (_FP_ADD_INTERNAL_ediff == 0) \ + { \ + _FP_FRAC_ADD_##wc (R, X, Y); \ + goto add3; \ + } \ + if (X##_e == _FP_EXPMAX_##fs) \ + { \ + _FP_CHECK_SIGNAN_SEMIRAW (fs, wc, X); \ + _FP_FRAC_COPY_##wc (R, X); \ + goto add_done; \ + } \ + goto add1; \ + } \ + } \ + else if (X##_e == _FP_EXPMAX_##fs) \ + { \ + /* X is NaN or Inf, Y is normal. */ \ + _FP_CHECK_SIGNAN_SEMIRAW (fs, wc, X); \ + _FP_FRAC_COPY_##wc (R, X); \ + goto add_done; \ + } \ + \ + /* Insert implicit MSB of Y. */ \ + _FP_FRAC_HIGH_##fs (Y) |= _FP_IMPLBIT_SH_##fs; \ + \ + add1: \ + /* Shift the mantissa of Y to the right \ + _FP_ADD_INTERNAL_EDIFF steps; remember to account \ + later for the implicit MSB of X. */ \ + if (_FP_ADD_INTERNAL_ediff <= _FP_WFRACBITS_##fs) \ + _FP_FRAC_SRS_##wc (Y, _FP_ADD_INTERNAL_ediff, \ + _FP_WFRACBITS_##fs); \ + else if (!_FP_FRAC_ZEROP_##wc (Y)) \ + _FP_FRAC_SET_##wc (Y, _FP_MINFRAC_##wc); \ + _FP_FRAC_ADD_##wc (R, X, Y); \ + } \ + else if (_FP_ADD_INTERNAL_ediff < 0) \ + { \ + _FP_ADD_INTERNAL_ediff = -_FP_ADD_INTERNAL_ediff; \ + R##_e = Y##_e; \ + if (X##_e == 0) \ + { \ + /* X is zero or denormalized. */ \ + if (_FP_FRAC_ZEROP_##wc (X)) \ + { \ + _FP_CHECK_SIGNAN_SEMIRAW (fs, wc, Y); \ + _FP_FRAC_COPY_##wc (R, Y); \ + goto add_done; \ + } \ + else \ + { \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + _FP_ADD_INTERNAL_ediff--; \ + if (_FP_ADD_INTERNAL_ediff == 0) \ + { \ + _FP_FRAC_ADD_##wc (R, Y, X); \ + goto add3; \ + } \ + if (Y##_e == _FP_EXPMAX_##fs) \ + { \ + _FP_CHECK_SIGNAN_SEMIRAW (fs, wc, Y); \ + _FP_FRAC_COPY_##wc (R, Y); \ + goto add_done; \ + } \ + goto add2; \ + } \ + } \ + else if (Y##_e == _FP_EXPMAX_##fs) \ + { \ + /* Y is NaN or Inf, X is normal. */ \ + _FP_CHECK_SIGNAN_SEMIRAW (fs, wc, Y); \ + _FP_FRAC_COPY_##wc (R, Y); \ + goto add_done; \ + } \ + \ + /* Insert implicit MSB of X. */ \ + _FP_FRAC_HIGH_##fs (X) |= _FP_IMPLBIT_SH_##fs; \ + \ + add2: \ + /* Shift the mantissa of X to the right \ + _FP_ADD_INTERNAL_EDIFF steps; remember to account \ + later for the implicit MSB of Y. */ \ + if (_FP_ADD_INTERNAL_ediff <= _FP_WFRACBITS_##fs) \ + _FP_FRAC_SRS_##wc (X, _FP_ADD_INTERNAL_ediff, \ + _FP_WFRACBITS_##fs); \ + else if (!_FP_FRAC_ZEROP_##wc (X)) \ + _FP_FRAC_SET_##wc (X, _FP_MINFRAC_##wc); \ + _FP_FRAC_ADD_##wc (R, Y, X); \ + } \ + else \ + { \ + /* _FP_ADD_INTERNAL_ediff == 0. */ \ + if (!_FP_EXP_NORMAL (fs, wc, X)) \ + { \ + if (X##_e == 0) \ + { \ + /* X and Y are zero or denormalized. */ \ + R##_e = 0; \ + if (_FP_FRAC_ZEROP_##wc (X)) \ + { \ + if (!_FP_FRAC_ZEROP_##wc (Y)) \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + _FP_FRAC_COPY_##wc (R, Y); \ + goto add_done; \ + } \ + else if (_FP_FRAC_ZEROP_##wc (Y)) \ + { \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + _FP_FRAC_COPY_##wc (R, X); \ + goto add_done; \ + } \ + else \ + { \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + _FP_FRAC_ADD_##wc (R, X, Y); \ + if (_FP_FRAC_HIGH_##fs (R) & _FP_IMPLBIT_SH_##fs) \ + { \ + /* Normalized result. */ \ + _FP_FRAC_HIGH_##fs (R) \ + &= ~(_FP_W_TYPE) _FP_IMPLBIT_SH_##fs; \ + R##_e = 1; \ + } \ + goto add_done; \ + } \ + } \ + else \ + { \ + /* X and Y are NaN or Inf. */ \ + _FP_CHECK_SIGNAN_SEMIRAW (fs, wc, X); \ + _FP_CHECK_SIGNAN_SEMIRAW (fs, wc, Y); \ + R##_e = _FP_EXPMAX_##fs; \ + if (_FP_FRAC_ZEROP_##wc (X)) \ + _FP_FRAC_COPY_##wc (R, Y); \ + else if (_FP_FRAC_ZEROP_##wc (Y)) \ + _FP_FRAC_COPY_##wc (R, X); \ + else \ + _FP_CHOOSENAN_SEMIRAW (fs, wc, R, X, Y, OP); \ + goto add_done; \ + } \ + } \ + /* The exponents of X and Y, both normal, are equal. The \ + implicit MSBs will always add to increase the \ + exponent. */ \ + _FP_FRAC_ADD_##wc (R, X, Y); \ + R##_e = X##_e + 1; \ + _FP_FRAC_SRS_##wc (R, 1, _FP_WFRACBITS_##fs); \ + if (R##_e == _FP_EXPMAX_##fs) \ + /* Overflow to infinity (depending on rounding mode). */ \ + _FP_OVERFLOW_SEMIRAW (fs, wc, R); \ + goto add_done; \ + } \ + add3: \ + if (_FP_FRAC_HIGH_##fs (R) & _FP_IMPLBIT_SH_##fs) \ + { \ + /* Overflow. */ \ + _FP_FRAC_HIGH_##fs (R) &= ~(_FP_W_TYPE) _FP_IMPLBIT_SH_##fs; \ + R##_e++; \ + _FP_FRAC_SRS_##wc (R, 1, _FP_WFRACBITS_##fs); \ + if (R##_e == _FP_EXPMAX_##fs) \ + /* Overflow to infinity (depending on rounding mode). */ \ + _FP_OVERFLOW_SEMIRAW (fs, wc, R); \ + } \ + add_done: ; \ + } \ + else \ + { \ + /* Subtraction. */ \ + __label__ sub1, sub2, sub3, norm, sub_done; \ + int _FP_ADD_INTERNAL_ediff = X##_e - Y##_e; \ + if (_FP_ADD_INTERNAL_ediff > 0) \ + { \ + R##_e = X##_e; \ + R##_s = X##_s; \ + if (Y##_e == 0) \ + { \ + /* Y is zero or denormalized. */ \ + if (_FP_FRAC_ZEROP_##wc (Y)) \ + { \ + _FP_CHECK_SIGNAN_SEMIRAW (fs, wc, X); \ + _FP_FRAC_COPY_##wc (R, X); \ + goto sub_done; \ + } \ + else \ + { \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + _FP_ADD_INTERNAL_ediff--; \ + if (_FP_ADD_INTERNAL_ediff == 0) \ + { \ + _FP_FRAC_SUB_##wc (R, X, Y); \ + goto sub3; \ + } \ + if (X##_e == _FP_EXPMAX_##fs) \ + { \ + _FP_CHECK_SIGNAN_SEMIRAW (fs, wc, X); \ + _FP_FRAC_COPY_##wc (R, X); \ + goto sub_done; \ + } \ + goto sub1; \ + } \ + } \ + else if (X##_e == _FP_EXPMAX_##fs) \ + { \ + /* X is NaN or Inf, Y is normal. */ \ + _FP_CHECK_SIGNAN_SEMIRAW (fs, wc, X); \ + _FP_FRAC_COPY_##wc (R, X); \ + goto sub_done; \ + } \ + \ + /* Insert implicit MSB of Y. */ \ + _FP_FRAC_HIGH_##fs (Y) |= _FP_IMPLBIT_SH_##fs; \ + \ + sub1: \ + /* Shift the mantissa of Y to the right \ + _FP_ADD_INTERNAL_EDIFF steps; remember to account \ + later for the implicit MSB of X. */ \ + if (_FP_ADD_INTERNAL_ediff <= _FP_WFRACBITS_##fs) \ + _FP_FRAC_SRS_##wc (Y, _FP_ADD_INTERNAL_ediff, \ + _FP_WFRACBITS_##fs); \ + else if (!_FP_FRAC_ZEROP_##wc (Y)) \ + _FP_FRAC_SET_##wc (Y, _FP_MINFRAC_##wc); \ + _FP_FRAC_SUB_##wc (R, X, Y); \ + } \ + else if (_FP_ADD_INTERNAL_ediff < 0) \ + { \ + _FP_ADD_INTERNAL_ediff = -_FP_ADD_INTERNAL_ediff; \ + R##_e = Y##_e; \ + R##_s = Y##_s; \ + if (X##_e == 0) \ + { \ + /* X is zero or denormalized. */ \ + if (_FP_FRAC_ZEROP_##wc (X)) \ + { \ + _FP_CHECK_SIGNAN_SEMIRAW (fs, wc, Y); \ + _FP_FRAC_COPY_##wc (R, Y); \ + goto sub_done; \ + } \ + else \ + { \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + _FP_ADD_INTERNAL_ediff--; \ + if (_FP_ADD_INTERNAL_ediff == 0) \ + { \ + _FP_FRAC_SUB_##wc (R, Y, X); \ + goto sub3; \ + } \ + if (Y##_e == _FP_EXPMAX_##fs) \ + { \ + _FP_CHECK_SIGNAN_SEMIRAW (fs, wc, Y); \ + _FP_FRAC_COPY_##wc (R, Y); \ + goto sub_done; \ + } \ + goto sub2; \ + } \ + } \ + else if (Y##_e == _FP_EXPMAX_##fs) \ + { \ + /* Y is NaN or Inf, X is normal. */ \ + _FP_CHECK_SIGNAN_SEMIRAW (fs, wc, Y); \ + _FP_FRAC_COPY_##wc (R, Y); \ + goto sub_done; \ + } \ + \ + /* Insert implicit MSB of X. */ \ + _FP_FRAC_HIGH_##fs (X) |= _FP_IMPLBIT_SH_##fs; \ + \ + sub2: \ + /* Shift the mantissa of X to the right \ + _FP_ADD_INTERNAL_EDIFF steps; remember to account \ + later for the implicit MSB of Y. */ \ + if (_FP_ADD_INTERNAL_ediff <= _FP_WFRACBITS_##fs) \ + _FP_FRAC_SRS_##wc (X, _FP_ADD_INTERNAL_ediff, \ + _FP_WFRACBITS_##fs); \ + else if (!_FP_FRAC_ZEROP_##wc (X)) \ + _FP_FRAC_SET_##wc (X, _FP_MINFRAC_##wc); \ + _FP_FRAC_SUB_##wc (R, Y, X); \ + } \ + else \ + { \ + /* ediff == 0. */ \ + if (!_FP_EXP_NORMAL (fs, wc, X)) \ + { \ + if (X##_e == 0) \ + { \ + /* X and Y are zero or denormalized. */ \ + R##_e = 0; \ + if (_FP_FRAC_ZEROP_##wc (X)) \ + { \ + _FP_FRAC_COPY_##wc (R, Y); \ + if (_FP_FRAC_ZEROP_##wc (Y)) \ + R##_s = (FP_ROUNDMODE == FP_RND_MINF); \ + else \ + { \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + R##_s = Y##_s; \ + } \ + goto sub_done; \ + } \ + else if (_FP_FRAC_ZEROP_##wc (Y)) \ + { \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + _FP_FRAC_COPY_##wc (R, X); \ + R##_s = X##_s; \ + goto sub_done; \ + } \ + else \ + { \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + _FP_FRAC_SUB_##wc (R, X, Y); \ + R##_s = X##_s; \ + if (_FP_FRAC_HIGH_##fs (R) & _FP_IMPLBIT_SH_##fs) \ + { \ + /* |X| < |Y|, negate result. */ \ + _FP_FRAC_SUB_##wc (R, Y, X); \ + R##_s = Y##_s; \ + } \ + else if (_FP_FRAC_ZEROP_##wc (R)) \ + R##_s = (FP_ROUNDMODE == FP_RND_MINF); \ + goto sub_done; \ + } \ + } \ + else \ + { \ + /* X and Y are NaN or Inf, of opposite signs. */ \ + _FP_CHECK_SIGNAN_SEMIRAW (fs, wc, X); \ + _FP_CHECK_SIGNAN_SEMIRAW (fs, wc, Y); \ + R##_e = _FP_EXPMAX_##fs; \ + if (_FP_FRAC_ZEROP_##wc (X)) \ + { \ + if (_FP_FRAC_ZEROP_##wc (Y)) \ + { \ + /* Inf - Inf. */ \ + R##_s = _FP_NANSIGN_##fs; \ + _FP_FRAC_SET_##wc (R, _FP_NANFRAC_##fs); \ + _FP_FRAC_SLL_##wc (R, _FP_WORKBITS); \ + FP_SET_EXCEPTION (FP_EX_INVALID \ + | FP_EX_INVALID_ISI); \ + } \ + else \ + { \ + /* Inf - NaN. */ \ + R##_s = Y##_s; \ + _FP_FRAC_COPY_##wc (R, Y); \ + } \ + } \ + else \ + { \ + if (_FP_FRAC_ZEROP_##wc (Y)) \ + { \ + /* NaN - Inf. */ \ + R##_s = X##_s; \ + _FP_FRAC_COPY_##wc (R, X); \ + } \ + else \ + { \ + /* NaN - NaN. */ \ + _FP_CHOOSENAN_SEMIRAW (fs, wc, R, X, Y, OP); \ + } \ + } \ + goto sub_done; \ + } \ + } \ + /* The exponents of X and Y, both normal, are equal. The \ + implicit MSBs cancel. */ \ + R##_e = X##_e; \ + _FP_FRAC_SUB_##wc (R, X, Y); \ + R##_s = X##_s; \ + if (_FP_FRAC_HIGH_##fs (R) & _FP_IMPLBIT_SH_##fs) \ + { \ + /* |X| < |Y|, negate result. */ \ + _FP_FRAC_SUB_##wc (R, Y, X); \ + R##_s = Y##_s; \ + } \ + else if (_FP_FRAC_ZEROP_##wc (R)) \ + { \ + R##_e = 0; \ + R##_s = (FP_ROUNDMODE == FP_RND_MINF); \ + goto sub_done; \ + } \ + goto norm; \ + } \ + sub3: \ + if (_FP_FRAC_HIGH_##fs (R) & _FP_IMPLBIT_SH_##fs) \ + { \ + int _FP_ADD_INTERNAL_diff; \ + /* Carry into most significant bit of larger one of X and Y, \ + canceling it; renormalize. */ \ + _FP_FRAC_HIGH_##fs (R) &= _FP_IMPLBIT_SH_##fs - 1; \ + norm: \ + _FP_FRAC_CLZ_##wc (_FP_ADD_INTERNAL_diff, R); \ + _FP_ADD_INTERNAL_diff -= _FP_WFRACXBITS_##fs; \ + _FP_FRAC_SLL_##wc (R, _FP_ADD_INTERNAL_diff); \ + if (R##_e <= _FP_ADD_INTERNAL_diff) \ + { \ + /* R is denormalized. */ \ + _FP_ADD_INTERNAL_diff \ + = _FP_ADD_INTERNAL_diff - R##_e + 1; \ + _FP_FRAC_SRS_##wc (R, _FP_ADD_INTERNAL_diff, \ + _FP_WFRACBITS_##fs); \ + R##_e = 0; \ + } \ + else \ + { \ + R##_e -= _FP_ADD_INTERNAL_diff; \ + _FP_FRAC_HIGH_##fs (R) &= ~(_FP_W_TYPE) _FP_IMPLBIT_SH_##fs; \ + } \ + } \ + sub_done: ; \ + } \ + } \ + while (0) + +#define _FP_ADD(fs, wc, R, X, Y) _FP_ADD_INTERNAL (fs, wc, R, X, Y, '+') +#define _FP_SUB(fs, wc, R, X, Y) \ + do \ + { \ + if (!(Y##_e == _FP_EXPMAX_##fs && !_FP_FRAC_ZEROP_##wc (Y))) \ + Y##_s ^= 1; \ + _FP_ADD_INTERNAL (fs, wc, R, X, Y, '-'); \ + } \ + while (0) + + +/* Main negation routine. The input value is raw. */ + +#define _FP_NEG(fs, wc, R, X) \ + do \ + { \ + _FP_FRAC_COPY_##wc (R, X); \ + R##_e = X##_e; \ + R##_s = 1 ^ X##_s; \ + } \ + while (0) + + +/* Main multiplication routine. The input values should be cooked. */ + +#define _FP_MUL(fs, wc, R, X, Y) \ + do \ + { \ + R##_s = X##_s ^ Y##_s; \ + R##_e = X##_e + Y##_e + 1; \ + switch (_FP_CLS_COMBINE (X##_c, Y##_c)) \ + { \ + case _FP_CLS_COMBINE (FP_CLS_NORMAL, FP_CLS_NORMAL): \ + R##_c = FP_CLS_NORMAL; \ + \ + _FP_MUL_MEAT_##fs (R, X, Y); \ + \ + if (_FP_FRAC_OVERP_##wc (fs, R)) \ + _FP_FRAC_SRS_##wc (R, 1, _FP_WFRACBITS_##fs); \ + else \ + R##_e--; \ + break; \ + \ + case _FP_CLS_COMBINE (FP_CLS_NAN, FP_CLS_NAN): \ + _FP_CHOOSENAN (fs, wc, R, X, Y, '*'); \ + break; \ + \ + case _FP_CLS_COMBINE (FP_CLS_NAN, FP_CLS_NORMAL): \ + case _FP_CLS_COMBINE (FP_CLS_NAN, FP_CLS_INF): \ + case _FP_CLS_COMBINE (FP_CLS_NAN, FP_CLS_ZERO): \ + R##_s = X##_s; \ + /* FALLTHRU */ \ + \ + case _FP_CLS_COMBINE (FP_CLS_INF, FP_CLS_INF): \ + case _FP_CLS_COMBINE (FP_CLS_INF, FP_CLS_NORMAL): \ + case _FP_CLS_COMBINE (FP_CLS_ZERO, FP_CLS_NORMAL): \ + case _FP_CLS_COMBINE (FP_CLS_ZERO, FP_CLS_ZERO): \ + _FP_FRAC_COPY_##wc (R, X); \ + R##_c = X##_c; \ + break; \ + \ + case _FP_CLS_COMBINE (FP_CLS_NORMAL, FP_CLS_NAN): \ + case _FP_CLS_COMBINE (FP_CLS_INF, FP_CLS_NAN): \ + case _FP_CLS_COMBINE (FP_CLS_ZERO, FP_CLS_NAN): \ + R##_s = Y##_s; \ + /* FALLTHRU */ \ + \ + case _FP_CLS_COMBINE (FP_CLS_NORMAL, FP_CLS_INF): \ + case _FP_CLS_COMBINE (FP_CLS_NORMAL, FP_CLS_ZERO): \ + _FP_FRAC_COPY_##wc (R, Y); \ + R##_c = Y##_c; \ + break; \ + \ + case _FP_CLS_COMBINE (FP_CLS_INF, FP_CLS_ZERO): \ + case _FP_CLS_COMBINE (FP_CLS_ZERO, FP_CLS_INF): \ + R##_s = _FP_NANSIGN_##fs; \ + R##_c = FP_CLS_NAN; \ + _FP_FRAC_SET_##wc (R, _FP_NANFRAC_##fs); \ + FP_SET_EXCEPTION (FP_EX_INVALID | FP_EX_INVALID_IMZ); \ + break; \ + \ + default: \ + _FP_UNREACHABLE; \ + } \ + } \ + while (0) + + +/* Fused multiply-add. The input values should be cooked. */ + +#define _FP_FMA(fs, wc, dwc, R, X, Y, Z) \ + do \ + { \ + __label__ done_fma; \ + FP_DECL_##fs (_FP_FMA_T); \ + _FP_FMA_T##_s = X##_s ^ Y##_s; \ + _FP_FMA_T##_e = X##_e + Y##_e + 1; \ + switch (_FP_CLS_COMBINE (X##_c, Y##_c)) \ + { \ + case _FP_CLS_COMBINE (FP_CLS_NORMAL, FP_CLS_NORMAL): \ + switch (Z##_c) \ + { \ + case FP_CLS_INF: \ + case FP_CLS_NAN: \ + R##_s = Z##_s; \ + _FP_FRAC_COPY_##wc (R, Z); \ + R##_c = Z##_c; \ + break; \ + \ + case FP_CLS_ZERO: \ + R##_c = FP_CLS_NORMAL; \ + R##_s = _FP_FMA_T##_s; \ + R##_e = _FP_FMA_T##_e; \ + \ + _FP_MUL_MEAT_##fs (R, X, Y); \ + \ + if (_FP_FRAC_OVERP_##wc (fs, R)) \ + _FP_FRAC_SRS_##wc (R, 1, _FP_WFRACBITS_##fs); \ + else \ + R##_e--; \ + break; \ + \ + case FP_CLS_NORMAL:; \ + _FP_FRAC_DECL_##dwc (_FP_FMA_TD); \ + _FP_FRAC_DECL_##dwc (_FP_FMA_ZD); \ + _FP_FRAC_DECL_##dwc (_FP_FMA_RD); \ + _FP_MUL_MEAT_DW_##fs (_FP_FMA_TD, X, Y); \ + R##_e = _FP_FMA_T##_e; \ + int _FP_FMA_tsh \ + = _FP_FRAC_HIGHBIT_DW_##dwc (fs, _FP_FMA_TD) == 0; \ + _FP_FMA_T##_e -= _FP_FMA_tsh; \ + int _FP_FMA_ediff = _FP_FMA_T##_e - Z##_e; \ + if (_FP_FMA_ediff >= 0) \ + { \ + int _FP_FMA_shift \ + = _FP_WFRACBITS_##fs - _FP_FMA_tsh - _FP_FMA_ediff; \ + if (_FP_FMA_shift <= -_FP_WFRACBITS_##fs) \ + _FP_FRAC_SET_##dwc (_FP_FMA_ZD, _FP_MINFRAC_##dwc); \ + else \ + { \ + _FP_FRAC_COPY_##dwc##_##wc (_FP_FMA_ZD, Z); \ + if (_FP_FMA_shift < 0) \ + _FP_FRAC_SRS_##dwc (_FP_FMA_ZD, -_FP_FMA_shift, \ + _FP_WFRACBITS_DW_##fs); \ + else if (_FP_FMA_shift > 0) \ + _FP_FRAC_SLL_##dwc (_FP_FMA_ZD, _FP_FMA_shift); \ + } \ + R##_s = _FP_FMA_T##_s; \ + if (_FP_FMA_T##_s == Z##_s) \ + _FP_FRAC_ADD_##dwc (_FP_FMA_RD, _FP_FMA_TD, \ + _FP_FMA_ZD); \ + else \ + { \ + _FP_FRAC_SUB_##dwc (_FP_FMA_RD, _FP_FMA_TD, \ + _FP_FMA_ZD); \ + if (_FP_FRAC_NEGP_##dwc (_FP_FMA_RD)) \ + { \ + R##_s = Z##_s; \ + _FP_FRAC_SUB_##dwc (_FP_FMA_RD, _FP_FMA_ZD, \ + _FP_FMA_TD); \ + } \ + } \ + } \ + else \ + { \ + R##_e = Z##_e; \ + R##_s = Z##_s; \ + _FP_FRAC_COPY_##dwc##_##wc (_FP_FMA_ZD, Z); \ + _FP_FRAC_SLL_##dwc (_FP_FMA_ZD, _FP_WFRACBITS_##fs); \ + int _FP_FMA_shift = -_FP_FMA_ediff - _FP_FMA_tsh; \ + if (_FP_FMA_shift >= _FP_WFRACBITS_DW_##fs) \ + _FP_FRAC_SET_##dwc (_FP_FMA_TD, _FP_MINFRAC_##dwc); \ + else if (_FP_FMA_shift > 0) \ + _FP_FRAC_SRS_##dwc (_FP_FMA_TD, _FP_FMA_shift, \ + _FP_WFRACBITS_DW_##fs); \ + if (Z##_s == _FP_FMA_T##_s) \ + _FP_FRAC_ADD_##dwc (_FP_FMA_RD, _FP_FMA_ZD, \ + _FP_FMA_TD); \ + else \ + _FP_FRAC_SUB_##dwc (_FP_FMA_RD, _FP_FMA_ZD, \ + _FP_FMA_TD); \ + } \ + if (_FP_FRAC_ZEROP_##dwc (_FP_FMA_RD)) \ + { \ + if (_FP_FMA_T##_s == Z##_s) \ + R##_s = Z##_s; \ + else \ + R##_s = (FP_ROUNDMODE == FP_RND_MINF); \ + _FP_FRAC_SET_##wc (R, _FP_ZEROFRAC_##wc); \ + R##_c = FP_CLS_ZERO; \ + } \ + else \ + { \ + int _FP_FMA_rlz; \ + _FP_FRAC_CLZ_##dwc (_FP_FMA_rlz, _FP_FMA_RD); \ + _FP_FMA_rlz -= _FP_WFRACXBITS_DW_##fs; \ + R##_e -= _FP_FMA_rlz; \ + int _FP_FMA_shift = _FP_WFRACBITS_##fs - _FP_FMA_rlz; \ + if (_FP_FMA_shift > 0) \ + _FP_FRAC_SRS_##dwc (_FP_FMA_RD, _FP_FMA_shift, \ + _FP_WFRACBITS_DW_##fs); \ + else if (_FP_FMA_shift < 0) \ + _FP_FRAC_SLL_##dwc (_FP_FMA_RD, -_FP_FMA_shift); \ + _FP_FRAC_COPY_##wc##_##dwc (R, _FP_FMA_RD); \ + R##_c = FP_CLS_NORMAL; \ + } \ + break; \ + } \ + goto done_fma; \ + \ + case _FP_CLS_COMBINE (FP_CLS_NAN, FP_CLS_NAN): \ + _FP_CHOOSENAN (fs, wc, _FP_FMA_T, X, Y, '*'); \ + break; \ + \ + case _FP_CLS_COMBINE (FP_CLS_NAN, FP_CLS_NORMAL): \ + case _FP_CLS_COMBINE (FP_CLS_NAN, FP_CLS_INF): \ + case _FP_CLS_COMBINE (FP_CLS_NAN, FP_CLS_ZERO): \ + _FP_FMA_T##_s = X##_s; \ + /* FALLTHRU */ \ + \ + case _FP_CLS_COMBINE (FP_CLS_INF, FP_CLS_INF): \ + case _FP_CLS_COMBINE (FP_CLS_INF, FP_CLS_NORMAL): \ + case _FP_CLS_COMBINE (FP_CLS_ZERO, FP_CLS_NORMAL): \ + case _FP_CLS_COMBINE (FP_CLS_ZERO, FP_CLS_ZERO): \ + _FP_FRAC_COPY_##wc (_FP_FMA_T, X); \ + _FP_FMA_T##_c = X##_c; \ + break; \ + \ + case _FP_CLS_COMBINE (FP_CLS_NORMAL, FP_CLS_NAN): \ + case _FP_CLS_COMBINE (FP_CLS_INF, FP_CLS_NAN): \ + case _FP_CLS_COMBINE (FP_CLS_ZERO, FP_CLS_NAN): \ + _FP_FMA_T##_s = Y##_s; \ + /* FALLTHRU */ \ + \ + case _FP_CLS_COMBINE (FP_CLS_NORMAL, FP_CLS_INF): \ + case _FP_CLS_COMBINE (FP_CLS_NORMAL, FP_CLS_ZERO): \ + _FP_FRAC_COPY_##wc (_FP_FMA_T, Y); \ + _FP_FMA_T##_c = Y##_c; \ + break; \ + \ + case _FP_CLS_COMBINE (FP_CLS_INF, FP_CLS_ZERO): \ + case _FP_CLS_COMBINE (FP_CLS_ZERO, FP_CLS_INF): \ + _FP_FMA_T##_s = _FP_NANSIGN_##fs; \ + _FP_FMA_T##_c = FP_CLS_NAN; \ + _FP_FRAC_SET_##wc (_FP_FMA_T, _FP_NANFRAC_##fs); \ + FP_SET_EXCEPTION (FP_EX_INVALID | FP_EX_INVALID_IMZ_FMA); \ + break; \ + \ + default: \ + _FP_UNREACHABLE; \ + } \ + \ + /* T = X * Y is zero, infinity or NaN. */ \ + switch (_FP_CLS_COMBINE (_FP_FMA_T##_c, Z##_c)) \ + { \ + case _FP_CLS_COMBINE (FP_CLS_NAN, FP_CLS_NAN): \ + _FP_CHOOSENAN (fs, wc, R, _FP_FMA_T, Z, '+'); \ + break; \ + \ + case _FP_CLS_COMBINE (FP_CLS_NAN, FP_CLS_NORMAL): \ + case _FP_CLS_COMBINE (FP_CLS_NAN, FP_CLS_INF): \ + case _FP_CLS_COMBINE (FP_CLS_NAN, FP_CLS_ZERO): \ + case _FP_CLS_COMBINE (FP_CLS_INF, FP_CLS_NORMAL): \ + case _FP_CLS_COMBINE (FP_CLS_INF, FP_CLS_ZERO): \ + R##_s = _FP_FMA_T##_s; \ + _FP_FRAC_COPY_##wc (R, _FP_FMA_T); \ + R##_c = _FP_FMA_T##_c; \ + break; \ + \ + case _FP_CLS_COMBINE (FP_CLS_INF, FP_CLS_NAN): \ + case _FP_CLS_COMBINE (FP_CLS_ZERO, FP_CLS_NAN): \ + case _FP_CLS_COMBINE (FP_CLS_ZERO, FP_CLS_NORMAL): \ + case _FP_CLS_COMBINE (FP_CLS_ZERO, FP_CLS_INF): \ + R##_s = Z##_s; \ + _FP_FRAC_COPY_##wc (R, Z); \ + R##_c = Z##_c; \ + R##_e = Z##_e; \ + break; \ + \ + case _FP_CLS_COMBINE (FP_CLS_INF, FP_CLS_INF): \ + if (_FP_FMA_T##_s == Z##_s) \ + { \ + R##_s = Z##_s; \ + _FP_FRAC_COPY_##wc (R, Z); \ + R##_c = Z##_c; \ + } \ + else \ + { \ + R##_s = _FP_NANSIGN_##fs; \ + R##_c = FP_CLS_NAN; \ + _FP_FRAC_SET_##wc (R, _FP_NANFRAC_##fs); \ + FP_SET_EXCEPTION (FP_EX_INVALID | FP_EX_INVALID_ISI); \ + } \ + break; \ + \ + case _FP_CLS_COMBINE (FP_CLS_ZERO, FP_CLS_ZERO): \ + if (_FP_FMA_T##_s == Z##_s) \ + R##_s = Z##_s; \ + else \ + R##_s = (FP_ROUNDMODE == FP_RND_MINF); \ + _FP_FRAC_COPY_##wc (R, Z); \ + R##_c = Z##_c; \ + break; \ + \ + default: \ + _FP_UNREACHABLE; \ + } \ + done_fma: ; \ + } \ + while (0) + + +/* Main division routine. The input values should be cooked. */ + +#define _FP_DIV(fs, wc, R, X, Y) \ + do \ + { \ + R##_s = X##_s ^ Y##_s; \ + R##_e = X##_e - Y##_e; \ + switch (_FP_CLS_COMBINE (X##_c, Y##_c)) \ + { \ + case _FP_CLS_COMBINE (FP_CLS_NORMAL, FP_CLS_NORMAL): \ + R##_c = FP_CLS_NORMAL; \ + \ + _FP_DIV_MEAT_##fs (R, X, Y); \ + break; \ + \ + case _FP_CLS_COMBINE (FP_CLS_NAN, FP_CLS_NAN): \ + _FP_CHOOSENAN (fs, wc, R, X, Y, '/'); \ + break; \ + \ + case _FP_CLS_COMBINE (FP_CLS_NAN, FP_CLS_NORMAL): \ + case _FP_CLS_COMBINE (FP_CLS_NAN, FP_CLS_INF): \ + case _FP_CLS_COMBINE (FP_CLS_NAN, FP_CLS_ZERO): \ + R##_s = X##_s; \ + _FP_FRAC_COPY_##wc (R, X); \ + R##_c = X##_c; \ + break; \ + \ + case _FP_CLS_COMBINE (FP_CLS_NORMAL, FP_CLS_NAN): \ + case _FP_CLS_COMBINE (FP_CLS_INF, FP_CLS_NAN): \ + case _FP_CLS_COMBINE (FP_CLS_ZERO, FP_CLS_NAN): \ + R##_s = Y##_s; \ + _FP_FRAC_COPY_##wc (R, Y); \ + R##_c = Y##_c; \ + break; \ + \ + case _FP_CLS_COMBINE (FP_CLS_NORMAL, FP_CLS_INF): \ + case _FP_CLS_COMBINE (FP_CLS_ZERO, FP_CLS_INF): \ + case _FP_CLS_COMBINE (FP_CLS_ZERO, FP_CLS_NORMAL): \ + R##_c = FP_CLS_ZERO; \ + break; \ + \ + case _FP_CLS_COMBINE (FP_CLS_NORMAL, FP_CLS_ZERO): \ + FP_SET_EXCEPTION (FP_EX_DIVZERO); \ + /* FALLTHRU */ \ + case _FP_CLS_COMBINE (FP_CLS_INF, FP_CLS_ZERO): \ + case _FP_CLS_COMBINE (FP_CLS_INF, FP_CLS_NORMAL): \ + R##_c = FP_CLS_INF; \ + break; \ + \ + case _FP_CLS_COMBINE (FP_CLS_INF, FP_CLS_INF): \ + case _FP_CLS_COMBINE (FP_CLS_ZERO, FP_CLS_ZERO): \ + R##_s = _FP_NANSIGN_##fs; \ + R##_c = FP_CLS_NAN; \ + _FP_FRAC_SET_##wc (R, _FP_NANFRAC_##fs); \ + FP_SET_EXCEPTION (FP_EX_INVALID \ + | (X##_c == FP_CLS_INF \ + ? FP_EX_INVALID_IDI \ + : FP_EX_INVALID_ZDZ)); \ + break; \ + \ + default: \ + _FP_UNREACHABLE; \ + } \ + } \ + while (0) + + +/* Helper for comparisons. EX is 0 not to raise exceptions, 1 to + raise exceptions for signaling NaN operands, 2 to raise exceptions + for all NaN operands. Conditionals are organized to allow the + compiler to optimize away code based on the value of EX. */ + +#define _FP_CMP_CHECK_NAN(fs, wc, X, Y, ex) \ + do \ + { \ + /* The arguments are unordered, which may or may not result in \ + an exception. */ \ + if (ex) \ + { \ + /* At least some cases of unordered arguments result in \ + exceptions; check whether this is one. */ \ + if (FP_EX_INVALID_SNAN || FP_EX_INVALID_VC) \ + { \ + /* Check separately for each case of "invalid" \ + exceptions. */ \ + if ((ex) == 2) \ + FP_SET_EXCEPTION (FP_EX_INVALID | FP_EX_INVALID_VC); \ + if (_FP_ISSIGNAN (fs, wc, X) \ + || _FP_ISSIGNAN (fs, wc, Y)) \ + FP_SET_EXCEPTION (FP_EX_INVALID | FP_EX_INVALID_SNAN); \ + } \ + /* Otherwise, we only need to check whether to raise an \ + exception, not which case or cases it is. */ \ + else if ((ex) == 2 \ + || _FP_ISSIGNAN (fs, wc, X) \ + || _FP_ISSIGNAN (fs, wc, Y)) \ + FP_SET_EXCEPTION (FP_EX_INVALID); \ + } \ + } \ + while (0) + +/* Helper for comparisons. If denormal operands would raise an + exception, check for them, and flush to zero as appropriate + (otherwise, we need only check and flush to zero if it might affect + the result, which is done later with _FP_CMP_CHECK_FLUSH_ZERO). */ +#define _FP_CMP_CHECK_DENORM(fs, wc, X, Y) \ + do \ + { \ + if (FP_EX_DENORM != 0) \ + { \ + /* We must ensure the correct exceptions are raised for \ + denormal operands, even though this may not affect the \ + result of the comparison. */ \ + if (FP_DENORM_ZERO) \ + { \ + _FP_CHECK_FLUSH_ZERO (fs, wc, X); \ + _FP_CHECK_FLUSH_ZERO (fs, wc, Y); \ + } \ + else \ + { \ + if ((X##_e == 0 && !_FP_FRAC_ZEROP_##wc (X)) \ + || (Y##_e == 0 && !_FP_FRAC_ZEROP_##wc (Y))) \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + } \ + } \ + } \ + while (0) + +/* Helper for comparisons. Check for flushing denormals for zero if + we didn't need to check earlier for any denormal operands. */ +#define _FP_CMP_CHECK_FLUSH_ZERO(fs, wc, X, Y) \ + do \ + { \ + if (FP_EX_DENORM == 0) \ + { \ + _FP_CHECK_FLUSH_ZERO (fs, wc, X); \ + _FP_CHECK_FLUSH_ZERO (fs, wc, Y); \ + } \ + } \ + while (0) + +/* Main differential comparison routine. The inputs should be raw not + cooked. The return is -1, 0, 1 for normal values, UN + otherwise. */ + +#define _FP_CMP(fs, wc, ret, X, Y, un, ex) \ + do \ + { \ + _FP_CMP_CHECK_DENORM (fs, wc, X, Y); \ + /* NANs are unordered. */ \ + if ((X##_e == _FP_EXPMAX_##fs && !_FP_FRAC_ZEROP_##wc (X)) \ + || (Y##_e == _FP_EXPMAX_##fs && !_FP_FRAC_ZEROP_##wc (Y))) \ + { \ + (ret) = (un); \ + _FP_CMP_CHECK_NAN (fs, wc, X, Y, (ex)); \ + } \ + else \ + { \ + int _FP_CMP_is_zero_x; \ + int _FP_CMP_is_zero_y; \ + \ + _FP_CMP_CHECK_FLUSH_ZERO (fs, wc, X, Y); \ + \ + _FP_CMP_is_zero_x \ + = (!X##_e && _FP_FRAC_ZEROP_##wc (X)) ? 1 : 0; \ + _FP_CMP_is_zero_y \ + = (!Y##_e && _FP_FRAC_ZEROP_##wc (Y)) ? 1 : 0; \ + \ + if (_FP_CMP_is_zero_x && _FP_CMP_is_zero_y) \ + (ret) = 0; \ + else if (_FP_CMP_is_zero_x) \ + (ret) = Y##_s ? 1 : -1; \ + else if (_FP_CMP_is_zero_y) \ + (ret) = X##_s ? -1 : 1; \ + else if (X##_s != Y##_s) \ + (ret) = X##_s ? -1 : 1; \ + else if (X##_e > Y##_e) \ + (ret) = X##_s ? -1 : 1; \ + else if (X##_e < Y##_e) \ + (ret) = X##_s ? 1 : -1; \ + else if (_FP_FRAC_GT_##wc (X, Y)) \ + (ret) = X##_s ? -1 : 1; \ + else if (_FP_FRAC_GT_##wc (Y, X)) \ + (ret) = X##_s ? 1 : -1; \ + else \ + (ret) = 0; \ + } \ + } \ + while (0) + + +/* Simplification for strict equality. */ + +#define _FP_CMP_EQ(fs, wc, ret, X, Y, ex) \ + do \ + { \ + _FP_CMP_CHECK_DENORM (fs, wc, X, Y); \ + /* NANs are unordered. */ \ + if ((X##_e == _FP_EXPMAX_##fs && !_FP_FRAC_ZEROP_##wc (X)) \ + || (Y##_e == _FP_EXPMAX_##fs && !_FP_FRAC_ZEROP_##wc (Y))) \ + { \ + (ret) = 1; \ + _FP_CMP_CHECK_NAN (fs, wc, X, Y, (ex)); \ + } \ + else \ + { \ + _FP_CMP_CHECK_FLUSH_ZERO (fs, wc, X, Y); \ + \ + (ret) = !(X##_e == Y##_e \ + && _FP_FRAC_EQ_##wc (X, Y) \ + && (X##_s == Y##_s \ + || (!X##_e && _FP_FRAC_ZEROP_##wc (X)))); \ + } \ + } \ + while (0) + +/* Version to test unordered. */ + +#define _FP_CMP_UNORD(fs, wc, ret, X, Y, ex) \ + do \ + { \ + _FP_CMP_CHECK_DENORM (fs, wc, X, Y); \ + (ret) = ((X##_e == _FP_EXPMAX_##fs && !_FP_FRAC_ZEROP_##wc (X)) \ + || (Y##_e == _FP_EXPMAX_##fs && !_FP_FRAC_ZEROP_##wc (Y))); \ + if (ret) \ + _FP_CMP_CHECK_NAN (fs, wc, X, Y, (ex)); \ + } \ + while (0) + +/* Main square root routine. The input value should be cooked. */ + +#define _FP_SQRT(fs, wc, R, X) \ + do \ + { \ + _FP_FRAC_DECL_##wc (_FP_SQRT_T); \ + _FP_FRAC_DECL_##wc (_FP_SQRT_S); \ + _FP_W_TYPE _FP_SQRT_q; \ + switch (X##_c) \ + { \ + case FP_CLS_NAN: \ + _FP_FRAC_COPY_##wc (R, X); \ + R##_s = X##_s; \ + R##_c = FP_CLS_NAN; \ + break; \ + case FP_CLS_INF: \ + if (X##_s) \ + { \ + R##_s = _FP_NANSIGN_##fs; \ + R##_c = FP_CLS_NAN; /* NAN */ \ + _FP_FRAC_SET_##wc (R, _FP_NANFRAC_##fs); \ + FP_SET_EXCEPTION (FP_EX_INVALID | FP_EX_INVALID_SQRT); \ + } \ + else \ + { \ + R##_s = 0; \ + R##_c = FP_CLS_INF; /* sqrt(+inf) = +inf */ \ + } \ + break; \ + case FP_CLS_ZERO: \ + R##_s = X##_s; \ + R##_c = FP_CLS_ZERO; /* sqrt(+-0) = +-0 */ \ + break; \ + case FP_CLS_NORMAL: \ + R##_s = 0; \ + if (X##_s) \ + { \ + R##_c = FP_CLS_NAN; /* NAN */ \ + R##_s = _FP_NANSIGN_##fs; \ + _FP_FRAC_SET_##wc (R, _FP_NANFRAC_##fs); \ + FP_SET_EXCEPTION (FP_EX_INVALID | FP_EX_INVALID_SQRT); \ + break; \ + } \ + R##_c = FP_CLS_NORMAL; \ + if (X##_e & 1) \ + _FP_FRAC_SLL_##wc (X, 1); \ + R##_e = X##_e >> 1; \ + _FP_FRAC_SET_##wc (_FP_SQRT_S, _FP_ZEROFRAC_##wc); \ + _FP_FRAC_SET_##wc (R, _FP_ZEROFRAC_##wc); \ + _FP_SQRT_q = _FP_OVERFLOW_##fs >> 1; \ + _FP_SQRT_MEAT_##wc (R, _FP_SQRT_S, _FP_SQRT_T, X, \ + _FP_SQRT_q); \ + } \ + } \ + while (0) + +/* Convert from FP to integer. Input is raw. */ + +/* RSIGNED can have following values: + 0: the number is required to be 0..(2^rsize)-1, if not, NV is set plus + the result is either 0 or (2^rsize)-1 depending on the sign in such + case. + 1: the number is required to be -(2^(rsize-1))..(2^(rsize-1))-1, if not, + NV is set plus the result is either -(2^(rsize-1)) or (2^(rsize-1))-1 + depending on the sign in such case. + 2: the number is required to be -(2^(rsize-1))..(2^(rsize-1))-1, if not, + NV is set plus the result is reduced modulo 2^rsize. + -1: the number is required to be -(2^(rsize-1))..(2^rsize)-1, if not, NV is + set plus the result is either -(2^(rsize-1)) or (2^(rsize-1))-1 + depending on the sign in such case. */ +#define _FP_TO_INT(fs, wc, r, X, rsize, rsigned) \ + do \ + { \ + if (X##_e < _FP_EXPBIAS_##fs) \ + { \ + (r) = 0; \ + if (X##_e == 0) \ + { \ + if (!_FP_FRAC_ZEROP_##wc (X)) \ + { \ + if (!FP_DENORM_ZERO) \ + FP_SET_EXCEPTION (FP_EX_INEXACT); \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + } \ + } \ + else \ + FP_SET_EXCEPTION (FP_EX_INEXACT); \ + } \ + else if ((rsigned) == 2 \ + && (X##_e \ + >= ((_FP_EXPMAX_##fs \ + < _FP_EXPBIAS_##fs + _FP_FRACBITS_##fs + (rsize) - 1) \ + ? _FP_EXPMAX_##fs \ + : _FP_EXPBIAS_##fs + _FP_FRACBITS_##fs + (rsize) - 1))) \ + { \ + /* Overflow resulting in 0. */ \ + (r) = 0; \ + FP_SET_EXCEPTION (FP_EX_INVALID \ + | FP_EX_INVALID_CVI \ + | ((FP_EX_INVALID_SNAN \ + && _FP_ISSIGNAN (fs, wc, X)) \ + ? FP_EX_INVALID_SNAN \ + : 0)); \ + } \ + else if ((rsigned) != 2 \ + && (X##_e >= (_FP_EXPMAX_##fs < _FP_EXPBIAS_##fs + (rsize) \ + ? _FP_EXPMAX_##fs \ + : (_FP_EXPBIAS_##fs + (rsize) \ + - ((rsigned) > 0 || X##_s))) \ + || (!(rsigned) && X##_s))) \ + { \ + /* Overflow or converting to the most negative integer. */ \ + if (rsigned) \ + { \ + (r) = 1; \ + (r) <<= (rsize) - 1; \ + (r) -= 1 - X##_s; \ + } \ + else \ + { \ + (r) = 0; \ + if (!X##_s) \ + (r) = ~(r); \ + } \ + \ + if (_FP_EXPBIAS_##fs + (rsize) - 1 < _FP_EXPMAX_##fs \ + && (rsigned) \ + && X##_s \ + && X##_e == _FP_EXPBIAS_##fs + (rsize) - 1) \ + { \ + /* Possibly converting to most negative integer; check the \ + mantissa. */ \ + int _FP_TO_INT_inexact = 0; \ + (void) ((_FP_FRACBITS_##fs > (rsize)) \ + ? ({ \ + _FP_FRAC_SRST_##wc (X, _FP_TO_INT_inexact, \ + _FP_FRACBITS_##fs - (rsize), \ + _FP_FRACBITS_##fs); \ + 0; \ + }) \ + : 0); \ + if (!_FP_FRAC_ZEROP_##wc (X)) \ + FP_SET_EXCEPTION (FP_EX_INVALID | FP_EX_INVALID_CVI); \ + else if (_FP_TO_INT_inexact) \ + FP_SET_EXCEPTION (FP_EX_INEXACT); \ + } \ + else \ + FP_SET_EXCEPTION (FP_EX_INVALID \ + | FP_EX_INVALID_CVI \ + | ((FP_EX_INVALID_SNAN \ + && _FP_ISSIGNAN (fs, wc, X)) \ + ? FP_EX_INVALID_SNAN \ + : 0)); \ + } \ + else \ + { \ + int _FP_TO_INT_inexact = 0; \ + _FP_FRAC_HIGH_RAW_##fs (X) |= _FP_IMPLBIT_##fs; \ + if (X##_e >= _FP_EXPBIAS_##fs + _FP_FRACBITS_##fs - 1) \ + { \ + _FP_FRAC_ASSEMBLE_##wc ((r), X, (rsize)); \ + (r) <<= X##_e - _FP_EXPBIAS_##fs - _FP_FRACBITS_##fs + 1; \ + } \ + else \ + { \ + _FP_FRAC_SRST_##wc (X, _FP_TO_INT_inexact, \ + (_FP_FRACBITS_##fs + _FP_EXPBIAS_##fs - 1 \ + - X##_e), \ + _FP_FRACBITS_##fs); \ + _FP_FRAC_ASSEMBLE_##wc ((r), X, (rsize)); \ + } \ + if ((rsigned) && X##_s) \ + (r) = -(r); \ + if ((rsigned) == 2 && X##_e >= _FP_EXPBIAS_##fs + (rsize) - 1) \ + { \ + /* Overflow or converting to the most negative integer. */ \ + if (X##_e > _FP_EXPBIAS_##fs + (rsize) - 1 \ + || !X##_s \ + || (r) != (((typeof (r)) 1) << ((rsize) - 1))) \ + { \ + _FP_TO_INT_inexact = 0; \ + FP_SET_EXCEPTION (FP_EX_INVALID | FP_EX_INVALID_CVI); \ + } \ + } \ + if (_FP_TO_INT_inexact) \ + FP_SET_EXCEPTION (FP_EX_INEXACT); \ + } \ + } \ + while (0) + +/* Convert from floating point to integer, rounding according to the + current rounding direction. Input is raw. RSIGNED is as for + _FP_TO_INT. */ +#define _FP_TO_INT_ROUND(fs, wc, r, X, rsize, rsigned) \ + do \ + { \ + __label__ _FP_TO_INT_ROUND_done; \ + if (X##_e < _FP_EXPBIAS_##fs) \ + { \ + int _FP_TO_INT_ROUND_rounds_away = 0; \ + if (X##_e == 0) \ + { \ + if (_FP_FRAC_ZEROP_##wc (X)) \ + { \ + (r) = 0; \ + goto _FP_TO_INT_ROUND_done; \ + } \ + else \ + { \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + if (FP_DENORM_ZERO) \ + { \ + (r) = 0; \ + goto _FP_TO_INT_ROUND_done; \ + } \ + } \ + } \ + /* The result is 0, 1 or -1 depending on the rounding mode; \ + -1 may cause overflow in the unsigned case. */ \ + switch (FP_ROUNDMODE) \ + { \ + case FP_RND_NEAREST: \ + _FP_TO_INT_ROUND_rounds_away \ + = (X##_e == _FP_EXPBIAS_##fs - 1 \ + && !_FP_FRAC_ZEROP_##wc (X)); \ + break; \ + case FP_RND_ZERO: \ + /* _FP_TO_INT_ROUND_rounds_away is already 0. */ \ + break; \ + case FP_RND_PINF: \ + _FP_TO_INT_ROUND_rounds_away = !X##_s; \ + break; \ + case FP_RND_MINF: \ + _FP_TO_INT_ROUND_rounds_away = X##_s; \ + break; \ + } \ + if ((rsigned) == 0 && _FP_TO_INT_ROUND_rounds_away && X##_s) \ + { \ + /* Result of -1 for an unsigned conversion. */ \ + (r) = 0; \ + FP_SET_EXCEPTION (FP_EX_INVALID | FP_EX_INVALID_CVI); \ + } \ + else if ((rsize) == 1 && (rsigned) > 0 \ + && _FP_TO_INT_ROUND_rounds_away && !X##_s) \ + { \ + /* Converting to a 1-bit signed bit-field, which cannot \ + represent +1. */ \ + (r) = ((rsigned) == 2 ? -1 : 0); \ + FP_SET_EXCEPTION (FP_EX_INVALID | FP_EX_INVALID_CVI); \ + } \ + else \ + { \ + (r) = (_FP_TO_INT_ROUND_rounds_away \ + ? (X##_s ? -1 : 1) \ + : 0); \ + FP_SET_EXCEPTION (FP_EX_INEXACT); \ + } \ + } \ + else if ((rsigned) == 2 \ + && (X##_e \ + >= ((_FP_EXPMAX_##fs \ + < _FP_EXPBIAS_##fs + _FP_FRACBITS_##fs + (rsize) - 1) \ + ? _FP_EXPMAX_##fs \ + : _FP_EXPBIAS_##fs + _FP_FRACBITS_##fs + (rsize) - 1))) \ + { \ + /* Overflow resulting in 0. */ \ + (r) = 0; \ + FP_SET_EXCEPTION (FP_EX_INVALID \ + | FP_EX_INVALID_CVI \ + | ((FP_EX_INVALID_SNAN \ + && _FP_ISSIGNAN (fs, wc, X)) \ + ? FP_EX_INVALID_SNAN \ + : 0)); \ + } \ + else if ((rsigned) != 2 \ + && (X##_e >= (_FP_EXPMAX_##fs < _FP_EXPBIAS_##fs + (rsize) \ + ? _FP_EXPMAX_##fs \ + : (_FP_EXPBIAS_##fs + (rsize) \ + - ((rsigned) > 0 && !X##_s))) \ + || ((rsigned) == 0 && X##_s))) \ + { \ + /* Definite overflow (does not require rounding to tell). */ \ + if ((rsigned) != 0) \ + { \ + (r) = 1; \ + (r) <<= (rsize) - 1; \ + (r) -= 1 - X##_s; \ + } \ + else \ + { \ + (r) = 0; \ + if (!X##_s) \ + (r) = ~(r); \ + } \ + \ + FP_SET_EXCEPTION (FP_EX_INVALID \ + | FP_EX_INVALID_CVI \ + | ((FP_EX_INVALID_SNAN \ + && _FP_ISSIGNAN (fs, wc, X)) \ + ? FP_EX_INVALID_SNAN \ + : 0)); \ + } \ + else \ + { \ + /* The value is finite, with magnitude at least 1. If \ + the conversion is unsigned, the value is positive. \ + If RSIGNED is not 2, the value does not definitely \ + overflow by virtue of its exponent, but may still turn \ + out to overflow after rounding; if RSIGNED is 2, the \ + exponent may be such that the value definitely overflows, \ + but at least one mantissa bit will not be shifted out. */ \ + int _FP_TO_INT_ROUND_inexact = 0; \ + _FP_FRAC_HIGH_RAW_##fs (X) |= _FP_IMPLBIT_##fs; \ + if (X##_e >= _FP_EXPBIAS_##fs + _FP_FRACBITS_##fs - 1) \ + { \ + /* The value is an integer, no rounding needed. */ \ + _FP_FRAC_ASSEMBLE_##wc ((r), X, (rsize)); \ + (r) <<= X##_e - _FP_EXPBIAS_##fs - _FP_FRACBITS_##fs + 1; \ + } \ + else \ + { \ + /* May need to shift in order to round (unless there \ + are exactly _FP_WORKBITS fractional bits already). */ \ + int _FP_TO_INT_ROUND_rshift \ + = (_FP_FRACBITS_##fs + _FP_EXPBIAS_##fs \ + - 1 - _FP_WORKBITS - X##_e); \ + if (_FP_TO_INT_ROUND_rshift > 0) \ + _FP_FRAC_SRS_##wc (X, _FP_TO_INT_ROUND_rshift, \ + _FP_WFRACBITS_##fs); \ + else if (_FP_TO_INT_ROUND_rshift < 0) \ + _FP_FRAC_SLL_##wc (X, -_FP_TO_INT_ROUND_rshift); \ + /* Round like _FP_ROUND, but setting \ + _FP_TO_INT_ROUND_inexact instead of directly setting \ + the "inexact" exception, since it may turn out we \ + should set "invalid" instead. */ \ + if (_FP_FRAC_LOW_##wc (X) & 7) \ + { \ + _FP_TO_INT_ROUND_inexact = 1; \ + switch (FP_ROUNDMODE) \ + { \ + case FP_RND_NEAREST: \ + _FP_ROUND_NEAREST (wc, X); \ + break; \ + case FP_RND_ZERO: \ + _FP_ROUND_ZERO (wc, X); \ + break; \ + case FP_RND_PINF: \ + _FP_ROUND_PINF (wc, X); \ + break; \ + case FP_RND_MINF: \ + _FP_ROUND_MINF (wc, X); \ + break; \ + } \ + } \ + _FP_FRAC_SRL_##wc (X, _FP_WORKBITS); \ + _FP_FRAC_ASSEMBLE_##wc ((r), X, (rsize)); \ + } \ + if ((rsigned) != 0 && X##_s) \ + (r) = -(r); \ + /* An exponent of RSIZE - 1 always needs testing for \ + overflow (either directly overflowing, or overflowing \ + when rounding up results in 2^RSIZE). An exponent of \ + RSIZE - 2 can overflow for positive values when rounding \ + up to 2^(RSIZE-1), but cannot overflow for negative \ + values. Smaller exponents cannot overflow. */ \ + if (X##_e >= (_FP_EXPBIAS_##fs + (rsize) - 1 \ + - ((rsigned) > 0 && !X##_s))) \ + { \ + if (X##_e > _FP_EXPBIAS_##fs + (rsize) - 1 \ + || (X##_e == _FP_EXPBIAS_##fs + (rsize) - 1 \ + && (X##_s \ + ? (r) != (((typeof (r)) 1) << ((rsize) - 1)) \ + : ((rsigned) > 0 || (r) == 0))) \ + || ((rsigned) > 0 \ + && !X##_s \ + && X##_e == _FP_EXPBIAS_##fs + (rsize) - 2 \ + && (r) == (((typeof (r)) 1) << ((rsize) - 1)))) \ + { \ + if ((rsigned) != 2) \ + { \ + if ((rsigned) != 0) \ + { \ + (r) = 1; \ + (r) <<= (rsize) - 1; \ + (r) -= 1 - X##_s; \ + } \ + else \ + { \ + (r) = 0; \ + (r) = ~(r); \ + } \ + } \ + _FP_TO_INT_ROUND_inexact = 0; \ + FP_SET_EXCEPTION (FP_EX_INVALID | FP_EX_INVALID_CVI); \ + } \ + } \ + if (_FP_TO_INT_ROUND_inexact) \ + FP_SET_EXCEPTION (FP_EX_INEXACT); \ + } \ + _FP_TO_INT_ROUND_done: ; \ + } \ + while (0) + +/* Convert integer to fp. Output is raw. RTYPE is unsigned even if + input is signed. */ +#define _FP_FROM_INT(fs, wc, X, r, rsize, rtype) \ + do \ + { \ + __label__ pack_semiraw; \ + if (r) \ + { \ + rtype _FP_FROM_INT_ur = (r); \ + \ + if ((X##_s = ((r) < 0))) \ + _FP_FROM_INT_ur = -_FP_FROM_INT_ur; \ + \ + _FP_STATIC_ASSERT ((rsize) <= 2 * _FP_W_TYPE_SIZE, \ + "rsize too large"); \ + (void) (((rsize) <= _FP_W_TYPE_SIZE) \ + ? ({ \ + int _FP_FROM_INT_lz; \ + __FP_CLZ (_FP_FROM_INT_lz, \ + (_FP_W_TYPE) _FP_FROM_INT_ur); \ + X##_e = (_FP_EXPBIAS_##fs + _FP_W_TYPE_SIZE - 1 \ + - _FP_FROM_INT_lz); \ + }) \ + : ({ \ + int _FP_FROM_INT_lz; \ + __FP_CLZ_2 (_FP_FROM_INT_lz, \ + (_FP_W_TYPE) (_FP_FROM_INT_ur \ + >> _FP_W_TYPE_SIZE), \ + (_FP_W_TYPE) _FP_FROM_INT_ur); \ + X##_e = (_FP_EXPBIAS_##fs + 2 * _FP_W_TYPE_SIZE - 1 \ + - _FP_FROM_INT_lz); \ + })); \ + \ + if ((rsize) - 1 + _FP_EXPBIAS_##fs >= _FP_EXPMAX_##fs \ + && X##_e >= _FP_EXPMAX_##fs) \ + { \ + /* Exponent too big; overflow to infinity. (May also \ + happen after rounding below.) */ \ + _FP_OVERFLOW_SEMIRAW (fs, wc, X); \ + goto pack_semiraw; \ + } \ + \ + if ((rsize) <= _FP_FRACBITS_##fs \ + || X##_e < _FP_EXPBIAS_##fs + _FP_FRACBITS_##fs) \ + { \ + /* Exactly representable; shift left. */ \ + _FP_FRAC_DISASSEMBLE_##wc (X, _FP_FROM_INT_ur, (rsize)); \ + if (_FP_EXPBIAS_##fs + _FP_FRACBITS_##fs - 1 - X##_e > 0) \ + _FP_FRAC_SLL_##wc (X, (_FP_EXPBIAS_##fs \ + + _FP_FRACBITS_##fs - 1 - X##_e)); \ + } \ + else \ + { \ + /* More bits in integer than in floating type; need to \ + round. */ \ + if (_FP_EXPBIAS_##fs + _FP_WFRACBITS_##fs - 1 < X##_e) \ + _FP_FROM_INT_ur \ + = ((_FP_FROM_INT_ur >> (X##_e - _FP_EXPBIAS_##fs \ + - _FP_WFRACBITS_##fs + 1)) \ + | ((_FP_FROM_INT_ur \ + << ((rsize) - (X##_e - _FP_EXPBIAS_##fs \ + - _FP_WFRACBITS_##fs + 1))) \ + != 0)); \ + _FP_FRAC_DISASSEMBLE_##wc (X, _FP_FROM_INT_ur, (rsize)); \ + if ((_FP_EXPBIAS_##fs + _FP_WFRACBITS_##fs - 1 - X##_e) > 0) \ + _FP_FRAC_SLL_##wc (X, (_FP_EXPBIAS_##fs \ + + _FP_WFRACBITS_##fs - 1 - X##_e)); \ + _FP_FRAC_HIGH_##fs (X) &= ~(_FP_W_TYPE) _FP_IMPLBIT_SH_##fs; \ + pack_semiraw: \ + _FP_PACK_SEMIRAW (fs, wc, X); \ + } \ + } \ + else \ + { \ + X##_s = 0; \ + X##_e = 0; \ + _FP_FRAC_SET_##wc (X, _FP_ZEROFRAC_##wc); \ + } \ + } \ + while (0) + + +/* Extend from a narrower floating-point format to a wider one. Input + and output are raw. If CHECK_NAN, then signaling NaNs are + converted to quiet with the "invalid" exception raised; otherwise + signaling NaNs remain signaling with no exception. */ +#define _FP_EXTEND_CNAN(dfs, sfs, dwc, swc, D, S, check_nan) \ + do \ + { \ + _FP_STATIC_ASSERT (_FP_FRACBITS_##dfs >= _FP_FRACBITS_##sfs, \ + "destination mantissa narrower than source"); \ + _FP_STATIC_ASSERT ((_FP_EXPMAX_##dfs - _FP_EXPBIAS_##dfs \ + >= _FP_EXPMAX_##sfs - _FP_EXPBIAS_##sfs), \ + "destination max exponent smaller" \ + " than source"); \ + _FP_STATIC_ASSERT (((_FP_EXPBIAS_##dfs \ + >= (_FP_EXPBIAS_##sfs \ + + _FP_FRACBITS_##sfs - 1)) \ + || (_FP_EXPBIAS_##dfs == _FP_EXPBIAS_##sfs)), \ + "source subnormals do not all become normal," \ + " but bias not the same"); \ + D##_s = S##_s; \ + _FP_FRAC_COPY_##dwc##_##swc (D, S); \ + if (_FP_EXP_NORMAL (sfs, swc, S)) \ + { \ + D##_e = S##_e + _FP_EXPBIAS_##dfs - _FP_EXPBIAS_##sfs; \ + _FP_FRAC_SLL_##dwc (D, (_FP_FRACBITS_##dfs - _FP_FRACBITS_##sfs)); \ + } \ + else \ + { \ + if (S##_e == 0) \ + { \ + _FP_CHECK_FLUSH_ZERO (sfs, swc, S); \ + if (_FP_FRAC_ZEROP_##swc (S)) \ + D##_e = 0; \ + else if (_FP_EXPBIAS_##dfs \ + < _FP_EXPBIAS_##sfs + _FP_FRACBITS_##sfs - 1) \ + { \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + _FP_FRAC_SLL_##dwc (D, (_FP_FRACBITS_##dfs \ + - _FP_FRACBITS_##sfs)); \ + D##_e = 0; \ + if (FP_TRAPPING_EXCEPTIONS & FP_EX_UNDERFLOW) \ + FP_SET_EXCEPTION (FP_EX_UNDERFLOW); \ + } \ + else \ + { \ + int FP_EXTEND_lz; \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + _FP_FRAC_CLZ_##swc (FP_EXTEND_lz, S); \ + _FP_FRAC_SLL_##dwc (D, \ + FP_EXTEND_lz + _FP_FRACBITS_##dfs \ + - _FP_FRACTBITS_##sfs); \ + D##_e = (_FP_EXPBIAS_##dfs - _FP_EXPBIAS_##sfs + 1 \ + + _FP_FRACXBITS_##sfs - FP_EXTEND_lz); \ + } \ + } \ + else \ + { \ + D##_e = _FP_EXPMAX_##dfs; \ + if (!_FP_FRAC_ZEROP_##swc (S)) \ + { \ + if (check_nan && _FP_FRAC_SNANP (sfs, S)) \ + FP_SET_EXCEPTION (FP_EX_INVALID \ + | FP_EX_INVALID_SNAN); \ + _FP_FRAC_SLL_##dwc (D, (_FP_FRACBITS_##dfs \ + - _FP_FRACBITS_##sfs)); \ + if (check_nan) \ + _FP_SETQNAN (dfs, dwc, D); \ + } \ + } \ + } \ + } \ + while (0) + +#define FP_EXTEND(dfs, sfs, dwc, swc, D, S) \ + _FP_EXTEND_CNAN (dfs, sfs, dwc, swc, D, S, 1) + +/* Truncate from a wider floating-point format to a narrower one. + Input and output are semi-raw. */ +#define FP_TRUNC(dfs, sfs, dwc, swc, D, S) \ + do \ + { \ + _FP_STATIC_ASSERT (_FP_FRACBITS_##sfs >= _FP_FRACBITS_##dfs, \ + "destination mantissa wider than source"); \ + _FP_STATIC_ASSERT (((_FP_EXPBIAS_##sfs \ + >= (_FP_EXPBIAS_##dfs \ + + _FP_FRACBITS_##dfs - 1)) \ + || _FP_EXPBIAS_##sfs == _FP_EXPBIAS_##dfs), \ + "source subnormals do not all become same," \ + " but bias not the same"); \ + D##_s = S##_s; \ + if (_FP_EXP_NORMAL (sfs, swc, S)) \ + { \ + D##_e = S##_e + _FP_EXPBIAS_##dfs - _FP_EXPBIAS_##sfs; \ + if (D##_e >= _FP_EXPMAX_##dfs) \ + _FP_OVERFLOW_SEMIRAW (dfs, dwc, D); \ + else \ + { \ + if (D##_e <= 0) \ + { \ + if (D##_e < 1 - _FP_FRACBITS_##dfs) \ + { \ + _FP_FRAC_SET_##swc (S, _FP_ZEROFRAC_##swc); \ + _FP_FRAC_LOW_##swc (S) |= 1; \ + } \ + else \ + { \ + _FP_FRAC_HIGH_##sfs (S) |= _FP_IMPLBIT_SH_##sfs; \ + _FP_FRAC_SRS_##swc (S, (_FP_WFRACBITS_##sfs \ + - _FP_WFRACBITS_##dfs \ + + 1 - D##_e), \ + _FP_WFRACBITS_##sfs); \ + } \ + D##_e = 0; \ + } \ + else \ + _FP_FRAC_SRS_##swc (S, (_FP_WFRACBITS_##sfs \ + - _FP_WFRACBITS_##dfs), \ + _FP_WFRACBITS_##sfs); \ + _FP_FRAC_COPY_##dwc##_##swc (D, S); \ + } \ + } \ + else \ + { \ + if (S##_e == 0) \ + { \ + _FP_CHECK_FLUSH_ZERO (sfs, swc, S); \ + D##_e = 0; \ + if (_FP_FRAC_ZEROP_##swc (S)) \ + _FP_FRAC_SET_##dwc (D, _FP_ZEROFRAC_##dwc); \ + else \ + { \ + FP_SET_EXCEPTION (FP_EX_DENORM); \ + if (_FP_EXPBIAS_##sfs \ + < _FP_EXPBIAS_##dfs + _FP_FRACBITS_##dfs - 1) \ + { \ + _FP_FRAC_SRS_##swc (S, (_FP_WFRACBITS_##sfs \ + - _FP_WFRACBITS_##dfs), \ + _FP_WFRACBITS_##sfs); \ + _FP_FRAC_COPY_##dwc##_##swc (D, S); \ + } \ + else \ + { \ + _FP_FRAC_SET_##dwc (D, _FP_ZEROFRAC_##dwc); \ + _FP_FRAC_LOW_##dwc (D) |= 1; \ + } \ + } \ + } \ + else \ + { \ + D##_e = _FP_EXPMAX_##dfs; \ + if (_FP_FRAC_ZEROP_##swc (S)) \ + _FP_FRAC_SET_##dwc (D, _FP_ZEROFRAC_##dwc); \ + else \ + { \ + _FP_CHECK_SIGNAN_SEMIRAW (sfs, swc, S); \ + _FP_FRAC_SRL_##swc (S, (_FP_WFRACBITS_##sfs \ + - _FP_WFRACBITS_##dfs)); \ + _FP_FRAC_COPY_##dwc##_##swc (D, S); \ + /* Semi-raw NaN must have all workbits cleared. */ \ + _FP_FRAC_LOW_##dwc (D) \ + &= ~(_FP_W_TYPE) ((1 << _FP_WORKBITS) - 1); \ + _FP_SETQNAN_SEMIRAW (dfs, dwc, D); \ + } \ + } \ + } \ + } \ + while (0) + +/* Helper primitives. */ + +/* Count leading zeros in a word. */ + +#ifndef __FP_CLZ +/* GCC 3.4 and later provide the builtins for us. */ +# define __FP_CLZ(r, x) \ + do \ + { \ + _FP_STATIC_ASSERT ((sizeof (_FP_W_TYPE) == sizeof (unsigned int) \ + || (sizeof (_FP_W_TYPE) \ + == sizeof (unsigned long)) \ + || (sizeof (_FP_W_TYPE) \ + == sizeof (unsigned long long))), \ + "_FP_W_TYPE size unsupported for clz"); \ + if (sizeof (_FP_W_TYPE) == sizeof (unsigned int)) \ + (r) = __builtin_clz (x); \ + else if (sizeof (_FP_W_TYPE) == sizeof (unsigned long)) \ + (r) = __builtin_clzl (x); \ + else /* sizeof (_FP_W_TYPE) == sizeof (unsigned long long). */ \ + (r) = __builtin_clzll (x); \ + } \ + while (0) +#endif /* ndef __FP_CLZ */ + +#define _FP_DIV_HELP_imm(q, r, n, d) \ + do \ + { \ + (q) = (n) / (d), (r) = (n) % (d); \ + } \ + while (0) + + +/* A restoring bit-by-bit division primitive. */ + +#define _FP_DIV_MEAT_N_loop(fs, wc, R, X, Y) \ + do \ + { \ + int _FP_DIV_MEAT_N_loop_count = _FP_WFRACBITS_##fs; \ + _FP_FRAC_DECL_##wc (_FP_DIV_MEAT_N_loop_u); \ + _FP_FRAC_DECL_##wc (_FP_DIV_MEAT_N_loop_v); \ + _FP_FRAC_COPY_##wc (_FP_DIV_MEAT_N_loop_u, X); \ + _FP_FRAC_COPY_##wc (_FP_DIV_MEAT_N_loop_v, Y); \ + _FP_FRAC_SET_##wc (R, _FP_ZEROFRAC_##wc); \ + /* Normalize _FP_DIV_MEAT_N_LOOP_U and _FP_DIV_MEAT_N_LOOP_V. */ \ + _FP_FRAC_SLL_##wc (_FP_DIV_MEAT_N_loop_u, _FP_WFRACXBITS_##fs); \ + _FP_FRAC_SLL_##wc (_FP_DIV_MEAT_N_loop_v, _FP_WFRACXBITS_##fs); \ + /* First round. Since the operands are normalized, either the \ + first or second bit will be set in the fraction. Produce a \ + normalized result by checking which and adjusting the loop \ + count and exponent accordingly. */ \ + if (_FP_FRAC_GE_1 (_FP_DIV_MEAT_N_loop_u, _FP_DIV_MEAT_N_loop_v)) \ + { \ + _FP_FRAC_SUB_##wc (_FP_DIV_MEAT_N_loop_u, \ + _FP_DIV_MEAT_N_loop_u, \ + _FP_DIV_MEAT_N_loop_v); \ + _FP_FRAC_LOW_##wc (R) |= 1; \ + _FP_DIV_MEAT_N_loop_count--; \ + } \ + else \ + R##_e--; \ + /* Subsequent rounds. */ \ + do \ + { \ + int _FP_DIV_MEAT_N_loop_msb \ + = (_FP_WS_TYPE) _FP_FRAC_HIGH_##wc (_FP_DIV_MEAT_N_loop_u) < 0; \ + _FP_FRAC_SLL_##wc (_FP_DIV_MEAT_N_loop_u, 1); \ + _FP_FRAC_SLL_##wc (R, 1); \ + if (_FP_DIV_MEAT_N_loop_msb \ + || _FP_FRAC_GE_1 (_FP_DIV_MEAT_N_loop_u, \ + _FP_DIV_MEAT_N_loop_v)) \ + { \ + _FP_FRAC_SUB_##wc (_FP_DIV_MEAT_N_loop_u, \ + _FP_DIV_MEAT_N_loop_u, \ + _FP_DIV_MEAT_N_loop_v); \ + _FP_FRAC_LOW_##wc (R) |= 1; \ + } \ + } \ + while (--_FP_DIV_MEAT_N_loop_count > 0); \ + /* If there's anything left in _FP_DIV_MEAT_N_LOOP_U, the result \ + is inexact. */ \ + _FP_FRAC_LOW_##wc (R) \ + |= !_FP_FRAC_ZEROP_##wc (_FP_DIV_MEAT_N_loop_u); \ + } \ + while (0) + +#define _FP_DIV_MEAT_1_loop(fs, R, X, Y) _FP_DIV_MEAT_N_loop (fs, 1, R, X, Y) +#define _FP_DIV_MEAT_2_loop(fs, R, X, Y) _FP_DIV_MEAT_N_loop (fs, 2, R, X, Y) +#define _FP_DIV_MEAT_4_loop(fs, R, X, Y) _FP_DIV_MEAT_N_loop (fs, 4, R, X, Y) + +#endif /* !SOFT_FP_OP_COMMON_H */ diff --git a/REORG.TODO/soft-fp/quad.h b/REORG.TODO/soft-fp/quad.h new file mode 100644 index 0000000000..388601fd81 --- /dev/null +++ b/REORG.TODO/soft-fp/quad.h @@ -0,0 +1,330 @@ +/* Software floating-point emulation. + Definitions for IEEE Quad Precision. + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com), + Jakub Jelinek (jj@ultra.linux.cz), + David S. Miller (davem@redhat.com) and + Peter Maydell (pmaydell@chiark.greenend.org.uk). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#ifndef SOFT_FP_QUAD_H +#define SOFT_FP_QUAD_H 1 + +#if _FP_W_TYPE_SIZE < 32 +# error "Here's a nickel, kid. Go buy yourself a real computer." +#endif + +#if _FP_W_TYPE_SIZE < 64 +# define _FP_FRACTBITS_Q (4*_FP_W_TYPE_SIZE) +# define _FP_FRACTBITS_DW_Q (8*_FP_W_TYPE_SIZE) +#else +# define _FP_FRACTBITS_Q (2*_FP_W_TYPE_SIZE) +# define _FP_FRACTBITS_DW_Q (4*_FP_W_TYPE_SIZE) +#endif + +#define _FP_FRACBITS_Q 113 +#define _FP_FRACXBITS_Q (_FP_FRACTBITS_Q - _FP_FRACBITS_Q) +#define _FP_WFRACBITS_Q (_FP_WORKBITS + _FP_FRACBITS_Q) +#define _FP_WFRACXBITS_Q (_FP_FRACTBITS_Q - _FP_WFRACBITS_Q) +#define _FP_EXPBITS_Q 15 +#define _FP_EXPBIAS_Q 16383 +#define _FP_EXPMAX_Q 32767 + +#define _FP_QNANBIT_Q \ + ((_FP_W_TYPE) 1 << (_FP_FRACBITS_Q-2) % _FP_W_TYPE_SIZE) +#define _FP_QNANBIT_SH_Q \ + ((_FP_W_TYPE) 1 << (_FP_FRACBITS_Q-2+_FP_WORKBITS) % _FP_W_TYPE_SIZE) +#define _FP_IMPLBIT_Q \ + ((_FP_W_TYPE) 1 << (_FP_FRACBITS_Q-1) % _FP_W_TYPE_SIZE) +#define _FP_IMPLBIT_SH_Q \ + ((_FP_W_TYPE) 1 << (_FP_FRACBITS_Q-1+_FP_WORKBITS) % _FP_W_TYPE_SIZE) +#define _FP_OVERFLOW_Q \ + ((_FP_W_TYPE) 1 << (_FP_WFRACBITS_Q % _FP_W_TYPE_SIZE)) + +#define _FP_WFRACBITS_DW_Q (2 * _FP_WFRACBITS_Q) +#define _FP_WFRACXBITS_DW_Q (_FP_FRACTBITS_DW_Q - _FP_WFRACBITS_DW_Q) +#define _FP_HIGHBIT_DW_Q \ + ((_FP_W_TYPE) 1 << (_FP_WFRACBITS_DW_Q - 1) % _FP_W_TYPE_SIZE) + +typedef float TFtype __attribute__ ((mode (TF))); + +#if _FP_W_TYPE_SIZE < 64 + +union _FP_UNION_Q +{ + TFtype flt; + struct _FP_STRUCT_LAYOUT + { +# if __BYTE_ORDER == __BIG_ENDIAN + unsigned sign : 1; + unsigned exp : _FP_EXPBITS_Q; + unsigned long frac3 : _FP_FRACBITS_Q - (_FP_IMPLBIT_Q != 0)-(_FP_W_TYPE_SIZE * 3); + unsigned long frac2 : _FP_W_TYPE_SIZE; + unsigned long frac1 : _FP_W_TYPE_SIZE; + unsigned long frac0 : _FP_W_TYPE_SIZE; +# else + unsigned long frac0 : _FP_W_TYPE_SIZE; + unsigned long frac1 : _FP_W_TYPE_SIZE; + unsigned long frac2 : _FP_W_TYPE_SIZE; + unsigned long frac3 : _FP_FRACBITS_Q - (_FP_IMPLBIT_Q != 0)-(_FP_W_TYPE_SIZE * 3); + unsigned exp : _FP_EXPBITS_Q; + unsigned sign : 1; +# endif /* not bigendian */ + } bits __attribute__ ((packed)); +}; + + +# define FP_DECL_Q(X) _FP_DECL (4, X) +# define FP_UNPACK_RAW_Q(X, val) _FP_UNPACK_RAW_4 (Q, X, (val)) +# define FP_UNPACK_RAW_QP(X, val) _FP_UNPACK_RAW_4_P (Q, X, (val)) +# define FP_PACK_RAW_Q(val, X) _FP_PACK_RAW_4 (Q, (val), X) +# define FP_PACK_RAW_QP(val, X) \ + do \ + { \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_4_P (Q, (val), X); \ + } \ + while (0) + +# define FP_UNPACK_Q(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_4 (Q, X, (val)); \ + _FP_UNPACK_CANONICAL (Q, 4, X); \ + } \ + while (0) + +# define FP_UNPACK_QP(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_4_P (Q, X, (val)); \ + _FP_UNPACK_CANONICAL (Q, 4, X); \ + } \ + while (0) + +# define FP_UNPACK_SEMIRAW_Q(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_4 (Q, X, (val)); \ + _FP_UNPACK_SEMIRAW (Q, 4, X); \ + } \ + while (0) + +# define FP_UNPACK_SEMIRAW_QP(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_4_P (Q, X, (val)); \ + _FP_UNPACK_SEMIRAW (Q, 4, X); \ + } \ + while (0) + +# define FP_PACK_Q(val, X) \ + do \ + { \ + _FP_PACK_CANONICAL (Q, 4, X); \ + _FP_PACK_RAW_4 (Q, (val), X); \ + } \ + while (0) + +# define FP_PACK_QP(val, X) \ + do \ + { \ + _FP_PACK_CANONICAL (Q, 4, X); \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_4_P (Q, (val), X); \ + } \ + while (0) + +# define FP_PACK_SEMIRAW_Q(val, X) \ + do \ + { \ + _FP_PACK_SEMIRAW (Q, 4, X); \ + _FP_PACK_RAW_4 (Q, (val), X); \ + } \ + while (0) + +# define FP_PACK_SEMIRAW_QP(val, X) \ + do \ + { \ + _FP_PACK_SEMIRAW (Q, 4, X); \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_4_P (Q, (val), X); \ + } \ + while (0) + +# define FP_ISSIGNAN_Q(X) _FP_ISSIGNAN (Q, 4, X) +# define FP_NEG_Q(R, X) _FP_NEG (Q, 4, R, X) +# define FP_ADD_Q(R, X, Y) _FP_ADD (Q, 4, R, X, Y) +# define FP_SUB_Q(R, X, Y) _FP_SUB (Q, 4, R, X, Y) +# define FP_MUL_Q(R, X, Y) _FP_MUL (Q, 4, R, X, Y) +# define FP_DIV_Q(R, X, Y) _FP_DIV (Q, 4, R, X, Y) +# define FP_SQRT_Q(R, X) _FP_SQRT (Q, 4, R, X) +# define _FP_SQRT_MEAT_Q(R, S, T, X, Q) _FP_SQRT_MEAT_4 (R, S, T, X, (Q)) +# define FP_FMA_Q(R, X, Y, Z) _FP_FMA (Q, 4, 8, R, X, Y, Z) + +# define FP_CMP_Q(r, X, Y, un, ex) _FP_CMP (Q, 4, (r), X, Y, (un), (ex)) +# define FP_CMP_EQ_Q(r, X, Y, ex) _FP_CMP_EQ (Q, 4, (r), X, Y, (ex)) +# define FP_CMP_UNORD_Q(r, X, Y, ex) _FP_CMP_UNORD (Q, 4, (r), X, Y, (ex)) + +# define FP_TO_INT_Q(r, X, rsz, rsg) _FP_TO_INT (Q, 4, (r), X, (rsz), (rsg)) +# define FP_TO_INT_ROUND_Q(r, X, rsz, rsg) \ + _FP_TO_INT_ROUND (Q, 4, (r), X, (rsz), (rsg)) +# define FP_FROM_INT_Q(X, r, rs, rt) _FP_FROM_INT (Q, 4, X, (r), (rs), rt) + +# define _FP_FRAC_HIGH_Q(X) _FP_FRAC_HIGH_4 (X) +# define _FP_FRAC_HIGH_RAW_Q(X) _FP_FRAC_HIGH_4 (X) + +# define _FP_FRAC_HIGH_DW_Q(X) _FP_FRAC_HIGH_8 (X) + +#else /* not _FP_W_TYPE_SIZE < 64 */ +union _FP_UNION_Q +{ + TFtype flt /* __attribute__ ((mode (TF))) */ ; + struct _FP_STRUCT_LAYOUT + { + _FP_W_TYPE a, b; + } longs; + struct _FP_STRUCT_LAYOUT + { +# if __BYTE_ORDER == __BIG_ENDIAN + unsigned sign : 1; + unsigned exp : _FP_EXPBITS_Q; + _FP_W_TYPE frac1 : _FP_FRACBITS_Q - (_FP_IMPLBIT_Q != 0) - _FP_W_TYPE_SIZE; + _FP_W_TYPE frac0 : _FP_W_TYPE_SIZE; +# else + _FP_W_TYPE frac0 : _FP_W_TYPE_SIZE; + _FP_W_TYPE frac1 : _FP_FRACBITS_Q - (_FP_IMPLBIT_Q != 0) - _FP_W_TYPE_SIZE; + unsigned exp : _FP_EXPBITS_Q; + unsigned sign : 1; +# endif + } bits; +}; + +# define FP_DECL_Q(X) _FP_DECL (2, X) +# define FP_UNPACK_RAW_Q(X, val) _FP_UNPACK_RAW_2 (Q, X, (val)) +# define FP_UNPACK_RAW_QP(X, val) _FP_UNPACK_RAW_2_P (Q, X, (val)) +# define FP_PACK_RAW_Q(val, X) _FP_PACK_RAW_2 (Q, (val), X) +# define FP_PACK_RAW_QP(val, X) \ + do \ + { \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_2_P (Q, (val), X); \ + } \ + while (0) + +# define FP_UNPACK_Q(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_2 (Q, X, (val)); \ + _FP_UNPACK_CANONICAL (Q, 2, X); \ + } \ + while (0) + +# define FP_UNPACK_QP(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_2_P (Q, X, (val)); \ + _FP_UNPACK_CANONICAL (Q, 2, X); \ + } \ + while (0) + +# define FP_UNPACK_SEMIRAW_Q(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_2 (Q, X, (val)); \ + _FP_UNPACK_SEMIRAW (Q, 2, X); \ + } \ + while (0) + +# define FP_UNPACK_SEMIRAW_QP(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_2_P (Q, X, (val)); \ + _FP_UNPACK_SEMIRAW (Q, 2, X); \ + } \ + while (0) + +# define FP_PACK_Q(val, X) \ + do \ + { \ + _FP_PACK_CANONICAL (Q, 2, X); \ + _FP_PACK_RAW_2 (Q, (val), X); \ + } \ + while (0) + +# define FP_PACK_QP(val, X) \ + do \ + { \ + _FP_PACK_CANONICAL (Q, 2, X); \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_2_P (Q, (val), X); \ + } \ + while (0) + +# define FP_PACK_SEMIRAW_Q(val, X) \ + do \ + { \ + _FP_PACK_SEMIRAW (Q, 2, X); \ + _FP_PACK_RAW_2 (Q, (val), X); \ + } \ + while (0) + +# define FP_PACK_SEMIRAW_QP(val, X) \ + do \ + { \ + _FP_PACK_SEMIRAW (Q, 2, X); \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_2_P (Q, (val), X); \ + } \ + while (0) + +# define FP_ISSIGNAN_Q(X) _FP_ISSIGNAN (Q, 2, X) +# define FP_NEG_Q(R, X) _FP_NEG (Q, 2, R, X) +# define FP_ADD_Q(R, X, Y) _FP_ADD (Q, 2, R, X, Y) +# define FP_SUB_Q(R, X, Y) _FP_SUB (Q, 2, R, X, Y) +# define FP_MUL_Q(R, X, Y) _FP_MUL (Q, 2, R, X, Y) +# define FP_DIV_Q(R, X, Y) _FP_DIV (Q, 2, R, X, Y) +# define FP_SQRT_Q(R, X) _FP_SQRT (Q, 2, R, X) +# define _FP_SQRT_MEAT_Q(R, S, T, X, Q) _FP_SQRT_MEAT_2 (R, S, T, X, (Q)) +# define FP_FMA_Q(R, X, Y, Z) _FP_FMA (Q, 2, 4, R, X, Y, Z) + +# define FP_CMP_Q(r, X, Y, un, ex) _FP_CMP (Q, 2, (r), X, Y, (un), (ex)) +# define FP_CMP_EQ_Q(r, X, Y, ex) _FP_CMP_EQ (Q, 2, (r), X, Y, (ex)) +# define FP_CMP_UNORD_Q(r, X, Y, ex) _FP_CMP_UNORD (Q, 2, (r), X, Y, (ex)) + +# define FP_TO_INT_Q(r, X, rsz, rsg) _FP_TO_INT (Q, 2, (r), X, (rsz), (rsg)) +# define FP_TO_INT_ROUND_Q(r, X, rsz, rsg) \ + _FP_TO_INT_ROUND (Q, 2, (r), X, (rsz), (rsg)) +# define FP_FROM_INT_Q(X, r, rs, rt) _FP_FROM_INT (Q, 2, X, (r), (rs), rt) + +# define _FP_FRAC_HIGH_Q(X) _FP_FRAC_HIGH_2 (X) +# define _FP_FRAC_HIGH_RAW_Q(X) _FP_FRAC_HIGH_2 (X) + +# define _FP_FRAC_HIGH_DW_Q(X) _FP_FRAC_HIGH_4 (X) + +#endif /* not _FP_W_TYPE_SIZE < 64 */ + +#endif /* !SOFT_FP_QUAD_H */ diff --git a/REORG.TODO/soft-fp/single.h b/REORG.TODO/soft-fp/single.h new file mode 100644 index 0000000000..75ade9fbe5 --- /dev/null +++ b/REORG.TODO/soft-fp/single.h @@ -0,0 +1,199 @@ +/* Software floating-point emulation. + Definitions for IEEE Single Precision. + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com), + Jakub Jelinek (jj@ultra.linux.cz), + David S. Miller (davem@redhat.com) and + Peter Maydell (pmaydell@chiark.greenend.org.uk). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#ifndef SOFT_FP_SINGLE_H +#define SOFT_FP_SINGLE_H 1 + +#if _FP_W_TYPE_SIZE < 32 +# error "Here's a nickel kid. Go buy yourself a real computer." +#endif + +#define _FP_FRACTBITS_S _FP_W_TYPE_SIZE + +#if _FP_W_TYPE_SIZE < 64 +# define _FP_FRACTBITS_DW_S (2 * _FP_W_TYPE_SIZE) +#else +# define _FP_FRACTBITS_DW_S _FP_W_TYPE_SIZE +#endif + +#define _FP_FRACBITS_S 24 +#define _FP_FRACXBITS_S (_FP_FRACTBITS_S - _FP_FRACBITS_S) +#define _FP_WFRACBITS_S (_FP_WORKBITS + _FP_FRACBITS_S) +#define _FP_WFRACXBITS_S (_FP_FRACTBITS_S - _FP_WFRACBITS_S) +#define _FP_EXPBITS_S 8 +#define _FP_EXPBIAS_S 127 +#define _FP_EXPMAX_S 255 +#define _FP_QNANBIT_S ((_FP_W_TYPE) 1 << (_FP_FRACBITS_S-2)) +#define _FP_QNANBIT_SH_S ((_FP_W_TYPE) 1 << (_FP_FRACBITS_S-2+_FP_WORKBITS)) +#define _FP_IMPLBIT_S ((_FP_W_TYPE) 1 << (_FP_FRACBITS_S-1)) +#define _FP_IMPLBIT_SH_S ((_FP_W_TYPE) 1 << (_FP_FRACBITS_S-1+_FP_WORKBITS)) +#define _FP_OVERFLOW_S ((_FP_W_TYPE) 1 << (_FP_WFRACBITS_S)) + +#define _FP_WFRACBITS_DW_S (2 * _FP_WFRACBITS_S) +#define _FP_WFRACXBITS_DW_S (_FP_FRACTBITS_DW_S - _FP_WFRACBITS_DW_S) +#define _FP_HIGHBIT_DW_S \ + ((_FP_W_TYPE) 1 << (_FP_WFRACBITS_DW_S - 1) % _FP_W_TYPE_SIZE) + +/* The implementation of _FP_MUL_MEAT_S and _FP_DIV_MEAT_S should be + chosen by the target machine. */ + +typedef float SFtype __attribute__ ((mode (SF))); + +union _FP_UNION_S +{ + SFtype flt; + struct _FP_STRUCT_LAYOUT + { +#if __BYTE_ORDER == __BIG_ENDIAN + unsigned sign : 1; + unsigned exp : _FP_EXPBITS_S; + unsigned frac : _FP_FRACBITS_S - (_FP_IMPLBIT_S != 0); +#else + unsigned frac : _FP_FRACBITS_S - (_FP_IMPLBIT_S != 0); + unsigned exp : _FP_EXPBITS_S; + unsigned sign : 1; +#endif + } bits __attribute__ ((packed)); +}; + +#define FP_DECL_S(X) _FP_DECL (1, X) +#define FP_UNPACK_RAW_S(X, val) _FP_UNPACK_RAW_1 (S, X, (val)) +#define FP_UNPACK_RAW_SP(X, val) _FP_UNPACK_RAW_1_P (S, X, (val)) +#define FP_PACK_RAW_S(val, X) _FP_PACK_RAW_1 (S, (val), X) +#define FP_PACK_RAW_SP(val, X) \ + do \ + { \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_1_P (S, (val), X); \ + } \ + while (0) + +#define FP_UNPACK_S(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_1 (S, X, (val)); \ + _FP_UNPACK_CANONICAL (S, 1, X); \ + } \ + while (0) + +#define FP_UNPACK_SP(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_1_P (S, X, (val)); \ + _FP_UNPACK_CANONICAL (S, 1, X); \ + } \ + while (0) + +#define FP_UNPACK_SEMIRAW_S(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_1 (S, X, (val)); \ + _FP_UNPACK_SEMIRAW (S, 1, X); \ + } \ + while (0) + +#define FP_UNPACK_SEMIRAW_SP(X, val) \ + do \ + { \ + _FP_UNPACK_RAW_1_P (S, X, (val)); \ + _FP_UNPACK_SEMIRAW (S, 1, X); \ + } \ + while (0) + +#define FP_PACK_S(val, X) \ + do \ + { \ + _FP_PACK_CANONICAL (S, 1, X); \ + _FP_PACK_RAW_1 (S, (val), X); \ + } \ + while (0) + +#define FP_PACK_SP(val, X) \ + do \ + { \ + _FP_PACK_CANONICAL (S, 1, X); \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_1_P (S, (val), X); \ + } \ + while (0) + +#define FP_PACK_SEMIRAW_S(val, X) \ + do \ + { \ + _FP_PACK_SEMIRAW (S, 1, X); \ + _FP_PACK_RAW_1 (S, (val), X); \ + } \ + while (0) + +#define FP_PACK_SEMIRAW_SP(val, X) \ + do \ + { \ + _FP_PACK_SEMIRAW (S, 1, X); \ + if (!FP_INHIBIT_RESULTS) \ + _FP_PACK_RAW_1_P (S, (val), X); \ + } \ + while (0) + +#define FP_ISSIGNAN_S(X) _FP_ISSIGNAN (S, 1, X) +#define FP_NEG_S(R, X) _FP_NEG (S, 1, R, X) +#define FP_ADD_S(R, X, Y) _FP_ADD (S, 1, R, X, Y) +#define FP_SUB_S(R, X, Y) _FP_SUB (S, 1, R, X, Y) +#define FP_MUL_S(R, X, Y) _FP_MUL (S, 1, R, X, Y) +#define FP_DIV_S(R, X, Y) _FP_DIV (S, 1, R, X, Y) +#define FP_SQRT_S(R, X) _FP_SQRT (S, 1, R, X) +#define _FP_SQRT_MEAT_S(R, S, T, X, Q) _FP_SQRT_MEAT_1 (R, S, T, X, (Q)) + +#if _FP_W_TYPE_SIZE < 64 +# define FP_FMA_S(R, X, Y, Z) _FP_FMA (S, 1, 2, R, X, Y, Z) +#else +# define FP_FMA_S(R, X, Y, Z) _FP_FMA (S, 1, 1, R, X, Y, Z) +#endif + +#define FP_CMP_S(r, X, Y, un, ex) _FP_CMP (S, 1, (r), X, Y, (un), (ex)) +#define FP_CMP_EQ_S(r, X, Y, ex) _FP_CMP_EQ (S, 1, (r), X, Y, (ex)) +#define FP_CMP_UNORD_S(r, X, Y, ex) _FP_CMP_UNORD (S, 1, (r), X, Y, (ex)) + +#define FP_TO_INT_S(r, X, rsz, rsg) _FP_TO_INT (S, 1, (r), X, (rsz), (rsg)) +#define FP_TO_INT_ROUND_S(r, X, rsz, rsg) \ + _FP_TO_INT_ROUND (S, 1, (r), X, (rsz), (rsg)) +#define FP_FROM_INT_S(X, r, rs, rt) _FP_FROM_INT (S, 1, X, (r), (rs), rt) + +#define _FP_FRAC_HIGH_S(X) _FP_FRAC_HIGH_1 (X) +#define _FP_FRAC_HIGH_RAW_S(X) _FP_FRAC_HIGH_1 (X) + +#if _FP_W_TYPE_SIZE < 64 +# define _FP_FRAC_HIGH_DW_S(X) _FP_FRAC_HIGH_2 (X) +#else +# define _FP_FRAC_HIGH_DW_S(X) _FP_FRAC_HIGH_1 (X) +#endif + +#endif /* !SOFT_FP_SINGLE_H */ diff --git a/REORG.TODO/soft-fp/soft-fp.h b/REORG.TODO/soft-fp/soft-fp.h new file mode 100644 index 0000000000..a1cdac8e59 --- /dev/null +++ b/REORG.TODO/soft-fp/soft-fp.h @@ -0,0 +1,354 @@ +/* Software floating-point emulation. + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com), + Jakub Jelinek (jj@ultra.linux.cz), + David S. Miller (davem@redhat.com) and + Peter Maydell (pmaydell@chiark.greenend.org.uk). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#ifndef SOFT_FP_H +#define SOFT_FP_H 1 + +#ifdef _LIBC +# include <sfp-machine.h> +#elif defined __KERNEL__ +/* The Linux kernel uses asm/ names for architecture-specific + files. */ +# include <asm/sfp-machine.h> +#else +# include "sfp-machine.h" +#endif + +/* Allow sfp-machine to have its own byte order definitions. */ +#ifndef __BYTE_ORDER +# ifdef _LIBC +# include <endian.h> +# else +# error "endianness not defined by sfp-machine.h" +# endif +#endif + +/* For unreachable default cases in switch statements over bitwise OR + of FP_CLS_* values. */ +#if (defined __GNUC__ \ + && (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 5))) +# define _FP_UNREACHABLE __builtin_unreachable () +#else +# define _FP_UNREACHABLE abort () +#endif + +#if ((defined __GNUC__ \ + && (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 6))) \ + || (defined __STDC_VERSION__ && __STDC_VERSION__ >= 201112L)) +# define _FP_STATIC_ASSERT(expr, msg) \ + _Static_assert ((expr), msg) +#else +# define _FP_STATIC_ASSERT(expr, msg) \ + extern int (*__Static_assert_function (void)) \ + [!!sizeof (struct { int __error_if_negative: (expr) ? 2 : -1; })] +#endif + +/* In the Linux kernel, some architectures have a single function that + uses different kinds of unpacking and packing depending on the + instruction being emulated, meaning it is not readily visible to + the compiler that variables from _FP_DECL and _FP_FRAC_DECL_* + macros are only used in cases where they were initialized. */ +#ifdef __KERNEL__ +# define _FP_ZERO_INIT = 0 +#else +# define _FP_ZERO_INIT +#endif + +#define _FP_WORKBITS 3 +#define _FP_WORK_LSB ((_FP_W_TYPE) 1 << 3) +#define _FP_WORK_ROUND ((_FP_W_TYPE) 1 << 2) +#define _FP_WORK_GUARD ((_FP_W_TYPE) 1 << 1) +#define _FP_WORK_STICKY ((_FP_W_TYPE) 1 << 0) + +#ifndef FP_RND_NEAREST +# define FP_RND_NEAREST 0 +# define FP_RND_ZERO 1 +# define FP_RND_PINF 2 +# define FP_RND_MINF 3 +#endif +#ifndef FP_ROUNDMODE +# define FP_ROUNDMODE FP_RND_NEAREST +#endif + +/* By default don't care about exceptions. */ +#ifndef FP_EX_INVALID +# define FP_EX_INVALID 0 +#endif +#ifndef FP_EX_OVERFLOW +# define FP_EX_OVERFLOW 0 +#endif +#ifndef FP_EX_UNDERFLOW +# define FP_EX_UNDERFLOW 0 +#endif +#ifndef FP_EX_DIVZERO +# define FP_EX_DIVZERO 0 +#endif +#ifndef FP_EX_INEXACT +# define FP_EX_INEXACT 0 +#endif +#ifndef FP_EX_DENORM +# define FP_EX_DENORM 0 +#endif + +/* Sub-exceptions of "invalid". */ +/* Signaling NaN operand. */ +#ifndef FP_EX_INVALID_SNAN +# define FP_EX_INVALID_SNAN 0 +#endif +/* Inf * 0. */ +#ifndef FP_EX_INVALID_IMZ +# define FP_EX_INVALID_IMZ 0 +#endif +/* fma (Inf, 0, c). */ +#ifndef FP_EX_INVALID_IMZ_FMA +# define FP_EX_INVALID_IMZ_FMA 0 +#endif +/* Inf - Inf. */ +#ifndef FP_EX_INVALID_ISI +# define FP_EX_INVALID_ISI 0 +#endif +/* 0 / 0. */ +#ifndef FP_EX_INVALID_ZDZ +# define FP_EX_INVALID_ZDZ 0 +#endif +/* Inf / Inf. */ +#ifndef FP_EX_INVALID_IDI +# define FP_EX_INVALID_IDI 0 +#endif +/* sqrt (negative). */ +#ifndef FP_EX_INVALID_SQRT +# define FP_EX_INVALID_SQRT 0 +#endif +/* Invalid conversion to integer. */ +#ifndef FP_EX_INVALID_CVI +# define FP_EX_INVALID_CVI 0 +#endif +/* Invalid comparison. */ +#ifndef FP_EX_INVALID_VC +# define FP_EX_INVALID_VC 0 +#endif + +/* _FP_STRUCT_LAYOUT may be defined as an attribute to determine the + struct layout variant used for structures where bit-fields are used + to access specific parts of binary floating-point numbers. This is + required for systems where the default ABI uses struct layout with + differences in how consecutive bit-fields are laid out from the + default expected by soft-fp. */ +#ifndef _FP_STRUCT_LAYOUT +# define _FP_STRUCT_LAYOUT +#endif + +#ifdef _FP_DECL_EX +# define FP_DECL_EX \ + int _fex = 0; \ + _FP_DECL_EX +#else +# define FP_DECL_EX int _fex = 0 +#endif + +/* Initialize any machine-specific state used in FP_ROUNDMODE, + FP_TRAPPING_EXCEPTIONS or FP_HANDLE_EXCEPTIONS. */ +#ifndef FP_INIT_ROUNDMODE +# define FP_INIT_ROUNDMODE do {} while (0) +#endif + +/* Initialize any machine-specific state used in + FP_TRAPPING_EXCEPTIONS or FP_HANDLE_EXCEPTIONS. */ +#ifndef FP_INIT_TRAPPING_EXCEPTIONS +# define FP_INIT_TRAPPING_EXCEPTIONS FP_INIT_ROUNDMODE +#endif + +/* Initialize any machine-specific state used in + FP_HANDLE_EXCEPTIONS. */ +#ifndef FP_INIT_EXCEPTIONS +# define FP_INIT_EXCEPTIONS FP_INIT_TRAPPING_EXCEPTIONS +#endif + +#ifndef FP_HANDLE_EXCEPTIONS +# define FP_HANDLE_EXCEPTIONS do {} while (0) +#endif + +/* Whether to flush subnormal inputs to zero with the same sign. */ +#ifndef FP_DENORM_ZERO +# define FP_DENORM_ZERO 0 +#endif + +#ifndef FP_INHIBIT_RESULTS +/* By default we write the results always. + sfp-machine may override this and e.g. + check if some exceptions are unmasked + and inhibit it in such a case. */ +# define FP_INHIBIT_RESULTS 0 +#endif + +#define FP_SET_EXCEPTION(ex) \ + _fex |= (ex) + +#define FP_CUR_EXCEPTIONS \ + (_fex) + +#ifndef FP_TRAPPING_EXCEPTIONS +# define FP_TRAPPING_EXCEPTIONS 0 +#endif + +/* A file using soft-fp may define FP_NO_EXCEPTIONS before including + soft-fp.h to indicate that, although a macro used there could raise + exceptions, or do rounding and potentially thereby raise + exceptions, for some arguments, for the particular arguments used + in that file no exceptions or rounding can occur. Such a file + should not itself use macros relating to handling exceptions and + rounding modes; this is only for indirect uses (in particular, in + _FP_FROM_INT and the macros it calls). */ +#ifdef FP_NO_EXCEPTIONS + +# undef FP_SET_EXCEPTION +# define FP_SET_EXCEPTION(ex) do {} while (0) + +# undef FP_CUR_EXCEPTIONS +# define FP_CUR_EXCEPTIONS 0 + +# undef FP_TRAPPING_EXCEPTIONS +# define FP_TRAPPING_EXCEPTIONS 0 + +# undef FP_ROUNDMODE +# define FP_ROUNDMODE FP_RND_ZERO + +# undef _FP_TININESS_AFTER_ROUNDING +# define _FP_TININESS_AFTER_ROUNDING 0 + +#endif + +/* A file using soft-fp may define FP_NO_EXACT_UNDERFLOW before + including soft-fp.h to indicate that, although a macro used there + could allow for the case of exact underflow requiring the underflow + exception to be raised if traps are enabled, for the particular + arguments used in that file no exact underflow can occur. */ +#ifdef FP_NO_EXACT_UNDERFLOW +# undef FP_TRAPPING_EXCEPTIONS +# define FP_TRAPPING_EXCEPTIONS 0 +#endif + +#define _FP_ROUND_NEAREST(wc, X) \ + do \ + { \ + if ((_FP_FRAC_LOW_##wc (X) & 15) != _FP_WORK_ROUND) \ + _FP_FRAC_ADDI_##wc (X, _FP_WORK_ROUND); \ + } \ + while (0) + +#define _FP_ROUND_ZERO(wc, X) (void) 0 + +#define _FP_ROUND_PINF(wc, X) \ + do \ + { \ + if (!X##_s && (_FP_FRAC_LOW_##wc (X) & 7)) \ + _FP_FRAC_ADDI_##wc (X, _FP_WORK_LSB); \ + } \ + while (0) + +#define _FP_ROUND_MINF(wc, X) \ + do \ + { \ + if (X##_s && (_FP_FRAC_LOW_##wc (X) & 7)) \ + _FP_FRAC_ADDI_##wc (X, _FP_WORK_LSB); \ + } \ + while (0) + +#define _FP_ROUND(wc, X) \ + do \ + { \ + if (_FP_FRAC_LOW_##wc (X) & 7) \ + { \ + FP_SET_EXCEPTION (FP_EX_INEXACT); \ + switch (FP_ROUNDMODE) \ + { \ + case FP_RND_NEAREST: \ + _FP_ROUND_NEAREST (wc, X); \ + break; \ + case FP_RND_ZERO: \ + _FP_ROUND_ZERO (wc, X); \ + break; \ + case FP_RND_PINF: \ + _FP_ROUND_PINF (wc, X); \ + break; \ + case FP_RND_MINF: \ + _FP_ROUND_MINF (wc, X); \ + break; \ + } \ + } \ + } \ + while (0) + +#define FP_CLS_NORMAL 0 +#define FP_CLS_ZERO 1 +#define FP_CLS_INF 2 +#define FP_CLS_NAN 3 + +#define _FP_CLS_COMBINE(x, y) (((x) << 2) | (y)) + +#include "op-1.h" +#include "op-2.h" +#include "op-4.h" +#include "op-8.h" +#include "op-common.h" + +/* Sigh. Silly things longlong.h needs. */ +#define UWtype _FP_W_TYPE +#define W_TYPE_SIZE _FP_W_TYPE_SIZE + +typedef int QItype __attribute__ ((mode (QI))); +typedef int SItype __attribute__ ((mode (SI))); +typedef int DItype __attribute__ ((mode (DI))); +typedef unsigned int UQItype __attribute__ ((mode (QI))); +typedef unsigned int USItype __attribute__ ((mode (SI))); +typedef unsigned int UDItype __attribute__ ((mode (DI))); +#if _FP_W_TYPE_SIZE == 32 +typedef unsigned int UHWtype __attribute__ ((mode (HI))); +#elif _FP_W_TYPE_SIZE == 64 +typedef USItype UHWtype; +#endif + +#ifndef CMPtype +# define CMPtype int +#endif + +#define SI_BITS (__CHAR_BIT__ * (int) sizeof (SItype)) +#define DI_BITS (__CHAR_BIT__ * (int) sizeof (DItype)) + +#ifndef umul_ppmm +# ifdef _LIBC +# include <stdlib/longlong.h> +# else +# include "longlong.h" +# endif +#endif + +#endif /* !SOFT_FP_H */ diff --git a/REORG.TODO/soft-fp/sqrtdf2.c b/REORG.TODO/soft-fp/sqrtdf2.c new file mode 100644 index 0000000000..82b71d0995 --- /dev/null +++ b/REORG.TODO/soft-fp/sqrtdf2.c @@ -0,0 +1,49 @@ +/* Software floating-point emulation. + Return sqrt(a) + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +DFtype +__sqrtdf2 (DFtype a) +{ + FP_DECL_EX; + FP_DECL_D (A); + FP_DECL_D (R); + DFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_D (A, a); + FP_SQRT_D (R, A); + FP_PACK_D (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/sqrtsf2.c b/REORG.TODO/soft-fp/sqrtsf2.c new file mode 100644 index 0000000000..9f89640349 --- /dev/null +++ b/REORG.TODO/soft-fp/sqrtsf2.c @@ -0,0 +1,49 @@ +/* Software floating-point emulation. + Return sqrt(a) + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +SFtype +__sqrtsf2 (SFtype a) +{ + FP_DECL_EX; + FP_DECL_S (A); + FP_DECL_S (R); + SFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_S (A, a); + FP_SQRT_S (R, A); + FP_PACK_S (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/sqrttf2.c b/REORG.TODO/soft-fp/sqrttf2.c new file mode 100644 index 0000000000..7cf9bc6ac6 --- /dev/null +++ b/REORG.TODO/soft-fp/sqrttf2.c @@ -0,0 +1,49 @@ +/* Software floating-point emulation. + Return sqrt(a) + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +TFtype +__sqrttf2 (TFtype a) +{ + FP_DECL_EX; + FP_DECL_Q (A); + FP_DECL_Q (R); + TFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_Q (A, a); + FP_SQRT_Q (R, A); + FP_PACK_Q (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/subdf3.c b/REORG.TODO/soft-fp/subdf3.c new file mode 100644 index 0000000000..4e25d0fcf9 --- /dev/null +++ b/REORG.TODO/soft-fp/subdf3.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return a - b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +DFtype +__subdf3 (DFtype a, DFtype b) +{ + FP_DECL_EX; + FP_DECL_D (A); + FP_DECL_D (B); + FP_DECL_D (R); + DFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_SEMIRAW_D (A, a); + FP_UNPACK_SEMIRAW_D (B, b); + FP_SUB_D (R, A, B); + FP_PACK_SEMIRAW_D (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/subsf3.c b/REORG.TODO/soft-fp/subsf3.c new file mode 100644 index 0000000000..6a78a8bdba --- /dev/null +++ b/REORG.TODO/soft-fp/subsf3.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return a - b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +SFtype +__subsf3 (SFtype a, SFtype b) +{ + FP_DECL_EX; + FP_DECL_S (A); + FP_DECL_S (B); + FP_DECL_S (R); + SFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_SEMIRAW_S (A, a); + FP_UNPACK_SEMIRAW_S (B, b); + FP_SUB_S (R, A, B); + FP_PACK_SEMIRAW_S (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/subtf3.c b/REORG.TODO/soft-fp/subtf3.c new file mode 100644 index 0000000000..04781b2eb9 --- /dev/null +++ b/REORG.TODO/soft-fp/subtf3.c @@ -0,0 +1,51 @@ +/* Software floating-point emulation. + Return a - b + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +TFtype +__subtf3 (TFtype a, TFtype b) +{ + FP_DECL_EX; + FP_DECL_Q (A); + FP_DECL_Q (B); + FP_DECL_Q (R); + TFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_SEMIRAW_Q (A, a); + FP_UNPACK_SEMIRAW_Q (B, b); + FP_SUB_Q (R, A, B); + FP_PACK_SEMIRAW_Q (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/testit.c b/REORG.TODO/soft-fp/testit.c new file mode 100644 index 0000000000..1aaf8b45c8 --- /dev/null +++ b/REORG.TODO/soft-fp/testit.c @@ -0,0 +1,788 @@ +#include <stdio.h> +#include <stdlib.h> +#include <math.h> + +#include "soft-fp.h" +#include "single.h" +#include "double.h" + +#include <fpu_control.h> + +/*======================================================================*/ +/* declarations for the functions we are testing */ + +double __adddf3(double, double); +double __subdf3(double, double); +double __muldf3(double, double); +double __divdf3(double, double); +double __negdf2(double); +double __sqrtdf2(double); +double __negdf3(double a, double dummy) { return __negdf2(a); } +double __sqrtdf3(double a, double dummy) { return __sqrtdf2(a); } + +float __addsf3(float, float); +float __subsf3(float, float); +float __mulsf3(float, float); +float __divsf3(float, float); +float __negsf2(float); +float __sqrtsf2(float); +float __negsf3(float a, float dummy) { return __negsf2(a); } +float __sqrtsf3(float a, float dummy) { return __sqrtsf2(a); } + +int __fixdfsi(double); +int __fixsfsi(float); +double __floatsidf(int); +float __floatsisf(int); +double __extendsfdf2(float); +float __truncdfsf2(double); + +int __eqdf2(double, double); +int __nedf2(double, double); +int __gtdf2(double, double); +int __gedf2(double, double); +int __ltdf2(double, double); +int __ledf2(double, double); + +int __eqsf2(float, float); +int __nesf2(float, float); +int __gtsf2(float, float); +int __gesf2(float, float); +int __ltsf2(float, float); +int __lesf2(float, float); + +/*======================================================================*/ +/* definitions for functions we are checking against */ + +double r_adddf3(double a, double b) { return a + b; } +double r_subdf3(double a, double b) { return a - b; } +double r_muldf3(double a, double b) { return a * b; } +double r_divdf3(double a, double b) { return a / b; } +double r_negdf3(double a, double b) { return -a; } +double sqrt(double x); +double r_sqrtdf3(double a, double b) { return sqrt(a); } + +float r_addsf3(float a, float b) { return a + b; } +float r_subsf3(float a, float b) { return a - b; } +float r_mulsf3(float a, float b) { return a * b; } +float r_divsf3(float a, float b) { return a / b; } +float r_negsf3(float a, float b) { return -a; } +float sqrtf(float x); +float r_sqrtsf3(float a, float b) { return sqrtf(a); } + +int r_fixdfsi(double a) { return (int)a; } +int r_fixsfsi(float a) { return (int)a; } +double r_floatsidf(int a) { return (double)a; } +float r_floatsisf(int a) { return (float)a; } +double r_extendsfdf2(float a) { return (double)a; } +float r_truncdfsf2(double a) { return (float)a; } + +int r_eqdf2(double a, double b) { return !(a == b); } +int r_nedf2(double a, double b) { return a != b; } +int r_gtdf2(double a, double b) { return a > b; } +int r_gedf2(double a, double b) { return (a >= b) - 1; } +int r_ltdf2(double a, double b) { return -(a < b); } +int r_ledf2(double a, double b) { return 1 - (a <= b); } + +int r_eqsf2(float a, float b) { return !(a == b); } +int r_nesf2(float a, float b) { return a != b; } +int r_gtsf2(float a, float b) { return a > b; } +int r_gesf2(float a, float b) { return (a >= b) - 1; } +int r_ltsf2(float a, float b) { return -(a < b); } +int r_lesf2(float a, float b) { return 1 - (a <= b); } + +/*======================================================================*/ + +void print_float(float x) +{ + union _FP_UNION_S ux; + ux.flt = x; + printf("%-20.8e %X %02X %06lX", + x, ux.bits.sign, ux.bits.exp, (unsigned long)ux.bits.frac); +} + +void print_double(double x) +{ + union _FP_UNION_D ux; + ux.flt = x; +#if _FP_W_TYPE_SIZE < _FP_FRACBITS_D + printf("%-30.18e %X %04X %06lX%08lX", + x, ux.bits.sign, ux.bits.exp, + (unsigned long)ux.bits.frac1, (unsigned long)ux.bits.frac0); +#else + printf("%-30.18e %X %04X %014lX", + x, ux.bits.sign, ux.bits.exp, + (unsigned long)ux.bits.frac); +#endif +} + +float rand_float(void) +{ + union { + union _FP_UNION_S u; + int i; + } u; + + u.i = lrand48() << 1; + + if (u.u.bits.exp == _FP_EXPMAX_S) + u.u.bits.exp--; + else if (u.u.bits.exp == 0 && u.u.bits.frac != 0) + u.u.bits.exp++; + + return u.u.flt; +} + + +double rand_double(void) +{ + union { + union _FP_UNION_D u; + int i[2]; + } u; + + u.i[0] = lrand48() << 1; + u.i[1] = lrand48() << 1; + + if (u.u.bits.exp == _FP_EXPMAX_D) + u.u.bits.exp--; +#if _FP_W_TYPE_SIZE < _FP_FRACBITS_D + else if (u.u.bits.exp == 0 && !(u.u.bits.frac0 == 0 && u.u.bits.frac1 == 0)) + u.u.bits.exp++; +#else + else if (u.u.bits.exp == 0 && u.u.bits.frac != 0) + u.u.bits.exp++; +#endif + + return u.u.flt; +} + +#define NSPECIALS 10 + +float gen_special_float(int i) +{ + FP_DECL_EX; + FP_DECL_S(X); + float x; + + switch (i & ~1) + { + case 0: + X_c = FP_CLS_NAN; X_f = 0x1234; + break; + case 2: + X_c = FP_CLS_NAN; X_f = 0x1; + break; + case 4: + X_c = FP_CLS_INF; + break; + case 6: + X_c = FP_CLS_ZERO; + break; + case 8: + X_c = FP_CLS_NORMAL; X_e = 0; + X_f = 0x4321; + break; + } + X_s = (i & 1); + + FP_PACK_S(x, X); + return x; +} + +double gen_special_double(int i) +{ + FP_DECL_EX; + FP_DECL_D(X); + double x; + + switch (i & ~1) + { + case 0: + X_c = FP_CLS_NAN; +#if _FP_W_TYPE_SIZE < _FP_FRACBITS_D + __FP_FRAC_SET_2(X, _FP_QNANNEGATEDP ? 0 : _FP_QNANBIT_D, 0x1234); +#else + _FP_FRAC_SET_1(X, (_FP_QNANNEGATEDP ? 0 : _FP_QNANBIT_D) | 0x1234); +#endif + break; + case 2: + X_c = FP_CLS_NAN; +#if _FP_W_TYPE_SIZE < _FP_FRACBITS_D + __FP_FRAC_SET_2(X, _FP_QNANNEGATEDP ? 0 : _FP_QNANBIT_D, 0x1); +#else + _FP_FRAC_SET_1(X, (_FP_QNANNEGATEDP ? 0 : _FP_QNANBIT_D) | 0x1); +#endif + break; + case 4: + X_c = FP_CLS_INF; + break; + case 6: + X_c = FP_CLS_ZERO; + break; + case 8: + X_c = FP_CLS_NORMAL; X_e = 0; +#if _FP_W_TYPE_SIZE < _FP_FRACBITS_D + __FP_FRAC_SET_2(X, 0, 0x87654321); +#else + _FP_FRAC_SET_1(X, 0x87654321); +#endif + break; + } + X_s = (i & 1); + + FP_PACK_D(x, X); + return x; +} + +float build_float(const char *s, const char *e, const char *f) +{ + union _FP_UNION_S u; + + u.bits.sign = strtoul(s, 0, 16); + u.bits.exp = strtoul(e, 0, 16); + u.bits.frac = strtoul(f, 0, 16); + + return u.flt; +} + +double build_double(const char *s, const char *e, const char *f) +{ + union _FP_UNION_D u; + + u.bits.sign = strtoul(s, 0, 16); + u.bits.exp = strtoul(e, 0, 16); +#if _FP_W_TYPE_SIZE < _FP_FRACBITS_D + { + size_t len = strlen(f)+1; + char *dup = memcpy(alloca(len), f, len); + char *low = dup + len - _FP_W_TYPE_SIZE/4 - 1; + + u.bits.frac0 = strtoul(low, 0, 16); + *low = 0; + u.bits.frac1 = strtoul(dup, 0, 16); + } +#else + u.bits.frac = strtoul(f, 0, 16); +#endif + + return u.flt; +} + +/*======================================================================*/ + +fpu_control_t fcw0, fcw1; + +void test_float_arith(float (*tf)(float, float), + float (*rf)(float, float), + float x, float y) +{ + float tr, rr; + rr = (*rf)(x, y); + tr = (*tf)(x, y); + if (memcmp(&tr, &rr, sizeof(float)) != 0) + { + fputs("error:\n\tx = ", stdout); print_float(x); + fputs("\n\ty = ", stdout); print_float(y); + fputs("\n\ttrue = ", stdout); print_float(rr); + fputs("\n\tfalse = ", stdout); print_float(tr); + putchar('\n'); + } +} + +void test_double_arith(double (*tf)(double, double), + double (*rf)(double, double), + double x, double y) +{ + double tr, rr; +#ifdef __i386__ + /* Don't worry. Even this does not make it error free + on ia32. If the result is denormal, it will not + honour the double precision and generate bad results + anyway. On the other side, who wants to use ia32 + for IEEE math? I don't. */ + _FPU_GETCW(fcw0); + fcw1 = ((fcw0 & ~_FPU_EXTENDED) | _FPU_DOUBLE); + _FPU_SETCW(fcw1); +#endif + rr = (*rf)(x, y); +#ifdef __i386__ + _FPU_SETCW(fcw0); +#endif + tr = (*tf)(x, y); + if (memcmp(&tr, &rr, sizeof(double)) != 0) + { + fputs("error:\n\tx = ", stdout); print_double(x); + fputs("\n\ty = ", stdout); print_double(y); + fputs("\n\ttrue = ", stdout); print_double(rr); + fputs("\n\tfalse = ", stdout); print_double(tr); + putchar('\n'); + } +} + +void test_float_double_conv(float x) +{ + double tr, rr; + rr = r_extendsfdf2(x); + tr = __extendsfdf2(x); + if (memcmp(&tr, &rr, sizeof(double)) != 0) + { + fputs("error:\n\tx = ", stdout); print_float(x); + fputs("\n\ttrue = ", stdout); print_double(rr); + fputs("\n\tfalse = ", stdout); print_double(tr); + putchar('\n'); + } +} + +void test_double_float_conv(double x) +{ + float tr, rr; + rr = r_truncdfsf2(x); + tr = __truncdfsf2(x); + if (memcmp(&tr, &rr, sizeof(float)) != 0) + { + fputs("error:\n\tx = ", stdout); print_double(x); + fputs("\n\ttrue = ", stdout); print_float(rr); + fputs("\n\tfalse = ", stdout); print_float(tr); + putchar('\n'); + } +} + +void test_int_float_conv(int x) +{ + float tr, rr; + rr = r_floatsisf(x); + tr = __floatsisf(x); + if (memcmp(&tr, &rr, sizeof(float)) != 0) + { + printf("error\n\tx = %d", x); + fputs("\n\ttrue = ", stdout); print_float(rr); + fputs("\n\tfalse = ", stdout); print_float(tr); + putchar('\n'); + } +} + +void test_int_double_conv(int x) +{ + double tr, rr; + rr = r_floatsidf(x); + tr = __floatsidf(x); + if (memcmp(&tr, &rr, sizeof(double)) != 0) + { + printf("error\n\tx = %d", x); + fputs("\n\ttrue = ", stdout); print_double(rr); + fputs("\n\tfalse = ", stdout); print_double(tr); + putchar('\n'); + } +} + +void test_float_int_conv(float x) +{ + int tr, rr; + rr = r_fixsfsi(x); + tr = __fixsfsi(x); + if (rr != tr) + { + fputs("error:\n\tx = ", stdout); print_float(x); + printf("\n\ttrue = %d\n\tfalse = %d\n", rr, tr); + } +} + +void test_double_int_conv(double x) +{ + int tr, rr; + rr = r_fixsfsi(x); + tr = __fixsfsi(x); + if (rr != tr) + { + fputs("error:\n\tx = ", stdout); print_double(x); + printf("\n\ttrue = %d\n\tfalse = %d\n", rr, tr); + } +} + +int eq0(int x) { return x == 0; } +int ne0(int x) { return x != 0; } +int le0(int x) { return x <= 0; } +int lt0(int x) { return x < 0; } +int ge0(int x) { return x >= 0; } +int gt0(int x) { return x > 0; } + +void test_float_cmp(int (*tf)(float, float), + int (*rf)(float, float), + int (*cmp0)(int), + float x, float y) +{ + int tr, rr; + rr = (*rf)(x, y); + tr = (*tf)(x, y); + if (cmp0(rr) != cmp0(tr)) + { + fputs("error:\n\tx = ", stdout); print_float(x); + fputs("\n\ty = ", stdout); print_float(y); + printf("\n\ttrue = %d\n\tfalse = %d\n", rr, tr); + } +} + +void test_double_cmp(int (*tf)(double, double), + int (*rf)(double, double), + int (*cmp0)(int), + double x, double y) +{ + int tr, rr; + rr = (*rf)(x, y); + tr = (*tf)(x, y); + if (cmp0(rr) != cmp0(tr)) + { + fputs("error:\n\tx = ", stdout); print_double(x); + fputs("\n\ty = ", stdout); print_double(y); + printf("\n\ttrue = %d\n\tfalse = %d\n", rr, tr); + } +} + + +/*======================================================================*/ + + +int main(int ac, char **av) +{ +#ifdef __alpha__ + __ieee_set_fp_control(0); +#endif + av++, ac--; + switch (*(*av)++) + { + { + float (*r)(float, float); + float (*t)(float, float); + + do { + case 'a': r = r_addsf3; t = __addsf3; break; + case 's': r = r_subsf3; t = __subsf3; break; + case 'm': r = r_mulsf3; t = __mulsf3; break; + case 'd': r = r_divsf3; t = __divsf3; break; + case 'r': r = r_sqrtsf3; t = __sqrtsf3; break; + case 'j': r = r_negsf3; t = __negsf3; break; + } while (0); + + switch (*(*av)++) + { + case 'n': + { + int count = (ac > 1 ? atoi(av[1]) : 100); + while (count--) + test_float_arith(t, r, rand_float(), rand_float()); + } + break; + + case 's': + { + int i, j; + for (i = 0; i < NSPECIALS; i++) + for (j = 0; j < NSPECIALS; j++) + test_float_arith(t, r, gen_special_float(i), + gen_special_float(j)); + } + break; + + case 0: + if (ac < 7) abort(); + test_float_arith(t, r, build_float(av[1], av[2], av[3]), + build_float(av[4], av[5], av[6])); + break; + } + } + break; + + { + double (*r)(double, double); + double (*t)(double, double); + + do { + case 'A': r = r_adddf3; t = __adddf3; break; + case 'S': r = r_subdf3; t = __subdf3; break; + case 'M': r = r_muldf3; t = __muldf3; break; + case 'D': r = r_divdf3; t = __divdf3; break; + case 'R': r = r_sqrtdf3; t = __sqrtdf3; break; + case 'J': r = r_negdf3; t = __negdf3; break; + } while (0); + + switch (*(*av)++) + { + case 'n': + { + int count = (ac > 1 ? atoi(av[1]) : 100); + while (count--) + test_double_arith(t, r, rand_double(), rand_double()); + } + break; + + case 's': + { + int i, j; + for (i = 0; i < NSPECIALS; i++) + for (j = 0; j < NSPECIALS; j++) + test_double_arith(t, r, gen_special_double(i), + gen_special_double(j)); + } + break; + + case 0: + if (ac < 7) abort(); + test_double_arith(t, r, build_double(av[1], av[2], av[3]), + build_double(av[4], av[5], av[6])); + break; + } + } + break; + + case 'c': + switch (*(*av)++) + { + case 'n': + { + int count = (ac > 1 ? atoi(av[1]) : 100); + while (count--) + test_float_double_conv(rand_float()); + } + break; + + case 's': + { + int i; + for (i = 0; i < NSPECIALS; i++) + test_float_double_conv(gen_special_float(i)); + } + break; + + case 0: + if (ac < 4) abort(); + test_float_double_conv(build_float(av[1], av[2], av[3])); + break; + } + break; + + case 'C': + switch (*(*av)++) + { + case 'n': + { + int count = (ac > 1 ? atoi(av[1]) : 100); + while (count--) + test_double_float_conv(rand_double()); + } + break; + + case 's': + { + int i; + for (i = 0; i < NSPECIALS; i++) + test_double_float_conv(gen_special_double(i)); + } + break; + + case 0: + if (ac < 4) abort(); + test_double_float_conv(build_double(av[1], av[2], av[3])); + break; + } + break; + + case 'i': + switch (*(*av)++) + { + case 'n': + { + int count = (ac > 1 ? atoi(av[1]) : 100); + while (count--) + test_int_float_conv(lrand48() << 1); + } + break; + + case 0: + if (ac < 2) abort(); + test_int_float_conv(strtol(av[1], 0, 0)); + break; + } + break; + + case 'I': + switch (*(*av)++) + { + case 'n': + { + int count = (ac > 1 ? atoi(av[1]) : 100); + while (count--) + test_int_double_conv(lrand48() << 1); + } + break; + + case 0: + if (ac < 2) abort(); + test_int_double_conv(strtol(av[1], 0, 0)); + break; + } + break; + + case 'f': + switch (*(*av)++) + { + case 'n': + { + int count = (ac > 1 ? atoi(av[1]) : 100); + while (count--) + test_float_int_conv(rand_float()); + } + break; + + case 's': + { + int i; + for (i = 0; i < NSPECIALS; i++) + test_float_int_conv(gen_special_float(i)); + } + break; + + case 0: + if (ac < 4) abort(); + test_float_int_conv(build_float(av[1], av[2], av[3])); + break; + } + break; + + case 'F': + switch (*(*av)++) + { + case 'n': + { + int count = (ac > 1 ? atoi(av[1]) : 100); + while (count--) + test_double_int_conv(rand_double()); + } + break; + + case 's': + { + int i; + for (i = 0; i < NSPECIALS; i++) + test_double_int_conv(gen_special_double(i)); + } + break; + + case 0: + if (ac < 4) abort(); + test_double_int_conv(build_double(av[1], av[2], av[3])); + break; + } + break; + + { + int (*r)(float, float); + int (*t)(float, float); + int (*c)(int); + + do { + case 'e': r = r_eqsf2; t = __eqsf2; c = eq0; break; + case 'n': r = r_nesf2; t = __nesf2; c = ne0; break; + case 'l': + switch (*(*av)++) + { + case 'e': r = r_lesf2; t = __lesf2; c = le0; break; + case 't': r = r_ltsf2; t = __ltsf2; c = lt0; break; + } + break; + case 'g': + switch (*(*av)++) + { + case 'e': r = r_gesf2; t = __gesf2; c = ge0; break; + case 't': r = r_gtsf2; t = __gtsf2; c = gt0; break; + } + break; + } while (0); + + switch (*(*av)++) + { + case 'n': + { + int count = (ac > 1 ? atoi(av[1]) : 100); + while (count--) + test_float_cmp(t, r, c, rand_float(), rand_float()); + } + break; + + case 's': + { + int i, j; + for (i = 0; i < NSPECIALS; i++) + for (j = 0; j < NSPECIALS; j++) + test_float_cmp(t, r, c, gen_special_float(i), + gen_special_float(j)); + } + break; + + case 0: + if (ac < 7) abort(); + test_float_cmp(t, r, c, build_float(av[1], av[2], av[3]), + build_float(av[4], av[5], av[6])); + break; + } + } + break; + + { + int (*r)(double, double); + int (*t)(double, double); + int (*c)(int); + + do { + case 'E': r = r_eqdf2; t = __eqdf2; c = eq0; break; + case 'N': r = r_nedf2; t = __nedf2; c = ne0; break; + case 'L': + switch (*(*av)++) + { + case 'E': r = r_ledf2; t = __ledf2; c = le0; break; + case 'T': r = r_ltdf2; t = __ltdf2; c = lt0; break; + } + break; + case 'G': + switch (*(*av)++) + { + case 'E': r = r_gedf2; t = __gedf2; c = ge0; break; + case 'T': r = r_gtdf2; t = __gtdf2; c = gt0; break; + } + break; + } while (0); + + switch (*(*av)++) + { + case 'n': + { + int count = (ac > 1 ? atoi(av[1]) : 100); + while (count--) + test_double_cmp(t, r, c, rand_double(), rand_double()); + } + break; + + case 's': + { + int i, j; + for (i = 0; i < NSPECIALS; i++) + for (j = 0; j < NSPECIALS; j++) + test_double_cmp(t, r, c, gen_special_double(i), + gen_special_double(j)); + } + break; + + case 0: + if (ac < 7) abort(); + test_double_cmp(t, r, c, build_double(av[1], av[2], av[3]), + build_double(av[4], av[5], av[6])); + break; + } + } + break; + + default: + abort(); + } + + return 0; +} diff --git a/REORG.TODO/soft-fp/truncdfsf2.c b/REORG.TODO/soft-fp/truncdfsf2.c new file mode 100644 index 0000000000..9c82dbbdb6 --- /dev/null +++ b/REORG.TODO/soft-fp/truncdfsf2.c @@ -0,0 +1,54 @@ +/* Software floating-point emulation. + Truncate IEEE double into IEEE single + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" +#include "double.h" + +SFtype +__truncdfsf2 (DFtype a) +{ + FP_DECL_EX; + FP_DECL_D (A); + FP_DECL_S (R); + SFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_SEMIRAW_D (A, a); +#if _FP_W_TYPE_SIZE < _FP_FRACBITS_D + FP_TRUNC (S, D, 1, 2, R, A); +#else + FP_TRUNC (S, D, 1, 1, R, A); +#endif + FP_PACK_SEMIRAW_S (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/trunctfdf2.c b/REORG.TODO/soft-fp/trunctfdf2.c new file mode 100644 index 0000000000..9ecae0e6ec --- /dev/null +++ b/REORG.TODO/soft-fp/trunctfdf2.c @@ -0,0 +1,54 @@ +/* Software floating-point emulation. + Truncate IEEE quad into IEEE double + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" +#include "quad.h" + +DFtype +__trunctfdf2 (TFtype a) +{ + FP_DECL_EX; + FP_DECL_Q (A); + FP_DECL_D (R); + DFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_SEMIRAW_Q (A, a); +#if (2 * _FP_W_TYPE_SIZE) < _FP_FRACBITS_Q + FP_TRUNC (D, Q, 2, 4, R, A); +#else + FP_TRUNC (D, Q, 1, 2, R, A); +#endif + FP_PACK_SEMIRAW_D (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/trunctfhf2.c b/REORG.TODO/soft-fp/trunctfhf2.c new file mode 100644 index 0000000000..2b8836cb19 --- /dev/null +++ b/REORG.TODO/soft-fp/trunctfhf2.c @@ -0,0 +1,52 @@ +/* Software floating-point emulation. + Truncate IEEE quad into IEEE half. + Copyright (C) 1997-2017 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "half.h" +#include "quad.h" + +HFtype +__trunctfhf2 (TFtype a) +{ + FP_DECL_EX; + FP_DECL_Q (A); + FP_DECL_H (R); + HFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_SEMIRAW_Q (A, a); +#if (2 * _FP_W_TYPE_SIZE) < _FP_FRACBITS_Q + FP_TRUNC (H, Q, 1, 4, R, A); +#else + FP_TRUNC (H, Q, 1, 2, R, A); +#endif + FP_PACK_SEMIRAW_H (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/trunctfsf2.c b/REORG.TODO/soft-fp/trunctfsf2.c new file mode 100644 index 0000000000..d39bcc2b06 --- /dev/null +++ b/REORG.TODO/soft-fp/trunctfsf2.c @@ -0,0 +1,54 @@ +/* Software floating-point emulation. + Truncate IEEE quad into IEEE single + Copyright (C) 1997-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson (rth@cygnus.com) and + Jakub Jelinek (jj@ultra.linux.cz). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" +#include "quad.h" + +SFtype +__trunctfsf2 (TFtype a) +{ + FP_DECL_EX; + FP_DECL_Q (A); + FP_DECL_S (R); + SFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_SEMIRAW_Q (A, a); +#if (2 * _FP_W_TYPE_SIZE) < _FP_FRACBITS_Q + FP_TRUNC (S, Q, 1, 4, R, A); +#else + FP_TRUNC (S, Q, 1, 2, R, A); +#endif + FP_PACK_SEMIRAW_S (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/trunctfxf2.c b/REORG.TODO/soft-fp/trunctfxf2.c new file mode 100644 index 0000000000..404f66865c --- /dev/null +++ b/REORG.TODO/soft-fp/trunctfxf2.c @@ -0,0 +1,53 @@ +/* Software floating-point emulation. + Truncate IEEE quad into IEEE extended + Copyright (C) 2007-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Uros Bizjak (ubizjak@gmail.com). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "extended.h" +#include "quad.h" + +XFtype +__trunctfxf2 (TFtype a) +{ + FP_DECL_EX; + FP_DECL_Q (A); + FP_DECL_E (R); + XFtype r; + + FP_INIT_ROUNDMODE; + FP_UNPACK_SEMIRAW_Q (A, a); +#if (2 * _FP_W_TYPE_SIZE) < _FP_FRACBITS_Q + FP_TRUNC (E, Q, 4, 4, R, A); +#else + FP_TRUNC (E, Q, 2, 2, R, A); +#endif + FP_PACK_SEMIRAW_E (r, R); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/unorddf2.c b/REORG.TODO/soft-fp/unorddf2.c new file mode 100644 index 0000000000..646733c02e --- /dev/null +++ b/REORG.TODO/soft-fp/unorddf2.c @@ -0,0 +1,48 @@ +/* Software floating-point emulation. + Return 1 iff a or b is a NaN, 0 otherwise. + Copyright (C) 2006-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Joseph Myers (joseph@codesourcery.com). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "double.h" + +CMPtype +__unorddf2 (DFtype a, DFtype b) +{ + FP_DECL_EX; + FP_DECL_D (A); + FP_DECL_D (B); + CMPtype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_D (A, a); + FP_UNPACK_RAW_D (B, b); + FP_CMP_UNORD_D (r, A, B, 1); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/unordsf2.c b/REORG.TODO/soft-fp/unordsf2.c new file mode 100644 index 0000000000..4f2470400d --- /dev/null +++ b/REORG.TODO/soft-fp/unordsf2.c @@ -0,0 +1,48 @@ +/* Software floating-point emulation. + Return 1 iff a or b is a NaN, 0 otherwise. + Copyright (C) 2006-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Joseph Myers (joseph@codesourcery.com). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "single.h" + +CMPtype +__unordsf2 (SFtype a, SFtype b) +{ + FP_DECL_EX; + FP_DECL_S (A); + FP_DECL_S (B); + CMPtype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_S (A, a); + FP_UNPACK_RAW_S (B, b); + FP_CMP_UNORD_S (r, A, B, 1); + FP_HANDLE_EXCEPTIONS; + + return r; +} diff --git a/REORG.TODO/soft-fp/unordtf2.c b/REORG.TODO/soft-fp/unordtf2.c new file mode 100644 index 0000000000..50c64c124b --- /dev/null +++ b/REORG.TODO/soft-fp/unordtf2.c @@ -0,0 +1,48 @@ +/* Software floating-point emulation. + Return 1 iff a or b is a NaN, 0 otherwise. + Copyright (C) 2006-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Joseph Myers (joseph@codesourcery.com). + + 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. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file into + combinations with other programs, and to distribute those + combinations without any restriction coming from the use of this + file. (The Lesser General Public License restrictions do apply in + other respects; for example, they cover modification of the file, + and distribution when not linked into a combine executable.) + + 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 + <http://www.gnu.org/licenses/>. */ + +#include "soft-fp.h" +#include "quad.h" + +CMPtype +__unordtf2 (TFtype a, TFtype b) +{ + FP_DECL_EX; + FP_DECL_Q (A); + FP_DECL_Q (B); + CMPtype r; + + FP_INIT_EXCEPTIONS; + FP_UNPACK_RAW_Q (A, a); + FP_UNPACK_RAW_Q (B, b); + FP_CMP_UNORD_Q (r, A, B, 1); + FP_HANDLE_EXCEPTIONS; + + return r; +} |