use alloc::vec::*;
#[cfg(not(all(any(target_arch = "x86", target_arch = "x86_64"), feature = "simd")))]
pub fn get_bitmap(a: &Vec<f32>, length: usize) -> Vec<u8> {
use crate::platform::{abs, clamp};
use alloc::vec;
let mut height = 0.0;
assert!(length <= a.len());
let mut output = vec![0; length];
for i in 0..length {
unsafe {
height += a.get_unchecked(i);
*(output.get_unchecked_mut(i)) = clamp(abs(height) * 255.9, 0.0, 255.0) as u8;
}
}
output
}
#[allow(clippy::uninit_vec)]
#[cfg(all(any(target_arch = "x86", target_arch = "x86_64"), feature = "simd"))]
pub fn get_bitmap(a: &Vec<f32>, length: usize) -> Vec<u8> {
#[cfg(target_arch = "x86")]
use core::arch::x86::*;
#[cfg(target_arch = "x86_64")]
use core::arch::x86_64::*;
let aligned_length = (length + 3) & !3;
assert!(aligned_length <= a.len());
let mut output = Vec::with_capacity(aligned_length);
unsafe {
output.set_len(aligned_length);
let mut offset = _mm_setzero_ps();
let nzero = _mm_castps_si128(_mm_set1_ps(-0.0));
for i in (0..aligned_length).step_by(4) {
let mut x = _mm_loadu_ps(a.get_unchecked(i));
x = _mm_add_ps(x, _mm_castsi128_ps(_mm_slli_si128(_mm_castps_si128(x), 4)));
x = _mm_add_ps(x, _mm_castsi128_ps(_mm_slli_si128(_mm_castps_si128(x), 8)));
x = _mm_add_ps(x, offset);
let y = _mm_mul_ps(x, _mm_set1_ps(255.9));
let y = _mm_andnot_ps(_mm_castsi128_ps(nzero), y);
let mut y = _mm_cvttps_epi32(y);
y = _mm_packus_epi16(_mm_packs_epi32(y, nzero), nzero);
let pointer: &mut i32 = core::mem::transmute(output.get_unchecked_mut(i));
*pointer = core::mem::transmute::<__m128i, [i32; 4]>(y)[0];
offset = _mm_set1_ps(core::mem::transmute::<__m128, [f32; 4]>(x)[3]);
}
}
output.truncate(length);
output
}