Skip to content

Instantly share code, notes, and snippets.

@luojia65
Last active March 16, 2022 10:12
Show Gist options
  • Select an option

  • Save luojia65/5355bf7fea7b783d36e86ffa6467febe to your computer and use it in GitHub Desktop.

Select an option

Save luojia65/5355bf7fea7b783d36e86ffa6467febe to your computer and use it in GitHub Desktop.
RISC-V V DynSimd
/// Runtime dynamic SIMD value
///
/// This structure a wrap of an unsized slice, whose memory layout varies by architecture
/// under #[repr(simd)].
///
/// In RISC-V, this type represents a group of elements to be processed in application,
/// or VL number of T values. Length of current vector is placed in separate vector length
/// CSR register `vl`.
#[repr(simd)]
pub struct DynSimd<T>([T]);
impl<T> DynSimd<T> {
#[inline]
pub fn len(&self) -> usize {
#[cfg(target_arch = "riscv32")]
core::arch::riscv32::vl()
#[cfg(target_arch = "riscv64")]
core::arch::riscv64::vl()
#[cfg(not(any(target_arch = "riscv32", target_arch = "riscv64")))]
unimplemented!("not supported under current architecture")
}
#[inline]
pub fn as_slice(&self) -> &[T] {
}
}
impl<T> Index<usize> for DynSimd<T> {
type Output = T;
fn index(&self, idx: usize) -> &Self::Output {
simd_dyn_extract(self, idx) // ?
}
}
// IndexMut??
extern "platform-intrinsic" {
fn simd_dyn_extract<V, T>(x: V, i: usize) -> T;
}
/*
compiler/rustc_codegen_llvm/src/intrinsic.rs
*/
pub type u64xN = DynSimd<u64>;
// pub fn as_simd(&self) -> (&[T], SimdSteps<T>, &[T])
struct SimdSteps<T> {
len: usize
}
impl<T> Iterator for SimdSteps<T> {
type Item = T;
fn next(&mut self) -> Option<&Self::Item> {
// ...
}
}
fn main() {
let a: &[u64] = &[1, 2, 3, 4, 5];
let (lo_a, steps_a, hi_a) = a.as_simd();
let mut ret = scalar_sum(lo_a);
for step_a in steps_a {
ret += step_a.sum();
}
ret += scalar_sum(hi_a);
assert_eq!(ret, 15);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment