diff --git a/libcxx/include/__math/traits.h b/libcxx/include/__math/traits.h index a4482667975576c..27ec52ecef022e9 100644 --- a/libcxx/include/__math/traits.h +++ b/libcxx/include/__math/traits.h @@ -55,6 +55,18 @@ _LIBCPP_NODISCARD _LIBCPP_CONSTEXPR_SINCE_CXX23 _LIBCPP_HIDE_FROM_ABI bool isfin return true; } +_LIBCPP_NODISCARD inline _LIBCPP_CONSTEXPR_SINCE_CXX23 _LIBCPP_HIDE_FROM_ABI bool isfinite(float __x) _NOEXCEPT { + return __builtin_isfinite(__x); +} + +_LIBCPP_NODISCARD inline _LIBCPP_CONSTEXPR_SINCE_CXX23 _LIBCPP_HIDE_FROM_ABI bool isfinite(double __x) _NOEXCEPT { + return __builtin_isfinite(__x); +} + +_LIBCPP_NODISCARD inline _LIBCPP_CONSTEXPR_SINCE_CXX23 _LIBCPP_HIDE_FROM_ABI bool isfinite(long double __x) _NOEXCEPT { + return __builtin_isfinite(__x); +} + // isinf template ::value && numeric_limits<_A1>::has_infinity, int> = 0> diff --git a/libcxx/test/std/numerics/c.math/isfinite.pass.cpp b/libcxx/test/std/numerics/c.math/isfinite.pass.cpp index 6bbc3aaac6d130f..3d5be616343343e 100644 --- a/libcxx/test/std/numerics/c.math/isfinite.pass.cpp +++ b/libcxx/test/std/numerics/c.math/isfinite.pass.cpp @@ -62,9 +62,21 @@ struct TestInt { } }; +template +struct ConvertibleTo { + operator T() const { return T(); } +}; + int main(int, char**) { types::for_each(types::floating_point_types(), TestFloat()); types::for_each(types::integral_types(), TestInt()); + // Make sure we can call `std::isfinite` with convertible types + { + assert(std::isfinite(ConvertibleTo())); + assert(std::isfinite(ConvertibleTo())); + assert(std::isfinite(ConvertibleTo())); + } + return 0; }