public inbox for gcc-cvs@sourceware.org
help / color / mirror / Atom feed
* [gcc/devel/gccgo] libgfortran: Provide some further math library fallbacks [PR94694]
@ 2020-07-12 17:27 Ian Lance Taylor
  0 siblings, 0 replies; only message in thread
From: Ian Lance Taylor @ 2020-07-12 17:27 UTC (permalink / raw)
  To: gcc-cvs

[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #1: Type: text/plain; charset="us-ascii", Size: 19553 bytes --]

https://gcc.gnu.org/g:1868599f8daf7798018ce8a8f314015f5a2ac520

commit 1868599f8daf7798018ce8a8f314015f5a2ac520
Author: Jakub Jelinek <jakub@redhat.com>
Date:   Wed Apr 22 19:17:15 2020 +0200

    libgfortran: Provide some further math library fallbacks [PR94694]
    
    The following patch provides some further math library fallbacks.
    fmaf can be implemented using fma if available, fma and fmal can use
    x * y + z as fallback, it is not perfect, but e.g. glibc on various arches
    has been using that as fallback for many years,
    and copysign/copysignl/fabs/fabsl can be implemented using corresponding
    __builtin_* if we make sure that gcc expands it inline instead of using
    a library call (these days it is expanded inline on most targets).
    
    2020-04-22  Jakub Jelinek  <jakub@redhat.com>
    
            PR libfortran/94694
            PR libfortran/94586
            * configure.ac: Add math func checks for fmaf, fma and fmal.  Add
            HAVE_INLINE_BUILTIN_COPYSIGN check.
            * c99_protos.h (copysign, fmaf, fma, fmal): Provide fallback
            prototypes.
            (HAVE_COPYSIGN, HAVE_FMAF, HAVE_FMA, HAVE_FMAL): Define if not
            defined and fallback version is provided.
            * intrinsics/c99_functions.c (copysign, fmaf, fma, fmal): Provide
            fallback implementations if possible
            * configure: Regenerated.
            * config.h.in: Regenerated.
    
            * math.m4 (GCC_CHECK_MATH_INLINE_BUILTIN_FALLBACK1,
            GCC_CHECK_MATH_INLINE_BUILTIN_FALLBACK2): New.

Diff:
---
 config/ChangeLog                       |   8 +-
 config/math.m4                         |  64 +++++++
 libgfortran/ChangeLog                  |  15 ++
 libgfortran/c99_protos.h               |  34 ++++
 libgfortran/config.h.in                |  21 +++
 libgfortran/configure                  | 325 +++++++++++++++++++++++++++++++++
 libgfortran/configure.ac               |   8 +
 libgfortran/intrinsics/c99_functions.c |  77 ++++++++
 8 files changed, 551 insertions(+), 1 deletion(-)

diff --git a/config/ChangeLog b/config/ChangeLog
index 01428dd04ee..82b6d35ede7 100644
--- a/config/ChangeLog
+++ b/config/ChangeLog
@@ -1,8 +1,14 @@
+2020-04-22  Jakub Jelinek  <jakub@redhat.com>
+
+	PR libfortran/94694
+	PR libfortran/94586
+	* math.m4 (GCC_CHECK_MATH_INLINE_BUILTIN_FALLBACK1,
+	GCC_CHECK_MATH_INLINE_BUILTIN_FALLBACK2): New.
+
 2020-02-12  Sandra Loosemore  <sandra@codesourcery.com>
 
 	PR libstdc++/79193
 	PR libstdc++/88999
-
 	* no-executables.m4: Use a non-empty program to test for linker
 	support.
 
diff --git a/config/math.m4 b/config/math.m4
index 155967e5071..e1e88d075ed 100644
--- a/config/math.m4
+++ b/config/math.m4
@@ -48,3 +48,67 @@ main ()
                        [Define to 1 if you have the `$1' function.])
   fi
 ])
+
+dnl GCC_CHECK_MATH_INLINE_BUILTIN_FALLBACK1([name], [type])
+dnl
+dnl Check if math function NAME fallback for function with single
+dnl TYPE argument and TYPE result can be implemented using
+dnl __builtin_NAME expanded inline without needing unavailable math
+dnl library function.
+AC_DEFUN([GCC_CHECK_MATH_INLINE_BUILTIN_FALLBACK1],
+[
+  AC_REQUIRE([GCC_CHECK_LIBM])
+if test $gcc_cv_math_func_$1 = no; then
+  AC_CACHE_CHECK([for inline __builtin_$1], [gcc_cv_math_inline_builtin_$1],
+		 [AC_LINK_IFELSE([AC_LANG_SOURCE([
+$2
+$1_fallback ($2 x)
+{
+  return __builtin_$1 (x);
+}
+
+int
+main ()
+{
+  return 0;
+}
+])],
+[gcc_cv_math_inline_builtin_$1=yes],
+[gcc_cv_math_inline_builtin_$1=no])])
+  if test $gcc_cv_math_inline_builtin_$1 = yes; then
+    AC_DEFINE_UNQUOTED(AS_TR_CPP(HAVE_INLINE_BUILTIN_$1),[1],
+	      [Define to 1 if `__builtin_$1' is expanded inline.])
+  fi
+fi])
+
+dnl GCC_CHECK_MATH_INLINE_BUILTIN_FALLBACK2([name], [type])
+dnl
+dnl Check if math function NAME fallback for function with two
+dnl TYPE arguments and TYPE result can be implemented using
+dnl __builtin_NAME expanded inline without needing unavailable math
+dnl library function.
+AC_DEFUN([GCC_CHECK_MATH_INLINE_BUILTIN_FALLBACK2],
+[
+  AC_REQUIRE([GCC_CHECK_LIBM])
+if test $gcc_cv_math_func_$1 = no; then
+  AC_CACHE_CHECK([for inline __builtin_$1], [gcc_cv_math_inline_builtin_$1],
+		 [AC_LINK_IFELSE([AC_LANG_SOURCE([
+$2
+$1_fallback ($2 x, $2 y)
+{
+  return __builtin_$1 (x, y);
+}
+
+int
+main ()
+{
+  return 0;
+}
+])],
+[gcc_cv_math_inline_builtin_$1=yes],
+[gcc_cv_math_inline_builtin_$1=no])])
+  if test $gcc_cv_math_inline_builtin_$1 = yes; then
+    AC_DEFINE_UNQUOTED(AS_TR_CPP(HAVE_INLINE_BUILTIN_$1),[1],
+	      [Define to 1 if `__builtin_$1' is expanded inline.])
+  fi
+fi])
diff --git a/libgfortran/ChangeLog b/libgfortran/ChangeLog
index 2ca75f190bc..e4d3756f0ca 100644
--- a/libgfortran/ChangeLog
+++ b/libgfortran/ChangeLog
@@ -1,3 +1,18 @@
+2020-04-22  Jakub Jelinek  <jakub@redhat.com>
+
+	PR libfortran/94694
+	PR libfortran/94586
+	* configure.ac: Add math func checks for fmaf, fma and fmal.  Add
+	HAVE_INLINE_BUILTIN_COPYSIGN check.
+	* c99_protos.h (copysign, fmaf, fma, fmal): Provide fallback
+	prototypes.
+	(HAVE_COPYSIGN, HAVE_FMAF, HAVE_FMA, HAVE_FMAL): Define if not
+	defined and fallback version is provided.
+	* intrinsics/c99_functions.c (copysign, fmaf, fma, fmal): Provide
+	fallback implementations if possible
+	* configure: Regenerated.
+	* config.h.in: Regenerated.
+
 2020-04-19  Uroš Bizjak  <ubizjak@gmail.com>
 
 	* config/fpu-387.h (local_feraiseexcept) [__SSE_MATH__]:
diff --git a/libgfortran/c99_protos.h b/libgfortran/c99_protos.h
index 7b0bc720de3..1ffc645cfeb 100644
--- a/libgfortran/c99_protos.h
+++ b/libgfortran/c99_protos.h
@@ -71,6 +71,16 @@ extern float ceilf(float);
 extern float copysignf(float, float);
 #endif
 
+#if !defined(HAVE_COPYSIGN) && defined(HAVE_INLINE_BUILTIN_COPYSIGN)
+#define HAVE_COPYSIGN 1
+extern double copysign(double, double);
+#endif
+
+#if !defined(HAVE_COPYSIGNL) && defined(HAVE_INLINE_BUILTIN_COPYSIGNL)
+#define HAVE_COPYSIGNL 1
+extern long double copysignl(long double, long double);
+#endif
+
 #ifndef HAVE_COSF
 #define HAVE_COSF 1
 extern float cosf(float);
@@ -91,6 +101,16 @@ extern float expf(float);
 extern float fabsf(float);
 #endif
 
+#if !defined(HAVE_FABS) && defined(HAVE_INLINE_BUILTIN_FABS)
+#define HAVE_FABS 1
+extern double fabs(double);
+#endif
+
+#if !defined(HAVE_FABSL) && defined(HAVE_INLINE_BUILTIN_FABSL)
+#define HAVE_FABSL 1
+extern long double fabsl(long double);
+#endif
+
 #ifndef HAVE_FLOORF
 #define HAVE_FLOORF 1
 extern float floorf(float);
@@ -628,6 +648,20 @@ extern float tgammaf (float);
 extern float lgammaf (float);
 #endif
 
+#ifndef HAVE_FMA
+#define HAVE_FMA 1
+extern double fma(double, double, double);
+#endif
+
+#ifndef HAVE_FMAF
+#define HAVE_FMAF 1
+extern float fmaf(float, float, float);
+#endif
+
+#ifndef HAVE_FMAL
+#define HAVE_FMAL 1
+extern long double fmal(long double, long double, long double);
+#endif
 
 #endif  /* C99_PROTOS_H  */
 
diff --git a/libgfortran/config.h.in b/libgfortran/config.h.in
index 44786399987..2d58188e50c 100644
--- a/libgfortran/config.h.in
+++ b/libgfortran/config.h.in
@@ -381,12 +381,21 @@
 /* Define to 1 if you have the `floorl' function. */
 #undef HAVE_FLOORL
 
+/* Define to 1 if you have the `fma' function. */
+#undef HAVE_FMA
+
 /* Define if FMA3 instructions can be compiled. */
 #undef HAVE_FMA3
 
 /* Define if FMA4 instructions can be compiled. */
 #undef HAVE_FMA4
 
+/* Define to 1 if you have the `fmaf' function. */
+#undef HAVE_FMAF
+
+/* Define to 1 if you have the `fmal' function. */
+#undef HAVE_FMAL
+
 /* Define to 1 if you have the `fmod' function. */
 #undef HAVE_FMOD
 
@@ -504,6 +513,18 @@
 /* Define to 1 if you have the <ieeefp.h> header file. */
 #undef HAVE_IEEEFP_H
 
+/* Define to 1 if `__builtin_copysign' is expanded inline. */
+#undef HAVE_INLINE_BUILTIN_COPYSIGN
+
+/* Define to 1 if `__builtin_copysignl' is expanded inline. */
+#undef HAVE_INLINE_BUILTIN_COPYSIGNL
+
+/* Define to 1 if `__builtin_fabs' is expanded inline. */
+#undef HAVE_INLINE_BUILTIN_FABS
+
+/* Define to 1 if `__builtin_fabsl' is expanded inline. */
+#undef HAVE_INLINE_BUILTIN_FABSL
+
 /* Define to 1 if the system has the type `intptr_t'. */
 #undef HAVE_INTPTR_T
 
diff --git a/libgfortran/configure b/libgfortran/configure
index d01654e7c4b..b4cf854ddb3 100755
--- a/libgfortran/configure
+++ b/libgfortran/configure
@@ -19848,6 +19848,150 @@ _ACEOF
 
 
 
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for fmaf" >&5
+$as_echo_n "checking for fmaf... " >&6; }
+if ${gcc_cv_math_func_fmaf+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test x$gcc_no_link = xyes; then
+  as_fn_error $? "Link tests are not allowed after GCC_NO_EXECUTABLES." "$LINENO" 5
+fi
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+#ifdef HAVE_COMPLEX_H
+#include <complex.h>
+#endif
+#ifdef HAVE_MATH_H
+#include <math.h>
+#endif
+
+int (*ptr)() = (int (*)())fmaf;
+
+int
+main ()
+{
+  return 0;
+}
+
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  gcc_cv_math_func_fmaf=yes
+else
+  gcc_cv_math_func_fmaf=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $gcc_cv_math_func_fmaf" >&5
+$as_echo "$gcc_cv_math_func_fmaf" >&6; }
+  if test $gcc_cv_math_func_fmaf = yes; then
+
+cat >>confdefs.h <<_ACEOF
+#define HAVE_FMAF 1
+_ACEOF
+
+  fi
+
+
+
+
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for fma" >&5
+$as_echo_n "checking for fma... " >&6; }
+if ${gcc_cv_math_func_fma+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test x$gcc_no_link = xyes; then
+  as_fn_error $? "Link tests are not allowed after GCC_NO_EXECUTABLES." "$LINENO" 5
+fi
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+#ifdef HAVE_COMPLEX_H
+#include <complex.h>
+#endif
+#ifdef HAVE_MATH_H
+#include <math.h>
+#endif
+
+int (*ptr)() = (int (*)())fma;
+
+int
+main ()
+{
+  return 0;
+}
+
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  gcc_cv_math_func_fma=yes
+else
+  gcc_cv_math_func_fma=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $gcc_cv_math_func_fma" >&5
+$as_echo "$gcc_cv_math_func_fma" >&6; }
+  if test $gcc_cv_math_func_fma = yes; then
+
+cat >>confdefs.h <<_ACEOF
+#define HAVE_FMA 1
+_ACEOF
+
+  fi
+
+
+
+
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for fmal" >&5
+$as_echo_n "checking for fmal... " >&6; }
+if ${gcc_cv_math_func_fmal+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test x$gcc_no_link = xyes; then
+  as_fn_error $? "Link tests are not allowed after GCC_NO_EXECUTABLES." "$LINENO" 5
+fi
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+#ifdef HAVE_COMPLEX_H
+#include <complex.h>
+#endif
+#ifdef HAVE_MATH_H
+#include <math.h>
+#endif
+
+int (*ptr)() = (int (*)())fmal;
+
+int
+main ()
+{
+  return 0;
+}
+
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  gcc_cv_math_func_fmal=yes
+else
+  gcc_cv_math_func_fmal=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $gcc_cv_math_func_fmal" >&5
+$as_echo "$gcc_cv_math_func_fmal" >&6; }
+  if test $gcc_cv_math_func_fmal = yes; then
+
+cat >>confdefs.h <<_ACEOF
+#define HAVE_FMAL 1
+_ACEOF
+
+  fi
+
+
+
+
   { $as_echo "$as_me:${as_lineno-$LINENO}: checking for fmodf" >&5
 $as_echo_n "checking for fmodf... " >&6; }
 if ${gcc_cv_math_func_fmodf+:} false; then :
@@ -25559,6 +25703,187 @@ $as_echo "#define HAVE_CLOG 1" >>confdefs.h
 fi
 
 
+
+
+if test $gcc_cv_math_func_copysign = no; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for inline __builtin_copysign" >&5
+$as_echo_n "checking for inline __builtin_copysign... " >&6; }
+if ${gcc_cv_math_inline_builtin_copysign+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test x$gcc_no_link = xyes; then
+  as_fn_error $? "Link tests are not allowed after GCC_NO_EXECUTABLES." "$LINENO" 5
+fi
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+double
+copysign_fallback (double x, double y)
+{
+  return __builtin_copysign (x, y);
+}
+
+int
+main ()
+{
+  return 0;
+}
+
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  gcc_cv_math_inline_builtin_copysign=yes
+else
+  gcc_cv_math_inline_builtin_copysign=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $gcc_cv_math_inline_builtin_copysign" >&5
+$as_echo "$gcc_cv_math_inline_builtin_copysign" >&6; }
+  if test $gcc_cv_math_inline_builtin_copysign = yes; then
+
+cat >>confdefs.h <<_ACEOF
+#define HAVE_INLINE_BUILTIN_COPYSIGN 1
+_ACEOF
+
+  fi
+fi
+
+
+if test $gcc_cv_math_func_copysignl = no; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for inline __builtin_copysignl" >&5
+$as_echo_n "checking for inline __builtin_copysignl... " >&6; }
+if ${gcc_cv_math_inline_builtin_copysignl+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test x$gcc_no_link = xyes; then
+  as_fn_error $? "Link tests are not allowed after GCC_NO_EXECUTABLES." "$LINENO" 5
+fi
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+long double
+copysignl_fallback (long double x, long double y)
+{
+  return __builtin_copysignl (x, y);
+}
+
+int
+main ()
+{
+  return 0;
+}
+
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  gcc_cv_math_inline_builtin_copysignl=yes
+else
+  gcc_cv_math_inline_builtin_copysignl=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $gcc_cv_math_inline_builtin_copysignl" >&5
+$as_echo "$gcc_cv_math_inline_builtin_copysignl" >&6; }
+  if test $gcc_cv_math_inline_builtin_copysignl = yes; then
+
+cat >>confdefs.h <<_ACEOF
+#define HAVE_INLINE_BUILTIN_COPYSIGNL 1
+_ACEOF
+
+  fi
+fi
+
+
+if test $gcc_cv_math_func_fabs = no; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for inline __builtin_fabs" >&5
+$as_echo_n "checking for inline __builtin_fabs... " >&6; }
+if ${gcc_cv_math_inline_builtin_fabs+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test x$gcc_no_link = xyes; then
+  as_fn_error $? "Link tests are not allowed after GCC_NO_EXECUTABLES." "$LINENO" 5
+fi
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+double
+fabs_fallback (double x)
+{
+  return __builtin_fabs (x);
+}
+
+int
+main ()
+{
+  return 0;
+}
+
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  gcc_cv_math_inline_builtin_fabs=yes
+else
+  gcc_cv_math_inline_builtin_fabs=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $gcc_cv_math_inline_builtin_fabs" >&5
+$as_echo "$gcc_cv_math_inline_builtin_fabs" >&6; }
+  if test $gcc_cv_math_inline_builtin_fabs = yes; then
+
+cat >>confdefs.h <<_ACEOF
+#define HAVE_INLINE_BUILTIN_FABS 1
+_ACEOF
+
+  fi
+fi
+
+
+if test $gcc_cv_math_func_fabsl = no; then
+  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for inline __builtin_fabsl" >&5
+$as_echo_n "checking for inline __builtin_fabsl... " >&6; }
+if ${gcc_cv_math_inline_builtin_fabsl+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  if test x$gcc_no_link = xyes; then
+  as_fn_error $? "Link tests are not allowed after GCC_NO_EXECUTABLES." "$LINENO" 5
+fi
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+long double
+fabsl_fallback (long double x)
+{
+  return __builtin_fabsl (x);
+}
+
+int
+main ()
+{
+  return 0;
+}
+
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+  gcc_cv_math_inline_builtin_fabsl=yes
+else
+  gcc_cv_math_inline_builtin_fabsl=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $gcc_cv_math_inline_builtin_fabsl" >&5
+$as_echo "$gcc_cv_math_inline_builtin_fabsl" >&6; }
+  if test $gcc_cv_math_inline_builtin_fabsl = yes; then
+
+cat >>confdefs.h <<_ACEOF
+#define HAVE_INLINE_BUILTIN_FABSL 1
+_ACEOF
+
+  fi
+fi
+
 # Check whether the system has a working stat()
 
   { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether the target stat is reliable" >&5
diff --git a/libgfortran/configure.ac b/libgfortran/configure.ac
index b2b9ee994aa..711dc60ff78 100644
--- a/libgfortran/configure.ac
+++ b/libgfortran/configure.ac
@@ -392,6 +392,9 @@ GCC_CHECK_MATH_FUNC([cabsl])
 GCC_CHECK_MATH_FUNC([floorf])
 GCC_CHECK_MATH_FUNC([floor])
 GCC_CHECK_MATH_FUNC([floorl])
+GCC_CHECK_MATH_FUNC([fmaf])
+GCC_CHECK_MATH_FUNC([fma])
+GCC_CHECK_MATH_FUNC([fmal])
 GCC_CHECK_MATH_FUNC([fmodf])
 GCC_CHECK_MATH_FUNC([fmod])
 GCC_CHECK_MATH_FUNC([fmodl])
@@ -516,6 +519,11 @@ GCC_CHECK_MATH_FUNC([catanl])
 # On AIX, clog is present in libm as __clog
 AC_CHECK_LIB([m],[__clog],[AC_DEFINE([HAVE_CLOG],[1],[libm includes clog])])
 
+GCC_CHECK_MATH_INLINE_BUILTIN_FALLBACK2([copysign], [double])
+GCC_CHECK_MATH_INLINE_BUILTIN_FALLBACK2([copysignl], [long double])
+GCC_CHECK_MATH_INLINE_BUILTIN_FALLBACK1([fabs], [double])
+GCC_CHECK_MATH_INLINE_BUILTIN_FALLBACK1([fabsl], [long double])
+
 # Check whether the system has a working stat()
 LIBGFOR_CHECK_WORKING_STAT
 
diff --git a/libgfortran/intrinsics/c99_functions.c b/libgfortran/intrinsics/c99_functions.c
index 3ec5aeb8e05..b75d1777c4c 100644
--- a/libgfortran/intrinsics/c99_functions.c
+++ b/libgfortran/intrinsics/c99_functions.c
@@ -229,6 +229,17 @@ ceilf (float x)
 }
 #endif
 
+#if !defined(HAVE_COPYSIGN) && defined(HAVE_INLINE_BUILTIN_COPYSIGN)
+#define HAVE_COPYSIGN 1
+double copysign (double x, double y);
+
+double
+copysign (double x, double y)
+{
+  return __builtin_copysign (x, y);
+}
+#endif
+
 #ifndef HAVE_COPYSIGNF
 #define HAVE_COPYSIGNF 1
 float copysignf (float x, float y);
@@ -240,6 +251,17 @@ copysignf (float x, float y)
 }
 #endif
 
+#if !defined(HAVE_COPYSIGNL) && defined(HAVE_INLINE_BUILTIN_COPYSIGNL)
+#define HAVE_COPYSIGNL 1
+long double copysignl (long double x, long double y);
+
+long double
+copysignl (long double x, long double y)
+{
+  return __builtin_copysignl (x, y);
+}
+#endif
+
 #ifndef HAVE_COSF
 #define HAVE_COSF 1
 float cosf (float x);
@@ -273,6 +295,17 @@ expf (float x)
 }
 #endif
 
+#if !defined(HAVE_FABS) && defined(HAVE_INLINE_BUILTIN_FABS)
+#define HAVE_FABS 1
+double fabs (double x);
+
+double
+fabs (double x)
+{
+  return __builtin_fabs (x);
+}
+#endif
+
 #ifndef HAVE_FABSF
 #define HAVE_FABSF 1
 float fabsf (float x);
@@ -284,6 +317,17 @@ fabsf (float x)
 }
 #endif
 
+#if !defined(HAVE_FABSL) && defined(HAVE_INLINE_BUILTIN_FABSL)
+#define HAVE_FABSL 1
+long double fabsl (long double x);
+
+long double
+fabsl (long double x)
+{
+  return __builtin_fabsl (x);
+}
+#endif
+
 #ifndef HAVE_FLOORF
 #define HAVE_FLOORF 1
 float floorf (float x);
@@ -2112,3 +2156,36 @@ lgammaf (float x)
   return (float) lgamma ((double) x);
 }
 #endif
+
+#ifndef HAVE_FMA
+#define HAVE_FMA 1
+double fma (double, double, double);
+
+double
+fma (double x, double y, double z)
+{
+  return x * y + z;
+}
+#endif
+
+#ifndef HAVE_FMAF
+#define HAVE_FMAF 1
+float fmaf (float, float, float);
+
+float
+fmaf (float x, float y, float z)
+{
+  return fma (x, y, z);
+}
+#endif
+
+#ifndef HAVE_FMAL
+#define HAVE_FMAL 1
+long double fmal (long double, long double, long double);
+
+long double
+fmal (long double x, long double y, long double z)
+{
+  return x * y + z;
+}
+#endif


^ permalink raw reply	[flat|nested] only message in thread

only message in thread, other threads:[~2020-07-12 17:27 UTC | newest]

Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2020-07-12 17:27 [gcc/devel/gccgo] libgfortran: Provide some further math library fallbacks [PR94694] Ian Lance Taylor

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).