add float math: sin, cos
This commit is contained in:
parent
c8491ea363
commit
d62b7dbc64
4 changed files with 140 additions and 1 deletions
|
|
@ -39,6 +39,20 @@ macro_rules! impl_float_math {
|
|||
use coresimd::ppsv::codegen::fma::FloatFma;
|
||||
FloatFma::fma(self, y, z)
|
||||
}
|
||||
|
||||
/// Sin
|
||||
#[inline(always)]
|
||||
pub fn sin(self) -> Self {
|
||||
use coresimd::ppsv::codegen::sin::FloatSin;
|
||||
FloatSin::sin(self)
|
||||
}
|
||||
|
||||
/// Cos
|
||||
#[inline]
|
||||
pub fn cos(self) -> Self {
|
||||
use coresimd::ppsv::codegen::cos::FloatCos;
|
||||
FloatCos::cos(self)
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
|
|
@ -54,6 +68,14 @@ macro_rules! test_float_math {
|
|||
}
|
||||
}
|
||||
|
||||
fn pi() -> $elem_ty {
|
||||
match ::mem::size_of::<$elem_ty>() {
|
||||
4 => ::std::f32::consts::PI as $elem_ty,
|
||||
8 => ::std::f64::consts::PI as $elem_ty,
|
||||
_ => unreachable!(),
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn abs() {
|
||||
use coresimd::simd::*;
|
||||
|
|
@ -126,7 +148,36 @@ macro_rules! test_float_math {
|
|||
|
||||
assert_eq!(f, t.fma(t, z));
|
||||
assert_eq!(f, t.fma(o, t));
|
||||
assert_eq!(t3, t.fma(t, o));
|
||||
assert_eq!(t3, t.fma(o, o));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn sin() {
|
||||
use coresimd::simd::*;
|
||||
let z = $id::splat(0 as $elem_ty);
|
||||
let p = $id::splat(pi() as $elem_ty);
|
||||
let ph = $id::splat(pi() as $elem_ty / 2.);
|
||||
let o_r = $id::splat((pi() as $elem_ty / 2.).sin());
|
||||
let z_r = $id::splat((pi() as $elem_ty).sin());
|
||||
|
||||
assert_eq!(z, z.sin());
|
||||
assert_eq!(o_r, ph.sin());
|
||||
assert_eq!(z_r, p.sin());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn cos() {
|
||||
use coresimd::simd::*;
|
||||
let z = $id::splat(0 as $elem_ty);
|
||||
let o = $id::splat(1 as $elem_ty);
|
||||
let p = $id::splat(pi() as $elem_ty);
|
||||
let ph = $id::splat(pi() as $elem_ty / 2.);
|
||||
let z_r = $id::splat((pi() as $elem_ty / 2.).cos());
|
||||
let o_r = $id::splat((pi() as $elem_ty).cos());
|
||||
|
||||
assert_eq!(o, z.cos());
|
||||
assert_eq!(z_r, ph.cos());
|
||||
assert_eq!(o_r, p.cos());
|
||||
}
|
||||
};
|
||||
}
|
||||
|
|
|
|||
43
library/stdarch/coresimd/ppsv/codegen/cos.rs
Normal file
43
library/stdarch/coresimd/ppsv/codegen/cos.rs
Normal file
|
|
@ -0,0 +1,43 @@
|
|||
//! Exact vector cos
|
||||
|
||||
use coresimd::simd::*;
|
||||
|
||||
#[allow(improper_ctypes)]
|
||||
extern "C" {
|
||||
#[link_name = "llvm.cos.v2f32"]
|
||||
fn cos_v2f32(x: f32x2) -> f32x2;
|
||||
#[link_name = "llvm.cos.v4f32"]
|
||||
fn cos_v4f32(x: f32x4) -> f32x4;
|
||||
#[link_name = "llvm.cos.v8f32"]
|
||||
fn cos_v8f32(x: f32x8) -> f32x8;
|
||||
#[link_name = "llvm.cos.v16f32"]
|
||||
fn cos_v16f32(x: f32x16) -> f32x16;
|
||||
#[link_name = "llvm.cos.v2f64"]
|
||||
fn cos_v2f64(x: f64x2) -> f64x2;
|
||||
#[link_name = "llvm.cos.v4f64"]
|
||||
fn cos_v4f64(x: f64x4) -> f64x4;
|
||||
#[link_name = "llvm.cos.v8f64"]
|
||||
fn cos_v8f64(x: f64x8) -> f64x8;
|
||||
}
|
||||
|
||||
pub(crate) trait FloatCos {
|
||||
fn cos(self) -> Self;
|
||||
}
|
||||
|
||||
macro_rules! impl_fcos {
|
||||
($id:ident: $fn:ident) => {
|
||||
impl FloatCos for $id {
|
||||
fn cos(self) -> Self {
|
||||
unsafe { $fn(self) }
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl_fcos!(f32x2: cos_v2f32);
|
||||
impl_fcos!(f32x4: cos_v4f32);
|
||||
impl_fcos!(f32x8: cos_v8f32);
|
||||
impl_fcos!(f32x16: cos_v16f32);
|
||||
impl_fcos!(f64x2: cos_v2f64);
|
||||
impl_fcos!(f64x4: cos_v4f64);
|
||||
impl_fcos!(f64x8: cos_v8f64);
|
||||
|
|
@ -8,3 +8,5 @@ pub mod masks_reductions;
|
|||
pub mod sqrt;
|
||||
pub mod abs;
|
||||
pub mod fma;
|
||||
pub mod sin;
|
||||
pub mod cos;
|
||||
|
|
|
|||
43
library/stdarch/coresimd/ppsv/codegen/sin.rs
Normal file
43
library/stdarch/coresimd/ppsv/codegen/sin.rs
Normal file
|
|
@ -0,0 +1,43 @@
|
|||
//! Exact vector sin
|
||||
|
||||
use coresimd::simd::*;
|
||||
|
||||
#[allow(improper_ctypes)]
|
||||
extern "C" {
|
||||
#[link_name = "llvm.sin.v2f32"]
|
||||
fn sin_v2f32(x: f32x2) -> f32x2;
|
||||
#[link_name = "llvm.sin.v4f32"]
|
||||
fn sin_v4f32(x: f32x4) -> f32x4;
|
||||
#[link_name = "llvm.sin.v8f32"]
|
||||
fn sin_v8f32(x: f32x8) -> f32x8;
|
||||
#[link_name = "llvm.sin.v16f32"]
|
||||
fn sin_v16f32(x: f32x16) -> f32x16;
|
||||
#[link_name = "llvm.sin.v2f64"]
|
||||
fn sin_v2f64(x: f64x2) -> f64x2;
|
||||
#[link_name = "llvm.sin.v4f64"]
|
||||
fn sin_v4f64(x: f64x4) -> f64x4;
|
||||
#[link_name = "llvm.sin.v8f64"]
|
||||
fn sin_v8f64(x: f64x8) -> f64x8;
|
||||
}
|
||||
|
||||
pub(crate) trait FloatSin {
|
||||
fn sin(self) -> Self;
|
||||
}
|
||||
|
||||
macro_rules! impl_fsin {
|
||||
($id:ident: $fn:ident) => {
|
||||
impl FloatSin for $id {
|
||||
fn sin(self) -> Self {
|
||||
unsafe { $fn(self) }
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl_fsin!(f32x2: sin_v2f32);
|
||||
impl_fsin!(f32x4: sin_v4f32);
|
||||
impl_fsin!(f32x8: sin_v8f32);
|
||||
impl_fsin!(f32x16: sin_v16f32);
|
||||
impl_fsin!(f64x2: sin_v2f64);
|
||||
impl_fsin!(f64x4: sin_v4f64);
|
||||
impl_fsin!(f64x8: sin_v8f64);
|
||||
Loading…
Add table
Add a link
Reference in a new issue