Add vec_mergel and vec_mergeh
This commit is contained in:
committed by
Amanieu d'Antras
parent
1dcba9edde
commit
7b080559bb
@@ -2002,6 +2002,142 @@ mod sealed {
|
|||||||
vec_ctf_u32::<IMM5>(self)
|
vec_ctf_u32::<IMM5>(self)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
|
#[target_feature(enable = "altivec")]
|
||||||
|
#[cfg_attr(all(test, target_endian = "little"), assert_instr(vmrghb))]
|
||||||
|
#[cfg_attr(all(test, target_endian = "big"), assert_instr(vmrglb))]
|
||||||
|
unsafe fn vec_vmrglb(a: vector_signed_char, b: vector_signed_char) -> vector_signed_char {
|
||||||
|
let mergel_perm = transmute(u8x16::new(
|
||||||
|
0x08, 0x18, 0x09, 0x19, 0x0A, 0x1A, 0x0B, 0x1B, 0x0C, 0x1C, 0x0D, 0x1D, 0x0E, 0x1E,
|
||||||
|
0x0F, 0x1F,
|
||||||
|
));
|
||||||
|
vec_perm(a, b, mergel_perm)
|
||||||
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
|
#[target_feature(enable = "altivec")]
|
||||||
|
#[cfg_attr(all(test, target_endian = "little"), assert_instr(vmrghh))]
|
||||||
|
#[cfg_attr(all(test, target_endian = "big"), assert_instr(vmrglh))]
|
||||||
|
unsafe fn vec_vmrglh(a: vector_signed_short, b: vector_signed_short) -> vector_signed_short {
|
||||||
|
let mergel_perm = transmute(u8x16::new(
|
||||||
|
0x08, 0x09, 0x18, 0x19, 0x0A, 0x0B, 0x1A, 0x1B, 0x0C, 0x0D, 0x1C, 0x1D, 0x0E, 0x0F,
|
||||||
|
0x1E, 0x1F,
|
||||||
|
));
|
||||||
|
vec_perm(a, b, mergel_perm)
|
||||||
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
|
#[target_feature(enable = "altivec")]
|
||||||
|
#[cfg_attr(
|
||||||
|
all(test, target_endian = "little", not(target_feature = "vsx")),
|
||||||
|
assert_instr(vmrghw)
|
||||||
|
)]
|
||||||
|
#[cfg_attr(
|
||||||
|
all(test, target_endian = "little", target_feature = "vsx"),
|
||||||
|
assert_instr(xxmrghw)
|
||||||
|
)]
|
||||||
|
#[cfg_attr(
|
||||||
|
all(test, target_endian = "big", not(target_feature = "vsx")),
|
||||||
|
assert_instr(vmrglw)
|
||||||
|
)]
|
||||||
|
#[cfg_attr(
|
||||||
|
all(test, target_endian = "big", target_feature = "vsx"),
|
||||||
|
assert_instr(xxmrglw)
|
||||||
|
)]
|
||||||
|
unsafe fn vec_vmrglw(a: vector_signed_int, b: vector_signed_int) -> vector_signed_int {
|
||||||
|
let mergel_perm = transmute(u8x16::new(
|
||||||
|
0x08, 0x09, 0x0A, 0x0B, 0x18, 0x19, 0x1A, 0x1B, 0x0C, 0x0D, 0x0E, 0x0F, 0x1C, 0x1D,
|
||||||
|
0x1E, 0x1F,
|
||||||
|
));
|
||||||
|
vec_perm(a, b, mergel_perm)
|
||||||
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
|
#[target_feature(enable = "altivec")]
|
||||||
|
#[cfg_attr(all(test, target_endian = "little"), assert_instr(vmrglb))]
|
||||||
|
#[cfg_attr(all(test, target_endian = "big"), assert_instr(vmrghb))]
|
||||||
|
unsafe fn vec_vmrghb(a: vector_signed_char, b: vector_signed_char) -> vector_signed_char {
|
||||||
|
let mergel_perm = transmute(u8x16::new(
|
||||||
|
0x00, 0x10, 0x01, 0x11, 0x02, 0x12, 0x03, 0x13, 0x04, 0x14, 0x05, 0x15, 0x06, 0x16,
|
||||||
|
0x07, 0x17,
|
||||||
|
));
|
||||||
|
vec_perm(a, b, mergel_perm)
|
||||||
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
|
#[target_feature(enable = "altivec")]
|
||||||
|
#[cfg_attr(all(test, target_endian = "little"), assert_instr(vmrglh))]
|
||||||
|
#[cfg_attr(all(test, target_endian = "big"), assert_instr(vmrghh))]
|
||||||
|
unsafe fn vec_vmrghh(a: vector_signed_short, b: vector_signed_short) -> vector_signed_short {
|
||||||
|
let mergel_perm = transmute(u8x16::new(
|
||||||
|
0x00, 0x01, 0x10, 0x11, 0x02, 0x03, 0x12, 0x13, 0x04, 0x05, 0x14, 0x15, 0x06, 0x07,
|
||||||
|
0x16, 0x17,
|
||||||
|
));
|
||||||
|
vec_perm(a, b, mergel_perm)
|
||||||
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
|
#[target_feature(enable = "altivec")]
|
||||||
|
#[cfg_attr(
|
||||||
|
all(test, target_endian = "little", not(target_feature = "vsx")),
|
||||||
|
assert_instr(vmrglw)
|
||||||
|
)]
|
||||||
|
#[cfg_attr(
|
||||||
|
all(test, target_endian = "little", target_feature = "vsx"),
|
||||||
|
assert_instr(xxmrglw)
|
||||||
|
)]
|
||||||
|
#[cfg_attr(
|
||||||
|
all(test, target_endian = "big", not(target_feature = "vsx")),
|
||||||
|
assert_instr(vmrghw)
|
||||||
|
)]
|
||||||
|
#[cfg_attr(
|
||||||
|
all(test, target_endian = "big", target_feature = "vsx"),
|
||||||
|
assert_instr(xxmrghw)
|
||||||
|
)]
|
||||||
|
unsafe fn vec_vmrghw(a: vector_signed_int, b: vector_signed_int) -> vector_signed_int {
|
||||||
|
let mergel_perm = transmute(u8x16::new(
|
||||||
|
0x00, 0x01, 0x02, 0x03, 0x10, 0x11, 0x12, 0x13, 0x04, 0x05, 0x06, 0x07, 0x14, 0x15,
|
||||||
|
0x16, 0x17,
|
||||||
|
));
|
||||||
|
vec_perm(a, b, mergel_perm)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub trait VectorMergeh<Other> {
|
||||||
|
type Result;
|
||||||
|
unsafe fn vec_mergeh(self, b: Other) -> Self::Result;
|
||||||
|
}
|
||||||
|
|
||||||
|
impl_vec_trait! { [VectorMergeh vec_mergeh]+ 2b (vec_vmrghb, vec_vmrghh, vec_vmrghw) }
|
||||||
|
impl_vec_trait! { [VectorMergeh vec_mergeh]+ vec_vmrghw (vector_float, vector_float) -> vector_float }
|
||||||
|
|
||||||
|
pub trait VectorMergel<Other> {
|
||||||
|
type Result;
|
||||||
|
unsafe fn vec_mergel(self, b: Other) -> Self::Result;
|
||||||
|
}
|
||||||
|
|
||||||
|
impl_vec_trait! { [VectorMergel vec_mergel]+ 2b (vec_vmrglb, vec_vmrglh, vec_vmrglw) }
|
||||||
|
impl_vec_trait! { [VectorMergel vec_mergel]+ vec_vmrglw (vector_float, vector_float) -> vector_float }
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Vector Merge Low
|
||||||
|
#[inline]
|
||||||
|
#[target_feature(enable = "altivec")]
|
||||||
|
pub unsafe fn vec_mergel<T, U>(a: T, b: U) -> <T as sealed::VectorMergel<U>>::Result
|
||||||
|
where
|
||||||
|
T: sealed::VectorMergel<U>,
|
||||||
|
{
|
||||||
|
a.vec_mergel(b)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Vector Merge High
|
||||||
|
#[inline]
|
||||||
|
#[target_feature(enable = "altivec")]
|
||||||
|
pub unsafe fn vec_mergeh<T, U>(a: T, b: U) -> <T as sealed::VectorMergeh<U>>::Result
|
||||||
|
where
|
||||||
|
T: sealed::VectorMergeh<U>,
|
||||||
|
{
|
||||||
|
a.vec_mergeh(b)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Vector Load Indexed.
|
/// Vector Load Indexed.
|
||||||
|
|||||||
@@ -58,6 +58,16 @@ macro_rules! impl_vec_trait {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
([$Trait:ident $m:ident]+ $fun:ident ($a:ty, $b:ty) -> $r:ty) => {
|
||||||
|
impl $Trait<$b> for $a {
|
||||||
|
type Result = $r;
|
||||||
|
#[inline]
|
||||||
|
#[target_feature(enable = "altivec")]
|
||||||
|
unsafe fn $m(self, b: $b) -> Self::Result {
|
||||||
|
transmute($fun(transmute(self), transmute(b)))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
([$Trait:ident $m:ident] $fun:ident ($a:ty, ~$b:ty) -> $r:ty) => {
|
([$Trait:ident $m:ident] $fun:ident ($a:ty, ~$b:ty) -> $r:ty) => {
|
||||||
impl_vec_trait!{ [$Trait $m] $fun ($a, $a) -> $r }
|
impl_vec_trait!{ [$Trait $m] $fun ($a, $a) -> $r }
|
||||||
impl_vec_trait!{ [$Trait $m] $fun ($a, $b) -> $r }
|
impl_vec_trait!{ [$Trait $m] $fun ($a, $b) -> $r }
|
||||||
@@ -84,5 +94,16 @@ macro_rules! impl_vec_trait {
|
|||||||
};
|
};
|
||||||
([$Trait:ident $m:ident] 2 ($fn:ident)) => {
|
([$Trait:ident $m:ident] 2 ($fn:ident)) => {
|
||||||
impl_vec_trait!{ [$Trait $m] ($fn, $fn, $fn, $fn, $fn, $fn) }
|
impl_vec_trait!{ [$Trait $m] ($fn, $fn, $fn, $fn, $fn, $fn) }
|
||||||
|
};
|
||||||
|
([$Trait:ident $m:ident]+ 2b ($b:ident, $h:ident, $w:ident)) => {
|
||||||
|
impl_vec_trait!{ [$Trait $m]+ $b (vector_bool_char, vector_bool_char) -> vector_bool_char }
|
||||||
|
impl_vec_trait!{ [$Trait $m]+ $b (vector_unsigned_char, vector_unsigned_char) -> vector_unsigned_char }
|
||||||
|
impl_vec_trait!{ [$Trait $m]+ $b (vector_signed_char, vector_signed_char) -> vector_signed_char }
|
||||||
|
impl_vec_trait!{ [$Trait $m]+ $h (vector_bool_short, vector_bool_short) -> vector_bool_short }
|
||||||
|
impl_vec_trait!{ [$Trait $m]+ $h (vector_unsigned_short, vector_unsigned_short) -> vector_unsigned_short }
|
||||||
|
impl_vec_trait!{ [$Trait $m]+ $h (vector_signed_short, vector_signed_short) -> vector_signed_short }
|
||||||
|
impl_vec_trait!{ [$Trait $m]+ $w (vector_bool_int, vector_bool_int) -> vector_bool_int }
|
||||||
|
impl_vec_trait!{ [$Trait $m]+ $w (vector_unsigned_int, vector_unsigned_int) -> vector_unsigned_int }
|
||||||
|
impl_vec_trait!{ [$Trait $m]+ $w (vector_signed_int, vector_signed_int) -> vector_signed_int }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user