This is the mail archive of the
libc-alpha@sourceware.org
mailing list for the glibc project.
[PATCH 2/2] soft-fp: Add new KF routines
- From: "Tulio Magno Quites Machado Filho" <tuliom at linux dot vnet dot ibm dot com>
- To: libc-alpha at sourceware dot org
- Cc: joseph at codesourcery dot com, munroesj at linux dot vnet dot ibm dot com, meissner at linux dot vnet dot ibm dot com, Ulrich dot Weigand at de dot ibm dot com, dje dot gcc at gmail dot com, jakub at redhat dot com, carlos at redhat dot com
- Date: Mon, 26 Oct 2015 16:05:17 -0200
- Subject: [PATCH 2/2] soft-fp: Add new KF routines
- Authentication-results: sourceware.org; auth=none
- References: <cover dot 1445882428 dot git dot tuliom at linux dot vnet dot ibm dot com>
- References: <alpine dot DEB dot 2 dot 10 dot 1509302017260 dot 21553 at digraph dot polyomino dot org dot uk> <cover dot 1445882428 dot git dot tuliom at linux dot vnet dot ibm dot com>
From: Michael Meissner <meissner@linux.vnet.ibm.com>
Add cmpukf2, extendkftf2 and trunctfk2 to soft-fp.
This is the minimal set of routines required to be imported in GCC for
IEEE 128-bit floating point support.
2015-10-26 Michael Meissner <meissner@linux.vnet.ibm.com>
Tulio Magno Quites Machado Filho <tuliom@linux.vnet.ibm.com>
* soft-fp/.gitignore: Negate cmpukf2.c, extendkftf2.c and trunctfk2.c.
* soft-fp/Makefile (gcc-kf-routines): New variable with all KF
routines.
* soft-fp/cmpukf2.c: New file
* soft-fp/extendkftf2.c: Likewise
* soft-fp/trunctfk2.c: Likewise
---
soft-fp/.gitignore | 3 ++
soft-fp/Makefile | 2 ++
soft-fp/cmpukf2.c | 87 +++++++++++++++++++++++++++++++++++++++++++++++++++
soft-fp/extendkftf2.c | 59 ++++++++++++++++++++++++++++++++++
soft-fp/trunctfk2.c | 65 ++++++++++++++++++++++++++++++++++++++
5 files changed, 216 insertions(+)
create mode 100644 soft-fp/cmpukf2.c
create mode 100644 soft-fp/extendkftf2.c
create mode 100644 soft-fp/trunctfk2.c
diff --git a/soft-fp/.gitignore b/soft-fp/.gitignore
index 833e136..f68a4fa 100644
--- a/soft-fp/.gitignore
+++ b/soft-fp/.gitignore
@@ -1 +1,4 @@
*kf*.c
+!cmpukf2.c
+!extendkftf2.c
+!trunctfk2.c
\ No newline at end of file
diff --git a/soft-fp/Makefile b/soft-fp/Makefile
index e392b9d..b398615 100644
--- a/soft-fp/Makefile
+++ b/soft-fp/Makefile
@@ -41,6 +41,8 @@ gcc-quad-routines := negtf2 addtf3 subtf3 multf3 divtf3 eqtf2 \
gcc-kf-routines-auto := $(subst tf,kf,\
$(filter-out sqrttf2,$(gcc-quad-routines)))
+gcc-kf-routines := cmpukf2 extendtfkf2 trunctfk2 $(gcc-kf-routines-auto)
+
generate-routines: $(addsuffix .c,$(gcc-kf-routines-auto))
clean:
diff --git a/soft-fp/cmpukf2.c b/soft-fp/cmpukf2.c
new file mode 100644
index 0000000..d27c544
--- /dev/null
+++ b/soft-fp/cmpukf2.c
@@ -0,0 +1,87 @@
+/* Software IEEE 128-bit floating-point emulation for PowerPC.
+ Copyright (C) 2015 Free Software Foundation, Inc.
+ This file is part of the GNU C Library.
+ Contributed by Michael Meissner (meissner@linux.vnet.ibm.com)
+ Code is based on the main soft-fp library written 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/>. */
+
+/* Force the use of the VSX instruction set. */
+#if defined(_ARCH_PPC) && (!defined(__VSX__) || !defined(__FLOAT128__))
+#pragma GCC target ("vsx,float128")
+#endif
+
+#include "soft-fp.h"
+#include "double.h"
+#include "single.h"
+#include "quad-float128.h"
+
+/* PowerPC condition register bits. */
+#define PPC_UNORDERED 0x1 /* isnan (a) || isnan (b). */
+#define PPC_EQUAL 0x2 /* a == b. */
+#define PPC_GREATER_THEN 0x4 /* a > b. */
+#define PPC_LESS_THEN 0x8 /* a < b. */
+
+/* Map FP_CMP_Q output to PowerPC condition register bits. */
+#define CMP_UNORDERED (-2) /* isnan (a) || isnan (b). */
+#define CMP_LESS_THEN (-1) /* a < b. */
+#define CMP_EQUAL 0 /* a == b. */
+#define CMP_GREATER_THEN 1 /* a < b. */
+#define CMP_INVALID 2 /* raise invalid exception. */
+
+#define CMP_LOW CMP_UNORDERED /* comparison low value. */
+#define CMP_HIGH CMP_INVALID /* comparison high value. */
+
+static const unsigned char ppc_cr_map[] = {
+ PPC_UNORDERED, /* -2: unordered. */
+ PPC_LESS_THEN, /* -1: a < b. */
+ PPC_EQUAL, /* 0: a == b. */
+ PPC_GREATER_THEN, /* 1: a > b. */
+ PPC_UNORDERED, /* 2: invalid. */
+};
+
+/* Compare two IEEE 128-bit floating point values and return the status. We
+ return the status as a 4-bit value that can be copied into an appropriate
+ PowerPC conditon code register. */
+
+CMPtype
+__cmpukf2 (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);
+ if (r == CMP_INVALID)
+ FP_SET_EXCEPTION (FP_EX_INVALID);
+ FP_HANDLE_EXCEPTIONS;
+
+ return (r < CMP_LOW || r > CMP_HIGH) ? PPC_UNORDERED : ppc_cr_map[r-CMP_LOW];
+}
diff --git a/soft-fp/extendkftf2.c b/soft-fp/extendkftf2.c
new file mode 100644
index 0000000..4b78b86
--- /dev/null
+++ b/soft-fp/extendkftf2.c
@@ -0,0 +1,59 @@
+/* Software IEEE 128-bit floating-point emulation for PowerPC.
+ Copyright (C) 2015 Free Software Foundation, Inc.
+ This file is part of the GNU C Library.
+ Contributed by Michael Meissner (meissner@linux.vnet.ibm.com)
+ Code is based on the main soft-fp library written 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/>. */
+
+/* Convert IEEE 128-bit floating point to IBM long double. */
+
+/* Force the use of the VSX instruction set. */
+#if defined(_ARCH_PPC) && (!defined(__VSX__) || !defined(__FLOAT128__))
+#pragma GCC target ("vsx,float128")
+#endif
+
+extern __ibm128 __extendkftf2 (__float128);
+
+__ibm128
+__extendkftf2 (__float128 value)
+{
+ double high, low;
+
+ high = (double) value;
+ if (__builtin_isnan (high) || __builtin_isinf (high))
+ low = high;
+
+ else
+ {
+ low = (double) (value - (__float128)high);
+
+ /* Use copysign to propigate the sign bit so that -0.0Q becomes -0.0L. */
+ low = __builtin_copysign (low, high);
+ }
+
+ return __builtin_pack_longdouble (high, low);
+}
diff --git a/soft-fp/trunctfk2.c b/soft-fp/trunctfk2.c
new file mode 100644
index 0000000..0d38c5a
--- /dev/null
+++ b/soft-fp/trunctfk2.c
@@ -0,0 +1,65 @@
+/* Software IEEE 128-bit floating-point emulation for PowerPC.
+ Copyright (C) 2015 Free Software Foundation, Inc.
+ This file is part of the GNU C Library.
+ Contributed by Michael Meissner (meissner@linux.vnet.ibm.com)
+ Code is based on the main soft-fp library written 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/>. */
+
+/* Convert IBM long double to IEEE 128-bit floating point. */
+
+/* Force the use of the VSX instruction set. */
+#if defined(_ARCH_PPC) && (!defined(__VSX__) || !defined(__FLOAT128__))
+#pragma GCC target ("vsx,float128")
+#endif
+
+extern __float128 __trunctfkf2 (__ibm128);
+
+#ifdef __LITTLE_ENDIAN__
+#define HIGH_WORD 1
+#define LOW_WORD 0
+#else
+#define HIGH_WORD 0
+#define LOW_WORD 1
+#endif
+
+__float128
+__trunctfkf2 (__ibm128 value)
+{
+ double high = __builtin_unpack_longdouble (value, HIGH_WORD);
+ double low = __builtin_unpack_longdouble (value, LOW_WORD);
+
+ /* Handle the special cases of NAN and inifinity. */
+ if (__builtin_isnan (high) || __builtin_isinf (high))
+ return (__float128) high;
+
+ /* If low is 0.0, there no need to do the add. In addition, avoiding the add
+ produces the correct sign if high is -0.0. */
+ if (low == 0.0)
+ return (__float128) high;
+
+ return ((__float128)high) + ((__float128)low);
+}
--
2.1.0