use crate::support::rounding::RoundingMode;
macro_rules! decl_trig_kernel {
(
$sin_name:ident,
$cos_name:ident,
$tan_name:ident,
$atan_name:ident,
$Storage:ty,
$core_path:path,
$tier_label:literal
) => {
#[inline]
#[must_use]
pub(crate) fn $sin_name(raw: $Storage, mode: RoundingMode, scale: u32) -> $Storage {
use $core_path as core;
let w = scale + core::GUARD;
let r = core::sin_fixed(core::to_work(raw), w);
core::round_to_storage_with(r, w, scale, mode)
}
#[inline]
#[must_use]
pub(crate) fn $cos_name(raw: $Storage, mode: RoundingMode, scale: u32) -> $Storage {
use $core_path as core;
let w = scale + core::GUARD;
let r = core::cos_fixed(core::to_work(raw), w);
core::round_to_storage_with(r, w, scale, mode)
}
#[inline]
#[must_use]
pub(crate) fn $tan_name(raw: $Storage, mode: RoundingMode, scale: u32) -> $Storage {
use $core_path as core;
let w = scale + core::GUARD;
let (sin_w, cos_w) = core::sin_cos_fixed(core::to_work(raw), w);
if cos_w == core::zero() {
panic!(concat!(
$tier_label,
"::tan: cosine is zero (argument is an odd multiple of pi/2)"
));
}
let r = core::div(sin_w, cos_w, w);
core::round_to_storage_with(r, w, scale, mode)
}
#[inline]
#[must_use]
pub(crate) fn $atan_name(raw: $Storage, mode: RoundingMode, scale: u32) -> $Storage {
use $core_path as core;
let w = scale + core::GUARD;
let r = core::atan_fixed(core::to_work(raw), w);
core::round_to_storage_with(r, w, scale, mode)
}
};
}
#[cfg(any(feature = "d57", feature = "wide"))]
decl_trig_kernel!(
sin_strict_d57,
cos_strict_d57,
tan_strict_d57,
atan_strict_d57,
crate::wide_int::I192,
crate::types::widths::wide_trig_d57,
"D57"
);
#[cfg(any(feature = "d76", feature = "wide"))]
decl_trig_kernel!(
sin_strict_d76,
cos_strict_d76,
tan_strict_d76,
atan_strict_d76,
crate::wide_int::I256,
crate::types::widths::wide_trig_d76,
"D76"
);
#[cfg(any(feature = "d115", feature = "wide"))]
decl_trig_kernel!(
sin_strict_d115,
cos_strict_d115,
tan_strict_d115,
atan_strict_d115,
crate::wide_int::I384,
crate::types::widths::wide_trig_d115,
"D115"
);
#[cfg(any(feature = "d153", feature = "wide"))]
decl_trig_kernel!(
sin_strict_d153,
cos_strict_d153,
tan_strict_d153,
atan_strict_d153,
crate::wide_int::I512,
crate::types::widths::wide_trig_d153,
"D153"
);
#[cfg(any(feature = "d230", feature = "wide"))]
decl_trig_kernel!(
sin_strict_d230,
cos_strict_d230,
tan_strict_d230,
atan_strict_d230,
crate::wide_int::I768,
crate::types::widths::wide_trig_d230,
"D230"
);
#[cfg(any(feature = "d307", feature = "wide", feature = "x-wide"))]
decl_trig_kernel!(
sin_strict_d307,
cos_strict_d307,
tan_strict_d307,
atan_strict_d307,
crate::wide_int::I1024,
crate::types::widths::wide_trig_d307,
"D307"
);
#[cfg(any(feature = "d462", feature = "x-wide"))]
decl_trig_kernel!(
sin_strict_d462,
cos_strict_d462,
tan_strict_d462,
atan_strict_d462,
crate::wide_int::I1536,
crate::types::widths::wide_trig_d462,
"D462"
);
#[cfg(any(feature = "d616", feature = "x-wide"))]
decl_trig_kernel!(
sin_strict_d616,
cos_strict_d616,
tan_strict_d616,
atan_strict_d616,
crate::wide_int::I2048,
crate::types::widths::wide_trig_d616,
"D616"
);
#[cfg(any(feature = "d924", feature = "xx-wide"))]
decl_trig_kernel!(
sin_strict_d924,
cos_strict_d924,
tan_strict_d924,
atan_strict_d924,
crate::wide_int::I3072,
crate::types::widths::wide_trig_d924,
"D924"
);
#[cfg(any(feature = "d1232", feature = "xx-wide"))]
decl_trig_kernel!(
sin_strict_d1232,
cos_strict_d1232,
tan_strict_d1232,
atan_strict_d1232,
crate::wide_int::I4096,
crate::types::widths::wide_trig_d1232,
"D1232"
);