config_vars="$config_vars
have-x86-isa-level = $libc_cv_have_x86_isa_level"
config_vars="$config_vars
+x86-isa-level-2-or-above = 2 3 4"
+config_vars="$config_vars
x86-isa-level-3-or-above = 3 4"
config_vars="$config_vars
+x86-isa-level-4-or-above = 4"
+config_vars="$config_vars
enable-x86-isa-level = $libc_cv_include_x86_isa_level"
AC_DEFINE_UNQUOTED(MINIMUM_X86_ISA_LEVEL, $libc_cv_have_x86_isa_level)
fi
LIBC_CONFIG_VAR([have-x86-isa-level], [$libc_cv_have_x86_isa_level])
+LIBC_CONFIG_VAR([x86-isa-level-2-or-above], [2 3 4])
LIBC_CONFIG_VAR([x86-isa-level-3-or-above], [3 4])
+LIBC_CONFIG_VAR([x86-isa-level-4-or-above], [4])
LIBC_CONFIG_VAR([enable-x86-isa-level], [$libc_cv_include_x86_isa_level])
dnl Check if TEST_CC supports -mfpmath=387
CFLAGS-s_cosf-fma.c = -mfma -mavx2
CFLAGS-s_sincosf-fma.c = -mfma -mavx2
+# Check if ISA level is 2 or above.
+ifeq (,$(filter $(have-x86-isa-level),$(x86-isa-level-2-or-above)))
+sysdep_calls += \
+ s_modf-sse4_1 \
+ s_modff-sse4_1 \
+# sysdep_calls
+endif
+
# Check if ISA level is 3 or above.
ifneq (,$(filter $(have-x86-isa-level),$(x86-isa-level-3-or-above)))
-sysdep_routines += \
- s_modf-avx \
- s_modff-avx \
-# sysdep_routines
libm-sysdep_routines += \
s_ceil-avx \
s_ceilf-avx \
s_floor-avx \
s_floorf-avx \
- s_modf-avx \
- s_modff-avx \
s_nearbyint-avx \
s_nearbyintf-avx \
s_rint-avx \
s_truncf-avx \
# libm-sysdep_routines
else
+sysdep_calls += \
+ s_modf-avx \
+ s_modff-avx \
+# sysdep_calls
ifeq (no,$(have-x86-apx))
libm-sysdep_routines += \
e_asin-fma4 \
s_tan-fma4 \
# libm-sysdep_routines
endif
-sysdep_routines += \
- s_modf-sse4_1 \
- s_modff-sse4_1 \
-# sysdep_routines
libm-sysdep_routines += \
e_asin-fma \
e_atan2-avx \
s_floor-sse4_1 \
s_floorf-sse4_1 \
s_log1p-fma \
- s_modf-sse4_1 \
- s_modff-sse4_1 \
s_nearbyint-sse4_1 \
s_nearbyintf-sse4_1 \
s_rint-sse4_1 \
s_truncf-sse4_1 \
# libm-sysdep_routines
ifeq ($(have-x86-isa-level),baseline)
-sysdep_routines += \
- s_modf-c \
- s_modff-c \
-# sysdep-routines
libm-sysdep_routines += \
s_ceil-c \
s_ceilf-c \
s_floor-c \
s_floorf-c \
- s_modf-c \
- s_modff-c \
s_nearbyint-c \
s_nearbyintf-c \
s_rint-c \
s_truncf-c \
# libm-sysdep_routines
endif
+
+# $(sysdep_calls) functions are built both for libc and libm. While the
+# libc objects have the prefix s_, the libm ones are prefixed with m_.
+sysdep_routines += $(sysdep_calls)
+libm-sysdep_routines += $(sysdep_calls:s_%=m_%)
endif
CFLAGS-e_asin-fma4.c = -mfma4
CFLAGS-s_tan-avx.c = -msse2avx -DSSE2AVX
CFLAGS-s_sincos-avx.c = -msse2avx -DSSE2AVX
-CFLAGS-s_modf-c.c = $(no-stack-protector)
-CFLAGS-s_modff-c.c = $(no-stack-protector)
-
-CFLAGS-s_modf-sse4_1.c = -msse4.1 -fno-builtin-modff32x \
- -fno-builtin-modff64 $(no-stack-protector)
-CFLAGS-s_modff-sse4_1.c = -msse4.1 -fno-builtin-modff32 \
- $(no-stack-protector)
+CFLAGS-s_modf-sse4_1.c = -msse4.1 -fno-builtin-modff32x -fno-builtin-modff64
+CFLAGS-s_modff-sse4_1.c = -msse4.1 -fno-builtin-modff32
-CFLAGS-s_modf-avx.c = -msse2avx -DSSE2AVX -fno-builtin-modff32x \
- $(no-stack-protector) -fno-builtin-modff64
-CFLAGS-s_modff-avx.c = -msse2avx -DSSE2AVX -fno-builtin-modff32 \
- $(no-stack-protector)
+CFLAGS-s_modf-avx.c = -mavx -fno-builtin-modff32x -fno-builtin-modff64
+CFLAGS-s_modff-avx.c = -mavx -fno-builtin-modff32
endif
ifeq ($(subdir),mathvec)
--- /dev/null
+/* Common definition for ifunc selections optimized with SSE4.1 and AVX.
+ Copyright (C) 2025 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
+ <https://www.gnu.org/licenses/>. */
+
+#include <init-arch.h>
+
+extern __typeof (REDIRECT_NAME) OPTIMIZE (sse2) attribute_hidden;
+extern __typeof (REDIRECT_NAME) OPTIMIZE (sse41) attribute_hidden;
+extern __typeof (REDIRECT_NAME) OPTIMIZE (avx) attribute_hidden;
+
+static inline void *
+IFUNC_SELECTOR (void)
+{
+ const struct cpu_features* cpu_features = __get_cpu_features ();
+
+ if (CPU_FEATURE_USABLE_P (cpu_features, AVX))
+ return OPTIMIZE (avx);
+
+#if MINIMUM_X86_ISA_LEVEL == SSE4_1_X86_ISA_LEVEL
+ return OPTIMIZE (sse41);
+#else
+ if (CPU_FEATURE_USABLE_P (cpu_features, SSE4_1))
+ return OPTIMIZE (sse41);
+
+ return OPTIMIZE (sse2);
+#endif
+}
+#define __modf __modf_avx
+
#include <sysdeps/ieee754/dbl-64/s_modf.c>
+++ /dev/null
-#define __modf __modf_c
-#include <sysdeps/ieee754/dbl-64/s_modf.c>
-#include <sysdeps/x86/isa-level.h>
-
-#if MINIMUM_X86_ISA_LEVEL != SSE4_1_X86_ISA_LEVEL
-# define __modf __modf_sse41
-#endif
+#define __modf __modf_sse41
#include <sysdeps/ieee754/dbl-64/s_modf.c>
<https://www.gnu.org/licenses/>. */
#include <sysdeps/x86/isa-level.h>
-#if MINIMUM_X86_ISA_LEVEL < SSE4_1_X86_ISA_LEVEL
+#if MINIMUM_X86_ISA_LEVEL < AVX_X86_ISA_LEVEL
# define NO_MATH_REDIRECT
# include <libm-alias-double.h>
# undef __modf
# define SYMBOL_NAME modf
-# include "ifunc-sse4_1.h"
+# include "ifunc-sse4_1-avx.h"
libc_ifunc_redirected (__redirect_modf, __modf, IFUNC_SELECTOR ());
libm_alias_double (__modf, modf)
+# if MINIMUM_X86_ISA_LEVEL == SSE4_1_X86_ISA_LEVEL
+# define __modf __modf_sse41
+# else
+# define __modf __modf_sse2
+# endif
#endif
+#include <sysdeps/ieee754/dbl-64/s_modf.c>
+#define __modff __modff_avx
+
#include <sysdeps/ieee754/flt-32/s_modff.c>
+++ /dev/null
-#define __modff __modff_c
-#include <sysdeps/ieee754/flt-32/s_modff.c>
-#include <sysdeps/x86/isa-level.h>
-
-#if MINIMUM_X86_ISA_LEVEL != SSE4_1_X86_ISA_LEVEL
-# define __modff __modff_sse41
-#endif
+#define __modff __modff_sse41
#include <sysdeps/ieee754/flt-32/s_modff.c>
<https://www.gnu.org/licenses/>. */
#include <sysdeps/x86/isa-level.h>
-#if MINIMUM_X86_ISA_LEVEL < SSE4_1_X86_ISA_LEVEL
+#if MINIMUM_X86_ISA_LEVEL < AVX_X86_ISA_LEVEL
# define NO_MATH_REDIRECT
# include <libm-alias-float.h>
# undef __modff
# define SYMBOL_NAME modff
-# include "ifunc-sse4_1.h"
+# include "ifunc-sse4_1-avx.h"
libc_ifunc_redirected (__redirect_modff, __modff, IFUNC_SELECTOR ());
libm_alias_float (__modf, modf)
+# if MINIMUM_X86_ISA_LEVEL == SSE4_1_X86_ISA_LEVEL
+# define __modff __modff_sse41
+# else
+# define __modff __modff_sse2
+# endif
#endif
+#include <sysdeps/ieee754/flt-32/s_modff.c>