From 1689055c0db7c4c4d6b1a60894461b0a07991eca Mon Sep 17 00:00:00 2001 From: Wildan M Date: Wed, 15 Apr 2026 05:50:21 +0700 Subject: [PATCH] Add more definition to rust math.h --- src/header/math/cbindgen.toml | 47 ++++++++++++ src/header/math/mod.rs | 133 ++++++++++++++++++++++++++++++---- 2 files changed, 164 insertions(+), 16 deletions(-) diff --git a/src/header/math/cbindgen.toml b/src/header/math/cbindgen.toml index 6d866d3705..97345d7770 100644 --- a/src/header/math/cbindgen.toml +++ b/src/header/math/cbindgen.toml @@ -5,6 +5,53 @@ language = "C" style = "Type" no_includes = true cpp_compat = true +# constants from openlibm +after_includes = """ + +#define HUGE_VALF (float)HUGE_VAL +#define HUGE_VALL (long double)HUGE_VAL +#define INFINITY HUGE_VALF +#define NAN (__nan.__uf) + +#define FP_ILOGB0 (-INT_MAX) +#define FP_ILOGBNAN INT_MAX + +#define MAXFLOAT 3.40282346638528859812e+38F + +#define M_E 2.7182818284590452354 /* e */ +#define M_LOG2E 1.4426950408889634074 /* log_2 e */ +#define M_LOG10E 0.43429448190325182765 /* log_10 e */ +#define M_LN2 0.69314718055994530942 /* log_e 2 */ +#define M_LN10 2.30258509299404568402 /* log_e 10 */ +#define M_PI 3.14159265358979323846 /* pi */ +#define M_PI_2 1.57079632679489661923 /* pi/2 */ +#define M_PI_4 0.78539816339744830962 /* pi/4 */ +#define M_1_PI 0.31830988618379067154 /* 1/pi */ +#define M_2_PI 0.63661977236758134308 /* 2/pi */ +#define M_2_SQRTPI 1.12837916709551257390 /* 2/sqrt(pi) */ +#define M_SQRT2 1.41421356237309504880 /* sqrt(2) */ +#define M_SQRT1_2 0.70710678118654752440 /* 1/sqrt(2) */ + +#define FP_NAN 0 +#define FP_INFINITE 1 +#define FP_ZERO 2 +#define FP_SUBNORMAL 3 +#define FP_NORMAL 4 +#define fpclassify(x) __builtin_fpclassify(FP_NAN, FP_INFINITE, FP_NORMAL, FP_SUBNORMAL, FP_ZERO, x) + +#define signbit(x) __builtin_signbit(x) +#define isnan(x) __builtin_isnan(x) +#define isinf(x) __builtin_isinf_sign(x) +#define isfinite(x) __builtin_isfinite(x) +#define isnormal(x) __builtin_isnormal(x) +#define isgreater(x, y) __builtin_isgreater((x), (y)) +#define isgreaterequal(x, y) __builtin_isgreaterequal((x), (y)) +#define isless(x, y) __builtin_isless((x), (y)) +#define islessequal(x, y) __builtin_islessequal((x), (y)) +#define islessgreater(x, y) __builtin_islessgreater((x), (y)) +#define isunordered(x, y) __builtin_isunordered((x), (y)) + +""" [enum] prefix_with_name = true diff --git a/src/header/math/mod.rs b/src/header/math/mod.rs index 8f56d518fa..b529bd2633 100644 --- a/src/header/math/mod.rs +++ b/src/header/math/mod.rs @@ -2,9 +2,11 @@ //! //! See . -use crate::platform::types::{c_double, c_float, c_int}; +use crate::platform::types::{c_double, c_float, c_int, c_long, c_longlong}; -// TODO constants (some already defined in C) +// TODO move constants from cbindgen (openlibm) +// TODO all is* function is defined as "real-floating", so it can both f32 and f64 +// TODO cover edge cases (EDOM and ERANGE) /// See . #[unsafe(no_mangle)] @@ -384,6 +386,34 @@ pub unsafe extern "C" fn ilogbf(x: c_float) -> c_int { // TODO ilogbl (long double) +/// See . +#[unsafe(no_mangle)] +unsafe extern "C" fn isfinite(x: c_double) -> c_int { + if x.is_finite() { 1 } else { 0 } +} + +/// See . +#[unsafe(no_mangle)] +unsafe extern "C" fn isinf(x: c_double) -> c_int { + match x { + f64::INFINITY => 1, + f64::NEG_INFINITY => -1, + _ => 0, + } +} + +/// See . +#[unsafe(no_mangle)] +unsafe extern "C" fn isnan(x: c_double) -> c_int { + if x.is_nan() { 1 } else { 0 } +} + +/// See . +#[unsafe(no_mangle)] +unsafe extern "C" fn isnormal(x: c_double) -> c_int { + if x.is_normal() { 1 } else { 0 } +} + /// See . #[unsafe(no_mangle)] pub unsafe extern "C" fn j0(x: c_double) -> c_double { @@ -416,26 +446,53 @@ pub unsafe extern "C" fn ldexpf(x: c_float, exp: c_int) -> c_float { // TODO ldexpl (long double) +#[unsafe(no_mangle)] +static mut signgam: c_int = 0; + /// See . #[unsafe(no_mangle)] pub unsafe extern "C" fn lgamma(x: c_double) -> c_double { - libm::lgamma(x) + let (a, b) = libm::lgamma_r(x); + unsafe { signgam = b }; + a } /// See . #[unsafe(no_mangle)] pub unsafe extern "C" fn lgammaf(x: c_float) -> c_float { - libm::lgammaf(x) + let (a, b) = libm::lgammaf_r(x); + unsafe { signgam = b }; + a } // TODO lgammal (long double) -// TODO llrint (c_double to c_longlong) -// TODO llrintf (c_float to c_longlong) +/// See . +#[unsafe(no_mangle)] +unsafe extern "C" fn llrint(x: c_double) -> c_longlong { + libm::rint(x) as _ +} + +/// See . +#[unsafe(no_mangle)] +unsafe extern "C" fn llrintf(x: c_float) -> c_longlong { + libm::rintf(x) as _ +} + // TODO llrintl (long double to c_longlong) -// TODO llround (c_double to c_longlong) -// TODO llroundf (c_float to c_longlong) +/// See . +#[unsafe(no_mangle)] +unsafe extern "C" fn llround(x: c_double) -> c_longlong { + libm::round(x) as _ +} + +/// See . +#[unsafe(no_mangle)] +unsafe extern "C" fn llroundf(x: c_float) -> c_longlong { + libm::roundf(x) as _ +} + // TODO llroundl (long double to c_longlong) /// See . @@ -486,8 +543,20 @@ pub unsafe extern "C" fn log2f(x: c_float) -> c_float { // TODO log2l (long double) -// TODO logb (c_double) -// TODO logbf (c_float) +/// See . +#[unsafe(no_mangle)] +unsafe extern "C" fn logb(x: c_double) -> c_double { + // TODO: errno + libm::ilogb(x) as _ +} + +/// See . +#[unsafe(no_mangle)] +unsafe extern "C" fn logbf(x: c_float) -> c_float { + // TODO: errno + libm::ilogbf(x) as _ +} + // TODO logbl (long double) /// See . @@ -498,12 +567,34 @@ pub unsafe extern "C" fn logf(x: c_float) -> c_float { // TODO logl (long double) -// TODO lrint (c_double) -// TODO lrintf (c_float) +/// See . +#[unsafe(no_mangle)] +unsafe extern "C" fn lrint(x: c_double) -> c_long { + // TODO: errno + libm::rint(x) as _ +} + +/// See . +#[unsafe(no_mangle)] +unsafe extern "C" fn lrintf(x: c_float) -> c_long { + // TODO: errno + libm::rintf(x) as _ +} + // TODO lrintl (long double) -// TODO lround (c_double) -// TODO lroundf (c_float) +/// See . +#[unsafe(no_mangle)] +unsafe extern "C" fn lround(x: c_double) -> c_long { + libm::round(x) as _ +} + +/// See . +#[unsafe(no_mangle)] +unsafe extern "C" fn lroundf(x: c_float) -> c_long { + libm::roundf(x) as _ +} + // TODO lroundl (long double) /// See . @@ -533,8 +624,18 @@ pub unsafe extern "C" fn modff(value: c_float, iptr: *mut c_float) -> c_float { // TODO nanf (c_float) // TODO nanl (long double) -// TODO nearbyint (c_double) -// TODO nearbyintf (c_float) +/// See . +#[unsafe(no_mangle)] +unsafe extern "C" fn nearbyint(x: c_double) -> c_double { + libm::rint(x) +} + +/// See . +#[unsafe(no_mangle)] +unsafe extern "C" fn nearbyintf(x: c_float) -> c_float { + libm::rintf(x) +} + // TODO nearbyintl (long double) /// See .